@@ -295,7 +295,7 @@ void bdrv_register(BlockDriver *bdrv)
/* create a new block device (by default it is empty) */
static BlockDriverState *bdrv_new_int(const char *device_name,
- BlockDriverState *child)
+ BlockDriverState *child, void *opaque)
{
BlockDriverState *bs;
@@ -307,13 +307,14 @@ static BlockDriverState *bdrv_new_int(const char *device_name,
bdrv_iostatus_disable(bs);
notifier_list_init(&bs->close_notifiers);
bs->child = child;
+ bs->opaque = opaque;
return bs;
}
BlockDriverState *bdrv_new(const char *device_name)
{
- return bdrv_new_int(device_name, NULL);
+ return bdrv_new_int(device_name, NULL, NULL);
}
void bdrv_add_close_notifier(BlockDriverState *bs, Notifier *notify)
@@ -729,7 +730,9 @@ static int bdrv_open_common(BlockDriverState *bs, BlockDriverState *file,
}
bs->drv = drv;
- bs->opaque = g_malloc0(drv->instance_size);
+ if (bs->opaque == NULL) {
+ bs->opaque = g_malloc0(drv->instance_size);
+ }
bs->enable_write_cache = !!(flags & BDRV_O_CACHE_WB);
@@ -777,7 +780,7 @@ free_and_fail:
}
static int bdrv_file_open_int(BlockDriverState **pbs, const char *filename,
- QDict *options, int flags, BlockDriverState *child)
+ QDict *options, int flags, BlockDriverState *child, void *opaque)
{
BlockDriverState *bs;
BlockDriver *drv;
@@ -789,7 +792,7 @@ static int bdrv_file_open_int(BlockDriverState **pbs, const char *filename,
options = qdict_new();
}
- bs = bdrv_new_int("", child);
+ bs = bdrv_new_int("", child, opaque);
bs->options = options;
options = qdict_clone_shallow(options);
@@ -882,18 +885,11 @@ fail:
int bdrv_file_open(BlockDriverState **pbs, const char *filename,
QDict *options, int flags)
{
- return bdrv_file_open_int(pbs, filename, options, flags, NULL);
+ return bdrv_file_open_int(pbs, filename, options, flags, NULL, NULL);
}
-/*
- * Opens the backing file for a BlockDriverState if not yet open
- *
- * options is a QDict of options to pass to the block drivers, or NULL for an
- * empty set of options. The reference to the QDict is transferred to this
- * function (even on failure), so if the caller intends to reuse the dictionary,
- * it needs to use QINCREF() before calling bdrv_file_open.
- */
-int bdrv_open_backing_file(BlockDriverState *bs, QDict *options)
+static int bdrv_open_backing_file_int(BlockDriverState *bs,
+ QDict *options, void *opaque)
{
char backing_filename[PATH_MAX];
int back_flags, ret;
@@ -917,7 +913,7 @@ int bdrv_open_backing_file(BlockDriverState *bs, QDict *options)
return 0;
}
- bs->backing_hd = bdrv_new_int("", bs);
+ bs->backing_hd = bdrv_new_int("", bs, opaque);
bdrv_get_full_backing_filename(bs, backing_filename,
sizeof(backing_filename));
@@ -940,6 +936,19 @@ int bdrv_open_backing_file(BlockDriverState *bs, QDict *options)
return 0;
}
+/*
+ * Opens the backing file for a BlockDriverState if not yet open
+ *
+ * options is a QDict of options to pass to the block drivers, or NULL for an
+ * empty set of options. The reference to the QDict is transferred to this
+ * function (even on failure), so if the caller intends to reuse the dictionary,
+ * it needs to use QINCREF() before calling bdrv_file_open.
+ */
+int bdrv_open_backing_file(BlockDriverState *bs, QDict *options)
+{
+ return bdrv_open_backing_file_int(bs, options, NULL);
+}
+
static void extract_subqdict(QDict *src, QDict **dst, const char *start)
{
const QDictEntry *entry, *next;
@@ -1056,7 +1065,7 @@ int bdrv_open(BlockDriverState *bs, const char *filename, QDict *options,
}
if (total_size == -1) {
- bs1 = bdrv_new_int("", NULL);
+ bs1 = bdrv_new_int("", NULL, NULL);
ret = bdrv_open(bs1, filename, NULL, 0, drv);
if (ret < 0) {
bdrv_delete(bs1);
@@ -1079,7 +1088,7 @@ int bdrv_open(BlockDriverState *bs, const char *filename, QDict *options,
extract_subqdict(options, &file_options, "file.");
ret = bdrv_file_open_int(&file, filename, file_options,
- bdrv_open_flags(bs, flags), bs);
+ bdrv_open_flags(bs, flags), bs, NULL);
if (ret < 0) {
goto fail;
}
@@ -1109,7 +1118,7 @@ int bdrv_open(BlockDriverState *bs, const char *filename, QDict *options,
QDict *backing_options;
extract_subqdict(options, &backing_options, "backing.");
- ret = bdrv_open_backing_file(bs, backing_options);
+ ret = bdrv_open_backing_file_int(bs, backing_options, NULL);
if (ret < 0) {
goto close_and_fail;
}
If the block driver is given an opaque data, there is no need to allocate a new one. This allows to pass an existing driver state to the new driver. Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com> --- block.c | 47 ++++++++++++++++++++++++++++------------------- 1 file changed, 28 insertions(+), 19 deletions(-)