qemu-img: introduce --target-image-opts for 'convert' command
The '--image-opts' flag indicates whether the source filename includes options. The target filename has to remain in the plain filename format though, since it needs to be passed to bdrv_create(). When using --skip-create though, it would be possible to use image-opts syntax. This adds --target-image-opts to indicate that the target filename includes options. Currently this mandates use of the --skip-create flag too. Signed-off-by: Daniel P. Berrange <berrange@redhat.com> Message-id: 20170515164712.6643-4-berrange@redhat.com Reviewed-by: Max Reitz <mreitz@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com> Signed-off-by: Max Reitz <mreitz@redhat.com>
This commit is contained in:
parent
ea204ddac7
commit
305b4c60f2
@ -40,9 +40,9 @@ STEXI
|
|||||||
ETEXI
|
ETEXI
|
||||||
|
|
||||||
DEF("convert", img_convert,
|
DEF("convert", img_convert,
|
||||||
"convert [--object objectdef] [--image-opts] [-U] [-c] [-p] [-q] [-n] [-f fmt] [-t cache] [-T src_cache] [-O output_fmt] [-B backing_file] [-o options] [-s snapshot_id_or_name] [-l snapshot_param] [-S sparse_size] [-m num_coroutines] [-W] filename [filename2 [...]] output_filename")
|
"convert [--object objectdef] [--image-opts] [--target-image-opts] [-U] [-c] [-p] [-q] [-n] [-f fmt] [-t cache] [-T src_cache] [-O output_fmt] [-B backing_file] [-o options] [-s snapshot_id_or_name] [-l snapshot_param] [-S sparse_size] [-m num_coroutines] [-W] filename [filename2 [...]] output_filename")
|
||||||
STEXI
|
STEXI
|
||||||
@item convert [--object @var{objectdef}] [--image-opts] [-U] [-c] [-p] [-q] [-n] [-f @var{fmt}] [-t @var{cache}] [-T @var{src_cache}] [-O @var{output_fmt}] [-B @var{backing_file}] [-o @var{options}] [-s @var{snapshot_id_or_name}] [-l @var{snapshot_param}] [-S @var{sparse_size}] [-m @var{num_coroutines}] [-W] @var{filename} [@var{filename2} [...]] @var{output_filename}
|
@item convert [--object @var{objectdef}] [--image-opts] [--target-image-opts] [-U] [-c] [-p] [-q] [-n] [-f @var{fmt}] [-t @var{cache}] [-T @var{src_cache}] [-O @var{output_fmt}] [-B @var{backing_file}] [-o @var{options}] [-s @var{snapshot_id_or_name}] [-l @var{snapshot_param}] [-S @var{sparse_size}] [-m @var{num_coroutines}] [-W] @var{filename} [@var{filename2} [...]] @var{output_filename}
|
||||||
ETEXI
|
ETEXI
|
||||||
|
|
||||||
DEF("dd", img_dd,
|
DEF("dd", img_dd,
|
||||||
|
52
qemu-img.c
52
qemu-img.c
@ -60,6 +60,7 @@ enum {
|
|||||||
OPTION_PATTERN = 260,
|
OPTION_PATTERN = 260,
|
||||||
OPTION_FLUSH_INTERVAL = 261,
|
OPTION_FLUSH_INTERVAL = 261,
|
||||||
OPTION_NO_DRAIN = 262,
|
OPTION_NO_DRAIN = 262,
|
||||||
|
OPTION_TARGET_IMAGE_OPTS = 263,
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef enum OutputFormat {
|
typedef enum OutputFormat {
|
||||||
@ -1913,10 +1914,10 @@ static int convert_do_copy(ImgConvertState *s)
|
|||||||
static int img_convert(int argc, char **argv)
|
static int img_convert(int argc, char **argv)
|
||||||
{
|
{
|
||||||
int c, bs_i, flags, src_flags = 0;
|
int c, bs_i, flags, src_flags = 0;
|
||||||
const char *fmt = NULL, *out_fmt = "raw", *cache = "unsafe",
|
const char *fmt = NULL, *out_fmt = NULL, *cache = "unsafe",
|
||||||
*src_cache = BDRV_DEFAULT_CACHE, *out_baseimg = NULL,
|
*src_cache = BDRV_DEFAULT_CACHE, *out_baseimg = NULL,
|
||||||
*out_filename, *out_baseimg_param, *snapshot_name = NULL;
|
*out_filename, *out_baseimg_param, *snapshot_name = NULL;
|
||||||
BlockDriver *drv, *proto_drv;
|
BlockDriver *drv = NULL, *proto_drv = NULL;
|
||||||
BlockDriverInfo bdi;
|
BlockDriverInfo bdi;
|
||||||
BlockDriverState *out_bs;
|
BlockDriverState *out_bs;
|
||||||
QemuOpts *opts = NULL, *sn_opts = NULL;
|
QemuOpts *opts = NULL, *sn_opts = NULL;
|
||||||
@ -1924,7 +1925,7 @@ static int img_convert(int argc, char **argv)
|
|||||||
char *options = NULL;
|
char *options = NULL;
|
||||||
Error *local_err = NULL;
|
Error *local_err = NULL;
|
||||||
bool writethrough, src_writethrough, quiet = false, image_opts = false,
|
bool writethrough, src_writethrough, quiet = false, image_opts = false,
|
||||||
skip_create = false, progress = false;
|
skip_create = false, progress = false, tgt_image_opts = false;
|
||||||
int64_t ret = -EINVAL;
|
int64_t ret = -EINVAL;
|
||||||
bool force_share = false;
|
bool force_share = false;
|
||||||
|
|
||||||
@ -1942,6 +1943,7 @@ static int img_convert(int argc, char **argv)
|
|||||||
{"object", required_argument, 0, OPTION_OBJECT},
|
{"object", required_argument, 0, OPTION_OBJECT},
|
||||||
{"image-opts", no_argument, 0, OPTION_IMAGE_OPTS},
|
{"image-opts", no_argument, 0, OPTION_IMAGE_OPTS},
|
||||||
{"force-share", no_argument, 0, 'U'},
|
{"force-share", no_argument, 0, 'U'},
|
||||||
|
{"target-image-opts", no_argument, 0, OPTION_TARGET_IMAGE_OPTS},
|
||||||
{0, 0, 0, 0}
|
{0, 0, 0, 0}
|
||||||
};
|
};
|
||||||
c = getopt_long(argc, argv, ":hf:O:B:ce6o:s:l:S:pt:T:qnm:WU",
|
c = getopt_long(argc, argv, ":hf:O:B:ce6o:s:l:S:pt:T:qnm:WU",
|
||||||
@ -2062,9 +2064,16 @@ static int img_convert(int argc, char **argv)
|
|||||||
case OPTION_IMAGE_OPTS:
|
case OPTION_IMAGE_OPTS:
|
||||||
image_opts = true;
|
image_opts = true;
|
||||||
break;
|
break;
|
||||||
|
case OPTION_TARGET_IMAGE_OPTS:
|
||||||
|
tgt_image_opts = true;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!out_fmt && !tgt_image_opts) {
|
||||||
|
out_fmt = "raw";
|
||||||
|
}
|
||||||
|
|
||||||
if (qemu_opts_foreach(&qemu_object_opts,
|
if (qemu_opts_foreach(&qemu_object_opts,
|
||||||
user_creatable_add_opts_foreach,
|
user_creatable_add_opts_foreach,
|
||||||
NULL, NULL)) {
|
NULL, NULL)) {
|
||||||
@ -2076,12 +2085,22 @@ static int img_convert(int argc, char **argv)
|
|||||||
goto fail_getopt;
|
goto fail_getopt;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (tgt_image_opts && !skip_create) {
|
||||||
|
error_report("--target-image-opts requires use of -n flag");
|
||||||
|
goto fail_getopt;
|
||||||
|
}
|
||||||
|
|
||||||
s.src_num = argc - optind - 1;
|
s.src_num = argc - optind - 1;
|
||||||
out_filename = s.src_num >= 1 ? argv[argc - 1] : NULL;
|
out_filename = s.src_num >= 1 ? argv[argc - 1] : NULL;
|
||||||
|
|
||||||
if (options && has_help_option(options)) {
|
if (options && has_help_option(options)) {
|
||||||
|
if (out_fmt) {
|
||||||
ret = print_block_option_help(out_filename, out_fmt);
|
ret = print_block_option_help(out_filename, out_fmt);
|
||||||
goto fail_getopt;
|
goto fail_getopt;
|
||||||
|
} else {
|
||||||
|
error_report("Option help requires a format be specified");
|
||||||
|
goto fail_getopt;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (s.src_num < 1) {
|
if (s.src_num < 1) {
|
||||||
@ -2146,6 +2165,7 @@ static int img_convert(int argc, char **argv)
|
|||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!skip_create) {
|
||||||
/* Find driver and parse its options */
|
/* Find driver and parse its options */
|
||||||
drv = bdrv_find_format(out_fmt);
|
drv = bdrv_find_format(out_fmt);
|
||||||
if (!drv) {
|
if (!drv) {
|
||||||
@ -2161,7 +2181,6 @@ static int img_convert(int argc, char **argv)
|
|||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!skip_create) {
|
|
||||||
if (!drv->create_opts) {
|
if (!drv->create_opts) {
|
||||||
error_report("Format driver '%s' does not support image creation",
|
error_report("Format driver '%s' does not support image creation",
|
||||||
drv->format_name);
|
drv->format_name);
|
||||||
@ -2218,7 +2237,7 @@ static int img_convert(int argc, char **argv)
|
|||||||
const char *preallocation =
|
const char *preallocation =
|
||||||
qemu_opt_get(opts, BLOCK_OPT_PREALLOC);
|
qemu_opt_get(opts, BLOCK_OPT_PREALLOC);
|
||||||
|
|
||||||
if (!drv->bdrv_co_pwritev_compressed) {
|
if (drv && !drv->bdrv_co_pwritev_compressed) {
|
||||||
error_report("Compression not supported for this file format");
|
error_report("Compression not supported for this file format");
|
||||||
ret = -1;
|
ret = -1;
|
||||||
goto out;
|
goto out;
|
||||||
@ -2258,19 +2277,30 @@ static int img_convert(int argc, char **argv)
|
|||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* XXX we should allow --image-opts to trigger use of
|
if (skip_create) {
|
||||||
* img_open() here, but then we have trouble with
|
s.target = img_open(tgt_image_opts, out_filename, out_fmt,
|
||||||
* the bdrv_create() call which takes different params.
|
flags, writethrough, quiet, false);
|
||||||
* Not critical right now, so fix can wait...
|
} else {
|
||||||
|
/* TODO ultimately we should allow --target-image-opts
|
||||||
|
* to be used even when -n is not given.
|
||||||
|
* That has to wait for bdrv_create to be improved
|
||||||
|
* to allow filenames in option syntax
|
||||||
*/
|
*/
|
||||||
s.target = img_open_file(out_filename, out_fmt, flags, writethrough, quiet,
|
s.target = img_open_file(out_filename, out_fmt, flags,
|
||||||
false);
|
writethrough, quiet, false);
|
||||||
|
}
|
||||||
if (!s.target) {
|
if (!s.target) {
|
||||||
ret = -1;
|
ret = -1;
|
||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
out_bs = blk_bs(s.target);
|
out_bs = blk_bs(s.target);
|
||||||
|
|
||||||
|
if (s.compressed && !out_bs->drv->bdrv_co_pwritev_compressed) {
|
||||||
|
error_report("Compression not supported for this file format");
|
||||||
|
ret = -1;
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
/* increase bufsectors from the default 4096 (2M) if opt_transfer
|
/* increase bufsectors from the default 4096 (2M) if opt_transfer
|
||||||
* or discard_alignment of the out_bs is greater. Limit to 32768 (16MB)
|
* or discard_alignment of the out_bs is greater. Limit to 32768 (16MB)
|
||||||
* as maximum. */
|
* as maximum. */
|
||||||
|
@ -45,9 +45,17 @@ keys.
|
|||||||
|
|
||||||
@item --image-opts
|
@item --image-opts
|
||||||
|
|
||||||
Indicates that the @var{filename} parameter is to be interpreted as a
|
Indicates that the source @var{filename} parameter is to be interpreted as a
|
||||||
full option string, not a plain filename. This parameter is mutually
|
full option string, not a plain filename. This parameter is mutually
|
||||||
exclusive with the @var{-f} and @var{-F} parameters.
|
exclusive with the @var{-f} parameter.
|
||||||
|
|
||||||
|
@item --target-image-opts
|
||||||
|
|
||||||
|
Indicates that the @var{output_filename} parameter(s) are to be interpreted as
|
||||||
|
a full option string, not a plain filename. This parameter is mutually
|
||||||
|
exclusive with the @var{-O} parameters. It is currently required to also use
|
||||||
|
the @var{-n} parameter to skip image creation. This restriction may be relaxed
|
||||||
|
in a future release.
|
||||||
|
|
||||||
@item fmt
|
@item fmt
|
||||||
is the disk image format. It is guessed automatically in most cases. See below
|
is the disk image format. It is guessed automatically in most cases. See below
|
||||||
|
Loading…
Reference in New Issue
Block a user