blob: 558f47306bf1b4270ff2137cfdf115bc16467cad [file] [log] [blame]
Hans Wennborgdcfba332015-10-06 23:40:43 +00001//===--- ToolChains.cpp - ToolChain Implementations -------------*- C++ -*-===//
Daniel Dunbar59e5e882009-03-20 00:20:03 +00002//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9
10#include "ToolChains.h"
Justin Lebarc43ad9e2016-07-07 18:17:52 +000011#include "clang/Basic/Cuda.h"
Chandler Carruth3a022472012-12-04 09:13:33 +000012#include "clang/Basic/ObjCRuntime.h"
13#include "clang/Basic/Version.h"
Benjamin Kramerd45b2052015-10-07 15:48:01 +000014#include "clang/Basic/VirtualFileSystem.h"
Alp Toker1d257e12014-06-04 03:28:55 +000015#include "clang/Config/config.h" // for GCC_INSTALL_PREFIX
Daniel Dunbar6232d342010-05-20 21:48:38 +000016#include "clang/Driver/Compilation.h"
Daniel Dunbar76ce7412009-03-23 16:15:50 +000017#include "clang/Driver/Driver.h"
Daniel Dunbaraabb0b12009-03-25 06:12:34 +000018#include "clang/Driver/DriverDiagnostic.h"
Daniel Dunbarda13faf2009-11-19 04:25:22 +000019#include "clang/Driver/Options.h"
Alexey Samsonov609213f92013-08-19 09:14:21 +000020#include "clang/Driver/SanitizerArgs.h"
Chandler Carruth3a022472012-12-04 09:13:33 +000021#include "llvm/ADT/STLExtras.h"
Daniel Dunbar82eb4ce2010-08-23 22:35:37 +000022#include "llvm/ADT/SmallString.h"
Daniel Dunbar76ce7412009-03-23 16:15:50 +000023#include "llvm/ADT/StringExtras.h"
Bob Wilson997a97f2011-10-07 00:37:57 +000024#include "llvm/ADT/StringSwitch.h"
Reid Kleckner898229a2013-06-14 17:17:23 +000025#include "llvm/Option/Arg.h"
26#include "llvm/Option/ArgList.h"
27#include "llvm/Option/OptTable.h"
28#include "llvm/Option/Option.h"
Xinliang David Li170cd102015-10-27 05:15:35 +000029#include "llvm/ProfileData/InstrProf.h"
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +000030#include "llvm/Support/ErrorHandling.h"
Michael J. Spencerf6efe582011-01-10 02:34:13 +000031#include "llvm/Support/FileSystem.h"
Rafael Espindolac8f008f2010-11-07 20:14:31 +000032#include "llvm/Support/MemoryBuffer.h"
Michael J. Spencer8aaf4992010-11-29 18:12:39 +000033#include "llvm/Support/Path.h"
Chandler Carruth5553d0d2014-01-07 11:51:46 +000034#include "llvm/Support/Program.h"
Renato Golin33e1f822015-05-28 15:49:28 +000035#include "llvm/Support/TargetParser.h"
Chandler Carruth3a022472012-12-04 09:13:33 +000036#include "llvm/Support/raw_ostream.h"
Daniel Dunbarb5023e92009-04-10 21:00:07 +000037#include <cstdlib> // ::getenv
Rafael Espindola8a8e5542014-06-12 17:19:42 +000038#include <system_error>
Daniel Dunbarb5023e92009-04-10 21:00:07 +000039
Daniel Dunbar59e5e882009-03-20 00:20:03 +000040using namespace clang::driver;
41using namespace clang::driver::toolchains;
Chris Lattner0e62c1c2011-07-23 10:55:15 +000042using namespace clang;
Reid Kleckner898229a2013-06-14 17:17:23 +000043using namespace llvm::opt;
Daniel Dunbar59e5e882009-03-20 00:20:03 +000044
Douglas Katzmana67e50c2015-06-26 15:47:46 +000045MachO::MachO(const Driver &D, const llvm::Triple &Triple, const ArgList &Args)
46 : ToolChain(D, Triple, Args) {
Tim Northover15ff71d2014-05-22 13:12:14 +000047 // We expect 'as', 'ld', etc. to be adjacent to our install dir.
48 getProgramPaths().push_back(getDriver().getInstalledDir());
49 if (getDriver().getInstalledDir() != getDriver().Dir)
50 getProgramPaths().push_back(getDriver().Dir);
Tim Northover157d9112014-01-16 08:48:16 +000051}
Daniel Dunbar03e0a4f2009-03-20 00:57:52 +000052
Tim Northover157d9112014-01-16 08:48:16 +000053/// Darwin - Darwin tool chain for i386 and x86_64.
Alexey Samsonov905c8022015-06-18 21:46:05 +000054Darwin::Darwin(const Driver &D, const llvm::Triple &Triple, const ArgList &Args)
55 : MachO(D, Triple, Args), TargetInitialized(false) {}
Daniel Dunbar6276f992009-09-18 08:15:13 +000056
Mehdi Amini6fcd4eb2016-10-07 21:41:00 +000057types::ID MachO::LookupTypeForExtension(StringRef Ext) const {
Daniel Dunbarcc7df6c2010-08-02 05:43:56 +000058 types::ID Ty = types::lookupTypeForExtension(Ext);
59
60 // Darwin always preprocesses assembly files (unless -x is used explicitly).
61 if (Ty == types::TY_PP_Asm)
62 return types::TY_Asm;
63
64 return Ty;
65}
66
Douglas Katzmana67e50c2015-06-26 15:47:46 +000067bool MachO::HasNativeLLVMSupport() const { return true; }
Daniel Dunbar62123a12010-09-17 00:24:52 +000068
Jonas Hahnfeldaae83742016-02-12 07:48:37 +000069ToolChain::CXXStdlibType Darwin::GetDefaultCXXStdlibType() const {
70 // Default to use libc++ on OS X 10.9+ and iOS 7+.
71 if ((isTargetMacOS() && !isMacosxVersionLT(10, 9)) ||
72 (isTargetIOSBased() && !isIPhoneOSVersionLT(7, 0)) ||
73 isTargetWatchOSBased())
74 return ToolChain::CST_Libcxx;
75
76 return ToolChain::CST_Libstdcxx;
77}
78
John McCall24fc0de2011-07-06 00:26:06 +000079/// Darwin provides an ARC runtime starting in MacOS X 10.7 and iOS 5.0.
John McCall5fb5df92012-06-20 06:18:46 +000080ObjCRuntime Darwin::getDefaultObjCRuntime(bool isNonFragile) const {
Tim Northover6f3ff222015-10-30 16:30:27 +000081 if (isTargetWatchOSBased())
Tim Northover756447a2015-10-30 16:30:36 +000082 return ObjCRuntime(ObjCRuntime::WatchOS, TargetVersion);
Tim Northover9c7e0352013-12-12 11:55:52 +000083 if (isTargetIOSBased())
John McCall5fb5df92012-06-20 06:18:46 +000084 return ObjCRuntime(ObjCRuntime::iOS, TargetVersion);
Bob Wilson5ad5a952012-11-09 01:59:30 +000085 if (isNonFragile)
86 return ObjCRuntime(ObjCRuntime::MacOSX, TargetVersion);
87 return ObjCRuntime(ObjCRuntime::FragileMacOSX, TargetVersion);
John McCall24fc0de2011-07-06 00:26:06 +000088}
89
John McCall7959fee2011-09-09 20:41:01 +000090/// Darwin provides a blocks runtime starting in MacOS X 10.6 and iOS 3.2.
91bool Darwin::hasBlocksRuntime() const {
Tim Northover6f3ff222015-10-30 16:30:27 +000092 if (isTargetWatchOSBased())
93 return true;
94 else if (isTargetIOSBased())
John McCall7959fee2011-09-09 20:41:01 +000095 return !isIPhoneOSVersionLT(3, 2);
Tim Northover9c7e0352013-12-12 11:55:52 +000096 else {
Tim Northover157d9112014-01-16 08:48:16 +000097 assert(isTargetMacOS() && "unexpected darwin target");
98 return !isMacosxVersionLT(10, 6);
Tim Northover9c7e0352013-12-12 11:55:52 +000099 }
John McCall7959fee2011-09-09 20:41:01 +0000100}
101
Renato Golin33e1f822015-05-28 15:49:28 +0000102// This is just a MachO name translation routine and there's no
103// way to join this into ARMTargetParser without breaking all
104// other assumptions. Maybe MachO should consider standardising
105// their nomenclature.
106static const char *ArmMachOArchName(StringRef Arch) {
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000107 return llvm::StringSwitch<const char *>(Arch)
108 .Case("armv6k", "armv6")
109 .Case("armv6m", "armv6m")
110 .Case("armv5tej", "armv5")
111 .Case("xscale", "xscale")
112 .Case("armv4t", "armv4t")
113 .Case("armv7", "armv7")
114 .Cases("armv7a", "armv7-a", "armv7")
115 .Cases("armv7r", "armv7-r", "armv7")
116 .Cases("armv7em", "armv7e-m", "armv7em")
117 .Cases("armv7k", "armv7-k", "armv7k")
118 .Cases("armv7m", "armv7-m", "armv7m")
119 .Cases("armv7s", "armv7-s", "armv7s")
120 .Default(nullptr);
Daniel Dunbardcc3b652010-01-22 02:04:58 +0000121}
122
Renato Golin33e1f822015-05-28 15:49:28 +0000123static const char *ArmMachOArchNameCPU(StringRef CPU) {
Chandler Carruthaa0caeb2015-08-30 02:16:36 +0000124 unsigned ArchKind = llvm::ARM::parseCPUArch(CPU);
Renato Golin33e1f822015-05-28 15:49:28 +0000125 if (ArchKind == llvm::ARM::AK_INVALID)
126 return nullptr;
Chandler Carruthaa0caeb2015-08-30 02:16:36 +0000127 StringRef Arch = llvm::ARM::getArchName(ArchKind);
Renato Golin33e1f822015-05-28 15:49:28 +0000128
129 // FIXME: Make sure this MachO triple mangling is really necessary.
130 // ARMv5* normalises to ARMv5.
131 if (Arch.startswith("armv5"))
132 Arch = Arch.substr(0, 5);
133 // ARMv6*, except ARMv6M, normalises to ARMv6.
134 else if (Arch.startswith("armv6") && !Arch.endswith("6m"))
135 Arch = Arch.substr(0, 5);
136 // ARMv7A normalises to ARMv7.
137 else if (Arch.endswith("v7a"))
138 Arch = Arch.substr(0, 5);
139 return Arch.data();
Daniel Dunbardcc3b652010-01-22 02:04:58 +0000140}
141
Tim Northover9c7e0352013-12-12 11:55:52 +0000142static bool isSoftFloatABI(const ArgList &Args) {
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +0000143 Arg *A = Args.getLastArg(options::OPT_msoft_float, options::OPT_mhard_float,
Tim Northover9c7e0352013-12-12 11:55:52 +0000144 options::OPT_mfloat_abi_EQ);
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +0000145 if (!A)
146 return false;
Rafael Auler3f7abf72014-09-29 21:50:34 +0000147
Tim Northover9c7e0352013-12-12 11:55:52 +0000148 return A->getOption().matches(options::OPT_msoft_float) ||
149 (A->getOption().matches(options::OPT_mfloat_abi_EQ) &&
150 A->getValue() == StringRef("soft"));
151}
152
Tim Northover157d9112014-01-16 08:48:16 +0000153StringRef MachO::getMachOArchName(const ArgList &Args) const {
Daniel Dunbardcc3b652010-01-22 02:04:58 +0000154 switch (getTriple().getArch()) {
155 default:
Rafael Espindolaed1233e2014-08-28 21:23:05 +0000156 return getDefaultUniversalArchName();
NAKAMURA Takumi8b73b3e2011-06-03 03:49:51 +0000157
Tim Northover40956e62014-07-23 12:32:58 +0000158 case llvm::Triple::aarch64:
159 return "arm64";
160
Douglas Gregord9bb1522011-03-06 19:11:49 +0000161 case llvm::Triple::thumb:
Hans Wennborgdcfba332015-10-06 23:40:43 +0000162 case llvm::Triple::arm:
Daniel Dunbardcc3b652010-01-22 02:04:58 +0000163 if (const Arg *A = Args.getLastArg(options::OPT_march_EQ))
Renato Golin33e1f822015-05-28 15:49:28 +0000164 if (const char *Arch = ArmMachOArchName(A->getValue()))
Daniel Dunbardcc3b652010-01-22 02:04:58 +0000165 return Arch;
166
167 if (const Arg *A = Args.getLastArg(options::OPT_mcpu_EQ))
Renato Golin33e1f822015-05-28 15:49:28 +0000168 if (const char *Arch = ArmMachOArchNameCPU(A->getValue()))
Daniel Dunbardcc3b652010-01-22 02:04:58 +0000169 return Arch;
170
171 return "arm";
172 }
Daniel Dunbardcc3b652010-01-22 02:04:58 +0000173}
174
Angel Garcia Gomez637d1e62015-10-20 13:23:58 +0000175Darwin::~Darwin() {}
Daniel Dunbar03e0a4f2009-03-20 00:57:52 +0000176
Angel Garcia Gomez637d1e62015-10-20 13:23:58 +0000177MachO::~MachO() {}
Tim Northover157d9112014-01-16 08:48:16 +0000178
Chad Rosierd3a0f952011-09-20 20:44:06 +0000179std::string Darwin::ComputeEffectiveClangTriple(const ArgList &Args,
180 types::ID InputType) const {
181 llvm::Triple Triple(ComputeLLVMTriple(Args, InputType));
Daniel Dunbar82eb4ce2010-08-23 22:35:37 +0000182
183 // If the target isn't initialized (e.g., an unknown Darwin platform, return
184 // the default triple).
185 if (!isTargetInitialized())
186 return Triple.getTriple();
NAKAMURA Takumi8b73b3e2011-06-03 03:49:51 +0000187
Tim Northover157d9112014-01-16 08:48:16 +0000188 SmallString<16> Str;
Tim Northover6f3ff222015-10-30 16:30:27 +0000189 if (isTargetWatchOSBased())
190 Str += "watchos";
191 else if (isTargetTvOSBased())
192 Str += "tvos";
193 else if (isTargetIOSBased())
194 Str += "ios";
195 else
196 Str += "macosx";
Tim Northover157d9112014-01-16 08:48:16 +0000197 Str += getTargetVersion().getAsString();
198 Triple.setOSName(Str);
Daniel Dunbar82eb4ce2010-08-23 22:35:37 +0000199
200 return Triple.getTriple();
201}
202
David Blaikie68e081d2011-12-20 02:48:34 +0000203void Generic_ELF::anchor() {}
204
Tim Northover157d9112014-01-16 08:48:16 +0000205Tool *MachO::getTool(Action::ActionClass AC) const {
Rafael Espindola260e28d2013-03-18 20:48:54 +0000206 switch (AC) {
Rafael Espindolac8e3a012013-03-18 18:50:01 +0000207 case Action::LipoJobClass:
Rafael Espindola7cf32212013-03-20 03:05:54 +0000208 if (!Lipo)
209 Lipo.reset(new tools::darwin::Lipo(*this));
210 return Lipo.get();
Rafael Espindolac8e3a012013-03-18 18:50:01 +0000211 case Action::DsymutilJobClass:
Rafael Espindola7cf32212013-03-20 03:05:54 +0000212 if (!Dsymutil)
213 Dsymutil.reset(new tools::darwin::Dsymutil(*this));
214 return Dsymutil.get();
Ben Langmuir9b9a8d32014-02-06 18:53:25 +0000215 case Action::VerifyDebugInfoJobClass:
Rafael Espindola7cf32212013-03-20 03:05:54 +0000216 if (!VerifyDebug)
217 VerifyDebug.reset(new tools::darwin::VerifyDebug(*this));
218 return VerifyDebug.get();
Rafael Espindolad15a8912013-03-19 00:36:57 +0000219 default:
Rafael Espindola7cf32212013-03-20 03:05:54 +0000220 return ToolChain::getTool(AC);
Daniel Dunbar03e0a4f2009-03-20 00:57:52 +0000221 }
Daniel Dunbar03e0a4f2009-03-20 00:57:52 +0000222}
223
Douglas Katzman95354292015-06-23 20:42:09 +0000224Tool *MachO::buildLinker() const { return new tools::darwin::Linker(*this); }
Rafael Espindola7cf32212013-03-20 03:05:54 +0000225
Tim Northover157d9112014-01-16 08:48:16 +0000226Tool *MachO::buildAssembler() const {
Douglas Katzman95354292015-06-23 20:42:09 +0000227 return new tools::darwin::Assembler(*this);
Rafael Espindola7cf32212013-03-20 03:05:54 +0000228}
Daniel Dunbar26d482a2009-09-18 08:15:03 +0000229
Douglas Katzman95354292015-06-23 20:42:09 +0000230DarwinClang::DarwinClang(const Driver &D, const llvm::Triple &Triple,
Rafael Espindola84b588b2013-03-18 18:10:27 +0000231 const ArgList &Args)
Douglas Katzman95354292015-06-23 20:42:09 +0000232 : Darwin(D, Triple, Args) {}
Daniel Dunbar6276f992009-09-18 08:15:13 +0000233
Tim Northover336f1892014-03-29 13:16:12 +0000234void DarwinClang::addClangWarningOptions(ArgStringList &CC1Args) const {
Tim Northover6f3ff222015-10-30 16:30:27 +0000235 // For modern targets, promote certain warnings to errors.
236 if (isTargetWatchOSBased() || getTriple().isArch64Bit()) {
Tim Northover336f1892014-03-29 13:16:12 +0000237 // Always enable -Wdeprecated-objc-isa-usage and promote it
238 // to an error.
239 CC1Args.push_back("-Wdeprecated-objc-isa-usage");
240 CC1Args.push_back("-Werror=deprecated-objc-isa-usage");
241
Tim Northover6f3ff222015-10-30 16:30:27 +0000242 // For iOS and watchOS, also error about implicit function declarations,
243 // as that can impact calling conventions.
244 if (!isTargetMacOS())
245 CC1Args.push_back("-Werror=implicit-function-declaration");
Tim Northover336f1892014-03-29 13:16:12 +0000246 }
247}
248
Tim Northover157d9112014-01-16 08:48:16 +0000249/// \brief Determine whether Objective-C automated reference counting is
250/// enabled.
251static bool isObjCAutoRefCount(const ArgList &Args) {
252 return Args.hasFlag(options::OPT_fobjc_arc, options::OPT_fno_objc_arc, false);
253}
254
John McCall31168b02011-06-15 23:02:42 +0000255void DarwinClang::AddLinkARCArgs(const ArgList &Args,
256 ArgStringList &CmdArgs) const {
Tim Northover157d9112014-01-16 08:48:16 +0000257 // Avoid linking compatibility stubs on i386 mac.
258 if (isTargetMacOS() && getArch() == llvm::Triple::x86)
259 return;
260
261 ObjCRuntime runtime = getDefaultObjCRuntime(/*nonfragile*/ true);
262
263 if ((runtime.hasNativeARC() || !isObjCAutoRefCount(Args)) &&
264 runtime.hasSubscripting())
265 return;
Eric Christopher551ef452011-08-23 17:56:55 +0000266
267 CmdArgs.push_back("-force_load");
Rafael Espindola358256c2013-06-26 02:13:00 +0000268 SmallString<128> P(getDriver().ClangExecutable);
269 llvm::sys::path::remove_filename(P); // 'clang'
270 llvm::sys::path::remove_filename(P); // 'bin'
Benjamin Kramer17381a02013-06-28 16:25:46 +0000271 llvm::sys::path::append(P, "lib", "arc", "libarclite_");
John McCall31168b02011-06-15 23:02:42 +0000272 // Mash in the platform.
Tim Northover6f3ff222015-10-30 16:30:27 +0000273 if (isTargetWatchOSSimulator())
274 P += "watchsimulator";
275 else if (isTargetWatchOS())
276 P += "watchos";
277 else if (isTargetTvOSSimulator())
278 P += "appletvsimulator";
279 else if (isTargetTvOS())
280 P += "appletvos";
281 else if (isTargetIOSSimulator())
Rafael Espindola358256c2013-06-26 02:13:00 +0000282 P += "iphonesimulator";
Argyrios Kyrtzidis058b4512011-10-18 17:40:15 +0000283 else if (isTargetIPhoneOS())
Rafael Espindola358256c2013-06-26 02:13:00 +0000284 P += "iphoneos";
John McCall31168b02011-06-15 23:02:42 +0000285 else
Rafael Espindola358256c2013-06-26 02:13:00 +0000286 P += "macosx";
287 P += ".a";
John McCall31168b02011-06-15 23:02:42 +0000288
Rafael Espindola358256c2013-06-26 02:13:00 +0000289 CmdArgs.push_back(Args.MakeArgString(P));
John McCall31168b02011-06-15 23:02:42 +0000290}
291
Adrian Prantld50d56c2016-10-17 19:36:18 +0000292unsigned DarwinClang::GetDefaultDwarfVersion() const {
293 // Default to use DWARF 2 on OS X 10.10 / iOS 8 and lower.
294 if ((isTargetMacOS() && isMacosxVersionLT(10, 11)) ||
295 (isTargetIOSBased() && isIPhoneOSVersionLT(9)))
296 return 2;
297 return 4;
298}
299
Tim Northover157d9112014-01-16 08:48:16 +0000300void MachO::AddLinkRuntimeLib(const ArgList &Args, ArgStringList &CmdArgs,
Kuba Brecka2735a0252014-10-31 00:08:57 +0000301 StringRef DarwinLibName, bool AlwaysLink,
Kuba Brecka9ff912d2014-11-04 17:35:17 +0000302 bool IsEmbedded, bool AddRPath) const {
303 SmallString<128> Dir(getDriver().ResourceDir);
304 llvm::sys::path::append(Dir, "lib", IsEmbedded ? "macho_embedded" : "darwin");
305
306 SmallString<128> P(Dir);
307 llvm::sys::path::append(P, DarwinLibName);
Eric Christopher551ef452011-08-23 17:56:55 +0000308
Eric Christopherc235d0c62011-06-22 17:41:40 +0000309 // For now, allow missing resource libraries to support developers who may
Alexey Samsonov8368b372012-11-21 14:17:42 +0000310 // not have compiler-rt checked out or integrated into their build (unless
311 // we explicitly force linking with this library).
Benjamin Kramerd45b2052015-10-07 15:48:01 +0000312 if (AlwaysLink || getVFS().exists(P))
Yaron Keren92e1b622015-03-18 10:17:07 +0000313 CmdArgs.push_back(Args.MakeArgString(P));
Kuba Brecka9ff912d2014-11-04 17:35:17 +0000314
315 // Adding the rpaths might negatively interact when other rpaths are involved,
316 // so we should make sure we add the rpaths last, after all user-specified
317 // rpaths. This is currently true from this place, but we need to be
318 // careful if this function is ever called before user's rpaths are emitted.
319 if (AddRPath) {
320 assert(DarwinLibName.endswith(".dylib") && "must be a dynamic library");
321
322 // Add @executable_path to rpath to support having the dylib copied with
323 // the executable.
324 CmdArgs.push_back("-rpath");
325 CmdArgs.push_back("@executable_path");
326
327 // Add the path to the resource dir to rpath to support using the dylib
328 // from the default location without copying.
329 CmdArgs.push_back("-rpath");
Yaron Keren92e1b622015-03-18 10:17:07 +0000330 CmdArgs.push_back(Args.MakeArgString(Dir));
Kuba Brecka9ff912d2014-11-04 17:35:17 +0000331 }
Eric Christopherc235d0c62011-06-22 17:41:40 +0000332}
333
Chris Bienemane60e7c22016-04-29 22:28:34 +0000334StringRef Darwin::getPlatformFamily() const {
335 switch (TargetPlatform) {
336 case DarwinPlatformKind::MacOS:
337 return "MacOSX";
338 case DarwinPlatformKind::IPhoneOS:
339 case DarwinPlatformKind::IPhoneOSSimulator:
340 return "iPhone";
341 case DarwinPlatformKind::TvOS:
342 case DarwinPlatformKind::TvOSSimulator:
343 return "AppleTV";
344 case DarwinPlatformKind::WatchOS:
345 case DarwinPlatformKind::WatchOSSimulator:
346 return "Watch";
347 }
348 llvm_unreachable("Unsupported platform");
349}
350
351StringRef Darwin::getSDKName(StringRef isysroot) {
352 // Assume SDK has path: SOME_PATH/SDKs/PlatformXX.YY.sdk
353 llvm::sys::path::const_iterator SDKDir;
354 auto BeginSDK = llvm::sys::path::begin(isysroot);
355 auto EndSDK = llvm::sys::path::end(isysroot);
356 for (auto IT = BeginSDK; IT != EndSDK; ++IT) {
357 StringRef SDK = *IT;
358 if (SDK.endswith(".sdk"))
359 return SDK.slice(0, SDK.size() - 4);
360 }
361 return "";
362}
363
Anna Zakse67b4022016-02-02 02:04:48 +0000364StringRef Darwin::getOSLibraryNameSuffix() const {
365 switch(TargetPlatform) {
366 case DarwinPlatformKind::MacOS:
367 return "osx";
368 case DarwinPlatformKind::IPhoneOS:
369 return "ios";
370 case DarwinPlatformKind::IPhoneOSSimulator:
371 return "iossim";
372 case DarwinPlatformKind::TvOS:
373 return "tvos";
374 case DarwinPlatformKind::TvOSSimulator:
375 return "tvossim";
376 case DarwinPlatformKind::WatchOS:
377 return "watchos";
378 case DarwinPlatformKind::WatchOSSimulator:
379 return "watchossim";
380 }
381 llvm_unreachable("Unsupported platform");
382}
383
Vedant Kumar5fb00e42016-07-27 23:01:55 +0000384void Darwin::addProfileRTLibs(const ArgList &Args,
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000385 ArgStringList &CmdArgs) const {
Vedant Kumar5fb00e42016-07-27 23:01:55 +0000386 if (!needsProfileRT(Args)) return;
Justin Bognerc7701242015-05-12 05:44:36 +0000387
Vedant Kumar5fb00e42016-07-27 23:01:55 +0000388 AddLinkRuntimeLib(Args, CmdArgs, (Twine("libclang_rt.profile_") +
389 getOSLibraryNameSuffix() + ".a").str(),
390 /*AlwaysLink*/ true);
Justin Bognerc7701242015-05-12 05:44:36 +0000391}
392
Alexey Samsonov498f3c32015-03-23 23:14:05 +0000393void DarwinClang::AddLinkSanitizerLibArgs(const ArgList &Args,
394 ArgStringList &CmdArgs,
395 StringRef Sanitizer) const {
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000396 AddLinkRuntimeLib(
397 Args, CmdArgs,
Anna Zakse67b4022016-02-02 02:04:48 +0000398 (Twine("libclang_rt.") + Sanitizer + "_" +
399 getOSLibraryNameSuffix() + "_dynamic.dylib").str(),
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000400 /*AlwaysLink*/ true, /*IsEmbedded*/ false,
401 /*AddRPath*/ true);
Alexey Samsonov498f3c32015-03-23 23:14:05 +0000402}
403
Jonas Hahnfeldd196fa52016-07-27 08:15:54 +0000404ToolChain::RuntimeLibType DarwinClang::GetRuntimeLibType(
405 const ArgList &Args) const {
406 if (Arg* A = Args.getLastArg(options::OPT_rtlib_EQ)) {
407 StringRef Value = A->getValue();
408 if (Value != "compiler-rt")
409 getDriver().Diag(diag::err_drv_unsupported_rtlib_for_platform)
410 << Value << "darwin";
411 }
412
413 return ToolChain::RLT_CompilerRT;
414}
415
Vedant Kumar5fb00e42016-07-27 23:01:55 +0000416void DarwinClang::AddLinkRuntimeLibArgs(const ArgList &Args,
Daniel Dunbar6276f992009-09-18 08:15:13 +0000417 ArgStringList &CmdArgs) const {
Jonas Hahnfeldd196fa52016-07-27 08:15:54 +0000418 // Call once to ensure diagnostic is printed if wrong value was specified
419 GetRuntimeLibType(Args);
Daniel Dunbarf4916cd2011-12-07 23:03:15 +0000420
Daniel Dunbar7cde09a2010-01-22 03:38:14 +0000421 // Darwin doesn't support real static executables, don't link any runtime
422 // libraries with -static.
Daniel Dunbarbd847cc2012-10-15 22:23:53 +0000423 if (Args.hasArg(options::OPT_static) ||
424 Args.hasArg(options::OPT_fapple_kext) ||
425 Args.hasArg(options::OPT_mkernel))
Daniel Dunbar6276f992009-09-18 08:15:13 +0000426 return;
Daniel Dunbar6276f992009-09-18 08:15:13 +0000427
428 // Reject -static-libgcc for now, we can deal with this when and if someone
429 // cares. This is useful in situations where someone wants to statically link
430 // something like libstdc++, and needs its runtime support routines.
431 if (const Arg *A = Args.getLastArg(options::OPT_static_libgcc)) {
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000432 getDriver().Diag(diag::err_drv_unsupported_opt) << A->getAsString(Args);
Daniel Dunbar6276f992009-09-18 08:15:13 +0000433 return;
434 }
435
Peter Collingbourne32701642013-11-01 18:16:25 +0000436 const SanitizerArgs &Sanitize = getSanitizerArgs();
Alexey Samsonov7f2a0d22015-06-19 21:36:47 +0000437 if (Sanitize.needsAsanRt())
438 AddLinkSanitizerLibArgs(Args, CmdArgs, "asan");
439 if (Sanitize.needsUbsanRt())
440 AddLinkSanitizerLibArgs(Args, CmdArgs, "ubsan");
Kuba Brecka85e01c02015-11-06 15:09:20 +0000441 if (Sanitize.needsTsanRt())
442 AddLinkSanitizerLibArgs(Args, CmdArgs, "tsan");
Peter Collingbournedc134532016-01-16 00:31:22 +0000443 if (Sanitize.needsStatsRt()) {
444 StringRef OS = isTargetMacOS() ? "osx" : "iossim";
445 AddLinkRuntimeLib(Args, CmdArgs,
446 (Twine("libclang_rt.stats_client_") + OS + ".a").str(),
447 /*AlwaysLink=*/true);
448 AddLinkSanitizerLibArgs(Args, CmdArgs, "stats");
449 }
Derek Bruening256c2e12016-04-21 21:32:04 +0000450 if (Sanitize.needsEsanRt())
451 AddLinkSanitizerLibArgs(Args, CmdArgs, "esan");
Daniel Dunbar1d6469f2011-12-01 23:40:18 +0000452
Daniel Dunbar7cde09a2010-01-22 03:38:14 +0000453 // Otherwise link libSystem, then the dynamic runtime library, and finally any
454 // target specific static runtime library.
Daniel Dunbar6276f992009-09-18 08:15:13 +0000455 CmdArgs.push_back("-lSystem");
Daniel Dunbar7cde09a2010-01-22 03:38:14 +0000456
457 // Select the dynamic runtime library and the target specific static library.
Tim Northover6f3ff222015-10-30 16:30:27 +0000458 if (isTargetWatchOSBased()) {
459 // We currently always need a static runtime library for watchOS.
460 AddLinkRuntimeLib(Args, CmdArgs, "libclang_rt.watchos.a");
461 } else if (isTargetTvOSBased()) {
462 // We currently always need a static runtime library for tvOS.
463 AddLinkRuntimeLib(Args, CmdArgs, "libclang_rt.tvos.a");
464 } else if (isTargetIOSBased()) {
Daniel Dunbar2f31fb92011-04-30 04:25:16 +0000465 // If we are compiling as iOS / simulator, don't attempt to link libgcc_s.1,
466 // it never went into the SDK.
Bob Wilson102be442011-10-07 17:54:41 +0000467 // Linking against libgcc_s.1 isn't needed for iOS 5.0+
Tim Northovera2ee4332014-03-29 15:09:45 +0000468 if (isIPhoneOSVersionLT(5, 0) && !isTargetIOSSimulator() &&
Tim Northover40956e62014-07-23 12:32:58 +0000469 getTriple().getArch() != llvm::Triple::aarch64)
Bob Wilson102be442011-10-07 17:54:41 +0000470 CmdArgs.push_back("-lgcc_s.1");
Daniel Dunbar7cde09a2010-01-22 03:38:14 +0000471
Daniel Dunbard1076382011-04-18 23:48:36 +0000472 // We currently always need a static runtime library for iOS.
Eric Christopherc235d0c62011-06-22 17:41:40 +0000473 AddLinkRuntimeLib(Args, CmdArgs, "libclang_rt.ios.a");
Daniel Dunbar7cde09a2010-01-22 03:38:14 +0000474 } else {
Tim Northover9c7e0352013-12-12 11:55:52 +0000475 assert(isTargetMacOS() && "unexpected non MacOS platform");
Daniel Dunbar7cde09a2010-01-22 03:38:14 +0000476 // The dynamic runtime library was merged with libSystem for 10.6 and
477 // beyond; only 10.4 and 10.5 need an additional runtime library.
Daniel Dunbar6d23b2f2010-01-27 00:57:03 +0000478 if (isMacosxVersionLT(10, 5))
Daniel Dunbar7cde09a2010-01-22 03:38:14 +0000479 CmdArgs.push_back("-lgcc_s.10.4");
Daniel Dunbar6d23b2f2010-01-27 00:57:03 +0000480 else if (isMacosxVersionLT(10, 6))
Daniel Dunbar7cde09a2010-01-22 03:38:14 +0000481 CmdArgs.push_back("-lgcc_s.10.5");
482
Chris Bieneman90743412016-08-17 21:54:30 +0000483 // Originally for OS X, we thought we would only need a static runtime
484 // library when targeting 10.4, to provide versions of the static functions
485 // which were omitted from 10.4.dylib. This led to the creation of the 10.4
486 // builtins library.
Daniel Dunbarda4f6b52010-09-22 00:03:52 +0000487 //
488 // Unfortunately, that turned out to not be true, because Darwin system
489 // headers can still use eprintf on i386, and it is not exported from
490 // libSystem. Therefore, we still must provide a runtime library just for
491 // the tiny tiny handful of projects that *might* use that symbol.
Chris Bieneman90743412016-08-17 21:54:30 +0000492 //
493 // Then over time, we figured out it was useful to add more things to the
494 // runtime so we created libclang_rt.osx.a to provide new functions when
495 // deploying to old OS builds, and for a long time we had both eprintf and
496 // osx builtin libraries. Which just seems excessive. So with PR 28855, we
497 // are removing the eprintf library and expecting eprintf to be provided by
498 // the OS X builtins library.
499 if (isMacosxVersionLT(10, 5))
Eric Christopherc235d0c62011-06-22 17:41:40 +0000500 AddLinkRuntimeLib(Args, CmdArgs, "libclang_rt.10.4.a");
Chris Bieneman90743412016-08-17 21:54:30 +0000501 else
Eric Christopherc235d0c62011-06-22 17:41:40 +0000502 AddLinkRuntimeLib(Args, CmdArgs, "libclang_rt.osx.a");
Daniel Dunbar7cde09a2010-01-22 03:38:14 +0000503 }
Daniel Dunbar6276f992009-09-18 08:15:13 +0000504}
505
Daniel Dunbar354e96d2010-07-19 17:11:36 +0000506void Darwin::AddDeploymentTarget(DerivedArgList &Args) const {
Daniel Dunbar083edf72009-12-21 18:54:17 +0000507 const OptTable &Opts = getDriver().getOpts();
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000508
Daniel Dunbar455a0492012-08-17 18:43:50 +0000509 // Support allowing the SDKROOT environment variable used by xcrun and other
510 // Xcode tools to define the default sysroot, by making it the default for
511 // isysroot.
Chad Rosier6c2b11c2012-12-19 23:41:50 +0000512 if (const Arg *A = Args.getLastArg(options::OPT_isysroot)) {
513 // Warn if the path does not exist.
Benjamin Kramerd45b2052015-10-07 15:48:01 +0000514 if (!getVFS().exists(A->getValue()))
Chad Rosier6c2b11c2012-12-19 23:41:50 +0000515 getDriver().Diag(clang::diag::warn_missing_sysroot) << A->getValue();
516 } else {
Daniel Dunbar455a0492012-08-17 18:43:50 +0000517 if (char *env = ::getenv("SDKROOT")) {
Daniel Dunbarb2543042013-01-15 20:33:56 +0000518 // We only use this value as the default if it is an absolute path,
519 // exists, and it is not the root path.
Benjamin Kramerd45b2052015-10-07 15:48:01 +0000520 if (llvm::sys::path::is_absolute(env) && getVFS().exists(env) &&
Daniel Dunbarb2543042013-01-15 20:33:56 +0000521 StringRef(env) != "/") {
Daniel Dunbar455a0492012-08-17 18:43:50 +0000522 Args.append(Args.MakeSeparateArg(
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000523 nullptr, Opts.getOption(options::OPT_isysroot), env));
Daniel Dunbar455a0492012-08-17 18:43:50 +0000524 }
525 }
526 }
527
Daniel Dunbar3b8e50d2010-01-27 00:56:25 +0000528 Arg *OSXVersion = Args.getLastArg(options::OPT_mmacosx_version_min_EQ);
Daniel Dunbar9aaeb642011-04-30 04:15:58 +0000529 Arg *iOSVersion = Args.getLastArg(options::OPT_miphoneos_version_min_EQ);
Tim Northover6f3ff222015-10-30 16:30:27 +0000530 Arg *TvOSVersion = Args.getLastArg(options::OPT_mtvos_version_min_EQ);
531 Arg *WatchOSVersion = Args.getLastArg(options::OPT_mwatchos_version_min_EQ);
Eli Friedman027e9c32012-01-11 02:41:15 +0000532
Tim Northover6f3ff222015-10-30 16:30:27 +0000533 if (OSXVersion && (iOSVersion || TvOSVersion || WatchOSVersion)) {
Chris Lattner0e62c1c2011-07-23 10:55:15 +0000534 getDriver().Diag(diag::err_drv_argument_not_allowed_with)
Tim Northover6f3ff222015-10-30 16:30:27 +0000535 << OSXVersion->getAsString(Args)
536 << (iOSVersion ? iOSVersion :
537 TvOSVersion ? TvOSVersion : WatchOSVersion)->getAsString(Args);
538 iOSVersion = TvOSVersion = WatchOSVersion = nullptr;
539 } else if (iOSVersion && (TvOSVersion || WatchOSVersion)) {
540 getDriver().Diag(diag::err_drv_argument_not_allowed_with)
541 << iOSVersion->getAsString(Args)
542 << (TvOSVersion ? TvOSVersion : WatchOSVersion)->getAsString(Args);
543 TvOSVersion = WatchOSVersion = nullptr;
544 } else if (TvOSVersion && WatchOSVersion) {
545 getDriver().Diag(diag::err_drv_argument_not_allowed_with)
546 << TvOSVersion->getAsString(Args)
547 << WatchOSVersion->getAsString(Args);
548 WatchOSVersion = nullptr;
549 } else if (!OSXVersion && !iOSVersion && !TvOSVersion && !WatchOSVersion) {
Chad Rosier64707fe2011-08-31 20:56:25 +0000550 // If no deployment target was specified on the command line, check for
Daniel Dunbard54669d2010-01-26 01:45:19 +0000551 // environment defines.
Alexey Samsonov905c8022015-06-18 21:46:05 +0000552 std::string OSXTarget;
553 std::string iOSTarget;
Tim Northover6f3ff222015-10-30 16:30:27 +0000554 std::string TvOSTarget;
555 std::string WatchOSTarget;
556
Chad Rosier64707fe2011-08-31 20:56:25 +0000557 if (char *env = ::getenv("MACOSX_DEPLOYMENT_TARGET"))
558 OSXTarget = env;
559 if (char *env = ::getenv("IPHONEOS_DEPLOYMENT_TARGET"))
560 iOSTarget = env;
Tim Northover6f3ff222015-10-30 16:30:27 +0000561 if (char *env = ::getenv("TVOS_DEPLOYMENT_TARGET"))
562 TvOSTarget = env;
563 if (char *env = ::getenv("WATCHOS_DEPLOYMENT_TARGET"))
564 WatchOSTarget = env;
Daniel Dunbarb5023e92009-04-10 21:00:07 +0000565
Steven Wu7a1372c2015-06-25 01:59:35 +0000566 // If there is no command-line argument to specify the Target version and
567 // no environment variable defined, see if we can set the default based
568 // on -isysroot.
Tim Northover6f3ff222015-10-30 16:30:27 +0000569 if (OSXTarget.empty() && iOSTarget.empty() && WatchOSTarget.empty() &&
Frederic Riss3ad83bd2016-01-12 23:47:59 +0000570 TvOSTarget.empty() && Args.hasArg(options::OPT_isysroot)) {
Chad Rosier64707fe2011-08-31 20:56:25 +0000571 if (const Arg *A = Args.getLastArg(options::OPT_isysroot)) {
Richard Smithbd55daf2012-11-01 04:30:05 +0000572 StringRef isysroot = A->getValue();
Chris Bienemane60e7c22016-04-29 22:28:34 +0000573 StringRef SDK = getSDKName(isysroot);
574 if (SDK.size() > 0) {
Steven Wu7a1372c2015-06-25 01:59:35 +0000575 // Slice the version number out.
576 // Version number is between the first and the last number.
577 size_t StartVer = SDK.find_first_of("0123456789");
578 size_t EndVer = SDK.find_last_of("0123456789");
579 if (StartVer != StringRef::npos && EndVer > StartVer) {
580 StringRef Version = SDK.slice(StartVer, EndVer + 1);
581 if (SDK.startswith("iPhoneOS") ||
582 SDK.startswith("iPhoneSimulator"))
583 iOSTarget = Version;
584 else if (SDK.startswith("MacOSX"))
585 OSXTarget = Version;
Tim Northover6f3ff222015-10-30 16:30:27 +0000586 else if (SDK.startswith("WatchOS") ||
587 SDK.startswith("WatchSimulator"))
588 WatchOSTarget = Version;
589 else if (SDK.startswith("AppleTVOS") ||
590 SDK.startswith("AppleTVSimulator"))
591 TvOSTarget = Version;
Steven Wu7a1372c2015-06-25 01:59:35 +0000592 }
593 }
Chad Rosier64707fe2011-08-31 20:56:25 +0000594 }
595 }
Daniel Dunbard54669d2010-01-26 01:45:19 +0000596
Alexey Samsonovfd0bb3a2015-06-18 00:36:38 +0000597 // If no OSX or iOS target has been specified, try to guess platform
Alexey Samsonov905c8022015-06-18 21:46:05 +0000598 // from arch name and compute the version from the triple.
Tim Northover6f3ff222015-10-30 16:30:27 +0000599 if (OSXTarget.empty() && iOSTarget.empty() && TvOSTarget.empty() &&
600 WatchOSTarget.empty()) {
Alexey Samsonovfd0bb3a2015-06-18 00:36:38 +0000601 StringRef MachOArchName = getMachOArchName(Args);
Alexey Samsonov905c8022015-06-18 21:46:05 +0000602 unsigned Major, Minor, Micro;
Alexey Samsonovfd0bb3a2015-06-18 00:36:38 +0000603 if (MachOArchName == "armv7" || MachOArchName == "armv7s" ||
Alexey Samsonov905c8022015-06-18 21:46:05 +0000604 MachOArchName == "arm64") {
605 getTriple().getiOSVersion(Major, Minor, Micro);
606 llvm::raw_string_ostream(iOSTarget) << Major << '.' << Minor << '.'
607 << Micro;
Tim Northover6f3ff222015-10-30 16:30:27 +0000608 } else if (MachOArchName == "armv7k") {
609 getTriple().getWatchOSVersion(Major, Minor, Micro);
610 llvm::raw_string_ostream(WatchOSTarget) << Major << '.' << Minor << '.'
611 << Micro;
Alexey Samsonov905c8022015-06-18 21:46:05 +0000612 } else if (MachOArchName != "armv6m" && MachOArchName != "armv7m" &&
613 MachOArchName != "armv7em") {
614 if (!getTriple().getMacOSXVersion(Major, Minor, Micro)) {
615 getDriver().Diag(diag::err_drv_invalid_darwin_version)
616 << getTriple().getOSName();
617 }
618 llvm::raw_string_ostream(OSXTarget) << Major << '.' << Minor << '.'
619 << Micro;
620 }
Alexey Samsonovfd0bb3a2015-06-18 00:36:38 +0000621 }
Chad Rosierfe6fd362011-09-28 00:46:32 +0000622
Tim Northover6f3ff222015-10-30 16:30:27 +0000623 // Do not allow conflicts with the watchOS target.
624 if (!WatchOSTarget.empty() && (!iOSTarget.empty() || !TvOSTarget.empty())) {
625 getDriver().Diag(diag::err_drv_conflicting_deployment_targets)
626 << "WATCHOS_DEPLOYMENT_TARGET"
627 << (!iOSTarget.empty() ? "IPHONEOS_DEPLOYMENT_TARGET" :
628 "TVOS_DEPLOYMENT_TARGET");
629 }
630
631 // Do not allow conflicts with the tvOS target.
632 if (!TvOSTarget.empty() && !iOSTarget.empty()) {
633 getDriver().Diag(diag::err_drv_conflicting_deployment_targets)
634 << "TVOS_DEPLOYMENT_TARGET"
635 << "IPHONEOS_DEPLOYMENT_TARGET";
636 }
637
Daniel Dunbar9aaeb642011-04-30 04:15:58 +0000638 // Allow conflicts among OSX and iOS for historical reasons, but choose the
639 // default platform.
Tim Northover6f3ff222015-10-30 16:30:27 +0000640 if (!OSXTarget.empty() && (!iOSTarget.empty() ||
641 !WatchOSTarget.empty() ||
642 !TvOSTarget.empty())) {
Daniel Dunbarffa70e82010-02-02 17:31:12 +0000643 if (getTriple().getArch() == llvm::Triple::arm ||
Tim Northover573cbee2014-05-24 12:52:07 +0000644 getTriple().getArch() == llvm::Triple::aarch64 ||
Daniel Dunbarffa70e82010-02-02 17:31:12 +0000645 getTriple().getArch() == llvm::Triple::thumb)
Chad Rosier64707fe2011-08-31 20:56:25 +0000646 OSXTarget = "";
Daniel Dunbarffa70e82010-02-02 17:31:12 +0000647 else
Tim Northover6f3ff222015-10-30 16:30:27 +0000648 iOSTarget = WatchOSTarget = TvOSTarget = "";
Daniel Dunbarffa70e82010-02-02 17:31:12 +0000649 }
Daniel Dunbar65969842010-01-29 17:02:25 +0000650
Chad Rosier64707fe2011-08-31 20:56:25 +0000651 if (!OSXTarget.empty()) {
Michael J. Spencerfc790902012-10-19 22:36:40 +0000652 const Option O = Opts.getOption(options::OPT_mmacosx_version_min_EQ);
Craig Topper92fc2df2014-05-17 16:56:41 +0000653 OSXVersion = Args.MakeJoinedArg(nullptr, O, OSXTarget);
Daniel Dunbar354e96d2010-07-19 17:11:36 +0000654 Args.append(OSXVersion);
Chad Rosier64707fe2011-08-31 20:56:25 +0000655 } else if (!iOSTarget.empty()) {
Michael J. Spencerfc790902012-10-19 22:36:40 +0000656 const Option O = Opts.getOption(options::OPT_miphoneos_version_min_EQ);
Craig Topper92fc2df2014-05-17 16:56:41 +0000657 iOSVersion = Args.MakeJoinedArg(nullptr, O, iOSTarget);
Daniel Dunbar9aaeb642011-04-30 04:15:58 +0000658 Args.append(iOSVersion);
Tim Northover6f3ff222015-10-30 16:30:27 +0000659 } else if (!TvOSTarget.empty()) {
660 const Option O = Opts.getOption(options::OPT_mtvos_version_min_EQ);
661 TvOSVersion = Args.MakeJoinedArg(nullptr, O, TvOSTarget);
662 Args.append(TvOSVersion);
663 } else if (!WatchOSTarget.empty()) {
664 const Option O = Opts.getOption(options::OPT_mwatchos_version_min_EQ);
665 WatchOSVersion = Args.MakeJoinedArg(nullptr, O, WatchOSTarget);
666 Args.append(WatchOSVersion);
Daniel Dunbar84e727f2009-09-04 18:35:21 +0000667 }
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000668 }
Mike Stump11289f42009-09-09 15:08:12 +0000669
Tim Northover9c7e0352013-12-12 11:55:52 +0000670 DarwinPlatformKind Platform;
671 if (OSXVersion)
672 Platform = MacOS;
673 else if (iOSVersion)
674 Platform = IPhoneOS;
Tim Northover6f3ff222015-10-30 16:30:27 +0000675 else if (TvOSVersion)
676 Platform = TvOS;
677 else if (WatchOSVersion)
678 Platform = WatchOS;
Tim Northover9c7e0352013-12-12 11:55:52 +0000679 else
Tim Northover157d9112014-01-16 08:48:16 +0000680 llvm_unreachable("Unable to infer Darwin variant");
Tim Northover9c7e0352013-12-12 11:55:52 +0000681
Daniel Dunbar3b8e50d2010-01-27 00:56:25 +0000682 // Set the tool chain target information.
683 unsigned Major, Minor, Micro;
684 bool HadExtra;
Tim Northover9c7e0352013-12-12 11:55:52 +0000685 if (Platform == MacOS) {
Tim Northover6f3ff222015-10-30 16:30:27 +0000686 assert((!iOSVersion && !TvOSVersion && !WatchOSVersion) &&
687 "Unknown target platform!");
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000688 if (!Driver::GetReleaseVersion(OSXVersion->getValue(), Major, Minor, Micro,
689 HadExtra) ||
690 HadExtra || Major != 10 || Minor >= 100 || Micro >= 100)
Chris Lattner0e62c1c2011-07-23 10:55:15 +0000691 getDriver().Diag(diag::err_drv_invalid_version_number)
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000692 << OSXVersion->getAsString(Args);
Bob Wilson7f294b52014-10-10 23:10:10 +0000693 } else if (Platform == IPhoneOS) {
694 assert(iOSVersion && "Unknown target platform!");
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000695 if (!Driver::GetReleaseVersion(iOSVersion->getValue(), Major, Minor, Micro,
696 HadExtra) ||
Bob Wilson4cf27c42016-07-18 20:29:14 +0000697 HadExtra || Major >= 100 || Minor >= 100 || Micro >= 100)
Eli Friedman027e9c32012-01-11 02:41:15 +0000698 getDriver().Diag(diag::err_drv_invalid_version_number)
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000699 << iOSVersion->getAsString(Args);
Tim Northover6f3ff222015-10-30 16:30:27 +0000700 } else if (Platform == TvOS) {
701 if (!Driver::GetReleaseVersion(TvOSVersion->getValue(), Major, Minor,
702 Micro, HadExtra) || HadExtra ||
Bob Wilson4cf27c42016-07-18 20:29:14 +0000703 Major >= 100 || Minor >= 100 || Micro >= 100)
Tim Northover6f3ff222015-10-30 16:30:27 +0000704 getDriver().Diag(diag::err_drv_invalid_version_number)
705 << TvOSVersion->getAsString(Args);
706 } else if (Platform == WatchOS) {
707 if (!Driver::GetReleaseVersion(WatchOSVersion->getValue(), Major, Minor,
708 Micro, HadExtra) || HadExtra ||
709 Major >= 10 || Minor >= 100 || Micro >= 100)
710 getDriver().Diag(diag::err_drv_invalid_version_number)
711 << WatchOSVersion->getAsString(Args);
Tim Northover157d9112014-01-16 08:48:16 +0000712 } else
713 llvm_unreachable("unknown kind of Darwin platform");
Daniel Dunbar9aaeb642011-04-30 04:15:58 +0000714
Bob Wilson7f294b52014-10-10 23:10:10 +0000715 // Recognize iOS targets with an x86 architecture as the iOS simulator.
Daniel Dunbarb1189432011-04-30 04:18:16 +0000716 if (iOSVersion && (getTriple().getArch() == llvm::Triple::x86 ||
717 getTriple().getArch() == llvm::Triple::x86_64))
Tim Northover9c7e0352013-12-12 11:55:52 +0000718 Platform = IPhoneOSSimulator;
Tim Northover6f3ff222015-10-30 16:30:27 +0000719 if (TvOSVersion && (getTriple().getArch() == llvm::Triple::x86 ||
720 getTriple().getArch() == llvm::Triple::x86_64))
721 Platform = TvOSSimulator;
722 if (WatchOSVersion && (getTriple().getArch() == llvm::Triple::x86 ||
723 getTriple().getArch() == llvm::Triple::x86_64))
724 Platform = WatchOSSimulator;
Daniel Dunbarb1189432011-04-30 04:18:16 +0000725
Tim Northover9c7e0352013-12-12 11:55:52 +0000726 setTarget(Platform, Major, Minor, Micro);
Chris Bienemane60e7c22016-04-29 22:28:34 +0000727
728 if (const Arg *A = Args.getLastArg(options::OPT_isysroot)) {
729 StringRef SDK = getSDKName(A->getValue());
730 if (SDK.size() > 0) {
731 size_t StartVer = SDK.find_first_of("0123456789");
732 StringRef SDKName = SDK.slice(0, StartVer);
733 if (!SDKName.startswith(getPlatformFamily()))
734 getDriver().Diag(diag::warn_incompatible_sysroot)
735 << SDKName << getPlatformFamily();
736 }
737 }
Daniel Dunbarb2b8a912010-07-19 17:11:33 +0000738}
739
Daniel Dunbar3f7796f2010-09-17 01:20:05 +0000740void DarwinClang::AddCXXStdlibLibArgs(const ArgList &Args,
Daniel Dunbar8fa86b12010-09-17 01:16:06 +0000741 ArgStringList &CmdArgs) const {
742 CXXStdlibType Type = GetCXXStdlibType(Args);
743
744 switch (Type) {
745 case ToolChain::CST_Libcxx:
746 CmdArgs.push_back("-lc++");
747 break;
748
Hans Wennborgdcfba332015-10-06 23:40:43 +0000749 case ToolChain::CST_Libstdcxx:
Daniel Dunbar8fa86b12010-09-17 01:16:06 +0000750 // Unfortunately, -lstdc++ doesn't always exist in the standard search path;
751 // it was previously found in the gcc lib dir. However, for all the Darwin
752 // platforms we care about it was -lstdc++.6, so we search for that
753 // explicitly if we can't see an obvious -lstdc++ candidate.
754
755 // Check in the sysroot first.
756 if (const Arg *A = Args.getLastArg(options::OPT_isysroot)) {
Rafael Espindola358256c2013-06-26 02:13:00 +0000757 SmallString<128> P(A->getValue());
Benjamin Kramer17381a02013-06-28 16:25:46 +0000758 llvm::sys::path::append(P, "usr", "lib", "libstdc++.dylib");
Daniel Dunbar8fa86b12010-09-17 01:16:06 +0000759
Benjamin Kramerd45b2052015-10-07 15:48:01 +0000760 if (!getVFS().exists(P)) {
Rafael Espindola358256c2013-06-26 02:13:00 +0000761 llvm::sys::path::remove_filename(P);
762 llvm::sys::path::append(P, "libstdc++.6.dylib");
Benjamin Kramerd45b2052015-10-07 15:48:01 +0000763 if (getVFS().exists(P)) {
Yaron Keren92e1b622015-03-18 10:17:07 +0000764 CmdArgs.push_back(Args.MakeArgString(P));
Daniel Dunbar8fa86b12010-09-17 01:16:06 +0000765 return;
766 }
767 }
768 }
769
770 // Otherwise, look in the root.
Bob Wilson1a9ad0f2011-11-11 07:47:04 +0000771 // FIXME: This should be removed someday when we don't have to care about
772 // 10.6 and earlier, where /usr/lib/libstdc++.dylib does not exist.
Benjamin Kramerd45b2052015-10-07 15:48:01 +0000773 if (!getVFS().exists("/usr/lib/libstdc++.dylib") &&
774 getVFS().exists("/usr/lib/libstdc++.6.dylib")) {
Daniel Dunbar8fa86b12010-09-17 01:16:06 +0000775 CmdArgs.push_back("/usr/lib/libstdc++.6.dylib");
776 return;
777 }
778
779 // Otherwise, let the linker search.
780 CmdArgs.push_back("-lstdc++");
781 break;
782 }
Daniel Dunbar8fa86b12010-09-17 01:16:06 +0000783}
784
Shantonu Senafeb03b2010-09-17 18:39:08 +0000785void DarwinClang::AddCCKextLibArgs(const ArgList &Args,
786 ArgStringList &CmdArgs) const {
Shantonu Senafeb03b2010-09-17 18:39:08 +0000787 // For Darwin platforms, use the compiler-rt-based support library
788 // instead of the gcc-provided one (which is also incidentally
789 // only present in the gcc lib dir, which makes it hard to find).
790
Rafael Espindola358256c2013-06-26 02:13:00 +0000791 SmallString<128> P(getDriver().ResourceDir);
Benjamin Kramer17381a02013-06-28 16:25:46 +0000792 llvm::sys::path::append(P, "lib", "darwin");
Daniel Dunbarbd847cc2012-10-15 22:23:53 +0000793
794 // Use the newer cc_kext for iOS ARM after 6.0.
Tim Northover6f3ff222015-10-30 16:30:27 +0000795 if (isTargetWatchOS()) {
796 llvm::sys::path::append(P, "libclang_rt.cc_kext_watchos.a");
797 } else if (isTargetTvOS()) {
798 llvm::sys::path::append(P, "libclang_rt.cc_kext_tvos.a");
799 } else if (isTargetIPhoneOS()) {
Chris Bieneman25bc0de2015-09-23 22:52:35 +0000800 llvm::sys::path::append(P, "libclang_rt.cc_kext_ios.a");
Daniel Dunbarbd847cc2012-10-15 22:23:53 +0000801 } else {
Chris Bieneman25bc0de2015-09-23 22:52:35 +0000802 llvm::sys::path::append(P, "libclang_rt.cc_kext.a");
Daniel Dunbarbd847cc2012-10-15 22:23:53 +0000803 }
NAKAMURA Takumi8b73b3e2011-06-03 03:49:51 +0000804
Shantonu Senafeb03b2010-09-17 18:39:08 +0000805 // For now, allow missing resource libraries to support developers who may
806 // not have compiler-rt checked out or integrated into their build.
Benjamin Kramerd45b2052015-10-07 15:48:01 +0000807 if (getVFS().exists(P))
Yaron Keren92e1b622015-03-18 10:17:07 +0000808 CmdArgs.push_back(Args.MakeArgString(P));
Shantonu Senafeb03b2010-09-17 18:39:08 +0000809}
810
Tim Northover157d9112014-01-16 08:48:16 +0000811DerivedArgList *MachO::TranslateArgs(const DerivedArgList &Args,
Mehdi Aminic50b1a22016-10-07 21:27:26 +0000812 StringRef BoundArch) const {
Daniel Dunbarb2b8a912010-07-19 17:11:33 +0000813 DerivedArgList *DAL = new DerivedArgList(Args.getBaseArgs());
814 const OptTable &Opts = getDriver().getOpts();
815
816 // FIXME: We really want to get out of the tool chain level argument
817 // translation business, as it makes the driver functionality much
818 // more opaque. For now, we follow gcc closely solely for the
819 // purpose of easily achieving feature parity & testability. Once we
820 // have something that works, we should reevaluate each translation
821 // and try to push it down into tool specific logic.
Daniel Dunbar3b8e50d2010-01-27 00:56:25 +0000822
Simon Atanasyan6f657c42014-05-08 19:32:46 +0000823 for (Arg *A : Args) {
Daniel Dunbaraabb0b12009-03-25 06:12:34 +0000824 if (A->getOption().matches(options::OPT_Xarch__)) {
Daniel Dunbar471c4f82011-06-21 00:20:17 +0000825 // Skip this argument unless the architecture matches either the toolchain
826 // triple arch, or the arch being bound.
Rafael Espindola35ca7d92012-10-07 04:44:33 +0000827 llvm::Triple::ArchType XarchArch =
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000828 tools::darwin::getArchTypeForMachOArchName(A->getValue(0));
829 if (!(XarchArch == getArch() ||
Mehdi Aminic50b1a22016-10-07 21:27:26 +0000830 (!BoundArch.empty() &&
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000831 XarchArch ==
832 tools::darwin::getArchTypeForMachOArchName(BoundArch))))
Daniel Dunbaraabb0b12009-03-25 06:12:34 +0000833 continue;
834
Daniel Dunbar1094bb12011-02-19 05:33:51 +0000835 Arg *OriginalArg = A;
Richard Smithbd55daf2012-11-01 04:30:05 +0000836 unsigned Index = Args.getBaseArgs().MakeIndex(A->getValue(1));
Daniel Dunbar3f1a1ff2010-06-14 21:23:08 +0000837 unsigned Prev = Index;
Nico Webera04d5f82014-05-11 17:27:13 +0000838 std::unique_ptr<Arg> XarchArg(Opts.ParseOneArg(Args, Index));
Mike Stump11289f42009-09-09 15:08:12 +0000839
Daniel Dunbaraabb0b12009-03-25 06:12:34 +0000840 // If the argument parsing failed or more than one argument was
841 // consumed, the -Xarch_ argument's parameter tried to consume
842 // extra arguments. Emit an error and ignore.
843 //
844 // We also want to disallow any options which would alter the
845 // driver behavior; that isn't going to work in our model. We
846 // use isDriverOption() as an approximation, although things
847 // like -O4 are going to slip through.
Daniel Dunbar5a784c82011-04-21 17:41:34 +0000848 if (!XarchArg || Index > Prev + 1) {
Chris Lattner0e62c1c2011-07-23 10:55:15 +0000849 getDriver().Diag(diag::err_drv_invalid_Xarch_argument_with_args)
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000850 << A->getAsString(Args);
Daniel Dunbar6914a982011-04-21 17:32:21 +0000851 continue;
Michael J. Spencer66e2b202012-10-19 22:37:06 +0000852 } else if (XarchArg->getOption().hasFlag(options::DriverOption)) {
Chris Lattner0e62c1c2011-07-23 10:55:15 +0000853 getDriver().Diag(diag::err_drv_invalid_Xarch_argument_isdriver)
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000854 << A->getAsString(Args);
Daniel Dunbaraabb0b12009-03-25 06:12:34 +0000855 continue;
856 }
857
Daniel Dunbar53b406f2009-03-29 22:29:05 +0000858 XarchArg->setBaseArg(A);
Daniel Dunbar3f1a1ff2010-06-14 21:23:08 +0000859
Nico Webera04d5f82014-05-11 17:27:13 +0000860 A = XarchArg.release();
Daniel Dunbar3f1a1ff2010-06-14 21:23:08 +0000861 DAL->AddSynthesizedArg(A);
Daniel Dunbar1094bb12011-02-19 05:33:51 +0000862
863 // Linker input arguments require custom handling. The problem is that we
864 // have already constructed the phase actions, so we can not treat them as
865 // "input arguments".
Michael J. Spencer66e2b202012-10-19 22:37:06 +0000866 if (A->getOption().hasFlag(options::LinkerInput)) {
Daniel Dunbar1094bb12011-02-19 05:33:51 +0000867 // Convert the argument into individual Zlinker_input_args.
Douglas Katzman6bbffc42015-06-25 18:51:37 +0000868 for (const char *Value : A->getValues()) {
869 DAL->AddSeparateArg(
870 OriginalArg, Opts.getOption(options::OPT_Zlinker_input), Value);
Daniel Dunbar1094bb12011-02-19 05:33:51 +0000871 }
872 continue;
873 }
Mike Stump11289f42009-09-09 15:08:12 +0000874 }
Daniel Dunbaraabb0b12009-03-25 06:12:34 +0000875
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000876 // Sob. These is strictly gcc compatible for the time being. Apple
877 // gcc translates options twice, which means that self-expanding
878 // options add duplicates.
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000879 switch ((options::ID)A->getOption().getID()) {
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000880 default:
881 DAL->append(A);
882 break;
883
884 case options::OPT_mkernel:
885 case options::OPT_fapple_kext:
886 DAL->append(A);
Daniel Dunbar2d6e9ee2010-06-14 20:20:41 +0000887 DAL->AddFlagArg(A, Opts.getOption(options::OPT_static));
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000888 break;
Mike Stump11289f42009-09-09 15:08:12 +0000889
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000890 case options::OPT_dependency_file:
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000891 DAL->AddSeparateArg(A, Opts.getOption(options::OPT_MF), A->getValue());
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000892 break;
893
894 case options::OPT_gfull:
Daniel Dunbar2d6e9ee2010-06-14 20:20:41 +0000895 DAL->AddFlagArg(A, Opts.getOption(options::OPT_g_Flag));
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000896 DAL->AddFlagArg(
897 A, Opts.getOption(options::OPT_fno_eliminate_unused_debug_symbols));
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000898 break;
899
900 case options::OPT_gused:
Daniel Dunbar2d6e9ee2010-06-14 20:20:41 +0000901 DAL->AddFlagArg(A, Opts.getOption(options::OPT_g_Flag));
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000902 DAL->AddFlagArg(
903 A, Opts.getOption(options::OPT_feliminate_unused_debug_symbols));
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000904 break;
905
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000906 case options::OPT_shared:
Daniel Dunbar2d6e9ee2010-06-14 20:20:41 +0000907 DAL->AddFlagArg(A, Opts.getOption(options::OPT_dynamiclib));
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000908 break;
909
910 case options::OPT_fconstant_cfstrings:
Daniel Dunbar2d6e9ee2010-06-14 20:20:41 +0000911 DAL->AddFlagArg(A, Opts.getOption(options::OPT_mconstant_cfstrings));
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000912 break;
913
914 case options::OPT_fno_constant_cfstrings:
Daniel Dunbar2d6e9ee2010-06-14 20:20:41 +0000915 DAL->AddFlagArg(A, Opts.getOption(options::OPT_mno_constant_cfstrings));
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000916 break;
917
918 case options::OPT_Wnonportable_cfstrings:
Daniel Dunbar2d6e9ee2010-06-14 20:20:41 +0000919 DAL->AddFlagArg(A,
920 Opts.getOption(options::OPT_mwarn_nonportable_cfstrings));
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000921 break;
922
923 case options::OPT_Wno_nonportable_cfstrings:
Douglas Katzmana67e50c2015-06-26 15:47:46 +0000924 DAL->AddFlagArg(
925 A, Opts.getOption(options::OPT_mno_warn_nonportable_cfstrings));
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000926 break;
927
928 case options::OPT_fpascal_strings:
Daniel Dunbar2d6e9ee2010-06-14 20:20:41 +0000929 DAL->AddFlagArg(A, Opts.getOption(options::OPT_mpascal_strings));
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000930 break;
931
932 case options::OPT_fno_pascal_strings:
Daniel Dunbar2d6e9ee2010-06-14 20:20:41 +0000933 DAL->AddFlagArg(A, Opts.getOption(options::OPT_mno_pascal_strings));
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000934 break;
935 }
Daniel Dunbaraabb0b12009-03-25 06:12:34 +0000936 }
937
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000938 if (getTriple().getArch() == llvm::Triple::x86 ||
939 getTriple().getArch() == llvm::Triple::x86_64)
Daniel Dunbarfffd1812009-11-19 04:00:53 +0000940 if (!Args.hasArgNoClaim(options::OPT_mtune_EQ))
Craig Topper92fc2df2014-05-17 16:56:41 +0000941 DAL->AddJoinedArg(nullptr, Opts.getOption(options::OPT_mtune_EQ),
942 "core2");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000943
944 // Add the arch options based on the particular spelling of -arch, to match
Chad Rosier7c5d9082012-04-27 14:58:16 +0000945 // how the driver driver works.
Mehdi Aminic50b1a22016-10-07 21:27:26 +0000946 if (!BoundArch.empty()) {
Chris Lattner0e62c1c2011-07-23 10:55:15 +0000947 StringRef Name = BoundArch;
Michael J. Spencerfc790902012-10-19 22:36:40 +0000948 const Option MCpu = Opts.getOption(options::OPT_mcpu_EQ);
949 const Option MArch = Opts.getOption(options::OPT_march_EQ);
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000950
951 // This code must be kept in sync with LLVM's getArchTypeForDarwinArch,
952 // which defines the list of which architectures we accept.
953 if (Name == "ppc")
954 ;
955 else if (Name == "ppc601")
Craig Topper92fc2df2014-05-17 16:56:41 +0000956 DAL->AddJoinedArg(nullptr, MCpu, "601");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000957 else if (Name == "ppc603")
Craig Topper92fc2df2014-05-17 16:56:41 +0000958 DAL->AddJoinedArg(nullptr, MCpu, "603");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000959 else if (Name == "ppc604")
Craig Topper92fc2df2014-05-17 16:56:41 +0000960 DAL->AddJoinedArg(nullptr, MCpu, "604");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000961 else if (Name == "ppc604e")
Craig Topper92fc2df2014-05-17 16:56:41 +0000962 DAL->AddJoinedArg(nullptr, MCpu, "604e");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000963 else if (Name == "ppc750")
Craig Topper92fc2df2014-05-17 16:56:41 +0000964 DAL->AddJoinedArg(nullptr, MCpu, "750");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000965 else if (Name == "ppc7400")
Craig Topper92fc2df2014-05-17 16:56:41 +0000966 DAL->AddJoinedArg(nullptr, MCpu, "7400");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000967 else if (Name == "ppc7450")
Craig Topper92fc2df2014-05-17 16:56:41 +0000968 DAL->AddJoinedArg(nullptr, MCpu, "7450");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000969 else if (Name == "ppc970")
Craig Topper92fc2df2014-05-17 16:56:41 +0000970 DAL->AddJoinedArg(nullptr, MCpu, "970");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000971
Bill Schmidt778d3872013-07-26 01:36:11 +0000972 else if (Name == "ppc64" || Name == "ppc64le")
Craig Topper92fc2df2014-05-17 16:56:41 +0000973 DAL->AddFlagArg(nullptr, Opts.getOption(options::OPT_m64));
Daniel Dunbar0af75a12009-03-25 06:58:31 +0000974
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000975 else if (Name == "i386")
976 ;
977 else if (Name == "i486")
Craig Topper92fc2df2014-05-17 16:56:41 +0000978 DAL->AddJoinedArg(nullptr, MArch, "i486");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000979 else if (Name == "i586")
Craig Topper92fc2df2014-05-17 16:56:41 +0000980 DAL->AddJoinedArg(nullptr, MArch, "i586");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000981 else if (Name == "i686")
Craig Topper92fc2df2014-05-17 16:56:41 +0000982 DAL->AddJoinedArg(nullptr, MArch, "i686");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000983 else if (Name == "pentium")
Craig Topper92fc2df2014-05-17 16:56:41 +0000984 DAL->AddJoinedArg(nullptr, MArch, "pentium");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000985 else if (Name == "pentium2")
Craig Topper92fc2df2014-05-17 16:56:41 +0000986 DAL->AddJoinedArg(nullptr, MArch, "pentium2");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000987 else if (Name == "pentpro")
Craig Topper92fc2df2014-05-17 16:56:41 +0000988 DAL->AddJoinedArg(nullptr, MArch, "pentiumpro");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000989 else if (Name == "pentIIm3")
Craig Topper92fc2df2014-05-17 16:56:41 +0000990 DAL->AddJoinedArg(nullptr, MArch, "pentium2");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000991
992 else if (Name == "x86_64")
Craig Topper92fc2df2014-05-17 16:56:41 +0000993 DAL->AddFlagArg(nullptr, Opts.getOption(options::OPT_m64));
Jim Grosbach82eee262013-11-16 00:53:35 +0000994 else if (Name == "x86_64h") {
Craig Topper92fc2df2014-05-17 16:56:41 +0000995 DAL->AddFlagArg(nullptr, Opts.getOption(options::OPT_m64));
996 DAL->AddJoinedArg(nullptr, MArch, "x86_64h");
Jim Grosbach82eee262013-11-16 00:53:35 +0000997 }
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +0000998
999 else if (Name == "arm")
Craig Topper92fc2df2014-05-17 16:56:41 +00001000 DAL->AddJoinedArg(nullptr, MArch, "armv4t");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +00001001 else if (Name == "armv4t")
Craig Topper92fc2df2014-05-17 16:56:41 +00001002 DAL->AddJoinedArg(nullptr, MArch, "armv4t");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +00001003 else if (Name == "armv5")
Craig Topper92fc2df2014-05-17 16:56:41 +00001004 DAL->AddJoinedArg(nullptr, MArch, "armv5tej");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +00001005 else if (Name == "xscale")
Craig Topper92fc2df2014-05-17 16:56:41 +00001006 DAL->AddJoinedArg(nullptr, MArch, "xscale");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +00001007 else if (Name == "armv6")
Craig Topper92fc2df2014-05-17 16:56:41 +00001008 DAL->AddJoinedArg(nullptr, MArch, "armv6k");
Bob Wilson743bf672013-03-04 22:37:49 +00001009 else if (Name == "armv6m")
Craig Topper92fc2df2014-05-17 16:56:41 +00001010 DAL->AddJoinedArg(nullptr, MArch, "armv6m");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +00001011 else if (Name == "armv7")
Craig Topper92fc2df2014-05-17 16:56:41 +00001012 DAL->AddJoinedArg(nullptr, MArch, "armv7a");
Bob Wilson743bf672013-03-04 22:37:49 +00001013 else if (Name == "armv7em")
Craig Topper92fc2df2014-05-17 16:56:41 +00001014 DAL->AddJoinedArg(nullptr, MArch, "armv7em");
Bob Wilsond7cf1042012-09-29 23:52:50 +00001015 else if (Name == "armv7k")
Craig Topper92fc2df2014-05-17 16:56:41 +00001016 DAL->AddJoinedArg(nullptr, MArch, "armv7k");
Bob Wilson743bf672013-03-04 22:37:49 +00001017 else if (Name == "armv7m")
Craig Topper92fc2df2014-05-17 16:56:41 +00001018 DAL->AddJoinedArg(nullptr, MArch, "armv7m");
Bob Wilsond7cf1042012-09-29 23:52:50 +00001019 else if (Name == "armv7s")
Craig Topper92fc2df2014-05-17 16:56:41 +00001020 DAL->AddJoinedArg(nullptr, MArch, "armv7s");
Daniel Dunbar3c7b9ca2009-09-09 22:33:15 +00001021 }
Daniel Dunbar0af75a12009-03-25 06:58:31 +00001022
Tim Northover157d9112014-01-16 08:48:16 +00001023 return DAL;
1024}
1025
Vedant Kumar5fb00e42016-07-27 23:01:55 +00001026void MachO::AddLinkRuntimeLibArgs(const ArgList &Args,
Douglas Katzmanf08fadf2015-06-04 14:40:44 +00001027 ArgStringList &CmdArgs) const {
Tim Northover157d9112014-01-16 08:48:16 +00001028 // Embedded targets are simple at the moment, not supporting sanitizers and
1029 // with different libraries for each member of the product { static, PIC } x
1030 // { hard-float, soft-float }
1031 llvm::SmallString<32> CompilerRT = StringRef("libclang_rt.");
Vedant Kumar5fb00e42016-07-27 23:01:55 +00001032 CompilerRT +=
1033 (tools::arm::getARMFloatABI(*this, Args) == tools::arm::FloatABI::Hard)
1034 ? "hard"
1035 : "soft";
Tim Northover157d9112014-01-16 08:48:16 +00001036 CompilerRT += Args.hasArg(options::OPT_fPIC) ? "_pic.a" : "_static.a";
1037
1038 AddLinkRuntimeLib(Args, CmdArgs, CompilerRT, false, true);
1039}
1040
Tim Northover157d9112014-01-16 08:48:16 +00001041DerivedArgList *Darwin::TranslateArgs(const DerivedArgList &Args,
Mehdi Aminic50b1a22016-10-07 21:27:26 +00001042 StringRef BoundArch) const {
Tim Northover157d9112014-01-16 08:48:16 +00001043 // First get the generic Apple args, before moving onto Darwin-specific ones.
1044 DerivedArgList *DAL = MachO::TranslateArgs(Args, BoundArch);
Tim Northoverb534ce42016-02-12 22:30:42 +00001045 const OptTable &Opts = getDriver().getOpts();
Tim Northover157d9112014-01-16 08:48:16 +00001046
Bob Wilsonf8cf1612014-02-21 00:20:07 +00001047 // If no architecture is bound, none of the translations here are relevant.
Mehdi Aminic50b1a22016-10-07 21:27:26 +00001048 if (BoundArch.empty())
Bob Wilsonf8cf1612014-02-21 00:20:07 +00001049 return DAL;
1050
Daniel Dunbar354e96d2010-07-19 17:11:36 +00001051 // Add an explicit version min argument for the deployment target. We do this
1052 // after argument translation because -Xarch_ arguments may add a version min
1053 // argument.
Bob Wilsonf8cf1612014-02-21 00:20:07 +00001054 AddDeploymentTarget(*DAL);
Daniel Dunbar354e96d2010-07-19 17:11:36 +00001055
Daniel Dunbarbd847cc2012-10-15 22:23:53 +00001056 // For iOS 6, undo the translation to add -static for -mkernel/-fapple-kext.
1057 // FIXME: It would be far better to avoid inserting those -static arguments,
1058 // but we can't check the deployment target in the translation code until
1059 // it is set here.
Tim Northover6f3ff222015-10-30 16:30:27 +00001060 if (isTargetWatchOSBased() ||
1061 (isTargetIOSBased() && !isIPhoneOSVersionLT(6, 0))) {
1062 for (ArgList::iterator it = DAL->begin(), ie = DAL->end(); it != ie; ) {
Daniel Dunbarbd847cc2012-10-15 22:23:53 +00001063 Arg *A = *it;
1064 ++it;
1065 if (A->getOption().getID() != options::OPT_mkernel &&
1066 A->getOption().getID() != options::OPT_fapple_kext)
1067 continue;
1068 assert(it != ie && "unexpected argument translation");
1069 A = *it;
1070 assert(A->getOption().getID() == options::OPT_static &&
1071 "missing expected -static argument");
1072 it = DAL->getArgs().erase(it);
1073 }
1074 }
1075
Tim Northoverb534ce42016-02-12 22:30:42 +00001076 if (!Args.getLastArg(options::OPT_stdlib_EQ) &&
Tim Northover3a098c12016-02-15 16:38:10 +00001077 GetCXXStdlibType(Args) == ToolChain::CST_Libcxx)
Tim Northoverb534ce42016-02-12 22:30:42 +00001078 DAL->AddJoinedArg(nullptr, Opts.getOption(options::OPT_stdlib_EQ),
1079 "libc++");
1080
Bob Wilson102be442011-10-07 17:54:41 +00001081 // Validate the C++ standard library choice.
1082 CXXStdlibType Type = GetCXXStdlibType(*DAL);
1083 if (Type == ToolChain::CST_Libcxx) {
John McCall5fb5df92012-06-20 06:18:46 +00001084 // Check whether the target provides libc++.
1085 StringRef where;
1086
Alp Tokerf6a24ce2013-12-05 16:25:25 +00001087 // Complain about targeting iOS < 5.0 in any way.
Tim Northover9c7e0352013-12-12 11:55:52 +00001088 if (isTargetIOSBased() && isIPhoneOSVersionLT(5, 0))
Bob Wilson5ad5a952012-11-09 01:59:30 +00001089 where = "iOS 5.0";
John McCall5fb5df92012-06-20 06:18:46 +00001090
1091 if (where != StringRef()) {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001092 getDriver().Diag(clang::diag::err_drv_invalid_libcxx_deployment) << where;
Bob Wilson102be442011-10-07 17:54:41 +00001093 }
1094 }
1095
Tim Northoverc0f6c9b2016-08-23 18:12:58 +00001096 auto Arch = tools::darwin::getArchTypeForMachOArchName(BoundArch);
1097 if ((Arch == llvm::Triple::arm || Arch == llvm::Triple::thumb)) {
1098 if (Args.hasFlag(options::OPT_fomit_frame_pointer,
1099 options::OPT_fno_omit_frame_pointer, false))
1100 getDriver().Diag(clang::diag::warn_drv_unsupported_opt_for_target)
1101 << "-fomit-frame-pointer" << BoundArch;
1102 if (Args.hasFlag(options::OPT_momit_leaf_frame_pointer,
1103 options::OPT_mno_omit_leaf_frame_pointer, false))
1104 getDriver().Diag(clang::diag::warn_drv_unsupported_opt_for_target)
1105 << "-momit-leaf-frame-pointer" << BoundArch;
1106 }
1107
Daniel Dunbaraabb0b12009-03-25 06:12:34 +00001108 return DAL;
Mike Stump11289f42009-09-09 15:08:12 +00001109}
Daniel Dunbar03e0a4f2009-03-20 00:57:52 +00001110
Tim Northover157d9112014-01-16 08:48:16 +00001111bool MachO::IsUnwindTablesDefault() const {
Rafael Espindolae8bd4e52012-10-07 03:23:40 +00001112 return getArch() == llvm::Triple::x86_64;
Daniel Dunbar03e0a4f2009-03-20 00:57:52 +00001113}
1114
Tim Northover157d9112014-01-16 08:48:16 +00001115bool MachO::UseDwarfDebugFlags() const {
Daniel Dunbar24c7f5e2009-12-18 02:43:17 +00001116 if (const char *S = ::getenv("RC_DEBUG_OPTIONS"))
1117 return S[0] != '\0';
1118 return false;
1119}
1120
Tim Northovere931f9f2015-10-30 16:30:41 +00001121bool Darwin::UseSjLjExceptions(const ArgList &Args) const {
Daniel Dunbar3241d402010-02-10 18:49:11 +00001122 // Darwin uses SjLj exceptions on ARM.
Tim Northovere931f9f2015-10-30 16:30:41 +00001123 if (getTriple().getArch() != llvm::Triple::arm &&
1124 getTriple().getArch() != llvm::Triple::thumb)
1125 return false;
1126
Tim Northoverc741b042015-11-17 18:27:27 +00001127 // Only watchOS uses the new DWARF/Compact unwinding method.
Tim Northoverd88ecb32016-01-27 19:32:40 +00001128 llvm::Triple Triple(ComputeLLVMTriple(Args));
Tim Northover4c9ac7d2016-01-27 22:14:02 +00001129 return !Triple.isWatchABI();
Daniel Dunbar3241d402010-02-10 18:49:11 +00001130}
1131
Steven Wu574b0f22016-03-01 01:07:58 +00001132bool Darwin::SupportsEmbeddedBitcode() const {
1133 assert(TargetInitialized && "Target not initialized!");
1134 if (isTargetIPhoneOS() && isIPhoneOSVersionLT(6, 0))
1135 return false;
1136 return true;
1137}
1138
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001139bool MachO::isPICDefault() const { return true; }
Daniel Dunbar03e0a4f2009-03-20 00:57:52 +00001140
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001141bool MachO::isPIEDefault() const { return false; }
Peter Collingbourne54d770c2013-04-09 04:35:11 +00001142
Tim Northover157d9112014-01-16 08:48:16 +00001143bool MachO::isPICDefaultForced() const {
Tim Northovera2ee4332014-03-29 15:09:45 +00001144 return (getArch() == llvm::Triple::x86_64 ||
Tim Northover573cbee2014-05-24 12:52:07 +00001145 getArch() == llvm::Triple::aarch64);
Daniel Dunbar03e0a4f2009-03-20 00:57:52 +00001146}
1147
Tim Northover157d9112014-01-16 08:48:16 +00001148bool MachO::SupportsProfiling() const {
Daniel Dunbar733b0f82011-03-01 18:49:30 +00001149 // Profiling instrumentation is only supported on x86.
Rafael Espindola35ca7d92012-10-07 04:44:33 +00001150 return getArch() == llvm::Triple::x86 || getArch() == llvm::Triple::x86_64;
Daniel Dunbar733b0f82011-03-01 18:49:30 +00001151}
1152
Douglas Katzmanf08fadf2015-06-04 14:40:44 +00001153void Darwin::addMinVersionArgs(const ArgList &Args,
1154 ArgStringList &CmdArgs) const {
Tim Northover157d9112014-01-16 08:48:16 +00001155 VersionTuple TargetVersion = getTargetVersion();
1156
Tim Northover6f3ff222015-10-30 16:30:27 +00001157 if (isTargetWatchOS())
1158 CmdArgs.push_back("-watchos_version_min");
1159 else if (isTargetWatchOSSimulator())
1160 CmdArgs.push_back("-watchos_simulator_version_min");
1161 else if (isTargetTvOS())
1162 CmdArgs.push_back("-tvos_version_min");
1163 else if (isTargetTvOSSimulator())
1164 CmdArgs.push_back("-tvos_simulator_version_min");
1165 else if (isTargetIOSSimulator())
Tim Northover157d9112014-01-16 08:48:16 +00001166 CmdArgs.push_back("-ios_simulator_version_min");
Bob Wilson5cfc55e2014-02-01 21:06:21 +00001167 else if (isTargetIOSBased())
Tim Northover157d9112014-01-16 08:48:16 +00001168 CmdArgs.push_back("-iphoneos_version_min");
1169 else {
1170 assert(isTargetMacOS() && "unexpected target");
1171 CmdArgs.push_back("-macosx_version_min");
1172 }
1173
1174 CmdArgs.push_back(Args.MakeArgString(TargetVersion.getAsString()));
1175}
1176
Douglas Katzmanf08fadf2015-06-04 14:40:44 +00001177void Darwin::addStartObjectFileArgs(const ArgList &Args,
1178 ArgStringList &CmdArgs) const {
Tim Northover157d9112014-01-16 08:48:16 +00001179 // Derived from startfile spec.
1180 if (Args.hasArg(options::OPT_dynamiclib)) {
1181 // Derived from darwin_dylib1 spec.
Tim Northover6f3ff222015-10-30 16:30:27 +00001182 if (isTargetWatchOSBased()) {
1183 ; // watchOS does not need dylib1.o.
1184 } else if (isTargetIOSSimulator()) {
Bob Wilson74b6cd12014-01-21 00:17:10 +00001185 ; // iOS simulator does not need dylib1.o.
Tim Northover157d9112014-01-16 08:48:16 +00001186 } else if (isTargetIPhoneOS()) {
1187 if (isIPhoneOSVersionLT(3, 1))
1188 CmdArgs.push_back("-ldylib1.o");
1189 } else {
1190 if (isMacosxVersionLT(10, 5))
1191 CmdArgs.push_back("-ldylib1.o");
1192 else if (isMacosxVersionLT(10, 6))
1193 CmdArgs.push_back("-ldylib1.10.5.o");
1194 }
1195 } else {
1196 if (Args.hasArg(options::OPT_bundle)) {
1197 if (!Args.hasArg(options::OPT_static)) {
1198 // Derived from darwin_bundle1 spec.
Tim Northover6f3ff222015-10-30 16:30:27 +00001199 if (isTargetWatchOSBased()) {
1200 ; // watchOS does not need bundle1.o.
1201 } else if (isTargetIOSSimulator()) {
Bob Wilson74b6cd12014-01-21 00:17:10 +00001202 ; // iOS simulator does not need bundle1.o.
Tim Northover157d9112014-01-16 08:48:16 +00001203 } else if (isTargetIPhoneOS()) {
1204 if (isIPhoneOSVersionLT(3, 1))
1205 CmdArgs.push_back("-lbundle1.o");
1206 } else {
1207 if (isMacosxVersionLT(10, 6))
1208 CmdArgs.push_back("-lbundle1.o");
1209 }
1210 }
1211 } else {
1212 if (Args.hasArg(options::OPT_pg) && SupportsProfiling()) {
1213 if (Args.hasArg(options::OPT_static) ||
1214 Args.hasArg(options::OPT_object) ||
1215 Args.hasArg(options::OPT_preload)) {
1216 CmdArgs.push_back("-lgcrt0.o");
1217 } else {
1218 CmdArgs.push_back("-lgcrt1.o");
1219
1220 // darwin_crt2 spec is empty.
1221 }
1222 // By default on OS X 10.8 and later, we don't link with a crt1.o
1223 // file and the linker knows to use _main as the entry point. But,
1224 // when compiling with -pg, we need to link with the gcrt1.o file,
1225 // so pass the -no_new_main option to tell the linker to use the
1226 // "start" symbol as the entry point.
1227 if (isTargetMacOS() && !isMacosxVersionLT(10, 8))
1228 CmdArgs.push_back("-no_new_main");
1229 } else {
1230 if (Args.hasArg(options::OPT_static) ||
1231 Args.hasArg(options::OPT_object) ||
1232 Args.hasArg(options::OPT_preload)) {
1233 CmdArgs.push_back("-lcrt0.o");
1234 } else {
1235 // Derived from darwin_crt1 spec.
Tim Northover6f3ff222015-10-30 16:30:27 +00001236 if (isTargetWatchOSBased()) {
1237 ; // watchOS does not need crt1.o.
1238 } else if (isTargetIOSSimulator()) {
Bob Wilson74b6cd12014-01-21 00:17:10 +00001239 ; // iOS simulator does not need crt1.o.
Tim Northover157d9112014-01-16 08:48:16 +00001240 } else if (isTargetIPhoneOS()) {
Tim Northover40956e62014-07-23 12:32:58 +00001241 if (getArch() == llvm::Triple::aarch64)
Tim Northovera2ee4332014-03-29 15:09:45 +00001242 ; // iOS does not need any crt1 files for arm64
1243 else if (isIPhoneOSVersionLT(3, 1))
Tim Northover157d9112014-01-16 08:48:16 +00001244 CmdArgs.push_back("-lcrt1.o");
1245 else if (isIPhoneOSVersionLT(6, 0))
1246 CmdArgs.push_back("-lcrt1.3.1.o");
1247 } else {
1248 if (isMacosxVersionLT(10, 5))
1249 CmdArgs.push_back("-lcrt1.o");
1250 else if (isMacosxVersionLT(10, 6))
1251 CmdArgs.push_back("-lcrt1.10.5.o");
1252 else if (isMacosxVersionLT(10, 8))
1253 CmdArgs.push_back("-lcrt1.10.6.o");
1254
1255 // darwin_crt2 spec is empty.
1256 }
1257 }
1258 }
1259 }
1260 }
1261
1262 if (!isTargetIPhoneOS() && Args.hasArg(options::OPT_shared_libgcc) &&
Tim Northover6f3ff222015-10-30 16:30:27 +00001263 !isTargetWatchOS() &&
Tim Northover157d9112014-01-16 08:48:16 +00001264 isMacosxVersionLT(10, 5)) {
1265 const char *Str = Args.MakeArgString(GetFilePath("crt3.o"));
1266 CmdArgs.push_back(Str);
1267 }
1268}
1269
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001270bool Darwin::SupportsObjCGC() const { return isTargetMacOS(); }
Daniel Dunbar16334e12010-04-10 16:20:23 +00001271
John McCall3deb1ad2012-08-21 02:47:43 +00001272void Darwin::CheckObjCARC() const {
Tim Northover6f3ff222015-10-30 16:30:27 +00001273 if (isTargetIOSBased() || isTargetWatchOSBased() ||
1274 (isTargetMacOS() && !isMacosxVersionLT(10, 6)))
John McCall3deb1ad2012-08-21 02:47:43 +00001275 return;
John McCall93207072012-08-27 01:56:21 +00001276 getDriver().Diag(diag::err_arc_unsupported_on_toolchain);
Argyrios Kyrtzidis3dbeb552012-02-29 03:43:52 +00001277}
1278
Alexey Samsonov7f2a0d22015-06-19 21:36:47 +00001279SanitizerMask Darwin::getSupportedSanitizers() const {
Devin Coughlinfcfa38c2016-03-20 18:24:33 +00001280 const bool IsX86_64 = getTriple().getArch() == llvm::Triple::x86_64;
Alexey Samsonov7f2a0d22015-06-19 21:36:47 +00001281 SanitizerMask Res = ToolChain::getSupportedSanitizers();
Anna Zakse67b4022016-02-02 02:04:48 +00001282 Res |= SanitizerKind::Address;
Alexey Samsonov1d4cff22015-06-25 00:58:02 +00001283 if (isTargetMacOS()) {
1284 if (!isMacosxVersionLT(10, 9))
1285 Res |= SanitizerKind::Vptr;
Alexey Samsonov7f2a0d22015-06-19 21:36:47 +00001286 Res |= SanitizerKind::SafeStack;
Devin Coughlinfcfa38c2016-03-20 18:24:33 +00001287 if (IsX86_64)
1288 Res |= SanitizerKind::Thread;
1289 } else if (isTargetIOSSimulator() || isTargetTvOSSimulator()) {
1290 if (IsX86_64)
1291 Res |= SanitizerKind::Thread;
Alexey Samsonov1d4cff22015-06-25 00:58:02 +00001292 }
Alexey Samsonov7f2a0d22015-06-19 21:36:47 +00001293 return Res;
1294}
1295
Daniel Dunbar59e5e882009-03-20 00:20:03 +00001296/// Generic_GCC - A tool chain using the 'gcc' command to perform
1297/// all subcommands; this relies on gcc translating the majority of
1298/// command line options.
1299
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001300/// \brief Parse a GCCVersion object out of a string of text.
1301///
1302/// This is the primary means of forming GCCVersion objects.
1303/*static*/
1304Generic_GCC::GCCVersion Linux::GCCVersion::Parse(StringRef VersionText) {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001305 const GCCVersion BadVersion = {VersionText.str(), -1, -1, -1, "", "", ""};
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001306 std::pair<StringRef, StringRef> First = VersionText.split('.');
1307 std::pair<StringRef, StringRef> Second = First.second.split('.');
1308
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001309 GCCVersion GoodVersion = {VersionText.str(), -1, -1, -1, "", "", ""};
1310 if (First.first.getAsInteger(10, GoodVersion.Major) || GoodVersion.Major < 0)
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001311 return BadVersion;
Chandler Carruth1f2b2f82013-08-26 08:59:53 +00001312 GoodVersion.MajorStr = First.first.str();
Bryan Chand346ae62016-06-17 16:47:14 +00001313 if (First.second.empty())
1314 return GoodVersion;
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001315 if (Second.first.getAsInteger(10, GoodVersion.Minor) || GoodVersion.Minor < 0)
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001316 return BadVersion;
Chandler Carruth1f2b2f82013-08-26 08:59:53 +00001317 GoodVersion.MinorStr = Second.first.str();
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001318
1319 // First look for a number prefix and parse that if present. Otherwise just
1320 // stash the entire patch string in the suffix, and leave the number
1321 // unspecified. This covers versions strings such as:
Bryan Chand346ae62016-06-17 16:47:14 +00001322 // 5 (handled above)
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001323 // 4.4
1324 // 4.4.0
1325 // 4.4.x
1326 // 4.4.2-rc4
1327 // 4.4.x-patched
1328 // And retains any patch number it finds.
1329 StringRef PatchText = GoodVersion.PatchSuffix = Second.second.str();
1330 if (!PatchText.empty()) {
Will Dietza38608b2013-01-10 22:20:02 +00001331 if (size_t EndNumber = PatchText.find_first_not_of("0123456789")) {
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001332 // Try to parse the number and any suffix.
1333 if (PatchText.slice(0, EndNumber).getAsInteger(10, GoodVersion.Patch) ||
1334 GoodVersion.Patch < 0)
1335 return BadVersion;
Chandler Carruth1f2b2f82013-08-26 08:59:53 +00001336 GoodVersion.PatchSuffix = PatchText.substr(EndNumber);
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001337 }
1338 }
1339
1340 return GoodVersion;
1341}
1342
1343/// \brief Less-than for GCCVersion, implementing a Strict Weak Ordering.
Benjamin Kramer604e8482013-08-09 17:17:48 +00001344bool Generic_GCC::GCCVersion::isOlderThan(int RHSMajor, int RHSMinor,
1345 int RHSPatch,
1346 StringRef RHSPatchSuffix) const {
1347 if (Major != RHSMajor)
1348 return Major < RHSMajor;
1349 if (Minor != RHSMinor)
1350 return Minor < RHSMinor;
1351 if (Patch != RHSPatch) {
Chandler Carruth5193dfc2012-12-29 12:01:08 +00001352 // Note that versions without a specified patch sort higher than those with
1353 // a patch.
Benjamin Kramer604e8482013-08-09 17:17:48 +00001354 if (RHSPatch == -1)
Chandler Carruth5193dfc2012-12-29 12:01:08 +00001355 return true;
1356 if (Patch == -1)
1357 return false;
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001358
Chandler Carruth5193dfc2012-12-29 12:01:08 +00001359 // Otherwise just sort on the patch itself.
Benjamin Kramer604e8482013-08-09 17:17:48 +00001360 return Patch < RHSPatch;
Chandler Carruth5193dfc2012-12-29 12:01:08 +00001361 }
Benjamin Kramer604e8482013-08-09 17:17:48 +00001362 if (PatchSuffix != RHSPatchSuffix) {
Chandler Carruth5193dfc2012-12-29 12:01:08 +00001363 // Sort empty suffixes higher.
Benjamin Kramer604e8482013-08-09 17:17:48 +00001364 if (RHSPatchSuffix.empty())
Chandler Carruth5193dfc2012-12-29 12:01:08 +00001365 return true;
1366 if (PatchSuffix.empty())
Chandler Carruth19e8bea2012-12-29 13:00:47 +00001367 return false;
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001368
Chandler Carruth5193dfc2012-12-29 12:01:08 +00001369 // Provide a lexicographic sort to make this a total ordering.
Benjamin Kramer604e8482013-08-09 17:17:48 +00001370 return PatchSuffix < RHSPatchSuffix;
Chandler Carruth5193dfc2012-12-29 12:01:08 +00001371 }
1372
1373 // The versions are equal.
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001374 return false;
1375}
1376
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00001377static llvm::StringRef getGCCToolchainDir(const ArgList &Args) {
Rafael Espindola1af7c212012-02-19 01:38:32 +00001378 const Arg *A = Args.getLastArg(options::OPT_gcc_toolchain);
1379 if (A)
Richard Smithbd55daf2012-11-01 04:30:05 +00001380 return A->getValue();
Rafael Espindola1af7c212012-02-19 01:38:32 +00001381 return GCC_INSTALL_PREFIX;
1382}
1383
Roman Divacky326d9982013-12-06 18:32:18 +00001384/// \brief Initialize a GCCInstallationDetector from the driver.
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001385///
1386/// This performs all of the autodetection and sets up the various paths.
Gabor Greif8a45d572012-04-17 11:16:26 +00001387/// Once constructed, a GCCInstallationDetector is essentially immutable.
Chandler Carruth866faab2012-01-25 07:21:38 +00001388///
1389/// FIXME: We shouldn't need an explicit TargetTriple parameter here, and
1390/// should instead pull the target out of the driver. This is currently
1391/// necessary because the driver doesn't store the final version of the target
1392/// triple.
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001393void Generic_GCC::GCCInstallationDetector::init(
Benjamin Kramerd45b2052015-10-07 15:48:01 +00001394 const llvm::Triple &TargetTriple, const ArgList &Args,
Douglas Katzman8c39e6a2015-09-18 15:23:16 +00001395 ArrayRef<std::string> ExtraTripleAliases) {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001396 llvm::Triple BiarchVariantTriple = TargetTriple.isArch32Bit()
1397 ? TargetTriple.get64BitArchVariant()
1398 : TargetTriple.get32BitArchVariant();
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001399 // The library directories which may contain GCC installations.
Chandler Carruthb427c562013-06-22 11:35:51 +00001400 SmallVector<StringRef, 4> CandidateLibDirs, CandidateBiarchLibDirs;
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001401 // The compatible GCC triples for this particular architecture.
Hans Wennborg90aa63f2014-08-11 18:09:28 +00001402 SmallVector<StringRef, 16> CandidateTripleAliases;
1403 SmallVector<StringRef, 16> CandidateBiarchTripleAliases;
Chandler Carruthb427c562013-06-22 11:35:51 +00001404 CollectLibDirsAndTriples(TargetTriple, BiarchVariantTriple, CandidateLibDirs,
1405 CandidateTripleAliases, CandidateBiarchLibDirs,
1406 CandidateBiarchTripleAliases);
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001407
1408 // Compute the set of prefixes for our search.
1409 SmallVector<std::string, 8> Prefixes(D.PrefixDirs.begin(),
1410 D.PrefixDirs.end());
Rafael Espindolac29af942012-02-03 01:01:20 +00001411
Rafael Espindola1af7c212012-02-19 01:38:32 +00001412 StringRef GCCToolchainDir = getGCCToolchainDir(Args);
1413 if (GCCToolchainDir != "") {
1414 if (GCCToolchainDir.back() == '/')
1415 GCCToolchainDir = GCCToolchainDir.drop_back(); // remove the /
Rafael Espindolac29af942012-02-03 01:01:20 +00001416
Rafael Espindola1af7c212012-02-19 01:38:32 +00001417 Prefixes.push_back(GCCToolchainDir);
Rafael Espindolac29af942012-02-03 01:01:20 +00001418 } else {
Rafael Espindola0f4b04e2013-08-28 23:17:47 +00001419 // If we have a SysRoot, try that first.
1420 if (!D.SysRoot.empty()) {
1421 Prefixes.push_back(D.SysRoot);
1422 Prefixes.push_back(D.SysRoot + "/usr");
1423 }
1424
1425 // Then look for gcc installed alongside clang.
Rafael Espindolac29af942012-02-03 01:01:20 +00001426 Prefixes.push_back(D.InstalledDir + "/..");
Rafael Espindola0f4b04e2013-08-28 23:17:47 +00001427
Rafael Espindola2edca412016-05-09 13:03:10 +00001428 // Then look for distribution supplied gcc installations.
1429 if (D.SysRoot.empty()) {
1430 // Look for RHEL devtoolsets.
1431 Prefixes.push_back("/opt/rh/devtoolset-4/root/usr");
1432 Prefixes.push_back("/opt/rh/devtoolset-3/root/usr");
1433 Prefixes.push_back("/opt/rh/devtoolset-2/root/usr");
1434 Prefixes.push_back("/opt/rh/devtoolset-1.1/root/usr");
1435 Prefixes.push_back("/opt/rh/devtoolset-1.0/root/usr");
1436 // And finally in /usr.
Rafael Espindola0f4b04e2013-08-28 23:17:47 +00001437 Prefixes.push_back("/usr");
Rafael Espindola2edca412016-05-09 13:03:10 +00001438 }
Rafael Espindolac29af942012-02-03 01:01:20 +00001439 }
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001440
1441 // Loop over the various components which exist and select the best GCC
1442 // installation available. GCC installs are ranked by version number.
1443 Version = GCCVersion::Parse("0.0.0");
Douglas Katzman6bbffc42015-06-25 18:51:37 +00001444 for (const std::string &Prefix : Prefixes) {
Benjamin Kramerd45b2052015-10-07 15:48:01 +00001445 if (!D.getVFS().exists(Prefix))
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001446 continue;
Benjamin Kramer72e64312015-09-24 14:48:49 +00001447 for (StringRef Suffix : CandidateLibDirs) {
Douglas Katzman6bbffc42015-06-25 18:51:37 +00001448 const std::string LibDir = Prefix + Suffix.str();
Benjamin Kramerd45b2052015-10-07 15:48:01 +00001449 if (!D.getVFS().exists(LibDir))
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001450 continue;
Benjamin Kramer72e64312015-09-24 14:48:49 +00001451 for (StringRef Candidate : ExtraTripleAliases) // Try these first.
Douglas Katzmand6e597c2015-09-17 19:56:40 +00001452 ScanLibDirForGCCTriple(TargetTriple, Args, LibDir, Candidate);
Benjamin Kramer72e64312015-09-24 14:48:49 +00001453 for (StringRef Candidate : CandidateTripleAliases)
Douglas Katzman6bbffc42015-06-25 18:51:37 +00001454 ScanLibDirForGCCTriple(TargetTriple, Args, LibDir, Candidate);
Chandler Carruth866faab2012-01-25 07:21:38 +00001455 }
Benjamin Kramer72e64312015-09-24 14:48:49 +00001456 for (StringRef Suffix : CandidateBiarchLibDirs) {
Douglas Katzman6bbffc42015-06-25 18:51:37 +00001457 const std::string LibDir = Prefix + Suffix.str();
Benjamin Kramerd45b2052015-10-07 15:48:01 +00001458 if (!D.getVFS().exists(LibDir))
Chandler Carruth866faab2012-01-25 07:21:38 +00001459 continue;
Benjamin Kramer72e64312015-09-24 14:48:49 +00001460 for (StringRef Candidate : CandidateBiarchTripleAliases)
Douglas Katzman6bbffc42015-06-25 18:51:37 +00001461 ScanLibDirForGCCTriple(TargetTriple, Args, LibDir, Candidate,
Chandler Carruthb427c562013-06-22 11:35:51 +00001462 /*NeedsBiarchSuffix=*/ true);
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001463 }
1464 }
1465}
1466
Chandler Carruth0ae39aa2013-07-30 17:57:09 +00001467void Generic_GCC::GCCInstallationDetector::print(raw_ostream &OS) const {
Simon Atanasyan6f657c42014-05-08 19:32:46 +00001468 for (const auto &InstallPath : CandidateGCCInstallPaths)
1469 OS << "Found candidate GCC installation: " << InstallPath << "\n";
Chandler Carruth0ae39aa2013-07-30 17:57:09 +00001470
Yunzhong Gaoe3f902c2014-02-19 19:06:58 +00001471 if (!GCCInstallPath.empty())
1472 OS << "Selected GCC installation: " << GCCInstallPath << "\n";
1473
Simon Atanasyan6f657c42014-05-08 19:32:46 +00001474 for (const auto &Multilib : Multilibs)
1475 OS << "Candidate multilib: " << Multilib << "\n";
Yunzhong Gaoe3f902c2014-02-19 19:06:58 +00001476
1477 if (Multilibs.size() != 0 || !SelectedMultilib.isDefault())
1478 OS << "Selected multilib: " << SelectedMultilib << "\n";
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00001479}
1480
1481bool Generic_GCC::GCCInstallationDetector::getBiarchSibling(Multilib &M) const {
1482 if (BiarchSibling.hasValue()) {
1483 M = BiarchSibling.getValue();
1484 return true;
1485 }
1486 return false;
Chandler Carruth0ae39aa2013-07-30 17:57:09 +00001487}
1488
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001489/*static*/ void Generic_GCC::GCCInstallationDetector::CollectLibDirsAndTriples(
Chandler Carruthb427c562013-06-22 11:35:51 +00001490 const llvm::Triple &TargetTriple, const llvm::Triple &BiarchTriple,
Chandler Carruth866faab2012-01-25 07:21:38 +00001491 SmallVectorImpl<StringRef> &LibDirs,
1492 SmallVectorImpl<StringRef> &TripleAliases,
Chandler Carruthb427c562013-06-22 11:35:51 +00001493 SmallVectorImpl<StringRef> &BiarchLibDirs,
1494 SmallVectorImpl<StringRef> &BiarchTripleAliases) {
Chandler Carruth866faab2012-01-25 07:21:38 +00001495 // Declare a bunch of static data sets that we'll select between below. These
1496 // are specifically designed to always refer to string literals to avoid any
1497 // lifetime or initialization issues.
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001498 static const char *const AArch64LibDirs[] = {"/lib64", "/lib"};
1499 static const char *const AArch64Triples[] = {
1500 "aarch64-none-linux-gnu", "aarch64-linux-gnu", "aarch64-linux-android",
1501 "aarch64-redhat-linux"};
1502 static const char *const AArch64beLibDirs[] = {"/lib"};
1503 static const char *const AArch64beTriples[] = {"aarch64_be-none-linux-gnu",
1504 "aarch64_be-linux-gnu"};
Tim Northover9bb857a2013-01-31 12:13:10 +00001505
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001506 static const char *const ARMLibDirs[] = {"/lib"};
1507 static const char *const ARMTriples[] = {"arm-linux-gnueabi",
1508 "arm-linux-androideabi"};
1509 static const char *const ARMHFTriples[] = {"arm-linux-gnueabihf",
1510 "armv7hl-redhat-linux-gnueabi"};
1511 static const char *const ARMebLibDirs[] = {"/lib"};
1512 static const char *const ARMebTriples[] = {"armeb-linux-gnueabi",
1513 "armeb-linux-androideabi"};
1514 static const char *const ARMebHFTriples[] = {
1515 "armeb-linux-gnueabihf", "armebv7hl-redhat-linux-gnueabi"};
Chandler Carruth866faab2012-01-25 07:21:38 +00001516
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001517 static const char *const X86_64LibDirs[] = {"/lib64", "/lib"};
Chandler Carruth866faab2012-01-25 07:21:38 +00001518 static const char *const X86_64Triples[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001519 "x86_64-linux-gnu", "x86_64-unknown-linux-gnu",
1520 "x86_64-pc-linux-gnu", "x86_64-redhat-linux6E",
1521 "x86_64-redhat-linux", "x86_64-suse-linux",
1522 "x86_64-manbo-linux-gnu", "x86_64-linux-gnu",
1523 "x86_64-slackware-linux", "x86_64-linux-android",
1524 "x86_64-unknown-linux"};
1525 static const char *const X32LibDirs[] = {"/libx32"};
1526 static const char *const X86LibDirs[] = {"/lib32", "/lib"};
Chandler Carruth866faab2012-01-25 07:21:38 +00001527 static const char *const X86Triples[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001528 "i686-linux-gnu", "i686-pc-linux-gnu", "i486-linux-gnu",
1529 "i386-linux-gnu", "i386-redhat-linux6E", "i686-redhat-linux",
1530 "i586-redhat-linux", "i386-redhat-linux", "i586-suse-linux",
1531 "i486-slackware-linux", "i686-montavista-linux", "i686-linux-android",
1532 "i586-linux-gnu"};
Chandler Carruth866faab2012-01-25 07:21:38 +00001533
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001534 static const char *const MIPSLibDirs[] = {"/lib"};
Vasileios Kalintirisc744e122015-11-12 15:26:54 +00001535 static const char *const MIPSTriples[] = {"mips-linux-gnu", "mips-mti-linux",
1536 "mips-mti-linux-gnu",
1537 "mips-img-linux-gnu"};
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001538 static const char *const MIPSELLibDirs[] = {"/lib"};
Simon Atanasyan603018a2016-07-19 07:09:48 +00001539 static const char *const MIPSELTriples[] = {"mipsel-linux-gnu",
1540 "mips-img-linux-gnu"};
Chandler Carruth866faab2012-01-25 07:21:38 +00001541
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001542 static const char *const MIPS64LibDirs[] = {"/lib64", "/lib"};
1543 static const char *const MIPS64Triples[] = {
1544 "mips64-linux-gnu", "mips-mti-linux-gnu", "mips-img-linux-gnu",
1545 "mips64-linux-gnuabi64"};
1546 static const char *const MIPS64ELLibDirs[] = {"/lib64", "/lib"};
1547 static const char *const MIPS64ELTriples[] = {
1548 "mips64el-linux-gnu", "mips-mti-linux-gnu", "mips-img-linux-gnu",
Simon Atanasyan603018a2016-07-19 07:09:48 +00001549 "mips64el-linux-gnuabi64"};
1550
1551 static const char *const MIPSELAndroidLibDirs[] = {"/lib", "/libr2",
1552 "/libr6"};
1553 static const char *const MIPSELAndroidTriples[] = {"mipsel-linux-android"};
1554 static const char *const MIPS64ELAndroidLibDirs[] = {"/lib64", "/lib",
1555 "/libr2", "/libr6"};
1556 static const char *const MIPS64ELAndroidTriples[] = {
1557 "mips64el-linux-android"};
Simon Atanasyan9bb634d2012-04-26 19:57:02 +00001558
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001559 static const char *const PPCLibDirs[] = {"/lib32", "/lib"};
Chandler Carruth866faab2012-01-25 07:21:38 +00001560 static const char *const PPCTriples[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001561 "powerpc-linux-gnu", "powerpc-unknown-linux-gnu", "powerpc-linux-gnuspe",
1562 "powerpc-suse-linux", "powerpc-montavista-linuxspe"};
1563 static const char *const PPC64LibDirs[] = {"/lib64", "/lib"};
1564 static const char *const PPC64Triples[] = {
1565 "powerpc64-linux-gnu", "powerpc64-unknown-linux-gnu",
1566 "powerpc64-suse-linux", "ppc64-redhat-linux"};
1567 static const char *const PPC64LELibDirs[] = {"/lib64", "/lib"};
1568 static const char *const PPC64LETriples[] = {
1569 "powerpc64le-linux-gnu", "powerpc64le-unknown-linux-gnu",
1570 "powerpc64le-suse-linux", "ppc64le-redhat-linux"};
Chandler Carruth866faab2012-01-25 07:21:38 +00001571
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001572 static const char *const SPARCv8LibDirs[] = {"/lib32", "/lib"};
1573 static const char *const SPARCv8Triples[] = {"sparc-linux-gnu",
1574 "sparcv8-linux-gnu"};
1575 static const char *const SPARCv9LibDirs[] = {"/lib64", "/lib"};
1576 static const char *const SPARCv9Triples[] = {"sparc64-linux-gnu",
1577 "sparcv9-linux-gnu"};
Jakob Stoklund Olesenb3f938e2014-01-10 06:53:02 +00001578
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001579 static const char *const SystemZLibDirs[] = {"/lib64", "/lib"};
Ulrich Weigand47445072013-05-06 16:26:41 +00001580 static const char *const SystemZTriples[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001581 "s390x-linux-gnu", "s390x-unknown-linux-gnu", "s390x-ibm-linux-gnu",
1582 "s390x-suse-linux", "s390x-redhat-linux"};
Ulrich Weigand47445072013-05-06 16:26:41 +00001583
Rafael Espindolac53c5b12015-08-31 19:17:51 +00001584 // Solaris.
1585 static const char *const SolarisSPARCLibDirs[] = {"/gcc"};
1586 static const char *const SolarisSPARCTriples[] = {"sparc-sun-solaris2.11",
1587 "i386-pc-solaris2.11"};
1588
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001589 using std::begin;
1590 using std::end;
1591
Rafael Espindolac53c5b12015-08-31 19:17:51 +00001592 if (TargetTriple.getOS() == llvm::Triple::Solaris) {
1593 LibDirs.append(begin(SolarisSPARCLibDirs), end(SolarisSPARCLibDirs));
1594 TripleAliases.append(begin(SolarisSPARCTriples), end(SolarisSPARCTriples));
Rafael Espindolac53c5b12015-08-31 19:17:51 +00001595 return;
1596 }
1597
Chandler Carruth866faab2012-01-25 07:21:38 +00001598 switch (TargetTriple.getArch()) {
Tim Northover9bb857a2013-01-31 12:13:10 +00001599 case llvm::Triple::aarch64:
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001600 LibDirs.append(begin(AArch64LibDirs), end(AArch64LibDirs));
1601 TripleAliases.append(begin(AArch64Triples), end(AArch64Triples));
1602 BiarchLibDirs.append(begin(AArch64LibDirs), end(AArch64LibDirs));
1603 BiarchTripleAliases.append(begin(AArch64Triples), end(AArch64Triples));
Tim Northover9bb857a2013-01-31 12:13:10 +00001604 break;
Christian Pirkera74c7912014-03-14 12:15:45 +00001605 case llvm::Triple::aarch64_be:
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001606 LibDirs.append(begin(AArch64beLibDirs), end(AArch64beLibDirs));
1607 TripleAliases.append(begin(AArch64beTriples), end(AArch64beTriples));
1608 BiarchLibDirs.append(begin(AArch64beLibDirs), end(AArch64beLibDirs));
1609 BiarchTripleAliases.append(begin(AArch64beTriples), end(AArch64beTriples));
Christian Pirkera74c7912014-03-14 12:15:45 +00001610 break;
Chandler Carruth866faab2012-01-25 07:21:38 +00001611 case llvm::Triple::arm:
1612 case llvm::Triple::thumb:
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001613 LibDirs.append(begin(ARMLibDirs), end(ARMLibDirs));
Jiangning Liu61b06cb2012-07-31 08:06:29 +00001614 if (TargetTriple.getEnvironment() == llvm::Triple::GNUEABIHF) {
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001615 TripleAliases.append(begin(ARMHFTriples), end(ARMHFTriples));
Jiangning Liu61b06cb2012-07-31 08:06:29 +00001616 } else {
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001617 TripleAliases.append(begin(ARMTriples), end(ARMTriples));
Jiangning Liu61b06cb2012-07-31 08:06:29 +00001618 }
Chandler Carruth866faab2012-01-25 07:21:38 +00001619 break;
Christian Pirkerf01cd6f2014-03-28 14:40:46 +00001620 case llvm::Triple::armeb:
1621 case llvm::Triple::thumbeb:
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001622 LibDirs.append(begin(ARMebLibDirs), end(ARMebLibDirs));
Christian Pirkerf01cd6f2014-03-28 14:40:46 +00001623 if (TargetTriple.getEnvironment() == llvm::Triple::GNUEABIHF) {
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001624 TripleAliases.append(begin(ARMebHFTriples), end(ARMebHFTriples));
Christian Pirkerf01cd6f2014-03-28 14:40:46 +00001625 } else {
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001626 TripleAliases.append(begin(ARMebTriples), end(ARMebTriples));
Christian Pirkerf01cd6f2014-03-28 14:40:46 +00001627 }
1628 break;
Chandler Carruth866faab2012-01-25 07:21:38 +00001629 case llvm::Triple::x86_64:
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001630 LibDirs.append(begin(X86_64LibDirs), end(X86_64LibDirs));
1631 TripleAliases.append(begin(X86_64Triples), end(X86_64Triples));
1632 // x32 is always available when x86_64 is available, so adding it as
1633 // secondary arch with x86_64 triples
Zinovy Nis1db95732014-07-10 15:27:19 +00001634 if (TargetTriple.getEnvironment() == llvm::Triple::GNUX32) {
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001635 BiarchLibDirs.append(begin(X32LibDirs), end(X32LibDirs));
1636 BiarchTripleAliases.append(begin(X86_64Triples), end(X86_64Triples));
Zinovy Nis1db95732014-07-10 15:27:19 +00001637 } else {
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001638 BiarchLibDirs.append(begin(X86LibDirs), end(X86LibDirs));
1639 BiarchTripleAliases.append(begin(X86Triples), end(X86Triples));
Zinovy Nis1db95732014-07-10 15:27:19 +00001640 }
Chandler Carruth866faab2012-01-25 07:21:38 +00001641 break;
1642 case llvm::Triple::x86:
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001643 LibDirs.append(begin(X86LibDirs), end(X86LibDirs));
Andrey Turetskiy4798eb62016-06-16 10:36:09 +00001644 // MCU toolchain is 32 bit only and its triple alias is TargetTriple
1645 // itself, which will be appended below.
1646 if (!TargetTriple.isOSIAMCU()) {
1647 TripleAliases.append(begin(X86Triples), end(X86Triples));
1648 BiarchLibDirs.append(begin(X86_64LibDirs), end(X86_64LibDirs));
1649 BiarchTripleAliases.append(begin(X86_64Triples), end(X86_64Triples));
1650 }
Chandler Carruth866faab2012-01-25 07:21:38 +00001651 break;
1652 case llvm::Triple::mips:
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001653 LibDirs.append(begin(MIPSLibDirs), end(MIPSLibDirs));
1654 TripleAliases.append(begin(MIPSTriples), end(MIPSTriples));
1655 BiarchLibDirs.append(begin(MIPS64LibDirs), end(MIPS64LibDirs));
1656 BiarchTripleAliases.append(begin(MIPS64Triples), end(MIPS64Triples));
Chandler Carruth866faab2012-01-25 07:21:38 +00001657 break;
1658 case llvm::Triple::mipsel:
Simon Atanasyan603018a2016-07-19 07:09:48 +00001659 if (TargetTriple.isAndroid()) {
1660 LibDirs.append(begin(MIPSELAndroidLibDirs), end(MIPSELAndroidLibDirs));
1661 TripleAliases.append(begin(MIPSELAndroidTriples),
1662 end(MIPSELAndroidTriples));
1663 BiarchLibDirs.append(begin(MIPS64ELAndroidLibDirs),
1664 end(MIPS64ELAndroidLibDirs));
1665 BiarchTripleAliases.append(begin(MIPS64ELAndroidTriples),
1666 end(MIPS64ELAndroidTriples));
1667
1668 } else {
1669 LibDirs.append(begin(MIPSELLibDirs), end(MIPSELLibDirs));
1670 TripleAliases.append(begin(MIPSELTriples), end(MIPSELTriples));
1671 TripleAliases.append(begin(MIPSTriples), end(MIPSTriples));
1672 BiarchLibDirs.append(begin(MIPS64ELLibDirs), end(MIPS64ELLibDirs));
1673 BiarchTripleAliases.append(begin(MIPS64ELTriples), end(MIPS64ELTriples));
1674 }
Simon Atanasyan9bb634d2012-04-26 19:57:02 +00001675 break;
1676 case llvm::Triple::mips64:
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001677 LibDirs.append(begin(MIPS64LibDirs), end(MIPS64LibDirs));
1678 TripleAliases.append(begin(MIPS64Triples), end(MIPS64Triples));
1679 BiarchLibDirs.append(begin(MIPSLibDirs), end(MIPSLibDirs));
1680 BiarchTripleAliases.append(begin(MIPSTriples), end(MIPSTriples));
Simon Atanasyan9bb634d2012-04-26 19:57:02 +00001681 break;
1682 case llvm::Triple::mips64el:
Simon Atanasyan603018a2016-07-19 07:09:48 +00001683 if (TargetTriple.isAndroid()) {
1684 LibDirs.append(begin(MIPS64ELAndroidLibDirs),
1685 end(MIPS64ELAndroidLibDirs));
1686 TripleAliases.append(begin(MIPS64ELAndroidTriples),
1687 end(MIPS64ELAndroidTriples));
1688 BiarchLibDirs.append(begin(MIPSELAndroidLibDirs),
1689 end(MIPSELAndroidLibDirs));
1690 BiarchTripleAliases.append(begin(MIPSELAndroidTriples),
1691 end(MIPSELAndroidTriples));
1692
1693 } else {
1694 LibDirs.append(begin(MIPS64ELLibDirs), end(MIPS64ELLibDirs));
1695 TripleAliases.append(begin(MIPS64ELTriples), end(MIPS64ELTriples));
1696 BiarchLibDirs.append(begin(MIPSELLibDirs), end(MIPSELLibDirs));
1697 BiarchTripleAliases.append(begin(MIPSELTriples), end(MIPSELTriples));
1698 BiarchTripleAliases.append(begin(MIPSTriples), end(MIPSTriples));
1699 }
Chandler Carruth866faab2012-01-25 07:21:38 +00001700 break;
1701 case llvm::Triple::ppc:
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001702 LibDirs.append(begin(PPCLibDirs), end(PPCLibDirs));
1703 TripleAliases.append(begin(PPCTriples), end(PPCTriples));
1704 BiarchLibDirs.append(begin(PPC64LibDirs), end(PPC64LibDirs));
1705 BiarchTripleAliases.append(begin(PPC64Triples), end(PPC64Triples));
Chandler Carruth866faab2012-01-25 07:21:38 +00001706 break;
1707 case llvm::Triple::ppc64:
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001708 LibDirs.append(begin(PPC64LibDirs), end(PPC64LibDirs));
1709 TripleAliases.append(begin(PPC64Triples), end(PPC64Triples));
1710 BiarchLibDirs.append(begin(PPCLibDirs), end(PPCLibDirs));
1711 BiarchTripleAliases.append(begin(PPCTriples), end(PPCTriples));
Chandler Carruth866faab2012-01-25 07:21:38 +00001712 break;
Bill Schmidt778d3872013-07-26 01:36:11 +00001713 case llvm::Triple::ppc64le:
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001714 LibDirs.append(begin(PPC64LELibDirs), end(PPC64LELibDirs));
1715 TripleAliases.append(begin(PPC64LETriples), end(PPC64LETriples));
Bill Schmidt778d3872013-07-26 01:36:11 +00001716 break;
Jakob Stoklund Olesenb3f938e2014-01-10 06:53:02 +00001717 case llvm::Triple::sparc:
Douglas Katzmanb76a3df2015-09-02 13:33:42 +00001718 case llvm::Triple::sparcel:
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001719 LibDirs.append(begin(SPARCv8LibDirs), end(SPARCv8LibDirs));
1720 TripleAliases.append(begin(SPARCv8Triples), end(SPARCv8Triples));
1721 BiarchLibDirs.append(begin(SPARCv9LibDirs), end(SPARCv9LibDirs));
1722 BiarchTripleAliases.append(begin(SPARCv9Triples), end(SPARCv9Triples));
Jakob Stoklund Olesenb3f938e2014-01-10 06:53:02 +00001723 break;
1724 case llvm::Triple::sparcv9:
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001725 LibDirs.append(begin(SPARCv9LibDirs), end(SPARCv9LibDirs));
1726 TripleAliases.append(begin(SPARCv9Triples), end(SPARCv9Triples));
1727 BiarchLibDirs.append(begin(SPARCv8LibDirs), end(SPARCv8LibDirs));
1728 BiarchTripleAliases.append(begin(SPARCv8Triples), end(SPARCv8Triples));
Jakob Stoklund Olesenb3f938e2014-01-10 06:53:02 +00001729 break;
Ulrich Weigand47445072013-05-06 16:26:41 +00001730 case llvm::Triple::systemz:
Benjamin Kramer6ec434e2014-10-18 10:43:51 +00001731 LibDirs.append(begin(SystemZLibDirs), end(SystemZLibDirs));
1732 TripleAliases.append(begin(SystemZTriples), end(SystemZTriples));
Ulrich Weigand47445072013-05-06 16:26:41 +00001733 break;
Chandler Carruth866faab2012-01-25 07:21:38 +00001734 default:
1735 // By default, just rely on the standard lib directories and the original
1736 // triple.
1737 break;
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001738 }
Chandler Carruth866faab2012-01-25 07:21:38 +00001739
1740 // Always append the drivers target triple to the end, in case it doesn't
1741 // match any of our aliases.
1742 TripleAliases.push_back(TargetTriple.str());
1743
1744 // Also include the multiarch variant if it's different.
Chandler Carruthb427c562013-06-22 11:35:51 +00001745 if (TargetTriple.str() != BiarchTriple.str())
1746 BiarchTripleAliases.push_back(BiarchTriple.str());
Chandler Carruth4c90fba2011-11-06 23:39:34 +00001747}
1748
Justin Lebarc43ad9e2016-07-07 18:17:52 +00001749// Parses the contents of version.txt in an CUDA installation. It should
1750// contain one line of the from e.g. "CUDA Version 7.5.2".
1751static CudaVersion ParseCudaVersionFile(llvm::StringRef V) {
1752 if (!V.startswith("CUDA Version "))
1753 return CudaVersion::UNKNOWN;
1754 V = V.substr(strlen("CUDA Version "));
1755 int Major = -1, Minor = -1;
1756 auto First = V.split('.');
1757 auto Second = First.second.split('.');
Justin Lebara27654a2016-08-15 20:38:48 +00001758 if (First.first.getAsInteger(10, Major) ||
1759 Second.first.getAsInteger(10, Minor))
Justin Lebarc43ad9e2016-07-07 18:17:52 +00001760 return CudaVersion::UNKNOWN;
1761
1762 if (Major == 7 && Minor == 0) {
1763 // This doesn't appear to ever happen -- version.txt doesn't exist in the
1764 // CUDA 7 installs I've seen. But no harm in checking.
1765 return CudaVersion::CUDA_70;
1766 }
1767 if (Major == 7 && Minor == 5)
1768 return CudaVersion::CUDA_75;
1769 if (Major == 8 && Minor == 0)
1770 return CudaVersion::CUDA_80;
1771 return CudaVersion::UNKNOWN;
1772}
1773
Artem Belevich98607b62015-09-23 21:49:39 +00001774// \brief -- try common CUDA installation paths looking for files we need for
1775// CUDA compilation.
Benjamin Kramerd45b2052015-10-07 15:48:01 +00001776void Generic_GCC::CudaInstallationDetector::init(
1777 const llvm::Triple &TargetTriple, const llvm::opt::ArgList &Args) {
NAKAMURA Takumi0c8decd2015-09-24 03:15:44 +00001778 SmallVector<std::string, 4> CudaPathCandidates;
Artem Belevich98607b62015-09-23 21:49:39 +00001779
1780 if (Args.hasArg(options::OPT_cuda_path_EQ))
1781 CudaPathCandidates.push_back(
1782 Args.getLastArgValue(options::OPT_cuda_path_EQ));
1783 else {
1784 CudaPathCandidates.push_back(D.SysRoot + "/usr/local/cuda");
Artem Belevichd4d9dc82016-09-28 17:47:40 +00001785 CudaPathCandidates.push_back(D.SysRoot + "/usr/local/cuda-8.0");
Artem Belevich86017332015-11-17 22:28:55 +00001786 CudaPathCandidates.push_back(D.SysRoot + "/usr/local/cuda-7.5");
Artem Belevich98607b62015-09-23 21:49:39 +00001787 CudaPathCandidates.push_back(D.SysRoot + "/usr/local/cuda-7.0");
1788 }
1789
Benjamin Kramere8b76412015-09-24 14:48:37 +00001790 for (const auto &CudaPath : CudaPathCandidates) {
Benjamin Kramerd45b2052015-10-07 15:48:01 +00001791 if (CudaPath.empty() || !D.getVFS().exists(CudaPath))
Artem Belevich98607b62015-09-23 21:49:39 +00001792 continue;
1793
Justin Lebar710c1312016-07-06 21:21:43 +00001794 InstallPath = CudaPath;
1795 BinPath = CudaPath + "/bin";
1796 IncludePath = InstallPath + "/include";
1797 LibDevicePath = InstallPath + "/nvvm/libdevice";
1798 LibPath = InstallPath + (TargetTriple.isArch64Bit() ? "/lib64" : "/lib");
Artem Belevich98607b62015-09-23 21:49:39 +00001799
Justin Lebar710c1312016-07-06 21:21:43 +00001800 auto &FS = D.getVFS();
1801 if (!(FS.exists(IncludePath) && FS.exists(BinPath) && FS.exists(LibPath) &&
1802 FS.exists(LibDevicePath)))
Artem Belevich98607b62015-09-23 21:49:39 +00001803 continue;
1804
Artem Belevichd4d9dc82016-09-28 17:47:40 +00001805 llvm::ErrorOr<std::unique_ptr<llvm::MemoryBuffer>> VersionFile =
1806 FS.getBufferForFile(InstallPath + "/version.txt");
1807 if (!VersionFile) {
1808 // CUDA 7.0 doesn't have a version.txt, so guess that's our version if
1809 // version.txt isn't present.
1810 Version = CudaVersion::CUDA_70;
1811 } else {
1812 Version = ParseCudaVersionFile((*VersionFile)->getBuffer());
1813 }
1814
Artem Belevich34f481a2015-11-17 22:28:50 +00001815 std::error_code EC;
Justin Lebar710c1312016-07-06 21:21:43 +00001816 for (llvm::sys::fs::directory_iterator LI(LibDevicePath, EC), LE;
Artem Belevich34f481a2015-11-17 22:28:50 +00001817 !EC && LI != LE; LI = LI.increment(EC)) {
1818 StringRef FilePath = LI->path();
1819 StringRef FileName = llvm::sys::path::filename(FilePath);
1820 // Process all bitcode filenames that look like libdevice.compute_XX.YY.bc
1821 const StringRef LibDeviceName = "libdevice.";
1822 if (!(FileName.startswith(LibDeviceName) && FileName.endswith(".bc")))
1823 continue;
1824 StringRef GpuArch = FileName.slice(
1825 LibDeviceName.size(), FileName.find('.', LibDeviceName.size()));
Justin Lebar710c1312016-07-06 21:21:43 +00001826 LibDeviceMap[GpuArch] = FilePath.str();
Artem Belevichd4d9dc82016-09-28 17:47:40 +00001827 // Insert map entries for specifc devices with this compute
1828 // capability. NVCC's choice of the libdevice library version is
1829 // rather peculiar and depends on the CUDA version.
Artem Belevich34f481a2015-11-17 22:28:50 +00001830 if (GpuArch == "compute_20") {
Justin Lebar710c1312016-07-06 21:21:43 +00001831 LibDeviceMap["sm_20"] = FilePath;
1832 LibDeviceMap["sm_21"] = FilePath;
Artem Belevich02a1e972016-08-02 23:12:51 +00001833 LibDeviceMap["sm_32"] = FilePath;
Artem Belevich34f481a2015-11-17 22:28:50 +00001834 } else if (GpuArch == "compute_30") {
Justin Lebar710c1312016-07-06 21:21:43 +00001835 LibDeviceMap["sm_30"] = FilePath;
Artem Belevichd4d9dc82016-09-28 17:47:40 +00001836 if (Version < CudaVersion::CUDA_80) {
1837 LibDeviceMap["sm_50"] = FilePath;
1838 LibDeviceMap["sm_52"] = FilePath;
1839 LibDeviceMap["sm_53"] = FilePath;
1840 }
Artem Belevich02a1e972016-08-02 23:12:51 +00001841 LibDeviceMap["sm_60"] = FilePath;
1842 LibDeviceMap["sm_61"] = FilePath;
1843 LibDeviceMap["sm_62"] = FilePath;
Artem Belevich34f481a2015-11-17 22:28:50 +00001844 } else if (GpuArch == "compute_35") {
Justin Lebar710c1312016-07-06 21:21:43 +00001845 LibDeviceMap["sm_35"] = FilePath;
1846 LibDeviceMap["sm_37"] = FilePath;
Artem Belevichffa5fc52016-05-19 17:47:47 +00001847 } else if (GpuArch == "compute_50") {
Artem Belevichd4d9dc82016-09-28 17:47:40 +00001848 if (Version >= CudaVersion::CUDA_80) {
1849 LibDeviceMap["sm_50"] = FilePath;
1850 LibDeviceMap["sm_52"] = FilePath;
1851 LibDeviceMap["sm_53"] = FilePath;
1852 }
Artem Belevich34f481a2015-11-17 22:28:50 +00001853 }
1854 }
1855
Artem Belevich98607b62015-09-23 21:49:39 +00001856 IsValid = true;
1857 break;
1858 }
1859}
1860
Justin Lebarc43ad9e2016-07-07 18:17:52 +00001861void Generic_GCC::CudaInstallationDetector::CheckCudaVersionSupportsArch(
1862 CudaArch Arch) const {
1863 if (Arch == CudaArch::UNKNOWN || Version == CudaVersion::UNKNOWN ||
1864 ArchsWithVersionTooLowErrors.count(Arch) > 0)
1865 return;
1866
1867 auto RequiredVersion = MinVersionForCudaArch(Arch);
1868 if (Version < RequiredVersion) {
1869 ArchsWithVersionTooLowErrors.insert(Arch);
1870 D.Diag(diag::err_drv_cuda_version_too_low)
1871 << InstallPath << CudaArchToString(Arch) << CudaVersionToString(Version)
1872 << CudaVersionToString(RequiredVersion);
1873 }
1874}
1875
Artem Belevich98607b62015-09-23 21:49:39 +00001876void Generic_GCC::CudaInstallationDetector::print(raw_ostream &OS) const {
1877 if (isValid())
Justin Lebarc43ad9e2016-07-07 18:17:52 +00001878 OS << "Found CUDA installation: " << InstallPath << ", version "
1879 << CudaVersionToString(Version) << "\n";
Artem Belevich98607b62015-09-23 21:49:39 +00001880}
1881
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00001882namespace {
1883// Filter to remove Multilibs that don't exist as a suffix to Path
Benjamin Kramerac75baa2015-03-22 15:56:12 +00001884class FilterNonExistent {
Andrey Turetskiy4798eb62016-06-16 10:36:09 +00001885 StringRef Base, File;
Benjamin Kramerc5862f02015-10-09 13:03:18 +00001886 vfs::FileSystem &VFS;
Benjamin Kramerac75baa2015-03-22 15:56:12 +00001887
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00001888public:
Andrey Turetskiy4798eb62016-06-16 10:36:09 +00001889 FilterNonExistent(StringRef Base, StringRef File, vfs::FileSystem &VFS)
1890 : Base(Base), File(File), VFS(VFS) {}
Benjamin Kramerac75baa2015-03-22 15:56:12 +00001891 bool operator()(const Multilib &M) {
Andrey Turetskiy4798eb62016-06-16 10:36:09 +00001892 return !VFS.exists(Base + M.gccSuffix() + File);
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00001893 }
1894};
1895} // end anonymous namespace
1896
1897static void addMultilibFlag(bool Enabled, const char *const Flag,
1898 std::vector<std::string> &Flags) {
1899 if (Enabled)
1900 Flags.push_back(std::string("+") + Flag);
1901 else
1902 Flags.push_back(std::string("-") + Flag);
1903}
1904
Chih-Hung Hsiehb4d3bf72016-06-01 20:48:46 +00001905static bool isArmOrThumbArch(llvm::Triple::ArchType Arch) {
1906 return Arch == llvm::Triple::arm || Arch == llvm::Triple::thumb;
1907}
1908
Simon Atanasyan08450bd2013-04-20 08:15:03 +00001909static bool isMipsArch(llvm::Triple::ArchType Arch) {
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00001910 return Arch == llvm::Triple::mips || Arch == llvm::Triple::mipsel ||
1911 Arch == llvm::Triple::mips64 || Arch == llvm::Triple::mips64el;
1912}
1913
1914static bool isMips32(llvm::Triple::ArchType Arch) {
1915 return Arch == llvm::Triple::mips || Arch == llvm::Triple::mipsel;
1916}
1917
1918static bool isMips64(llvm::Triple::ArchType Arch) {
1919 return Arch == llvm::Triple::mips64 || Arch == llvm::Triple::mips64el;
1920}
1921
1922static bool isMipsEL(llvm::Triple::ArchType Arch) {
1923 return Arch == llvm::Triple::mipsel || Arch == llvm::Triple::mips64el;
1924}
1925
Simon Atanasyan08450bd2013-04-20 08:15:03 +00001926static bool isMips16(const ArgList &Args) {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001927 Arg *A = Args.getLastArg(options::OPT_mips16, options::OPT_mno_mips16);
Simon Atanasyan08450bd2013-04-20 08:15:03 +00001928 return A && A->getOption().matches(options::OPT_mips16);
1929}
1930
1931static bool isMicroMips(const ArgList &Args) {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00001932 Arg *A = Args.getLastArg(options::OPT_mmicromips, options::OPT_mno_micromips);
Simon Atanasyan08450bd2013-04-20 08:15:03 +00001933 return A && A->getOption().matches(options::OPT_mmicromips);
1934}
1935
Benjamin Kramere003ca22015-10-28 13:54:16 +00001936namespace {
Simon Atanasyan60280b42014-05-12 07:37:51 +00001937struct DetectedMultilibs {
1938 /// The set of multilibs that the detected installation supports.
1939 MultilibSet Multilibs;
1940
1941 /// The primary multilib appropriate for the given flags.
1942 Multilib SelectedMultilib;
1943
1944 /// On Biarch systems, this corresponds to the default multilib when
1945 /// targeting the non-default multilib. Otherwise, it is empty.
1946 llvm::Optional<Multilib> BiarchSibling;
1947};
Benjamin Kramere003ca22015-10-28 13:54:16 +00001948} // end anonymous namespace
Simon Atanasyan60280b42014-05-12 07:37:51 +00001949
Simon Atanasyan1b0542e2014-07-30 09:15:10 +00001950static Multilib makeMultilib(StringRef commonSuffix) {
1951 return Multilib(commonSuffix, commonSuffix, commonSuffix);
1952}
1953
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00001954static bool findMipsCsMultilibs(const Multilib::flags_list &Flags,
1955 FilterNonExistent &NonExistent,
1956 DetectedMultilibs &Result) {
1957 // Check for Code Sourcery toolchain multilibs
1958 MultilibSet CSMipsMultilibs;
1959 {
1960 auto MArchMips16 = makeMultilib("/mips16").flag("+m32").flag("+mips16");
Simon Atanasyanee1accf2013-09-28 13:45:11 +00001961
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00001962 auto MArchMicroMips =
1963 makeMultilib("/micromips").flag("+m32").flag("+mmicromips");
Jonathan Roelofs3fa96d82014-02-12 01:36:51 +00001964
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00001965 auto MArchDefault = makeMultilib("").flag("-mips16").flag("-mmicromips");
1966
1967 auto UCLibc = makeMultilib("/uclibc").flag("+muclibc");
1968
1969 auto SoftFloat = makeMultilib("/soft-float").flag("+msoft-float");
1970
1971 auto Nan2008 = makeMultilib("/nan2008").flag("+mnan=2008");
1972
1973 auto DefaultFloat =
1974 makeMultilib("").flag("-msoft-float").flag("-mnan=2008");
1975
1976 auto BigEndian = makeMultilib("").flag("+EB").flag("-EL");
1977
1978 auto LittleEndian = makeMultilib("/el").flag("+EL").flag("-EB");
1979
1980 // Note that this one's osSuffix is ""
1981 auto MAbi64 = makeMultilib("")
1982 .gccSuffix("/64")
1983 .includeSuffix("/64")
1984 .flag("+mabi=n64")
1985 .flag("-mabi=n32")
1986 .flag("-m32");
1987
1988 CSMipsMultilibs =
1989 MultilibSet()
1990 .Either(MArchMips16, MArchMicroMips, MArchDefault)
1991 .Maybe(UCLibc)
1992 .Either(SoftFloat, Nan2008, DefaultFloat)
1993 .FilterOut("/micromips/nan2008")
1994 .FilterOut("/mips16/nan2008")
1995 .Either(BigEndian, LittleEndian)
1996 .Maybe(MAbi64)
1997 .FilterOut("/mips16.*/64")
1998 .FilterOut("/micromips.*/64")
1999 .FilterOut(NonExistent)
2000 .setIncludeDirsCallback([](const Multilib &M) {
2001 std::vector<std::string> Dirs({"/include"});
2002 if (StringRef(M.includeSuffix()).startswith("/uclibc"))
2003 Dirs.push_back(
2004 "/../../../../mips-linux-gnu/libc/uclibc/usr/include");
2005 else
2006 Dirs.push_back("/../../../../mips-linux-gnu/libc/usr/include");
2007 return Dirs;
2008 });
2009 }
2010
2011 MultilibSet DebianMipsMultilibs;
2012 {
2013 Multilib MAbiN32 =
2014 Multilib().gccSuffix("/n32").includeSuffix("/n32").flag("+mabi=n32");
2015
2016 Multilib M64 = Multilib()
2017 .gccSuffix("/64")
2018 .includeSuffix("/64")
2019 .flag("+m64")
2020 .flag("-m32")
2021 .flag("-mabi=n32");
2022
2023 Multilib M32 = Multilib().flag("-m64").flag("+m32").flag("-mabi=n32");
2024
2025 DebianMipsMultilibs =
2026 MultilibSet().Either(M32, M64, MAbiN32).FilterOut(NonExistent);
2027 }
2028
2029 // Sort candidates. Toolchain that best meets the directories tree goes first.
2030 // Then select the first toolchains matches command line flags.
2031 MultilibSet *Candidates[] = {&CSMipsMultilibs, &DebianMipsMultilibs};
2032 if (CSMipsMultilibs.size() < DebianMipsMultilibs.size())
2033 std::iter_swap(Candidates, Candidates + 1);
2034 for (const MultilibSet *Candidate : Candidates) {
2035 if (Candidate->select(Flags, Result.SelectedMultilib)) {
2036 if (Candidate == &DebianMipsMultilibs)
2037 Result.BiarchSibling = Multilib();
2038 Result.Multilibs = *Candidate;
2039 return true;
2040 }
2041 }
2042 return false;
2043}
2044
Simon Atanasyan603018a2016-07-19 07:09:48 +00002045static bool findMipsAndroidMultilibs(vfs::FileSystem &VFS, StringRef Path,
2046 const Multilib::flags_list &Flags,
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00002047 FilterNonExistent &NonExistent,
2048 DetectedMultilibs &Result) {
2049
2050 MultilibSet AndroidMipsMultilibs =
2051 MultilibSet()
2052 .Maybe(Multilib("/mips-r2").flag("+march=mips32r2"))
2053 .Maybe(Multilib("/mips-r6").flag("+march=mips32r6"))
2054 .FilterOut(NonExistent);
2055
Simon Atanasyan603018a2016-07-19 07:09:48 +00002056 MultilibSet AndroidMipselMultilibs =
2057 MultilibSet()
2058 .Either(Multilib().flag("+march=mips32"),
2059 Multilib("/mips-r2", "", "/mips-r2").flag("+march=mips32r2"),
2060 Multilib("/mips-r6", "", "/mips-r6").flag("+march=mips32r6"))
2061 .FilterOut(NonExistent);
2062
2063 MultilibSet AndroidMips64elMultilibs =
2064 MultilibSet()
2065 .Either(
2066 Multilib().flag("+march=mips64r6"),
2067 Multilib("/32/mips-r1", "", "/mips-r1").flag("+march=mips32"),
2068 Multilib("/32/mips-r2", "", "/mips-r2").flag("+march=mips32r2"),
2069 Multilib("/32/mips-r6", "", "/mips-r6").flag("+march=mips32r6"))
2070 .FilterOut(NonExistent);
2071
2072 MultilibSet *MS = &AndroidMipsMultilibs;
2073 if (VFS.exists(Path + "/mips-r6"))
2074 MS = &AndroidMipselMultilibs;
2075 else if (VFS.exists(Path + "/32"))
2076 MS = &AndroidMips64elMultilibs;
2077 if (MS->select(Flags, Result.SelectedMultilib)) {
2078 Result.Multilibs = *MS;
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00002079 return true;
2080 }
2081 return false;
2082}
2083
2084static bool findMipsMuslMultilibs(const Multilib::flags_list &Flags,
2085 FilterNonExistent &NonExistent,
2086 DetectedMultilibs &Result) {
2087 // Musl toolchain multilibs
2088 MultilibSet MuslMipsMultilibs;
2089 {
2090 auto MArchMipsR2 = makeMultilib("")
2091 .osSuffix("/mips-r2-hard-musl")
2092 .flag("+EB")
2093 .flag("-EL")
2094 .flag("+march=mips32r2");
2095
2096 auto MArchMipselR2 = makeMultilib("/mipsel-r2-hard-musl")
2097 .flag("-EB")
2098 .flag("+EL")
2099 .flag("+march=mips32r2");
2100
2101 MuslMipsMultilibs = MultilibSet().Either(MArchMipsR2, MArchMipselR2);
2102
2103 // Specify the callback that computes the include directories.
2104 MuslMipsMultilibs.setIncludeDirsCallback([](const Multilib &M) {
2105 return std::vector<std::string>(
2106 {"/../sysroot" + M.osSuffix() + "/usr/include"});
2107 });
2108 }
2109 if (MuslMipsMultilibs.select(Flags, Result.SelectedMultilib)) {
2110 Result.Multilibs = MuslMipsMultilibs;
2111 return true;
2112 }
2113 return false;
2114}
2115
2116static bool findMipsMtiMultilibs(const Multilib::flags_list &Flags,
2117 FilterNonExistent &NonExistent,
2118 DetectedMultilibs &Result) {
2119 // CodeScape MTI toolchain v1.2 and early.
Simon Atanasyancf7ac672016-05-22 15:27:58 +00002120 MultilibSet MtiMipsMultilibsV1;
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002121 {
Simon Atanasyan1b0542e2014-07-30 09:15:10 +00002122 auto MArchMips32 = makeMultilib("/mips32")
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002123 .flag("+m32")
2124 .flag("-m64")
2125 .flag("-mmicromips")
2126 .flag("+march=mips32");
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002127
Simon Atanasyan1b0542e2014-07-30 09:15:10 +00002128 auto MArchMicroMips = makeMultilib("/micromips")
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002129 .flag("+m32")
2130 .flag("-m64")
2131 .flag("+mmicromips");
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002132
Simon Atanasyan1b0542e2014-07-30 09:15:10 +00002133 auto MArchMips64r2 = makeMultilib("/mips64r2")
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002134 .flag("-m32")
2135 .flag("+m64")
2136 .flag("+march=mips64r2");
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002137
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002138 auto MArchMips64 = makeMultilib("/mips64").flag("-m32").flag("+m64").flag(
2139 "-march=mips64r2");
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002140
Simon Atanasyan1b0542e2014-07-30 09:15:10 +00002141 auto MArchDefault = makeMultilib("")
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002142 .flag("+m32")
2143 .flag("-m64")
2144 .flag("-mmicromips")
2145 .flag("+march=mips32r2");
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002146
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002147 auto Mips16 = makeMultilib("/mips16").flag("+mips16");
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002148
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002149 auto UCLibc = makeMultilib("/uclibc").flag("+muclibc");
Simon Atanasyand95c67d2014-08-13 14:34:14 +00002150
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002151 auto MAbi64 =
2152 makeMultilib("/64").flag("+mabi=n64").flag("-mabi=n32").flag("-m32");
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002153
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002154 auto BigEndian = makeMultilib("").flag("+EB").flag("-EL");
Simon Atanasyan738f85a2014-03-04 18:37:28 +00002155
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002156 auto LittleEndian = makeMultilib("/el").flag("+EL").flag("-EB");
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002157
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002158 auto SoftFloat = makeMultilib("/sof").flag("+msoft-float");
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002159
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002160 auto Nan2008 = makeMultilib("/nan2008").flag("+mnan=2008");
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002161
Simon Atanasyancf7ac672016-05-22 15:27:58 +00002162 MtiMipsMultilibsV1 =
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002163 MultilibSet()
2164 .Either(MArchMips32, MArchMicroMips, MArchMips64r2, MArchMips64,
2165 MArchDefault)
2166 .Maybe(UCLibc)
2167 .Maybe(Mips16)
2168 .FilterOut("/mips64/mips16")
2169 .FilterOut("/mips64r2/mips16")
2170 .FilterOut("/micromips/mips16")
2171 .Maybe(MAbi64)
2172 .FilterOut("/micromips/64")
2173 .FilterOut("/mips32/64")
2174 .FilterOut("^/64")
2175 .FilterOut("/mips16/64")
2176 .Either(BigEndian, LittleEndian)
2177 .Maybe(SoftFloat)
2178 .Maybe(Nan2008)
2179 .FilterOut(".*sof/nan2008")
2180 .FilterOut(NonExistent)
Simon Atanasyana45502d2016-05-19 15:07:21 +00002181 .setIncludeDirsCallback([](const Multilib &M) {
2182 std::vector<std::string> Dirs({"/include"});
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002183 if (StringRef(M.includeSuffix()).startswith("/uclibc"))
Simon Atanasyana45502d2016-05-19 15:07:21 +00002184 Dirs.push_back("/../../../../sysroot/uclibc/usr/include");
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002185 else
Simon Atanasyana45502d2016-05-19 15:07:21 +00002186 Dirs.push_back("/../../../../sysroot/usr/include");
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002187 return Dirs;
2188 });
Simon Atanasyan13e965a2013-11-26 11:57:14 +00002189 }
2190
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00002191 // CodeScape IMG toolchain starting from v1.3.
Simon Atanasyan2834a222016-05-22 18:18:07 +00002192 MultilibSet MtiMipsMultilibsV2;
2193 {
2194 auto BeHard = makeMultilib("/mips-r2-hard")
2195 .flag("+EB")
2196 .flag("-msoft-float")
2197 .flag("-mnan=2008")
2198 .flag("-muclibc");
2199 auto BeSoft = makeMultilib("/mips-r2-soft")
2200 .flag("+EB")
2201 .flag("+msoft-float")
2202 .flag("-mnan=2008");
2203 auto ElHard = makeMultilib("/mipsel-r2-hard")
2204 .flag("+EL")
2205 .flag("-msoft-float")
2206 .flag("-mnan=2008")
2207 .flag("-muclibc");
2208 auto ElSoft = makeMultilib("/mipsel-r2-soft")
2209 .flag("+EL")
2210 .flag("+msoft-float")
2211 .flag("-mnan=2008")
2212 .flag("-mmicromips");
2213 auto BeHardNan = makeMultilib("/mips-r2-hard-nan2008")
2214 .flag("+EB")
2215 .flag("-msoft-float")
2216 .flag("+mnan=2008")
2217 .flag("-muclibc");
2218 auto ElHardNan = makeMultilib("/mipsel-r2-hard-nan2008")
2219 .flag("+EL")
2220 .flag("-msoft-float")
2221 .flag("+mnan=2008")
2222 .flag("-muclibc")
2223 .flag("-mmicromips");
2224 auto BeHardNanUclibc = makeMultilib("/mips-r2-hard-nan2008-uclibc")
2225 .flag("+EB")
2226 .flag("-msoft-float")
2227 .flag("+mnan=2008")
2228 .flag("+muclibc");
2229 auto ElHardNanUclibc = makeMultilib("/mipsel-r2-hard-nan2008-uclibc")
2230 .flag("+EL")
2231 .flag("-msoft-float")
2232 .flag("+mnan=2008")
2233 .flag("+muclibc");
2234 auto BeHardUclibc = makeMultilib("/mips-r2-hard-uclibc")
2235 .flag("+EB")
2236 .flag("-msoft-float")
2237 .flag("-mnan=2008")
2238 .flag("+muclibc");
2239 auto ElHardUclibc = makeMultilib("/mipsel-r2-hard-uclibc")
2240 .flag("+EL")
2241 .flag("-msoft-float")
2242 .flag("-mnan=2008")
2243 .flag("+muclibc");
2244 auto ElMicroHardNan = makeMultilib("/micromipsel-r2-hard-nan2008")
2245 .flag("+EL")
2246 .flag("-msoft-float")
2247 .flag("+mnan=2008")
2248 .flag("+mmicromips");
2249 auto ElMicroSoft = makeMultilib("/micromipsel-r2-soft")
2250 .flag("+EL")
2251 .flag("+msoft-float")
2252 .flag("-mnan=2008")
2253 .flag("+mmicromips");
2254
2255 auto O32 =
2256 makeMultilib("/lib").osSuffix("").flag("-mabi=n32").flag("-mabi=n64");
2257 auto N32 =
2258 makeMultilib("/lib32").osSuffix("").flag("+mabi=n32").flag("-mabi=n64");
2259 auto N64 =
2260 makeMultilib("/lib64").osSuffix("").flag("-mabi=n32").flag("+mabi=n64");
2261
2262 MtiMipsMultilibsV2 =
2263 MultilibSet()
2264 .Either({BeHard, BeSoft, ElHard, ElSoft, BeHardNan, ElHardNan,
2265 BeHardNanUclibc, ElHardNanUclibc, BeHardUclibc,
2266 ElHardUclibc, ElMicroHardNan, ElMicroSoft})
2267 .Either(O32, N32, N64)
2268 .FilterOut(NonExistent)
2269 .setIncludeDirsCallback([](const Multilib &M) {
2270 return std::vector<std::string>({"/../../../../sysroot" +
2271 M.includeSuffix() +
2272 "/../usr/include"});
2273 })
2274 .setFilePathsCallback([](const Multilib &M) {
2275 return std::vector<std::string>(
2276 {"/../../../../mips-mti-linux-gnu/lib" + M.gccSuffix()});
2277 });
2278 }
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00002279 for (auto Candidate : {&MtiMipsMultilibsV1, &MtiMipsMultilibsV2}) {
2280 if (Candidate->select(Flags, Result.SelectedMultilib)) {
2281 Result.Multilibs = *Candidate;
2282 return true;
2283 }
Vasileios Kalintirisc744e122015-11-12 15:26:54 +00002284 }
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00002285 return false;
2286}
Vasileios Kalintirisc744e122015-11-12 15:26:54 +00002287
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00002288static bool findMipsImgMultilibs(const Multilib::flags_list &Flags,
2289 FilterNonExistent &NonExistent,
2290 DetectedMultilibs &Result) {
2291 // CodeScape IMG toolchain v1.2 and early.
Simon Atanasyancf7ac672016-05-22 15:27:58 +00002292 MultilibSet ImgMultilibsV1;
Daniel Sanders2bf13662014-07-10 14:40:57 +00002293 {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002294 auto Mips64r6 = makeMultilib("/mips64r6").flag("+m64").flag("-m32");
Daniel Sanders2bf13662014-07-10 14:40:57 +00002295
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002296 auto LittleEndian = makeMultilib("/el").flag("+EL").flag("-EB");
Daniel Sanders2bf13662014-07-10 14:40:57 +00002297
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002298 auto MAbi64 =
2299 makeMultilib("/64").flag("+mabi=n64").flag("-mabi=n32").flag("-m32");
Daniel Sanders2bf13662014-07-10 14:40:57 +00002300
Simon Atanasyancf7ac672016-05-22 15:27:58 +00002301 ImgMultilibsV1 =
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002302 MultilibSet()
2303 .Maybe(Mips64r6)
2304 .Maybe(MAbi64)
2305 .Maybe(LittleEndian)
2306 .FilterOut(NonExistent)
Simon Atanasyana45502d2016-05-19 15:07:21 +00002307 .setIncludeDirsCallback([](const Multilib &M) {
2308 return std::vector<std::string>(
2309 {"/include", "/../../../../sysroot/usr/include"});
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002310 });
Daniel Sanders2bf13662014-07-10 14:40:57 +00002311 }
2312
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00002313 // CodeScape IMG toolchain starting from v1.3.
Simon Atanasyan2834a222016-05-22 18:18:07 +00002314 MultilibSet ImgMultilibsV2;
2315 {
2316 auto BeHard = makeMultilib("/mips-r6-hard")
2317 .flag("+EB")
2318 .flag("-msoft-float")
2319 .flag("-mmicromips");
2320 auto BeSoft = makeMultilib("/mips-r6-soft")
2321 .flag("+EB")
2322 .flag("+msoft-float")
2323 .flag("-mmicromips");
2324 auto ElHard = makeMultilib("/mipsel-r6-hard")
2325 .flag("+EL")
2326 .flag("-msoft-float")
2327 .flag("-mmicromips");
2328 auto ElSoft = makeMultilib("/mipsel-r6-soft")
2329 .flag("+EL")
2330 .flag("+msoft-float")
2331 .flag("-mmicromips");
2332 auto BeMicroHard = makeMultilib("/micromips-r6-hard")
Simon Atanasyan6c51f5a2016-05-22 18:18:41 +00002333 .flag("+EB")
2334 .flag("-msoft-float")
2335 .flag("+mmicromips");
Simon Atanasyan2834a222016-05-22 18:18:07 +00002336 auto BeMicroSoft = makeMultilib("/micromips-r6-soft")
Simon Atanasyan6c51f5a2016-05-22 18:18:41 +00002337 .flag("+EB")
2338 .flag("+msoft-float")
2339 .flag("+mmicromips");
Simon Atanasyan2834a222016-05-22 18:18:07 +00002340 auto ElMicroHard = makeMultilib("/micromipsel-r6-hard")
Simon Atanasyan6c51f5a2016-05-22 18:18:41 +00002341 .flag("+EL")
2342 .flag("-msoft-float")
2343 .flag("+mmicromips");
Simon Atanasyan2834a222016-05-22 18:18:07 +00002344 auto ElMicroSoft = makeMultilib("/micromipsel-r6-soft")
Simon Atanasyan6c51f5a2016-05-22 18:18:41 +00002345 .flag("+EL")
2346 .flag("+msoft-float")
2347 .flag("+mmicromips");
Simon Atanasyan2834a222016-05-22 18:18:07 +00002348
2349 auto O32 =
2350 makeMultilib("/lib").osSuffix("").flag("-mabi=n32").flag("-mabi=n64");
2351 auto N32 =
2352 makeMultilib("/lib32").osSuffix("").flag("+mabi=n32").flag("-mabi=n64");
2353 auto N64 =
2354 makeMultilib("/lib64").osSuffix("").flag("-mabi=n32").flag("+mabi=n64");
2355
Simon Atanasyan6c51f5a2016-05-22 18:18:41 +00002356 ImgMultilibsV2 =
2357 MultilibSet()
2358 .Either({BeHard, BeSoft, ElHard, ElSoft, BeMicroHard, BeMicroSoft,
2359 ElMicroHard, ElMicroSoft})
2360 .Either(O32, N32, N64)
2361 .FilterOut(NonExistent)
2362 .setIncludeDirsCallback([](const Multilib &M) {
2363 return std::vector<std::string>({"/../../../../sysroot" +
2364 M.includeSuffix() +
2365 "/../usr/include"});
2366 })
2367 .setFilePathsCallback([](const Multilib &M) {
2368 return std::vector<std::string>(
2369 {"/../../../../mips-img-linux-gnu/lib" + M.gccSuffix()});
2370 });
Simon Atanasyan2834a222016-05-22 18:18:07 +00002371 }
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00002372 for (auto Candidate : {&ImgMultilibsV1, &ImgMultilibsV2}) {
2373 if (Candidate->select(Flags, Result.SelectedMultilib)) {
2374 Result.Multilibs = *Candidate;
2375 return true;
2376 }
2377 }
2378 return false;
2379}
2380
2381static bool findMIPSMultilibs(const Driver &D, const llvm::Triple &TargetTriple,
2382 StringRef Path, const ArgList &Args,
2383 DetectedMultilibs &Result) {
2384 FilterNonExistent NonExistent(Path, "/crtbegin.o", D.getVFS());
Simon Atanasyan2834a222016-05-22 18:18:07 +00002385
Simon Atanasyan7018e1d2014-07-16 12:29:22 +00002386 StringRef CPUName;
2387 StringRef ABIName;
2388 tools::mips::getMipsCPUAndABI(Args, TargetTriple, CPUName, ABIName);
2389
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002390 llvm::Triple::ArchType TargetArch = TargetTriple.getArch();
2391
2392 Multilib::flags_list Flags;
2393 addMultilibFlag(isMips32(TargetArch), "m32", Flags);
2394 addMultilibFlag(isMips64(TargetArch), "m64", Flags);
2395 addMultilibFlag(isMips16(Args), "mips16", Flags);
Simon Atanasyan9988e3a2014-07-16 17:34:54 +00002396 addMultilibFlag(CPUName == "mips32", "march=mips32", Flags);
Simon Atanasyan59b25cb2015-02-26 04:45:57 +00002397 addMultilibFlag(CPUName == "mips32r2" || CPUName == "mips32r3" ||
Daniel Sandersff952582015-10-05 12:24:30 +00002398 CPUName == "mips32r5" || CPUName == "p5600",
Simon Atanasyan59b25cb2015-02-26 04:45:57 +00002399 "march=mips32r2", Flags);
Simon Atanasyan3f024032015-02-25 07:31:12 +00002400 addMultilibFlag(CPUName == "mips32r6", "march=mips32r6", Flags);
Simon Atanasyan9988e3a2014-07-16 17:34:54 +00002401 addMultilibFlag(CPUName == "mips64", "march=mips64", Flags);
Simon Atanasyan59b25cb2015-02-26 04:45:57 +00002402 addMultilibFlag(CPUName == "mips64r2" || CPUName == "mips64r3" ||
2403 CPUName == "mips64r5" || CPUName == "octeon",
Simon Atanasyan9988e3a2014-07-16 17:34:54 +00002404 "march=mips64r2", Flags);
Simon Atanasyan603018a2016-07-19 07:09:48 +00002405 addMultilibFlag(CPUName == "mips64r6", "march=mips64r6", Flags);
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002406 addMultilibFlag(isMicroMips(Args), "mmicromips", Flags);
Simon Atanasyand95c67d2014-08-13 14:34:14 +00002407 addMultilibFlag(tools::mips::isUCLibc(Args), "muclibc", Flags);
Simon Atanasyanab6db9f2014-07-16 12:24:48 +00002408 addMultilibFlag(tools::mips::isNaN2008(Args, TargetTriple), "mnan=2008",
2409 Flags);
Simon Atanasyan7018e1d2014-07-16 12:29:22 +00002410 addMultilibFlag(ABIName == "n32", "mabi=n32", Flags);
2411 addMultilibFlag(ABIName == "n64", "mabi=n64", Flags);
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002412 addMultilibFlag(isSoftFloatABI(Args), "msoft-float", Flags);
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002413 addMultilibFlag(!isSoftFloatABI(Args), "mhard-float", Flags);
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002414 addMultilibFlag(isMipsEL(TargetArch), "EL", Flags);
Simon Atanasyan7018e1d2014-07-16 12:29:22 +00002415 addMultilibFlag(!isMipsEL(TargetArch), "EB", Flags);
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002416
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00002417 if (TargetTriple.isAndroid())
Simon Atanasyan603018a2016-07-19 07:09:48 +00002418 return findMipsAndroidMultilibs(D.getVFS(), Path, Flags, NonExistent,
2419 Result);
Simon Atanasyan738f85a2014-03-04 18:37:28 +00002420
Vasileios Kalintirisc744e122015-11-12 15:26:54 +00002421 if (TargetTriple.getVendor() == llvm::Triple::MipsTechnologies &&
2422 TargetTriple.getOS() == llvm::Triple::Linux &&
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00002423 TargetTriple.getEnvironment() == llvm::Triple::UnknownEnvironment)
2424 return findMipsMuslMultilibs(Flags, NonExistent, Result);
Vasileios Kalintirisc744e122015-11-12 15:26:54 +00002425
Simon Atanasyan4f3fe5b2016-05-22 15:28:34 +00002426 if (TargetTriple.getVendor() == llvm::Triple::MipsTechnologies &&
2427 TargetTriple.getOS() == llvm::Triple::Linux &&
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00002428 TargetTriple.getEnvironment() == llvm::Triple::GNU)
2429 return findMipsMtiMultilibs(Flags, NonExistent, Result);
Simon Atanasyan4f3fe5b2016-05-22 15:28:34 +00002430
Daniel Sanders2bf13662014-07-10 14:40:57 +00002431 if (TargetTriple.getVendor() == llvm::Triple::ImaginationTechnologies &&
2432 TargetTriple.getOS() == llvm::Triple::Linux &&
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00002433 TargetTriple.getEnvironment() == llvm::Triple::GNU)
2434 return findMipsImgMultilibs(Flags, NonExistent, Result);
Daniel Sanders2bf13662014-07-10 14:40:57 +00002435
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00002436 if (findMipsCsMultilibs(Flags, NonExistent, Result))
2437 return true;
Simon Atanasyan738f85a2014-03-04 18:37:28 +00002438
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00002439 // Fallback to the regular toolchain-tree structure.
2440 Multilib Default;
2441 Result.Multilibs.push_back(Default);
2442 Result.Multilibs.FilterOut(NonExistent);
Simon Atanasyan3a46afa2014-06-24 19:00:12 +00002443
Simon Atanasyanb4abcc52016-06-22 20:00:50 +00002444 if (Result.Multilibs.select(Flags, Result.SelectedMultilib)) {
2445 Result.BiarchSibling = Multilib();
2446 return true;
Simon Atanasyan3a46afa2014-06-24 19:00:12 +00002447 }
2448
Simon Atanasyan738f85a2014-03-04 18:37:28 +00002449 return false;
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002450}
2451
Chih-Hung Hsiehb4d3bf72016-06-01 20:48:46 +00002452static void findAndroidArmMultilibs(const Driver &D,
2453 const llvm::Triple &TargetTriple,
2454 StringRef Path, const ArgList &Args,
2455 DetectedMultilibs &Result) {
2456 // Find multilibs with subdirectories like armv7-a, thumb, armv7-a/thumb.
Andrey Turetskiy4798eb62016-06-16 10:36:09 +00002457 FilterNonExistent NonExistent(Path, "/crtbegin.o", D.getVFS());
Chih-Hung Hsiehb4d3bf72016-06-01 20:48:46 +00002458 Multilib ArmV7Multilib = makeMultilib("/armv7-a")
2459 .flag("+armv7")
2460 .flag("-thumb");
2461 Multilib ThumbMultilib = makeMultilib("/thumb")
2462 .flag("-armv7")
2463 .flag("+thumb");
2464 Multilib ArmV7ThumbMultilib = makeMultilib("/armv7-a/thumb")
2465 .flag("+armv7")
2466 .flag("+thumb");
2467 Multilib DefaultMultilib = makeMultilib("")
2468 .flag("-armv7")
2469 .flag("-thumb");
2470 MultilibSet AndroidArmMultilibs =
2471 MultilibSet()
2472 .Either(ThumbMultilib, ArmV7Multilib,
2473 ArmV7ThumbMultilib, DefaultMultilib)
2474 .FilterOut(NonExistent);
2475
2476 Multilib::flags_list Flags;
2477 llvm::StringRef Arch = Args.getLastArgValue(options::OPT_march_EQ);
2478 bool IsArmArch = TargetTriple.getArch() == llvm::Triple::arm;
2479 bool IsThumbArch = TargetTriple.getArch() == llvm::Triple::thumb;
2480 bool IsV7SubArch = TargetTriple.getSubArch() == llvm::Triple::ARMSubArch_v7;
2481 bool IsThumbMode = IsThumbArch ||
2482 Args.hasFlag(options::OPT_mthumb, options::OPT_mno_thumb, false) ||
2483 (IsArmArch && llvm::ARM::parseArchISA(Arch) == llvm::ARM::IK_THUMB);
2484 bool IsArmV7Mode = (IsArmArch || IsThumbArch) &&
2485 (llvm::ARM::parseArchVersion(Arch) == 7 ||
2486 (IsArmArch && Arch == "" && IsV7SubArch));
2487 addMultilibFlag(IsArmV7Mode, "armv7", Flags);
2488 addMultilibFlag(IsThumbMode, "thumb", Flags);
2489
2490 if (AndroidArmMultilibs.select(Flags, Result.SelectedMultilib))
2491 Result.Multilibs = AndroidArmMultilibs;
2492}
2493
Benjamin Kramerc5862f02015-10-09 13:03:18 +00002494static bool findBiarchMultilibs(const Driver &D,
2495 const llvm::Triple &TargetTriple,
Simon Atanasyan60280b42014-05-12 07:37:51 +00002496 StringRef Path, const ArgList &Args,
2497 bool NeedsBiarchSuffix,
2498 DetectedMultilibs &Result) {
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002499 // Some versions of SUSE and Fedora on ppc64 put 32-bit libs
2500 // in what would normally be GCCInstallPath and put the 64-bit
2501 // libs in a subdirectory named 64. The simple logic we follow is that
2502 // *if* there is a subdirectory of the right name with crtbegin.o in it,
2503 // we use that. If not, and if not a biarch triple alias, we look for
2504 // crtbegin.o without the subdirectory.
2505
2506 Multilib Default;
2507 Multilib Alt64 = Multilib()
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002508 .gccSuffix("/64")
2509 .includeSuffix("/64")
2510 .flag("-m32")
2511 .flag("+m64")
2512 .flag("-mx32");
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002513 Multilib Alt32 = Multilib()
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002514 .gccSuffix("/32")
2515 .includeSuffix("/32")
2516 .flag("+m32")
2517 .flag("-m64")
2518 .flag("-mx32");
Zinovy Nis1db95732014-07-10 15:27:19 +00002519 Multilib Altx32 = Multilib()
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002520 .gccSuffix("/x32")
2521 .includeSuffix("/x32")
2522 .flag("-m32")
2523 .flag("-m64")
2524 .flag("+mx32");
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002525
Andrey Turetskiy4798eb62016-06-16 10:36:09 +00002526 // GCC toolchain for IAMCU doesn't have crtbegin.o, so look for libgcc.a.
2527 FilterNonExistent NonExistent(
2528 Path, TargetTriple.isOSIAMCU() ? "/libgcc.a" : "/crtbegin.o", D.getVFS());
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002529
Zinovy Nis1db95732014-07-10 15:27:19 +00002530 // Determine default multilib from: 32, 64, x32
2531 // Also handle cases such as 64 on 32, 32 on 64, etc.
2532 enum { UNKNOWN, WANT32, WANT64, WANTX32 } Want = UNKNOWN;
David Blaikie40f842d2014-07-10 18:46:15 +00002533 const bool IsX32 = TargetTriple.getEnvironment() == llvm::Triple::GNUX32;
Alp Tokerf45fa3d2014-02-25 04:21:44 +00002534 if (TargetTriple.isArch32Bit() && !NonExistent(Alt32))
Zinovy Nis1db95732014-07-10 15:27:19 +00002535 Want = WANT64;
Zinovy Nis6e3c6302014-07-10 15:42:35 +00002536 else if (TargetTriple.isArch64Bit() && IsX32 && !NonExistent(Altx32))
Zinovy Nis1db95732014-07-10 15:27:19 +00002537 Want = WANT64;
Zinovy Nis6e3c6302014-07-10 15:42:35 +00002538 else if (TargetTriple.isArch64Bit() && !IsX32 && !NonExistent(Alt64))
Zinovy Nis1db95732014-07-10 15:27:19 +00002539 Want = WANT32;
Jonathan Roelofs3fa96d82014-02-12 01:36:51 +00002540 else {
Zinovy Nis1db95732014-07-10 15:27:19 +00002541 if (TargetTriple.isArch32Bit())
2542 Want = NeedsBiarchSuffix ? WANT64 : WANT32;
Zinovy Nis6e3c6302014-07-10 15:42:35 +00002543 else if (IsX32)
Zinovy Nis1db95732014-07-10 15:27:19 +00002544 Want = NeedsBiarchSuffix ? WANT64 : WANTX32;
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002545 else
Zinovy Nis1db95732014-07-10 15:27:19 +00002546 Want = NeedsBiarchSuffix ? WANT32 : WANT64;
Jonathan Roelofs0e7ec602014-02-12 01:29:25 +00002547 }
2548
Zinovy Nis1db95732014-07-10 15:27:19 +00002549 if (Want == WANT32)
2550 Default.flag("+m32").flag("-m64").flag("-mx32");
2551 else if (Want == WANT64)
2552 Default.flag("-m32").flag("+m64").flag("-mx32");
2553 else if (Want == WANTX32)
2554 Default.flag("-m32").flag("-m64").flag("+mx32");
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002555 else
Zinovy Nis1db95732014-07-10 15:27:19 +00002556 return false;
Jonathan Roelofs3fa96d82014-02-12 01:36:51 +00002557
Simon Atanasyan60280b42014-05-12 07:37:51 +00002558 Result.Multilibs.push_back(Default);
2559 Result.Multilibs.push_back(Alt64);
2560 Result.Multilibs.push_back(Alt32);
Zinovy Nis1db95732014-07-10 15:27:19 +00002561 Result.Multilibs.push_back(Altx32);
Jonathan Roelofs3fa96d82014-02-12 01:36:51 +00002562
Simon Atanasyan60280b42014-05-12 07:37:51 +00002563 Result.Multilibs.FilterOut(NonExistent);
Jonathan Roelofs3fa96d82014-02-12 01:36:51 +00002564
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002565 Multilib::flags_list Flags;
Zinovy Nis6e3c6302014-07-10 15:42:35 +00002566 addMultilibFlag(TargetTriple.isArch64Bit() && !IsX32, "m64", Flags);
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002567 addMultilibFlag(TargetTriple.isArch32Bit(), "m32", Flags);
Zinovy Nis6e3c6302014-07-10 15:42:35 +00002568 addMultilibFlag(TargetTriple.isArch64Bit() && IsX32, "mx32", Flags);
Jonathan Roelofs3fa96d82014-02-12 01:36:51 +00002569
Simon Atanasyan60280b42014-05-12 07:37:51 +00002570 if (!Result.Multilibs.select(Flags, Result.SelectedMultilib))
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002571 return false;
Jonathan Roelofs3fa96d82014-02-12 01:36:51 +00002572
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002573 if (Result.SelectedMultilib == Alt64 || Result.SelectedMultilib == Alt32 ||
Zinovy Nis1db95732014-07-10 15:27:19 +00002574 Result.SelectedMultilib == Altx32)
Simon Atanasyan60280b42014-05-12 07:37:51 +00002575 Result.BiarchSibling = Default;
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002576
2577 return true;
Simon Atanasyan08450bd2013-04-20 08:15:03 +00002578}
2579
Rafael Espindolac53c5b12015-08-31 19:17:51 +00002580void Generic_GCC::GCCInstallationDetector::scanLibDirForGCCTripleSolaris(
2581 const llvm::Triple &TargetArch, const llvm::opt::ArgList &Args,
2582 const std::string &LibDir, StringRef CandidateTriple,
2583 bool NeedsBiarchSuffix) {
2584 // Solaris is a special case. The GCC installation is under
2585 // /usr/gcc/<major>.<minor>/lib/gcc/<triple>/<major>.<minor>.<patch>/, so we
2586 // need to iterate twice.
2587 std::error_code EC;
Benjamin Kramerd45b2052015-10-07 15:48:01 +00002588 for (vfs::directory_iterator LI = D.getVFS().dir_begin(LibDir, EC), LE;
2589 !EC && LI != LE; LI = LI.increment(EC)) {
2590 StringRef VersionText = llvm::sys::path::filename(LI->getName());
Rafael Espindolac53c5b12015-08-31 19:17:51 +00002591 GCCVersion CandidateVersion = GCCVersion::Parse(VersionText);
2592
2593 if (CandidateVersion.Major != -1) // Filter obviously bad entries.
Benjamin Kramerd45b2052015-10-07 15:48:01 +00002594 if (!CandidateGCCInstallPaths.insert(LI->getName()).second)
Rafael Espindolac53c5b12015-08-31 19:17:51 +00002595 continue; // Saw this path before; no need to look at it again.
2596 if (CandidateVersion.isOlderThan(4, 1, 1))
2597 continue;
2598 if (CandidateVersion <= Version)
2599 continue;
2600
2601 GCCInstallPath =
2602 LibDir + "/" + VersionText.str() + "/lib/gcc/" + CandidateTriple.str();
Benjamin Kramerd45b2052015-10-07 15:48:01 +00002603 if (!D.getVFS().exists(GCCInstallPath))
Rafael Espindolac53c5b12015-08-31 19:17:51 +00002604 continue;
2605
2606 // If we make it here there has to be at least one GCC version, let's just
2607 // use the latest one.
2608 std::error_code EEC;
Benjamin Kramerd45b2052015-10-07 15:48:01 +00002609 for (vfs::directory_iterator
2610 LLI = D.getVFS().dir_begin(GCCInstallPath, EEC),
2611 LLE;
Rafael Espindolac53c5b12015-08-31 19:17:51 +00002612 !EEC && LLI != LLE; LLI = LLI.increment(EEC)) {
2613
Benjamin Kramerd45b2052015-10-07 15:48:01 +00002614 StringRef SubVersionText = llvm::sys::path::filename(LLI->getName());
Rafael Espindolac53c5b12015-08-31 19:17:51 +00002615 GCCVersion CandidateSubVersion = GCCVersion::Parse(SubVersionText);
2616
2617 if (CandidateSubVersion > Version)
2618 Version = CandidateSubVersion;
2619 }
2620
2621 GCCTriple.setTriple(CandidateTriple);
2622
2623 GCCInstallPath += "/" + Version.Text;
2624 GCCParentLibPath = GCCInstallPath + "/../../../../";
2625
2626 IsValid = true;
2627 }
2628}
2629
Chandler Carruth4c90fba2011-11-06 23:39:34 +00002630void Generic_GCC::GCCInstallationDetector::ScanLibDirForGCCTriple(
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002631 const llvm::Triple &TargetTriple, const ArgList &Args,
Chandler Carruthb427c562013-06-22 11:35:51 +00002632 const std::string &LibDir, StringRef CandidateTriple,
2633 bool NeedsBiarchSuffix) {
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002634 llvm::Triple::ArchType TargetArch = TargetTriple.getArch();
Chandler Carruth4c90fba2011-11-06 23:39:34 +00002635 // There are various different suffixes involving the triple we
2636 // check for. We also record what is necessary to walk from each back
Douglas Katzmancb07d152015-08-14 15:52:12 +00002637 // up to the lib directory. Specifically, the number of "up" steps
2638 // in the second half of each row is 1 + the number of path separators
2639 // in the first half.
2640 const std::string LibAndInstallSuffixes[][2] = {
2641 {"/gcc/" + CandidateTriple.str(), "/../../.."},
2642
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002643 // Debian puts cross-compilers in gcc-cross
Douglas Katzmancb07d152015-08-14 15:52:12 +00002644 {"/gcc-cross/" + CandidateTriple.str(), "/../../.."},
2645
2646 {"/" + CandidateTriple.str() + "/gcc/" + CandidateTriple.str(),
2647 "/../../../.."},
Chandler Carruth4c90fba2011-11-06 23:39:34 +00002648
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002649 // The Freescale PPC SDK has the gcc libraries in
2650 // <sysroot>/usr/lib/<triple>/x.y.z so have a look there as well.
Douglas Katzmancb07d152015-08-14 15:52:12 +00002651 {"/" + CandidateTriple.str(), "/../.."},
Hal Finkelf3587912012-09-18 22:25:07 +00002652
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002653 // Ubuntu has a strange mis-matched pair of triples that this happens to
2654 // match.
2655 // FIXME: It may be worthwhile to generalize this and look for a second
2656 // triple.
Douglas Katzmancb07d152015-08-14 15:52:12 +00002657 {"/i386-linux-gnu/gcc/" + CandidateTriple.str(), "/../../../.."}};
2658
Rafael Espindolac53c5b12015-08-31 19:17:51 +00002659 if (TargetTriple.getOS() == llvm::Triple::Solaris) {
2660 scanLibDirForGCCTripleSolaris(TargetTriple, Args, LibDir, CandidateTriple,
2661 NeedsBiarchSuffix);
2662 return;
2663 }
2664
Chandler Carruth4c90fba2011-11-06 23:39:34 +00002665 // Only look at the final, weird Ubuntu suffix for i386-linux-gnu.
Douglas Katzmancb07d152015-08-14 15:52:12 +00002666 const unsigned NumLibSuffixes = (llvm::array_lengthof(LibAndInstallSuffixes) -
2667 (TargetArch != llvm::Triple::x86));
Chandler Carruth866faab2012-01-25 07:21:38 +00002668 for (unsigned i = 0; i < NumLibSuffixes; ++i) {
Douglas Katzmancb07d152015-08-14 15:52:12 +00002669 StringRef LibSuffix = LibAndInstallSuffixes[i][0];
Rafael Espindolac0809172014-06-12 14:02:15 +00002670 std::error_code EC;
Benjamin Kramerd45b2052015-10-07 15:48:01 +00002671 for (vfs::directory_iterator
2672 LI = D.getVFS().dir_begin(LibDir + LibSuffix, EC),
2673 LE;
Chandler Carruth4c90fba2011-11-06 23:39:34 +00002674 !EC && LI != LE; LI = LI.increment(EC)) {
Benjamin Kramerd45b2052015-10-07 15:48:01 +00002675 StringRef VersionText = llvm::sys::path::filename(LI->getName());
Chandler Carruth4c90fba2011-11-06 23:39:34 +00002676 GCCVersion CandidateVersion = GCCVersion::Parse(VersionText);
Benjamin Kramera97e4d12013-08-14 18:38:51 +00002677 if (CandidateVersion.Major != -1) // Filter obviously bad entries.
Benjamin Kramerd45b2052015-10-07 15:48:01 +00002678 if (!CandidateGCCInstallPaths.insert(LI->getName()).second)
Benjamin Kramera97e4d12013-08-14 18:38:51 +00002679 continue; // Saw this path before; no need to look at it again.
Benjamin Kramer604e8482013-08-09 17:17:48 +00002680 if (CandidateVersion.isOlderThan(4, 1, 1))
Chandler Carruth4c90fba2011-11-06 23:39:34 +00002681 continue;
2682 if (CandidateVersion <= Version)
2683 continue;
Hal Finkel221e11e2011-12-08 05:50:03 +00002684
Simon Atanasyan60280b42014-05-12 07:37:51 +00002685 DetectedMultilibs Detected;
Simon Atanasyanee1accf2013-09-28 13:45:11 +00002686
Chih-Hung Hsiehb4d3bf72016-06-01 20:48:46 +00002687 // Android standalone toolchain could have multilibs for ARM and Thumb.
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002688 // Debian mips multilibs behave more like the rest of the biarch ones,
2689 // so handle them there
Chih-Hung Hsiehb4d3bf72016-06-01 20:48:46 +00002690 if (isArmOrThumbArch(TargetArch) && TargetTriple.isAndroid()) {
2691 // It should also work without multilibs in a simplified toolchain.
2692 findAndroidArmMultilibs(D, TargetTriple, LI->getName(), Args, Detected);
2693 } else if (isMipsArch(TargetArch)) {
Benjamin Kramerc5862f02015-10-09 13:03:18 +00002694 if (!findMIPSMultilibs(D, TargetTriple, LI->getName(), Args, Detected))
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00002695 continue;
Benjamin Kramerc5862f02015-10-09 13:03:18 +00002696 } else if (!findBiarchMultilibs(D, TargetTriple, LI->getName(), Args,
Simon Atanasyan60280b42014-05-12 07:37:51 +00002697 NeedsBiarchSuffix, Detected)) {
Simon Atanasyanee1accf2013-09-28 13:45:11 +00002698 continue;
Simon Atanasyan60280b42014-05-12 07:37:51 +00002699 }
Chandler Carruth4c90fba2011-11-06 23:39:34 +00002700
Simon Atanasyan60280b42014-05-12 07:37:51 +00002701 Multilibs = Detected.Multilibs;
2702 SelectedMultilib = Detected.SelectedMultilib;
2703 BiarchSibling = Detected.BiarchSibling;
Chandler Carruth4c90fba2011-11-06 23:39:34 +00002704 Version = CandidateVersion;
Chandler Carruth4d9d7682012-01-24 19:28:29 +00002705 GCCTriple.setTriple(CandidateTriple);
Chandler Carruth4c90fba2011-11-06 23:39:34 +00002706 // FIXME: We hack together the directory name here instead of
2707 // using LI to ensure stable path separators across Windows and
2708 // Linux.
Douglas Katzmancb07d152015-08-14 15:52:12 +00002709 GCCInstallPath =
2710 LibDir + LibAndInstallSuffixes[i][0] + "/" + VersionText.str();
2711 GCCParentLibPath = GCCInstallPath + LibAndInstallSuffixes[i][1];
Chandler Carruth4c90fba2011-11-06 23:39:34 +00002712 IsValid = true;
2713 }
2714 }
2715}
2716
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002717Generic_GCC::Generic_GCC(const Driver &D, const llvm::Triple &Triple,
Rafael Espindola1af7c212012-02-19 01:38:32 +00002718 const ArgList &Args)
Benjamin Kramerd45b2052015-10-07 15:48:01 +00002719 : ToolChain(D, Triple, Args), GCCInstallation(D), CudaInstallation(D) {
Daniel Dunbar88979912010-08-01 22:29:51 +00002720 getProgramPaths().push_back(getDriver().getInstalledDir());
Benjamin Kramer51477bd2011-03-01 22:50:47 +00002721 if (getDriver().getInstalledDir() != getDriver().Dir)
Daniel Dunbar88979912010-08-01 22:29:51 +00002722 getProgramPaths().push_back(getDriver().Dir);
Daniel Dunbar76ce7412009-03-23 16:15:50 +00002723}
2724
Angel Garcia Gomez637d1e62015-10-20 13:23:58 +00002725Generic_GCC::~Generic_GCC() {}
Daniel Dunbar59e5e882009-03-20 00:20:03 +00002726
Rafael Espindola7cf32212013-03-20 03:05:54 +00002727Tool *Generic_GCC::getTool(Action::ActionClass AC) const {
Rafael Espindola260e28d2013-03-18 20:48:54 +00002728 switch (AC) {
Rafael Espindolac8e3a012013-03-18 18:50:01 +00002729 case Action::PreprocessJobClass:
Rafael Espindola7cf32212013-03-20 03:05:54 +00002730 if (!Preprocess)
Douglas Katzman95354292015-06-23 20:42:09 +00002731 Preprocess.reset(new tools::gcc::Preprocessor(*this));
Rafael Espindola7cf32212013-03-20 03:05:54 +00002732 return Preprocess.get();
Rafael Espindolac8e3a012013-03-18 18:50:01 +00002733 case Action::CompileJobClass:
Rafael Espindola7cf32212013-03-20 03:05:54 +00002734 if (!Compile)
Douglas Katzman95354292015-06-23 20:42:09 +00002735 Compile.reset(new tools::gcc::Compiler(*this));
Rafael Espindola7cf32212013-03-20 03:05:54 +00002736 return Compile.get();
Rafael Espindolad15a8912013-03-19 00:36:57 +00002737 default:
Rafael Espindola7cf32212013-03-20 03:05:54 +00002738 return ToolChain::getTool(AC);
Daniel Dunbar59e5e882009-03-20 00:20:03 +00002739 }
Daniel Dunbar59e5e882009-03-20 00:20:03 +00002740}
2741
Rafael Espindola7cf32212013-03-20 03:05:54 +00002742Tool *Generic_GCC::buildAssembler() const {
Douglas Katzman95354292015-06-23 20:42:09 +00002743 return new tools::gnutools::Assembler(*this);
Rafael Espindola7cf32212013-03-20 03:05:54 +00002744}
2745
Douglas Katzman95354292015-06-23 20:42:09 +00002746Tool *Generic_GCC::buildLinker() const { return new tools::gcc::Linker(*this); }
Rafael Espindola7cf32212013-03-20 03:05:54 +00002747
Chandler Carruth0ae39aa2013-07-30 17:57:09 +00002748void Generic_GCC::printVerboseInfo(raw_ostream &OS) const {
2749 // Print the information about how we detected the GCC installation.
2750 GCCInstallation.print(OS);
Artem Belevich98607b62015-09-23 21:49:39 +00002751 CudaInstallation.print(OS);
Chandler Carruth0ae39aa2013-07-30 17:57:09 +00002752}
2753
Daniel Dunbar59e5e882009-03-20 00:20:03 +00002754bool Generic_GCC::IsUnwindTablesDefault() const {
Rafael Espindola08f1ebb2012-09-22 15:04:11 +00002755 return getArch() == llvm::Triple::x86_64;
Daniel Dunbar59e5e882009-03-20 00:20:03 +00002756}
2757
David Majnemer17f448b2015-06-28 04:23:33 +00002758bool Generic_GCC::isPICDefault() const {
2759 return getArch() == llvm::Triple::x86_64 && getTriple().isOSWindows();
2760}
Daniel Dunbar59e5e882009-03-20 00:20:03 +00002761
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002762bool Generic_GCC::isPIEDefault() const { return false; }
Peter Collingbourne54d770c2013-04-09 04:35:11 +00002763
David Majnemer17f448b2015-06-28 04:23:33 +00002764bool Generic_GCC::isPICDefaultForced() const {
2765 return getArch() == llvm::Triple::x86_64 && getTriple().isOSWindows();
2766}
Chandler Carruth76a943b2012-11-19 03:52:03 +00002767
Rafael Espindolaa8b3b682013-11-25 18:50:53 +00002768bool Generic_GCC::IsIntegratedAssemblerDefault() const {
Douglas Katzman7ae27b82015-06-03 19:40:30 +00002769 switch (getTriple().getArch()) {
2770 case llvm::Triple::x86:
2771 case llvm::Triple::x86_64:
2772 case llvm::Triple::aarch64:
2773 case llvm::Triple::aarch64_be:
2774 case llvm::Triple::arm:
2775 case llvm::Triple::armeb:
Alexei Starovoitovf657ca82015-06-10 22:59:13 +00002776 case llvm::Triple::bpfel:
2777 case llvm::Triple::bpfeb:
Douglas Katzman7ae27b82015-06-03 19:40:30 +00002778 case llvm::Triple::thumb:
2779 case llvm::Triple::thumbeb:
2780 case llvm::Triple::ppc:
2781 case llvm::Triple::ppc64:
2782 case llvm::Triple::ppc64le:
Douglas Katzman7ae27b82015-06-03 19:40:30 +00002783 case llvm::Triple::systemz:
Daniel Sanderse160f832016-05-14 12:43:08 +00002784 case llvm::Triple::mips:
2785 case llvm::Triple::mipsel:
Douglas Katzman7ae27b82015-06-03 19:40:30 +00002786 return true;
Simon Dardis9edf96e2016-09-15 14:01:55 +00002787 case llvm::Triple::mips64:
2788 case llvm::Triple::mips64el:
2789 // Enabled for Debian mips64/mips64el only. Other targets are unable to
2790 // distinguish N32 from N64.
2791 if (getTriple().getEnvironment() == llvm::Triple::GNUABI64)
2792 return true;
2793 return false;
Douglas Katzman7ae27b82015-06-03 19:40:30 +00002794 default:
2795 return false;
2796 }
Rafael Espindolaa8b3b682013-11-25 18:50:53 +00002797}
2798
James Y Knighta6c9ee72015-10-16 18:46:26 +00002799/// \brief Helper to add the variant paths of a libstdc++ installation.
2800bool Generic_GCC::addLibStdCXXIncludePaths(
2801 Twine Base, Twine Suffix, StringRef GCCTriple, StringRef GCCMultiarchTriple,
2802 StringRef TargetMultiarchTriple, Twine IncludeSuffix,
2803 const ArgList &DriverArgs, ArgStringList &CC1Args) const {
2804 if (!getVFS().exists(Base + Suffix))
2805 return false;
2806
2807 addSystemInclude(DriverArgs, CC1Args, Base + Suffix);
2808
2809 // The vanilla GCC layout of libstdc++ headers uses a triple subdirectory. If
2810 // that path exists or we have neither a GCC nor target multiarch triple, use
2811 // this vanilla search path.
2812 if ((GCCMultiarchTriple.empty() && TargetMultiarchTriple.empty()) ||
2813 getVFS().exists(Base + Suffix + "/" + GCCTriple + IncludeSuffix)) {
2814 addSystemInclude(DriverArgs, CC1Args,
2815 Base + Suffix + "/" + GCCTriple + IncludeSuffix);
2816 } else {
2817 // Otherwise try to use multiarch naming schemes which have normalized the
2818 // triples and put the triple before the suffix.
2819 //
2820 // GCC surprisingly uses *both* the GCC triple with a multilib suffix and
2821 // the target triple, so we support that here.
2822 addSystemInclude(DriverArgs, CC1Args,
2823 Base + "/" + GCCMultiarchTriple + Suffix + IncludeSuffix);
2824 addSystemInclude(DriverArgs, CC1Args,
2825 Base + "/" + TargetMultiarchTriple + Suffix);
2826 }
2827
2828 addSystemInclude(DriverArgs, CC1Args, Base + Suffix + "/backward");
2829 return true;
2830}
2831
Kristof Beylsfb387292014-01-10 13:44:34 +00002832void Generic_ELF::addClangTargetOptions(const ArgList &DriverArgs,
2833 ArgStringList &CC1Args) const {
2834 const Generic_GCC::GCCVersion &V = GCCInstallation.getVersion();
Tim Northovera2ee4332014-03-29 15:09:45 +00002835 bool UseInitArrayDefault =
Kristof Beylsfb387292014-01-10 13:44:34 +00002836 getTriple().getArch() == llvm::Triple::aarch64 ||
Christian Pirker9b019ae2014-02-25 13:51:00 +00002837 getTriple().getArch() == llvm::Triple::aarch64_be ||
Tim Northovera2ee4332014-03-29 15:09:45 +00002838 (getTriple().getOS() == llvm::Triple::Linux &&
Evgeniy Stepanov14deb7b2015-10-08 21:21:44 +00002839 (!V.isOlderThan(4, 7, 0) || getTriple().isAndroid())) ||
Vasileios Kalintirisc744e122015-11-12 15:26:54 +00002840 getTriple().getOS() == llvm::Triple::NaCl ||
2841 (getTriple().getVendor() == llvm::Triple::MipsTechnologies &&
2842 !getTriple().hasEnvironment());
Kristof Beylsfb387292014-01-10 13:44:34 +00002843
2844 if (DriverArgs.hasFlag(options::OPT_fuse_init_array,
Douglas Katzmana67e50c2015-06-26 15:47:46 +00002845 options::OPT_fno_use_init_array, UseInitArrayDefault))
Kristof Beylsfb387292014-01-10 13:44:34 +00002846 CC1Args.push_back("-fuse-init-array");
2847}
2848
Vasileios Kalintirisc744e122015-11-12 15:26:54 +00002849/// Mips Toolchain
2850MipsLLVMToolChain::MipsLLVMToolChain(const Driver &D,
2851 const llvm::Triple &Triple,
2852 const ArgList &Args)
2853 : Linux(D, Triple, Args) {
2854 // Select the correct multilib according to the given arguments.
2855 DetectedMultilibs Result;
2856 findMIPSMultilibs(D, Triple, "", Args, Result);
2857 Multilibs = Result.Multilibs;
2858 SelectedMultilib = Result.SelectedMultilib;
2859
2860 // Find out the library suffix based on the ABI.
2861 LibSuffix = tools::mips::getMipsABILibSuffix(Args, Triple);
2862 getFilePaths().clear();
2863 getFilePaths().push_back(computeSysRoot() + "/usr/lib" + LibSuffix);
2864
2865 // Use LLD by default.
Peter Collingbourne39719a72015-11-20 20:49:39 +00002866 DefaultLinker = "lld";
Vasileios Kalintirisc744e122015-11-12 15:26:54 +00002867}
2868
2869void MipsLLVMToolChain::AddClangSystemIncludeArgs(
2870 const ArgList &DriverArgs, ArgStringList &CC1Args) const {
2871 if (DriverArgs.hasArg(options::OPT_nostdinc))
2872 return;
2873
2874 const Driver &D = getDriver();
2875
2876 if (!DriverArgs.hasArg(options::OPT_nobuiltininc)) {
2877 SmallString<128> P(D.ResourceDir);
2878 llvm::sys::path::append(P, "include");
2879 addSystemInclude(DriverArgs, CC1Args, P);
2880 }
2881
2882 if (DriverArgs.hasArg(options::OPT_nostdlibinc))
2883 return;
2884
2885 const auto &Callback = Multilibs.includeDirsCallback();
2886 if (Callback) {
Simon Atanasyana45502d2016-05-19 15:07:21 +00002887 for (const auto &Path : Callback(SelectedMultilib))
2888 addExternCSystemIncludeIfExists(DriverArgs, CC1Args,
2889 D.getInstalledDir() + Path);
Vasileios Kalintirisc744e122015-11-12 15:26:54 +00002890 }
2891}
2892
2893Tool *MipsLLVMToolChain::buildLinker() const {
2894 return new tools::gnutools::Linker(*this);
2895}
2896
2897std::string MipsLLVMToolChain::computeSysRoot() const {
2898 if (!getDriver().SysRoot.empty())
2899 return getDriver().SysRoot + SelectedMultilib.osSuffix();
2900
2901 const std::string InstalledDir(getDriver().getInstalledDir());
2902 std::string SysRootPath =
2903 InstalledDir + "/../sysroot" + SelectedMultilib.osSuffix();
2904 if (llvm::sys::fs::exists(SysRootPath))
2905 return SysRootPath;
2906
2907 return std::string();
2908}
2909
2910ToolChain::CXXStdlibType
2911MipsLLVMToolChain::GetCXXStdlibType(const ArgList &Args) const {
2912 Arg *A = Args.getLastArg(options::OPT_stdlib_EQ);
2913 if (A) {
2914 StringRef Value = A->getValue();
2915 if (Value != "libc++")
2916 getDriver().Diag(diag::err_drv_invalid_stdlib_name)
2917 << A->getAsString(Args);
2918 }
2919
2920 return ToolChain::CST_Libcxx;
2921}
2922
2923void MipsLLVMToolChain::AddClangCXXStdlibIncludeArgs(
2924 const ArgList &DriverArgs, ArgStringList &CC1Args) const {
2925 if (DriverArgs.hasArg(options::OPT_nostdlibinc) ||
2926 DriverArgs.hasArg(options::OPT_nostdincxx))
2927 return;
2928
2929 assert((GetCXXStdlibType(DriverArgs) == ToolChain::CST_Libcxx) &&
2930 "Only -lc++ (aka libcxx) is suported in this toolchain.");
2931
2932 const auto &Callback = Multilibs.includeDirsCallback();
2933 if (Callback) {
Simon Atanasyana45502d2016-05-19 15:07:21 +00002934 for (std::string Path : Callback(SelectedMultilib)) {
2935 Path = getDriver().getInstalledDir() + Path + "/c++/v1";
2936 if (llvm::sys::fs::exists(Path)) {
2937 addSystemInclude(DriverArgs, CC1Args, Path);
Vasileios Kalintirisc744e122015-11-12 15:26:54 +00002938 break;
2939 }
2940 }
2941 }
2942}
2943
2944void MipsLLVMToolChain::AddCXXStdlibLibArgs(const ArgList &Args,
2945 ArgStringList &CmdArgs) const {
2946 assert((GetCXXStdlibType(Args) == ToolChain::CST_Libcxx) &&
2947 "Only -lc++ (aka libxx) is suported in this toolchain.");
2948
2949 CmdArgs.push_back("-lc++");
2950 CmdArgs.push_back("-lc++abi");
2951 CmdArgs.push_back("-lunwind");
2952}
2953
Vedant Kumar5fb00e42016-07-27 23:01:55 +00002954std::string MipsLLVMToolChain::getCompilerRT(const ArgList &Args,
2955 StringRef Component,
2956 bool Shared) const {
Vasileios Kalintirisc744e122015-11-12 15:26:54 +00002957 SmallString<128> Path(getDriver().ResourceDir);
2958 llvm::sys::path::append(Path, SelectedMultilib.osSuffix(), "lib" + LibSuffix,
2959 getOS());
2960 llvm::sys::path::append(Path, Twine("libclang_rt." + Component + "-" +
Vasileios Kalintirisbbc99302015-11-16 15:41:30 +00002961 "mips" + (Shared ? ".so" : ".a")));
Vasileios Kalintirisc744e122015-11-12 15:26:54 +00002962 return Path.str();
2963}
2964
Tony Linthicum76329bf2011-12-12 21:14:55 +00002965/// Hexagon Toolchain
2966
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00002967std::string HexagonToolChain::getHexagonTargetDir(
2968 const std::string &InstalledDir,
2969 const SmallVectorImpl<std::string> &PrefixDirs) const {
2970 std::string InstallRelDir;
2971 const Driver &D = getDriver();
2972
Matthew Curtis22dd8da2012-12-06 12:43:18 +00002973 // Locate the rest of the toolchain ...
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00002974 for (auto &I : PrefixDirs)
2975 if (D.getVFS().exists(I))
2976 return I;
Samuel Antaoc909c992014-11-07 17:48:03 +00002977
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00002978 if (getVFS().exists(InstallRelDir = InstalledDir + "/../target"))
Matthew Curtis22dd8da2012-12-06 12:43:18 +00002979 return InstallRelDir;
2980
Krzysztof Parzyszek50fd6152016-10-17 15:30:10 +00002981 return InstalledDir;
Matthew Curtis22dd8da2012-12-06 12:43:18 +00002982}
2983
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00002984Optional<unsigned> HexagonToolChain::getSmallDataThreshold(
2985 const ArgList &Args) {
2986 StringRef Gn = "";
2987 if (Arg *A = Args.getLastArg(options::OPT_G, options::OPT_G_EQ,
2988 options::OPT_msmall_data_threshold_EQ)) {
2989 Gn = A->getValue();
2990 } else if (Args.getLastArg(options::OPT_shared, options::OPT_fpic,
2991 options::OPT_fPIC)) {
2992 Gn = "0";
2993 }
Ikhlas Ajbar522e6192015-05-14 13:52:08 +00002994
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00002995 unsigned G;
2996 if (!Gn.getAsInteger(10, G))
2997 return G;
Ikhlas Ajbar522e6192015-05-14 13:52:08 +00002998
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00002999 return None;
Ikhlas Ajbar522e6192015-05-14 13:52:08 +00003000}
3001
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00003002void HexagonToolChain::getHexagonLibraryPaths(const ArgList &Args,
3003 ToolChain::path_list &LibPaths) const {
3004 const Driver &D = getDriver();
Matthew Curtise689b052012-12-06 15:46:07 +00003005
3006 //----------------------------------------------------------------------------
3007 // -L Args
3008 //----------------------------------------------------------------------------
Douglas Katzman6bbffc42015-06-25 18:51:37 +00003009 for (Arg *A : Args.filtered(options::OPT_L))
3010 for (const char *Value : A->getValues())
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00003011 LibPaths.push_back(Value);
Matthew Curtise689b052012-12-06 15:46:07 +00003012
3013 //----------------------------------------------------------------------------
3014 // Other standard paths
3015 //----------------------------------------------------------------------------
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00003016 std::vector<std::string> RootDirs;
Krzysztof Parzyszekf4467cd2016-01-06 14:13:11 +00003017 std::copy(D.PrefixDirs.begin(), D.PrefixDirs.end(),
3018 std::back_inserter(RootDirs));
Matthew Curtise689b052012-12-06 15:46:07 +00003019
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00003020 std::string TargetDir = getHexagonTargetDir(D.getInstalledDir(),
3021 D.PrefixDirs);
3022 if (std::find(RootDirs.begin(), RootDirs.end(), TargetDir) == RootDirs.end())
3023 RootDirs.push_back(TargetDir);
3024
3025 bool HasPIC = Args.hasArg(options::OPT_fpic, options::OPT_fPIC);
3026 // Assume G0 with -shared.
3027 bool HasG0 = Args.hasArg(options::OPT_shared);
3028 if (auto G = getSmallDataThreshold(Args))
3029 HasG0 = G.getValue() == 0;
3030
3031 const std::string CpuVer = GetTargetCPUVersion(Args).str();
3032 for (auto &Dir : RootDirs) {
3033 std::string LibDir = Dir + "/hexagon/lib";
3034 std::string LibDirCpu = LibDir + '/' + CpuVer;
3035 if (HasG0) {
3036 if (HasPIC)
3037 LibPaths.push_back(LibDirCpu + "/G0/pic");
3038 LibPaths.push_back(LibDirCpu + "/G0");
3039 }
3040 LibPaths.push_back(LibDirCpu);
3041 LibPaths.push_back(LibDir);
Matthew Curtise689b052012-12-06 15:46:07 +00003042 }
Matthew Curtise689b052012-12-06 15:46:07 +00003043}
3044
Douglas Katzman54366072015-07-27 16:53:08 +00003045HexagonToolChain::HexagonToolChain(const Driver &D, const llvm::Triple &Triple,
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00003046 const llvm::opt::ArgList &Args)
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003047 : Linux(D, Triple, Args) {
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00003048 const std::string TargetDir = getHexagonTargetDir(D.getInstalledDir(),
3049 D.PrefixDirs);
Matthew Curtis22dd8da2012-12-06 12:43:18 +00003050
3051 // Note: Generic_GCC::Generic_GCC adds InstalledDir and getDriver().Dir to
3052 // program paths
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00003053 const std::string BinDir(TargetDir + "/bin");
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003054 if (D.getVFS().exists(BinDir))
Matthew Curtis22dd8da2012-12-06 12:43:18 +00003055 getProgramPaths().push_back(BinDir);
3056
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00003057 ToolChain::path_list &LibPaths = getFilePaths();
Matthew Curtise689b052012-12-06 15:46:07 +00003058
3059 // Remove paths added by Linux toolchain. Currently Hexagon_TC really targets
3060 // 'elf' OS type, so the Linux paths are not appropriate. When we actually
3061 // support 'linux' we'll need to fix this up
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00003062 LibPaths.clear();
3063 getHexagonLibraryPaths(Args, LibPaths);
Tony Linthicum76329bf2011-12-12 21:14:55 +00003064}
3065
Angel Garcia Gomez637d1e62015-10-20 13:23:58 +00003066HexagonToolChain::~HexagonToolChain() {}
Tony Linthicum76329bf2011-12-12 21:14:55 +00003067
Douglas Katzman54366072015-07-27 16:53:08 +00003068Tool *HexagonToolChain::buildAssembler() const {
Douglas Katzman95354292015-06-23 20:42:09 +00003069 return new tools::hexagon::Assembler(*this);
Rafael Espindola7cf32212013-03-20 03:05:54 +00003070}
3071
Douglas Katzman54366072015-07-27 16:53:08 +00003072Tool *HexagonToolChain::buildLinker() const {
Douglas Katzman95354292015-06-23 20:42:09 +00003073 return new tools::hexagon::Linker(*this);
Tony Linthicum76329bf2011-12-12 21:14:55 +00003074}
3075
Douglas Katzman54366072015-07-27 16:53:08 +00003076void HexagonToolChain::AddClangSystemIncludeArgs(const ArgList &DriverArgs,
3077 ArgStringList &CC1Args) const {
Matthew Curtis22dd8da2012-12-06 12:43:18 +00003078 if (DriverArgs.hasArg(options::OPT_nostdinc) ||
3079 DriverArgs.hasArg(options::OPT_nostdlibinc))
3080 return;
3081
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00003082 const Driver &D = getDriver();
3083 std::string TargetDir = getHexagonTargetDir(D.getInstalledDir(),
3084 D.PrefixDirs);
3085 addExternCSystemInclude(DriverArgs, CC1Args, TargetDir + "/hexagon/include");
Tony Linthicum76329bf2011-12-12 21:14:55 +00003086}
3087
Douglas Katzman54366072015-07-27 16:53:08 +00003088void HexagonToolChain::AddClangCXXStdlibIncludeArgs(
3089 const ArgList &DriverArgs, ArgStringList &CC1Args) const {
Matthew Curtis22dd8da2012-12-06 12:43:18 +00003090 if (DriverArgs.hasArg(options::OPT_nostdlibinc) ||
3091 DriverArgs.hasArg(options::OPT_nostdincxx))
3092 return;
3093
3094 const Driver &D = getDriver();
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00003095 std::string TargetDir = getHexagonTargetDir(D.InstalledDir, D.PrefixDirs);
3096 addSystemInclude(DriverArgs, CC1Args, TargetDir + "/hexagon/include/c++");
Chandler Carruth76a943b2012-11-19 03:52:03 +00003097}
Matthew Curtisf10a5952012-12-06 14:16:43 +00003098
Matthew Curtise689b052012-12-06 15:46:07 +00003099ToolChain::CXXStdlibType
Douglas Katzman54366072015-07-27 16:53:08 +00003100HexagonToolChain::GetCXXStdlibType(const ArgList &Args) const {
Matthew Curtise689b052012-12-06 15:46:07 +00003101 Arg *A = Args.getLastArg(options::OPT_stdlib_EQ);
3102 if (!A)
3103 return ToolChain::CST_Libstdcxx;
3104
3105 StringRef Value = A->getValue();
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00003106 if (Value != "libstdc++")
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003107 getDriver().Diag(diag::err_drv_invalid_stdlib_name) << A->getAsString(Args);
Matthew Curtise689b052012-12-06 15:46:07 +00003108
3109 return ToolChain::CST_Libstdcxx;
3110}
3111
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00003112//
3113// Returns the default CPU for Hexagon. This is the default compilation target
3114// if no Hexagon processor is selected at the command-line.
3115//
3116const StringRef HexagonToolChain::GetDefaultCPU() {
3117 return "hexagonv60";
Matthew Curtisf10a5952012-12-06 14:16:43 +00003118}
3119
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00003120const StringRef HexagonToolChain::GetTargetCPUVersion(const ArgList &Args) {
3121 Arg *CpuArg = nullptr;
Krzysztof Parzyszek972f72c2016-01-06 21:12:03 +00003122 if (Arg *A = Args.getLastArg(options::OPT_mcpu_EQ, options::OPT_march_EQ))
3123 CpuArg = A;
Krzysztof Parzyszek1e6e3c62015-12-14 15:03:57 +00003124
3125 StringRef CPU = CpuArg ? CpuArg->getValue() : GetDefaultCPU();
3126 if (CPU.startswith("hexagon"))
3127 return CPU.substr(sizeof("hexagon") - 1);
3128 return CPU;
Matthew Curtisf10a5952012-12-06 14:16:43 +00003129}
Matthew Curtis22dd8da2012-12-06 12:43:18 +00003130// End Hexagon
Daniel Dunbardac54a82009-03-25 04:13:45 +00003131
Tom Stellard8fa33092015-07-18 01:49:05 +00003132/// AMDGPU Toolchain
3133AMDGPUToolChain::AMDGPUToolChain(const Driver &D, const llvm::Triple &Triple,
3134 const ArgList &Args)
3135 : Generic_ELF(D, Triple, Args) { }
3136
3137Tool *AMDGPUToolChain::buildLinker() const {
3138 return new tools::amdgpu::Linker(*this);
3139}
3140// End AMDGPU
3141
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003142/// NaCl Toolchain
Douglas Katzman54366072015-07-27 16:53:08 +00003143NaClToolChain::NaClToolChain(const Driver &D, const llvm::Triple &Triple,
3144 const ArgList &Args)
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003145 : Generic_ELF(D, Triple, Args) {
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003146
3147 // Remove paths added by Generic_GCC. NaCl Toolchain cannot use the
3148 // default paths, and must instead only use the paths provided
3149 // with this toolchain based on architecture.
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003150 path_list &file_paths = getFilePaths();
3151 path_list &prog_paths = getProgramPaths();
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003152
3153 file_paths.clear();
3154 prog_paths.clear();
3155
3156 // Path for library files (libc.a, ...)
3157 std::string FilePath(getDriver().Dir + "/../");
3158
3159 // Path for tools (clang, ld, etc..)
3160 std::string ProgPath(getDriver().Dir + "/../");
3161
3162 // Path for toolchain libraries (libgcc.a, ...)
3163 std::string ToolPath(getDriver().ResourceDir + "/lib/");
3164
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003165 switch (Triple.getArch()) {
Hans Wennborgdcfba332015-10-06 23:40:43 +00003166 case llvm::Triple::x86:
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003167 file_paths.push_back(FilePath + "x86_64-nacl/lib32");
Derek Schuff9afb0502015-08-26 17:14:08 +00003168 file_paths.push_back(FilePath + "i686-nacl/usr/lib");
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003169 prog_paths.push_back(ProgPath + "x86_64-nacl/bin");
3170 file_paths.push_back(ToolPath + "i686-nacl");
3171 break;
Hans Wennborgdcfba332015-10-06 23:40:43 +00003172 case llvm::Triple::x86_64:
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003173 file_paths.push_back(FilePath + "x86_64-nacl/lib");
3174 file_paths.push_back(FilePath + "x86_64-nacl/usr/lib");
3175 prog_paths.push_back(ProgPath + "x86_64-nacl/bin");
3176 file_paths.push_back(ToolPath + "x86_64-nacl");
3177 break;
Hans Wennborgdcfba332015-10-06 23:40:43 +00003178 case llvm::Triple::arm:
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003179 file_paths.push_back(FilePath + "arm-nacl/lib");
3180 file_paths.push_back(FilePath + "arm-nacl/usr/lib");
3181 prog_paths.push_back(ProgPath + "arm-nacl/bin");
3182 file_paths.push_back(ToolPath + "arm-nacl");
3183 break;
Hans Wennborgdcfba332015-10-06 23:40:43 +00003184 case llvm::Triple::mipsel:
Petar Jovanovic26a4a402015-07-08 13:07:31 +00003185 file_paths.push_back(FilePath + "mipsel-nacl/lib");
3186 file_paths.push_back(FilePath + "mipsel-nacl/usr/lib");
3187 prog_paths.push_back(ProgPath + "bin");
3188 file_paths.push_back(ToolPath + "mipsel-nacl");
3189 break;
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003190 default:
3191 break;
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003192 }
3193
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003194 NaClArmMacrosPath = GetFilePath("nacl-arm-macros.s");
3195}
3196
Douglas Katzman54366072015-07-27 16:53:08 +00003197void NaClToolChain::AddClangSystemIncludeArgs(const ArgList &DriverArgs,
3198 ArgStringList &CC1Args) const {
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003199 const Driver &D = getDriver();
3200 if (DriverArgs.hasArg(options::OPT_nostdinc))
3201 return;
3202
3203 if (!DriverArgs.hasArg(options::OPT_nobuiltininc)) {
3204 SmallString<128> P(D.ResourceDir);
3205 llvm::sys::path::append(P, "include");
3206 addSystemInclude(DriverArgs, CC1Args, P.str());
3207 }
3208
3209 if (DriverArgs.hasArg(options::OPT_nostdlibinc))
3210 return;
3211
3212 SmallString<128> P(D.Dir + "/../");
Douglas Katzman7e37afb2015-06-23 03:02:39 +00003213 switch (getTriple().getArch()) {
Derek Schuff9afb0502015-08-26 17:14:08 +00003214 case llvm::Triple::x86:
3215 // x86 is special because multilib style uses x86_64-nacl/include for libc
3216 // headers but the SDK wants i686-nacl/usr/include. The other architectures
3217 // have the same substring.
3218 llvm::sys::path::append(P, "i686-nacl/usr/include");
3219 addSystemInclude(DriverArgs, CC1Args, P.str());
3220 llvm::sys::path::remove_filename(P);
3221 llvm::sys::path::remove_filename(P);
3222 llvm::sys::path::remove_filename(P);
3223 llvm::sys::path::append(P, "x86_64-nacl/include");
3224 addSystemInclude(DriverArgs, CC1Args, P.str());
3225 return;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00003226 case llvm::Triple::arm:
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003227 llvm::sys::path::append(P, "arm-nacl/usr/include");
Douglas Katzman7e37afb2015-06-23 03:02:39 +00003228 break;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00003229 case llvm::Triple::x86_64:
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003230 llvm::sys::path::append(P, "x86_64-nacl/usr/include");
Douglas Katzman7e37afb2015-06-23 03:02:39 +00003231 break;
Petar Jovanovic26a4a402015-07-08 13:07:31 +00003232 case llvm::Triple::mipsel:
3233 llvm::sys::path::append(P, "mipsel-nacl/usr/include");
3234 break;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00003235 default:
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003236 return;
3237 }
3238
3239 addSystemInclude(DriverArgs, CC1Args, P.str());
3240 llvm::sys::path::remove_filename(P);
3241 llvm::sys::path::remove_filename(P);
3242 llvm::sys::path::append(P, "include");
3243 addSystemInclude(DriverArgs, CC1Args, P.str());
3244}
3245
Douglas Katzman54366072015-07-27 16:53:08 +00003246void NaClToolChain::AddCXXStdlibLibArgs(const ArgList &Args,
3247 ArgStringList &CmdArgs) const {
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003248 // Check for -stdlib= flags. We only support libc++ but this consumes the arg
3249 // if the value is libc++, and emits an error for other values.
3250 GetCXXStdlibType(Args);
3251 CmdArgs.push_back("-lc++");
3252}
3253
Douglas Katzman54366072015-07-27 16:53:08 +00003254void NaClToolChain::AddClangCXXStdlibIncludeArgs(const ArgList &DriverArgs,
3255 ArgStringList &CC1Args) const {
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003256 const Driver &D = getDriver();
3257 if (DriverArgs.hasArg(options::OPT_nostdlibinc) ||
3258 DriverArgs.hasArg(options::OPT_nostdincxx))
3259 return;
3260
3261 // Check for -stdlib= flags. We only support libc++ but this consumes the arg
3262 // if the value is libc++, and emits an error for other values.
3263 GetCXXStdlibType(DriverArgs);
3264
Douglas Katzman7e37afb2015-06-23 03:02:39 +00003265 SmallString<128> P(D.Dir + "/../");
3266 switch (getTriple().getArch()) {
3267 case llvm::Triple::arm:
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003268 llvm::sys::path::append(P, "arm-nacl/include/c++/v1");
3269 addSystemInclude(DriverArgs, CC1Args, P.str());
Douglas Katzman7e37afb2015-06-23 03:02:39 +00003270 break;
3271 case llvm::Triple::x86:
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003272 llvm::sys::path::append(P, "x86_64-nacl/include/c++/v1");
3273 addSystemInclude(DriverArgs, CC1Args, P.str());
Douglas Katzman7e37afb2015-06-23 03:02:39 +00003274 break;
3275 case llvm::Triple::x86_64:
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003276 llvm::sys::path::append(P, "x86_64-nacl/include/c++/v1");
3277 addSystemInclude(DriverArgs, CC1Args, P.str());
Douglas Katzman7e37afb2015-06-23 03:02:39 +00003278 break;
Petar Jovanovic26a4a402015-07-08 13:07:31 +00003279 case llvm::Triple::mipsel:
3280 llvm::sys::path::append(P, "mipsel-nacl/include/c++/v1");
3281 addSystemInclude(DriverArgs, CC1Args, P.str());
3282 break;
Douglas Katzman9ad0ec22015-06-23 04:20:44 +00003283 default:
3284 break;
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003285 }
3286}
3287
Douglas Katzman54366072015-07-27 16:53:08 +00003288ToolChain::CXXStdlibType
3289NaClToolChain::GetCXXStdlibType(const ArgList &Args) const {
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003290 if (Arg *A = Args.getLastArg(options::OPT_stdlib_EQ)) {
3291 StringRef Value = A->getValue();
3292 if (Value == "libc++")
3293 return ToolChain::CST_Libcxx;
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003294 getDriver().Diag(diag::err_drv_invalid_stdlib_name) << A->getAsString(Args);
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003295 }
3296
3297 return ToolChain::CST_Libcxx;
3298}
3299
Douglas Katzman54366072015-07-27 16:53:08 +00003300std::string
3301NaClToolChain::ComputeEffectiveClangTriple(const ArgList &Args,
3302 types::ID InputType) const {
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003303 llvm::Triple TheTriple(ComputeLLVMTriple(Args, InputType));
3304 if (TheTriple.getArch() == llvm::Triple::arm &&
3305 TheTriple.getEnvironment() == llvm::Triple::UnknownEnvironment)
3306 TheTriple.setEnvironment(llvm::Triple::GNUEABIHF);
3307 return TheTriple.getTriple();
3308}
3309
Douglas Katzman54366072015-07-27 16:53:08 +00003310Tool *NaClToolChain::buildLinker() const {
Douglas Katzman95354292015-06-23 20:42:09 +00003311 return new tools::nacltools::Linker(*this);
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003312}
3313
Douglas Katzman54366072015-07-27 16:53:08 +00003314Tool *NaClToolChain::buildAssembler() const {
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003315 if (getTriple().getArch() == llvm::Triple::arm)
Douglas Katzman95354292015-06-23 20:42:09 +00003316 return new tools::nacltools::AssemblerARM(*this);
3317 return new tools::gnutools::Assembler(*this);
Derek Schuff6ab52fa2015-03-30 20:31:33 +00003318}
3319// End NaCl
3320
Chris Lattner09797542010-03-04 21:07:38 +00003321/// TCEToolChain - A tool chain using the llvm bitcode tools to perform
3322/// all subcommands. See http://tce.cs.tut.fi for our peculiar target.
3323/// Currently does not support anything else but compilation.
3324
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003325TCEToolChain::TCEToolChain(const Driver &D, const llvm::Triple &Triple,
Rafael Espindola84b588b2013-03-18 18:10:27 +00003326 const ArgList &Args)
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003327 : ToolChain(D, Triple, Args) {
Chris Lattner09797542010-03-04 21:07:38 +00003328 // Path mangling to find libexec
3329 std::string Path(getDriver().Dir);
3330
3331 Path += "/../libexec";
3332 getProgramPaths().push_back(Path);
3333}
3334
Angel Garcia Gomez637d1e62015-10-20 13:23:58 +00003335TCEToolChain::~TCEToolChain() {}
Chris Lattner09797542010-03-04 21:07:38 +00003336
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003337bool TCEToolChain::IsMathErrnoDefault() const { return true; }
Chris Lattner09797542010-03-04 21:07:38 +00003338
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003339bool TCEToolChain::isPICDefault() const { return false; }
Chris Lattner09797542010-03-04 21:07:38 +00003340
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003341bool TCEToolChain::isPIEDefault() const { return false; }
Peter Collingbourne54d770c2013-04-09 04:35:11 +00003342
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003343bool TCEToolChain::isPICDefaultForced() const { return false; }
Chris Lattner09797542010-03-04 21:07:38 +00003344
Ed Schouten3c3e58c2015-03-26 11:13:44 +00003345// CloudABI - CloudABI tool chain which can call ld(1) directly.
3346
3347CloudABI::CloudABI(const Driver &D, const llvm::Triple &Triple,
3348 const ArgList &Args)
3349 : Generic_ELF(D, Triple, Args) {
3350 SmallString<128> P(getDriver().Dir);
3351 llvm::sys::path::append(P, "..", getTriple().str(), "lib");
3352 getFilePaths().push_back(P.str());
3353}
3354
3355void CloudABI::AddClangCXXStdlibIncludeArgs(const ArgList &DriverArgs,
3356 ArgStringList &CC1Args) const {
3357 if (DriverArgs.hasArg(options::OPT_nostdlibinc) &&
3358 DriverArgs.hasArg(options::OPT_nostdincxx))
3359 return;
3360
3361 SmallString<128> P(getDriver().Dir);
3362 llvm::sys::path::append(P, "..", getTriple().str(), "include/c++/v1");
3363 addSystemInclude(DriverArgs, CC1Args, P.str());
3364}
3365
3366void CloudABI::AddCXXStdlibLibArgs(const ArgList &Args,
3367 ArgStringList &CmdArgs) const {
3368 CmdArgs.push_back("-lc++");
3369 CmdArgs.push_back("-lc++abi");
3370 CmdArgs.push_back("-lunwind");
3371}
3372
Douglas Katzman95354292015-06-23 20:42:09 +00003373Tool *CloudABI::buildLinker() const {
3374 return new tools::cloudabi::Linker(*this);
3375}
Ed Schouten3c3e58c2015-03-26 11:13:44 +00003376
Ed Schouten610adae2016-08-11 20:03:22 +00003377bool CloudABI::isPIEDefault() const {
3378 // Only enable PIE on architectures that support PC-relative
3379 // addressing. PC-relative addressing is required, as the process
3380 // startup code must be able to relocate itself.
3381 switch (getTriple().getArch()) {
3382 case llvm::Triple::aarch64:
3383 case llvm::Triple::x86_64:
3384 return true;
3385 default:
3386 return false;
3387 }
3388}
3389
Ed Schouten51bfbe72016-02-17 18:56:20 +00003390SanitizerMask CloudABI::getSupportedSanitizers() const {
3391 SanitizerMask Res = ToolChain::getSupportedSanitizers();
3392 Res |= SanitizerKind::SafeStack;
3393 return Res;
3394}
3395
Ed Schoutenfc79d2c2016-03-29 21:13:53 +00003396SanitizerMask CloudABI::getDefaultSanitizers() const {
3397 return SanitizerKind::SafeStack;
3398}
3399
Reid Kleckner330fb172016-05-11 16:19:05 +00003400/// Haiku - Haiku tool chain which can call as(1) and ld(1) directly.
3401
3402Haiku::Haiku(const Driver &D, const llvm::Triple& Triple, const ArgList &Args)
3403 : Generic_ELF(D, Triple, Args) {
3404
3405}
3406
3407void Haiku::AddClangCXXStdlibIncludeArgs(const ArgList &DriverArgs,
3408 ArgStringList &CC1Args) const {
3409 if (DriverArgs.hasArg(options::OPT_nostdlibinc) ||
3410 DriverArgs.hasArg(options::OPT_nostdincxx))
3411 return;
3412
3413 switch (GetCXXStdlibType(DriverArgs)) {
3414 case ToolChain::CST_Libcxx:
3415 addSystemInclude(DriverArgs, CC1Args,
3416 getDriver().SysRoot + "/system/develop/headers/c++/v1");
3417 break;
3418 case ToolChain::CST_Libstdcxx:
3419 addSystemInclude(DriverArgs, CC1Args,
3420 getDriver().SysRoot + "/system/develop/headers/c++");
3421 addSystemInclude(DriverArgs, CC1Args,
3422 getDriver().SysRoot + "/system/develop/headers/c++/backward");
3423
3424 StringRef Triple = getTriple().str();
3425 addSystemInclude(DriverArgs, CC1Args,
3426 getDriver().SysRoot + "/system/develop/headers/c++/" +
3427 Triple);
3428 break;
3429 }
3430}
3431
Daniel Dunbar10de9e62009-06-29 20:52:51 +00003432/// OpenBSD - OpenBSD tool chain which can call as(1) and ld(1) directly.
3433
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003434OpenBSD::OpenBSD(const Driver &D, const llvm::Triple &Triple,
3435 const ArgList &Args)
3436 : Generic_ELF(D, Triple, Args) {
Daniel Dunbar083edf72009-12-21 18:54:17 +00003437 getFilePaths().push_back(getDriver().Dir + "/../lib");
Daniel Dunbar10de9e62009-06-29 20:52:51 +00003438 getFilePaths().push_back("/usr/lib");
3439}
3440
Rafael Espindola7cf32212013-03-20 03:05:54 +00003441Tool *OpenBSD::buildAssembler() const {
Douglas Katzman95354292015-06-23 20:42:09 +00003442 return new tools::openbsd::Assembler(*this);
Rafael Espindola7cf32212013-03-20 03:05:54 +00003443}
3444
Douglas Katzman95354292015-06-23 20:42:09 +00003445Tool *OpenBSD::buildLinker() const { return new tools::openbsd::Linker(*this); }
Daniel Dunbar10de9e62009-06-29 20:52:51 +00003446
Eli Friedman9fa28852012-08-08 23:57:20 +00003447/// Bitrig - Bitrig tool chain which can call as(1) and ld(1) directly.
3448
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003449Bitrig::Bitrig(const Driver &D, const llvm::Triple &Triple, const ArgList &Args)
3450 : Generic_ELF(D, Triple, Args) {
Eli Friedman9fa28852012-08-08 23:57:20 +00003451 getFilePaths().push_back(getDriver().Dir + "/../lib");
3452 getFilePaths().push_back("/usr/lib");
3453}
3454
Rafael Espindola7cf32212013-03-20 03:05:54 +00003455Tool *Bitrig::buildAssembler() const {
Douglas Katzman95354292015-06-23 20:42:09 +00003456 return new tools::bitrig::Assembler(*this);
Rafael Espindola7cf32212013-03-20 03:05:54 +00003457}
3458
Douglas Katzman95354292015-06-23 20:42:09 +00003459Tool *Bitrig::buildLinker() const { return new tools::bitrig::Linker(*this); }
Eli Friedman9fa28852012-08-08 23:57:20 +00003460
Jonas Hahnfeldaae83742016-02-12 07:48:37 +00003461ToolChain::CXXStdlibType Bitrig::GetDefaultCXXStdlibType() const {
Richard Smith51af5192014-05-01 23:24:24 +00003462 return ToolChain::CST_Libcxx;
3463}
3464
Eli Friedman9fa28852012-08-08 23:57:20 +00003465void Bitrig::AddClangCXXStdlibIncludeArgs(const ArgList &DriverArgs,
3466 ArgStringList &CC1Args) const {
3467 if (DriverArgs.hasArg(options::OPT_nostdlibinc) ||
3468 DriverArgs.hasArg(options::OPT_nostdincxx))
3469 return;
3470
Chandler Carruthc0f5cd12012-10-08 21:31:38 +00003471 switch (GetCXXStdlibType(DriverArgs)) {
3472 case ToolChain::CST_Libcxx:
3473 addSystemInclude(DriverArgs, CC1Args,
Richard Smith51af5192014-05-01 23:24:24 +00003474 getDriver().SysRoot + "/usr/include/c++/v1");
Chandler Carruthc0f5cd12012-10-08 21:31:38 +00003475 break;
3476 case ToolChain::CST_Libstdcxx:
3477 addSystemInclude(DriverArgs, CC1Args,
3478 getDriver().SysRoot + "/usr/include/c++/stdc++");
3479 addSystemInclude(DriverArgs, CC1Args,
3480 getDriver().SysRoot + "/usr/include/c++/stdc++/backward");
Eli Friedman9fa28852012-08-08 23:57:20 +00003481
Chandler Carruthc0f5cd12012-10-08 21:31:38 +00003482 StringRef Triple = getTriple().str();
3483 if (Triple.startswith("amd64"))
3484 addSystemInclude(DriverArgs, CC1Args,
3485 getDriver().SysRoot + "/usr/include/c++/stdc++/x86_64" +
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003486 Triple.substr(5));
Chandler Carruthc0f5cd12012-10-08 21:31:38 +00003487 else
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003488 addSystemInclude(DriverArgs, CC1Args, getDriver().SysRoot +
3489 "/usr/include/c++/stdc++/" +
3490 Triple);
Chandler Carruthc0f5cd12012-10-08 21:31:38 +00003491 break;
3492 }
Eli Friedman9fa28852012-08-08 23:57:20 +00003493}
3494
3495void Bitrig::AddCXXStdlibLibArgs(const ArgList &Args,
3496 ArgStringList &CmdArgs) const {
Chandler Carruthc0f5cd12012-10-08 21:31:38 +00003497 switch (GetCXXStdlibType(Args)) {
3498 case ToolChain::CST_Libcxx:
3499 CmdArgs.push_back("-lc++");
Richard Smith51af5192014-05-01 23:24:24 +00003500 CmdArgs.push_back("-lc++abi");
3501 CmdArgs.push_back("-lpthread");
Chandler Carruthc0f5cd12012-10-08 21:31:38 +00003502 break;
3503 case ToolChain::CST_Libstdcxx:
3504 CmdArgs.push_back("-lstdc++");
3505 break;
3506 }
Eli Friedman9fa28852012-08-08 23:57:20 +00003507}
3508
Daniel Dunbare24297c2009-03-30 21:06:03 +00003509/// FreeBSD - FreeBSD tool chain which can call as(1) and ld(1) directly.
3510
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003511FreeBSD::FreeBSD(const Driver &D, const llvm::Triple &Triple,
3512 const ArgList &Args)
3513 : Generic_ELF(D, Triple, Args) {
Daniel Dunbara18a4872010-08-02 05:43:59 +00003514
Chandler Carruth0b1756b2012-01-26 01:35:15 +00003515 // When targeting 32-bit platforms, look for '/usr/lib32/crt1.o' and fall
3516 // back to '/usr/lib' if it doesn't exist.
Chandler Carruthf7bf3db2012-01-25 11:24:24 +00003517 if ((Triple.getArch() == llvm::Triple::x86 ||
3518 Triple.getArch() == llvm::Triple::ppc) &&
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003519 D.getVFS().exists(getDriver().SysRoot + "/usr/lib32/crt1.o"))
Chandler Carruthf7bf3db2012-01-25 11:24:24 +00003520 getFilePaths().push_back(getDriver().SysRoot + "/usr/lib32");
3521 else
3522 getFilePaths().push_back(getDriver().SysRoot + "/usr/lib");
Daniel Dunbare24297c2009-03-30 21:06:03 +00003523}
3524
Jonas Hahnfeld09954192016-03-14 14:34:04 +00003525ToolChain::CXXStdlibType FreeBSD::GetDefaultCXXStdlibType() const {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003526 if (getTriple().getOSMajorVersion() >= 10)
David Chisnall867ccd82013-11-09 15:10:56 +00003527 return ToolChain::CST_Libcxx;
3528 return ToolChain::CST_Libstdcxx;
3529}
3530
3531void FreeBSD::AddClangCXXStdlibIncludeArgs(const ArgList &DriverArgs,
3532 ArgStringList &CC1Args) const {
3533 if (DriverArgs.hasArg(options::OPT_nostdlibinc) ||
3534 DriverArgs.hasArg(options::OPT_nostdincxx))
3535 return;
3536
3537 switch (GetCXXStdlibType(DriverArgs)) {
3538 case ToolChain::CST_Libcxx:
3539 addSystemInclude(DriverArgs, CC1Args,
3540 getDriver().SysRoot + "/usr/include/c++/v1");
3541 break;
3542 case ToolChain::CST_Libstdcxx:
3543 addSystemInclude(DriverArgs, CC1Args,
3544 getDriver().SysRoot + "/usr/include/c++/4.2");
3545 addSystemInclude(DriverArgs, CC1Args,
3546 getDriver().SysRoot + "/usr/include/c++/4.2/backward");
3547 break;
3548 }
3549}
3550
Dimitry Andric60907392016-02-14 16:08:20 +00003551void FreeBSD::AddCXXStdlibLibArgs(const ArgList &Args,
3552 ArgStringList &CmdArgs) const {
3553 CXXStdlibType Type = GetCXXStdlibType(Args);
3554 bool Profiling = Args.hasArg(options::OPT_pg);
3555
3556 switch (Type) {
3557 case ToolChain::CST_Libcxx:
3558 CmdArgs.push_back(Profiling ? "-lc++_p" : "-lc++");
3559 break;
3560
3561 case ToolChain::CST_Libstdcxx:
3562 CmdArgs.push_back(Profiling ? "-lstdc++_p" : "-lstdc++");
3563 break;
3564 }
3565}
3566
Rafael Espindola7cf32212013-03-20 03:05:54 +00003567Tool *FreeBSD::buildAssembler() const {
Douglas Katzman95354292015-06-23 20:42:09 +00003568 return new tools::freebsd::Assembler(*this);
Rafael Espindola7cf32212013-03-20 03:05:54 +00003569}
3570
Douglas Katzman95354292015-06-23 20:42:09 +00003571Tool *FreeBSD::buildLinker() const { return new tools::freebsd::Linker(*this); }
Daniel Dunbarcc912342009-05-02 18:28:39 +00003572
Tim Northovere931f9f2015-10-30 16:30:41 +00003573bool FreeBSD::UseSjLjExceptions(const ArgList &Args) const {
Rafael Espindola0f207ed2012-12-13 04:17:14 +00003574 // FreeBSD uses SjLj exceptions on ARM oabi.
3575 switch (getTriple().getEnvironment()) {
Renato Golinf4421f72014-02-19 10:44:07 +00003576 case llvm::Triple::GNUEABIHF:
Rafael Espindola0f207ed2012-12-13 04:17:14 +00003577 case llvm::Triple::GNUEABI:
3578 case llvm::Triple::EABI:
3579 return false;
3580
3581 default:
3582 return (getTriple().getArch() == llvm::Triple::arm ||
3583 getTriple().getArch() == llvm::Triple::thumb);
3584 }
3585}
3586
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003587bool FreeBSD::HasNativeLLVMSupport() const { return true; }
Alexey Samsonove65ceb92014-02-25 13:26:03 +00003588
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003589bool FreeBSD::isPIEDefault() const { return getSanitizerArgs().requiresPIE(); }
Alexey Samsonove65ceb92014-02-25 13:26:03 +00003590
Alexey Samsonov7f2a0d22015-06-19 21:36:47 +00003591SanitizerMask FreeBSD::getSupportedSanitizers() const {
3592 const bool IsX86 = getTriple().getArch() == llvm::Triple::x86;
3593 const bool IsX86_64 = getTriple().getArch() == llvm::Triple::x86_64;
3594 const bool IsMIPS64 = getTriple().getArch() == llvm::Triple::mips64 ||
3595 getTriple().getArch() == llvm::Triple::mips64el;
3596 SanitizerMask Res = ToolChain::getSupportedSanitizers();
3597 Res |= SanitizerKind::Address;
3598 Res |= SanitizerKind::Vptr;
3599 if (IsX86_64 || IsMIPS64) {
3600 Res |= SanitizerKind::Leak;
3601 Res |= SanitizerKind::Thread;
3602 }
3603 if (IsX86 || IsX86_64) {
3604 Res |= SanitizerKind::SafeStack;
3605 }
3606 return Res;
3607}
3608
Benjamin Kramer24f1d3e2011-02-02 18:59:27 +00003609/// NetBSD - NetBSD tool chain which can call as(1) and ld(1) directly.
3610
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003611NetBSD::NetBSD(const Driver &D, const llvm::Triple &Triple, const ArgList &Args)
3612 : Generic_ELF(D, Triple, Args) {
Joerg Sonnenbergerbc923f32011-03-21 13:59:26 +00003613 if (getDriver().UseStdLib) {
Chandler Carruth1ccbed82012-01-25 11:18:20 +00003614 // When targeting a 32-bit platform, try the special directory used on
3615 // 64-bit hosts, and only fall back to the main library directory if that
3616 // doesn't work.
3617 // FIXME: It'd be nicer to test if this directory exists, but I'm not sure
3618 // what all logic is needed to emulate the '=' prefix here.
Joerg Sonnenberger25de31d2014-02-02 22:47:37 +00003619 switch (Triple.getArch()) {
3620 case llvm::Triple::x86:
Joerg Sonnenbergerbc923f32011-03-21 13:59:26 +00003621 getFilePaths().push_back("=/usr/lib/i386");
Joerg Sonnenberger25de31d2014-02-02 22:47:37 +00003622 break;
3623 case llvm::Triple::arm:
Joerg Sonnenberger3a6c28a2014-05-07 08:24:23 +00003624 case llvm::Triple::armeb:
Joerg Sonnenberger25de31d2014-02-02 22:47:37 +00003625 case llvm::Triple::thumb:
Joerg Sonnenberger3a6c28a2014-05-07 08:24:23 +00003626 case llvm::Triple::thumbeb:
Joerg Sonnenberger25de31d2014-02-02 22:47:37 +00003627 switch (Triple.getEnvironment()) {
3628 case llvm::Triple::EABI:
Joerg Sonnenberger25de31d2014-02-02 22:47:37 +00003629 case llvm::Triple::GNUEABI:
Joerg Sonnenberger25de31d2014-02-02 22:47:37 +00003630 getFilePaths().push_back("=/usr/lib/eabi");
3631 break;
Joerg Sonnenberger17a80e42014-08-09 19:01:52 +00003632 case llvm::Triple::EABIHF:
3633 case llvm::Triple::GNUEABIHF:
3634 getFilePaths().push_back("=/usr/lib/eabihf");
3635 break;
Joerg Sonnenberger25de31d2014-02-02 22:47:37 +00003636 default:
3637 getFilePaths().push_back("=/usr/lib/oabi");
3638 break;
3639 }
3640 break;
Joerg Sonnenbergere7f97592014-02-02 22:59:16 +00003641 case llvm::Triple::mips64:
3642 case llvm::Triple::mips64el:
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00003643 if (tools::mips::hasMipsAbiArg(Args, "o32"))
Joerg Sonnenbergere7f97592014-02-02 22:59:16 +00003644 getFilePaths().push_back("=/usr/lib/o32");
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00003645 else if (tools::mips::hasMipsAbiArg(Args, "64"))
Joerg Sonnenbergere7f97592014-02-02 22:59:16 +00003646 getFilePaths().push_back("=/usr/lib/64");
3647 break;
Joerg Sonnenbergerdd13b302014-08-13 14:17:32 +00003648 case llvm::Triple::ppc:
3649 getFilePaths().push_back("=/usr/lib/powerpc");
3650 break;
Joerg Sonnenberger8280abe2014-04-16 20:44:17 +00003651 case llvm::Triple::sparc:
3652 getFilePaths().push_back("=/usr/lib/sparc");
3653 break;
Joerg Sonnenberger25de31d2014-02-02 22:47:37 +00003654 default:
3655 break;
3656 }
Chandler Carruth1ccbed82012-01-25 11:18:20 +00003657
3658 getFilePaths().push_back("=/usr/lib");
Benjamin Kramer24f1d3e2011-02-02 18:59:27 +00003659 }
3660}
3661
Rafael Espindola7cf32212013-03-20 03:05:54 +00003662Tool *NetBSD::buildAssembler() const {
Douglas Katzman95354292015-06-23 20:42:09 +00003663 return new tools::netbsd::Assembler(*this);
Rafael Espindola7cf32212013-03-20 03:05:54 +00003664}
3665
Douglas Katzman95354292015-06-23 20:42:09 +00003666Tool *NetBSD::buildLinker() const { return new tools::netbsd::Linker(*this); }
Benjamin Kramer24f1d3e2011-02-02 18:59:27 +00003667
Jonas Hahnfeld09954192016-03-14 14:34:04 +00003668ToolChain::CXXStdlibType NetBSD::GetDefaultCXXStdlibType() const {
Joerg Sonnenbergera4435632013-10-14 20:13:05 +00003669 unsigned Major, Minor, Micro;
3670 getTriple().getOSVersion(Major, Minor, Micro);
Joerg Sonnenberger21156e82016-02-11 23:35:03 +00003671 if (Major >= 7 || Major == 0) {
Joerg Sonnenbergerd769a1e2014-01-18 00:50:49 +00003672 switch (getArch()) {
Joerg Sonnenberger323cea92014-08-09 18:28:36 +00003673 case llvm::Triple::aarch64:
Joerg Sonnenberger1ea66472014-05-07 08:45:26 +00003674 case llvm::Triple::arm:
3675 case llvm::Triple::armeb:
3676 case llvm::Triple::thumb:
3677 case llvm::Triple::thumbeb:
Joerg Sonnenbergerc8887572014-07-25 20:57:24 +00003678 case llvm::Triple::ppc:
Joerg Sonnenbergerdd13b302014-08-13 14:17:32 +00003679 case llvm::Triple::ppc64:
3680 case llvm::Triple::ppc64le:
Joerg Sonnenberger059613c2016-02-11 23:18:36 +00003681 case llvm::Triple::sparc:
3682 case llvm::Triple::sparcv9:
Joerg Sonnenbergerd769a1e2014-01-18 00:50:49 +00003683 case llvm::Triple::x86:
3684 case llvm::Triple::x86_64:
Joerg Sonnenbergera4435632013-10-14 20:13:05 +00003685 return ToolChain::CST_Libcxx;
Joerg Sonnenbergerd769a1e2014-01-18 00:50:49 +00003686 default:
3687 break;
3688 }
Joerg Sonnenbergera4435632013-10-14 20:13:05 +00003689 }
Joerg Sonnenberger428ef1e2013-04-30 01:21:43 +00003690 return ToolChain::CST_Libstdcxx;
3691}
3692
3693void NetBSD::AddClangCXXStdlibIncludeArgs(const ArgList &DriverArgs,
3694 ArgStringList &CC1Args) const {
3695 if (DriverArgs.hasArg(options::OPT_nostdlibinc) ||
3696 DriverArgs.hasArg(options::OPT_nostdincxx))
3697 return;
3698
3699 switch (GetCXXStdlibType(DriverArgs)) {
3700 case ToolChain::CST_Libcxx:
3701 addSystemInclude(DriverArgs, CC1Args,
3702 getDriver().SysRoot + "/usr/include/c++/");
3703 break;
3704 case ToolChain::CST_Libstdcxx:
3705 addSystemInclude(DriverArgs, CC1Args,
3706 getDriver().SysRoot + "/usr/include/g++");
3707 addSystemInclude(DriverArgs, CC1Args,
3708 getDriver().SysRoot + "/usr/include/g++/backward");
3709 break;
3710 }
3711}
3712
Chris Lattner3e2ee142010-07-07 16:01:42 +00003713/// Minix - Minix tool chain which can call as(1) and ld(1) directly.
3714
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003715Minix::Minix(const Driver &D, const llvm::Triple &Triple, const ArgList &Args)
3716 : Generic_ELF(D, Triple, Args) {
Chris Lattner3e2ee142010-07-07 16:01:42 +00003717 getFilePaths().push_back(getDriver().Dir + "/../lib");
3718 getFilePaths().push_back("/usr/lib");
Chris Lattner3e2ee142010-07-07 16:01:42 +00003719}
3720
Rafael Espindola7cf32212013-03-20 03:05:54 +00003721Tool *Minix::buildAssembler() const {
Douglas Katzman95354292015-06-23 20:42:09 +00003722 return new tools::minix::Assembler(*this);
Rafael Espindola7cf32212013-03-20 03:05:54 +00003723}
3724
Douglas Katzman95354292015-06-23 20:42:09 +00003725Tool *Minix::buildLinker() const { return new tools::minix::Linker(*this); }
Chris Lattner3e2ee142010-07-07 16:01:42 +00003726
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003727static void addPathIfExists(const Driver &D, const Twine &Path,
3728 ToolChain::path_list &Paths) {
3729 if (D.getVFS().exists(Path))
Rafael Espindolac53c5b12015-08-31 19:17:51 +00003730 Paths.push_back(Path.str());
3731}
3732
David Chisnallf571cde2012-02-15 13:39:01 +00003733/// Solaris - Solaris tool chain which can call as(1) and ld(1) directly.
3734
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003735Solaris::Solaris(const Driver &D, const llvm::Triple &Triple,
Rafael Espindola1af7c212012-02-19 01:38:32 +00003736 const ArgList &Args)
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003737 : Generic_GCC(D, Triple, Args) {
David Chisnallf571cde2012-02-15 13:39:01 +00003738
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003739 GCCInstallation.init(Triple, Args);
David Chisnallf571cde2012-02-15 13:39:01 +00003740
Rafael Espindolac53c5b12015-08-31 19:17:51 +00003741 path_list &Paths = getFilePaths();
3742 if (GCCInstallation.isValid())
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003743 addPathIfExists(D, GCCInstallation.getInstallPath(), Paths);
Rafael Espindolac53c5b12015-08-31 19:17:51 +00003744
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003745 addPathIfExists(D, getDriver().getInstalledDir(), Paths);
Rafael Espindolac53c5b12015-08-31 19:17:51 +00003746 if (getDriver().getInstalledDir() != getDriver().Dir)
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003747 addPathIfExists(D, getDriver().Dir, Paths);
Rafael Espindolac53c5b12015-08-31 19:17:51 +00003748
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003749 addPathIfExists(D, getDriver().SysRoot + getDriver().Dir + "/../lib", Paths);
Rafael Espindolac53c5b12015-08-31 19:17:51 +00003750
3751 std::string LibPath = "/usr/lib/";
3752 switch (Triple.getArch()) {
3753 case llvm::Triple::x86:
3754 case llvm::Triple::sparc:
3755 break;
3756 case llvm::Triple::x86_64:
3757 LibPath += "amd64/";
3758 break;
3759 case llvm::Triple::sparcv9:
3760 LibPath += "sparcv9/";
3761 break;
3762 default:
3763 llvm_unreachable("Unsupported architecture");
3764 }
3765
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003766 addPathIfExists(D, getDriver().SysRoot + LibPath, Paths);
David Chisnallf571cde2012-02-15 13:39:01 +00003767}
3768
Rafael Espindola7cf32212013-03-20 03:05:54 +00003769Tool *Solaris::buildAssembler() const {
Douglas Katzman95354292015-06-23 20:42:09 +00003770 return new tools::solaris::Assembler(*this);
Rafael Espindola7cf32212013-03-20 03:05:54 +00003771}
3772
Douglas Katzman95354292015-06-23 20:42:09 +00003773Tool *Solaris::buildLinker() const { return new tools::solaris::Linker(*this); }
Edward O'Callaghan856e4ff2009-08-22 01:06:46 +00003774
Rafael Espindolad5117262015-09-09 13:36:00 +00003775void Solaris::AddClangCXXStdlibIncludeArgs(const ArgList &DriverArgs,
3776 ArgStringList &CC1Args) const {
3777 if (DriverArgs.hasArg(options::OPT_nostdlibinc) ||
3778 DriverArgs.hasArg(options::OPT_nostdincxx))
3779 return;
3780
3781 // Include the support directory for things like xlocale and fudged system
3782 // headers.
3783 addSystemInclude(DriverArgs, CC1Args, "/usr/include/c++/v1/support/solaris");
3784
3785 if (GCCInstallation.isValid()) {
3786 GCCVersion Version = GCCInstallation.getVersion();
3787 addSystemInclude(DriverArgs, CC1Args,
3788 getDriver().SysRoot + "/usr/gcc/" +
3789 Version.MajorStr + "." +
3790 Version.MinorStr +
3791 "/include/c++/" + Version.Text);
3792 addSystemInclude(DriverArgs, CC1Args,
3793 getDriver().SysRoot + "/usr/gcc/" + Version.MajorStr +
3794 "." + Version.MinorStr + "/include/c++/" +
3795 Version.Text + "/" +
3796 GCCInstallation.getTriple().str());
3797 }
3798}
3799
Thomas Schwinge6d94da02013-03-28 19:02:48 +00003800/// Distribution (very bare-bones at the moment).
Eli Friedman5cd659f2009-05-26 07:52:18 +00003801
Thomas Schwinge6d94da02013-03-28 19:02:48 +00003802enum Distro {
Douglas Katzmana5df0c82015-06-22 20:55:31 +00003803 // NB: Releases of a particular Linux distro should be kept together
3804 // in this enum, because some tests are done by integer comparison against
3805 // the first and last known member in the family, e.g. IsRedHat().
Chandler Carruth6a4e8e32011-02-25 06:39:53 +00003806 ArchLinux,
Rafael Espindolac8f008f2010-11-07 20:14:31 +00003807 DebianLenny,
3808 DebianSqueeze,
Eli Friedmanf7600942011-06-02 21:36:53 +00003809 DebianWheezy,
Sylvestre Ledrubdef2892013-01-06 08:09:29 +00003810 DebianJessie,
Benjamin Kramer1a8fa8b2015-04-06 12:30:43 +00003811 DebianStretch,
Rafael Espindola12479842010-11-11 02:07:13 +00003812 Exherbo,
Chris Lattner84e38552011-05-22 05:36:06 +00003813 RHEL5,
3814 RHEL6,
Benjamin Kramer1a8fa8b2015-04-06 12:30:43 +00003815 RHEL7,
Rafael Espindola0d2cbc02013-10-25 18:09:41 +00003816 Fedora,
Rafael Espindola10a63c22013-07-03 14:14:00 +00003817 OpenSUSE,
Douglas Gregor0a36f4d2011-03-14 15:39:50 +00003818 UbuntuHardy,
3819 UbuntuIntrepid,
Rafael Espindola66b291a2010-11-10 05:00:22 +00003820 UbuntuJaunty,
Zhongxing Xu14776cf2010-11-15 09:01:52 +00003821 UbuntuKarmic,
Rafael Espindolac8f008f2010-11-07 20:14:31 +00003822 UbuntuLucid,
3823 UbuntuMaverick,
Ted Kremenek43d47cc2011-04-05 22:04:27 +00003824 UbuntuNatty,
Benjamin Kramerf90b5de2011-06-05 16:08:59 +00003825 UbuntuOneiric,
Benjamin Kramer7c3f09d2012-02-06 14:36:09 +00003826 UbuntuPrecise,
Rafael Espindola62e87702012-12-13 20:26:05 +00003827 UbuntuQuantal,
3828 UbuntuRaring,
Sylvestre Ledru93c47b72013-06-13 11:52:27 +00003829 UbuntuSaucy,
Sylvestre Ledruaaf01a72013-11-07 09:31:30 +00003830 UbuntuTrusty,
Benjamin Kramer1a8fa8b2015-04-06 12:30:43 +00003831 UbuntuUtopic,
3832 UbuntuVivid,
Benjamin Kramer2d469802015-07-09 15:31:17 +00003833 UbuntuWily,
Sylvestre Ledru43b95712015-10-29 17:27:55 +00003834 UbuntuXenial,
Sylvestre Ledrud3078e72016-07-19 14:00:57 +00003835 UbuntuYakkety,
Rafael Espindolac8f008f2010-11-07 20:14:31 +00003836 UnknownDistro
3837};
3838
Thomas Schwinge6d94da02013-03-28 19:02:48 +00003839static bool IsRedhat(enum Distro Distro) {
Rafael Espindola52fe8962016-05-09 13:13:50 +00003840 return Distro == Fedora || (Distro >= RHEL5 && Distro <= RHEL7);
Rafael Espindolac8f008f2010-11-07 20:14:31 +00003841}
3842
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003843static bool IsOpenSUSE(enum Distro Distro) { return Distro == OpenSUSE; }
Rafael Espindolac8f008f2010-11-07 20:14:31 +00003844
Thomas Schwinge6d94da02013-03-28 19:02:48 +00003845static bool IsDebian(enum Distro Distro) {
Benjamin Kramer1a8fa8b2015-04-06 12:30:43 +00003846 return Distro >= DebianLenny && Distro <= DebianStretch;
Rafael Espindolac8f008f2010-11-07 20:14:31 +00003847}
3848
Thomas Schwinge6d94da02013-03-28 19:02:48 +00003849static bool IsUbuntu(enum Distro Distro) {
Sylvestre Ledrud3078e72016-07-19 14:00:57 +00003850 return Distro >= UbuntuHardy && Distro <= UbuntuYakkety;
Rafael Espindolac8f008f2010-11-07 20:14:31 +00003851}
3852
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003853static Distro DetectDistro(const Driver &D, llvm::Triple::ArchType Arch) {
Rafael Espindola2d2b4202014-07-06 17:43:24 +00003854 llvm::ErrorOr<std::unique_ptr<llvm::MemoryBuffer>> File =
Michal Gorny9e1b6e12016-10-17 18:07:15 +00003855 D.getVFS().getBufferForFile("/etc/lsb-release");
Rafael Espindola2d2b4202014-07-06 17:43:24 +00003856 if (File) {
Chris Lattner0e62c1c2011-07-23 10:55:15 +00003857 StringRef Data = File.get()->getBuffer();
Hans Wennborg3b7dd8d2014-08-11 18:09:32 +00003858 SmallVector<StringRef, 16> Lines;
Rafael Espindolac8f008f2010-11-07 20:14:31 +00003859 Data.split(Lines, "\n");
Thomas Schwinge6d94da02013-03-28 19:02:48 +00003860 Distro Version = UnknownDistro;
Benjamin Kramer72e64312015-09-24 14:48:49 +00003861 for (StringRef Line : Lines)
Douglas Katzman6bbffc42015-06-25 18:51:37 +00003862 if (Version == UnknownDistro && Line.startswith("DISTRIB_CODENAME="))
3863 Version = llvm::StringSwitch<Distro>(Line.substr(17))
3864 .Case("hardy", UbuntuHardy)
3865 .Case("intrepid", UbuntuIntrepid)
3866 .Case("jaunty", UbuntuJaunty)
3867 .Case("karmic", UbuntuKarmic)
3868 .Case("lucid", UbuntuLucid)
3869 .Case("maverick", UbuntuMaverick)
3870 .Case("natty", UbuntuNatty)
3871 .Case("oneiric", UbuntuOneiric)
3872 .Case("precise", UbuntuPrecise)
3873 .Case("quantal", UbuntuQuantal)
3874 .Case("raring", UbuntuRaring)
3875 .Case("saucy", UbuntuSaucy)
3876 .Case("trusty", UbuntuTrusty)
3877 .Case("utopic", UbuntuUtopic)
3878 .Case("vivid", UbuntuVivid)
Benjamin Kramer2d469802015-07-09 15:31:17 +00003879 .Case("wily", UbuntuWily)
Sylvestre Ledru43b95712015-10-29 17:27:55 +00003880 .Case("xenial", UbuntuXenial)
Sylvestre Ledrud3078e72016-07-19 14:00:57 +00003881 .Case("yakkety", UbuntuYakkety)
Douglas Katzman6bbffc42015-06-25 18:51:37 +00003882 .Default(UnknownDistro);
Rafael Espindola52fe8962016-05-09 13:13:50 +00003883 if (Version != UnknownDistro)
3884 return Version;
Rafael Espindolac8f008f2010-11-07 20:14:31 +00003885 }
3886
Michal Gorny9e1b6e12016-10-17 18:07:15 +00003887 File = D.getVFS().getBufferForFile("/etc/redhat-release");
Rafael Espindola2d2b4202014-07-06 17:43:24 +00003888 if (File) {
Chris Lattner0e62c1c2011-07-23 10:55:15 +00003889 StringRef Data = File.get()->getBuffer();
Rafael Espindola0d2cbc02013-10-25 18:09:41 +00003890 if (Data.startswith("Fedora release"))
3891 return Fedora;
Benjamin Kramer6af073b2014-05-05 12:39:32 +00003892 if (Data.startswith("Red Hat Enterprise Linux") ||
Rafael Espindola52fe8962016-05-09 13:13:50 +00003893 Data.startswith("CentOS") ||
3894 Data.startswith("Scientific Linux")) {
Benjamin Kramer1a8fa8b2015-04-06 12:30:43 +00003895 if (Data.find("release 7") != StringRef::npos)
3896 return RHEL7;
3897 else if (Data.find("release 6") != StringRef::npos)
Benjamin Kramer6af073b2014-05-05 12:39:32 +00003898 return RHEL6;
3899 else if (Data.find("release 5") != StringRef::npos)
3900 return RHEL5;
Benjamin Kramer6af073b2014-05-05 12:39:32 +00003901 }
Rafael Espindolac8f008f2010-11-07 20:14:31 +00003902 return UnknownDistro;
3903 }
3904
Michal Gorny9e1b6e12016-10-17 18:07:15 +00003905 File = D.getVFS().getBufferForFile("/etc/debian_version");
Rafael Espindola2d2b4202014-07-06 17:43:24 +00003906 if (File) {
Chris Lattner0e62c1c2011-07-23 10:55:15 +00003907 StringRef Data = File.get()->getBuffer();
Rafael Espindolac8f008f2010-11-07 20:14:31 +00003908 if (Data[0] == '5')
3909 return DebianLenny;
Rafael Espindola1510c852011-12-28 18:17:14 +00003910 else if (Data.startswith("squeeze/sid") || Data[0] == '6')
Rafael Espindolac8f008f2010-11-07 20:14:31 +00003911 return DebianSqueeze;
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003912 else if (Data.startswith("wheezy/sid") || Data[0] == '7')
Eli Friedmanf7600942011-06-02 21:36:53 +00003913 return DebianWheezy;
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003914 else if (Data.startswith("jessie/sid") || Data[0] == '8')
Sylvestre Ledrubdef2892013-01-06 08:09:29 +00003915 return DebianJessie;
Benjamin Kramer1a8fa8b2015-04-06 12:30:43 +00003916 else if (Data.startswith("stretch/sid") || Data[0] == '9')
3917 return DebianStretch;
Rafael Espindolac8f008f2010-11-07 20:14:31 +00003918 return UnknownDistro;
3919 }
3920
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003921 if (D.getVFS().exists("/etc/SuSE-release"))
Rafael Espindola10a63c22013-07-03 14:14:00 +00003922 return OpenSUSE;
Rafael Espindolac8f008f2010-11-07 20:14:31 +00003923
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003924 if (D.getVFS().exists("/etc/exherbo-release"))
Rafael Espindola12479842010-11-11 02:07:13 +00003925 return Exherbo;
3926
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003927 if (D.getVFS().exists("/etc/arch-release"))
Chandler Carruth6a4e8e32011-02-25 06:39:53 +00003928 return ArchLinux;
3929
Rafael Espindolac8f008f2010-11-07 20:14:31 +00003930 return UnknownDistro;
3931}
3932
Chandler Carruthfb7fa242011-10-31 08:42:24 +00003933/// \brief Get our best guess at the multiarch triple for a target.
3934///
3935/// Debian-based systems are starting to use a multiarch setup where they use
3936/// a target-triple directory in the library and header search paths.
3937/// Unfortunately, this triple does not align with the vanilla target triple,
3938/// so we provide a rough mapping here.
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003939static std::string getMultiarchTriple(const Driver &D,
3940 const llvm::Triple &TargetTriple,
Chandler Carruthfb7fa242011-10-31 08:42:24 +00003941 StringRef SysRoot) {
Eric Christopherefef8ef2015-12-07 22:43:05 +00003942 llvm::Triple::EnvironmentType TargetEnvironment =
3943 TargetTriple.getEnvironment();
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00003944
Chandler Carruthfb7fa242011-10-31 08:42:24 +00003945 // For most architectures, just use whatever we have rather than trying to be
3946 // clever.
3947 switch (TargetTriple.getArch()) {
3948 default:
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00003949 break;
Chandler Carruthfb7fa242011-10-31 08:42:24 +00003950
Douglas Katzmana67e50c2015-06-26 15:47:46 +00003951 // We use the existence of '/lib/<triple>' as a directory to detect some
3952 // common linux triples that don't quite match the Clang triple for both
3953 // 32-bit and 64-bit targets. Multiarch fixes its install triples to these
3954 // regardless of what the actual target triple is.
Chad Rosier4dce73a2012-07-11 19:08:21 +00003955 case llvm::Triple::arm:
3956 case llvm::Triple::thumb:
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00003957 if (TargetEnvironment == llvm::Triple::GNUEABIHF) {
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003958 if (D.getVFS().exists(SysRoot + "/lib/arm-linux-gnueabihf"))
Jiangning Liu61b06cb2012-07-31 08:06:29 +00003959 return "arm-linux-gnueabihf";
3960 } else {
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003961 if (D.getVFS().exists(SysRoot + "/lib/arm-linux-gnueabi"))
Jiangning Liu61b06cb2012-07-31 08:06:29 +00003962 return "arm-linux-gnueabi";
3963 }
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00003964 break;
Christian Pirkerf01cd6f2014-03-28 14:40:46 +00003965 case llvm::Triple::armeb:
3966 case llvm::Triple::thumbeb:
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00003967 if (TargetEnvironment == llvm::Triple::GNUEABIHF) {
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003968 if (D.getVFS().exists(SysRoot + "/lib/armeb-linux-gnueabihf"))
Christian Pirkerf01cd6f2014-03-28 14:40:46 +00003969 return "armeb-linux-gnueabihf";
3970 } else {
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003971 if (D.getVFS().exists(SysRoot + "/lib/armeb-linux-gnueabi"))
Christian Pirkerf01cd6f2014-03-28 14:40:46 +00003972 return "armeb-linux-gnueabi";
3973 }
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00003974 break;
Chandler Carruthfb7fa242011-10-31 08:42:24 +00003975 case llvm::Triple::x86:
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003976 if (D.getVFS().exists(SysRoot + "/lib/i386-linux-gnu"))
Chandler Carruthfb7fa242011-10-31 08:42:24 +00003977 return "i386-linux-gnu";
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00003978 break;
Chandler Carruthfb7fa242011-10-31 08:42:24 +00003979 case llvm::Triple::x86_64:
Zinovy Nis1db95732014-07-10 15:27:19 +00003980 // We don't want this for x32, otherwise it will match x86_64 libs
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00003981 if (TargetEnvironment != llvm::Triple::GNUX32 &&
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003982 D.getVFS().exists(SysRoot + "/lib/x86_64-linux-gnu"))
Chandler Carruthfb7fa242011-10-31 08:42:24 +00003983 return "x86_64-linux-gnu";
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00003984 break;
Tim Northover9bb857a2013-01-31 12:13:10 +00003985 case llvm::Triple::aarch64:
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003986 if (D.getVFS().exists(SysRoot + "/lib/aarch64-linux-gnu"))
Tim Northover9bb857a2013-01-31 12:13:10 +00003987 return "aarch64-linux-gnu";
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00003988 break;
Christian Pirkera74c7912014-03-14 12:15:45 +00003989 case llvm::Triple::aarch64_be:
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003990 if (D.getVFS().exists(SysRoot + "/lib/aarch64_be-linux-gnu"))
Christian Pirkera74c7912014-03-14 12:15:45 +00003991 return "aarch64_be-linux-gnu";
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00003992 break;
Eli Friedman27b8c4f2011-11-08 19:43:37 +00003993 case llvm::Triple::mips:
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003994 if (D.getVFS().exists(SysRoot + "/lib/mips-linux-gnu"))
Eli Friedman27b8c4f2011-11-08 19:43:37 +00003995 return "mips-linux-gnu";
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00003996 break;
Eli Friedman27b8c4f2011-11-08 19:43:37 +00003997 case llvm::Triple::mipsel:
Benjamin Kramerd45b2052015-10-07 15:48:01 +00003998 if (D.getVFS().exists(SysRoot + "/lib/mipsel-linux-gnu"))
Eli Friedman27b8c4f2011-11-08 19:43:37 +00003999 return "mipsel-linux-gnu";
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00004000 break;
Simon Atanasyan3a46afa2014-06-24 19:00:12 +00004001 case llvm::Triple::mips64:
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004002 if (D.getVFS().exists(SysRoot + "/lib/mips64-linux-gnu"))
Simon Atanasyan3a46afa2014-06-24 19:00:12 +00004003 return "mips64-linux-gnu";
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004004 if (D.getVFS().exists(SysRoot + "/lib/mips64-linux-gnuabi64"))
Simon Atanasyan3a46afa2014-06-24 19:00:12 +00004005 return "mips64-linux-gnuabi64";
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00004006 break;
Simon Atanasyan3a46afa2014-06-24 19:00:12 +00004007 case llvm::Triple::mips64el:
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004008 if (D.getVFS().exists(SysRoot + "/lib/mips64el-linux-gnu"))
Simon Atanasyan3a46afa2014-06-24 19:00:12 +00004009 return "mips64el-linux-gnu";
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004010 if (D.getVFS().exists(SysRoot + "/lib/mips64el-linux-gnuabi64"))
Simon Atanasyan3a46afa2014-06-24 19:00:12 +00004011 return "mips64el-linux-gnuabi64";
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00004012 break;
Chandler Carruthaf3c2092012-02-26 09:03:21 +00004013 case llvm::Triple::ppc:
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004014 if (D.getVFS().exists(SysRoot + "/lib/powerpc-linux-gnuspe"))
Sylvestre Ledrue0bf5812013-03-15 16:22:43 +00004015 return "powerpc-linux-gnuspe";
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004016 if (D.getVFS().exists(SysRoot + "/lib/powerpc-linux-gnu"))
Chandler Carruthaf3c2092012-02-26 09:03:21 +00004017 return "powerpc-linux-gnu";
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00004018 break;
Chandler Carruthaf3c2092012-02-26 09:03:21 +00004019 case llvm::Triple::ppc64:
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004020 if (D.getVFS().exists(SysRoot + "/lib/powerpc64-linux-gnu"))
Chandler Carruthaf3c2092012-02-26 09:03:21 +00004021 return "powerpc64-linux-gnu";
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00004022 break;
Bill Schmidt778d3872013-07-26 01:36:11 +00004023 case llvm::Triple::ppc64le:
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004024 if (D.getVFS().exists(SysRoot + "/lib/powerpc64le-linux-gnu"))
Bill Schmidt778d3872013-07-26 01:36:11 +00004025 return "powerpc64le-linux-gnu";
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00004026 break;
James Y Knightc0aeadf2015-06-04 15:36:30 +00004027 case llvm::Triple::sparc:
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004028 if (D.getVFS().exists(SysRoot + "/lib/sparc-linux-gnu"))
James Y Knightc0aeadf2015-06-04 15:36:30 +00004029 return "sparc-linux-gnu";
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00004030 break;
James Y Knightc0aeadf2015-06-04 15:36:30 +00004031 case llvm::Triple::sparcv9:
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004032 if (D.getVFS().exists(SysRoot + "/lib/sparc64-linux-gnu"))
James Y Knightc0aeadf2015-06-04 15:36:30 +00004033 return "sparc64-linux-gnu";
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00004034 break;
Sylvestre Ledruc0babf22015-08-28 12:26:09 +00004035 case llvm::Triple::systemz:
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004036 if (D.getVFS().exists(SysRoot + "/lib/s390x-linux-gnu"))
Sylvestre Ledruc0babf22015-08-28 12:26:09 +00004037 return "s390x-linux-gnu";
4038 break;
Chandler Carruthfb7fa242011-10-31 08:42:24 +00004039 }
Douglas Katzmanecddb3a2015-06-26 18:37:15 +00004040 return TargetTriple.str();
Chandler Carruthfb7fa242011-10-31 08:42:24 +00004041}
4042
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004043static StringRef getOSLibDir(const llvm::Triple &Triple, const ArgList &Args) {
Chandler Carruthda797042013-10-29 10:27:30 +00004044 if (isMipsArch(Triple.getArch())) {
Simon Atanasyan603018a2016-07-19 07:09:48 +00004045 if (Triple.isAndroid()) {
4046 StringRef CPUName;
4047 StringRef ABIName;
4048 tools::mips::getMipsCPUAndABI(Args, Triple, CPUName, ABIName);
4049 if (CPUName == "mips32r6")
4050 return "libr6";
4051 if (CPUName == "mips32r2")
4052 return "libr2";
4053 }
Chandler Carruthda797042013-10-29 10:27:30 +00004054 // lib32 directory has a special meaning on MIPS targets.
4055 // It contains N32 ABI binaries. Use this folder if produce
4056 // code for N32 ABI only.
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004057 if (tools::mips::hasMipsAbiArg(Args, "n32"))
Chandler Carruthda797042013-10-29 10:27:30 +00004058 return "lib32";
4059 return Triple.isArch32Bit() ? "lib" : "lib64";
4060 }
Simon Atanasyand4413882012-09-14 11:27:24 +00004061
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004062 // It happens that only x86 and PPC use the 'lib32' variant of oslibdir, and
Chandler Carruthda797042013-10-29 10:27:30 +00004063 // using that variant while targeting other architectures causes problems
4064 // because the libraries are laid out in shared system roots that can't cope
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004065 // with a 'lib32' library search path being considered. So we only enable
Chandler Carruthda797042013-10-29 10:27:30 +00004066 // them when we know we may need it.
4067 //
4068 // FIXME: This is a bit of a hack. We should really unify this code for
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004069 // reasoning about oslibdir spellings with the lib dir spellings in the
Chandler Carruthda797042013-10-29 10:27:30 +00004070 // GCCInstallationDetector, but that is a more significant refactoring.
4071 if (Triple.getArch() == llvm::Triple::x86 ||
4072 Triple.getArch() == llvm::Triple::ppc)
Simon Atanasyand4413882012-09-14 11:27:24 +00004073 return "lib32";
4074
Zinovy Nis1db95732014-07-10 15:27:19 +00004075 if (Triple.getArch() == llvm::Triple::x86_64 &&
4076 Triple.getEnvironment() == llvm::Triple::GNUX32)
4077 return "libx32";
4078
Simon Atanasyand4413882012-09-14 11:27:24 +00004079 return Triple.isArch32Bit() ? "lib" : "lib64";
4080}
4081
Simon Atanasyan2834a222016-05-22 18:18:07 +00004082static void addMultilibsFilePaths(const Driver &D, const MultilibSet &Multilibs,
4083 const Multilib &Multilib,
4084 StringRef InstallPath,
4085 ToolChain::path_list &Paths) {
4086 if (const auto &PathsCallback = Multilibs.filePathsCallback())
4087 for (const auto &Path : PathsCallback(Multilib))
4088 addPathIfExists(D, InstallPath + Path, Paths);
4089}
4090
Rafael Espindola1af7c212012-02-19 01:38:32 +00004091Linux::Linux(const Driver &D, const llvm::Triple &Triple, const ArgList &Args)
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004092 : Generic_ELF(D, Triple, Args) {
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004093 GCCInstallation.init(Triple, Args);
4094 CudaInstallation.init(Triple, Args);
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004095 Multilibs = GCCInstallation.getMultilibs();
Chandler Carruth96bae7b2012-01-24 20:08:17 +00004096 llvm::Triple::ArchType Arch = Triple.getArch();
Simon Atanasyana0d89572013-10-05 14:37:55 +00004097 std::string SysRoot = computeSysRoot();
Rafael Espindolac8f008f2010-11-07 20:14:31 +00004098
Rafael Espindola10a63c22013-07-03 14:14:00 +00004099 // Cross-compiling binutils and GCC installations (vanilla and openSUSE at
Chandler Carruthd6c62b62013-06-20 23:37:54 +00004100 // least) put various tools in a triple-prefixed directory off of the parent
4101 // of the GCC installation. We use the GCC triple here to ensure that we end
4102 // up with tools that support the same amount of cross compiling as the
4103 // detected GCC installation. For example, if we find a GCC installation
4104 // targeting x86_64, but it is a bi-arch GCC installation, it can also be
4105 // used to target i386.
4106 // FIXME: This seems unlikely to be Linux-specific.
Rafael Espindola5f344ff2011-09-01 16:25:49 +00004107 ToolChain::path_list &PPaths = getProgramPaths();
Chandler Carruth4be70dd2011-11-06 09:21:54 +00004108 PPaths.push_back(Twine(GCCInstallation.getParentLibPath() + "/../" +
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004109 GCCInstallation.getTriple().str() + "/bin")
4110 .str());
Rafael Espindola5f344ff2011-09-01 16:25:49 +00004111
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004112 Distro Distro = DetectDistro(D, Arch);
Rafael Espindolac8f008f2010-11-07 20:14:31 +00004113
Rafael Espindola10a63c22013-07-03 14:14:00 +00004114 if (IsOpenSUSE(Distro) || IsUbuntu(Distro)) {
Rafael Espindolac5688622010-11-08 14:48:47 +00004115 ExtraOpts.push_back("-z");
4116 ExtraOpts.push_back("relro");
4117 }
Rafael Espindolac8f008f2010-11-07 20:14:31 +00004118
Douglas Gregord9bb1522011-03-06 19:11:49 +00004119 if (Arch == llvm::Triple::arm || Arch == llvm::Triple::thumb)
Rafael Espindolac8f008f2010-11-07 20:14:31 +00004120 ExtraOpts.push_back("-X");
4121
Evgeniy Stepanov14deb7b2015-10-08 21:21:44 +00004122 const bool IsAndroid = Triple.isAndroid();
Simon Atanasyan08450bd2013-04-20 08:15:03 +00004123 const bool IsMips = isMipsArch(Arch);
4124
4125 if (IsMips && !SysRoot.empty())
4126 ExtraOpts.push_back("--sysroot=" + SysRoot);
Evgeniy Stepanov2ca1aa52012-01-13 09:30:38 +00004127
Chandler Carruth0b842912011-12-09 04:45:18 +00004128 // Do not use 'gnu' hash style for Mips targets because .gnu.hash
4129 // and the MIPS ABI require .dynsym to be sorted in different ways.
4130 // .gnu.hash needs symbols to be grouped by hash code whereas the MIPS
4131 // ABI requires a mapping between the GOT and the symbol table.
Evgeniy Stepanov2ca1aa52012-01-13 09:30:38 +00004132 // Android loader does not support .gnu.hash.
Simon Atanasyan08450bd2013-04-20 08:15:03 +00004133 if (!IsMips && !IsAndroid) {
Rafael Espindola10a63c22013-07-03 14:14:00 +00004134 if (IsRedhat(Distro) || IsOpenSUSE(Distro) ||
Benjamin Kramer7c3f09d2012-02-06 14:36:09 +00004135 (IsUbuntu(Distro) && Distro >= UbuntuMaverick))
Chandler Carruth0b842912011-12-09 04:45:18 +00004136 ExtraOpts.push_back("--hash-style=gnu");
4137
Rafael Espindola10a63c22013-07-03 14:14:00 +00004138 if (IsDebian(Distro) || IsOpenSUSE(Distro) || Distro == UbuntuLucid ||
Chandler Carruth0b842912011-12-09 04:45:18 +00004139 Distro == UbuntuJaunty || Distro == UbuntuKarmic)
4140 ExtraOpts.push_back("--hash-style=both");
4141 }
Rafael Espindolac8f008f2010-11-07 20:14:31 +00004142
Rafael Espindola52fe8962016-05-09 13:13:50 +00004143 if (IsRedhat(Distro) && Distro != RHEL5 && Distro != RHEL6)
Rafael Espindolac8f008f2010-11-07 20:14:31 +00004144 ExtraOpts.push_back("--no-add-needed");
4145
Rafael Espindola5ed89d42016-06-03 17:26:16 +00004146#ifdef ENABLE_LINKER_BUILD_ID
4147 ExtraOpts.push_back("--build-id");
4148#endif
Rafael Espindolac8f008f2010-11-07 20:14:31 +00004149
Rafael Espindola10a63c22013-07-03 14:14:00 +00004150 if (IsOpenSUSE(Distro))
Chandler Carruthe5d9d902011-05-24 07:51:17 +00004151 ExtraOpts.push_back("--enable-new-dtags");
Chris Lattnerd075c822011-05-22 16:45:07 +00004152
Chandler Carruth413e5ac2011-10-03 05:28:29 +00004153 // The selection of paths to try here is designed to match the patterns which
4154 // the GCC driver itself uses, as this is part of the GCC-compatible driver.
4155 // This was determined by running GCC in a fake filesystem, creating all
4156 // possible permutations of these directories, and seeing which ones it added
4157 // to the link paths.
4158 path_list &Paths = getFilePaths();
Chandler Carruth6a4e8e32011-02-25 06:39:53 +00004159
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004160 const std::string OSLibDir = getOSLibDir(Triple, Args);
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004161 const std::string MultiarchTriple = getMultiarchTriple(D, Triple, SysRoot);
Chandler Carruth413e5ac2011-10-03 05:28:29 +00004162
Chandler Carruthd0b93d62011-11-06 23:09:05 +00004163 // Add the multilib suffixed paths where they are available.
4164 if (GCCInstallation.isValid()) {
Chandler Carruth4d9d7682012-01-24 19:28:29 +00004165 const llvm::Triple &GCCTriple = GCCInstallation.getTriple();
Chandler Carruth96bae7b2012-01-24 20:08:17 +00004166 const std::string &LibPath = GCCInstallation.getParentLibPath();
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004167 const Multilib &Multilib = GCCInstallation.getMultilib();
Simon Atanasyan2834a222016-05-22 18:18:07 +00004168 const MultilibSet &Multilibs = GCCInstallation.getMultilibs();
4169
4170 // Add toolchain / multilib specific file paths.
4171 addMultilibsFilePaths(D, Multilibs, Multilib,
4172 GCCInstallation.getInstallPath(), Paths);
Simon Atanasyan53fefd12012-10-03 17:46:38 +00004173
Chandler Carruth7f8042c2013-07-31 00:37:07 +00004174 // Sourcery CodeBench MIPS toolchain holds some libraries under
Chandler Carruth9b6ce932013-10-29 02:27:56 +00004175 // a biarch-like suffix of the GCC installation.
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004176 addPathIfExists(D, GCCInstallation.getInstallPath() + Multilib.gccSuffix(),
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004177 Paths);
Chandler Carruth7f8042c2013-07-31 00:37:07 +00004178
4179 // GCC cross compiling toolchains will install target libraries which ship
4180 // as part of the toolchain under <prefix>/<triple>/<libdir> rather than as
4181 // any part of the GCC installation in
4182 // <prefix>/<libdir>/gcc/<triple>/<version>. This decision is somewhat
4183 // debatable, but is the reality today. We need to search this tree even
4184 // when we have a sysroot somewhere else. It is the responsibility of
Alp Tokerf6a24ce2013-12-05 16:25:25 +00004185 // whomever is doing the cross build targeting a sysroot using a GCC
Chandler Carruth7f8042c2013-07-31 00:37:07 +00004186 // installation that is *not* within the system root to ensure two things:
4187 //
4188 // 1) Any DSOs that are linked in from this tree or from the install path
Alexander Potapenkoc8e749a2014-09-01 12:35:57 +00004189 // above must be present on the system root and found via an
Chandler Carruth7f8042c2013-07-31 00:37:07 +00004190 // appropriate rpath.
4191 // 2) There must not be libraries installed into
4192 // <prefix>/<triple>/<libdir> unless they should be preferred over
4193 // those within the system root.
4194 //
4195 // Note that this matches the GCC behavior. See the below comment for where
4196 // Clang diverges from GCC's behavior.
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004197 addPathIfExists(D, LibPath + "/../" + GCCTriple.str() + "/lib/../" +
4198 OSLibDir + Multilib.osSuffix(),
Chandler Carruth7f8042c2013-07-31 00:37:07 +00004199 Paths);
4200
Chandler Carruth69a125b2012-04-06 16:32:06 +00004201 // If the GCC installation we found is inside of the sysroot, we want to
4202 // prefer libraries installed in the parent prefix of the GCC installation.
4203 // It is important to *not* use these paths when the GCC installation is
Gabor Greif5d3231c2012-04-18 10:59:08 +00004204 // outside of the system root as that can pick up unintended libraries.
Chandler Carruth69a125b2012-04-06 16:32:06 +00004205 // This usually happens when there is an external cross compiler on the
4206 // host system, and a more minimal sysroot available that is the target of
Chandler Carruth7f8042c2013-07-31 00:37:07 +00004207 // the cross. Note that GCC does include some of these directories in some
4208 // configurations but this seems somewhere between questionable and simply
4209 // a bug.
Chandler Carruth69a125b2012-04-06 16:32:06 +00004210 if (StringRef(LibPath).startswith(SysRoot)) {
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004211 addPathIfExists(D, LibPath + "/" + MultiarchTriple, Paths);
4212 addPathIfExists(D, LibPath + "/../" + OSLibDir, Paths);
Chandler Carruth69a125b2012-04-06 16:32:06 +00004213 }
Rafael Espindolac8f008f2010-11-07 20:14:31 +00004214 }
Chandler Carruth902efc62014-01-21 22:49:05 +00004215
4216 // Similar to the logic for GCC above, if we currently running Clang inside
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004217 // of the requested system root, add its parent library paths to
Chandler Carruth902efc62014-01-21 22:49:05 +00004218 // those searched.
4219 // FIXME: It's not clear whether we should use the driver's installed
4220 // directory ('Dir' below) or the ResourceDir.
4221 if (StringRef(D.Dir).startswith(SysRoot)) {
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004222 addPathIfExists(D, D.Dir + "/../lib/" + MultiarchTriple, Paths);
4223 addPathIfExists(D, D.Dir + "/../" + OSLibDir, Paths);
Chandler Carruth902efc62014-01-21 22:49:05 +00004224 }
4225
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004226 addPathIfExists(D, SysRoot + "/lib/" + MultiarchTriple, Paths);
4227 addPathIfExists(D, SysRoot + "/lib/../" + OSLibDir, Paths);
4228 addPathIfExists(D, SysRoot + "/usr/lib/" + MultiarchTriple, Paths);
4229 addPathIfExists(D, SysRoot + "/usr/lib/../" + OSLibDir, Paths);
Chandler Carruthd0b93d62011-11-06 23:09:05 +00004230
Chandler Carruthb427c562013-06-22 11:35:51 +00004231 // Try walking via the GCC triple path in case of biarch or multiarch GCC
Chandler Carruthd0b93d62011-11-06 23:09:05 +00004232 // installations with strange symlinks.
Rafael Espindolab6250162013-10-25 17:06:04 +00004233 if (GCCInstallation.isValid()) {
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004234 addPathIfExists(D,
4235 SysRoot + "/usr/lib/" + GCCInstallation.getTriple().str() +
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004236 "/../../" + OSLibDir,
4237 Paths);
Rafael Espindola30490212011-06-03 15:39:42 +00004238
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004239 // Add the 'other' biarch variant path
4240 Multilib BiarchSibling;
4241 if (GCCInstallation.getBiarchSibling(BiarchSibling)) {
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004242 addPathIfExists(D, GCCInstallation.getInstallPath() +
4243 BiarchSibling.gccSuffix(),
4244 Paths);
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004245 }
Chandler Carruth69a125b2012-04-06 16:32:06 +00004246
Chandler Carruth7f8042c2013-07-31 00:37:07 +00004247 // See comments above on the multilib variant for details of why this is
4248 // included even from outside the sysroot.
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004249 const std::string &LibPath = GCCInstallation.getParentLibPath();
4250 const llvm::Triple &GCCTriple = GCCInstallation.getTriple();
4251 const Multilib &Multilib = GCCInstallation.getMultilib();
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004252 addPathIfExists(D, LibPath + "/../" + GCCTriple.str() + "/lib" +
4253 Multilib.osSuffix(),
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004254 Paths);
Chandler Carruth7f8042c2013-07-31 00:37:07 +00004255
4256 // See comments above on the multilib variant for details of why this is
4257 // only included from within the sysroot.
4258 if (StringRef(LibPath).startswith(SysRoot))
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004259 addPathIfExists(D, LibPath, Paths);
Chandler Carruth413e5ac2011-10-03 05:28:29 +00004260 }
Chandler Carruth902efc62014-01-21 22:49:05 +00004261
4262 // Similar to the logic for GCC above, if we are currently running Clang
4263 // inside of the requested system root, add its parent library path to those
4264 // searched.
4265 // FIXME: It's not clear whether we should use the driver's installed
4266 // directory ('Dir' below) or the ResourceDir.
4267 if (StringRef(D.Dir).startswith(SysRoot))
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004268 addPathIfExists(D, D.Dir + "/../lib", Paths);
Chandler Carruth902efc62014-01-21 22:49:05 +00004269
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004270 addPathIfExists(D, SysRoot + "/lib", Paths);
4271 addPathIfExists(D, SysRoot + "/usr/lib", Paths);
Rafael Espindolac8f008f2010-11-07 20:14:31 +00004272}
4273
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004274bool Linux::HasNativeLLVMSupport() const { return true; }
Eli Friedman5cd659f2009-05-26 07:52:18 +00004275
Douglas Katzman95354292015-06-23 20:42:09 +00004276Tool *Linux::buildLinker() const { return new tools::gnutools::Linker(*this); }
Rafael Espindola7cf32212013-03-20 03:05:54 +00004277
4278Tool *Linux::buildAssembler() const {
Douglas Katzman95354292015-06-23 20:42:09 +00004279 return new tools::gnutools::Assembler(*this);
Rafael Espindola92b00932010-08-10 00:25:48 +00004280}
4281
Simon Atanasyana0d89572013-10-05 14:37:55 +00004282std::string Linux::computeSysRoot() const {
Simon Atanasyan08450bd2013-04-20 08:15:03 +00004283 if (!getDriver().SysRoot.empty())
4284 return getDriver().SysRoot;
4285
4286 if (!GCCInstallation.isValid() || !isMipsArch(getTriple().getArch()))
4287 return std::string();
4288
Simon Atanasyana61b7ec2013-10-10 07:57:44 +00004289 // Standalone MIPS toolchains use different names for sysroot folder
4290 // and put it into different places. Here we try to check some known
4291 // variants.
Simon Atanasyan08450bd2013-04-20 08:15:03 +00004292
Simon Atanasyana61b7ec2013-10-10 07:57:44 +00004293 const StringRef InstallDir = GCCInstallation.getInstallPath();
4294 const StringRef TripleStr = GCCInstallation.getTriple().str();
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004295 const Multilib &Multilib = GCCInstallation.getMultilib();
Simon Atanasyana61b7ec2013-10-10 07:57:44 +00004296
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004297 std::string Path =
4298 (InstallDir + "/../../../../" + TripleStr + "/libc" + Multilib.osSuffix())
4299 .str();
Simon Atanasyana61b7ec2013-10-10 07:57:44 +00004300
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004301 if (getVFS().exists(Path))
Simon Atanasyana61b7ec2013-10-10 07:57:44 +00004302 return Path;
4303
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004304 Path = (InstallDir + "/../../../../sysroot" + Multilib.osSuffix()).str();
Simon Atanasyana61b7ec2013-10-10 07:57:44 +00004305
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004306 if (getVFS().exists(Path))
Simon Atanasyana61b7ec2013-10-10 07:57:44 +00004307 return Path;
4308
4309 return std::string();
Simon Atanasyan08450bd2013-04-20 08:15:03 +00004310}
4311
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004312std::string Linux::getDynamicLinker(const ArgList &Args) const {
4313 const llvm::Triple::ArchType Arch = getArch();
4314 const llvm::Triple &Triple = getTriple();
4315
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004316 const enum Distro Distro = DetectDistro(getDriver(), Arch);
4317
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004318 if (Triple.isAndroid())
4319 return Triple.isArch64Bit() ? "/system/bin/linker64" : "/system/bin/linker";
Diana Picus86db9e72016-08-08 08:27:36 +00004320
4321 if (Triple.isMusl()) {
Rafael Espindola0fa66802016-06-24 21:35:06 +00004322 std::string ArchName;
Diana Picus86db9e72016-08-08 08:27:36 +00004323 bool IsArm = false;
4324
Rafael Espindola0fa66802016-06-24 21:35:06 +00004325 switch (Arch) {
Diana Picus86db9e72016-08-08 08:27:36 +00004326 case llvm::Triple::arm:
Rafael Espindola0fa66802016-06-24 21:35:06 +00004327 case llvm::Triple::thumb:
4328 ArchName = "arm";
Diana Picus86db9e72016-08-08 08:27:36 +00004329 IsArm = true;
Rafael Espindola0fa66802016-06-24 21:35:06 +00004330 break;
Diana Picus86db9e72016-08-08 08:27:36 +00004331 case llvm::Triple::armeb:
Rafael Espindola0fa66802016-06-24 21:35:06 +00004332 case llvm::Triple::thumbeb:
4333 ArchName = "armeb";
Diana Picus86db9e72016-08-08 08:27:36 +00004334 IsArm = true;
Rafael Espindola0fa66802016-06-24 21:35:06 +00004335 break;
4336 default:
4337 ArchName = Triple.getArchName().str();
4338 }
Diana Picus86db9e72016-08-08 08:27:36 +00004339 if (IsArm &&
4340 (Triple.getEnvironment() == llvm::Triple::MuslEABIHF ||
4341 tools::arm::getARMFloatABI(*this, Args) == tools::arm::FloatABI::Hard))
Rafael Espindola0fa66802016-06-24 21:35:06 +00004342 ArchName += "hf";
4343
4344 return "/lib/ld-musl-" + ArchName + ".so.1";
4345 }
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004346
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004347 std::string LibDir;
4348 std::string Loader;
4349
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004350 switch (Arch) {
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004351 default:
4352 llvm_unreachable("unsupported architecture");
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004353
4354 case llvm::Triple::aarch64:
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004355 LibDir = "lib";
4356 Loader = "ld-linux-aarch64.so.1";
4357 break;
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004358 case llvm::Triple::aarch64_be:
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004359 LibDir = "lib";
4360 Loader = "ld-linux-aarch64_be.so.1";
4361 break;
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004362 case llvm::Triple::arm:
4363 case llvm::Triple::thumb:
4364 case llvm::Triple::armeb:
4365 case llvm::Triple::thumbeb: {
Vedant Kumar5fb00e42016-07-27 23:01:55 +00004366 const bool HF =
4367 Triple.getEnvironment() == llvm::Triple::GNUEABIHF ||
4368 tools::arm::getARMFloatABI(*this, Args) == tools::arm::FloatABI::Hard;
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004369
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004370 LibDir = "lib";
4371 Loader = HF ? "ld-linux-armhf.so.3" : "ld-linux.so.3";
4372 break;
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004373 }
4374 case llvm::Triple::mips:
4375 case llvm::Triple::mipsel:
4376 case llvm::Triple::mips64:
4377 case llvm::Triple::mips64el: {
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004378 bool LE = (Triple.getArch() == llvm::Triple::mipsel) ||
4379 (Triple.getArch() == llvm::Triple::mips64el);
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004380 bool IsNaN2008 = tools::mips::isNaN2008(Args, Triple);
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004381
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004382 LibDir = "lib" + tools::mips::getMipsABILibSuffix(Args, Triple);
4383
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004384 if (tools::mips::isUCLibc(Args))
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004385 Loader = IsNaN2008 ? "ld-uClibc-mipsn8.so.0" : "ld-uClibc.so.0";
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004386 else if (!Triple.hasEnvironment() &&
4387 Triple.getVendor() == llvm::Triple::VendorType::MipsTechnologies)
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004388 Loader = LE ? "ld-musl-mipsel.so.1" : "ld-musl-mips.so.1";
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004389 else
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004390 Loader = IsNaN2008 ? "ld-linux-mipsn8.so.1" : "ld.so.1";
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004391
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004392 break;
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004393 }
4394 case llvm::Triple::ppc:
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004395 LibDir = "lib";
4396 Loader = "ld.so.1";
4397 break;
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004398 case llvm::Triple::ppc64:
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004399 LibDir = "lib64";
4400 Loader =
4401 (tools::ppc::hasPPCAbiArg(Args, "elfv2")) ? "ld64.so.2" : "ld64.so.1";
4402 break;
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004403 case llvm::Triple::ppc64le:
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004404 LibDir = "lib64";
4405 Loader =
4406 (tools::ppc::hasPPCAbiArg(Args, "elfv1")) ? "ld64.so.1" : "ld64.so.2";
4407 break;
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004408 case llvm::Triple::sparc:
4409 case llvm::Triple::sparcel:
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004410 LibDir = "lib";
4411 Loader = "ld-linux.so.2";
4412 break;
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004413 case llvm::Triple::sparcv9:
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004414 LibDir = "lib64";
4415 Loader = "ld-linux.so.2";
4416 break;
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004417 case llvm::Triple::systemz:
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004418 LibDir = "lib";
4419 Loader = "ld64.so.1";
4420 break;
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004421 case llvm::Triple::x86:
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004422 LibDir = "lib";
4423 Loader = "ld-linux.so.2";
4424 break;
4425 case llvm::Triple::x86_64: {
4426 bool X32 = Triple.getEnvironment() == llvm::Triple::GNUX32;
4427
4428 LibDir = X32 ? "libx32" : "lib64";
4429 Loader = X32 ? "ld-linux-x32.so.2" : "ld-linux-x86-64.so.2";
4430 break;
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004431 }
Saleem Abdulrasool6f8442b2016-05-23 02:17:28 +00004432 }
4433
4434 if (Distro == Exherbo && (Triple.getVendor() == llvm::Triple::UnknownVendor ||
4435 Triple.getVendor() == llvm::Triple::PC))
4436 return "/usr/" + Triple.str() + "/lib/" + Loader;
4437 return "/" + LibDir + "/" + Loader;
Saleem Abdulrasool783fc632016-05-22 03:12:19 +00004438}
4439
Chandler Carrutha796f532011-11-05 20:17:13 +00004440void Linux::AddClangSystemIncludeArgs(const ArgList &DriverArgs,
4441 ArgStringList &CC1Args) const {
4442 const Driver &D = getDriver();
Simon Atanasyana0d89572013-10-05 14:37:55 +00004443 std::string SysRoot = computeSysRoot();
Chandler Carrutha796f532011-11-05 20:17:13 +00004444
4445 if (DriverArgs.hasArg(options::OPT_nostdinc))
4446 return;
4447
4448 if (!DriverArgs.hasArg(options::OPT_nostdlibinc))
Simon Atanasyan08450bd2013-04-20 08:15:03 +00004449 addSystemInclude(DriverArgs, CC1Args, SysRoot + "/usr/local/include");
Chandler Carrutha796f532011-11-05 20:17:13 +00004450
4451 if (!DriverArgs.hasArg(options::OPT_nobuiltininc)) {
Rafael Espindola358256c2013-06-26 02:13:00 +00004452 SmallString<128> P(D.ResourceDir);
4453 llvm::sys::path::append(P, "include");
Yaron Keren92e1b622015-03-18 10:17:07 +00004454 addSystemInclude(DriverArgs, CC1Args, P);
Chandler Carrutha796f532011-11-05 20:17:13 +00004455 }
4456
4457 if (DriverArgs.hasArg(options::OPT_nostdlibinc))
4458 return;
4459
4460 // Check for configure-time C include directories.
4461 StringRef CIncludeDirs(C_INCLUDE_DIRS);
4462 if (CIncludeDirs != "") {
4463 SmallVector<StringRef, 5> dirs;
4464 CIncludeDirs.split(dirs, ":");
Simon Atanasyan6f657c42014-05-08 19:32:46 +00004465 for (StringRef dir : dirs) {
Benjamin Kramer33cd6dc2015-02-18 18:45:54 +00004466 StringRef Prefix =
4467 llvm::sys::path::is_absolute(dir) ? StringRef(SysRoot) : "";
Simon Atanasyan6f657c42014-05-08 19:32:46 +00004468 addExternCSystemInclude(DriverArgs, CC1Args, Prefix + dir);
Chandler Carrutha796f532011-11-05 20:17:13 +00004469 }
4470 return;
4471 }
4472
4473 // Lacking those, try to detect the correct set of system includes for the
4474 // target triple.
4475
Simon Atanasyan9e49e142014-08-06 05:44:47 +00004476 // Add include directories specific to the selected multilib set and multilib.
4477 if (GCCInstallation.isValid()) {
Benjamin Kramerac75baa2015-03-22 15:56:12 +00004478 const auto &Callback = Multilibs.includeDirsCallback();
Simon Atanasyan9e49e142014-08-06 05:44:47 +00004479 if (Callback) {
Simon Atanasyana45502d2016-05-19 15:07:21 +00004480 for (const auto &Path : Callback(GCCInstallation.getMultilib()))
4481 addExternCSystemIncludeIfExists(
4482 DriverArgs, CC1Args, GCCInstallation.getInstallPath() + Path);
Simon Atanasyan9e49e142014-08-06 05:44:47 +00004483 }
Simon Atanasyan08450bd2013-04-20 08:15:03 +00004484 }
4485
Chandler Carruth5b77c6c2011-11-06 08:21:07 +00004486 // Implement generic Debian multiarch support.
4487 const StringRef X86_64MultiarchIncludeDirs[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004488 "/usr/include/x86_64-linux-gnu",
Chandler Carruth5b77c6c2011-11-06 08:21:07 +00004489
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004490 // FIXME: These are older forms of multiarch. It's not clear that they're
4491 // in use in any released version of Debian, so we should consider
4492 // removing them.
4493 "/usr/include/i686-linux-gnu/64", "/usr/include/i486-linux-gnu/64"};
Chandler Carruth5b77c6c2011-11-06 08:21:07 +00004494 const StringRef X86MultiarchIncludeDirs[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004495 "/usr/include/i386-linux-gnu",
Chandler Carruth5b77c6c2011-11-06 08:21:07 +00004496
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004497 // FIXME: These are older forms of multiarch. It's not clear that they're
4498 // in use in any released version of Debian, so we should consider
4499 // removing them.
4500 "/usr/include/x86_64-linux-gnu/32", "/usr/include/i686-linux-gnu",
4501 "/usr/include/i486-linux-gnu"};
Tim Northover9bb857a2013-01-31 12:13:10 +00004502 const StringRef AArch64MultiarchIncludeDirs[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004503 "/usr/include/aarch64-linux-gnu"};
Chandler Carruth5b77c6c2011-11-06 08:21:07 +00004504 const StringRef ARMMultiarchIncludeDirs[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004505 "/usr/include/arm-linux-gnueabi"};
Jiangning Liu61b06cb2012-07-31 08:06:29 +00004506 const StringRef ARMHFMultiarchIncludeDirs[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004507 "/usr/include/arm-linux-gnueabihf"};
Saleem Abdulrasool20f733a2015-12-11 06:20:59 +00004508 const StringRef ARMEBMultiarchIncludeDirs[] = {
4509 "/usr/include/armeb-linux-gnueabi"};
4510 const StringRef ARMEBHFMultiarchIncludeDirs[] = {
4511 "/usr/include/armeb-linux-gnueabihf"};
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004512 const StringRef MIPSMultiarchIncludeDirs[] = {"/usr/include/mips-linux-gnu"};
Eli Friedman7771c832011-11-11 03:05:19 +00004513 const StringRef MIPSELMultiarchIncludeDirs[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004514 "/usr/include/mipsel-linux-gnu"};
Simon Atanasyan3a46afa2014-06-24 19:00:12 +00004515 const StringRef MIPS64MultiarchIncludeDirs[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004516 "/usr/include/mips64-linux-gnu", "/usr/include/mips64-linux-gnuabi64"};
Simon Atanasyan3a46afa2014-06-24 19:00:12 +00004517 const StringRef MIPS64ELMultiarchIncludeDirs[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004518 "/usr/include/mips64el-linux-gnu",
4519 "/usr/include/mips64el-linux-gnuabi64"};
Chandler Carruth2e9d7312012-02-26 09:21:43 +00004520 const StringRef PPCMultiarchIncludeDirs[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004521 "/usr/include/powerpc-linux-gnu"};
Chandler Carruth2e9d7312012-02-26 09:21:43 +00004522 const StringRef PPC64MultiarchIncludeDirs[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004523 "/usr/include/powerpc64-linux-gnu"};
Ulrich Weiganda8331b92014-06-20 13:41:24 +00004524 const StringRef PPC64LEMultiarchIncludeDirs[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004525 "/usr/include/powerpc64le-linux-gnu"};
James Y Knight09677ad2015-06-05 13:44:43 +00004526 const StringRef SparcMultiarchIncludeDirs[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004527 "/usr/include/sparc-linux-gnu"};
James Y Knight09677ad2015-06-05 13:44:43 +00004528 const StringRef Sparc64MultiarchIncludeDirs[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004529 "/usr/include/sparc64-linux-gnu"};
Sylvestre Ledruc0babf22015-08-28 12:26:09 +00004530 const StringRef SYSTEMZMultiarchIncludeDirs[] = {
4531 "/usr/include/s390x-linux-gnu"};
Chandler Carruth5b77c6c2011-11-06 08:21:07 +00004532 ArrayRef<StringRef> MultiarchIncludeDirs;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004533 switch (getTriple().getArch()) {
4534 case llvm::Triple::x86_64:
Chandler Carruth5b77c6c2011-11-06 08:21:07 +00004535 MultiarchIncludeDirs = X86_64MultiarchIncludeDirs;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004536 break;
4537 case llvm::Triple::x86:
Chandler Carruth5b77c6c2011-11-06 08:21:07 +00004538 MultiarchIncludeDirs = X86MultiarchIncludeDirs;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004539 break;
4540 case llvm::Triple::aarch64:
4541 case llvm::Triple::aarch64_be:
Tim Northover9bb857a2013-01-31 12:13:10 +00004542 MultiarchIncludeDirs = AArch64MultiarchIncludeDirs;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004543 break;
4544 case llvm::Triple::arm:
Saleem Abdulrasool20f733a2015-12-11 06:20:59 +00004545 case llvm::Triple::thumb:
Jiangning Liu61b06cb2012-07-31 08:06:29 +00004546 if (getTriple().getEnvironment() == llvm::Triple::GNUEABIHF)
4547 MultiarchIncludeDirs = ARMHFMultiarchIncludeDirs;
4548 else
4549 MultiarchIncludeDirs = ARMMultiarchIncludeDirs;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004550 break;
Saleem Abdulrasool20f733a2015-12-11 06:20:59 +00004551 case llvm::Triple::armeb:
4552 case llvm::Triple::thumbeb:
4553 if (getTriple().getEnvironment() == llvm::Triple::GNUEABIHF)
4554 MultiarchIncludeDirs = ARMEBHFMultiarchIncludeDirs;
4555 else
4556 MultiarchIncludeDirs = ARMEBMultiarchIncludeDirs;
4557 break;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004558 case llvm::Triple::mips:
Eli Friedman7771c832011-11-11 03:05:19 +00004559 MultiarchIncludeDirs = MIPSMultiarchIncludeDirs;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004560 break;
4561 case llvm::Triple::mipsel:
Eli Friedman7771c832011-11-11 03:05:19 +00004562 MultiarchIncludeDirs = MIPSELMultiarchIncludeDirs;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004563 break;
4564 case llvm::Triple::mips64:
Simon Atanasyan3a46afa2014-06-24 19:00:12 +00004565 MultiarchIncludeDirs = MIPS64MultiarchIncludeDirs;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004566 break;
4567 case llvm::Triple::mips64el:
Simon Atanasyan3a46afa2014-06-24 19:00:12 +00004568 MultiarchIncludeDirs = MIPS64ELMultiarchIncludeDirs;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004569 break;
4570 case llvm::Triple::ppc:
Chandler Carruth2e9d7312012-02-26 09:21:43 +00004571 MultiarchIncludeDirs = PPCMultiarchIncludeDirs;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004572 break;
4573 case llvm::Triple::ppc64:
Chandler Carruth2e9d7312012-02-26 09:21:43 +00004574 MultiarchIncludeDirs = PPC64MultiarchIncludeDirs;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004575 break;
4576 case llvm::Triple::ppc64le:
Ulrich Weiganda8331b92014-06-20 13:41:24 +00004577 MultiarchIncludeDirs = PPC64LEMultiarchIncludeDirs;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004578 break;
4579 case llvm::Triple::sparc:
James Y Knight09677ad2015-06-05 13:44:43 +00004580 MultiarchIncludeDirs = SparcMultiarchIncludeDirs;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004581 break;
4582 case llvm::Triple::sparcv9:
James Y Knight09677ad2015-06-05 13:44:43 +00004583 MultiarchIncludeDirs = Sparc64MultiarchIncludeDirs;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004584 break;
Sylvestre Ledruc0babf22015-08-28 12:26:09 +00004585 case llvm::Triple::systemz:
4586 MultiarchIncludeDirs = SYSTEMZMultiarchIncludeDirs;
4587 break;
Douglas Katzman7e37afb2015-06-23 03:02:39 +00004588 default:
4589 break;
Chandler Carruth5b77c6c2011-11-06 08:21:07 +00004590 }
Simon Atanasyan6f657c42014-05-08 19:32:46 +00004591 for (StringRef Dir : MultiarchIncludeDirs) {
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004592 if (D.getVFS().exists(SysRoot + Dir)) {
Simon Atanasyan6f657c42014-05-08 19:32:46 +00004593 addExternCSystemInclude(DriverArgs, CC1Args, SysRoot + Dir);
Chandler Carruth5b77c6c2011-11-06 08:21:07 +00004594 break;
4595 }
Chandler Carrutha796f532011-11-05 20:17:13 +00004596 }
4597
4598 if (getTriple().getOS() == llvm::Triple::RTEMS)
4599 return;
4600
Chandler Carruth475ab6a2011-11-08 17:19:47 +00004601 // Add an include of '/include' directly. This isn't provided by default by
4602 // system GCCs, but is often used with cross-compiling GCCs, and harmless to
4603 // add even when Clang is acting as-if it were a system compiler.
Simon Atanasyan08450bd2013-04-20 08:15:03 +00004604 addExternCSystemInclude(DriverArgs, CC1Args, SysRoot + "/include");
Chandler Carruth475ab6a2011-11-08 17:19:47 +00004605
Simon Atanasyan08450bd2013-04-20 08:15:03 +00004606 addExternCSystemInclude(DriverArgs, CC1Args, SysRoot + "/usr/include");
Chandler Carrutha796f532011-11-05 20:17:13 +00004607}
4608
Evgeniy Stepanov65bc2b12015-11-09 21:10:54 +00004609static std::string DetectLibcxxIncludePath(StringRef base) {
4610 std::error_code EC;
4611 int MaxVersion = 0;
4612 std::string MaxVersionString = "";
4613 for (llvm::sys::fs::directory_iterator LI(base, EC), LE; !EC && LI != LE;
4614 LI = LI.increment(EC)) {
4615 StringRef VersionText = llvm::sys::path::filename(LI->path());
4616 int Version;
4617 if (VersionText[0] == 'v' &&
4618 !VersionText.slice(1, StringRef::npos).getAsInteger(10, Version)) {
4619 if (Version > MaxVersion) {
4620 MaxVersion = Version;
4621 MaxVersionString = VersionText;
4622 }
4623 }
4624 }
4625 return MaxVersion ? (base + "/" + MaxVersionString).str() : "";
4626}
4627
Chandler Carrutha796f532011-11-05 20:17:13 +00004628void Linux::AddClangCXXStdlibIncludeArgs(const ArgList &DriverArgs,
4629 ArgStringList &CC1Args) const {
4630 if (DriverArgs.hasArg(options::OPT_nostdlibinc) ||
4631 DriverArgs.hasArg(options::OPT_nostdincxx))
4632 return;
4633
Chandler Carruthf4701732011-11-07 09:01:17 +00004634 // Check if libc++ has been enabled and provide its include paths if so.
4635 if (GetCXXStdlibType(DriverArgs) == ToolChain::CST_Libcxx) {
Chandler Carruth5a3d8982014-01-20 09:42:24 +00004636 const std::string LibCXXIncludePathCandidates[] = {
Evgeniy Stepanov65bc2b12015-11-09 21:10:54 +00004637 DetectLibcxxIncludePath(getDriver().Dir + "/../include/c++"),
Yaron Keren5439b642016-05-17 19:01:16 +00004638 // If this is a development, non-installed, clang, libcxx will
4639 // not be found at ../include/c++ but it likely to be found at
4640 // one of the following two locations:
4641 DetectLibcxxIncludePath(getDriver().SysRoot + "/usr/local/include/c++"),
4642 DetectLibcxxIncludePath(getDriver().SysRoot + "/usr/include/c++") };
Simon Atanasyan6f657c42014-05-08 19:32:46 +00004643 for (const auto &IncludePath : LibCXXIncludePathCandidates) {
Evgeniy Stepanov65bc2b12015-11-09 21:10:54 +00004644 if (IncludePath.empty() || !getVFS().exists(IncludePath))
Chandler Carruth5a3d8982014-01-20 09:42:24 +00004645 continue;
4646 // Add the first candidate that exists.
Simon Atanasyan6f657c42014-05-08 19:32:46 +00004647 addSystemInclude(DriverArgs, CC1Args, IncludePath);
Chandler Carruth5a3d8982014-01-20 09:42:24 +00004648 break;
4649 }
Chandler Carruthf4701732011-11-07 09:01:17 +00004650 return;
4651 }
4652
Chandler Carrutha1f1fd32012-01-25 08:04:13 +00004653 // We need a detected GCC installation on Linux to provide libstdc++'s
4654 // headers. We handled the libc++ case above.
4655 if (!GCCInstallation.isValid())
4656 return;
Chandler Carrutha796f532011-11-05 20:17:13 +00004657
Chandler Carruthf5d4df92011-11-06 10:31:01 +00004658 // By default, look for the C++ headers in an include directory adjacent to
4659 // the lib directory of the GCC installation. Note that this is expect to be
4660 // equivalent to '/usr/include/c++/X.Y' in almost all cases.
4661 StringRef LibDir = GCCInstallation.getParentLibPath();
4662 StringRef InstallDir = GCCInstallation.getInstallPath();
Evgeniy Stepanov763671e2012-09-03 09:05:50 +00004663 StringRef TripleStr = GCCInstallation.getTriple().str();
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004664 const Multilib &Multilib = GCCInstallation.getMultilib();
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004665 const std::string GCCMultiarchTriple = getMultiarchTriple(
4666 getDriver(), GCCInstallation.getTriple(), getDriver().SysRoot);
Chandler Carruthc44f4d42014-08-27 08:41:41 +00004667 const std::string TargetMultiarchTriple =
Benjamin Kramerd45b2052015-10-07 15:48:01 +00004668 getMultiarchTriple(getDriver(), getTriple(), getDriver().SysRoot);
Chandler Carruth1f2b2f82013-08-26 08:59:53 +00004669 const GCCVersion &Version = GCCInstallation.getVersion();
Evgeniy Stepanov763671e2012-09-03 09:05:50 +00004670
Chandler Carruthc44f4d42014-08-27 08:41:41 +00004671 // The primary search for libstdc++ supports multiarch variants.
Chandler Carruth8677d922013-10-29 08:53:03 +00004672 if (addLibStdCXXIncludePaths(LibDir.str() + "/../include",
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004673 "/c++/" + Version.Text, TripleStr,
4674 GCCMultiarchTriple, TargetMultiarchTriple,
Jonathan Roelofs2cea1be2014-02-12 03:21:20 +00004675 Multilib.includeSuffix(), DriverArgs, CC1Args))
Dmitri Gribenko15225ae2013-03-06 17:14:05 +00004676 return;
4677
Chandler Carruthc44f4d42014-08-27 08:41:41 +00004678 // Otherwise, fall back on a bunch of options which don't use multiarch
4679 // layouts for simplicity.
Chandler Carruth5a3d8982014-01-20 09:42:24 +00004680 const std::string LibStdCXXIncludePathCandidates[] = {
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004681 // Gentoo is weird and places its headers inside the GCC install,
4682 // so if the first attempt to find the headers fails, try these patterns.
Chandler Carruth81296fb2016-05-08 07:59:56 +00004683 InstallDir.str() + "/include/g++-v" + Version.Text,
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004684 InstallDir.str() + "/include/g++-v" + Version.MajorStr + "." +
4685 Version.MinorStr,
4686 InstallDir.str() + "/include/g++-v" + Version.MajorStr,
4687 // Android standalone toolchain has C++ headers in yet another place.
4688 LibDir.str() + "/../" + TripleStr.str() + "/include/c++/" + Version.Text,
4689 // Freescale SDK C++ headers are directly in <sysroot>/usr/include/c++,
4690 // without a subdirectory corresponding to the gcc version.
4691 LibDir.str() + "/../include/c++",
Evgeniy Stepanov763671e2012-09-03 09:05:50 +00004692 };
4693
Simon Atanasyan6f657c42014-05-08 19:32:46 +00004694 for (const auto &IncludePath : LibStdCXXIncludePathCandidates) {
Chandler Carruthc44f4d42014-08-27 08:41:41 +00004695 if (addLibStdCXXIncludePaths(IncludePath, /*Suffix*/ "", TripleStr,
4696 /*GCCMultiarchTriple*/ "",
4697 /*TargetMultiarchTriple*/ "",
4698 Multilib.includeSuffix(), DriverArgs, CC1Args))
Evgeniy Stepanov763671e2012-09-03 09:05:50 +00004699 break;
Chandler Carruthf5d4df92011-11-06 10:31:01 +00004700 }
Chandler Carrutha796f532011-11-05 20:17:13 +00004701}
4702
Artem Belevichfa11ab52015-11-17 22:28:46 +00004703void Linux::AddCudaIncludeArgs(const ArgList &DriverArgs,
4704 ArgStringList &CC1Args) const {
Justin Lebar49ec1462016-10-11 17:36:03 +00004705 if (!DriverArgs.hasArg(options::OPT_nobuiltininc)) {
4706 // Add cuda_wrappers/* to our system include path. This lets us wrap
4707 // standard library headers.
4708 SmallString<128> P(getDriver().ResourceDir);
4709 llvm::sys::path::append(P, "include");
4710 llvm::sys::path::append(P, "cuda_wrappers");
4711 addSystemInclude(DriverArgs, CC1Args, P);
4712 }
4713
Artem Belevichfa11ab52015-11-17 22:28:46 +00004714 if (DriverArgs.hasArg(options::OPT_nocudainc))
4715 return;
4716
Justin Lebar423019d2016-04-16 00:11:11 +00004717 if (!CudaInstallation.isValid()) {
4718 getDriver().Diag(diag::err_drv_no_cuda_installation);
4719 return;
Artem Belevich86017332015-11-17 22:28:55 +00004720 }
Justin Lebar423019d2016-04-16 00:11:11 +00004721
4722 addSystemInclude(DriverArgs, CC1Args, CudaInstallation.getIncludePath());
4723 CC1Args.push_back("-include");
4724 CC1Args.push_back("__clang_cuda_runtime_wrapper.h");
Artem Belevichfa11ab52015-11-17 22:28:46 +00004725}
4726
Andrey Turetskiy4798eb62016-06-16 10:36:09 +00004727void Linux::AddIAMCUIncludeArgs(const ArgList &DriverArgs,
4728 ArgStringList &CC1Args) const {
4729 if (GCCInstallation.isValid()) {
4730 CC1Args.push_back("-isystem");
4731 CC1Args.push_back(DriverArgs.MakeArgString(
4732 GCCInstallation.getParentLibPath() + "/../" +
4733 GCCInstallation.getTriple().str() + "/include"));
4734 }
4735}
4736
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004737bool Linux::isPIEDefault() const { return getSanitizerArgs().requiresPIE(); }
Peter Collingbourne54d770c2013-04-09 04:35:11 +00004738
Alexey Samsonov7f2a0d22015-06-19 21:36:47 +00004739SanitizerMask Linux::getSupportedSanitizers() const {
4740 const bool IsX86 = getTriple().getArch() == llvm::Triple::x86;
4741 const bool IsX86_64 = getTriple().getArch() == llvm::Triple::x86_64;
4742 const bool IsMIPS64 = getTriple().getArch() == llvm::Triple::mips64 ||
4743 getTriple().getArch() == llvm::Triple::mips64el;
Jay Foade967dd02015-06-25 10:35:19 +00004744 const bool IsPowerPC64 = getTriple().getArch() == llvm::Triple::ppc64 ||
4745 getTriple().getArch() == llvm::Triple::ppc64le;
Adhemerval Zanella76aee672015-07-30 20:50:39 +00004746 const bool IsAArch64 = getTriple().getArch() == llvm::Triple::aarch64 ||
4747 getTriple().getArch() == llvm::Triple::aarch64_be;
Alexey Samsonov7f2a0d22015-06-19 21:36:47 +00004748 SanitizerMask Res = ToolChain::getSupportedSanitizers();
4749 Res |= SanitizerKind::Address;
4750 Res |= SanitizerKind::KernelAddress;
4751 Res |= SanitizerKind::Vptr;
Evgeniy Stepanov299238a2015-09-24 17:22:46 +00004752 Res |= SanitizerKind::SafeStack;
Adhemerval Zanella76aee672015-07-30 20:50:39 +00004753 if (IsX86_64 || IsMIPS64 || IsAArch64)
Alexey Samsonov7f2a0d22015-06-19 21:36:47 +00004754 Res |= SanitizerKind::DataFlow;
Adhemerval Zanellabffb20d2015-10-05 19:16:42 +00004755 if (IsX86_64 || IsMIPS64 || IsAArch64)
Alexey Samsonov7f2a0d22015-06-19 21:36:47 +00004756 Res |= SanitizerKind::Leak;
Bill Schmidt4b8841a2015-12-08 22:48:02 +00004757 if (IsX86_64 || IsMIPS64 || IsAArch64 || IsPowerPC64)
Alexey Samsonov7f2a0d22015-06-19 21:36:47 +00004758 Res |= SanitizerKind::Thread;
Adhemerval Zanella567b9262015-09-16 15:11:21 +00004759 if (IsX86_64 || IsMIPS64 || IsPowerPC64 || IsAArch64)
Jay Foade967dd02015-06-25 10:35:19 +00004760 Res |= SanitizerKind::Memory;
Sagar Thakurc9113e42016-09-07 12:23:15 +00004761 if (IsX86_64 || IsMIPS64)
Derek Bruening256c2e12016-04-21 21:32:04 +00004762 Res |= SanitizerKind::Efficiency;
Alexey Samsonov7f2a0d22015-06-19 21:36:47 +00004763 if (IsX86 || IsX86_64) {
4764 Res |= SanitizerKind::Function;
Alexey Samsonov7f2a0d22015-06-19 21:36:47 +00004765 }
4766 return Res;
4767}
4768
Vedant Kumar5fb00e42016-07-27 23:01:55 +00004769void Linux::addProfileRTLibs(const llvm::opt::ArgList &Args,
Xinliang David Li170cd102015-10-27 05:15:35 +00004770 llvm::opt::ArgStringList &CmdArgs) const {
Vedant Kumar5fb00e42016-07-27 23:01:55 +00004771 if (!needsProfileRT(Args)) return;
Xinliang David Li170cd102015-10-27 05:15:35 +00004772
4773 // Add linker option -u__llvm_runtime_variable to cause runtime
4774 // initialization module to be linked in.
4775 if (!Args.hasArg(options::OPT_coverage))
4776 CmdArgs.push_back(Args.MakeArgString(
4777 Twine("-u", llvm::getInstrProfRuntimeHookVarName())));
Vedant Kumar5fb00e42016-07-27 23:01:55 +00004778 ToolChain::addProfileRTLibs(Args, CmdArgs);
Xinliang David Li170cd102015-10-27 05:15:35 +00004779}
4780
Petr Hosek62e1d232016-10-06 06:08:09 +00004781/// Fuchsia - Fuchsia tool chain which can call as(1) and ld(1) directly.
4782
4783Fuchsia::Fuchsia(const Driver &D, const llvm::Triple &Triple,
4784 const ArgList &Args)
4785 : Generic_ELF(D, Triple, Args) {
4786
4787 getFilePaths().push_back(D.SysRoot + "/lib");
4788 getFilePaths().push_back(D.ResourceDir + "/lib/fuchsia");
4789
4790 // Use LLD by default.
4791 DefaultLinker = "lld";
4792}
4793
4794Tool *Fuchsia::buildAssembler() const {
4795 return new tools::gnutools::Assembler(*this);
4796}
4797
4798Tool *Fuchsia::buildLinker() const {
4799 return new tools::fuchsia::Linker(*this);
4800}
4801
4802ToolChain::RuntimeLibType Fuchsia::GetRuntimeLibType(
4803 const ArgList &Args) const {
4804 if (Arg *A = Args.getLastArg(options::OPT_rtlib_EQ)) {
4805 StringRef Value = A->getValue();
4806 if (Value != "compiler-rt")
4807 getDriver().Diag(diag::err_drv_invalid_rtlib_name)
4808 << A->getAsString(Args);
4809 }
4810
4811 return ToolChain::RLT_CompilerRT;
4812}
4813
4814ToolChain::CXXStdlibType
4815Fuchsia::GetCXXStdlibType(const ArgList &Args) const {
4816 if (Arg *A = Args.getLastArg(options::OPT_stdlib_EQ)) {
4817 StringRef Value = A->getValue();
4818 if (Value != "libc++")
4819 getDriver().Diag(diag::err_drv_invalid_stdlib_name)
4820 << A->getAsString(Args);
4821 }
4822
4823 return ToolChain::CST_Libcxx;
4824}
4825
4826void Fuchsia::addClangTargetOptions(const ArgList &DriverArgs,
4827 ArgStringList &CC1Args) const {
4828 if (DriverArgs.hasFlag(options::OPT_fuse_init_array,
4829 options::OPT_fno_use_init_array, true))
4830 CC1Args.push_back("-fuse-init-array");
4831}
4832
4833void Fuchsia::AddClangSystemIncludeArgs(const ArgList &DriverArgs,
4834 ArgStringList &CC1Args) const {
4835 const Driver &D = getDriver();
4836
4837 if (DriverArgs.hasArg(options::OPT_nostdinc))
4838 return;
4839
4840 if (!DriverArgs.hasArg(options::OPT_nobuiltininc)) {
4841 SmallString<128> P(D.ResourceDir);
4842 llvm::sys::path::append(P, "include");
4843 addSystemInclude(DriverArgs, CC1Args, P);
4844 }
4845
4846 if (DriverArgs.hasArg(options::OPT_nostdlibinc))
4847 return;
4848
4849 // Check for configure-time C include directories.
4850 StringRef CIncludeDirs(C_INCLUDE_DIRS);
4851 if (CIncludeDirs != "") {
4852 SmallVector<StringRef, 5> dirs;
4853 CIncludeDirs.split(dirs, ":");
4854 for (StringRef dir : dirs) {
4855 StringRef Prefix =
4856 llvm::sys::path::is_absolute(dir) ? StringRef(D.SysRoot) : "";
4857 addExternCSystemInclude(DriverArgs, CC1Args, Prefix + dir);
4858 }
4859 return;
4860 }
4861
4862 addExternCSystemInclude(DriverArgs, CC1Args, D.SysRoot + "/include");
4863}
4864
4865void Fuchsia::AddClangCXXStdlibIncludeArgs(const ArgList &DriverArgs,
4866 ArgStringList &CC1Args) const {
4867 if (DriverArgs.hasArg(options::OPT_nostdlibinc) ||
4868 DriverArgs.hasArg(options::OPT_nostdincxx))
4869 return;
4870
4871 addSystemInclude(DriverArgs, CC1Args,
4872 getDriver().SysRoot + "/include/c++/v1");
4873}
4874
4875void Fuchsia::AddCXXStdlibLibArgs(const ArgList &Args,
4876 ArgStringList &CmdArgs) const {
4877 (void) GetCXXStdlibType(Args);
4878 CmdArgs.push_back("-lc++");
4879 CmdArgs.push_back("-lc++abi");
4880 CmdArgs.push_back("-lunwind");
4881}
4882
Daniel Dunbarcc912342009-05-02 18:28:39 +00004883/// DragonFly - DragonFly tool chain which can call as(1) and ld(1) directly.
4884
Douglas Katzmana67e50c2015-06-26 15:47:46 +00004885DragonFly::DragonFly(const Driver &D, const llvm::Triple &Triple,
4886 const ArgList &Args)
4887 : Generic_ELF(D, Triple, Args) {
Daniel Dunbarcc912342009-05-02 18:28:39 +00004888
4889 // Path mangling to find libexec
Daniel Dunbar88979912010-08-01 22:29:51 +00004890 getProgramPaths().push_back(getDriver().getInstalledDir());
Benjamin Kramer51477bd2011-03-01 22:50:47 +00004891 if (getDriver().getInstalledDir() != getDriver().Dir)
Daniel Dunbar88979912010-08-01 22:29:51 +00004892 getProgramPaths().push_back(getDriver().Dir);
Daniel Dunbarcc912342009-05-02 18:28:39 +00004893
Daniel Dunbar083edf72009-12-21 18:54:17 +00004894 getFilePaths().push_back(getDriver().Dir + "/../lib");
Daniel Dunbarcc912342009-05-02 18:28:39 +00004895 getFilePaths().push_back("/usr/lib");
Dimitry Andricf59a2b32015-12-27 10:01:44 +00004896 getFilePaths().push_back("/usr/lib/gcc50");
Daniel Dunbarcc912342009-05-02 18:28:39 +00004897}
4898
Rafael Espindola7cf32212013-03-20 03:05:54 +00004899Tool *DragonFly::buildAssembler() const {
Douglas Katzman95354292015-06-23 20:42:09 +00004900 return new tools::dragonfly::Assembler(*this);
Rafael Espindola7cf32212013-03-20 03:05:54 +00004901}
4902
4903Tool *DragonFly::buildLinker() const {
Douglas Katzman95354292015-06-23 20:42:09 +00004904 return new tools::dragonfly::Linker(*this);
Daniel Dunbarcc912342009-05-02 18:28:39 +00004905}
Robert Lyttoncf1dd692013-10-11 10:29:40 +00004906
Justin Lebar21e5d4f2016-01-14 21:41:27 +00004907/// CUDA toolchain. Our assembler is ptxas, and our "linker" is fatbinary,
4908/// which isn't properly a linker but nonetheless performs the step of stitching
4909/// together object files from the assembler into a single blob.
Artem Belevich0ff05cd2015-07-13 23:27:56 +00004910
4911CudaToolChain::CudaToolChain(const Driver &D, const llvm::Triple &Triple,
4912 const ArgList &Args)
Justin Lebar21e5d4f2016-01-14 21:41:27 +00004913 : Linux(D, Triple, Args) {
4914 if (CudaInstallation.isValid())
4915 getProgramPaths().push_back(CudaInstallation.getBinPath());
4916}
Artem Belevich0ff05cd2015-07-13 23:27:56 +00004917
4918void
4919CudaToolChain::addClangTargetOptions(const llvm::opt::ArgList &DriverArgs,
4920 llvm::opt::ArgStringList &CC1Args) const {
4921 Linux::addClangTargetOptions(DriverArgs, CC1Args);
4922 CC1Args.push_back("-fcuda-is-device");
Artem Belevich34f481a2015-11-17 22:28:50 +00004923
Justin Lebard3a44f62016-04-05 18:26:20 +00004924 if (DriverArgs.hasFlag(options::OPT_fcuda_flush_denormals_to_zero,
4925 options::OPT_fno_cuda_flush_denormals_to_zero, false))
4926 CC1Args.push_back("-fcuda-flush-denormals-to-zero");
4927
Justin Lebar91f6f072016-05-23 20:19:56 +00004928 if (DriverArgs.hasFlag(options::OPT_fcuda_approx_transcendentals,
4929 options::OPT_fno_cuda_approx_transcendentals, false))
4930 CC1Args.push_back("-fcuda-approx-transcendentals");
4931
Artem Belevich34f481a2015-11-17 22:28:50 +00004932 if (DriverArgs.hasArg(options::OPT_nocudalib))
4933 return;
4934
Artem Belevich02a1e972016-08-02 23:12:51 +00004935 StringRef GpuArch = DriverArgs.getLastArgValue(options::OPT_march_EQ);
4936 assert(!GpuArch.empty() && "Must have an explicit GPU arch.");
4937 std::string LibDeviceFile = CudaInstallation.getLibDeviceFile(GpuArch);
Artem Belevich34f481a2015-11-17 22:28:50 +00004938
Artem Belevich02a1e972016-08-02 23:12:51 +00004939 if (LibDeviceFile.empty()) {
4940 getDriver().Diag(diag::err_drv_no_cuda_libdevice) << GpuArch;
4941 return;
Artem Belevich34f481a2015-11-17 22:28:50 +00004942 }
Artem Belevich02a1e972016-08-02 23:12:51 +00004943
4944 CC1Args.push_back("-mlink-cuda-bitcode");
4945 CC1Args.push_back(DriverArgs.MakeArgString(LibDeviceFile));
4946
4947 // Libdevice in CUDA-7.0 requires PTX version that's more recent
4948 // than LLVM defaults to. Use PTX4.2 which is the PTX version that
4949 // came with CUDA-7.0.
4950 CC1Args.push_back("-target-feature");
4951 CC1Args.push_back("+ptx42");
Artem Belevich0ff05cd2015-07-13 23:27:56 +00004952}
4953
Justin Lebarc43ad9e2016-07-07 18:17:52 +00004954void CudaToolChain::AddCudaIncludeArgs(const ArgList &DriverArgs,
4955 ArgStringList &CC1Args) const {
4956 // Check our CUDA version if we're going to include the CUDA headers.
4957 if (!DriverArgs.hasArg(options::OPT_nocudainc) &&
Justin Lebarf3997712016-07-07 18:24:28 +00004958 !DriverArgs.hasArg(options::OPT_no_cuda_version_check)) {
Justin Lebarc43ad9e2016-07-07 18:17:52 +00004959 StringRef Arch = DriverArgs.getLastArgValue(options::OPT_march_EQ);
4960 assert(!Arch.empty() && "Must have an explicit GPU arch.");
4961 CudaInstallation.CheckCudaVersionSupportsArch(StringToCudaArch(Arch));
4962 }
4963 Linux::AddCudaIncludeArgs(DriverArgs, CC1Args);
4964}
4965
Artem Belevich0ff05cd2015-07-13 23:27:56 +00004966llvm::opt::DerivedArgList *
4967CudaToolChain::TranslateArgs(const llvm::opt::DerivedArgList &Args,
Mehdi Aminic50b1a22016-10-07 21:27:26 +00004968 StringRef BoundArch) const {
Artem Belevich0ff05cd2015-07-13 23:27:56 +00004969 DerivedArgList *DAL = new DerivedArgList(Args.getBaseArgs());
4970 const OptTable &Opts = getDriver().getOpts();
4971
4972 for (Arg *A : Args) {
4973 if (A->getOption().matches(options::OPT_Xarch__)) {
4974 // Skip this argument unless the architecture matches BoundArch
Mehdi Aminic50b1a22016-10-07 21:27:26 +00004975 if (BoundArch.empty() || A->getValue(0) != BoundArch)
Artem Belevich0ff05cd2015-07-13 23:27:56 +00004976 continue;
4977
4978 unsigned Index = Args.getBaseArgs().MakeIndex(A->getValue(1));
4979 unsigned Prev = Index;
4980 std::unique_ptr<Arg> XarchArg(Opts.ParseOneArg(Args, Index));
4981
4982 // If the argument parsing failed or more than one argument was
4983 // consumed, the -Xarch_ argument's parameter tried to consume
4984 // extra arguments. Emit an error and ignore.
4985 //
4986 // We also want to disallow any options which would alter the
4987 // driver behavior; that isn't going to work in our model. We
4988 // use isDriverOption() as an approximation, although things
4989 // like -O4 are going to slip through.
4990 if (!XarchArg || Index > Prev + 1) {
4991 getDriver().Diag(diag::err_drv_invalid_Xarch_argument_with_args)
4992 << A->getAsString(Args);
4993 continue;
4994 } else if (XarchArg->getOption().hasFlag(options::DriverOption)) {
4995 getDriver().Diag(diag::err_drv_invalid_Xarch_argument_isdriver)
4996 << A->getAsString(Args);
4997 continue;
4998 }
4999 XarchArg->setBaseArg(A);
5000 A = XarchArg.release();
5001 DAL->AddSynthesizedArg(A);
5002 }
5003 DAL->append(A);
5004 }
5005
Mehdi Aminic50b1a22016-10-07 21:27:26 +00005006 if (!BoundArch.empty()) {
Justin Lebar4db224e2016-06-15 23:46:11 +00005007 DAL->eraseArg(options::OPT_march_EQ);
Justin Lebar21e5d4f2016-01-14 21:41:27 +00005008 DAL->AddJoinedArg(nullptr, Opts.getOption(options::OPT_march_EQ), BoundArch);
Justin Lebar4db224e2016-06-15 23:46:11 +00005009 }
Artem Belevich0ff05cd2015-07-13 23:27:56 +00005010 return DAL;
5011}
5012
Justin Lebar21e5d4f2016-01-14 21:41:27 +00005013Tool *CudaToolChain::buildAssembler() const {
5014 return new tools::NVPTX::Assembler(*this);
5015}
5016
5017Tool *CudaToolChain::buildLinker() const {
5018 return new tools::NVPTX::Linker(*this);
5019}
5020
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005021/// XCore tool chain
Douglas Katzman54366072015-07-27 16:53:08 +00005022XCoreToolChain::XCoreToolChain(const Driver &D, const llvm::Triple &Triple,
5023 const ArgList &Args)
Douglas Katzmana67e50c2015-06-26 15:47:46 +00005024 : ToolChain(D, Triple, Args) {
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005025 // ProgramPaths are found via 'PATH' environment variable.
5026}
5027
Douglas Katzman54366072015-07-27 16:53:08 +00005028Tool *XCoreToolChain::buildAssembler() const {
Douglas Katzman95354292015-06-23 20:42:09 +00005029 return new tools::XCore::Assembler(*this);
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005030}
5031
Douglas Katzman54366072015-07-27 16:53:08 +00005032Tool *XCoreToolChain::buildLinker() const {
5033 return new tools::XCore::Linker(*this);
5034}
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005035
Douglas Katzman54366072015-07-27 16:53:08 +00005036bool XCoreToolChain::isPICDefault() const { return false; }
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005037
Douglas Katzman54366072015-07-27 16:53:08 +00005038bool XCoreToolChain::isPIEDefault() const { return false; }
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005039
Douglas Katzman54366072015-07-27 16:53:08 +00005040bool XCoreToolChain::isPICDefaultForced() const { return false; }
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005041
Douglas Katzman54366072015-07-27 16:53:08 +00005042bool XCoreToolChain::SupportsProfiling() const { return false; }
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005043
Douglas Katzman54366072015-07-27 16:53:08 +00005044bool XCoreToolChain::hasBlocksRuntime() const { return false; }
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005045
Douglas Katzman54366072015-07-27 16:53:08 +00005046void XCoreToolChain::AddClangSystemIncludeArgs(const ArgList &DriverArgs,
5047 ArgStringList &CC1Args) const {
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005048 if (DriverArgs.hasArg(options::OPT_nostdinc) ||
5049 DriverArgs.hasArg(options::OPT_nostdlibinc))
5050 return;
5051 if (const char *cl_include_dir = getenv("XCC_C_INCLUDE_PATH")) {
5052 SmallVector<StringRef, 4> Dirs;
Douglas Katzmana67e50c2015-06-26 15:47:46 +00005053 const char EnvPathSeparatorStr[] = {llvm::sys::EnvPathSeparator, '\0'};
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005054 StringRef(cl_include_dir).split(Dirs, StringRef(EnvPathSeparatorStr));
5055 ArrayRef<StringRef> DirVec(Dirs);
5056 addSystemIncludes(DriverArgs, CC1Args, DirVec);
5057 }
5058}
5059
Douglas Katzman54366072015-07-27 16:53:08 +00005060void XCoreToolChain::addClangTargetOptions(const ArgList &DriverArgs,
5061 ArgStringList &CC1Args) const {
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005062 CC1Args.push_back("-nostdsysteminc");
5063}
5064
Douglas Katzman54366072015-07-27 16:53:08 +00005065void XCoreToolChain::AddClangCXXStdlibIncludeArgs(
5066 const ArgList &DriverArgs, ArgStringList &CC1Args) const {
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005067 if (DriverArgs.hasArg(options::OPT_nostdinc) ||
Robert Lyttonf9710b32014-08-01 13:11:46 +00005068 DriverArgs.hasArg(options::OPT_nostdlibinc) ||
5069 DriverArgs.hasArg(options::OPT_nostdincxx))
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005070 return;
5071 if (const char *cl_include_dir = getenv("XCC_CPLUS_INCLUDE_PATH")) {
5072 SmallVector<StringRef, 4> Dirs;
Douglas Katzmana67e50c2015-06-26 15:47:46 +00005073 const char EnvPathSeparatorStr[] = {llvm::sys::EnvPathSeparator, '\0'};
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005074 StringRef(cl_include_dir).split(Dirs, StringRef(EnvPathSeparatorStr));
5075 ArrayRef<StringRef> DirVec(Dirs);
5076 addSystemIncludes(DriverArgs, CC1Args, DirVec);
5077 }
5078}
5079
Douglas Katzman54366072015-07-27 16:53:08 +00005080void XCoreToolChain::AddCXXStdlibLibArgs(const ArgList &Args,
5081 ArgStringList &CmdArgs) const {
Robert Lyttoncf1dd692013-10-11 10:29:40 +00005082 // We don't output any lib args. This is handled by xcc.
5083}
Douglas Katzman84a75642015-06-19 14:55:19 +00005084
Douglas Katzmand6e597c2015-09-17 19:56:40 +00005085MyriadToolChain::MyriadToolChain(const Driver &D, const llvm::Triple &Triple,
5086 const ArgList &Args)
Douglas Katzman5eddc232016-05-09 19:09:59 +00005087 : Generic_ELF(D, Triple, Args) {
Douglas Katzmand6e597c2015-09-17 19:56:40 +00005088 // If a target of 'sparc-myriad-elf' is specified to clang, it wants to use
5089 // 'sparc-myriad--elf' (note the unknown OS) as the canonical triple.
5090 // This won't work to find gcc. Instead we give the installation detector an
5091 // extra triple, which is preferable to further hacks of the logic that at
5092 // present is based solely on getArch(). In particular, it would be wrong to
5093 // choose the myriad installation when targeting a non-myriad sparc install.
5094 switch (Triple.getArch()) {
5095 default:
Eric Christopherefef8ef2015-12-07 22:43:05 +00005096 D.Diag(diag::err_target_unsupported_arch) << Triple.getArchName()
5097 << "myriad";
Douglas Katzmand6e597c2015-09-17 19:56:40 +00005098 case llvm::Triple::sparc:
5099 case llvm::Triple::sparcel:
5100 case llvm::Triple::shave:
Benjamin Kramerd45b2052015-10-07 15:48:01 +00005101 GCCInstallation.init(Triple, Args, {"sparc-myriad-elf"});
Douglas Katzmand6e597c2015-09-17 19:56:40 +00005102 }
Douglas Katzman674a3122015-11-18 16:24:46 +00005103
5104 if (GCCInstallation.isValid()) {
5105 // The contents of LibDir are independent of the version of gcc.
Douglas Katzman87da5f42016-07-25 16:36:02 +00005106 // This contains libc, libg, libm, libstdc++, libssp.
5107 // The 'ma1x00' and 'nofpu' variants are irrelevant.
Douglas Katzman674a3122015-11-18 16:24:46 +00005108 SmallString<128> LibDir(GCCInstallation.getParentLibPath());
Douglas Katzman87da5f42016-07-25 16:36:02 +00005109 llvm::sys::path::append(LibDir, "../sparc-myriad-elf/lib");
Douglas Katzman674a3122015-11-18 16:24:46 +00005110 addPathIfExists(D, LibDir, getFilePaths());
5111
5112 // This directory contains crt{i,n,begin,end}.o as well as libgcc.
5113 // These files are tied to a particular version of gcc.
5114 SmallString<128> CompilerSupportDir(GCCInstallation.getInstallPath());
Douglas Katzman674a3122015-11-18 16:24:46 +00005115 addPathIfExists(D, CompilerSupportDir, getFilePaths());
5116 }
Douglas Katzmand6e597c2015-09-17 19:56:40 +00005117}
5118
Angel Garcia Gomez637d1e62015-10-20 13:23:58 +00005119MyriadToolChain::~MyriadToolChain() {}
Douglas Katzmand6e597c2015-09-17 19:56:40 +00005120
Douglas Katzmanb1278f32015-09-17 21:20:16 +00005121void MyriadToolChain::AddClangSystemIncludeArgs(const ArgList &DriverArgs,
5122 ArgStringList &CC1Args) const {
5123 if (!DriverArgs.hasArg(options::OPT_nostdinc))
5124 addSystemInclude(DriverArgs, CC1Args, getDriver().SysRoot + "/include");
5125}
5126
Eric Christopherefef8ef2015-12-07 22:43:05 +00005127void MyriadToolChain::AddClangCXXStdlibIncludeArgs(
5128 const ArgList &DriverArgs, ArgStringList &CC1Args) const {
James Y Knighta6c9ee72015-10-16 18:46:26 +00005129 if (DriverArgs.hasArg(options::OPT_nostdlibinc) ||
5130 DriverArgs.hasArg(options::OPT_nostdincxx))
5131 return;
5132
Douglas Katzman69d7cf02016-10-19 17:30:40 +00005133 if (GetCXXStdlibType(DriverArgs) == ToolChain::CST_Libcxx) {
5134 std::string Path(getDriver().getInstalledDir());
5135 Path += "/../include/c++/v1";
5136 addSystemInclude(DriverArgs, CC1Args, Path);
5137 } else {
5138 StringRef LibDir = GCCInstallation.getParentLibPath();
5139 const GCCVersion &Version = GCCInstallation.getVersion();
5140 StringRef TripleStr = GCCInstallation.getTriple().str();
5141 const Multilib &Multilib = GCCInstallation.getMultilib();
5142 addLibStdCXXIncludePaths(
5143 LibDir.str() + "/../" + TripleStr.str() + "/include/c++/" + Version.Text,
5144 "", TripleStr, "", "", Multilib.includeSuffix(), DriverArgs, CC1Args);
5145 }
James Y Knighta6c9ee72015-10-16 18:46:26 +00005146}
5147
Douglas Katzmand6e597c2015-09-17 19:56:40 +00005148// MyriadToolChain handles several triples:
5149// {shave,sparc{,el}}-myriad-{rtems,unknown}-elf
5150Tool *MyriadToolChain::SelectTool(const JobAction &JA) const {
5151 // The inherited method works fine if not targeting the SHAVE.
5152 if (!isShaveCompilation(getTriple()))
5153 return ToolChain::SelectTool(JA);
Douglas Katzman84a75642015-06-19 14:55:19 +00005154 switch (JA.getKind()) {
Douglas Katzman9dc4c622015-11-20 04:58:12 +00005155 case Action::PreprocessJobClass:
Douglas Katzman84a75642015-06-19 14:55:19 +00005156 case Action::CompileJobClass:
5157 if (!Compiler)
Douglas Katzman95354292015-06-23 20:42:09 +00005158 Compiler.reset(new tools::SHAVE::Compiler(*this));
Douglas Katzman84a75642015-06-19 14:55:19 +00005159 return Compiler.get();
5160 case Action::AssembleJobClass:
5161 if (!Assembler)
Douglas Katzman95354292015-06-23 20:42:09 +00005162 Assembler.reset(new tools::SHAVE::Assembler(*this));
Douglas Katzman84a75642015-06-19 14:55:19 +00005163 return Assembler.get();
5164 default:
5165 return ToolChain::getTool(JA.getKind());
5166 }
5167}
5168
Douglas Katzmand6e597c2015-09-17 19:56:40 +00005169Tool *MyriadToolChain::buildLinker() const {
5170 return new tools::Myriad::Linker(*this);
Douglas Katzman84a75642015-06-19 14:55:19 +00005171}
Dan Gohmanc2853072015-09-03 22:51:53 +00005172
Douglas Katzman3972f9e2016-09-09 18:20:49 +00005173SanitizerMask MyriadToolChain::getSupportedSanitizers() const {
5174 return SanitizerKind::Address;
5175}
5176
Dan Gohman52816862015-12-16 23:30:41 +00005177WebAssembly::WebAssembly(const Driver &D, const llvm::Triple &Triple,
5178 const llvm::opt::ArgList &Args)
5179 : ToolChain(D, Triple, Args) {
Dan Gohman57b62c52016-02-22 19:26:15 +00005180
5181 assert(Triple.isArch32Bit() != Triple.isArch64Bit());
5182 getFilePaths().push_back(
5183 getDriver().SysRoot + "/lib" + (Triple.isArch32Bit() ? "32" : "64"));
5184
Dan Gohman52816862015-12-16 23:30:41 +00005185 // Use LLD by default.
5186 DefaultLinker = "lld";
5187}
5188
Dan Gohmanc2853072015-09-03 22:51:53 +00005189bool WebAssembly::IsMathErrnoDefault() const { return false; }
5190
5191bool WebAssembly::IsObjCNonFragileABIDefault() const { return true; }
5192
5193bool WebAssembly::UseObjCMixedDispatch() const { return true; }
5194
5195bool WebAssembly::isPICDefault() const { return false; }
5196
5197bool WebAssembly::isPIEDefault() const { return false; }
5198
5199bool WebAssembly::isPICDefaultForced() const { return false; }
5200
5201bool WebAssembly::IsIntegratedAssemblerDefault() const { return true; }
5202
5203// TODO: Support Objective C stuff.
5204bool WebAssembly::SupportsObjCGC() const { return false; }
5205
5206bool WebAssembly::hasBlocksRuntime() const { return false; }
5207
5208// TODO: Support profiling.
5209bool WebAssembly::SupportsProfiling() const { return false; }
5210
Dan Gohman52816862015-12-16 23:30:41 +00005211bool WebAssembly::HasNativeLLVMSupport() const { return true; }
5212
Dan Gohmanc2853072015-09-03 22:51:53 +00005213void WebAssembly::addClangTargetOptions(const ArgList &DriverArgs,
5214 ArgStringList &CC1Args) const {
5215 if (DriverArgs.hasFlag(options::OPT_fuse_init_array,
5216 options::OPT_fno_use_init_array, true))
5217 CC1Args.push_back("-fuse-init-array");
5218}
Filipe Cabecinhasc888e192015-10-14 12:25:43 +00005219
Dan Gohman6ad8f612016-01-14 16:00:13 +00005220ToolChain::RuntimeLibType WebAssembly::GetDefaultRuntimeLibType() const {
5221 return ToolChain::RLT_CompilerRT;
5222}
5223
5224ToolChain::CXXStdlibType WebAssembly::GetCXXStdlibType(const ArgList &Args) const {
5225 return ToolChain::CST_Libcxx;
5226}
5227
5228void WebAssembly::AddClangSystemIncludeArgs(const ArgList &DriverArgs,
5229 ArgStringList &CC1Args) const {
5230 if (!DriverArgs.hasArg(options::OPT_nostdinc))
5231 addSystemInclude(DriverArgs, CC1Args, getDriver().SysRoot + "/include");
5232}
5233
5234void WebAssembly::AddClangCXXStdlibIncludeArgs(
5235 const llvm::opt::ArgList &DriverArgs,
5236 llvm::opt::ArgStringList &CC1Args) const {
5237 if (!DriverArgs.hasArg(options::OPT_nostdlibinc) &&
5238 !DriverArgs.hasArg(options::OPT_nostdincxx))
5239 addSystemInclude(DriverArgs, CC1Args,
5240 getDriver().SysRoot + "/include/c++/v1");
5241}
5242
Dan Gohman52816862015-12-16 23:30:41 +00005243Tool *WebAssembly::buildLinker() const {
5244 return new tools::wasm::Linker(*this);
5245}
5246
Filipe Cabecinhasc888e192015-10-14 12:25:43 +00005247PS4CPU::PS4CPU(const Driver &D, const llvm::Triple &Triple, const ArgList &Args)
5248 : Generic_ELF(D, Triple, Args) {
5249 if (Args.hasArg(options::OPT_static))
5250 D.Diag(diag::err_drv_unsupported_opt_for_target) << "-static" << "PS4";
5251
Paul Robinson9d613612016-05-16 17:22:25 +00005252 // Determine where to find the PS4 libraries. We use SCE_ORBIS_SDK_DIR
Filipe Cabecinhasc888e192015-10-14 12:25:43 +00005253 // if it exists; otherwise use the driver's installation path, which
5254 // should be <SDK_DIR>/host_tools/bin.
5255
5256 SmallString<512> PS4SDKDir;
Paul Robinson9d613612016-05-16 17:22:25 +00005257 if (const char *EnvValue = getenv("SCE_ORBIS_SDK_DIR")) {
Filipe Cabecinhasc888e192015-10-14 12:25:43 +00005258 if (!llvm::sys::fs::exists(EnvValue))
5259 getDriver().Diag(clang::diag::warn_drv_ps4_sdk_dir) << EnvValue;
5260 PS4SDKDir = EnvValue;
5261 } else {
5262 PS4SDKDir = getDriver().Dir;
5263 llvm::sys::path::append(PS4SDKDir, "/../../");
Eric Christopherefef8ef2015-12-07 22:43:05 +00005264 }
Filipe Cabecinhasc888e192015-10-14 12:25:43 +00005265
Eric Christopherefef8ef2015-12-07 22:43:05 +00005266 // By default, the driver won't report a warning if it can't find
Filipe Cabecinhasc888e192015-10-14 12:25:43 +00005267 // PS4's include or lib directories. This behavior could be changed if
Eric Christopherefef8ef2015-12-07 22:43:05 +00005268 // -Weverything or -Winvalid-or-nonexistent-directory options are passed.
Filipe Cabecinhasc888e192015-10-14 12:25:43 +00005269 // If -isysroot was passed, use that as the SDK base path.
5270 std::string PrefixDir;
5271 if (const Arg *A = Args.getLastArg(options::OPT_isysroot)) {
5272 PrefixDir = A->getValue();
5273 if (!llvm::sys::fs::exists(PrefixDir))
5274 getDriver().Diag(clang::diag::warn_missing_sysroot) << PrefixDir;
5275 } else
5276 PrefixDir = PS4SDKDir.str();
5277
5278 SmallString<512> PS4SDKIncludeDir(PrefixDir);
5279 llvm::sys::path::append(PS4SDKIncludeDir, "target/include");
5280 if (!Args.hasArg(options::OPT_nostdinc) &&
5281 !Args.hasArg(options::OPT_nostdlibinc) &&
5282 !Args.hasArg(options::OPT_isysroot) &&
5283 !Args.hasArg(options::OPT__sysroot_EQ) &&
5284 !llvm::sys::fs::exists(PS4SDKIncludeDir)) {
5285 getDriver().Diag(clang::diag::warn_drv_unable_to_find_directory_expected)
5286 << "PS4 system headers" << PS4SDKIncludeDir;
5287 }
5288
5289 SmallString<512> PS4SDKLibDir(PS4SDKDir);
5290 llvm::sys::path::append(PS4SDKLibDir, "target/lib");
5291 if (!Args.hasArg(options::OPT_nostdlib) &&
5292 !Args.hasArg(options::OPT_nodefaultlibs) &&
5293 !Args.hasArg(options::OPT__sysroot_EQ) && !Args.hasArg(options::OPT_E) &&
5294 !Args.hasArg(options::OPT_c) && !Args.hasArg(options::OPT_S) &&
5295 !Args.hasArg(options::OPT_emit_ast) &&
5296 !llvm::sys::fs::exists(PS4SDKLibDir)) {
5297 getDriver().Diag(clang::diag::warn_drv_unable_to_find_directory_expected)
5298 << "PS4 system libraries" << PS4SDKLibDir;
5299 return;
5300 }
5301 getFilePaths().push_back(PS4SDKLibDir.str());
5302}
5303
5304Tool *PS4CPU::buildAssembler() const {
5305 return new tools::PS4cpu::Assemble(*this);
5306}
5307
5308Tool *PS4CPU::buildLinker() const { return new tools::PS4cpu::Link(*this); }
5309
5310bool PS4CPU::isPICDefault() const { return true; }
5311
5312bool PS4CPU::HasNativeLLVMSupport() const { return true; }
5313
5314SanitizerMask PS4CPU::getSupportedSanitizers() const {
5315 SanitizerMask Res = ToolChain::getSupportedSanitizers();
5316 Res |= SanitizerKind::Address;
5317 Res |= SanitizerKind::Vptr;
5318 return Res;
5319}
David L Kreitzerd397ea42016-10-14 20:44:33 +00005320
5321Contiki::Contiki(const Driver &D, const llvm::Triple &Triple, const ArgList &Args)
5322 : Generic_ELF(D, Triple, Args) {}
5323
5324SanitizerMask Contiki::getSupportedSanitizers() const {
5325 const bool IsX86 = getTriple().getArch() == llvm::Triple::x86;
5326 SanitizerMask Res = ToolChain::getSupportedSanitizers();
5327 if (IsX86)
5328 Res |= SanitizerKind::SafeStack;
5329 return Res;
5330}