Index: lld/COFF/Config.h =================================================================== --- lld/COFF/Config.h +++ lld/COFF/Config.h @@ -94,7 +94,7 @@ std::vector Argv; // Symbols in this set are considered as live by the garbage collector. - std::set GCRoot; + std::vector GCRoot; std::set NoDefaultLibs; bool NoDefaultLibAll = false; Index: lld/COFF/Driver.cpp =================================================================== --- lld/COFF/Driver.cpp +++ lld/COFF/Driver.cpp @@ -355,7 +355,10 @@ SymbolBody *LinkerDriver::addUndefined(StringRef Name) { SymbolBody *B = Symtab->addUndefined(Name); - Config->GCRoot.insert(B); + if (!B->IsGCRoot) { + B->IsGCRoot = true; + Config->GCRoot.push_back(B); + } return B; } Index: lld/COFF/DriverUtils.cpp =================================================================== --- lld/COFF/DriverUtils.cpp +++ lld/COFF/DriverUtils.cpp @@ -594,7 +594,7 @@ } // Uniquefy by name. - std::map Map; + DenseMap Map(Config->Exports.size()); std::vector V; for (Export &E : Config->Exports) { auto Pair = Map.insert(std::make_pair(E.ExportName, &E)); Index: lld/COFF/Symbols.h =================================================================== --- lld/COFF/Symbols.h +++ lld/COFF/Symbols.h @@ -77,7 +77,8 @@ friend SymbolTable; explicit SymbolBody(Kind K, StringRef N = "") : SymbolKind(K), IsExternal(true), IsCOMDAT(false), - WrittenToSymtab(false), Name(N) {} + WrittenToSymtab(false), PendingArchiveLoad(false), IsGCRoot(false), + Name(N) {} const unsigned SymbolKind : 8; unsigned IsExternal : 1; @@ -98,6 +99,9 @@ // not load any more archive members to resolve the same symbol. unsigned PendingArchiveLoad : 1; + /// True if we've already added this symbol to the list of GC roots. + unsigned IsGCRoot : 1; + protected: StringRef Name; };