diff options
author | Paolo Bonzini | 2020-11-03 14:48:11 +0100 |
---|---|---|
committer | Paolo Bonzini | 2021-01-23 21:55:08 +0100 |
commit | afd736252f106ec54734d4e412220a978f668430 (patch) | |
tree | 4a911bf4aadee42b5abdb9b50d44a9767457bb54 | |
parent | qemu-option: clean up id vs. list->merge_lists (diff) | |
download | qemu-afd736252f106ec54734d4e412220a978f668430.tar.gz qemu-afd736252f106ec54734d4e412220a978f668430.tar.xz qemu-afd736252f106ec54734d4e412220a978f668430.zip |
qemu-option: move help handling to get_opt_name_value
Right now, help options are parsed normally and then checked
specially in opt_validate, but only if coming from
qemu_opts_parse_noisily. has_help_option does the check on its own.
opt_validate() has two callers: qemu_opt_set(), which passes null and is
therefore unaffected, and opts_do_parse(), which is affected.
opts_do_parse() is called by qemu_opts_do_parse(), which passes null and
is therefore unaffected, and opts_parse().
opts_parse() is called by qemu_opts_parse() and qemu_opts_set_defaults(),
which pass null and are therefore unaffected, and
qemu_opts_parse_noisily().
Move the check from opt_validate to the parsing workhorse of QemuOpts,
get_opt_name_value. This will come in handy in the next patch, which
will raise a warning for "-object memory-backend-ram,share" ("flag" option
with no =on/=off part) but not for "-object memory-backend-ram,help".
As a result:
- opts_parse and opts_do_parse do not return an error anymore
when help is requested; qemu_opts_parse_noisily does not have
to work around that anymore.
- various crazy ways to request help are not recognized anymore:
- "help=..."
- "nohelp" (sugar for "help=off")
- "?=..."
- "no?" (sugar for "?=off")
- "help" would be recognized as help request even if there is a (foolishly
named) parameter "help". No such parameters exist, though.
Reviewed-by: Markus Armbruster <armbru@redhat.com>
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
-rw-r--r-- | util/qemu-option.c | 38 |
1 files changed, 23 insertions, 15 deletions
diff --git a/util/qemu-option.c b/util/qemu-option.c index 91f4120ce1..5f27d4369d 100644 --- a/util/qemu-option.c +++ b/util/qemu-option.c @@ -496,8 +496,7 @@ static QemuOpt *opt_create(QemuOpts *opts, const char *name, char *value, return opt; } -static bool opt_validate(QemuOpt *opt, bool *help_wanted, - Error **errp) +static bool opt_validate(QemuOpt *opt, Error **errp) { const QemuOptDesc *desc; const QemuOptsList *list = opt->opts->list; @@ -505,9 +504,6 @@ static bool opt_validate(QemuOpt *opt, bool *help_wanted, desc = find_desc_by_name(list->desc, opt->name); if (!desc && !opts_accepts_any(list)) { error_setg(errp, QERR_INVALID_PARAMETER, opt->name); - if (help_wanted && is_help_option(opt->name)) { - *help_wanted = true; - } return false; } @@ -524,7 +520,7 @@ bool qemu_opt_set(QemuOpts *opts, const char *name, const char *value, { QemuOpt *opt = opt_create(opts, name, g_strdup(value), false); - if (!opt_validate(opt, NULL, errp)) { + if (!opt_validate(opt, errp)) { qemu_opt_del(opt); return false; } @@ -760,10 +756,12 @@ void qemu_opts_print(QemuOpts *opts, const char *separator) static const char *get_opt_name_value(const char *params, const char *firstname, + bool *help_wanted, char **name, char **value) { const char *p; size_t len; + bool is_help = false; len = strcspn(params, "=,"); if (params[len] != '=') { @@ -780,6 +778,7 @@ static const char *get_opt_name_value(const char *params, *value = g_strdup("off"); } else { *value = g_strdup("on"); + is_help = is_help_option(*name); } } } else { @@ -791,6 +790,9 @@ static const char *get_opt_name_value(const char *params, } assert(!*p || *p == ','); + if (help_wanted && is_help) { + *help_wanted = true; + } if (*p == ',') { p++; } @@ -806,7 +808,12 @@ static bool opts_do_parse(QemuOpts *opts, const char *params, QemuOpt *opt; for (p = params; *p;) { - p = get_opt_name_value(p, firstname, &option, &value); + p = get_opt_name_value(p, firstname, help_wanted, &option, &value); + if (help_wanted && *help_wanted) { + g_free(option); + g_free(value); + return false; + } firstname = NULL; if (!strcmp(option, "id")) { @@ -817,7 +824,7 @@ static bool opts_do_parse(QemuOpts *opts, const char *params, opt = opt_create(opts, option, value, prepend); g_free(option); - if (!opt_validate(opt, help_wanted, errp)) { + if (!opt_validate(opt, errp)) { qemu_opt_del(opt); return false; } @@ -832,7 +839,7 @@ static char *opts_parse_id(const char *params) char *name, *value; for (p = params; *p;) { - p = get_opt_name_value(p, NULL, &name, &value); + p = get_opt_name_value(p, NULL, NULL, &name, &value); if (!strcmp(name, "id")) { g_free(name); return value; @@ -848,11 +855,10 @@ bool has_help_option(const char *params) { const char *p; char *name, *value; - bool ret; + bool ret = false; for (p = params; *p;) { - p = get_opt_name_value(p, NULL, &name, &value); - ret = is_help_option(name); + p = get_opt_name_value(p, NULL, &ret, &name, &value); g_free(name); g_free(value); if (ret) { @@ -937,11 +943,13 @@ QemuOpts *qemu_opts_parse_noisily(QemuOptsList *list, const char *params, QemuOpts *opts; bool help_wanted = false; - opts = opts_parse(list, params, permit_abbrev, false, &help_wanted, &err); - if (err) { + opts = opts_parse(list, params, permit_abbrev, false, + opts_accepts_any(list) ? NULL : &help_wanted, + &err); + if (!opts) { + assert(!!err + !!help_wanted == 1); if (help_wanted) { qemu_opts_print_help(list, true); - error_free(err); } else { error_report_err(err); } |