.. | .. |
---|
85 | 85 | if (panic_on_oops) |
---|
86 | 86 | panic("Fatal exception"); |
---|
87 | 87 | |
---|
88 | | - do_exit(SIGSEGV); |
---|
| 88 | + make_task_dead(SIGSEGV); |
---|
89 | 89 | return 0; |
---|
90 | 90 | } |
---|
91 | 91 | |
---|
.. | .. |
---|
100 | 100 | void |
---|
101 | 101 | __kprobes ia64_bad_break (unsigned long break_num, struct pt_regs *regs) |
---|
102 | 102 | { |
---|
103 | | - siginfo_t siginfo; |
---|
104 | 103 | int sig, code; |
---|
105 | | - |
---|
106 | | - /* SIGILL, SIGFPE, SIGSEGV, and SIGBUS want these field initialized: */ |
---|
107 | | - clear_siginfo(&siginfo); |
---|
108 | | - siginfo.si_addr = (void __user *) (regs->cr_iip + ia64_psr(regs)->ri); |
---|
109 | | - siginfo.si_imm = break_num; |
---|
110 | | - siginfo.si_flags = 0; /* clear __ISR_VALID */ |
---|
111 | | - siginfo.si_isr = 0; |
---|
112 | 104 | |
---|
113 | 105 | switch (break_num) { |
---|
114 | 106 | case 0: /* unknown error (used by GCC for __builtin_abort()) */ |
---|
.. | .. |
---|
182 | 174 | sig = SIGTRAP; code = TRAP_BRKPT; |
---|
183 | 175 | } |
---|
184 | 176 | } |
---|
185 | | - siginfo.si_signo = sig; |
---|
186 | | - siginfo.si_errno = 0; |
---|
187 | | - siginfo.si_code = code; |
---|
188 | | - force_sig_info(sig, &siginfo, current); |
---|
| 177 | + force_sig_fault(sig, code, |
---|
| 178 | + (void __user *) (regs->cr_iip + ia64_psr(regs)->ri), |
---|
| 179 | + break_num, 0 /* clear __ISR_VALID */, 0); |
---|
189 | 180 | } |
---|
190 | 181 | |
---|
191 | 182 | /* |
---|
.. | .. |
---|
344 | 335 | printk(KERN_ERR "handle_fpu_swa: fp_emulate() returned -1\n"); |
---|
345 | 336 | return -1; |
---|
346 | 337 | } else { |
---|
347 | | - struct siginfo siginfo; |
---|
348 | | - |
---|
349 | 338 | /* is next instruction a trap? */ |
---|
| 339 | + int si_code; |
---|
| 340 | + |
---|
350 | 341 | if (exception & 2) { |
---|
351 | 342 | ia64_increment_ip(regs); |
---|
352 | 343 | } |
---|
353 | | - clear_siginfo(&siginfo); |
---|
354 | | - siginfo.si_signo = SIGFPE; |
---|
355 | | - siginfo.si_errno = 0; |
---|
356 | | - siginfo.si_code = FPE_FLTUNK; /* default code */ |
---|
357 | | - siginfo.si_addr = (void __user *) (regs->cr_iip + ia64_psr(regs)->ri); |
---|
| 344 | + si_code = FPE_FLTUNK; /* default code */ |
---|
358 | 345 | if (isr & 0x11) { |
---|
359 | | - siginfo.si_code = FPE_FLTINV; |
---|
| 346 | + si_code = FPE_FLTINV; |
---|
360 | 347 | } else if (isr & 0x22) { |
---|
361 | 348 | /* denormal operand gets the same si_code as underflow |
---|
362 | 349 | * see arch/i386/kernel/traps.c:math_error() */ |
---|
363 | | - siginfo.si_code = FPE_FLTUND; |
---|
| 350 | + si_code = FPE_FLTUND; |
---|
364 | 351 | } else if (isr & 0x44) { |
---|
365 | | - siginfo.si_code = FPE_FLTDIV; |
---|
| 352 | + si_code = FPE_FLTDIV; |
---|
366 | 353 | } |
---|
367 | | - siginfo.si_isr = isr; |
---|
368 | | - siginfo.si_flags = __ISR_VALID; |
---|
369 | | - siginfo.si_imm = 0; |
---|
370 | | - force_sig_info(SIGFPE, &siginfo, current); |
---|
| 354 | + force_sig_fault(SIGFPE, si_code, |
---|
| 355 | + (void __user *) (regs->cr_iip + ia64_psr(regs)->ri), |
---|
| 356 | + 0, __ISR_VALID, isr); |
---|
371 | 357 | } |
---|
372 | 358 | } else { |
---|
373 | 359 | if (exception == -1) { |
---|
.. | .. |
---|
375 | 361 | return -1; |
---|
376 | 362 | } else if (exception != 0) { |
---|
377 | 363 | /* raise exception */ |
---|
378 | | - struct siginfo siginfo; |
---|
| 364 | + int si_code; |
---|
379 | 365 | |
---|
380 | | - clear_siginfo(&siginfo); |
---|
381 | | - siginfo.si_signo = SIGFPE; |
---|
382 | | - siginfo.si_errno = 0; |
---|
383 | | - siginfo.si_code = FPE_FLTUNK; /* default code */ |
---|
384 | | - siginfo.si_addr = (void __user *) (regs->cr_iip + ia64_psr(regs)->ri); |
---|
| 366 | + si_code = FPE_FLTUNK; /* default code */ |
---|
385 | 367 | if (isr & 0x880) { |
---|
386 | | - siginfo.si_code = FPE_FLTOVF; |
---|
| 368 | + si_code = FPE_FLTOVF; |
---|
387 | 369 | } else if (isr & 0x1100) { |
---|
388 | | - siginfo.si_code = FPE_FLTUND; |
---|
| 370 | + si_code = FPE_FLTUND; |
---|
389 | 371 | } else if (isr & 0x2200) { |
---|
390 | | - siginfo.si_code = FPE_FLTRES; |
---|
| 372 | + si_code = FPE_FLTRES; |
---|
391 | 373 | } |
---|
392 | | - siginfo.si_isr = isr; |
---|
393 | | - siginfo.si_flags = __ISR_VALID; |
---|
394 | | - siginfo.si_imm = 0; |
---|
395 | | - force_sig_info(SIGFPE, &siginfo, current); |
---|
| 374 | + force_sig_fault(SIGFPE, si_code, |
---|
| 375 | + (void __user *) (regs->cr_iip + ia64_psr(regs)->ri), |
---|
| 376 | + 0, __ISR_VALID, isr); |
---|
396 | 377 | } |
---|
397 | 378 | } |
---|
398 | 379 | return 0; |
---|
.. | .. |
---|
408 | 389 | struct pt_regs regs) |
---|
409 | 390 | { |
---|
410 | 391 | struct illegal_op_return rv; |
---|
411 | | - struct siginfo si; |
---|
412 | 392 | char buf[128]; |
---|
413 | 393 | |
---|
414 | 394 | #ifdef CONFIG_IA64_BRL_EMU |
---|
.. | .. |
---|
426 | 406 | if (die_if_kernel(buf, ®s, 0)) |
---|
427 | 407 | return rv; |
---|
428 | 408 | |
---|
429 | | - clear_siginfo(&si); |
---|
430 | | - si.si_signo = SIGILL; |
---|
431 | | - si.si_code = ILL_ILLOPC; |
---|
432 | | - si.si_addr = (void __user *) (regs.cr_iip + ia64_psr(®s)->ri); |
---|
433 | | - force_sig_info(SIGILL, &si, current); |
---|
| 409 | + force_sig_fault(SIGILL, ILL_ILLOPC, |
---|
| 410 | + (void __user *) (regs.cr_iip + ia64_psr(®s)->ri), |
---|
| 411 | + 0, 0, 0); |
---|
434 | 412 | return rv; |
---|
435 | 413 | } |
---|
436 | 414 | |
---|
.. | .. |
---|
441 | 419 | { |
---|
442 | 420 | unsigned long code, error = isr, iip; |
---|
443 | 421 | char buf[128]; |
---|
444 | | - int result, sig; |
---|
| 422 | + int result, sig, si_code; |
---|
445 | 423 | static const char *reason[] = { |
---|
446 | 424 | "IA-64 Illegal Operation fault", |
---|
447 | 425 | "IA-64 Privileged Operation fault", |
---|
.. | .. |
---|
490 | 468 | |
---|
491 | 469 | case 26: /* NaT Consumption */ |
---|
492 | 470 | if (user_mode(®s)) { |
---|
493 | | - struct siginfo siginfo; |
---|
494 | 471 | void __user *addr; |
---|
495 | 472 | |
---|
496 | 473 | if (((isr >> 4) & 0xf) == 2) { |
---|
.. | .. |
---|
505 | 482 | addr = (void __user *) (regs.cr_iip |
---|
506 | 483 | + ia64_psr(®s)->ri); |
---|
507 | 484 | } |
---|
508 | | - clear_siginfo(&siginfo); |
---|
509 | | - siginfo.si_signo = sig; |
---|
510 | | - siginfo.si_code = code; |
---|
511 | | - siginfo.si_errno = 0; |
---|
512 | | - siginfo.si_addr = addr; |
---|
513 | | - siginfo.si_imm = vector; |
---|
514 | | - siginfo.si_flags = __ISR_VALID; |
---|
515 | | - siginfo.si_isr = isr; |
---|
516 | | - force_sig_info(sig, &siginfo, current); |
---|
| 485 | + force_sig_fault(sig, code, addr, |
---|
| 486 | + vector, __ISR_VALID, isr); |
---|
517 | 487 | return; |
---|
518 | 488 | } else if (ia64_done_with_exception(®s)) |
---|
519 | 489 | return; |
---|
.. | .. |
---|
522 | 492 | |
---|
523 | 493 | case 31: /* Unsupported Data Reference */ |
---|
524 | 494 | if (user_mode(®s)) { |
---|
525 | | - struct siginfo siginfo; |
---|
526 | | - |
---|
527 | | - clear_siginfo(&siginfo); |
---|
528 | | - siginfo.si_signo = SIGILL; |
---|
529 | | - siginfo.si_code = ILL_ILLOPN; |
---|
530 | | - siginfo.si_errno = 0; |
---|
531 | | - siginfo.si_addr = (void __user *) iip; |
---|
532 | | - siginfo.si_imm = vector; |
---|
533 | | - siginfo.si_flags = __ISR_VALID; |
---|
534 | | - siginfo.si_isr = isr; |
---|
535 | | - force_sig_info(SIGILL, &siginfo, current); |
---|
| 495 | + force_sig_fault(SIGILL, ILL_ILLOPN, (void __user *) iip, |
---|
| 496 | + vector, __ISR_VALID, isr); |
---|
536 | 497 | return; |
---|
537 | 498 | } |
---|
538 | 499 | sprintf(buf, "Unsupported data reference"); |
---|
.. | .. |
---|
541 | 502 | case 29: /* Debug */ |
---|
542 | 503 | case 35: /* Taken Branch Trap */ |
---|
543 | 504 | case 36: /* Single Step Trap */ |
---|
544 | | - { |
---|
545 | | - struct siginfo siginfo; |
---|
546 | | - |
---|
547 | | - clear_siginfo(&siginfo); |
---|
548 | 505 | if (fsys_mode(current, ®s)) { |
---|
549 | 506 | extern char __kernel_syscall_via_break[]; |
---|
550 | 507 | /* |
---|
.. | .. |
---|
568 | 525 | switch (vector) { |
---|
569 | 526 | default: |
---|
570 | 527 | case 29: |
---|
571 | | - siginfo.si_code = TRAP_HWBKPT; |
---|
| 528 | + si_code = TRAP_HWBKPT; |
---|
572 | 529 | #ifdef CONFIG_ITANIUM |
---|
573 | 530 | /* |
---|
574 | 531 | * Erratum 10 (IFA may contain incorrect address) now has |
---|
.. | .. |
---|
578 | 535 | ifa = regs.cr_iip; |
---|
579 | 536 | #endif |
---|
580 | 537 | break; |
---|
581 | | - case 35: siginfo.si_code = TRAP_BRANCH; ifa = 0; break; |
---|
582 | | - case 36: siginfo.si_code = TRAP_TRACE; ifa = 0; break; |
---|
| 538 | + case 35: si_code = TRAP_BRANCH; ifa = 0; break; |
---|
| 539 | + case 36: si_code = TRAP_TRACE; ifa = 0; break; |
---|
583 | 540 | } |
---|
584 | | - if (notify_die(DIE_FAULT, "ia64_fault", ®s, vector, siginfo.si_code, SIGTRAP) |
---|
| 541 | + if (notify_die(DIE_FAULT, "ia64_fault", ®s, vector, si_code, SIGTRAP) |
---|
585 | 542 | == NOTIFY_STOP) |
---|
586 | 543 | return; |
---|
587 | | - siginfo.si_signo = SIGTRAP; |
---|
588 | | - siginfo.si_errno = 0; |
---|
589 | | - siginfo.si_addr = (void __user *) ifa; |
---|
590 | | - siginfo.si_imm = 0; |
---|
591 | | - siginfo.si_flags = __ISR_VALID; |
---|
592 | | - siginfo.si_isr = isr; |
---|
593 | | - force_sig_info(SIGTRAP, &siginfo, current); |
---|
| 544 | + force_sig_fault(SIGTRAP, si_code, (void __user *) ifa, |
---|
| 545 | + 0, __ISR_VALID, isr); |
---|
594 | 546 | return; |
---|
595 | | - } |
---|
596 | 547 | |
---|
597 | 548 | case 32: /* fp fault */ |
---|
598 | 549 | case 33: /* fp trap */ |
---|
599 | 550 | result = handle_fpu_swa((vector == 32) ? 1 : 0, ®s, isr); |
---|
600 | 551 | if ((result < 0) || (current->thread.flags & IA64_THREAD_FPEMU_SIGFPE)) { |
---|
601 | | - struct siginfo siginfo; |
---|
602 | | - |
---|
603 | | - clear_siginfo(&siginfo); |
---|
604 | | - siginfo.si_signo = SIGFPE; |
---|
605 | | - siginfo.si_errno = 0; |
---|
606 | | - siginfo.si_code = FPE_FLTINV; |
---|
607 | | - siginfo.si_addr = (void __user *) iip; |
---|
608 | | - siginfo.si_flags = __ISR_VALID; |
---|
609 | | - siginfo.si_isr = isr; |
---|
610 | | - siginfo.si_imm = 0; |
---|
611 | | - force_sig_info(SIGFPE, &siginfo, current); |
---|
| 552 | + force_sig_fault(SIGFPE, FPE_FLTINV, (void __user *) iip, |
---|
| 553 | + 0, __ISR_VALID, isr); |
---|
612 | 554 | } |
---|
613 | 555 | return; |
---|
614 | 556 | |
---|
.. | .. |
---|
634 | 576 | } else { |
---|
635 | 577 | /* Unimplemented Instr. Address Trap */ |
---|
636 | 578 | if (user_mode(®s)) { |
---|
637 | | - struct siginfo siginfo; |
---|
638 | | - |
---|
639 | | - clear_siginfo(&siginfo); |
---|
640 | | - siginfo.si_signo = SIGILL; |
---|
641 | | - siginfo.si_code = ILL_BADIADDR; |
---|
642 | | - siginfo.si_errno = 0; |
---|
643 | | - siginfo.si_flags = 0; |
---|
644 | | - siginfo.si_isr = 0; |
---|
645 | | - siginfo.si_imm = 0; |
---|
646 | | - siginfo.si_addr = (void __user *) iip; |
---|
647 | | - force_sig_info(SIGILL, &siginfo, current); |
---|
| 579 | + force_sig_fault(SIGILL, ILL_BADIADDR, |
---|
| 580 | + (void __user *) iip, |
---|
| 581 | + 0, 0, 0); |
---|
648 | 582 | return; |
---|
649 | 583 | } |
---|
650 | 584 | sprintf(buf, "Unimplemented Instruction Address fault"); |
---|
.. | .. |
---|
655 | 589 | printk(KERN_ERR "Unexpected IA-32 exception (Trap 45)\n"); |
---|
656 | 590 | printk(KERN_ERR " iip - 0x%lx, ifa - 0x%lx, isr - 0x%lx\n", |
---|
657 | 591 | iip, ifa, isr); |
---|
658 | | - force_sig(SIGSEGV, current); |
---|
| 592 | + force_sig(SIGSEGV); |
---|
659 | 593 | return; |
---|
660 | 594 | |
---|
661 | 595 | case 46: |
---|
662 | 596 | printk(KERN_ERR "Unexpected IA-32 intercept trap (Trap 46)\n"); |
---|
663 | 597 | printk(KERN_ERR " iip - 0x%lx, ifa - 0x%lx, isr - 0x%lx, iim - 0x%lx\n", |
---|
664 | 598 | iip, ifa, isr, iim); |
---|
665 | | - force_sig(SIGSEGV, current); |
---|
| 599 | + force_sig(SIGSEGV); |
---|
666 | 600 | return; |
---|
667 | 601 | |
---|
668 | 602 | case 47: |
---|
.. | .. |
---|
674 | 608 | break; |
---|
675 | 609 | } |
---|
676 | 610 | if (!die_if_kernel(buf, ®s, error)) |
---|
677 | | - force_sig(SIGILL, current); |
---|
| 611 | + force_sig(SIGILL); |
---|
678 | 612 | } |
---|