1/1

|
Enter ISR when interrupt gets called
by eschwede on Apr 3, 2012 |
eschwede
Posts: 9 Joined: Mar 19, 2012 Last seen: Jul 17, 2012 |
||
|
Hello all,
I would need some help to enter the interrupt service routine when an interrupt gets called. I have a TLM Sensor model attached to the or1ksim as a generic peripheral. It generates the interrupt, by writing '1' to the interrupt line for 100 us. The PIC seems to capture the interrupt correctly after 110 us (SPR_PICSR = 0x00000004), but the processor doesn't enter the isr. Since the interrupt isn't cleared, it then starts pending. I use the or1k-support.h functions. My Or1ksim SW looks as follows: #ifndef BASE_ADDR_ACTUATOR #define BASE_ADDR_ACTUATOR 0X96000000 #endif #ifndef BASE_ADDR_SENSOR #define BASE_ADDR_SENSOR 0X95000000 #endif struct sensordata { volatile float alpha; volatile float dalpha; volatile float theta; volatile float dtheta; }; struct actuatordata { volatile float u1; volatile float u2; volatile float v; }; void sensor_isr(void *r){ int q; q = (int) r; printf("\nInterrupt Service Routine %u: SENSOR \n", q); or1k_mtspr(SPR_PICSR, 0x00000000); }; int main() { // Register Interface struct sensordata *sensor_ptr = (struct sensordata *) BASE_ADDR_SENSOR; struct sensordata sensor_local = {0,0,0,0}; struct actuatordata *actuator_ptr = (struct actuatordata *) BASE_ADDR_ACTUATOR; struct actuatordata actuator_local = {0,0,0}; or1k_interrupt_handler_add(2, sensor_isr); or1k_interrupt_enable(2); printf("\nSPR_UPR = 0x%08lx\n", or1k_mfspr(SPR_UPR)); printf("PICMR = 0x%08lx\n", or1k_mfspr(SPR_PICMR)); printf("SPR_SR = 0x%08lx\n", or1k_mfspr(SPR_SR)); printf("SPR_PICPR = 0x%08lx\n", or1k_mfspr(SPR_PICPR)); while(1){ printf("SPR_PICSR = 0x%08lx\n", or1k_mfspr(SPR_PICSR)); } return 0; } The Output looks as follows: 0 s SPR_UPR = 0x00000601 PICMR = 0x00000007 SPR_SR = 0x00008201 10 us: PhyModel: [STATE_VAR]: x=0 y=0 al=0 th=0 da=0 dt=0 v=0 SPR_PICPR = 0x00000000 SPR_PICSR = 0x00000000 SPR_PICSR = 0x00000000 SPR_PICSR = 0x00000000 110 us: PhyModel: [STATE_VAR]: x=-nan y=-nan al=-nan th=-nan da=-nan dt=-nan v=-nan SPR_PICSR = 0x00000000 SPR_PICSR = 0x00000004 SPR_PICSR = 0x00000004 SPR_PICSR = 0x00000004 210 us: PhyModel: [STATE_VAR]: x=-nan y=-nan al=-nan th=-nan da=-nan dt=-nan v=nan SPR_PICSR = 0x00000004 SPR_PICSR = 0x00000004 SPR_PICSR = 0x00000004 SPR_PICSR = 0x00000004 310 us: PhyModel: [STATE_VAR]: x=-nan y=-nan al=-nan th=-nan da=-nan dt=-nan v=nan Warning: Int on line 2 pending: ignored SPR_PICSR = 0x00000004 SPR_PICSR = 0x00000004 SPR_PICSR = 0x00000004 SPR_PICSR = 0x00000004 410 us: PhyModel: [STATE_VAR]: x=-nan y=-nan al=-nan th=-nan da=-nan dt=-nan v=nan SPR_PICSR = 0x00000004 SPR_PICSR = 0x00000004 SPR_PICSR = 0x00000004 SPR_PICSR = 0x00000004 510 us: PhyModel: [STATE_VAR]: x=-nan y=-nan al=-nan th=-nan da=-nan dt=-nan v=nan Warning: Int on line 2 pending: ignored SPR_PICSR = 0x00000004 SPR_PICSR = 0x00000004 SPR_PICSR = 0x00000004 SPR_PICSR = 0x00000004 ... I would really appreciate some help. Regards, Erik |
|||
|
RE: Enter ISR when interrupt gets called
by firefalcon on Apr 3, 2012 |
firefalcon
Posts: 99 Joined: Jan 10, 2011 Last seen: Mar 26, 2024 |
||
|
Check what your value of SR means. Interrupt exceptions are not enabled.
|
|||
|
RE: Enter ISR when interrupt gets called
by eschwede on Apr 3, 2012 |
eschwede
Posts: 9 Joined: Mar 19, 2012 Last seen: Jul 17, 2012 |
||
|
Thank you for your response.
In the SR Register the Supervisor Mode, Condition flag and Fixed One bits are set. If I additionally set the Interrupt Exception Enable bit, the simulation crashes when the interrupt occurs or should occur: ... 110 us: PhyModel: [STATE_VAR]: x=-nan y=-nan al=-nan th=-nan da=-nan dt=-nan v=-nan SPR_PICSR = 0xexit(39416) @reset : cycles 0, insn #0 @exit : cycles 21491, insn #14705 diff : cycles 21491, insn #14705 |
|||
|
RE: Enter ISR when interrupt gets called
by firefalcon on Apr 3, 2012 |
firefalcon
Posts: 99 Joined: Jan 10, 2011 Last seen: Mar 26, 2024 |
||
|
So, now your exception is being taken. That is progress. The problem now is that the handler for the exception is calling the exit function. You need to install/register your own handler for the exception. I see that you tried to do that in your code, but I am guessing that you used the wrong number.
|
|||
|
RE: Enter ISR when interrupt gets called
by eschwede on Apr 4, 2012 |
eschwede
Posts: 9 Joined: Mar 19, 2012 Last seen: Jul 17, 2012 |
||
|
What do you mean by the "wrong number"? The interrupt request? If I change the interrupt request number the exception isn't taken anymore, so it should be right.
|
|||
|
RE: Enter ISR when interrupt gets called
by firefalcon on Apr 4, 2012 |
firefalcon
Posts: 99 Joined: Jan 10, 2011 Last seen: Mar 26, 2024 |
||
|
If it were me, I would use GDB at this point, with a breakpoint set at 0x800.
|
|||
|
RE: Enter ISR when interrupt gets called
by eschwede on Apr 13, 2012 |
eschwede
Posts: 9 Joined: Mar 19, 2012 Last seen: Jul 17, 2012 |
||
|
So I disassembled the binary file and traced the PC with gdb. The PC doesn't jump to the ISR address, but ends up in the exit function within the exception handler. Apparently the ISR is not set up correctly and instead of jumping to the ISR, exception_exit is executed (see attachment).
When the interrupt occurs the PC goes something like this: 0x800 or1k_exception_handler exception_exit exit __call_exitprocs __fini __do_global_dtors_aux __fini __call_exitprocs exit _exit Has anybody worked with the or1k-support.h functions, especially the ones concerning the interrupts and can assure that they are working properly or does anyone have an example application using them? best regards, Erik
code.out (821 kb)
|
|||
|
RE: Enter ISR when interrupt gets called
by eschwede on Apr 16, 2012 |
eschwede
Posts: 9 Joined: Mar 19, 2012 Last seen: Jul 17, 2012 |
||
|
I've found a workaround by using the exception handling, but I believe it is not the way it is supposed to be.
Work Around: Exception Handling or1k_mtspr(SPR_SR, or1k_mfspr(SPR_SR) | SPR_SR_IEE); or1k_exception_handler_add (0x8, &exception_handling_function); or1k_interrupt_enable(0x2); 1.Interrupt gets called: PC = 0x800 2.0x800 calls or1k_exception_handler() 3.IF no exception handler is set:exception_exit() 4.ELSE Enter exception_handling_function() (This is the case) I believe it should be something like this: or1k_mtspr(SPR_SR, or1k_mfspr(SPR_SR) | SPR_SR_IEE); or1k_exception_handler_add (0x8, &or1k_interrupt_handler); //I'm not sure how to include or1k_interrupt_handler, since it is not defined in or1k-support.h or1k_interrupt_handler_add(0x2, &ISR); or1k_interrupt_enable(0x2); 1.Interrupt gets called: PC = 0x800 2.0x800 calls or1k_exception_handler() 3.IF no exception handler is set: exception_exit() (This is the case) 4.ELSE : or1k_exception_handler() should call or1k_interrupt_handler() to enter ISR() Is there maybe a bug in the or1k-support.h library? The link between the exception handling and the interrupt handling seems to be missing. |
|||
|
RE: Enter ISR when interrupt gets called
by NeoBelerophon on Jul 10, 2012 |
NeoBelerophon
Posts: 10 Joined: Nov 29, 2011 Last seen: Jul 16, 2012 |
||
|
Hi,
I have the same problem as you described in this thread. Where you able to solve this problem or is your workaround the only working solution by now? Best regards, Stefan |
|||
|
RE: Enter ISR when interrupt gets called
by ClockworkRed on Jul 10, 2012 |
ClockworkRed
Posts: 19 Joined: May 6, 2011 Last seen: Oct 26, 2016 |
||
|
Hi Stefan,
from our understanding there is some code not working in the assembly code of the functions that handle external interrupts in the newlib library for calling the ISR. We did some modifications to the file or1k-support-asm.S to handle interrupts correctly. We attached the file to our bug report: http://bugzilla.opencores.org/bugzilla4/show_bug.cgi?id=86 The new file works well with calling an ISR for single interrupt handling. We now consider the case that we have two sources for external interrupts and there we have encountered another problem with our modified version when two interrupts come simultaneously. As soon as we have solved this problem we will upload an updated version of the file. In order to use the new version you need to compile the newlib library with the modified or1k-support-asm.S. Is is located under gnu-src/newlib-1.18.0/newlib/libc/machine/or32. You also need to declare the function or1k_interrupt_handler() in or1k-support.h because you manually must register this function as exception handler for external interrupts (vector 0x800): // Add External interrupt Handler or1k_exception_handler_add (0x8, &or1k_interrupt_handler); With best regards, Daniel |
|||
|
RE: Enter ISR when interrupt gets called
by NeoBelerophon on Jul 12, 2012 |
NeoBelerophon
Posts: 10 Joined: Nov 29, 2011 Last seen: Jul 16, 2012 |
||
|
Thx for this hint.
I changed newlib according to your bug report and recompiled it. Now the exception is handled and my openrisc program keeps running. But as it seems there appears no interrupt in the SPR_PICSR. What i did is: void isr(void* null) { printf("interrupt received\n"); or1k_mtspr(SPR_PICSR, 0x00000000); } int main() { ... or1k_mtspr(SPR_SR, or1k_mfspr(SPR_SR) | SPR_SR_IEE); or1k_exception_handler_add (0x8, &or1k_interrupt_handler); or1k_interrupt_handler_add(6, &isr); or1k_interrupt_enable(6); while(1) { printf("SPR_PICSR = 0x%08lx\n", or1k_mfspr(SPR_PICSR)); } } the output is: SPR_PICSR = 0x00000000 SPR_PICSR = 0x00000000 SPR_PICSR = 0x00000000 SPR_PICSR = 0x00000000 SPR_PIC Or1ksim > firing Event 6 SR = 0x00000000 SPR_PICSR = 0x00000000 <-- not crashing but also no interrupt handling? SPR_PICSR = 0x00000000 SPR_PICSR = 0x00000000 I connected the interrupt to the or1ksim this way: SC_METHOD( intrMethod ); sensitive << myIntrrupt; void intrMethod() { std::cout << "Or1ksim > firing Event 6" << std::endl; or1ksim_interrupt(6); } Is there something missing to trigger the event? |
|||
|
RE: Enter ISR when interrupt gets called
by ClockworkRed on Jul 13, 2012 |
ClockworkRed
Posts: 19 Joined: May 6, 2011 Last seen: Oct 26, 2016 |
||
|
Did you use our complete file?
We modified the code at two places, once is in the interrupt_handler function()'s assembly code and once in the interrupt_handler_add() assembly code routine. The interrupt_handler_add() function actually was in our eyes not consistent because adding an ISR to interrupt line 6 registered the ISR for interrupt line 5. Otherwise, I do not know why your ISR does not get called. The code looks at first sight ok to me. |
|||
|
RE: Enter ISR when interrupt gets called
by NeoBelerophon on Jul 13, 2012 |
NeoBelerophon
Posts: 10 Joined: Nov 29, 2011 Last seen: Jul 16, 2012 |
||
|
I replaced the whole file .S file and added the declaration to the header file.
So I assume all changes are applied to the newlib? |
|||
|
RE: Enter ISR when interrupt gets called
by ClockworkRed on Jul 16, 2012 |
ClockworkRed
Posts: 19 Joined: May 6, 2011 Last seen: Oct 26, 2016 |
||
|
Hi,
maybe you have then a problem with your SystemC wrapper because it works in our simulation. Please consider, the or1ksim must use local time when you connect it to SystemC because it is written in pure C. For interrupts, the call to the or1ksim_interrupt routine only registers the interrupt but does not make the or1ksim simulate the execution of the interrupt handler nor ISR. For this, you need to run the or1ksim_run function in a while loop with a local time quantum. You may either synchronize it with the SystemC simulation time when it makes an external memory access (in the address range given in the generics section) or after a quantum passed. Anyway, the ISR will only be executed in a call to or1ksim_run which synchronized with SystemC after the call to or1ksim_interrupt. An example of a working SystemC wrapper is given in the Embecosm example. I hope that helps, Daniel |
|||
|
RE: Enter ISR when interrupt gets called
by ClockworkRed on Jul 17, 2012 |
ClockworkRed
Posts: 19 Joined: May 6, 2011 Last seen: Oct 26, 2016 |
||
|
We updated the file or1k-support-asm.S in
http://bugzilla.opencores.org/bugzilla4/show_bug.cgi?id=86 to Support nested interrupts from different sources. |
|||
1/1

