source: mainline/kernel/arch/ia64/src/interrupt.c@ b2fb47f

lfn serial ticket/834-toolchain-update topic/msim-upgrade topic/simplify-dev-export
Last change on this file since b2fb47f was 7e752b2, checked in by Martin Decky <martin@…>, 15 years ago
  • correct printf() formatting strings and corresponding arguments
  • minor cstyle changes and other small fixes
  • Property mode set to 100644
File size: 7.5 KB
Line 
1/*
2 * Copyright (c) 2005 Jakub Jermar
3 * Copyright (c) 2005 Jakub Vana
4 * All rights reserved.
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
8 * are met:
9 *
10 * - Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * - Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
15 * - The name of the author may not be used to endorse or promote products
16 * derived from this software without specific prior written permission.
17 *
18 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
19 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
20 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
21 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
22 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
23 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
27 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 */
29
30/** @addtogroup ia64interrupt
31 * @{
32 */
33/** @file
34 */
35
36#include <arch/interrupt.h>
37#include <interrupt.h>
38#include <ddi/irq.h>
39#include <panic.h>
40#include <print.h>
41#include <debug.h>
42#include <console/console.h>
43#include <typedefs.h>
44#include <arch/asm.h>
45#include <arch/barrier.h>
46#include <arch/register.h>
47#include <arch.h>
48#include <syscall/syscall.h>
49#include <print.h>
50#include <proc/scheduler.h>
51#include <ipc/sysipc.h>
52#include <ipc/irq.h>
53#include <ipc/ipc.h>
54#include <synch/spinlock.h>
55#include <mm/tlb.h>
56#include <symtab.h>
57#include <putchar.h>
58
59#define VECTORS_64_BUNDLE 20
60#define VECTORS_16_BUNDLE 48
61#define VECTORS_16_BUNDLE_START 0x5000
62
63#define VECTOR_MAX 0x7f00
64
65#define BUNDLE_SIZE 16
66
67static const char *vector_names_64_bundle[VECTORS_64_BUNDLE] = {
68 "VHPT Translation vector",
69 "Instruction TLB vector",
70 "Data TLB vector",
71 "Alternate Instruction TLB vector",
72 "Alternate Data TLB vector",
73 "Data Nested TLB vector",
74 "Instruction Key Miss vector",
75 "Data Key Miss vector",
76 "Dirty-Bit vector",
77 "Instruction Access-Bit vector",
78 "Data Access-Bit vector"
79 "Break Instruction vector",
80 "External Interrupt vector"
81 "Reserved",
82 "Reserved",
83 "Reserved",
84 "Reserved",
85 "Reserved",
86 "Reserved",
87 "Reserved"
88};
89
90static const char *vector_names_16_bundle[VECTORS_16_BUNDLE] = {
91 "Page Not Present vector",
92 "Key Permission vector",
93 "Instruction Access rights vector",
94 "Data Access Rights vector",
95 "General Exception vector",
96 "Disabled FP-Register vector",
97 "NaT Consumption vector",
98 "Speculation vector",
99 "Reserved",
100 "Debug vector",
101 "Unaligned Reference vector",
102 "Unsupported Data Reference vector",
103 "Floating-point Fault vector",
104 "Floating-point Trap vector",
105 "Lower-Privilege Transfer Trap vector",
106 "Taken Branch Trap vector",
107 "Single Step Trap vector",
108 "Reserved",
109 "Reserved",
110 "Reserved",
111 "Reserved",
112 "Reserved",
113 "Reserved",
114 "Reserved",
115 "Reserved",
116 "IA-32 Exception vector",
117 "IA-32 Intercept vector",
118 "IA-32 Interrupt vector",
119 "Reserved",
120 "Reserved",
121 "Reserved"
122};
123
124static const char *vector_to_string(uint16_t vector)
125{
126 ASSERT(vector <= VECTOR_MAX);
127
128 if (vector >= VECTORS_16_BUNDLE_START)
129 return vector_names_16_bundle[(vector -
130 VECTORS_16_BUNDLE_START) / (16 * BUNDLE_SIZE)];
131 else
132 return vector_names_64_bundle[vector / (64 * BUNDLE_SIZE)];
133}
134
135void istate_decode(istate_t *istate)
136{
137 printf("ar.bsp=%p\tar.bspstore=%p\n",
138 (void *) istate->ar_bsp, (void *) istate->ar_bspstore);
139 printf("ar.rnat=%#0" PRIx64 "\tar.rsc=%#0" PRIx64 "\n",
140 istate->ar_rnat, istate->ar_rsc);
141 printf("ar.ifs=%#0" PRIx64 "\tar.pfs=%#0" PRIx64 "\n",
142 istate->ar_ifs, istate->ar_pfs);
143 printf("cr.isr=%#0" PRIx64 "\tcr.ipsr=%#0" PRIx64 "\n",
144 istate->cr_isr.value, istate->cr_ipsr.value);
145
146 printf("cr.iip=%#0" PRIx64 ", #%u\t(%s)\n",
147 istate->cr_iip, istate->cr_isr.ei,
148 symtab_fmt_name_lookup(istate->cr_iip));
149 printf("cr.iipa=%#0" PRIx64 "\t(%s)\n", istate->cr_iipa,
150 symtab_fmt_name_lookup(istate->cr_iipa));
151 printf("cr.ifa=%#0" PRIx64 "\t(%s)\n", istate->cr_ifa,
152 symtab_fmt_name_lookup(istate->cr_ifa));
153}
154
155void general_exception(uint64_t vector, istate_t *istate)
156{
157 const char *desc;
158
159 switch (istate->cr_isr.ge_code) {
160 case GE_ILLEGALOP:
161 desc = "Illegal Operation fault";
162 break;
163 case GE_PRIVOP:
164 desc = "Privileged Operation fault";
165 break;
166 case GE_PRIVREG:
167 desc = "Privileged Register fault";
168 break;
169 case GE_RESREGFLD:
170 desc = "Reserved Register/Field fault";
171 break;
172 case GE_DISBLDISTRAN:
173 desc = "Disabled Instruction Set Transition fault";
174 break;
175 case GE_ILLEGALDEP:
176 desc = "Illegal Dependency fault";
177 break;
178 default:
179 desc = "unknown";
180 break;
181 }
182
183 fault_if_from_uspace(istate, "General Exception (%s).", desc);
184 panic_badtrap(istate, vector, "General Exception (%s).", desc);
185}
186
187void disabled_fp_register(uint64_t vector, istate_t *istate)
188{
189#ifdef CONFIG_FPU_LAZY
190 scheduler_fpu_lazy_request();
191#else
192 fault_if_from_uspace(istate, "Interruption: %#hx (%s).",
193 (uint16_t) vector, vector_to_string(vector));
194 panic_badtrap(istate, vector, "Interruption: %#hx (%s).",
195 (uint16_t) vector, vector_to_string(vector));
196#endif
197}
198
199void nop_handler(uint64_t vector, istate_t *istate)
200{
201}
202
203/** Handle syscall. */
204int break_instruction(uint64_t vector, istate_t *istate)
205{
206 /*
207 * Move to next instruction after BREAK.
208 */
209 if (istate->cr_ipsr.ri == 2) {
210 istate->cr_ipsr.ri = 0;
211 istate->cr_iip += 16;
212 } else {
213 istate->cr_ipsr.ri++;
214 }
215
216 return syscall_handler(istate->in0, istate->in1, istate->in2,
217 istate->in3, istate->in4, istate->in5, istate->in6);
218}
219
220void universal_handler(uint64_t vector, istate_t *istate)
221{
222 fault_if_from_uspace(istate, "Interruption: %#hx (%s).",
223 (uint16_t) vector, vector_to_string(vector));
224 panic_badtrap(istate, vector, "Interruption: %#hx (%s).",
225 (uint16_t) vector, vector_to_string(vector));
226}
227
228static void end_of_local_irq(void)
229{
230 asm volatile (
231 "mov cr.eoi=r0;;"
232 );
233}
234
235void external_interrupt(uint64_t vector, istate_t *istate)
236{
237 cr_ivr_t ivr;
238
239 ivr.value = ivr_read();
240 srlz_d();
241
242 irq_t *irq;
243
244 switch (ivr.vector) {
245 case INTERRUPT_SPURIOUS:
246#ifdef CONFIG_DEBUG
247 printf("cpu%d: spurious interrupt\n", CPU->id);
248#endif
249 break;
250
251#ifdef CONFIG_SMP
252 case VECTOR_TLB_SHOOTDOWN_IPI:
253 tlb_shootdown_ipi_recv();
254 end_of_local_irq();
255 break;
256#endif
257
258 case INTERRUPT_TIMER:
259 irq = irq_dispatch_and_lock(ivr.vector);
260 if (irq) {
261 irq->handler(irq);
262 irq_spinlock_unlock(&irq->lock, false);
263 } else {
264 panic("Unhandled Internal Timer Interrupt (%d).",
265 ivr.vector);
266 }
267 break;
268 default:
269 irq = irq_dispatch_and_lock(ivr.vector);
270 if (irq) {
271 /*
272 * The IRQ handler was found.
273 */
274 if (irq->preack) {
275 /* Send EOI before processing the interrupt */
276 end_of_local_irq();
277 }
278 irq->handler(irq);
279 if (!irq->preack)
280 end_of_local_irq();
281 irq_spinlock_unlock(&irq->lock, false);
282 } else {
283 /*
284 * Unhandled interrupt.
285 */
286 end_of_local_irq();
287#ifdef CONFIG_DEBUG
288 printf("\nUnhandled External Interrupt Vector %d\n",
289 ivr.vector);
290#endif
291 }
292 break;
293 }
294}
295
296void trap_virtual_enable_irqs(uint16_t irqmask)
297{
298}
299
300/** @}
301 */
Note: See TracBrowser for help on using the repository browser.