Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[RFC] Refactor command line options #4404

Open
wants to merge 2 commits into
base: develop
Choose a base branch
from

Conversation

peterschrammel
Copy link
Member

@peterschrammel peterschrammel commented Mar 18, 2019

Before I go ahead with this rather big refactoring, I'd like to collect some feedback and additional requirements that you might think of.

a1496e0 is to showcase some of the capabilities.
CI is expected to fail.

Currently, I have the following requirements:

  • export machine-readable commandline options output (JSON/XML) for downstream consumption
  • export information on deprecated options for downstream consumption
  • a step further towards making plain/json/xml output clean (there's no help/usage output in JSON/XML at the moment)
  • make sure plain help text is always properly formatted and wrapped
  • prepare for unifying cmdlinet->optionst parsing code

Checklist:

  • Each commit message has a non-empty body, explaining why the change was made.
  • Methods or procedures I have added are documented, following the guidelines provided in CODING_STANDARD.md.
  • The feature or user visible behaviour I have added or modified has been documented in the User Guide in doc/cprover-manual/
  • Regression or unit tests are included, or existing tests cover the modified code (in this case I have detailed which ones those are in the commit message).
  • My commit message includes data points confirming performance improvements (if claimed).
  • My PR is restricted to a single feature or bugfix.
  • White-space or formatting changes outside the feature-related changed lines are in commits of their own.

@LAJW
Copy link
Contributor

LAJW commented Mar 20, 2019

Looks decent, though I had something like this in mind: https://www.npmjs.com/package/commander where each command could have its own parser. But it requires std::any (or a polyfill).

@peterschrammel
Copy link
Member Author

peterschrammel commented Mar 21, 2019

where each command could have its own parser.

I don't think that we have an issue with the raw parsing. Most of the mess comes from duplicating the translation into a configuration object (optionst) across all driver programs. My vague plans for the second step there are to associate these translations with a cmdline_definitiont/cmdline_optiont. That will factor out all the verbose cmdline->options code. In third step we could then transition to more structured configuration objects.

@peterschrammel peterschrammel force-pushed the refactor-parse-options branch from 6ecae31 to a1496e0 Compare March 21, 2019 15:43
@martin-cs
Copy link
Collaborator

These sound like reasonable goals. Bringing some sanity to the option handling of goto-instrument and goto-analyzer and not having to manually duplicate and parallel maintain their command options would make me very happy. If we could also do a rationalisation / orthogonalisation on the options that would also be great. One of the selling points of CBMC used to be that it didn't have an insane number of options.

I'm not sure that I understand from the patch how the new system is supposed to work; perhaps you could write a little bit describing it? The main value(?) of separating cmdlinet and optionst is in giving sane defaults and flagging combinations that don't work. As long as we can do that I think it could be a big improvement.

One point of pedantry; can we call the combined thing something more like options or parameters rather than command line because it would be nice to believe in a world where that config might come from somewhere else.

[ Inflammatory, unhelpful suggestion -- maybe we could also include configt in this refactor ... ]

@martin-cs
Copy link
Collaborator

Oh yes; for keeping things in sync, there is also the question of the Java tools.

Copy link
Collaborator

@tautschnig tautschnig left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you for starting to work on this! Yet I am surprised that #1521 isn't referenced here. Maybe this PR can even go all the way and eventually close that issue?

OPT_VALIDATE \
OPT_ANSI_C_LANGUAGE \
"(claim):(show-claims)(floatbv)(all-claims)(all-properties)" // legacy, and will eventually disappear // NOLINT(whitespace/line_length)
const cmdline_definitiont ui_options
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A rather unrelated comment: does anyone know why this ever needed to go in the header file? I.e., not just the changes in this PR, but also the current CBMC_OPTIONS?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No idea :D

optionalt<argumentt> argument,
std::string help_text,
std::string option_group,
optionalt<deprecatedt> deprecated);
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Wouldn't it make for a very easy (and IMHO) nice extension to have a second constructor that takes a std::function for argument parsing (possibly achieving what @LAJW suggested)?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That requires a bit more thinking as many options are not independent... I have a few ideas...

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Speaking of dependent options: it would actually be nice if one had a way to specify implied options (e.g., --z3 implies --smt2). But I suppose the wish-list is unbounded (what about conflicting options...) 😇


cmdline_optiont(
std::string name,
optionalt<argumentt> argument,
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think we should use optionalt here (or below, for deprecated), just have multiple constructors with varying numbers of parameters. The optionalt class members of course still remain in place.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, although {} flows quite intuitively in the initialiser list...

optionalt<argumentt> argument;
std::string help_text;
std::string option_group;
optionalt<deprecatedt> deprecated;
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would like to propose one more member: hidden. At the moment, we have a number of command-line options that are intentionally undocumented, because either we consider them harmful (such as --no-propagation) or because they used to be supported and we just don't want to break scripts or other tooling still using them (such as --floatbv).

@tautschnig
Copy link
Collaborator

Maybe we should actually have a class hierarchy under cmdline_optiont, including cmdline_option_with_argumentt, deprecated_cmdline_optiont, hidden_cmdline_optiont? cmdline_optiont would just provide some virtual functions so that printing and reading any set values can be achieved. But I guess for a start multiple constructors with a single class make things easier.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
do not merge RFC Request for comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

9 participants