|
|
View previous topic :: View next topic |
Author |
Message |
Oli Guest
|
Strange problem (missing data) with USB / RS232 on PIC24 |
Posted: Mon May 18, 2009 4:45 am |
|
|
Hi all,
I have a couple of strange problems that are occuring with the PCD 4.092 compiler and PIC24FJ256GB110
1/ I have the USB CDC drivers running fine. I can print / receive chars as quick as I need with no problems.... Until I include the int_rda interrupt to receive chars over RS232. As soon as this is included, the USB data being printed over USB to the PCB starts to go missing. Parts of text will just disappear. Data to the PIC via USB seems unaffected.
I first thought that int_rda would be triggering all of the time for some reason and so the two interrupts are competing with each other - this isn't the case though - after debugging using an LED to determine when it was being triggered, it was not triggering at all (the correct behaviour) unless I actually sent data via rs232. So it's not a competing interrupt.
Further proof is if I clear the int_rda interrupt at the beginning of the program and disable it, like so: Code: | clear_interrupt(INT_RDA); disable_interrupts(int_rda); | it makes no difference.
Strangely, if I comment out the actual interrupt code: Code: | /*
#int_rda
void serial_isr() {
int8 t;
main_buffer[next_in]=debug_getc();
t=next_in;
next_in=(next_in+1) % BUFFER_SIZE;
if(next_in==next_out)
next_in=t; // Buffer full !!
tmr1_count_data = TMR1_INT_DATA; // start the countdown
}*/ |
everything starts working fine.
A temporary solution has been to create a new usb_cdc_putc layer with a delay in, like so:
Code: | void usb_cdc_putc_robust(char c)
{
usb_cdc_putc_fast(c);
delay_us(500);
} |
which alleviates the problem.
So it leads me to the question: I know int_rda isn't being triggered, so why does including it affect the USB operation. Secondly, whatever part of int_rda is causing the problem isn't affected by disabling it --- why? I have manually tried to disable it too:
Code: | #word U1MODE = 0x0220
U1MODE = 0b0000000000000000;
|
but commenting out the actual interrupt code makes a difference.
2/ Sometimes declaring a global variable will break other bits of code. I have a specific example where I can declare an int8 and what was previously working code stops working. Another where increasing the size of a global buffer causes the program to continually reset itself. I know I need to post complete code examples for you to help, but can anyone offer me pointers on specifically hunting down what is going on?
It's worth noting that I've completed a couple of large ish projects using usb and multiple UARTs together with no issues, however this is my first using PCD.
Many thanks
Oli
EDIT: I have also used UART2, successfully and the same thing occurs for all situations. |
|
|
Ttelmah Guest
|
|
Posted: Mon May 18, 2009 8:09 am |
|
|
Why are you using 'debug_getc'. What is in your debug_getc?.
I'd guess you perhaps have a printf or something in it?. If so, then interrupts will automatically be disabled around all similar statements in the main code, whether or not the interrupt is enabled.
Best Wishes |
|
|
Oli Guest
|
|
Posted: Mon May 18, 2009 8:34 am |
|
|
Hi Ttelmah and thanks for your quick response
You have a point - within debug_getc() it actually does this
Code: |
BYTE debug_getc(void)
{
BYTE cvar;
cvar = fgetc(GSM);
if (DEBUG_OVER_USB == 1) // if USB debugging is enabled
usb_cdc_putc_robust(cvar);
return cvar;
}
|
however, remember that the interrupt is not being called - so it should not interfere with USB functionality. DEBUG_OVER_USB whether set to 1 or 0 has no bearing on the problem.
I know in theory it is possible for the system to work flawlessly (in principle), because I use the same set of debug routines in another project and there are no timing issues - on an 18F series PIC.
Two additional things things I have tried are prioritising the interrupts with USB being the highest and int_rda being the lowest using the PIC24F hardware interrupt priorities. I have also tried disabling the timers (I have two that trigger ~6 times a second at the moment) and that has no effect.
Any other ideas? I'm not sure what other things I can try now. |
|
|
Oli Guest
|
|
Posted: Mon May 18, 2009 9:12 am |
|
|
Another interesting point -
If too much data is sent over a short space of time, it seems to have the effect of resetting the processor. buffer overflow somewhere perhaps? |
|
|
Ttelmah Guest
|
|
Posted: Mon May 18, 2009 9:48 am |
|
|
The 'point' is, _whether or not the interrupt is enabled_, if you use any of the functions that are inside the debug_getc (so in your case):
fgetc(GSM)
usb_cdc_putc_robust()
Anywhere else in the code. Interrupts _will_ be disabled around them.
This will also apply to any routines used inside these.
So depending what is inside usb_cdc_putc_robust, _interrupts will be disabled for parts of the USB code, whether or not the interrupt is enabled_.
This is becasue the PIC, does not support re-entrancy (there is no hardware variable stack).
Try with just fgetc(GSM), instead of the debug_getc.
Best Wishes |
|
|
|
|
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
|