diff --git a/clang/include/clang/Driver/ClangOptionDocs.td b/clang/include/clang/Driver/ClangOptionDocs.td index a5ee577c5f45db..dea6a7ccb12c9a 100644 --- a/clang/include/clang/Driver/ClangOptionDocs.td +++ b/clang/include/clang/Driver/ClangOptionDocs.td @@ -27,11 +27,12 @@ GCC-compatible ``clang`` and ``clang++`` drivers. }]; - string Program = "clang"; + string Program = "Clang"; // Note: We *must* use DefaultVis and not ClangOption, since that's // the name of the actual TableGen record. The alias will not work. list VisibilityMask = ["DefaultVis"]; list IgnoreFlags = ["HelpHidden", "Unsupported", "Ignored"]; } +#define GENERATING_DOCS include "Options.td" diff --git a/clang/include/clang/Driver/Options.td b/clang/include/clang/Driver/Options.td index 95b464e7d61834..da0e97cc9be076 100644 --- a/clang/include/clang/Driver/Options.td +++ b/clang/include/clang/Driver/Options.td @@ -13,6 +13,25 @@ // Include the common option parsing interfaces. include "llvm/Option/OptParser.td" +// When generating documentation, we expect there to be a GlobalDocumentation +// def containing the program name that we are generating documentation for. +// This object should only be used by things that are used in documentation, +// such as the group descriptions. +#ifndef GENERATING_DOCS +// So that this file can still be parsed without such a def, define one if there +// isn't one provided. +def GlobalDocumentation { + // Sensible default in case of mistakes. + string Program = "Clang"; +} +#endif + +// Use this to generate program specific documentation, for example: +// StringForProgram<"Control how %Program behaves.">.str +class StringForProgram { + string str = !subst("%Program", GlobalDocumentation.Program, _str); +} + ///////// // Flags @@ -100,14 +119,16 @@ def Action_Group : OptionGroup<"">, DocName<"Actions">, // Meta-group for options which are only used for compilation, // and not linking etc. def CompileOnly_Group : OptionGroup<"">, - DocName<"Compilation options">, DocBrief<[{ -Flags controlling the behavior of Clang during compilation. These flags have -no effect during actions that do not perform compilation.}]>; + DocName<"Compilation options">, + DocBrief.str>; def Preprocessor_Group : OptionGroup<"">, Group, - DocName<"Preprocessor options">, DocBrief<[{ -Flags controlling the behavior of the Clang preprocessor.}]>; + DocName<"Preprocessor options">, + DocBrief.str>; def IncludePath_Group : OptionGroup<"">, Group, DocName<"Include path management">, @@ -128,9 +149,15 @@ def d_Group : OptionGroup<"">, Group, Flags allowing the state of the preprocessor to be dumped in various ways.}]>; def Diag_Group : OptionGroup<"">, Group, - DocName<"Diagnostic options">, DocBrief<[{ -Flags controlling which warnings, errors, and remarks Clang will generate. -See the :doc:`full list of warning and remark flags `.}]>; + DocName<"Diagnostic options">, + DocBrief.str, + // When in clang link directly to the page. + !cond(!eq(GlobalDocumentation.Program, "Clang"): +"See the :doc:`full list of warning and remark flags `.", + // When elsewhere the link will not work. + true: +"See Clang's Diagnostic Reference for a full list of warning and remark flags."))>; def R_Group : OptionGroup<"">, Group, DocFlatten; def R_value_Group : OptionGroup<"">, Group, diff --git a/clang/utils/TableGen/ClangOptionDocEmitter.cpp b/clang/utils/TableGen/ClangOptionDocEmitter.cpp index a4095950ca975f..3fe98909940749 100644 --- a/clang/utils/TableGen/ClangOptionDocEmitter.cpp +++ b/clang/utils/TableGen/ClangOptionDocEmitter.cpp @@ -342,9 +342,10 @@ void emitOption(const DocumentedOption &Option, const Record *DocInfo, })]; for (auto &S : SphinxOptionIDs) NextSuffix[S] = SphinxWorkaroundSuffix + 1; + + std::string Program = DocInfo->getValueAsString("Program").lower(); if (SphinxWorkaroundSuffix) - OS << ".. program:: " << DocInfo->getValueAsString("Program") - << SphinxWorkaroundSuffix << "\n"; + OS << ".. program:: " << Program << SphinxWorkaroundSuffix << "\n"; // Emit the names of the option. OS << ".. option:: "; @@ -353,7 +354,7 @@ void emitOption(const DocumentedOption &Option, const Record *DocInfo, EmittedAny = emitOptionNames(Option, OS, EmittedAny); }); if (SphinxWorkaroundSuffix) - OS << "\n.. program:: " << DocInfo->getValueAsString("Program"); + OS << "\n.. program:: " << Program; OS << "\n\n"; // Emit the description, if we have one. @@ -421,7 +422,7 @@ void clang::EmitClangOptDocs(RecordKeeper &Records, raw_ostream &OS) { return; } OS << DocInfo->getValueAsString("Intro") << "\n"; - OS << ".. program:: " << DocInfo->getValueAsString("Program") << "\n"; + OS << ".. program:: " << DocInfo->getValueAsString("Program").lower() << "\n"; emitDocumentation(0, extractDocumentation(Records, DocInfo), DocInfo, OS); } diff --git a/flang/docs/FlangOptionsDocs.td b/flang/docs/FlangOptionsDocs.td index 9189899e82c62d..14d033f8587e3b 100644 --- a/flang/docs/FlangOptionsDocs.td +++ b/flang/docs/FlangOptionsDocs.td @@ -24,10 +24,10 @@ Introduction }]; - string Program = "flang"; + string Program = "Flang"; list VisibilityMask = ["FlangOption"]; list IgnoreFlags = ["HelpHidden", "Unsupported", "Ignored"]; } - +#define GENERATING_DOCS include "Options.td"