View previous topic :: View next topic |
Author |
Message |
nathani Guest
|
CAN Receive Interrupts |
Posted: Wed May 17, 2006 11:10 am |
|
|
Is anyone aware of any problems with the transmission interrupt for enhanced can mode on the pic18F6680. I have done:
Code: |
enable_interrupts(INT_CANTX2);
enable_interrupts(GLOBAL);
|
But I I am unable to get into the interrupt unless I manually trigger an event that does this: bit_set(PIR3,4). I checked the list file and the both the above enables are setting the appropriate bits in the appropriate registers according to the data sheet. I am definitely transmitting messages on the can however it seems that the actually hardware transmission completion is not setting the pir3 bit.
Signed: confused and thankful for any help |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
|
nathani Guest
|
|
Posted: Wed May 17, 2006 12:09 pm |
|
|
Cool. I'm in enhanced mode, more specifically I use mode 2. |
|
|
nathani Guest
|
|
Posted: Wed May 17, 2006 12:27 pm |
|
|
Yes I read that post previously. It applies to me somewhat. I have decided to implement a method to ensure correct ordering of my messages by filling all the buffers but only flagging one buffer at a time to be transmitted. The problem I am facing is that I can't get the transmission interrupt to fire. No matter what I do. I can get it to fire if I manually set the interrupt flag, so I know that the interrupt is setup fine and everything.
I haven't tried implementing it in legacy mode (mode 0). But I've read the data sheet and it indicates that if the mode is set to 1 or 2 then a general interupt is triggered that indicated that a message has been sent, unlike legacy mode where each buffer has its own interupt.
Thanks for you response. |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Wed May 17, 2006 12:42 pm |
|
|
For PIE bit 4, the data sheet says:
Quote: | When CAN is in Mode 1 or 2:
TXBnIE: CAN Transmit Buffer Interrupts Enable bit
1 = Enable transmit buffer interrupt; individual interrupt is enabled by TXBIE and BIE0
0 = Disable all transmit buffer interrupts |
The following line doesn't do anything to those two registers.
Code: | enable_interrupts(INT_CANTX2); |
I think CCS only supports Mode 0. For Mode 2, you need to use
#byte statements to declare the address of the TXBIE and BIE0
registers, and then load them with the appropriate values with
code in main(). I haven't used Mode 2 so I'm not sure of exactly
how to do it, but this information should help.
Also, you might want to edit the title of your post. The title says
"receive interrupts" but the thread is about transmit interrupts. |
|
|
nathani Guest
|
|
Posted: Wed May 17, 2006 12:57 pm |
|
|
Senility seems to be setting in early for me. Thanks. |
|
|
nathani Guest
|
|
Posted: Wed May 17, 2006 4:47 pm |
|
|
Hmm. I guess I need to be a registered member to edit my post. Oh well, sorry about that anywho. I'm having problems with my interrupts and was wondering if you could offer some insight.
This code will not trigger the interrupt at all
Code: |
enable_interrupts(INT_CANTX2);
bit_set(TXBIE,2);
//bit_set(TXBIE,3);
bit_set(TXBIE,4);
enable_interrupts(GLOBAL);
|
Howerver if I do this:
Code: |
enable_interrupts(INT_CANTX2);
bit_set(TXBIE,2);
bit_set(TXBIE,3);
bit_set(TXBIE,4);
enable_interrupts(GLOBAL);
|
The interrupt get triggered on a transmission but the interrupt seems to be triggered infinitely as the watch dog timer eventually has to reset the pic.
My interrupt handler looks like this:
Code: |
/**************************************************************************/
/* Can Transmit interupt service routine */
#int_CANTX2
void canTXISR()
{
bit_clear(PIR3,4);
output_c(0b11111001);
}
|
Where the output c simply lights up a bunch of led so that I can tell when the interrupt is being triggered.
Thanks again. |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Wed May 17, 2006 5:06 pm |
|
|
A transmit interrupt will be an infinite interrupt if there are no bytes
to send. Inside the isr, you have to check if you have more
bytes to send, and if not, then disable the Tx interrupt. |
|
|
dilandau
Joined: 25 Aug 2010 Posts: 11
|
|
Posted: Wed Sep 21, 2011 5:05 am |
|
|
Don´t know if this code will entirely cover your question but I had similar problem with interrupts in enhanced mode for receiving data, and this is the way I solved it:
In a pic 18f4580 these are the registers to mind:
Code: |
// Peripheral Register 3
#byte PIR3 = 0xFA4
#bit RXBnIF = PIR3.1 // Bit flag de recepcion de CAN Mode 1
#byte PIE3 = 0xFA3
#bit RXBnIE = PIE3.1 // Bit enable/diable CAN mode 1 interrupts
// Buffer interrupt enable register
#byte BIE0 = 0xDFA
#bit B5IE = BIE0.7
#bit B4IE = BIE0.6
#bit B3IE = BIE0.5
#bit B2IE = BIE0.4
#bit B1IE = BIE0.3
#bit B0IE = BIE0.2
#bit RXB1IE = BIE0.1
#bit RXB0IE = BIE0.0 |
As for the configuration part itself I have done this to handle 5 interrputs
(2 dedicated and 3 of the programable ones).
If you dont do this then RXBnIF flag will never fires.
Code: | // Configuración adicional para usar interrupciones
RXBnIE = 1; // Can Receive Buffer Interrupts Enable
RXB0IE = 1; // dedicated Receive buffer Interrupt 0 enable
RXB1IE = 1; // dedicated Receive buffer Interrupt 1 enable
B0IE = 1; // Programmable Receive buffer Interrupt 0 enable
B1IE = 1; // Programmable Receive buffer Interrupt 1 enable
B2IE = 1; // Programmable Receive buffer Interrupt 2 enable
enable_interrupts(INT_CANRX1);
enable_interrupts(GLOBAL);
|
So now I get the interrupt working normally in enhanced mode.
(And why INT_CANRX1 instead of INT_CANRX0, well it just happens to be same address in datasheet for receiving interrupts in enhanced mode so you dont need to handle #int_default to get this particular one in PIR3)
Code: | #INT_CANRX1
void CAN_DataInterrupt1()
{
if (can_kbhit())
{
if (can_getd(rx_id, buffer, rx_len, rxstat))
{
}
}
} |
|
|
|
|