aboutsummaryrefslogtreecommitdiffstats
path: root/arch/i386
diff options
context:
space:
mode:
Diffstat (limited to 'arch/i386')
-rw-r--r--arch/i386/kernel/nmi.c16
-rw-r--r--arch/i386/kernel/traps.c24
2 files changed, 24 insertions, 16 deletions
diff --git a/arch/i386/kernel/nmi.c b/arch/i386/kernel/nmi.c
index d88004343034..bd96ea4f2942 100644
--- a/arch/i386/kernel/nmi.c
+++ b/arch/i386/kernel/nmi.c
@@ -781,7 +781,7 @@ EXPORT_SYMBOL(touch_nmi_watchdog);
781 781
782extern void die_nmi(struct pt_regs *, const char *msg); 782extern void die_nmi(struct pt_regs *, const char *msg);
783 783
784void nmi_watchdog_tick (struct pt_regs * regs, unsigned reason) 784int nmi_watchdog_tick (struct pt_regs * regs, unsigned reason)
785{ 785{
786 786
787 /* 787 /*
@@ -794,10 +794,12 @@ void nmi_watchdog_tick (struct pt_regs * regs, unsigned reason)
794 int cpu = smp_processor_id(); 794 int cpu = smp_processor_id();
795 struct nmi_watchdog_ctlblk *wd = &__get_cpu_var(nmi_watchdog_ctlblk); 795 struct nmi_watchdog_ctlblk *wd = &__get_cpu_var(nmi_watchdog_ctlblk);
796 u64 dummy; 796 u64 dummy;
797 int rc=0;
797 798
798 /* check for other users first */ 799 /* check for other users first */
799 if (notify_die(DIE_NMI, "nmi", regs, reason, 2, SIGINT) 800 if (notify_die(DIE_NMI, "nmi", regs, reason, 2, SIGINT)
800 == NOTIFY_STOP) { 801 == NOTIFY_STOP) {
802 rc = 1;
801 touched = 1; 803 touched = 1;
802 } 804 }
803 805
@@ -850,10 +852,18 @@ void nmi_watchdog_tick (struct pt_regs * regs, unsigned reason)
850 } 852 }
851 /* start the cycle over again */ 853 /* start the cycle over again */
852 write_watchdog_counter(wd->perfctr_msr, NULL); 854 write_watchdog_counter(wd->perfctr_msr, NULL);
853 } 855 rc = 1;
856 } else if (nmi_watchdog == NMI_IO_APIC) {
857 /* don't know how to accurately check for this.
858 * just assume it was a watchdog timer interrupt
859 * This matches the old behaviour.
860 */
861 rc = 1;
862 } else
863 printk(KERN_WARNING "Unknown enabled NMI hardware?!\n");
854 } 864 }
855done: 865done:
856 return; 866 return rc;
857} 867}
858 868
859#ifdef CONFIG_SYSCTL 869#ifdef CONFIG_SYSCTL
diff --git a/arch/i386/kernel/traps.c b/arch/i386/kernel/traps.c
index 3a07b2677e2a..282f0bd40dfd 100644
--- a/arch/i386/kernel/traps.c
+++ b/arch/i386/kernel/traps.c
@@ -706,6 +706,13 @@ void die_nmi (struct pt_regs *regs, const char *msg)
706 do_exit(SIGSEGV); 706 do_exit(SIGSEGV);
707} 707}
708 708
709static int dummy_nmi_callback(struct pt_regs * regs, int cpu)
710{
711 return 0;
712}
713
714static nmi_callback_t nmi_callback = dummy_nmi_callback;
715
709static void default_do_nmi(struct pt_regs * regs) 716static void default_do_nmi(struct pt_regs * regs)
710{ 717{
711 unsigned char reason = 0; 718 unsigned char reason = 0;
@@ -723,12 +730,11 @@ static void default_do_nmi(struct pt_regs * regs)
723 * Ok, so this is none of the documented NMI sources, 730 * Ok, so this is none of the documented NMI sources,
724 * so it must be the NMI watchdog. 731 * so it must be the NMI watchdog.
725 */ 732 */
726 if (nmi_watchdog) { 733 if (nmi_watchdog_tick(regs, reason))
727 nmi_watchdog_tick(regs, reason);
728 return; 734 return;
729 }
730#endif 735#endif
731 unknown_nmi_error(reason, regs); 736 if (!rcu_dereference(nmi_callback)(regs, smp_processor_id()))
737 unknown_nmi_error(reason, regs);
732 return; 738 return;
733 } 739 }
734 if (notify_die(DIE_NMI, "nmi", regs, reason, 2, SIGINT) == NOTIFY_STOP) 740 if (notify_die(DIE_NMI, "nmi", regs, reason, 2, SIGINT) == NOTIFY_STOP)
@@ -744,13 +750,6 @@ static void default_do_nmi(struct pt_regs * regs)
744 reassert_nmi(); 750 reassert_nmi();
745} 751}
746 752
747static int dummy_nmi_callback(struct pt_regs * regs, int cpu)
748{
749 return 0;
750}
751
752static nmi_callback_t nmi_callback = dummy_nmi_callback;
753
754fastcall void do_nmi(struct pt_regs * regs, long error_code) 753fastcall void do_nmi(struct pt_regs * regs, long error_code)
755{ 754{
756 int cpu; 755 int cpu;
@@ -761,8 +760,7 @@ fastcall void do_nmi(struct pt_regs * regs, long error_code)
761 760
762 ++nmi_count(cpu); 761 ++nmi_count(cpu);
763 762
764 if (!rcu_dereference(nmi_callback)(regs, cpu)) 763 default_do_nmi(regs);
765 default_do_nmi(regs);
766 764
767 nmi_exit(); 765 nmi_exit();
768} 766}