Index: COFF/Config.h =================================================================== --- COFF/Config.h +++ COFF/Config.h @@ -115,7 +115,7 @@ // Symbols in this set are considered as live by the garbage collector. std::vector GCRoot; - std::set NoDefaultLibs; + std::set NoDefaultLibs; bool NoDefaultLibAll = false; // True if we are creating a DLL. Index: COFF/Driver.cpp =================================================================== --- COFF/Driver.cpp +++ COFF/Driver.cpp @@ -296,6 +296,17 @@ (!Config->MinGW && Sym.contains('@')); } +// The casing of the libraries path stamped in the OBJ can differ from the +// actual path on disk. With this, we ensure to always use lowercase as a key +// and for comparisons, at least on Windows. +static std::string normalizeLibPath(StringRef path) { +#if defined(_WIN32) + return path.lower(); +#else // LINUX + return path; +#endif +} + // Parses .drectve section contents and returns a list of files // specified by /defaultlib. void LinkerDriver::parseDirectives(InputFile *File) { @@ -356,7 +367,8 @@ parseMerge(Arg->getValue()); break; case OPT_nodefaultlib: - Config->NoDefaultLibs.insert(doFindLib(Arg->getValue())); + Config->NoDefaultLibs.insert( + normalizeLibPath(doFindLib(Arg->getValue()))); break; case OPT_section: parseSection(Arg->getValue()); @@ -457,7 +469,7 @@ return None; StringRef Path = doFindLib(Filename); - if (Config->NoDefaultLibs.count(Path)) + if (Config->NoDefaultLibs.count(normalizeLibPath(Path))) return None; if (Optional ID = getUniqueID(Path)) @@ -1240,7 +1252,7 @@ // Handle /nodefaultlib: for (auto *Arg : Args.filtered(OPT_nodefaultlib)) - Config->NoDefaultLibs.insert(doFindLib(Arg->getValue())); + Config->NoDefaultLibs.insert(normalizeLibPath(doFindLib(Arg->getValue()))); // Handle /nodefaultlib if (Args.hasArg(OPT_nodefaultlib_all)) Index: test/COFF/nodefaultlib.test =================================================================== --- test/COFF/nodefaultlib.test +++ test/COFF/nodefaultlib.test @@ -29,3 +29,10 @@ # RUN: env LIB=%T lld-link /out:%t.exe /entry:main \ # RUN: /subsystem:console hello64.obj /defaultlib:std64.lib + +MSVC stamps uppercase references in OBJ directives, thus ensure that passing lowercase 'libcmt' and 'oldnames' to /nodefaultlib works. +# RUN: lld-link %S/Inputs/precomp.obj %S/Inputs/precomp-a.obj %S/Inputs/precomp-b.obj /nodefaultlib:libcmt /nodefaultlib:oldnames /entry:main /debug /pdb:%t.pdb /out:%t.exe /opt:ref /opt:icf +# RUN: llvm-pdbutil dump -types %t.pdb | FileCheck %s -check-prefix UPPERCASE + +UPPERCASE-NOT: OLDNAMES +UPPERCASE-NOT: LIBCMT \ No newline at end of file