@@ -81,10 +81,36 @@ toolchains::Windows::constructInvocation(const DynamicLinkJobAction &job,
8181    llvm_unreachable (" invalid link kind" 
8282  }
8383
84+   //  Check to see whether we need to use lld as the linker.
85+   auto  requiresLLD = [&]{
86+     if  (const  Arg *A = context.Args .getLastArg (options::OPT_use_ld)) {
87+       return  llvm::StringSwitch<bool >(A->getValue ())
88+         .Cases (" lld" " lld.exe" " lld-link" " lld-link.exe" true )
89+         .Default (false );
90+     }
91+     //  Force to use lld for LTO on Windows because we don't support link LTO or
92+     //  something else except for lld LTO at this time.
93+     if  (context.OI .LTOVariant  != OutputInfo::LTOKind::None) {
94+       return  true ;
95+     }
96+     //  Profiling currently relies on the ability to emit duplicate weak
97+     //  symbols across translation units and having the linker coalesce them.
98+     //  Unfortunately link.exe does not support this, so require lld-link
99+     //  for now, which supports the behavior via a flag.
100+     //  TODO: Once we've changed coverage to no longer rely on emitting
101+     //  duplicate weak symbols (rdar://131295678), we can remove this.
102+     if  (context.Args .getLastArg (options::OPT_profile_generate)) {
103+       return  true ;
104+     }
105+     return  false ;
106+   }();
107+ 
84108  //  Select the linker to use.
85109  std::string Linker;
86110  if  (const  Arg *A = context.Args .getLastArg (options::OPT_use_ld)) {
87111    Linker = A->getValue ();
112+   } else  if  (requiresLLD) {
113+     Linker = " lld" 
88114  }
89115
90116  switch  (context.OI .LTOVariant ) {
@@ -98,12 +124,6 @@ toolchains::Windows::constructInvocation(const DynamicLinkJobAction &job,
98124    break ;
99125  }
100126
101-   if  (Linker.empty () && context.OI .LTOVariant  != OutputInfo::LTOKind::None) {
102-     //  Force to use lld for LTO on Windows because we don't support link LTO or
103-     //  something else except for lld LTO at this time.
104-     Linker = " lld" 
105-   }
106- 
107127  if  (!Linker.empty ())
108128    Arguments.push_back (context.Args .MakeArgString (" -fuse-ld=" 
109129
@@ -186,6 +206,14 @@ toolchains::Windows::constructInvocation(const DynamicLinkJobAction &job,
186206    Arguments.push_back (context.Args .MakeArgString (
187207        Twine ({" -include:" llvm::getInstrProfRuntimeHookVarName ()})));
188208    Arguments.push_back (context.Args .MakeArgString (" -lclang_rt.profile" 
209+ 
210+     //  FIXME(rdar://131295678): Currently profiling requires the ability to
211+     //  emit duplicate weak symbols. Assuming we're using lld, pass
212+     //  -lld-allow-duplicate-weak to enable this behavior.
213+     if  (requiresLLD) {
214+       Arguments.push_back (" -Xlinker" 
215+       Arguments.push_back (" -lld-allow-duplicate-weak" 
216+     }
189217  }
190218
191219  context.Args .AddAllArgs (Arguments, options::OPT_Xlinker);
0 commit comments