CCS C Software and Maintenance Offers
FAQFAQ   FAQForum Help   FAQOfficial CCS Support   SearchSearch  RegisterRegister 

ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

CCS does not monitor this forum on a regular basis.

Please do not post bug reports on this forum. Send them to support@ccsinfo.com

Very weird RTCC, InT_RDA, and delay_ms problem

 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
evsource



Joined: 21 Nov 2006
Posts: 129

View user's profile Send private message

Very weird RTCC, InT_RDA, and delay_ms problem
PostPosted: Mon Feb 23, 2009 4:46 pm     Reply with quote

I'm wondering if someone else can duplicate this error.

I'm using PCH 4.030, 18F2620.

If I put a delay in the INT_RDA ISR, or a delay in main's while loop, then timing for timer0 is messed up by a factor of about 18 or 20.

Here's the code. I tried to strip out everything that wasn't needed, but it's still sort of long. Basically, I just have the RTCC ISR turning on and off a LED. You're probably saying "don't put a delay in an ISR you dummy!" ... I know, I'm not looking for code guidance, just trying to understand why the delay is affecting the timing, especially when INT_RDA isn't even turned on! What's more interesting is that if *either* delay (in INT_RDA or main) is commented out, then the timing works correctly. Very weird!

Code:

#include <18f2620.h>
#device ADC=10 // use 10 bit ADC reading
#fuses HS,WDT256,NOMCLR,NOWDT,NOPROTECT,NOBROWNOUT,BORV21,NOPROTECT,NOLVP
#use delay(clock=20000000)
#use rs232(baud=115200, xmit=PIN_C6, rcv=PIN_C7, errors)

#int_rda
void serial_isr() {
     delay_ms(100);  // comment this out, and timing for timer0 works correctly
}

/* !!!!!!!!  LED functions, defines, and variables !!!!!!!! */
#define SLOW_FLASH 1 // transition every second
#define NO_FLASH 0
#define INTS_PER_SECOND 76     // (20000000/(4*256*256))
#define BLUE_LED_PIN PIN_C4

void blue_LED_on(int1);
void toggle_blue_LED();
void check_LEDs(int);

// Number of interrupts left before a second has elapsed
BYTE int_count1;

// variables to store current state of LED
int1 blue_LED;
int blue_flashrate;

#int_rtcc
void clock_isr() {
     if(--int_count1==0) {
          check_LEDs(SLOW_FLASH);
          int_count1=INTS_PER_SECOND;
     }
}
/* !!!!!!!!  END LED functions, defines, and variables !!!!!!!! */

void main() {
     setup_adc(  ADC_CLOCK_INTERNAL  );
     setup_adc_ports( ALL_ANALOG );

     enable_interrupts(INT_RTCC);
     enable_interrupts(GLOBAL);

     /* setup counter parameters */
     int_count1=INTS_PER_SECOND;
     setup_timer_0( RTCC_INTERNAL | RTCC_8_BIT | RTCC_DIV_256);
     set_timer0(0);
     /* end setup on counter parameters */

     blue_LED = FALSE;
     blue_LED_on(FALSE);
     blue_flashrate = SLOW_FLASH;

     setup_wdt(WDT_ON); // WDT on in software

     while(1) {
          printf("Hi\r\n");
    //      delay_ms(500);  // comment this out, and timing for timer0 works correctly
          restart_wdt();
     }
}

/********************* Functions **************************/
void check_LEDs(int rate) {
     if(blue_flashrate == rate) {
          toggle_blue_LED();
     }
}

void blue_LED_on(int1 on) {
     if(on) output_low(BLUE_LED_PIN);
     else output_high(BLUE_LED_PIN);
}

void toggle_blue_LED() {
     blue_LED = !blue_LED;
     blue_LED_on(blue_LED);
}
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Mon Feb 23, 2009 5:26 pm     Reply with quote

If you have both delay_ms() statements in your program, you'll get a
"re-entrancy" warning message. To fix that, you can create another
instance of the delay library code by adding the line shown in bold below
just above main():
Quote:
#use delay(clock=20000000)
void main() {

Then the interrupt routine will have it's own dedicated delay routine,
and the main code will another it's own routine. Their won't be any
re-entrancy issues and the compiler won't disable interrupts while the
delay_ms() statement in main() is running.
dyeatman



Joined: 06 Sep 2003
Posts: 1923
Location: Norman, OK

View user's profile Send private message

PostPosted: Mon Feb 23, 2009 6:02 pm     Reply with quote

Also, if the #int_rda is enabled you will have another
problem. Without a getc() in the interrupt routine to clear
the interrupt, the interrupt will not be cleared and it will be
called repeatedly which will cause the program to stay in the
#int_rda delay_ms() almost continously.
Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group