1 //===- FrontendOptions.h ----------------------------------------*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 9 #ifndef LLVM_CLANG_FRONTEND_FRONTENDOPTIONS_H 10 #define LLVM_CLANG_FRONTEND_FRONTENDOPTIONS_H 11 12 #include "clang/AST/ASTDumperUtils.h" 13 #include "clang/Basic/LangStandard.h" 14 #include "clang/Frontend/CommandLineSourceLoc.h" 15 #include "clang/Sema/CodeCompleteOptions.h" 16 #include "clang/Serialization/ModuleFileExtension.h" 17 #include "llvm/ADT/StringRef.h" 18 #include "llvm/Support/Compiler.h" 19 #include "llvm/Support/MemoryBuffer.h" 20 #include <cassert> 21 #include <map> 22 #include <memory> 23 #include <optional> 24 #include <string> 25 #include <vector> 26 27 namespace llvm { 28 29 class MemoryBuffer; 30 31 } // namespace llvm 32 33 namespace clang { 34 35 namespace frontend { 36 37 enum ActionKind { 38 /// Parse ASTs and list Decl nodes. 39 ASTDeclList, 40 41 /// Parse ASTs and dump them. 42 ASTDump, 43 44 /// Parse ASTs and print them. 45 ASTPrint, 46 47 /// Parse ASTs and view them in Graphviz. 48 ASTView, 49 50 /// Dump the compiler configuration. 51 DumpCompilerOptions, 52 53 /// Dump out raw tokens. 54 DumpRawTokens, 55 56 /// Dump out preprocessed tokens. 57 DumpTokens, 58 59 /// Emit a .s file. 60 EmitAssembly, 61 62 /// Emit a .bc file. 63 EmitBC, 64 65 /// Translate input source into HTML. 66 EmitHTML, 67 68 /// Emit a .cir file 69 EmitCIR, 70 71 /// Emit a .ll file. 72 EmitLLVM, 73 74 /// Generate LLVM IR, but do not emit anything. 75 EmitLLVMOnly, 76 77 /// Generate machine code, but don't emit anything. 78 EmitCodeGenOnly, 79 80 /// Emit a .o file. 81 EmitObj, 82 83 // Extract API information 84 ExtractAPI, 85 86 /// Parse and apply any fixits to the source. 87 FixIt, 88 89 /// Generate pre-compiled module from a module map. 90 GenerateModule, 91 92 /// Generate pre-compiled module from a standard C++ module interface unit. 93 GenerateModuleInterface, 94 95 /// Generate reduced module interface for a standard C++ module interface 96 /// unit. 97 GenerateReducedModuleInterface, 98 99 /// Generate a C++20 header unit module from a header file. 100 GenerateHeaderUnit, 101 102 /// Generate pre-compiled header. 103 GeneratePCH, 104 105 /// Generate Interface Stub Files. 106 GenerateInterfaceStubs, 107 108 /// Only execute frontend initialization. 109 InitOnly, 110 111 /// Dump information about a module file. 112 ModuleFileInfo, 113 114 /// Load and verify that a PCH file is usable. 115 VerifyPCH, 116 117 /// Parse and perform semantic analysis. 118 ParseSyntaxOnly, 119 120 /// Run a plugin action, \see ActionName. 121 PluginAction, 122 123 /// Print the "preamble" of the input file 124 PrintPreamble, 125 126 /// -E mode. 127 PrintPreprocessedInput, 128 129 /// Expand macros but not \#includes. 130 RewriteMacros, 131 132 /// ObjC->C Rewriter. 133 RewriteObjC, 134 135 /// Rewriter playground 136 RewriteTest, 137 138 /// Run one or more source code analyses. 139 RunAnalysis, 140 141 /// Dump template instantiations 142 TemplightDump, 143 144 /// Just lex, no output. 145 RunPreprocessorOnly, 146 147 /// Print the output of the dependency directives source minimizer. 148 PrintDependencyDirectivesSourceMinimizerOutput 149 }; 150 151 } // namespace frontend 152 153 /// The kind of a file that we've been handed as an input. 154 class InputKind { 155 public: 156 /// The input file format. 157 enum Format { 158 Source, 159 ModuleMap, 160 Precompiled 161 }; 162 163 // If we are building a header unit, what kind it is; this affects whether 164 // we look for the file in the user or system include search paths before 165 // flagging a missing input. 166 enum HeaderUnitKind { 167 HeaderUnit_None, 168 HeaderUnit_User, 169 HeaderUnit_System, 170 HeaderUnit_Abs 171 }; 172 173 private: 174 Language Lang; 175 LLVM_PREFERRED_TYPE(Format) 176 unsigned Fmt : 3; 177 LLVM_PREFERRED_TYPE(bool) 178 unsigned Preprocessed : 1; 179 LLVM_PREFERRED_TYPE(HeaderUnitKind) 180 unsigned HeaderUnit : 3; 181 LLVM_PREFERRED_TYPE(bool) 182 unsigned IsHeader : 1; 183 184 public: 185 constexpr InputKind(Language L = Language::Unknown, Format F = Source, 186 bool PP = false, HeaderUnitKind HU = HeaderUnit_None, 187 bool HD = false) Lang(L)188 : Lang(L), Fmt(F), Preprocessed(PP), HeaderUnit(HU), IsHeader(HD) {} 189 getLanguage()190 Language getLanguage() const { return static_cast<Language>(Lang); } getFormat()191 Format getFormat() const { return static_cast<Format>(Fmt); } getHeaderUnitKind()192 HeaderUnitKind getHeaderUnitKind() const { 193 return static_cast<HeaderUnitKind>(HeaderUnit); 194 } isPreprocessed()195 bool isPreprocessed() const { return Preprocessed; } isHeader()196 bool isHeader() const { return IsHeader; } isHeaderUnit()197 bool isHeaderUnit() const { return HeaderUnit != HeaderUnit_None; } 198 199 /// Is the input kind fully-unknown? isUnknown()200 bool isUnknown() const { return Lang == Language::Unknown && Fmt == Source; } 201 202 /// Is the language of the input some dialect of Objective-C? isObjectiveC()203 bool isObjectiveC() const { 204 return Lang == Language::ObjC || Lang == Language::ObjCXX; 205 } 206 getPreprocessed()207 InputKind getPreprocessed() const { 208 return InputKind(getLanguage(), getFormat(), true, getHeaderUnitKind(), 209 isHeader()); 210 } 211 getHeader()212 InputKind getHeader() const { 213 return InputKind(getLanguage(), getFormat(), isPreprocessed(), 214 getHeaderUnitKind(), true); 215 } 216 withHeaderUnit(HeaderUnitKind HU)217 InputKind withHeaderUnit(HeaderUnitKind HU) const { 218 return InputKind(getLanguage(), getFormat(), isPreprocessed(), HU, 219 isHeader()); 220 } 221 withFormat(Format F)222 InputKind withFormat(Format F) const { 223 return InputKind(getLanguage(), F, isPreprocessed(), getHeaderUnitKind(), 224 isHeader()); 225 } 226 }; 227 228 /// An input file for the front end. 229 class FrontendInputFile { 230 /// The file name, or "-" to read from standard input. 231 std::string File; 232 233 /// The input, if it comes from a buffer rather than a file. This object 234 /// does not own the buffer, and the caller is responsible for ensuring 235 /// that it outlives any users. 236 std::optional<llvm::MemoryBufferRef> Buffer; 237 238 /// The kind of input, e.g., C source, AST file, LLVM IR. 239 InputKind Kind; 240 241 /// Whether we're dealing with a 'system' input (vs. a 'user' input). 242 bool IsSystem = false; 243 244 public: 245 FrontendInputFile() = default; 246 FrontendInputFile(StringRef File, InputKind Kind, bool IsSystem = false) 247 : File(File.str()), Kind(Kind), IsSystem(IsSystem) {} 248 FrontendInputFile(llvm::MemoryBufferRef Buffer, InputKind Kind, 249 bool IsSystem = false) Buffer(Buffer)250 : Buffer(Buffer), Kind(Kind), IsSystem(IsSystem) {} 251 getKind()252 InputKind getKind() const { return Kind; } isSystem()253 bool isSystem() const { return IsSystem; } 254 isEmpty()255 bool isEmpty() const { return File.empty() && Buffer == std::nullopt; } isFile()256 bool isFile() const { return !isBuffer(); } isBuffer()257 bool isBuffer() const { return Buffer != std::nullopt; } isPreprocessed()258 bool isPreprocessed() const { return Kind.isPreprocessed(); } isHeader()259 bool isHeader() const { return Kind.isHeader(); } getHeaderUnitKind()260 InputKind::HeaderUnitKind getHeaderUnitKind() const { 261 return Kind.getHeaderUnitKind(); 262 } 263 getFile()264 StringRef getFile() const { 265 assert(isFile()); 266 return File; 267 } 268 getBuffer()269 llvm::MemoryBufferRef getBuffer() const { 270 assert(isBuffer()); 271 return *Buffer; 272 } 273 }; 274 275 /// FrontendOptions - Options for controlling the behavior of the frontend. 276 class FrontendOptions { 277 public: 278 /// Disable memory freeing on exit. 279 LLVM_PREFERRED_TYPE(bool) 280 unsigned DisableFree : 1; 281 282 /// When generating PCH files, instruct the AST writer to create relocatable 283 /// PCH files. 284 LLVM_PREFERRED_TYPE(bool) 285 unsigned RelocatablePCH : 1; 286 287 /// Show the -help text. 288 LLVM_PREFERRED_TYPE(bool) 289 unsigned ShowHelp : 1; 290 291 /// Show frontend performance metrics and statistics. 292 LLVM_PREFERRED_TYPE(bool) 293 unsigned ShowStats : 1; 294 295 LLVM_PREFERRED_TYPE(bool) 296 unsigned AppendStats : 1; 297 298 /// print the supported cpus for the current target 299 LLVM_PREFERRED_TYPE(bool) 300 unsigned PrintSupportedCPUs : 1; 301 302 /// Print the supported extensions for the current target. 303 LLVM_PREFERRED_TYPE(bool) 304 unsigned PrintSupportedExtensions : 1; 305 306 /// Print the extensions enabled for the current target. 307 LLVM_PREFERRED_TYPE(bool) 308 unsigned PrintEnabledExtensions : 1; 309 310 /// Show the -version text. 311 LLVM_PREFERRED_TYPE(bool) 312 unsigned ShowVersion : 1; 313 314 /// Apply fixes even if there are unfixable errors. 315 LLVM_PREFERRED_TYPE(bool) 316 unsigned FixWhatYouCan : 1; 317 318 /// Apply fixes only for warnings. 319 LLVM_PREFERRED_TYPE(bool) 320 unsigned FixOnlyWarnings : 1; 321 322 /// Apply fixes and recompile. 323 LLVM_PREFERRED_TYPE(bool) 324 unsigned FixAndRecompile : 1; 325 326 /// Apply fixes to temporary files. 327 LLVM_PREFERRED_TYPE(bool) 328 unsigned FixToTemporaries : 1; 329 330 /// Skip over function bodies to speed up parsing in cases you do not need 331 /// them (e.g. with code completion). 332 LLVM_PREFERRED_TYPE(bool) 333 unsigned SkipFunctionBodies : 1; 334 335 /// Whether we can use the global module index if available. 336 LLVM_PREFERRED_TYPE(bool) 337 unsigned UseGlobalModuleIndex : 1; 338 339 /// Whether we can generate the global module index if needed. 340 LLVM_PREFERRED_TYPE(bool) 341 unsigned GenerateGlobalModuleIndex : 1; 342 343 /// Whether we include declaration dumps in AST dumps. 344 LLVM_PREFERRED_TYPE(bool) 345 unsigned ASTDumpDecls : 1; 346 347 /// Whether we deserialize all decls when forming AST dumps. 348 LLVM_PREFERRED_TYPE(bool) 349 unsigned ASTDumpAll : 1; 350 351 /// Whether we include lookup table dumps in AST dumps. 352 LLVM_PREFERRED_TYPE(bool) 353 unsigned ASTDumpLookups : 1; 354 355 /// Whether we include declaration type dumps in AST dumps. 356 LLVM_PREFERRED_TYPE(bool) 357 unsigned ASTDumpDeclTypes : 1; 358 359 /// Whether we are performing an implicit module build. 360 LLVM_PREFERRED_TYPE(bool) 361 unsigned BuildingImplicitModule : 1; 362 363 /// Whether to use a filesystem lock when building implicit modules. 364 LLVM_PREFERRED_TYPE(bool) 365 unsigned BuildingImplicitModuleUsesLock : 1; 366 367 /// Whether we should embed all used files into the PCM file. 368 LLVM_PREFERRED_TYPE(bool) 369 unsigned ModulesEmbedAllFiles : 1; 370 371 /// Whether timestamps should be written to the produced PCH file. 372 LLVM_PREFERRED_TYPE(bool) 373 unsigned IncludeTimestamps : 1; 374 375 /// Should a temporary file be used during compilation. 376 LLVM_PREFERRED_TYPE(bool) 377 unsigned UseTemporary : 1; 378 379 /// When using -emit-module, treat the modulemap as a system module. 380 LLVM_PREFERRED_TYPE(bool) 381 unsigned IsSystemModule : 1; 382 383 /// Output (and read) PCM files regardless of compiler errors. 384 LLVM_PREFERRED_TYPE(bool) 385 unsigned AllowPCMWithCompilerErrors : 1; 386 387 /// Whether to share the FileManager when building modules. 388 LLVM_PREFERRED_TYPE(bool) 389 unsigned ModulesShareFileManager : 1; 390 391 /// Whether to emit symbol graph files as a side effect of compilation. 392 LLVM_PREFERRED_TYPE(bool) 393 unsigned EmitSymbolGraph : 1; 394 395 /// Whether to emit additional symbol graphs for extended modules. 396 LLVM_PREFERRED_TYPE(bool) 397 unsigned EmitExtensionSymbolGraphs : 1; 398 399 /// Whether to emit symbol labels for testing in generated symbol graphs 400 LLVM_PREFERRED_TYPE(bool) 401 unsigned EmitSymbolGraphSymbolLabelsForTesting : 1; 402 403 /// Whether to emit symbol labels for testing in generated symbol graphs 404 LLVM_PREFERRED_TYPE(bool) 405 unsigned EmitPrettySymbolGraphs : 1; 406 407 /// Whether to generate reduced BMI for C++20 named modules. 408 LLVM_PREFERRED_TYPE(bool) 409 unsigned GenReducedBMI : 1; 410 411 /// Use Clang IR pipeline to emit code 412 LLVM_PREFERRED_TYPE(bool) 413 unsigned UseClangIRPipeline : 1; 414 415 /// Disable Clang IR specific (CIR) passes 416 LLVM_PREFERRED_TYPE(bool) 417 unsigned ClangIRDisablePasses : 1; 418 419 /// Disable Clang IR (CIR) verifier 420 LLVM_PREFERRED_TYPE(bool) 421 unsigned ClangIRDisableCIRVerifier : 1; 422 423 CodeCompleteOptions CodeCompleteOpts; 424 425 /// Specifies the output format of the AST. 426 ASTDumpOutputFormat ASTDumpFormat = ADOF_Default; 427 428 /// The input kind, either specified via -x argument or deduced from the input 429 /// file name. 430 InputKind DashX; 431 432 /// The input files and their types. 433 SmallVector<FrontendInputFile, 0> Inputs; 434 435 /// When the input is a module map, the original module map file from which 436 /// that map was inferred, if any (for umbrella modules). 437 std::string OriginalModuleMap; 438 439 /// The output file, if any. 440 std::string OutputFile; 441 442 /// If given, the new suffix for fix-it rewritten files. 443 std::string FixItSuffix; 444 445 /// If given, filter dumped AST Decl nodes by this substring. 446 std::string ASTDumpFilter; 447 448 /// If given, enable code completion at the provided location. 449 ParsedSourceLocation CodeCompletionAt; 450 451 /// The frontend action to perform. 452 frontend::ActionKind ProgramAction = frontend::ParseSyntaxOnly; 453 454 /// The name of the action to run when using a plugin action. 455 std::string ActionName; 456 457 // Currently this is only used as part of the `-extract-api` action. 458 /// The name of the product the input files belong too. 459 std::string ProductName; 460 461 // Currently this is only used as part of the `-extract-api` action. 462 // A comma separated list of files providing a list of APIs to 463 // ignore when extracting documentation. 464 std::vector<std::string> ExtractAPIIgnoresFileList; 465 466 // Location of output directory where symbol graph information would 467 // be dumped. This overrides regular -o output file specification 468 std::string SymbolGraphOutputDir; 469 470 /// Args to pass to the plugins 471 std::map<std::string, std::vector<std::string>> PluginArgs; 472 473 /// The list of plugin actions to run in addition to the normal action. 474 std::vector<std::string> AddPluginActions; 475 476 /// The list of plugins to load. 477 std::vector<std::string> Plugins; 478 479 /// The list of module file extensions. 480 std::vector<std::shared_ptr<ModuleFileExtension>> ModuleFileExtensions; 481 482 /// The list of module map files to load before processing the input. 483 std::vector<std::string> ModuleMapFiles; 484 485 /// The list of additional prebuilt module files to load before 486 /// processing the input. 487 std::vector<std::string> ModuleFiles; 488 489 /// The list of files to embed into the compiled module file. 490 std::vector<std::string> ModulesEmbedFiles; 491 492 /// The list of AST files to merge. 493 std::vector<std::string> ASTMergeFiles; 494 495 /// A list of arguments to forward to LLVM's option processing; this 496 /// should only be used for debugging and experimental features. 497 std::vector<std::string> LLVMArgs; 498 499 /// A list of arguments to forward to MLIR's option processing; this 500 /// should only be used for debugging and experimental features. 501 std::vector<std::string> MLIRArgs; 502 503 /// File name of the file that will provide record layouts 504 /// (in the format produced by -fdump-record-layouts). 505 std::string OverrideRecordLayoutsFile; 506 507 /// Auxiliary triple for CUDA/HIP compilation. 508 std::string AuxTriple; 509 510 /// Auxiliary target CPU for CUDA/HIP compilation. 511 std::optional<std::string> AuxTargetCPU; 512 513 /// Auxiliary target features for CUDA/HIP compilation. 514 std::optional<std::vector<std::string>> AuxTargetFeatures; 515 516 /// Filename to write statistics to. 517 std::string StatsFile; 518 519 /// Minimum time granularity (in microseconds) traced by time profiler. 520 unsigned TimeTraceGranularity; 521 522 /// Make time trace capture verbose event details (e.g. source filenames). 523 /// This can increase the size of the output by 2-3 times. 524 LLVM_PREFERRED_TYPE(bool) 525 unsigned TimeTraceVerbose : 1; 526 527 /// Path which stores the output files for -ftime-trace 528 std::string TimeTracePath; 529 530 /// Output Path for module output file. 531 std::string ModuleOutputPath; 532 533 /// Output path to dump ranges of deserialized declarations to use as 534 /// minimization hints. 535 std::string DumpMinimizationHintsPath; 536 537 public: FrontendOptions()538 FrontendOptions() 539 : DisableFree(false), RelocatablePCH(false), ShowHelp(false), 540 ShowStats(false), AppendStats(false), ShowVersion(false), 541 FixWhatYouCan(false), FixOnlyWarnings(false), FixAndRecompile(false), 542 FixToTemporaries(false), SkipFunctionBodies(false), 543 UseGlobalModuleIndex(true), GenerateGlobalModuleIndex(true), 544 ASTDumpDecls(false), ASTDumpLookups(false), 545 BuildingImplicitModule(false), BuildingImplicitModuleUsesLock(true), 546 ModulesEmbedAllFiles(false), IncludeTimestamps(true), 547 UseTemporary(true), AllowPCMWithCompilerErrors(false), 548 ModulesShareFileManager(true), EmitSymbolGraph(false), 549 EmitExtensionSymbolGraphs(false), 550 EmitSymbolGraphSymbolLabelsForTesting(false), 551 EmitPrettySymbolGraphs(false), GenReducedBMI(false), 552 UseClangIRPipeline(false), ClangIRDisablePasses(false), 553 ClangIRDisableCIRVerifier(false), TimeTraceGranularity(500), 554 TimeTraceVerbose(false) {} 555 556 /// getInputKindForExtension - Return the appropriate input kind for a file 557 /// extension. For example, "c" would return Language::C. 558 /// 559 /// \return The input kind for the extension, or Language::Unknown if the 560 /// extension is not recognized. 561 static InputKind getInputKindForExtension(StringRef Extension); 562 }; 563 564 } // namespace clang 565 566 #endif // LLVM_CLANG_FRONTEND_FRONTENDOPTIONS_H 567