Other Parts Discussed in Thread: SYSBIOS
Tool/software: TI-RTOS
I am attempting to make use of the HWI on the Sitara, within SysBios. I have configured the pins and associated my interrupt successfully, and I can generate the event.... once. Debugging has revealed that within the SysBios function Hwi_dispatchIRQC(), one of the last steps before the dispatcher returns is to disable ALL HWI. Why? Given that the dispatcher is called after my HWI ISR completes, I can't easily take an enable all HWI call to override this.
Here is the code from HWI.c:
/*
* ======== Hwi_dispatchIRQC ========
* Configurable IRQ interrupt dispatcher.
*/
Void Hwi_dispatchIRQC(Hwi_Irp irp)
{
/*
* Enough room is reserved above the isr stack to handle
* as many as 16 32-bit stack resident local variables.
* This space is reserved for the Swi scheduler.
*
* If the swi scheduler requires more than this, you must
* handle this in Hwi_Module_startup().
*/
Hwi_Object *hwi;
BIOS_ThreadType prevThreadType;
UInt intNum;
Int swiKey;
UInt32 oldThreshold;
#ifndef ti_sysbios_hal_Hwi_DISABLE_ALL_HOOKS
Int i;
#endif
/* ignore spurious ints */
if (Hwi_intc.SIR_IRQ & 0x80000000) {
Hwi_module->spuriousInts++;
Hwi_module->lastSpuriousInt = Hwi_intc.SIR_IRQ & 0x7f;
Hwi_intc.CONTROL = NEW_IRQ_AGR;
return;
}
/* save irp for ROV call stack view */
Hwi_module->irp = irp;
if (Hwi_dispatcherSwiSupport) {
swiKey = SWI_DISABLE();
}
/* set thread type to Hwi */
prevThreadType = BIOS_setThreadType(BIOS_ThreadType_Hwi);
/* Process only this pending interrupt */
intNum = Hwi_intc.SIR_IRQ; /* get current int num */
/* remember previous priority threshold */
oldThreshold = Hwi_intc.THRESHOLD;
/* set the threshold to this interrupt's priority */
Hwi_intc.THRESHOLD = Hwi_intc.IRQ_PRIORITY & (Hwi_NUM_PRIORITIES - 1);
/* clear this interrupt, force a re-sort, and allow new ones in */
Hwi_intc.CONTROL = NEW_IRQ_AGR;
hwi = Hwi_module->dispatchTable[intNum];
hwi->irp = Hwi_module->irp;
#ifndef ti_sysbios_hal_Hwi_DISABLE_ALL_HOOKS
/* call the begin hooks */
for (i = 0; i < Hwi_hooks.length; i++) {
if (Hwi_hooks.elem[i].beginFxn != NULL) {
Hwi_hooks.elem[i].beginFxn((IHwi_Handle)hwi);
}
}
#endif
Log_write5(Hwi_LM_begin, (IArg)hwi, (IArg)hwi->fxn,
(IArg)prevThreadType, (IArg)intNum, hwi->irp);
if (Hwi_dispatcherAutoNestingSupport) {
Hwi_enable();
}
/* call user's ISR func */
(hwi->fxn)(hwi->arg); <------- MY ISR GETS CALLED
Hwi_disable(); <-------- TI Dispatcher code DISABLES ALL HWI
Log_write1(Hwi_LD_end, (IArg)hwi);
/* restore previous threshold priority */
Hwi_intc.THRESHOLD = oldThreshold;
#ifndef ti_sysbios_hal_Hwi_DISABLE_ALL_HOOKS
/* call the end hooks */
for (i = 0; i < Hwi_hooks.length; i++) {
if (Hwi_hooks.elem[i].endFxn != NULL) {
Hwi_hooks.elem[i].endFxn((IHwi_Handle)hwi);
}
}
#endif
/* Run Swi scheduler */
if (Hwi_dispatcherSwiSupport) {
SWI_RESTORE(swiKey);
}
/* restore thread type */
BIOS_setThreadType(prevThreadType);
}
By disabling all of the HWI after my initial interrupt, it turns my interrupt into a one-shot. I've gone through what example code I can find from TI, and the Sys/Bios User Manual, and the Doxygen files, but I have not been able to resolve this. Your assistance is requested.
Thanks.
- Tim