-
Notifications
You must be signed in to change notification settings - Fork 5.3k
Description
With some stability patches to libunwind that expands the patch of
https://lists.nongnu.org/archive/html/libunwind-devel/2015-05/msg00002.html
for the case of read as well as write, we get the following error.
(Without it, we just get "segmentation fault" without any information)
sh-3.2# ./corerun csc.exe
Assert failure(PID 9230 [0x0000240e], Thread: 9230 [0x240e]): !"Thread::VirtualUnwindToFirstManagedCallFrame: PAL_VirtualUnwind failed"
File: /work/dotnet/arm32/coreclr/src/vm/stackwalk.cpp Line: 784
Image: /sdcard/hf/Release/dirty/corerun
**** MessageBox invoked, title 'corerun - Assert Failure (PID 9230, Thread 9230/0x240e)' ****
!"Thread::VirtualUnwindToFirstManagedCallFrame: PAL_VirtualUnwind failed"
/work/dotnet/arm32/coreclr/src/vm/stackwalk.cpp, Line: 784
Abort - Kill program
Retry - Debug
Ignore - Keep running
Image:
/sdcard/hf/Release/dirty/corerun
********
Aborted (core dumped)
sh-3.2#
When we reach that point, the stack looks like this:
Assert failure(PID 12916 [0x00003274], Thread: 12916 [0x3274]): !"Thread::VirtualUnwindToFirstManagedCallFrame: PAL_VirtualUnwind failed"
File: /work/dotnet/arm32/coreclr/src/vm/stackwalk.cpp Line: 784
Image: /sdcard/hf/Release/dirty/corerun
Program received signal SIGABRT, Aborted.
0xb6d9f8e6 in ?? () from /lib/arm-linux-gnueabihf/libc.so.6
(gdb) bt
#0 0xb6d9f8e6 in ?? () from /lib/arm-linux-gnueabihf/libc.so.6
dotnet/coreclr#1 0xb6dadf0e in raise () from /lib/arm-linux-gnueabihf/libc.so.6
dotnet/coreclr#2 0xb6db0766 in abort () from /lib/arm-linux-gnueabihf/libc.so.6
dotnet/coreclr#3 0xb6b62952 in PROCEndProcess (hProcess=0xffffff01, uExitCode=1,
bTerminateUnconditionally=1)
at /work/dotnet/arm32/coreclr/src/pal/src/thread/process.cpp:1338
dotnet/coreclr#4 0xb6b62aa6 in TerminateProcess (hProcess=0xffffff01, uExitCode=1)
at /work/dotnet/arm32/coreclr/src/pal/src/thread/process.cpp:1254
dotnet/coreclr#5 0xb6300edc in _DbgBreakCheck (
szFile=0xb6b9847c "/work/dotnet/arm32/coreclr/src/vm/stackwalk.cpp",
iLine=784,
szExpr=0xb6b9851d "!\"Thread::VirtualUnwindToFirstManagedCallFrame: PAL_VirtualUnwind failed\"", fConstrained=0)
at /work/dotnet/arm32/coreclr/src/utilcode/debug.cpp:492
dotnet/coreclr#6 0xb63011c4 in _DbgBreakCheckNoThrow (
szFile=0xb6b9847c "/work/dotnet/arm32/coreclr/src/vm/stackwalk.cpp",
iLine=784,
szExpr=0xb6b9851d "!\"Thread::VirtualUnwindToFirstManagedCallFrame: PAL_VirtualUnwind failed\"", fConstrained=0)
at /work/dotnet/arm32/coreclr/src/utilcode/debug.cpp:558
dotnet/coreclr#7 0xb63014da in DbgAssertDialog (
szFile=0xb6b9847c "/work/dotnet/arm32/coreclr/src/vm/stackwalk.cpp",
iLine=784,
---Type <return> to continue, or q <return> to quit---
szExpr=0xb6b9851d "!\"Thread::VirtualUnwindToFirstManagedCallFrame: PAL_VirtualUnwind failed\"") at /work/dotnet/arm32/coreclr/src/utilcode/debug.cpp:745
dotnet/coreclr#8 0xb63be9b2 in Thread::VirtualUnwindToFirstManagedCallFrame (
pContext=0xbeffe720) at /work/dotnet/arm32/coreclr/src/vm/stackwalk.cpp:784
dotnet/coreclr#9 0xb6544c14 in DispatchManagedException (ex=...)
at /work/dotnet/arm32/coreclr/src/vm/exceptionhandling.cpp:4665
dotnet/coreclr#10 0xb672d474 in PreStubWorker (pTransitionBlock=0xbeffec84, pMD=0xb00c8390)
at /work/dotnet/arm32/coreclr/src/vm/prestub.cpp:1040
dotnet/coreclr#11 0xb6557768 in ThePreStub () at asmhelpers.S:787
dotnet/coreclr#12 0x7dd8252e in ?? ()
Backtrace stopped: previous frame identical to this frame (corrupt stack?)
(gdb)
The problem is that the saved LR at Frame 11 (ThePreStub) is BROKEN (the PC of Frame 12 is incorrect)
(gdb) info frame 11
Stack frame at 0xbeffec64:
pc = 0xb6557768 in ThePreStub (asmhelpers.S:787); saved pc = 0x7dd8252e
called by frame at 0xbeffec64, caller of frame at 0xbeffec40
source language asm.
Arglist at 0xbeffec40, args:
Locals at 0xbeffec40, Previous frame's sp is 0xbeffec64
Saved registers:
r4 at 0xbeffec40, r5 at 0xbeffec44, r6 at 0xbeffec48, r7 at 0xbeffec4c,
r8 at 0xbeffec50, r9 at 0xbeffec54, r10 at 0xbeffec58, r11 at 0xbeffec5c,
lr at 0xbeffec60
(gdb) p/x *0xbeffec60
$1 = 0x7dd8252f
(gdb) p/x *0x7dd8252f
Cannot access memory at address 0x7dd8252f
(gdb)
Looking at the assembly of ThePreStub: (note that PC is located elsewhere in the following instance because I made a watchpoint at 0xbeffec60 this time, which means that 0xbeffec60 is being overwritten by "+10 vstmia r6, {d0-d7]")
<ThePreStub> push {r0, r1, r2, r3} �
<ThePreStub+2> stmdb sp!, {r4, r5, r6, r7, r8, r9�
<ThePreStub+6> sub sp, dotnet/runtime#3883 ; 0x44 �
<ThePreStub+8> add r6, sp, #0 �
<ThePreStub+10> vstmia r6, {d0-d7} �
>>> <ThePreStub+14> push {r0} �
<ThePreStub+16> add r0, sp, dotnet/coreclr#4 �
<ThePreStub+18> tst.w r0, dotnet/coreclr#7 �
<ThePreStub+22> pop {r0} �
<ThePreStub+24> beq.n 0xb6557760 <ThePreStub+30> �
<ThePreStub+26> movs r0, r0 �
<ThePreStub+28> udf dotnet/coreclr#1 �
<ThePreStub+30> add r0, sp, dotnet/runtime#3883 ; 0x44 �
<ThePreStub+32> mov r1, r12 �
<ThePreStub+34> bl 0xb672d098 <PreStubWorker(Transition�
<ThePreStub+38> mov r12, r0 �
<ThePreStub+40> add r6, sp, #0 �
<ThePreStub+42> vldmia r6, {d0-d7} �
<ThePreStub+46> add sp, dotnet/runtime#3883 ; 0x44 �
<ThePreStub+48> ldmia.w sp!, {r4, r5, r6, r7, r8, r9, r10, r�
<ThePreStub+52> pop {r0, r1, r2, r3} �
<ThePreStub+54>
(gdb) p/x $d4
$28 = {u8 = {0x2f, 0x25, 0xd8, 0x7d, 0xba, 0x6f, 0xc9, 0xf}, u16 = {0x252f,
0x7dd8, 0x6fba, 0xfc9}, u32 = {0x7dd8252f, 0xfc96fba},
u64 = 0xfc96fba7dd8252f, f32 = {0xffffffff, 0x0}, f64 = 0x0}
(gdb) p/x $r6
$29 = 0xbeffec40
Later on, when CORECLR breaks with the exception above, the stored LR of ThePreStub is the value of stored D4 above. It is too strange to understand for now, but there seems to be some sort of buffer overrun, incorrect memory addressing, or sort of such things in coreclr regarding the assembly codes.
My first guess is on the constant "#68" or 0x44, which seems to assume that storing {r4, r5, r6, r7, r8, r9, r10, r11, lr}, and {d0-d7} requires 11 words. Because D registers are "double words", it requires 19 words. However, this doesn't add up exactly because lr is stored where d8 is going to be located if it did vstmia r6, {d0-d8} instead of vstmia r6, {d0-d7}.
I'm currently looking for the code that emitted sub sp, dotnet/runtime#3883.
ps. I'm just using Roslyn as the first "serious" test case for ARM/Linux coreclr. I'm not actually trying to build things inside ARM/Linux box.