summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--test/passes/multi_line_table.bin.txt32
-rw-r--r--test/unit/input/dwarf/cubescript.wasmbin0 -> 193546 bytes
-rw-r--r--test/unit/input/dwarf/zlib.wasmbin0 -> 171100 bytes
-rw-r--r--test/unit/test_dwarf.py16
-rw-r--r--third_party/llvm-project/DWARFEmitter.cpp8
-rw-r--r--third_party/llvm-project/DWARFVisitor.cpp25
-rw-r--r--third_party/llvm-project/dwarf2yaml.cpp8
7 files changed, 75 insertions, 14 deletions
diff --git a/test/passes/multi_line_table.bin.txt b/test/passes/multi_line_table.bin.txt
index 5d5f53f8b..3212e1c14 100644
--- a/test/passes/multi_line_table.bin.txt
+++ b/test/passes/multi_line_table.bin.txt
@@ -211,7 +211,7 @@ DWARF debug info
================
Contains section .debug_info (130 bytes)
-Contains section .debug_abbrev (99 bytes)
+Contains section .debug_abbrev (100 bytes)
Contains section .debug_line (145 bytes)
Contains section .debug_str (407 bytes)
@@ -240,6 +240,7 @@ Abbrev table for offset: 0x00000000
DW_AT_encoding DW_FORM_data1
DW_AT_byte_size DW_FORM_data1
+Abbrev table for offset: 0x00000032
[1] DW_TAG_compile_unit DW_CHILDREN_yes
DW_AT_producer DW_FORM_strp
DW_AT_language DW_FORM_data2
@@ -291,9 +292,32 @@ Abbrev table for offset: 0x00000000
DW_AT_byte_size [DW_FORM_data1] (0x04)
0x00000040: NULL
-0x00000041: Compile Unit: length = 0x0000003d version = 0x0004 addr_size = 0x04 (next unit at 0x00000082)
-<compile unit can't be parsed!>
+0x00000041: Compile Unit: length = 0x0000003d version = 0x0004 abbr_offset = 0x0032 addr_size = 0x04 (next unit at 0x00000082)
+
+0x0000004c: DW_TAG_compile_unit [1] *
+ DW_AT_producer [DW_FORM_strp] ( .debug_str[0x000000cc] = "clang version 10.0.0 (/b/s/w/ir/cache/git/chromium.googlesource.com-external-github.com-llvm-llvm--project 7fcd9e3f70830a9c4bf631a602c2764180b5c3a8)")
+ DW_AT_language [DW_FORM_data2] (DW_LANG_C_plus_plus)
+ DW_AT_name [DW_FORM_strp] ( .debug_str[0x00000161] = "third.cpp")
+ DW_AT_stmt_list [DW_FORM_sec_offset] (0x00000049)
+ DW_AT_comp_dir [DW_FORM_strp] ( .debug_str[0x0000016b] = "/tmp/emscripten_test_wasm0_xkAHBX")
+ DW_AT_low_pc [DW_FORM_addr] (0x0000000000000016)
+ DW_AT_high_pc [DW_FORM_data4] (0x0000000b)
+
+0x00000067: DW_TAG_subprogram [2]
+ DW_AT_low_pc [DW_FORM_addr] (0x0000000000000016)
+ DW_AT_high_pc [DW_FORM_data4] (0x0000000b)
+ DW_AT_name [DW_FORM_strp] ( .debug_str[0x0000018d] = "sidef")
+ DW_AT_decl_file [DW_FORM_data1] ("/tmp/emscripten_test_wasm0_xkAHBX/third.cpp")
+ DW_AT_decl_line [DW_FORM_data1] (1)
+ DW_AT_type [DW_FORM_ref4] (cu + 0x0039 => {0x0000007a} "int")
+ DW_AT_external [DW_FORM_flag_present] (true)
+0x0000007a: DW_TAG_base_type [3]
+ DW_AT_name [DW_FORM_strp] ( .debug_str[0x00000193] = "int")
+ DW_AT_encoding [DW_FORM_data1] (DW_ATE_signed)
+ DW_AT_byte_size [DW_FORM_data1] (0x04)
+
+0x00000081: NULL
.debug_line contents:
debug_line[0x00000000]
@@ -444,7 +468,7 @@ file_names[ 1]:
)
;; custom section "dylink", size 5
;; custom section ".debug_info", size 130
- ;; custom section ".debug_abbrev", size 99
+ ;; custom section ".debug_abbrev", size 100
;; custom section ".debug_line", size 145
;; custom section ".debug_str", size 407
;; custom section "producers", size 180
diff --git a/test/unit/input/dwarf/cubescript.wasm b/test/unit/input/dwarf/cubescript.wasm
new file mode 100644
index 000000000..4fcbf2216
--- /dev/null
+++ b/test/unit/input/dwarf/cubescript.wasm
Binary files differ
diff --git a/test/unit/input/dwarf/zlib.wasm b/test/unit/input/dwarf/zlib.wasm
new file mode 100644
index 000000000..40674c0a4
--- /dev/null
+++ b/test/unit/input/dwarf/zlib.wasm
Binary files differ
diff --git a/test/unit/test_dwarf.py b/test/unit/test_dwarf.py
new file mode 100644
index 000000000..5078efeeb
--- /dev/null
+++ b/test/unit/test_dwarf.py
@@ -0,0 +1,16 @@
+import os
+
+from scripts.test import shared
+from . import utils
+
+
+class DWARFTest(utils.BinaryenTestCase):
+ def test_no_crash(self):
+ # run dwarf processing on some interesting large files, too big to be
+ # worth putting in passes where the text output would be massive. We
+ # just check that no assertion are hit.
+ path = self.input_path('dwarf')
+ for name in os.listdir(path):
+ args = [os.path.join(path, name)] + \
+ ['-g', '--dwarfdump', '--roundtrip', '--dwarfdump']
+ shared.run_process(shared.WASM_OPT + args, capture_output=True)
diff --git a/third_party/llvm-project/DWARFEmitter.cpp b/third_party/llvm-project/DWARFEmitter.cpp
index 92efcdfa0..6e4ee6119 100644
--- a/third_party/llvm-project/DWARFEmitter.cpp
+++ b/third_party/llvm-project/DWARFEmitter.cpp
@@ -78,6 +78,10 @@ void DWARFYAML::EmitDebugStr(raw_ostream &OS, const DWARFYAML::Data &DI) {
void DWARFYAML::EmitDebugAbbrev(raw_ostream &OS, const DWARFYAML::Data &DI) {
for (auto AbbrevDecl : DI.AbbrevDecls) {
encodeULEB128(AbbrevDecl.Code, OS);
+ // XXX BINARYEN This is a terminator.
+ if (!AbbrevDecl.Code) {
+ continue;
+ }
encodeULEB128(AbbrevDecl.Tag, OS);
OS.write(AbbrevDecl.Children);
for (auto Attr : AbbrevDecl.Attributes) {
@@ -89,10 +93,6 @@ void DWARFYAML::EmitDebugAbbrev(raw_ostream &OS, const DWARFYAML::Data &DI) {
encodeULEB128(0, OS);
encodeULEB128(0, OS);
}
- // XXX BINARYEN: end the list with a zero. LLVM works with or without this,
- // but other decoders may error. See
- // https://bugs.llvm.org/show_bug.cgi?id=44511
- writeInteger((uint8_t)0, OS, true /* isLittleEndian */);
}
void DWARFYAML::EmitDebugAranges(raw_ostream &OS, const DWARFYAML::Data &DI) {
diff --git a/third_party/llvm-project/DWARFVisitor.cpp b/third_party/llvm-project/DWARFVisitor.cpp
index 05c4194e3..44bb33b47 100644
--- a/third_party/llvm-project/DWARFVisitor.cpp
+++ b/third_party/llvm-project/DWARFVisitor.cpp
@@ -44,25 +44,38 @@ static unsigned getRefSize(const DWARFYAML::Unit &Unit) {
}
template <typename T> void DWARFYAML::VisitorImpl<T>::traverseDebugInfo() {
+ // XXX BINARYEN: Handle multiple linked compile units. Each one has its own
+ // range of values, terminated by a zero. AbbrevStart refers to the start
+ // index for the current unit, and AbbrevEnd to one past the last one
+ // (which is the index of the 0 terminator).
+ // TODO: This code appears to assume that abbreviation codes increment by 1
+ // so that lookups are linear. In LLVM output that is true, but it might not
+ // be in general.
+ size_t AbbrevStart = 0, AbbrevEnd = -1;
for (auto &Unit : DebugInfo.CompileUnits) {
+ // Skip the 0 terminator.
+ AbbrevEnd = AbbrevStart = AbbrevEnd + 1;
+ while (AbbrevEnd < DebugInfo.AbbrevDecls.size() &&
+ DebugInfo.AbbrevDecls[AbbrevEnd].Code) {
+ AbbrevEnd++;
+ }
onStartCompileUnit(Unit);
if (Unit.Entries.empty()) { // XXX BINARYEN
continue;
}
auto FirstAbbrevCode = Unit.Entries[0].AbbrCode;
-
for (auto &Entry : Unit.Entries) {
onStartDIE(Unit, Entry);
if (Entry.AbbrCode == 0u)
continue;
// XXX BINARYEN
- if (Entry.AbbrCode - FirstAbbrevCode >= DebugInfo.AbbrevDecls.size()) {
- errs() << "warning: invalid abbreviation code " << Entry.AbbrCode <<
- " (range: " << FirstAbbrevCode << "-" <<
- (DebugInfo.AbbrevDecls.size() - FirstAbbrevCode) << ")\n";
+ if (Entry.AbbrCode - FirstAbbrevCode + AbbrevStart >= AbbrevEnd) {
+ errs() << "warning: invalid abbreviation code " << Entry.AbbrCode
+ << " (range: " << FirstAbbrevCode << " : " << AbbrevStart
+ << ".." << AbbrevEnd << ")\n";
continue;
}
- auto &Abbrev = DebugInfo.AbbrevDecls[Entry.AbbrCode - FirstAbbrevCode];
+ auto &Abbrev = DebugInfo.AbbrevDecls[Entry.AbbrCode - FirstAbbrevCode + AbbrevStart];
auto FormVal = Entry.Values.begin();
auto AbbrForm = Abbrev.Attributes.begin();
for (;
diff --git a/third_party/llvm-project/dwarf2yaml.cpp b/third_party/llvm-project/dwarf2yaml.cpp
index b43b0e420..52e875637 100644
--- a/third_party/llvm-project/dwarf2yaml.cpp
+++ b/third_party/llvm-project/dwarf2yaml.cpp
@@ -43,6 +43,14 @@ void dumpDebugAbbrev(DWARFContext &DCtx, DWARFYAML::Data &Y) {
}
Y.AbbrevDecls.push_back(Abbrv);
}
+ // XXX BINARYEN: null-terminate the DeclSet. This is needed to separate
+ // DeclSets from each other, and to null-terminate the entire list
+ // (LLVM works with or without this, but other decoders may error, see
+ // https://bugs.llvm.org/show_bug.cgi?id=44511).
+ DWARFYAML::Abbrev Abbrv;
+ Abbrv.Code = 0;
+ Abbrv.Tag = dwarf::Tag(0);
+ Y.AbbrevDecls.push_back(Abbrv);
}
}
}