xref: /inferno-os/os/boot/puma/ebsit.trap.c (revision 74a4d8c26dd3c1e9febcb717cfd6cb6512991a7a)
1 #include "u.h"
2 #include "../port/lib.h"
3 #include "mem.h"
4 #include "ebsit.h"
5 #include "dat.h"
6 #include "fns.h"
7 
8 #include "ureg.h"
9 
10 int inpanic;
11 
12 #define CSR ((ushort *) 0x2000000)
13 
14 
15 typedef struct Irqctlr {
16 	uint	addr;
17   	uint	enabled;
18 	struct {
19 		void	(*r)(Ureg*, void*);
20 		void 	*a;
21 	} h[16];
22 } Irqctlr;
23 
24 static Irqctlr irqctlr;
25 
26 void
csrset(int bit)27 csrset( int bit )
28 {
29 static ushort *csr_val = 0x8c;
30 
31 	*csr_val ^= (1 << bit);
32 	putcsr(*csr_val);
33 }
34 
35 void
intrinit(void)36 intrinit( void )
37 {
38 int offset;
39 ulong op;
40 
41 
42 	irqctlr.addr = 1;
43 	irqctlr.enabled = 0;
44 
45 	/* Reset Exception */
46 	offset = ((((ulong) _vsvccall) - 0x0)-8) >> 2;
47 	op = ( 0xea << 24 ) | offset;
48 	*((ulong *) 0x0) = op;
49 
50 	/* Undefined Instruction Exception */
51 	offset = ((((ulong) _vundcall) - 0x4)-8) >> 2;
52 	op = ( 0xea << 24 ) | offset;
53 	*((ulong *) 0x4) = op;
54 
55 	/* SWI Exception */
56 	offset = ((((ulong) _vsvccall) - 0x8)-8) >> 2;
57 	op = ( 0xea << 24 ) | offset;
58 	*((ulong *) 0x8) = op;
59 
60 	/* Prefetch Abort Exception */
61 	offset = ((((ulong) _vpabcall) - 0xc)-8) >> 2;
62 	op = ( 0xea << 24 ) | offset;
63 	*((ulong *) 0xc) = op;
64 
65 	/* Data Abort Exception */
66 	offset = ((((ulong) _vdabcall) - 0x10)-8) >> 2;
67 	op = ( 0xea << 24 ) | offset;
68 	*((ulong *) 0x10) = op;
69 
70 	/* IRQ Exception */
71 	offset = ((((ulong) _virqcall) - 0x18)-8) >> 2;
72 	op = ( 0xea << 24 ) | offset;
73 	*((ulong *) 0x18) = op;
74 
75 
76 }
77 
78 void
intrenable(uint addr,int bit,void (* r)(Ureg *,void *),void * a)79 intrenable(uint addr, int bit, void (*r)(Ureg*, void*), void* a)
80 {
81 	int i;
82 	USED(addr);
83 	for(i = 0; i < 16; i++)
84 		{
85 		if((bit & (1<<i)) == 0)
86 			continue;
87 		irqctlr.h[i].r = r;
88 		irqctlr.h[i].a = a;
89 		irqctlr.enabled |= (1<<i);
90 		if (i < 7)
91 			csrset(i);
92 		}
93 	return;
94 }
95 
96 int lucifer;					/* Global to store the last CSR (eric) */
97 
98 static void
interrupt(Ureg * ureg)99 interrupt(Ureg* ureg)
100 {
101 	int i, mask;
102 
103  		mask = *CSR;
104 		lucifer = mask;			/* eric */
105 		if(irqctlr.enabled == 0){
106 
107 			return;
108  			}
109 		for(i = 0; i < 16; i++)
110 			{
111 
112 			if((irqctlr.enabled & (1<<i)) == 0)
113 				continue;
114 			if(( mask & (1 << i)) == 0)
115 				continue;
116 			if (!irqctlr.h[i].r)
117 				continue;
118 			(irqctlr.h[i].r)(ureg, irqctlr.h[i].a);
119 			mask &= ~(1 << i);
120 			}
121 
122 		if ((mask) && (mask < 0x90))		/* ignore non-maskable interrupts */
123 			{
124 			print("unknown or unhandled interrupt\n");
125 			panic("unknown or unhandled interrupt: mask=%ux",mask);
126 			}
127 
128 }
129 
130 static void
dumpregs(Ureg * ureg)131 dumpregs(Ureg* ureg)
132 {
133 	print("PSR %8.8uX type %2.2uX PC %8.8uX LINK %8.8uX\n",
134 		ureg->psr, ureg->type, ureg->pc, ureg->link);
135 	print("R14 %8.8uX R13 %8.8uX R12 %8.8uX R11 %8.8uX R10 %8.8uX\n",
136 		ureg->r14, ureg->r13, ureg->r12, ureg->r11, ureg->r10);
137 	print("R9  %8.8uX R8  %8.8uX R7  %8.8uX R6  %8.8uX R5  %8.8uX\n",
138 		ureg->r9, ureg->r8, ureg->r7, ureg->r6, ureg->r5);
139 	print("R4  %8.8uX R3  %8.8uX R2  %8.8uX R1  %8.8uX R0  %8.8uX\n",
140 		ureg->r4, ureg->r3, ureg->r2, ureg->r1, ureg->r0);
141 	print("Last Interrupt's CSR: %8.8uX\n",lucifer);
142 	print("CPSR %8.8uX SPSR %8.8uX\n", cpsrr(), spsrr());
143 }
144 
145 void
dumpstack(void)146 dumpstack(void)
147 {
148 }
149 
150 void
exception(Ureg * ureg)151 exception(Ureg* ureg)
152 {
153 	static Ureg old_ureg;
154 	uint far =0;
155 	uint fsr =0;
156 
157 	static lasttype = 0;
158 
159 	LOWBAT;
160 
161 	USED(far, fsr);
162 
163 	lasttype = ureg->type;
164 
165 	/*
166 	 * All interrupts/exceptions should be resumed at ureg->pc-4,
167 	 * except for Data Abort which resumes at ureg->pc-8.
168 	 */
169 
170 	if(ureg->type == (PsrMabt+1))
171 		ureg->pc -= 8;
172 	else
173 		ureg->pc -= 4;
174 
175 	switch(ureg->type){
176 
177 	case PsrMfiq:				/* (Fast) */
178 		print("Fast\n");
179 		print("We should never be here\n");
180 		while(1);
181 
182 	case PsrMirq:				/* Interrupt Request */
183 		interrupt(ureg);
184 		break;
185 
186 	case PsrMund:				/* Undefined instruction */
187 		print("Undefined instruction\n");
188 	case PsrMsvc:				/* Jump through 0, SWI or reserved trap */
189 		print("SWI/SVC trap\n");
190 	case PsrMabt:				/* Prefetch abort */
191 		print("Prefetch Abort\n");
192 	case PsrMabt+1:				/* Data abort */
193 		print("Data Abort\n");
194 
195 
196 	default:
197 		dumpregs(ureg);
198 		/* panic("exception %uX\n", ureg->type); */
199 		break;
200 	}
201 
202 	LOWBAT;				/* Low bat off after interrupt */
203 
204 	splhi();
205 
206 }
207