<!doctype html public "-//w3c//dtd html 4.0 transitional//en">
<html>
Rachita Kothiyal wrote:
<blockquote TYPE=CITE> 
<br>> Hi Rachita,
<br>>
<br>> I've only been able to test this on a live system that has __start_unwind
<br>> and __end_unwind symbols, so I don't know what a backtrace with an
<br>> in-kernel exception frame, or a backtrace with a transition to the
x86_64
<br>> IRQ stack or x86_64 exception stacks, would look like.  If you
have
<br>> an example, I'd be interested in seeing how they get handled.
<p>Hi Dave
<p>I was trying to use LKDTM to create various scenarios for crash dump.
<br>To start with is the case of panic() in an interrupt context. Here
I
<br>am inducing a panic in handle_IRQ_event(), where I am registering a
<br>jprobe. jp_handle_irq_event() is the jprobe handler which in turn calls
<br>lkdtm_handler(). Running crash on the dump gives the following:
<p>crash> bt
<br>PID: 3898   TASK: ffff81022e988e20  CPU: 0  
COMMAND: "slapd"
<br> #0 [ffffffff8064bcf8] crash_kexec at ffffffff80152211
<br> #1 [ffffffff8064bd40] machine_kexec at ffffffff8011a739
<br> #2 [ffffffff8064bd80] crash_kexec at ffffffff8015222d
<br> #3 [ffffffff8064be08] crash_kexec at ffffffff80152211
<br> #4 [ffffffff8064be30] bust_spinlocks at ffffffff8011fd6d
<br> #5 [ffffffff8064be40] panic at ffffffff80131410
<br> #6 [ffffffff8064beb0] cdrom_pc_intr at ffffffff802ebe68
<br> #7 [ffffffff8064bef0] ide_intr at ffffffff802df26f
<br> #8 [ffffffff8064bf30] lkdtm_handler at ffffffff8800230d
<br> #9 [ffffffff8064bf40] jp_handle_irq_event at ffffffff880023e8
<br>#10 [ffffffff8064bf50] __do_IRQ at ffffffff801544f4
<br>#11 [ffffffff8064bf58] __do_softirq at ffffffff80136b8f
<br>#12 [ffffffff8064bf90] do_IRQ at ffffffff8010bda1
<br>--- <IRQ stack> ---
<br>#13 [ffff810229fd5f80] ret_from_intr at ffffffff80109b95
<br>    [exception RIP: unknown or invalid address]
<br>    RIP: 0000000000000000  RSP: 0000000000000000 
RFLAGS: 00000000
<br>    RAX: ffffffffffffffff  RBX: 00002afe35608c98 
RCX: 00002afe359f7be4
<br>    RDX: 0000000000000033  RSI: 0000000000000202 
RDI: 00007fff754bfbe0
<br>    RBP: 000000000000000a   R8: 000055555590bca0  
R9: 0000000000000000
<br>    R10: 00002afe35608c98  R11: 0000000000000001 
R12: 0000000000000000
<br>    R13: 0000000000000000  R14: 00002afe3597b1e0 
R15: 000055555590b760
<br>    ORIG_RAX: 000000000000002b  CS: 0000 
SS: 0000
<br>bt: WARNING: possibly bogus exception frame
<br>    RIP: 00002afe359f7be4  RSP: 00007fff754bfbe0 
RFLAGS: 00000202
<br>    RAX: 00002afe35608c98  RBX: 000055555590b760 
RCX: 0000000000000001
<br>    RDX: 00002afe35608c98  RSI: 0000000000000000 
RDI: 000055555590bca0
<br>    RBP: ffffffff80109c0b   R8: 000000000000000a  
R9: 0000000000000000
<br>    R10: 0000000000000000  R11: 00002afe3597b1e0 
R12: 000055555590b760
<br>    R13: 00007fff754bfd38  R14: 0000000000000001 
R15: 000055555590b760
<br>    ORIG_RAX: ffffffffffffffff  CS: 0033 
SS: 002b
<br>crash> set unwind on
<br>unwind: on
<br>crash> bt
<br>PID: 3898   TASK: ffff81022e988e20  CPU: 0  
COMMAND: "slapd"
<br> #0 [ffffffff8064bd88] crash_kexec at ffffffff80152211
<br> #1 [ffffffff8064be48] panic at ffffffff80131410
<br> #2 [ffffffff8064bf38] lkdtm_handler at ffffffff8800230d
<br>--- <IRQ stack> ---
<br> #3 [ffff810229fd5f80] ret_from_intr at ffffffff80109b95
<br>    [exception RIP: unknown or invalid address]
<br>    RIP: 0000000000000000  RSP: 0000000000000000 
RFLAGS: 00000000
<br>    RAX: ffffffffffffffff  RBX: 00002afe35608c98 
RCX: 00002afe359f7be4
<br>    RDX: 0000000000000033  RSI: 0000000000000202 
RDI: 00007fff754bfbe0
<br>    RBP: 000000000000000a   R8: 000055555590bca0  
R9: 0000000000000000
<br>    R10: 00002afe35608c98  R11: 0000000000000001 
R12: 0000000000000000
<br>    R13: 0000000000000000  R14: 00002afe3597b1e0 
R15: 000055555590b760
<br>    ORIG_RAX: 000000000000002b  CS: 0000 
SS: 0000
<br>bt: WARNING: possibly bogus exception frame
<br> #4 [ffff810229fd5f80] common_interrupt at ffffffff80109b95
<br>    RIP: 00002afe359f7be4  RSP: 00007fff754bfbe0 
RFLAGS: 00000202
<br>    RAX: 00002afe35608c98  RBX: 000055555590b760 
RCX: 0000000000000001
<br>    RDX: 00002afe35608c98  RSI: 0000000000000000 
RDI: 000055555590bca0
<br>    RBP: ffffffff80109c0b   R8: 000000000000000a  
R9: 0000000000000000
<br>    R10: 0000000000000000  R11: 00002afe3597b1e0 
R12: 000055555590b760
<br>    R13: 00007fff754bfd38  R14: 0000000000000001 
R15: 000055555590b760
<br>    ORIG_RAX: ffffffffffffffff  CS: 0033 
SS: 002b
<br>crash>
<p>Comments?
<br> </blockquote>
<tt>Not really.  I don't understand why IRQ exception frame contents</tt>
<br><tt>look the way they do.  The crash utility's "irq_eframe" value,</tt>
<br><tt>which gets assigned from a fixed location at the top of the</tt>
<br><tt>interrupt stack, is obviously pointing to a bogus exception frame.</tt>
<br><tt>There might be something different in newer kernels, although I</tt>
<br><tt>don't see it in 2.6.18?</tt><tt></tt>
<p><tt>If you do a "help -m", the very last line shows the base address</tt>
<br><tt>of each per-cpu interrupt stack, as in:</tt><tt></tt>
<p><tt>crash> help -m</tt>
<br><tt>...</tt>
<br><tt>                         
ibase[cpus]:</tt>
<br><tt>   ffffffff80453d00 0000010037e28000 0000010037e60000
0000010037e94000</tt>
<br><tt>crash></tt><tt></tt>
<p><tt>Each of the interrupt stacks are 16k long, so you can</tt>
<br><tt>look at them with a "rd" with a count of 2048.  The linkage</tt>
<br><tt>between the interrupt stack and the stack from where it came</tt>
<br><tt>is supposed to be at the first word just below the top 64 words</tt>
<br><tt>on that stack.</tt><tt></tt>
<p><tt>So if I take cpu 2's interrupt stack from above, which is at</tt>
<br><tt>10037e60000, and dump it using "rd -s", I see this:</tt><tt></tt>
<p><tt>crash> rd -s 10037e60000 2048</tt>
<br><tt>...</tt>
<br><tt>     10037e63f90:  0000007fbffff4b0 0000007fbffff410</tt>
<br><tt>     10037e63fa0:  0000000000000046 0000000000000046</tt>
<br><tt>     10037e63fb0:  apic_timer_interrupt+0x85
<b>000001003741df58</b></tt>
<br><tt>     10037e63fc0:  0000000000000000 0000000000000000</tt>
<br><tt>     10037e63fd0:  0000000000000000 0000000000000000</tt>
<br><tt>     10037e63fe0:  0000000000000000 0000000000000000</tt>
<br><tt>     10037e63ff0:  0000000000000000 0000000000000000</tt>
<br><tt>crash></tt><tt></tt>
<p><tt>The linkage to the previous stack is at IRQ stack address</tt>
<br><tt>10037e63fb8, which points back to a process stack address of</tt>
<br><tt>1003741df58.  That process stack address is also a pointer</tt>
<br><tt>to the exception frame that was laid down there:</tt><tt></tt>
<p><tt>crash> pt_regs 000001003741df58</tt>
<br><tt>struct pt_regs {</tt>
<br><tt>  r15 = 0x0,</tt>
<br><tt>  r14 = 0x1003741df58,</tt>
<br><tt>  r13 = 0x7fbfffe840,</tt>
<br><tt>  r12 = 0xa8,</tt>
<br><tt>  rbp = 0x17dbfc0,</tt>
<br><tt>  rbx = 0xffffffff801103ce,</tt>
<br><tt>  r11 = 0x246,</tt>
<br><tt>  r10 = 0x31d072f928,</tt>
<br><tt>  r9 = 0x4587d9,</tt>
<br><tt>  r8 = 0x3741df58,</tt>
<br><tt>  rax = 0xffffffffffffffda,</tt>
<br><tt>  rcx = 0xffffffffffffffff,</tt>
<br><tt>  rdx = 0xa8,</tt>
<br><tt>  rsi = 0x17dbfc0,</tt>
<br><tt>  rdi = 0x4,</tt>
<br><tt>  orig_rax = 0x0,</tt>
<br><tt>  rip = 0x31d05b85b2,</tt>
<br><tt>  cs = 0x33,</tt>
<br><tt>  eflags = 0x246,</tt>
<br><tt>  rsp = 0x7fbfffe808,</tt>
<br><tt>  ss = 0x2b</tt>
<br><tt>}</tt><tt></tt>
<p><tt>So the last time an interrupt occurred on this</tt>
<br><tt>cpu, a program was running in user space (cs 0x33)</tt>
<br><tt>when a timer interrupt occurred.</tt>
<p><tt>If it had occurred in kernel mode, a kernel mode</tt>
<br><tt>exception frame should be there,  So for example,</tt>
<br><tt>if I take cpu 3's interrupt stack from above, it</tt>
<br><tt>shows this:</tt><tt></tt>
<p><tt>crash> rd -s 0000010037e94000 2048</tt>
<br><tt>...</tt>
<br><tt>     10037e97f90:  0000000000000000 0000000000000000  
................</tt>
<br><tt>     10037e97fa0:  0000000000000046 0000000000000046  
F.......F.......</tt>
<br><tt>     10037e97fb0:  apic_timer_interrupt+0x85
<b>0000010037e83e98</b>   .........>.7....</tt>
<br><tt>     10037e97fc0:  0000000000000000 0000000000000000  
................</tt>
<br><tt>     10037e97fd0:  0000000000000000 0000000000000000  
................</tt>
<br><tt>     10037e97fe0:  0000000000000000 0000000000000000  
................</tt>
<br><tt>     10037e97ff0:  0000000000000000 0000000000000000  
................</tt>
<br><tt>crash></tt><tt></tt>
<p><tt>And in this case, the timer interrupt occurred while running</tt>
<br><tt>in kernel mode (cs 0x10):</tt><tt></tt>
<p><tt>crash> pt_regs 0000010037e83e98</tt>
<br><tt>struct pt_regs {</tt>
<br><tt>  r15 = 0x0,</tt>
<br><tt>  r14 = 0x0,</tt>
<br><tt>  r13 = 0x0,</tt>
<br><tt>  r12 = 0x0,</tt>
<br><tt>  rbp = 0x1,</tt>
<br><tt>  rbx = 0x0,</tt>
<br><tt>  r11 = 0x5,</tt>
<br><tt>  r10 = 0x0,</tt>
<br><tt>  r9 = 0x8,</tt>
<br><tt>  r8 = 0x10037e82000,</tt>
<br><tt>  rax = 0x0,</tt>
<br><tt>  rcx = 0x0,</tt>
<br><tt>  rdx = 0x0,</tt>
<br><tt>  rsi = 0x1003f047030,</tt>
<br><tt>  rdi = 0x1000102a7e0,</tt>
<br><tt>  orig_rax = 0xffffffffffffffef,</tt>
<br><tt>  rip = 0xffffffff8010e84c,</tt>
<br><tt>  cs = 0x10,</tt>
<br><tt>  eflags = 0x246,</tt>
<br><tt>  rsp = 0x10037e83f48,</tt>
<br><tt>  ss = 0x18</tt>
<br><tt>}</tt>
<br><tt>crash></tt><tt></tt>
<p><tt>The rip above shows that the cpu was in idle:</tt><tt></tt>
<p><tt>crash> sym 0xffffffff8010e84c</tt>
<br><tt>ffffffff8010e84c (t) mwait_idle+0x56  include/asm/thread_info.h:
63</tt>
<br><tt>crash></tt><tt></tt>
<p><tt>So I cannot explain what's going on in your kernel,</tt>
<br><tt>where it looks like that basic stack-linkage assumption</tt>
<br><tt>is being violated, or has changed somehow?  Maybe kdump</tt>
<br><tt>or jprobes has done something?  I don't know what else to</tt>
<br><tt>tell you.</tt>
<blockquote TYPE=CITE> 
<br>In the stacktrace with 'unwind on', I was expecting to see jp_handle_irq_event
<br>appear too (as frame 3)..Could my using a module to register the probe
be the
<br>reason ?
<br> </blockquote>
<tt>I don't know.  Maybe since the jprobes procedure mucks with</tt>
<br><tt>the text, it somehow alter the unwind mechanism?</tt><tt></tt>
<p><tt>Helpless,</tt>
<br><tt>  Dave</tt>
<br> </html>