[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: [PATCH 12/25] qemu-config: add error propagation to qemu_config_pars
From: |
Markus Armbruster |
Subject: |
Re: [PATCH 12/25] qemu-config: add error propagation to qemu_config_parse |
Date: |
Mon, 25 Jan 2021 14:54:32 +0100 |
User-agent: |
Gnus/5.13 (Gnus v5.13) Emacs/27.1 (gnu/linux) |
Paolo Bonzini <pbonzini@redhat.com> writes:
> This enables some simplification of vl.c via error_fatal.
>
> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
> ---
> block/blkdebug.c | 3 +--
> include/qemu/config-file.h | 4 ++--
> softmmu/vl.c | 30 ++++++++++++------------------
> util/qemu-config.c | 20 ++++++++++----------
> 4 files changed, 25 insertions(+), 32 deletions(-)
>
> diff --git a/block/blkdebug.c b/block/blkdebug.c
> index 5fe6172da9..7eaa8a28bf 100644
> --- a/block/blkdebug.c
> +++ b/block/blkdebug.c
> @@ -279,9 +279,8 @@ static int read_config(BDRVBlkdebugState *s, const char
> *filename,
> return -errno;
> }
>
> - ret = qemu_config_parse(f, config_groups, filename);
> + ret = qemu_config_parse(f, config_groups, filename, errp);
> if (ret < 0) {
> - error_setg(errp, "Could not parse blkdebug config file");
> goto fail;
> }
> }
> diff --git a/include/qemu/config-file.h b/include/qemu/config-file.h
> index 7d26fe3816..da6f4690b7 100644
> --- a/include/qemu/config-file.h
> +++ b/include/qemu/config-file.h
> @@ -10,9 +10,9 @@ void qemu_add_opts(QemuOptsList *list);
> void qemu_add_drive_opts(QemuOptsList *list);
> int qemu_global_option(const char *str);
>
> -int qemu_config_parse(FILE *fp, QemuOptsList **lists, const char *fname);
> +int qemu_config_parse(FILE *fp, QemuOptsList **lists, const char *fname,
> Error **errp);
Long line.
>
> -int qemu_read_config_file(const char *filename);
> +int qemu_read_config_file(const char *filename, Error **errp);
>
> /* Parse QDict options as a replacement for a config file (allowing multiple
> enumerated (0..(n-1)) configuration "sections") */
> diff --git a/softmmu/vl.c b/softmmu/vl.c
> index d34307bf11..d991919155 100644
> --- a/softmmu/vl.c
> +++ b/softmmu/vl.c
> @@ -2056,17 +2056,20 @@ static int global_init_func(void *opaque, QemuOpts
> *opts, Error **errp)
> return 0;
> }
>
> -static int qemu_read_default_config_file(void)
> +static void qemu_read_default_config_file(Error **errp)
> {
> int ret;
> + Error *local_err = NULL;
> g_autofree char *file = get_relocated_path(CONFIG_QEMU_CONFDIR
> "/qemu.conf");
>
> - ret = qemu_read_config_file(file);
> - if (ret < 0 && ret != -ENOENT) {
> - return ret;
> + ret = qemu_read_config_file(file, &local_err);
> + if (ret < 0) {
> + if (ret == -ENOENT) {
> + error_free(local_err);
> + } else {
> + error_propagate(errp, local_err);
> + }
> }
> -
> - return 0;
> }
Please use ERRP_GUARD() in new code:
static void qemu_read_default_config_file(Error **errp)
{
ERRP_GUARD();
int ret;
g_autofree char *file = get_relocated_path(CONFIG_QEMU_CONFDIR
"/qemu.conf");
ret = qemu_read_config_file(file, errp);
if (ret == -ENOENT) {
error_free(*errp);
*errp = NULL;
}
}
>
> static int qemu_set_option(const char *str)
> @@ -2622,9 +2625,7 @@ void qemu_init(int argc, char **argv, char **envp)
> }
>
> if (userconfig) {
> - if (qemu_read_default_config_file() < 0) {
> - exit(1);
> - }
> + qemu_read_default_config_file(&error_fatal);
> }
>
> /* second pass of option parsing */
> @@ -3312,15 +3313,8 @@ void qemu_init(int argc, char **argv, char **envp)
> qemu_plugin_opt_parse(optarg, &plugin_list);
> break;
> case QEMU_OPTION_readconfig:
> - {
> - int ret = qemu_read_config_file(optarg);
> - if (ret < 0) {
> - error_report("read config %s: %s", optarg,
> - strerror(-ret));
> - exit(1);
> - }
> - break;
> - }
> + qemu_read_config_file(optarg, &error_fatal);
> + break;
More than just code simplifcation: you're deleting an extra error
message. Test case:
$ qemu-system-x86_64 -readconfig .
qemu: error reading file
qemu: -readconfig .: read config .: Invalid argument
Pretty bad. With your patch applied:
qemu-system-x86_64: error reading file
Worse :)
I actually expected this to come out as
qemu-system-x86_64: -readconfig .: error reading file
That would be an improvement.
The reason for the bad location information is here:
int qemu_config_parse(FILE *fp, QemuOptsList **lists, const char *fname,
Error **errp)
{
char line[1024], group[64], id[64], arg[64], value[1024];
Location loc;
QemuOptsList *list = NULL;
Error *local_err = NULL;
QemuOpts *opts = NULL;
int res = -EINVAL, lno = 0;
int count = 0;
loc_push_none(&loc);
while (fgets(line, sizeof(line), fp) != NULL) {
If the very first fgets() fails setting @fp's error indicator, ...
loc_set_file(fname, ++lno);
[...]
}
if (ferror(fp)) {
... we get here with error location "none", and ...
error_setg(errp, "error reading file");
... use it to report the error (remember, @errp is &error_fatal).
Independently, error_setg_errno() would be nice. Assuming we're willing
to rely on errno being useful after fgets().
goto out;
}
res = count;
out:
loc_pop(&loc);
return res;
}
Always, always, always test the error messages.
> case QEMU_OPTION_spice:
> olist = qemu_find_opts_err("spice", NULL);
> if (!olist) {
> diff --git a/util/qemu-config.c b/util/qemu-config.c
> index a4a1324c68..d0629f4960 100644
> --- a/util/qemu-config.c
> +++ b/util/qemu-config.c
> @@ -308,7 +308,7 @@ void qemu_add_opts(QemuOptsList *list)
> }
>
> /* Returns number of config groups on success, -errno on error */
> -int qemu_config_parse(FILE *fp, QemuOptsList **lists, const char *fname)
> +int qemu_config_parse(FILE *fp, QemuOptsList **lists, const char *fname,
> Error **errp)
> {
> char line[1024], group[64], id[64], arg[64], value[1024];
> Location loc;
> @@ -333,7 +333,7 @@ int qemu_config_parse(FILE *fp, QemuOptsList **lists,
> const char *fname)
> /* group with id */
> list = find_list(lists, group, &local_err);
> if (local_err) {
> - error_report_err(local_err);
> + error_propagate(errp, local_err);
> goto out;
> }
Please avoid error_propagate() where possible:
list = find_list(lists, group, errp);
if (!list) {
goto out;
}
> opts = qemu_opts_create(list, id, 1, NULL);
> @@ -344,7 +344,7 @@ int qemu_config_parse(FILE *fp, QemuOptsList **lists,
> const char *fname)
> /* group without id */
> list = find_list(lists, group, &local_err);
> if (local_err) {
> - error_report_err(local_err);
> + error_propagate(errp, local_err);
> goto out;
> }
Likewise.
> opts = qemu_opts_create(list, NULL, 0, &error_abort);
> @@ -356,20 +356,19 @@ int qemu_config_parse(FILE *fp, QemuOptsList **lists,
> const char *fname)
> sscanf(line, " %63s = \"\"", arg) == 1) {
> /* arg = value */
> if (opts == NULL) {
> - error_report("no group defined");
> + error_setg(errp, "no group defined");
> goto out;
> }
> - if (!qemu_opt_set(opts, arg, value, &local_err)) {
> - error_report_err(local_err);
> + if (!qemu_opt_set(opts, arg, value, errp)) {
> goto out;
> }
> continue;
> }
> - error_report("parse error");
> + error_setg(errp, "parse error");
*Ächz* Not your patch's fault.
> goto out;
> }
> if (ferror(fp)) {
> - error_report("error reading file");
> + error_setg(errp, "error reading file");
> goto out;
> }
> res = count;
> @@ -378,16 +377,17 @@ out:
> return res;
> }
>
> -int qemu_read_config_file(const char *filename)
> +int qemu_read_config_file(const char *filename, Error **errp)
> {
> FILE *f = fopen(filename, "r");
> int ret;
>
> if (f == NULL) {
> + error_setg_errno(errp, errno, "Cannot read config file %s",
> filename);
> return -errno;
> }
>
> - ret = qemu_config_parse(f, vm_config_groups, filename);
> + ret = qemu_config_parse(f, vm_config_groups, filename, errp);
> fclose(f);
> return ret;
> }
- Re: [PATCH 06/25] tests: convert check-qom-proplist to keyval, (continued)
- [PATCH 10/25] hmp: special case help options for object_add, Paolo Bonzini, 2021/01/18
- [PATCH 15/25] vl: plumb keyval-based options into -set and -readconfig, Paolo Bonzini, 2021/01/18
- [PATCH 16/25] qom: do not modify QDict argument in user_creatable_add_dict, Paolo Bonzini, 2021/01/18
- [PATCH 14/25] qemu-config: parse configuration files to a QDict, Paolo Bonzini, 2021/01/18
- [PATCH 12/25] qemu-config: add error propagation to qemu_config_parse, Paolo Bonzini, 2021/01/18
- Re: [PATCH 12/25] qemu-config: add error propagation to qemu_config_parse,
Markus Armbruster <=
- [PATCH 13/25] qemu-option: support accept-any QemuOptsList in qemu_opts_absorb_qdict, Paolo Bonzini, 2021/01/18
- [PATCH 08/25] hmp: replace "O" parser with keyval, Paolo Bonzini, 2021/01/18
- [PATCH 17/25] qemu-io: use keyval for -object parsing, Paolo Bonzini, 2021/01/18
- [PATCH 20/25] qemu: use keyval for -object parsing, Paolo Bonzini, 2021/01/18
- [PATCH 21/25] storage-daemon: do not register the "object" group with QemuOpts, Paolo Bonzini, 2021/01/18
- [PATCH 25/25] vl: switch -accel parsing to keyval, Paolo Bonzini, 2021/01/18
- [PATCH 24/25] qemu-option: remove now-dead code, Paolo Bonzini, 2021/01/18
- [PATCH 18/25] qemu-nbd: use keyval for -object parsing, Paolo Bonzini, 2021/01/18
- [PATCH 22/25] qom: export more functions for use with non-UserCreatable objects, Paolo Bonzini, 2021/01/18