aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--blockdev.c14
-rw-r--r--qapi/block-core.json29
-rwxr-xr-xtests/qemu-iotests/0852
-rw-r--r--tests/qemu-iotests/1392
4 files changed, 38 insertions, 9 deletions
diff --git a/blockdev.c b/blockdev.c
index 6469f161df..02cd69bc21 100644
--- a/blockdev.c
+++ b/blockdev.c
@@ -3887,6 +3887,7 @@ void qmp_blockdev_add(BlockdevOptions *options, Error **errp)
QObject *obj;
Visitor *v = qobject_output_visitor_new(&obj);
QDict *qdict;
+ const QDictEntry *ent;
Error *local_err = NULL;
visit_type_BlockdevOptions(v, NULL, &options, &local_err);
@@ -3900,6 +3901,19 @@ void qmp_blockdev_add(BlockdevOptions *options, Error **errp)
qdict_flatten(qdict);
+ /*
+ * Rewrite "backing": null to "backing": ""
+ * TODO Rewrite "" to null instead, and perhaps not even here
+ */
+ for (ent = qdict_first(qdict); ent; ent = qdict_next(qdict, ent)) {
+ char *dot = strrchr(ent->key, '.');
+
+ if (!strcmp(dot ? dot + 1 : ent->key, "backing")
+ && qobject_type(ent->value) == QTYPE_QNULL) {
+ qdict_put(qdict, ent->key, qstring_new());
+ }
+ }
+
if (!qdict_get_try_str(qdict, "node-name")) {
error_setg(errp, "'node-name' must be specified for the root node");
goto fail;
diff --git a/qapi/block-core.json b/qapi/block-core.json
index ff8e2ba0cb..6866ae8a38 100644
--- a/qapi/block-core.json
+++ b/qapi/block-core.json
@@ -2273,15 +2273,14 @@
# besides their data source and an optional backing file.
#
# @backing: reference to or definition of the backing file block
-# device (if missing, taken from the image file content). It is
-# allowed to pass an empty string here in order to disable the
-# default backing file.
+# device, null disables the backing file entirely.
+# Defaults to the backing file stored the image file.
#
# Since: 2.9
##
{ 'struct': 'BlockdevOptionsGenericCOWFormat',
'base': 'BlockdevOptionsGenericFormat',
- 'data': { '*backing': 'BlockdevRef' } }
+ 'data': { '*backing': 'BlockdevRefOrNull' } }
##
# @Qcow2OverlapCheckMode:
@@ -3120,9 +3119,7 @@
# Reference to a block device.
#
# @definition: defines a new block device inline
-# @reference: references the ID of an existing block device. An
-# empty string means that no block device should be
-# referenced.
+# @reference: references the ID of an existing block device
#
# Since: 2.9
##
@@ -3131,6 +3128,24 @@
'reference': 'str' } }
##
+# @BlockdevRefOrNull:
+#
+# Reference to a block device.
+#
+# @definition: defines a new block device inline
+# @reference: references the ID of an existing block device.
+# An empty string means that no block device should
+# be referenced. Deprecated; use null instead.
+# @null: No block device should be referenced (since 2.10)
+#
+# Since: 2.9
+##
+{ 'alternate': 'BlockdevRefOrNull',
+ 'data': { 'definition': 'BlockdevOptions',
+ 'reference': 'str',
+ 'null': 'null' } }
+
+##
# @blockdev-add:
#
# Creates a new block device. If the @id option is given at the top level, a
diff --git a/tests/qemu-iotests/085 b/tests/qemu-iotests/085
index 71efe50d34..5c7668cf9b 100755
--- a/tests/qemu-iotests/085
+++ b/tests/qemu-iotests/085
@@ -106,7 +106,7 @@ function add_snapshot_image()
snapshot_file="${TEST_DIR}/${1}-${snapshot_virt0}"
_make_test_img -u -b "${base_image}" "$size"
mv "${TEST_IMG}" "${snapshot_file}"
- do_blockdev_add "$1" "'backing': '', " "${snapshot_file}"
+ do_blockdev_add "$1" "'backing': null, " "${snapshot_file}"
}
# ${1}: unique identifier for the snapshot filename
diff --git a/tests/qemu-iotests/139 b/tests/qemu-iotests/139
index 9ff51d9647..50cf40fbd5 100644
--- a/tests/qemu-iotests/139
+++ b/tests/qemu-iotests/139
@@ -69,7 +69,7 @@ class TestBlockdevDel(iotests.QMPTestCase):
'-b', base_img, new_img, '1M')
opts = {'driver': iotests.imgfmt,
'node-name': node,
- 'backing': '',
+ 'backing': None,
'file': {'driver': 'file',
'filename': new_img}}
result = self.vm.qmp('blockdev-add', conv_keys = False, **opts)