xref: /openbmc/linux/arch/ia64/kernel/traps.c (revision 174cd4b1)
1 /*
2  * Architecture-specific trap handling.
3  *
4  * Copyright (C) 1998-2003 Hewlett-Packard Co
5  *	David Mosberger-Tang <davidm@hpl.hp.com>
6  *
7  * 05/12/00 grao <goutham.rao@intel.com> : added isr in siginfo for SIGFPE
8  */
9 
10 #include <linux/kernel.h>
11 #include <linux/init.h>
12 #include <linux/sched/signal.h>
13 #include <linux/tty.h>
14 #include <linux/vt_kern.h>		/* For unblank_screen() */
15 #include <linux/export.h>
16 #include <linux/extable.h>
17 #include <linux/hardirq.h>
18 #include <linux/kprobes.h>
19 #include <linux/delay.h>		/* for ssleep() */
20 #include <linux/kdebug.h>
21 #include <linux/uaccess.h>
22 
23 #include <asm/fpswa.h>
24 #include <asm/intrinsics.h>
25 #include <asm/processor.h>
26 #include <asm/exception.h>
27 #include <asm/setup.h>
28 
29 fpswa_interface_t *fpswa_interface;
30 EXPORT_SYMBOL(fpswa_interface);
31 
32 void __init
33 trap_init (void)
34 {
35 	if (ia64_boot_param->fpswa)
36 		/* FPSWA fixup: make the interface pointer a kernel virtual address: */
37 		fpswa_interface = __va(ia64_boot_param->fpswa);
38 }
39 
40 int
41 die (const char *str, struct pt_regs *regs, long err)
42 {
43 	static struct {
44 		spinlock_t lock;
45 		u32 lock_owner;
46 		int lock_owner_depth;
47 	} die = {
48 		.lock =	__SPIN_LOCK_UNLOCKED(die.lock),
49 		.lock_owner = -1,
50 		.lock_owner_depth = 0
51 	};
52 	static int die_counter;
53 	int cpu = get_cpu();
54 
55 	if (die.lock_owner != cpu) {
56 		console_verbose();
57 		spin_lock_irq(&die.lock);
58 		die.lock_owner = cpu;
59 		die.lock_owner_depth = 0;
60 		bust_spinlocks(1);
61 	}
62 	put_cpu();
63 
64 	if (++die.lock_owner_depth < 3) {
65 		printk("%s[%d]: %s %ld [%d]\n",
66 		current->comm, task_pid_nr(current), str, err, ++die_counter);
67 		if (notify_die(DIE_OOPS, str, regs, err, 255, SIGSEGV)
68 	            != NOTIFY_STOP)
69 			show_regs(regs);
70 		else
71 			regs = NULL;
72   	} else
73 		printk(KERN_ERR "Recursive die() failure, output suppressed\n");
74 
75 	bust_spinlocks(0);
76 	die.lock_owner = -1;
77 	add_taint(TAINT_DIE, LOCKDEP_NOW_UNRELIABLE);
78 	spin_unlock_irq(&die.lock);
79 
80 	if (!regs)
81 		return 1;
82 
83 	if (panic_on_oops)
84 		panic("Fatal exception");
85 
86   	do_exit(SIGSEGV);
87 	return 0;
88 }
89 
90 int
91 die_if_kernel (char *str, struct pt_regs *regs, long err)
92 {
93 	if (!user_mode(regs))
94 		return die(str, regs, err);
95 	return 0;
96 }
97 
98 void
99 __kprobes ia64_bad_break (unsigned long break_num, struct pt_regs *regs)
100 {
101 	siginfo_t siginfo;
102 	int sig, code;
103 
104 	/* SIGILL, SIGFPE, SIGSEGV, and SIGBUS want these field initialized: */
105 	siginfo.si_addr = (void __user *) (regs->cr_iip + ia64_psr(regs)->ri);
106 	siginfo.si_imm = break_num;
107 	siginfo.si_flags = 0;		/* clear __ISR_VALID */
108 	siginfo.si_isr = 0;
109 
110 	switch (break_num) {
111 	      case 0: /* unknown error (used by GCC for __builtin_abort()) */
112 		if (notify_die(DIE_BREAK, "break 0", regs, break_num, TRAP_BRKPT, SIGTRAP)
113 			       	== NOTIFY_STOP)
114 			return;
115 		if (die_if_kernel("bugcheck!", regs, break_num))
116 			return;
117 		sig = SIGILL; code = ILL_ILLOPC;
118 		break;
119 
120 	      case 1: /* integer divide by zero */
121 		sig = SIGFPE; code = FPE_INTDIV;
122 		break;
123 
124 	      case 2: /* integer overflow */
125 		sig = SIGFPE; code = FPE_INTOVF;
126 		break;
127 
128 	      case 3: /* range check/bounds check */
129 		sig = SIGFPE; code = FPE_FLTSUB;
130 		break;
131 
132 	      case 4: /* null pointer dereference */
133 		sig = SIGSEGV; code = SEGV_MAPERR;
134 		break;
135 
136 	      case 5: /* misaligned data */
137 		sig = SIGSEGV; code = BUS_ADRALN;
138 		break;
139 
140 	      case 6: /* decimal overflow */
141 		sig = SIGFPE; code = __FPE_DECOVF;
142 		break;
143 
144 	      case 7: /* decimal divide by zero */
145 		sig = SIGFPE; code = __FPE_DECDIV;
146 		break;
147 
148 	      case 8: /* packed decimal error */
149 		sig = SIGFPE; code = __FPE_DECERR;
150 		break;
151 
152 	      case 9: /* invalid ASCII digit */
153 		sig = SIGFPE; code = __FPE_INVASC;
154 		break;
155 
156 	      case 10: /* invalid decimal digit */
157 		sig = SIGFPE; code = __FPE_INVDEC;
158 		break;
159 
160 	      case 11: /* paragraph stack overflow */
161 		sig = SIGSEGV; code = __SEGV_PSTKOVF;
162 		break;
163 
164 	      case 0x3f000 ... 0x3ffff:	/* bundle-update in progress */
165 		sig = SIGILL; code = __ILL_BNDMOD;
166 		break;
167 
168 	      default:
169 		if ((break_num < 0x40000 || break_num > 0x100000)
170 		    && die_if_kernel("Bad break", regs, break_num))
171 			return;
172 
173 		if (break_num < 0x80000) {
174 			sig = SIGILL; code = __ILL_BREAK;
175 		} else {
176 			if (notify_die(DIE_BREAK, "bad break", regs, break_num, TRAP_BRKPT, SIGTRAP)
177 					== NOTIFY_STOP)
178 				return;
179 			sig = SIGTRAP; code = TRAP_BRKPT;
180 		}
181 	}
182 	siginfo.si_signo = sig;
183 	siginfo.si_errno = 0;
184 	siginfo.si_code = code;
185 	force_sig_info(sig, &siginfo, current);
186 }
187 
188 /*
189  * disabled_fph_fault() is called when a user-level process attempts to access f32..f127
190  * and it doesn't own the fp-high register partition.  When this happens, we save the
191  * current fph partition in the task_struct of the fpu-owner (if necessary) and then load
192  * the fp-high partition of the current task (if necessary).  Note that the kernel has
193  * access to fph by the time we get here, as the IVT's "Disabled FP-Register" handler takes
194  * care of clearing psr.dfh.
195  */
196 static inline void
197 disabled_fph_fault (struct pt_regs *regs)
198 {
199 	struct ia64_psr *psr = ia64_psr(regs);
200 
201 	/* first, grant user-level access to fph partition: */
202 	psr->dfh = 0;
203 
204 	/*
205 	 * Make sure that no other task gets in on this processor
206 	 * while we're claiming the FPU
207 	 */
208 	preempt_disable();
209 #ifndef CONFIG_SMP
210 	{
211 		struct task_struct *fpu_owner
212 			= (struct task_struct *)ia64_get_kr(IA64_KR_FPU_OWNER);
213 
214 		if (ia64_is_local_fpu_owner(current)) {
215 			preempt_enable_no_resched();
216 			return;
217 		}
218 
219 		if (fpu_owner)
220 			ia64_flush_fph(fpu_owner);
221 	}
222 #endif /* !CONFIG_SMP */
223 	ia64_set_local_fpu_owner(current);
224 	if ((current->thread.flags & IA64_THREAD_FPH_VALID) != 0) {
225 		__ia64_load_fpu(current->thread.fph);
226 		psr->mfh = 0;
227 	} else {
228 		__ia64_init_fpu();
229 		/*
230 		 * Set mfh because the state in thread.fph does not match the state in
231 		 * the fph partition.
232 		 */
233 		psr->mfh = 1;
234 	}
235 	preempt_enable_no_resched();
236 }
237 
238 static inline int
239 fp_emulate (int fp_fault, void *bundle, long *ipsr, long *fpsr, long *isr, long *pr, long *ifs,
240 	    struct pt_regs *regs)
241 {
242 	fp_state_t fp_state;
243 	fpswa_ret_t ret;
244 
245 	if (!fpswa_interface)
246 		return -1;
247 
248 	memset(&fp_state, 0, sizeof(fp_state_t));
249 
250 	/*
251 	 * compute fp_state.  only FP registers f6 - f11 are used by the
252 	 * kernel, so set those bits in the mask and set the low volatile
253 	 * pointer to point to these registers.
254 	 */
255 	fp_state.bitmask_low64 = 0xfc0;  /* bit6..bit11 */
256 
257 	fp_state.fp_state_low_volatile = (fp_state_low_volatile_t *) &regs->f6;
258 	/*
259 	 * unsigned long (*EFI_FPSWA) (
260 	 *      unsigned long    trap_type,
261 	 *	void             *Bundle,
262 	 *	unsigned long    *pipsr,
263 	 *	unsigned long    *pfsr,
264 	 *	unsigned long    *pisr,
265 	 *	unsigned long    *ppreds,
266 	 *	unsigned long    *pifs,
267 	 *	void             *fp_state);
268 	 */
269 	ret = (*fpswa_interface->fpswa)((unsigned long) fp_fault, bundle,
270 					(unsigned long *) ipsr, (unsigned long *) fpsr,
271 					(unsigned long *) isr, (unsigned long *) pr,
272 					(unsigned long *) ifs, &fp_state);
273 
274 	return ret.status;
275 }
276 
277 struct fpu_swa_msg {
278 	unsigned long count;
279 	unsigned long time;
280 };
281 static DEFINE_PER_CPU(struct fpu_swa_msg, cpulast);
282 DECLARE_PER_CPU(struct fpu_swa_msg, cpulast);
283 static struct fpu_swa_msg last __cacheline_aligned;
284 
285 
286 /*
287  * Handle floating-point assist faults and traps.
288  */
289 static int
290 handle_fpu_swa (int fp_fault, struct pt_regs *regs, unsigned long isr)
291 {
292 	long exception, bundle[2];
293 	unsigned long fault_ip;
294 	struct siginfo siginfo;
295 
296 	fault_ip = regs->cr_iip;
297 	if (!fp_fault && (ia64_psr(regs)->ri == 0))
298 		fault_ip -= 16;
299 	if (copy_from_user(bundle, (void __user *) fault_ip, sizeof(bundle)))
300 		return -1;
301 
302 	if (!(current->thread.flags & IA64_THREAD_FPEMU_NOPRINT))  {
303 		unsigned long count, current_jiffies = jiffies;
304 		struct fpu_swa_msg *cp = this_cpu_ptr(&cpulast);
305 
306 		if (unlikely(current_jiffies > cp->time))
307 			cp->count = 0;
308 		if (unlikely(cp->count < 5)) {
309 			cp->count++;
310 			cp->time = current_jiffies + 5 * HZ;
311 
312 			/* minimize races by grabbing a copy of count BEFORE checking last.time. */
313 			count = last.count;
314 			barrier();
315 
316 			/*
317 			 * Lower 4 bits are used as a count. Upper bits are a sequence
318 			 * number that is updated when count is reset. The cmpxchg will
319 			 * fail is seqno has changed. This minimizes mutiple cpus
320 			 * resetting the count.
321 			 */
322 			if (current_jiffies > last.time)
323 				(void) cmpxchg_acq(&last.count, count, 16 + (count & ~15));
324 
325 			/* used fetchadd to atomically update the count */
326 			if ((last.count & 15) < 5 && (ia64_fetchadd(1, &last.count, acq) & 15) < 5) {
327 				last.time = current_jiffies + 5 * HZ;
328 				printk(KERN_WARNING
329 		       			"%s(%d): floating-point assist fault at ip %016lx, isr %016lx\n",
330 		       			current->comm, task_pid_nr(current), regs->cr_iip + ia64_psr(regs)->ri, isr);
331 			}
332 		}
333 	}
334 
335 	exception = fp_emulate(fp_fault, bundle, &regs->cr_ipsr, &regs->ar_fpsr, &isr, &regs->pr,
336 			       &regs->cr_ifs, regs);
337 	if (fp_fault) {
338 		if (exception == 0) {
339 			/* emulation was successful */
340 			ia64_increment_ip(regs);
341 		} else if (exception == -1) {
342 			printk(KERN_ERR "handle_fpu_swa: fp_emulate() returned -1\n");
343 			return -1;
344 		} else {
345 			/* is next instruction a trap? */
346 			if (exception & 2) {
347 				ia64_increment_ip(regs);
348 			}
349 			siginfo.si_signo = SIGFPE;
350 			siginfo.si_errno = 0;
351 			siginfo.si_code = __SI_FAULT;	/* default code */
352 			siginfo.si_addr = (void __user *) (regs->cr_iip + ia64_psr(regs)->ri);
353 			if (isr & 0x11) {
354 				siginfo.si_code = FPE_FLTINV;
355 			} else if (isr & 0x22) {
356 				/* denormal operand gets the same si_code as underflow
357 				* see arch/i386/kernel/traps.c:math_error()  */
358 				siginfo.si_code = FPE_FLTUND;
359 			} else if (isr & 0x44) {
360 				siginfo.si_code = FPE_FLTDIV;
361 			}
362 			siginfo.si_isr = isr;
363 			siginfo.si_flags = __ISR_VALID;
364 			siginfo.si_imm = 0;
365 			force_sig_info(SIGFPE, &siginfo, current);
366 		}
367 	} else {
368 		if (exception == -1) {
369 			printk(KERN_ERR "handle_fpu_swa: fp_emulate() returned -1\n");
370 			return -1;
371 		} else if (exception != 0) {
372 			/* raise exception */
373 			siginfo.si_signo = SIGFPE;
374 			siginfo.si_errno = 0;
375 			siginfo.si_code = __SI_FAULT;	/* default code */
376 			siginfo.si_addr = (void __user *) (regs->cr_iip + ia64_psr(regs)->ri);
377 			if (isr & 0x880) {
378 				siginfo.si_code = FPE_FLTOVF;
379 			} else if (isr & 0x1100) {
380 				siginfo.si_code = FPE_FLTUND;
381 			} else if (isr & 0x2200) {
382 				siginfo.si_code = FPE_FLTRES;
383 			}
384 			siginfo.si_isr = isr;
385 			siginfo.si_flags = __ISR_VALID;
386 			siginfo.si_imm = 0;
387 			force_sig_info(SIGFPE, &siginfo, current);
388 		}
389 	}
390 	return 0;
391 }
392 
393 struct illegal_op_return {
394 	unsigned long fkt, arg1, arg2, arg3;
395 };
396 
397 struct illegal_op_return
398 ia64_illegal_op_fault (unsigned long ec, long arg1, long arg2, long arg3,
399 		       long arg4, long arg5, long arg6, long arg7,
400 		       struct pt_regs regs)
401 {
402 	struct illegal_op_return rv;
403 	struct siginfo si;
404 	char buf[128];
405 
406 #ifdef CONFIG_IA64_BRL_EMU
407 	{
408 		extern struct illegal_op_return ia64_emulate_brl (struct pt_regs *, unsigned long);
409 
410 		rv = ia64_emulate_brl(&regs, ec);
411 		if (rv.fkt != (unsigned long) -1)
412 			return rv;
413 	}
414 #endif
415 
416 	sprintf(buf, "IA-64 Illegal operation fault");
417 	rv.fkt = 0;
418 	if (die_if_kernel(buf, &regs, 0))
419 		return rv;
420 
421 	memset(&si, 0, sizeof(si));
422 	si.si_signo = SIGILL;
423 	si.si_code = ILL_ILLOPC;
424 	si.si_addr = (void __user *) (regs.cr_iip + ia64_psr(&regs)->ri);
425 	force_sig_info(SIGILL, &si, current);
426 	return rv;
427 }
428 
429 void __kprobes
430 ia64_fault (unsigned long vector, unsigned long isr, unsigned long ifa,
431 	    unsigned long iim, unsigned long itir, long arg5, long arg6,
432 	    long arg7, struct pt_regs regs)
433 {
434 	unsigned long code, error = isr, iip;
435 	struct siginfo siginfo;
436 	char buf[128];
437 	int result, sig;
438 	static const char *reason[] = {
439 		"IA-64 Illegal Operation fault",
440 		"IA-64 Privileged Operation fault",
441 		"IA-64 Privileged Register fault",
442 		"IA-64 Reserved Register/Field fault",
443 		"Disabled Instruction Set Transition fault",
444 		"Unknown fault 5", "Unknown fault 6", "Unknown fault 7", "Illegal Hazard fault",
445 		"Unknown fault 9", "Unknown fault 10", "Unknown fault 11", "Unknown fault 12",
446 		"Unknown fault 13", "Unknown fault 14", "Unknown fault 15"
447 	};
448 
449 	if ((isr & IA64_ISR_NA) && ((isr & IA64_ISR_CODE_MASK) == IA64_ISR_CODE_LFETCH)) {
450 		/*
451 		 * This fault was due to lfetch.fault, set "ed" bit in the psr to cancel
452 		 * the lfetch.
453 		 */
454 		ia64_psr(&regs)->ed = 1;
455 		return;
456 	}
457 
458 	iip = regs.cr_iip + ia64_psr(&regs)->ri;
459 
460 	switch (vector) {
461 	      case 24: /* General Exception */
462 		code = (isr >> 4) & 0xf;
463 		sprintf(buf, "General Exception: %s%s", reason[code],
464 			(code == 3) ? ((isr & (1UL << 37))
465 				       ? " (RSE access)" : " (data access)") : "");
466 		if (code == 8) {
467 # ifdef CONFIG_IA64_PRINT_HAZARDS
468 			printk("%s[%d]: possible hazard @ ip=%016lx (pr = %016lx)\n",
469 			       current->comm, task_pid_nr(current),
470 			       regs.cr_iip + ia64_psr(&regs)->ri, regs.pr);
471 # endif
472 			return;
473 		}
474 		break;
475 
476 	      case 25: /* Disabled FP-Register */
477 		if (isr & 2) {
478 			disabled_fph_fault(&regs);
479 			return;
480 		}
481 		sprintf(buf, "Disabled FPL fault---not supposed to happen!");
482 		break;
483 
484 	      case 26: /* NaT Consumption */
485 		if (user_mode(&regs)) {
486 			void __user *addr;
487 
488 			if (((isr >> 4) & 0xf) == 2) {
489 				/* NaT page consumption */
490 				sig = SIGSEGV;
491 				code = SEGV_ACCERR;
492 				addr = (void __user *) ifa;
493 			} else {
494 				/* register NaT consumption */
495 				sig = SIGILL;
496 				code = ILL_ILLOPN;
497 				addr = (void __user *) (regs.cr_iip
498 							+ ia64_psr(&regs)->ri);
499 			}
500 			siginfo.si_signo = sig;
501 			siginfo.si_code = code;
502 			siginfo.si_errno = 0;
503 			siginfo.si_addr = addr;
504 			siginfo.si_imm = vector;
505 			siginfo.si_flags = __ISR_VALID;
506 			siginfo.si_isr = isr;
507 			force_sig_info(sig, &siginfo, current);
508 			return;
509 		} else if (ia64_done_with_exception(&regs))
510 			return;
511 		sprintf(buf, "NaT consumption");
512 		break;
513 
514 	      case 31: /* Unsupported Data Reference */
515 		if (user_mode(&regs)) {
516 			siginfo.si_signo = SIGILL;
517 			siginfo.si_code = ILL_ILLOPN;
518 			siginfo.si_errno = 0;
519 			siginfo.si_addr = (void __user *) iip;
520 			siginfo.si_imm = vector;
521 			siginfo.si_flags = __ISR_VALID;
522 			siginfo.si_isr = isr;
523 			force_sig_info(SIGILL, &siginfo, current);
524 			return;
525 		}
526 		sprintf(buf, "Unsupported data reference");
527 		break;
528 
529 	      case 29: /* Debug */
530 	      case 35: /* Taken Branch Trap */
531 	      case 36: /* Single Step Trap */
532 		if (fsys_mode(current, &regs)) {
533 			extern char __kernel_syscall_via_break[];
534 			/*
535 			 * Got a trap in fsys-mode: Taken Branch Trap
536 			 * and Single Step trap need special handling;
537 			 * Debug trap is ignored (we disable it here
538 			 * and re-enable it in the lower-privilege trap).
539 			 */
540 			if (unlikely(vector == 29)) {
541 				set_thread_flag(TIF_DB_DISABLED);
542 				ia64_psr(&regs)->db = 0;
543 				ia64_psr(&regs)->lp = 1;
544 				return;
545 			}
546 			/* re-do the system call via break 0x100000: */
547 			regs.cr_iip = (unsigned long) __kernel_syscall_via_break;
548 			ia64_psr(&regs)->ri = 0;
549 			ia64_psr(&regs)->cpl = 3;
550 			return;
551 		}
552 		switch (vector) {
553 		      default:
554 		      case 29:
555 			siginfo.si_code = TRAP_HWBKPT;
556 #ifdef CONFIG_ITANIUM
557 			/*
558 			 * Erratum 10 (IFA may contain incorrect address) now has
559 			 * "NoFix" status.  There are no plans for fixing this.
560 			 */
561 			if (ia64_psr(&regs)->is == 0)
562 			  ifa = regs.cr_iip;
563 #endif
564 			break;
565 		      case 35: siginfo.si_code = TRAP_BRANCH; ifa = 0; break;
566 		      case 36: siginfo.si_code = TRAP_TRACE; ifa = 0; break;
567 		}
568 		if (notify_die(DIE_FAULT, "ia64_fault", &regs, vector, siginfo.si_code, SIGTRAP)
569 			       	== NOTIFY_STOP)
570 			return;
571 		siginfo.si_signo = SIGTRAP;
572 		siginfo.si_errno = 0;
573 		siginfo.si_addr  = (void __user *) ifa;
574 		siginfo.si_imm   = 0;
575 		siginfo.si_flags = __ISR_VALID;
576 		siginfo.si_isr   = isr;
577 		force_sig_info(SIGTRAP, &siginfo, current);
578 		return;
579 
580 	      case 32: /* fp fault */
581 	      case 33: /* fp trap */
582 		result = handle_fpu_swa((vector == 32) ? 1 : 0, &regs, isr);
583 		if ((result < 0) || (current->thread.flags & IA64_THREAD_FPEMU_SIGFPE)) {
584 			siginfo.si_signo = SIGFPE;
585 			siginfo.si_errno = 0;
586 			siginfo.si_code = FPE_FLTINV;
587 			siginfo.si_addr = (void __user *) iip;
588 			siginfo.si_flags = __ISR_VALID;
589 			siginfo.si_isr = isr;
590 			siginfo.si_imm = 0;
591 			force_sig_info(SIGFPE, &siginfo, current);
592 		}
593 		return;
594 
595 	      case 34:
596 		if (isr & 0x2) {
597 			/* Lower-Privilege Transfer Trap */
598 
599 			/* If we disabled debug traps during an fsyscall,
600 			 * re-enable them here.
601 			 */
602 			if (test_thread_flag(TIF_DB_DISABLED)) {
603 				clear_thread_flag(TIF_DB_DISABLED);
604 				ia64_psr(&regs)->db = 1;
605 			}
606 
607 			/*
608 			 * Just clear PSR.lp and then return immediately:
609 			 * all the interesting work (e.g., signal delivery)
610 			 * is done in the kernel exit path.
611 			 */
612 			ia64_psr(&regs)->lp = 0;
613 			return;
614 		} else {
615 			/* Unimplemented Instr. Address Trap */
616 			if (user_mode(&regs)) {
617 				siginfo.si_signo = SIGILL;
618 				siginfo.si_code = ILL_BADIADDR;
619 				siginfo.si_errno = 0;
620 				siginfo.si_flags = 0;
621 				siginfo.si_isr = 0;
622 				siginfo.si_imm = 0;
623 				siginfo.si_addr = (void __user *) iip;
624 				force_sig_info(SIGILL, &siginfo, current);
625 				return;
626 			}
627 			sprintf(buf, "Unimplemented Instruction Address fault");
628 		}
629 		break;
630 
631 	      case 45:
632 		printk(KERN_ERR "Unexpected IA-32 exception (Trap 45)\n");
633 		printk(KERN_ERR "  iip - 0x%lx, ifa - 0x%lx, isr - 0x%lx\n",
634 		       iip, ifa, isr);
635 		force_sig(SIGSEGV, current);
636 		return;
637 
638 	      case 46:
639 		printk(KERN_ERR "Unexpected IA-32 intercept trap (Trap 46)\n");
640 		printk(KERN_ERR "  iip - 0x%lx, ifa - 0x%lx, isr - 0x%lx, iim - 0x%lx\n",
641 		       iip, ifa, isr, iim);
642 		force_sig(SIGSEGV, current);
643 		return;
644 
645 	      case 47:
646 		sprintf(buf, "IA-32 Interruption Fault (int 0x%lx)", isr >> 16);
647 		break;
648 
649 	      default:
650 		sprintf(buf, "Fault %lu", vector);
651 		break;
652 	}
653 	if (!die_if_kernel(buf, &regs, error))
654 		force_sig(SIGILL, current);
655 }
656