KallistiOS  2.0.0
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Macros Groups
Data Structures | Macros | Typedefs | Functions
irq.h File Reference

Interrupt and exception handling. More...

#include <sys/cdefs.h>
#include <arch/types.h>

Go to the source code of this file.

Data Structures

struct  irq_context
 Architecture-specific structure for holding the processor state. More...

Macros

#define REG_BYTE_CNT   256 /* Currently really 228 */
 The number of bytes required to save thread context.
#define CONTEXT_PC(c)   ((c).pc)
 Fetch the program counter from an irq_context_t.
#define CONTEXT_FP(c)   ((c).r[14])
 Fetch the frame pointer from an irq_context_t.
#define CONTEXT_SP(c)   ((c).r[15])
 Fetch the stack pointer from an irq_context_t.
#define CONTEXT_RET(c)   ((c).r[0])
 Fetch the return value from an irq_context_t.
#define EXC_RESET_POWERON   0x0000
 Power-on reset.
#define EXC_RESET_MANUAL   0x0020
 Manual reset.
#define EXC_RESET_UDI   0x0000
 Hitachi UDI reset.
#define EXC_ITLB_MULTIPLE   0x0140
 Instruction TLB multiple hit.
#define EXC_DTLB_MULTIPLE   0x0140
 Data TLB multiple hit.
#define EXC_USER_BREAK_PRE   0x01e0
 User break before instruction.
#define EXC_INSTR_ADDRESS   0x00e0
 Instruction address.
#define EXC_ITLB_MISS   0x0040
 Instruction TLB miss.
#define EXC_ITLB_PV   0x00a0
 Instruction TLB protection violation.
#define EXC_ILLEGAL_INSTR   0x0180
 Illegal instruction.
#define EXC_SLOT_ILLEGAL_INSTR   0x01a0
 Slot illegal instruction.
#define EXC_GENERAL_FPU   0x0800
 General FPU exception.
#define EXC_SLOT_FPU   0x0820
 Slot FPU exception.
#define EXC_DATA_ADDRESS_READ   0x00e0
 Data address (read)
#define EXC_DATA_ADDRESS_WRITE   0x0100
 Data address (write)
#define EXC_DTLB_MISS_READ   0x0040
 Data TLB miss (read)
#define EXC_DTLB_MISS_WRITE   0x0060
 Data TLB miss (write)
#define EXC_DTLB_PV_READ   0x00a0
 Data TLB protection violation (read)
#define EXC_DTLB_PV_WRITE   0x00c0
 Data TLB protection violation (write)
#define EXC_FPU   0x0120
 FPU exception.
#define EXC_INITIAL_PAGE_WRITE   0x0080
 Initial page write exception.
#define EXC_TRAPA   0x0160
 Unconditional trap (trapa)
#define EXC_USER_BREAK_POST   0x01e0
 User break after instruction.
#define EXC_NMI   0x01c0
 Nonmaskable interrupt.
#define EXC_IRQ0   0x0200
 External IRQ request (level 0)
#define EXC_IRQ1   0x0220
 External IRQ request (level 1)
#define EXC_IRQ2   0x0240
 External IRQ request (level 2)
#define EXC_IRQ3   0x0260
 External IRQ request (level 3)
#define EXC_IRQ4   0x0280
 External IRQ request (level 4)
#define EXC_IRQ5   0x02a0
 External IRQ request (level 5)
#define EXC_IRQ6   0x02c0
 External IRQ request (level 6)
#define EXC_IRQ7   0x02e0
 External IRQ request (level 7)
#define EXC_IRQ8   0x0300
 External IRQ request (level 8)
#define EXC_IRQ9   0x0320
 External IRQ request (level 9)
#define EXC_IRQA   0x0340
 External IRQ request (level 10)
#define EXC_IRQB   0x0360
 External IRQ request (level 11)
#define EXC_IRQC   0x0380
 External IRQ request (level 12)
#define EXC_IRQD   0x03a0
 External IRQ request (level 13)
#define EXC_IRQE   0x03c0
 External IRQ request (level 14)
#define EXC_TMU0_TUNI0   0x0400
 TMU0 underflow.
#define EXC_TMU1_TUNI1   0x0420
 TMU1 underflow.
#define EXC_TMU2_TUNI2   0x0440
 TMU2 underflow.
#define EXC_TMU2_TICPI2   0x0460
 TMU2 input capture.
#define EXC_RTC_ATI   0x0480
 RTC alarm interrupt.
#define EXC_RTC_PRI   0x04a0
 RTC periodic interrupt.
#define EXC_RTC_CUI   0x04c0
 RTC carry interrupt.
#define EXC_SCI_ERI   0x04e0
 SCI Error receive.
#define EXC_SCI_RXI   0x0500
 SCI Receive ready.
#define EXC_SCI_TXI   0x0520
 SCI Transmit ready.
#define EXC_SCI_TEI   0x0540
 SCI Transmit error.
#define EXC_WDT_ITI   0x0560
 Watchdog timer.
#define EXC_REF_RCMI   0x0580
 Memory refresh compare-match interrupt.
#define EXC_REF_ROVI   0x05a0
 Memory refresh counter overflow interrupt.
#define EXC_UDI   0x0600
 Hitachi UDI.
#define EXC_GPIO_GPIOI   0x0620
 I/O port interrupt.
#define EXC_DMAC_DMTE0   0x0640
 DMAC transfer end (channel 0)
#define EXC_DMAC_DMTE1   0x0660
 DMAC transfer end (channel 1)
#define EXC_DMAC_DMTE2   0x0680
 DMAC transfer end (channel 2)
#define EXC_DMAC_DMTE3   0x06a0
 DMAC transfer end (channel 3)
#define EXC_DMA_DMAE   0x06c0
 DMAC address error.
#define EXC_SCIF_ERI   0x0700
 SCIF Error receive.
#define EXC_SCIF_RXI   0x0720
 SCIF Receive ready.
#define EXC_SCIF_BRI   0x0740
 SCIF break.
#define EXC_SCIF_TXI   0x0760
 SCIF Transmit ready.
#define EXC_DOUBLE_FAULT   0x0ff0
 Double fault.
#define EXC_UNHANDLED_EXC   0x0fe0
 Unhandled exception.
#define TIMER_IRQ   EXC_TMU0_TUNI0
 The value of the timer IRQ.
#define EXC_OFFSET_000   0
 irq_type_offsets Exception type offsets
#define EXC_OFFSET_100   1
 Offset 0x100.
#define EXC_OFFSET_400   2
 Offset 0x400.
#define EXC_OFFSET_600   3
 Offset 0x600.

Typedefs

typedef struct irq_context irq_context_t
 Architecture-specific structure for holding the processor state.
typedef uint32 irq_t
 The type of an interrupt identifier.
typedef void(* irq_handler )(irq_t source, irq_context_t *context)
 The type of an IRQ handler.

Functions

int irq_inside_int ()
 Are we inside an interrupt handler?
void irq_force_return ()
 Pretend like we just came in from an interrupt and force a context switch back to the "current" context.
int irq_set_handler (irq_t source, irq_handler hnd)
 Set or remove an IRQ handler.
irq_handler irq_get_handler (irq_t source)
 Get the address of the current handler for the IRQ type.
int trapa_set_handler (irq_t code, irq_handler hnd)
 Set or remove a handler for a trapa code.
int irq_set_global_handler (irq_handler hnd)
 Set a global exception handler.
irq_handler irq_get_global_handler ()
 Get the global exception handler.
void irq_set_context (irq_context_t *regbank)
 Switch out contexts (for interrupt return).
irq_context_tirq_get_context ()
 Get the current IRQ context.
void irq_create_context (irq_context_t *context, uint32 stack_pointer, uint32 routine, uint32 *args, int usermode)
 Fill a newly allocated context block for usage with supervisor or user mode.
int irq_disable ()
 Disable interrupts.
void irq_enable ()
 Enable all interrupts.
void irq_restore (int v)
 Restore IRQ state.
int irq_init ()
 Initialize interrupts.
void irq_shutdown ()
 Shutdown interrupts, restoring the state to how it was before irq_init() was called.

Detailed Description

Interrupt and exception handling.

This file contains various definitions and declarations related to handling interrupts and exceptions on the Dreamcast. This level deals with IRQs and exceptions generated on the SH4, versus the asic layer which deals with actually differentiating "external" interrupts.

Author:
Dan Potter
See also:
dc/asic.h

Macro Definition Documentation

#define CONTEXT_FP (   c)    ((c).r[14])

Fetch the frame pointer from an irq_context_t.

Parameters:
cThe context to read from.
Returns:
The frame pointer value.
#define CONTEXT_PC (   c)    ((c).pc)

Fetch the program counter from an irq_context_t.

Parameters:
cThe context to read from.
Returns:
The program counter value.
#define CONTEXT_RET (   c)    ((c).r[0])

Fetch the return value from an irq_context_t.

Parameters:
cThe context to read from.
Returns:
The return value.
#define CONTEXT_SP (   c)    ((c).r[15])

Fetch the stack pointer from an irq_context_t.

Parameters:
cThe context to read from.
Returns:
The stack pointer value.
#define EXC_OFFSET_000   0

irq_type_offsets Exception type offsets

The following are a table of "type offsets" (see the Hitachi PDF). These are the 0x000, 0x100, 0x400, and 0x600 offsets. Offset 0x000

#define EXC_OFFSET_100   1

Offset 0x100.

#define EXC_OFFSET_400   2

Offset 0x400.

#define EXC_OFFSET_600   3

Offset 0x600.

#define REG_BYTE_CNT   256 /* Currently really 228 */

The number of bytes required to save thread context.

This should include all general CPU registers, FP registers, and status regs (even if not all of these are actually used).

On the Dreamcast, we need 228 bytes for all of that, but we round it up to a nicer number for sanity.

#define TIMER_IRQ   EXC_TMU0_TUNI0

The value of the timer IRQ.


Typedef Documentation

typedef struct irq_context irq_context_t

Architecture-specific structure for holding the processor state.

This structure should hold register values and other important parts of the processor state. The size of this structure should be less than or equal to the REG_BYTE_CNT value.

typedef void(* irq_handler)(irq_t source, irq_context_t *context)

The type of an IRQ handler.

Parameters:
sourceThe IRQ that caused the handler to be called.
contextThe CPU's context.
typedef uint32 irq_t

The type of an interrupt identifier.


Function Documentation

void irq_create_context ( irq_context_t context,
uint32  stack_pointer,
uint32  routine,
uint32 args,
int  usermode 
)

Fill a newly allocated context block for usage with supervisor or user mode.

The given parameters will be passed to the called routine (up to the architecture maximum). For the Dreamcast, this maximum is 4.

Parameters:
contextThe IRQ context to fill in.
stack_pointerThe value to set in the stack pointer.
routineThe address of the program counter for the context.
argsAny arguments to set in the registers. This cannot be NULL, and must have enough values to fill in up to the architecture maximum.
usermode1 to run the routine in user mode, 0 for supervisor.
int irq_disable ( )

Disable interrupts.

This function will disable interrupts, but will leave exceptions enabled.

Returns:
The state of IRQs before calling the function. This can be used to restore this state later on with irq_restore().
void irq_enable ( )

Enable all interrupts.

This function will enable ALL interrupts, including external ones.

void irq_force_return ( )

Pretend like we just came in from an interrupt and force a context switch back to the "current" context.

Make sure you've called irq_set_context() before doing this!

irq_context_t* irq_get_context ( )

Get the current IRQ context.

This will fetch the processor context prior to the exception handling during an IRQ service routine.

Returns:
The current IRQ context.
irq_handler irq_get_global_handler ( )

Get the global exception handler.

Returns:
The global exception handler set with irq_set_global_handler(), or NULL if none is set.
irq_handler irq_get_handler ( irq_t  source)

Get the address of the current handler for the IRQ type.

Parameters:
sourceThe IRQ type to look up.
Returns:
A pointer to the procedure to handle the exception.
int irq_init ( )

Initialize interrupts.

Return values:
0On success (no error conditions defined).
int irq_inside_int ( )

Are we inside an interrupt handler?

Return values:
1If interrupt handling is in progress.
0If normal processing is in progress.
void irq_restore ( int  v)

Restore IRQ state.

This function will restore the interrupt state to the value specified. This should correspond to a value returned by irq_disable().

Parameters:
vThe IRQ state to restore. This should be a value returned by irq_disable().
void irq_set_context ( irq_context_t regbank)

Switch out contexts (for interrupt return).

This function will set the processor state that will be restored when the exception returns.

Parameters:
regbankThe values of all registers to be restored.
int irq_set_global_handler ( irq_handler  hnd)

Set a global exception handler.

This function sets a global catch-all handler for all exception types.

Parameters:
hndA pointer to the procedure to handle the exception.
Return values:
0On success (no error conditions defined).
Note:
The specific handler will still be called for the exception if one is set. If not, setting one of these will stop the unhandled exception error.
int irq_set_handler ( irq_t  source,
irq_handler  hnd 
)

Set or remove an IRQ handler.

Passing a NULL value for hnd will remove the current handler, if any.

Parameters:
sourceThe IRQ type to set the handler for (see SH4 exception codes).
hndA pointer to a procedure to handle the exception.
Return values:
0On success.
-1If the source is invalid.
void irq_shutdown ( )

Shutdown interrupts, restoring the state to how it was before irq_init() was called.

int trapa_set_handler ( irq_t  code,
irq_handler  hnd 
)

Set or remove a handler for a trapa code.

Parameters:
codeThe value passed to the trapa opcode.
hndA pointer to the procedure to handle the trap.
Return values:
0On success.
-1If the code is invalid (greater than 0xFF).