jeffcharles opened issue #3884:
Test Case
#include <stdio.h> int main() { int i; for(i = 0; i < 5; i++) { printf("%d\n", i); } return 0; }
compiled with:
wasi-sdk-14.0/bin/clang -g -O0 test.c -o test.wasm
Steps to Reproduce
> lldb -- wasmtime run -g test.wasm (lldb) target create "wasmtime" Current executable set to 'wasmtime' (arm64). (lldb) settings set -- target.run-args "run" "-g" "test.wasm" (lldb) settings set plugin.jit-loader.gdb.enable on (lldb) b test.c:6 Breakpoint 1: no locations (pending). WARNING: Unable to resolve breakpoint to any actual locations. (lldb) run Process 40146 launched: '/Users/jeffcharles/.cargo/bin/wasmtime' (arm64) 1 location added to breakpoint 1 Process 40146 stopped * thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 1.1 frame #0: 0x0000000100e940e0 JIT(0x1102b0000)`main at test.c:6:24 3 int main() { 4 int i; 5 for(i = 0; i < 5; i++) { -> 6 printf("%d\n", i); 7 } 8 return 0; 9 } Target 0: (wasmtime) stopped. (lldb) fr v (WasmtimeVMContext *) __vmctx = <variable not available> (int) i = <no location, value may have been optimized out>
Expected Results
Running
fr v
in lldb in this context should display:(int) i = 0
Actual Results
(int) i = <no location, value may have been optimized out>
Versions and Environment
Wasmtime version or commit: 0.34.0
Operating system: MacOS Monterrey (12.2.1)
Architecture: arm64
Extra Info
Anything else you'd like to add?
jeffcharles labeled issue #3884:
Test Case
#include <stdio.h> int main() { int i; for(i = 0; i < 5; i++) { printf("%d\n", i); } return 0; }
compiled with:
wasi-sdk-14.0/bin/clang -g -O0 test.c -o test.wasm
Steps to Reproduce
> lldb -- wasmtime run -g test.wasm (lldb) target create "wasmtime" Current executable set to 'wasmtime' (arm64). (lldb) settings set -- target.run-args "run" "-g" "test.wasm" (lldb) settings set plugin.jit-loader.gdb.enable on (lldb) b test.c:6 Breakpoint 1: no locations (pending). WARNING: Unable to resolve breakpoint to any actual locations. (lldb) run Process 40146 launched: '/Users/jeffcharles/.cargo/bin/wasmtime' (arm64) 1 location added to breakpoint 1 Process 40146 stopped * thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 1.1 frame #0: 0x0000000100e940e0 JIT(0x1102b0000)`main at test.c:6:24 3 int main() { 4 int i; 5 for(i = 0; i < 5; i++) { -> 6 printf("%d\n", i); 7 } 8 return 0; 9 } Target 0: (wasmtime) stopped. (lldb) fr v (WasmtimeVMContext *) __vmctx = <variable not available> (int) i = <no location, value may have been optimized out>
Expected Results
Running
fr v
in lldb in this context should display:(int) i = 0
Actual Results
(int) i = <no location, value may have been optimized out>
Versions and Environment
Wasmtime version or commit: 0.34.0
Operating system: MacOS Monterrey (12.2.1)
Architecture: arm64
Extra Info
Anything else you'd like to add?
jeffcharles edited issue #3884:
Test Case
#include <stdio.h> int main() { int i; for(i = 0; i < 5; i++) { printf("%d\n", i); } return 0; }
compiled with:
wasi-sdk-14.0/bin/clang -g -O0 test.c -o test.wasm
Steps to Reproduce
> lldb -- wasmtime run -g test.wasm (lldb) target create "wasmtime" Current executable set to 'wasmtime' (arm64). (lldb) settings set -- target.run-args "run" "-g" "test.wasm" (lldb) settings set plugin.jit-loader.gdb.enable on (lldb) b test.c:6 Breakpoint 1: no locations (pending). WARNING: Unable to resolve breakpoint to any actual locations. (lldb) run Process 40146 launched: '/Users/jeffcharles/.cargo/bin/wasmtime' (arm64) 1 location added to breakpoint 1 Process 40146 stopped * thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 1.1 frame #0: 0x0000000100e940e0 JIT(0x1102b0000)`main at test.c:6:24 3 int main() { 4 int i; 5 for(i = 0; i < 5; i++) { -> 6 printf("%d\n", i); 7 } 8 return 0; 9 } Target 0: (wasmtime) stopped. (lldb) fr v (WasmtimeVMContext *) __vmctx = <variable not available> (int) i = <no location, value may have been optimized out>
Expected Results
Running
fr v
in lldb in this context should display:(int) i = 0
Actual Results
(int) i = <no location, value may have been optimized out>
Versions and Environment
Wasmtime version or commit: 0.34.0
Operating system: MacOS Monterrey (12.2.1)
Architecture: arm64
Extra Info
Anything else you'd like to add?
This is what happens when I try to compile and run natively to show what I'm expecting:
> clang -g -O0 test.c -o test > lldb -- test (lldb) target create "test" Current executable set to '/Users/jeffcharles/projects/wasm32-wasi/test-c-app/test' (arm64). (lldb) b test.c:6 Breakpoint 1: where = test`main + 32 at test.c:6:24, address = 0x0000000100003f6c (lldb) run Process 40384 launched: '/Users/jeffcharles/projects/wasm32-wasi/test-c-app/test' (arm64) Process 40384 stopped * thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 1.1 frame #0: 0x0000000100003f6c test`main at test.c:6:24 3 int main() { 4 int i; 5 for(i = 0; i < 5; i++) { -> 6 printf("%d\n", i); 7 } 8 return 0; 9 } Target 0: (test) stopped. (lldb) fr v (int) i = 0
jeffcharles edited issue #3884:
Test Case
#include <stdio.h> int main() { int i; for(i = 0; i < 5; i++) { printf("%d\n", i); } return 0; }
compiled with:
wasi-sdk-14.0/bin/clang -g -O0 test.c -o test.wasm
Steps to Reproduce
> lldb -- wasmtime run -g test.wasm (lldb) target create "wasmtime" Current executable set to 'wasmtime' (arm64). (lldb) settings set -- target.run-args "run" "-g" "test.wasm" (lldb) settings set plugin.jit-loader.gdb.enable on (lldb) b test.c:6 Breakpoint 1: no locations (pending). WARNING: Unable to resolve breakpoint to any actual locations. (lldb) run Process 40146 launched: '/Users/jeffcharles/.cargo/bin/wasmtime' (arm64) 1 location added to breakpoint 1 Process 40146 stopped * thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 1.1 frame #0: 0x0000000100e940e0 JIT(0x1102b0000)`main at test.c:6:24 3 int main() { 4 int i; 5 for(i = 0; i < 5; i++) { -> 6 printf("%d\n", i); 7 } 8 return 0; 9 } Target 0: (wasmtime) stopped. (lldb) fr v (WasmtimeVMContext *) __vmctx = <variable not available> (int) i = <no location, value may have been optimized out>
Expected Results
Running
fr v
in lldb in this context should display:(int) i = 0
Actual Results
(int) i = <no location, value may have been optimized out>
Versions and Environment
Wasmtime version or commit: 0.34.0
Operating system: MacOS Monterrey (12.2.1)
Architecture: arm64
Extra Info
LLDB version:
> lldb --version lldb-1300.0.42.3 Swift version 5.5.2-dev
This is what happens when I try to compile and run natively to show what I'm expecting:
> clang -g -O0 test.c -o test > lldb -- test (lldb) target create "test" Current executable set to '/Users/jeffcharles/projects/wasm32-wasi/test-c-app/test' (arm64). (lldb) b test.c:6 Breakpoint 1: where = test`main + 32 at test.c:6:24, address = 0x0000000100003f6c (lldb) run Process 40384 launched: '/Users/jeffcharles/projects/wasm32-wasi/test-c-app/test' (arm64) Process 40384 stopped * thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 1.1 frame #0: 0x0000000100003f6c test`main at test.c:6:24 3 int main() { 4 int i; 5 for(i = 0; i < 5; i++) { -> 6 printf("%d\n", i); 7 } 8 return 0; 9 } Target 0: (test) stopped. (lldb) fr v (int) i = 0
cfallin commented on issue #3884:
It looks like the
i
variable is placed on the in-wasm-heap pseudostack by LLVM:$ /opt/wasi-sdk/bin/llvm-dwarfdump test.wasm [ ... ] 0x0000003e: DW_TAG_variable DW_AT_location (DW_OP_fbreg +8) DW_AT_name ("i") DW_AT_decl_file ("/Users/jeffcharles/projects/wasm32-wasi/test-c-app/test.c") DW_AT_decl_line (4) DW_AT_type (0x0000004d "int")
(
fbreg
is the frame-buffer "register".) I'm not sure how well-supported this is; I'm more familiar with the machinery that passes through debug locations for SSA values, which come from Wasm locals. @yurydelendik wrote the original DWARF expression translation code I think -- Yury, any thoughts on this (whether it is expected to work with the existing code, what it would take if not)?
alexcrichton labeled issue #3884:
Test Case
#include <stdio.h> int main() { int i; for(i = 0; i < 5; i++) { printf("%d\n", i); } return 0; }
compiled with:
wasi-sdk-14.0/bin/clang -g -O0 test.c -o test.wasm
Steps to Reproduce
> lldb -- wasmtime run -g test.wasm (lldb) target create "wasmtime" Current executable set to 'wasmtime' (arm64). (lldb) settings set -- target.run-args "run" "-g" "test.wasm" (lldb) settings set plugin.jit-loader.gdb.enable on (lldb) b test.c:6 Breakpoint 1: no locations (pending). WARNING: Unable to resolve breakpoint to any actual locations. (lldb) run Process 40146 launched: '/Users/jeffcharles/.cargo/bin/wasmtime' (arm64) 1 location added to breakpoint 1 Process 40146 stopped * thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 1.1 frame #0: 0x0000000100e940e0 JIT(0x1102b0000)`main at test.c:6:24 3 int main() { 4 int i; 5 for(i = 0; i < 5; i++) { -> 6 printf("%d\n", i); 7 } 8 return 0; 9 } Target 0: (wasmtime) stopped. (lldb) fr v (WasmtimeVMContext *) __vmctx = <variable not available> (int) i = <no location, value may have been optimized out>
Expected Results
Running
fr v
in lldb in this context should display:(int) i = 0
Actual Results
(int) i = <no location, value may have been optimized out>
Versions and Environment
Wasmtime version or commit: 0.34.0
Operating system: MacOS Monterrey (12.2.1)
Architecture: arm64
Extra Info
LLDB version:
> lldb --version lldb-1300.0.42.3 Swift version 5.5.2-dev
This is what happens when I try to compile and run natively to show what I'm expecting:
> clang -g -O0 test.c -o test > lldb -- test (lldb) target create "test" Current executable set to '/Users/jeffcharles/projects/wasm32-wasi/test-c-app/test' (arm64). (lldb) b test.c:6 Breakpoint 1: where = test`main + 32 at test.c:6:24, address = 0x0000000100003f6c (lldb) run Process 40384 launched: '/Users/jeffcharles/projects/wasm32-wasi/test-c-app/test' (arm64) Process 40384 stopped * thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 1.1 frame #0: 0x0000000100003f6c test`main at test.c:6:24 3 int main() { 4 int i; 5 for(i = 0; i < 5; i++) { -> 6 printf("%d\n", i); 7 } 8 return 0; 9 } Target 0: (test) stopped. (lldb) fr v (int) i = 0
yurydelendik commented on issue #3884:
whether it is expected to work with the existing code, what it would take if not
Based on https://github.com/bytecodealliance/wasmtime/pull/842 it was supported at some time. Missing tests though because format was evolving on LLVM side.
ianks commented on issue #3884:
Getting the same issue on lldb 12.0.1
YoungWenMing commented on issue #3884:
Any updates about this issue?
bjorn3 commented on issue #3884:
To quote @cfallin from https://github.com/bytecodealliance/wasmtime/issues/4669#issuecomment-1210997950 (which is another debuginfo issue):
We currently don't have anyone on the project who understands our DWARF-handling code well and has time to work on it; so while this is definitely a bug, it's not likely to have a fast resolution. We do have an intent to have someone eventually focus on this, as priorities allow, so we should keep this issue open. Just wanted to give some context on the current situation...
SingleAccretion commented on issue #3884:
I have tried the simple C code above the issue and the issue no longer reproduces. However, I have a larger example (not yet in C/C++) that does show bad behavior with local variables.
We start with:
public static int Main() { SimpleStruct simpleStruct = new() { IntField = 1, FloatField = 2.0f }; SimpleClass simpleClass = new() { IntField = 1, FloatField = 2.0f }; TestBasicTypesDisplay(true, false, 'a', 1, -1, 2, -2, 3, -3, 4, -4, 5, -5, 1.0f, 2.0); TestEnumDisplay(DayOfWeek.Monday); TestByRefDisplay(ref simpleStruct, ref simpleClass); TestPointerDisplay(&simpleStruct); TestStringDisplay("Basic string"); TestBasicArrayDisplay(new int[] { 1, 2, 3 }, new double[] { 1, 2, 3 }); TestComplexArrayDisplay(new[] { simpleClass }, new[] { simpleStruct }); TestBasicMultiDimensionalArrayDisplay(new int[,] { { 1, 2, 3 }, { 4, 5, 6 } }); TestSimpleStructDisplay(simpleStruct); TestSimpleClassDisplay(simpleClass); TestDerivedClassDisplay(new() { IntField = 1, FloatField = 2.0f, LongField = 3 }); TestRecursiveClassDisplay(new() { Value = 1, Next = new() { Value = 2 } }); simpleStruct.TestStructInstanceMethod(); simpleClass.TestClassInstanceMethod(); TestVariables(5, simpleStruct, simpleClass); return 100; }
We have this DWARF for the generated WASM:
0x0011c6f2: DW_TAG_subprogram DW_AT_low_pc (0x004d9992) DW_AT_high_pc (0x004daf32) DW_AT_frame_base (DW_OP_WASM_location 0x0 0x3, DW_OP_stack_value) DW_AT_linkage_name ("WasmDebugging_Program__Main") DW_AT_name ("Main") DW_AT_decl_file ("C:\Users\Accretion\source\dotnet\runtimelab\src\tests\nativeaot\SmokeTests\HelloWasm\WasmDebugging.cs") DW_AT_decl_line (15) DW_AT_type (0x000000000010c1b2 "int") 0x0011c70e: DW_TAG_variable DW_AT_location (DW_OP_fbreg +88) DW_AT_name ("simpleStruct") DW_AT_type (0x0011c72d "WasmDebugging_SimpleStruct") 0x0011c71b: DW_TAG_variable DW_AT_location (DW_OP_fbreg +4, DW_OP_deref, DW_OP_plus_uconst 0x0) DW_AT_name ("simpleClass") DW_AT_type (0x0011c748 "WasmDebugging_SimpleClass &")
Pretty standard/expected.
I compiled this with
-g -opt-level 0
, and extracted the generated DWARF from the cached compressed ELF object (side note: it is _huge_, 350MB uncompressed, while the input is ~25MB, with the most output space taken up by debug info).We get (with offsets for location lists for better legibility):
0x001446e5: DW_TAG_subprogram DW_AT_low_pc (0x00000000005b1780) DW_AT_high_pc (0x00000000005b3200) DW_AT_linkage_name ("WasmDebugging_Program__Main") DW_AT_name ("Main") DW_AT_decl_file ("C:\Users\Accretion\source\dotnet\runtimelab\src\tests\nativeaot\SmokeTests\HelloWasm\WasmDebugging.cs") DW_AT_decl_line (15) DW_AT_type (0x000000000012a78c "int") 0x001446fe: DW_TAG_variable DW_AT_name ("__vmctx") DW_AT_type (0x001446d6 "WasmtimeVMContext *") DW_AT_location (0x03785671: (+75, +722): DW_OP_reg5 (+722, +753): DW_OP_reg5 (+753, +953): DW_OP_reg14 (+955, +1062): DW_OP_reg14 (+1064, +1940): DW_OP_reg14 (+1942, +2804): DW_OP_reg14 (+2806, +3534): DW_OP_reg14 (+3536, +3614): DW_OP_reg14 (+3616, +4501): DW_OP_reg14 (+4503, +5296): DW_OP_reg14 (+5298, +5400): DW_OP_reg14 (+5402, +5512): DW_OP_reg14 (+5514, +5801): DW_OP_reg14 (+5803, +6028): DW_OP_reg14 (+6030, +6150): DW_OP_reg14 (+6158, +6399): DW_OP_reg14 (+6401, +6626): DW_OP_reg14 (+6678, +6696): DW_OP_reg14) 0x0014470b: DW_TAG_variable DW_AT_location (0x037857d7: (+75, +90): DW_OP_breg10 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+90, +104): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+104, +116): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+116, +128): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+128, +140): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+140, +152): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+152, +164): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+164, +176): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+176, +188): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+188, +200): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+200, +212): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+212, +224): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+224, +236): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+236, +248): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+248, +260): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+260, +272): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+272, +284): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+284, +296): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+296, +308): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+308, +320): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+320, +332): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+332, +344): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+344, +356): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+356, +368): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+368, +380): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+380, +394): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+394, +406): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+406, +420): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+420, +432): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+432, +616): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+616, +628): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+628, +645): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_d [message truncated]
SingleAccretion edited a comment on issue #3884:
I have tried the simple C code above the issue and the issue no longer reproduces. However, I have a larger example (not yet in C/C++) that does show bad behavior with local variables.
We start with:
public static int Main() { SimpleStruct simpleStruct = new() { IntField = 1, FloatField = 2.0f }; SimpleClass simpleClass = new() { IntField = 1, FloatField = 2.0f }; TestBasicTypesDisplay(true, false, 'a', 1, -1, 2, -2, 3, -3, 4, -4, 5, -5, 1.0f, 2.0); TestEnumDisplay(DayOfWeek.Monday); TestByRefDisplay(ref simpleStruct, ref simpleClass); TestPointerDisplay(&simpleStruct); TestStringDisplay("Basic string"); TestBasicArrayDisplay(new int[] { 1, 2, 3 }, new double[] { 1, 2, 3 }); TestComplexArrayDisplay(new[] { simpleClass }, new[] { simpleStruct }); TestBasicMultiDimensionalArrayDisplay(new int[,] { { 1, 2, 3 }, { 4, 5, 6 } }); TestSimpleStructDisplay(simpleStruct); TestSimpleClassDisplay(simpleClass); TestDerivedClassDisplay(new() { IntField = 1, FloatField = 2.0f, LongField = 3 }); TestRecursiveClassDisplay(new() { Value = 1, Next = new() { Value = 2 } }); simpleStruct.TestStructInstanceMethod(); simpleClass.TestClassInstanceMethod(); TestVariables(5, simpleStruct, simpleClass); return 100; }
We have this DWARF for the generated WASM:
0x0011c6f2: DW_TAG_subprogram DW_AT_low_pc (0x004d9992) DW_AT_high_pc (0x004daf32) DW_AT_frame_base (DW_OP_WASM_location 0x0 0x3, DW_OP_stack_value) DW_AT_linkage_name ("WasmDebugging_Program__Main") DW_AT_name ("Main") DW_AT_decl_file ("C:\Users\Accretion\source\dotnet\runtimelab\src\tests\nativeaot\SmokeTests\HelloWasm\WasmDebugging.cs") DW_AT_decl_line (15) DW_AT_type (0x000000000010c1b2 "int") 0x0011c70e: DW_TAG_variable DW_AT_location (DW_OP_fbreg +88) DW_AT_name ("simpleStruct") DW_AT_type (0x0011c72d "WasmDebugging_SimpleStruct") 0x0011c71b: DW_TAG_variable DW_AT_location (DW_OP_fbreg +4, DW_OP_deref, DW_OP_plus_uconst 0x0) DW_AT_name ("simpleClass") DW_AT_type (0x0011c748 "WasmDebugging_SimpleClass &")
Pretty standard/expected.
I compiled this with
-g -opt-level 0
, and extracted the generated DWARF from the cached compressed ELF object (side note: it is _huge_, 350MB uncompressed, while the input is ~25MB, with the most output space taken up by debug info).We get (with offsets for location lists for better legibility):
0x001446e5: DW_TAG_subprogram DW_AT_low_pc (0x00000000005b1780) DW_AT_high_pc (0x00000000005b3200) DW_AT_linkage_name ("WasmDebugging_Program__Main") DW_AT_name ("Main") DW_AT_decl_file ("C:\Users\Accretion\source\dotnet\runtimelab\src\tests\nativeaot\SmokeTests\HelloWasm\WasmDebugging.cs") DW_AT_decl_line (15) DW_AT_type (0x000000000012a78c "int") 0x001446fe: DW_TAG_variable DW_AT_name ("__vmctx") DW_AT_type (0x001446d6 "WasmtimeVMContext *") DW_AT_location (0x03785671: (+75, +722): DW_OP_reg5 (+722, +753): DW_OP_reg5 (+753, +953): DW_OP_reg14 (+955, +1062): DW_OP_reg14 (+1064, +1940): DW_OP_reg14 (+1942, +2804): DW_OP_reg14 (+2806, +3534): DW_OP_reg14 (+3536, +3614): DW_OP_reg14 (+3616, +4501): DW_OP_reg14 (+4503, +5296): DW_OP_reg14 (+5298, +5400): DW_OP_reg14 (+5402, +5512): DW_OP_reg14 (+5514, +5801): DW_OP_reg14 (+5803, +6028): DW_OP_reg14 (+6030, +6150): DW_OP_reg14 (+6158, +6399): DW_OP_reg14 (+6401, +6626): DW_OP_reg14 (+6678, +6696): DW_OP_reg14) 0x0014470b: DW_TAG_variable DW_AT_location (0x037857d7: (+75, +90): DW_OP_breg10 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+90, +104): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+104, +116): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+116, +128): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+128, +140): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+140, +152): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+152, +164): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+164, +176): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+176, +188): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+188, +200): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+200, +212): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+212, +224): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+224, +236): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+236, +248): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+248, +260): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+260, +272): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+272, +284): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+284, +296): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+296, +308): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+308, +320): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+320, +332): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+332, +344): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+344, +356): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+356, +368): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+368, +380): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+380, +394): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+394, +406): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+406, +420): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+420, +432): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+432, +616): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+616, +628): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+628, +645): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, [message truncated]
SingleAccretion edited a comment on issue #3884:
I have tried the simple C code above the issue and the issue no longer reproduces. However, I have a larger example (not yet in C/C++) that does show bad behavior with local variables.
We start with:
public static int Main() { SimpleStruct simpleStruct = new() { IntField = 1, FloatField = 2.0f }; SimpleClass simpleClass = new() { IntField = 1, FloatField = 2.0f }; TestBasicTypesDisplay(true, false, 'a', 1, -1, 2, -2, 3, -3, 4, -4, 5, -5, 1.0f, 2.0); TestEnumDisplay(DayOfWeek.Monday); TestByRefDisplay(ref simpleStruct, ref simpleClass); TestPointerDisplay(&simpleStruct); TestStringDisplay("Basic string"); TestBasicArrayDisplay(new int[] { 1, 2, 3 }, new double[] { 1, 2, 3 }); TestComplexArrayDisplay(new[] { simpleClass }, new[] { simpleStruct }); TestBasicMultiDimensionalArrayDisplay(new int[,] { { 1, 2, 3 }, { 4, 5, 6 } }); TestSimpleStructDisplay(simpleStruct); TestSimpleClassDisplay(simpleClass); TestDerivedClassDisplay(new() { IntField = 1, FloatField = 2.0f, LongField = 3 }); TestRecursiveClassDisplay(new() { Value = 1, Next = new() { Value = 2 } }); simpleStruct.TestStructInstanceMethod(); simpleClass.TestClassInstanceMethod(); TestVariables(5, simpleStruct, simpleClass); return 100; }
We have this DWARF for the generated WASM:
0x0011c6f2: DW_TAG_subprogram DW_AT_low_pc (0x004d9992) DW_AT_high_pc (0x004daf32) DW_AT_frame_base (DW_OP_WASM_location 0x0 0x3, DW_OP_stack_value) DW_AT_linkage_name ("WasmDebugging_Program__Main") DW_AT_name ("Main") DW_AT_decl_file ("C:\Users\Accretion\source\dotnet\runtimelab\src\tests\nativeaot\SmokeTests\HelloWasm\WasmDebugging.cs") DW_AT_decl_line (15) DW_AT_type (0x000000000010c1b2 "int") 0x0011c70e: DW_TAG_variable DW_AT_location (DW_OP_fbreg +0x58) DW_AT_name ("simpleStruct") DW_AT_type (0x0011c72d "WasmDebugging_SimpleStruct") 0x0011c71b: DW_TAG_variable DW_AT_location (DW_OP_fbreg +0x4, DW_OP_deref, DW_OP_plus_uconst 0x0) DW_AT_name ("simpleClass") DW_AT_type (0x0011c748 "WasmDebugging_SimpleClass &")
Pretty standard/expected.
I compiled this with
-g -opt-level 0
, and extracted the generated DWARF from the cached compressed ELF object (side note: it is _huge_, 350MB uncompressed, while the input is ~25MB, with the most output space taken up by debug info).We get (with offsets for location lists for better legibility):
0x001446e5: DW_TAG_subprogram DW_AT_low_pc (0x00000000005b1780) DW_AT_high_pc (0x00000000005b3200) DW_AT_linkage_name ("WasmDebugging_Program__Main") DW_AT_name ("Main") DW_AT_decl_file ("C:\Users\Accretion\source\dotnet\runtimelab\src\tests\nativeaot\SmokeTests\HelloWasm\WasmDebugging.cs") DW_AT_decl_line (15) DW_AT_type (0x000000000012a78c "int") 0x001446fe: DW_TAG_variable DW_AT_name ("__vmctx") DW_AT_type (0x001446d6 "WasmtimeVMContext *") DW_AT_location (0x03785671: (+75, +722): DW_OP_reg5 (+722, +753): DW_OP_reg5 (+753, +953): DW_OP_reg14 (+955, +1062): DW_OP_reg14 (+1064, +1940): DW_OP_reg14 (+1942, +2804): DW_OP_reg14 (+2806, +3534): DW_OP_reg14 (+3536, +3614): DW_OP_reg14 (+3616, +4501): DW_OP_reg14 (+4503, +5296): DW_OP_reg14 (+5298, +5400): DW_OP_reg14 (+5402, +5512): DW_OP_reg14 (+5514, +5801): DW_OP_reg14 (+5803, +6028): DW_OP_reg14 (+6030, +6150): DW_OP_reg14 (+6158, +6399): DW_OP_reg14 (+6401, +6626): DW_OP_reg14 (+6678, +6696): DW_OP_reg14) 0x0014470b: DW_TAG_variable DW_AT_location (0x037857d7: (+75, +90): DW_OP_breg10 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+90, +104): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+104, +116): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+116, +128): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+128, +140): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+140, +152): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+152, +164): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+164, +176): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+176, +188): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+188, +200): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+200, +212): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+212, +224): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+224, +236): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+236, +248): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+248, +260): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+260, +272): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+272, +284): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+284, +296): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+296, +308): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+308, +320): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+320, +332): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+332, +344): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+344, +356): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+356, +368): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+368, +380): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+380, +394): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+394, +406): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+406, +420): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+420, +432): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+432, +616): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+616, +628): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +928, DW_OP_deref, DW_OP_swap, DW_OP_const4u 0xffffffff, DW_OP_and, DW_OP_plus (+628, +645): DW_OP_breg9 +0, DW_OP_plus_uconst 0x58, DW_OP_breg5 +9 [message truncated]
SingleAccretion commented on issue #3884:
I think I see what is going here quite clearly now. During DWARF translation, actual as-reported-by-the-code-generator live ranges of "value labels" (side note: quite the confusing name for what are actually simply WASM locals) are intersected with the ranges in the WASM DWARF. So for a composite
DW_OP_fbreg
-based expression like the above, availability of the final result is limited by the availability of all its constituent locals. Importantly, one of those locals, the WASM LLVM stack pointer, is not always available. This is presumably due to the limitation that only register locations are supported right now. This explains the sparce ranges: in the disassembly, they correspond to spots where the the LLVM stack pointer is reloaded from the native frame for temporary use.
alexcrichton closed issue #3884:
Test Case
#include <stdio.h> int main() { int i; for(i = 0; i < 5; i++) { printf("%d\n", i); } return 0; }
compiled with:
wasi-sdk-14.0/bin/clang -g -O0 test.c -o test.wasm
Steps to Reproduce
> lldb -- wasmtime run -g test.wasm (lldb) target create "wasmtime" Current executable set to 'wasmtime' (arm64). (lldb) settings set -- target.run-args "run" "-g" "test.wasm" (lldb) settings set plugin.jit-loader.gdb.enable on (lldb) b test.c:6 Breakpoint 1: no locations (pending). WARNING: Unable to resolve breakpoint to any actual locations. (lldb) run Process 40146 launched: '/Users/jeffcharles/.cargo/bin/wasmtime' (arm64) 1 location added to breakpoint 1 Process 40146 stopped * thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 1.1 frame #0: 0x0000000100e940e0 JIT(0x1102b0000)`main at test.c:6:24 3 int main() { 4 int i; 5 for(i = 0; i < 5; i++) { -> 6 printf("%d\n", i); 7 } 8 return 0; 9 } Target 0: (wasmtime) stopped. (lldb) fr v (WasmtimeVMContext *) __vmctx = <variable not available> (int) i = <no location, value may have been optimized out>
Expected Results
Running
fr v
in lldb in this context should display:(int) i = 0
Actual Results
(int) i = <no location, value may have been optimized out>
Versions and Environment
Wasmtime version or commit: 0.34.0
Operating system: MacOS Monterrey (12.2.1)
Architecture: arm64
Extra Info
LLDB version:
> lldb --version lldb-1300.0.42.3 Swift version 5.5.2-dev
This is what happens when I try to compile and run natively to show what I'm expecting:
> clang -g -O0 test.c -o test > lldb -- test (lldb) target create "test" Current executable set to '/Users/jeffcharles/projects/wasm32-wasi/test-c-app/test' (arm64). (lldb) b test.c:6 Breakpoint 1: where = test`main + 32 at test.c:6:24, address = 0x0000000100003f6c (lldb) run Process 40384 launched: '/Users/jeffcharles/projects/wasm32-wasi/test-c-app/test' (arm64) Process 40384 stopped * thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 1.1 frame #0: 0x0000000100003f6c test`main at test.c:6:24 3 int main() { 4 int i; 5 for(i = 0; i < 5; i++) { -> 6 printf("%d\n", i); 7 } 8 return 0; 9 } Target 0: (test) stopped. (lldb) fr v (int) i = 0
Last updated: Nov 22 2024 at 16:03 UTC