Index: llvm/trunk/include/llvm/BinaryFormat/Wasm.h =================================================================== --- llvm/trunk/include/llvm/BinaryFormat/Wasm.h +++ llvm/trunk/include/llvm/BinaryFormat/Wasm.h @@ -289,6 +289,7 @@ const unsigned WASM_SYMBOL_VISIBILITY_DEFAULT = 0x0; const unsigned WASM_SYMBOL_VISIBILITY_HIDDEN = 0x4; const unsigned WASM_SYMBOL_UNDEFINED = 0x10; +const unsigned WASM_SYMBOL_EXPORTED = 0x20; #define WASM_RELOC(name, value) name = value, Index: llvm/trunk/include/llvm/MC/MCSymbolWasm.h =================================================================== --- llvm/trunk/include/llvm/MC/MCSymbolWasm.h +++ llvm/trunk/include/llvm/MC/MCSymbolWasm.h @@ -46,6 +46,13 @@ wasm::WasmSymbolType getType() const { return Type; } void setType(wasm::WasmSymbolType type) { Type = type; } + bool isExported() const { + return getFlags() & wasm::WASM_SYMBOL_EXPORTED; + } + void setExported() const { + modifyFlags(wasm::WASM_SYMBOL_EXPORTED, wasm::WASM_SYMBOL_EXPORTED); + } + bool isWeak() const { return IsWeak; } void setWeak(bool isWeak) { IsWeak = isWeak; } Index: llvm/trunk/lib/MC/MCAsmInfoWasm.cpp =================================================================== --- llvm/trunk/lib/MC/MCAsmInfoWasm.cpp +++ llvm/trunk/lib/MC/MCAsmInfoWasm.cpp @@ -18,6 +18,7 @@ MCAsmInfoWasm::MCAsmInfoWasm() { HasIdentDirective = true; + HasNoDeadStrip = true; WeakRefDirective = "\t.weak\t"; PrivateGlobalPrefix = ".L"; PrivateLabelPrefix = ".L"; Index: llvm/trunk/lib/MC/MCWasmStreamer.cpp =================================================================== --- llvm/trunk/lib/MC/MCWasmStreamer.cpp +++ llvm/trunk/lib/MC/MCWasmStreamer.cpp @@ -121,6 +121,10 @@ case MCSA_Cold: break; + case MCSA_NoDeadStrip: + Symbol->setExported(); + break; + default: // unrecognized directive llvm_unreachable("unexpected MCSymbolAttr"); Index: llvm/trunk/lib/MC/WasmObjectWriter.cpp =================================================================== --- llvm/trunk/lib/MC/WasmObjectWriter.cpp +++ llvm/trunk/lib/MC/WasmObjectWriter.cpp @@ -1454,6 +1454,8 @@ Flags |= wasm::WASM_SYMBOL_BINDING_LOCAL; if (WS.isUndefined()) Flags |= wasm::WASM_SYMBOL_UNDEFINED; + if (WS.isExported()) + Flags |= wasm::WASM_SYMBOL_EXPORTED; wasm::WasmSymbolInfo Info; Info.Name = WS.getName(); Index: llvm/trunk/lib/ObjectYAML/WasmYAML.cpp =================================================================== --- llvm/trunk/lib/ObjectYAML/WasmYAML.cpp +++ llvm/trunk/lib/ObjectYAML/WasmYAML.cpp @@ -486,6 +486,7 @@ // BCaseMask(VISIBILITY_MASK, VISIBILITY_DEFAULT); BCaseMask(VISIBILITY_MASK, VISIBILITY_HIDDEN); BCaseMask(UNDEFINED, UNDEFINED); + BCaseMask(EXPORTED, EXPORTED); #undef BCaseMask } Index: llvm/trunk/test/MC/WebAssembly/no-dead-strip.ll =================================================================== --- llvm/trunk/test/MC/WebAssembly/no-dead-strip.ll +++ llvm/trunk/test/MC/WebAssembly/no-dead-strip.ll @@ -0,0 +1,21 @@ +; RUN: llc -filetype=obj -wasm-keep-registers %s -o - | llvm-readobj --symbols | FileCheck %s + +target triple = "wasm32-unknown-unknown" + +@llvm.used = appending global [1 x i8*] [i8* bitcast (i32 ()* @foo to i8*)], section "llvm.metadata" + +define i32 @foo() { +entry: + ret i32 0 +} + +; CHECK: Symbols [ +; CHECK-NEXT: Symbol { +; CHECK-NEXT: Name: foo +; CHECK-NEXT: Type: FUNCTION (0x0) +; CHECK-NEXT: Flags [ (0x20) +; CHECK-NEXT: EXPORTED (0x20) +; CHECK-NEXT: ] +; CHECK-NEXT: ElementIndex: 0x0 +; CHECK-NEXT: } +; CHECK-NEXT: ] Index: llvm/trunk/tools/llvm-readobj/WasmDumper.cpp =================================================================== --- llvm/trunk/tools/llvm-readobj/WasmDumper.cpp +++ llvm/trunk/tools/llvm-readobj/WasmDumper.cpp @@ -49,6 +49,7 @@ ENUM_ENTRY(VISIBILITY_DEFAULT), ENUM_ENTRY(VISIBILITY_HIDDEN), ENUM_ENTRY(UNDEFINED), + ENUM_ENTRY(EXPORTED), #undef ENUM_ENTRY };