Просмотр исходного кода

Revert PR #3194 (#3199)

- Address values in call stack dump are relative to file beginning
- If running under fast-interp mode, address values are relative to
  every pre-compiled function beginning, which is not compatible
  with addr2line
liang.he 2 лет назад
Родитель
Сommit
d555c16d11
1 измененных файлов с 58 добавлено и 2 удалено
  1. 58 2
      test-tools/addr2line/addr2line.py

+ 58 - 2
test-tools/addr2line/addr2line.py

@@ -31,9 +31,10 @@ For example, there is a call-stack dump:
 - run the following command to transfer the address to line info:
   ```
   $ cd test-tools/addr2line
-  $ python3 addr2line.py --wasi-sdk <wasi-sdk installation> --wasm-file <wasm file path> call_stack.txt
+  $ python3 addr2line.py --wasi-sdk <wasi-sdk installation> --wabt <wabt installation> --wasm-file <wasm file path> call_stack.txt
   ```
-- the script will use *llvm-dwarfdump* to lookup the line info for each address in the call-stack dump.
+- the script will use *wasm-objdump* in wabt to transform address, then use *llvm-dwarfdump* to lookup the line info for each address
+  in the call-stack dump.
 - the output will be:
   ```
   #00: 0x0a04 - $f18
@@ -45,6 +46,42 @@ For example, there is a call-stack dump:
 """
 
 
+def get_code_section_start(wasm_objdump: Path, wasm_file: Path) -> int:
+    """
+    Find the start offset of Code section in a wasm file.
+
+    if the code section header likes:
+      Code start=0x0000017c end=0x00004382 (size=0x00004206) count: 47
+
+    the start offset is 0x0000017c
+    """
+    cmd = f"{wasm_objdump} -h {wasm_file}"
+    p = subprocess.run(
+        shlex.split(cmd),
+        check=True,
+        capture_output=True,
+        text=True,
+        universal_newlines=True,
+    )
+    outputs = p.stdout.split(os.linesep)
+
+    # if there is no .debug section, return -1
+    for line in outputs:
+        line = line.strip()
+        if ".debug_info" in line:
+            break
+    else:
+        print(f"No .debug_info section found {wasm_file}")
+        return -1
+
+    for line in outputs:
+        line = line.strip()
+        if "Code" in line:
+            return int(line.split()[1].split("=")[1], 16)
+
+    return -1
+
+
 def get_line_info(dwarf_dump: Path, wasm_file: Path, offset: int) -> str:
     """
     Find the location info of a given offset in a wasm file.
@@ -105,13 +142,21 @@ def parse_call_stack_line(line: str) -> ():
 def main():
     parser = argparse.ArgumentParser(description="addr2line for wasm")
     parser.add_argument("--wasi-sdk", type=Path, help="path to wasi-sdk")
+    parser.add_argument("--wabt", type=Path, help="path to wabt")
     parser.add_argument("--wasm-file", type=Path, help="path to wasm file")
     parser.add_argument("call_stack_file", type=Path, help="path to a call stack file")
     args = parser.parse_args()
 
+    wasm_objdump = args.wabt.joinpath("bin/wasm-objdump")
+    assert wasm_objdump.exists()
+
     llvm_dwarf_dump = args.wasi_sdk.joinpath("bin/llvm-dwarfdump")
     assert llvm_dwarf_dump.exists()
 
+    code_section_start = get_code_section_start(wasm_objdump, args.wasm_file)
+    if code_section_start == -1:
+        return -1
+
     assert args.call_stack_file.exists()
     with open(args.call_stack_file, "rt", encoding="ascii") as f:
         for line in f:
@@ -128,6 +173,7 @@ def main():
             _, offset, _ = splitted
 
             offset = int(offset, 16)
+            offset = offset - code_section_start
             line_info = get_line_info(llvm_dwarf_dump, args.wasm_file, offset)
             if not line_info:
                 print(line)
@@ -143,4 +189,14 @@ def main():
 
 
 if __name__ == "__main__":
+    print(
+        "**************************************************\n"
+        + "Before running this script, please make sure:\n"
+        + "  - the wasm file is compiled with debug info. (like: clang -g) \n"
+        + "  - the call-stack dump is generated by iwasm\n"
+        + "  - iwasm is compiled with -DWAMR_BUILD_DUMP_CALL_STACK=1\n"
+        + "  - iwasm isn't running under fast-interp mode. -DWAMR_BUILD_FAST_INTERP=0\n"
+        + "  - if using .aot, the aot file is generated with `--enable-dump-call-stack`\n"
+        + "**************************************************\n"
+    )
     sys.exit(main())