TRIMUI SMART >> Assembly
GIC
參考資訊:
1. pdf
2. baremetal-arm
Timer0的中斷號碼是50
GIC-400 DIST
GIC-400 CPUIF
main.s
.global _start .equ SCU_BASE, 0x01c80000 .equ GPIO_BASE, 0x01c20800 .equ TIMER_BASE, 0x01c20c00 .equ PG, (0x24 * 6) .equ TMR_IRQ_EN_REG, 0x00 .equ TMR_IRQ_STA_REG, 0x04 .equ TMR0_CTRL_REG, 0x10 .equ TMR0_INTV_VALUE_REG, 0x14 .equ TMR0_CUR_VALUE_REG, 0x18 .equ CFG1, 0x04 .equ DATA, 0x10 .equ TMR0_INT, 50 .equ GIC_DIST, (SCU_BASE + 0x1000) .equ GIC_CPUIF, (SCU_BASE + 0x2000) .equ DCTLR, (GIC_DIST + 0x0000) /* 0x0000 Distributor Control register */ .equ DISENABLER, (GIC_DIST + 0x0100) /* 0x0100 Interrupt set-enable registers */ .equ DITARGETSR, (GIC_DIST + 0x0820) /* 0x0820 Interrupt CPU targets */ .equ CCTLR, (GIC_CPUIF + 0x0000) /* 0x0000 CPU Interface control register */ .equ CCPMR, (GIC_CPUIF + 0x0004) /* 0x0004 Interrupt priority mask register */ .equ CEOIR, (GIC_CPUIF + 0x0010) /* 0x0010 End of interrupt register */ .arm .text _start: .long 0xea000016 .byte 'e', 'G', 'O', 'N', '.', 'B', 'T', '0' .long 0, __spl_size .byte 'S', 'P', 'L', 2 .long 0, 0 .long 0, 0, 0, 0, 0, 0, 0, 0 .long 0, 0, 0, 0, 0, 0, 0, 0 _vector: b reset b . b . b . b . b . ldr pc, _irq b . _irq: .word irq_handler irq_handler: ldr r0, =GPIO_BASE eor r2, r3 str r2, [r0, #(PG + DATA)] ldr r0, =TIMER_BASE ldr r1, [r0, #TMR_IRQ_STA_REG] str r1, [r0, #TMR_IRQ_STA_REG] ldr r0, =CEOIR ldr r1, =(0x3ff & TMR0_INT) str r1, [r0] subs pc, lr, #4 reset: mrc p15, 0, r0, c1, c0, 0 bic r0, #(1 << 13) mcr p15, 0, r0, c1, c0, 0 adr r0, _vector mrc p15, 0, r2, c1, c0, 0 ands r2, r2, #(1 << 13) ldreq r1, =0x00000000 ldrne r1, =0xffff0000 ldmia r0!, {r2-r8, r10} stmia r1!, {r2-r8, r10} ldmia r0!, {r2-r8, r10} stmia r1!, {r2-r8, r10} mrs r0, cpsr bic r0, #0x80 msr cpsr_c, r0 ldr r0, =CCPMR ldr r1, =0xffff str r1, [r0] ldr r0, =CCTLR ldr r1, =(1 << 0) str r1, [r0] ldr r0, =DCTLR ldr r1, =(1 << 0) str r1, [r0] ldr r0, =DISENABLER + ((TMR0_INT / 32) * 4) ldr r1, [r0] orr r1, #(1 << (TMR0_INT % 32)) str r1, [r0] ldr r0, =DITARGETSR + ((TMR0_INT / 4) * 4) ldr r1, [r0] orr r1, #(1 << ((TMR0_INT % 4) * 8)) str r1, [r0] ldr r0, =TIMER_BASE ldr r1, =(1 << 0) str r1, [r0, #TMR_IRQ_EN_REG] ldr r1, =187500 str r1, [r0, #TMR0_INTV_VALUE_REG] str r1, [r0, #TMR0_CUR_VALUE_REG] ldr r1, =(7 << 4) | (1 << 2) | (1 << 1) | (1 << 0) str r1, [r0, #TMR0_CTRL_REG] ldr r0, =GPIO_BASE ldr r1, =0x11111111 str r1, [r0, #(PG + CFG1)] ldr r2, =0xffff ldr r3, =(1 << 10) str r2, [r0, #(PG + DATA)] 0: b 0b .end
完成