ROSE
0.11.96.11
|
Command line parsing.
This namespace encapsulates those things necessary for parsing the command-line for a ROSE-based tool. Command-lines consist of switches and their arguments, and positional arguments. The command-line parsers in this class are mainly for parsing the switches and their arguments, while the remaining non-switch, positional arguments can be retreived for parsing in a per-tool specific manner.
Command-line switches consist of an introductory sequence of characters (usually a hyphen or two) followed by the switch name. If the switch takes an argument (or arguments), that argument can be specified either as a separate entry in the program argument list (usually "argv") or separated from the switch name with an equal sign. On Unix systems, switches can also be single letters, can nestle together, and can take arguments either in the same argv
entry or in the following entry.
Related switches are collected into switch groups which also have names. The name of the group is usually precedes the switch name and is separated from it by a colon. Group names are optional on the command-line if the switch name is unambiguous.
All of these behaviors can be adjusted using the underlying Sawyer::CommandLine API.
Parsers come in two flavors. The first flavor, "normal parsers", are suitable for programs that are able to define all their legal switches. They parse command-line switches and until they get to the first positional argument, or they can be configured to collect and skip over the positional arguments if desired.
The second flavor of parser, a "parser stage", is for programs that are unable or unwilling to define all their switches. In this mode, if a program argument has a prefix (e.g., "-") that looks like a switch but hasn't been defined as one, then it's considered to be an unrecognized switch and that single program argument is consumed and stored in an unrecognized switches list. Note that this is not a rigorous way to parse command-lines since the parser has no knowledge of how many arguments a switch takes. For instance, if "-log" is a valid, defined switch that takes one argument, and "-yaxis" is undefined but takes as an argument a sign ("+" or "-") followed by the word "linear" or "log", then the command "a.out -yaxis -log foo bar" will be parsed as having an undefined switch "-yaxis" followed by the switch "-log" whose argument is "foo", followed by one positional argument "bar". The correct parsing, had yaxis been defined, would have been switch "-yaxis" whose argument is "-log" followed by two positional arguments "foo" and "bar".
This API is part of the ROSE library and can call any functions in the ROSE library. See also, CommandlineProcessing, which has only lower-level functions that cannot call other parts of the ROSE library.
Classes | |
class | DurationParser |
Command-line parser for durations. More... | |
struct | GenericSwitchArgs |
Type for storing generic switch arguments. More... | |
class | IntervalParser |
Parse an interval. More... | |
class | SelfTest |
Base class for self tests. More... | |
class | SelfTests |
Run self tests from the command-line, then exit. More... | |
class | ShowLicenseAndExit |
Show license text and exit. More... | |
class | SuffixMultiplierParser |
Parse values followed by unit names. More... | |
Functions | |
DurationParser::Ptr | durationParser () |
Constructs a DurationParser. | |
template<class Interval > | |
IntervalParser< Interval >::Ptr | intervalParser (Interval &storage) |
template<class Interval > | |
IntervalParser< Interval >::Ptr | intervalParser (std::vector< Interval > &storage) |
template<class Interval > | |
IntervalParser< Interval >::Ptr | intervalParser (Sawyer::Container::IntervalSet< Interval > &storage) |
template<class Interval > | |
IntervalParser< Interval >::Ptr | intervalParser () |
ROSE_DLL_API Sawyer::CommandLine::Parser | createEmptyParser (const std::string &purpose, const std::string &description) |
Empty command-line parser. More... | |
ROSE_DLL_API Sawyer::CommandLine::Parser | createEmptyParserStage (const std::string &purpose, const std::string &description) |
Empty command-line parser suitable for use with other parsers. More... | |
ROSE_DLL_API Sawyer::CommandLine::SwitchGroup | genericSwitches () |
Generic command-line components. More... | |
ROSE_DLL_API void | insertBooleanSwitch (Sawyer::CommandLine::SwitchGroup &, const std::string &switchName, bool &storageLocation, const std::string &documentation) |
Convenience for for adding Boolean switches. More... | |
ROSE_DLL_API void | runSelfTestsAndExit () |
Runs the self tests and then exits the program. More... | |
template<class SelfTest > | |
void | insertSelfTest () |
Convenient way to add a command-line self test. | |
template<class T > | |
SuffixMultiplierParser< T >::Ptr | suffixMultiplierParser (T &storage) |
template<class T > | |
SuffixMultiplierParser< T >::Ptr | suffixMultiplierParser (std::vector< T > &storage) |
template<class T > | |
SuffixMultiplierParser< T >::Ptr | suffixMultiplierParser () |
Variables | |
const char * | licenseText |
Text of the ROSE software license. More... | |
ROSE_DLL_API GenericSwitchArgs | genericSwitchArgs |
Global location for parsed generic command-line switches. More... | |
ROSE_DLL_API std::vector< SelfTest::Ptr > | selfTests |
Collection of self tests to be run by –self-tests switch. More... | |
ROSE_DLL_API std::string | versionString |
Global location for version string. More... | |
DurationParser::Ptr Rose::CommandLine::durationParser | ( | uint64_t & | storage | ) |
Constructs a DurationParser.
When the parser runs, it stores the parsed result in storage
.
DurationParser::Ptr Rose::CommandLine::durationParser | ( | Sawyer::Optional< uint64_t > & | storage | ) |
Constructs a DurationParser.
When the parser runs, it stores the parsed result in storage
.
ROSE_DLL_API Sawyer::CommandLine::Parser Rose::CommandLine::createEmptyParser | ( | const std::string & | purpose, |
const std::string & | description | ||
) |
Empty command-line parser.
Returns a command-line parser that has no switch declarations, but is set up consistently for ROSE tools. The purpose
should be an uncapitalized, short, single-line string that appears near the top of the man page. The description
can be much longer, multiple paragraphs, free-format, with Sawyer markup. It will appear under the heading "Description" in the man page.
See also, createEmptyParserStage.
ROSE_DLL_API Sawyer::CommandLine::Parser Rose::CommandLine::createEmptyParserStage | ( | const std::string & | purpose, |
const std::string & | description | ||
) |
Empty command-line parser suitable for use with other parsers.
Returns a command-line parser that has no switch declarations, but is set up consistently for ROSE tools. The parser is configured to skip over any program arguments it doesn't recognize, with the assumption that those arguments will be passed to another parser. This also means that this parser cannot report errors for misspelled or misused switches because it cannot tell whether the switch is misspelled or simply intended for the next parser.
The purpose
should be an uncapitalized, short, single-line string that appears near the top of the man page. The description
can be much longer, multiple paragraphs, free-format, with Sawyer markup. It will appear under the heading "Description" in the man page.
See also, createEmptyParser, genericSwitches.
ROSE_DLL_API Sawyer::CommandLine::SwitchGroup Rose::CommandLine::genericSwitches | ( | ) |
Generic command-line components.
Returns a description of the switches that should be available for all ROSE tools. For consistency's sake, most tools will want to have at least this set of switches which is intended to be common across all tools. These switches fall into some categories:
To make a command-line parser that recognizes these switches, add the switches to the parser using its with
method. For example, here's how to construct a parser that recognizes only these switches:
In general, we want all tools to have all these switches. At a minimum, a tool developer should be aware that the switches in this group are in some sense reserved across all tools and should not be circumvented for other purposes. However, if a tool doesn't use a switch, the developer can remove that switch from the parser and its documentation in order to prevent user confusion. Here's an example of removing the "--threads" switch from a parser for a tool that doesn't support multiple threads:
If you encounter strange errors near this call, make sure you're using -pthread consistently in your compile and link commands. Its presence or absence should be the same as however the ROSE library itself was compiled and linked. Mixing up the -pthread switch creates ABI incompatibilities that manifest themselves in various ways that usually look like a problem with a function that's called from a program that uses librose: often a segmentation fault, but can also be hangs, incorrect results, etc. Note that -pthread is both a compile and a link switch.
See any recent tool for more examples.
See also, createEmptyParser, createEmptyParserStage.
ROSE_DLL_API void Rose::CommandLine::insertBooleanSwitch | ( | Sawyer::CommandLine::SwitchGroup & | , |
const std::string & | switchName, | ||
bool & | storageLocation, | ||
const std::string & | documentation | ||
) |
Convenience for for adding Boolean switches.
Adds "--foo" (if switchName
is "foo") and "--no-foo" to the specified switch group. The storage location's lifetime must extend to the point where the command-line is parsed. This function adds additional documentation describing how to disable the switch using "--no-foo" and what the default is (current value of storage location).
An alternative is to use a switch that takes a Boolean argument (e.g., "--foo=yes" or "--foo=no"), but this is more difficult for users to remember and type than just "--foo" and "--no-foo".
See also, createEmptyParser, createEmptyParserStage.
ROSE_DLL_API void Rose::CommandLine::runSelfTestsAndExit | ( | ) |
Runs the self tests and then exits the program.
Sequentially runs the self tests in selfTests
and then exits. Exit status is success if and only if no test returns false. Tests that are null pointers are ignored.
const char* Rose::CommandLine::licenseText |
Text of the ROSE software license.
This text comes directly from the LicenseInformation/ROSE_BSD_License.txt file in the source code.
ROSE_DLL_API GenericSwitchArgs Rose::CommandLine::genericSwitchArgs |
Global location for parsed generic command-line switches.
This global variable holds the results of command-line parsing using genericSwitches. Normally these settings are passed per command-line parsing request, but the interface in ROSE doesn't have that ability yet, so we use a global variable.
See also, genericSwitches.
ROSE_DLL_API std::vector<SelfTest::Ptr> Rose::CommandLine::selfTests |
Collection of self tests to be run by –self-tests switch.
The unit tests are run sequentially from first to last, optionally stopping at the first test that fails. Null pointers are ignored without causing any failure.
Referenced by insertSelfTest().
ROSE_DLL_API std::string Rose::CommandLine::versionString |
Global location for version string.
This is the string that's printed by the –version switch (usually). It defaults to the ROSE library version number, but can be overridden by tools. When overriding, the tool should change this version string before constructing the command-line parser.
See also, genericSwitches.