Index: include/llvm/MC/MCSymbolWasm.h =================================================================== --- include/llvm/MC/MCSymbolWasm.h +++ include/llvm/MC/MCSymbolWasm.h @@ -19,6 +19,7 @@ bool IsFunction = false; bool IsWeak = false; bool IsHidden = false; + bool IsComdat = false; std::string ModuleName; SmallVector Returns; SmallVector Params; @@ -49,6 +50,9 @@ bool isHidden() const { return IsHidden; } void setHidden(bool isHidden) { IsHidden = isHidden; } + bool isComdat() const { return IsComdat; } + void setComdat(bool isComdat) { IsComdat = isComdat; } + const StringRef getModuleName() const { return ModuleName; } const SmallVector &getReturns() const { Index: lib/MC/MCContext.cpp =================================================================== --- lib/MC/MCContext.cpp +++ lib/MC/MCContext.cpp @@ -490,8 +490,10 @@ const Twine &Group, unsigned UniqueID, const char *BeginSymName) { MCSymbolWasm *GroupSym = nullptr; - if (!Group.isTriviallyEmpty() && !Group.str().empty()) + if (!Group.isTriviallyEmpty() && !Group.str().empty()) { GroupSym = cast(getOrCreateSymbol(Group)); + GroupSym->setComdat(true); + } return getWasmSection(Section, K, GroupSym, UniqueID, BeginSymName); } Index: lib/MC/WasmObjectWriter.cpp =================================================================== --- lib/MC/WasmObjectWriter.cpp +++ lib/MC/WasmObjectWriter.cpp @@ -1122,7 +1122,8 @@ continue; // If the symbol is not defined in this translation unit, import it. - if (!WS.isDefined(/*SetUsed=*/false) || WS.isVariable()) { + if ((!WS.isDefined(/*SetUsed=*/false) && !WS.isComdat()) || + WS.isVariable()) { WasmImport Import; Import.ModuleName = WS.getModuleName(); Import.FieldName = WS.getName(); Index: test/MC/WebAssembly/comdat.ll =================================================================== --- test/MC/WebAssembly/comdat.ll +++ test/MC/WebAssembly/comdat.ll @@ -22,7 +22,41 @@ ret i32 0 } -; CHECK: - Type: EXPORT +; CHECK: Sections: +; CHECK-NEXT: - Type: TYPE +; CHECK-NEXT: Signatures: +; CHECK-NEXT: - Index: 0 +; CHECK-NEXT: ReturnType: I32 +; CHECK-NEXT: ParamTypes: +; CHECK-NEXT: - Type: IMPORT +; CHECK-NEXT: Imports: +; CHECK-NEXT: - Module: env +; CHECK-NEXT: Field: __linear_memory +; CHECK-NEXT: Kind: MEMORY +; CHECK-NEXT: Memory: +; CHECK-NEXT: Initial: 0x00000001 +; CHECK-NEXT: - Module: env +; CHECK-NEXT: Field: __indirect_function_table +; CHECK-NEXT: Kind: TABLE +; CHECK-NEXT: Table: +; CHECK-NEXT: ElemType: ANYFUNC +; CHECK-NEXT: Limits: +; CHECK-NEXT: Initial: 0x00000000 +; CHECK-NEXT: - Module: env +; CHECK-NEXT: Field: funcImport +; CHECK-NEXT: Kind: FUNCTION +; CHECK-NEXT: SigIndex: 0 +; CHECK-NEXT: - Type: FUNCTION +; CHECK-NEXT: FunctionTypes: [ 0, 0, 0 ] +; CHECK-NEXT: - Type: GLOBAL +; CHECK-NEXT: Globals: +; CHECK-NEXT: - Index: 0 +; CHECK-NEXT: Type: I32 +; CHECK-NEXT: Mutable: false +; CHECK-NEXT: InitExpr: +; CHECK-NEXT: Opcode: I32_CONST +; CHECK-NEXT: Value: 0 +; CHECK-NEXT: - Type: EXPORT ; CHECK-NEXT: Exports: ; CHECK-NEXT: - Name: callImport ; CHECK-NEXT: Kind: FUNCTION @@ -35,7 +69,7 @@ ; CHECK-NEXT: Index: 3 ; CHECK-NEXT: - Name: constantData ; CHECK-NEXT: Kind: GLOBAL -; CHECK-NEXT: Index: 1 +; CHECK-NEXT: Index: 0 ; CHECK-NEXT: - Type: CODE ; CHECK-NEXT: Relocations: ; CHECK-NEXT: - Type: R_WEBASSEMBLY_FUNCTION_INDEX_LEB