PDA

View Full Version : Bulletproof interrupt



Charles Linquis
- 22nd October 2010, 14:06
I have an interrupt-driven (D-Ts INSTANT INTERRUPTS) I2C slave running (using the SSP hardware). I'm worried that in some instances (like SCL being held low), the interrupt will get "stuck" and never return, thereby "hanging" my slave.

In an attempt to prevent this, I made-
SPP a low-priority interrupt, and TMR4 a high-priority interrupt
The TMR4 interrupt is turned on, but Timer 4 itself is turned off (with T4CON.2 = 0). As soon as the SPP (low-priority) interrupt is entered, it turns TMR4 on. Just before the SPPs INT_RETURN, TMR4 is shut off and cleared.

The goal is that if the SPP interrupt gets stuck, TMR4 will time out, (and being a higher priority) will put things back in order.

The high-priority TMR4 interrupt (which occurs on TMR4 overflow) has only a few instructions:

ASM
unsticker
bcf TMR3,0 ; Stop the timer
clrf TMR4 ; clear the timer
bcf PIR3,3 ; clear the interrupt flag register
retfie 1 ; restore the shadow registers (for the lp interrupt)
INT_RETURN ; Should put me back in the main program
ENDASM


It compiles, but doesn't "unstick" the SPP INT if I (for example) put a PAUSE 1000 in the middle of it. Before I spend a lot of time on this, my question is:

Is this the proper way to get out of a stuck interrupt? Is there a better way?

rmteo
- 22nd October 2010, 15:08
How about using the watchdog timer (remember to kick the dog periodically)?

Darrel Taylor
- 22nd October 2010, 15:24
I think the bigger question is if the SSP interrupt is being handled correctly to begin with.

The clk line can be held low all day long and you'll never get an interrupt.
But if you are trying to send more than one byte at a time without leaving the handler, then the master may fail in the middle and stop clocking out the data, which could cause it to hang.

If you only send one byte at a time and exit the handler ... when it's time to send the next byte, you'll get another interrupt ... dump a byte into SSPBUF and exit again. If the master fails, it won't matter, and can never hang-up.

In your "unstick" routine, the retfie 1 will just exit the HP int, then execution will return to the LP int. It would never make it to the INT_RETURN after the retfie.

If you are sending more than one byte in the slave's handler without exiting, then you're probably sitting in a loop waiting for SSPIF before putting the next byte in SSPBUF. So in that loop, watch for TMR4IF too. If the timer overflows, exit the handler.

Charles Linquis
- 22nd October 2010, 16:02
Maybe I don't understand things correctly, but if a MASTER-READ is in process, and I'm the slave, if SCL stops before I have shifted out my entire byte, I assume that I sit and wait for the clock to reappear- which it never will, and I'm stuck.

Is this correct?

Darrel Taylor
- 22nd October 2010, 16:19
Once you put a byte in SSPBUF, execution of the program resumes and the hardware takes over the process of sending the byte.

If the hardware process fails, then only the hardware SSP module hangs, and you will not receive anymore interrupts. But the program will not hang if you are only sending one byte at a time per interrupt.

Charles Linquis
- 22nd October 2010, 17:25
Thanks Darrel. I should have realized this. I get paranoid pretty easy, since all my customers are.