From: Kevin Wolf <kwolf@redhat.com>
To: qemu-devel@nongnu.org
Cc: Kevin Wolf <kwolf@redhat.com>
Subject: [Qemu-devel] [PATCH 2/4] Convert all block drivers to new bdrv_create
Date: Mon, 18 May 2009 16:42:10 +0200 [thread overview]
Message-ID: <1242657732-29043-3-git-send-email-kwolf@redhat.com> (raw)
In-Reply-To: <1242657732-29043-1-git-send-email-kwolf@redhat.com>
Now we can make use of the newly introduced option structures. Instead of
having bdrv_create carry more and more parameters (which are format specific in
most cases), just pass a option structure as defined by the driver itself.
bdrv_create2() contains an emulation of the old interface to simplify the
transition.
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
---
block.c | 44 +++++++++++++++++++++++++++++++++-----------
block.h | 6 +++---
block/cow.c | 26 +++++++++++++++++++++-----
block/qcow.c | 28 ++++++++++++++++++++++++++--
block/qcow2.c | 36 +++++++++++++++++++++++++++++++-----
block/raw-posix.c | 37 +++++++++++++++++++++++++++----------
block/raw-win32.c | 20 ++++++++++++++++----
block/vmdk.c | 28 ++++++++++++++++++++++++++--
block/vpc.c | 21 +++++++++++++++++----
block/vvfat.c | 4 ++--
block_int.h | 17 +++++++++++------
qemu-img.c | 2 +-
12 files changed, 214 insertions(+), 55 deletions(-)
diff --git a/block.c b/block.c
index 980fbec..7f4cf9e 100644
--- a/block.c
+++ b/block.c
@@ -189,22 +189,44 @@ int bdrv_create2(BlockDriver *drv,
const char *backing_file, const char *backing_format,
int flags)
{
- if (drv->bdrv_create2)
- return drv->bdrv_create2(filename, size_in_sectors, backing_file,
- backing_format, flags);
- if (drv->bdrv_create)
- return drv->bdrv_create(filename, size_in_sectors, backing_file,
- flags);
- return -ENOTSUP;
+ QEMUOptionParameter *options;
+
+ options = parse_option_parameters("", drv->create_options, NULL);
+
+ // Process flags
+ if (flags & ~(BLOCK_FLAG_ENCRYPT | BLOCK_FLAG_COMPAT6 | BLOCK_FLAG_COMPRESS)) {
+ return -ENOTSUP;
+ }
+
+ if (flags & BLOCK_FLAG_ENCRYPT) {
+ set_option_parameter_int(options, BLOCK_OPT_ENCRYPT, 1);
+ }
+ if (flags & BLOCK_FLAG_COMPAT6) {
+ set_option_parameter_int(options, BLOCK_OPT_COMPAT6, 1);
+ }
+
+ // Add size to options
+ set_option_parameter_int(options, BLOCK_OPT_SIZE, size_in_sectors * 512);
+
+ // Backing files
+ if ((backing_file != NULL && set_option_parameter(options,
+ BLOCK_OPT_BACKING_FILE, backing_file))
+ || (backing_format != NULL && set_option_parameter(options,
+ BLOCK_OPT_BACKING_FMT, backing_format)))
+ {
+ return -ENOTSUP;
+ }
+
+ return bdrv_create(drv, filename, options);
}
-int bdrv_create(BlockDriver *drv,
- const char *filename, int64_t size_in_sectors,
- const char *backing_file, int flags)
+int bdrv_create(BlockDriver *drv, const char* filename,
+ QEMUOptionParameter *options)
{
if (!drv->bdrv_create)
return -ENOTSUP;
- return drv->bdrv_create(filename, size_in_sectors, backing_file, flags);
+
+ return drv->bdrv_create(filename, options);
}
#ifdef _WIN32
diff --git a/block.h b/block.h
index 22df8ca..0acac63 100644
--- a/block.h
+++ b/block.h
@@ -3,6 +3,7 @@
#include "qemu-aio.h"
#include "qemu-common.h"
+#include "qemu-option.h"
/* block.c */
typedef struct BlockDriver BlockDriver;
@@ -45,9 +46,8 @@ void bdrv_info_stats(Monitor *mon);
void bdrv_init(void);
BlockDriver *bdrv_find_format(const char *format_name);
-int bdrv_create(BlockDriver *drv,
- const char *filename, int64_t size_in_sectors,
- const char *backing_file, int flags);
+int bdrv_create(BlockDriver *drv, const char* filename,
+ QEMUOptionParameter *options);
int bdrv_create2(BlockDriver *drv,
const char *filename, int64_t size_in_sectors,
const char *backing_file, const char *backing_format,
diff --git a/block/cow.c b/block/cow.c
index 94b3549..41d292a 100644
--- a/block/cow.c
+++ b/block/cow.c
@@ -202,15 +202,23 @@ static void cow_close(BlockDriverState *bs)
close(s->fd);
}
-static int cow_create(const char *filename, int64_t image_sectors,
- const char *image_filename, int flags)
+static int cow_create(const char *filename, QEMUOptionParameter *options)
{
int fd, cow_fd;
struct cow_header_v2 cow_header;
struct stat st;
-
- if (flags)
- return -ENOTSUP;
+ int64_t image_sectors = 0;
+ const char *image_filename = NULL;
+
+ /* Read out options */
+ while (options && options->name) {
+ if (!strcmp(options->name, BLOCK_OPT_SIZE)) {
+ image_sectors = options->value.n / 512;
+ } else if (!strcmp(options->name, BLOCK_OPT_BACKING_FILE)) {
+ image_filename = options->value.s;
+ }
+ options++;
+ }
cow_fd = open(filename, O_WRONLY | O_CREAT | O_TRUNC | O_BINARY,
0644);
@@ -253,6 +261,12 @@ static void cow_flush(BlockDriverState *bs)
fsync(s->fd);
}
+static QEMUOptionParameter cow_create_options[] = {
+ { BLOCK_OPT_SIZE, OPT_SIZE },
+ { BLOCK_OPT_BACKING_FILE, OPT_STRING },
+ { NULL }
+};
+
static BlockDriver bdrv_cow = {
.format_name = "cow",
.instance_size = sizeof(BDRVCowState),
@@ -264,6 +278,8 @@ static BlockDriver bdrv_cow = {
.bdrv_create = cow_create,
.bdrv_flush = cow_flush,
.bdrv_is_allocated = cow_is_allocated,
+
+ .create_options = cow_create_options,
};
static void bdrv_cow_init(void)
diff --git a/block/qcow.c b/block/qcow.c
index 1cf7c3b..6ecf2e8 100644
--- a/block/qcow.c
+++ b/block/qcow.c
@@ -767,12 +767,26 @@ static void qcow_close(BlockDriverState *bs)
bdrv_delete(s->hd);
}
-static int qcow_create(const char *filename, int64_t total_size,
- const char *backing_file, int flags)
+static int qcow_create(const char *filename, QEMUOptionParameter *options)
{
int fd, header_size, backing_filename_len, l1_size, i, shift;
QCowHeader header;
uint64_t tmp;
+ int64_t total_size = 0;
+ const char *backing_file = NULL;
+ int flags = 0;
+
+ /* 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++;
+ }
fd = open(filename, O_WRONLY | O_CREAT | O_TRUNC | O_BINARY, 0644);
if (fd < 0)
@@ -918,6 +932,14 @@ static int qcow_get_info(BlockDriverState *bs, BlockDriverInfo *bdi)
return 0;
}
+
+static QEMUOptionParameter qcow_create_options[] = {
+ { BLOCK_OPT_SIZE, OPT_SIZE },
+ { BLOCK_OPT_BACKING_FILE, OPT_STRING },
+ { BLOCK_OPT_ENCRYPT, OPT_FLAG },
+ { NULL }
+};
+
static BlockDriver bdrv_qcow = {
.format_name = "qcow",
.instance_size = sizeof(BDRVQcowState),
@@ -935,6 +957,8 @@ static BlockDriver bdrv_qcow = {
.aiocb_size = sizeof(QCowAIOCB),
.bdrv_write_compressed = qcow_write_compressed,
.bdrv_get_info = qcow_get_info,
+
+ .create_options = qcow_create_options,
};
static void bdrv_qcow_init(void)
diff --git a/block/qcow2.c b/block/qcow2.c
index a6de9b6..b6171d2 100644
--- a/block/qcow2.c
+++ b/block/qcow2.c
@@ -1696,10 +1696,28 @@ static int qcow_create2(const char *filename, int64_t total_size,
return 0;
}
-static int qcow_create(const char *filename, int64_t total_size,
- const char *backing_file, int flags)
-{
- return qcow_create2(filename, total_size, backing_file, NULL, flags);
+static int qcow_create(const char *filename, QEMUOptionParameter *options)
+{
+ const char *backing_file = NULL;
+ const char *backing_fmt = NULL;
+ uint64_t sectors = 0;
+ int flags = 0;
+
+ /* Read out options */
+ while (options && options->name) {
+ if (!strcmp(options->name, BLOCK_OPT_SIZE)) {
+ sectors = 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_BACKING_FMT)) {
+ backing_fmt = options->value.s;
+ } else if (!strcmp(options->name, BLOCK_OPT_ENCRYPT)) {
+ flags |= options->value.n ? BLOCK_FLAG_ENCRYPT : 0;
+ }
+ options++;
+ }
+
+ return qcow_create2(filename, sectors, backing_file, backing_fmt, flags);
}
static int qcow_make_empty(BlockDriverState *bs)
@@ -2892,6 +2910,14 @@ static int qcow_get_buffer(BlockDriverState *bs, uint8_t *buf,
return ret;
}
+static QEMUOptionParameter qcow_create_options[] = {
+ { BLOCK_OPT_SIZE, OPT_SIZE },
+ { BLOCK_OPT_BACKING_FILE, OPT_STRING },
+ { BLOCK_OPT_BACKING_FMT, OPT_STRING },
+ { BLOCK_OPT_ENCRYPT, OPT_FLAG },
+ { NULL }
+};
+
static BlockDriver bdrv_qcow2 = {
.format_name = "qcow2",
.instance_size = sizeof(BDRVQcowState),
@@ -2919,7 +2945,7 @@ static BlockDriver bdrv_qcow2 = {
.bdrv_put_buffer = qcow_put_buffer,
.bdrv_get_buffer = qcow_get_buffer,
- .bdrv_create2 = qcow_create2,
+ .create_options = qcow_create_options,
.bdrv_check = qcow_check,
};
diff --git a/block/raw-posix.c b/block/raw-posix.c
index f3a9476..86e3067 100644
--- a/block/raw-posix.c
+++ b/block/raw-posix.c
@@ -823,13 +823,18 @@ again:
}
#endif
-static int raw_create(const char *filename, int64_t total_size,
- const char *backing_file, int flags)
+static int raw_create(const char *filename, QEMUOptionParameter *options)
{
int fd;
+ int64_t total_size = 0;
- if (flags || backing_file)
- return -ENOTSUP;
+ /* Read out options */
+ while (options && options->name) {
+ if (!strcmp(options->name, BLOCK_OPT_SIZE)) {
+ total_size = options->value.n / 512;
+ }
+ options++;
+ }
fd = open(filename, O_WRONLY | O_CREAT | O_TRUNC | O_BINARY,
0644);
@@ -846,6 +851,12 @@ static void raw_flush(BlockDriverState *bs)
fsync(s->fd);
}
+
+static QEMUOptionParameter raw_create_options[] = {
+ { BLOCK_OPT_SIZE, OPT_SIZE },
+ { NULL }
+};
+
static BlockDriver bdrv_raw = {
.format_name = "raw",
.instance_size = sizeof(BDRVRawState),
@@ -866,6 +877,8 @@ static BlockDriver bdrv_raw = {
.bdrv_truncate = raw_truncate,
.bdrv_getlength = raw_getlength,
+
+ .create_options = raw_create_options,
};
/***********************************************/
@@ -1364,15 +1377,20 @@ static BlockDriverAIOCB *raw_aio_ioctl(BlockDriverState *bs,
#endif /* !linux && !FreeBSD */
#if defined(__linux__) || defined(__FreeBSD__)
-static int hdev_create(const char *filename, int64_t total_size,
- const char *backing_file, int flags)
+static int hdev_create(const char *filename, QEMUOptionParameter *options)
{
int fd;
int ret = 0;
struct stat stat_buf;
+ int64_t total_size = 0;
- if (flags || backing_file)
- return -ENOTSUP;
+ /* Read out options */
+ while (options && options->name) {
+ if (!strcmp(options->name, "size")) {
+ total_size = options->value.n / 512;
+ }
+ options++;
+ }
fd = open(filename, O_WRONLY | O_BINARY);
if (fd < 0)
@@ -1391,8 +1409,7 @@ static int hdev_create(const char *filename, int64_t total_size,
#else /* !(linux || freebsd) */
-static int hdev_create(const char *filename, int64_t total_size,
- const char *backing_file, int flags)
+static int hdev_create(const char *filename, QEMUOptionParameter *options)
{
return -ENOTSUP;
}
diff --git a/block/raw-win32.c b/block/raw-win32.c
index 15f3ec4..6e5c09b 100644
--- a/block/raw-win32.c
+++ b/block/raw-win32.c
@@ -210,13 +210,18 @@ static int64_t raw_getlength(BlockDriverState *bs)
return l.QuadPart;
}
-static int raw_create(const char *filename, int64_t total_size,
- const char *backing_file, int flags)
+static int raw_create(const char *filename, QEMUOptionParameter *options)
{
int fd;
+ int64_t total_size = 0;
- if (flags || backing_file)
- return -ENOTSUP;
+ /* Read out options */
+ while (options && options->name) {
+ if (!strcmp(options->name, BLOCK_OPT_SIZE)) {
+ total_size = options->value.n / 512;
+ }
+ options++;
+ }
fd = open(filename, O_WRONLY | O_CREAT | O_TRUNC | O_BINARY,
0644);
@@ -228,6 +233,11 @@ static int raw_create(const char *filename, int64_t total_size,
return 0;
}
+static QEMUOptionParameter raw_create_options[] = {
+ { BLOCK_OPT_SIZE, OPT_SIZE },
+ { NULL }
+};
+
static BlockDriver bdrv_raw = {
.format_name = "raw",
.instance_size = sizeof(BDRVRawState),
@@ -239,6 +249,8 @@ static BlockDriver bdrv_raw = {
.bdrv_write = raw_write,
.bdrv_truncate = raw_truncate,
.bdrv_getlength = raw_getlength,
+
+ .create_options = raw_create_options,
};
/***********************************************/
diff --git a/block/vmdk.c b/block/vmdk.c
index 13866e9..b3ea686 100644
--- a/block/vmdk.c
+++ b/block/vmdk.c
@@ -687,8 +687,7 @@ static int vmdk_write(BlockDriverState *bs, int64_t sector_num,
return 0;
}
-static int vmdk_create(const char *filename, int64_t total_size,
- const char *backing_file, int flags)
+static int vmdk_create(const char *filename, QEMUOptionParameter *options)
{
int fd, i;
VMDK4Header header;
@@ -713,6 +712,21 @@ static int vmdk_create(const char *filename, int64_t total_size,
"ddb.adapterType = \"ide\"\n";
char desc[1024];
const char *real_filename, *temp_str;
+ int64_t total_size = 0;
+ const char *backing_file = NULL;
+ int flags = 0;
+
+ // 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_COMPAT6)) {
+ flags |= options->value.n ? BLOCK_FLAG_COMPAT6: 0;
+ }
+ options++;
+ }
/* XXX: add support for backing file */
if (backing_file) {
@@ -812,6 +826,14 @@ static void vmdk_flush(BlockDriverState *bs)
bdrv_flush(s->hd);
}
+
+static QEMUOptionParameter vmdk_create_options[] = {
+ { BLOCK_OPT_SIZE, OPT_SIZE },
+ { BLOCK_OPT_BACKING_FILE, OPT_STRING },
+ { BLOCK_OPT_COMPAT6, OPT_FLAG },
+ { NULL }
+};
+
static BlockDriver bdrv_vmdk = {
.format_name = "vmdk",
.instance_size = sizeof(BDRVVmdkState),
@@ -823,6 +845,8 @@ static BlockDriver bdrv_vmdk = {
.bdrv_create = vmdk_create,
.bdrv_flush = vmdk_flush,
.bdrv_is_allocated = vmdk_is_allocated,
+
+ .create_options = vmdk_create_options,
};
static void bdrv_vmdk_init(void)
diff --git a/block/vpc.c b/block/vpc.c
index 211ae5c..662a6f6 100644
--- a/block/vpc.c
+++ b/block/vpc.c
@@ -477,8 +477,7 @@ static int calculate_geometry(int64_t total_sectors, uint16_t* cyls,
return 0;
}
-static int vpc_create(const char *filename, int64_t total_sectors,
- const char *backing_file, int flags)
+static int vpc_create(const char *filename, QEMUOptionParameter *options)
{
uint8_t buf[1024];
struct vhd_footer* footer = (struct vhd_footer*) buf;
@@ -489,10 +488,17 @@ static int vpc_create(const char *filename, int64_t total_sectors,
uint8_t heads;
uint8_t secs_per_cyl;
size_t block_size, num_bat_entries;
+ int64_t total_sectors = 0;
- if (backing_file != NULL)
- return -ENOTSUP;
+ // Read out options
+ while (options && options->name) {
+ if (!strcmp(options->name, "size")) {
+ total_sectors = options->value.n / 512;
+ }
+ options++;
+ }
+ // Create the file
fd = open(filename, O_WRONLY | O_CREAT | O_TRUNC | O_BINARY, 0644);
if (fd < 0)
return -EIO;
@@ -587,6 +593,11 @@ static void vpc_close(BlockDriverState *bs)
bdrv_delete(s->hd);
}
+static QEMUOptionParameter vpc_create_options[] = {
+ { "size", OPT_SIZE },
+ { NULL }
+};
+
static BlockDriver bdrv_vpc = {
.format_name = "vpc",
.instance_size = sizeof(BDRVVPCState),
@@ -596,6 +607,8 @@ static BlockDriver bdrv_vpc = {
.bdrv_write = vpc_write,
.bdrv_close = vpc_close,
.bdrv_create = vpc_create,
+
+ .create_options = vpc_create_options,
};
static void bdrv_vpc_init(void)
diff --git a/block/vvfat.c b/block/vvfat.c
index 2a8feb3..13960e9 100644
--- a/block/vvfat.c
+++ b/block/vvfat.c
@@ -2777,8 +2777,8 @@ static int enable_write_target(BDRVVVFATState *s)
s->qcow_filename = qemu_malloc(1024);
get_tmp_filename(s->qcow_filename, 1024);
- if (bdrv_create(bdrv_find_format("qcow"),
- s->qcow_filename, s->sector_count, "fat:", 0) < 0)
+ if (bdrv_create2(bdrv_find_format("qcow"),
+ s->qcow_filename, s->sector_count, "fat:", NULL, 0) < 0)
return -1;
s->qcow = bdrv_new("");
if (s->qcow == NULL || bdrv_open(s->qcow, s->qcow_filename, 0) < 0)
diff --git a/block_int.h b/block_int.h
index 9d11940..782de6c 100644
--- a/block_int.h
+++ b/block_int.h
@@ -25,11 +25,18 @@
#define BLOCK_INT_H
#include "block.h"
+#include "qemu-option.h"
#define BLOCK_FLAG_ENCRYPT 1
#define BLOCK_FLAG_COMPRESS 2
#define BLOCK_FLAG_COMPAT6 4
+#define BLOCK_OPT_SIZE "size"
+#define BLOCK_OPT_ENCRYPT "encryption"
+#define BLOCK_OPT_COMPAT6 "compat6"
+#define BLOCK_OPT_BACKING_FILE "backing_file"
+#define BLOCK_OPT_BACKING_FMT "backing_fmt"
+
typedef struct AIOPool {
void (*cancel)(BlockDriverAIOCB *acb);
int aiocb_size;
@@ -46,8 +53,7 @@ struct BlockDriver {
int (*bdrv_write)(BlockDriverState *bs, int64_t sector_num,
const uint8_t *buf, int nb_sectors);
void (*bdrv_close)(BlockDriverState *bs);
- int (*bdrv_create)(const char *filename, int64_t total_sectors,
- const char *backing_file, int flags);
+ int (*bdrv_create)(const char *filename, QEMUOptionParameter *options);
void (*bdrv_flush)(BlockDriverState *bs);
int (*bdrv_is_allocated)(BlockDriverState *bs, int64_t sector_num,
int nb_sectors, int *pnum);
@@ -97,10 +103,9 @@ struct BlockDriver {
AIOPool aio_pool;
- /* new create with backing file format */
- int (*bdrv_create2)(const char *filename, int64_t total_sectors,
- const char *backing_file, const char *backing_format,
- int flags);
+ /* List of options for creating images, terminated by name == NULL */
+ QEMUOptionParameter *create_options;
+
/* Returns number of errors in image, -errno for internal errors */
int (*bdrv_check)(BlockDriverState* bs);
diff --git a/qemu-img.c b/qemu-img.c
index a3d15e7..190153f 100644
--- a/qemu-img.c
+++ b/qemu-img.c
@@ -551,7 +551,7 @@ static int img_convert(int argc, char **argv)
if (flags & BLOCK_FLAG_ENCRYPT && flags & BLOCK_FLAG_COMPRESS)
error("Compression and encryption not supported at the same time");
- ret = bdrv_create(drv, out_filename, total_sectors, out_baseimg, flags);
+ ret = bdrv_create2(drv, out_filename, total_sectors, out_baseimg, NULL, flags);
if (ret < 0) {
if (ret == -ENOTSUP) {
error("Formatting not supported for file format '%s'", out_fmt);
--
1.6.0.6
next prev parent reply other threads:[~2009-05-18 14:43 UTC|newest]
Thread overview: 7+ messages / expand[flat|nested] mbox.gz Atom feed top
2009-05-18 14:42 [Qemu-devel] [PATCH 0/4] Make qemu-img create options generic Kevin Wolf
2009-05-18 14:42 ` [Qemu-devel] [PATCH 1/4] Create qemu-option.h Kevin Wolf
2009-05-18 14:42 ` Kevin Wolf [this message]
2009-05-18 14:42 ` [Qemu-devel] [PATCH 3/4] Convert qemu-img create to new bdrv_create Kevin Wolf
2009-05-18 14:42 ` [Qemu-devel] [PATCH 4/4] Convert qemu-img convert " Kevin Wolf
2009-05-18 17:05 ` Christoph Hellwig
2009-05-19 7:48 ` Kevin Wolf
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=1242657732-29043-3-git-send-email-kwolf@redhat.com \
--to=kwolf@redhat.com \
--cc=qemu-devel@nongnu.org \
/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.