Coverage Report

Created: 2021-01-23 06:44

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