1 1.1 joerg //===--- CommonArgs.cpp - Args handling for multiple toolchains -*- C++ -*-===// 2 1.1 joerg // 3 1.1 joerg // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 1.1 joerg // See https://llvm.org/LICENSE.txt for license information. 5 1.1 joerg // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 1.1 joerg // 7 1.1 joerg //===----------------------------------------------------------------------===// 8 1.1 joerg 9 1.1 joerg #include "CommonArgs.h" 10 1.1 joerg #include "Arch/AArch64.h" 11 1.1 joerg #include "Arch/ARM.h" 12 1.1.1.2 joerg #include "Arch/M68k.h" 13 1.1 joerg #include "Arch/Mips.h" 14 1.1 joerg #include "Arch/PPC.h" 15 1.1 joerg #include "Arch/SystemZ.h" 16 1.1.1.2 joerg #include "Arch/VE.h" 17 1.1 joerg #include "Arch/X86.h" 18 1.1 joerg #include "HIP.h" 19 1.1 joerg #include "Hexagon.h" 20 1.1 joerg #include "InputInfo.h" 21 1.1 joerg #include "clang/Basic/CharInfo.h" 22 1.1 joerg #include "clang/Basic/LangOptions.h" 23 1.1 joerg #include "clang/Basic/ObjCRuntime.h" 24 1.1 joerg #include "clang/Basic/Version.h" 25 1.1 joerg #include "clang/Config/config.h" 26 1.1 joerg #include "clang/Driver/Action.h" 27 1.1 joerg #include "clang/Driver/Compilation.h" 28 1.1 joerg #include "clang/Driver/Driver.h" 29 1.1 joerg #include "clang/Driver/DriverDiagnostic.h" 30 1.1 joerg #include "clang/Driver/Job.h" 31 1.1 joerg #include "clang/Driver/Options.h" 32 1.1 joerg #include "clang/Driver/SanitizerArgs.h" 33 1.1 joerg #include "clang/Driver/ToolChain.h" 34 1.1 joerg #include "clang/Driver/Util.h" 35 1.1 joerg #include "clang/Driver/XRayArgs.h" 36 1.1 joerg #include "llvm/ADT/STLExtras.h" 37 1.1 joerg #include "llvm/ADT/SmallString.h" 38 1.1 joerg #include "llvm/ADT/StringExtras.h" 39 1.1 joerg #include "llvm/ADT/StringSwitch.h" 40 1.1 joerg #include "llvm/ADT/Twine.h" 41 1.1.1.2 joerg #include "llvm/Config/llvm-config.h" 42 1.1 joerg #include "llvm/Option/Arg.h" 43 1.1 joerg #include "llvm/Option/ArgList.h" 44 1.1 joerg #include "llvm/Option/Option.h" 45 1.1 joerg #include "llvm/Support/CodeGen.h" 46 1.1 joerg #include "llvm/Support/Compression.h" 47 1.1 joerg #include "llvm/Support/Debug.h" 48 1.1 joerg #include "llvm/Support/ErrorHandling.h" 49 1.1 joerg #include "llvm/Support/FileSystem.h" 50 1.1 joerg #include "llvm/Support/Host.h" 51 1.1 joerg #include "llvm/Support/Path.h" 52 1.1 joerg #include "llvm/Support/Process.h" 53 1.1 joerg #include "llvm/Support/Program.h" 54 1.1 joerg #include "llvm/Support/ScopedPrinter.h" 55 1.1 joerg #include "llvm/Support/TargetParser.h" 56 1.1.1.2 joerg #include "llvm/Support/Threading.h" 57 1.1 joerg #include "llvm/Support/VirtualFileSystem.h" 58 1.1 joerg #include "llvm/Support/YAMLParser.h" 59 1.1 joerg 60 1.1 joerg using namespace clang::driver; 61 1.1 joerg using namespace clang::driver::tools; 62 1.1 joerg using namespace clang; 63 1.1 joerg using namespace llvm::opt; 64 1.1 joerg 65 1.1.1.2 joerg static void renderRpassOptions(const ArgList &Args, ArgStringList &CmdArgs) { 66 1.1.1.2 joerg if (const Arg *A = Args.getLastArg(options::OPT_Rpass_EQ)) 67 1.1.1.2 joerg CmdArgs.push_back(Args.MakeArgString(Twine("--plugin-opt=-pass-remarks=") + 68 1.1.1.2 joerg A->getValue())); 69 1.1.1.2 joerg 70 1.1.1.2 joerg if (const Arg *A = Args.getLastArg(options::OPT_Rpass_missed_EQ)) 71 1.1.1.2 joerg CmdArgs.push_back(Args.MakeArgString( 72 1.1.1.2 joerg Twine("--plugin-opt=-pass-remarks-missed=") + A->getValue())); 73 1.1.1.2 joerg 74 1.1.1.2 joerg if (const Arg *A = Args.getLastArg(options::OPT_Rpass_analysis_EQ)) 75 1.1.1.2 joerg CmdArgs.push_back(Args.MakeArgString( 76 1.1.1.2 joerg Twine("--plugin-opt=-pass-remarks-analysis=") + A->getValue())); 77 1.1.1.2 joerg } 78 1.1.1.2 joerg 79 1.1.1.2 joerg static void renderRemarksOptions(const ArgList &Args, ArgStringList &CmdArgs, 80 1.1.1.2 joerg const llvm::Triple &Triple, 81 1.1.1.2 joerg const InputInfo &Input, 82 1.1.1.2 joerg const InputInfo &Output) { 83 1.1.1.2 joerg StringRef Format = "yaml"; 84 1.1.1.2 joerg if (const Arg *A = Args.getLastArg(options::OPT_fsave_optimization_record_EQ)) 85 1.1.1.2 joerg Format = A->getValue(); 86 1.1.1.2 joerg 87 1.1.1.2 joerg SmallString<128> F; 88 1.1.1.2 joerg const Arg *A = Args.getLastArg(options::OPT_foptimization_record_file_EQ); 89 1.1.1.2 joerg if (A) 90 1.1.1.2 joerg F = A->getValue(); 91 1.1.1.2 joerg else if (Output.isFilename()) 92 1.1.1.2 joerg F = Output.getFilename(); 93 1.1.1.2 joerg 94 1.1.1.2 joerg assert(!F.empty() && "Cannot determine remarks output name."); 95 1.1.1.2 joerg // Append "opt.ld.<format>" to the end of the file name. 96 1.1.1.2 joerg CmdArgs.push_back( 97 1.1.1.2 joerg Args.MakeArgString(Twine("--plugin-opt=opt-remarks-filename=") + F + 98 1.1.1.2 joerg Twine(".opt.ld.") + Format)); 99 1.1.1.2 joerg 100 1.1.1.2 joerg if (const Arg *A = 101 1.1.1.2 joerg Args.getLastArg(options::OPT_foptimization_record_passes_EQ)) 102 1.1.1.2 joerg CmdArgs.push_back(Args.MakeArgString( 103 1.1.1.2 joerg Twine("--plugin-opt=opt-remarks-passes=") + A->getValue())); 104 1.1.1.2 joerg 105 1.1.1.2 joerg CmdArgs.push_back(Args.MakeArgString( 106 1.1.1.2 joerg Twine("--plugin-opt=opt-remarks-format=") + Format.data())); 107 1.1.1.2 joerg } 108 1.1.1.2 joerg 109 1.1.1.2 joerg static void renderRemarksHotnessOptions(const ArgList &Args, 110 1.1.1.2 joerg ArgStringList &CmdArgs) { 111 1.1.1.2 joerg if (Args.hasFlag(options::OPT_fdiagnostics_show_hotness, 112 1.1.1.2 joerg options::OPT_fno_diagnostics_show_hotness, false)) 113 1.1.1.2 joerg CmdArgs.push_back("--plugin-opt=opt-remarks-with-hotness"); 114 1.1.1.2 joerg 115 1.1.1.2 joerg if (const Arg *A = 116 1.1.1.2 joerg Args.getLastArg(options::OPT_fdiagnostics_hotness_threshold_EQ)) 117 1.1.1.2 joerg CmdArgs.push_back(Args.MakeArgString( 118 1.1.1.2 joerg Twine("--plugin-opt=opt-remarks-hotness-threshold=") + A->getValue())); 119 1.1.1.2 joerg } 120 1.1.1.2 joerg 121 1.1 joerg void tools::addPathIfExists(const Driver &D, const Twine &Path, 122 1.1 joerg ToolChain::path_list &Paths) { 123 1.1 joerg if (D.getVFS().exists(Path)) 124 1.1 joerg Paths.push_back(Path.str()); 125 1.1 joerg } 126 1.1 joerg 127 1.1 joerg void tools::handleTargetFeaturesGroup(const ArgList &Args, 128 1.1 joerg std::vector<StringRef> &Features, 129 1.1 joerg OptSpecifier Group) { 130 1.1 joerg for (const Arg *A : Args.filtered(Group)) { 131 1.1 joerg StringRef Name = A->getOption().getName(); 132 1.1 joerg A->claim(); 133 1.1 joerg 134 1.1 joerg // Skip over "-m". 135 1.1 joerg assert(Name.startswith("m") && "Invalid feature name."); 136 1.1 joerg Name = Name.substr(1); 137 1.1 joerg 138 1.1 joerg bool IsNegative = Name.startswith("no-"); 139 1.1 joerg if (IsNegative) 140 1.1 joerg Name = Name.substr(3); 141 1.1 joerg Features.push_back(Args.MakeArgString((IsNegative ? "-" : "+") + Name)); 142 1.1 joerg } 143 1.1 joerg } 144 1.1 joerg 145 1.1.1.2 joerg std::vector<StringRef> 146 1.1.1.2 joerg tools::unifyTargetFeatures(const std::vector<StringRef> &Features) { 147 1.1.1.2 joerg std::vector<StringRef> UnifiedFeatures; 148 1.1.1.2 joerg // Find the last of each feature. 149 1.1.1.2 joerg llvm::StringMap<unsigned> LastOpt; 150 1.1.1.2 joerg for (unsigned I = 0, N = Features.size(); I < N; ++I) { 151 1.1.1.2 joerg StringRef Name = Features[I]; 152 1.1.1.2 joerg assert(Name[0] == '-' || Name[0] == '+'); 153 1.1.1.2 joerg LastOpt[Name.drop_front(1)] = I; 154 1.1.1.2 joerg } 155 1.1.1.2 joerg 156 1.1.1.2 joerg for (unsigned I = 0, N = Features.size(); I < N; ++I) { 157 1.1.1.2 joerg // If this feature was overridden, ignore it. 158 1.1.1.2 joerg StringRef Name = Features[I]; 159 1.1.1.2 joerg llvm::StringMap<unsigned>::iterator LastI = LastOpt.find(Name.drop_front(1)); 160 1.1.1.2 joerg assert(LastI != LastOpt.end()); 161 1.1.1.2 joerg unsigned Last = LastI->second; 162 1.1.1.2 joerg if (Last != I) 163 1.1.1.2 joerg continue; 164 1.1.1.2 joerg 165 1.1.1.2 joerg UnifiedFeatures.push_back(Name); 166 1.1.1.2 joerg } 167 1.1.1.2 joerg return UnifiedFeatures; 168 1.1.1.2 joerg } 169 1.1.1.2 joerg 170 1.1 joerg void tools::addDirectoryList(const ArgList &Args, ArgStringList &CmdArgs, 171 1.1 joerg const char *ArgName, const char *EnvVar) { 172 1.1 joerg const char *DirList = ::getenv(EnvVar); 173 1.1 joerg bool CombinedArg = false; 174 1.1 joerg 175 1.1 joerg if (!DirList) 176 1.1 joerg return; // Nothing to do. 177 1.1 joerg 178 1.1 joerg StringRef Name(ArgName); 179 1.1.1.2 joerg if (Name.equals("-I") || Name.equals("-L") || Name.empty()) 180 1.1 joerg CombinedArg = true; 181 1.1 joerg 182 1.1 joerg StringRef Dirs(DirList); 183 1.1 joerg if (Dirs.empty()) // Empty string should not add '.'. 184 1.1 joerg return; 185 1.1 joerg 186 1.1 joerg StringRef::size_type Delim; 187 1.1 joerg while ((Delim = Dirs.find(llvm::sys::EnvPathSeparator)) != StringRef::npos) { 188 1.1 joerg if (Delim == 0) { // Leading colon. 189 1.1 joerg if (CombinedArg) { 190 1.1 joerg CmdArgs.push_back(Args.MakeArgString(std::string(ArgName) + ".")); 191 1.1 joerg } else { 192 1.1 joerg CmdArgs.push_back(ArgName); 193 1.1 joerg CmdArgs.push_back("."); 194 1.1 joerg } 195 1.1 joerg } else { 196 1.1 joerg if (CombinedArg) { 197 1.1 joerg CmdArgs.push_back( 198 1.1 joerg Args.MakeArgString(std::string(ArgName) + Dirs.substr(0, Delim))); 199 1.1 joerg } else { 200 1.1 joerg CmdArgs.push_back(ArgName); 201 1.1 joerg CmdArgs.push_back(Args.MakeArgString(Dirs.substr(0, Delim))); 202 1.1 joerg } 203 1.1 joerg } 204 1.1 joerg Dirs = Dirs.substr(Delim + 1); 205 1.1 joerg } 206 1.1 joerg 207 1.1 joerg if (Dirs.empty()) { // Trailing colon. 208 1.1 joerg if (CombinedArg) { 209 1.1 joerg CmdArgs.push_back(Args.MakeArgString(std::string(ArgName) + ".")); 210 1.1 joerg } else { 211 1.1 joerg CmdArgs.push_back(ArgName); 212 1.1 joerg CmdArgs.push_back("."); 213 1.1 joerg } 214 1.1 joerg } else { // Add the last path. 215 1.1 joerg if (CombinedArg) { 216 1.1 joerg CmdArgs.push_back(Args.MakeArgString(std::string(ArgName) + Dirs)); 217 1.1 joerg } else { 218 1.1 joerg CmdArgs.push_back(ArgName); 219 1.1 joerg CmdArgs.push_back(Args.MakeArgString(Dirs)); 220 1.1 joerg } 221 1.1 joerg } 222 1.1 joerg } 223 1.1 joerg 224 1.1 joerg void tools::AddLinkerInputs(const ToolChain &TC, const InputInfoList &Inputs, 225 1.1 joerg const ArgList &Args, ArgStringList &CmdArgs, 226 1.1 joerg const JobAction &JA) { 227 1.1 joerg const Driver &D = TC.getDriver(); 228 1.1 joerg 229 1.1 joerg // Add extra linker input arguments which are not treated as inputs 230 1.1 joerg // (constructed via -Xarch_). 231 1.1 joerg Args.AddAllArgValues(CmdArgs, options::OPT_Zlinker_input); 232 1.1 joerg 233 1.1 joerg // LIBRARY_PATH are included before user inputs and only supported on native 234 1.1 joerg // toolchains. 235 1.1 joerg if (!TC.isCrossCompiling()) 236 1.1 joerg addDirectoryList(Args, CmdArgs, "-L", "LIBRARY_PATH"); 237 1.1 joerg 238 1.1 joerg for (const auto &II : Inputs) { 239 1.1.1.2 joerg // If the current tool chain refers to an OpenMP offloading host, we 240 1.1.1.2 joerg // should ignore inputs that refer to OpenMP offloading devices - 241 1.1 joerg // they will be embedded according to a proper linker script. 242 1.1 joerg if (auto *IA = II.getAction()) 243 1.1 joerg if ((JA.isHostOffloading(Action::OFK_OpenMP) && 244 1.1.1.2 joerg IA->isDeviceOffloading(Action::OFK_OpenMP))) 245 1.1 joerg continue; 246 1.1 joerg 247 1.1 joerg if (!TC.HasNativeLLVMSupport() && types::isLLVMIR(II.getType())) 248 1.1 joerg // Don't try to pass LLVM inputs unless we have native support. 249 1.1 joerg D.Diag(diag::err_drv_no_linker_llvm_support) << TC.getTripleString(); 250 1.1 joerg 251 1.1 joerg // Add filenames immediately. 252 1.1 joerg if (II.isFilename()) { 253 1.1 joerg CmdArgs.push_back(II.getFilename()); 254 1.1 joerg continue; 255 1.1 joerg } 256 1.1 joerg 257 1.1 joerg // Otherwise, this is a linker input argument. 258 1.1 joerg const Arg &A = II.getInputArg(); 259 1.1 joerg 260 1.1 joerg // Handle reserved library options. 261 1.1 joerg if (A.getOption().matches(options::OPT_Z_reserved_lib_stdcxx)) 262 1.1 joerg TC.AddCXXStdlibLibArgs(Args, CmdArgs); 263 1.1 joerg else if (A.getOption().matches(options::OPT_Z_reserved_lib_cckext)) 264 1.1 joerg TC.AddCCKextLibArgs(Args, CmdArgs); 265 1.1 joerg else if (A.getOption().matches(options::OPT_z)) { 266 1.1 joerg // Pass -z prefix for gcc linker compatibility. 267 1.1 joerg A.claim(); 268 1.1 joerg A.render(Args, CmdArgs); 269 1.1 joerg } else { 270 1.1 joerg A.renderAsInput(Args, CmdArgs); 271 1.1 joerg } 272 1.1 joerg } 273 1.1 joerg } 274 1.1 joerg 275 1.1.1.2 joerg void tools::addLinkerCompressDebugSectionsOption( 276 1.1.1.2 joerg const ToolChain &TC, const llvm::opt::ArgList &Args, 277 1.1.1.2 joerg llvm::opt::ArgStringList &CmdArgs) { 278 1.1.1.2 joerg // GNU ld supports --compress-debug-sections=none|zlib|zlib-gnu|zlib-gabi 279 1.1.1.2 joerg // whereas zlib is an alias to zlib-gabi. Therefore -gz=none|zlib|zlib-gnu 280 1.1.1.2 joerg // are translated to --compress-debug-sections=none|zlib|zlib-gnu. 281 1.1.1.2 joerg // -gz is not translated since ld --compress-debug-sections option requires an 282 1.1.1.2 joerg // argument. 283 1.1.1.2 joerg if (const Arg *A = Args.getLastArg(options::OPT_gz_EQ)) { 284 1.1.1.2 joerg StringRef V = A->getValue(); 285 1.1.1.2 joerg if (V == "none" || V == "zlib" || V == "zlib-gnu") 286 1.1.1.2 joerg CmdArgs.push_back(Args.MakeArgString("--compress-debug-sections=" + V)); 287 1.1.1.2 joerg else 288 1.1.1.2 joerg TC.getDriver().Diag(diag::err_drv_unsupported_option_argument) 289 1.1.1.2 joerg << A->getOption().getName() << V; 290 1.1.1.2 joerg } 291 1.1.1.2 joerg } 292 1.1.1.2 joerg 293 1.1 joerg void tools::AddTargetFeature(const ArgList &Args, 294 1.1 joerg std::vector<StringRef> &Features, 295 1.1 joerg OptSpecifier OnOpt, OptSpecifier OffOpt, 296 1.1 joerg StringRef FeatureName) { 297 1.1 joerg if (Arg *A = Args.getLastArg(OnOpt, OffOpt)) { 298 1.1 joerg if (A->getOption().matches(OnOpt)) 299 1.1 joerg Features.push_back(Args.MakeArgString("+" + FeatureName)); 300 1.1 joerg else 301 1.1 joerg Features.push_back(Args.MakeArgString("-" + FeatureName)); 302 1.1 joerg } 303 1.1 joerg } 304 1.1 joerg 305 1.1.1.2 joerg /// Get the (LLVM) name of the AMDGPU gpu we are targeting. 306 1.1.1.2 joerg static std::string getAMDGPUTargetGPU(const llvm::Triple &T, 307 1.1.1.2 joerg const ArgList &Args) { 308 1.1 joerg if (Arg *A = Args.getLastArg(options::OPT_mcpu_EQ)) { 309 1.1.1.2 joerg auto GPUName = getProcessorFromTargetID(T, A->getValue()); 310 1.1.1.2 joerg return llvm::StringSwitch<std::string>(GPUName) 311 1.1 joerg .Cases("rv630", "rv635", "r600") 312 1.1 joerg .Cases("rv610", "rv620", "rs780", "rs880") 313 1.1 joerg .Case("rv740", "rv770") 314 1.1 joerg .Case("palm", "cedar") 315 1.1 joerg .Cases("sumo", "sumo2", "sumo") 316 1.1 joerg .Case("hemlock", "cypress") 317 1.1 joerg .Case("aruba", "cayman") 318 1.1.1.2 joerg .Default(GPUName.str()); 319 1.1 joerg } 320 1.1 joerg return ""; 321 1.1 joerg } 322 1.1 joerg 323 1.1 joerg static std::string getLanaiTargetCPU(const ArgList &Args) { 324 1.1 joerg if (Arg *A = Args.getLastArg(options::OPT_mcpu_EQ)) { 325 1.1 joerg return A->getValue(); 326 1.1 joerg } 327 1.1 joerg return ""; 328 1.1 joerg } 329 1.1 joerg 330 1.1 joerg /// Get the (LLVM) name of the WebAssembly cpu we are targeting. 331 1.1 joerg static StringRef getWebAssemblyTargetCPU(const ArgList &Args) { 332 1.1 joerg // If we have -mcpu=, use that. 333 1.1 joerg if (Arg *A = Args.getLastArg(options::OPT_mcpu_EQ)) { 334 1.1 joerg StringRef CPU = A->getValue(); 335 1.1 joerg 336 1.1 joerg #ifdef __wasm__ 337 1.1 joerg // Handle "native" by examining the host. "native" isn't meaningful when 338 1.1 joerg // cross compiling, so only support this when the host is also WebAssembly. 339 1.1 joerg if (CPU == "native") 340 1.1 joerg return llvm::sys::getHostCPUName(); 341 1.1 joerg #endif 342 1.1 joerg 343 1.1 joerg return CPU; 344 1.1 joerg } 345 1.1 joerg 346 1.1 joerg return "generic"; 347 1.1 joerg } 348 1.1 joerg 349 1.1 joerg std::string tools::getCPUName(const ArgList &Args, const llvm::Triple &T, 350 1.1 joerg bool FromAs) { 351 1.1 joerg Arg *A; 352 1.1 joerg 353 1.1 joerg switch (T.getArch()) { 354 1.1 joerg default: 355 1.1 joerg return ""; 356 1.1 joerg 357 1.1 joerg case llvm::Triple::aarch64: 358 1.1.1.2 joerg case llvm::Triple::aarch64_32: 359 1.1 joerg case llvm::Triple::aarch64_be: 360 1.1 joerg return aarch64::getAArch64TargetCPU(Args, T, A); 361 1.1 joerg 362 1.1 joerg case llvm::Triple::arm: 363 1.1 joerg case llvm::Triple::armeb: 364 1.1 joerg case llvm::Triple::thumb: 365 1.1 joerg case llvm::Triple::thumbeb: { 366 1.1 joerg StringRef MArch, MCPU; 367 1.1 joerg arm::getARMArchCPUFromArgs(Args, MArch, MCPU, FromAs); 368 1.1 joerg return arm::getARMTargetCPU(MCPU, MArch, T); 369 1.1 joerg } 370 1.1 joerg 371 1.1 joerg case llvm::Triple::avr: 372 1.1 joerg if (const Arg *A = Args.getLastArg(options::OPT_mmcu_EQ)) 373 1.1 joerg return A->getValue(); 374 1.1 joerg return ""; 375 1.1 joerg 376 1.1.1.2 joerg case llvm::Triple::m68k: 377 1.1.1.2 joerg return m68k::getM68kTargetCPU(Args); 378 1.1.1.2 joerg 379 1.1 joerg case llvm::Triple::mips: 380 1.1 joerg case llvm::Triple::mipsel: 381 1.1 joerg case llvm::Triple::mips64: 382 1.1 joerg case llvm::Triple::mips64el: { 383 1.1 joerg StringRef CPUName; 384 1.1 joerg StringRef ABIName; 385 1.1 joerg mips::getMipsCPUAndABI(Args, T, CPUName, ABIName); 386 1.1.1.2 joerg return std::string(CPUName); 387 1.1 joerg } 388 1.1 joerg 389 1.1 joerg case llvm::Triple::nvptx: 390 1.1 joerg case llvm::Triple::nvptx64: 391 1.1 joerg if (const Arg *A = Args.getLastArg(options::OPT_march_EQ)) 392 1.1 joerg return A->getValue(); 393 1.1 joerg return ""; 394 1.1 joerg 395 1.1 joerg case llvm::Triple::ppc: 396 1.1.1.2 joerg case llvm::Triple::ppcle: 397 1.1 joerg case llvm::Triple::ppc64: 398 1.1 joerg case llvm::Triple::ppc64le: { 399 1.1 joerg std::string TargetCPUName = ppc::getPPCTargetCPU(Args); 400 1.1 joerg // LLVM may default to generating code for the native CPU, 401 1.1 joerg // but, like gcc, we default to a more generic option for 402 1.1.1.2 joerg // each architecture. (except on AIX) 403 1.1.1.2 joerg if (!TargetCPUName.empty()) 404 1.1.1.2 joerg return TargetCPUName; 405 1.1.1.2 joerg 406 1.1.1.2 joerg if (T.isOSAIX()) { 407 1.1.1.2 joerg unsigned major, minor, unused_micro; 408 1.1.1.2 joerg T.getOSVersion(major, minor, unused_micro); 409 1.1.1.2 joerg // The minimal arch level moved from pwr4 for AIX7.1 to 410 1.1.1.2 joerg // pwr7 for AIX7.2. 411 1.1.1.2 joerg TargetCPUName = 412 1.1.1.2 joerg (major < 7 || (major == 7 && minor < 2)) ? "pwr4" : "pwr7"; 413 1.1.1.2 joerg } else if (T.getArch() == llvm::Triple::ppc64le) 414 1.1.1.2 joerg TargetCPUName = "ppc64le"; 415 1.1.1.2 joerg else if (T.getArch() == llvm::Triple::ppc64) 416 1.1.1.2 joerg TargetCPUName = "ppc64"; 417 1.1.1.2 joerg else 418 1.1.1.2 joerg TargetCPUName = "ppc"; 419 1.1.1.2 joerg 420 1.1 joerg return TargetCPUName; 421 1.1 joerg } 422 1.1.1.2 joerg case llvm::Triple::riscv32: 423 1.1.1.2 joerg case llvm::Triple::riscv64: 424 1.1.1.2 joerg if (const Arg *A = Args.getLastArg(options::OPT_mcpu_EQ)) 425 1.1.1.2 joerg return A->getValue(); 426 1.1.1.2 joerg return ""; 427 1.1 joerg 428 1.1 joerg case llvm::Triple::bpfel: 429 1.1 joerg case llvm::Triple::bpfeb: 430 1.1 joerg case llvm::Triple::sparc: 431 1.1 joerg case llvm::Triple::sparcel: 432 1.1 joerg case llvm::Triple::sparcv9: 433 1.1 joerg if (const Arg *A = Args.getLastArg(options::OPT_mcpu_EQ)) 434 1.1 joerg return A->getValue(); 435 1.1.1.2 joerg if (T.getArch() == llvm::Triple::sparc && T.isOSSolaris()) 436 1.1.1.2 joerg return "v9"; 437 1.1 joerg return ""; 438 1.1 joerg 439 1.1 joerg case llvm::Triple::x86: 440 1.1 joerg case llvm::Triple::x86_64: 441 1.1 joerg return x86::getX86TargetCPU(Args, T); 442 1.1 joerg 443 1.1 joerg case llvm::Triple::hexagon: 444 1.1 joerg return "hexagon" + 445 1.1 joerg toolchains::HexagonToolChain::GetTargetCPUVersion(Args).str(); 446 1.1 joerg 447 1.1 joerg case llvm::Triple::lanai: 448 1.1 joerg return getLanaiTargetCPU(Args); 449 1.1 joerg 450 1.1 joerg case llvm::Triple::systemz: 451 1.1 joerg return systemz::getSystemZTargetCPU(Args); 452 1.1 joerg 453 1.1 joerg case llvm::Triple::r600: 454 1.1 joerg case llvm::Triple::amdgcn: 455 1.1.1.2 joerg return getAMDGPUTargetGPU(T, Args); 456 1.1 joerg 457 1.1 joerg case llvm::Triple::wasm32: 458 1.1 joerg case llvm::Triple::wasm64: 459 1.1.1.2 joerg return std::string(getWebAssemblyTargetCPU(Args)); 460 1.1 joerg } 461 1.1 joerg } 462 1.1 joerg 463 1.1.1.2 joerg llvm::StringRef tools::getLTOParallelism(const ArgList &Args, const Driver &D) { 464 1.1 joerg Arg *LtoJobsArg = Args.getLastArg(options::OPT_flto_jobs_EQ); 465 1.1.1.2 joerg if (!LtoJobsArg) 466 1.1.1.2 joerg return {}; 467 1.1.1.2 joerg if (!llvm::get_threadpool_strategy(LtoJobsArg->getValue())) 468 1.1.1.2 joerg D.Diag(diag::err_drv_invalid_int_value) 469 1.1.1.2 joerg << LtoJobsArg->getAsString(Args) << LtoJobsArg->getValue(); 470 1.1.1.2 joerg return LtoJobsArg->getValue(); 471 1.1 joerg } 472 1.1 joerg 473 1.1 joerg // CloudABI uses -ffunction-sections and -fdata-sections by default. 474 1.1 joerg bool tools::isUseSeparateSections(const llvm::Triple &Triple) { 475 1.1 joerg return Triple.getOS() == llvm::Triple::CloudABI; 476 1.1 joerg } 477 1.1 joerg 478 1.1.1.2 joerg void tools::addLTOOptions(const ToolChain &ToolChain, const ArgList &Args, 479 1.1 joerg ArgStringList &CmdArgs, const InputInfo &Output, 480 1.1 joerg const InputInfo &Input, bool IsThinLTO) { 481 1.1.1.2 joerg const char *Linker = Args.MakeArgString(ToolChain.GetLinkerPath()); 482 1.1.1.2 joerg const Driver &D = ToolChain.getDriver(); 483 1.1.1.2 joerg if (llvm::sys::path::filename(Linker) != "ld.lld" && 484 1.1.1.2 joerg llvm::sys::path::stem(Linker) != "ld.lld") { 485 1.1.1.2 joerg // Tell the linker to load the plugin. This has to come before 486 1.1.1.2 joerg // AddLinkerInputs as gold requires -plugin to come before any -plugin-opt 487 1.1.1.2 joerg // that -Wl might forward. 488 1.1.1.2 joerg CmdArgs.push_back("-plugin"); 489 1.1 joerg 490 1.1 joerg #if defined(_WIN32) 491 1.1.1.2 joerg const char *Suffix = ".dll"; 492 1.1 joerg #elif defined(__APPLE__) 493 1.1.1.2 joerg const char *Suffix = ".dylib"; 494 1.1 joerg #else 495 1.1.1.2 joerg const char *Suffix = ".so"; 496 1.1 joerg #endif 497 1.1 joerg 498 1.1.1.2 joerg SmallString<1024> Plugin; 499 1.1.1.2 joerg llvm::sys::path::native( 500 1.1.1.2 joerg Twine(D.Dir) + "/../lib" CLANG_LIBDIR_SUFFIX "/LLVMgold" + Suffix, 501 1.1.1.2 joerg Plugin); 502 1.1.1.2 joerg CmdArgs.push_back(Args.MakeArgString(Plugin)); 503 1.1.1.2 joerg } 504 1.1 joerg 505 1.1 joerg // Try to pass driver level flags relevant to LTO code generation down to 506 1.1 joerg // the plugin. 507 1.1 joerg 508 1.1 joerg // Handle flags for selecting CPU variants. 509 1.1 joerg std::string CPU = getCPUName(Args, ToolChain.getTriple()); 510 1.1 joerg if (!CPU.empty()) 511 1.1 joerg CmdArgs.push_back(Args.MakeArgString(Twine("-plugin-opt=mcpu=") + CPU)); 512 1.1 joerg 513 1.1 joerg if (Arg *A = Args.getLastArg(options::OPT_O_Group)) { 514 1.1.1.2 joerg // The optimization level matches 515 1.1.1.2 joerg // CompilerInvocation.cpp:getOptimizationLevel(). 516 1.1 joerg StringRef OOpt; 517 1.1 joerg if (A->getOption().matches(options::OPT_O4) || 518 1.1 joerg A->getOption().matches(options::OPT_Ofast)) 519 1.1 joerg OOpt = "3"; 520 1.1.1.2 joerg else if (A->getOption().matches(options::OPT_O)) { 521 1.1 joerg OOpt = A->getValue(); 522 1.1.1.2 joerg if (OOpt == "g") 523 1.1.1.2 joerg OOpt = "1"; 524 1.1.1.2 joerg else if (OOpt == "s" || OOpt == "z") 525 1.1.1.2 joerg OOpt = "2"; 526 1.1.1.2 joerg } else if (A->getOption().matches(options::OPT_O0)) 527 1.1 joerg OOpt = "0"; 528 1.1 joerg if (!OOpt.empty()) 529 1.1 joerg CmdArgs.push_back(Args.MakeArgString(Twine("-plugin-opt=O") + OOpt)); 530 1.1 joerg } 531 1.1 joerg 532 1.1 joerg if (Args.hasArg(options::OPT_gsplit_dwarf)) { 533 1.1 joerg CmdArgs.push_back( 534 1.1 joerg Args.MakeArgString(Twine("-plugin-opt=dwo_dir=") + 535 1.1 joerg Output.getFilename() + "_dwo")); 536 1.1 joerg } 537 1.1 joerg 538 1.1 joerg if (IsThinLTO) 539 1.1 joerg CmdArgs.push_back("-plugin-opt=thinlto"); 540 1.1 joerg 541 1.1.1.2 joerg StringRef Parallelism = getLTOParallelism(Args, D); 542 1.1.1.2 joerg if (!Parallelism.empty()) 543 1.1 joerg CmdArgs.push_back( 544 1.1 joerg Args.MakeArgString("-plugin-opt=jobs=" + Twine(Parallelism))); 545 1.1 joerg 546 1.1 joerg // If an explicit debugger tuning argument appeared, pass it along. 547 1.1 joerg if (Arg *A = Args.getLastArg(options::OPT_gTune_Group, 548 1.1 joerg options::OPT_ggdbN_Group)) { 549 1.1 joerg if (A->getOption().matches(options::OPT_glldb)) 550 1.1 joerg CmdArgs.push_back("-plugin-opt=-debugger-tune=lldb"); 551 1.1 joerg else if (A->getOption().matches(options::OPT_gsce)) 552 1.1 joerg CmdArgs.push_back("-plugin-opt=-debugger-tune=sce"); 553 1.1.1.2 joerg else if (A->getOption().matches(options::OPT_gdbx)) 554 1.1.1.2 joerg CmdArgs.push_back("-plugin-opt=-debugger-tune=dbx"); 555 1.1 joerg else 556 1.1 joerg CmdArgs.push_back("-plugin-opt=-debugger-tune=gdb"); 557 1.1 joerg } 558 1.1 joerg 559 1.1 joerg bool UseSeparateSections = 560 1.1 joerg isUseSeparateSections(ToolChain.getEffectiveTriple()); 561 1.1 joerg 562 1.1 joerg if (Args.hasFlag(options::OPT_ffunction_sections, 563 1.1 joerg options::OPT_fno_function_sections, UseSeparateSections)) { 564 1.1 joerg CmdArgs.push_back("-plugin-opt=-function-sections"); 565 1.1 joerg } 566 1.1 joerg 567 1.1 joerg if (Args.hasFlag(options::OPT_fdata_sections, options::OPT_fno_data_sections, 568 1.1 joerg UseSeparateSections)) { 569 1.1 joerg CmdArgs.push_back("-plugin-opt=-data-sections"); 570 1.1 joerg } 571 1.1 joerg 572 1.1 joerg if (Arg *A = getLastProfileSampleUseArg(Args)) { 573 1.1 joerg StringRef FName = A->getValue(); 574 1.1 joerg if (!llvm::sys::fs::exists(FName)) 575 1.1.1.2 joerg D.Diag(diag::err_drv_no_such_file) << FName; 576 1.1 joerg else 577 1.1 joerg CmdArgs.push_back( 578 1.1 joerg Args.MakeArgString(Twine("-plugin-opt=sample-profile=") + FName)); 579 1.1 joerg } 580 1.1 joerg 581 1.1 joerg auto *CSPGOGenerateArg = Args.getLastArg(options::OPT_fcs_profile_generate, 582 1.1 joerg options::OPT_fcs_profile_generate_EQ, 583 1.1 joerg options::OPT_fno_profile_generate); 584 1.1 joerg if (CSPGOGenerateArg && 585 1.1 joerg CSPGOGenerateArg->getOption().matches(options::OPT_fno_profile_generate)) 586 1.1 joerg CSPGOGenerateArg = nullptr; 587 1.1 joerg 588 1.1 joerg auto *ProfileUseArg = getLastProfileUseArg(Args); 589 1.1 joerg 590 1.1 joerg if (CSPGOGenerateArg) { 591 1.1 joerg CmdArgs.push_back(Args.MakeArgString("-plugin-opt=cs-profile-generate")); 592 1.1 joerg if (CSPGOGenerateArg->getOption().matches( 593 1.1 joerg options::OPT_fcs_profile_generate_EQ)) { 594 1.1 joerg SmallString<128> Path(CSPGOGenerateArg->getValue()); 595 1.1 joerg llvm::sys::path::append(Path, "default_%m.profraw"); 596 1.1 joerg CmdArgs.push_back( 597 1.1 joerg Args.MakeArgString(Twine("-plugin-opt=cs-profile-path=") + Path)); 598 1.1 joerg } else 599 1.1 joerg CmdArgs.push_back( 600 1.1 joerg Args.MakeArgString("-plugin-opt=cs-profile-path=default_%m.profraw")); 601 1.1 joerg } else if (ProfileUseArg) { 602 1.1 joerg SmallString<128> Path( 603 1.1 joerg ProfileUseArg->getNumValues() == 0 ? "" : ProfileUseArg->getValue()); 604 1.1 joerg if (Path.empty() || llvm::sys::fs::is_directory(Path)) 605 1.1 joerg llvm::sys::path::append(Path, "default.profdata"); 606 1.1 joerg CmdArgs.push_back(Args.MakeArgString(Twine("-plugin-opt=cs-profile-path=") + 607 1.1 joerg Path)); 608 1.1 joerg } 609 1.1 joerg 610 1.1.1.2 joerg // Pass an option to enable/disable the new pass manager. 611 1.1.1.2 joerg if (auto *A = Args.getLastArg(options::OPT_flegacy_pass_manager, 612 1.1.1.2 joerg options::OPT_fno_legacy_pass_manager)) { 613 1.1.1.2 joerg if (A->getOption().matches(options::OPT_flegacy_pass_manager)) 614 1.1.1.2 joerg CmdArgs.push_back("-plugin-opt=legacy-pass-manager"); 615 1.1.1.2 joerg else 616 1.1.1.2 joerg CmdArgs.push_back("-plugin-opt=new-pass-manager"); 617 1.1 joerg } 618 1.1 joerg 619 1.1.1.2 joerg // Pass an option to enable pseudo probe emission. 620 1.1.1.2 joerg if (Args.hasFlag(options::OPT_fpseudo_probe_for_profiling, 621 1.1.1.2 joerg options::OPT_fno_pseudo_probe_for_profiling, false)) 622 1.1.1.2 joerg CmdArgs.push_back("-plugin-opt=pseudo-probe-for-profiling"); 623 1.1.1.2 joerg 624 1.1 joerg // Setup statistics file output. 625 1.1.1.2 joerg SmallString<128> StatsFile = getStatsFileName(Args, Output, Input, D); 626 1.1 joerg if (!StatsFile.empty()) 627 1.1 joerg CmdArgs.push_back( 628 1.1 joerg Args.MakeArgString(Twine("-plugin-opt=stats-file=") + StatsFile)); 629 1.1 joerg 630 1.1.1.2 joerg addX86AlignBranchArgs(D, Args, CmdArgs, /*IsLTO=*/true); 631 1.1 joerg 632 1.1.1.2 joerg // Handle remark diagnostics on screen options: '-Rpass-*'. 633 1.1.1.2 joerg renderRpassOptions(Args, CmdArgs); 634 1.1.1.2 joerg 635 1.1.1.2 joerg // Handle serialized remarks options: '-fsave-optimization-record' 636 1.1.1.2 joerg // and '-foptimization-record-*'. 637 1.1.1.2 joerg if (willEmitRemarks(Args)) 638 1.1.1.2 joerg renderRemarksOptions(Args, CmdArgs, ToolChain.getEffectiveTriple(), Input, 639 1.1.1.2 joerg Output); 640 1.1.1.2 joerg 641 1.1.1.2 joerg // Handle remarks hotness/threshold related options. 642 1.1.1.2 joerg renderRemarksHotnessOptions(Args, CmdArgs); 643 1.1.1.2 joerg 644 1.1.1.2 joerg addMachineOutlinerArgs(D, Args, CmdArgs, ToolChain.getEffectiveTriple(), 645 1.1.1.2 joerg /*IsLTO=*/true); 646 1.1 joerg } 647 1.1 joerg 648 1.1 joerg void tools::addArchSpecificRPath(const ToolChain &TC, const ArgList &Args, 649 1.1 joerg ArgStringList &CmdArgs) { 650 1.1.1.2 joerg // Enable -frtlib-add-rpath by default for the case of VE. 651 1.1.1.2 joerg const bool IsVE = TC.getTriple().isVE(); 652 1.1.1.2 joerg bool DefaultValue = IsVE; 653 1.1 joerg if (!Args.hasFlag(options::OPT_frtlib_add_rpath, 654 1.1.1.2 joerg options::OPT_fno_rtlib_add_rpath, DefaultValue)) 655 1.1 joerg return; 656 1.1 joerg 657 1.1 joerg std::string CandidateRPath = TC.getArchSpecificLibPath(); 658 1.1 joerg if (TC.getVFS().exists(CandidateRPath)) { 659 1.1 joerg CmdArgs.push_back("-rpath"); 660 1.1 joerg CmdArgs.push_back(Args.MakeArgString(CandidateRPath.c_str())); 661 1.1 joerg } 662 1.1 joerg } 663 1.1 joerg 664 1.1 joerg bool tools::addOpenMPRuntime(ArgStringList &CmdArgs, const ToolChain &TC, 665 1.1 joerg const ArgList &Args, bool ForceStaticHostRuntime, 666 1.1 joerg bool IsOffloadingHost, bool GompNeedsRT) { 667 1.1 joerg if (!Args.hasFlag(options::OPT_fopenmp, options::OPT_fopenmp_EQ, 668 1.1 joerg options::OPT_fno_openmp, false)) 669 1.1 joerg return false; 670 1.1 joerg 671 1.1 joerg Driver::OpenMPRuntimeKind RTKind = TC.getDriver().getOpenMPRuntime(Args); 672 1.1 joerg 673 1.1 joerg if (RTKind == Driver::OMPRT_Unknown) 674 1.1 joerg // Already diagnosed. 675 1.1 joerg return false; 676 1.1 joerg 677 1.1 joerg if (ForceStaticHostRuntime) 678 1.1 joerg CmdArgs.push_back("-Bstatic"); 679 1.1 joerg 680 1.1 joerg switch (RTKind) { 681 1.1 joerg case Driver::OMPRT_OMP: 682 1.1 joerg CmdArgs.push_back("-lomp"); 683 1.1 joerg break; 684 1.1 joerg case Driver::OMPRT_GOMP: 685 1.1 joerg CmdArgs.push_back("-lgomp"); 686 1.1 joerg break; 687 1.1 joerg case Driver::OMPRT_IOMP5: 688 1.1 joerg CmdArgs.push_back("-liomp5"); 689 1.1 joerg break; 690 1.1 joerg case Driver::OMPRT_Unknown: 691 1.1 joerg break; 692 1.1 joerg } 693 1.1 joerg 694 1.1 joerg if (ForceStaticHostRuntime) 695 1.1 joerg CmdArgs.push_back("-Bdynamic"); 696 1.1 joerg 697 1.1 joerg if (RTKind == Driver::OMPRT_GOMP && GompNeedsRT) 698 1.1 joerg CmdArgs.push_back("-lrt"); 699 1.1 joerg 700 1.1 joerg if (IsOffloadingHost) 701 1.1 joerg CmdArgs.push_back("-lomptarget"); 702 1.1 joerg 703 1.1 joerg addArchSpecificRPath(TC, Args, CmdArgs); 704 1.1 joerg 705 1.1 joerg return true; 706 1.1 joerg } 707 1.1 joerg 708 1.1 joerg static void addSanitizerRuntime(const ToolChain &TC, const ArgList &Args, 709 1.1 joerg ArgStringList &CmdArgs, StringRef Sanitizer, 710 1.1 joerg bool IsShared, bool IsWhole) { 711 1.1 joerg // Wrap any static runtimes that must be forced into executable in 712 1.1 joerg // whole-archive. 713 1.1 joerg if (IsWhole) CmdArgs.push_back("--whole-archive"); 714 1.1 joerg CmdArgs.push_back(TC.getCompilerRTArgString( 715 1.1 joerg Args, Sanitizer, IsShared ? ToolChain::FT_Shared : ToolChain::FT_Static)); 716 1.1 joerg if (IsWhole) CmdArgs.push_back("--no-whole-archive"); 717 1.1 joerg 718 1.1 joerg if (IsShared) { 719 1.1 joerg addArchSpecificRPath(TC, Args, CmdArgs); 720 1.1 joerg } 721 1.1 joerg } 722 1.1 joerg 723 1.1 joerg // Tries to use a file with the list of dynamic symbols that need to be exported 724 1.1 joerg // from the runtime library. Returns true if the file was found. 725 1.1 joerg static bool addSanitizerDynamicList(const ToolChain &TC, const ArgList &Args, 726 1.1 joerg ArgStringList &CmdArgs, 727 1.1 joerg StringRef Sanitizer) { 728 1.1 joerg // Solaris ld defaults to --export-dynamic behaviour but doesn't support 729 1.1 joerg // the option, so don't try to pass it. 730 1.1 joerg if (TC.getTriple().getOS() == llvm::Triple::Solaris) 731 1.1 joerg return true; 732 1.1 joerg // Myriad is static linking only. Furthermore, some versions of its 733 1.1 joerg // linker have the bug where --export-dynamic overrides -static, so 734 1.1 joerg // don't use --export-dynamic on that platform. 735 1.1 joerg if (TC.getTriple().getVendor() == llvm::Triple::Myriad) 736 1.1 joerg return true; 737 1.1 joerg SmallString<128> SanRT(TC.getCompilerRT(Args, Sanitizer)); 738 1.1 joerg if (llvm::sys::fs::exists(SanRT + ".syms")) { 739 1.1 joerg CmdArgs.push_back(Args.MakeArgString("--dynamic-list=" + SanRT + ".syms")); 740 1.1 joerg return true; 741 1.1 joerg } 742 1.1 joerg return false; 743 1.1 joerg } 744 1.1 joerg 745 1.1.1.2 joerg static const char *getAsNeededOption(const ToolChain &TC, bool as_needed) { 746 1.1.1.2 joerg // While the Solaris 11.2 ld added --as-needed/--no-as-needed as aliases 747 1.1.1.2 joerg // for the native forms -z ignore/-z record, they are missing in Illumos, 748 1.1.1.2 joerg // so always use the native form. 749 1.1.1.2 joerg if (TC.getTriple().isOSSolaris()) 750 1.1.1.2 joerg return as_needed ? "-zignore" : "-zrecord"; 751 1.1.1.2 joerg else 752 1.1.1.2 joerg return as_needed ? "--as-needed" : "--no-as-needed"; 753 1.1.1.2 joerg } 754 1.1.1.2 joerg 755 1.1 joerg void tools::linkSanitizerRuntimeDeps(const ToolChain &TC, 756 1.1 joerg ArgStringList &CmdArgs) { 757 1.1.1.2 joerg // Fuchsia never needs these. Any sanitizer runtimes with system 758 1.1.1.2 joerg // dependencies use the `.deplibs` feature instead. 759 1.1.1.2 joerg if (TC.getTriple().isOSFuchsia()) 760 1.1.1.2 joerg return; 761 1.1.1.2 joerg 762 1.1 joerg // Force linking against the system libraries sanitizers depends on 763 1.1 joerg // (see PR15823 why this is necessary). 764 1.1.1.2 joerg CmdArgs.push_back(getAsNeededOption(TC, false)); 765 1.1 joerg // There's no libpthread or librt on RTEMS & Android. 766 1.1 joerg if (TC.getTriple().getOS() != llvm::Triple::RTEMS && 767 1.1 joerg !TC.getTriple().isAndroid()) { 768 1.1 joerg CmdArgs.push_back("-lpthread"); 769 1.1 joerg if (!TC.getTriple().isOSOpenBSD()) 770 1.1 joerg CmdArgs.push_back("-lrt"); 771 1.1 joerg } 772 1.1 joerg CmdArgs.push_back("-lm"); 773 1.1 joerg // There's no libdl on all OSes. 774 1.1 joerg if (!TC.getTriple().isOSFreeBSD() && 775 1.1 joerg !TC.getTriple().isOSNetBSD() && 776 1.1 joerg !TC.getTriple().isOSOpenBSD() && 777 1.1 joerg TC.getTriple().getOS() != llvm::Triple::RTEMS) 778 1.1 joerg CmdArgs.push_back("-ldl"); 779 1.1 joerg // Required for backtrace on some OSes 780 1.1 joerg if (TC.getTriple().isOSFreeBSD() || 781 1.1 joerg TC.getTriple().isOSNetBSD()) 782 1.1 joerg CmdArgs.push_back("-lexecinfo"); 783 1.1 joerg } 784 1.1 joerg 785 1.1 joerg static void 786 1.1 joerg collectSanitizerRuntimes(const ToolChain &TC, const ArgList &Args, 787 1.1 joerg SmallVectorImpl<StringRef> &SharedRuntimes, 788 1.1 joerg SmallVectorImpl<StringRef> &StaticRuntimes, 789 1.1 joerg SmallVectorImpl<StringRef> &NonWholeStaticRuntimes, 790 1.1 joerg SmallVectorImpl<StringRef> &HelperStaticRuntimes, 791 1.1 joerg SmallVectorImpl<StringRef> &RequiredSymbols) { 792 1.1 joerg const SanitizerArgs &SanArgs = TC.getSanitizerArgs(); 793 1.1 joerg // Collect shared runtimes. 794 1.1 joerg if (SanArgs.needsSharedRt()) { 795 1.1 joerg if (SanArgs.needsAsanRt() && SanArgs.linkRuntimes()) { 796 1.1 joerg SharedRuntimes.push_back("asan"); 797 1.1 joerg if (!Args.hasArg(options::OPT_shared) && !TC.getTriple().isAndroid()) 798 1.1 joerg HelperStaticRuntimes.push_back("asan-preinit"); 799 1.1 joerg } 800 1.1.1.2 joerg if (SanArgs.needsMemProfRt() && SanArgs.linkRuntimes()) { 801 1.1.1.2 joerg SharedRuntimes.push_back("memprof"); 802 1.1.1.2 joerg if (!Args.hasArg(options::OPT_shared) && !TC.getTriple().isAndroid()) 803 1.1.1.2 joerg HelperStaticRuntimes.push_back("memprof-preinit"); 804 1.1.1.2 joerg } 805 1.1 joerg if (SanArgs.needsUbsanRt() && SanArgs.linkRuntimes()) { 806 1.1 joerg if (SanArgs.requiresMinimalRuntime()) 807 1.1 joerg SharedRuntimes.push_back("ubsan_minimal"); 808 1.1 joerg else 809 1.1 joerg SharedRuntimes.push_back("ubsan_standalone"); 810 1.1 joerg } 811 1.1 joerg if (SanArgs.needsScudoRt() && SanArgs.linkRuntimes()) { 812 1.1 joerg if (SanArgs.requiresMinimalRuntime()) 813 1.1 joerg SharedRuntimes.push_back("scudo_minimal"); 814 1.1 joerg else 815 1.1 joerg SharedRuntimes.push_back("scudo"); 816 1.1 joerg } 817 1.1.1.2 joerg if (SanArgs.needsTsanRt() && SanArgs.linkRuntimes()) 818 1.1.1.2 joerg SharedRuntimes.push_back("tsan"); 819 1.1.1.2 joerg if (SanArgs.needsHwasanRt() && SanArgs.linkRuntimes()) { 820 1.1.1.2 joerg if (SanArgs.needsHwasanAliasesRt()) 821 1.1.1.2 joerg SharedRuntimes.push_back("hwasan_aliases"); 822 1.1.1.2 joerg else 823 1.1.1.2 joerg SharedRuntimes.push_back("hwasan"); 824 1.1.1.2 joerg } 825 1.1 joerg } 826 1.1 joerg 827 1.1 joerg // The stats_client library is also statically linked into DSOs. 828 1.1 joerg if (SanArgs.needsStatsRt() && SanArgs.linkRuntimes()) 829 1.1 joerg StaticRuntimes.push_back("stats_client"); 830 1.1 joerg 831 1.1 joerg // Collect static runtimes. 832 1.1.1.2 joerg if (Args.hasArg(options::OPT_shared)) { 833 1.1.1.2 joerg // Don't link static runtimes into DSOs. 834 1.1 joerg return; 835 1.1 joerg } 836 1.1.1.2 joerg 837 1.1.1.2 joerg // Each static runtime that has a DSO counterpart above is excluded below, 838 1.1.1.2 joerg // but runtimes that exist only as static are not affected by needsSharedRt. 839 1.1.1.2 joerg 840 1.1.1.2 joerg if (!SanArgs.needsSharedRt() && SanArgs.needsAsanRt() && SanArgs.linkRuntimes()) { 841 1.1 joerg StaticRuntimes.push_back("asan"); 842 1.1 joerg if (SanArgs.linkCXXRuntimes()) 843 1.1 joerg StaticRuntimes.push_back("asan_cxx"); 844 1.1 joerg } 845 1.1 joerg 846 1.1.1.2 joerg if (!SanArgs.needsSharedRt() && SanArgs.needsMemProfRt() && 847 1.1.1.2 joerg SanArgs.linkRuntimes()) { 848 1.1.1.2 joerg StaticRuntimes.push_back("memprof"); 849 1.1 joerg if (SanArgs.linkCXXRuntimes()) 850 1.1.1.2 joerg StaticRuntimes.push_back("memprof_cxx"); 851 1.1.1.2 joerg } 852 1.1.1.2 joerg 853 1.1.1.2 joerg if (!SanArgs.needsSharedRt() && SanArgs.needsHwasanRt() && SanArgs.linkRuntimes()) { 854 1.1.1.2 joerg if (SanArgs.needsHwasanAliasesRt()) { 855 1.1.1.2 joerg StaticRuntimes.push_back("hwasan_aliases"); 856 1.1.1.2 joerg if (SanArgs.linkCXXRuntimes()) 857 1.1.1.2 joerg StaticRuntimes.push_back("hwasan_aliases_cxx"); 858 1.1.1.2 joerg } else { 859 1.1.1.2 joerg StaticRuntimes.push_back("hwasan"); 860 1.1.1.2 joerg if (SanArgs.linkCXXRuntimes()) 861 1.1.1.2 joerg StaticRuntimes.push_back("hwasan_cxx"); 862 1.1.1.2 joerg } 863 1.1 joerg } 864 1.1 joerg if (SanArgs.needsDfsanRt() && SanArgs.linkRuntimes()) 865 1.1 joerg StaticRuntimes.push_back("dfsan"); 866 1.1 joerg if (SanArgs.needsLsanRt() && SanArgs.linkRuntimes()) 867 1.1 joerg StaticRuntimes.push_back("lsan"); 868 1.1 joerg if (SanArgs.needsMsanRt() && SanArgs.linkRuntimes()) { 869 1.1 joerg StaticRuntimes.push_back("msan"); 870 1.1 joerg if (SanArgs.linkCXXRuntimes()) 871 1.1 joerg StaticRuntimes.push_back("msan_cxx"); 872 1.1 joerg } 873 1.1.1.2 joerg if (!SanArgs.needsSharedRt() && SanArgs.needsTsanRt() && 874 1.1.1.2 joerg SanArgs.linkRuntimes()) { 875 1.1 joerg StaticRuntimes.push_back("tsan"); 876 1.1 joerg if (SanArgs.linkCXXRuntimes()) 877 1.1 joerg StaticRuntimes.push_back("tsan_cxx"); 878 1.1 joerg } 879 1.1.1.2 joerg if (!SanArgs.needsSharedRt() && SanArgs.needsUbsanRt() && SanArgs.linkRuntimes()) { 880 1.1 joerg if (SanArgs.requiresMinimalRuntime()) { 881 1.1 joerg StaticRuntimes.push_back("ubsan_minimal"); 882 1.1 joerg } else { 883 1.1 joerg StaticRuntimes.push_back("ubsan_standalone"); 884 1.1 joerg if (SanArgs.linkCXXRuntimes()) 885 1.1 joerg StaticRuntimes.push_back("ubsan_standalone_cxx"); 886 1.1 joerg } 887 1.1 joerg } 888 1.1 joerg if (SanArgs.needsSafeStackRt() && SanArgs.linkRuntimes()) { 889 1.1 joerg NonWholeStaticRuntimes.push_back("safestack"); 890 1.1 joerg RequiredSymbols.push_back("__safestack_init"); 891 1.1 joerg } 892 1.1.1.2 joerg if (!(SanArgs.needsSharedRt() && SanArgs.needsUbsanRt() && SanArgs.linkRuntimes())) { 893 1.1.1.2 joerg if (SanArgs.needsCfiRt() && SanArgs.linkRuntimes()) 894 1.1.1.2 joerg StaticRuntimes.push_back("cfi"); 895 1.1.1.2 joerg if (SanArgs.needsCfiDiagRt() && SanArgs.linkRuntimes()) { 896 1.1.1.2 joerg StaticRuntimes.push_back("cfi_diag"); 897 1.1.1.2 joerg if (SanArgs.linkCXXRuntimes()) 898 1.1.1.2 joerg StaticRuntimes.push_back("ubsan_standalone_cxx"); 899 1.1.1.2 joerg } 900 1.1 joerg } 901 1.1 joerg if (SanArgs.needsStatsRt() && SanArgs.linkRuntimes()) { 902 1.1 joerg NonWholeStaticRuntimes.push_back("stats"); 903 1.1 joerg RequiredSymbols.push_back("__sanitizer_stats_register"); 904 1.1 joerg } 905 1.1.1.2 joerg if (!SanArgs.needsSharedRt() && SanArgs.needsScudoRt() && SanArgs.linkRuntimes()) { 906 1.1 joerg if (SanArgs.requiresMinimalRuntime()) { 907 1.1 joerg StaticRuntimes.push_back("scudo_minimal"); 908 1.1 joerg if (SanArgs.linkCXXRuntimes()) 909 1.1 joerg StaticRuntimes.push_back("scudo_cxx_minimal"); 910 1.1 joerg } else { 911 1.1 joerg StaticRuntimes.push_back("scudo"); 912 1.1 joerg if (SanArgs.linkCXXRuntimes()) 913 1.1 joerg StaticRuntimes.push_back("scudo_cxx"); 914 1.1 joerg } 915 1.1 joerg } 916 1.1 joerg } 917 1.1 joerg 918 1.1 joerg // Should be called before we add system libraries (C++ ABI, libstdc++/libc++, 919 1.1 joerg // C runtime, etc). Returns true if sanitizer system deps need to be linked in. 920 1.1 joerg bool tools::addSanitizerRuntimes(const ToolChain &TC, const ArgList &Args, 921 1.1 joerg ArgStringList &CmdArgs) { 922 1.1 joerg SmallVector<StringRef, 4> SharedRuntimes, StaticRuntimes, 923 1.1 joerg NonWholeStaticRuntimes, HelperStaticRuntimes, RequiredSymbols; 924 1.1 joerg collectSanitizerRuntimes(TC, Args, SharedRuntimes, StaticRuntimes, 925 1.1 joerg NonWholeStaticRuntimes, HelperStaticRuntimes, 926 1.1 joerg RequiredSymbols); 927 1.1 joerg 928 1.1 joerg const SanitizerArgs &SanArgs = TC.getSanitizerArgs(); 929 1.1 joerg // Inject libfuzzer dependencies. 930 1.1 joerg if (SanArgs.needsFuzzer() && SanArgs.linkRuntimes() && 931 1.1 joerg !Args.hasArg(options::OPT_shared)) { 932 1.1 joerg 933 1.1 joerg addSanitizerRuntime(TC, Args, CmdArgs, "fuzzer", false, true); 934 1.1.1.2 joerg if (SanArgs.needsFuzzerInterceptors()) 935 1.1.1.2 joerg addSanitizerRuntime(TC, Args, CmdArgs, "fuzzer_interceptors", false, 936 1.1.1.2 joerg true); 937 1.1.1.2 joerg if (!Args.hasArg(clang::driver::options::OPT_nostdlibxx)) { 938 1.1.1.2 joerg bool OnlyLibstdcxxStatic = Args.hasArg(options::OPT_static_libstdcxx) && 939 1.1.1.2 joerg !Args.hasArg(options::OPT_static); 940 1.1.1.2 joerg if (OnlyLibstdcxxStatic) 941 1.1.1.2 joerg CmdArgs.push_back("-Bstatic"); 942 1.1 joerg TC.AddCXXStdlibLibArgs(Args, CmdArgs); 943 1.1.1.2 joerg if (OnlyLibstdcxxStatic) 944 1.1.1.2 joerg CmdArgs.push_back("-Bdynamic"); 945 1.1.1.2 joerg } 946 1.1 joerg } 947 1.1 joerg 948 1.1 joerg for (auto RT : SharedRuntimes) 949 1.1 joerg addSanitizerRuntime(TC, Args, CmdArgs, RT, true, false); 950 1.1 joerg for (auto RT : HelperStaticRuntimes) 951 1.1 joerg addSanitizerRuntime(TC, Args, CmdArgs, RT, false, true); 952 1.1 joerg bool AddExportDynamic = false; 953 1.1 joerg for (auto RT : StaticRuntimes) { 954 1.1 joerg addSanitizerRuntime(TC, Args, CmdArgs, RT, false, true); 955 1.1 joerg AddExportDynamic |= !addSanitizerDynamicList(TC, Args, CmdArgs, RT); 956 1.1 joerg } 957 1.1 joerg for (auto RT : NonWholeStaticRuntimes) { 958 1.1 joerg addSanitizerRuntime(TC, Args, CmdArgs, RT, false, false); 959 1.1 joerg AddExportDynamic |= !addSanitizerDynamicList(TC, Args, CmdArgs, RT); 960 1.1 joerg } 961 1.1 joerg for (auto S : RequiredSymbols) { 962 1.1 joerg CmdArgs.push_back("-u"); 963 1.1 joerg CmdArgs.push_back(Args.MakeArgString(S)); 964 1.1 joerg } 965 1.1 joerg // If there is a static runtime with no dynamic list, force all the symbols 966 1.1 joerg // to be dynamic to be sure we export sanitizer interface functions. 967 1.1 joerg if (AddExportDynamic) 968 1.1 joerg CmdArgs.push_back("--export-dynamic"); 969 1.1 joerg 970 1.1 joerg if (SanArgs.hasCrossDsoCfi() && !AddExportDynamic) 971 1.1.1.2 joerg CmdArgs.push_back("--export-dynamic-symbol=__cfi_check"); 972 1.1 joerg 973 1.1 joerg return !StaticRuntimes.empty() || !NonWholeStaticRuntimes.empty(); 974 1.1 joerg } 975 1.1 joerg 976 1.1 joerg bool tools::addXRayRuntime(const ToolChain&TC, const ArgList &Args, ArgStringList &CmdArgs) { 977 1.1 joerg if (Args.hasArg(options::OPT_shared)) 978 1.1 joerg return false; 979 1.1 joerg 980 1.1 joerg if (TC.getXRayArgs().needsXRayRt()) { 981 1.1 joerg CmdArgs.push_back("-whole-archive"); 982 1.1 joerg CmdArgs.push_back(TC.getCompilerRTArgString(Args, "xray")); 983 1.1 joerg for (const auto &Mode : TC.getXRayArgs().modeList()) 984 1.1 joerg CmdArgs.push_back(TC.getCompilerRTArgString(Args, Mode)); 985 1.1 joerg CmdArgs.push_back("-no-whole-archive"); 986 1.1 joerg return true; 987 1.1 joerg } 988 1.1 joerg 989 1.1 joerg return false; 990 1.1 joerg } 991 1.1 joerg 992 1.1 joerg void tools::linkXRayRuntimeDeps(const ToolChain &TC, ArgStringList &CmdArgs) { 993 1.1.1.2 joerg CmdArgs.push_back(getAsNeededOption(TC, false)); 994 1.1 joerg CmdArgs.push_back("-lpthread"); 995 1.1 joerg if (!TC.getTriple().isOSOpenBSD()) 996 1.1 joerg CmdArgs.push_back("-lrt"); 997 1.1 joerg CmdArgs.push_back("-lm"); 998 1.1 joerg 999 1.1 joerg if (!TC.getTriple().isOSFreeBSD() && 1000 1.1 joerg !TC.getTriple().isOSNetBSD() && 1001 1.1 joerg !TC.getTriple().isOSOpenBSD()) 1002 1.1 joerg CmdArgs.push_back("-ldl"); 1003 1.1 joerg } 1004 1.1 joerg 1005 1.1 joerg bool tools::areOptimizationsEnabled(const ArgList &Args) { 1006 1.1 joerg // Find the last -O arg and see if it is non-zero. 1007 1.1 joerg if (Arg *A = Args.getLastArg(options::OPT_O_Group)) 1008 1.1 joerg return !A->getOption().matches(options::OPT_O0); 1009 1.1 joerg // Defaults to -O0. 1010 1.1 joerg return false; 1011 1.1 joerg } 1012 1.1 joerg 1013 1.1.1.2 joerg const char *tools::SplitDebugName(const JobAction &JA, const ArgList &Args, 1014 1.1.1.2 joerg const InputInfo &Input, 1015 1.1 joerg const InputInfo &Output) { 1016 1.1.1.2 joerg auto AddPostfix = [JA](auto &F) { 1017 1.1.1.2 joerg if (JA.getOffloadingDeviceKind() == Action::OFK_HIP) 1018 1.1.1.2 joerg F += (Twine("_") + JA.getOffloadingArch()).str(); 1019 1.1.1.2 joerg F += ".dwo"; 1020 1.1.1.2 joerg }; 1021 1.1 joerg if (Arg *A = Args.getLastArg(options::OPT_gsplit_dwarf_EQ)) 1022 1.1 joerg if (StringRef(A->getValue()) == "single") 1023 1.1 joerg return Args.MakeArgString(Output.getFilename()); 1024 1.1 joerg 1025 1.1 joerg Arg *FinalOutput = Args.getLastArg(options::OPT_o); 1026 1.1 joerg if (FinalOutput && Args.hasArg(options::OPT_c)) { 1027 1.1 joerg SmallString<128> T(FinalOutput->getValue()); 1028 1.1.1.2 joerg llvm::sys::path::remove_filename(T); 1029 1.1.1.2 joerg llvm::sys::path::append(T, llvm::sys::path::stem(FinalOutput->getValue())); 1030 1.1.1.2 joerg AddPostfix(T); 1031 1.1 joerg return Args.MakeArgString(T); 1032 1.1 joerg } else { 1033 1.1 joerg // Use the compilation dir. 1034 1.1.1.2 joerg Arg *A = Args.getLastArg(options::OPT_ffile_compilation_dir_EQ, 1035 1.1.1.2 joerg options::OPT_fdebug_compilation_dir_EQ); 1036 1.1.1.2 joerg SmallString<128> T(A ? A->getValue() : ""); 1037 1.1 joerg SmallString<128> F(llvm::sys::path::stem(Input.getBaseInput())); 1038 1.1.1.2 joerg AddPostfix(F); 1039 1.1 joerg T += F; 1040 1.1.1.2 joerg return Args.MakeArgString(T); 1041 1.1 joerg } 1042 1.1 joerg } 1043 1.1 joerg 1044 1.1 joerg void tools::SplitDebugInfo(const ToolChain &TC, Compilation &C, const Tool &T, 1045 1.1 joerg const JobAction &JA, const ArgList &Args, 1046 1.1 joerg const InputInfo &Output, const char *OutFile) { 1047 1.1 joerg ArgStringList ExtractArgs; 1048 1.1 joerg ExtractArgs.push_back("--extract-dwo"); 1049 1.1 joerg 1050 1.1 joerg ArgStringList StripArgs; 1051 1.1 joerg StripArgs.push_back("--strip-dwo"); 1052 1.1 joerg 1053 1.1 joerg // Grabbing the output of the earlier compile step. 1054 1.1 joerg StripArgs.push_back(Output.getFilename()); 1055 1.1 joerg ExtractArgs.push_back(Output.getFilename()); 1056 1.1 joerg ExtractArgs.push_back(OutFile); 1057 1.1 joerg 1058 1.1 joerg const char *Exec = 1059 1.1 joerg Args.MakeArgString(TC.GetProgramPath(CLANG_DEFAULT_OBJCOPY)); 1060 1.1 joerg InputInfo II(types::TY_Object, Output.getFilename(), Output.getFilename()); 1061 1.1 joerg 1062 1.1 joerg // First extract the dwo sections. 1063 1.1.1.2 joerg C.addCommand(std::make_unique<Command>(JA, T, 1064 1.1.1.2 joerg ResponseFileSupport::AtFileCurCP(), 1065 1.1.1.2 joerg Exec, ExtractArgs, II, Output)); 1066 1.1 joerg 1067 1.1 joerg // Then remove them from the original .o file. 1068 1.1.1.2 joerg C.addCommand(std::make_unique<Command>( 1069 1.1.1.2 joerg JA, T, ResponseFileSupport::AtFileCurCP(), Exec, StripArgs, II, Output)); 1070 1.1 joerg } 1071 1.1 joerg 1072 1.1 joerg // Claim options we don't want to warn if they are unused. We do this for 1073 1.1 joerg // options that build systems might add but are unused when assembling or only 1074 1.1 joerg // running the preprocessor for example. 1075 1.1 joerg void tools::claimNoWarnArgs(const ArgList &Args) { 1076 1.1 joerg // Don't warn about unused -f(no-)?lto. This can happen when we're 1077 1.1 joerg // preprocessing, precompiling or assembling. 1078 1.1 joerg Args.ClaimAllArgs(options::OPT_flto_EQ); 1079 1.1 joerg Args.ClaimAllArgs(options::OPT_flto); 1080 1.1 joerg Args.ClaimAllArgs(options::OPT_fno_lto); 1081 1.1 joerg } 1082 1.1 joerg 1083 1.1 joerg Arg *tools::getLastProfileUseArg(const ArgList &Args) { 1084 1.1 joerg auto *ProfileUseArg = Args.getLastArg( 1085 1.1 joerg options::OPT_fprofile_instr_use, options::OPT_fprofile_instr_use_EQ, 1086 1.1 joerg options::OPT_fprofile_use, options::OPT_fprofile_use_EQ, 1087 1.1 joerg options::OPT_fno_profile_instr_use); 1088 1.1 joerg 1089 1.1 joerg if (ProfileUseArg && 1090 1.1 joerg ProfileUseArg->getOption().matches(options::OPT_fno_profile_instr_use)) 1091 1.1 joerg ProfileUseArg = nullptr; 1092 1.1 joerg 1093 1.1 joerg return ProfileUseArg; 1094 1.1 joerg } 1095 1.1 joerg 1096 1.1 joerg Arg *tools::getLastProfileSampleUseArg(const ArgList &Args) { 1097 1.1 joerg auto *ProfileSampleUseArg = Args.getLastArg( 1098 1.1 joerg options::OPT_fprofile_sample_use, options::OPT_fprofile_sample_use_EQ, 1099 1.1 joerg options::OPT_fauto_profile, options::OPT_fauto_profile_EQ, 1100 1.1 joerg options::OPT_fno_profile_sample_use, options::OPT_fno_auto_profile); 1101 1.1 joerg 1102 1.1 joerg if (ProfileSampleUseArg && 1103 1.1 joerg (ProfileSampleUseArg->getOption().matches( 1104 1.1 joerg options::OPT_fno_profile_sample_use) || 1105 1.1 joerg ProfileSampleUseArg->getOption().matches(options::OPT_fno_auto_profile))) 1106 1.1 joerg return nullptr; 1107 1.1 joerg 1108 1.1 joerg return Args.getLastArg(options::OPT_fprofile_sample_use_EQ, 1109 1.1 joerg options::OPT_fauto_profile_EQ); 1110 1.1 joerg } 1111 1.1 joerg 1112 1.1 joerg /// Parses the various -fpic/-fPIC/-fpie/-fPIE arguments. Then, 1113 1.1 joerg /// smooshes them together with platform defaults, to decide whether 1114 1.1 joerg /// this compile should be using PIC mode or not. Returns a tuple of 1115 1.1 joerg /// (RelocationModel, PICLevel, IsPIE). 1116 1.1 joerg std::tuple<llvm::Reloc::Model, unsigned, bool> 1117 1.1 joerg tools::ParsePICArgs(const ToolChain &ToolChain, const ArgList &Args) { 1118 1.1 joerg const llvm::Triple &EffectiveTriple = ToolChain.getEffectiveTriple(); 1119 1.1 joerg const llvm::Triple &Triple = ToolChain.getTriple(); 1120 1.1 joerg 1121 1.1 joerg bool PIE = ToolChain.isPIEDefault(); 1122 1.1 joerg bool PIC = PIE || ToolChain.isPICDefault(); 1123 1.1 joerg // The Darwin/MachO default to use PIC does not apply when using -static. 1124 1.1 joerg if (Triple.isOSBinFormatMachO() && Args.hasArg(options::OPT_static)) 1125 1.1 joerg PIE = PIC = false; 1126 1.1 joerg bool IsPICLevelTwo = PIC; 1127 1.1 joerg 1128 1.1 joerg bool KernelOrKext = 1129 1.1 joerg Args.hasArg(options::OPT_mkernel, options::OPT_fapple_kext); 1130 1.1 joerg 1131 1.1 joerg // Android-specific defaults for PIC/PIE 1132 1.1 joerg if (Triple.isAndroid()) { 1133 1.1 joerg switch (Triple.getArch()) { 1134 1.1 joerg case llvm::Triple::arm: 1135 1.1 joerg case llvm::Triple::armeb: 1136 1.1 joerg case llvm::Triple::thumb: 1137 1.1 joerg case llvm::Triple::thumbeb: 1138 1.1 joerg case llvm::Triple::aarch64: 1139 1.1 joerg case llvm::Triple::mips: 1140 1.1 joerg case llvm::Triple::mipsel: 1141 1.1 joerg case llvm::Triple::mips64: 1142 1.1 joerg case llvm::Triple::mips64el: 1143 1.1 joerg PIC = true; // "-fpic" 1144 1.1 joerg break; 1145 1.1 joerg 1146 1.1 joerg case llvm::Triple::x86: 1147 1.1 joerg case llvm::Triple::x86_64: 1148 1.1 joerg PIC = true; // "-fPIC" 1149 1.1 joerg IsPICLevelTwo = true; 1150 1.1 joerg break; 1151 1.1 joerg 1152 1.1 joerg default: 1153 1.1 joerg break; 1154 1.1 joerg } 1155 1.1 joerg } 1156 1.1 joerg 1157 1.1 joerg // OpenBSD-specific defaults for PIE 1158 1.1 joerg if (Triple.isOSOpenBSD()) { 1159 1.1 joerg switch (ToolChain.getArch()) { 1160 1.1 joerg case llvm::Triple::arm: 1161 1.1 joerg case llvm::Triple::aarch64: 1162 1.1 joerg case llvm::Triple::mips64: 1163 1.1 joerg case llvm::Triple::mips64el: 1164 1.1 joerg case llvm::Triple::x86: 1165 1.1 joerg case llvm::Triple::x86_64: 1166 1.1 joerg IsPICLevelTwo = false; // "-fpie" 1167 1.1 joerg break; 1168 1.1 joerg 1169 1.1 joerg case llvm::Triple::ppc: 1170 1.1 joerg case llvm::Triple::sparcv9: 1171 1.1 joerg IsPICLevelTwo = true; // "-fPIE" 1172 1.1 joerg break; 1173 1.1 joerg 1174 1.1 joerg default: 1175 1.1 joerg break; 1176 1.1 joerg } 1177 1.1 joerg } 1178 1.1 joerg 1179 1.1 joerg // AMDGPU-specific defaults for PIC. 1180 1.1 joerg if (Triple.getArch() == llvm::Triple::amdgcn) 1181 1.1 joerg PIC = true; 1182 1.1 joerg 1183 1.1 joerg // The last argument relating to either PIC or PIE wins, and no 1184 1.1 joerg // other argument is used. If the last argument is any flavor of the 1185 1.1 joerg // '-fno-...' arguments, both PIC and PIE are disabled. Any PIE 1186 1.1 joerg // option implicitly enables PIC at the same level. 1187 1.1 joerg Arg *LastPICArg = Args.getLastArg(options::OPT_fPIC, options::OPT_fno_PIC, 1188 1.1 joerg options::OPT_fpic, options::OPT_fno_pic, 1189 1.1 joerg options::OPT_fPIE, options::OPT_fno_PIE, 1190 1.1 joerg options::OPT_fpie, options::OPT_fno_pie); 1191 1.1 joerg if (Triple.isOSWindows() && LastPICArg && 1192 1.1 joerg LastPICArg == 1193 1.1 joerg Args.getLastArg(options::OPT_fPIC, options::OPT_fpic, 1194 1.1 joerg options::OPT_fPIE, options::OPT_fpie)) { 1195 1.1 joerg ToolChain.getDriver().Diag(diag::err_drv_unsupported_opt_for_target) 1196 1.1 joerg << LastPICArg->getSpelling() << Triple.str(); 1197 1.1 joerg if (Triple.getArch() == llvm::Triple::x86_64) 1198 1.1 joerg return std::make_tuple(llvm::Reloc::PIC_, 2U, false); 1199 1.1 joerg return std::make_tuple(llvm::Reloc::Static, 0U, false); 1200 1.1 joerg } 1201 1.1 joerg 1202 1.1 joerg // Check whether the tool chain trumps the PIC-ness decision. If the PIC-ness 1203 1.1 joerg // is forced, then neither PIC nor PIE flags will have no effect. 1204 1.1 joerg if (!ToolChain.isPICDefaultForced()) { 1205 1.1 joerg if (LastPICArg) { 1206 1.1 joerg Option O = LastPICArg->getOption(); 1207 1.1 joerg if (O.matches(options::OPT_fPIC) || O.matches(options::OPT_fpic) || 1208 1.1 joerg O.matches(options::OPT_fPIE) || O.matches(options::OPT_fpie)) { 1209 1.1 joerg PIE = O.matches(options::OPT_fPIE) || O.matches(options::OPT_fpie); 1210 1.1 joerg PIC = 1211 1.1 joerg PIE || O.matches(options::OPT_fPIC) || O.matches(options::OPT_fpic); 1212 1.1 joerg IsPICLevelTwo = 1213 1.1 joerg O.matches(options::OPT_fPIE) || O.matches(options::OPT_fPIC); 1214 1.1 joerg } else { 1215 1.1 joerg PIE = PIC = false; 1216 1.1 joerg if (EffectiveTriple.isPS4CPU()) { 1217 1.1 joerg Arg *ModelArg = Args.getLastArg(options::OPT_mcmodel_EQ); 1218 1.1 joerg StringRef Model = ModelArg ? ModelArg->getValue() : ""; 1219 1.1 joerg if (Model != "kernel") { 1220 1.1 joerg PIC = true; 1221 1.1 joerg ToolChain.getDriver().Diag(diag::warn_drv_ps4_force_pic) 1222 1.1 joerg << LastPICArg->getSpelling(); 1223 1.1 joerg } 1224 1.1 joerg } 1225 1.1 joerg } 1226 1.1 joerg } 1227 1.1 joerg } 1228 1.1 joerg 1229 1.1 joerg // Introduce a Darwin and PS4-specific hack. If the default is PIC, but the 1230 1.1 joerg // PIC level would've been set to level 1, force it back to level 2 PIC 1231 1.1 joerg // instead. 1232 1.1 joerg if (PIC && (Triple.isOSDarwin() || EffectiveTriple.isPS4CPU())) 1233 1.1 joerg IsPICLevelTwo |= ToolChain.isPICDefault(); 1234 1.1 joerg 1235 1.1 joerg // This kernel flags are a trump-card: they will disable PIC/PIE 1236 1.1 joerg // generation, independent of the argument order. 1237 1.1 joerg if (KernelOrKext && 1238 1.1 joerg ((!EffectiveTriple.isiOS() || EffectiveTriple.isOSVersionLT(6)) && 1239 1.1 joerg !EffectiveTriple.isWatchOS())) 1240 1.1 joerg PIC = PIE = false; 1241 1.1 joerg 1242 1.1 joerg if (Arg *A = Args.getLastArg(options::OPT_mdynamic_no_pic)) { 1243 1.1 joerg // This is a very special mode. It trumps the other modes, almost no one 1244 1.1 joerg // uses it, and it isn't even valid on any OS but Darwin. 1245 1.1 joerg if (!Triple.isOSDarwin()) 1246 1.1 joerg ToolChain.getDriver().Diag(diag::err_drv_unsupported_opt_for_target) 1247 1.1 joerg << A->getSpelling() << Triple.str(); 1248 1.1 joerg 1249 1.1 joerg // FIXME: Warn when this flag trumps some other PIC or PIE flag. 1250 1.1 joerg 1251 1.1 joerg // Only a forced PIC mode can cause the actual compile to have PIC defines 1252 1.1 joerg // etc., no flags are sufficient. This behavior was selected to closely 1253 1.1 joerg // match that of llvm-gcc and Apple GCC before that. 1254 1.1 joerg PIC = ToolChain.isPICDefault() && ToolChain.isPICDefaultForced(); 1255 1.1 joerg 1256 1.1 joerg return std::make_tuple(llvm::Reloc::DynamicNoPIC, PIC ? 2U : 0U, false); 1257 1.1 joerg } 1258 1.1 joerg 1259 1.1 joerg bool EmbeddedPISupported; 1260 1.1 joerg switch (Triple.getArch()) { 1261 1.1 joerg case llvm::Triple::arm: 1262 1.1 joerg case llvm::Triple::armeb: 1263 1.1 joerg case llvm::Triple::thumb: 1264 1.1 joerg case llvm::Triple::thumbeb: 1265 1.1 joerg EmbeddedPISupported = true; 1266 1.1 joerg break; 1267 1.1 joerg default: 1268 1.1 joerg EmbeddedPISupported = false; 1269 1.1 joerg break; 1270 1.1 joerg } 1271 1.1 joerg 1272 1.1 joerg bool ROPI = false, RWPI = false; 1273 1.1 joerg Arg* LastROPIArg = Args.getLastArg(options::OPT_fropi, options::OPT_fno_ropi); 1274 1.1 joerg if (LastROPIArg && LastROPIArg->getOption().matches(options::OPT_fropi)) { 1275 1.1 joerg if (!EmbeddedPISupported) 1276 1.1 joerg ToolChain.getDriver().Diag(diag::err_drv_unsupported_opt_for_target) 1277 1.1 joerg << LastROPIArg->getSpelling() << Triple.str(); 1278 1.1 joerg ROPI = true; 1279 1.1 joerg } 1280 1.1 joerg Arg *LastRWPIArg = Args.getLastArg(options::OPT_frwpi, options::OPT_fno_rwpi); 1281 1.1 joerg if (LastRWPIArg && LastRWPIArg->getOption().matches(options::OPT_frwpi)) { 1282 1.1 joerg if (!EmbeddedPISupported) 1283 1.1 joerg ToolChain.getDriver().Diag(diag::err_drv_unsupported_opt_for_target) 1284 1.1 joerg << LastRWPIArg->getSpelling() << Triple.str(); 1285 1.1 joerg RWPI = true; 1286 1.1 joerg } 1287 1.1 joerg 1288 1.1 joerg // ROPI and RWPI are not compatible with PIC or PIE. 1289 1.1 joerg if ((ROPI || RWPI) && (PIC || PIE)) 1290 1.1 joerg ToolChain.getDriver().Diag(diag::err_drv_ropi_rwpi_incompatible_with_pic); 1291 1.1 joerg 1292 1.1 joerg if (Triple.isMIPS()) { 1293 1.1 joerg StringRef CPUName; 1294 1.1 joerg StringRef ABIName; 1295 1.1 joerg mips::getMipsCPUAndABI(Args, Triple, CPUName, ABIName); 1296 1.1 joerg // When targeting the N64 ABI, PIC is the default, except in the case 1297 1.1 joerg // when the -mno-abicalls option is used. In that case we exit 1298 1.1 joerg // at next check regardless of PIC being set below. 1299 1.1 joerg if (ABIName == "n64") 1300 1.1 joerg PIC = true; 1301 1.1 joerg // When targettng MIPS with -mno-abicalls, it's always static. 1302 1.1 joerg if(Args.hasArg(options::OPT_mno_abicalls)) 1303 1.1 joerg return std::make_tuple(llvm::Reloc::Static, 0U, false); 1304 1.1 joerg // Unlike other architectures, MIPS, even with -fPIC/-mxgot/multigot, 1305 1.1 joerg // does not use PIC level 2 for historical reasons. 1306 1.1 joerg IsPICLevelTwo = false; 1307 1.1 joerg } 1308 1.1 joerg 1309 1.1 joerg if (PIC) 1310 1.1 joerg return std::make_tuple(llvm::Reloc::PIC_, IsPICLevelTwo ? 2U : 1U, PIE); 1311 1.1 joerg 1312 1.1 joerg llvm::Reloc::Model RelocM = llvm::Reloc::Static; 1313 1.1 joerg if (ROPI && RWPI) 1314 1.1 joerg RelocM = llvm::Reloc::ROPI_RWPI; 1315 1.1 joerg else if (ROPI) 1316 1.1 joerg RelocM = llvm::Reloc::ROPI; 1317 1.1 joerg else if (RWPI) 1318 1.1 joerg RelocM = llvm::Reloc::RWPI; 1319 1.1 joerg 1320 1.1 joerg return std::make_tuple(RelocM, 0U, false); 1321 1.1 joerg } 1322 1.1 joerg 1323 1.1 joerg // `-falign-functions` indicates that the functions should be aligned to a 1324 1.1 joerg // 16-byte boundary. 1325 1.1 joerg // 1326 1.1 joerg // `-falign-functions=1` is the same as `-fno-align-functions`. 1327 1.1 joerg // 1328 1.1 joerg // The scalar `n` in `-falign-functions=n` must be an integral value between 1329 1.1 joerg // [0, 65536]. If the value is not a power-of-two, it will be rounded up to 1330 1.1 joerg // the nearest power-of-two. 1331 1.1 joerg // 1332 1.1 joerg // If we return `0`, the frontend will default to the backend's preferred 1333 1.1 joerg // alignment. 1334 1.1 joerg // 1335 1.1 joerg // NOTE: icc only allows values between [0, 4096]. icc uses `-falign-functions` 1336 1.1 joerg // to mean `-falign-functions=16`. GCC defaults to the backend's preferred 1337 1.1 joerg // alignment. For unaligned functions, we default to the backend's preferred 1338 1.1 joerg // alignment. 1339 1.1 joerg unsigned tools::ParseFunctionAlignment(const ToolChain &TC, 1340 1.1 joerg const ArgList &Args) { 1341 1.1 joerg const Arg *A = Args.getLastArg(options::OPT_falign_functions, 1342 1.1 joerg options::OPT_falign_functions_EQ, 1343 1.1 joerg options::OPT_fno_align_functions); 1344 1.1 joerg if (!A || A->getOption().matches(options::OPT_fno_align_functions)) 1345 1.1 joerg return 0; 1346 1.1 joerg 1347 1.1 joerg if (A->getOption().matches(options::OPT_falign_functions)) 1348 1.1 joerg return 0; 1349 1.1 joerg 1350 1.1 joerg unsigned Value = 0; 1351 1.1 joerg if (StringRef(A->getValue()).getAsInteger(10, Value) || Value > 65536) 1352 1.1 joerg TC.getDriver().Diag(diag::err_drv_invalid_int_value) 1353 1.1 joerg << A->getAsString(Args) << A->getValue(); 1354 1.1 joerg return Value ? llvm::Log2_32_Ceil(std::min(Value, 65536u)) : Value; 1355 1.1 joerg } 1356 1.1 joerg 1357 1.1.1.2 joerg unsigned tools::ParseDebugDefaultVersion(const ToolChain &TC, 1358 1.1.1.2 joerg const ArgList &Args) { 1359 1.1.1.2 joerg const Arg *A = Args.getLastArg(options::OPT_fdebug_default_version); 1360 1.1.1.2 joerg 1361 1.1.1.2 joerg if (!A) 1362 1.1.1.2 joerg return 0; 1363 1.1.1.2 joerg 1364 1.1.1.2 joerg unsigned Value = 0; 1365 1.1.1.2 joerg if (StringRef(A->getValue()).getAsInteger(10, Value) || Value > 5 || 1366 1.1.1.2 joerg Value < 2) 1367 1.1.1.2 joerg TC.getDriver().Diag(diag::err_drv_invalid_int_value) 1368 1.1.1.2 joerg << A->getAsString(Args) << A->getValue(); 1369 1.1.1.2 joerg return Value; 1370 1.1.1.2 joerg } 1371 1.1.1.2 joerg 1372 1.1 joerg void tools::AddAssemblerKPIC(const ToolChain &ToolChain, const ArgList &Args, 1373 1.1 joerg ArgStringList &CmdArgs) { 1374 1.1 joerg llvm::Reloc::Model RelocationModel; 1375 1.1 joerg unsigned PICLevel; 1376 1.1 joerg bool IsPIE; 1377 1.1 joerg std::tie(RelocationModel, PICLevel, IsPIE) = ParsePICArgs(ToolChain, Args); 1378 1.1 joerg 1379 1.1 joerg if (RelocationModel != llvm::Reloc::Static) 1380 1.1 joerg CmdArgs.push_back("-KPIC"); 1381 1.1 joerg } 1382 1.1 joerg 1383 1.1 joerg /// Determine whether Objective-C automated reference counting is 1384 1.1 joerg /// enabled. 1385 1.1 joerg bool tools::isObjCAutoRefCount(const ArgList &Args) { 1386 1.1 joerg return Args.hasFlag(options::OPT_fobjc_arc, options::OPT_fno_objc_arc, false); 1387 1.1 joerg } 1388 1.1 joerg 1389 1.1 joerg enum class LibGccType { UnspecifiedLibGcc, StaticLibGcc, SharedLibGcc }; 1390 1.1 joerg 1391 1.1.1.2 joerg static LibGccType getLibGccType(const ToolChain &TC, const Driver &D, 1392 1.1.1.2 joerg const ArgList &Args) { 1393 1.1 joerg if (Args.hasArg(options::OPT_static_libgcc) || 1394 1.1 joerg Args.hasArg(options::OPT_static) || Args.hasArg(options::OPT_static_pie)) 1395 1.1 joerg return LibGccType::StaticLibGcc; 1396 1.1.1.2 joerg if (Args.hasArg(options::OPT_shared_libgcc)) 1397 1.1.1.2 joerg return LibGccType::SharedLibGcc; 1398 1.1.1.2 joerg // The Android NDK only provides libunwind.a, not libunwind.so. 1399 1.1.1.2 joerg if (TC.getTriple().isAndroid()) 1400 1.1.1.2 joerg return LibGccType::StaticLibGcc; 1401 1.1.1.2 joerg // For MinGW, don't imply a shared libgcc here, we only want to return 1402 1.1.1.2 joerg // SharedLibGcc if that was explicitly requested. 1403 1.1.1.2 joerg if (D.CCCIsCXX() && !TC.getTriple().isOSCygMing()) 1404 1.1 joerg return LibGccType::SharedLibGcc; 1405 1.1 joerg return LibGccType::UnspecifiedLibGcc; 1406 1.1 joerg } 1407 1.1 joerg 1408 1.1 joerg // Gcc adds libgcc arguments in various ways: 1409 1.1 joerg // 1410 1.1 joerg // gcc <none>: -lgcc --as-needed -lgcc_s --no-as-needed 1411 1.1 joerg // g++ <none>: -lgcc_s -lgcc 1412 1.1 joerg // gcc shared: -lgcc_s -lgcc 1413 1.1 joerg // g++ shared: -lgcc_s -lgcc 1414 1.1 joerg // gcc static: -lgcc -lgcc_eh 1415 1.1 joerg // g++ static: -lgcc -lgcc_eh 1416 1.1 joerg // gcc static-pie: -lgcc -lgcc_eh 1417 1.1 joerg // g++ static-pie: -lgcc -lgcc_eh 1418 1.1 joerg // 1419 1.1 joerg // Also, certain targets need additional adjustments. 1420 1.1 joerg 1421 1.1 joerg static void AddUnwindLibrary(const ToolChain &TC, const Driver &D, 1422 1.1 joerg ArgStringList &CmdArgs, const ArgList &Args) { 1423 1.1 joerg ToolChain::UnwindLibType UNW = TC.GetUnwindLibType(Args); 1424 1.1 joerg // Targets that don't use unwind libraries. 1425 1.1.1.2 joerg if ((TC.getTriple().isAndroid() && UNW == ToolChain::UNW_Libgcc) || 1426 1.1.1.2 joerg TC.getTriple().isOSIAMCU() || TC.getTriple().isOSBinFormatWasm() || 1427 1.1 joerg UNW == ToolChain::UNW_None) 1428 1.1 joerg return; 1429 1.1 joerg 1430 1.1.1.2 joerg LibGccType LGT = getLibGccType(TC, D, Args); 1431 1.1 joerg bool AsNeeded = LGT == LibGccType::UnspecifiedLibGcc && 1432 1.1 joerg !TC.getTriple().isAndroid() && !TC.getTriple().isOSCygMing(); 1433 1.1 joerg if (AsNeeded) 1434 1.1.1.2 joerg CmdArgs.push_back(getAsNeededOption(TC, true)); 1435 1.1 joerg 1436 1.1 joerg switch (UNW) { 1437 1.1 joerg case ToolChain::UNW_None: 1438 1.1 joerg return; 1439 1.1 joerg case ToolChain::UNW_Libgcc: { 1440 1.1 joerg if (LGT == LibGccType::StaticLibGcc) 1441 1.1 joerg CmdArgs.push_back("-lgcc_eh"); 1442 1.1 joerg else 1443 1.1 joerg CmdArgs.push_back("-lgcc_s"); 1444 1.1 joerg break; 1445 1.1 joerg } 1446 1.1 joerg case ToolChain::UNW_CompilerRT: 1447 1.1.1.2 joerg if (LGT == LibGccType::StaticLibGcc) 1448 1.1.1.2 joerg CmdArgs.push_back("-l:libunwind.a"); 1449 1.1.1.2 joerg else if (TC.getTriple().isOSCygMing()) { 1450 1.1.1.2 joerg if (LGT == LibGccType::SharedLibGcc) 1451 1.1.1.2 joerg CmdArgs.push_back("-l:libunwind.dll.a"); 1452 1.1.1.2 joerg else 1453 1.1.1.2 joerg // Let the linker choose between libunwind.dll.a and libunwind.a 1454 1.1.1.2 joerg // depending on what's available, and depending on the -static flag 1455 1.1.1.2 joerg CmdArgs.push_back("-lunwind"); 1456 1.1.1.2 joerg } else 1457 1.1.1.2 joerg CmdArgs.push_back("-l:libunwind.so"); 1458 1.1 joerg break; 1459 1.1 joerg } 1460 1.1 joerg 1461 1.1 joerg if (AsNeeded) 1462 1.1.1.2 joerg CmdArgs.push_back(getAsNeededOption(TC, false)); 1463 1.1 joerg } 1464 1.1 joerg 1465 1.1 joerg static void AddLibgcc(const ToolChain &TC, const Driver &D, 1466 1.1 joerg ArgStringList &CmdArgs, const ArgList &Args) { 1467 1.1.1.2 joerg LibGccType LGT = getLibGccType(TC, D, Args); 1468 1.1 joerg if (LGT != LibGccType::SharedLibGcc) 1469 1.1 joerg CmdArgs.push_back("-lgcc"); 1470 1.1 joerg AddUnwindLibrary(TC, D, CmdArgs, Args); 1471 1.1 joerg if (LGT == LibGccType::SharedLibGcc) 1472 1.1 joerg CmdArgs.push_back("-lgcc"); 1473 1.1 joerg } 1474 1.1 joerg 1475 1.1 joerg void tools::AddRunTimeLibs(const ToolChain &TC, const Driver &D, 1476 1.1 joerg ArgStringList &CmdArgs, const ArgList &Args) { 1477 1.1 joerg // Make use of compiler-rt if --rtlib option is used 1478 1.1 joerg ToolChain::RuntimeLibType RLT = TC.GetRuntimeLibType(Args); 1479 1.1 joerg 1480 1.1 joerg switch (RLT) { 1481 1.1 joerg case ToolChain::RLT_CompilerRT: 1482 1.1 joerg CmdArgs.push_back(TC.getCompilerRTArgString(Args, "builtins")); 1483 1.1 joerg AddUnwindLibrary(TC, D, CmdArgs, Args); 1484 1.1 joerg break; 1485 1.1 joerg case ToolChain::RLT_Libgcc: 1486 1.1 joerg // Make sure libgcc is not used under MSVC environment by default 1487 1.1 joerg if (TC.getTriple().isKnownWindowsMSVCEnvironment()) { 1488 1.1 joerg // Issue error diagnostic if libgcc is explicitly specified 1489 1.1 joerg // through command line as --rtlib option argument. 1490 1.1 joerg if (Args.hasArg(options::OPT_rtlib_EQ)) { 1491 1.1 joerg TC.getDriver().Diag(diag::err_drv_unsupported_rtlib_for_platform) 1492 1.1 joerg << Args.getLastArg(options::OPT_rtlib_EQ)->getValue() << "MSVC"; 1493 1.1 joerg } 1494 1.1 joerg } else 1495 1.1 joerg AddLibgcc(TC, D, CmdArgs, Args); 1496 1.1 joerg break; 1497 1.1 joerg } 1498 1.1 joerg 1499 1.1.1.2 joerg // On Android, the unwinder uses dl_iterate_phdr (or one of 1500 1.1.1.2 joerg // dl_unwind_find_exidx/__gnu_Unwind_Find_exidx on arm32) from libdl.so. For 1501 1.1.1.2 joerg // statically-linked executables, these functions come from libc.a instead. 1502 1.1.1.2 joerg if (TC.getTriple().isAndroid() && !Args.hasArg(options::OPT_static) && 1503 1.1.1.2 joerg !Args.hasArg(options::OPT_static_pie)) 1504 1.1.1.2 joerg CmdArgs.push_back("-ldl"); 1505 1.1 joerg } 1506 1.1 joerg 1507 1.1 joerg SmallString<128> tools::getStatsFileName(const llvm::opt::ArgList &Args, 1508 1.1 joerg const InputInfo &Output, 1509 1.1 joerg const InputInfo &Input, 1510 1.1 joerg const Driver &D) { 1511 1.1 joerg const Arg *A = Args.getLastArg(options::OPT_save_stats_EQ); 1512 1.1 joerg if (!A) 1513 1.1 joerg return {}; 1514 1.1 joerg 1515 1.1 joerg StringRef SaveStats = A->getValue(); 1516 1.1 joerg SmallString<128> StatsFile; 1517 1.1 joerg if (SaveStats == "obj" && Output.isFilename()) { 1518 1.1 joerg StatsFile.assign(Output.getFilename()); 1519 1.1 joerg llvm::sys::path::remove_filename(StatsFile); 1520 1.1 joerg } else if (SaveStats != "cwd") { 1521 1.1 joerg D.Diag(diag::err_drv_invalid_value) << A->getAsString(Args) << SaveStats; 1522 1.1 joerg return {}; 1523 1.1 joerg } 1524 1.1 joerg 1525 1.1 joerg StringRef BaseName = llvm::sys::path::filename(Input.getBaseInput()); 1526 1.1 joerg llvm::sys::path::append(StatsFile, BaseName); 1527 1.1 joerg llvm::sys::path::replace_extension(StatsFile, "stats"); 1528 1.1 joerg return StatsFile; 1529 1.1 joerg } 1530 1.1 joerg 1531 1.1 joerg void tools::addMultilibFlag(bool Enabled, const char *const Flag, 1532 1.1 joerg Multilib::flags_list &Flags) { 1533 1.1 joerg Flags.push_back(std::string(Enabled ? "+" : "-") + Flag); 1534 1.1 joerg } 1535 1.1 joerg 1536 1.1.1.2 joerg void tools::addX86AlignBranchArgs(const Driver &D, const ArgList &Args, 1537 1.1.1.2 joerg ArgStringList &CmdArgs, bool IsLTO) { 1538 1.1.1.2 joerg auto addArg = [&, IsLTO](const Twine &Arg) { 1539 1.1.1.2 joerg if (IsLTO) { 1540 1.1.1.2 joerg CmdArgs.push_back(Args.MakeArgString("-plugin-opt=" + Arg)); 1541 1.1.1.2 joerg } else { 1542 1.1.1.2 joerg CmdArgs.push_back("-mllvm"); 1543 1.1.1.2 joerg CmdArgs.push_back(Args.MakeArgString(Arg)); 1544 1.1.1.2 joerg } 1545 1.1.1.2 joerg }; 1546 1.1 joerg 1547 1.1.1.2 joerg if (Args.hasArg(options::OPT_mbranches_within_32B_boundaries)) { 1548 1.1.1.2 joerg addArg(Twine("-x86-branches-within-32B-boundaries")); 1549 1.1.1.2 joerg } 1550 1.1.1.2 joerg if (const Arg *A = Args.getLastArg(options::OPT_malign_branch_boundary_EQ)) { 1551 1.1.1.2 joerg StringRef Value = A->getValue(); 1552 1.1.1.2 joerg unsigned Boundary; 1553 1.1.1.2 joerg if (Value.getAsInteger(10, Boundary) || Boundary < 16 || 1554 1.1.1.2 joerg !llvm::isPowerOf2_64(Boundary)) { 1555 1.1.1.2 joerg D.Diag(diag::err_drv_invalid_argument_to_option) 1556 1.1.1.2 joerg << Value << A->getOption().getName(); 1557 1.1.1.2 joerg } else { 1558 1.1.1.2 joerg addArg("-x86-align-branch-boundary=" + Twine(Boundary)); 1559 1.1.1.2 joerg } 1560 1.1.1.2 joerg } 1561 1.1.1.2 joerg if (const Arg *A = Args.getLastArg(options::OPT_malign_branch_EQ)) { 1562 1.1.1.2 joerg std::string AlignBranch; 1563 1.1.1.2 joerg for (StringRef T : A->getValues()) { 1564 1.1.1.2 joerg if (T != "fused" && T != "jcc" && T != "jmp" && T != "call" && 1565 1.1.1.2 joerg T != "ret" && T != "indirect") 1566 1.1.1.2 joerg D.Diag(diag::err_drv_invalid_malign_branch_EQ) 1567 1.1.1.2 joerg << T << "fused, jcc, jmp, call, ret, indirect"; 1568 1.1.1.2 joerg if (!AlignBranch.empty()) 1569 1.1.1.2 joerg AlignBranch += '+'; 1570 1.1.1.2 joerg AlignBranch += T; 1571 1.1.1.2 joerg } 1572 1.1.1.2 joerg addArg("-x86-align-branch=" + Twine(AlignBranch)); 1573 1.1.1.2 joerg } 1574 1.1.1.2 joerg if (const Arg *A = Args.getLastArg(options::OPT_mpad_max_prefix_size_EQ)) { 1575 1.1.1.2 joerg StringRef Value = A->getValue(); 1576 1.1.1.2 joerg unsigned PrefixSize; 1577 1.1.1.2 joerg if (Value.getAsInteger(10, PrefixSize)) { 1578 1.1.1.2 joerg D.Diag(diag::err_drv_invalid_argument_to_option) 1579 1.1.1.2 joerg << Value << A->getOption().getName(); 1580 1.1.1.2 joerg } else { 1581 1.1.1.2 joerg addArg("-x86-pad-max-prefix-size=" + Twine(PrefixSize)); 1582 1.1.1.2 joerg } 1583 1.1.1.2 joerg } 1584 1.1.1.2 joerg } 1585 1.1 joerg 1586 1.1.1.2 joerg static llvm::opt::Arg * 1587 1.1.1.2 joerg getAMDGPUCodeObjectArgument(const Driver &D, const llvm::opt::ArgList &Args) { 1588 1.1.1.2 joerg // The last of -mcode-object-v3, -mno-code-object-v3 and 1589 1.1.1.2 joerg // -mcode-object-version=<version> wins. 1590 1.1.1.2 joerg return Args.getLastArg(options::OPT_mcode_object_v3_legacy, 1591 1.1.1.2 joerg options::OPT_mno_code_object_v3_legacy, 1592 1.1.1.2 joerg options::OPT_mcode_object_version_EQ); 1593 1.1.1.2 joerg } 1594 1.1.1.2 joerg 1595 1.1.1.2 joerg void tools::checkAMDGPUCodeObjectVersion(const Driver &D, 1596 1.1.1.2 joerg const llvm::opt::ArgList &Args) { 1597 1.1.1.2 joerg const unsigned MinCodeObjVer = 2; 1598 1.1.1.2 joerg const unsigned MaxCodeObjVer = 4; 1599 1.1.1.2 joerg 1600 1.1.1.2 joerg // Emit warnings for legacy options even if they are overridden. 1601 1.1.1.2 joerg if (Args.hasArg(options::OPT_mno_code_object_v3_legacy)) 1602 1.1.1.2 joerg D.Diag(diag::warn_drv_deprecated_arg) << "-mno-code-object-v3" 1603 1.1.1.2 joerg << "-mcode-object-version=2"; 1604 1.1.1.2 joerg 1605 1.1.1.2 joerg if (Args.hasArg(options::OPT_mcode_object_v3_legacy)) 1606 1.1.1.2 joerg D.Diag(diag::warn_drv_deprecated_arg) << "-mcode-object-v3" 1607 1.1.1.2 joerg << "-mcode-object-version=3"; 1608 1.1.1.2 joerg 1609 1.1.1.2 joerg if (auto *CodeObjArg = getAMDGPUCodeObjectArgument(D, Args)) { 1610 1.1.1.2 joerg if (CodeObjArg->getOption().getID() == 1611 1.1.1.2 joerg options::OPT_mcode_object_version_EQ) { 1612 1.1.1.2 joerg unsigned CodeObjVer = MaxCodeObjVer; 1613 1.1.1.2 joerg auto Remnant = 1614 1.1.1.2 joerg StringRef(CodeObjArg->getValue()).getAsInteger(0, CodeObjVer); 1615 1.1.1.2 joerg if (Remnant || CodeObjVer < MinCodeObjVer || CodeObjVer > MaxCodeObjVer) 1616 1.1.1.2 joerg D.Diag(diag::err_drv_invalid_int_value) 1617 1.1.1.2 joerg << CodeObjArg->getAsString(Args) << CodeObjArg->getValue(); 1618 1.1.1.2 joerg } 1619 1.1 joerg } 1620 1.1.1.2 joerg } 1621 1.1 joerg 1622 1.1.1.2 joerg unsigned tools::getAMDGPUCodeObjectVersion(const Driver &D, 1623 1.1.1.2 joerg const llvm::opt::ArgList &Args) { 1624 1.1.1.2 joerg unsigned CodeObjVer = 4; // default 1625 1.1.1.2 joerg if (auto *CodeObjArg = getAMDGPUCodeObjectArgument(D, Args)) { 1626 1.1.1.2 joerg if (CodeObjArg->getOption().getID() == 1627 1.1.1.2 joerg options::OPT_mno_code_object_v3_legacy) { 1628 1.1.1.2 joerg CodeObjVer = 2; 1629 1.1.1.2 joerg } else if (CodeObjArg->getOption().getID() == 1630 1.1.1.2 joerg options::OPT_mcode_object_v3_legacy) { 1631 1.1.1.2 joerg CodeObjVer = 3; 1632 1.1.1.2 joerg } else { 1633 1.1.1.2 joerg StringRef(CodeObjArg->getValue()).getAsInteger(0, CodeObjVer); 1634 1.1.1.2 joerg } 1635 1.1 joerg } 1636 1.1.1.2 joerg return CodeObjVer; 1637 1.1.1.2 joerg } 1638 1.1 joerg 1639 1.1.1.2 joerg bool tools::haveAMDGPUCodeObjectVersionArgument( 1640 1.1.1.2 joerg const Driver &D, const llvm::opt::ArgList &Args) { 1641 1.1.1.2 joerg return getAMDGPUCodeObjectArgument(D, Args) != nullptr; 1642 1.1.1.2 joerg } 1643 1.1.1.2 joerg 1644 1.1.1.2 joerg void tools::addMachineOutlinerArgs(const Driver &D, 1645 1.1.1.2 joerg const llvm::opt::ArgList &Args, 1646 1.1.1.2 joerg llvm::opt::ArgStringList &CmdArgs, 1647 1.1.1.2 joerg const llvm::Triple &Triple, bool IsLTO) { 1648 1.1.1.2 joerg auto addArg = [&, IsLTO](const Twine &Arg) { 1649 1.1.1.2 joerg if (IsLTO) { 1650 1.1.1.2 joerg CmdArgs.push_back(Args.MakeArgString("-plugin-opt=" + Arg)); 1651 1.1 joerg } else { 1652 1.1.1.2 joerg CmdArgs.push_back("-mllvm"); 1653 1.1.1.2 joerg CmdArgs.push_back(Args.MakeArgString(Arg)); 1654 1.1.1.2 joerg } 1655 1.1.1.2 joerg }; 1656 1.1.1.2 joerg 1657 1.1.1.2 joerg if (Arg *A = Args.getLastArg(options::OPT_moutline, 1658 1.1.1.2 joerg options::OPT_mno_outline)) { 1659 1.1.1.2 joerg if (A->getOption().matches(options::OPT_moutline)) { 1660 1.1.1.2 joerg // We only support -moutline in AArch64 and ARM targets right now. If 1661 1.1.1.2 joerg // we're not compiling for these, emit a warning and ignore the flag. 1662 1.1.1.2 joerg // Otherwise, add the proper mllvm flags. 1663 1.1.1.2 joerg if (!(Triple.isARM() || Triple.isThumb() || 1664 1.1.1.2 joerg Triple.getArch() == llvm::Triple::aarch64 || 1665 1.1.1.2 joerg Triple.getArch() == llvm::Triple::aarch64_32)) { 1666 1.1.1.2 joerg D.Diag(diag::warn_drv_moutline_unsupported_opt) << Triple.getArchName(); 1667 1.1.1.2 joerg } else { 1668 1.1.1.2 joerg addArg(Twine("-enable-machine-outliner")); 1669 1.1.1.2 joerg } 1670 1.1.1.2 joerg } else { 1671 1.1.1.2 joerg // Disable all outlining behaviour. 1672 1.1.1.2 joerg addArg(Twine("-enable-machine-outliner=never")); 1673 1.1 joerg } 1674 1.1 joerg } 1675 1.1 joerg } 1676 1.1 joerg 1677 1.1.1.2 joerg void tools::addOpenMPDeviceRTL(const Driver &D, 1678 1.1.1.2 joerg const llvm::opt::ArgList &DriverArgs, 1679 1.1.1.2 joerg llvm::opt::ArgStringList &CC1Args, 1680 1.1.1.2 joerg StringRef BitcodeSuffix, 1681 1.1.1.2 joerg const llvm::Triple &Triple) { 1682 1.1.1.2 joerg SmallVector<StringRef, 8> LibraryPaths; 1683 1.1.1.2 joerg // Add user defined library paths from LIBRARY_PATH. 1684 1.1.1.2 joerg llvm::Optional<std::string> LibPath = 1685 1.1.1.2 joerg llvm::sys::Process::GetEnv("LIBRARY_PATH"); 1686 1.1.1.2 joerg if (LibPath) { 1687 1.1.1.2 joerg SmallVector<StringRef, 8> Frags; 1688 1.1.1.2 joerg const char EnvPathSeparatorStr[] = {llvm::sys::EnvPathSeparator, '\0'}; 1689 1.1.1.2 joerg llvm::SplitString(*LibPath, Frags, EnvPathSeparatorStr); 1690 1.1.1.2 joerg for (StringRef Path : Frags) 1691 1.1.1.2 joerg LibraryPaths.emplace_back(Path.trim()); 1692 1.1.1.2 joerg } 1693 1.1.1.2 joerg 1694 1.1.1.2 joerg // Add path to lib / lib64 folder. 1695 1.1.1.2 joerg SmallString<256> DefaultLibPath = llvm::sys::path::parent_path(D.Dir); 1696 1.1.1.2 joerg llvm::sys::path::append(DefaultLibPath, Twine("lib") + CLANG_LIBDIR_SUFFIX); 1697 1.1.1.2 joerg LibraryPaths.emplace_back(DefaultLibPath.c_str()); 1698 1.1.1.2 joerg 1699 1.1.1.2 joerg OptSpecifier LibomptargetBCPathOpt = 1700 1.1.1.2 joerg Triple.isAMDGCN() ? options::OPT_libomptarget_amdgcn_bc_path_EQ 1701 1.1.1.2 joerg : options::OPT_libomptarget_nvptx_bc_path_EQ; 1702 1.1.1.2 joerg 1703 1.1.1.2 joerg StringRef ArchPrefix = Triple.isAMDGCN() ? "amdgcn" : "nvptx"; 1704 1.1.1.2 joerg // First check whether user specifies bc library 1705 1.1.1.2 joerg if (const Arg *A = DriverArgs.getLastArg(LibomptargetBCPathOpt)) { 1706 1.1.1.2 joerg std::string LibOmpTargetName(A->getValue()); 1707 1.1.1.2 joerg if (llvm::sys::fs::exists(LibOmpTargetName)) { 1708 1.1.1.2 joerg CC1Args.push_back("-mlink-builtin-bitcode"); 1709 1.1.1.2 joerg CC1Args.push_back(DriverArgs.MakeArgString(LibOmpTargetName)); 1710 1.1.1.2 joerg } else { 1711 1.1.1.2 joerg D.Diag(diag::err_drv_omp_offload_target_bcruntime_not_found) 1712 1.1.1.2 joerg << LibOmpTargetName; 1713 1.1.1.2 joerg } 1714 1.1.1.2 joerg } else { 1715 1.1.1.2 joerg bool FoundBCLibrary = false; 1716 1.1.1.2 joerg 1717 1.1.1.2 joerg std::string LibOmpTargetName = 1718 1.1.1.2 joerg "libomptarget-" + BitcodeSuffix.str() + ".bc"; 1719 1.1.1.2 joerg 1720 1.1.1.2 joerg for (StringRef LibraryPath : LibraryPaths) { 1721 1.1.1.2 joerg SmallString<128> LibOmpTargetFile(LibraryPath); 1722 1.1.1.2 joerg llvm::sys::path::append(LibOmpTargetFile, LibOmpTargetName); 1723 1.1.1.2 joerg if (llvm::sys::fs::exists(LibOmpTargetFile)) { 1724 1.1.1.2 joerg CC1Args.push_back("-mlink-builtin-bitcode"); 1725 1.1.1.2 joerg CC1Args.push_back(DriverArgs.MakeArgString(LibOmpTargetFile)); 1726 1.1.1.2 joerg FoundBCLibrary = true; 1727 1.1.1.2 joerg break; 1728 1.1.1.2 joerg } 1729 1.1.1.2 joerg } 1730 1.1.1.2 joerg 1731 1.1.1.2 joerg if (!FoundBCLibrary) 1732 1.1.1.2 joerg D.Diag(diag::err_drv_omp_offload_target_missingbcruntime) 1733 1.1.1.2 joerg << LibOmpTargetName << ArchPrefix; 1734 1.1 joerg } 1735 1.1 joerg } 1736