diff --git a/lld/test/wasm/lto/weak-undefined.ll b/lld/test/wasm/lto/weak-undefined.ll --- a/lld/test/wasm/lto/weak-undefined.ll +++ b/lld/test/wasm/lto/weak-undefined.ll @@ -11,6 +11,17 @@ declare extern_weak i32 @foo() +declare extern_weak i32 @bar() + +; The refernce to bar here will exist in the LTO file, but the LTO process will +; remove it, so it will never be referenced by an normal object file, and +; therefore never have a signature. +define void @unused_function() #0 { +entry: + %call2 = call i32 @bar() + ret void +} + define void @_start() #0 { entry: %call2 = call i32 @foo() diff --git a/lld/wasm/SymbolTable.cpp b/lld/wasm/SymbolTable.cpp --- a/lld/wasm/SymbolTable.cpp +++ b/lld/wasm/SymbolTable.cpp @@ -842,7 +842,7 @@ void SymbolTable::replaceWithUndefined(Symbol *sym) { // Add a synthetic dummy for weak undefined functions. These dummies will // be GC'd if not used as the target of any "call" instructions. - StringRef debugName = saver().save("undefined_weak:" + toString(*sym)); + StringRef debugName = saver().save("undefined_weak:" + sym->getName()); replaceWithUnreachable(sym, *sym->getSignature(), debugName); // Hide our dummy to prevent export. sym->setHidden(true); @@ -854,7 +854,7 @@ // the call instruction that passes Wasm validation. void SymbolTable::handleWeakUndefines() { for (Symbol *sym : getSymbols()) { - if (sym->isUndefWeak()) { + if (sym->isUndefWeak() && sym->isUsedInRegularObj) { if (sym->getSignature()) { replaceWithUndefined(sym); } else {