From: Daniel Dunbar Date: Fri, 4 Dec 2009 21:08:40 +0000 (+0000) Subject: OptTable: Allow option groups to be used to define "help groups", which will X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=2658f05caf1c1d86608a46ebc7be0b3bb21fef2a;p=clang OptTable: Allow option groups to be used to define "help groups", which will collate the options inside that group. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@90592 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/include/clang/Driver/OptParser.td b/include/clang/Driver/OptParser.td index 286c4d2336..a9f4289fc8 100644 --- a/include/clang/Driver/OptParser.td +++ b/include/clang/Driver/OptParser.td @@ -87,6 +87,7 @@ def HelpHidden : OptionFlag; class OptionGroup { string EnumName = ?; // Uses the def name if undefined. string Name = name; + string HelpText = ?; OptionGroup Group = ?; } diff --git a/include/clang/Driver/OptTable.h b/include/clang/Driver/OptTable.h index 840e669a27..edae75c9f0 100644 --- a/include/clang/Driver/OptTable.h +++ b/include/clang/Driver/OptTable.h @@ -118,6 +118,11 @@ namespace options { return getInfo(id).Kind; } + /// getOptionGroupID - Get the group id for the given option. + unsigned getOptionGroupID(OptSpecifier id) const { + return getInfo(id).GroupID; + } + /// isOptionHelpHidden - Should the help for the given option be hidden by /// default. bool isOptionHelpHidden(OptSpecifier id) const { diff --git a/lib/Driver/OptTable.cpp b/lib/Driver/OptTable.cpp index 9c6c9b49ae..f69d5d806d 100644 --- a/lib/Driver/OptTable.cpp +++ b/lib/Driver/OptTable.cpp @@ -14,7 +14,7 @@ #include "llvm/Support/raw_ostream.h" #include #include - +#include using namespace clang::driver; using namespace clang::driver::options; @@ -285,25 +285,10 @@ static std::string getOptionHelpName(const OptTable &Opts, OptSpecifier Id) { return Name; } -void OptTable::PrintHelp(llvm::raw_ostream &OS, const char *Name, - const char *Title, bool ShowHidden) const { - OS << "OVERVIEW: " << Title << "\n"; - OS << '\n'; - OS << "USAGE: " << Name << " [options] \n"; - OS << '\n'; - OS << "OPTIONS:\n"; - - // Render help text into (option, help) pairs. - std::vector< std::pair > OptionHelp; - for (unsigned i = 0, e = getNumOptions(); i != e; ++i) { - unsigned Id = i + 1; - - if (!ShowHidden && isOptionHelpHidden(Id)) - continue; - - if (const char *Text = getOptionHelpText(Id)) - OptionHelp.push_back(std::make_pair(getOptionHelpName(*this, Id), Text)); - } +static void PrintHelpOptionList(llvm::raw_ostream &OS, llvm::StringRef Title, + std::vector > &OptionHelp) { + OS << Title << ":\n"; // Find the maximum option length. unsigned OptionFieldWidth = 0; @@ -331,6 +316,62 @@ void OptTable::PrintHelp(llvm::raw_ostream &OS, const char *Name, } OS.indent(Pad + 1) << OptionHelp[i].second << '\n'; } +} + +static const char *getOptionHelpGroup(const OptTable &Opts, OptSpecifier Id) { + unsigned GroupID = Opts.getOptionGroupID(Id); + + // If not in a group, return the default help group. + if (!GroupID) + return "OPTIONS"; + + // Abuse the help text of the option groups to store the "help group" + // name. + // + // FIXME: Split out option groups. + if (const char *GroupHelp = Opts.getOptionHelpText(GroupID)) + return GroupHelp; + + // Otherwise keep looking. + return getOptionHelpGroup(Opts, GroupID); +} + +void OptTable::PrintHelp(llvm::raw_ostream &OS, const char *Name, + const char *Title, bool ShowHidden) const { + OS << "OVERVIEW: " << Title << "\n"; + OS << '\n'; + OS << "USAGE: " << Name << " [options] \n"; + OS << '\n'; + + // Render help text into a map of group-name to a list of (option, help) + // pairs. + typedef std::map > > helpmap_ty; + helpmap_ty GroupedOptionHelp; + + for (unsigned i = 0, e = getNumOptions(); i != e; ++i) { + unsigned Id = i + 1; + + // FIXME: Split out option groups. + if (getOptionKind(Id) == Option::GroupClass) + continue; + + if (!ShowHidden && isOptionHelpHidden(Id)) + continue; + + if (const char *Text = getOptionHelpText(Id)) { + const char *HelpGroup = getOptionHelpGroup(*this, Id); + const std::string &OptName = getOptionHelpName(*this, Id); + GroupedOptionHelp[HelpGroup].push_back(std::make_pair(OptName, Text)); + } + } + + for (helpmap_ty::iterator it = GroupedOptionHelp .begin(), + ie = GroupedOptionHelp.end(); it != ie; ++it) { + if (it != GroupedOptionHelp .begin()) + OS << "\n"; + PrintHelpOptionList(OS, it->first, it->second); + } OS.flush(); }