All of lore.kernel.org
 help / color / mirror / Atom feed
From: Eric Blake <eblake@redhat.com>
To: Dong Xu Wang <wdongxu@linux.vnet.ibm.com>
Cc: kwolf@redhat.com, wdongxu@cn.ibm.com, qemu-devel@nongnu.org,
	stefanha@redhat.com, armbru@redhat.com
Subject: Re: [Qemu-devel] [PATCH V16 5/7] Use QemuOpts support in block layer
Date: Wed, 10 Jul 2013 13:47:49 -0600	[thread overview]
Message-ID: <51DDBA65.2010401@redhat.com> (raw)
In-Reply-To: <1371547919-15654-6-git-send-email-wdongxu@linux.vnet.ibm.com>

[-- Attachment #1: Type: text/plain, Size: 13369 bytes --]

On 06/18/2013 03:31 AM, Dong Xu Wang wrote:
> This patch uses QemuOpts related functions in block layer, add
> a member bdrv_create_opts to BlockDriver struct, it returns
> a QemuOptsList pointer, which includes the image format's create
> options.
> 

> +++ b/block/cow.c

Concluding my review...

> @@ -315,21 +309,27 @@ static int cow_create(const char *filename, QEMUOptionParameter *options)
>  
>  exit:
>      bdrv_delete(cow_bs);
> +finish:
> +    g_free((/* !const */ char*)image_filename);

Yuck - the only reason you have to cast away const here is because patch
4/7 returned const in the first place.  It would be a lot easier to just
declare 'char *image_filename', after fixing qemu_opt_get_del to not
force const on something the caller must free.  And since doing that
means spinning a v17, I really would like to see this patch split into
manageable pieces (incremental conversion of one file at a time, rather
than everything in one blow).

> +++ b/block/gluster.c
> @@ -365,8 +365,7 @@ out:
>      return ret;
>  }
>  
> -static int qemu_gluster_create(const char *filename,
> -        QEMUOptionParameter *options)
> +static int qemu_gluster_create(const char *filename, QemuOpts *opts)

Kudos on fixing bad indentation in the process.indentation

> +++ b/block/iscsi.c
> @@ -1213,7 +1213,7 @@ static int iscsi_has_zero_init(BlockDriverState *bs)
>      return 0;
>  }
>  
> -static int iscsi_create(const char *filename, QEMUOptionParameter *options)
> +static int iscsi_create(const char *filename,  QemuOpts *opts)

Spacing is off.

> +++ b/block/qcow.c

> @@ -662,26 +662,21 @@ static int qcow_create(const char *filename, QEMUOptionParameter *options)
>      int ret;
>      BlockDriverState *qcow_bs;
>  
> -    /* Read out options */
> -    while (options && options->name) {
> -        if (!strcmp(options->name, BLOCK_OPT_SIZE)) {
> -            total_size = options->value.n / 512;
> -        } else if (!strcmp(options->name, BLOCK_OPT_BACKING_FILE)) {
> -            backing_file = options->value.s;
> -        } else if (!strcmp(options->name, BLOCK_OPT_ENCRYPT)) {
> -            flags |= options->value.n ? BLOCK_FLAG_ENCRYPT : 0;
> -        }
> -        options++;
> +    /* Read out opts */
> +    total_size = qemu_opt_get_size_del(opts, BLOCK_OPT_SIZE, 0) / 512;
> +    backing_file = qemu_opt_get_del(opts, BLOCK_OPT_BACKING_FILE);
> +    if (qemu_opt_get_bool_del(opts, BLOCK_OPT_ENCRYPT, 0)) {

s/0/false/ - you're passing a bool parameter

> @@ -752,6 +747,8 @@ static int qcow_create(const char *filename, QEMUOptionParameter *options)
>      ret = 0;
>  exit:
>      bdrv_delete(qcow_bs);
> +finish:
> +    g_free((/* !const */ char*)backing_file);

Again, this just feels like patch 4/7 declared the wrong signature.
(I'll quit pointing it out, but there are other instances)

> +++ b/block/qcow2.c

> @@ -1243,7 +1244,8 @@ static int qcow2_create2(const char *filename, int64_t total_size,
>          error_report(
>              "Cluster size must be a power of two between %d and %dk",
>              1 << MIN_CLUSTER_BITS, 1 << (MAX_CLUSTER_BITS - 10));
> -        return -EINVAL;
> +        ret =  -EINVAL;

Spacing looks odd.

> @@ -1375,61 +1379,67 @@ static int qcow2_create(const char *filename, QEMUOptionParameter *options)
>      size_t cluster_size = DEFAULT_CLUSTER_SIZE;
>      int prealloc = 0;
>      int version = 2;
> +    const char *buf;
> +    int ret = 0;
>  

> +    sectors = qemu_opt_get_size_del(opts, BLOCK_OPT_SIZE, 0) / 512;
> +    backing_file = qemu_opt_get_del(opts, BLOCK_OPT_BACKING_FILE);
> +    backing_fmt = qemu_opt_get_del(opts, BLOCK_OPT_BACKING_FMT);
> +    if (qemu_opt_get_bool_del(opts, BLOCK_OPT_ENCRYPT, 0)) {

s/0/false/ (I'll quit pointing it out, but probably other instances)

> @@ -1704,49 +1714,55 @@ static int qcow2_load_vmstate(BlockDriverState *bs, uint8_t *buf,
>  
>      .bdrv_invalidate_cache      = qcow2_invalidate_cache,
>  
> -    .create_options = qcow2_create_options,
>      .bdrv_check = qcow2_check,
> +
> +    .bdrv_create_opts     = &qcow2_create_opts,

In other files, you were aligning the '='.  Here, it looks especially
odd that you are using more than one ' ' but still didn't align things -
it looks more consistent if you either go for full alignment or use
exactly one ' ' everywhere (I don't care which, so long as the results
don't look odd).

> +++ b/block/qed.c
> @@ -555,12 +555,12 @@ static int qed_create(const char *filename, uint32_t cluster_size,
>  
>      ret = bdrv_create_file(filename, NULL);
>      if (ret < 0) {
> -        return ret;
> +        goto finish;
>      }
>  
>      ret = bdrv_file_open(&bs, filename, NULL, BDRV_O_RDWR | BDRV_O_CACHE_WB);
>      if (ret < 0) {
> -        return ret;
> +        goto finish;
>      }
>  
>      /* File must start empty and grow, check truncate is supported */
> @@ -600,55 +600,57 @@ static int qed_create(const char *filename, uint32_t cluster_size,
>  out:
>      g_free(l1_table);
>      bdrv_delete(bs);
> +finish:
> +    g_free((/* !const */ char*)backing_file);
> +    g_free((/* !const */ char*)backing_fmt);

Eww - you are freeing something in the client that was allocated in the
parent, but passed via 'const char *'.  That makes it hard to trace
allocation ownership.  I'd rather see the frees moved into the function
that gets the data allocated (and _this_ function keeps 'const char *'
arguments), rather than passing the buck to the helper function...

>      return ret;
>  }
>  
> -static int bdrv_qed_create(const char *filename, QEMUOptionParameter *options)
> +static int bdrv_qed_create(const char *filename, QemuOpts *opts)
>  {
>      uint64_t image_size = 0;
>      uint32_t cluster_size = QED_DEFAULT_CLUSTER_SIZE;
>      uint32_t table_size = QED_DEFAULT_TABLE_SIZE;
>      const char *backing_file = NULL;
>      const char *backing_fmt = NULL;

> +    image_size = qemu_opt_get_size_del(opts, BLOCK_OPT_SIZE, 0);
> +    backing_file = qemu_opt_get_del(opts, BLOCK_OPT_BACKING_FILE);
> +    backing_fmt = qemu_opt_get_del(opts, BLOCK_OPT_BACKING_FMT);

>  
>      return qed_create(filename, cluster_size, image_size, table_size,
>                        backing_file, backing_fmt);

...better would have been 'ret = qed_create(...);' with fallthrough...

> +
> +finish:
> +    g_free((/* !const */ char*)backing_file);
> +    g_free((/* !const */ char*)backing_fmt);
> +    return ret;

...and let finish do the cleanup on both success and error.

> +++ b/block/qed.h
> @@ -43,6 +43,7 @@
>   *
>   * All fields are little-endian on disk.
>   */
> +#define  QED_DEFAULT_CLUSTER_SIZE  65536
>  
>  enum {
>      QED_MAGIC = 'Q' | 'E' << 8 | 'D' << 16 | '\0' << 24,
> @@ -69,7 +70,6 @@ enum {
>       */
>      QED_MIN_CLUSTER_SIZE = 4 * 1024, /* in bytes */
>      QED_MAX_CLUSTER_SIZE = 64 * 1024 * 1024,
> -    QED_DEFAULT_CLUSTER_SIZE = 64 * 1024,

Why are you converting an enum into a define?  I personally find enums
slightly easier to debug while under gdb.  I don't think this hunk is
necessary.

> +++ b/block/raw-posix.c
> @@ -123,6 +123,19 @@
>  
>  #define MAX_BLOCKSIZE	4096
>  
> +static QemuOptsList file_proto_create_opts = {
> +    .name = "file-proto-create-opts",
> +    .head = QTAILQ_HEAD_INITIALIZER(file_proto_create_opts.head),
> +    .desc = {
> +        {
> +            .name = BLOCK_OPT_SIZE,
> +            .type = QEMU_OPT_SIZE,
> +            .help = "Virtual disk size"
> +        },
> +        { /* end of list */ }
> +    }
> +};
> +

In other files, you did the conversion...

> @@ -1179,15 +1187,6 @@ static coroutine_fn BlockDriverAIOCB *raw_aio_discard(BlockDriverState *bs,
>                         cb, opaque, QEMU_AIO_DISCARD);
>  }
>  
> -static QEMUOptionParameter raw_create_options[] = {
> -    {
> -        .name = BLOCK_OPT_SIZE,
> -        .type = OPT_SIZE,
> -        .help = "Virtual disk size"
> -    },
> -    { NULL }
> -};

...next to the place you were replacing.  Why the difference in this file?

> +++ b/block/rbd.c

> @@ -997,7 +995,7 @@ static BlockDriver bdrv_rbd = {
>      .bdrv_close         = qemu_rbd_close,
>      .bdrv_create        = qemu_rbd_create,
>      .bdrv_get_info      = qemu_rbd_getinfo,
> -    .create_options     = qemu_rbd_create_options,
> +    .bdrv_create_opts   = &rbd_create_opts,

Why the lost qemu_ prefix?

> +++ b/block/sheepdog.c

> @@ -2259,7 +2253,6 @@ static int sd_load_vmstate(BlockDriverState *bs, uint8_t *data,
>      return do_load_save_vmstate(s, data, pos, size, 1);
>  }
>  
> -
>  static coroutine_fn int sd_co_discard(BlockDriverState *bs, int64_t sector_num,

Spurious whitespace change.

> @@ -2364,7 +2361,7 @@ static BlockDriver bdrv_sheepdog = {
>      .bdrv_save_vmstate  = sd_save_vmstate,
>      .bdrv_load_vmstate  = sd_load_vmstate,
>  
> -    .create_options = sd_create_options,
> +    .bdrv_create_opts   = &sd_create_opts,
>  };
>  
>  static BlockDriver bdrv_sheepdog_tcp = {
> @@ -2391,7 +2388,7 @@ static BlockDriver bdrv_sheepdog_tcp = {
>      .bdrv_save_vmstate  = sd_save_vmstate,
>      .bdrv_load_vmstate  = sd_load_vmstate,
>  
> -    .create_options = sd_create_options,
> +    .bdrv_create_opts = &sd_create_opts,

Inconsistent alignment.

>  };
>  
>  static BlockDriver bdrv_sheepdog_unix = {
> @@ -2418,7 +2415,7 @@ static BlockDriver bdrv_sheepdog_unix = {
>      .bdrv_save_vmstate  = sd_save_vmstate,
>      .bdrv_load_vmstate  = sd_load_vmstate,
>  
> -    .create_options = sd_create_options,
> +    .bdrv_create_opts = &sd_create_opts,

and again.

> +++ b/block/vdi.c

> @@ -648,25 +648,18 @@ static int vdi_create(const char *filename, QEMUOptionParameter *options)
>      logout("\n");
>  
>      /* Read out options. */
> -    while (options && options->name) {
> -        if (!strcmp(options->name, BLOCK_OPT_SIZE)) {
> -            bytes = options->value.n;
> +    bytes = qemu_opt_get_size_del(opts, BLOCK_OPT_SIZE, 0);
>  #if defined(CONFIG_VDI_BLOCK_SIZE)
> -        } else if (!strcmp(options->name, BLOCK_OPT_CLUSTER_SIZE)) {
> -            if (options->value.n) {
> -                /* TODO: Additional checks (SECTOR_SIZE * 2^n, ...). */
> -                block_size = options->value.n;
> -            }
> +        /* TODO: Additional checks (SECTOR_SIZE * 2^n, ...). */
> +    block_size = qemu_opt_get_size_del(opts,

New comment alignment looks odd.

> +++ b/block/vpc.c
> @@ -827,7 +832,7 @@ static BlockDriver bdrv_vpc = {
>      .bdrv_read              = vpc_co_read,
>      .bdrv_write             = vpc_co_write,
>  
> -    .create_options = vpc_create_options,
> +    .bdrv_create_opts = &vpc_create_opts,

Alignment.

> +++ b/include/block/block.h
> @@ -115,9 +115,8 @@ BlockDriver *bdrv_find_protocol(const char *filename);
>  BlockDriver *bdrv_find_format(const char *format_name);
>  BlockDriver *bdrv_find_whitelisted_format(const char *format_name,
>                                            bool readonly);
> -int bdrv_create(BlockDriver *drv, const char* filename,
> -    QEMUOptionParameter *options);
> -int bdrv_create_file(const char* filename, QEMUOptionParameter *options);
> +int bdrv_create(BlockDriver *drv, const char* filename, QemuOpts *opts);
> +int bdrv_create_file(const char *filename, QemuOpts *opts);

I see why you did things all in one patch - you changed the signature,
so all the callbacks had to pick up the new signature.  But I still
think it will be easier to review if you created the new signature with
a new name, did conversion of one file at a time, then delete the old
signature and rename the new name back to the old name.

>  BlockDriverState *bdrv_new(const char *device_name);
>  void bdrv_make_anon(BlockDriverState *bs);
>  void bdrv_swap(BlockDriverState *bs_new, BlockDriverState *bs_old);
> diff --git a/include/block/block_int.h b/include/block/block_int.h
> index ba52247..41311e2 100644
> --- a/include/block/block_int.h
> +++ b/include/block/block_int.h
> @@ -95,7 +95,7 @@ struct BlockDriver {
>                        const uint8_t *buf, int nb_sectors);
>      void (*bdrv_close)(BlockDriverState *bs);
>      void (*bdrv_rebind)(BlockDriverState *bs);
> -    int (*bdrv_create)(const char *filename, QEMUOptionParameter *options);
> +    int (*bdrv_create)(const char *filename, QemuOpts *opts);

Likewise, by temporarily having two different callback names, where
clients provide one of the two callbacks during the transition over
multiple patches, makes it possible to split into reviewable portions.

> +++ b/qemu-img.c
> @@ -1531,8 +1526,10 @@ static int img_convert(int argc, char **argv)
>      }
>  out:
>      qemu_progress_end();
> -    free_option_parameters(create_options);
> -    free_option_parameters(param);
> +    qemu_opts_free(create_opts);
> +    if (opts) {
> +        qemu_opts_del(opts);

Should qemu_opts_del() be made more free-like, by having it be a no-op
if opts is NULL?  That would be an independent cleanup, though.

-- 
Eric Blake   eblake redhat com    +1-919-301-3266
Libvirt virtualization library http://libvirt.org


[-- Attachment #2: OpenPGP digital signature --]
[-- Type: application/pgp-signature, Size: 621 bytes --]

  parent reply	other threads:[~2013-07-10 19:48 UTC|newest]

Thread overview: 20+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2013-06-18  9:31 [Qemu-devel] [PATCH V16 0/7] replace QEMUOptionParameter with QemuOpts parser Dong Xu Wang
2013-06-18  9:31 ` [Qemu-devel] [PATCH V16 1/7] add def_value_str in QemuOptDesc struct and rewrite qemu_opts_print Dong Xu Wang
2013-06-18  9:31 ` [Qemu-devel] [PATCH V16 2/7] avoid duplication of default value in QemuOpts Dong Xu Wang
2013-06-18  9:31 ` [Qemu-devel] [PATCH V16 3/7] Create four QemuOptsList related functions Dong Xu Wang
2013-07-10 16:07   ` Eric Blake
2013-06-18  9:31 ` [Qemu-devel] [PATCH V16 4/7] Create some QemuOpts functons Dong Xu Wang
2013-07-10 16:51   ` Eric Blake
2013-07-10 19:06   ` Eric Blake
2013-06-18  9:31 ` [Qemu-devel] [PATCH V16 5/7] Use QemuOpts support in block layer Dong Xu Wang
2013-07-10 17:56   ` Eric Blake
2013-07-10 19:47   ` Eric Blake [this message]
2013-06-18  9:31 ` [Qemu-devel] [PATCH V16 6/7] query-command-line-options outputs def_value_str Dong Xu Wang
2013-07-10 19:56   ` Eric Blake
2013-06-18  9:31 ` [Qemu-devel] [PATCH V16 7/7] remove QEMUOptionParameter related functions and struct Dong Xu Wang
2013-07-10 19:57   ` Eric Blake
2013-07-04 12:52 ` [Qemu-devel] [PATCH V16 0/7] replace QEMUOptionParameter with QemuOpts parser Stefan Hajnoczi
2013-07-09 20:41   ` Eric Blake
2013-07-10 19:49     ` Eric Blake
2013-07-15  7:38       ` Dong Xu Wang
2013-07-09 22:05   ` Andreas Färber

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=51DDBA65.2010401@redhat.com \
    --to=eblake@redhat.com \
    --cc=armbru@redhat.com \
    --cc=kwolf@redhat.com \
    --cc=qemu-devel@nongnu.org \
    --cc=stefanha@redhat.com \
    --cc=wdongxu@cn.ibm.com \
    --cc=wdongxu@linux.vnet.ibm.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.