init vector implementation
[cortex-from-scratch] / ivt.c
1 #include <stdbool.h>
2 #include <stddef.h>
3 #include <stdint.h>
4 #include <stm32.h>
5 #include <mmap.h>
6
7 /* TIMER, TODO: move to timer.c */
8
9
10
11 /* Interrupt vector can contain 16 exceptions and up to 256 interrupts
12  * In this code we use 16 exceptions and 36 interrupts  
13  * (note: this should be aligned to the vector table size) 
14  * Offsets of each entry is:  0x0, 0x80, 0x100, 0x180 .. */
15
16 /* interrupt vector 1-15: processor exceptions
17  * interrupt vector 16-43: irq0 - irq .. */
18 uint32_t ivt[43];
19
20 /* * base is location of interrupt service request
21  * */
22 void ivt_set_gate(unsigned char num, void * isr(), short pri) {
23
24         ivt[num] = (uint32_t) isr;
25         // TODO priority
26 }
27
28 // test Interrupt service routine
29 void * test_ISR() {
30         uart_puts("PING!");
31 }
32
33 /* Initialize interrupt vector  */
34
35 void ivt_init() {
36
37         /* clear entiry IVT, in SRAM location for SRAM + .data (in .bss section) */
38         memset(&ivt, 0, (sizeof(uint32_t) * 44));
39
40         // stack top is loaded from the first entry table on boot/reset
41         // don't need to relocate or init this here
42
43         // copy old vectors 
44         extern void * reset,  * nmi, * hardfault;
45         //extern uint32_t reset, nmi, hardfault;
46         //ivt[1] = &reset;
47         //ivt[2] = &nmi;
48         //ivt[3] = &hardfault;
49
50         ivt_set_gate(1, test_ISR, 0);
51         ivt_set_gate(2, test_ISR, 0);
52         ivt_set_gate(3, test_ISR, 0);
53         ivt_set_gate(15, test_ISR ,0);
54
55         // enable all interrupts
56         
57         *SYSCTRL_RCGC1 = *SYSCTRL_RCGC1 | 0x00010000;
58
59         // TODO systimer 
60         // ivt[15]
61         *NVIC_EN0 = *NVIC_EN0 | 0x00008003;
62 //      *NVIC_EN1 = (volatile uint32_t) 0xFFFFFFFF; // TODO not all registers
63
64         // priority levels are 0 by default (only executable by kernel)
65         
66         /* disable all interrupts
67          * MOV R0, #1 ; disable all
68          * MSR PRIMASK, R0 
69          * MOV R0, #0 ; allow all
70          * MSR PRIMASK, R0 */
71
72         
73         
74         /* relocate the vector table to (S)RAM 
75          * vector table starts at 0x0. since the address 0x0 point to bootcode, it is on ROM or FLASH. 
76          * the value cannot be changed during runtime. however, the vector table can be
77          * relocated to other memory locations in the code or RAM later on
78          *
79          * we can do this by setting a register in the NVIC called
80          * the vector table offset register (address 0xE000ED08).  */
81
82
83         *NVIC_VECTTBL = (volatile unsigned long) &ivt; 
84
85 }