Skip to content

Commit 5d83087

Browse files
committed
MSVC linking
1 parent 9579fb8 commit 5d83087

File tree

4 files changed

+84
-2
lines changed

4 files changed

+84
-2
lines changed

lib/Driver/ToolChains/CommonArgs.cpp

+1-1
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ bool tools::needFortranLibs(const Driver &D, const ArgList &Args) {
6767
}
6868

6969
/// \brief Determine if Fortran "main" object is needed
70-
static bool needFortranMain(const Driver &D, const ArgList &Args) {
70+
bool tools::needFortranMain(const Driver &D, const ArgList &Args) {
7171
return (needFortranLibs(D, Args)
7272
&& (!Args.hasArg(options::OPT_Mnomain) ||
7373
!Args.hasArg(options::OPT_no_fortran_main)));

lib/Driver/ToolChains/CommonArgs.h

+2
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,8 @@ namespace tools {
2222

2323
bool needFortranLibs(const Driver &D, const llvm::opt::ArgList &Args);
2424

25+
bool needFortranMain(const Driver &D, const llvm::opt::ArgList &Args);
26+
2527
void addPathIfExists(const Driver &D, const Twine &Path,
2628
ToolChain::path_list &Paths);
2729

lib/Driver/ToolChains/MSVC.cpp

+78-1
Original file line numberDiff line numberDiff line change
@@ -326,7 +326,7 @@ void visualstudio::Linker::ConstructJob(Compilation &C, const JobAction &JA,
326326
Args.MakeArgString(std::string("-out:") + Output.getFilename()));
327327

328328
if (!Args.hasArg(options::OPT_nostdlib, options::OPT_nostartfiles) &&
329-
!C.getDriver().IsCLMode())
329+
!C.getDriver().IsCLMode() && !C.getDriver().IsFortranMode())
330330
CmdArgs.push_back("-defaultlib:libcmt");
331331

332332
if (!llvm::sys::Process::GetEnv("LIB")) {
@@ -426,6 +426,16 @@ void visualstudio::Linker::ConstructJob(Compilation &C, const JobAction &JA,
426426
}
427427
}
428428

429+
// Add Fortran runtime libraries
430+
if (needFortranLibs(TC.getDriver(), Args)) {
431+
TC.AddFortranStdlibLibArgs(Args, CmdArgs);
432+
} else {
433+
// Claim "no Flang libraries" arguments if any
434+
for (auto Arg : Args.filtered(options::OPT_noFlangLibs)) {
435+
Arg->claim();
436+
}
437+
}
438+
429439
// Add compiler-rt lib in case if it was explicitly
430440
// specified as an argument for --rtlib option.
431441
if (!Args.hasArg(options::OPT_nostdlib)) {
@@ -736,6 +746,73 @@ void MSVCToolChain::AddCudaIncludeArgs(const ArgList &DriverArgs,
736746
CudaInstallation.AddCudaIncludeArgs(DriverArgs, CC1Args);
737747
}
738748

749+
750+
void MSVCToolChain::AddFortranStdlibLibArgs(const ArgList &Args,
751+
ArgStringList &CmdArgs) const {
752+
bool staticFlangLibs = false;
753+
bool useOpenMP = false;
754+
755+
if (Args.hasArg(options::OPT_staticFlangLibs)) {
756+
for (auto *A: Args.filtered(options::OPT_staticFlangLibs)) {
757+
A->claim();
758+
staticFlangLibs = true;
759+
}
760+
}
761+
762+
Arg *A = Args.getLastArg(options::OPT_mp, options::OPT_nomp,
763+
options::OPT_fopenmp, options::OPT_fno_openmp);
764+
if (A &&
765+
(A->getOption().matches(options::OPT_mp) ||
766+
A->getOption().matches(options::OPT_fopenmp))) {
767+
useOpenMP = true;
768+
}
769+
770+
CmdArgs.push_back(Args.MakeArgString(std::string("-libpath:") +
771+
getDriver().Dir + "/../lib"));
772+
773+
if (needFortranMain(getDriver(), Args)) {
774+
// flangmain is always static
775+
CmdArgs.push_back("-subsystem:console");
776+
CmdArgs.push_back("-defaultlib:flangmain");
777+
}
778+
779+
if (staticFlangLibs) {
780+
CmdArgs.push_back("-defaultlib:libflang");
781+
CmdArgs.push_back("-defaultlib:libflangrti");
782+
CmdArgs.push_back("-defaultlib:libpgmath");
783+
} else {
784+
CmdArgs.push_back("-defaultlib:flang");
785+
CmdArgs.push_back("-defaultlib:flangrti");
786+
CmdArgs.push_back("-defaultlib:pgmath");
787+
}
788+
if (useOpenMP) {
789+
// openmp is added in ConstructJob
790+
}
791+
else {
792+
if (staticFlangLibs) {
793+
CmdArgs.push_back("-defaultlib:libompstub");
794+
} else {
795+
CmdArgs.push_back("-defaultlib:ompstub");
796+
}
797+
}
798+
799+
// Allways link Fortran executables with Pthreads
800+
// CmdArgs.push_back("-lpthread");
801+
802+
// These options are added clang-cl in Clang.cpp for C/C++
803+
// In clang-cl.exe -MD and -MT control these options, but in
804+
// flang.exe like clang.exe these are different options for
805+
// dependency tracking. Let's assume that if somebody needs
806+
// static flang libs, they need static runtime libs as well.
807+
if (staticFlangLibs) {
808+
CmdArgs.push_back("-defaultlib:libcmt");
809+
} else {
810+
CmdArgs.push_back("-defaultlib:msvcrt");
811+
}
812+
CmdArgs.push_back("-defaultlib:oldnames");
813+
814+
}
815+
739816
void MSVCToolChain::printVerboseInfo(raw_ostream &OS) const {
740817
CudaInstallation.print(OS);
741818
}

lib/Driver/ToolChains/MSVC.h

+3
Original file line numberDiff line numberDiff line change
@@ -109,6 +109,9 @@ class LLVM_LIBRARY_VISIBILITY MSVCToolChain : public ToolChain {
109109
void AddCudaIncludeArgs(const llvm::opt::ArgList &DriverArgs,
110110
llvm::opt::ArgStringList &CC1Args) const override;
111111

112+
void AddFortranStdlibLibArgs(const llvm::opt::ArgList &Args,
113+
llvm::opt::ArgStringList &CmdArgs) const override;
114+
112115
bool getWindowsSDKLibraryPath(std::string &path) const;
113116
/// \brief Check if Universal CRT should be used if available
114117
bool getUniversalCRTLibraryPath(std::string &path) const;

0 commit comments

Comments
 (0)