aboutsummaryrefslogtreecommitdiffstats
path: root/arch/i386
diff options
context:
space:
mode:
authorVivek Goyal <vgoyal@in.ibm.com>2005-06-25 17:58:13 -0400
committerLinus Torvalds <torvalds@ppc970.osdl.org>2005-06-25 19:24:52 -0400
commit4d55476c3f889e0f30d88e22da4682b5f10394ff (patch)
tree097c222aea3243596762e7c3b0fa02ba94d60fde /arch/i386
parent625f1c8219d95300ed32e4c67eb62a50ded095ba (diff)
[PATCH] kdump: NMI handler segment selector, stack pointer fix
CPU does not save ss and esp on stack if execution was already in kernel mode at the time of NMI occurrence. This leads to saving of erractic values for ss and esp. This patch fixes the issue. Signed-off-by: Vivek Goyal <vgoyal@in.ibm.com> Signed-off-by: Andrew Morton <akpm@osdl.org> Signed-off-by: Linus Torvalds <torvalds@osdl.org>
Diffstat (limited to 'arch/i386')
-rw-r--r--arch/i386/kernel/crash.c13
1 files changed, 13 insertions, 0 deletions
diff --git a/arch/i386/kernel/crash.c b/arch/i386/kernel/crash.c
index 3645ad7ac200..31e077bb0caa 100644
--- a/arch/i386/kernel/crash.c
+++ b/arch/i386/kernel/crash.c
@@ -112,7 +112,20 @@ static atomic_t waiting_for_crash_ipi;
112 112
113static int crash_nmi_callback(struct pt_regs *regs, int cpu) 113static int crash_nmi_callback(struct pt_regs *regs, int cpu)
114{ 114{
115 struct pt_regs fixed_regs;
115 local_irq_disable(); 116 local_irq_disable();
117
118 /* CPU does not save ss and esp on stack if execution is already
119 * running in kernel mode at the time of NMI occurrence. This code
120 * fixes it.
121 */
122 if (!user_mode(regs)) {
123 memcpy(&fixed_regs, regs, sizeof(*regs));
124 fixed_regs.esp = (unsigned long)&(regs->esp);
125 __asm__ __volatile__("xorl %eax, %eax;");
126 __asm__ __volatile__ ("movw %%ss, %%ax;" :"=a"(fixed_regs.xss));
127 regs = &fixed_regs;
128 }
116 crash_save_this_cpu(regs, cpu); 129 crash_save_this_cpu(regs, cpu);
117 disable_local_APIC(); 130 disable_local_APIC();
118 atomic_dec(&waiting_for_crash_ipi); 131 atomic_dec(&waiting_for_crash_ipi);