28#include "clang/Config/config.h"
44#include "llvm/ADT/APInt.h"
45#include "llvm/ADT/ArrayRef.h"
46#include "llvm/ADT/CachedHashString.h"
47#include "llvm/ADT/FloatingPointMode.h"
48#include "llvm/ADT/STLExtras.h"
49#include "llvm/ADT/SmallVector.h"
50#include "llvm/ADT/StringRef.h"
51#include "llvm/ADT/StringSwitch.h"
52#include "llvm/ADT/Twine.h"
53#include "llvm/Config/llvm-config.h"
54#include "llvm/Frontend/Debug/Options.h"
55#include "llvm/IR/DebugInfoMetadata.h"
56#include "llvm/Linker/Linker.h"
57#include "llvm/MC/MCTargetOptions.h"
58#include "llvm/Option/Arg.h"
59#include "llvm/Option/ArgList.h"
60#include "llvm/Option/OptSpecifier.h"
61#include "llvm/Option/OptTable.h"
62#include "llvm/Option/Option.h"
63#include "llvm/ProfileData/InstrProfReader.h"
64#include "llvm/Remarks/HotnessThresholdParser.h"
65#include "llvm/Support/CodeGen.h"
66#include "llvm/Support/Compiler.h"
67#include "llvm/Support/Error.h"
68#include "llvm/Support/ErrorHandling.h"
69#include "llvm/Support/ErrorOr.h"
70#include "llvm/Support/FileSystem.h"
71#include "llvm/Support/HashBuilder.h"
72#include "llvm/Support/MathExtras.h"
73#include "llvm/Support/MemoryBuffer.h"
74#include "llvm/Support/Path.h"
75#include "llvm/Support/Process.h"
76#include "llvm/Support/Regex.h"
77#include "llvm/Support/VersionTuple.h"
78#include "llvm/Support/VirtualFileSystem.h"
79#include "llvm/Support/raw_ostream.h"
80#include "llvm/Target/TargetOptions.h"
81#include "llvm/TargetParser/Host.h"
82#include "llvm/TargetParser/Triple.h"
99using namespace driver;
100using namespace options;
111 if (Arg.getAsInteger(10, Val))
112 return llvm::createStringError(llvm::inconvertibleErrorCode(),
113 "Not an integer: %s", Arg.data());
122 return std::make_shared<T>(
X);
193 if (Storage.use_count() > 1)
194 Storage = std::make_shared<T>(*Storage);
257#define OPTTABLE_STR_TABLE_CODE
258#include "clang/Driver/Options.inc"
259#undef OPTTABLE_STR_TABLE_CODE
262 return OptionStrTable[Offset];
265#define SIMPLE_ENUM_VALUE_TABLE
266#include "clang/Driver/Options.inc"
267#undef SIMPLE_ENUM_VALUE_TABLE
273 if (Args.hasArg(Opt))
282 if (Args.hasArg(Opt))
292 unsigned SpellingOffset, Option::OptionClass,
297 const Twine &Spelling, Option::OptionClass,
303 return !std::is_same_v<T, uint64_t> && llvm::is_integral_or_enum<T>::value;
307 std::enable_if_t<!is_uint64_t_convertible<T>(),
bool> =
false>
309 return [
Value](OptSpecifier Opt,
unsigned,
const ArgList &Args,
311 if (Args.hasArg(Opt))
318 std::enable_if_t<is_uint64_t_convertible<T>(),
bool> =
false>
324 OptSpecifier OtherOpt) {
325 return [
Value, OtherValue,
326 OtherOpt](OptSpecifier Opt,
unsigned,
const ArgList &Args,
328 if (
const Arg *A = Args.getLastArg(Opt, OtherOpt)) {
329 return A->getOption().matches(Opt) ?
Value : OtherValue;
337 Option::OptionClass,
unsigned,
bool KeyPath) {
338 if (KeyPath ==
Value)
344 const Twine &Spelling,
345 Option::OptionClass OptClass,
unsigned,
346 const Twine &
Value) {
348 case Option::SeparateClass:
349 case Option::JoinedOrSeparateClass:
350 case Option::JoinedAndSeparateClass:
354 case Option::JoinedClass:
355 case Option::CommaJoinedClass:
356 Consumer(Spelling +
Value);
359 llvm_unreachable(
"Cannot denormalize an option with option class "
360 "incompatible with string denormalization.");
367 Option::OptionClass OptClass,
unsigned TableIndex,
T Value) {
369 TableIndex, Twine(
Value));
374 Option::OptionClass OptClass,
unsigned TableIndex,
379static std::optional<SimpleEnumValue>
381 for (
int I = 0,
E = Table.Size; I !=
E; ++I)
382 if (Name == Table.Table[I].Name)
383 return Table.Table[I];
388static std::optional<SimpleEnumValue>
390 for (
int I = 0,
E = Table.Size; I !=
E; ++I)
392 return Table.Table[I];
401 assert(TableIndex < SimpleEnumValueTablesSize);
402 const SimpleEnumValueTable &Table = SimpleEnumValueTables[TableIndex];
404 auto *Arg = Args.getLastArg(Opt);
408 StringRef ArgValue = Arg->getValue();
410 return MaybeEnumVal->Value;
412 Diags.
Report(diag::err_drv_invalid_value)
413 << Arg->getAsString(Args) << ArgValue;
418 unsigned SpellingOffset,
419 Option::OptionClass OptClass,
420 unsigned TableIndex,
unsigned Value) {
421 assert(TableIndex < SimpleEnumValueTablesSize);
422 const SimpleEnumValueTable &Table = SimpleEnumValueTables[TableIndex];
425 TableIndex, MaybeEnumVal->Name);
427 llvm_unreachable(
"The simple enum value was not correctly defined in "
428 "the tablegen option description");
434 unsigned SpellingOffset,
435 Option::OptionClass OptClass,
436 unsigned TableIndex,
T Value) {
438 TableIndex,
static_cast<unsigned>(
Value));
445 auto *Arg = Args.getLastArg(Opt);
448 return std::string(Arg->getValue());
451template <
typename IntTy>
455 auto *Arg = Args.getLastArg(Opt);
459 if (StringRef(Arg->getValue()).getAsInteger(0, Res)) {
460 Diags.
Report(diag::err_drv_invalid_int_value)
461 << Arg->getAsString(Args) << Arg->getValue();
467static std::optional<std::vector<std::string>>
470 return Args.getAllArgValues(Opt);
474 unsigned SpellingOffset,
475 Option::OptionClass OptClass,
477 const std::vector<std::string> &Values) {
479 case Option::CommaJoinedClass: {
480 std::string CommaJoinedValue;
481 if (!Values.empty()) {
482 CommaJoinedValue.append(Values.front());
483 for (
const std::string &
Value : llvm::drop_begin(Values, 1)) {
484 CommaJoinedValue.append(
",");
485 CommaJoinedValue.append(
Value);
489 Option::OptionClass::JoinedClass, TableIndex,
493 case Option::JoinedClass:
494 case Option::SeparateClass:
495 case Option::JoinedOrSeparateClass:
496 for (
const std::string &
Value : Values)
500 llvm_unreachable(
"Cannot denormalize an option with option class "
501 "incompatible with string vector denormalization.");
509 auto *Arg = Args.getLastArg(Opt);
512 return llvm::Triple::normalize(Arg->getValue());
515template <
typename T,
typename U>
517 return static_cast<T>(
Value);
521 return KeyPath |
Value;
528template <
typename T,
typename U, U Value>
533#define PARSE_OPTION_WITH_MARSHALLING( \
534 ARGS, DIAGS, PREFIX_TYPE, SPELLING_OFFSET, ID, KIND, GROUP, ALIAS, \
535 ALIASARGS, FLAGS, VISIBILITY, PARAM, HELPTEXT, HELPTEXTSFORVARIANTS, \
536 METAVAR, VALUES, SHOULD_PARSE, ALWAYS_EMIT, KEYPATH, DEFAULT_VALUE, \
537 IMPLIED_CHECK, IMPLIED_VALUE, NORMALIZER, DENORMALIZER, MERGER, EXTRACTOR, \
539 if ((VISIBILITY) & options::CC1Option) { \
540 KEYPATH = MERGER(KEYPATH, DEFAULT_VALUE); \
542 KEYPATH = MERGER(KEYPATH, IMPLIED_VALUE); \
544 if (auto MaybeValue = NORMALIZER(OPT_##ID, TABLE_INDEX, ARGS, DIAGS)) \
546 MERGER(KEYPATH, static_cast<decltype(KEYPATH)>(*MaybeValue)); \
551#define GENERATE_OPTION_WITH_MARSHALLING( \
552 CONSUMER, PREFIX_TYPE, SPELLING_OFFSET, ID, KIND, GROUP, ALIAS, ALIASARGS, \
553 FLAGS, VISIBILITY, PARAM, HELPTEXT, HELPTEXTSFORVARIANTS, METAVAR, VALUES, \
554 SHOULD_PARSE, ALWAYS_EMIT, KEYPATH, DEFAULT_VALUE, IMPLIED_CHECK, \
555 IMPLIED_VALUE, NORMALIZER, DENORMALIZER, MERGER, EXTRACTOR, TABLE_INDEX) \
556 if ((VISIBILITY) & options::CC1Option) { \
557 [&](const auto &Extracted) { \
560 static_cast<decltype(KEYPATH)>((IMPLIED_CHECK) ? (IMPLIED_VALUE) \
561 : (DEFAULT_VALUE)))) \
562 DENORMALIZER(CONSUMER, SPELLING_OFFSET, Option::KIND##Class, \
563 TABLE_INDEX, Extracted); \
564 }(EXTRACTOR(KEYPATH)); \
578 CodeGenOpts.XRayInstrumentFunctions = LangOpts.XRayInstrument;
579 CodeGenOpts.XRayAlwaysEmitCustomEvents = LangOpts.XRayAlwaysEmitCustomEvents;
580 CodeGenOpts.XRayAlwaysEmitTypedEvents = LangOpts.XRayAlwaysEmitTypedEvents;
581 CodeGenOpts.DisableFree = FrontendOpts.
DisableFree;
584 CodeGenOpts.ClearASTBeforeBackend =
false;
586 LangOpts.ForceEmitVTables = CodeGenOpts.ForceEmitVTables;
587 LangOpts.SpeculativeLoadHardening = CodeGenOpts.SpeculativeLoadHardening;
590 llvm::Triple
T(TargetOpts.
Triple);
591 llvm::Triple::ArchType
Arch =
T.getArch();
596 if (CodeGenOpts.getExceptionHandling() !=
598 T.isWindowsMSVCEnvironment())
599 Diags.
Report(diag::err_fe_invalid_exception_model)
600 <<
static_cast<unsigned>(CodeGenOpts.getExceptionHandling()) <<
T.str();
602 if (LangOpts.AppleKext && !LangOpts.CPlusPlus)
603 Diags.
Report(diag::warn_c_kext);
605 if (LangOpts.NewAlignOverride &&
606 !llvm::isPowerOf2_32(LangOpts.NewAlignOverride)) {
607 Arg *A = Args.getLastArg(OPT_fnew_alignment_EQ);
608 Diags.
Report(diag::err_fe_invalid_alignment)
609 << A->getAsString(Args) << A->getValue();
610 LangOpts.NewAlignOverride = 0;
615 if (LangOpts.CPlusPlus11) {
616 if (Args.hasArg(OPT_fraw_string_literals, OPT_fno_raw_string_literals)) {
617 Args.claimAllArgs(OPT_fraw_string_literals, OPT_fno_raw_string_literals);
618 Diags.
Report(diag::warn_drv_fraw_string_literals_in_cxx11)
619 <<
bool(LangOpts.RawStringLiterals);
623 LangOpts.RawStringLiterals =
true;
626 LangOpts.NamedLoops =
627 Args.hasFlag(OPT_fnamed_loops, OPT_fno_named_loops, LangOpts.C2y);
630 if (LangOpts.SYCLIsDevice && LangOpts.SYCLIsHost)
631 Diags.
Report(diag::err_drv_argument_not_allowed_with) <<
"-fsycl-is-device"
634 if (Args.hasArg(OPT_fgnu89_inline) && LangOpts.CPlusPlus)
635 Diags.
Report(diag::err_drv_argument_not_allowed_with)
638 if (Args.hasArg(OPT_hlsl_entrypoint) && !LangOpts.HLSL)
639 Diags.
Report(diag::err_drv_argument_not_allowed_with)
642 if (Args.hasArg(OPT_fdx_rootsignature_version) && !LangOpts.HLSL)
643 Diags.
Report(diag::err_drv_argument_not_allowed_with)
646 if (Args.hasArg(OPT_fdx_rootsignature_define) && !LangOpts.HLSL)
647 Diags.
Report(diag::err_drv_argument_not_allowed_with)
650 if (Args.hasArg(OPT_fgpu_allow_device_init) && !LangOpts.HIP)
651 Diags.
Report(diag::warn_ignored_hip_only_option)
652 << Args.getLastArg(OPT_fgpu_allow_device_init)->getAsString(Args);
654 if (Args.hasArg(OPT_gpu_max_threads_per_block_EQ) && !LangOpts.HIP)
655 Diags.
Report(diag::warn_ignored_hip_only_option)
656 << Args.getLastArg(OPT_gpu_max_threads_per_block_EQ)->getAsString(Args);
665 if (Args.hasArg(OPT_ffp_eval_method_EQ)) {
666 if (LangOpts.ApproxFunc)
667 Diags.
Report(diag::err_incompatible_fp_eval_method_options) << 0;
668 if (LangOpts.AllowFPReassoc)
669 Diags.
Report(diag::err_incompatible_fp_eval_method_options) << 1;
670 if (LangOpts.AllowRecip)
671 Diags.
Report(diag::err_incompatible_fp_eval_method_options) << 2;
677 if (Args.getLastArg(OPT_cl_strict_aliasing) &&
679 Diags.
Report(diag::warn_option_invalid_ocl_version)
681 << Args.getLastArg(OPT_cl_strict_aliasing)->getAsString(Args);
683 if (Arg *A = Args.getLastArg(OPT_fdefault_calling_conv_EQ)) {
684 auto DefaultCC = LangOpts.getDefaultCallingConv();
688 Arch != llvm::Triple::x86;
694 Diags.
Report(diag::err_drv_argument_not_allowed_with)
695 << A->getSpelling() <<
T.getTriple();
707 unsigned DefaultOpt = 0;
710 !Args.hasArg(OPT_cl_opt_disable))
713 if (Arg *A = Args.getLastArg(options::OPT_O_Group)) {
714 if (A->getOption().matches(options::OPT_O0))
717 if (A->getOption().matches(options::OPT_Ofast))
720 assert(A->getOption().matches(options::OPT_O));
722 StringRef S(A->getValue());
723 if (S ==
"s" || S ==
"z")
736 if (Arg *A = Args.getLastArg(options::OPT_O_Group)) {
737 if (A->getOption().matches(options::OPT_O)) {
738 switch (A->getValue()[0]) {
752 llvm::opt::OptSpecifier OptSpecifier) {
755 Option::OptionClass::FlagClass, 0);
759 llvm::opt::OptSpecifier OptSpecifier,
760 const Twine &
Value) {
798 bool CheckAgainstOriginalInvocation =
false,
799 bool ForceRoundTrip =
false) {
801 bool DoRoundTripDefault =
true;
803 bool DoRoundTripDefault =
false;
806 bool DoRoundTrip = DoRoundTripDefault;
807 if (ForceRoundTrip) {
810 for (
const auto *Arg : CommandLineArgs) {
811 if (Arg == StringRef(
"-round-trip-args"))
813 if (Arg == StringRef(
"-no-round-trip-args"))
821 return Parse(RealInvocation, CommandLineArgs, Diags, Argv0);
826 llvm::raw_string_ostream OS(Buffer);
827 for (
const char *Arg : Args) {
828 llvm::sys::printArg(OS, Arg,
true);
841 if (!
Parse(DummyInvocation, CommandLineArgs, DummyDiags, Argv0) ||
848 auto Success =
Parse(RealInvocation, CommandLineArgs, Diags, Argv0);
854 Diags.
Report(diag::err_cc1_round_trip_fail_then_ok);
855 Diags.
Report(diag::note_cc1_round_trip_original)
856 << SerializeArgs(CommandLineArgs);
861 llvm::BumpPtrAllocator Alloc;
862 llvm::StringSaver StringPool(Alloc);
863 auto SA = [&StringPool](
const Twine &Arg) {
864 return StringPool.save(Arg).data();
871 Generate(DummyInvocation, GeneratedArgs, SA);
877 bool Success2 =
Parse(RealInvocation, GeneratedArgs, Diags, Argv0);
882 Diags.
Report(diag::err_cc1_round_trip_ok_then_fail);
883 Diags.
Report(diag::note_cc1_round_trip_generated)
884 << 1 << SerializeArgs(GeneratedArgs);
889 if (CheckAgainstOriginalInvocation)
891 ComparisonArgs.assign(CommandLineArgs.begin(), CommandLineArgs.end());
895 Generate(RealInvocation, ComparisonArgs, SA);
900 return std::equal(A.begin(), A.end(), B.begin(), B.end(),
901 [](
const char *AElem,
const char *BElem) {
902 return StringRef(AElem) == StringRef(BElem);
909 if (!
Equal(GeneratedArgs, ComparisonArgs)) {
910 Diags.
Report(diag::err_cc1_round_trip_mismatch);
911 Diags.
Report(diag::note_cc1_round_trip_generated)
912 << 1 << SerializeArgs(GeneratedArgs);
913 Diags.
Report(diag::note_cc1_round_trip_generated)
914 << 2 << SerializeArgs(ComparisonArgs);
918 Diags.
Report(diag::remark_cc1_round_trip_generated)
919 << 1 << SerializeArgs(GeneratedArgs);
920 Diags.
Report(diag::remark_cc1_round_trip_generated)
921 << 2 << SerializeArgs(ComparisonArgs);
933 return CreateFromArgsImpl(Invocation, CommandLineArgs, Diags, Argv0);
937 Args.push_back(
"-cc1");
940 DummyInvocation1, DummyInvocation2, Args, Diags, Argv0,
945 OptSpecifier GroupWithValue,
946 std::vector<std::string> &Diagnostics) {
947 for (
auto *A : Args.filtered(Group)) {
948 if (A->getOption().getKind() == Option::FlagClass) {
951 Diagnostics.push_back(
952 std::string(A->getOption().getName().drop_front(1)));
953 }
else if (A->getOption().matches(GroupWithValue)) {
956 Diagnostics.push_back(
957 std::string(A->getOption().getName().drop_front(1).rtrim(
"=-")));
960 Diagnostics.push_back(A->getValue());
971 std::vector<std::string> &Funcs) {
972 std::vector<std::string> Values = Args.getAllArgValues(OPT_fno_builtin_);
974 Funcs.insert(Funcs.end(), Values.begin(), BuiltinEnd);
981#define ANALYZER_OPTION_WITH_MARSHALLING(...) \
982 GENERATE_OPTION_WITH_MARSHALLING(Consumer, __VA_ARGS__)
983#include "clang/Driver/Options.inc"
984#undef ANALYZER_OPTION_WITH_MARSHALLING
988#define ANALYSIS_CONSTRAINTS(NAME, CMDFLAG, DESC, CREATFN) \
990 GenerateArg(Consumer, OPT_analyzer_constraints, CMDFLAG); \
992#include "clang/StaticAnalyzer/Core/Analyses.def"
994 llvm_unreachable(
"Tried to generate unknown analysis constraint.");
1000#define ANALYSIS_DIAGNOSTICS(NAME, CMDFLAG, DESC, CREATFN) \
1002 GenerateArg(Consumer, OPT_analyzer_output, CMDFLAG); \
1004#include "clang/StaticAnalyzer/Core/Analyses.def"
1006 llvm_unreachable(
"Tried to generate unknown analysis diagnostic client.");
1012#define ANALYSIS_PURGE(NAME, CMDFLAG, DESC) \
1014 GenerateArg(Consumer, OPT_analyzer_purge, CMDFLAG); \
1016#include "clang/StaticAnalyzer/Core/Analyses.def"
1018 llvm_unreachable(
"Tried to generate unknown analysis purge mode.");
1024#define ANALYSIS_INLINING_MODE(NAME, CMDFLAG, DESC) \
1026 GenerateArg(Consumer, OPT_analyzer_inlining_mode, CMDFLAG); \
1028#include "clang/StaticAnalyzer/Core/Analyses.def"
1030 llvm_unreachable(
"Tried to generate unknown analysis inlining mode.");
1036 CP.second ? OPT_analyzer_checker : OPT_analyzer_disable_checker;
1045 for (
const auto &
C : Opts.
Config)
1046 SortedConfigOpts.emplace_back(
C.getKey(),
C.getValue());
1047 llvm::sort(SortedConfigOpts, llvm::less_first());
1049 for (
const auto &[Key,
Value] : SortedConfigOpts) {
1052 auto Entry = ConfigOpts.
Config.find(Key);
1053 if (Entry != ConfigOpts.
Config.end() && Entry->getValue() ==
Value)
1068#define ANALYZER_OPTION_WITH_MARSHALLING(...) \
1069 PARSE_OPTION_WITH_MARSHALLING(Args, Diags, __VA_ARGS__)
1070#include "clang/Driver/Options.inc"
1071#undef ANALYZER_OPTION_WITH_MARSHALLING
1073 if (Arg *A = Args.getLastArg(OPT_analyzer_constraints)) {
1074 StringRef Name = A->getValue();
1076#define ANALYSIS_CONSTRAINTS(NAME, CMDFLAG, DESC, CREATFN) \
1077 .Case(CMDFLAG, NAME##Model)
1078#include "clang/StaticAnalyzer/Core/Analyses.def"
1081 Diags.
Report(diag::err_drv_invalid_value)
1082 << A->getAsString(Args) << Name;
1085 if (
Value == AnalysisConstraints::Z3ConstraintsModel) {
1086 Diags.
Report(diag::err_analyzer_not_built_with_z3);
1093 if (Arg *A = Args.getLastArg(OPT_analyzer_output)) {
1094 StringRef Name = A->getValue();
1096#define ANALYSIS_DIAGNOSTICS(NAME, CMDFLAG, DESC, CREATFN) \
1097 .Case(CMDFLAG, PD_##NAME)
1098#include "clang/StaticAnalyzer/Core/Analyses.def"
1101 Diags.
Report(diag::err_drv_invalid_value)
1102 << A->getAsString(Args) << Name;
1108 if (Arg *A = Args.getLastArg(OPT_analyzer_purge)) {
1109 StringRef Name = A->getValue();
1111#define ANALYSIS_PURGE(NAME, CMDFLAG, DESC) \
1112 .Case(CMDFLAG, NAME)
1113#include "clang/StaticAnalyzer/Core/Analyses.def"
1116 Diags.
Report(diag::err_drv_invalid_value)
1117 << A->getAsString(Args) << Name;
1123 if (Arg *A = Args.getLastArg(OPT_analyzer_inlining_mode)) {
1124 StringRef Name = A->getValue();
1126#define ANALYSIS_INLINING_MODE(NAME, CMDFLAG, DESC) \
1127 .Case(CMDFLAG, NAME)
1128#include "clang/StaticAnalyzer/Core/Analyses.def"
1131 Diags.
Report(diag::err_drv_invalid_value)
1132 << A->getAsString(Args) << Name;
1140 Args.filtered(OPT_analyzer_checker, OPT_analyzer_disable_checker)) {
1142 bool IsEnabled = A->getOption().getID() == OPT_analyzer_checker;
1145 StringRef CheckerAndPackageList = A->getValue();
1147 CheckerAndPackageList.split(CheckersAndPackages,
",");
1148 for (
const StringRef &CheckerOrPackage : CheckersAndPackages)
1154 for (
const auto *A : Args.filtered(OPT_analyzer_config)) {
1158 StringRef configList = A->getValue();
1160 configList.split(configVals,
",");
1161 for (
const auto &configVal : configVals) {
1163 std::tie(key, val) = configVal.split(
"=");
1166 diag::err_analyzer_config_no_value) << configVal;
1169 if (val.contains(
'=')) {
1171 diag::err_analyzer_config_multiple_values)
1180 Diags.
Report(diag::err_analyzer_config_unknown) << key;
1185 Opts.
Config[key] = std::string(val);
1195 for (
unsigned i = 0; i < Args.getNumInputArgStrings(); ++i) {
1198 os << Args.getArgString(i);
1205 StringRef OptionName, StringRef DefaultVal) {
1206 return Config.insert({OptionName, std::string(DefaultVal)}).first->second;
1211 StringRef &OptionField, StringRef Name,
1212 StringRef DefaultVal) {
1221 bool &OptionField, StringRef Name,
bool DefaultVal) {
1222 auto PossiblyInvalidVal =
1223 llvm::StringSwitch<std::optional<bool>>(
1226 .Case(
"false",
false)
1227 .Default(std::nullopt);
1229 if (!PossiblyInvalidVal) {
1231 Diags->
Report(diag::err_analyzer_config_invalid_input)
1232 << Name <<
"a boolean";
1234 OptionField = DefaultVal;
1236 OptionField = *PossiblyInvalidVal;
1241 unsigned &OptionField, StringRef Name,
1242 unsigned DefaultVal) {
1244 OptionField = DefaultVal;
1245 bool HasFailed =
getStringOption(Config, Name, std::to_string(DefaultVal))
1246 .getAsInteger(0, OptionField);
1247 if (Diags && HasFailed)
1248 Diags->
Report(diag::err_analyzer_config_invalid_input)
1249 << Name <<
"an unsigned";
1255 unsigned DefaultVal) {
1258 if (Parsed.has_value()) {
1259 OptionField = Parsed.value();
1262 if (Diags && !Parsed.has_value())
1263 Diags->
Report(diag::err_analyzer_config_invalid_input)
1264 << Name <<
"a positive";
1266 OptionField = DefaultVal;
1274#define ANALYZER_OPTION(TYPE, NAME, CMDFLAG, DESC, DEFAULT_VAL) \
1275 initOption(AnOpts.Config, Diags, AnOpts.NAME, CMDFLAG, DEFAULT_VAL);
1276#define ANALYZER_OPTION_DEPENDS_ON_USER_MODE(...)
1277#include "clang/StaticAnalyzer/Core/AnalyzerOptions.def"
1279 assert(AnOpts.UserMode ==
"shallow" || AnOpts.UserMode ==
"deep");
1280 const bool InShallowMode = AnOpts.UserMode ==
"shallow";
1282#define ANALYZER_OPTION(...)
1283#define ANALYZER_OPTION_DEPENDS_ON_USER_MODE(TYPE, NAME, CMDFLAG, DESC, \
1284 SHALLOW_VAL, DEEP_VAL) \
1285 initOption(AnOpts.Config, Diags, AnOpts.NAME, CMDFLAG, \
1286 InShallowMode ? SHALLOW_VAL : DEEP_VAL);
1287#include "clang/StaticAnalyzer/Core/AnalyzerOptions.def"
1294 if (!AnOpts.RawSilencedCheckersAndPackages.empty()) {
1295 std::vector<StringRef> Checkers =
1297 std::vector<StringRef> Packages =
1301 AnOpts.RawSilencedCheckersAndPackages.split(CheckersAndPackages,
";");
1303 for (
const StringRef &CheckerOrPackage : CheckersAndPackages) {
1305 bool IsChecker = CheckerOrPackage.contains(
'.');
1306 bool IsValidName = IsChecker
1307 ? llvm::is_contained(Checkers, CheckerOrPackage)
1308 : llvm::is_contained(Packages, CheckerOrPackage);
1311 Diags->
Report(diag::err_unknown_analyzer_checker_or_package)
1312 << CheckerOrPackage;
1322 if (AnOpts.ShouldTrackConditionsDebug && !AnOpts.ShouldTrackConditions)
1323 Diags->
Report(diag::err_analyzer_config_invalid_input)
1324 <<
"track-conditions-debug" <<
"'track-conditions' to also be enabled";
1332 if (
Remark.hasValidPattern()) {
1337 GenerateArg(Consumer, OPT_R_Joined, StringRef(
"no-") + Name);
1346 OptSpecifier OptEQ, StringRef Name) {
1349 auto InitializeResultPattern = [&Diags, &Args, &
Result](
const Arg *A,
1350 StringRef Pattern) {
1351 Result.Pattern = Pattern.str();
1353 std::string RegexError;
1354 Result.Regex = std::make_shared<llvm::Regex>(
Result.Pattern);
1355 if (!
Result.Regex->isValid(RegexError)) {
1356 Diags.
Report(diag::err_drv_optimization_remark_pattern)
1357 << RegexError << A->getAsString(Args);
1364 for (Arg *A : Args) {
1365 if (A->getOption().matches(OPT_R_Joined)) {
1366 StringRef
Value = A->getValue();
1370 else if (
Value ==
"everything")
1372 else if (
Value.split(
'-') == std::make_pair(StringRef(
"no"), Name))
1374 else if (
Value ==
"no-everything")
1384 InitializeResultPattern(A,
".*");
1386 }
else if (A->getOption().matches(OptEQ)) {
1388 if (!InitializeResultPattern(A, A->getValue()))
1397 const std::vector<std::string> &Levels,
1401 for (
const auto &Level : Levels) {
1403 llvm::StringSwitch<DiagnosticLevelMask>(Level)
1411 Diags.
Report(diag::err_drv_invalid_value) << FlagName << Level;
1419 const std::vector<std::string> &Sanitizers,
1421 for (
const auto &Sanitizer : Sanitizers) {
1424 Diags.
Report(diag::err_drv_invalid_value) << FlagName << Sanitizer;
1438 const std::vector<std::string> &Sanitizers,
1441 for (
const auto &Sanitizer : Sanitizers) {
1443 Diags.
Report(diag::err_drv_invalid_value) << FlagName << Sanitizer;
1452 llvm::SplitString(Bundle, BundleParts,
",");
1453 for (
const auto &B : BundleParts) {
1457 D.Report(diag::err_drv_invalid_value) << FlagName << Bundle;
1471 llvm::raw_string_ostream OS(Buffer);
1472 llvm::interleave(BundleParts, OS, [&OS](StringRef Part) { OS << Part; },
",");
1478 const Twine &ProfileName,
1479 llvm::vfs::FileSystem &FS,
1481 auto ReaderOrErr = llvm::IndexedInstrProfReader::create(ProfileName, FS);
1482 if (
auto E = ReaderOrErr.takeError()) {
1484 "Error in reading profile %0: %1");
1485 llvm::handleAllErrors(std::move(
E), [&](
const llvm::ErrorInfoBase &EI) {
1486 Diags.
Report(DiagID) << ProfileName.str() << EI.message();
1490 std::unique_ptr<llvm::IndexedInstrProfReader> PGOReader =
1491 std::move(ReaderOrErr.get());
1495 if (PGOReader->isIRLevelProfile() || PGOReader->hasMemoryProfile()) {
1496 if (PGOReader->hasCSIRLevelProfile())
1497 Opts.setProfileUse(llvm::driver::ProfileInstrKind::ProfileCSIRInstr);
1499 Opts.setProfileUse(llvm::driver::ProfileInstrKind::ProfileIRInstr);
1501 Opts.setProfileUse(llvm::driver::ProfileInstrKind::ProfileClangInstr);
1506 const llvm::Triple &Triple) {
1507 assert(Triple.getArch() == llvm::Triple::aarch64);
1514 LangOpts.PointerAuthFunctionTypeDiscrimination ? Discrimination::Type
1515 : Discrimination::None);
1518 Key::ASDA,
LangOpts.PointerAuthVTPtrAddressDiscrimination,
1519 LangOpts.PointerAuthVTPtrTypeDiscrimination ? Discrimination::Type
1520 : Discrimination::None);
1522 if (
LangOpts.PointerAuthTypeInfoVTPtrDiscrimination)
1537 if (
LangOpts.PointerAuthInitFini) {
1539 Key::ASIA,
LangOpts.PointerAuthInitFiniAddressDiscrimination,
1549 if (
LangOpts.PointerAuthBlockDescriptorPointers)
1568 if (
LangOpts.PointerAuthObjcClassROPointers)
1581 const llvm::Triple &Triple,
1583 if (!LangOpts.PointerAuthCalls && !LangOpts.PointerAuthReturns &&
1584 !LangOpts.PointerAuthAuthTraps && !LangOpts.PointerAuthIndirectGotos &&
1585 !LangOpts.AArch64JumpTableHardening)
1591void CompilerInvocationBase::GenerateCodeGenArgs(
const CodeGenOptions &Opts,
1593 const llvm::Triple &
T,
1594 const std::string &OutputFile,
1598 if (Opts.OptimizationLevel == 0)
1601 GenerateArg(Consumer, OPT_O, Twine(Opts.OptimizationLevel));
1603#define CODEGEN_OPTION_WITH_MARSHALLING(...) \
1604 GENERATE_OPTION_WITH_MARSHALLING(Consumer, __VA_ARGS__)
1605#include "clang/Driver/Options.inc"
1606#undef CODEGEN_OPTION_WITH_MARSHALLING
1608 if (Opts.OptimizationLevel > 0) {
1612 GenerateArg(Consumer, OPT_finline_hint_functions);
1617 if (Opts.DirectAccessExternalData &&
LangOpts->PICLevel != 0)
1618 GenerateArg(Consumer, OPT_fdirect_access_external_data);
1619 else if (!Opts.DirectAccessExternalData &&
LangOpts->PICLevel == 0)
1620 GenerateArg(Consumer, OPT_fno_direct_access_external_data);
1622 std::optional<StringRef> DebugInfoVal;
1623 switch (Opts.DebugInfo) {
1624 case llvm::codegenoptions::DebugLineTablesOnly:
1625 DebugInfoVal =
"line-tables-only";
1627 case llvm::codegenoptions::DebugDirectivesOnly:
1628 DebugInfoVal =
"line-directives-only";
1630 case llvm::codegenoptions::DebugInfoConstructor:
1631 DebugInfoVal =
"constructor";
1633 case llvm::codegenoptions::LimitedDebugInfo:
1634 DebugInfoVal =
"limited";
1636 case llvm::codegenoptions::FullDebugInfo:
1637 DebugInfoVal =
"standalone";
1639 case llvm::codegenoptions::UnusedTypeInfo:
1640 DebugInfoVal =
"unused-types";
1642 case llvm::codegenoptions::NoDebugInfo:
1643 DebugInfoVal = std::nullopt;
1645 case llvm::codegenoptions::LocTrackingOnly:
1646 DebugInfoVal = std::nullopt;
1650 GenerateArg(Consumer, OPT_debug_info_kind_EQ, *DebugInfoVal);
1654 Prefix.first +
"=" + Prefix.second);
1657 GenerateArg(Consumer, OPT_fcoverage_prefix_map_EQ,
1658 Prefix.first +
"=" + Prefix.second);
1660 if (Opts.NewStructPathTBAA)
1663 if (Opts.OptimizeSize == 1)
1665 else if (Opts.OptimizeSize == 2)
1673 if (Opts.UnrollLoops && Opts.OptimizationLevel <= 1)
1675 else if (!Opts.UnrollLoops && Opts.OptimizationLevel > 1)
1678 if (Opts.InterchangeLoops)
1686 if (Opts.DebugNameTable ==
1687 static_cast<unsigned>(llvm::DICompileUnit::DebugNameTableKind::GNU))
1689 else if (Opts.DebugNameTable ==
1690 static_cast<unsigned>(
1691 llvm::DICompileUnit::DebugNameTableKind::Default))
1694 if (Opts.DebugTemplateAlias)
1697 auto TNK = Opts.getDebugSimpleTemplateNames();
1698 if (TNK != llvm::codegenoptions::DebugTemplateNamesKind::Full) {
1699 if (TNK == llvm::codegenoptions::DebugTemplateNamesKind::Simple)
1700 GenerateArg(Consumer, OPT_gsimple_template_names_EQ,
"simple");
1701 else if (TNK == llvm::codegenoptions::DebugTemplateNamesKind::Mangled)
1702 GenerateArg(Consumer, OPT_gsimple_template_names_EQ,
"mangled");
1707 if (Opts.TimePasses) {
1708 if (Opts.TimePassesPerRun)
1709 GenerateArg(Consumer, OPT_ftime_report_EQ,
"per-pass-run");
1713 if (Opts.TimePassesJson)
1717 if (Opts.PrepareForLTO && !Opts.PrepareForThinLTO)
1720 if (Opts.PrepareForThinLTO)
1729 StringRef MemProfileBasename(
"memprof.profraw");
1750 std::string InstrBundle =
1752 if (!InstrBundle.empty())
1753 GenerateArg(Consumer, OPT_fxray_instrumentation_bundle, InstrBundle);
1756 if (Opts.CFProtectionReturn && Opts.CFProtectionBranch)
1757 GenerateArg(Consumer, OPT_fcf_protection_EQ,
"full");
1758 else if (Opts.CFProtectionReturn)
1759 GenerateArg(Consumer, OPT_fcf_protection_EQ,
"return");
1760 else if (Opts.CFProtectionBranch)
1761 GenerateArg(Consumer, OPT_fcf_protection_EQ,
"branch");
1763 if (Opts.CFProtectionBranch) {
1764 switch (Opts.getCFBranchLabelScheme()) {
1767#define CF_BRANCH_LABEL_SCHEME(Kind, FlagVal) \
1768 case CFBranchLabelSchemeKind::Kind: \
1769 GenerateArg(Consumer, OPT_mcf_branch_label_scheme_EQ, #FlagVal); \
1771#include "clang/Basic/CFProtectionOptions.def"
1775 if (Opts.FunctionReturnThunks)
1776 GenerateArg(Consumer, OPT_mfunction_return_EQ,
"thunk-extern");
1779 bool Builtint = F.LinkFlags == llvm::Linker::Flags::LinkOnlyNeeded &&
1780 F.PropagateAttrs && F.Internalize;
1782 Builtint ? OPT_mlink_builtin_bitcode : OPT_mlink_bitcode_file,
1786 if (Opts.EmulatedTLS)
1794 GenerateArg(Consumer, OPT_fdenormal_fp_math_f32_EQ,
1799 T.isPPC32() ? OPT_maix_struct_return : OPT_fpcc_struct_return;
1803 T.isPPC32() ? OPT_msvr4_struct_return : OPT_freg_struct_return;
1807 if (Opts.EnableAIXExtendedAltivecABI)
1810 if (Opts.XCOFFReadOnlyPointers)
1828 GenerateArg(Consumer, OPT_fdiagnostics_hotness_threshold_EQ,
1833 GenerateArg(Consumer, OPT_fdiagnostics_misexpect_tolerance_EQ,
1837 GenerateArg(Consumer, OPT_fsanitize_recover_EQ, Sanitizer);
1840 GenerateArg(Consumer, OPT_fsanitize_trap_EQ, Sanitizer);
1842 for (StringRef Sanitizer :
1844 GenerateArg(Consumer, OPT_fsanitize_merge_handlers_EQ, Sanitizer);
1848 for (std::string Sanitizer : Values)
1849 GenerateArg(Consumer, OPT_fsanitize_skip_hot_cutoff_EQ, Sanitizer);
1852 GenerateArg(Consumer, OPT_fallow_runtime_check_skip_hot_cutoff_EQ,
1856 for (StringRef Sanitizer :
1858 GenerateArg(Consumer, OPT_fsanitize_annotate_debug_info_EQ, Sanitizer);
1860 if (!Opts.EmitVersionIdentMetadata)
1863 switch (Opts.FiniteLoops) {
1874 if (Opts.StaticClosure)
1878bool CompilerInvocation::ParseCodeGenArgs(
CodeGenOptions &Opts, ArgList &Args,
1881 const llvm::Triple &
T,
1882 const std::string &OutputFile,
1888 unsigned MaxOptLevel = 3;
1889 if (OptimizationLevel > MaxOptLevel) {
1892 Diags.
Report(diag::warn_drv_optimization_value)
1893 << Args.getLastArg(OPT_O)->getAsString(Args) <<
"-O" << MaxOptLevel;
1894 OptimizationLevel = MaxOptLevel;
1896 Opts.OptimizationLevel = OptimizationLevel;
1905#define CODEGEN_OPTION_WITH_MARSHALLING(...) \
1906 PARSE_OPTION_WITH_MARSHALLING(Args, Diags, __VA_ARGS__)
1907#include "clang/Driver/Options.inc"
1908#undef CODEGEN_OPTION_WITH_MARSHALLING
1912 if (Opts.OptimizationLevel == 0) {
1914 }
else if (
const Arg *A = Args.getLastArg(options::OPT_finline_functions,
1915 options::OPT_finline_hint_functions,
1916 options::OPT_fno_inline_functions,
1917 options::OPT_fno_inline)) {
1920 if (A->getOption().matches(options::OPT_finline_functions))
1922 else if (A->getOption().matches(options::OPT_finline_hint_functions))
1932 Opts.DirectAccessExternalData =
1933 Args.hasArg(OPT_fdirect_access_external_data) ||
1934 (!Args.hasArg(OPT_fno_direct_access_external_data) &&
1937 if (Arg *A = Args.getLastArg(OPT_debug_info_kind_EQ)) {
1939 llvm::StringSwitch<unsigned>(A->getValue())
1940 .Case(
"line-tables-only", llvm::codegenoptions::DebugLineTablesOnly)
1941 .Case(
"line-directives-only",
1942 llvm::codegenoptions::DebugDirectivesOnly)
1943 .Case(
"constructor", llvm::codegenoptions::DebugInfoConstructor)
1944 .Case(
"limited", llvm::codegenoptions::LimitedDebugInfo)
1945 .Case(
"standalone", llvm::codegenoptions::FullDebugInfo)
1946 .Case(
"unused-types", llvm::codegenoptions::UnusedTypeInfo)
1949 Diags.
Report(diag::err_drv_invalid_value) << A->getAsString(Args)
1952 Opts.setDebugInfo(
static_cast<llvm::codegenoptions::DebugInfoKind
>(Val));
1958 Args.getLastArg(OPT_fuse_ctor_homing, OPT_fno_use_ctor_homing)) {
1959 if (A->getOption().matches(OPT_fuse_ctor_homing) &&
1960 Opts.getDebugInfo() == llvm::codegenoptions::LimitedDebugInfo)
1961 Opts.setDebugInfo(llvm::codegenoptions::DebugInfoConstructor);
1962 if (A->getOption().matches(OPT_fno_use_ctor_homing) &&
1963 Opts.getDebugInfo() == llvm::codegenoptions::DebugInfoConstructor)
1964 Opts.setDebugInfo(llvm::codegenoptions::LimitedDebugInfo);
1967 for (
const auto &Arg : Args.getAllArgValues(OPT_fdebug_prefix_map_EQ)) {
1968 auto Split = StringRef(Arg).split(
'=');
1972 for (
const auto &Arg : Args.getAllArgValues(OPT_fcoverage_prefix_map_EQ)) {
1973 auto Split = StringRef(Arg).split(
'=');
1977 const llvm::Triple::ArchType DebugEntryValueArchs[] = {
1978 llvm::Triple::x86, llvm::Triple::x86_64, llvm::Triple::aarch64,
1979 llvm::Triple::arm, llvm::Triple::armeb, llvm::Triple::mips,
1980 llvm::Triple::mipsel, llvm::Triple::mips64, llvm::Triple::mips64el};
1983 llvm::is_contained(DebugEntryValueArchs,
T.getArch()))
1984 Opts.EmitCallSiteInfo =
true;
1987 Diags.
Report(diag::warn_ignoring_verify_debuginfo_preserve_export)
1992 Opts.NewStructPathTBAA = !Args.hasArg(OPT_no_struct_path_tbaa) &&
1993 Args.hasArg(OPT_new_struct_path_tbaa);
1995 Opts.SimplifyLibCalls = !
LangOpts->NoBuiltin;
1996 if (Opts.SimplifyLibCalls)
1999 Args.hasFlag(OPT_funroll_loops, OPT_fno_unroll_loops,
2000 (Opts.OptimizationLevel > 1));
2001 Opts.InterchangeLoops =
2002 Args.hasFlag(OPT_floop_interchange, OPT_fno_loop_interchange,
false);
2004 std::string(Args.getLastArgValue(OPT_fbinutils_version_EQ));
2006 Opts.DebugTemplateAlias = Args.hasArg(OPT_gtemplate_alias);
2008 Opts.DebugNameTable =
static_cast<unsigned>(
2009 Args.hasArg(OPT_ggnu_pubnames)
2010 ? llvm::DICompileUnit::DebugNameTableKind::GNU
2011 : Args.hasArg(OPT_gpubnames)
2012 ? llvm::DICompileUnit::DebugNameTableKind::Default
2013 : llvm::DICompileUnit::DebugNameTableKind::None);
2014 if (
const Arg *A = Args.getLastArg(OPT_gsimple_template_names_EQ)) {
2015 StringRef
Value = A->getValue();
2017 Diags.
Report(diag::err_drv_unsupported_option_argument)
2018 << A->getSpelling() << A->getValue();
2019 Opts.setDebugSimpleTemplateNames(
2020 StringRef(A->getValue()) ==
"simple"
2021 ? llvm::codegenoptions::DebugTemplateNamesKind::Simple
2022 : llvm::codegenoptions::DebugTemplateNamesKind::Mangled);
2025 if (Args.hasArg(OPT_ftime_report, OPT_ftime_report_EQ, OPT_ftime_report_json,
2026 OPT_stats_file_timers)) {
2027 Opts.TimePasses =
true;
2030 if (
const Arg *EQ = Args.getLastArg(OPT_ftime_report_EQ)) {
2031 StringRef Val =
EQ->getValue();
2032 if (Val ==
"per-pass")
2033 Opts.TimePassesPerRun =
false;
2034 else if (Val ==
"per-pass-run")
2035 Opts.TimePassesPerRun =
true;
2037 Diags.
Report(diag::err_drv_invalid_value)
2038 <<
EQ->getAsString(Args) <<
EQ->getValue();
2041 if (Args.getLastArg(OPT_ftime_report_json))
2042 Opts.TimePassesJson =
true;
2045 Opts.PrepareForLTO =
false;
2046 Opts.PrepareForThinLTO =
false;
2047 if (Arg *A = Args.getLastArg(OPT_flto_EQ)) {
2048 Opts.PrepareForLTO =
true;
2049 StringRef S = A->getValue();
2051 Opts.PrepareForThinLTO =
true;
2052 else if (S !=
"full")
2053 Diags.
Report(diag::err_drv_invalid_value) << A->getAsString(Args) << S;
2054 if (Args.hasArg(OPT_funified_lto))
2055 Opts.PrepareForThinLTO =
true;
2057 if (Arg *A = Args.getLastArg(OPT_fthinlto_index_EQ)) {
2059 Diags.
Report(diag::err_drv_argument_only_allowed_with)
2060 << A->getAsString(Args) <<
"-x ir";
2062 std::string(Args.getLastArgValue(OPT_fthinlto_index_EQ));
2064 if (Arg *A = Args.getLastArg(OPT_save_temps_EQ))
2066 llvm::StringSwitch<std::string>(A->getValue())
2067 .Case(
"obj", OutputFile)
2068 .Default(llvm::sys::path::filename(OutputFile).str());
2071 const char *MemProfileBasename =
"memprof.profraw";
2072 if (Args.hasArg(OPT_fmemory_profile_EQ)) {
2074 llvm::sys::path::append(
Path, MemProfileBasename);
2076 }
else if (Args.hasArg(OPT_fmemory_profile))
2080 if (Args.hasArg(OPT_coverage_version_EQ)) {
2081 StringRef CoverageVersion = Args.getLastArgValue(OPT_coverage_version_EQ);
2082 if (CoverageVersion.size() != 4) {
2083 Diags.
Report(diag::err_drv_invalid_value)
2084 << Args.getLastArg(OPT_coverage_version_EQ)->getAsString(Args)
2094 for (
const auto &A : Args) {
2096 if (A->getOption().getID() == options::OPT_o ||
2097 A->getOption().getID() == options::OPT_INPUT ||
2098 A->getOption().getID() == options::OPT_x ||
2099 A->getOption().getID() == options::OPT_fembed_bitcode ||
2100 A->getOption().matches(options::OPT_W_Group))
2103 A->render(Args, ASL);
2104 for (
const auto &arg : ASL) {
2105 StringRef ArgStr(arg);
2106 llvm::append_range(Opts.
CmdArgs, ArgStr);
2112 auto XRayInstrBundles =
2113 Args.getAllArgValues(OPT_fxray_instrumentation_bundle);
2114 if (XRayInstrBundles.empty())
2117 for (
const auto &A : XRayInstrBundles)
2121 if (
const Arg *A = Args.getLastArg(OPT_fcf_protection_EQ)) {
2122 StringRef Name = A->getValue();
2123 if (Name ==
"full") {
2124 Opts.CFProtectionReturn = 1;
2125 Opts.CFProtectionBranch = 1;
2126 }
else if (Name ==
"return")
2127 Opts.CFProtectionReturn = 1;
2128 else if (Name ==
"branch")
2129 Opts.CFProtectionBranch = 1;
2130 else if (Name !=
"none")
2131 Diags.
Report(diag::err_drv_invalid_value) << A->getAsString(Args) << Name;
2134 if (Opts.CFProtectionBranch &&
T.isRISCV()) {
2135 if (
const Arg *A = Args.getLastArg(OPT_mcf_branch_label_scheme_EQ)) {
2137 llvm::StringSwitch<CFBranchLabelSchemeKind>(A->getValue())
2138#define CF_BRANCH_LABEL_SCHEME(Kind, FlagVal) \
2139 .Case(#FlagVal, CFBranchLabelSchemeKind::Kind)
2140#include "clang/Basic/CFProtectionOptions.def"
2143 Opts.setCFBranchLabelScheme(Scheme);
2145 Diags.
Report(diag::err_drv_invalid_value)
2146 << A->getAsString(Args) << A->getValue();
2150 if (
const Arg *A = Args.getLastArg(OPT_mfunction_return_EQ)) {
2151 auto Val = llvm::StringSwitch<llvm::FunctionReturnThunksKind>(A->getValue())
2152 .Case(
"keep", llvm::FunctionReturnThunksKind::Keep)
2153 .Case(
"thunk-extern", llvm::FunctionReturnThunksKind::Extern)
2154 .Default(llvm::FunctionReturnThunksKind::Invalid);
2157 Diags.
Report(diag::err_drv_argument_not_allowed_with)
2158 << A->getSpelling() <<
T.getTriple();
2159 else if (Val == llvm::FunctionReturnThunksKind::Invalid)
2160 Diags.
Report(diag::err_drv_invalid_value)
2161 << A->getAsString(Args) << A->getValue();
2162 else if (Val == llvm::FunctionReturnThunksKind::Extern &&
2163 Args.getLastArgValue(OPT_mcmodel_EQ) ==
"large")
2164 Diags.
Report(diag::err_drv_argument_not_allowed_with)
2165 << A->getAsString(Args)
2166 << Args.getLastArg(OPT_mcmodel_EQ)->getAsString(Args);
2168 Opts.FunctionReturnThunks =
static_cast<unsigned>(Val);
2172 Args.filtered(OPT_mlink_bitcode_file, OPT_mlink_builtin_bitcode)) {
2175 if (A->getOption().matches(OPT_mlink_builtin_bitcode)) {
2176 F.
LinkFlags = llvm::Linker::Flags::LinkOnlyNeeded;
2185 if (Arg *A = Args.getLastArg(OPT_fdenormal_fp_math_EQ)) {
2186 StringRef Val = A->getValue();
2190 Diags.
Report(diag::err_drv_invalid_value) << A->getAsString(Args) << Val;
2193 if (Arg *A = Args.getLastArg(OPT_fdenormal_fp_math_f32_EQ)) {
2194 StringRef Val = A->getValue();
2197 Diags.
Report(diag::err_drv_invalid_value) << A->getAsString(Args) << Val;
2203 Args.getLastArg(OPT_fpcc_struct_return, OPT_freg_struct_return,
2204 OPT_maix_struct_return, OPT_msvr4_struct_return)) {
2208 Diags.
Report(diag::err_drv_unsupported_opt_for_target)
2209 << A->getSpelling() <<
T.str();
2211 const Option &O = A->getOption();
2212 if (O.matches(OPT_fpcc_struct_return) ||
2213 O.matches(OPT_maix_struct_return)) {
2216 assert(O.matches(OPT_freg_struct_return) ||
2217 O.matches(OPT_msvr4_struct_return));
2222 if (Arg *A = Args.getLastArg(OPT_mxcoff_roptr)) {
2224 Diags.
Report(diag::err_drv_unsupported_opt_for_target)
2225 << A->getSpelling() <<
T.str();
2235 if (!Args.hasFlag(OPT_fdata_sections, OPT_fno_data_sections,
false))
2236 Diags.
Report(diag::err_roptr_requires_data_sections);
2238 Opts.XCOFFReadOnlyPointers =
true;
2241 if (Arg *A = Args.getLastArg(OPT_mabi_EQ_quadword_atomics)) {
2242 if (!
T.isOSAIX() ||
T.isPPC32())
2243 Diags.
Report(diag::err_drv_unsupported_opt_for_target)
2244 << A->getSpelling() <<
T.str();
2247 bool NeedLocTracking =
false;
2250 NeedLocTracking =
true;
2252 if (Arg *A = Args.getLastArg(OPT_opt_record_passes)) {
2254 NeedLocTracking =
true;
2257 if (Arg *A = Args.getLastArg(OPT_opt_record_format)) {
2259 NeedLocTracking =
true;
2269 Diags, Args, OPT_Rpass_analysis_EQ,
"pass-analysis");
2279 if (Opts.DiagnosticsWithHotness && !UsingProfile &&
2282 Diags.
Report(diag::warn_drv_diagnostics_hotness_requires_pgo)
2283 <<
"-fdiagnostics-show-hotness";
2287 Args.getLastArg(options::OPT_fdiagnostics_hotness_threshold_EQ)) {
2289 llvm::remarks::parseHotnessThresholdOption(
arg->getValue());
2292 Diags.
Report(diag::err_drv_invalid_diagnotics_hotness_threshold)
2293 <<
"-fdiagnostics-hotness-threshold=";
2299 Diags.
Report(diag::warn_drv_diagnostics_hotness_requires_pgo)
2300 <<
"-fdiagnostics-hotness-threshold=";
2305 Args.getLastArg(options::OPT_fdiagnostics_misexpect_tolerance_EQ)) {
2309 Diags.
Report(diag::err_drv_invalid_diagnotics_misexpect_tolerance)
2310 <<
"-fdiagnostics-misexpect-tolerance=";
2316 Diags.
Report(diag::warn_drv_diagnostics_misexpect_requires_pgo)
2317 <<
"-fdiagnostics-misexpect-tolerance=";
2324 if (UsingSampleProfile)
2325 NeedLocTracking =
true;
2328 NeedLocTracking =
true;
2332 if (NeedLocTracking &&
2333 Opts.getDebugInfo() == llvm::codegenoptions::NoDebugInfo)
2334 Opts.setDebugInfo(llvm::codegenoptions::LocTrackingOnly);
2339 Args.getAllArgValues(OPT_fsanitize_recover_EQ), Diags,
2342 Args.getAllArgValues(OPT_fsanitize_trap_EQ), Diags,
2345 Args.getAllArgValues(OPT_fsanitize_merge_handlers_EQ),
2350 "-fsanitize-skip-hot-cutoff=",
2351 Args.getAllArgValues(OPT_fsanitize_skip_hot_cutoff_EQ), Diags);
2354 "-fsanitize-annotate-debug-info=",
2355 Args.getAllArgValues(OPT_fsanitize_annotate_debug_info_EQ), Diags,
2359 Args.getLastArgValue(OPT_fallow_runtime_check_skip_hot_cutoff_EQ);
2362 if (
V.getAsDouble(A) || A < 0.0 || A > 1.0) {
2363 Diags.
Report(diag::err_drv_invalid_value)
2364 <<
"-fallow-runtime-check-skip-hot-cutoff=" <<
V;
2370 Opts.EmitVersionIdentMetadata = Args.hasFlag(OPT_Qy, OPT_Qn,
true);
2375 if (Args.hasArg(options::OPT_ffinite_loops))
2377 else if (Args.hasArg(options::OPT_fno_finite_loops))
2380 Opts.EmitIEEENaNCompliantInsts = Args.hasFlag(
2381 options::OPT_mamdgpu_ieee, options::OPT_mno_amdgpu_ieee,
true);
2382 if (!Opts.EmitIEEENaNCompliantInsts && !LangOptsRef.NoHonorNaNs)
2383 Diags.
Report(diag::err_drv_amdgpu_ieee_without_no_honor_nans);
2385 Opts.StaticClosure = Args.hasArg(options::OPT_static_libclosure);
2393#define DEPENDENCY_OUTPUT_OPTION_WITH_MARSHALLING(...) \
2394 GENERATE_OPTION_WITH_MARSHALLING(Consumer, __VA_ARGS__)
2395#include "clang/Driver/Options.inc"
2396#undef DEPENDENCY_OUTPUT_OPTION_WITH_MARSHALLING
2401 for (
const auto &Dep : Opts.
ExtraDeps) {
2402 switch (Dep.second) {
2415 GenerateArg(Consumer, OPT_fdepfile_entry, Dep.first);
2424 bool ShowLineMarkers) {
2428#define DEPENDENCY_OUTPUT_OPTION_WITH_MARSHALLING(...) \
2429 PARSE_OPTION_WITH_MARSHALLING(Args, Diags, __VA_ARGS__)
2430#include "clang/Driver/Options.inc"
2431#undef DEPENDENCY_OUTPUT_OPTION_WITH_MARSHALLING
2433 if (Args.hasArg(OPT_show_includes)) {
2448 if (!Args.hasArg(OPT_fno_sanitize_ignorelist)) {
2449 for (
const auto *A : Args.filtered(OPT_fsanitize_ignorelist_EQ)) {
2450 StringRef Val = A->getValue();
2451 if (!Val.contains(
'='))
2455 for (
const auto *A : Args.filtered(OPT_fsanitize_system_ignorelist_EQ)) {
2456 StringRef Val = A->getValue();
2457 if (!Val.contains(
'='))
2464 for (
const auto &
Filename : Args.getAllArgValues(OPT_fprofile_list_EQ))
2468 for (
const auto *A : Args.filtered(OPT_fdepfile_entry))
2472 for (
const auto *A : Args.filtered(OPT_fmodule_file)) {
2473 StringRef Val = A->getValue();
2474 if (!Val.contains(
'='))
2482 if (Args.hasArg(OPT_header_include_format_EQ))
2483 Diags.
Report(diag::err_drv_print_header_cc1_invalid_combination)
2487 Diags.
Report(diag::err_drv_print_header_cc1_invalid_filtering)
2491 if (Args.hasArg(OPT_header_include_filtering_EQ))
2492 Diags.
Report(diag::err_drv_print_header_cc1_invalid_combination)
2496 Diags.
Report(diag::err_drv_print_header_cc1_invalid_format)
2512 }
ShowColors = DefaultColor ? Colors_Auto : Colors_Off;
2513 for (
auto *A : Args) {
2514 const Option &O = A->getOption();
2515 if (O.matches(options::OPT_fcolor_diagnostics)) {
2517 }
else if (O.matches(options::OPT_fno_color_diagnostics)) {
2519 }
else if (O.matches(options::OPT_fdiagnostics_color_EQ)) {
2520 StringRef
Value(A->getValue());
2521 if (
Value ==
"always")
2523 else if (
Value ==
"never")
2525 else if (
Value ==
"auto")
2531 llvm::sys::Process::StandardErrHasColors());
2537 for (
const auto &Prefix : VerifyPrefixes) {
2540 auto BadChar = llvm::find_if(Prefix, [](
char C) {
2543 if (BadChar != Prefix.end() || !
isLetter(Prefix[0])) {
2545 Diags.
Report(diag::err_drv_invalid_value) <<
"-verify=" << Prefix;
2546 Diags.
Report(diag::note_drv_verify_prefix_spelling);
2556#define FILE_SYSTEM_OPTION_WITH_MARSHALLING(...) \
2557 GENERATE_OPTION_WITH_MARSHALLING(Consumer, __VA_ARGS__)
2558#include "clang/Driver/Options.inc"
2559#undef FILE_SYSTEM_OPTION_WITH_MARSHALLING
2568#define FILE_SYSTEM_OPTION_WITH_MARSHALLING(...) \
2569 PARSE_OPTION_WITH_MARSHALLING(Args, Diags, __VA_ARGS__)
2570#include "clang/Driver/Options.inc"
2571#undef FILE_SYSTEM_OPTION_WITH_MARSHALLING
2579#define MIGRATOR_OPTION_WITH_MARSHALLING(...) \
2580 GENERATE_OPTION_WITH_MARSHALLING(Consumer, __VA_ARGS__)
2581#include "clang/Driver/Options.inc"
2582#undef MIGRATOR_OPTION_WITH_MARSHALLING
2591#define MIGRATOR_OPTION_WITH_MARSHALLING(...) \
2592 PARSE_OPTION_WITH_MARSHALLING(Args, Diags, __VA_ARGS__)
2593#include "clang/Driver/Options.inc"
2594#undef MIGRATOR_OPTION_WITH_MARSHALLING
2599void CompilerInvocationBase::GenerateDiagnosticArgs(
2601 bool DefaultDiagColor) {
2603#define DIAG_OPTION_WITH_MARSHALLING(...) \
2604 GENERATE_OPTION_WITH_MARSHALLING(Consumer, __VA_ARGS__)
2605#include "clang/Driver/Options.inc"
2606#undef DIAG_OPTION_WITH_MARSHALLING
2609 GenerateArg(Consumer, OPT_diagnostic_serialized_file,
2612 if (Opts.ShowColors)
2615 if (Opts.VerifyDiagnostics &&
2620 if (Prefix !=
"expected")
2627 GenerateArg(Consumer, OPT_verify_ignore_unexpected);
2630 GenerateArg(Consumer, OPT_verify_ignore_unexpected_EQ,
"note");
2632 GenerateArg(Consumer, OPT_verify_ignore_unexpected_EQ,
"remark");
2634 GenerateArg(Consumer, OPT_verify_ignore_unexpected_EQ,
"warning");
2636 GenerateArg(Consumer, OPT_verify_ignore_unexpected_EQ,
"error");
2641 if (
Warning ==
"undef-prefix")
2644 if (
Warning ==
"invalid-constexpr" ||
Warning ==
"no-invalid-constexpr")
2646 Consumer(StringRef(
"-W") +
Warning);
2652 StringRef IgnoredRemarks[] = {
"pass",
"no-pass",
2653 "pass-analysis",
"no-pass-analysis",
2654 "pass-missed",
"no-pass-missed"};
2655 if (llvm::is_contained(IgnoredRemarks,
Remark))
2658 Consumer(StringRef(
"-R") +
Remark);
2662 GenerateArg(Consumer, OPT_warning_suppression_mappings_EQ,
2667std::unique_ptr<DiagnosticOptions>
2669 auto DiagOpts = std::make_unique<DiagnosticOptions>();
2670 unsigned MissingArgIndex, MissingArgCount;
2672 Argv.slice(1), MissingArgIndex, MissingArgCount);
2675 if (std::optional<std::string> NoColor =
2676 llvm::sys::Process::GetEnv(
"NO_COLOR");
2677 NoColor && !NoColor->empty()) {
2692 bool DefaultDiagColor) {
2693 std::optional<DiagnosticOptions> IgnoringDiagOpts;
2694 std::optional<DiagnosticsEngine> IgnoringDiags;
2696 IgnoringDiagOpts.emplace();
2699 Diags = &*IgnoringDiags;
2708#define DIAG_OPTION_WITH_MARSHALLING(...) \
2709 PARSE_OPTION_WITH_MARSHALLING(Args, *Diags, __VA_ARGS__)
2710#include "clang/Driver/Options.inc"
2711#undef DIAG_OPTION_WITH_MARSHALLING
2713 llvm::sys::Process::UseANSIEscapeCodes(Opts.UseANSIEscapeCodes);
2716 Args.getLastArg(OPT_diagnostic_serialized_file, OPT__serialize_diags))
2720 Opts.VerifyDiagnostics = Args.hasArg(OPT_verify) || Args.hasArg(OPT_verify_EQ);
2722 if (Args.hasArg(OPT_verify))
2727 Opts.VerifyDiagnostics =
false;
2732 "-verify-ignore-unexpected=",
2733 Args.getAllArgValues(OPT_verify_ignore_unexpected_EQ), *Diags, DiagMask);
2734 if (Args.hasArg(OPT_verify_ignore_unexpected))
2736 Opts.setVerifyIgnoreUnexpected(DiagMask);
2738 Diags->
Report(diag::warn_ignoring_ftabstop_value)
2743 if (
const Arg *A = Args.getLastArg(OPT_warning_suppression_mappings_EQ))
2757 std::string &BlockName,
2758 unsigned &MajorVersion,
2759 unsigned &MinorVersion,
2761 std::string &UserInfo) {
2763 Arg.split(Args,
':', 5);
2764 if (Args.size() < 5)
2767 BlockName = std::string(Args[0]);
2768 if (Args[1].getAsInteger(10, MajorVersion))
return true;
2769 if (Args[2].getAsInteger(10, MinorVersion))
return true;
2770 if (Args[3].getAsInteger(2, Hashed))
return true;
2771 if (Args.size() > 4)
2772 UserInfo = std::string(Args[4]);
2781 static const std::pair<frontend::ActionKind, unsigned> Table[] = {
2812 OPT_emit_reduced_module_interface},
2829 OPT_print_dependency_directives_minimized_source},
2836static std::optional<frontend::ActionKind>
2839 if (ActionOpt.second == Opt.getID())
2840 return ActionOpt.first;
2842 return std::nullopt;
2846static std::optional<OptSpecifier>
2849 if (ActionOpt.first == ProgramAction)
2850 return OptSpecifier(ActionOpt.second);
2852 return std::nullopt;
2858#define FRONTEND_OPTION_WITH_MARSHALLING(...) \
2859 GENERATE_OPTION_WITH_MARSHALLING(Consumer, __VA_ARGS__)
2860#include "clang/Driver/Options.inc"
2861#undef FRONTEND_OPTION_WITH_MARSHALLING
2863 std::optional<OptSpecifier> ProgramActionOpt =
2871 if (!ProgramActionOpt) {
2874 "Frontend action without option.");
2875 GenerateProgramAction = [&]() {
2882 GenerateProgramAction = [&]() {
2890 llvm_unreachable(
"Default AST dump format.");
2897 GenerateArg(Consumer, OPT_ast_dump_all_EQ, Format);
2910 GenerateProgramAction = [&]() {
2915 GenerateProgramAction();
2917 for (
const auto &PluginArgs : Opts.
PluginArgs) {
2919 for (
const auto &PluginArg : PluginArgs.second)
2921 Opt.getPrefix() + Opt.getName() + PluginArgs.first,
2922 Opt.getKind(), 0, PluginArg);
2926 if (
auto *TestExt = dyn_cast_or_null<TestModuleFileExtension>(Ext.get()))
2927 GenerateArg(Consumer, OPT_ftest_module_file_extension_EQ, TestExt->str());
2933 for (
const auto &Plugin : Opts.
Plugins)
2939 GenerateArg(Consumer, OPT_fmodule_file, ModuleFile);
2952 StringRef HeaderUnit =
"";
2957 HeaderUnit =
"-user";
2960 HeaderUnit =
"-system";
2963 HeaderUnit =
"-header-unit";
2966 StringRef Header = IsHeader ?
"-header" :
"";
2989 Lang =
"objective-c";
2992 Lang =
"objective-c++";
2995 Lang =
"assembler-with-cpp";
2999 "Generating -x argument for unknown language (not precompiled).");
3014 Lang + HeaderUnit + Header +
ModuleMap + Preprocessed);
3018 for (
const auto &Input : Opts.
Inputs)
3019 Consumer(Input.getFile());
3028#define FRONTEND_OPTION_WITH_MARSHALLING(...) \
3029 PARSE_OPTION_WITH_MARSHALLING(Args, Diags, __VA_ARGS__)
3030#include "clang/Driver/Options.inc"
3031#undef FRONTEND_OPTION_WITH_MARSHALLING
3034 if (
const Arg *A = Args.getLastArg(OPT_Action_Group)) {
3035 OptSpecifier Opt = OptSpecifier(A->getOption().getID());
3037 assert(ProgramAction &&
"Option specifier not in Action_Group.");
3040 (Opt == OPT_ast_dump_all_EQ || Opt == OPT_ast_dump_EQ)) {
3041 unsigned Val = llvm::StringSwitch<unsigned>(A->getValue())
3044 .Default(std::numeric_limits<unsigned>::max());
3046 if (Val != std::numeric_limits<unsigned>::max())
3049 Diags.
Report(diag::err_drv_invalid_value)
3050 << A->getAsString(Args) << A->getValue();
3060 Args.hasArg(OPT_interface_stub_version_EQ)
3061 ? Args.getLastArgValue(OPT_interface_stub_version_EQ)
3063 if (ArgStr ==
"experimental-yaml-elf-v1" ||
3064 ArgStr ==
"experimental-ifs-v1" || ArgStr ==
"experimental-ifs-v2" ||
3065 ArgStr ==
"experimental-tapi-elf-v1") {
3066 std::string ErrorMessage =
3067 "Invalid interface stub format: " + ArgStr.str() +
3069 Diags.
Report(diag::err_drv_invalid_value)
3070 <<
"Must specify a valid interface stub format type, ie: "
3071 "-interface-stub-version=ifs-v1"
3074 }
else if (!ArgStr.starts_with(
"ifs-")) {
3075 std::string ErrorMessage =
3076 "Invalid interface stub format: " + ArgStr.str() +
".";
3077 Diags.
Report(diag::err_drv_invalid_value)
3078 <<
"Must specify a valid interface stub format type, ie: "
3079 "-interface-stub-version=ifs-v1"
3094 if (!A->getSpelling().starts_with(
"-ast-dump")) {
3095 const Arg *SavedAction =
nullptr;
3096 for (
const Arg *AA :
3097 Args.filtered(OPT_Action_Group, OPT_main_file_name)) {
3098 if (AA->getOption().matches(OPT_main_file_name)) {
3099 SavedAction =
nullptr;
3100 }
else if (!SavedAction) {
3103 if (!A->getOption().matches(OPT_ast_dump_EQ))
3104 Diags.
Report(diag::err_fe_invalid_multiple_actions)
3105 << SavedAction->getSpelling() << A->getSpelling();
3112 if (
const Arg* A = Args.getLastArg(OPT_plugin)) {
3113 Opts.
Plugins.emplace_back(A->getValue(0));
3117 for (
const auto *AA : Args.filtered(OPT_plugin_arg))
3118 Opts.
PluginArgs[AA->getValue(0)].emplace_back(AA->getValue(1));
3120 for (
const std::string &Arg :
3121 Args.getAllArgValues(OPT_ftest_module_file_extension_EQ)) {
3122 std::string BlockName;
3123 unsigned MajorVersion;
3124 unsigned MinorVersion;
3126 std::string UserInfo;
3128 MinorVersion, Hashed, UserInfo)) {
3129 Diags.
Report(diag::err_test_module_file_extension_format) << Arg;
3136 std::make_shared<TestModuleFileExtension>(
3137 BlockName, MajorVersion, MinorVersion, Hashed, UserInfo));
3140 if (
const Arg *A = Args.getLastArg(OPT_code_completion_at)) {
3144 Diags.
Report(diag::err_drv_invalid_value)
3145 << A->getAsString(Args) << A->getValue();
3146 Diags.
Report(diag::note_command_line_code_loc_requirement);
3150 Opts.
Plugins = Args.getAllArgValues(OPT_load);
3151 Opts.
ASTDumpDecls = Args.hasArg(OPT_ast_dump, OPT_ast_dump_EQ);
3152 Opts.
ASTDumpAll = Args.hasArg(OPT_ast_dump_all, OPT_ast_dump_all_EQ);
3154 for (
const auto *A : Args.filtered(OPT_fmodule_file)) {
3155 StringRef Val = A->getValue();
3156 if (!Val.contains(
'='))
3161 Diags.
Report(diag::err_drv_argument_only_allowed_with) <<
"-fsystem-module"
3163 if (Args.hasArg(OPT_fclangir) || Args.hasArg(OPT_emit_cir))
3167 if (Args.hasArg(OPT_clangir_disable_passes))
3170 if (Args.hasArg(OPT_clangir_disable_verifier))
3174 if (Args.hasArg(OPT_aux_target_cpu))
3175 Opts.
AuxTargetCPU = std::string(Args.getLastArgValue(OPT_aux_target_cpu));
3176 if (Args.hasArg(OPT_aux_target_feature))
3180 if (
const Arg *A = Args.getLastArg(OPT_x)) {
3181 StringRef XValue = A->getValue();
3186 bool Preprocessed = XValue.consume_back(
"-cpp-output");
3187 bool ModuleMap = XValue.consume_back(
"-module-map");
3190 XValue !=
"precompiled-header" && XValue.consume_back(
"-header");
3196 if (IsHeader || Preprocessed) {
3197 if (XValue.consume_back(
"-header-unit"))
3199 else if (XValue.consume_back(
"-system"))
3201 else if (XValue.consume_back(
"-user"))
3207 IsHeaderFile = IsHeader && !Preprocessed && !
ModuleMap &&
3211 DashX = llvm::StringSwitch<InputKind>(XValue)
3227 DashX = llvm::StringSwitch<InputKind>(XValue)
3235 DashX = llvm::StringSwitch<InputKind>(XValue)
3238 .Cases(
"ast",
"pcm",
"precompiled-header",
3245 Diags.
Report(diag::err_drv_invalid_value)
3246 << A->getAsString(Args) << A->getValue();
3253 IsHeaderFile =
true;
3254 }
else if (IsHeaderFile)
3261 std::vector<std::string> Inputs = Args.getAllArgValues(OPT_INPUT);
3264 Inputs.push_back(
"-");
3268 Diags.
Report(diag::err_drv_header_unit_extra_inputs) << Inputs[1];
3270 for (
unsigned i = 0, e = Inputs.size(); i != e; ++i) {
3274 StringRef(Inputs[i]).rsplit(
'.').second);
3283 bool IsSystem =
false;
3292 Opts.
Inputs.emplace_back(std::move(Inputs[i]), IK, IsSystem);
3302 std::string ClangExecutable =
3303 llvm::sys::fs::getMainExecutable(Argv0, MainAddr);
3310#define HEADER_SEARCH_OPTION_WITH_MARSHALLING(...) \
3311 GENERATE_OPTION_WITH_MARSHALLING(Consumer, __VA_ARGS__)
3312#include "clang/Driver/Options.inc"
3313#undef HEADER_SEARCH_OPTION_WITH_MARSHALLING
3332 std::optional<bool> IsFramework,
3333 std::optional<bool> IgnoreSysRoot) {
3334 return llvm::is_contained(Groups, Entry.
Group) &&
3335 (!IsFramework || (Entry.
IsFramework == *IsFramework)) &&
3336 (!IgnoreSysRoot || (Entry.
IgnoreSysRoot == *IgnoreSysRoot));
3345 OptSpecifier Opt = [It, Matches]() {
3350 llvm_unreachable(
"Unexpected HeaderSearchOptions::Entry.");
3364 It->Group ==
frontend::After ? OPT_iwithprefix : OPT_iwithprefixbefore;
3371 for (; It < End && Matches(*It, {
frontend::After},
false,
true); ++It)
3377 GenerateArg(Consumer, It->IgnoreSysRoot ? OPT_isystem : OPT_iwithsysroot,
3382 GenerateArg(Consumer, OPT_iframeworkwithsysroot, It->Path);
3390 GenerateArg(Consumer, OPT_objc_isystem, It->Path);
3392 GenerateArg(Consumer, OPT_objcxx_isystem, It->Path);
3402 ? OPT_internal_isystem
3403 : OPT_internal_externc_isystem;
3407 GenerateArg(Consumer, OPT_internal_iframework, It->Path);
3409 assert(It == End &&
"Unhandled HeaderSearchOption::Entry.");
3413 OptSpecifier Opt =
P.IsSystemHeader ? OPT_system_header_prefix
3414 : OPT_no_system_header_prefix;
3424 const std::string &WorkingDir) {
3429#define HEADER_SEARCH_OPTION_WITH_MARSHALLING(...) \
3430 PARSE_OPTION_WITH_MARSHALLING(Args, Diags, __VA_ARGS__)
3431#include "clang/Driver/Options.inc"
3432#undef HEADER_SEARCH_OPTION_WITH_MARSHALLING
3434 if (
const Arg *A = Args.getLastArg(OPT_stdlib_EQ))
3435 Opts.
UseLibcxx = (strcmp(A->getValue(),
"libc++") == 0);
3439 if (!(
P.empty() || llvm::sys::path::is_absolute(
P))) {
3440 if (WorkingDir.empty())
3441 llvm::sys::fs::make_absolute(
P);
3443 llvm::sys::fs::make_absolute(WorkingDir,
P);
3445 llvm::sys::path::remove_dots(
P);
3449 for (
const auto *A : Args.filtered(OPT_fmodule_file)) {
3450 StringRef Val = A->getValue();
3451 if (Val.contains(
'=')) {
3452 auto Split = Val.split(
'=');
3454 std::string(Split.first), std::string(Split.second));
3457 for (
const auto *A : Args.filtered(OPT_fprebuilt_module_path))
3460 for (
const auto *A : Args.filtered(OPT_fmodules_ignore_macro)) {
3461 StringRef MacroDef = A->getValue();
3463 llvm::CachedHashString(MacroDef.split(
'=').first));
3467 bool IsSysrootSpecified =
3468 Args.hasArg(OPT__sysroot_EQ) || Args.hasArg(OPT_isysroot);
3472 auto PrefixHeaderPath = [IsSysrootSpecified,
3473 &Opts](
const llvm::opt::Arg *A,
3474 bool IsFramework =
false) -> std::string {
3475 assert(A->getNumValues() &&
"Unexpected empty search path flag!");
3476 if (IsSysrootSpecified && !IsFramework && A->getValue()[0] ==
'=') {
3478 llvm::sys::path::append(Buffer, Opts.
Sysroot,
3479 llvm::StringRef(A->getValue()).substr(1));
3480 return std::string(Buffer);
3482 return A->getValue();
3485 for (
const auto *A : Args.filtered(OPT_I, OPT_F)) {
3486 bool IsFramework = A->getOption().matches(OPT_F);
3492 StringRef Prefix =
"";
3493 for (
const auto *A :
3494 Args.filtered(OPT_iprefix, OPT_iwithprefix, OPT_iwithprefixbefore)) {
3495 if (A->getOption().matches(OPT_iprefix))
3496 Prefix = A->getValue();
3497 else if (A->getOption().matches(OPT_iwithprefix))
3503 for (
const auto *A : Args.filtered(OPT_idirafter))
3505 for (
const auto *A : Args.filtered(OPT_iquote))
3508 for (
const auto *A : Args.filtered(OPT_isystem, OPT_iwithsysroot)) {
3509 if (A->getOption().matches(OPT_iwithsysroot)) {
3516 for (
const auto *A : Args.filtered(OPT_iframework))
3518 for (
const auto *A : Args.filtered(OPT_iframeworkwithsysroot))
3523 for (
const auto *A : Args.filtered(OPT_c_isystem))
3525 for (
const auto *A : Args.filtered(OPT_cxx_isystem))
3527 for (
const auto *A : Args.filtered(OPT_objc_isystem))
3529 for (
const auto *A : Args.filtered(OPT_objcxx_isystem))
3533 for (
const auto *A :
3534 Args.filtered(OPT_internal_isystem, OPT_internal_externc_isystem)) {
3536 if (A->getOption().matches(OPT_internal_externc_isystem))
3538 Opts.
AddPath(A->getValue(), Group,
false,
true);
3540 for (
const auto *A : Args.filtered(OPT_internal_iframework))
3544 for (
const auto *A :
3545 Args.filtered(OPT_system_header_prefix, OPT_no_system_header_prefix))
3547 A->getValue(), A->getOption().matches(OPT_system_header_prefix));
3549 for (
const auto *A : Args.filtered(OPT_ivfsoverlay, OPT_vfsoverlay))
3558 GenerateArg(Consumer, OPT_fapinotes_swift_version,
3567 if (
const Arg *A = Args.getLastArg(OPT_fapinotes_swift_version)) {
3569 diags.
Report(diag::err_drv_invalid_value)
3570 << A->getAsString(Args) << A->getValue();
3572 for (
const Arg *A : Args.filtered(OPT_iapinotes_modules))
3578 if (Opts.PointerAuthIntrinsics)
3580 if (Opts.PointerAuthCalls)
3582 if (Opts.PointerAuthReturns)
3584 if (Opts.PointerAuthIndirectGotos)
3585 GenerateArg(Consumer, OPT_fptrauth_indirect_gotos);
3586 if (Opts.PointerAuthAuthTraps)
3588 if (Opts.PointerAuthVTPtrAddressDiscrimination)
3589 GenerateArg(Consumer, OPT_fptrauth_vtable_pointer_address_discrimination);
3590 if (Opts.PointerAuthVTPtrTypeDiscrimination)
3591 GenerateArg(Consumer, OPT_fptrauth_vtable_pointer_type_discrimination);
3592 if (Opts.PointerAuthTypeInfoVTPtrDiscrimination)
3593 GenerateArg(Consumer, OPT_fptrauth_type_info_vtable_pointer_discrimination);
3594 if (Opts.PointerAuthFunctionTypeDiscrimination)
3595 GenerateArg(Consumer, OPT_fptrauth_function_pointer_type_discrimination);
3596 if (Opts.PointerAuthInitFini)
3598 if (Opts.PointerAuthInitFiniAddressDiscrimination)
3599 GenerateArg(Consumer, OPT_fptrauth_init_fini_address_discrimination);
3600 if (Opts.PointerAuthELFGOT)
3602 if (Opts.AArch64JumpTableHardening)
3603 GenerateArg(Consumer, OPT_faarch64_jump_table_hardening);
3604 if (Opts.PointerAuthObjcIsa)
3606 if (Opts.PointerAuthObjcInterfaceSel)
3607 GenerateArg(Consumer, OPT_fptrauth_objc_interface_sel);
3608 if (Opts.PointerAuthObjcClassROPointers)
3609 GenerateArg(Consumer, OPT_fptrauth_objc_class_ro);
3610 if (Opts.PointerAuthBlockDescriptorPointers)
3611 GenerateArg(Consumer, OPT_fptrauth_block_descriptor_pointers);
3616 Opts.PointerAuthIntrinsics = Args.hasArg(OPT_fptrauth_intrinsics);
3617 Opts.PointerAuthCalls = Args.hasArg(OPT_fptrauth_calls);
3618 Opts.PointerAuthReturns = Args.hasArg(OPT_fptrauth_returns);
3619 Opts.PointerAuthIndirectGotos = Args.hasArg(OPT_fptrauth_indirect_gotos);
3620 Opts.PointerAuthAuthTraps = Args.hasArg(OPT_fptrauth_auth_traps);
3621 Opts.PointerAuthVTPtrAddressDiscrimination =
3622 Args.hasArg(OPT_fptrauth_vtable_pointer_address_discrimination);
3623 Opts.PointerAuthVTPtrTypeDiscrimination =
3624 Args.hasArg(OPT_fptrauth_vtable_pointer_type_discrimination);
3625 Opts.PointerAuthTypeInfoVTPtrDiscrimination =
3626 Args.hasArg(OPT_fptrauth_type_info_vtable_pointer_discrimination);
3627 Opts.PointerAuthFunctionTypeDiscrimination =
3628 Args.hasArg(OPT_fptrauth_function_pointer_type_discrimination);
3629 Opts.PointerAuthInitFini = Args.hasArg(OPT_fptrauth_init_fini);
3630 Opts.PointerAuthInitFiniAddressDiscrimination =
3631 Args.hasArg(OPT_fptrauth_init_fini_address_discrimination);
3632 Opts.PointerAuthELFGOT = Args.hasArg(OPT_fptrauth_elf_got);
3633 Opts.AArch64JumpTableHardening =
3634 Args.hasArg(OPT_faarch64_jump_table_hardening);
3635 Opts.PointerAuthBlockDescriptorPointers =
3636 Args.hasArg(OPT_fptrauth_block_descriptor_pointers);
3637 Opts.PointerAuthObjcIsa = Args.hasArg(OPT_fptrauth_objc_isa);
3638 Opts.PointerAuthObjcClassROPointers = Args.hasArg(OPT_fptrauth_objc_class_ro);
3639 Opts.PointerAuthObjcInterfaceSel =
3640 Args.hasArg(OPT_fptrauth_objc_interface_sel);
3642 if (Opts.PointerAuthObjcInterfaceSel)
3643 Opts.PointerAuthObjcInterfaceSelKey =
3654 llvm_unreachable(
"should not parse language flags for this input");
3689 llvm_unreachable(
"unexpected input language");
3698 return "Objective-C";
3702 return "Objective-C++";
3706 return "C++ for OpenCL";
3725 llvm_unreachable(
"unknown input language");
3728void CompilerInvocationBase::GenerateLangArgs(
const LangOptions &Opts,
3730 const llvm::Triple &
T,
3735 if (Opts.ObjCAutoRefCount)
3737 if (Opts.PICLevel != 0)
3738 GenerateArg(Consumer, OPT_pic_level, Twine(Opts.PICLevel));
3742 GenerateArg(Consumer, OPT_fsanitize_EQ, Sanitizer);
3747 OptSpecifier StdOpt;
3749 case LangStandard::lang_opencl10:
3750 case LangStandard::lang_opencl11:
3751 case LangStandard::lang_opencl12:
3752 case LangStandard::lang_opencl20:
3753 case LangStandard::lang_opencl30:
3754 case LangStandard::lang_openclcpp10:
3755 case LangStandard::lang_openclcpp2021:
3756 StdOpt = OPT_cl_std_EQ;
3759 StdOpt = OPT_std_EQ;
3766 if (Opts.IncludeDefaultHeader)
3767 GenerateArg(Consumer, OPT_finclude_default_header);
3768 if (Opts.DeclareOpenCLBuiltins)
3769 GenerateArg(Consumer, OPT_fdeclare_opencl_builtins);
3773#define LANG_OPTION_WITH_MARSHALLING(...) \
3774 GENERATE_OPTION_WITH_MARSHALLING(Consumer, __VA_ARGS__)
3775#include "clang/Driver/Options.inc"
3776#undef LANG_OPTION_WITH_MARSHALLING
3787 else if (Opts.ObjCAutoRefCount == 1)
3790 if (Opts.ObjCWeakRuntime)
3791 GenerateArg(Consumer, OPT_fobjc_runtime_has_weak);
3796 if (Opts.ObjCSubscriptingLegacyRuntime)
3797 GenerateArg(Consumer, OPT_fobjc_subscripting_legacy_runtime);
3800 if (Opts.GNUCVersion != 0) {
3801 unsigned Major = Opts.GNUCVersion / 100 / 100;
3802 unsigned Minor = (Opts.GNUCVersion / 100) % 100;
3803 unsigned Patch = Opts.GNUCVersion % 100;
3805 Twine(Major) +
"." + Twine(Minor) +
"." + Twine(Patch));
3808 if (Opts.IgnoreXCOFFVisibility)
3809 GenerateArg(Consumer, OPT_mignore_xcoff_visibility);
3817 if (Opts.PointerOverflowDefined)
3820 if (Opts.MSCompatibilityVersion != 0) {
3821 unsigned Major = Opts.MSCompatibilityVersion / 10000000;
3822 unsigned Minor = (Opts.MSCompatibilityVersion / 100000) % 100;
3823 unsigned Subminor = Opts.MSCompatibilityVersion % 100000;
3824 GenerateArg(Consumer, OPT_fms_compatibility_version,
3825 Twine(Major) +
"." + Twine(Minor) +
"." + Twine(Subminor));
3828 if ((!Opts.GNUMode && !Opts.MSVCCompat && !Opts.CPlusPlus17 && !Opts.C23) ||
3830 if (!Opts.Trigraphs)
3837 if (
T.isOSzOS() && !Opts.ZOSExt)
3839 else if (Opts.ZOSExt)
3842 if (Opts.Blocks && !(Opts.OpenCL && Opts.OpenCLVersion == 200))
3845 if (Opts.ConvergentFunctions)
3848 GenerateArg(Consumer, OPT_fno_convergent_functions);
3850 if (Opts.NoBuiltin && !Opts.Freestanding)
3853 if (!Opts.NoBuiltin)
3857 if (Opts.LongDoubleSize == 128)
3859 else if (Opts.LongDoubleSize == 64)
3861 else if (Opts.LongDoubleSize == 80)
3868 if (Opts.OpenMP && !Opts.OpenMPSimd) {
3871 if (Opts.OpenMP != 51)
3872 GenerateArg(Consumer, OPT_fopenmp_version_EQ, Twine(Opts.OpenMP));
3874 if (!Opts.OpenMPUseTLS)
3877 if (Opts.OpenMPIsTargetDevice)
3878 GenerateArg(Consumer, OPT_fopenmp_is_target_device);
3880 if (Opts.OpenMPIRBuilder)
3881 GenerateArg(Consumer, OPT_fopenmp_enable_irbuilder);
3884 if (Opts.OpenMPSimd) {
3887 if (Opts.OpenMP != 51)
3888 GenerateArg(Consumer, OPT_fopenmp_version_EQ, Twine(Opts.OpenMP));
3891 if (Opts.OpenMPThreadSubscription)
3892 GenerateArg(Consumer, OPT_fopenmp_assume_threads_oversubscription);
3894 if (Opts.OpenMPTeamSubscription)
3895 GenerateArg(Consumer, OPT_fopenmp_assume_teams_oversubscription);
3897 if (Opts.OpenMPTargetDebug != 0)
3898 GenerateArg(Consumer, OPT_fopenmp_target_debug_EQ,
3899 Twine(Opts.OpenMPTargetDebug));
3901 if (Opts.OpenMPCUDANumSMs != 0)
3902 GenerateArg(Consumer, OPT_fopenmp_cuda_number_of_sm_EQ,
3903 Twine(Opts.OpenMPCUDANumSMs));
3905 if (Opts.OpenMPCUDABlocksPerSM != 0)
3906 GenerateArg(Consumer, OPT_fopenmp_cuda_blocks_per_sm_EQ,
3907 Twine(Opts.OpenMPCUDABlocksPerSM));
3909 if (Opts.OpenMPCUDAReductionBufNum != 1024)
3910 GenerateArg(Consumer, OPT_fopenmp_cuda_teams_reduction_recs_num_EQ,
3911 Twine(Opts.OpenMPCUDAReductionBufNum));
3914 std::string Targets;
3915 llvm::raw_string_ostream OS(Targets);
3918 [&OS](
const llvm::Triple &
T) { OS << T.str(); },
",");
3919 GenerateArg(Consumer, OPT_offload_targets_EQ, Targets);
3922 if (Opts.OpenMPCUDAMode)
3938 GenerateArg(Consumer, OPT_ffp_contract,
"fast-honor-pragmas");
3941 GenerateArg(Consumer, OPT_fsanitize_EQ, Sanitizer);
3945 GenerateArg(Consumer, OPT_fsanitize_ignorelist_EQ, F);
3947 switch (Opts.getClangABICompat()) {
3948#define ABI_VER_MAJOR_MINOR(Major, Minor) \
3949 case LangOptions::ClangABI::Ver##Major##_##Minor: \
3950 GenerateArg(Consumer, OPT_fclang_abi_compat_EQ, #Major "." #Minor); \
3952#define ABI_VER_MAJOR(Major) \
3953 case LangOptions::ClangABI::Ver##Major: \
3954 GenerateArg(Consumer, OPT_fclang_abi_compat_EQ, #Major ".0"); \
3956#define ABI_VER_LATEST(Latest) \
3957 case LangOptions::ClangABI::Latest: \
3959#include "clang/Basic/ABIVersions.def"
3962 if (Opts.getSignReturnAddressScope() ==
3964 GenerateArg(Consumer, OPT_msign_return_address_EQ,
"all");
3965 else if (Opts.getSignReturnAddressScope() ==
3967 GenerateArg(Consumer, OPT_msign_return_address_EQ,
"non-leaf");
3969 if (Opts.getSignReturnAddressKey() ==
3971 GenerateArg(Consumer, OPT_msign_return_address_key_EQ,
"b_key");
3977 if (Opts.RelativeCXXABIVTables)
3978 GenerateArg(Consumer, OPT_fexperimental_relative_cxx_abi_vtables);
3980 GenerateArg(Consumer, OPT_fno_experimental_relative_cxx_abi_vtables);
3988 GenerateArg(Consumer, OPT_fmacro_prefix_map_EQ, MP.first +
"=" + MP.second);
3994bool CompilerInvocation::ParseLangArgs(
LangOptions &Opts, ArgList &Args,
3996 std::vector<std::string> &Includes,
4006 if (Args.hasArg(OPT_fobjc_arc))
4007 Opts.ObjCAutoRefCount = 1;
4011 Opts.PIE = Args.hasArg(OPT_pic_is_pie);
4023 if (
const Arg *A = Args.getLastArg(OPT_std_EQ)) {
4026 Diags.
Report(diag::err_drv_invalid_value)
4027 << A->getAsString(Args) << A->getValue();
4029 for (
unsigned KindValue = 0;
4035 auto Diag = Diags.
Report(diag::note_drv_use_standard);
4036 Diag <<
Std.getName() <<
Std.getDescription();
4037 unsigned NumAliases = 0;
4038#define LANGSTANDARD(id, name, lang, desc, features)
4039#define LANGSTANDARD_ALIAS(id, alias) \
4040 if (KindValue == LangStandard::lang_##id) ++NumAliases;
4041#define LANGSTANDARD_ALIAS_DEPR(id, alias)
4042#include "clang/Basic/LangStandards.def"
4044#define LANGSTANDARD(id, name, lang, desc, features)
4045#define LANGSTANDARD_ALIAS(id, alias) \
4046 if (KindValue == LangStandard::lang_##id) Diag << alias;
4047#define LANGSTANDARD_ALIAS_DEPR(id, alias)
4048#include "clang/Basic/LangStandards.def"
4056 Diags.
Report(diag::err_drv_argument_not_allowed_with)
4064 if (
const Arg *A = Args.getLastArg(OPT_cl_std_EQ)) {
4066 = llvm::StringSwitch<LangStandard::Kind>(A->getValue())
4067 .Cases(
"cl",
"CL", LangStandard::lang_opencl10)
4068 .Cases(
"cl1.0",
"CL1.0", LangStandard::lang_opencl10)
4069 .Cases(
"cl1.1",
"CL1.1", LangStandard::lang_opencl11)
4070 .Cases(
"cl1.2",
"CL1.2", LangStandard::lang_opencl12)
4071 .Cases(
"cl2.0",
"CL2.0", LangStandard::lang_opencl20)
4072 .Cases(
"cl3.0",
"CL3.0", LangStandard::lang_opencl30)
4073 .Cases(
"clc++",
"CLC++", LangStandard::lang_openclcpp10)
4074 .Cases(
"clc++1.0",
"CLC++1.0", LangStandard::lang_openclcpp10)
4075 .Cases(
"clc++2021",
"CLC++2021", LangStandard::lang_openclcpp2021)
4079 Diags.
Report(diag::err_drv_invalid_value)
4080 << A->getAsString(Args) << A->getValue();
4083 LangStd = OpenCLLangStd;
4087 Opts.IncludeDefaultHeader = Args.hasArg(OPT_finclude_default_header);
4088 Opts.DeclareOpenCLBuiltins = Args.hasArg(OPT_fdeclare_opencl_builtins);
4096#define LANG_OPTION_WITH_MARSHALLING(...) \
4097 PARSE_OPTION_WITH_MARSHALLING(Args, Diags, __VA_ARGS__)
4098#include "clang/Driver/Options.inc"
4099#undef LANG_OPTION_WITH_MARSHALLING
4101 if (
const Arg *A = Args.getLastArg(OPT_fcf_protection_EQ)) {
4102 StringRef Name = A->getValue();
4103 if (Name ==
"full") {
4104 Opts.CFProtectionBranch = 1;
4105 Opts.CFProtectionReturn = 1;
4106 }
else if (Name ==
"branch") {
4107 Opts.CFProtectionBranch = 1;
4108 }
else if (Name ==
"return") {
4109 Opts.CFProtectionReturn = 1;
4113 if (Opts.CFProtectionBranch) {
4114 if (
const Arg *A = Args.getLastArg(OPT_mcf_branch_label_scheme_EQ)) {
4116 llvm::StringSwitch<CFBranchLabelSchemeKind>(A->getValue())
4117#define CF_BRANCH_LABEL_SCHEME(Kind, FlagVal) \
4118 .Case(#FlagVal, CFBranchLabelSchemeKind::Kind)
4119#include "clang/Basic/CFProtectionOptions.def"
4121 Opts.setCFBranchLabelScheme(Scheme);
4125 if ((Args.hasArg(OPT_fsycl_is_device) || Args.hasArg(OPT_fsycl_is_host)) &&
4126 !Args.hasArg(OPT_sycl_std_EQ)) {
4136 if (Arg *arg = Args.getLastArg(OPT_fobjc_runtime_EQ)) {
4137 StringRef value =
arg->getValue();
4139 Diags.
Report(diag::err_drv_unknown_objc_runtime) << value;
4142 if (Args.hasArg(OPT_fobjc_gc_only))
4144 else if (Args.hasArg(OPT_fobjc_gc))
4146 else if (Args.hasArg(OPT_fobjc_arc)) {
4147 Opts.ObjCAutoRefCount = 1;
4149 Diags.
Report(diag::err_arc_unsupported_on_runtime);
4156 if (Args.hasArg(OPT_fobjc_runtime_has_weak))
4157 Opts.ObjCWeakRuntime = 1;
4163 if (
auto weakArg = Args.getLastArg(OPT_fobjc_weak, OPT_fno_objc_weak)) {
4164 if (!weakArg->getOption().matches(OPT_fobjc_weak)) {
4165 assert(!Opts.ObjCWeak);
4167 Diags.
Report(diag::err_objc_weak_with_gc);
4168 }
else if (!Opts.ObjCWeakRuntime) {
4169 Diags.
Report(diag::err_objc_weak_unsupported);
4173 }
else if (Opts.ObjCAutoRefCount) {
4174 Opts.ObjCWeak = Opts.ObjCWeakRuntime;
4177 if (Args.hasArg(OPT_fobjc_subscripting_legacy_runtime))
4178 Opts.ObjCSubscriptingLegacyRuntime =
4182 if (Arg *A = Args.getLastArg(options::OPT_fgnuc_version_EQ)) {
4185 VersionTuple GNUCVer;
4186 bool Invalid = GNUCVer.tryParse(A->getValue());
4187 unsigned Major = GNUCVer.getMajor();
4188 unsigned Minor = GNUCVer.getMinor().value_or(0);
4189 unsigned Patch = GNUCVer.getSubminor().value_or(0);
4190 if (
Invalid || GNUCVer.getBuild() || Minor >= 100 || Patch >= 100) {
4191 Diags.
Report(diag::err_drv_invalid_value)
4192 << A->getAsString(Args) << A->getValue();
4194 Opts.GNUCVersion = Major * 100 * 100 + Minor * 100 + Patch;
4197 if (
T.isOSAIX() && (Args.hasArg(OPT_mignore_xcoff_visibility)))
4198 Opts.IgnoreXCOFFVisibility = 1;
4200 if (Args.hasArg(OPT_ftrapv)) {
4204 std::string(Args.getLastArgValue(OPT_ftrapv_handler));
4206 else if (Args.hasArg(OPT_fwrapv))
4208 if (Args.hasArg(OPT_fwrapv_pointer))
4209 Opts.PointerOverflowDefined =
true;
4211 Opts.MSCompatibilityVersion = 0;
4212 if (
const Arg *A = Args.getLastArg(OPT_fms_compatibility_version)) {
4214 if (VT.tryParse(A->getValue()))
4215 Diags.
Report(diag::err_drv_invalid_value) << A->getAsString(Args)
4217 Opts.MSCompatibilityVersion = VT.getMajor() * 10000000 +
4218 VT.getMinor().value_or(0) * 100000 +
4219 VT.getSubminor().value_or(0);
4227 (!Opts.GNUMode && !Opts.MSVCCompat && !Opts.CPlusPlus17 && !Opts.C23) ||
4230 Args.hasFlag(OPT_ftrigraphs, OPT_fno_trigraphs, Opts.Trigraphs);
4233 Args.hasFlag(OPT_fzos_extensions, OPT_fno_zos_extensions,
T.isOSzOS());
4235 Opts.Blocks = Args.hasArg(OPT_fblocks) || (Opts.OpenCL
4236 && Opts.OpenCLVersion == 200);
4238 bool HasConvergentOperations = Opts.
isTargetDevice() || Opts.OpenCL ||
4239 Opts.HLSL ||
T.isAMDGPU() ||
T.isNVPTX();
4240 Opts.ConvergentFunctions =
4241 Args.hasFlag(OPT_fconvergent_functions, OPT_fno_convergent_functions,
4242 HasConvergentOperations);
4244 Opts.NoBuiltin = Args.hasArg(OPT_fno_builtin) || Opts.Freestanding;
4245 if (!Opts.NoBuiltin)
4247 if (Arg *A = Args.getLastArg(options::OPT_LongDouble_Group)) {
4248 if (A->getOption().matches(options::OPT_mlong_double_64))
4249 Opts.LongDoubleSize = 64;
4250 else if (A->getOption().matches(options::OPT_mlong_double_80))
4251 Opts.LongDoubleSize = 80;
4252 else if (A->getOption().matches(options::OPT_mlong_double_128))
4253 Opts.LongDoubleSize = 128;
4255 Opts.LongDoubleSize = 0;
4257 if (Opts.FastRelaxedMath || Opts.CLUnsafeMath)
4263 if (Arg *A = Args.getLastArg(OPT_mrtd)) {
4265 Diags.
Report(diag::err_drv_argument_not_allowed_with)
4266 << A->getSpelling() <<
"-fdefault-calling-conv";
4268 switch (
T.getArch()) {
4269 case llvm::Triple::x86:
4272 case llvm::Triple::m68k:
4276 Diags.
Report(diag::err_drv_argument_not_allowed_with)
4277 << A->getSpelling() <<
T.getTriple();
4283 Opts.OpenMP = Args.hasArg(OPT_fopenmp) ? 51 : 0;
4285 bool IsSimdSpecified =
4286 Args.hasFlag(options::OPT_fopenmp_simd, options::OPT_fno_openmp_simd,
4288 Opts.OpenMPSimd = !Opts.OpenMP && IsSimdSpecified;
4290 Opts.OpenMP && !Args.hasArg(options::OPT_fnoopenmp_use_tls);
4291 Opts.OpenMPIsTargetDevice =
4292 Opts.OpenMP && Args.hasArg(options::OPT_fopenmp_is_target_device);
4293 Opts.OpenMPIRBuilder =
4294 Opts.OpenMP && Args.hasArg(options::OPT_fopenmp_enable_irbuilder);
4295 bool IsTargetSpecified =
4296 Opts.OpenMPIsTargetDevice || Args.hasArg(options::OPT_offload_targets_EQ);
4298 if (Opts.OpenMP || Opts.OpenMPSimd) {
4300 Args, OPT_fopenmp_version_EQ,
4301 (IsSimdSpecified || IsTargetSpecified) ? 51 : Opts.OpenMP, Diags))
4302 Opts.OpenMP = Version;
4305 if (!Opts.OpenMPIsTargetDevice) {
4306 switch (
T.getArch()) {
4310 case llvm::Triple::nvptx:
4311 case llvm::Triple::nvptx64:
4312 Diags.
Report(diag::err_drv_omp_host_target_not_supported) <<
T.str();
4320 if ((Opts.OpenMPIsTargetDevice && (
T.isNVPTX() ||
T.isAMDGCN())) ||
4321 Opts.OpenCLCPlusPlus) {
4323 Opts.Exceptions = 0;
4324 Opts.CXXExceptions = 0;
4326 if (Opts.OpenMPIsTargetDevice &&
T.isNVPTX()) {
4327 Opts.OpenMPCUDANumSMs =
4329 Opts.OpenMPCUDANumSMs, Diags);
4330 Opts.OpenMPCUDABlocksPerSM =
4332 Opts.OpenMPCUDABlocksPerSM, Diags);
4334 Args, options::OPT_fopenmp_cuda_teams_reduction_recs_num_EQ,
4335 Opts.OpenMPCUDAReductionBufNum, Diags);
4340 if (Opts.OpenMPIsTargetDevice && (Args.hasArg(OPT_fopenmp_target_debug) ||
4341 Args.hasArg(OPT_fopenmp_target_debug_EQ))) {
4343 Args, OPT_fopenmp_target_debug_EQ, Opts.OpenMPTargetDebug, Diags);
4344 if (!Opts.OpenMPTargetDebug && Args.hasArg(OPT_fopenmp_target_debug))
4345 Opts.OpenMPTargetDebug = 1;
4348 if (Opts.OpenMPIsTargetDevice) {
4349 if (Args.hasArg(OPT_fopenmp_assume_teams_oversubscription))
4350 Opts.OpenMPTeamSubscription =
true;
4351 if (Args.hasArg(OPT_fopenmp_assume_threads_oversubscription))
4352 Opts.OpenMPThreadSubscription =
true;
4356 if (Arg *A = Args.getLastArg(options::OPT_offload_targets_EQ)) {
4357 enum ArchPtrSize { Arch16Bit, Arch32Bit, Arch64Bit };
4358 auto getArchPtrSize = [](
const llvm::Triple &
T) {
4359 if (
T.isArch16Bit())
4361 if (
T.isArch32Bit())
4363 assert(
T.isArch64Bit() &&
"Expected 64-bit architecture");
4367 for (
unsigned i = 0; i < A->getNumValues(); ++i) {
4368 llvm::Triple TT(A->getValue(i));
4370 if (TT.getArch() == llvm::Triple::UnknownArch ||
4371 !(TT.getArch() == llvm::Triple::aarch64 || TT.isPPC() ||
4372 TT.getArch() == llvm::Triple::spirv64 ||
4373 TT.getArch() == llvm::Triple::systemz ||
4374 TT.getArch() == llvm::Triple::loongarch64 ||
4375 TT.getArch() == llvm::Triple::nvptx ||
4376 TT.getArch() == llvm::Triple::nvptx64 || TT.isAMDGCN() ||
4377 TT.getArch() == llvm::Triple::x86 ||
4378 TT.getArch() == llvm::Triple::x86_64))
4379 Diags.
Report(diag::err_drv_invalid_omp_target) << A->getValue(i);
4380 else if (getArchPtrSize(
T) != getArchPtrSize(TT))
4381 Diags.
Report(diag::err_drv_incompatible_omp_arch)
4382 << A->getValue(i) <<
T.str();
4389 Opts.OpenMPCUDAMode = Opts.OpenMPIsTargetDevice &&
4390 (
T.isNVPTX() ||
T.isAMDGCN()) &&
4391 Args.hasArg(options::OPT_fopenmp_cuda_mode);
4394 if (Args.hasArg(options::OPT_fopenacc))
4395 Opts.OpenACC =
true;
4397 if (Arg *A = Args.getLastArg(OPT_ffp_contract)) {
4398 StringRef Val = A->getValue();
4401 else if (Val ==
"on")
4403 else if (Val ==
"off")
4405 else if (Val ==
"fast-honor-pragmas")
4408 Diags.
Report(diag::err_drv_invalid_value) << A->getAsString(Args) << Val;
4412 Args.getLastArg(OPT_fsanitize_undefined_ignore_overflow_pattern_EQ)) {
4413 for (
int i = 0, n = A->getNumValues(); i != n; ++i) {
4415 llvm::StringSwitch<unsigned>(A->getValue(i))
4418 .Case(
"add-unsigned-overflow-test",
4420 .Case(
"add-signed-overflow-test",
4423 .Case(
"unsigned-post-decr-while",
4432 Opts.
NoSanitizeFiles = Args.getAllArgValues(OPT_fsanitize_ignorelist_EQ);
4433 std::vector<std::string> systemIgnorelists =
4434 Args.getAllArgValues(OPT_fsanitize_system_ignorelist_EQ);
4436 systemIgnorelists.begin(),
4437 systemIgnorelists.end());
4439 if (Arg *A = Args.getLastArg(OPT_fclang_abi_compat_EQ)) {
4440 Opts.setClangABICompat(LangOptions::ClangABI::Latest);
4442 StringRef Ver = A->getValue();
4443 std::pair<StringRef, StringRef> VerParts = Ver.split(
'.');
4444 int Major, Minor = 0;
4448 if (!VerParts.first.starts_with(
"0") &&
4449 !VerParts.first.getAsInteger(10, Major) && 3 <= Major &&
4450 Major <= MAX_CLANG_ABI_COMPAT_VERSION &&
4452 ? VerParts.second.size() == 1 &&
4453 !VerParts.second.getAsInteger(10, Minor)
4454 : VerParts.first.size() == Ver.size() || VerParts.second ==
"0")) {
4456#define ABI_VER_MAJOR_MINOR(Major_, Minor_) \
4457 if (std::tuple(Major, Minor) <= std::tuple(Major_, Minor_)) \
4458 Opts.setClangABICompat(LangOptions::ClangABI::Ver##Major_##_##Minor_); \
4460#define ABI_VER_MAJOR(Major_) \
4461 if (Major <= Major_) \
4462 Opts.setClangABICompat(LangOptions::ClangABI::Ver##Major_); \
4464#define ABI_VER_LATEST(Latest) \
4467#include "clang/Basic/ABIVersions.def"
4468 }
else if (Ver !=
"latest") {
4469 Diags.
Report(diag::err_drv_invalid_value)
4470 << A->getAsString(Args) << A->getValue();
4474 if (Arg *A = Args.getLastArg(OPT_msign_return_address_EQ)) {
4475 StringRef SignScope = A->getValue();
4477 if (SignScope.equals_insensitive(
"none"))
4478 Opts.setSignReturnAddressScope(
4480 else if (SignScope.equals_insensitive(
"all"))
4481 Opts.setSignReturnAddressScope(
4483 else if (SignScope.equals_insensitive(
"non-leaf"))
4484 Opts.setSignReturnAddressScope(
4487 Diags.
Report(diag::err_drv_invalid_value)
4488 << A->getAsString(Args) << SignScope;
4490 if (Arg *A = Args.getLastArg(OPT_msign_return_address_key_EQ)) {
4491 StringRef SignKey = A->getValue();
4492 if (!SignScope.empty() && !SignKey.empty()) {
4493 if (SignKey ==
"a_key")
4494 Opts.setSignReturnAddressKey(
4496 else if (SignKey ==
"b_key")
4497 Opts.setSignReturnAddressKey(
4500 Diags.
Report(diag::err_drv_invalid_value)
4501 << A->getAsString(Args) << SignKey;
4507 StringRef
CXXABI = Args.getLastArgValue(OPT_fcxx_abi_EQ);
4514 Diags.
Report(diag::err_unsupported_cxx_abi) <<
CXXABI <<
T.str();
4520 Opts.RelativeCXXABIVTables =
4521 Args.hasFlag(options::OPT_fexperimental_relative_cxx_abi_vtables,
4522 options::OPT_fno_experimental_relative_cxx_abi_vtables,
4526 bool HasRTTI = !Args.hasArg(options::OPT_fno_rtti);
4527 Opts.OmitVTableRTTI =
4528 Args.hasFlag(options::OPT_fexperimental_omit_vtable_rtti,
4529 options::OPT_fno_experimental_omit_vtable_rtti,
false);
4530 if (Opts.OmitVTableRTTI && HasRTTI)
4531 Diags.
Report(diag::err_drv_using_omit_rtti_component_without_no_rtti);
4533 for (
const auto &A : Args.getAllArgValues(OPT_fmacro_prefix_map_EQ)) {
4534 auto Split = StringRef(A).split(
'=');
4536 {std::string(
Split.first), std::string(
Split.second)});
4540 !Args.getLastArg(OPT_fno_file_reproducible) &&
4541 (Args.getLastArg(OPT_ffile_compilation_dir_EQ) ||
4542 Args.getLastArg(OPT_fmacro_prefix_map_EQ) ||
4543 Args.getLastArg(OPT_ffile_reproducible));
4546 if (Arg *A = Args.getLastArg(options::OPT_mvscale_min_EQ)) {
4548 if (StringRef(A->getValue()).getAsInteger(10, VScaleMin) || VScaleMin == 0)
4549 Diags.
Report(diag::err_cc1_unbounded_vscale_min);
4551 if (Arg *A = Args.getLastArg(options::OPT_mvscale_streaming_min_EQ)) {
4553 if (StringRef(A->getValue()).getAsInteger(10, VScaleMin) || VScaleMin == 0)
4554 Diags.
Report(diag::err_cc1_unbounded_vscale_min);
4557 if (
const Arg *A = Args.getLastArg(OPT_frandomize_layout_seed_file_EQ)) {
4558 std::ifstream SeedFile(A->getValue(0));
4560 if (!SeedFile.is_open())
4561 Diags.
Report(diag::err_drv_cannot_open_randomize_layout_seed_file)
4567 if (
const Arg *A = Args.getLastArg(OPT_frandomize_layout_seed_EQ))
4574 if (
T.isDXIL() ||
T.isSPIRVLogical()) {
4576 enum { OS, Environment };
4578 int ExpectedOS =
T.isSPIRVLogical() ? VulkanEnv : ShaderModel;
4580 if (
T.getOSName().empty()) {
4581 Diags.
Report(diag::err_drv_hlsl_bad_shader_required_in_target)
4582 << ExpectedOS << OS <<
T.str();
4583 }
else if (
T.getEnvironmentName().empty()) {
4584 Diags.
Report(diag::err_drv_hlsl_bad_shader_required_in_target)
4586 }
else if (!
T.isShaderStageEnvironment()) {
4587 Diags.
Report(diag::err_drv_hlsl_bad_shader_unsupported)
4592 if (!
T.isShaderModelOS() ||
T.getOSVersion() == VersionTuple(0)) {
4593 Diags.
Report(diag::err_drv_hlsl_bad_shader_unsupported)
4594 << ShaderModel <<
T.getOSName() <<
T.str();
4599 if (Args.getLastArg(OPT_fnative_half_type)) {
4602 if (!(Opts.
LangStd >= LangStandard::lang_hlsl2018 &&
4603 T.getOSVersion() >= VersionTuple(6, 2)))
4604 Diags.
Report(diag::err_drv_hlsl_16bit_types_unsupported)
4605 <<
"-enable-16bit-types" <<
true <<
Std.getName()
4606 <<
T.getOSVersion().getAsString();
4608 }
else if (
T.isSPIRVLogical()) {
4609 if (!
T.isVulkanOS() ||
T.getVulkanVersion() == VersionTuple(0)) {
4610 Diags.
Report(diag::err_drv_hlsl_bad_shader_unsupported)
4611 << VulkanEnv <<
T.getOSName() <<
T.str();
4613 if (Args.getLastArg(OPT_fnative_half_type)) {
4616 if (!(Opts.
LangStd >= LangStandard::lang_hlsl2018))
4617 Diags.
Report(diag::err_drv_hlsl_16bit_types_unsupported)
4618 <<
"-fnative-half-type" <<
false <<
Std.getName();
4621 llvm_unreachable(
"expected DXIL or SPIR-V target");
4624 Diags.
Report(diag::err_drv_hlsl_unsupported_target) <<
T.str();
4626 if (Opts.
LangStd < LangStandard::lang_hlsl202x) {
4631 Diags.
Report(diag::warn_hlsl_langstd_minimal)
4682 llvm_unreachable(
"invalid frontend action");
4727 llvm_unreachable(
"invalid frontend action");
4737#define PREPROCESSOR_OPTION_WITH_MARSHALLING(...) \
4738 GENERATE_OPTION_WITH_MARSHALLING(Consumer, __VA_ARGS__)
4739#include "clang/Driver/Options.inc"
4740#undef PREPROCESSOR_OPTION_WITH_MARSHALLING
4743 GenerateArg(Consumer, OPT_pch_through_hdrstop_use);
4746 GenerateArg(Consumer, OPT_error_on_deserialized_pch_decl,
D);
4753 for (
const auto &M : Opts.
Macros) {
4756 if (M.first ==
"__CET__=1" && !M.second &&
4757 !CodeGenOpts.CFProtectionReturn && CodeGenOpts.CFProtectionBranch)
4759 if (M.first ==
"__CET__=2" && !M.second && CodeGenOpts.CFProtectionReturn &&
4760 !CodeGenOpts.CFProtectionBranch)
4762 if (M.first ==
"__CET__=3" && !M.second && CodeGenOpts.CFProtectionReturn &&
4763 CodeGenOpts.CFProtectionBranch)
4766 GenerateArg(Consumer, M.second ? OPT_U : OPT_D, M.first);
4769 for (
const auto &I : Opts.
Includes) {
4772 if (LangOpts.OpenCL && LangOpts.IncludeDefaultHeader &&
4773 ((LangOpts.DeclareOpenCLBuiltins && I ==
"opencl-c-base.h") ||
4778 if (LangOpts.HLSL && I ==
"hlsl.h")
4788 GenerateArg(Consumer, OPT_remap_file, RF.first +
";" + RF.second);
4794 GenerateArg(Consumer, OPT_fdefine_target_os_macros);
4797 GenerateArg(Consumer, OPT_embed_dir_EQ, EmbedEntry);
4811#define PREPROCESSOR_OPTION_WITH_MARSHALLING(...) \
4812 PARSE_OPTION_WITH_MARSHALLING(Args, Diags, __VA_ARGS__)
4813#include "clang/Driver/Options.inc"
4814#undef PREPROCESSOR_OPTION_WITH_MARSHALLING
4816 Opts.
PCHWithHdrStop = Args.hasArg(OPT_pch_through_hdrstop_create) ||
4817 Args.hasArg(OPT_pch_through_hdrstop_use);
4819 for (
const auto *A : Args.filtered(OPT_error_on_deserialized_pch_decl))
4822 if (
const Arg *A = Args.getLastArg(OPT_preamble_bytes_EQ)) {
4823 StringRef
Value(A->getValue());
4824 size_t Comma =
Value.find(
',');
4826 unsigned EndOfLine = 0;
4828 if (Comma == StringRef::npos ||
4829 Value.substr(0, Comma).getAsInteger(10, Bytes) ||
4830 Value.substr(Comma + 1).getAsInteger(10, EndOfLine))
4831 Diags.
Report(diag::err_drv_preamble_format);
4839 for (
const auto *A : Args.filtered(OPT_D, OPT_U)) {
4840 if (A->getOption().matches(OPT_D))
4847 for (
const auto *A : Args.filtered(OPT_include))
4848 Opts.
Includes.emplace_back(A->getValue());
4850 for (
const auto *A : Args.filtered(OPT_chain_include))
4853 for (
const auto *A : Args.filtered(OPT_remap_file)) {
4854 std::pair<StringRef, StringRef> Split = StringRef(A->getValue()).split(
';');
4856 if (Split.second.empty()) {
4857 Diags.
Report(diag::err_drv_invalid_remap_file) << A->getAsString(Args);
4864 if (
const Arg *A = Args.getLastArg(OPT_source_date_epoch)) {
4865 StringRef Epoch = A->getValue();
4869 const uint64_t MaxTimestamp =
4870 std::min<uint64_t>(std::numeric_limits<time_t>::max(), 253402300799);
4872 if (Epoch.getAsInteger(10,
V) ||
V > MaxTimestamp) {
4873 Diags.
Report(diag::err_fe_invalid_source_date_epoch)
4874 << Epoch << MaxTimestamp;
4880 for (
const auto *A : Args.filtered(OPT_embed_dir_EQ)) {
4881 StringRef Val = A->getValue();
4892 Args.hasFlag(OPT_fdefine_target_os_macros,
4904#define PREPROCESSOR_OUTPUT_OPTION_WITH_MARSHALLING(...) \
4905 GENERATE_OPTION_WITH_MARSHALLING(Consumer, __VA_ARGS__)
4906#include "clang/Driver/Options.inc"
4907#undef PREPROCESSOR_OUTPUT_OPTION_WITH_MARSHALLING
4925#define PREPROCESSOR_OUTPUT_OPTION_WITH_MARSHALLING(...) \
4926 PARSE_OPTION_WITH_MARSHALLING(Args, Diags, __VA_ARGS__)
4927#include "clang/Driver/Options.inc"
4928#undef PREPROCESSOR_OUTPUT_OPTION_WITH_MARSHALLING
4931 Opts.
ShowMacros = Args.hasArg(OPT_dM) || Args.hasArg(OPT_dD);
4940#define TARGET_OPTION_WITH_MARSHALLING(...) \
4941 GENERATE_OPTION_WITH_MARSHALLING(Consumer, __VA_ARGS__)
4942#include "clang/Driver/Options.inc"
4943#undef TARGET_OPTION_WITH_MARSHALLING
4949 GenerateArg(Consumer, OPT_darwin_target_variant_sdk_version_EQ,
4959#define TARGET_OPTION_WITH_MARSHALLING(...) \
4960 PARSE_OPTION_WITH_MARSHALLING(Args, Diags, __VA_ARGS__)
4961#include "clang/Driver/Options.inc"
4962#undef TARGET_OPTION_WITH_MARSHALLING
4964 if (Arg *A = Args.getLastArg(options::OPT_target_sdk_version_EQ)) {
4965 llvm::VersionTuple Version;
4966 if (Version.tryParse(A->getValue()))
4967 Diags.
Report(diag::err_drv_invalid_value)
4968 << A->getAsString(Args) << A->getValue();
4973 Args.getLastArg(options::OPT_darwin_target_variant_sdk_version_EQ)) {
4974 llvm::VersionTuple Version;
4975 if (Version.tryParse(A->getValue()))
4976 Diags.
Report(diag::err_drv_invalid_value)
4977 << A->getAsString(Args) << A->getValue();
4985bool CompilerInvocation::CreateFromArgsImpl(
4993 unsigned MissingArgIndex, MissingArgCount;
4994 InputArgList Args = Opts.ParseArgs(CommandLineArgs, MissingArgIndex,
4995 MissingArgCount, VisibilityMask);
4999 if (MissingArgCount)
5000 Diags.
Report(diag::err_drv_missing_argument)
5001 << Args.getArgString(MissingArgIndex) << MissingArgCount;
5004 for (
const auto *A : Args.filtered(OPT_UNKNOWN)) {
5005 auto ArgString = A->getAsString(Args);
5006 std::string Nearest;
5007 if (Opts.findNearest(ArgString, Nearest, VisibilityMask) > 1)
5008 Diags.
Report(diag::err_drv_unknown_argument) << ArgString;
5010 Diags.
Report(diag::err_drv_unknown_argument_with_suggestion)
5011 << ArgString << Nearest;
5059 Diags.
Report(diag::warn_drv_openacc_without_cir);
5072 !
LangOpts.Sanitize.has(SanitizerKind::Address) &&
5073 !
LangOpts.Sanitize.has(SanitizerKind::KernelAddress) &&
5074 !
LangOpts.Sanitize.has(SanitizerKind::Memory) &&
5075 !
LangOpts.Sanitize.has(SanitizerKind::KernelMemory);
5088 Diags.
Report(diag::err_fe_dependency_file_requires_MT);
5094 Diags.
Report(diag::warn_drv_fine_grained_bitfield_accesses_ignored);
5108 Diags, llvm::vfs::getRealFileSystem());
5122 const char *Argv0) {
5128 return CreateFromArgsImpl(Invocation, CommandLineArgs, Diags, Argv0);
5132 Args.push_back(
"-cc1");
5135 Invocation, DummyInvocation, CommandLineArgs, Diags, Argv0);
5140 llvm::HashBuilder<llvm::MD5, llvm::endianness::native> HBuilder;
5155#define LANGOPT(Name, Bits, Default, Compatibility, Description) \
5156 if constexpr (CK::Compatibility != CK::Benign) \
5157 HBuilder.add(LangOpts->Name);
5158#define ENUM_LANGOPT(Name, Type, Bits, Default, Compatibility, Description) \
5159 if constexpr (CK::Compatibility != CK::Benign) \
5160 HBuilder.add(static_cast<unsigned>(LangOpts->get##Name()));
5161#include "clang/Basic/LangOptions.def"
5166 HBuilder.addRange(
getLangOpts().CommentOpts.BlockCommandNames);
5183 StringRef MacroDef =
Macro.first;
5185 llvm::CachedHashString(MacroDef.split(
'=').first)))
5189 HBuilder.add(
Macro);
5205#define DIAGOPT(Name, Bits, Default) HBuilder.add(diagOpts.Name);
5206#define ENUM_DIAGOPT(Name, Type, Bits, Default) \
5207 HBuilder.add(diagOpts.get##Name());
5208#include "clang/Basic/DiagnosticOptions.def"
5218 ext->hashExtension(HBuilder);
5225 HBuilder.add(*Minor);
5226 if (
auto Subminor =
APINotesOpts.SwiftVersion.getSubminor())
5227 HBuilder.add(*Subminor);
5229 HBuilder.add(*Build);
5235#define CODEGENOPT(Name, Bits, Default, Compatibility) \
5236 if constexpr (CK::Compatibility != CK::Benign) \
5237 HBuilder.add(CodeGenOpts->Name);
5238#define ENUM_CODEGENOPT(Name, Type, Bits, Default, Compatibility) \
5239 if constexpr (CK::Compatibility != CK::Benign) \
5240 HBuilder.add(static_cast<unsigned>(CodeGenOpts->get##Name()));
5241#define DEBUGOPT(Name, Bits, Default, Compatibility)
5242#define VALUE_DEBUGOPT(Name, Bits, Default, Compatibility)
5243#define ENUM_DEBUGOPT(Name, Type, Bits, Default, Compatibility)
5244#include "clang/Basic/CodeGenOptions.def"
5256#define DEBUGOPT(Name, Bits, Default, Compatibility) \
5257 if constexpr (CK::Compatibility != CK::Benign) \
5258 HBuilder.add(CodeGenOpts->Name);
5259#define VALUE_DEBUGOPT(Name, Bits, Default, Compatibility) \
5260 if constexpr (CK::Compatibility != CK::Benign) \
5261 HBuilder.add(CodeGenOpts->Name);
5262#define ENUM_DEBUGOPT(Name, Type, Bits, Default, Compatibility) \
5263 if constexpr (CK::Compatibility != CK::Benign) \
5264 HBuilder.add(static_cast<unsigned>(CodeGenOpts->get##Name()));
5265#include "clang/Basic/DebugOptions.def"
5272 if (!SanHash.
empty())
5273 HBuilder.add(SanHash.
Mask);
5275 llvm::MD5::MD5Result
Result;
5276 HBuilder.getHasher().final(
Result);
5278 return toString(llvm::APInt(64, Hash), 36,
false);
5306 std::vector<std::string> Args{
"-cc1"};
5308 [&Args](
const Twine &Arg) { Args.push_back(Arg.str()); });
5334 llvm::vfs::getRealFileSystem());
5342 Diags, std::move(BaseFS));
5348 if (VFSOverlayFiles.empty())
5353 for (
const auto &
File : VFSOverlayFiles) {
5354 llvm::ErrorOr<std::unique_ptr<llvm::MemoryBuffer>> Buffer =
5357 Diags.
Report(diag::err_missing_vfs_overlay_file) <<
File;
5362 std::move(Buffer.get()),
nullptr,
File,
5365 Diags.
Report(diag::err_invalid_vfs_overlay) <<
File;
Defines the Diagnostic-related interfaces.
Defines enum values for all the target-independent builtin functions.
static void getAllNoBuiltinFuncValues(ArgList &Args, std::vector< std::string > &Funcs)
static T extractMaskValue(T KeyPath)
static std::optional< IntTy > normalizeStringIntegral(OptSpecifier Opt, int, const ArgList &Args, DiagnosticsEngine &Diags)
static T mergeMaskValue(T KeyPath, U Value)
static std::optional< std::string > normalizeString(OptSpecifier Opt, int TableIndex, const ArgList &Args, DiagnosticsEngine &Diags)
static auto makeBooleanOptionNormalizer(bool Value, bool OtherValue, OptSpecifier OtherOpt)
static void parsePointerAuthOptions(PointerAuthOptions &Opts, const LangOptions &LangOpts, const llvm::Triple &Triple, DiagnosticsEngine &Diags)
static void denormalizeString(ArgumentConsumer Consumer, unsigned SpellingOffset, Option::OptionClass OptClass, unsigned TableIndex, T Value)
static SmallVector< StringRef, 4 > serializeSanitizerKinds(SanitizerSet S)
static void parseXRayInstrumentationBundle(StringRef FlagName, StringRef Bundle, ArgList &Args, DiagnosticsEngine &D, XRayInstrSet &S)
static unsigned getOptimizationLevelSize(ArgList &Args)
static void GenerateFrontendArgs(const FrontendOptions &Opts, ArgumentConsumer Consumer, bool IsHeader)
static std::optional< SimpleEnumValue > findValueTableByValue(const SimpleEnumValueTable &Table, unsigned Value)
static bool ParseTargetArgs(TargetOptions &Opts, ArgList &Args, DiagnosticsEngine &Diags)
static auto makeFlagToValueNormalizer(T Value)
static CodeGenOptions::OptRemark ParseOptimizationRemark(DiagnosticsEngine &Diags, ArgList &Args, OptSpecifier OptEQ, StringRef Name)
Parse a remark command line argument.
static bool ParseFileSystemArgs(FileSystemOptions &Opts, const ArgList &Args, DiagnosticsEngine &Diags)
static constexpr bool is_uint64_t_convertible()
static void GeneratePointerAuthArgs(const LangOptions &Opts, ArgumentConsumer Consumer)
static std::optional< SimpleEnumValue > findValueTableByName(const SimpleEnumValueTable &Table, StringRef Name)
static std::optional< OptSpecifier > getProgramActionOpt(frontend::ActionKind ProgramAction)
Maps frontend action to command line option.
static bool parseDiagnosticLevelMask(StringRef FlagName, const std::vector< std::string > &Levels, DiagnosticsEngine &Diags, DiagnosticLevelMask &M)
static std::optional< bool > normalizeSimpleFlag(OptSpecifier Opt, unsigned TableIndex, const ArgList &Args, DiagnosticsEngine &Diags)
CompilerInvocation::ArgumentConsumer ArgumentConsumer
static void denormalizeSimpleEnumImpl(ArgumentConsumer Consumer, unsigned SpellingOffset, Option::OptionClass OptClass, unsigned TableIndex, unsigned Value)
static void GenerateArg(ArgumentConsumer Consumer, llvm::opt::OptSpecifier OptSpecifier)
static void addDiagnosticArgs(ArgList &Args, OptSpecifier Group, OptSpecifier GroupWithValue, std::vector< std::string > &Diagnostics)
static bool ParseAnalyzerArgs(AnalyzerOptions &Opts, ArgList &Args, DiagnosticsEngine &Diags)
static void ParsePointerAuthArgs(LangOptions &Opts, ArgList &Args, DiagnosticsEngine &Diags)
static void parseAnalyzerConfigs(AnalyzerOptions &AnOpts, DiagnosticsEngine *Diags)
static void denormalizeSimpleFlag(ArgumentConsumer Consumer, unsigned SpellingOffset, Option::OptionClass, unsigned,...)
The tblgen-erated code passes in a fifth parameter of an arbitrary type, but denormalizeSimpleFlags n...
static bool ParsePreprocessorArgs(PreprocessorOptions &Opts, ArgList &Args, DiagnosticsEngine &Diags, frontend::ActionKind Action, const FrontendOptions &FrontendOpts)
static std::optional< unsigned > normalizeSimpleEnum(OptSpecifier Opt, unsigned TableIndex, const ArgList &Args, DiagnosticsEngine &Diags)
static StringRef GetInputKindName(InputKind IK)
Get language name for given input kind.
static void initOption(AnalyzerOptions::ConfigTable &Config, DiagnosticsEngine *Diags, StringRef &OptionField, StringRef Name, StringRef DefaultVal)
static std::optional< std::string > normalizeTriple(OptSpecifier Opt, int TableIndex, const ArgList &Args, DiagnosticsEngine &Diags)
llvm::function_ref< bool(CompilerInvocation &, ArrayRef< const char * >, DiagnosticsEngine &, const char *)> ParseFn
T & ensureOwned(std::shared_ptr< T > &Storage)
llvm::function_ref< void(CompilerInvocation &, SmallVectorImpl< const char * > &, CompilerInvocation::StringAllocator)> GenerateFn
static void GenerateMigratorArgs(const MigratorOptions &Opts, ArgumentConsumer Consumer)
static const auto & getFrontendActionTable()
Return a table that associates command line option specifiers with the frontend action.
static void GenerateTargetArgs(const TargetOptions &Opts, ArgumentConsumer Consumer)
static std::optional< frontend::ActionKind > getFrontendAction(OptSpecifier &Opt)
Maps command line option to frontend action.
static bool checkVerifyPrefixes(const std::vector< std::string > &VerifyPrefixes, DiagnosticsEngine &Diags)
static SanitizerMaskCutoffs parseSanitizerWeightedKinds(StringRef FlagName, const std::vector< std::string > &Sanitizers, DiagnosticsEngine &Diags)
static void GenerateAPINotesArgs(const APINotesOptions &Opts, ArgumentConsumer Consumer)
static bool isCodeGenAction(frontend::ActionKind Action)
static std::optional< bool > normalizeSimpleNegativeFlag(OptSpecifier Opt, unsigned, const ArgList &Args, DiagnosticsEngine &)
static void GenerateFileSystemArgs(const FileSystemOptions &Opts, ArgumentConsumer Consumer)
static bool IsInputCompatibleWithStandard(InputKind IK, const LangStandard &S)
Check if input file kind and language standard are compatible.
static void denormalizeStringImpl(ArgumentConsumer Consumer, const Twine &Spelling, Option::OptionClass OptClass, unsigned, const Twine &Value)
static void setPGOUseInstrumentor(CodeGenOptions &Opts, const Twine &ProfileName, llvm::vfs::FileSystem &FS, DiagnosticsEngine &Diags)
static llvm::StringRef lookupStrInTable(unsigned Offset)
static void GeneratePreprocessorArgs(const PreprocessorOptions &Opts, ArgumentConsumer Consumer, const LangOptions &LangOpts, const FrontendOptions &FrontendOpts, const CodeGenOptions &CodeGenOpts)
static bool ParseHeaderSearchArgs(HeaderSearchOptions &Opts, ArgList &Args, DiagnosticsEngine &Diags, const std::string &WorkingDir)
static bool ParseFrontendArgs(FrontendOptions &Opts, ArgList &Args, DiagnosticsEngine &Diags, bool &IsHeaderFile)
static auto makeBooleanOptionDenormalizer(bool Value)
static void GeneratePreprocessorOutputArgs(const PreprocessorOutputOptions &Opts, ArgumentConsumer Consumer, frontend::ActionKind Action)
static bool isStrictlyPreprocessorAction(frontend::ActionKind Action)
static std::string serializeXRayInstrumentationBundle(const XRayInstrSet &S)
static bool ParseMigratorArgs(MigratorOptions &Opts, const ArgList &Args, DiagnosticsEngine &Diags)
static bool parseShowColorsArgs(const ArgList &Args, bool DefaultColor)
static T mergeForwardValue(T KeyPath, U Value)
static void ParseAPINotesArgs(APINotesOptions &Opts, ArgList &Args, DiagnosticsEngine &diags)
static void denormalizeStringVector(ArgumentConsumer Consumer, unsigned SpellingOffset, Option::OptionClass OptClass, unsigned TableIndex, const std::vector< std::string > &Values)
static bool ParseDependencyOutputArgs(DependencyOutputOptions &Opts, ArgList &Args, DiagnosticsEngine &Diags, frontend::ActionKind Action, bool ShowLineMarkers)
static Expected< std::optional< uint32_t > > parseToleranceOption(StringRef Arg)
static std::optional< std::vector< std::string > > normalizeStringVector(OptSpecifier Opt, int, const ArgList &Args, DiagnosticsEngine &)
static void GenerateAnalyzerArgs(const AnalyzerOptions &Opts, ArgumentConsumer Consumer)
static void GenerateOptimizationRemark(ArgumentConsumer Consumer, OptSpecifier OptEQ, StringRef Name, const CodeGenOptions::OptRemark &Remark)
Generate a remark argument. This is an inverse of ParseOptimizationRemark.
static bool ParsePreprocessorOutputArgs(PreprocessorOutputOptions &Opts, ArgList &Args, DiagnosticsEngine &Diags, frontend::ActionKind Action)
static bool RoundTrip(ParseFn Parse, GenerateFn Generate, CompilerInvocation &RealInvocation, CompilerInvocation &DummyInvocation, ArrayRef< const char * > CommandLineArgs, DiagnosticsEngine &Diags, const char *Argv0, bool CheckAgainstOriginalInvocation=false, bool ForceRoundTrip=false)
May perform round-trip of command line arguments.
static T extractForwardValue(T KeyPath)
static void denormalizeSimpleEnum(ArgumentConsumer Consumer, unsigned SpellingOffset, Option::OptionClass OptClass, unsigned TableIndex, T Value)
static unsigned getOptimizationLevel(ArgList &Args, InputKind IK, DiagnosticsEngine &Diags)
std::shared_ptr< T > make_shared_copy(const T &X)
static bool parseTestModuleFileExtensionArg(StringRef Arg, std::string &BlockName, unsigned &MajorVersion, unsigned &MinorVersion, bool &Hashed, std::string &UserInfo)
Parse the argument to the -ftest-module-file-extension command-line argument.
static void GenerateDependencyOutputArgs(const DependencyOutputOptions &Opts, ArgumentConsumer Consumer)
static StringRef getStringOption(AnalyzerOptions::ConfigTable &Config, StringRef OptionName, StringRef DefaultVal)
static bool FixupInvocation(CompilerInvocation &Invocation, DiagnosticsEngine &Diags, const ArgList &Args, InputKind IK)
static void parseSanitizerKinds(StringRef FlagName, const std::vector< std::string > &Sanitizers, DiagnosticsEngine &Diags, SanitizerSet &S)
static void GenerateHeaderSearchArgs(const HeaderSearchOptions &Opts, ArgumentConsumer Consumer)
Defines the clang::FileSystemOptions interface.
Forward-declares and imports various common LLVM datatypes that clang wants to use unqualified.
Defines the clang::LangOptions interface.
static DiagnosticBuilder Diag(DiagnosticsEngine *Diags, const LangOptions &Features, FullSourceLoc TokLoc, const char *TokBegin, const char *TokRangeBegin, const char *TokRangeEnd, unsigned DiagID)
Produce a diagnostic highlighting some portion of a literal.
Defines types useful for describing an Objective-C runtime.
static std::string toString(const clang::SanitizerSet &Sanitizers)
Produce a string containing comma-separated names of sanitizers in Sanitizers set.
Defines the clang::SanitizerKind enum.
Defines the clang::SourceLocation class and associated facilities.
Defines the clang::TargetOptions class.
Defines version macros and version-related utility functions for Clang.
Defines the clang::XRayInstrKind enum.
__DEVICE__ void * memcpy(void *__a, const void *__b, size_t __c)
Tracks various options which control how API notes are found and handled.
llvm::VersionTuple SwiftVersion
The Swift version which should be used for API notes.
std::vector< std::string > ModuleSearchPaths
The set of search paths where we API notes can be found for particular modules.
Stores options for the analyzer from the command line.
static std::vector< StringRef > getRegisteredPackages(bool IncludeExperimental=false)
Retrieves the list of packages generated from Checkers.td.
std::vector< std::pair< std::string, bool > > CheckersAndPackages
Pairs of checker/package name and enable/disable.
std::vector< std::string > SilencedCheckersAndPackages
Vector of checker/package names which will not emit warnings.
AnalysisDiagClients AnalysisDiagOpt
AnalysisConstraints AnalysisConstraintsOpt
ConfigTable Config
A key-value table of use-specified configuration values.
unsigned ShouldEmitErrorsOnInvalidConfigValue
AnalysisPurgeMode AnalysisPurgeOpt
bool isUnknownAnalyzerConfig(llvm::StringRef Name)
static std::vector< StringRef > getRegisteredCheckers(bool IncludeExperimental=false)
Retrieves the list of checkers generated from Checkers.td.
llvm::StringMap< std::string > ConfigTable
std::string FullCompilerInvocation
Store full compiler invocation for reproducible instructions in the generated report.
AnalysisInliningMode InliningMode
The mode of function selection used during inlining.
static bool isBuiltinFunc(llvm::StringRef Name)
Returns true if this is a libc/libm function without the '__builtin_' prefix.
Implements C++ ABI-specific semantic analysis functions.
CompatibilityKind
For ASTs produced with different option value, signifies their level of compatibility.
CodeGenOptions - Track various options which control how the code is optimized and passed to the back...
llvm::SmallVector< std::pair< std::string, std::string >, 0 > CoveragePrefixMap
Prefix replacement map for source-based code coverage to remap source file paths in coverage mapping.
SanitizerSet SanitizeMergeHandlers
Set of sanitizer checks that can merge handlers (smaller code size at the expense of debuggability).
llvm::SmallVector< std::pair< std::string, std::string >, 0 > DebugPrefixMap
std::string OptRecordFile
The name of the file to which the backend should save YAML optimization records.
std::string BinutilsVersion
std::vector< BitcodeFileToLink > LinkBitcodeFiles
The files specified here are linked in to the module before optimizations.
std::optional< uint64_t > DiagnosticsHotnessThreshold
The minimum hotness value a diagnostic needs in order to be included in optimization diagnostics.
char CoverageVersion[4]
The version string to put into coverage files.
llvm::DenormalMode FPDenormalMode
The floating-point denormal mode to use.
std::string CoverageNotesFile
The filename with path we use for coverage notes files.
std::string ProfileInstrumentUsePath
Name of the profile file to use as input for -fprofile-instr-use.
std::string SampleProfileFile
Name of the profile file to use with -fprofile-sample-use.
uint64_t LargeDataThreshold
The code model-specific large data threshold to use (-mlarge-data-threshold).
std::string MemoryProfileOutput
Name of the profile file to use as output for with -fmemory-profile.
std::string CodeModel
The code model to use (-mcmodel).
std::string CoverageDataFile
The filename with path we use for coverage data files.
std::optional< uint32_t > DiagnosticsMisExpectTolerance
The maximum percentage profiling weights can deviate from the expected values in order to be included...
std::string StackUsageOutput
Name of the stack usage file (i.e., .su file) if user passes -fstack-usage.
std::string OptRecordPasses
The regex that filters the passes that should be saved to the optimization records.
std::string SaveTempsFilePrefix
Prefix to use for -save-temps output.
XRayInstrSet XRayInstrumentationBundle
Set of XRay instrumentation kinds to emit.
bool hasSanitizeCoverage() const
SanitizerSet SanitizeAnnotateDebugInfo
Set of sanitizer checks, for which the instrumentation will be annotated with extra debug info.
PointerAuthOptions PointerAuth
Configuration for pointer-signing.
llvm::DenormalMode FP32DenormalMode
The floating-point denormal mode to use, for float.
SanitizerSet SanitizeTrap
Set of sanitizer checks that trap rather than diagnose.
SanitizerSet SanitizeRecover
Set of sanitizer checks that are non-fatal (i.e.
bool hasReducedDebugInfo() const
Check if type and variable info should be emitted.
OptRemark OptimizationRemark
Selected optimizations for which we should enable optimization remarks.
std::string ThinLTOIndexFile
Name of the function summary index file to use for ThinLTO function importing.
const char * Argv0
Executable and command-line used to create a given CompilerInvocation.
SanitizerMaskCutoffs SanitizeSkipHotCutoffs
Set of thresholds in a range [0.0, 1.0]: the top hottest code responsible for the given fraction of P...
std::vector< std::string > NoBuiltinFuncs
A list of all -fno-builtin-* function names (e.g., memset).
std::vector< uint8_t > CmdArgs
List of backend command-line options for -fembed-bitcode.
OptRemark OptimizationRemarkAnalysis
Selected optimizations for which we should enable optimization analyses.
std::optional< double > AllowRuntimeCheckSkipHotCutoff
std::vector< std::string > CommandLineArgs
void resetNonModularOptions(StringRef ModuleFormat)
Reset all of the options that are not considered when building a module.
std::string OptRecordFormat
The format used for serializing remarks (default: YAML)
std::string DIBugsReportFilePath
The file to use for dumping bug report by Debugify for original debug info.
OptRemark OptimizationRemarkMissed
Selected optimizations for which we should enable missed optimization remarks.
The base class of CompilerInvocation.
std::shared_ptr< DiagnosticOptions > DiagnosticOpts
Options controlling the diagnostic engine.
std::shared_ptr< AnalyzerOptions > AnalyzerOpts
Options controlling the static analyzer.
std::shared_ptr< MigratorOptions > MigratorOpts
std::shared_ptr< PreprocessorOutputOptions > PreprocessorOutputOpts
Options controlling preprocessed output.
std::shared_ptr< APINotesOptions > APINotesOpts
Options controlling API notes.
std::shared_ptr< TargetOptions > TargetOpts
Options controlling the target.
const FrontendOptions & getFrontendOpts() const
const CodeGenOptions & getCodeGenOpts() const
llvm::function_ref< const char *(const Twine &)> StringAllocator
Command line generation.
const FileSystemOptions & getFileSystemOpts() const
std::shared_ptr< PreprocessorOptions > PPOpts
Options controlling the preprocessor (aside from #include handling).
const PreprocessorOutputOptions & getPreprocessorOutputOpts() const
std::vector< std::string > getCC1CommandLine() const
Generate cc1-compatible command line arguments from this instance, wrapping the result as a std::vect...
std::shared_ptr< FileSystemOptions > FSOpts
Options controlling file system operations.
const AnalyzerOptions & getAnalyzerOpts() const
const MigratorOptions & getMigratorOpts() const
void generateCC1CommandLine(llvm::SmallVectorImpl< const char * > &Args, StringAllocator SA) const
Generate cc1-compatible command line arguments from this instance.
CompilerInvocationBase & deep_copy_assign(const CompilerInvocationBase &X)
const DependencyOutputOptions & getDependencyOutputOpts() const
CompilerInvocationBase & shallow_copy_assign(const CompilerInvocationBase &X)
const TargetOptions & getTargetOpts() const
std::shared_ptr< CodeGenOptions > CodeGenOpts
Options controlling IRgen and the backend.
std::shared_ptr< LangOptions > LangOpts
Options controlling the language variant.
const APINotesOptions & getAPINotesOpts() const
const HeaderSearchOptions & getHeaderSearchOpts() const
std::shared_ptr< HeaderSearchOptions > HSOpts
Options controlling the #include directive.
const PreprocessorOptions & getPreprocessorOpts() const
const DiagnosticOptions & getDiagnosticOpts() const
const LangOptions & getLangOpts() const
Const getters.
std::shared_ptr< FrontendOptions > FrontendOpts
Options controlling the frontend itself.
llvm::function_ref< void(const Twine &)> ArgumentConsumer
std::shared_ptr< DependencyOutputOptions > DependencyOutputOpts
Options controlling dependency output.
Helper class for holding the data necessary to invoke the compiler.
PreprocessorOptions & getPreprocessorOpts()
void clearImplicitModuleBuildOptions()
Disable implicit modules and canonicalize options that are only used by implicit modules.
MigratorOptions & getMigratorOpts()
AnalyzerOptions & getAnalyzerOpts()
APINotesOptions & getAPINotesOpts()
static std::string GetResourcesPath(const char *Argv0, void *MainAddr)
Get the directory where the compiler headers reside, relative to the compiler binary (found by the pa...
static bool CreateFromArgs(CompilerInvocation &Res, ArrayRef< const char * > CommandLineArgs, DiagnosticsEngine &Diags, const char *Argv0=nullptr)
Create a compiler invocation from a list of input options.
LangOptions & getLangOpts()
Mutable getters.
static bool checkCC1RoundTrip(ArrayRef< const char * > Args, DiagnosticsEngine &Diags, const char *Argv0=nullptr)
Check that Args can be parsed and re-serialized without change, emiting diagnostics for any differenc...
DependencyOutputOptions & getDependencyOutputOpts()
CompilerInvocation()=default
void resetNonModularOptions()
Reset all of the options that are not considered when building a module.
FrontendOptions & getFrontendOpts()
std::string getModuleHash() const
Retrieve a module hash string that is suitable for uniquely identifying the conditions under which th...
FileSystemOptions & getFileSystemOpts()
CompilerInvocation & operator=(const CompilerInvocation &X)
static void setDefaultPointerAuthOptions(PointerAuthOptions &Opts, const LangOptions &LangOpts, const llvm::Triple &Triple)
Populate Opts with the default set of pointer authentication-related options given LangOpts and Tripl...
CodeGenOptions & getCodeGenOpts()
TargetOptions & getTargetOpts()
HeaderSearchOptions & getHeaderSearchOpts()
DiagnosticOptions & getDiagnosticOpts()
PreprocessorOutputOptions & getPreprocessorOutputOpts()
Same as CompilerInvocation, but with copy-on-write optimization.
FrontendOptions & getMutFrontendOpts()
LangOptions & getMutLangOpts()
Mutable getters.
HeaderSearchOptions & getMutHeaderSearchOpts()
MigratorOptions & getMutMigratorOpts()
PreprocessorOptions & getMutPreprocessorOpts()
APINotesOptions & getMutAPINotesOpts()
PreprocessorOutputOptions & getMutPreprocessorOutputOpts()
CodeGenOptions & getMutCodeGenOpts()
TargetOptions & getMutTargetOpts()
FileSystemOptions & getMutFileSystemOpts()
AnalyzerOptions & getMutAnalyzerOpts()
DiagnosticOptions & getMutDiagnosticOpts()
DependencyOutputOptions & getMutDependencyOutputOpts()
DependencyOutputOptions - Options for controlling the compiler dependency file generation.
ShowIncludesDestination ShowIncludesDest
Destination of cl.exe style /showIncludes info.
HeaderIncludeFormatKind HeaderIncludeFormat
The format of header information.
std::string OutputFile
The file to write dependency output to.
HeaderIncludeFilteringKind HeaderIncludeFiltering
Determine whether header information should be filtered.
std::vector< std::string > Targets
A list of names to use as the targets in the dependency file; this list must contain at least one ent...
std::vector< std::pair< std::string, ExtraDepKind > > ExtraDeps
A list of extra dependencies (filename and kind) to be used for every target.
unsigned IncludeSystemHeaders
Include system header dependencies.
static llvm::IntrusiveRefCntPtr< DiagnosticIDs > create()
Options for controlling the compiler diagnostics engine.
std::string DiagnosticSuppressionMappingsFile
Path for the file that defines diagnostic suppression mappings.
std::vector< std::string > Remarks
The list of -R... options used to alter the diagnostic mappings, with the prefixes removed.
std::vector< std::string > Warnings
The list of -W... options used to alter the diagnostic mappings, with the prefixes removed.
std::vector< std::string > VerifyPrefixes
The prefixes for comment directives sought by -verify ("expected" by default).
std::string DiagnosticSerializationFile
The file to serialize diagnostics to (non-appending).
Concrete class used by the front-end to report problems and issues.
DiagnosticBuilder Report(SourceLocation Loc, unsigned DiagID)
Issue the message to the client.
unsigned getCustomDiagID(Level L, const char(&FormatString)[N])
Return an ID for a diagnostic with the specified format string and level.
void setClient(DiagnosticConsumer *client, bool ShouldOwnClient=true)
Set the diagnostic client associated with this diagnostic object.
unsigned getNumErrors() const
bool isIgnored(unsigned DiagID, SourceLocation Loc) const
Determine whether the diagnostic is known to be ignored.
unsigned getNumWarnings() const
Keeps track of options that affect how file operations are performed.
std::string WorkingDir
If set, paths are resolved as if the working directory was set to the value of WorkingDir.
FrontendOptions - Options for controlling the behavior of the frontend.
InputKind DashX
The input kind, either specified via -x argument or deduced from the input file name.
std::vector< std::string > ModuleFiles
The list of additional prebuilt module files to load before processing the input.
unsigned ClangIRDisablePasses
Disable Clang IR specific (CIR) passes.
std::map< std::string, std::vector< std::string > > PluginArgs
Args to pass to the plugins.
unsigned ClangIRDisableCIRVerifier
Disable Clang IR (CIR) verifier.
unsigned IsSystemModule
When using -emit-module, treat the modulemap as a system module.
unsigned UseClangIRPipeline
Use Clang IR pipeline to emit code.
ASTDumpOutputFormat ASTDumpFormat
Specifies the output format of the AST.
std::optional< std::string > AuxTargetCPU
Auxiliary target CPU for CUDA/HIP compilation.
std::string OutputFile
The output file, if any.
unsigned ShowStats
Show frontend performance metrics and statistics.
unsigned GenReducedBMI
Whether to generate reduced BMI for C++20 named modules.
std::string ActionName
The name of the action to run when using a plugin action.
std::vector< std::shared_ptr< ModuleFileExtension > > ModuleFileExtensions
The list of module file extensions.
ParsedSourceLocation CodeCompletionAt
If given, enable code completion at the provided location.
std::string FixItSuffix
If given, the new suffix for fix-it rewritten files.
static InputKind getInputKindForExtension(StringRef Extension)
getInputKindForExtension - Return the appropriate input kind for a file extension.
std::vector< std::string > Plugins
The list of plugins to load.
unsigned ASTDumpAll
Whether we deserialize all decls when forming AST dumps.
unsigned GenerateGlobalModuleIndex
Whether we can generate the global module index if needed.
unsigned DisableFree
Disable memory freeing on exit.
SmallVector< FrontendInputFile, 0 > Inputs
The input files and their types.
frontend::ActionKind ProgramAction
The frontend action to perform.
std::optional< std::vector< std::string > > AuxTargetFeatures
Auxiliary target features for CUDA/HIP compilation.
std::string AuxTriple
Auxiliary triple for CUDA/HIP compilation.
unsigned UseGlobalModuleIndex
Whether we can use the global module index if available.
unsigned ASTDumpDecls
Whether we include declaration dumps in AST dumps.
A diagnostic client that ignores all diagnostics.
@ None
No signing for any function.
@ NonLeaf
Sign the return address of functions that spill LR.
@ All
Sign the return address of all functions,.
@ BKey
Return address signing uses APIB key.
@ AKey
Return address signing uses APIA key.
@ None
Don't exclude any overflow patterns from sanitizers.
@ AddUnsignedOverflowTest
if (a + b < a)
@ All
Exclude all overflow patterns (below)
@ AddSignedOverflowTest
if (a + b < a)
@ PostDecrInWhile
while (count–)
CompatibilityKind
For ASTs produced with different option value, signifies their level of compatibility.
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
void resetNonModularOptions()
Reset all of the options that are not considered when building a module.
std::optional< TargetCXXABI::Kind > CXXABI
C++ ABI to compile with, if specified by the frontend through -fc++-abi=.
std::vector< std::string > NoBuiltinFuncs
A list of all -fno-builtin-* function names (e.g., memset).
std::string ModuleName
The module currently being compiled as specified by -fmodule-name.
clang::ObjCRuntime ObjCRuntime
std::string getOpenCLVersionString() const
Return the OpenCL C or C++ for OpenCL language name and version as a string.
unsigned OverflowPatternExclusionMask
Which overflow patterns should be excluded from sanitizer instrumentation.
SanitizerSet Sanitize
Set of enabled sanitizers.
bool UseTargetPathSeparator
Indicates whether to use target's platform-specific file separator when FILE macro is used and when c...
static void setLangDefaults(LangOptions &Opts, Language Lang, const llvm::Triple &T, std::vector< std::string > &Includes, LangStandard::Kind LangStd=LangStandard::lang_unspecified)
Set language defaults for the given input language and language standard in the given LangOptions obj...
std::string OverflowHandler
The name of the handler function to be called when -ftrapv is specified.
std::string RandstructSeed
The seed used by the randomize structure layout feature.
std::map< std::string, std::string, std::greater< std::string > > MacroPrefixMap
A prefix map for FILE, BASE_FILE and __builtin_FILE().
bool isTargetDevice() const
True when compiling for an offloading target device.
LangStandard::Kind LangStd
The used language standard.
unsigned getOpenCLCompatibleVersion() const
Return the OpenCL version that kernel language is compatible with.
bool SanitizeCoverage
Is at least one coverage instrumentation type enabled.
std::vector< llvm::Triple > OMPTargetTriples
Triples of the OpenMP targets that the host code codegen should take into account in order to generat...
std::vector< std::string > NoSanitizeFiles
Paths to files specifying which objects (files, functions, variables) should not be instrumented.
std::string CurrentModule
The name of the current module, of which the main source file is a part.
std::vector< std::string > ModuleFeatures
The names of any features to enable in module 'requires' decls in addition to the hard-coded list in ...
The basic abstraction for the target Objective-C runtime.
bool allowsWeak() const
Does this runtime allow the use of __weak?
bool tryParse(StringRef input)
Try to parse an Objective-C runtime specification from the given string.
std::string getAsString() const
bool allowsARC() const
Does this runtime allow ARC at all?
@ FragileMacOSX
'macosx-fragile' is the Apple-provided NeXT-derived runtime on Mac OS X platforms that use the fragil...
Discrimination
Forms of extra discrimination.
ARM8_3Key
Hardware pointer-signing keys in ARM8.3.
static constexpr std::optional< PositiveAnalyzerOption > create(unsigned Val)
PreprocessorOptions - This class is used for passing the various options used in preprocessor initial...
std::vector< std::pair< std::string, std::string > > RemappedFiles
The set of file remappings, which take existing files on the system (the first part of each pair) and...
bool PCHWithHdrStopCreate
When true, we are creating a PCH or creating the PCH object while expecting a #pragma hdrstop to sepa...
std::vector< std::string > Includes
std::pair< unsigned, bool > PrecompiledPreambleBytes
If non-zero, the implicit PCH include is actually a precompiled preamble that covers this number of b...
bool LexEditorPlaceholders
When enabled, the preprocessor will construct editor placeholder tokens.
void resetNonModularOptions()
Reset any options that are not considered when building a module.
void addMacroUndef(StringRef Name)
std::set< std::string > DeserializedPCHDeclsToErrorOn
This is a set of names for decls that we do not want to be deserialized, and we emit an error if they...
std::vector< std::string > EmbedEntries
User specified embed entries.
void addMacroDef(StringRef Name)
bool DefineTargetOSMacros
Indicates whether to predefine target OS macros.
bool DetailedRecord
Whether we should maintain a detailed record of all macro definitions and expansions.
std::vector< std::string > ChainedIncludes
Headers that will be converted to chained PCHs in memory.
bool PCHWithHdrStop
When true, we are creating or using a PCH where a #pragma hdrstop is expected to indicate the beginni...
std::optional< uint64_t > SourceDateEpoch
If set, the UNIX timestamp specified by SOURCE_DATE_EPOCH.
bool UsePredefines
Initialize the preprocessor with the compiler and target specific predefines.
void addRemappedFile(StringRef From, StringRef To)
std::vector< std::pair< std::string, bool > > Macros
PreprocessorOutputOptions - Options for controlling the C preprocessor output (e.g....
unsigned ShowMacros
Print macro definitions.
unsigned ShowCPP
Print normal preprocessed output.
unsigned ShowLineMarkers
Show #line markers.
unsigned DirectivesOnly
Process directives but do not expand macros.
Encodes a location in the source.
static bool isSupportedCXXABI(const llvm::Triple &T, Kind Kind)
static const auto & getSpelling(Kind ABIKind)
static bool usesRelativeVTables(const llvm::Triple &T)
static bool isABI(StringRef Name)
Options for controlling the target.
std::string Triple
The name of the target triple to compile for.
llvm::VersionTuple SDKVersion
The version of the SDK which was used during the compilation.
uint64_t LargeDataThreshold
llvm::VersionTuple DarwinTargetVariantSDKVersion
The version of the darwin target variant SDK which was used during the compilation.
std::string HostTriple
When compiling for the device side, contains the triple used to compile for the host.
Action - Represent an abstract compilation step to perform.
static std::string GetResourcesPath(StringRef BinaryPath)
Takes the path to a binary that's either in bin/ or lib/ and returns the path to clang's resource dir...
constexpr XRayInstrMask None
constexpr XRayInstrMask All
const llvm::opt::OptTable & getDriverOptTable()
IncludeDirGroup
IncludeDirGroup - Identifies the group an include Entry belongs to, representing its relative positiv...
@ CXXSystem
Like System, but only used for C++.
@ Angled
Paths for '#include <>' added by '-I'.
@ CSystem
Like System, but only used for C.
@ System
Like Angled, but marks system directories.
@ Quoted
'#include ""' paths, added by 'gcc -iquote'.
@ ExternCSystem
Like System, but headers are implicitly wrapped in extern "C".
@ ObjCSystem
Like System, but only used for ObjC.
@ ObjCXXSystem
Like System, but only used for ObjC++.
@ After
Like System, but searched after the system directories.
@ GenerateHeaderUnit
Generate a C++20 header unit module from a header file.
@ VerifyPCH
Load and verify that a PCH file is usable.
@ PrintPreprocessedInput
-E mode.
@ RewriteTest
Rewriter playground.
@ ParseSyntaxOnly
Parse and perform semantic analysis.
@ TemplightDump
Dump template instantiations.
@ GenerateModuleInterface
Generate pre-compiled module from a standard C++ module interface unit.
@ EmitLLVM
Emit a .ll file.
@ PrintPreamble
Print the "preamble" of the input file.
@ InitOnly
Only execute frontend initialization.
@ ASTView
Parse ASTs and view them in Graphviz.
@ PluginAction
Run a plugin action,.
@ DumpRawTokens
Dump out raw tokens.
@ PrintDependencyDirectivesSourceMinimizerOutput
Print the output of the dependency directives source minimizer.
@ RewriteObjC
ObjC->C Rewriter.
@ RunPreprocessorOnly
Just lex, no output.
@ ModuleFileInfo
Dump information about a module file.
@ EmitCIR
Emit a .cir file.
@ DumpCompilerOptions
Dump the compiler configuration.
@ RunAnalysis
Run one or more source code analyses.
@ ASTPrint
Parse ASTs and print them.
@ GenerateReducedModuleInterface
Generate reduced module interface for a standard C++ module interface unit.
@ GenerateInterfaceStubs
Generate Interface Stub Files.
@ ASTDump
Parse ASTs and dump them.
@ DumpTokens
Dump out preprocessed tokens.
@ FixIt
Parse and apply any fixits to the source.
@ EmitAssembly
Emit a .s file.
@ EmitCodeGenOnly
Generate machine code, but don't emit anything.
@ RewriteMacros
Expand macros but not #includes.
@ EmitHTML
Translate input source into HTML.
@ GeneratePCH
Generate pre-compiled header.
@ EmitLLVMOnly
Generate LLVM IR, but do not emit anything.
@ GenerateModule
Generate pre-compiled module from a module map.
@ ASTDeclList
Parse ASTs and list Decl nodes.
bool EQ(InterpState &S, CodePtr OpPC)
const unsigned VERSION_MINOR
AST file minor version number supported by this version of Clang.
const unsigned VERSION_MAJOR
AST file major version number supported by this version of Clang.
The JSON file list parser is used to communicate input to InstallAPI.
ASTDumpOutputFormat
Used to specify the format for printing AST dump information.
SanitizerMask getPPTransparentSanitizers()
Return the sanitizers which do not affect preprocessing.
if(T->getSizeExpr()) TRY_TO(TraverseStmt(const_cast< Expr * >(T -> getSizeExpr())))
IntrusiveRefCntPtr< llvm::vfs::FileSystem > createVFSFromOverlayFiles(ArrayRef< std::string > VFSOverlayFiles, DiagnosticsEngine &Diags, IntrusiveRefCntPtr< llvm::vfs::FileSystem > BaseFS)
DiagnosticLevelMask
A bitmask representing the diagnostic levels used by VerifyDiagnosticConsumer.
const char * headerIncludeFormatKindToString(HeaderIncludeFormatKind K)
std::unique_ptr< DiagnosticOptions > CreateAndPopulateDiagOpts(ArrayRef< const char * > Argv)
constexpr uint16_t BlockDescriptorConstantDiscriminator
Constant discriminator to be used with block descriptor pointers.
constexpr uint16_t IsaPointerConstantDiscriminator
Constant discriminator to be used with objective-c isa pointers.
const char * headerIncludeFilteringKindToString(HeaderIncludeFilteringKind K)
AnalysisConstraints
AnalysisConstraints - Set of available constraint models.
@ Success
Annotation was successful.
@ Parse
Parse the block; this code is always used.
constexpr uint16_t SuperPointerConstantDiscriminator
Constant discriminator to be used with objective-c superclass pointers.
void serializeSanitizerSet(SanitizerSet Set, SmallVectorImpl< StringRef > &Values)
Serialize a SanitizerSet into values for -fsanitize= or -fno-sanitize=.
LLVM_READONLY bool isLetter(unsigned char c)
Return true if this character is an ASCII letter: [a-zA-Z].
LLVM_READONLY bool isAlphanumeric(unsigned char c)
Return true if this character is an ASCII letter or digit: [a-zA-Z0-9].
constexpr uint16_t MethodListPointerConstantDiscriminator
Constant discriminator to be used with method list pointers.
constexpr uint16_t ClassROConstantDiscriminator
Constant discriminator to be used with objective-c class_ro_t pointers.
constexpr uint16_t InitFiniPointerConstantDiscriminator
Constant discriminator to be used with function pointers in .init_array and .fini_array.
@ C
Languages that the frontend can parse and compile.
@ CIR
LLVM IR & CIR: we accept these so that we can run the optimizer on them, and compile them to assembly...
@ Asm
Assembly: we accept this only so that we can preprocess it.
bool parseSanitizerWeightedValue(StringRef Value, bool AllowGroups, SanitizerMaskCutoffs &Cutoffs)
Parse a single weighted value (e.g., 'undefined=0.05') from a -fsanitize= or -fno-sanitize= value lis...
@ Result
The result type of a method or function.
XRayInstrMask parseXRayInstrValue(StringRef Value)
Parses a command line argument into a mask.
IntrusiveRefCntPtr< llvm::vfs::FileSystem > createVFSFromCompilerInvocation(const CompilerInvocation &CI, DiagnosticsEngine &Diags)
void serializeXRayInstrValue(XRayInstrSet Set, SmallVectorImpl< StringRef > &Values)
Serializes a set into a list of command line arguments.
AnalysisPurgeMode
AnalysisPurgeModes - Set of available strategies for dead symbol removal.
void serializeSanitizerMaskCutoffs(const SanitizerMaskCutoffs &Cutoffs, SmallVectorImpl< std::string > &Values)
Serialize a SanitizerMaskCutoffs into command line arguments.
ShaderStage
Shader programs run in specific pipeline stages.
constexpr uint16_t StdTypeInfoVTablePointerConstantDiscrimination
Constant discriminator for std::type_info vtable pointers: 0xB1EA/45546 The value is ptrauth_string_d...
SanitizerMask parseSanitizerValue(StringRef Value, bool AllowGroups)
Parse a single value from a -fsanitize= or -fno-sanitize= value list.
const FunctionProtoType * T
AnalysisDiagClients
AnalysisDiagClients - Set of available diagnostic clients for rendering analysis results.
@ NUM_ANALYSIS_DIAG_CLIENTS
std::string getClangFullRepositoryVersion()
Retrieves the full repository version that is an amalgamation of the information in getClangRepositor...
int getLastArgIntValue(const llvm::opt::ArgList &Args, llvm::opt::OptSpecifier Id, int Default, DiagnosticsEngine *Diags=nullptr, unsigned Base=0)
Return the value of the last argument as an integer, or a default.
bool ParseDiagnosticArgs(DiagnosticOptions &Opts, llvm::opt::ArgList &Args, DiagnosticsEngine *Diags=nullptr, bool DefaultDiagColor=true)
Fill out Opts based on the options given in Args.
AnalysisInliningMode
AnalysisInlineFunctionSelection - Set of inlining function selection heuristics.
int const char * function
__DEVICE__ _Tp arg(const std::complex< _Tp > &__c)
bool Internalize
If true, we use LLVM module internalizer.
bool PropagateAttrs
If true, we set attributes functions in the bitcode library according to our CodeGenOptions,...
std::string Filename
The filename of the bitcode file to link in.
unsigned LinkFlags
Bitwise combination of llvm::Linker::Flags, passed to the LLVM linker.
Dummy tag type whose instance can be passed into the constructor to prevent creation of the reference...
LangStandard - Information about the properties of a particular language standard.
static const LangStandard & getLangStandardForKind(Kind K)
const char * getName() const
getName - Get the name of this standard.
static Kind getLangKind(StringRef Name)
static ParsedSourceLocation FromString(StringRef Str)
Construct a parsed source location from a string; the Filename is empty on error.
std::string ToString() const
Serialize ParsedSourceLocation back to a string.
PointerAuthSchema BlockDescriptorPointers
The ABI for pointers to block descriptors.
PointerAuthSchema BlockHelperFunctionPointers
The ABI for block object copy/destroy function pointers.
PointerAuthSchema CXXVTablePointers
The ABI for C++ virtual table pointers (the pointer to the table itself) as installed in an actual cl...
PointerAuthSchema InitFiniPointers
The ABI for function addresses in .init_array and .fini_array.
PointerAuthSchema BlockInvocationFunctionPointers
The ABI for block invocation function pointers.
PointerAuthSchema BlockByrefHelperFunctionPointers
The ABI for __block variable copy/destroy function pointers.
PointerAuthSchema CXXVTTVTablePointers
The ABI for C++ virtual table pointers as installed in a VTT.
bool ReturnAddresses
Should return addresses be authenticated?
PointerAuthSchema CXXTypeInfoVTablePointer
TypeInfo has external ABI requirements and is emitted without actually having parsed the libcxx defin...
bool AArch64JumpTableHardening
Use hardened lowering for jump-table dispatch?
PointerAuthSchema ObjCMethodListPointer
The ABI for a reference to an Objective-C method list in _class_ro_t.
PointerAuthSchema FunctionPointers
The ABI for C function pointers.
PointerAuthSchema ObjCSuperPointers
The ABI for Objective-C superclass pointers.
bool AuthTraps
Do authentication failures cause a trap?
PointerAuthSchema CXXMemberFunctionPointers
The ABI for C++ member function pointers.
PointerAuthSchema CXXVirtualVariadicFunctionPointers
The ABI for variadic C++ virtual function pointers.
PointerAuthSchema ObjCMethodListFunctionPointers
The ABI for Objective-C method lists.
PointerAuthSchema ObjCClassROPointers
The ABI for Objective-C class_ro_t pointers.
PointerAuthSchema CXXVirtualFunctionPointers
The ABI for most C++ virtual function pointers, i.e. v-table entries.
PointerAuthSchema ObjCIsaPointers
The ABI for Objective-C isa pointers.
bool IndirectGotos
Do indirect goto label addresses need to be authenticated?
void clear(SanitizerMask K=SanitizerKind::All)
Disable the sanitizers specified in K.
bool empty() const
Returns true if no sanitizers are enabled.
SanitizerMask Mask
Bitmask of enabled sanitizers.