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 CCS Technical Support

Problems with rs232 interruption

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



Joined: 31 Jan 2005
Posts: 3

View user's profile Send private message MSN Messenger ICQ Number

Problems with rs232 interruption
PostPosted: Mon Jan 31, 2005 5:57 am     Reply with quote

Hi,

I wrote this code:
*************************************************************
#include "16F627.H"

#fuses XT, NOWDT, NOPROTECT, NOMCLR, NOBROWNOUT, NOLVP, NOCPD, PUT

#use delay (clock=3686400) //3.6864mHz
#use rs232(baud=115200, xmit=PIN_B2, rcv=PIN_B1, parity=N, bits=8)

//Functions definitions
void initPins(void);
void blinkLed(void);

#int_rda
void rs232_handler()
{
blinkLed();
}

void main()
{
initPins();
enable_interrupts(global);
enable_interrupts(int_rda);
while(1);
}

void initPins()
{
SET_TRIS_A(0xB0);
SET_TRIS_B(0x32);
setup_ccp1(CCP_OFF);
setup_comparator(NC_NC_NC_NC);
setup_vref(FALSE);
output_low(PIN_A0);
output_low(PIN_A1);
output_low(PIN_A2);
output_low(PIN_A3);
output_low(PIN_B0);
}

void blinkLed()
{
int cont = 5;
while (cont)
{
output_high(PIN_A0); //LED on
delay_ms(200);
output_low(PIN_A0); //LED off
delay_ms(200);
cont--;
}
}
*************************************************************
When I compile does not return error, but when I run the program and send a char through of rs232, the program not execute the function blinkLed() one time, but it seems that the function enters in loop.
Somebody would know to say me what it can be wrong?

Hmmm... forgive me for my english Wink

Vinicius
Douglas Kennedy



Joined: 07 Sep 2003
Posts: 755
Location: Florida

View user's profile Send private message AIM Address

PostPosted: Mon Jan 31, 2005 6:36 am     Reply with quote

The problem is time is not on your programs side.
Each received char will cause your interrupt service routine to execute..but guess what ...you call blink led that has a delay in it ..that's because you wanted to see it blink. While it is blinking the service routine is frozen out and that's likely to be the problem.
Suggestion
Set a global flag in the interrupt service routine to indicate a char is received. In your main code blink the led if the flag is set and clear the flag after one blink.
That way the isr can be called during the blinking of the led..sure it will add a few micro secs to the blink as the isr consumes a few cycles but it won't hang your code.
Mark



Joined: 07 Sep 2003
Posts: 2838
Location: Atlanta, GA

View user's profile Send private message Send e-mail

PostPosted: Mon Jan 31, 2005 7:04 am     Reply with quote

You should add the ERRORS parameter to the #use rs232 also.
valemike
Guest







PostPosted: Mon Jan 31, 2005 7:05 am     Reply with quote

I have an application right now where i have a 4 digit LED display, and I have to strobe thru each digit for 4ms, then go to the next digit, etc., to make it appear continuous to the human eye.

In my loop I noticed that other interrupts and i/o cause a disruption in the continuous display.

What i'm going to try to do is to use TMR0 (?), set it to interrupt me every 4ms, then update the next digit in the ISR.

In your case, instead of your calll to delay_ms(200), perhaps you should set a timer to interrupt you every 200ms (you'll need to calculate that based on your Fosc speed), and update that LED in the ISR.

-Mike
Bill Boucher



Joined: 04 Feb 2005
Posts: 34
Location: Chatham,ON,CA

View user's profile Send private message Send e-mail Visit poster's website

PostPosted: Fri Feb 04, 2005 1:43 pm     Reply with quote

If your program enters an endless loop, it sounds like the ISR is reentering itself. Try clearing the interupt flag within your ISR. I'm a newbie to CCS C so I'm not sure if it clears the flags automatically, but I doubt it. It will reassert GIE upon exiting the ISR, but it doesn't likely clear the int-source flags!

Also, your "blink" routine is time consuming. You wouldn't be able to "receive" again until that's done. Obviously, it blinks for you to say "Hey, I received a byte!!!". That's just fine for your first try at serial communications. Later, you'll want to keep your ISR short and sweet, say dedicated to moving data received into a user defined receive buffer variable [i.e. R_buffer(n)]. The ISR could load a var with a number. The main loop could be checking that number and if not 0, then blink that many times. No matter how slow the blink, the ISR will still run once for each byte received. Alternatively, the suggestion from valemike regarding setting the blink timing with a hardware timer is excellent. While this could be easily interupt driven (just like serial reception is), it isn't mandatory. I often use the TMR0 or TMR1 to regulate my main loop speed without triggering an interupt. All you do is wait at the bottom of the main loop for the timer flag bit to become set. When it does, you clear it, re-load the timer with a constant that sets your loop speed, then jump back to the beginning of the loop. For each pass through the main loop, you decrement a counter or something to determine when it is time to change the state of the LED. The advantage here is that the LED blinking doesn't lock the uC into delay loops so it can perform other tasks while blinking.
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