1 //===--- Darwin.cpp - Darwin Tool and ToolChain Implementations -*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 9 #include "Darwin.h" 10 #include "Arch/ARM.h" 11 #include "CommonArgs.h" 12 #include "clang/Basic/AlignedAllocation.h" 13 #include "clang/Basic/ObjCRuntime.h" 14 #include "clang/Config/config.h" 15 #include "clang/Driver/Compilation.h" 16 #include "clang/Driver/Driver.h" 17 #include "clang/Driver/DriverDiagnostic.h" 18 #include "clang/Driver/Options.h" 19 #include "clang/Driver/SanitizerArgs.h" 20 #include "llvm/ADT/StringSwitch.h" 21 #include "llvm/Option/ArgList.h" 22 #include "llvm/ProfileData/InstrProf.h" 23 #include "llvm/Support/Path.h" 24 #include "llvm/Support/ScopedPrinter.h" 25 #include "llvm/Support/TargetParser.h" 26 #include "llvm/Support/VirtualFileSystem.h" 27 #include <cstdlib> // ::getenv 28 29 using namespace clang::driver; 30 using namespace clang::driver::tools; 31 using namespace clang::driver::toolchains; 32 using namespace clang; 33 using namespace llvm::opt; 34 35 llvm::Triple::ArchType darwin::getArchTypeForMachOArchName(StringRef Str) { 36 // See arch(3) and llvm-gcc's driver-driver.c. We don't implement support for 37 // archs which Darwin doesn't use. 38 39 // The matching this routine does is fairly pointless, since it is neither the 40 // complete architecture list, nor a reasonable subset. The problem is that 41 // historically the driver driver accepts this and also ties its -march= 42 // handling to the architecture name, so we need to be careful before removing 43 // support for it. 44 45 // This code must be kept in sync with Clang's Darwin specific argument 46 // translation. 47 48 return llvm::StringSwitch<llvm::Triple::ArchType>(Str) 49 .Cases("ppc", "ppc601", "ppc603", "ppc604", "ppc604e", llvm::Triple::ppc) 50 .Cases("ppc750", "ppc7400", "ppc7450", "ppc970", llvm::Triple::ppc) 51 .Case("ppc64", llvm::Triple::ppc64) 52 .Cases("i386", "i486", "i486SX", "i586", "i686", llvm::Triple::x86) 53 .Cases("pentium", "pentpro", "pentIIm3", "pentIIm5", "pentium4", 54 llvm::Triple::x86) 55 .Cases("x86_64", "x86_64h", llvm::Triple::x86_64) 56 // This is derived from the driver driver. 57 .Cases("arm", "armv4t", "armv5", "armv6", "armv6m", llvm::Triple::arm) 58 .Cases("armv7", "armv7em", "armv7k", "armv7m", llvm::Triple::arm) 59 .Cases("armv7s", "xscale", llvm::Triple::arm) 60 .Case("arm64", llvm::Triple::aarch64) 61 .Case("r600", llvm::Triple::r600) 62 .Case("amdgcn", llvm::Triple::amdgcn) 63 .Case("nvptx", llvm::Triple::nvptx) 64 .Case("nvptx64", llvm::Triple::nvptx64) 65 .Case("amdil", llvm::Triple::amdil) 66 .Case("spir", llvm::Triple::spir) 67 .Default(llvm::Triple::UnknownArch); 68 } 69 70 void darwin::setTripleTypeForMachOArchName(llvm::Triple &T, StringRef Str) { 71 const llvm::Triple::ArchType Arch = getArchTypeForMachOArchName(Str); 72 llvm::ARM::ArchKind ArchKind = llvm::ARM::parseArch(Str); 73 T.setArch(Arch); 74 75 if (Str == "x86_64h") 76 T.setArchName(Str); 77 else if (ArchKind == llvm::ARM::ArchKind::ARMV6M || 78 ArchKind == llvm::ARM::ArchKind::ARMV7M || 79 ArchKind == llvm::ARM::ArchKind::ARMV7EM) { 80 T.setOS(llvm::Triple::UnknownOS); 81 T.setObjectFormat(llvm::Triple::MachO); 82 } 83 } 84 85 void darwin::Assembler::ConstructJob(Compilation &C, const JobAction &JA, 86 const InputInfo &Output, 87 const InputInfoList &Inputs, 88 const ArgList &Args, 89 const char *LinkingOutput) const { 90 ArgStringList CmdArgs; 91 92 assert(Inputs.size() == 1 && "Unexpected number of inputs."); 93 const InputInfo &Input = Inputs[0]; 94 95 // Determine the original source input. 96 const Action *SourceAction = &JA; 97 while (SourceAction->getKind() != Action::InputClass) { 98 assert(!SourceAction->getInputs().empty() && "unexpected root action!"); 99 SourceAction = SourceAction->getInputs()[0]; 100 } 101 102 // If -fno-integrated-as is used add -Q to the darwin assembler driver to make 103 // sure it runs its system assembler not clang's integrated assembler. 104 // Applicable to darwin11+ and Xcode 4+. darwin<10 lacked integrated-as. 105 // FIXME: at run-time detect assembler capabilities or rely on version 106 // information forwarded by -target-assembler-version. 107 if (Args.hasArg(options::OPT_fno_integrated_as)) { 108 const llvm::Triple &T(getToolChain().getTriple()); 109 if (!(T.isMacOSX() && T.isMacOSXVersionLT(10, 7))) 110 CmdArgs.push_back("-Q"); 111 } 112 113 // Forward -g, assuming we are dealing with an actual assembly file. 114 if (SourceAction->getType() == types::TY_Asm || 115 SourceAction->getType() == types::TY_PP_Asm) { 116 if (Args.hasArg(options::OPT_gstabs)) 117 CmdArgs.push_back("--gstabs"); 118 else if (Args.hasArg(options::OPT_g_Group)) 119 CmdArgs.push_back("-g"); 120 } 121 122 // Derived from asm spec. 123 AddMachOArch(Args, CmdArgs); 124 125 // Use -force_cpusubtype_ALL on x86 by default. 126 if (getToolChain().getArch() == llvm::Triple::x86 || 127 getToolChain().getArch() == llvm::Triple::x86_64 || 128 Args.hasArg(options::OPT_force__cpusubtype__ALL)) 129 CmdArgs.push_back("-force_cpusubtype_ALL"); 130 131 if (getToolChain().getArch() != llvm::Triple::x86_64 && 132 (((Args.hasArg(options::OPT_mkernel) || 133 Args.hasArg(options::OPT_fapple_kext)) && 134 getMachOToolChain().isKernelStatic()) || 135 Args.hasArg(options::OPT_static))) 136 CmdArgs.push_back("-static"); 137 138 Args.AddAllArgValues(CmdArgs, options::OPT_Wa_COMMA, options::OPT_Xassembler); 139 140 assert(Output.isFilename() && "Unexpected lipo output."); 141 CmdArgs.push_back("-o"); 142 CmdArgs.push_back(Output.getFilename()); 143 144 assert(Input.isFilename() && "Invalid input."); 145 CmdArgs.push_back(Input.getFilename()); 146 147 // asm_final spec is empty. 148 149 const char *Exec = Args.MakeArgString(getToolChain().GetProgramPath("as")); 150 C.addCommand(std::make_unique<Command>(JA, *this, Exec, CmdArgs, Inputs)); 151 } 152 153 void darwin::MachOTool::anchor() {} 154 155 void darwin::MachOTool::AddMachOArch(const ArgList &Args, 156 ArgStringList &CmdArgs) const { 157 StringRef ArchName = getMachOToolChain().getMachOArchName(Args); 158 159 // Derived from darwin_arch spec. 160 CmdArgs.push_back("-arch"); 161 CmdArgs.push_back(Args.MakeArgString(ArchName)); 162 163 // FIXME: Is this needed anymore? 164 if (ArchName == "arm") 165 CmdArgs.push_back("-force_cpusubtype_ALL"); 166 } 167 168 bool darwin::Linker::NeedsTempPath(const InputInfoList &Inputs) const { 169 // We only need to generate a temp path for LTO if we aren't compiling object 170 // files. When compiling source files, we run 'dsymutil' after linking. We 171 // don't run 'dsymutil' when compiling object files. 172 for (const auto &Input : Inputs) 173 if (Input.getType() != types::TY_Object) 174 return true; 175 176 return false; 177 } 178 179 /// Pass -no_deduplicate to ld64 under certain conditions: 180 /// 181 /// - Either -O0 or -O1 is explicitly specified 182 /// - No -O option is specified *and* this is a compile+link (implicit -O0) 183 /// 184 /// Also do *not* add -no_deduplicate when no -O option is specified and this 185 /// is just a link (we can't imply -O0) 186 static bool shouldLinkerNotDedup(bool IsLinkerOnlyAction, const ArgList &Args) { 187 if (Arg *A = Args.getLastArg(options::OPT_O_Group)) { 188 if (A->getOption().matches(options::OPT_O0)) 189 return true; 190 if (A->getOption().matches(options::OPT_O)) 191 return llvm::StringSwitch<bool>(A->getValue()) 192 .Case("1", true) 193 .Default(false); 194 return false; // OPT_Ofast & OPT_O4 195 } 196 197 if (!IsLinkerOnlyAction) // Implicit -O0 for compile+linker only. 198 return true; 199 return false; 200 } 201 202 void darwin::Linker::AddLinkArgs(Compilation &C, const ArgList &Args, 203 ArgStringList &CmdArgs, 204 const InputInfoList &Inputs) const { 205 const Driver &D = getToolChain().getDriver(); 206 const toolchains::MachO &MachOTC = getMachOToolChain(); 207 208 unsigned Version[5] = {0, 0, 0, 0, 0}; 209 if (Arg *A = Args.getLastArg(options::OPT_mlinker_version_EQ)) { 210 if (!Driver::GetReleaseVersion(A->getValue(), Version)) 211 D.Diag(diag::err_drv_invalid_version_number) << A->getAsString(Args); 212 } 213 214 // Newer linkers support -demangle. Pass it if supported and not disabled by 215 // the user. 216 if (Version[0] >= 100 && !Args.hasArg(options::OPT_Z_Xlinker__no_demangle)) 217 CmdArgs.push_back("-demangle"); 218 219 if (Args.hasArg(options::OPT_rdynamic) && Version[0] >= 137) 220 CmdArgs.push_back("-export_dynamic"); 221 222 // If we are using App Extension restrictions, pass a flag to the linker 223 // telling it that the compiled code has been audited. 224 if (Args.hasFlag(options::OPT_fapplication_extension, 225 options::OPT_fno_application_extension, false)) 226 CmdArgs.push_back("-application_extension"); 227 228 if (D.isUsingLTO() && Version[0] >= 116 && NeedsTempPath(Inputs)) { 229 std::string TmpPathName; 230 if (D.getLTOMode() == LTOK_Full) { 231 // If we are using full LTO, then automatically create a temporary file 232 // path for the linker to use, so that it's lifetime will extend past a 233 // possible dsymutil step. 234 TmpPathName = 235 D.GetTemporaryPath("cc", types::getTypeTempSuffix(types::TY_Object)); 236 } else if (D.getLTOMode() == LTOK_Thin) 237 // If we are using thin LTO, then create a directory instead. 238 TmpPathName = D.GetTemporaryDirectory("thinlto"); 239 240 if (!TmpPathName.empty()) { 241 auto *TmpPath = C.getArgs().MakeArgString(TmpPathName); 242 C.addTempFile(TmpPath); 243 CmdArgs.push_back("-object_path_lto"); 244 CmdArgs.push_back(TmpPath); 245 } 246 } 247 248 // Use -lto_library option to specify the libLTO.dylib path. Try to find 249 // it in clang installed libraries. ld64 will only look at this argument 250 // when it actually uses LTO, so libLTO.dylib only needs to exist at link 251 // time if ld64 decides that it needs to use LTO. 252 // Since this is passed unconditionally, ld64 will never look for libLTO.dylib 253 // next to it. That's ok since ld64 using a libLTO.dylib not matching the 254 // clang version won't work anyways. 255 if (Version[0] >= 133) { 256 // Search for libLTO in <InstalledDir>/../lib/libLTO.dylib 257 StringRef P = llvm::sys::path::parent_path(D.Dir); 258 SmallString<128> LibLTOPath(P); 259 llvm::sys::path::append(LibLTOPath, "lib"); 260 llvm::sys::path::append(LibLTOPath, "libLTO.dylib"); 261 CmdArgs.push_back("-lto_library"); 262 CmdArgs.push_back(C.getArgs().MakeArgString(LibLTOPath)); 263 } 264 265 // ld64 version 262 and above run the deduplicate pass by default. 266 if (Version[0] >= 262 && shouldLinkerNotDedup(C.getJobs().empty(), Args)) 267 CmdArgs.push_back("-no_deduplicate"); 268 269 // Derived from the "link" spec. 270 Args.AddAllArgs(CmdArgs, options::OPT_static); 271 if (!Args.hasArg(options::OPT_static)) 272 CmdArgs.push_back("-dynamic"); 273 if (Args.hasArg(options::OPT_fgnu_runtime)) { 274 // FIXME: gcc replaces -lobjc in forward args with -lobjc-gnu 275 // here. How do we wish to handle such things? 276 } 277 278 if (!Args.hasArg(options::OPT_dynamiclib)) { 279 AddMachOArch(Args, CmdArgs); 280 // FIXME: Why do this only on this path? 281 Args.AddLastArg(CmdArgs, options::OPT_force__cpusubtype__ALL); 282 283 Args.AddLastArg(CmdArgs, options::OPT_bundle); 284 Args.AddAllArgs(CmdArgs, options::OPT_bundle__loader); 285 Args.AddAllArgs(CmdArgs, options::OPT_client__name); 286 287 Arg *A; 288 if ((A = Args.getLastArg(options::OPT_compatibility__version)) || 289 (A = Args.getLastArg(options::OPT_current__version)) || 290 (A = Args.getLastArg(options::OPT_install__name))) 291 D.Diag(diag::err_drv_argument_only_allowed_with) << A->getAsString(Args) 292 << "-dynamiclib"; 293 294 Args.AddLastArg(CmdArgs, options::OPT_force__flat__namespace); 295 Args.AddLastArg(CmdArgs, options::OPT_keep__private__externs); 296 Args.AddLastArg(CmdArgs, options::OPT_private__bundle); 297 } else { 298 CmdArgs.push_back("-dylib"); 299 300 Arg *A; 301 if ((A = Args.getLastArg(options::OPT_bundle)) || 302 (A = Args.getLastArg(options::OPT_bundle__loader)) || 303 (A = Args.getLastArg(options::OPT_client__name)) || 304 (A = Args.getLastArg(options::OPT_force__flat__namespace)) || 305 (A = Args.getLastArg(options::OPT_keep__private__externs)) || 306 (A = Args.getLastArg(options::OPT_private__bundle))) 307 D.Diag(diag::err_drv_argument_not_allowed_with) << A->getAsString(Args) 308 << "-dynamiclib"; 309 310 Args.AddAllArgsTranslated(CmdArgs, options::OPT_compatibility__version, 311 "-dylib_compatibility_version"); 312 Args.AddAllArgsTranslated(CmdArgs, options::OPT_current__version, 313 "-dylib_current_version"); 314 315 AddMachOArch(Args, CmdArgs); 316 317 Args.AddAllArgsTranslated(CmdArgs, options::OPT_install__name, 318 "-dylib_install_name"); 319 } 320 321 Args.AddLastArg(CmdArgs, options::OPT_all__load); 322 Args.AddAllArgs(CmdArgs, options::OPT_allowable__client); 323 Args.AddLastArg(CmdArgs, options::OPT_bind__at__load); 324 if (MachOTC.isTargetIOSBased()) 325 Args.AddLastArg(CmdArgs, options::OPT_arch__errors__fatal); 326 Args.AddLastArg(CmdArgs, options::OPT_dead__strip); 327 Args.AddLastArg(CmdArgs, options::OPT_no__dead__strip__inits__and__terms); 328 Args.AddAllArgs(CmdArgs, options::OPT_dylib__file); 329 Args.AddLastArg(CmdArgs, options::OPT_dynamic); 330 Args.AddAllArgs(CmdArgs, options::OPT_exported__symbols__list); 331 Args.AddLastArg(CmdArgs, options::OPT_flat__namespace); 332 Args.AddAllArgs(CmdArgs, options::OPT_force__load); 333 Args.AddAllArgs(CmdArgs, options::OPT_headerpad__max__install__names); 334 Args.AddAllArgs(CmdArgs, options::OPT_image__base); 335 Args.AddAllArgs(CmdArgs, options::OPT_init); 336 337 // Add the deployment target. 338 MachOTC.addMinVersionArgs(Args, CmdArgs); 339 340 Args.AddLastArg(CmdArgs, options::OPT_nomultidefs); 341 Args.AddLastArg(CmdArgs, options::OPT_multi__module); 342 Args.AddLastArg(CmdArgs, options::OPT_single__module); 343 Args.AddAllArgs(CmdArgs, options::OPT_multiply__defined); 344 Args.AddAllArgs(CmdArgs, options::OPT_multiply__defined__unused); 345 346 if (const Arg *A = 347 Args.getLastArg(options::OPT_fpie, options::OPT_fPIE, 348 options::OPT_fno_pie, options::OPT_fno_PIE)) { 349 if (A->getOption().matches(options::OPT_fpie) || 350 A->getOption().matches(options::OPT_fPIE)) 351 CmdArgs.push_back("-pie"); 352 else 353 CmdArgs.push_back("-no_pie"); 354 } 355 356 // for embed-bitcode, use -bitcode_bundle in linker command 357 if (C.getDriver().embedBitcodeEnabled()) { 358 // Check if the toolchain supports bitcode build flow. 359 if (MachOTC.SupportsEmbeddedBitcode()) { 360 CmdArgs.push_back("-bitcode_bundle"); 361 if (C.getDriver().embedBitcodeMarkerOnly() && Version[0] >= 278) { 362 CmdArgs.push_back("-bitcode_process_mode"); 363 CmdArgs.push_back("marker"); 364 } 365 } else 366 D.Diag(diag::err_drv_bitcode_unsupported_on_toolchain); 367 } 368 369 Args.AddLastArg(CmdArgs, options::OPT_prebind); 370 Args.AddLastArg(CmdArgs, options::OPT_noprebind); 371 Args.AddLastArg(CmdArgs, options::OPT_nofixprebinding); 372 Args.AddLastArg(CmdArgs, options::OPT_prebind__all__twolevel__modules); 373 Args.AddLastArg(CmdArgs, options::OPT_read__only__relocs); 374 Args.AddAllArgs(CmdArgs, options::OPT_sectcreate); 375 Args.AddAllArgs(CmdArgs, options::OPT_sectorder); 376 Args.AddAllArgs(CmdArgs, options::OPT_seg1addr); 377 Args.AddAllArgs(CmdArgs, options::OPT_segprot); 378 Args.AddAllArgs(CmdArgs, options::OPT_segaddr); 379 Args.AddAllArgs(CmdArgs, options::OPT_segs__read__only__addr); 380 Args.AddAllArgs(CmdArgs, options::OPT_segs__read__write__addr); 381 Args.AddAllArgs(CmdArgs, options::OPT_seg__addr__table); 382 Args.AddAllArgs(CmdArgs, options::OPT_seg__addr__table__filename); 383 Args.AddAllArgs(CmdArgs, options::OPT_sub__library); 384 Args.AddAllArgs(CmdArgs, options::OPT_sub__umbrella); 385 386 // Give --sysroot= preference, over the Apple specific behavior to also use 387 // --isysroot as the syslibroot. 388 StringRef sysroot = C.getSysRoot(); 389 if (sysroot != "") { 390 CmdArgs.push_back("-syslibroot"); 391 CmdArgs.push_back(C.getArgs().MakeArgString(sysroot)); 392 } else if (const Arg *A = Args.getLastArg(options::OPT_isysroot)) { 393 CmdArgs.push_back("-syslibroot"); 394 CmdArgs.push_back(A->getValue()); 395 } 396 397 Args.AddLastArg(CmdArgs, options::OPT_twolevel__namespace); 398 Args.AddLastArg(CmdArgs, options::OPT_twolevel__namespace__hints); 399 Args.AddAllArgs(CmdArgs, options::OPT_umbrella); 400 Args.AddAllArgs(CmdArgs, options::OPT_undefined); 401 Args.AddAllArgs(CmdArgs, options::OPT_unexported__symbols__list); 402 Args.AddAllArgs(CmdArgs, options::OPT_weak__reference__mismatches); 403 Args.AddLastArg(CmdArgs, options::OPT_X_Flag); 404 Args.AddAllArgs(CmdArgs, options::OPT_y); 405 Args.AddLastArg(CmdArgs, options::OPT_w); 406 Args.AddAllArgs(CmdArgs, options::OPT_pagezero__size); 407 Args.AddAllArgs(CmdArgs, options::OPT_segs__read__); 408 Args.AddLastArg(CmdArgs, options::OPT_seglinkedit); 409 Args.AddLastArg(CmdArgs, options::OPT_noseglinkedit); 410 Args.AddAllArgs(CmdArgs, options::OPT_sectalign); 411 Args.AddAllArgs(CmdArgs, options::OPT_sectobjectsymbols); 412 Args.AddAllArgs(CmdArgs, options::OPT_segcreate); 413 Args.AddLastArg(CmdArgs, options::OPT_whyload); 414 Args.AddLastArg(CmdArgs, options::OPT_whatsloaded); 415 Args.AddAllArgs(CmdArgs, options::OPT_dylinker__install__name); 416 Args.AddLastArg(CmdArgs, options::OPT_dylinker); 417 Args.AddLastArg(CmdArgs, options::OPT_Mach); 418 } 419 420 /// Determine whether we are linking the ObjC runtime. 421 static bool isObjCRuntimeLinked(const ArgList &Args) { 422 if (isObjCAutoRefCount(Args)) { 423 Args.ClaimAllArgs(options::OPT_fobjc_link_runtime); 424 return true; 425 } 426 return Args.hasArg(options::OPT_fobjc_link_runtime); 427 } 428 429 void darwin::Linker::ConstructJob(Compilation &C, const JobAction &JA, 430 const InputInfo &Output, 431 const InputInfoList &Inputs, 432 const ArgList &Args, 433 const char *LinkingOutput) const { 434 assert(Output.getType() == types::TY_Image && "Invalid linker output type."); 435 436 // If the number of arguments surpasses the system limits, we will encode the 437 // input files in a separate file, shortening the command line. To this end, 438 // build a list of input file names that can be passed via a file with the 439 // -filelist linker option. 440 llvm::opt::ArgStringList InputFileList; 441 442 // The logic here is derived from gcc's behavior; most of which 443 // comes from specs (starting with link_command). Consult gcc for 444 // more information. 445 ArgStringList CmdArgs; 446 447 /// Hack(tm) to ignore linking errors when we are doing ARC migration. 448 if (Args.hasArg(options::OPT_ccc_arcmt_check, 449 options::OPT_ccc_arcmt_migrate)) { 450 for (const auto &Arg : Args) 451 Arg->claim(); 452 const char *Exec = 453 Args.MakeArgString(getToolChain().GetProgramPath("touch")); 454 CmdArgs.push_back(Output.getFilename()); 455 C.addCommand(std::make_unique<Command>(JA, *this, Exec, CmdArgs, None)); 456 return; 457 } 458 459 // I'm not sure why this particular decomposition exists in gcc, but 460 // we follow suite for ease of comparison. 461 AddLinkArgs(C, Args, CmdArgs, Inputs); 462 463 // For LTO, pass the name of the optimization record file and other 464 // opt-remarks flags. 465 if (Args.hasFlag(options::OPT_fsave_optimization_record, 466 options::OPT_fsave_optimization_record_EQ, 467 options::OPT_fno_save_optimization_record, false)) { 468 CmdArgs.push_back("-mllvm"); 469 CmdArgs.push_back("-lto-pass-remarks-output"); 470 CmdArgs.push_back("-mllvm"); 471 472 SmallString<128> F; 473 F = Output.getFilename(); 474 F += ".opt."; 475 if (const Arg *A = 476 Args.getLastArg(options::OPT_fsave_optimization_record_EQ)) 477 F += A->getValue(); 478 else 479 F += "yaml"; 480 481 CmdArgs.push_back(Args.MakeArgString(F)); 482 483 if (getLastProfileUseArg(Args)) { 484 CmdArgs.push_back("-mllvm"); 485 CmdArgs.push_back("-lto-pass-remarks-with-hotness"); 486 487 if (const Arg *A = 488 Args.getLastArg(options::OPT_fdiagnostics_hotness_threshold_EQ)) { 489 CmdArgs.push_back("-mllvm"); 490 std::string Opt = 491 std::string("-lto-pass-remarks-hotness-threshold=") + A->getValue(); 492 CmdArgs.push_back(Args.MakeArgString(Opt)); 493 } 494 } 495 496 if (const Arg *A = 497 Args.getLastArg(options::OPT_foptimization_record_passes_EQ)) { 498 CmdArgs.push_back("-mllvm"); 499 std::string Passes = 500 std::string("-lto-pass-remarks-filter=") + A->getValue(); 501 CmdArgs.push_back(Args.MakeArgString(Passes)); 502 } 503 504 if (const Arg *A = 505 Args.getLastArg(options::OPT_fsave_optimization_record_EQ)) { 506 CmdArgs.push_back("-mllvm"); 507 std::string Format = 508 std::string("-lto-pass-remarks-format=") + A->getValue(); 509 CmdArgs.push_back(Args.MakeArgString(Format)); 510 } 511 } 512 513 // Propagate the -moutline flag to the linker in LTO. 514 if (Arg *A = 515 Args.getLastArg(options::OPT_moutline, options::OPT_mno_outline)) { 516 if (A->getOption().matches(options::OPT_moutline)) { 517 if (getMachOToolChain().getMachOArchName(Args) == "arm64") { 518 CmdArgs.push_back("-mllvm"); 519 CmdArgs.push_back("-enable-machine-outliner"); 520 521 // Outline from linkonceodr functions by default in LTO. 522 CmdArgs.push_back("-mllvm"); 523 CmdArgs.push_back("-enable-linkonceodr-outlining"); 524 } 525 } else { 526 // Disable all outlining behaviour if we have mno-outline. We need to do 527 // this explicitly, because targets which support default outlining will 528 // try to do work if we don't. 529 CmdArgs.push_back("-mllvm"); 530 CmdArgs.push_back("-enable-machine-outliner=never"); 531 } 532 } 533 534 // Setup statistics file output. 535 SmallString<128> StatsFile = 536 getStatsFileName(Args, Output, Inputs[0], getToolChain().getDriver()); 537 if (!StatsFile.empty()) { 538 CmdArgs.push_back("-mllvm"); 539 CmdArgs.push_back(Args.MakeArgString("-lto-stats-file=" + StatsFile.str())); 540 } 541 542 // It seems that the 'e' option is completely ignored for dynamic executables 543 // (the default), and with static executables, the last one wins, as expected. 544 Args.AddAllArgs(CmdArgs, {options::OPT_d_Flag, options::OPT_s, options::OPT_t, 545 options::OPT_Z_Flag, options::OPT_u_Group, 546 options::OPT_e, options::OPT_r}); 547 548 // Forward -ObjC when either -ObjC or -ObjC++ is used, to force loading 549 // members of static archive libraries which implement Objective-C classes or 550 // categories. 551 if (Args.hasArg(options::OPT_ObjC) || Args.hasArg(options::OPT_ObjCXX)) 552 CmdArgs.push_back("-ObjC"); 553 554 CmdArgs.push_back("-o"); 555 CmdArgs.push_back(Output.getFilename()); 556 557 if (!Args.hasArg(options::OPT_nostdlib, options::OPT_nostartfiles)) 558 getMachOToolChain().addStartObjectFileArgs(Args, CmdArgs); 559 560 Args.AddAllArgs(CmdArgs, options::OPT_L); 561 562 AddLinkerInputs(getToolChain(), Inputs, Args, CmdArgs, JA); 563 // Build the input file for -filelist (list of linker input files) in case we 564 // need it later 565 for (const auto &II : Inputs) { 566 if (!II.isFilename()) { 567 // This is a linker input argument. 568 // We cannot mix input arguments and file names in a -filelist input, thus 569 // we prematurely stop our list (remaining files shall be passed as 570 // arguments). 571 if (InputFileList.size() > 0) 572 break; 573 574 continue; 575 } 576 577 InputFileList.push_back(II.getFilename()); 578 } 579 580 if (!Args.hasArg(options::OPT_nostdlib, options::OPT_nodefaultlibs)) 581 addOpenMPRuntime(CmdArgs, getToolChain(), Args); 582 583 if (isObjCRuntimeLinked(Args) && 584 !Args.hasArg(options::OPT_nostdlib, options::OPT_nodefaultlibs)) { 585 // We use arclite library for both ARC and subscripting support. 586 getMachOToolChain().AddLinkARCArgs(Args, CmdArgs); 587 588 CmdArgs.push_back("-framework"); 589 CmdArgs.push_back("Foundation"); 590 // Link libobj. 591 CmdArgs.push_back("-lobjc"); 592 } 593 594 if (LinkingOutput) { 595 CmdArgs.push_back("-arch_multiple"); 596 CmdArgs.push_back("-final_output"); 597 CmdArgs.push_back(LinkingOutput); 598 } 599 600 if (Args.hasArg(options::OPT_fnested_functions)) 601 CmdArgs.push_back("-allow_stack_execute"); 602 603 getMachOToolChain().addProfileRTLibs(Args, CmdArgs); 604 605 if (unsigned Parallelism = 606 getLTOParallelism(Args, getToolChain().getDriver())) { 607 CmdArgs.push_back("-mllvm"); 608 CmdArgs.push_back(Args.MakeArgString("-threads=" + Twine(Parallelism))); 609 } 610 611 if (getToolChain().ShouldLinkCXXStdlib(Args)) 612 getToolChain().AddCXXStdlibLibArgs(Args, CmdArgs); 613 614 bool NoStdOrDefaultLibs = 615 Args.hasArg(options::OPT_nostdlib, options::OPT_nodefaultlibs); 616 bool ForceLinkBuiltins = Args.hasArg(options::OPT_fapple_link_rtlib); 617 if (!NoStdOrDefaultLibs || ForceLinkBuiltins) { 618 // link_ssp spec is empty. 619 620 // If we have both -nostdlib/nodefaultlibs and -fapple-link-rtlib then 621 // we just want to link the builtins, not the other libs like libSystem. 622 if (NoStdOrDefaultLibs && ForceLinkBuiltins) { 623 getMachOToolChain().AddLinkRuntimeLib(Args, CmdArgs, "builtins"); 624 } else { 625 // Let the tool chain choose which runtime library to link. 626 getMachOToolChain().AddLinkRuntimeLibArgs(Args, CmdArgs, 627 ForceLinkBuiltins); 628 629 // No need to do anything for pthreads. Claim argument to avoid warning. 630 Args.ClaimAllArgs(options::OPT_pthread); 631 Args.ClaimAllArgs(options::OPT_pthreads); 632 } 633 } 634 635 if (!Args.hasArg(options::OPT_nostdlib, options::OPT_nostartfiles)) { 636 // endfile_spec is empty. 637 } 638 639 Args.AddAllArgs(CmdArgs, options::OPT_T_Group); 640 Args.AddAllArgs(CmdArgs, options::OPT_F); 641 642 // -iframework should be forwarded as -F. 643 for (const Arg *A : Args.filtered(options::OPT_iframework)) 644 CmdArgs.push_back(Args.MakeArgString(std::string("-F") + A->getValue())); 645 646 if (!Args.hasArg(options::OPT_nostdlib, options::OPT_nodefaultlibs)) { 647 if (Arg *A = Args.getLastArg(options::OPT_fveclib)) { 648 if (A->getValue() == StringRef("Accelerate")) { 649 CmdArgs.push_back("-framework"); 650 CmdArgs.push_back("Accelerate"); 651 } 652 } 653 } 654 655 const char *Exec = Args.MakeArgString(getToolChain().GetLinkerPath()); 656 std::unique_ptr<Command> Cmd = 657 std::make_unique<Command>(JA, *this, Exec, CmdArgs, Inputs); 658 Cmd->setInputFileList(std::move(InputFileList)); 659 C.addCommand(std::move(Cmd)); 660 } 661 662 void darwin::Lipo::ConstructJob(Compilation &C, const JobAction &JA, 663 const InputInfo &Output, 664 const InputInfoList &Inputs, 665 const ArgList &Args, 666 const char *LinkingOutput) const { 667 ArgStringList CmdArgs; 668 669 CmdArgs.push_back("-create"); 670 assert(Output.isFilename() && "Unexpected lipo output."); 671 672 CmdArgs.push_back("-output"); 673 CmdArgs.push_back(Output.getFilename()); 674 675 for (const auto &II : Inputs) { 676 assert(II.isFilename() && "Unexpected lipo input."); 677 CmdArgs.push_back(II.getFilename()); 678 } 679 680 const char *Exec = Args.MakeArgString(getToolChain().GetProgramPath("lipo")); 681 C.addCommand(std::make_unique<Command>(JA, *this, Exec, CmdArgs, Inputs)); 682 } 683 684 void darwin::Dsymutil::ConstructJob(Compilation &C, const JobAction &JA, 685 const InputInfo &Output, 686 const InputInfoList &Inputs, 687 const ArgList &Args, 688 const char *LinkingOutput) const { 689 ArgStringList CmdArgs; 690 691 CmdArgs.push_back("-o"); 692 CmdArgs.push_back(Output.getFilename()); 693 694 assert(Inputs.size() == 1 && "Unable to handle multiple inputs."); 695 const InputInfo &Input = Inputs[0]; 696 assert(Input.isFilename() && "Unexpected dsymutil input."); 697 CmdArgs.push_back(Input.getFilename()); 698 699 const char *Exec = 700 Args.MakeArgString(getToolChain().GetProgramPath("dsymutil")); 701 C.addCommand(std::make_unique<Command>(JA, *this, Exec, CmdArgs, Inputs)); 702 } 703 704 void darwin::VerifyDebug::ConstructJob(Compilation &C, const JobAction &JA, 705 const InputInfo &Output, 706 const InputInfoList &Inputs, 707 const ArgList &Args, 708 const char *LinkingOutput) const { 709 ArgStringList CmdArgs; 710 CmdArgs.push_back("--verify"); 711 CmdArgs.push_back("--debug-info"); 712 CmdArgs.push_back("--eh-frame"); 713 CmdArgs.push_back("--quiet"); 714 715 assert(Inputs.size() == 1 && "Unable to handle multiple inputs."); 716 const InputInfo &Input = Inputs[0]; 717 assert(Input.isFilename() && "Unexpected verify input"); 718 719 // Grabbing the output of the earlier dsymutil run. 720 CmdArgs.push_back(Input.getFilename()); 721 722 const char *Exec = 723 Args.MakeArgString(getToolChain().GetProgramPath("dwarfdump")); 724 C.addCommand(std::make_unique<Command>(JA, *this, Exec, CmdArgs, Inputs)); 725 } 726 727 MachO::MachO(const Driver &D, const llvm::Triple &Triple, const ArgList &Args) 728 : ToolChain(D, Triple, Args) { 729 // We expect 'as', 'ld', etc. to be adjacent to our install dir. 730 getProgramPaths().push_back(getDriver().getInstalledDir()); 731 if (getDriver().getInstalledDir() != getDriver().Dir) 732 getProgramPaths().push_back(getDriver().Dir); 733 } 734 735 /// Darwin - Darwin tool chain for i386 and x86_64. 736 Darwin::Darwin(const Driver &D, const llvm::Triple &Triple, const ArgList &Args) 737 : MachO(D, Triple, Args), TargetInitialized(false), 738 CudaInstallation(D, Triple, Args) {} 739 740 types::ID MachO::LookupTypeForExtension(StringRef Ext) const { 741 types::ID Ty = ToolChain::LookupTypeForExtension(Ext); 742 743 // Darwin always preprocesses assembly files (unless -x is used explicitly). 744 if (Ty == types::TY_PP_Asm) 745 return types::TY_Asm; 746 747 return Ty; 748 } 749 750 bool MachO::HasNativeLLVMSupport() const { return true; } 751 752 ToolChain::CXXStdlibType Darwin::GetDefaultCXXStdlibType() const { 753 // Default to use libc++ on OS X 10.9+ and iOS 7+. 754 if ((isTargetMacOS() && !isMacosxVersionLT(10, 9)) || 755 (isTargetIOSBased() && !isIPhoneOSVersionLT(7, 0)) || 756 isTargetWatchOSBased()) 757 return ToolChain::CST_Libcxx; 758 759 return ToolChain::CST_Libstdcxx; 760 } 761 762 /// Darwin provides an ARC runtime starting in MacOS X 10.7 and iOS 5.0. 763 ObjCRuntime Darwin::getDefaultObjCRuntime(bool isNonFragile) const { 764 if (isTargetWatchOSBased()) 765 return ObjCRuntime(ObjCRuntime::WatchOS, TargetVersion); 766 if (isTargetIOSBased()) 767 return ObjCRuntime(ObjCRuntime::iOS, TargetVersion); 768 if (isNonFragile) 769 return ObjCRuntime(ObjCRuntime::MacOSX, TargetVersion); 770 return ObjCRuntime(ObjCRuntime::FragileMacOSX, TargetVersion); 771 } 772 773 /// Darwin provides a blocks runtime starting in MacOS X 10.6 and iOS 3.2. 774 bool Darwin::hasBlocksRuntime() const { 775 if (isTargetWatchOSBased()) 776 return true; 777 else if (isTargetIOSBased()) 778 return !isIPhoneOSVersionLT(3, 2); 779 else { 780 assert(isTargetMacOS() && "unexpected darwin target"); 781 return !isMacosxVersionLT(10, 6); 782 } 783 } 784 785 void Darwin::AddCudaIncludeArgs(const ArgList &DriverArgs, 786 ArgStringList &CC1Args) const { 787 CudaInstallation.AddCudaIncludeArgs(DriverArgs, CC1Args); 788 } 789 790 // This is just a MachO name translation routine and there's no 791 // way to join this into ARMTargetParser without breaking all 792 // other assumptions. Maybe MachO should consider standardising 793 // their nomenclature. 794 static const char *ArmMachOArchName(StringRef Arch) { 795 return llvm::StringSwitch<const char *>(Arch) 796 .Case("armv6k", "armv6") 797 .Case("armv6m", "armv6m") 798 .Case("armv5tej", "armv5") 799 .Case("xscale", "xscale") 800 .Case("armv4t", "armv4t") 801 .Case("armv7", "armv7") 802 .Cases("armv7a", "armv7-a", "armv7") 803 .Cases("armv7r", "armv7-r", "armv7") 804 .Cases("armv7em", "armv7e-m", "armv7em") 805 .Cases("armv7k", "armv7-k", "armv7k") 806 .Cases("armv7m", "armv7-m", "armv7m") 807 .Cases("armv7s", "armv7-s", "armv7s") 808 .Default(nullptr); 809 } 810 811 static const char *ArmMachOArchNameCPU(StringRef CPU) { 812 llvm::ARM::ArchKind ArchKind = llvm::ARM::parseCPUArch(CPU); 813 if (ArchKind == llvm::ARM::ArchKind::INVALID) 814 return nullptr; 815 StringRef Arch = llvm::ARM::getArchName(ArchKind); 816 817 // FIXME: Make sure this MachO triple mangling is really necessary. 818 // ARMv5* normalises to ARMv5. 819 if (Arch.startswith("armv5")) 820 Arch = Arch.substr(0, 5); 821 // ARMv6*, except ARMv6M, normalises to ARMv6. 822 else if (Arch.startswith("armv6") && !Arch.endswith("6m")) 823 Arch = Arch.substr(0, 5); 824 // ARMv7A normalises to ARMv7. 825 else if (Arch.endswith("v7a")) 826 Arch = Arch.substr(0, 5); 827 return Arch.data(); 828 } 829 830 StringRef MachO::getMachOArchName(const ArgList &Args) const { 831 switch (getTriple().getArch()) { 832 default: 833 return getDefaultUniversalArchName(); 834 835 case llvm::Triple::aarch64: 836 return "arm64"; 837 838 case llvm::Triple::thumb: 839 case llvm::Triple::arm: 840 if (const Arg *A = Args.getLastArg(clang::driver::options::OPT_march_EQ)) 841 if (const char *Arch = ArmMachOArchName(A->getValue())) 842 return Arch; 843 844 if (const Arg *A = Args.getLastArg(options::OPT_mcpu_EQ)) 845 if (const char *Arch = ArmMachOArchNameCPU(A->getValue())) 846 return Arch; 847 848 return "arm"; 849 } 850 } 851 852 Darwin::~Darwin() {} 853 854 MachO::~MachO() {} 855 856 std::string Darwin::ComputeEffectiveClangTriple(const ArgList &Args, 857 types::ID InputType) const { 858 llvm::Triple Triple(ComputeLLVMTriple(Args, InputType)); 859 860 // If the target isn't initialized (e.g., an unknown Darwin platform, return 861 // the default triple). 862 if (!isTargetInitialized()) 863 return Triple.getTriple(); 864 865 SmallString<16> Str; 866 if (isTargetWatchOSBased()) 867 Str += "watchos"; 868 else if (isTargetTvOSBased()) 869 Str += "tvos"; 870 else if (isTargetIOSBased()) 871 Str += "ios"; 872 else 873 Str += "macosx"; 874 Str += getTargetVersion().getAsString(); 875 Triple.setOSName(Str); 876 877 return Triple.getTriple(); 878 } 879 880 Tool *MachO::getTool(Action::ActionClass AC) const { 881 switch (AC) { 882 case Action::LipoJobClass: 883 if (!Lipo) 884 Lipo.reset(new tools::darwin::Lipo(*this)); 885 return Lipo.get(); 886 case Action::DsymutilJobClass: 887 if (!Dsymutil) 888 Dsymutil.reset(new tools::darwin::Dsymutil(*this)); 889 return Dsymutil.get(); 890 case Action::VerifyDebugInfoJobClass: 891 if (!VerifyDebug) 892 VerifyDebug.reset(new tools::darwin::VerifyDebug(*this)); 893 return VerifyDebug.get(); 894 default: 895 return ToolChain::getTool(AC); 896 } 897 } 898 899 Tool *MachO::buildLinker() const { return new tools::darwin::Linker(*this); } 900 901 Tool *MachO::buildAssembler() const { 902 return new tools::darwin::Assembler(*this); 903 } 904 905 DarwinClang::DarwinClang(const Driver &D, const llvm::Triple &Triple, 906 const ArgList &Args) 907 : Darwin(D, Triple, Args) {} 908 909 void DarwinClang::addClangWarningOptions(ArgStringList &CC1Args) const { 910 // For modern targets, promote certain warnings to errors. 911 if (isTargetWatchOSBased() || getTriple().isArch64Bit()) { 912 // Always enable -Wdeprecated-objc-isa-usage and promote it 913 // to an error. 914 CC1Args.push_back("-Wdeprecated-objc-isa-usage"); 915 CC1Args.push_back("-Werror=deprecated-objc-isa-usage"); 916 917 // For iOS and watchOS, also error about implicit function declarations, 918 // as that can impact calling conventions. 919 if (!isTargetMacOS()) 920 CC1Args.push_back("-Werror=implicit-function-declaration"); 921 } 922 } 923 924 /// Take a path that speculatively points into Xcode and return the 925 /// `XCODE/Contents/Developer` path if it is an Xcode path, or an empty path 926 /// otherwise. 927 static StringRef getXcodeDeveloperPath(StringRef PathIntoXcode) { 928 static constexpr llvm::StringLiteral XcodeAppSuffix( 929 ".app/Contents/Developer"); 930 size_t Index = PathIntoXcode.find(XcodeAppSuffix); 931 if (Index == StringRef::npos) 932 return ""; 933 return PathIntoXcode.take_front(Index + XcodeAppSuffix.size()); 934 } 935 936 void DarwinClang::AddLinkARCArgs(const ArgList &Args, 937 ArgStringList &CmdArgs) const { 938 // Avoid linking compatibility stubs on i386 mac. 939 if (isTargetMacOS() && getArch() == llvm::Triple::x86) 940 return; 941 942 ObjCRuntime runtime = getDefaultObjCRuntime(/*nonfragile*/ true); 943 944 if ((runtime.hasNativeARC() || !isObjCAutoRefCount(Args)) && 945 runtime.hasSubscripting()) 946 return; 947 948 SmallString<128> P(getDriver().ClangExecutable); 949 llvm::sys::path::remove_filename(P); // 'clang' 950 llvm::sys::path::remove_filename(P); // 'bin' 951 952 // 'libarclite' usually lives in the same toolchain as 'clang'. However, the 953 // Swift open source toolchains for macOS distribute Clang without libarclite. 954 // In that case, to allow the linker to find 'libarclite', we point to the 955 // 'libarclite' in the XcodeDefault toolchain instead. 956 if (getXcodeDeveloperPath(P).empty()) { 957 if (const Arg *A = Args.getLastArg(options::OPT_isysroot)) { 958 // Try to infer the path to 'libarclite' in the toolchain from the 959 // specified SDK path. 960 StringRef XcodePathForSDK = getXcodeDeveloperPath(A->getValue()); 961 if (!XcodePathForSDK.empty()) { 962 P = XcodePathForSDK; 963 llvm::sys::path::append(P, "Toolchains/XcodeDefault.xctoolchain/usr"); 964 } 965 } 966 } 967 968 CmdArgs.push_back("-force_load"); 969 llvm::sys::path::append(P, "lib", "arc", "libarclite_"); 970 // Mash in the platform. 971 if (isTargetWatchOSSimulator()) 972 P += "watchsimulator"; 973 else if (isTargetWatchOS()) 974 P += "watchos"; 975 else if (isTargetTvOSSimulator()) 976 P += "appletvsimulator"; 977 else if (isTargetTvOS()) 978 P += "appletvos"; 979 else if (isTargetIOSSimulator()) 980 P += "iphonesimulator"; 981 else if (isTargetIPhoneOS()) 982 P += "iphoneos"; 983 else 984 P += "macosx"; 985 P += ".a"; 986 987 CmdArgs.push_back(Args.MakeArgString(P)); 988 } 989 990 unsigned DarwinClang::GetDefaultDwarfVersion() const { 991 // Default to use DWARF 2 on OS X 10.10 / iOS 8 and lower. 992 if ((isTargetMacOS() && isMacosxVersionLT(10, 11)) || 993 (isTargetIOSBased() && isIPhoneOSVersionLT(9))) 994 return 2; 995 return 4; 996 } 997 998 void MachO::AddLinkRuntimeLib(const ArgList &Args, ArgStringList &CmdArgs, 999 StringRef Component, RuntimeLinkOptions Opts, 1000 bool IsShared) const { 1001 SmallString<64> DarwinLibName = StringRef("libclang_rt."); 1002 // an Darwin the builtins compomnent is not in the library name 1003 if (Component != "builtins") { 1004 DarwinLibName += Component; 1005 if (!(Opts & RLO_IsEmbedded)) 1006 DarwinLibName += "_"; 1007 DarwinLibName += getOSLibraryNameSuffix(); 1008 } else 1009 DarwinLibName += getOSLibraryNameSuffix(true); 1010 1011 DarwinLibName += IsShared ? "_dynamic.dylib" : ".a"; 1012 SmallString<128> Dir(getDriver().ResourceDir); 1013 llvm::sys::path::append( 1014 Dir, "lib", (Opts & RLO_IsEmbedded) ? "macho_embedded" : "darwin"); 1015 1016 SmallString<128> P(Dir); 1017 llvm::sys::path::append(P, DarwinLibName); 1018 1019 // For now, allow missing resource libraries to support developers who may 1020 // not have compiler-rt checked out or integrated into their build (unless 1021 // we explicitly force linking with this library). 1022 if ((Opts & RLO_AlwaysLink) || getVFS().exists(P)) { 1023 const char *LibArg = Args.MakeArgString(P); 1024 if (Opts & RLO_FirstLink) 1025 CmdArgs.insert(CmdArgs.begin(), LibArg); 1026 else 1027 CmdArgs.push_back(LibArg); 1028 } 1029 1030 // Adding the rpaths might negatively interact when other rpaths are involved, 1031 // so we should make sure we add the rpaths last, after all user-specified 1032 // rpaths. This is currently true from this place, but we need to be 1033 // careful if this function is ever called before user's rpaths are emitted. 1034 if (Opts & RLO_AddRPath) { 1035 assert(DarwinLibName.endswith(".dylib") && "must be a dynamic library"); 1036 1037 // Add @executable_path to rpath to support having the dylib copied with 1038 // the executable. 1039 CmdArgs.push_back("-rpath"); 1040 CmdArgs.push_back("@executable_path"); 1041 1042 // Add the path to the resource dir to rpath to support using the dylib 1043 // from the default location without copying. 1044 CmdArgs.push_back("-rpath"); 1045 CmdArgs.push_back(Args.MakeArgString(Dir)); 1046 } 1047 } 1048 1049 StringRef Darwin::getPlatformFamily() const { 1050 switch (TargetPlatform) { 1051 case DarwinPlatformKind::MacOS: 1052 return "MacOSX"; 1053 case DarwinPlatformKind::IPhoneOS: 1054 return "iPhone"; 1055 case DarwinPlatformKind::TvOS: 1056 return "AppleTV"; 1057 case DarwinPlatformKind::WatchOS: 1058 return "Watch"; 1059 } 1060 llvm_unreachable("Unsupported platform"); 1061 } 1062 1063 StringRef Darwin::getSDKName(StringRef isysroot) { 1064 // Assume SDK has path: SOME_PATH/SDKs/PlatformXX.YY.sdk 1065 llvm::sys::path::const_iterator SDKDir; 1066 auto BeginSDK = llvm::sys::path::begin(isysroot); 1067 auto EndSDK = llvm::sys::path::end(isysroot); 1068 for (auto IT = BeginSDK; IT != EndSDK; ++IT) { 1069 StringRef SDK = *IT; 1070 if (SDK.endswith(".sdk")) 1071 return SDK.slice(0, SDK.size() - 4); 1072 } 1073 return ""; 1074 } 1075 1076 StringRef Darwin::getOSLibraryNameSuffix(bool IgnoreSim) const { 1077 switch (TargetPlatform) { 1078 case DarwinPlatformKind::MacOS: 1079 return "osx"; 1080 case DarwinPlatformKind::IPhoneOS: 1081 return TargetEnvironment == NativeEnvironment || IgnoreSim ? "ios" 1082 : "iossim"; 1083 case DarwinPlatformKind::TvOS: 1084 return TargetEnvironment == NativeEnvironment || IgnoreSim ? "tvos" 1085 : "tvossim"; 1086 case DarwinPlatformKind::WatchOS: 1087 return TargetEnvironment == NativeEnvironment || IgnoreSim ? "watchos" 1088 : "watchossim"; 1089 } 1090 llvm_unreachable("Unsupported platform"); 1091 } 1092 1093 /// Check if the link command contains a symbol export directive. 1094 static bool hasExportSymbolDirective(const ArgList &Args) { 1095 for (Arg *A : Args) { 1096 if (A->getOption().matches(options::OPT_exported__symbols__list)) 1097 return true; 1098 if (!A->getOption().matches(options::OPT_Wl_COMMA) && 1099 !A->getOption().matches(options::OPT_Xlinker)) 1100 continue; 1101 if (A->containsValue("-exported_symbols_list") || 1102 A->containsValue("-exported_symbol")) 1103 return true; 1104 } 1105 return false; 1106 } 1107 1108 /// Add an export directive for \p Symbol to the link command. 1109 static void addExportedSymbol(ArgStringList &CmdArgs, const char *Symbol) { 1110 CmdArgs.push_back("-exported_symbol"); 1111 CmdArgs.push_back(Symbol); 1112 } 1113 1114 /// Add a sectalign directive for \p Segment and \p Section to the maximum 1115 /// expected page size for Darwin. 1116 /// 1117 /// On iPhone 6+ the max supported page size is 16K. On macOS, the max is 4K. 1118 /// Use a common alignment constant (16K) for now, and reduce the alignment on 1119 /// macOS if it proves important. 1120 static void addSectalignToPage(const ArgList &Args, ArgStringList &CmdArgs, 1121 StringRef Segment, StringRef Section) { 1122 for (const char *A : {"-sectalign", Args.MakeArgString(Segment), 1123 Args.MakeArgString(Section), "0x4000"}) 1124 CmdArgs.push_back(A); 1125 } 1126 1127 void Darwin::addProfileRTLibs(const ArgList &Args, 1128 ArgStringList &CmdArgs) const { 1129 if (!needsProfileRT(Args)) return; 1130 1131 AddLinkRuntimeLib(Args, CmdArgs, "profile", 1132 RuntimeLinkOptions(RLO_AlwaysLink | RLO_FirstLink)); 1133 1134 bool ForGCOV = needsGCovInstrumentation(Args); 1135 1136 // If we have a symbol export directive and we're linking in the profile 1137 // runtime, automatically export symbols necessary to implement some of the 1138 // runtime's functionality. 1139 if (hasExportSymbolDirective(Args)) { 1140 if (ForGCOV) { 1141 addExportedSymbol(CmdArgs, "___gcov_flush"); 1142 addExportedSymbol(CmdArgs, "_flush_fn_list"); 1143 addExportedSymbol(CmdArgs, "_writeout_fn_list"); 1144 } else { 1145 addExportedSymbol(CmdArgs, "___llvm_profile_filename"); 1146 addExportedSymbol(CmdArgs, "___llvm_profile_raw_version"); 1147 } 1148 addExportedSymbol(CmdArgs, "_lprofDirMode"); 1149 } 1150 1151 // Align __llvm_prf_{cnts,data} sections to the maximum expected page 1152 // alignment. This allows profile counters to be mmap()'d to disk. Note that 1153 // it's not enough to just page-align __llvm_prf_cnts: the following section 1154 // must also be page-aligned so that its data is not clobbered by mmap(). 1155 // 1156 // The section alignment is only needed when continuous profile sync is 1157 // enabled, but this is expected to be the default in Xcode. Specifying the 1158 // extra alignment also allows the same binary to be used with/without sync 1159 // enabled. 1160 if (!ForGCOV) { 1161 for (auto IPSK : {llvm::IPSK_cnts, llvm::IPSK_data}) { 1162 addSectalignToPage( 1163 Args, CmdArgs, "__DATA", 1164 llvm::getInstrProfSectionName(IPSK, llvm::Triple::MachO, 1165 /*AddSegmentInfo=*/false)); 1166 } 1167 } 1168 } 1169 1170 void DarwinClang::AddLinkSanitizerLibArgs(const ArgList &Args, 1171 ArgStringList &CmdArgs, 1172 StringRef Sanitizer, 1173 bool Shared) const { 1174 auto RLO = RuntimeLinkOptions(RLO_AlwaysLink | (Shared ? RLO_AddRPath : 0U)); 1175 AddLinkRuntimeLib(Args, CmdArgs, Sanitizer, RLO, Shared); 1176 } 1177 1178 ToolChain::RuntimeLibType DarwinClang::GetRuntimeLibType( 1179 const ArgList &Args) const { 1180 if (Arg* A = Args.getLastArg(options::OPT_rtlib_EQ)) { 1181 StringRef Value = A->getValue(); 1182 if (Value != "compiler-rt") 1183 getDriver().Diag(clang::diag::err_drv_unsupported_rtlib_for_platform) 1184 << Value << "darwin"; 1185 } 1186 1187 return ToolChain::RLT_CompilerRT; 1188 } 1189 1190 void DarwinClang::AddLinkRuntimeLibArgs(const ArgList &Args, 1191 ArgStringList &CmdArgs, 1192 bool ForceLinkBuiltinRT) const { 1193 // Call once to ensure diagnostic is printed if wrong value was specified 1194 GetRuntimeLibType(Args); 1195 1196 // Darwin doesn't support real static executables, don't link any runtime 1197 // libraries with -static. 1198 if (Args.hasArg(options::OPT_static) || 1199 Args.hasArg(options::OPT_fapple_kext) || 1200 Args.hasArg(options::OPT_mkernel)) { 1201 if (ForceLinkBuiltinRT) 1202 AddLinkRuntimeLib(Args, CmdArgs, "builtins"); 1203 return; 1204 } 1205 1206 // Reject -static-libgcc for now, we can deal with this when and if someone 1207 // cares. This is useful in situations where someone wants to statically link 1208 // something like libstdc++, and needs its runtime support routines. 1209 if (const Arg *A = Args.getLastArg(options::OPT_static_libgcc)) { 1210 getDriver().Diag(diag::err_drv_unsupported_opt) << A->getAsString(Args); 1211 return; 1212 } 1213 1214 const SanitizerArgs &Sanitize = getSanitizerArgs(); 1215 if (Sanitize.needsAsanRt()) 1216 AddLinkSanitizerLibArgs(Args, CmdArgs, "asan"); 1217 if (Sanitize.needsLsanRt()) 1218 AddLinkSanitizerLibArgs(Args, CmdArgs, "lsan"); 1219 if (Sanitize.needsUbsanRt()) 1220 AddLinkSanitizerLibArgs(Args, CmdArgs, 1221 Sanitize.requiresMinimalRuntime() ? "ubsan_minimal" 1222 : "ubsan", 1223 Sanitize.needsSharedRt()); 1224 if (Sanitize.needsTsanRt()) 1225 AddLinkSanitizerLibArgs(Args, CmdArgs, "tsan"); 1226 if (Sanitize.needsFuzzer() && !Args.hasArg(options::OPT_dynamiclib)) { 1227 AddLinkSanitizerLibArgs(Args, CmdArgs, "fuzzer", /*shared=*/false); 1228 1229 // Libfuzzer is written in C++ and requires libcxx. 1230 AddCXXStdlibLibArgs(Args, CmdArgs); 1231 } 1232 if (Sanitize.needsStatsRt()) { 1233 AddLinkRuntimeLib(Args, CmdArgs, "stats_client", RLO_AlwaysLink); 1234 AddLinkSanitizerLibArgs(Args, CmdArgs, "stats"); 1235 } 1236 1237 const XRayArgs &XRay = getXRayArgs(); 1238 if (XRay.needsXRayRt()) { 1239 AddLinkRuntimeLib(Args, CmdArgs, "xray"); 1240 AddLinkRuntimeLib(Args, CmdArgs, "xray-basic"); 1241 AddLinkRuntimeLib(Args, CmdArgs, "xray-fdr"); 1242 } 1243 1244 // Otherwise link libSystem, then the dynamic runtime library, and finally any 1245 // target specific static runtime library. 1246 CmdArgs.push_back("-lSystem"); 1247 1248 // Select the dynamic runtime library and the target specific static library. 1249 if (isTargetIOSBased()) { 1250 // If we are compiling as iOS / simulator, don't attempt to link libgcc_s.1, 1251 // it never went into the SDK. 1252 // Linking against libgcc_s.1 isn't needed for iOS 5.0+ 1253 if (isIPhoneOSVersionLT(5, 0) && !isTargetIOSSimulator() && 1254 getTriple().getArch() != llvm::Triple::aarch64) 1255 CmdArgs.push_back("-lgcc_s.1"); 1256 } 1257 AddLinkRuntimeLib(Args, CmdArgs, "builtins"); 1258 } 1259 1260 /// Returns the most appropriate macOS target version for the current process. 1261 /// 1262 /// If the macOS SDK version is the same or earlier than the system version, 1263 /// then the SDK version is returned. Otherwise the system version is returned. 1264 static std::string getSystemOrSDKMacOSVersion(StringRef MacOSSDKVersion) { 1265 unsigned Major, Minor, Micro; 1266 llvm::Triple SystemTriple(llvm::sys::getProcessTriple()); 1267 if (!SystemTriple.isMacOSX()) 1268 return MacOSSDKVersion; 1269 SystemTriple.getMacOSXVersion(Major, Minor, Micro); 1270 VersionTuple SystemVersion(Major, Minor, Micro); 1271 bool HadExtra; 1272 if (!Driver::GetReleaseVersion(MacOSSDKVersion, Major, Minor, Micro, 1273 HadExtra)) 1274 return MacOSSDKVersion; 1275 VersionTuple SDKVersion(Major, Minor, Micro); 1276 if (SDKVersion > SystemVersion) 1277 return SystemVersion.getAsString(); 1278 return MacOSSDKVersion; 1279 } 1280 1281 namespace { 1282 1283 /// The Darwin OS that was selected or inferred from arguments / environment. 1284 struct DarwinPlatform { 1285 enum SourceKind { 1286 /// The OS was specified using the -target argument. 1287 TargetArg, 1288 /// The OS was specified using the -m<os>-version-min argument. 1289 OSVersionArg, 1290 /// The OS was specified using the OS_DEPLOYMENT_TARGET environment. 1291 DeploymentTargetEnv, 1292 /// The OS was inferred from the SDK. 1293 InferredFromSDK, 1294 /// The OS was inferred from the -arch. 1295 InferredFromArch 1296 }; 1297 1298 using DarwinPlatformKind = Darwin::DarwinPlatformKind; 1299 using DarwinEnvironmentKind = Darwin::DarwinEnvironmentKind; 1300 1301 DarwinPlatformKind getPlatform() const { return Platform; } 1302 1303 DarwinEnvironmentKind getEnvironment() const { return Environment; } 1304 1305 void setEnvironment(DarwinEnvironmentKind Kind) { 1306 Environment = Kind; 1307 InferSimulatorFromArch = false; 1308 } 1309 1310 StringRef getOSVersion() const { 1311 if (Kind == OSVersionArg) 1312 return Argument->getValue(); 1313 return OSVersion; 1314 } 1315 1316 void setOSVersion(StringRef S) { 1317 assert(Kind == TargetArg && "Unexpected kind!"); 1318 OSVersion = S; 1319 } 1320 1321 bool hasOSVersion() const { return HasOSVersion; } 1322 1323 /// Returns true if the target OS was explicitly specified. 1324 bool isExplicitlySpecified() const { return Kind <= DeploymentTargetEnv; } 1325 1326 /// Returns true if the simulator environment can be inferred from the arch. 1327 bool canInferSimulatorFromArch() const { return InferSimulatorFromArch; } 1328 1329 /// Adds the -m<os>-version-min argument to the compiler invocation. 1330 void addOSVersionMinArgument(DerivedArgList &Args, const OptTable &Opts) { 1331 if (Argument) 1332 return; 1333 assert(Kind != TargetArg && Kind != OSVersionArg && "Invalid kind"); 1334 options::ID Opt; 1335 switch (Platform) { 1336 case DarwinPlatformKind::MacOS: 1337 Opt = options::OPT_mmacosx_version_min_EQ; 1338 break; 1339 case DarwinPlatformKind::IPhoneOS: 1340 Opt = options::OPT_miphoneos_version_min_EQ; 1341 break; 1342 case DarwinPlatformKind::TvOS: 1343 Opt = options::OPT_mtvos_version_min_EQ; 1344 break; 1345 case DarwinPlatformKind::WatchOS: 1346 Opt = options::OPT_mwatchos_version_min_EQ; 1347 break; 1348 } 1349 Argument = Args.MakeJoinedArg(nullptr, Opts.getOption(Opt), OSVersion); 1350 Args.append(Argument); 1351 } 1352 1353 /// Returns the OS version with the argument / environment variable that 1354 /// specified it. 1355 std::string getAsString(DerivedArgList &Args, const OptTable &Opts) { 1356 switch (Kind) { 1357 case TargetArg: 1358 case OSVersionArg: 1359 case InferredFromSDK: 1360 case InferredFromArch: 1361 assert(Argument && "OS version argument not yet inferred"); 1362 return Argument->getAsString(Args); 1363 case DeploymentTargetEnv: 1364 return (llvm::Twine(EnvVarName) + "=" + OSVersion).str(); 1365 } 1366 llvm_unreachable("Unsupported Darwin Source Kind"); 1367 } 1368 1369 static DarwinPlatform createFromTarget(const llvm::Triple &TT, 1370 StringRef OSVersion, Arg *A) { 1371 DarwinPlatform Result(TargetArg, getPlatformFromOS(TT.getOS()), OSVersion, 1372 A); 1373 switch (TT.getEnvironment()) { 1374 case llvm::Triple::Simulator: 1375 Result.Environment = DarwinEnvironmentKind::Simulator; 1376 break; 1377 default: 1378 break; 1379 } 1380 unsigned Major, Minor, Micro; 1381 TT.getOSVersion(Major, Minor, Micro); 1382 if (Major == 0) 1383 Result.HasOSVersion = false; 1384 return Result; 1385 } 1386 static DarwinPlatform createOSVersionArg(DarwinPlatformKind Platform, 1387 Arg *A) { 1388 return DarwinPlatform(OSVersionArg, Platform, A); 1389 } 1390 static DarwinPlatform createDeploymentTargetEnv(DarwinPlatformKind Platform, 1391 StringRef EnvVarName, 1392 StringRef Value) { 1393 DarwinPlatform Result(DeploymentTargetEnv, Platform, Value); 1394 Result.EnvVarName = EnvVarName; 1395 return Result; 1396 } 1397 static DarwinPlatform createFromSDK(DarwinPlatformKind Platform, 1398 StringRef Value, 1399 bool IsSimulator = false) { 1400 DarwinPlatform Result(InferredFromSDK, Platform, Value); 1401 if (IsSimulator) 1402 Result.Environment = DarwinEnvironmentKind::Simulator; 1403 Result.InferSimulatorFromArch = false; 1404 return Result; 1405 } 1406 static DarwinPlatform createFromArch(llvm::Triple::OSType OS, 1407 StringRef Value) { 1408 return DarwinPlatform(InferredFromArch, getPlatformFromOS(OS), Value); 1409 } 1410 1411 /// Constructs an inferred SDKInfo value based on the version inferred from 1412 /// the SDK path itself. Only works for values that were created by inferring 1413 /// the platform from the SDKPath. 1414 DarwinSDKInfo inferSDKInfo() { 1415 assert(Kind == InferredFromSDK && "can infer SDK info only"); 1416 llvm::VersionTuple Version; 1417 bool IsValid = !Version.tryParse(OSVersion); 1418 (void)IsValid; 1419 assert(IsValid && "invalid SDK version"); 1420 return DarwinSDKInfo(Version); 1421 } 1422 1423 private: 1424 DarwinPlatform(SourceKind Kind, DarwinPlatformKind Platform, Arg *Argument) 1425 : Kind(Kind), Platform(Platform), Argument(Argument) {} 1426 DarwinPlatform(SourceKind Kind, DarwinPlatformKind Platform, StringRef Value, 1427 Arg *Argument = nullptr) 1428 : Kind(Kind), Platform(Platform), OSVersion(Value), Argument(Argument) {} 1429 1430 static DarwinPlatformKind getPlatformFromOS(llvm::Triple::OSType OS) { 1431 switch (OS) { 1432 case llvm::Triple::Darwin: 1433 case llvm::Triple::MacOSX: 1434 return DarwinPlatformKind::MacOS; 1435 case llvm::Triple::IOS: 1436 return DarwinPlatformKind::IPhoneOS; 1437 case llvm::Triple::TvOS: 1438 return DarwinPlatformKind::TvOS; 1439 case llvm::Triple::WatchOS: 1440 return DarwinPlatformKind::WatchOS; 1441 default: 1442 llvm_unreachable("Unable to infer Darwin variant"); 1443 } 1444 } 1445 1446 SourceKind Kind; 1447 DarwinPlatformKind Platform; 1448 DarwinEnvironmentKind Environment = DarwinEnvironmentKind::NativeEnvironment; 1449 std::string OSVersion; 1450 bool HasOSVersion = true, InferSimulatorFromArch = true; 1451 Arg *Argument; 1452 StringRef EnvVarName; 1453 }; 1454 1455 /// Returns the deployment target that's specified using the -m<os>-version-min 1456 /// argument. 1457 Optional<DarwinPlatform> 1458 getDeploymentTargetFromOSVersionArg(DerivedArgList &Args, 1459 const Driver &TheDriver) { 1460 Arg *OSXVersion = Args.getLastArg(options::OPT_mmacosx_version_min_EQ); 1461 Arg *iOSVersion = Args.getLastArg(options::OPT_miphoneos_version_min_EQ, 1462 options::OPT_mios_simulator_version_min_EQ); 1463 Arg *TvOSVersion = 1464 Args.getLastArg(options::OPT_mtvos_version_min_EQ, 1465 options::OPT_mtvos_simulator_version_min_EQ); 1466 Arg *WatchOSVersion = 1467 Args.getLastArg(options::OPT_mwatchos_version_min_EQ, 1468 options::OPT_mwatchos_simulator_version_min_EQ); 1469 if (OSXVersion) { 1470 if (iOSVersion || TvOSVersion || WatchOSVersion) { 1471 TheDriver.Diag(diag::err_drv_argument_not_allowed_with) 1472 << OSXVersion->getAsString(Args) 1473 << (iOSVersion ? iOSVersion 1474 : TvOSVersion ? TvOSVersion : WatchOSVersion) 1475 ->getAsString(Args); 1476 } 1477 return DarwinPlatform::createOSVersionArg(Darwin::MacOS, OSXVersion); 1478 } else if (iOSVersion) { 1479 if (TvOSVersion || WatchOSVersion) { 1480 TheDriver.Diag(diag::err_drv_argument_not_allowed_with) 1481 << iOSVersion->getAsString(Args) 1482 << (TvOSVersion ? TvOSVersion : WatchOSVersion)->getAsString(Args); 1483 } 1484 return DarwinPlatform::createOSVersionArg(Darwin::IPhoneOS, iOSVersion); 1485 } else if (TvOSVersion) { 1486 if (WatchOSVersion) { 1487 TheDriver.Diag(diag::err_drv_argument_not_allowed_with) 1488 << TvOSVersion->getAsString(Args) 1489 << WatchOSVersion->getAsString(Args); 1490 } 1491 return DarwinPlatform::createOSVersionArg(Darwin::TvOS, TvOSVersion); 1492 } else if (WatchOSVersion) 1493 return DarwinPlatform::createOSVersionArg(Darwin::WatchOS, WatchOSVersion); 1494 return None; 1495 } 1496 1497 /// Returns the deployment target that's specified using the 1498 /// OS_DEPLOYMENT_TARGET environment variable. 1499 Optional<DarwinPlatform> 1500 getDeploymentTargetFromEnvironmentVariables(const Driver &TheDriver, 1501 const llvm::Triple &Triple) { 1502 std::string Targets[Darwin::LastDarwinPlatform + 1]; 1503 const char *EnvVars[] = { 1504 "MACOSX_DEPLOYMENT_TARGET", 1505 "IPHONEOS_DEPLOYMENT_TARGET", 1506 "TVOS_DEPLOYMENT_TARGET", 1507 "WATCHOS_DEPLOYMENT_TARGET", 1508 }; 1509 static_assert(llvm::array_lengthof(EnvVars) == Darwin::LastDarwinPlatform + 1, 1510 "Missing platform"); 1511 for (const auto &I : llvm::enumerate(llvm::makeArrayRef(EnvVars))) { 1512 if (char *Env = ::getenv(I.value())) 1513 Targets[I.index()] = Env; 1514 } 1515 1516 // Allow conflicts among OSX and iOS for historical reasons, but choose the 1517 // default platform. 1518 if (!Targets[Darwin::MacOS].empty() && 1519 (!Targets[Darwin::IPhoneOS].empty() || 1520 !Targets[Darwin::WatchOS].empty() || !Targets[Darwin::TvOS].empty())) { 1521 if (Triple.getArch() == llvm::Triple::arm || 1522 Triple.getArch() == llvm::Triple::aarch64 || 1523 Triple.getArch() == llvm::Triple::thumb) 1524 Targets[Darwin::MacOS] = ""; 1525 else 1526 Targets[Darwin::IPhoneOS] = Targets[Darwin::WatchOS] = 1527 Targets[Darwin::TvOS] = ""; 1528 } else { 1529 // Don't allow conflicts in any other platform. 1530 int FirstTarget = llvm::array_lengthof(Targets); 1531 for (int I = 0; I != llvm::array_lengthof(Targets); ++I) { 1532 if (Targets[I].empty()) 1533 continue; 1534 if (FirstTarget == llvm::array_lengthof(Targets)) 1535 FirstTarget = I; 1536 else 1537 TheDriver.Diag(diag::err_drv_conflicting_deployment_targets) 1538 << Targets[FirstTarget] << Targets[I]; 1539 } 1540 } 1541 1542 for (const auto &Target : llvm::enumerate(llvm::makeArrayRef(Targets))) { 1543 if (!Target.value().empty()) 1544 return DarwinPlatform::createDeploymentTargetEnv( 1545 (Darwin::DarwinPlatformKind)Target.index(), EnvVars[Target.index()], 1546 Target.value()); 1547 } 1548 return None; 1549 } 1550 1551 /// Tries to infer the deployment target from the SDK specified by -isysroot 1552 /// (or SDKROOT). Uses the version specified in the SDKSettings.json file if 1553 /// it's available. 1554 Optional<DarwinPlatform> 1555 inferDeploymentTargetFromSDK(DerivedArgList &Args, 1556 const Optional<DarwinSDKInfo> &SDKInfo) { 1557 const Arg *A = Args.getLastArg(options::OPT_isysroot); 1558 if (!A) 1559 return None; 1560 StringRef isysroot = A->getValue(); 1561 StringRef SDK = Darwin::getSDKName(isysroot); 1562 if (!SDK.size()) 1563 return None; 1564 1565 std::string Version; 1566 if (SDKInfo) { 1567 // Get the version from the SDKSettings.json if it's available. 1568 Version = SDKInfo->getVersion().getAsString(); 1569 } else { 1570 // Slice the version number out. 1571 // Version number is between the first and the last number. 1572 size_t StartVer = SDK.find_first_of("0123456789"); 1573 size_t EndVer = SDK.find_last_of("0123456789"); 1574 if (StartVer != StringRef::npos && EndVer > StartVer) 1575 Version = SDK.slice(StartVer, EndVer + 1); 1576 } 1577 if (Version.empty()) 1578 return None; 1579 1580 if (SDK.startswith("iPhoneOS") || SDK.startswith("iPhoneSimulator")) 1581 return DarwinPlatform::createFromSDK( 1582 Darwin::IPhoneOS, Version, 1583 /*IsSimulator=*/SDK.startswith("iPhoneSimulator")); 1584 else if (SDK.startswith("MacOSX")) 1585 return DarwinPlatform::createFromSDK(Darwin::MacOS, 1586 getSystemOrSDKMacOSVersion(Version)); 1587 else if (SDK.startswith("WatchOS") || SDK.startswith("WatchSimulator")) 1588 return DarwinPlatform::createFromSDK( 1589 Darwin::WatchOS, Version, 1590 /*IsSimulator=*/SDK.startswith("WatchSimulator")); 1591 else if (SDK.startswith("AppleTVOS") || SDK.startswith("AppleTVSimulator")) 1592 return DarwinPlatform::createFromSDK( 1593 Darwin::TvOS, Version, 1594 /*IsSimulator=*/SDK.startswith("AppleTVSimulator")); 1595 return None; 1596 } 1597 1598 std::string getOSVersion(llvm::Triple::OSType OS, const llvm::Triple &Triple, 1599 const Driver &TheDriver) { 1600 unsigned Major, Minor, Micro; 1601 llvm::Triple SystemTriple(llvm::sys::getProcessTriple()); 1602 switch (OS) { 1603 case llvm::Triple::Darwin: 1604 case llvm::Triple::MacOSX: 1605 // If there is no version specified on triple, and both host and target are 1606 // macos, use the host triple to infer OS version. 1607 if (Triple.isMacOSX() && SystemTriple.isMacOSX() && 1608 !Triple.getOSMajorVersion()) 1609 SystemTriple.getMacOSXVersion(Major, Minor, Micro); 1610 else if (!Triple.getMacOSXVersion(Major, Minor, Micro)) 1611 TheDriver.Diag(diag::err_drv_invalid_darwin_version) 1612 << Triple.getOSName(); 1613 break; 1614 case llvm::Triple::IOS: 1615 Triple.getiOSVersion(Major, Minor, Micro); 1616 break; 1617 case llvm::Triple::TvOS: 1618 Triple.getOSVersion(Major, Minor, Micro); 1619 break; 1620 case llvm::Triple::WatchOS: 1621 Triple.getWatchOSVersion(Major, Minor, Micro); 1622 break; 1623 default: 1624 llvm_unreachable("Unexpected OS type"); 1625 break; 1626 } 1627 1628 std::string OSVersion; 1629 llvm::raw_string_ostream(OSVersion) << Major << '.' << Minor << '.' << Micro; 1630 return OSVersion; 1631 } 1632 1633 /// Tries to infer the target OS from the -arch. 1634 Optional<DarwinPlatform> 1635 inferDeploymentTargetFromArch(DerivedArgList &Args, const Darwin &Toolchain, 1636 const llvm::Triple &Triple, 1637 const Driver &TheDriver) { 1638 llvm::Triple::OSType OSTy = llvm::Triple::UnknownOS; 1639 1640 StringRef MachOArchName = Toolchain.getMachOArchName(Args); 1641 if (MachOArchName == "armv7" || MachOArchName == "armv7s" || 1642 MachOArchName == "arm64") 1643 OSTy = llvm::Triple::IOS; 1644 else if (MachOArchName == "armv7k") 1645 OSTy = llvm::Triple::WatchOS; 1646 else if (MachOArchName != "armv6m" && MachOArchName != "armv7m" && 1647 MachOArchName != "armv7em") 1648 OSTy = llvm::Triple::MacOSX; 1649 1650 if (OSTy == llvm::Triple::UnknownOS) 1651 return None; 1652 return DarwinPlatform::createFromArch(OSTy, 1653 getOSVersion(OSTy, Triple, TheDriver)); 1654 } 1655 1656 /// Returns the deployment target that's specified using the -target option. 1657 Optional<DarwinPlatform> getDeploymentTargetFromTargetArg( 1658 DerivedArgList &Args, const llvm::Triple &Triple, const Driver &TheDriver) { 1659 if (!Args.hasArg(options::OPT_target)) 1660 return None; 1661 if (Triple.getOS() == llvm::Triple::Darwin || 1662 Triple.getOS() == llvm::Triple::UnknownOS) 1663 return None; 1664 std::string OSVersion = getOSVersion(Triple.getOS(), Triple, TheDriver); 1665 return DarwinPlatform::createFromTarget(Triple, OSVersion, 1666 Args.getLastArg(options::OPT_target)); 1667 } 1668 1669 Optional<DarwinSDKInfo> parseSDKSettings(llvm::vfs::FileSystem &VFS, 1670 const ArgList &Args, 1671 const Driver &TheDriver) { 1672 const Arg *A = Args.getLastArg(options::OPT_isysroot); 1673 if (!A) 1674 return None; 1675 StringRef isysroot = A->getValue(); 1676 auto SDKInfoOrErr = driver::parseDarwinSDKInfo(VFS, isysroot); 1677 if (!SDKInfoOrErr) { 1678 llvm::consumeError(SDKInfoOrErr.takeError()); 1679 TheDriver.Diag(diag::warn_drv_darwin_sdk_invalid_settings); 1680 return None; 1681 } 1682 return *SDKInfoOrErr; 1683 } 1684 1685 } // namespace 1686 1687 void Darwin::AddDeploymentTarget(DerivedArgList &Args) const { 1688 const OptTable &Opts = getDriver().getOpts(); 1689 1690 // Support allowing the SDKROOT environment variable used by xcrun and other 1691 // Xcode tools to define the default sysroot, by making it the default for 1692 // isysroot. 1693 if (const Arg *A = Args.getLastArg(options::OPT_isysroot)) { 1694 // Warn if the path does not exist. 1695 if (!getVFS().exists(A->getValue())) 1696 getDriver().Diag(clang::diag::warn_missing_sysroot) << A->getValue(); 1697 } else { 1698 if (char *env = ::getenv("SDKROOT")) { 1699 // We only use this value as the default if it is an absolute path, 1700 // exists, and it is not the root path. 1701 if (llvm::sys::path::is_absolute(env) && getVFS().exists(env) && 1702 StringRef(env) != "/") { 1703 Args.append(Args.MakeSeparateArg( 1704 nullptr, Opts.getOption(options::OPT_isysroot), env)); 1705 } 1706 } 1707 } 1708 1709 // Read the SDKSettings.json file for more information, like the SDK version 1710 // that we can pass down to the compiler. 1711 SDKInfo = parseSDKSettings(getVFS(), Args, getDriver()); 1712 1713 // The OS and the version can be specified using the -target argument. 1714 Optional<DarwinPlatform> OSTarget = 1715 getDeploymentTargetFromTargetArg(Args, getTriple(), getDriver()); 1716 if (OSTarget) { 1717 Optional<DarwinPlatform> OSVersionArgTarget = 1718 getDeploymentTargetFromOSVersionArg(Args, getDriver()); 1719 if (OSVersionArgTarget) { 1720 unsigned TargetMajor, TargetMinor, TargetMicro; 1721 bool TargetExtra; 1722 unsigned ArgMajor, ArgMinor, ArgMicro; 1723 bool ArgExtra; 1724 if (OSTarget->getPlatform() != OSVersionArgTarget->getPlatform() || 1725 (Driver::GetReleaseVersion(OSTarget->getOSVersion(), TargetMajor, 1726 TargetMinor, TargetMicro, TargetExtra) && 1727 Driver::GetReleaseVersion(OSVersionArgTarget->getOSVersion(), 1728 ArgMajor, ArgMinor, ArgMicro, ArgExtra) && 1729 (VersionTuple(TargetMajor, TargetMinor, TargetMicro) != 1730 VersionTuple(ArgMajor, ArgMinor, ArgMicro) || 1731 TargetExtra != ArgExtra))) { 1732 // Select the OS version from the -m<os>-version-min argument when 1733 // the -target does not include an OS version. 1734 if (OSTarget->getPlatform() == OSVersionArgTarget->getPlatform() && 1735 !OSTarget->hasOSVersion()) { 1736 OSTarget->setOSVersion(OSVersionArgTarget->getOSVersion()); 1737 } else { 1738 // Warn about -m<os>-version-min that doesn't match the OS version 1739 // that's specified in the target. 1740 std::string OSVersionArg = 1741 OSVersionArgTarget->getAsString(Args, Opts); 1742 std::string TargetArg = OSTarget->getAsString(Args, Opts); 1743 getDriver().Diag(clang::diag::warn_drv_overriding_flag_option) 1744 << OSVersionArg << TargetArg; 1745 } 1746 } 1747 } 1748 } else { 1749 // The OS target can be specified using the -m<os>version-min argument. 1750 OSTarget = getDeploymentTargetFromOSVersionArg(Args, getDriver()); 1751 // If no deployment target was specified on the command line, check for 1752 // environment defines. 1753 if (!OSTarget) { 1754 OSTarget = 1755 getDeploymentTargetFromEnvironmentVariables(getDriver(), getTriple()); 1756 if (OSTarget) { 1757 // Don't infer simulator from the arch when the SDK is also specified. 1758 Optional<DarwinPlatform> SDKTarget = 1759 inferDeploymentTargetFromSDK(Args, SDKInfo); 1760 if (SDKTarget) 1761 OSTarget->setEnvironment(SDKTarget->getEnvironment()); 1762 } 1763 } 1764 // If there is no command-line argument to specify the Target version and 1765 // no environment variable defined, see if we can set the default based 1766 // on -isysroot using SDKSettings.json if it exists. 1767 if (!OSTarget) { 1768 OSTarget = inferDeploymentTargetFromSDK(Args, SDKInfo); 1769 /// If the target was successfully constructed from the SDK path, try to 1770 /// infer the SDK info if the SDK doesn't have it. 1771 if (OSTarget && !SDKInfo) 1772 SDKInfo = OSTarget->inferSDKInfo(); 1773 } 1774 // If no OS targets have been specified, try to guess platform from -target 1775 // or arch name and compute the version from the triple. 1776 if (!OSTarget) 1777 OSTarget = 1778 inferDeploymentTargetFromArch(Args, *this, getTriple(), getDriver()); 1779 } 1780 1781 assert(OSTarget && "Unable to infer Darwin variant"); 1782 OSTarget->addOSVersionMinArgument(Args, Opts); 1783 DarwinPlatformKind Platform = OSTarget->getPlatform(); 1784 1785 unsigned Major, Minor, Micro; 1786 bool HadExtra; 1787 // Set the tool chain target information. 1788 if (Platform == MacOS) { 1789 if (!Driver::GetReleaseVersion(OSTarget->getOSVersion(), Major, Minor, 1790 Micro, HadExtra) || 1791 HadExtra || Major != 10 || Minor >= 100 || Micro >= 100) 1792 getDriver().Diag(diag::err_drv_invalid_version_number) 1793 << OSTarget->getAsString(Args, Opts); 1794 } else if (Platform == IPhoneOS) { 1795 if (!Driver::GetReleaseVersion(OSTarget->getOSVersion(), Major, Minor, 1796 Micro, HadExtra) || 1797 HadExtra || Major >= 100 || Minor >= 100 || Micro >= 100) 1798 getDriver().Diag(diag::err_drv_invalid_version_number) 1799 << OSTarget->getAsString(Args, Opts); 1800 ; 1801 // For 32-bit targets, the deployment target for iOS has to be earlier than 1802 // iOS 11. 1803 if (getTriple().isArch32Bit() && Major >= 11) { 1804 // If the deployment target is explicitly specified, print a diagnostic. 1805 if (OSTarget->isExplicitlySpecified()) { 1806 getDriver().Diag(diag::warn_invalid_ios_deployment_target) 1807 << OSTarget->getAsString(Args, Opts); 1808 // Otherwise, set it to 10.99.99. 1809 } else { 1810 Major = 10; 1811 Minor = 99; 1812 Micro = 99; 1813 } 1814 } 1815 } else if (Platform == TvOS) { 1816 if (!Driver::GetReleaseVersion(OSTarget->getOSVersion(), Major, Minor, 1817 Micro, HadExtra) || 1818 HadExtra || Major >= 100 || Minor >= 100 || Micro >= 100) 1819 getDriver().Diag(diag::err_drv_invalid_version_number) 1820 << OSTarget->getAsString(Args, Opts); 1821 } else if (Platform == WatchOS) { 1822 if (!Driver::GetReleaseVersion(OSTarget->getOSVersion(), Major, Minor, 1823 Micro, HadExtra) || 1824 HadExtra || Major >= 10 || Minor >= 100 || Micro >= 100) 1825 getDriver().Diag(diag::err_drv_invalid_version_number) 1826 << OSTarget->getAsString(Args, Opts); 1827 } else 1828 llvm_unreachable("unknown kind of Darwin platform"); 1829 1830 DarwinEnvironmentKind Environment = OSTarget->getEnvironment(); 1831 // Recognize iOS targets with an x86 architecture as the iOS simulator. 1832 if (Environment == NativeEnvironment && Platform != MacOS && 1833 OSTarget->canInferSimulatorFromArch() && 1834 (getTriple().getArch() == llvm::Triple::x86 || 1835 getTriple().getArch() == llvm::Triple::x86_64)) 1836 Environment = Simulator; 1837 1838 setTarget(Platform, Environment, Major, Minor, Micro); 1839 1840 if (const Arg *A = Args.getLastArg(options::OPT_isysroot)) { 1841 StringRef SDK = getSDKName(A->getValue()); 1842 if (SDK.size() > 0) { 1843 size_t StartVer = SDK.find_first_of("0123456789"); 1844 StringRef SDKName = SDK.slice(0, StartVer); 1845 if (!SDKName.startswith(getPlatformFamily())) 1846 getDriver().Diag(diag::warn_incompatible_sysroot) 1847 << SDKName << getPlatformFamily(); 1848 } 1849 } 1850 } 1851 1852 // Returns the effective header sysroot path to use. This comes either from 1853 // -isysroot or --sysroot. 1854 llvm::StringRef DarwinClang::GetHeaderSysroot(const llvm::opt::ArgList &DriverArgs) const { 1855 if(DriverArgs.hasArg(options::OPT_isysroot)) 1856 return DriverArgs.getLastArgValue(options::OPT_isysroot); 1857 if (!getDriver().SysRoot.empty()) 1858 return getDriver().SysRoot; 1859 return "/"; 1860 } 1861 1862 void DarwinClang::AddClangSystemIncludeArgs(const llvm::opt::ArgList &DriverArgs, 1863 llvm::opt::ArgStringList &CC1Args) const { 1864 const Driver &D = getDriver(); 1865 1866 llvm::StringRef Sysroot = GetHeaderSysroot(DriverArgs); 1867 1868 bool NoStdInc = DriverArgs.hasArg(options::OPT_nostdinc); 1869 bool NoStdlibInc = DriverArgs.hasArg(options::OPT_nostdlibinc); 1870 bool NoBuiltinInc = DriverArgs.hasArg(options::OPT_nobuiltininc); 1871 1872 // Add <sysroot>/usr/local/include 1873 if (!NoStdInc && !NoStdlibInc) { 1874 SmallString<128> P(Sysroot); 1875 llvm::sys::path::append(P, "usr", "local", "include"); 1876 addSystemInclude(DriverArgs, CC1Args, P); 1877 } 1878 1879 // Add the Clang builtin headers (<resource>/include) 1880 if (!NoStdInc && !NoBuiltinInc) { 1881 SmallString<128> P(D.ResourceDir); 1882 llvm::sys::path::append(P, "include"); 1883 addSystemInclude(DriverArgs, CC1Args, P); 1884 } 1885 1886 if (NoStdInc || NoStdlibInc) 1887 return; 1888 1889 // Check for configure-time C include directories. 1890 llvm::StringRef CIncludeDirs(C_INCLUDE_DIRS); 1891 if (!CIncludeDirs.empty()) { 1892 llvm::SmallVector<llvm::StringRef, 5> dirs; 1893 CIncludeDirs.split(dirs, ":"); 1894 for (llvm::StringRef dir : dirs) { 1895 llvm::StringRef Prefix = 1896 llvm::sys::path::is_absolute(dir) ? llvm::StringRef(Sysroot) : ""; 1897 addExternCSystemInclude(DriverArgs, CC1Args, Prefix + dir); 1898 } 1899 } else { 1900 // Otherwise, add <sysroot>/usr/include. 1901 SmallString<128> P(Sysroot); 1902 llvm::sys::path::append(P, "usr", "include"); 1903 addExternCSystemInclude(DriverArgs, CC1Args, P.str()); 1904 } 1905 } 1906 1907 bool DarwinClang::AddGnuCPlusPlusIncludePaths(const llvm::opt::ArgList &DriverArgs, 1908 llvm::opt::ArgStringList &CC1Args, 1909 llvm::SmallString<128> Base, 1910 llvm::StringRef Version, 1911 llvm::StringRef ArchDir, 1912 llvm::StringRef BitDir) const { 1913 llvm::sys::path::append(Base, Version); 1914 1915 // Add the base dir 1916 addSystemInclude(DriverArgs, CC1Args, Base); 1917 1918 // Add the multilib dirs 1919 { 1920 llvm::SmallString<128> P = Base; 1921 if (!ArchDir.empty()) 1922 llvm::sys::path::append(P, ArchDir); 1923 if (!BitDir.empty()) 1924 llvm::sys::path::append(P, BitDir); 1925 addSystemInclude(DriverArgs, CC1Args, P); 1926 } 1927 1928 // Add the backward dir 1929 { 1930 llvm::SmallString<128> P = Base; 1931 llvm::sys::path::append(P, "backward"); 1932 addSystemInclude(DriverArgs, CC1Args, P); 1933 } 1934 1935 return getVFS().exists(Base); 1936 } 1937 1938 void DarwinClang::AddClangCXXStdlibIncludeArgs( 1939 const llvm::opt::ArgList &DriverArgs, 1940 llvm::opt::ArgStringList &CC1Args) const { 1941 // The implementation from a base class will pass through the -stdlib to 1942 // CC1Args. 1943 // FIXME: this should not be necessary, remove usages in the frontend 1944 // (e.g. HeaderSearchOptions::UseLibcxx) and don't pipe -stdlib. 1945 // Also check whether this is used for setting library search paths. 1946 ToolChain::AddClangCXXStdlibIncludeArgs(DriverArgs, CC1Args); 1947 1948 if (DriverArgs.hasArg(options::OPT_nostdlibinc) || 1949 DriverArgs.hasArg(options::OPT_nostdincxx)) 1950 return; 1951 1952 llvm::StringRef Sysroot = GetHeaderSysroot(DriverArgs); 1953 1954 switch (GetCXXStdlibType(DriverArgs)) { 1955 case ToolChain::CST_Libcxx: { 1956 // On Darwin, libc++ is installed alongside the compiler in 1957 // include/c++/v1, so get from '<install>/bin' to '<install>/include/c++/v1'. 1958 { 1959 llvm::SmallString<128> P = llvm::StringRef(getDriver().getInstalledDir()); 1960 // Note that P can be relative, so we have to '..' and not parent_path. 1961 llvm::sys::path::append(P, "..", "include", "c++", "v1"); 1962 addSystemInclude(DriverArgs, CC1Args, P); 1963 } 1964 // Also add <sysroot>/usr/include/c++/v1 unless -nostdinc is used, 1965 // to match the legacy behavior in CC1. 1966 if (!DriverArgs.hasArg(options::OPT_nostdinc)) { 1967 llvm::SmallString<128> P = Sysroot; 1968 llvm::sys::path::append(P, "usr", "include", "c++", "v1"); 1969 addSystemInclude(DriverArgs, CC1Args, P); 1970 } 1971 break; 1972 } 1973 1974 case ToolChain::CST_Libstdcxx: 1975 llvm::SmallString<128> UsrIncludeCxx = Sysroot; 1976 llvm::sys::path::append(UsrIncludeCxx, "usr", "include", "c++"); 1977 1978 llvm::Triple::ArchType arch = getTriple().getArch(); 1979 bool IsBaseFound = true; 1980 switch (arch) { 1981 default: break; 1982 1983 case llvm::Triple::ppc: 1984 case llvm::Triple::ppc64: 1985 IsBaseFound = AddGnuCPlusPlusIncludePaths(DriverArgs, CC1Args, UsrIncludeCxx, 1986 "4.2.1", 1987 "powerpc-apple-darwin10", 1988 arch == llvm::Triple::ppc64 ? "ppc64" : ""); 1989 IsBaseFound |= AddGnuCPlusPlusIncludePaths(DriverArgs, CC1Args, UsrIncludeCxx, 1990 "4.0.0", "powerpc-apple-darwin10", 1991 arch == llvm::Triple::ppc64 ? "ppc64" : ""); 1992 break; 1993 1994 case llvm::Triple::x86: 1995 case llvm::Triple::x86_64: 1996 IsBaseFound = AddGnuCPlusPlusIncludePaths(DriverArgs, CC1Args, UsrIncludeCxx, 1997 "4.2.1", 1998 "i686-apple-darwin10", 1999 arch == llvm::Triple::x86_64 ? "x86_64" : ""); 2000 IsBaseFound |= AddGnuCPlusPlusIncludePaths(DriverArgs, CC1Args, UsrIncludeCxx, 2001 "4.0.0", "i686-apple-darwin8", 2002 ""); 2003 break; 2004 2005 case llvm::Triple::arm: 2006 case llvm::Triple::thumb: 2007 IsBaseFound = AddGnuCPlusPlusIncludePaths(DriverArgs, CC1Args, UsrIncludeCxx, 2008 "4.2.1", 2009 "arm-apple-darwin10", 2010 "v7"); 2011 IsBaseFound |= AddGnuCPlusPlusIncludePaths(DriverArgs, CC1Args, UsrIncludeCxx, 2012 "4.2.1", 2013 "arm-apple-darwin10", 2014 "v6"); 2015 break; 2016 2017 case llvm::Triple::aarch64: 2018 IsBaseFound = AddGnuCPlusPlusIncludePaths(DriverArgs, CC1Args, UsrIncludeCxx, 2019 "4.2.1", 2020 "arm64-apple-darwin10", 2021 ""); 2022 break; 2023 } 2024 2025 if (!IsBaseFound) { 2026 getDriver().Diag(diag::warn_drv_libstdcxx_not_found); 2027 } 2028 2029 break; 2030 } 2031 } 2032 void DarwinClang::AddCXXStdlibLibArgs(const ArgList &Args, 2033 ArgStringList &CmdArgs) const { 2034 CXXStdlibType Type = GetCXXStdlibType(Args); 2035 2036 switch (Type) { 2037 case ToolChain::CST_Libcxx: 2038 CmdArgs.push_back("-lc++"); 2039 break; 2040 2041 case ToolChain::CST_Libstdcxx: 2042 // Unfortunately, -lstdc++ doesn't always exist in the standard search path; 2043 // it was previously found in the gcc lib dir. However, for all the Darwin 2044 // platforms we care about it was -lstdc++.6, so we search for that 2045 // explicitly if we can't see an obvious -lstdc++ candidate. 2046 2047 // Check in the sysroot first. 2048 if (const Arg *A = Args.getLastArg(options::OPT_isysroot)) { 2049 SmallString<128> P(A->getValue()); 2050 llvm::sys::path::append(P, "usr", "lib", "libstdc++.dylib"); 2051 2052 if (!getVFS().exists(P)) { 2053 llvm::sys::path::remove_filename(P); 2054 llvm::sys::path::append(P, "libstdc++.6.dylib"); 2055 if (getVFS().exists(P)) { 2056 CmdArgs.push_back(Args.MakeArgString(P)); 2057 return; 2058 } 2059 } 2060 } 2061 2062 // Otherwise, look in the root. 2063 // FIXME: This should be removed someday when we don't have to care about 2064 // 10.6 and earlier, where /usr/lib/libstdc++.dylib does not exist. 2065 if (!getVFS().exists("/usr/lib/libstdc++.dylib") && 2066 getVFS().exists("/usr/lib/libstdc++.6.dylib")) { 2067 CmdArgs.push_back("/usr/lib/libstdc++.6.dylib"); 2068 return; 2069 } 2070 2071 // Otherwise, let the linker search. 2072 CmdArgs.push_back("-lstdc++"); 2073 break; 2074 } 2075 } 2076 2077 void DarwinClang::AddCCKextLibArgs(const ArgList &Args, 2078 ArgStringList &CmdArgs) const { 2079 // For Darwin platforms, use the compiler-rt-based support library 2080 // instead of the gcc-provided one (which is also incidentally 2081 // only present in the gcc lib dir, which makes it hard to find). 2082 2083 SmallString<128> P(getDriver().ResourceDir); 2084 llvm::sys::path::append(P, "lib", "darwin"); 2085 2086 // Use the newer cc_kext for iOS ARM after 6.0. 2087 if (isTargetWatchOS()) { 2088 llvm::sys::path::append(P, "libclang_rt.cc_kext_watchos.a"); 2089 } else if (isTargetTvOS()) { 2090 llvm::sys::path::append(P, "libclang_rt.cc_kext_tvos.a"); 2091 } else if (isTargetIPhoneOS()) { 2092 llvm::sys::path::append(P, "libclang_rt.cc_kext_ios.a"); 2093 } else { 2094 llvm::sys::path::append(P, "libclang_rt.cc_kext.a"); 2095 } 2096 2097 // For now, allow missing resource libraries to support developers who may 2098 // not have compiler-rt checked out or integrated into their build. 2099 if (getVFS().exists(P)) 2100 CmdArgs.push_back(Args.MakeArgString(P)); 2101 } 2102 2103 DerivedArgList *MachO::TranslateArgs(const DerivedArgList &Args, 2104 StringRef BoundArch, 2105 Action::OffloadKind) const { 2106 DerivedArgList *DAL = new DerivedArgList(Args.getBaseArgs()); 2107 const OptTable &Opts = getDriver().getOpts(); 2108 2109 // FIXME: We really want to get out of the tool chain level argument 2110 // translation business, as it makes the driver functionality much 2111 // more opaque. For now, we follow gcc closely solely for the 2112 // purpose of easily achieving feature parity & testability. Once we 2113 // have something that works, we should reevaluate each translation 2114 // and try to push it down into tool specific logic. 2115 2116 for (Arg *A : Args) { 2117 if (A->getOption().matches(options::OPT_Xarch__)) { 2118 // Skip this argument unless the architecture matches either the toolchain 2119 // triple arch, or the arch being bound. 2120 llvm::Triple::ArchType XarchArch = 2121 tools::darwin::getArchTypeForMachOArchName(A->getValue(0)); 2122 if (!(XarchArch == getArch() || 2123 (!BoundArch.empty() && 2124 XarchArch == 2125 tools::darwin::getArchTypeForMachOArchName(BoundArch)))) 2126 continue; 2127 2128 Arg *OriginalArg = A; 2129 unsigned Index = Args.getBaseArgs().MakeIndex(A->getValue(1)); 2130 unsigned Prev = Index; 2131 std::unique_ptr<Arg> XarchArg(Opts.ParseOneArg(Args, Index)); 2132 2133 // If the argument parsing failed or more than one argument was 2134 // consumed, the -Xarch_ argument's parameter tried to consume 2135 // extra arguments. Emit an error and ignore. 2136 // 2137 // We also want to disallow any options which would alter the 2138 // driver behavior; that isn't going to work in our model. We 2139 // use isDriverOption() as an approximation, although things 2140 // like -O4 are going to slip through. 2141 if (!XarchArg || Index > Prev + 1) { 2142 getDriver().Diag(diag::err_drv_invalid_Xarch_argument_with_args) 2143 << A->getAsString(Args); 2144 continue; 2145 } else if (XarchArg->getOption().hasFlag(options::DriverOption)) { 2146 getDriver().Diag(diag::err_drv_invalid_Xarch_argument_isdriver) 2147 << A->getAsString(Args); 2148 continue; 2149 } 2150 2151 XarchArg->setBaseArg(A); 2152 2153 A = XarchArg.release(); 2154 DAL->AddSynthesizedArg(A); 2155 2156 // Linker input arguments require custom handling. The problem is that we 2157 // have already constructed the phase actions, so we can not treat them as 2158 // "input arguments". 2159 if (A->getOption().hasFlag(options::LinkerInput)) { 2160 // Convert the argument into individual Zlinker_input_args. 2161 for (const char *Value : A->getValues()) { 2162 DAL->AddSeparateArg( 2163 OriginalArg, Opts.getOption(options::OPT_Zlinker_input), Value); 2164 } 2165 continue; 2166 } 2167 } 2168 2169 // Sob. These is strictly gcc compatible for the time being. Apple 2170 // gcc translates options twice, which means that self-expanding 2171 // options add duplicates. 2172 switch ((options::ID)A->getOption().getID()) { 2173 default: 2174 DAL->append(A); 2175 break; 2176 2177 case options::OPT_mkernel: 2178 case options::OPT_fapple_kext: 2179 DAL->append(A); 2180 DAL->AddFlagArg(A, Opts.getOption(options::OPT_static)); 2181 break; 2182 2183 case options::OPT_dependency_file: 2184 DAL->AddSeparateArg(A, Opts.getOption(options::OPT_MF), A->getValue()); 2185 break; 2186 2187 case options::OPT_gfull: 2188 DAL->AddFlagArg(A, Opts.getOption(options::OPT_g_Flag)); 2189 DAL->AddFlagArg( 2190 A, Opts.getOption(options::OPT_fno_eliminate_unused_debug_symbols)); 2191 break; 2192 2193 case options::OPT_gused: 2194 DAL->AddFlagArg(A, Opts.getOption(options::OPT_g_Flag)); 2195 DAL->AddFlagArg( 2196 A, Opts.getOption(options::OPT_feliminate_unused_debug_symbols)); 2197 break; 2198 2199 case options::OPT_shared: 2200 DAL->AddFlagArg(A, Opts.getOption(options::OPT_dynamiclib)); 2201 break; 2202 2203 case options::OPT_fconstant_cfstrings: 2204 DAL->AddFlagArg(A, Opts.getOption(options::OPT_mconstant_cfstrings)); 2205 break; 2206 2207 case options::OPT_fno_constant_cfstrings: 2208 DAL->AddFlagArg(A, Opts.getOption(options::OPT_mno_constant_cfstrings)); 2209 break; 2210 2211 case options::OPT_Wnonportable_cfstrings: 2212 DAL->AddFlagArg(A, 2213 Opts.getOption(options::OPT_mwarn_nonportable_cfstrings)); 2214 break; 2215 2216 case options::OPT_Wno_nonportable_cfstrings: 2217 DAL->AddFlagArg( 2218 A, Opts.getOption(options::OPT_mno_warn_nonportable_cfstrings)); 2219 break; 2220 2221 case options::OPT_fpascal_strings: 2222 DAL->AddFlagArg(A, Opts.getOption(options::OPT_mpascal_strings)); 2223 break; 2224 2225 case options::OPT_fno_pascal_strings: 2226 DAL->AddFlagArg(A, Opts.getOption(options::OPT_mno_pascal_strings)); 2227 break; 2228 } 2229 } 2230 2231 if (getTriple().getArch() == llvm::Triple::x86 || 2232 getTriple().getArch() == llvm::Triple::x86_64) 2233 if (!Args.hasArgNoClaim(options::OPT_mtune_EQ)) 2234 DAL->AddJoinedArg(nullptr, Opts.getOption(options::OPT_mtune_EQ), 2235 "core2"); 2236 2237 // Add the arch options based on the particular spelling of -arch, to match 2238 // how the driver driver works. 2239 if (!BoundArch.empty()) { 2240 StringRef Name = BoundArch; 2241 const Option MCpu = Opts.getOption(options::OPT_mcpu_EQ); 2242 const Option MArch = Opts.getOption(clang::driver::options::OPT_march_EQ); 2243 2244 // This code must be kept in sync with LLVM's getArchTypeForDarwinArch, 2245 // which defines the list of which architectures we accept. 2246 if (Name == "ppc") 2247 ; 2248 else if (Name == "ppc601") 2249 DAL->AddJoinedArg(nullptr, MCpu, "601"); 2250 else if (Name == "ppc603") 2251 DAL->AddJoinedArg(nullptr, MCpu, "603"); 2252 else if (Name == "ppc604") 2253 DAL->AddJoinedArg(nullptr, MCpu, "604"); 2254 else if (Name == "ppc604e") 2255 DAL->AddJoinedArg(nullptr, MCpu, "604e"); 2256 else if (Name == "ppc750") 2257 DAL->AddJoinedArg(nullptr, MCpu, "750"); 2258 else if (Name == "ppc7400") 2259 DAL->AddJoinedArg(nullptr, MCpu, "7400"); 2260 else if (Name == "ppc7450") 2261 DAL->AddJoinedArg(nullptr, MCpu, "7450"); 2262 else if (Name == "ppc970") 2263 DAL->AddJoinedArg(nullptr, MCpu, "970"); 2264 2265 else if (Name == "ppc64" || Name == "ppc64le") 2266 DAL->AddFlagArg(nullptr, Opts.getOption(options::OPT_m64)); 2267 2268 else if (Name == "i386") 2269 ; 2270 else if (Name == "i486") 2271 DAL->AddJoinedArg(nullptr, MArch, "i486"); 2272 else if (Name == "i586") 2273 DAL->AddJoinedArg(nullptr, MArch, "i586"); 2274 else if (Name == "i686") 2275 DAL->AddJoinedArg(nullptr, MArch, "i686"); 2276 else if (Name == "pentium") 2277 DAL->AddJoinedArg(nullptr, MArch, "pentium"); 2278 else if (Name == "pentium2") 2279 DAL->AddJoinedArg(nullptr, MArch, "pentium2"); 2280 else if (Name == "pentpro") 2281 DAL->AddJoinedArg(nullptr, MArch, "pentiumpro"); 2282 else if (Name == "pentIIm3") 2283 DAL->AddJoinedArg(nullptr, MArch, "pentium2"); 2284 2285 else if (Name == "x86_64" || Name == "x86_64h") 2286 DAL->AddFlagArg(nullptr, Opts.getOption(options::OPT_m64)); 2287 2288 else if (Name == "arm") 2289 DAL->AddJoinedArg(nullptr, MArch, "armv4t"); 2290 else if (Name == "armv4t") 2291 DAL->AddJoinedArg(nullptr, MArch, "armv4t"); 2292 else if (Name == "armv5") 2293 DAL->AddJoinedArg(nullptr, MArch, "armv5tej"); 2294 else if (Name == "xscale") 2295 DAL->AddJoinedArg(nullptr, MArch, "xscale"); 2296 else if (Name == "armv6") 2297 DAL->AddJoinedArg(nullptr, MArch, "armv6k"); 2298 else if (Name == "armv6m") 2299 DAL->AddJoinedArg(nullptr, MArch, "armv6m"); 2300 else if (Name == "armv7") 2301 DAL->AddJoinedArg(nullptr, MArch, "armv7a"); 2302 else if (Name == "armv7em") 2303 DAL->AddJoinedArg(nullptr, MArch, "armv7em"); 2304 else if (Name == "armv7k") 2305 DAL->AddJoinedArg(nullptr, MArch, "armv7k"); 2306 else if (Name == "armv7m") 2307 DAL->AddJoinedArg(nullptr, MArch, "armv7m"); 2308 else if (Name == "armv7s") 2309 DAL->AddJoinedArg(nullptr, MArch, "armv7s"); 2310 } 2311 2312 return DAL; 2313 } 2314 2315 void MachO::AddLinkRuntimeLibArgs(const ArgList &Args, 2316 ArgStringList &CmdArgs, 2317 bool ForceLinkBuiltinRT) const { 2318 // Embedded targets are simple at the moment, not supporting sanitizers and 2319 // with different libraries for each member of the product { static, PIC } x 2320 // { hard-float, soft-float } 2321 llvm::SmallString<32> CompilerRT = StringRef(""); 2322 CompilerRT += 2323 (tools::arm::getARMFloatABI(*this, Args) == tools::arm::FloatABI::Hard) 2324 ? "hard" 2325 : "soft"; 2326 CompilerRT += Args.hasArg(options::OPT_fPIC) ? "_pic" : "_static"; 2327 2328 AddLinkRuntimeLib(Args, CmdArgs, CompilerRT, RLO_IsEmbedded); 2329 } 2330 2331 bool Darwin::isAlignedAllocationUnavailable() const { 2332 llvm::Triple::OSType OS; 2333 2334 switch (TargetPlatform) { 2335 case MacOS: // Earlier than 10.13. 2336 OS = llvm::Triple::MacOSX; 2337 break; 2338 case IPhoneOS: 2339 OS = llvm::Triple::IOS; 2340 break; 2341 case TvOS: // Earlier than 11.0. 2342 OS = llvm::Triple::TvOS; 2343 break; 2344 case WatchOS: // Earlier than 4.0. 2345 OS = llvm::Triple::WatchOS; 2346 break; 2347 } 2348 2349 return TargetVersion < alignedAllocMinVersion(OS); 2350 } 2351 2352 void Darwin::addClangTargetOptions(const llvm::opt::ArgList &DriverArgs, 2353 llvm::opt::ArgStringList &CC1Args, 2354 Action::OffloadKind DeviceOffloadKind) const { 2355 // Pass "-faligned-alloc-unavailable" only when the user hasn't manually 2356 // enabled or disabled aligned allocations. 2357 if (!DriverArgs.hasArgNoClaim(options::OPT_faligned_allocation, 2358 options::OPT_fno_aligned_allocation) && 2359 isAlignedAllocationUnavailable()) 2360 CC1Args.push_back("-faligned-alloc-unavailable"); 2361 2362 if (SDKInfo) { 2363 /// Pass the SDK version to the compiler when the SDK information is 2364 /// available. 2365 std::string Arg; 2366 llvm::raw_string_ostream OS(Arg); 2367 OS << "-target-sdk-version=" << SDKInfo->getVersion(); 2368 CC1Args.push_back(DriverArgs.MakeArgString(OS.str())); 2369 } 2370 } 2371 2372 DerivedArgList * 2373 Darwin::TranslateArgs(const DerivedArgList &Args, StringRef BoundArch, 2374 Action::OffloadKind DeviceOffloadKind) const { 2375 // First get the generic Apple args, before moving onto Darwin-specific ones. 2376 DerivedArgList *DAL = 2377 MachO::TranslateArgs(Args, BoundArch, DeviceOffloadKind); 2378 const OptTable &Opts = getDriver().getOpts(); 2379 2380 // If no architecture is bound, none of the translations here are relevant. 2381 if (BoundArch.empty()) 2382 return DAL; 2383 2384 // Add an explicit version min argument for the deployment target. We do this 2385 // after argument translation because -Xarch_ arguments may add a version min 2386 // argument. 2387 AddDeploymentTarget(*DAL); 2388 2389 // For iOS 6, undo the translation to add -static for -mkernel/-fapple-kext. 2390 // FIXME: It would be far better to avoid inserting those -static arguments, 2391 // but we can't check the deployment target in the translation code until 2392 // it is set here. 2393 if (isTargetWatchOSBased() || 2394 (isTargetIOSBased() && !isIPhoneOSVersionLT(6, 0))) { 2395 for (ArgList::iterator it = DAL->begin(), ie = DAL->end(); it != ie; ) { 2396 Arg *A = *it; 2397 ++it; 2398 if (A->getOption().getID() != options::OPT_mkernel && 2399 A->getOption().getID() != options::OPT_fapple_kext) 2400 continue; 2401 assert(it != ie && "unexpected argument translation"); 2402 A = *it; 2403 assert(A->getOption().getID() == options::OPT_static && 2404 "missing expected -static argument"); 2405 *it = nullptr; 2406 ++it; 2407 } 2408 } 2409 2410 if (!Args.getLastArg(options::OPT_stdlib_EQ) && 2411 GetCXXStdlibType(Args) == ToolChain::CST_Libcxx) 2412 DAL->AddJoinedArg(nullptr, Opts.getOption(options::OPT_stdlib_EQ), 2413 "libc++"); 2414 2415 // Validate the C++ standard library choice. 2416 CXXStdlibType Type = GetCXXStdlibType(*DAL); 2417 if (Type == ToolChain::CST_Libcxx) { 2418 // Check whether the target provides libc++. 2419 StringRef where; 2420 2421 // Complain about targeting iOS < 5.0 in any way. 2422 if (isTargetIOSBased() && isIPhoneOSVersionLT(5, 0)) 2423 where = "iOS 5.0"; 2424 2425 if (where != StringRef()) { 2426 getDriver().Diag(clang::diag::err_drv_invalid_libcxx_deployment) << where; 2427 } 2428 } 2429 2430 auto Arch = tools::darwin::getArchTypeForMachOArchName(BoundArch); 2431 if ((Arch == llvm::Triple::arm || Arch == llvm::Triple::thumb)) { 2432 if (Args.hasFlag(options::OPT_fomit_frame_pointer, 2433 options::OPT_fno_omit_frame_pointer, false)) 2434 getDriver().Diag(clang::diag::warn_drv_unsupported_opt_for_target) 2435 << "-fomit-frame-pointer" << BoundArch; 2436 } 2437 2438 return DAL; 2439 } 2440 2441 bool MachO::IsUnwindTablesDefault(const ArgList &Args) const { 2442 // Unwind tables are not emitted if -fno-exceptions is supplied (except when 2443 // targeting x86_64). 2444 return getArch() == llvm::Triple::x86_64 || 2445 (GetExceptionModel(Args) != llvm::ExceptionHandling::SjLj && 2446 Args.hasFlag(options::OPT_fexceptions, options::OPT_fno_exceptions, 2447 true)); 2448 } 2449 2450 bool MachO::UseDwarfDebugFlags() const { 2451 if (const char *S = ::getenv("RC_DEBUG_OPTIONS")) 2452 return S[0] != '\0'; 2453 return false; 2454 } 2455 2456 llvm::ExceptionHandling Darwin::GetExceptionModel(const ArgList &Args) const { 2457 // Darwin uses SjLj exceptions on ARM. 2458 if (getTriple().getArch() != llvm::Triple::arm && 2459 getTriple().getArch() != llvm::Triple::thumb) 2460 return llvm::ExceptionHandling::None; 2461 2462 // Only watchOS uses the new DWARF/Compact unwinding method. 2463 llvm::Triple Triple(ComputeLLVMTriple(Args)); 2464 if (Triple.isWatchABI()) 2465 return llvm::ExceptionHandling::DwarfCFI; 2466 2467 return llvm::ExceptionHandling::SjLj; 2468 } 2469 2470 bool Darwin::SupportsEmbeddedBitcode() const { 2471 assert(TargetInitialized && "Target not initialized!"); 2472 if (isTargetIPhoneOS() && isIPhoneOSVersionLT(6, 0)) 2473 return false; 2474 return true; 2475 } 2476 2477 bool MachO::isPICDefault() const { return true; } 2478 2479 bool MachO::isPIEDefault() const { return false; } 2480 2481 bool MachO::isPICDefaultForced() const { 2482 return (getArch() == llvm::Triple::x86_64 || 2483 getArch() == llvm::Triple::aarch64); 2484 } 2485 2486 bool MachO::SupportsProfiling() const { 2487 // Profiling instrumentation is only supported on x86. 2488 return getArch() == llvm::Triple::x86 || getArch() == llvm::Triple::x86_64; 2489 } 2490 2491 void Darwin::addMinVersionArgs(const ArgList &Args, 2492 ArgStringList &CmdArgs) const { 2493 VersionTuple TargetVersion = getTargetVersion(); 2494 2495 if (isTargetWatchOS()) 2496 CmdArgs.push_back("-watchos_version_min"); 2497 else if (isTargetWatchOSSimulator()) 2498 CmdArgs.push_back("-watchos_simulator_version_min"); 2499 else if (isTargetTvOS()) 2500 CmdArgs.push_back("-tvos_version_min"); 2501 else if (isTargetTvOSSimulator()) 2502 CmdArgs.push_back("-tvos_simulator_version_min"); 2503 else if (isTargetIOSSimulator()) 2504 CmdArgs.push_back("-ios_simulator_version_min"); 2505 else if (isTargetIOSBased()) 2506 CmdArgs.push_back("-iphoneos_version_min"); 2507 else { 2508 assert(isTargetMacOS() && "unexpected target"); 2509 CmdArgs.push_back("-macosx_version_min"); 2510 } 2511 2512 CmdArgs.push_back(Args.MakeArgString(TargetVersion.getAsString())); 2513 } 2514 2515 void Darwin::addStartObjectFileArgs(const ArgList &Args, 2516 ArgStringList &CmdArgs) const { 2517 // Derived from startfile spec. 2518 if (Args.hasArg(options::OPT_dynamiclib)) { 2519 // Derived from darwin_dylib1 spec. 2520 if (isTargetWatchOSBased()) { 2521 ; // watchOS does not need dylib1.o. 2522 } else if (isTargetIOSSimulator()) { 2523 ; // iOS simulator does not need dylib1.o. 2524 } else if (isTargetIPhoneOS()) { 2525 if (isIPhoneOSVersionLT(3, 1)) 2526 CmdArgs.push_back("-ldylib1.o"); 2527 } else { 2528 if (isMacosxVersionLT(10, 5)) 2529 CmdArgs.push_back("-ldylib1.o"); 2530 else if (isMacosxVersionLT(10, 6)) 2531 CmdArgs.push_back("-ldylib1.10.5.o"); 2532 } 2533 } else { 2534 if (Args.hasArg(options::OPT_bundle)) { 2535 if (!Args.hasArg(options::OPT_static)) { 2536 // Derived from darwin_bundle1 spec. 2537 if (isTargetWatchOSBased()) { 2538 ; // watchOS does not need bundle1.o. 2539 } else if (isTargetIOSSimulator()) { 2540 ; // iOS simulator does not need bundle1.o. 2541 } else if (isTargetIPhoneOS()) { 2542 if (isIPhoneOSVersionLT(3, 1)) 2543 CmdArgs.push_back("-lbundle1.o"); 2544 } else { 2545 if (isMacosxVersionLT(10, 6)) 2546 CmdArgs.push_back("-lbundle1.o"); 2547 } 2548 } 2549 } else { 2550 if (Args.hasArg(options::OPT_pg) && SupportsProfiling()) { 2551 if (isTargetMacOS() && isMacosxVersionLT(10, 9)) { 2552 if (Args.hasArg(options::OPT_static) || 2553 Args.hasArg(options::OPT_object) || 2554 Args.hasArg(options::OPT_preload)) { 2555 CmdArgs.push_back("-lgcrt0.o"); 2556 } else { 2557 CmdArgs.push_back("-lgcrt1.o"); 2558 2559 // darwin_crt2 spec is empty. 2560 } 2561 // By default on OS X 10.8 and later, we don't link with a crt1.o 2562 // file and the linker knows to use _main as the entry point. But, 2563 // when compiling with -pg, we need to link with the gcrt1.o file, 2564 // so pass the -no_new_main option to tell the linker to use the 2565 // "start" symbol as the entry point. 2566 if (isTargetMacOS() && !isMacosxVersionLT(10, 8)) 2567 CmdArgs.push_back("-no_new_main"); 2568 } else { 2569 getDriver().Diag(diag::err_drv_clang_unsupported_opt_pg_darwin) 2570 << isTargetMacOS(); 2571 } 2572 } else { 2573 if (Args.hasArg(options::OPT_static) || 2574 Args.hasArg(options::OPT_object) || 2575 Args.hasArg(options::OPT_preload)) { 2576 CmdArgs.push_back("-lcrt0.o"); 2577 } else { 2578 // Derived from darwin_crt1 spec. 2579 if (isTargetWatchOSBased()) { 2580 ; // watchOS does not need crt1.o. 2581 } else if (isTargetIOSSimulator()) { 2582 ; // iOS simulator does not need crt1.o. 2583 } else if (isTargetIPhoneOS()) { 2584 if (getArch() == llvm::Triple::aarch64) 2585 ; // iOS does not need any crt1 files for arm64 2586 else if (isIPhoneOSVersionLT(3, 1)) 2587 CmdArgs.push_back("-lcrt1.o"); 2588 else if (isIPhoneOSVersionLT(6, 0)) 2589 CmdArgs.push_back("-lcrt1.3.1.o"); 2590 } else { 2591 if (isMacosxVersionLT(10, 5)) 2592 CmdArgs.push_back("-lcrt1.o"); 2593 else if (isMacosxVersionLT(10, 6)) 2594 CmdArgs.push_back("-lcrt1.10.5.o"); 2595 else if (isMacosxVersionLT(10, 8)) 2596 CmdArgs.push_back("-lcrt1.10.6.o"); 2597 2598 // darwin_crt2 spec is empty. 2599 } 2600 } 2601 } 2602 } 2603 } 2604 2605 if (!isTargetIPhoneOS() && Args.hasArg(options::OPT_shared_libgcc) && 2606 !isTargetWatchOS() && isMacosxVersionLT(10, 5)) { 2607 const char *Str = Args.MakeArgString(GetFilePath("crt3.o")); 2608 CmdArgs.push_back(Str); 2609 } 2610 } 2611 2612 void Darwin::CheckObjCARC() const { 2613 if (isTargetIOSBased() || isTargetWatchOSBased() || 2614 (isTargetMacOS() && !isMacosxVersionLT(10, 6))) 2615 return; 2616 getDriver().Diag(diag::err_arc_unsupported_on_toolchain); 2617 } 2618 2619 SanitizerMask Darwin::getSupportedSanitizers() const { 2620 const bool IsX86_64 = getTriple().getArch() == llvm::Triple::x86_64; 2621 SanitizerMask Res = ToolChain::getSupportedSanitizers(); 2622 Res |= SanitizerKind::Address; 2623 Res |= SanitizerKind::PointerCompare; 2624 Res |= SanitizerKind::PointerSubtract; 2625 Res |= SanitizerKind::Leak; 2626 Res |= SanitizerKind::Fuzzer; 2627 Res |= SanitizerKind::FuzzerNoLink; 2628 Res |= SanitizerKind::Function; 2629 2630 // Prior to 10.9, macOS shipped a version of the C++ standard library without 2631 // C++11 support. The same is true of iOS prior to version 5. These OS'es are 2632 // incompatible with -fsanitize=vptr. 2633 if (!(isTargetMacOS() && isMacosxVersionLT(10, 9)) 2634 && !(isTargetIPhoneOS() && isIPhoneOSVersionLT(5, 0))) 2635 Res |= SanitizerKind::Vptr; 2636 2637 if (isTargetMacOS()) { 2638 if (IsX86_64) 2639 Res |= SanitizerKind::Thread; 2640 } else if (isTargetIOSSimulator() || isTargetTvOSSimulator()) { 2641 if (IsX86_64) 2642 Res |= SanitizerKind::Thread; 2643 } 2644 return Res; 2645 } 2646 2647 void Darwin::printVerboseInfo(raw_ostream &OS) const { 2648 CudaInstallation.print(OS); 2649 } 2650