The TSK3000A can generate both hardware exceptions (interrupts) and software exceptions.
Hardware Generated Exceptions (Interrupts)
The processor has 32 interrupt inputs. Interrupts are wired to the processor's
INT_I input pin.
Each interrupt can be individually configured to operate either as edge-triggered or level-sensitive by setting its corresponding bit in the IMode register – 0 for level-sensitive (active High) or 1 for edge-triggered (active on rising edge). By default, all interrupt inputs are configured for level-sensitive operation.
When an interrupt input is configured to operate as edge-triggered, then once an edge has occurred it must be cleared, to allow the detection of another edge. This is accomplished by writing a '1' to the corresponding bit in the IPending register. The following example C-code shows how this can be written:
void tsk3000_clear_interrupt_edge_flags(unsigned int value)
An activated edge-triggered interrupt will appear as pending in the IPending register until it is cleared using this method.
There are two modes of operation with respect to interrupts – Standard and Vectored. The mode itself is controlled by the
VIE bit in the Status register (Status.9).
This mode for interrupts is selected by writing a '0' into bit 9 of the Status register. When an interrupt line goes active, the processor will:
- Save a return address into the Exception Return register
- Save the current state of the Global Interrupt Enable bit,
IEc, (Status.0) and then clear this bit to disable all other interrupts
- Jump to the interrupt vector address stored in the EB register. Note that in this mode, all interrupts will jump to this vector.
The interrupt handler can then either look at:
- The IPending register to see the raw interrupt inputs in order to do its own priority encoding in software
- The Status register bits 15..11, which contain the current priority vector based on the current interrupt inputs. The software exception handler can use this value to help resolve interrupt priorities if required.
This mode for interrupts is selected by writing a '1' into bit 9 of the Status register. In this mode the 32 interrupt inputs –
INT_I[31..0] – will each jump to a separate interrupt vector.
Each vector slot requires 8 Bytes, allowing enough room for a jump and its associated branch delay slot. The target vector addresses are determined using the value stored in the EB register and range from (EB +
0000h) to (EB +
The priority of interrupts in this mode is from lowest to highest. Therefore, interrupt 0 (
INT_I) has a higher priority than interrupt 1 (
INT_I), which has a higher priority than interrupt 2 (
INT_I), and so on.
Generating an Interrupt
A hardware interrupt is generated if the following conditions are met:
IEcbit of the Status register (Status.0) is 1
- An interrupt input –
INT_I[n]– is active (High or Rising edge)
- The corresponding bit
nof the Interrupt Enable register (IEnable.
n) is High
Figure 1 shows the interrupt structure for the TSK3000A, which includes the dedicated interrupt inputs and also the interrupt generated by the Programmable Interval Timer.
Unless vectored interrupts are enabled, the exception handler code at the interrupt vector address must determine the cause of the exception and provide an appropriate response.
When interrupt inputs are active, they are ignored until the pipeline is not stalled. They are then handled as injected software exceptions.
The special case of an interrupt occurring when the processor is executing a branch delay slot instruction, is handled transparently. In this case, the processor finishes the branch delay slot instruction and then processes the interrupt.
Software Generated Exception
When a program issues the SYSCALL instruction, it generates a software exception. The exception handler for the operating system determines the reason for the SYSCALL and responds appropriately.
The SYSCALL instruction always results in a jump to the vector address stored in the Exception Base register (EB). To identify that the interrupt is indeed generated by the software rather than the hardware, bit 0 of the IPending register is interrogated. If it is '0' – i.e. there is no pending interrupt – then the interrupt is software-generated.
Returning from an Interrupt
Before returning from a hardware-generated exception (an interrupt), the application code must clear the cause of the interrupt.
To return from an interrupt there are two actions that must be completed:
- Jump to the address in the Exception Return register (ER). This is a special function register in the coprocessor (COP0-$7). The processor will have placed the correct return address in this register when the interrupt occurred. For hardware interrupts this would have been the address of the currently executing instruction. For software exceptions (SYSCALL instructions) this would be the address after that instruction.
- The RFE (Restore From Exception) instruction must be executed.
Any registers modified during exception processing must be restored by the exception handling software before returning. When executing the RFE instruction, the processor will restore the status bits in the Status register as follows:
The values of
UMo will remain unchanged.
In Assembly source code, the normal practice is to place the RFE instruction in the branch delay slot of the Jump instruction that returns from the interrupt. For example:
mfc0 t1, COP_ExceptionReturn
In C source code, this is all handled automatically by the Compiler.