I'm still having problems with interrupts apparently interacting with each other. Our design has timer0, ADC, UART0/1, and RTC running. The basic problem we're seeing is various anomalies in the UART interrupts, which vary depending upon which other interrupts are enabled. Since I never found a "canonical" reference for the Interrupt Handler, I've used various references over the past year. Originally I was using the version from the ST USB demo (RIDE), but that apparently is incomplete. I then switched to the version used by IAR, but I really have no guarantee that this is complete and correct in our current (Yagarto) build environment. I would be grateful if people here (especially those who are also using multiple interrupts, and are building with Yagarto or other GnuArm environments) could comment on this code, which I'm enclosing below. Thank you all very much!! Dan Miller /*;********************************************************************* ********** ;* Macro Name : SaveContext ;* Description : This macro used to save the context before entering ; an exception handler. ;* Input : The range of registers to store. ;* Output : none ;*********************************************************************** ********/ .macro SaveContext reg1 reg2 STMFD sp!,{\reg1-\reg2,lr} /* Save The workspace plus the current return */ /* address lr_ mode into the stack */ MRS r1, spsr /* Save the spsr_mode into r1 */ STMFD sp!, {r1} /* Save spsr */ .endm /*;********************************************************************* ********** ;* Macro Name : RestoreContext ;* Description : This macro used to restore the context to return from ; an exception handler and continue the program execution. ;* Input : The range of registers to restore. ;* Output : none ;*********************************************************************** ********/ .macro RestoreContext reg1 reg2 LDMFD sp!, {r1} /* Restore the saved spsr_mode into r1 */ MSR spsr_cxsf, r1 /* Restore spsr_mode */ LDMFD sp!, {\reg1-\reg2,pc}^ /* Return to the instruction following */ /* the exception interrupt */ .endm /*********************************************************************** ********* * Function Name : IRQHandler * Description : This function is called when IRQ exception is entered. * Input : none * Output : none ************************************************************************ ********/ IRQHandler: # STR9 firmware method from ST (Ride code) # SUB lr,lr ,#4 # SaveContext r0,r4 # LDR r0, = VectorAddress # LDR r0, [r0] /* Read the routine address from VIC0 Vector Address register */ # # BLX r0 /* Branch with link to the IRQ handler. */ # RestoreContext r0,r4 # STR9 firmware method from IAR SUB lr,lr,#4 /* ; Update the link register */ SaveContext r0,r12 /* ; Save the workspace plus the current */ /* ; return address lr_irq and spsr_irq */ LDR r0, = VectorAddress LDR r0, [r0] /* ; Read the routine address */ LDR r1, = VectorAddressDaisy LDR r1, [r1] /* ; Padding between the acknowledge and re-enable of interrupts */ /* ; For more details, please refer to the following URL */ /* ; http://www.arm.com/support/faqip/3682.html */ NOP NOP MSR cpsr_c, #Mode_SYS /* Switch to SYS mode and enable IRQ */ STMFD sp!,{lr} /* ; Save the link register. */ LDR lr, =IRQ_ReturnAddress /* ; Read the return address. */ BX r0 /* ; Branch to the IRQ handler. */ IRQ_ReturnAddress: LDMFD sp!,{lr} /* ; Restore the link register. */ MSR cpsr_c, #Mode_IRQ|I_Bit|F_Bit /* Switch to IRQ mode and disable IRQ */ LDR r0, =VectorAddress /* ; Write to the VectorAddress to clear the */ STR r0, [r0] /* ; respective interrupt in the internal interrupt */ LDR r1, =VectorAddressDaisy /* ; Write to the VectorAddressDaisy to clear the */ STR r1,[r1] /* ; respective interrupt in the internal interrupt */ RestoreContext r0,r12 /* ; Restore the context and return to the program execution. */
Greetings. We are having similar problems with uart: missing characters and uart interrupt stops triggering after some time. Using STR912FAW44. At other tests with minor modifications, it seems to work properly more often like 70%, but the remaining 30% still have the same problems. We have just inherited this project, and the source code is a mess, and we are new to ARM and still learning with difficulty. We are using an RTOS, but we believe it is not the cause of our problems. We are now investigating STR912 interrupt management issues that may be the cause, based on STMicro errata on the cpu revision that we are using. I have noticed your code as similar to ours, except that currently it has been modified for some reason in this line: original: MSR cpsr_c,#0x1F current: MSR cpsr_c,#0x1F | I_Bit Why I_Bit is set we have not yet received information from the original team. This will disable the interrupts. Other info: We are having problems with Uart1. Uart0 is also used but does not seem to have any problems. We have also utilized Uart2 for temporary debug output. Originally Uart1 enabled the FIFO. But someone from old team modified the settings to not use FIFO, without updating the Uart1 handler. We are fixing this now. But this would probably not cause the other problem of interrupts getting blocked. THank you for any info. Erwin
Please log in before posting. Registration is free and takes only a minute.
Existing account
Do you have a Google/GoogleMail account? No registration required!
Log in with Google account
Log in with Google account
No account? Register here.