From 08e16d68a993814ebcbe8aa32b4019b4fa6012b6 Mon Sep 17 00:00:00 2001 From: Sam Clegg Date: Wed, 19 Jun 2024 15:34:55 -0700 Subject: [PATCH] [lld][WebAssembly] Allow `--trace-symbol` to work with symbols with custom import names --- lld/test/wasm/trace-symbol.s | 14 +++++++++++++- lld/wasm/SymbolTable.cpp | 37 ++++++++++++++++++++++++++++++------ lld/wasm/SymbolTable.h | 5 +++++ 3 files changed, 49 insertions(+), 7 deletions(-) diff --git a/lld/test/wasm/trace-symbol.s b/lld/test/wasm/trace-symbol.s index 88e5c6f5829e3..3d79fa96f0942 100644 --- a/lld/test/wasm/trace-symbol.s +++ b/lld/test/wasm/trace-symbol.s @@ -1,19 +1,28 @@ +# Test -y symbol and -trace-symbol=symbol + # RUN: llvm-mc -filetype=obj -triple=wasm32-unknown-unknown %p/Inputs/ret32.s -o %t.ret32.o # RUN: llvm-mc -filetype=obj -triple=wasm32-unknown-unknown -o %t.start.o %s # RUN: wasm-ld -o %t.wasm %t.start.o %t.ret32.o -y ret32 -y _start | FileCheck %s -check-prefix=BOTH # RUN: wasm-ld -o %t.wasm %t.ret32.o %t.start.o -y ret32 -y _start | FileCheck %s -check-prefix=REVERSED -# check alias +# check long argument form # RUN: wasm-ld -o %t.wasm %t.start.o %t.ret32.o -trace-symbol=_start | FileCheck %s -check-prefixes=JUST-START +# check import names can be traced +# RUN: wasm-ld -o %t.wasm %t.start.o %t.ret32.o -trace-symbol=foo_external | FileCheck %s -check-prefixes=IMPORT-NAME + .functype ret32 (f32) -> (i32) +.functype foo_import () -> () +.import_name foo_import, foo_external + .globl _start _start: .functype _start () -> () f32.const 0.0 call ret32 drop + call foo_import end_function # BOTH: start.o: definition of _start @@ -26,3 +35,6 @@ _start: # JUST-START: start.o: definition of _start # JUST-START-NOT: ret32 + +# IMPORT-NAME: start.o: reference to foo_external +# IMPORT-NAME-NOT: ret32 diff --git a/lld/wasm/SymbolTable.cpp b/lld/wasm/SymbolTable.cpp index a5d37a5eba6d5..1feb17832b501 100644 --- a/lld/wasm/SymbolTable.cpp +++ b/lld/wasm/SymbolTable.cpp @@ -605,6 +605,15 @@ static void setImportAttributes(T *existing, } } +static void traceImport(std::optional importName, InputFile *file) { + if (importName.has_value()) { + auto name = importName.value(); + if (symtab->isTraced(name)) { + printTraceSymbolUndefined(name, file); + } + } +} + Symbol *SymbolTable::addUndefinedFunction(StringRef name, std::optional importName, std::optional importModule, @@ -624,6 +633,7 @@ Symbol *SymbolTable::addUndefinedFunction(StringRef name, printTraceSymbolUndefined(name, file); auto replaceSym = [&]() { + traceImport(importName, file); replaceSymbol(s, name, importName, importModule, flags, file, sig, isCalledDirectly); }; @@ -666,6 +676,7 @@ Symbol *SymbolTable::addUndefinedFunction(StringRef name, replaceSym(); } if (existingUndefined) { + traceImport(importName, file); setImportAttributes(existingUndefined, importName, importModule, flags, file); if (isCalledDirectly) @@ -718,10 +729,11 @@ Symbol *SymbolTable::addUndefinedGlobal(StringRef name, if (s->traced) printTraceSymbolUndefined(name, file); - if (wasInserted) + if (wasInserted) { + traceImport(importName, file); replaceSymbol(s, name, importName, importModule, flags, file, type); - else if (auto *lazy = dyn_cast(s)) + } else if (auto *lazy = dyn_cast(s)) lazy->extract(); else if (s->isDefined()) checkGlobalType(s, file, type); @@ -744,10 +756,11 @@ Symbol *SymbolTable::addUndefinedTable(StringRef name, if (s->traced) printTraceSymbolUndefined(name, file); - if (wasInserted) + if (wasInserted) { + traceImport(importName, file); replaceSymbol(s, name, importName, importModule, flags, file, type); - else if (auto *lazy = dyn_cast(s)) + } else if (auto *lazy = dyn_cast(s)) lazy->extract(); else if (s->isDefined()) checkTableType(s, file, type); @@ -770,10 +783,11 @@ Symbol *SymbolTable::addUndefinedTag(StringRef name, if (s->traced) printTraceSymbolUndefined(name, file); - if (wasInserted) + if (wasInserted) { + traceImport(importName, file); replaceSymbol(s, name, importName, importModule, flags, file, sig); - else if (auto *lazy = dyn_cast(s)) + } else if (auto *lazy = dyn_cast(s)) lazy->extract(); else if (s->isDefined()) checkTagType(s, file, sig); @@ -937,9 +951,20 @@ bool SymbolTable::getFunctionVariant(Symbol* sym, const WasmSignature *sig, // Set a flag for --trace-symbol so that we can print out a log message // if a new symbol with the same name is inserted into the symbol table. void SymbolTable::trace(StringRef name) { + tracingEnabled = true; symMap.insert({CachedHashStringRef(name), -1}); } +bool SymbolTable::isTraced(StringRef name) { + // Early exit in the default case to avoid symbol hashmap lookup. + if (!tracingEnabled) + return false; + auto it = symMap.find(CachedHashStringRef(name)); + if (it == symMap.end()) + return false; + return it->second == -1 || symVector[it->second]->traced; +} + void SymbolTable::wrap(Symbol *sym, Symbol *real, Symbol *wrap) { // Swap symbols as instructed by -wrap. int &origIdx = symMap[CachedHashStringRef(sym->getName())]; diff --git a/lld/wasm/SymbolTable.h b/lld/wasm/SymbolTable.h index 5d09d8b685716..06d8b6e68564a 100644 --- a/lld/wasm/SymbolTable.h +++ b/lld/wasm/SymbolTable.h @@ -50,9 +50,12 @@ class SymbolTable { void trace(StringRef name); + bool isTraced(StringRef name); + Symbol *addSharedFunction(StringRef name, uint32_t flags, InputFile *file, const WasmSignature *sig); Symbol *addSharedData(StringRef name, uint32_t flags, InputFile *file); + Symbol *addDefinedFunction(StringRef name, uint32_t flags, InputFile *file, InputFunction *function); Symbol *addDefinedData(StringRef name, uint32_t flags, InputFile *file, @@ -135,6 +138,8 @@ class SymbolTable { // For LTO. std::unique_ptr lto; + + bool tracingEnabled = false; }; extern SymbolTable *symtab;