1
The following changes since commit 609ef9f451759151d0bfe7c3843410ab94d68f18:
1
The following changes since commit b2f7a038bb4c4fc5ce6b8486e8513dfd97665e2a:
2
2
3
Merge remote-tracking branch 'remotes/berrange/tags/qio-next-pull-request' into staging (2018-06-28 17:53:31 +0100)
3
Merge remote-tracking branch 'remotes/rth/tags/pull-softfloat-20181104' into staging (2018-11-05 10:32:49 +0000)
4
4
5
are available in the git repository at:
5
are available in the Git repository at:
6
6
7
git://repo.or.cz/qemu/kevin.git tags/for-upstream
7
git://repo.or.cz/qemu/kevin.git tags/for-upstream
8
8
9
for you to fetch changes up to 583c99d39368526dfb57a715b04a6ceea27dbe1e:
9
for you to fetch changes up to 1240ac558d348f6c7a5752b1a57c1da58e4efe3e:
10
10
11
block: Remove unused sector-based vectored I/O (2018-06-29 14:20:56 +0200)
11
include: Add a comment to explain the origin of sizes' lookup table (2018-11-05 15:29:59 +0100)
12
12
13
----------------------------------------------------------------
13
----------------------------------------------------------------
14
Block layer patches:
14
Block layer patches:
15
15
16
- Make truncate operations asynchronous (so that preallocation in
16
- auto-read-only option to fix commit job when used with -blockdev
17
blockdev-create doesn't block the main loop any more)
17
- Fix help text related qemu-iotests failure (by improving the help text
18
- usb-storage: Add rerror/werror properties
18
and updating the reference output)
19
- nvme: Add num_queues property
19
- quorum: Add missing checks when adding/removing child nodes
20
- qemu-img convert: Copy offloading fixes (including data corruption fix)
20
- Don't take address of fields in packed structs
21
- qcow2: Fix cluster leak on temporary write error
21
- vvfat: Fix crash when reporting error about too many files in directory
22
- Use byte-based functions instead of bdrv_co_readv/writev()
23
- Various small fixes and cleanups
24
22
25
----------------------------------------------------------------
23
----------------------------------------------------------------
26
Eric Blake (8):
24
Alberto Garcia (7):
27
parallels: Switch to byte-based calls
25
block: replace "discard" literal with BDRV_OPT_DISCARD macro
28
qcow: Switch get_cluster_offset to be byte-based
26
qcow2: Get the request alignment for encrypted images from QCryptoBlock
29
qcow: Switch qcow_co_readv to byte-based calls
27
quorum: Remove quorum_err()
30
qcow: Switch qcow_co_writev to byte-based calls
28
quorum: Return an error if the blkverify mode has invalid settings
31
qcow: Switch to a byte-based driver
29
iotest: Test the blkverify mode of the Quorum driver
32
replication: Switch to byte-based calls
30
quorum: Forbid adding children in blkverify mode
33
vhdx: Switch to byte-based calls
31
iotest: Test x-blockdev-change on a Quorum
34
block: Remove unused sector-based vectored I/O
35
32
36
Fam Zheng (5):
33
Cleber Rosa (1):
37
qcow2: Remove dead check on !ret
34
iotests: make 083 specific to raw
38
block: Move request tracking to children in copy offloading
35
39
qcow2: Fix src_offset in copy offloading
36
Daniel P. Berrangé (1):
40
iscsi: Don't blindly use designator length in response for memcpy
37
crypto: initialize sector size even when opening with no IO flag
41
file-posix: Fix EINTR handling
42
38
43
Kevin Wolf (12):
39
Kevin Wolf (12):
44
qapi/job: The next release will be 3.0
40
vpc: Don't leak opts in vpc_open()
45
usb-storage: Add rerror/werror properties
41
block: Update flags in bdrv_set_read_only()
46
qcow2: Fix qcow2_truncate() error return value
42
block: Add auto-read-only option
47
block: Convert .bdrv_truncate callback to coroutine_fn
43
rbd: Close image in qemu_rbd_open() error path
48
qcow2: Remove coroutine trampoline for preallocate_co()
44
block: Require auto-read-only for existing fallbacks
49
block: Move bdrv_truncate() implementation to io.c
45
nbd: Support auto-read-only option
50
block: Use tracked request for truncate
46
file-posix: Support auto-read-only option
51
file-posix: Make .bdrv_co_truncate asynchronous
47
curl: Support auto-read-only option
52
qemu-iotests: Update 026.out.nocache reference output
48
gluster: Support auto-read-only option
53
qcow2: Free allocated clusters on write error
49
iscsi: Support auto-read-only option
54
qemu-iotests: Test qcow2 not leaking clusters on write error
50
block: Make auto-read-only=on default for -drive
55
file-posix: Implement co versions of discard/flush
51
qemu-iotests: Test auto-read-only with -drive and -blockdev
56
52
57
Markus Armbruster (3):
53
Leonid Bloch (2):
58
block-qdict: Pacify Coverity after commit f1b34a248e9
54
vdi: Use a literal number of bytes for DEFAULT_CLUSTER_SIZE
59
block/crypto: Pacify Coverity after commit f853465aacb
55
include: Add a comment to explain the origin of sizes' lookup table
60
block/crypto: Simplify block_crypto_{open,create}_opts_init()
61
56
62
Weiping Zhang (1):
57
Li Qiang (1):
63
hw/block/nvme: add optional parameter num_queues for nvme device
58
block: change some function return type to bool
64
59
65
qapi/job.json | 18 +-
60
Max Reitz (5):
66
block/crypto.h | 8 +-
61
option: Make option help nicer to read
67
block/qcow2.h | 1 +
62
chardev: Indent list of chardevs
68
include/block/block.h | 8 +-
63
qdev-monitor: Make device options help nicer
69
include/block/block_int.h | 7 +-
64
object: Make option help nicer to read
70
include/block/raw-aio.h | 4 +-
65
fw_cfg: Drop newline in @file description
71
include/hw/scsi/scsi.h | 2 +
72
block.c | 64 +------
73
block/copy-on-read.c | 8 +-
74
block/crypto.c | 112 +++--------
75
block/file-posix.c | 367 +++++++++++++++++++------------------
76
block/file-win32.c | 6 +-
77
block/gluster.c | 14 +-
78
block/io.c | 219 +++++++++++++++-------
79
block/iscsi.c | 10 +-
80
block/nfs.c | 7 +-
81
block/parallels.c | 16 +-
82
block/qcow.c | 135 +++++++-------
83
block/qcow2-cluster.c | 11 ++
84
block/qcow2.c | 140 ++++++--------
85
block/qed.c | 8 +-
86
block/raw-format.c | 8 +-
87
block/rbd.c | 8 +-
88
block/replication.c | 14 +-
89
block/sheepdog.c | 12 +-
90
block/ssh.c | 6 +-
91
block/vhdx.c | 12 +-
92
hw/block/nvme.c | 5 +-
93
hw/scsi/scsi-bus.c | 11 +-
94
hw/usb/dev-storage.c | 2 +
95
qobject/block-qdict.c | 16 +-
96
tests/qemu-iotests/026 | 17 ++
97
tests/qemu-iotests/026.out | 8 +
98
tests/qemu-iotests/026.out.nocache | 14 +-
99
tests/qemu-iotests/063 | 9 +
100
tests/qemu-iotests/063.out | 12 ++
101
36 files changed, 685 insertions(+), 634 deletions(-)
102
66
67
Peter Maydell (5):
68
block/qcow2: Don't take address of fields in packed structs
69
block/qcow: Don't take address of fields in packed structs
70
block/qcow2-bitmap: Don't take address of fields in packed structs
71
block/vhdx: Don't take address of fields in packed structs
72
block/vdi: Don't take address of fields in packed structs
73
74
Stefan Weil (1):
75
qemu-io-cmds: Fix two format strings
76
77
Thomas Huth (1):
78
block/vvfat: Fix crash when reporting error about too many files in directory
79
80
qapi/block-core.json | 7 +
81
block/vhdx.h | 12 +-
82
include/block/block.h | 5 +-
83
include/qemu/option.h | 2 +-
84
include/qemu/units.h | 18 +
85
include/sysemu/block-backend.h | 6 +-
86
block.c | 60 ++-
87
block/block-backend.c | 8 +-
88
block/bochs.c | 17 +-
89
block/cloop.c | 16 +-
90
block/curl.c | 8 +-
91
block/dmg.c | 16 +-
92
block/file-posix.c | 19 +-
93
block/gluster.c | 12 +-
94
block/iscsi.c | 8 +-
95
block/nbd-client.c | 10 +-
96
block/qcow.c | 18 +-
97
block/qcow2-bitmap.c | 24 +-
98
block/qcow2.c | 66 +--
99
block/quorum.c | 45 +-
100
block/rbd.c | 14 +-
101
block/vdi.c | 68 +--
102
block/vhdx-endian.c | 118 ++---
103
block/vhdx-log.c | 4 +-
104
block/vhdx.c | 18 +-
105
block/vpc.c | 2 +
106
block/vvfat.c | 15 +-
107
blockdev.c | 3 +-
108
chardev/char.c | 2 +-
109
crypto/block-qcow.c | 2 +
110
qdev-monitor.c | 13 +-
111
qemu-img.c | 4 +-
112
qemu-io-cmds.c | 4 +-
113
util/qemu-option.c | 32 +-
114
vl.c | 15 +-
115
tests/qemu-iotests/081 | 116 +++++
116
tests/qemu-iotests/081.out | 70 +++
117
tests/qemu-iotests/082.out | 956 ++++++++++++++++++++---------------------
118
tests/qemu-iotests/083 | 2 +-
119
tests/qemu-iotests/232 | 147 +++++++
120
tests/qemu-iotests/232.out | 59 +++
121
tests/qemu-iotests/group | 1 +
122
42 files changed, 1266 insertions(+), 776 deletions(-)
123
create mode 100755 tests/qemu-iotests/232
124
create mode 100644 tests/qemu-iotests/232.out
125
diff view generated by jsdifflib
New patch
1
From: Thomas Huth <thuth@redhat.com>
1
2
3
When using the vvfat driver with a directory that contains too many files,
4
QEMU currently crashes. This can be triggered like this for example:
5
6
mkdir /tmp/vvfattest
7
cd /tmp/vvfattest
8
for ((x=0;x<=513;x++)); do mkdir $x; done
9
qemu-system-x86_64 -drive \
10
file.driver=vvfat,file.dir=.,read-only=on,media=cdrom
11
12
Seems like read_directory() is changing the mapping->path variable. Make
13
sure we use the right pointer instead.
14
15
Signed-off-by: Thomas Huth <thuth@redhat.com>
16
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
17
---
18
block/vvfat.c | 4 ++--
19
1 file changed, 2 insertions(+), 2 deletions(-)
20
21
diff --git a/block/vvfat.c b/block/vvfat.c
22
index XXXXXXX..XXXXXXX 100644
23
--- a/block/vvfat.c
24
+++ b/block/vvfat.c
25
@@ -XXX,XX +XXX,XX @@ static int init_directories(BDRVVVFATState* s,
26
mapping = array_get(&(s->mapping), i);
27
28
if (mapping->mode & MODE_DIRECTORY) {
29
+ char *path = mapping->path;
30
mapping->begin = cluster;
31
if(read_directory(s, i)) {
32
- error_setg(errp, "Could not read directory %s",
33
- mapping->path);
34
+ error_setg(errp, "Could not read directory %s", path);
35
return -1;
36
}
37
mapping = array_get(&(s->mapping), i);
38
--
39
2.19.1
40
41
diff view generated by jsdifflib
New patch
1
From: Alberto Garcia <berto@igalia.com>
1
2
3
Signed-off-by: Alberto Garcia <berto@igalia.com>
4
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
5
---
6
block.c | 6 +++---
7
1 file changed, 3 insertions(+), 3 deletions(-)
8
9
diff --git a/block.c b/block.c
10
index XXXXXXX..XXXXXXX 100644
11
--- a/block.c
12
+++ b/block.c
13
@@ -XXX,XX +XXX,XX @@ QemuOptsList bdrv_runtime_opts = {
14
.help = "try to optimize zero writes (off, on, unmap)",
15
},
16
{
17
- .name = "discard",
18
+ .name = BDRV_OPT_DISCARD,
19
.type = QEMU_OPT_STRING,
20
.help = "discard operation (ignore/off, unmap/on)",
21
},
22
@@ -XXX,XX +XXX,XX @@ static int bdrv_open_common(BlockDriverState *bs, BlockBackend *file,
23
}
24
}
25
26
- discard = qemu_opt_get(opts, "discard");
27
+ discard = qemu_opt_get(opts, BDRV_OPT_DISCARD);
28
if (discard != NULL) {
29
if (bdrv_parse_discard_flags(discard, &bs->open_flags) != 0) {
30
error_setg(errp, "Invalid discard option");
31
@@ -XXX,XX +XXX,XX @@ int bdrv_reopen_prepare(BDRVReopenState *reopen_state, BlockReopenQueue *queue,
32
33
update_flags_from_options(&reopen_state->flags, opts);
34
35
- discard = qemu_opt_get_del(opts, "discard");
36
+ discard = qemu_opt_get_del(opts, BDRV_OPT_DISCARD);
37
if (discard != NULL) {
38
if (bdrv_parse_discard_flags(discard, &reopen_state->flags) != 0) {
39
error_setg(errp, "Invalid discard option");
40
--
41
2.19.1
42
43
diff view generated by jsdifflib
1
From: Fam Zheng <famz@redhat.com>
1
From: Stefan Weil <sw@weilnetz.de>
2
2
3
In the beginning of the function, we initialize the local variable to 0,
3
Use %zu instead of %zd for unsigned numbers.
4
and in the body of the function, we check the assigned values and exit
5
the loop immediately. So here it can never be non-zero.
6
4
7
Reported-by: Kevin Wolf <kwolf@redhat.com>
5
This fixes two error messages from the LSTM static code analyzer:
8
Signed-off-by: Fam Zheng <famz@redhat.com>
6
9
Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
7
This argument should be of type 'ssize_t' but is of type 'unsigned long'
8
9
Signed-off-by: Stefan Weil <sw@weilnetz.de>
10
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
10
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
11
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
11
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
12
---
12
---
13
block/qcow2.c | 2 +-
13
qemu-io-cmds.c | 4 ++--
14
1 file changed, 1 insertion(+), 1 deletion(-)
14
1 file changed, 2 insertions(+), 2 deletions(-)
15
15
16
diff --git a/block/qcow2.c b/block/qcow2.c
16
diff --git a/qemu-io-cmds.c b/qemu-io-cmds.c
17
index XXXXXXX..XXXXXXX 100644
17
index XXXXXXX..XXXXXXX 100644
18
--- a/block/qcow2.c
18
--- a/qemu-io-cmds.c
19
+++ b/block/qcow2.c
19
+++ b/qemu-io-cmds.c
20
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int qcow2_handle_l2meta(BlockDriverState *bs,
20
@@ -XXX,XX +XXX,XX @@ static int readv_f(BlockBackend *blk, int argc, char **argv)
21
while (l2meta != NULL) {
21
memset(cmp_buf, pattern, qiov.size);
22
QCowL2Meta *next;
22
if (memcmp(buf, cmp_buf, qiov.size)) {
23
23
printf("Pattern verification failed at offset %"
24
- if (!ret && link_l2) {
24
- PRId64 ", %zd bytes\n", offset, qiov.size);
25
+ if (link_l2) {
25
+ PRId64 ", %zu bytes\n", offset, qiov.size);
26
ret = qcow2_alloc_cluster_link_l2(bs, l2meta);
26
ret = -EINVAL;
27
if (ret) {
27
}
28
goto out;
28
g_free(cmp_buf);
29
@@ -XXX,XX +XXX,XX @@ static void aio_read_done(void *opaque, int ret)
30
memset(cmp_buf, ctx->pattern, ctx->qiov.size);
31
if (memcmp(ctx->buf, cmp_buf, ctx->qiov.size)) {
32
printf("Pattern verification failed at offset %"
33
- PRId64 ", %zd bytes\n", ctx->offset, ctx->qiov.size);
34
+ PRId64 ", %zu bytes\n", ctx->offset, ctx->qiov.size);
35
}
36
g_free(cmp_buf);
37
}
29
--
38
--
30
2.13.6
39
2.19.1
31
40
32
41
diff view generated by jsdifflib
1
All callers are coroutine_fns now, so we can just directly call
1
From: Peter Maydell <peter.maydell@linaro.org>
2
preallocate_co().
3
2
3
Taking the address of a field in a packed struct is a bad idea, because
4
it might not be actually aligned enough for that pointer type (and
5
thus cause a crash on dereference on some host architectures). Newer
6
versions of clang warn about this. Avoid the bug by not using the
7
"modify in place" byte swapping functions.
8
9
There are a few places where the in-place swap function is
10
used on something other than a packed struct field; we convert
11
those anyway, for consistency.
12
13
This patch was produced with the following spatch script
14
(and hand-editing to fold a few resulting overlength lines):
15
16
@@
17
expression E;
18
@@
19
-be16_to_cpus(&E);
20
+E = be16_to_cpu(E);
21
@@
22
expression E;
23
@@
24
-be32_to_cpus(&E);
25
+E = be32_to_cpu(E);
26
@@
27
expression E;
28
@@
29
-be64_to_cpus(&E);
30
+E = be64_to_cpu(E);
31
@@
32
expression E;
33
@@
34
-cpu_to_be16s(&E);
35
+E = cpu_to_be16(E);
36
@@
37
expression E;
38
@@
39
-cpu_to_be32s(&E);
40
+E = cpu_to_be32(E);
41
@@
42
expression E;
43
@@
44
-cpu_to_be64s(&E);
45
+E = cpu_to_be64(E);
46
47
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
48
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
49
Tested-by: John Snow <jsnow@redhat.com>
50
Reviewed-by: John Snow <jsnow@redhat.com>
4
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
51
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
5
Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
6
---
52
---
7
block/qcow2.c | 51 ++++++++-------------------------------------------
53
block/qcow2.c | 64 +++++++++++++++++++++++++++------------------------
8
1 file changed, 8 insertions(+), 43 deletions(-)
54
1 file changed, 34 insertions(+), 30 deletions(-)
9
55
10
diff --git a/block/qcow2.c b/block/qcow2.c
56
diff --git a/block/qcow2.c b/block/qcow2.c
11
index XXXXXXX..XXXXXXX 100644
57
index XXXXXXX..XXXXXXX 100644
12
--- a/block/qcow2.c
58
--- a/block/qcow2.c
13
+++ b/block/qcow2.c
59
+++ b/block/qcow2.c
14
@@ -XXX,XX +XXX,XX @@ static int qcow2_set_up_encryption(BlockDriverState *bs,
60
@@ -XXX,XX +XXX,XX @@ static int qcow2_read_extensions(BlockDriverState *bs, uint64_t start_offset,
15
return ret;
61
"pread fail from offset %" PRIu64, offset);
16
}
62
return 1;
17
18
-
19
-typedef struct PreallocCo {
20
- BlockDriverState *bs;
21
- uint64_t offset;
22
- uint64_t new_length;
23
-
24
- int ret;
25
-} PreallocCo;
26
-
27
/**
28
* Preallocates metadata structures for data clusters between @offset (in the
29
* guest disk) and @new_length (which is thus generally the new guest disk
30
@@ -XXX,XX +XXX,XX @@ typedef struct PreallocCo {
31
*
32
* Returns: 0 on success, -errno on failure.
33
*/
34
-static void coroutine_fn preallocate_co(void *opaque)
35
+static int coroutine_fn preallocate_co(BlockDriverState *bs, uint64_t offset,
36
+ uint64_t new_length)
37
{
38
- PreallocCo *params = opaque;
39
- BlockDriverState *bs = params->bs;
40
- uint64_t offset = params->offset;
41
- uint64_t new_length = params->new_length;
42
uint64_t bytes;
43
uint64_t host_offset = 0;
44
unsigned int cur_bytes;
45
@@ -XXX,XX +XXX,XX @@ static void coroutine_fn preallocate_co(void *opaque)
46
ret = qcow2_alloc_cluster_offset(bs, offset, &cur_bytes,
47
&host_offset, &meta);
48
if (ret < 0) {
49
- goto done;
50
+ return ret;
51
}
63
}
52
64
- be32_to_cpus(&ext.magic);
53
while (meta) {
65
- be32_to_cpus(&ext.len);
54
@@ -XXX,XX +XXX,XX @@ static void coroutine_fn preallocate_co(void *opaque)
66
+ ext.magic = be32_to_cpu(ext.magic);
55
if (ret < 0) {
67
+ ext.len = be32_to_cpu(ext.len);
56
qcow2_free_any_clusters(bs, meta->alloc_offset,
68
offset += sizeof(ext);
57
meta->nb_clusters, QCOW2_DISCARD_NEVER);
69
#ifdef DEBUG_EXT
58
- goto done;
70
printf("ext.magic = 0x%x\n", ext.magic);
59
+ return ret;
71
@@ -XXX,XX +XXX,XX @@ static int qcow2_read_extensions(BlockDriverState *bs, uint64_t start_offset,
72
"Unable to read CRYPTO header extension");
73
return ret;
60
}
74
}
61
75
- be64_to_cpus(&s->crypto_header.offset);
62
/* There are no dependent requests, but we need to remove our
76
- be64_to_cpus(&s->crypto_header.length);
63
@@ -XXX,XX +XXX,XX @@ static void coroutine_fn preallocate_co(void *opaque)
77
+ s->crypto_header.offset = be64_to_cpu(s->crypto_header.offset);
64
ret = bdrv_pwrite(bs->file, (host_offset + cur_bytes) - 1,
78
+ s->crypto_header.length = be64_to_cpu(s->crypto_header.length);
65
&data, 1);
79
66
if (ret < 0) {
80
if ((s->crypto_header.offset % s->cluster_size) != 0) {
67
- goto done;
81
error_setg(errp, "Encryption header offset '%" PRIu64 "' is "
68
+ return ret;
82
@@ -XXX,XX +XXX,XX @@ static int qcow2_read_extensions(BlockDriverState *bs, uint64_t start_offset,
83
return -EINVAL;
84
}
85
86
- be32_to_cpus(&bitmaps_ext.nb_bitmaps);
87
- be64_to_cpus(&bitmaps_ext.bitmap_directory_size);
88
- be64_to_cpus(&bitmaps_ext.bitmap_directory_offset);
89
+ bitmaps_ext.nb_bitmaps = be32_to_cpu(bitmaps_ext.nb_bitmaps);
90
+ bitmaps_ext.bitmap_directory_size =
91
+ be64_to_cpu(bitmaps_ext.bitmap_directory_size);
92
+ bitmaps_ext.bitmap_directory_offset =
93
+ be64_to_cpu(bitmaps_ext.bitmap_directory_offset);
94
95
if (bitmaps_ext.nb_bitmaps > QCOW2_MAX_BITMAPS) {
96
error_setg(errp,
97
@@ -XXX,XX +XXX,XX @@ static int coroutine_fn qcow2_do_open(BlockDriverState *bs, QDict *options,
98
error_setg_errno(errp, -ret, "Could not read qcow2 header");
99
goto fail;
100
}
101
- be32_to_cpus(&header.magic);
102
- be32_to_cpus(&header.version);
103
- be64_to_cpus(&header.backing_file_offset);
104
- be32_to_cpus(&header.backing_file_size);
105
- be64_to_cpus(&header.size);
106
- be32_to_cpus(&header.cluster_bits);
107
- be32_to_cpus(&header.crypt_method);
108
- be64_to_cpus(&header.l1_table_offset);
109
- be32_to_cpus(&header.l1_size);
110
- be64_to_cpus(&header.refcount_table_offset);
111
- be32_to_cpus(&header.refcount_table_clusters);
112
- be64_to_cpus(&header.snapshots_offset);
113
- be32_to_cpus(&header.nb_snapshots);
114
+ header.magic = be32_to_cpu(header.magic);
115
+ header.version = be32_to_cpu(header.version);
116
+ header.backing_file_offset = be64_to_cpu(header.backing_file_offset);
117
+ header.backing_file_size = be32_to_cpu(header.backing_file_size);
118
+ header.size = be64_to_cpu(header.size);
119
+ header.cluster_bits = be32_to_cpu(header.cluster_bits);
120
+ header.crypt_method = be32_to_cpu(header.crypt_method);
121
+ header.l1_table_offset = be64_to_cpu(header.l1_table_offset);
122
+ header.l1_size = be32_to_cpu(header.l1_size);
123
+ header.refcount_table_offset = be64_to_cpu(header.refcount_table_offset);
124
+ header.refcount_table_clusters =
125
+ be32_to_cpu(header.refcount_table_clusters);
126
+ header.snapshots_offset = be64_to_cpu(header.snapshots_offset);
127
+ header.nb_snapshots = be32_to_cpu(header.nb_snapshots);
128
129
if (header.magic != QCOW_MAGIC) {
130
error_setg(errp, "Image is not in qcow2 format");
131
@@ -XXX,XX +XXX,XX @@ static int coroutine_fn qcow2_do_open(BlockDriverState *bs, QDict *options,
132
header.refcount_order = 4;
133
header.header_length = 72;
134
} else {
135
- be64_to_cpus(&header.incompatible_features);
136
- be64_to_cpus(&header.compatible_features);
137
- be64_to_cpus(&header.autoclear_features);
138
- be32_to_cpus(&header.refcount_order);
139
- be32_to_cpus(&header.header_length);
140
+ header.incompatible_features =
141
+ be64_to_cpu(header.incompatible_features);
142
+ header.compatible_features = be64_to_cpu(header.compatible_features);
143
+ header.autoclear_features = be64_to_cpu(header.autoclear_features);
144
+ header.refcount_order = be32_to_cpu(header.refcount_order);
145
+ header.header_length = be32_to_cpu(header.header_length);
146
147
if (header.header_length < 104) {
148
error_setg(errp, "qcow2 header too short");
149
@@ -XXX,XX +XXX,XX @@ static int coroutine_fn qcow2_do_open(BlockDriverState *bs, QDict *options,
150
goto fail;
151
}
152
for(i = 0;i < s->l1_size; i++) {
153
- be64_to_cpus(&s->l1_table[i]);
154
+ s->l1_table[i] = be64_to_cpu(s->l1_table[i]);
69
}
155
}
70
}
156
}
71
157
72
- ret = 0;
158
@@ -XXX,XX +XXX,XX @@ int qcow2_update_header(BlockDriverState *bs)
73
-
159
74
-done:
160
/* Full disk encryption header pointer extension */
75
- params->ret = ret;
161
if (s->crypto_header.offset != 0) {
76
-}
162
- cpu_to_be64s(&s->crypto_header.offset);
77
-
163
- cpu_to_be64s(&s->crypto_header.length);
78
-static int preallocate(BlockDriverState *bs,
164
+ s->crypto_header.offset = cpu_to_be64(s->crypto_header.offset);
79
- uint64_t offset, uint64_t new_length)
165
+ s->crypto_header.length = cpu_to_be64(s->crypto_header.length);
80
-{
166
ret = header_ext_add(buf, QCOW2_EXT_MAGIC_CRYPTO_HEADER,
81
- PreallocCo params = {
167
&s->crypto_header, sizeof(s->crypto_header),
82
- .bs = bs,
168
buflen);
83
- .offset = offset,
169
- be64_to_cpus(&s->crypto_header.offset);
84
- .new_length = new_length,
170
- be64_to_cpus(&s->crypto_header.length);
85
- .ret = -EINPROGRESS,
171
+ s->crypto_header.offset = be64_to_cpu(s->crypto_header.offset);
86
- };
172
+ s->crypto_header.length = be64_to_cpu(s->crypto_header.length);
87
-
88
- if (qemu_in_coroutine()) {
89
- preallocate_co(&params);
90
- } else {
91
- Coroutine *co = qemu_coroutine_create(preallocate_co, &params);
92
- bdrv_coroutine_enter(bs, co);
93
- BDRV_POLL_WHILE(bs, params.ret == -EINPROGRESS);
94
- }
95
- return params.ret;
96
+ return 0;
97
}
98
99
/* qcow2_refcount_metadata_size:
100
@@ -XXX,XX +XXX,XX @@ qcow2_co_create(BlockdevCreateOptions *create_options, Error **errp)
101
if (qcow2_opts->preallocation != PREALLOC_MODE_OFF) {
102
BDRVQcow2State *s = blk_bs(blk)->opaque;
103
qemu_co_mutex_lock(&s->lock);
104
- ret = preallocate(blk_bs(blk), 0, qcow2_opts->size);
105
+ ret = preallocate_co(blk_bs(blk), 0, qcow2_opts->size);
106
qemu_co_mutex_unlock(&s->lock);
107
108
if (ret < 0) {
173
if (ret < 0) {
109
@@ -XXX,XX +XXX,XX @@ static int coroutine_fn qcow2_co_truncate(BlockDriverState *bs, int64_t offset,
110
break;
111
112
case PREALLOC_MODE_METADATA:
113
- ret = preallocate(bs, old_length, offset);
114
+ ret = preallocate_co(bs, old_length, offset);
115
if (ret < 0) {
116
error_setg_errno(errp, -ret, "Preallocation failed");
117
goto fail;
174
goto fail;
175
}
118
--
176
--
119
2.13.6
177
2.19.1
120
178
121
179
diff view generated by jsdifflib
1
From: Eric Blake <eblake@redhat.com>
1
From: Peter Maydell <peter.maydell@linaro.org>
2
2
3
We are gradually moving away from sector-based interfaces, towards
3
Taking the address of a field in a packed struct is a bad idea, because
4
byte-based. The qcow driver is now ready to fully utilize the
4
it might not be actually aligned enough for that pointer type (and
5
byte-based callback interface, as long as we override the default
5
thus cause a crash on dereference on some host architectures). Newer
6
alignment to still be 512 (needed at least for asserts present
6
versions of clang warn about this. Avoid the bug by not using the
7
because of encryption, but easier to do everywhere than to audit
7
"modify in place" byte swapping functions.
8
which sub-sector requests are handled correctly, especially since
9
we no longer recommend qcow for new disk images).
10
8
11
Signed-off-by: Eric Blake <eblake@redhat.com>
9
There are a few places where the in-place swap function is
12
Reviewed-by: Jeff Cody <jcody@redhat.com>
10
used on something other than a packed struct field; we convert
11
those anyway, for consistency.
12
13
This patch was produced with the following spatch script:
14
15
@@
16
expression E;
17
@@
18
-be16_to_cpus(&E);
19
+E = be16_to_cpu(E);
20
@@
21
expression E;
22
@@
23
-be32_to_cpus(&E);
24
+E = be32_to_cpu(E);
25
@@
26
expression E;
27
@@
28
-be64_to_cpus(&E);
29
+E = be64_to_cpu(E);
30
@@
31
expression E;
32
@@
33
-cpu_to_be16s(&E);
34
+E = cpu_to_be16(E);
35
@@
36
expression E;
37
@@
38
-cpu_to_be32s(&E);
39
+E = cpu_to_be32(E);
40
@@
41
expression E;
42
@@
43
-cpu_to_be64s(&E);
44
+E = cpu_to_be64(E);
45
46
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
47
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
48
Tested-by: John Snow <jsnow@redhat.com>
49
Reviewed-by: John Snow <jsnow@redhat.com>
13
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
50
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
14
---
51
---
15
block/qcow.c | 35 ++++++++++++++++++++---------------
52
block/qcow.c | 18 +++++++++---------
16
1 file changed, 20 insertions(+), 15 deletions(-)
53
1 file changed, 9 insertions(+), 9 deletions(-)
17
54
18
diff --git a/block/qcow.c b/block/qcow.c
55
diff --git a/block/qcow.c b/block/qcow.c
19
index XXXXXXX..XXXXXXX 100644
56
index XXXXXXX..XXXXXXX 100644
20
--- a/block/qcow.c
57
--- a/block/qcow.c
21
+++ b/block/qcow.c
58
+++ b/block/qcow.c
22
@@ -XXX,XX +XXX,XX @@ typedef struct QCowHeader {
59
@@ -XXX,XX +XXX,XX @@ static int qcow_open(BlockDriverState *bs, QDict *options, int flags,
23
typedef struct BDRVQcowState {
60
if (ret < 0) {
24
int cluster_bits;
61
goto fail;
25
int cluster_size;
62
}
26
- int cluster_sectors;
63
- be32_to_cpus(&header.magic);
27
int l2_bits;
64
- be32_to_cpus(&header.version);
28
int l2_size;
65
- be64_to_cpus(&header.backing_file_offset);
29
unsigned int l1_size;
66
- be32_to_cpus(&header.backing_file_size);
67
- be32_to_cpus(&header.mtime);
68
- be64_to_cpus(&header.size);
69
- be32_to_cpus(&header.crypt_method);
70
- be64_to_cpus(&header.l1_table_offset);
71
+ header.magic = be32_to_cpu(header.magic);
72
+ header.version = be32_to_cpu(header.version);
73
+ header.backing_file_offset = be64_to_cpu(header.backing_file_offset);
74
+ header.backing_file_size = be32_to_cpu(header.backing_file_size);
75
+ header.mtime = be32_to_cpu(header.mtime);
76
+ header.size = be64_to_cpu(header.size);
77
+ header.crypt_method = be32_to_cpu(header.crypt_method);
78
+ header.l1_table_offset = be64_to_cpu(header.l1_table_offset);
79
80
if (header.magic != QCOW_MAGIC) {
81
error_setg(errp, "Image not in qcow format");
30
@@ -XXX,XX +XXX,XX @@ static int qcow_open(BlockDriverState *bs, QDict *options, int flags,
82
@@ -XXX,XX +XXX,XX @@ static int qcow_open(BlockDriverState *bs, QDict *options, int flags,
31
}
83
}
32
s->cluster_bits = header.cluster_bits;
84
33
s->cluster_size = 1 << s->cluster_bits;
85
for(i = 0;i < s->l1_size; i++) {
34
- s->cluster_sectors = 1 << (s->cluster_bits - 9);
86
- be64_to_cpus(&s->l1_table[i]);
35
s->l2_bits = header.l2_bits;
87
+ s->l1_table[i] = be64_to_cpu(s->l1_table[i]);
36
s->l2_size = 1 << s->l2_bits;
88
}
37
bs->total_sectors = header.size / 512;
89
38
@@ -XXX,XX +XXX,XX @@ static int decompress_cluster(BlockDriverState *bs, uint64_t cluster_offset)
90
/* alloc L2 cache (max. 64k * 16 * 8 = 8 MB) */
39
return 0;
40
}
41
42
-static coroutine_fn int qcow_co_readv(BlockDriverState *bs, int64_t sector_num,
43
- int nb_sectors, QEMUIOVector *qiov)
44
+static void qcow_refresh_limits(BlockDriverState *bs, Error **errp)
45
+{
46
+ /* At least encrypted images require 512-byte alignment. Apply the
47
+ * limit universally, rather than just on encrypted images, as
48
+ * it's easier to let the block layer handle rounding than to
49
+ * audit this code further. */
50
+ bs->bl.request_alignment = BDRV_SECTOR_SIZE;
51
+}
52
+
53
+static coroutine_fn int qcow_co_preadv(BlockDriverState *bs, uint64_t offset,
54
+ uint64_t bytes, QEMUIOVector *qiov,
55
+ int flags)
56
{
57
BDRVQcowState *s = bs->opaque;
58
int offset_in_cluster;
59
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int qcow_co_readv(BlockDriverState *bs, int64_t sector_num,
60
QEMUIOVector hd_qiov;
61
uint8_t *buf;
62
void *orig_buf;
63
- int64_t offset = sector_num * BDRV_SECTOR_SIZE;
64
- int64_t bytes = nb_sectors * BDRV_SECTOR_SIZE;
65
66
+ assert(!flags);
67
if (qiov->niov > 1) {
68
buf = orig_buf = qemu_try_blockalign(bs, qiov->size);
69
if (buf == NULL) {
70
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int qcow_co_readv(BlockDriverState *bs, int64_t sector_num,
71
return ret;
72
}
73
74
-static coroutine_fn int qcow_co_writev(BlockDriverState *bs, int64_t sector_num,
75
- int nb_sectors, QEMUIOVector *qiov,
76
- int flags)
77
+static coroutine_fn int qcow_co_pwritev(BlockDriverState *bs, uint64_t offset,
78
+ uint64_t bytes, QEMUIOVector *qiov,
79
+ int flags)
80
{
81
BDRVQcowState *s = bs->opaque;
82
int offset_in_cluster;
83
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int qcow_co_writev(BlockDriverState *bs, int64_t sector_num,
84
QEMUIOVector hd_qiov;
85
uint8_t *buf;
86
void *orig_buf;
87
- int64_t offset = sector_num * BDRV_SECTOR_SIZE;
88
- int64_t bytes = nb_sectors * BDRV_SECTOR_SIZE;
89
90
assert(!flags);
91
s->cluster_cache_offset = -1; /* disable compressed cache */
92
@@ -XXX,XX +XXX,XX @@ qcow_co_pwritev_compressed(BlockDriverState *bs, uint64_t offset,
93
94
if (ret != Z_STREAM_END || out_len >= s->cluster_size) {
95
/* could not compress: write normal cluster */
96
- ret = qcow_co_writev(bs, offset >> BDRV_SECTOR_BITS,
97
- bytes >> BDRV_SECTOR_BITS, qiov, 0);
98
+ ret = qcow_co_pwritev(bs, offset, bytes, qiov, 0);
99
if (ret < 0) {
100
goto fail;
101
}
102
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_qcow = {
103
.bdrv_co_create_opts = qcow_co_create_opts,
104
.bdrv_has_zero_init = bdrv_has_zero_init_1,
105
.supports_backing = true,
106
+ .bdrv_refresh_limits = qcow_refresh_limits,
107
108
- .bdrv_co_readv = qcow_co_readv,
109
- .bdrv_co_writev = qcow_co_writev,
110
+ .bdrv_co_preadv = qcow_co_preadv,
111
+ .bdrv_co_pwritev = qcow_co_pwritev,
112
.bdrv_co_block_status = qcow_co_block_status,
113
114
.bdrv_make_empty = qcow_make_empty,
115
--
91
--
116
2.13.6
92
2.19.1
117
93
118
94
diff view generated by jsdifflib
1
From: Fam Zheng <famz@redhat.com>
1
From: Peter Maydell <peter.maydell@linaro.org>
2
2
3
in_flight and tracked requests need to be tracked in every layer during
3
Taking the address of a field in a packed struct is a bad idea, because
4
recursion. For now the only user is qemu-img convert where overlapping
4
it might not be actually aligned enough for that pointer type (and
5
requests and IOThreads don't exist, therefore this change doesn't make
5
thus cause a crash on dereference on some host architectures). Newer
6
much difference form user point of view, but it is incorrect as part of
6
versions of clang warn about this. Avoid the bug by not using the
7
the API. Fix it.
7
"modify in place" byte swapping functions.
8
8
9
Reported-by: Kevin Wolf <kwolf@redhat.com>
9
There are a few places where the in-place swap function is
10
Signed-off-by: Fam Zheng <famz@redhat.com>
10
used on something other than a packed struct field; we convert
11
Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
11
those anyway, for consistency.
12
13
This patch was produced with the following spatch script:
14
15
@@
16
expression E;
17
@@
18
-be16_to_cpus(&E);
19
+E = be16_to_cpu(E);
20
@@
21
expression E;
22
@@
23
-be32_to_cpus(&E);
24
+E = be32_to_cpu(E);
25
@@
26
expression E;
27
@@
28
-be64_to_cpus(&E);
29
+E = be64_to_cpu(E);
30
@@
31
expression E;
32
@@
33
-cpu_to_be16s(&E);
34
+E = cpu_to_be16(E);
35
@@
36
expression E;
37
@@
38
-cpu_to_be32s(&E);
39
+E = cpu_to_be32(E);
40
@@
41
expression E;
42
@@
43
-cpu_to_be64s(&E);
44
+E = cpu_to_be64(E);
45
46
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
47
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
48
Tested-by: John Snow <jsnow@redhat.com>
49
Reviewed-by: John Snow <jsnow@redhat.com>
12
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
50
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
13
---
51
---
14
block/io.c | 59 ++++++++++++++++++++++++++++-------------------------------
52
block/qcow2-bitmap.c | 24 ++++++++++++------------
15
1 file changed, 28 insertions(+), 31 deletions(-)
53
1 file changed, 12 insertions(+), 12 deletions(-)
16
54
17
diff --git a/block/io.c b/block/io.c
55
diff --git a/block/qcow2-bitmap.c b/block/qcow2-bitmap.c
18
index XXXXXXX..XXXXXXX 100644
56
index XXXXXXX..XXXXXXX 100644
19
--- a/block/io.c
57
--- a/block/qcow2-bitmap.c
20
+++ b/block/io.c
58
+++ b/block/qcow2-bitmap.c
21
@@ -XXX,XX +XXX,XX @@ static int coroutine_fn bdrv_co_copy_range_internal(BdrvChild *src,
59
@@ -XXX,XX +XXX,XX @@ static inline void bitmap_table_to_be(uint64_t *bitmap_table, size_t size)
22
BdrvRequestFlags flags,
60
size_t i;
23
bool recurse_src)
61
62
for (i = 0; i < size; ++i) {
63
- cpu_to_be64s(&bitmap_table[i]);
64
+ bitmap_table[i] = cpu_to_be64(bitmap_table[i]);
65
}
66
}
67
68
@@ -XXX,XX +XXX,XX @@ static int bitmap_table_load(BlockDriverState *bs, Qcow2BitmapTable *tb,
69
}
70
71
for (i = 0; i < tb->size; ++i) {
72
- be64_to_cpus(&table[i]);
73
+ table[i] = be64_to_cpu(table[i]);
74
ret = check_table_entry(table[i], s->cluster_size);
75
if (ret < 0) {
76
goto fail;
77
@@ -XXX,XX +XXX,XX @@ fail:
78
79
static inline void bitmap_dir_entry_to_cpu(Qcow2BitmapDirEntry *entry)
24
{
80
{
25
+ BdrvTrackedRequest src_req, dst_req;
81
- be64_to_cpus(&entry->bitmap_table_offset);
26
+ BlockDriverState *src_bs = src->bs;
82
- be32_to_cpus(&entry->bitmap_table_size);
27
+ BlockDriverState *dst_bs = dst->bs;
83
- be32_to_cpus(&entry->flags);
28
int ret;
84
- be16_to_cpus(&entry->name_size);
29
85
- be32_to_cpus(&entry->extra_data_size);
30
if (!src || !dst || !src->bs || !dst->bs) {
86
+ entry->bitmap_table_offset = be64_to_cpu(entry->bitmap_table_offset);
31
@@ -XXX,XX +XXX,XX @@ static int coroutine_fn bdrv_co_copy_range_internal(BdrvChild *src,
87
+ entry->bitmap_table_size = be32_to_cpu(entry->bitmap_table_size);
32
|| src->bs->encrypted || dst->bs->encrypted) {
88
+ entry->flags = be32_to_cpu(entry->flags);
33
return -ENOTSUP;
89
+ entry->name_size = be16_to_cpu(entry->name_size);
34
}
90
+ entry->extra_data_size = be32_to_cpu(entry->extra_data_size);
35
+ bdrv_inc_in_flight(src_bs);
36
+ bdrv_inc_in_flight(dst_bs);
37
+ tracked_request_begin(&src_req, src_bs, src_offset,
38
+ bytes, BDRV_TRACKED_READ);
39
+ tracked_request_begin(&dst_req, dst_bs, dst_offset,
40
+ bytes, BDRV_TRACKED_WRITE);
41
+
42
+ wait_serialising_requests(&src_req);
43
+ wait_serialising_requests(&dst_req);
44
if (recurse_src) {
45
- return src->bs->drv->bdrv_co_copy_range_from(src->bs,
46
- src, src_offset,
47
- dst, dst_offset,
48
- bytes, flags);
49
+ ret = src->bs->drv->bdrv_co_copy_range_from(src->bs,
50
+ src, src_offset,
51
+ dst, dst_offset,
52
+ bytes, flags);
53
} else {
54
- return dst->bs->drv->bdrv_co_copy_range_to(dst->bs,
55
- src, src_offset,
56
- dst, dst_offset,
57
- bytes, flags);
58
+ ret = dst->bs->drv->bdrv_co_copy_range_to(dst->bs,
59
+ src, src_offset,
60
+ dst, dst_offset,
61
+ bytes, flags);
62
}
63
+ tracked_request_end(&src_req);
64
+ tracked_request_end(&dst_req);
65
+ bdrv_dec_in_flight(src_bs);
66
+ bdrv_dec_in_flight(dst_bs);
67
+ return ret;
68
}
91
}
69
92
70
/* Copy range from @src to @dst.
93
static inline void bitmap_dir_entry_to_be(Qcow2BitmapDirEntry *entry)
71
@@ -XXX,XX +XXX,XX @@ int coroutine_fn bdrv_co_copy_range(BdrvChild *src, uint64_t src_offset,
72
BdrvChild *dst, uint64_t dst_offset,
73
uint64_t bytes, BdrvRequestFlags flags)
74
{
94
{
75
- BdrvTrackedRequest src_req, dst_req;
95
- cpu_to_be64s(&entry->bitmap_table_offset);
76
- BlockDriverState *src_bs = src->bs;
96
- cpu_to_be32s(&entry->bitmap_table_size);
77
- BlockDriverState *dst_bs = dst->bs;
97
- cpu_to_be32s(&entry->flags);
78
- int ret;
98
- cpu_to_be16s(&entry->name_size);
79
-
99
- cpu_to_be32s(&entry->extra_data_size);
80
- bdrv_inc_in_flight(src_bs);
100
+ entry->bitmap_table_offset = cpu_to_be64(entry->bitmap_table_offset);
81
- bdrv_inc_in_flight(dst_bs);
101
+ entry->bitmap_table_size = cpu_to_be32(entry->bitmap_table_size);
82
- tracked_request_begin(&src_req, src_bs, src_offset,
102
+ entry->flags = cpu_to_be32(entry->flags);
83
- bytes, BDRV_TRACKED_READ);
103
+ entry->name_size = cpu_to_be16(entry->name_size);
84
- tracked_request_begin(&dst_req, dst_bs, dst_offset,
104
+ entry->extra_data_size = cpu_to_be32(entry->extra_data_size);
85
- bytes, BDRV_TRACKED_WRITE);
86
-
87
- wait_serialising_requests(&src_req);
88
- wait_serialising_requests(&dst_req);
89
- ret = bdrv_co_copy_range_from(src, src_offset,
90
- dst, dst_offset,
91
- bytes, flags);
92
-
93
- tracked_request_end(&src_req);
94
- tracked_request_end(&dst_req);
95
- bdrv_dec_in_flight(src_bs);
96
- bdrv_dec_in_flight(dst_bs);
97
- return ret;
98
+ return bdrv_co_copy_range_from(src, src_offset,
99
+ dst, dst_offset,
100
+ bytes, flags);
101
}
105
}
102
106
103
static void bdrv_parent_cb_resize(BlockDriverState *bs)
107
static inline int calc_dir_entry_size(size_t name_size, size_t extra_data_size)
104
--
108
--
105
2.13.6
109
2.19.1
106
110
107
111
diff view generated by jsdifflib
New patch
1
From: Daniel P. Berrangé <berrange@redhat.com>
1
2
3
The qcow2 block driver expects to see a valid sector size even when it
4
has opened the crypto layer with QCRYPTO_BLOCK_OPEN_NO_IO.
5
6
Signed-off-by: Daniel P. Berrangé <berrange@redhat.com>
7
Reviewed-by: Alberto Garcia <berto@igalia.com>
8
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
9
---
10
crypto/block-qcow.c | 2 ++
11
1 file changed, 2 insertions(+)
12
13
diff --git a/crypto/block-qcow.c b/crypto/block-qcow.c
14
index XXXXXXX..XXXXXXX 100644
15
--- a/crypto/block-qcow.c
16
+++ b/crypto/block-qcow.c
17
@@ -XXX,XX +XXX,XX @@ qcrypto_block_qcow_open(QCryptoBlock *block,
18
Error **errp)
19
{
20
if (flags & QCRYPTO_BLOCK_OPEN_NO_IO) {
21
+ block->sector_size = QCRYPTO_BLOCK_QCOW_SECTOR_SIZE;
22
+ block->payload_offset = 0;
23
return 0;
24
} else {
25
if (!options->u.qcow.key_secret) {
26
--
27
2.19.1
28
29
diff view generated by jsdifflib
1
If qcow2_alloc_clusters_at() returns an error, we do need to negate it
1
From: Alberto Garcia <berto@igalia.com>
2
to get back the positive errno code for error_setg_errno(), but we still
3
need to return the negative error code.
4
2
5
Fixes: 772d1f973f87269f6a4a4ea4b880680f3779bbdf
3
This doesn't have any practical effect at the moment because the
4
values of BDRV_SECTOR_SIZE, QCRYPTO_BLOCK_LUKS_SECTOR_SIZE and
5
QCRYPTO_BLOCK_QCOW_SECTOR_SIZE are all the same (512 bytes), but
6
future encryption methods could have different requirements.
7
8
Signed-off-by: Alberto Garcia <berto@igalia.com>
9
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
6
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
10
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
7
Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
8
---
11
---
9
block/qcow2.c | 2 +-
12
block/qcow2.c | 2 +-
10
1 file changed, 1 insertion(+), 1 deletion(-)
13
1 file changed, 1 insertion(+), 1 deletion(-)
11
14
12
diff --git a/block/qcow2.c b/block/qcow2.c
15
diff --git a/block/qcow2.c b/block/qcow2.c
13
index XXXXXXX..XXXXXXX 100644
16
index XXXXXXX..XXXXXXX 100644
14
--- a/block/qcow2.c
17
--- a/block/qcow2.c
15
+++ b/block/qcow2.c
18
+++ b/block/qcow2.c
16
@@ -XXX,XX +XXX,XX @@ static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
19
@@ -XXX,XX +XXX,XX @@ static void qcow2_refresh_limits(BlockDriverState *bs, Error **errp)
17
if (clusters_allocated < 0) {
20
18
error_setg_errno(errp, -clusters_allocated,
21
if (bs->encrypted) {
19
"Failed to allocate data clusters");
22
/* Encryption works on a sector granularity */
20
- return -clusters_allocated;
23
- bs->bl.request_alignment = BDRV_SECTOR_SIZE;
21
+ return clusters_allocated;
24
+ bs->bl.request_alignment = qcrypto_block_get_sector_size(s->crypto);
22
}
25
}
23
26
bs->bl.pwrite_zeroes_alignment = s->cluster_size;
24
assert(clusters_allocated == nb_new_data_clusters);
27
bs->bl.pdiscard_alignment = s->cluster_size;
25
--
28
--
26
2.13.6
29
2.19.1
27
30
28
31
diff view generated by jsdifflib
1
From: Markus Armbruster <armbru@redhat.com>
1
From: Li Qiang <liq3ea@163.com>
2
2
3
block_crypto_open_opts_init() and block_crypto_create_opts_init()
3
Signed-off-by: Li Qiang <liq3ea@163.com>
4
contain a virtual visit of QCryptoBlockOptions and
4
Reviewed-by: Alberto Garcia <berto@igalia.com>
5
QCryptoBlockCreateOptions less member "format", respectively.
6
7
Change their callers to put member "format" in the QDict, so they can
8
use the generated visitors for these types instead.
9
10
Signed-off-by: Markus Armbruster <armbru@redhat.com>
11
Reviewed-by: Eric Blake <eblake@redhat.com>
12
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
5
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
13
---
6
---
14
block/crypto.h | 8 ++---
7
include/sysemu/block-backend.h | 6 +++---
15
block/crypto.c | 99 +++++++++-------------------------------------------------
8
block/block-backend.c | 8 ++++----
16
block/qcow.c | 5 ++-
9
2 files changed, 7 insertions(+), 7 deletions(-)
17
block/qcow2.c | 10 +++---
18
4 files changed, 22 insertions(+), 100 deletions(-)
19
10
20
diff --git a/block/crypto.h b/block/crypto.h
11
diff --git a/include/sysemu/block-backend.h b/include/sysemu/block-backend.h
21
index XXXXXXX..XXXXXXX 100644
12
index XXXXXXX..XXXXXXX 100644
22
--- a/block/crypto.h
13
--- a/include/sysemu/block-backend.h
23
+++ b/block/crypto.h
14
+++ b/include/sysemu/block-backend.h
24
@@ -XXX,XX +XXX,XX @@
15
@@ -XXX,XX +XXX,XX @@ BlockErrorAction blk_get_error_action(BlockBackend *blk, bool is_read,
16
int error);
17
void blk_error_action(BlockBackend *blk, BlockErrorAction action,
18
bool is_read, int error);
19
-int blk_is_read_only(BlockBackend *blk);
20
-int blk_is_sg(BlockBackend *blk);
21
-int blk_enable_write_cache(BlockBackend *blk);
22
+bool blk_is_read_only(BlockBackend *blk);
23
+bool blk_is_sg(BlockBackend *blk);
24
+bool blk_enable_write_cache(BlockBackend *blk);
25
void blk_set_enable_write_cache(BlockBackend *blk, bool wce);
26
void blk_invalidate_cache(BlockBackend *blk, Error **errp);
27
bool blk_is_inserted(BlockBackend *blk);
28
diff --git a/block/block-backend.c b/block/block-backend.c
29
index XXXXXXX..XXXXXXX 100644
30
--- a/block/block-backend.c
31
+++ b/block/block-backend.c
32
@@ -XXX,XX +XXX,XX @@ void blk_error_action(BlockBackend *blk, BlockErrorAction action,
25
}
33
}
26
34
}
27
QCryptoBlockCreateOptions *
35
28
-block_crypto_create_opts_init(QCryptoBlockFormat format,
36
-int blk_is_read_only(BlockBackend *blk)
29
- QDict *opts,
37
+bool blk_is_read_only(BlockBackend *blk)
30
- Error **errp);
31
+block_crypto_create_opts_init(QDict *opts, Error **errp);
32
33
QCryptoBlockOpenOptions *
34
-block_crypto_open_opts_init(QCryptoBlockFormat format,
35
- QDict *opts,
36
- Error **errp);
37
+block_crypto_open_opts_init(QDict *opts, Error **errp);
38
39
#endif /* BLOCK_CRYPTO_H__ */
40
diff --git a/block/crypto.c b/block/crypto.c
41
index XXXXXXX..XXXXXXX 100644
42
--- a/block/crypto.c
43
+++ b/block/crypto.c
44
@@ -XXX,XX +XXX,XX @@ static QemuOptsList block_crypto_create_opts_luks = {
45
46
47
QCryptoBlockOpenOptions *
48
-block_crypto_open_opts_init(QCryptoBlockFormat format,
49
- QDict *opts,
50
- Error **errp)
51
+block_crypto_open_opts_init(QDict *opts, Error **errp)
52
{
38
{
53
Visitor *v;
39
BlockDriverState *bs = blk_bs(blk);
54
- QCryptoBlockOpenOptions *ret = NULL;
40
55
- Error *local_err = NULL;
41
@@ -XXX,XX +XXX,XX @@ int blk_is_read_only(BlockBackend *blk)
56
-
57
- ret = g_new0(QCryptoBlockOpenOptions, 1);
58
- ret->format = format;
59
+ QCryptoBlockOpenOptions *ret;
60
61
- v = qobject_input_visitor_new_flat_confused(opts, &local_err);
62
+ v = qobject_input_visitor_new_flat_confused(opts, errp);
63
if (!v) {
64
- goto out;
65
- }
66
-
67
- visit_start_struct(v, NULL, NULL, 0, &local_err);
68
- if (local_err) {
69
- goto out;
70
- }
71
-
72
- switch (format) {
73
- case Q_CRYPTO_BLOCK_FORMAT_LUKS:
74
- visit_type_QCryptoBlockOptionsLUKS_members(
75
- v, &ret->u.luks, &local_err);
76
- break;
77
-
78
- case Q_CRYPTO_BLOCK_FORMAT_QCOW:
79
- visit_type_QCryptoBlockOptionsQCow_members(
80
- v, &ret->u.qcow, &local_err);
81
- break;
82
-
83
- default:
84
- error_setg(&local_err, "Unsupported block format %d", format);
85
- break;
86
- }
87
- if (!local_err) {
88
- visit_check_struct(v, &local_err);
89
+ return NULL;
90
}
42
}
91
92
- visit_end_struct(v, NULL);
93
+ visit_type_QCryptoBlockOpenOptions(v, NULL, &ret, errp);
94
95
- out:
96
- if (local_err) {
97
- error_propagate(errp, local_err);
98
- qapi_free_QCryptoBlockOpenOptions(ret);
99
- ret = NULL;
100
- }
101
visit_free(v);
102
return ret;
103
}
43
}
104
44
105
45
-int blk_is_sg(BlockBackend *blk)
106
QCryptoBlockCreateOptions *
46
+bool blk_is_sg(BlockBackend *blk)
107
-block_crypto_create_opts_init(QCryptoBlockFormat format,
108
- QDict *opts,
109
- Error **errp)
110
+block_crypto_create_opts_init(QDict *opts, Error **errp)
111
{
47
{
112
Visitor *v;
48
BlockDriverState *bs = blk_bs(blk);
113
- QCryptoBlockCreateOptions *ret = NULL;
49
114
- Error *local_err = NULL;
50
if (!bs) {
115
-
51
- return 0;
116
- ret = g_new0(QCryptoBlockCreateOptions, 1);
52
+ return false;
117
- ret->format = format;
118
+ QCryptoBlockCreateOptions *ret;
119
120
- v = qobject_input_visitor_new_flat_confused(opts, &local_err);
121
+ v = qobject_input_visitor_new_flat_confused(opts, errp);
122
if (!v) {
123
- goto out;
124
- }
125
-
126
- visit_start_struct(v, NULL, NULL, 0, &local_err);
127
- if (local_err) {
128
- goto out;
129
- }
130
-
131
- switch (format) {
132
- case Q_CRYPTO_BLOCK_FORMAT_LUKS:
133
- visit_type_QCryptoBlockCreateOptionsLUKS_members(
134
- v, &ret->u.luks, &local_err);
135
- break;
136
-
137
- case Q_CRYPTO_BLOCK_FORMAT_QCOW:
138
- visit_type_QCryptoBlockOptionsQCow_members(
139
- v, &ret->u.qcow, &local_err);
140
- break;
141
-
142
- default:
143
- error_setg(&local_err, "Unsupported block format %d", format);
144
- break;
145
- }
146
- if (!local_err) {
147
- visit_check_struct(v, &local_err);
148
+ return NULL;
149
}
53
}
150
54
151
- visit_end_struct(v, NULL);
55
return bdrv_is_sg(bs);
152
+ visit_type_QCryptoBlockCreateOptions(v, NULL, &ret, errp);
153
154
- out:
155
- if (local_err) {
156
- error_propagate(errp, local_err);
157
- qapi_free_QCryptoBlockCreateOptions(ret);
158
- ret = NULL;
159
- }
160
visit_free(v);
161
return ret;
162
}
56
}
163
@@ -XXX,XX +XXX,XX @@ static int block_crypto_open_generic(QCryptoBlockFormat format,
57
164
}
58
-int blk_enable_write_cache(BlockBackend *blk)
165
59
+bool blk_enable_write_cache(BlockBackend *blk)
166
cryptoopts = qemu_opts_to_qdict(opts, NULL);
60
{
167
+ qdict_put_str(cryptoopts, "format", QCryptoBlockFormat_str(format));
61
return blk->enable_write_cache;
168
62
}
169
- open_opts = block_crypto_open_opts_init(format, cryptoopts, errp);
170
+ open_opts = block_crypto_open_opts_init(cryptoopts, errp);
171
if (!open_opts) {
172
goto cleanup;
173
}
174
@@ -XXX,XX +XXX,XX @@ static int coroutine_fn block_crypto_co_create_opts_luks(const char *filename,
175
&block_crypto_create_opts_luks,
176
true);
177
178
- create_opts = block_crypto_create_opts_init(Q_CRYPTO_BLOCK_FORMAT_LUKS,
179
- cryptoopts, errp);
180
+ qdict_put_str(cryptoopts, "format", "luks");
181
+ create_opts = block_crypto_create_opts_init(cryptoopts, errp);
182
if (!create_opts) {
183
ret = -EINVAL;
184
goto fail;
185
diff --git a/block/qcow.c b/block/qcow.c
186
index XXXXXXX..XXXXXXX 100644
187
--- a/block/qcow.c
188
+++ b/block/qcow.c
189
@@ -XXX,XX +XXX,XX @@ static int qcow_open(BlockDriverState *bs, QDict *options, int flags,
190
ret = -EINVAL;
191
goto fail;
192
}
193
- qdict_del(encryptopts, "format");
194
- crypto_opts = block_crypto_open_opts_init(
195
- Q_CRYPTO_BLOCK_FORMAT_QCOW, encryptopts, errp);
196
+ qdict_put_str(encryptopts, "format", "qcow");
197
+ crypto_opts = block_crypto_open_opts_init(encryptopts, errp);
198
if (!crypto_opts) {
199
ret = -EINVAL;
200
goto fail;
201
diff --git a/block/qcow2.c b/block/qcow2.c
202
index XXXXXXX..XXXXXXX 100644
203
--- a/block/qcow2.c
204
+++ b/block/qcow2.c
205
@@ -XXX,XX +XXX,XX @@ static int qcow2_update_options_prepare(BlockDriverState *bs,
206
ret = -EINVAL;
207
goto fail;
208
}
209
- qdict_del(encryptopts, "format");
210
- r->crypto_opts = block_crypto_open_opts_init(
211
- Q_CRYPTO_BLOCK_FORMAT_QCOW, encryptopts, errp);
212
+ qdict_put_str(encryptopts, "format", "qcow");
213
+ r->crypto_opts = block_crypto_open_opts_init(encryptopts, errp);
214
break;
215
216
case QCOW_CRYPT_LUKS:
217
@@ -XXX,XX +XXX,XX @@ static int qcow2_update_options_prepare(BlockDriverState *bs,
218
ret = -EINVAL;
219
goto fail;
220
}
221
- qdict_del(encryptopts, "format");
222
- r->crypto_opts = block_crypto_open_opts_init(
223
- Q_CRYPTO_BLOCK_FORMAT_LUKS, encryptopts, errp);
224
+ qdict_put_str(encryptopts, "format", "luks");
225
+ r->crypto_opts = block_crypto_open_opts_init(encryptopts, errp);
226
break;
227
228
default:
229
--
63
--
230
2.13.6
64
2.19.1
231
65
232
66
diff view generated by jsdifflib
1
From: Eric Blake <eblake@redhat.com>
1
From: Cleber Rosa <crosa@redhat.com>
2
2
3
We are gradually moving away from sector-based interfaces, towards
3
While testing the Python 3 changes which touch the 083 test, I noticed
4
byte-based. Make the change for the internals of the qcow
4
that it would fail with qcow2. Expanding the testing, I noticed it
5
driver write function, by iterating over offset/bytes instead of
5
had nothing to do with the Python 3 changes, and in fact, it would not
6
sector_num/nb_sectors, and with a rename of index_in_cluster and
6
pass on anything but raw:
7
repurposing of n to track bytes instead of sectors.
8
7
9
A later patch will then switch the qcow driver as a whole over
8
raw: pass
10
to byte-based operation.
9
bochs: not generic
10
cloop: not generic
11
parallels: fail
12
qcow: fail
13
qcow2: fail
14
qed: fail
15
vdi: fail
16
vhdx: fail
17
vmdk: fail
18
vpc: fail
19
luks: fail
11
20
12
Signed-off-by: Eric Blake <eblake@redhat.com>
21
The errors are a mixture I/O and "image not in xxx format", such as:
13
Reviewed-by: Jeff Cody <jcody@redhat.com>
22
23
=== Check disconnect before data ===
24
25
Unexpected end-of-file before all bytes were read
26
-read failed: Input/output error
27
+can't open device nbd+tcp://127.0.0.1:PORT/foo: Could not open 'nbd://127.0.0.1:PORT/foo': Input/output error
28
29
=== Check disconnect after data ===
30
31
-read 512/512 bytes at offset 0
32
-512 bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
33
+can't open device nbd+tcp://127.0.0.1:PORT/foo: Image not in qcow format
34
35
I'm not aware if there's a quick fix, so, for the time being, it looks
36
like the honest approach is to make the test known to work on raw
37
only.
38
39
Signed-off-by: Cleber Rosa <crosa@redhat.com>
14
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
40
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
15
---
41
---
16
block/qcow.c | 36 +++++++++++++++++-------------------
42
tests/qemu-iotests/083 | 2 +-
17
1 file changed, 17 insertions(+), 19 deletions(-)
43
1 file changed, 1 insertion(+), 1 deletion(-)
18
44
19
diff --git a/block/qcow.c b/block/qcow.c
45
diff --git a/tests/qemu-iotests/083 b/tests/qemu-iotests/083
20
index XXXXXXX..XXXXXXX 100644
46
index XXXXXXX..XXXXXXX 100755
21
--- a/block/qcow.c
47
--- a/tests/qemu-iotests/083
22
+++ b/block/qcow.c
48
+++ b/tests/qemu-iotests/083
23
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int qcow_co_writev(BlockDriverState *bs, int64_t sector_num,
49
@@ -XXX,XX +XXX,XX @@ trap "_cleanup; exit \$status" 0 1 2 3 15
24
int flags)
50
. ./common.rc
25
{
51
. ./common.filter
26
BDRVQcowState *s = bs->opaque;
52
27
- int index_in_cluster;
53
-_supported_fmt generic
28
+ int offset_in_cluster;
54
+_supported_fmt raw
29
uint64_t cluster_offset;
55
_supported_proto nbd
30
int ret = 0, n;
56
_supported_os Linux
31
struct iovec hd_iov;
32
QEMUIOVector hd_qiov;
33
uint8_t *buf;
34
void *orig_buf;
35
+ int64_t offset = sector_num * BDRV_SECTOR_SIZE;
36
+ int64_t bytes = nb_sectors * BDRV_SECTOR_SIZE;
37
38
assert(!flags);
39
s->cluster_cache_offset = -1; /* disable compressed cache */
40
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int qcow_co_writev(BlockDriverState *bs, int64_t sector_num,
41
42
qemu_co_mutex_lock(&s->lock);
43
44
- while (nb_sectors != 0) {
45
-
46
- index_in_cluster = sector_num & (s->cluster_sectors - 1);
47
- n = s->cluster_sectors - index_in_cluster;
48
- if (n > nb_sectors) {
49
- n = nb_sectors;
50
+ while (bytes != 0) {
51
+ offset_in_cluster = offset & (s->cluster_size - 1);
52
+ n = s->cluster_size - offset_in_cluster;
53
+ if (n > bytes) {
54
+ n = bytes;
55
}
56
- ret = get_cluster_offset(bs, sector_num << 9, 1, 0,
57
- index_in_cluster << 9,
58
- (index_in_cluster + n) << 9, &cluster_offset);
59
+ ret = get_cluster_offset(bs, offset, 1, 0, offset_in_cluster,
60
+ offset_in_cluster + n, &cluster_offset);
61
if (ret < 0) {
62
break;
63
}
64
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int qcow_co_writev(BlockDriverState *bs, int64_t sector_num,
65
}
66
if (bs->encrypted) {
67
assert(s->crypto);
68
- if (qcrypto_block_encrypt(s->crypto, sector_num * BDRV_SECTOR_SIZE,
69
- buf, n * BDRV_SECTOR_SIZE, NULL) < 0) {
70
+ if (qcrypto_block_encrypt(s->crypto, offset, buf, n, NULL) < 0) {
71
ret = -EIO;
72
break;
73
}
74
}
75
76
hd_iov.iov_base = (void *)buf;
77
- hd_iov.iov_len = n * 512;
78
+ hd_iov.iov_len = n;
79
qemu_iovec_init_external(&hd_qiov, &hd_iov, 1);
80
qemu_co_mutex_unlock(&s->lock);
81
BLKDBG_EVENT(bs->file, BLKDBG_WRITE_AIO);
82
- ret = bdrv_co_writev(bs->file,
83
- (cluster_offset >> 9) + index_in_cluster,
84
- n, &hd_qiov);
85
+ ret = bdrv_co_pwritev(bs->file, cluster_offset + offset_in_cluster,
86
+ n, &hd_qiov, 0);
87
qemu_co_mutex_lock(&s->lock);
88
if (ret < 0) {
89
break;
90
}
91
ret = 0;
92
93
- nb_sectors -= n;
94
- sector_num += n;
95
- buf += n * 512;
96
+ bytes -= n;
97
+ offset += n;
98
+ buf += n;
99
}
100
qemu_co_mutex_unlock(&s->lock);
101
57
102
--
58
--
103
2.13.6
59
2.19.1
104
60
105
61
diff view generated by jsdifflib
New patch
1
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
2
Reviewed-by: Alberto Garcia <berto@igalia.com>
3
---
4
block/vpc.c | 2 ++
5
1 file changed, 2 insertions(+)
1
6
7
diff --git a/block/vpc.c b/block/vpc.c
8
index XXXXXXX..XXXXXXX 100644
9
--- a/block/vpc.c
10
+++ b/block/vpc.c
11
@@ -XXX,XX +XXX,XX @@ static int vpc_open(BlockDriverState *bs, QDict *options, int flags,
12
}
13
14
qemu_co_mutex_init(&s->lock);
15
+ qemu_opts_del(opts);
16
17
return 0;
18
19
fail:
20
+ qemu_opts_del(opts);
21
qemu_vfree(s->pagetable);
22
#ifdef CACHE
23
g_free(s->pageentry_u8);
24
--
25
2.19.1
26
27
diff view generated by jsdifflib
1
From: Eric Blake <eblake@redhat.com>
1
From: Peter Maydell <peter.maydell@linaro.org>
2
2
3
We are gradually moving away from sector-based interfaces, towards
3
Taking the address of a field in a packed struct is a bad idea, because
4
byte-based. Make the change for the last few sector-based calls
4
it might not be actually aligned enough for that pointer type (and
5
into the block layer from the vhdx driver.
5
thus cause a crash on dereference on some host architectures). Newer
6
6
versions of clang warn about this. Avoid the bug by not using the
7
Ideally, the vhdx driver should switch to doing everything
7
"modify in place" byte swapping functions.
8
byte-based, but that's a more invasive change that requires a
8
9
bit more auditing.
9
There are a few places where the in-place swap function is
10
10
used on something other than a packed struct field; we convert
11
Signed-off-by: Eric Blake <eblake@redhat.com>
11
those anyway, for consistency.
12
Reviewed-by: Jeff Cody <jcody@redhat.com>
12
13
Patch produced with scripts/coccinelle/inplace-byteswaps.cocci.
14
15
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
16
Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
13
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
17
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
14
---
18
---
15
block/vhdx.c | 12 ++++++------
19
block/vhdx.h | 12 ++---
16
1 file changed, 6 insertions(+), 6 deletions(-)
20
block/vhdx-endian.c | 118 ++++++++++++++++++++++----------------------
17
21
block/vhdx-log.c | 4 +-
22
block/vhdx.c | 18 +++----
23
4 files changed, 76 insertions(+), 76 deletions(-)
24
25
diff --git a/block/vhdx.h b/block/vhdx.h
26
index XXXXXXX..XXXXXXX 100644
27
--- a/block/vhdx.h
28
+++ b/block/vhdx.h
29
@@ -XXX,XX +XXX,XX @@ int vhdx_log_write_and_flush(BlockDriverState *bs, BDRVVHDXState *s,
30
31
static inline void leguid_to_cpus(MSGUID *guid)
32
{
33
- le32_to_cpus(&guid->data1);
34
- le16_to_cpus(&guid->data2);
35
- le16_to_cpus(&guid->data3);
36
+ guid->data1 = le32_to_cpu(guid->data1);
37
+ guid->data2 = le16_to_cpu(guid->data2);
38
+ guid->data3 = le16_to_cpu(guid->data3);
39
}
40
41
static inline void cpu_to_leguids(MSGUID *guid)
42
{
43
- cpu_to_le32s(&guid->data1);
44
- cpu_to_le16s(&guid->data2);
45
- cpu_to_le16s(&guid->data3);
46
+ guid->data1 = cpu_to_le32(guid->data1);
47
+ guid->data2 = cpu_to_le16(guid->data2);
48
+ guid->data3 = cpu_to_le16(guid->data3);
49
}
50
51
void vhdx_header_le_import(VHDXHeader *h);
52
diff --git a/block/vhdx-endian.c b/block/vhdx-endian.c
53
index XXXXXXX..XXXXXXX 100644
54
--- a/block/vhdx-endian.c
55
+++ b/block/vhdx-endian.c
56
@@ -XXX,XX +XXX,XX @@ void vhdx_header_le_import(VHDXHeader *h)
57
{
58
assert(h != NULL);
59
60
- le32_to_cpus(&h->signature);
61
- le32_to_cpus(&h->checksum);
62
- le64_to_cpus(&h->sequence_number);
63
+ h->signature = le32_to_cpu(h->signature);
64
+ h->checksum = le32_to_cpu(h->checksum);
65
+ h->sequence_number = le64_to_cpu(h->sequence_number);
66
67
leguid_to_cpus(&h->file_write_guid);
68
leguid_to_cpus(&h->data_write_guid);
69
leguid_to_cpus(&h->log_guid);
70
71
- le16_to_cpus(&h->log_version);
72
- le16_to_cpus(&h->version);
73
- le32_to_cpus(&h->log_length);
74
- le64_to_cpus(&h->log_offset);
75
+ h->log_version = le16_to_cpu(h->log_version);
76
+ h->version = le16_to_cpu(h->version);
77
+ h->log_length = le32_to_cpu(h->log_length);
78
+ h->log_offset = le64_to_cpu(h->log_offset);
79
}
80
81
void vhdx_header_le_export(VHDXHeader *orig_h, VHDXHeader *new_h)
82
@@ -XXX,XX +XXX,XX @@ void vhdx_log_desc_le_import(VHDXLogDescriptor *d)
83
{
84
assert(d != NULL);
85
86
- le32_to_cpus(&d->signature);
87
- le64_to_cpus(&d->file_offset);
88
- le64_to_cpus(&d->sequence_number);
89
+ d->signature = le32_to_cpu(d->signature);
90
+ d->file_offset = le64_to_cpu(d->file_offset);
91
+ d->sequence_number = le64_to_cpu(d->sequence_number);
92
}
93
94
void vhdx_log_desc_le_export(VHDXLogDescriptor *d)
95
{
96
assert(d != NULL);
97
98
- cpu_to_le32s(&d->signature);
99
- cpu_to_le32s(&d->trailing_bytes);
100
- cpu_to_le64s(&d->leading_bytes);
101
- cpu_to_le64s(&d->file_offset);
102
- cpu_to_le64s(&d->sequence_number);
103
+ d->signature = cpu_to_le32(d->signature);
104
+ d->trailing_bytes = cpu_to_le32(d->trailing_bytes);
105
+ d->leading_bytes = cpu_to_le64(d->leading_bytes);
106
+ d->file_offset = cpu_to_le64(d->file_offset);
107
+ d->sequence_number = cpu_to_le64(d->sequence_number);
108
}
109
110
void vhdx_log_data_le_import(VHDXLogDataSector *d)
111
{
112
assert(d != NULL);
113
114
- le32_to_cpus(&d->data_signature);
115
- le32_to_cpus(&d->sequence_high);
116
- le32_to_cpus(&d->sequence_low);
117
+ d->data_signature = le32_to_cpu(d->data_signature);
118
+ d->sequence_high = le32_to_cpu(d->sequence_high);
119
+ d->sequence_low = le32_to_cpu(d->sequence_low);
120
}
121
122
void vhdx_log_data_le_export(VHDXLogDataSector *d)
123
{
124
assert(d != NULL);
125
126
- cpu_to_le32s(&d->data_signature);
127
- cpu_to_le32s(&d->sequence_high);
128
- cpu_to_le32s(&d->sequence_low);
129
+ d->data_signature = cpu_to_le32(d->data_signature);
130
+ d->sequence_high = cpu_to_le32(d->sequence_high);
131
+ d->sequence_low = cpu_to_le32(d->sequence_low);
132
}
133
134
void vhdx_log_entry_hdr_le_import(VHDXLogEntryHeader *hdr)
135
{
136
assert(hdr != NULL);
137
138
- le32_to_cpus(&hdr->signature);
139
- le32_to_cpus(&hdr->checksum);
140
- le32_to_cpus(&hdr->entry_length);
141
- le32_to_cpus(&hdr->tail);
142
- le64_to_cpus(&hdr->sequence_number);
143
- le32_to_cpus(&hdr->descriptor_count);
144
+ hdr->signature = le32_to_cpu(hdr->signature);
145
+ hdr->checksum = le32_to_cpu(hdr->checksum);
146
+ hdr->entry_length = le32_to_cpu(hdr->entry_length);
147
+ hdr->tail = le32_to_cpu(hdr->tail);
148
+ hdr->sequence_number = le64_to_cpu(hdr->sequence_number);
149
+ hdr->descriptor_count = le32_to_cpu(hdr->descriptor_count);
150
leguid_to_cpus(&hdr->log_guid);
151
- le64_to_cpus(&hdr->flushed_file_offset);
152
- le64_to_cpus(&hdr->last_file_offset);
153
+ hdr->flushed_file_offset = le64_to_cpu(hdr->flushed_file_offset);
154
+ hdr->last_file_offset = le64_to_cpu(hdr->last_file_offset);
155
}
156
157
void vhdx_log_entry_hdr_le_export(VHDXLogEntryHeader *hdr)
158
{
159
assert(hdr != NULL);
160
161
- cpu_to_le32s(&hdr->signature);
162
- cpu_to_le32s(&hdr->checksum);
163
- cpu_to_le32s(&hdr->entry_length);
164
- cpu_to_le32s(&hdr->tail);
165
- cpu_to_le64s(&hdr->sequence_number);
166
- cpu_to_le32s(&hdr->descriptor_count);
167
+ hdr->signature = cpu_to_le32(hdr->signature);
168
+ hdr->checksum = cpu_to_le32(hdr->checksum);
169
+ hdr->entry_length = cpu_to_le32(hdr->entry_length);
170
+ hdr->tail = cpu_to_le32(hdr->tail);
171
+ hdr->sequence_number = cpu_to_le64(hdr->sequence_number);
172
+ hdr->descriptor_count = cpu_to_le32(hdr->descriptor_count);
173
cpu_to_leguids(&hdr->log_guid);
174
- cpu_to_le64s(&hdr->flushed_file_offset);
175
- cpu_to_le64s(&hdr->last_file_offset);
176
+ hdr->flushed_file_offset = cpu_to_le64(hdr->flushed_file_offset);
177
+ hdr->last_file_offset = cpu_to_le64(hdr->last_file_offset);
178
}
179
180
181
@@ -XXX,XX +XXX,XX @@ void vhdx_region_header_le_import(VHDXRegionTableHeader *hdr)
182
{
183
assert(hdr != NULL);
184
185
- le32_to_cpus(&hdr->signature);
186
- le32_to_cpus(&hdr->checksum);
187
- le32_to_cpus(&hdr->entry_count);
188
+ hdr->signature = le32_to_cpu(hdr->signature);
189
+ hdr->checksum = le32_to_cpu(hdr->checksum);
190
+ hdr->entry_count = le32_to_cpu(hdr->entry_count);
191
}
192
193
void vhdx_region_header_le_export(VHDXRegionTableHeader *hdr)
194
{
195
assert(hdr != NULL);
196
197
- cpu_to_le32s(&hdr->signature);
198
- cpu_to_le32s(&hdr->checksum);
199
- cpu_to_le32s(&hdr->entry_count);
200
+ hdr->signature = cpu_to_le32(hdr->signature);
201
+ hdr->checksum = cpu_to_le32(hdr->checksum);
202
+ hdr->entry_count = cpu_to_le32(hdr->entry_count);
203
}
204
205
void vhdx_region_entry_le_import(VHDXRegionTableEntry *e)
206
@@ -XXX,XX +XXX,XX @@ void vhdx_region_entry_le_import(VHDXRegionTableEntry *e)
207
assert(e != NULL);
208
209
leguid_to_cpus(&e->guid);
210
- le64_to_cpus(&e->file_offset);
211
- le32_to_cpus(&e->length);
212
- le32_to_cpus(&e->data_bits);
213
+ e->file_offset = le64_to_cpu(e->file_offset);
214
+ e->length = le32_to_cpu(e->length);
215
+ e->data_bits = le32_to_cpu(e->data_bits);
216
}
217
218
void vhdx_region_entry_le_export(VHDXRegionTableEntry *e)
219
@@ -XXX,XX +XXX,XX @@ void vhdx_region_entry_le_export(VHDXRegionTableEntry *e)
220
assert(e != NULL);
221
222
cpu_to_leguids(&e->guid);
223
- cpu_to_le64s(&e->file_offset);
224
- cpu_to_le32s(&e->length);
225
- cpu_to_le32s(&e->data_bits);
226
+ e->file_offset = cpu_to_le64(e->file_offset);
227
+ e->length = cpu_to_le32(e->length);
228
+ e->data_bits = cpu_to_le32(e->data_bits);
229
}
230
231
232
@@ -XXX,XX +XXX,XX @@ void vhdx_metadata_header_le_import(VHDXMetadataTableHeader *hdr)
233
{
234
assert(hdr != NULL);
235
236
- le64_to_cpus(&hdr->signature);
237
- le16_to_cpus(&hdr->entry_count);
238
+ hdr->signature = le64_to_cpu(hdr->signature);
239
+ hdr->entry_count = le16_to_cpu(hdr->entry_count);
240
}
241
242
void vhdx_metadata_header_le_export(VHDXMetadataTableHeader *hdr)
243
{
244
assert(hdr != NULL);
245
246
- cpu_to_le64s(&hdr->signature);
247
- cpu_to_le16s(&hdr->entry_count);
248
+ hdr->signature = cpu_to_le64(hdr->signature);
249
+ hdr->entry_count = cpu_to_le16(hdr->entry_count);
250
}
251
252
void vhdx_metadata_entry_le_import(VHDXMetadataTableEntry *e)
253
@@ -XXX,XX +XXX,XX @@ void vhdx_metadata_entry_le_import(VHDXMetadataTableEntry *e)
254
assert(e != NULL);
255
256
leguid_to_cpus(&e->item_id);
257
- le32_to_cpus(&e->offset);
258
- le32_to_cpus(&e->length);
259
- le32_to_cpus(&e->data_bits);
260
+ e->offset = le32_to_cpu(e->offset);
261
+ e->length = le32_to_cpu(e->length);
262
+ e->data_bits = le32_to_cpu(e->data_bits);
263
}
264
void vhdx_metadata_entry_le_export(VHDXMetadataTableEntry *e)
265
{
266
assert(e != NULL);
267
268
cpu_to_leguids(&e->item_id);
269
- cpu_to_le32s(&e->offset);
270
- cpu_to_le32s(&e->length);
271
- cpu_to_le32s(&e->data_bits);
272
+ e->offset = cpu_to_le32(e->offset);
273
+ e->length = cpu_to_le32(e->length);
274
+ e->data_bits = cpu_to_le32(e->data_bits);
275
}
276
diff --git a/block/vhdx-log.c b/block/vhdx-log.c
277
index XXXXXXX..XXXXXXX 100644
278
--- a/block/vhdx-log.c
279
+++ b/block/vhdx-log.c
280
@@ -XXX,XX +XXX,XX @@ static void vhdx_log_raw_to_le_sector(VHDXLogDescriptor *desc,
281
/* 8 + 4084 + 4 = 4096, 1 log sector */
282
memcpy(&desc->leading_bytes, data, 8);
283
data += 8;
284
- cpu_to_le64s(&desc->leading_bytes);
285
+ desc->leading_bytes = cpu_to_le64(desc->leading_bytes);
286
memcpy(sector->data, data, 4084);
287
data += 4084;
288
memcpy(&desc->trailing_bytes, data, 4);
289
- cpu_to_le32s(&desc->trailing_bytes);
290
+ desc->trailing_bytes = cpu_to_le32(desc->trailing_bytes);
291
data += 4;
292
293
sector->sequence_high = (uint32_t) (seq >> 32);
18
diff --git a/block/vhdx.c b/block/vhdx.c
294
diff --git a/block/vhdx.c b/block/vhdx.c
19
index XXXXXXX..XXXXXXX 100644
295
index XXXXXXX..XXXXXXX 100644
20
--- a/block/vhdx.c
296
--- a/block/vhdx.c
21
+++ b/block/vhdx.c
297
+++ b/block/vhdx.c
22
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int vhdx_co_readv(BlockDriverState *bs, int64_t sector_num,
298
@@ -XXX,XX +XXX,XX @@ uint32_t vhdx_update_checksum(uint8_t *buf, size_t size, int crc_offset)
23
break;
299
24
case PAYLOAD_BLOCK_FULLY_PRESENT:
300
memset(buf + crc_offset, 0, sizeof(crc));
25
qemu_co_mutex_unlock(&s->lock);
301
crc = crc32c(0xffffffff, buf, size);
26
- ret = bdrv_co_readv(bs->file,
302
- cpu_to_le32s(&crc);
27
- sinfo.file_offset >> BDRV_SECTOR_BITS,
303
+ crc = cpu_to_le32(crc);
28
- sinfo.sectors_avail, &hd_qiov);
304
memcpy(buf + crc_offset, &crc, sizeof(crc));
29
+ ret = bdrv_co_preadv(bs->file, sinfo.file_offset,
305
30
+ sinfo.sectors_avail * BDRV_SECTOR_SIZE,
306
return crc;
31
+ &hd_qiov, 0);
307
@@ -XXX,XX +XXX,XX @@ static int vhdx_parse_metadata(BlockDriverState *bs, BDRVVHDXState *s)
32
qemu_co_mutex_lock(&s->lock);
308
goto exit;
33
if (ret < 0) {
309
}
34
goto exit;
310
35
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int vhdx_co_writev(BlockDriverState *bs, int64_t sector_num,
311
- le32_to_cpus(&s->params.block_size);
36
}
312
- le32_to_cpus(&s->params.data_bits);
37
/* block exists, so we can just overwrite it */
313
+ s->params.block_size = le32_to_cpu(s->params.block_size);
38
qemu_co_mutex_unlock(&s->lock);
314
+ s->params.data_bits = le32_to_cpu(s->params.data_bits);
39
- ret = bdrv_co_writev(bs->file,
315
40
- sinfo.file_offset >> BDRV_SECTOR_BITS,
316
41
- sectors_to_write, &hd_qiov);
317
/* We now have the file parameters, so we can tell if this is a
42
+ ret = bdrv_co_pwritev(bs->file, sinfo.file_offset,
318
@@ -XXX,XX +XXX,XX @@ static int vhdx_parse_metadata(BlockDriverState *bs, BDRVVHDXState *s)
43
+ sectors_to_write * BDRV_SECTOR_SIZE,
319
goto exit;
44
+ &hd_qiov, 0);
320
}
45
qemu_co_mutex_lock(&s->lock);
321
46
if (ret < 0) {
322
- le64_to_cpus(&s->virtual_disk_size);
47
goto error_bat_restore;
323
- le32_to_cpus(&s->logical_sector_size);
324
- le32_to_cpus(&s->physical_sector_size);
325
+ s->virtual_disk_size = le64_to_cpu(s->virtual_disk_size);
326
+ s->logical_sector_size = le32_to_cpu(s->logical_sector_size);
327
+ s->physical_sector_size = le32_to_cpu(s->physical_sector_size);
328
329
if (s->params.block_size < VHDX_BLOCK_SIZE_MIN ||
330
s->params.block_size > VHDX_BLOCK_SIZE_MAX) {
331
@@ -XXX,XX +XXX,XX @@ static int vhdx_open(BlockDriverState *bs, QDict *options, int flags,
332
/* endian convert, and verify populated BAT field file offsets against
333
* region table and log entries */
334
for (i = 0; i < s->bat_entries; i++) {
335
- le64_to_cpus(&s->bat[i]);
336
+ s->bat[i] = le64_to_cpu(s->bat[i]);
337
if (payblocks--) {
338
/* payload bat entries */
339
if ((s->bat[i] & VHDX_BAT_STATE_BIT_MASK) ==
340
@@ -XXX,XX +XXX,XX @@ static int vhdx_create_new_metadata(BlockBackend *blk,
341
mt_file_params->block_size = cpu_to_le32(block_size);
342
if (type == VHDX_TYPE_FIXED) {
343
mt_file_params->data_bits |= VHDX_PARAMS_LEAVE_BLOCKS_ALLOCED;
344
- cpu_to_le32s(&mt_file_params->data_bits);
345
+ mt_file_params->data_bits = cpu_to_le32(mt_file_params->data_bits);
346
}
347
348
vhdx_guid_generate(&mt_page83->page_83_data);
349
@@ -XXX,XX +XXX,XX @@ static int vhdx_create_bat(BlockBackend *blk, BDRVVHDXState *s,
350
sinfo.file_offset = ROUND_UP(sinfo.file_offset, MiB);
351
vhdx_update_bat_table_entry(blk_bs(blk), s, &sinfo, &unused, &unused,
352
block_state);
353
- cpu_to_le64s(&s->bat[sinfo.bat_idx]);
354
+ s->bat[sinfo.bat_idx] = cpu_to_le64(s->bat[sinfo.bat_idx]);
355
sector_num += s->sectors_per_block;
356
}
357
ret = blk_pwrite(blk, file_offset, s->bat, length, 0);
48
--
358
--
49
2.13.6
359
2.19.1
50
360
51
361
diff view generated by jsdifflib
New patch
1
From: Peter Maydell <peter.maydell@linaro.org>
1
2
3
Taking the address of a field in a packed struct is a bad idea, because
4
it might not be actually aligned enough for that pointer type (and
5
thus cause a crash on dereference on some host architectures). Newer
6
versions of clang warn about this. Avoid the bug by not using the
7
"modify in place" byte swapping functions.
8
9
There are a few places where the in-place swap function is
10
used on something other than a packed struct field; we convert
11
those anyway, for consistency.
12
13
Patch produced with scripts/coccinelle/inplace-byteswaps.cocci.
14
15
There are other places where we take the address of a packed member
16
in this file for other purposes than passing it to a byteswap
17
function (all the calls to qemu_uuid_*()); we leave those for now.
18
19
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
20
Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
21
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
22
---
23
block/vdi.c | 64 ++++++++++++++++++++++++++---------------------------
24
1 file changed, 32 insertions(+), 32 deletions(-)
25
26
diff --git a/block/vdi.c b/block/vdi.c
27
index XXXXXXX..XXXXXXX 100644
28
--- a/block/vdi.c
29
+++ b/block/vdi.c
30
@@ -XXX,XX +XXX,XX @@ typedef struct {
31
32
static void vdi_header_to_cpu(VdiHeader *header)
33
{
34
- le32_to_cpus(&header->signature);
35
- le32_to_cpus(&header->version);
36
- le32_to_cpus(&header->header_size);
37
- le32_to_cpus(&header->image_type);
38
- le32_to_cpus(&header->image_flags);
39
- le32_to_cpus(&header->offset_bmap);
40
- le32_to_cpus(&header->offset_data);
41
- le32_to_cpus(&header->cylinders);
42
- le32_to_cpus(&header->heads);
43
- le32_to_cpus(&header->sectors);
44
- le32_to_cpus(&header->sector_size);
45
- le64_to_cpus(&header->disk_size);
46
- le32_to_cpus(&header->block_size);
47
- le32_to_cpus(&header->block_extra);
48
- le32_to_cpus(&header->blocks_in_image);
49
- le32_to_cpus(&header->blocks_allocated);
50
+ header->signature = le32_to_cpu(header->signature);
51
+ header->version = le32_to_cpu(header->version);
52
+ header->header_size = le32_to_cpu(header->header_size);
53
+ header->image_type = le32_to_cpu(header->image_type);
54
+ header->image_flags = le32_to_cpu(header->image_flags);
55
+ header->offset_bmap = le32_to_cpu(header->offset_bmap);
56
+ header->offset_data = le32_to_cpu(header->offset_data);
57
+ header->cylinders = le32_to_cpu(header->cylinders);
58
+ header->heads = le32_to_cpu(header->heads);
59
+ header->sectors = le32_to_cpu(header->sectors);
60
+ header->sector_size = le32_to_cpu(header->sector_size);
61
+ header->disk_size = le64_to_cpu(header->disk_size);
62
+ header->block_size = le32_to_cpu(header->block_size);
63
+ header->block_extra = le32_to_cpu(header->block_extra);
64
+ header->blocks_in_image = le32_to_cpu(header->blocks_in_image);
65
+ header->blocks_allocated = le32_to_cpu(header->blocks_allocated);
66
qemu_uuid_bswap(&header->uuid_image);
67
qemu_uuid_bswap(&header->uuid_last_snap);
68
qemu_uuid_bswap(&header->uuid_link);
69
@@ -XXX,XX +XXX,XX @@ static void vdi_header_to_cpu(VdiHeader *header)
70
71
static void vdi_header_to_le(VdiHeader *header)
72
{
73
- cpu_to_le32s(&header->signature);
74
- cpu_to_le32s(&header->version);
75
- cpu_to_le32s(&header->header_size);
76
- cpu_to_le32s(&header->image_type);
77
- cpu_to_le32s(&header->image_flags);
78
- cpu_to_le32s(&header->offset_bmap);
79
- cpu_to_le32s(&header->offset_data);
80
- cpu_to_le32s(&header->cylinders);
81
- cpu_to_le32s(&header->heads);
82
- cpu_to_le32s(&header->sectors);
83
- cpu_to_le32s(&header->sector_size);
84
- cpu_to_le64s(&header->disk_size);
85
- cpu_to_le32s(&header->block_size);
86
- cpu_to_le32s(&header->block_extra);
87
- cpu_to_le32s(&header->blocks_in_image);
88
- cpu_to_le32s(&header->blocks_allocated);
89
+ header->signature = cpu_to_le32(header->signature);
90
+ header->version = cpu_to_le32(header->version);
91
+ header->header_size = cpu_to_le32(header->header_size);
92
+ header->image_type = cpu_to_le32(header->image_type);
93
+ header->image_flags = cpu_to_le32(header->image_flags);
94
+ header->offset_bmap = cpu_to_le32(header->offset_bmap);
95
+ header->offset_data = cpu_to_le32(header->offset_data);
96
+ header->cylinders = cpu_to_le32(header->cylinders);
97
+ header->heads = cpu_to_le32(header->heads);
98
+ header->sectors = cpu_to_le32(header->sectors);
99
+ header->sector_size = cpu_to_le32(header->sector_size);
100
+ header->disk_size = cpu_to_le64(header->disk_size);
101
+ header->block_size = cpu_to_le32(header->block_size);
102
+ header->block_extra = cpu_to_le32(header->block_extra);
103
+ header->blocks_in_image = cpu_to_le32(header->blocks_in_image);
104
+ header->blocks_allocated = cpu_to_le32(header->blocks_allocated);
105
qemu_uuid_bswap(&header->uuid_image);
106
qemu_uuid_bswap(&header->uuid_last_snap);
107
qemu_uuid_bswap(&header->uuid_link);
108
--
109
2.19.1
110
111
diff view generated by jsdifflib
1
From: Eric Blake <eblake@redhat.com>
1
From: Alberto Garcia <berto@igalia.com>
2
2
3
We are gradually moving away from sector-based interfaces, towards
3
This is a static function with only one caller, so there's no need to
4
byte-based. Now that all callers of vectored I/O have been converted
4
keep it. Inlining the code in quorum_compare() makes it much simpler.
5
to use our preferred byte-based bdrv_co_p{read,write}v(), we can
6
delete the unused bdrv_co_{read,write}v().
7
5
8
Furthermore, this gets rid of the signature difference between the
6
Signed-off-by: Alberto Garcia <berto@igalia.com>
9
public bdrv_co_writev() and the callback .bdrv_co_writev (the
7
Reported-by: Markus Armbruster <armbru@redhat.com>
10
latter still exists, because some drivers still need more work
11
before they are fully byte-based).
12
13
Signed-off-by: Eric Blake <eblake@redhat.com>
14
Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
15
Reviewed-by: Jeff Cody <jcody@redhat.com>
16
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
8
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
17
---
9
---
18
include/block/block.h | 4 ----
10
block/quorum.c | 24 +++++-------------------
19
block/io.c | 36 ------------------------------------
11
1 file changed, 5 insertions(+), 19 deletions(-)
20
2 files changed, 40 deletions(-)
21
12
22
diff --git a/include/block/block.h b/include/block/block.h
13
diff --git a/block/quorum.c b/block/quorum.c
23
index XXXXXXX..XXXXXXX 100644
14
index XXXXXXX..XXXXXXX 100644
24
--- a/include/block/block.h
15
--- a/block/quorum.c
25
+++ b/include/block/block.h
16
+++ b/block/quorum.c
26
@@ -XXX,XX +XXX,XX @@ int bdrv_pwrite(BdrvChild *child, int64_t offset, const void *buf, int bytes);
17
@@ -XXX,XX +XXX,XX @@ static bool quorum_iovec_compare(QEMUIOVector *a, QEMUIOVector *b)
27
int bdrv_pwritev(BdrvChild *child, int64_t offset, QEMUIOVector *qiov);
18
return true;
28
int bdrv_pwrite_sync(BdrvChild *child, int64_t offset,
29
const void *buf, int count);
30
-int coroutine_fn bdrv_co_readv(BdrvChild *child, int64_t sector_num,
31
- int nb_sectors, QEMUIOVector *qiov);
32
-int coroutine_fn bdrv_co_writev(BdrvChild *child, int64_t sector_num,
33
- int nb_sectors, QEMUIOVector *qiov);
34
/*
35
* Efficiently zero a region of the disk image. Note that this is a regular
36
* I/O request like read or write and should have a reasonable size. This
37
diff --git a/block/io.c b/block/io.c
38
index XXXXXXX..XXXXXXX 100644
39
--- a/block/io.c
40
+++ b/block/io.c
41
@@ -XXX,XX +XXX,XX @@ int coroutine_fn bdrv_co_preadv(BdrvChild *child,
42
return ret;
43
}
19
}
44
20
45
-static int coroutine_fn bdrv_co_do_readv(BdrvChild *child,
21
-static void GCC_FMT_ATTR(2, 3) quorum_err(QuorumAIOCB *acb,
46
- int64_t sector_num, int nb_sectors, QEMUIOVector *qiov,
22
- const char *fmt, ...)
47
- BdrvRequestFlags flags)
48
-{
23
-{
49
- if (nb_sectors < 0 || nb_sectors > BDRV_REQUEST_MAX_SECTORS) {
24
- va_list ap;
50
- return -EINVAL;
51
- }
52
-
25
-
53
- return bdrv_co_preadv(child, sector_num << BDRV_SECTOR_BITS,
26
- va_start(ap, fmt);
54
- nb_sectors << BDRV_SECTOR_BITS, qiov, flags);
27
- fprintf(stderr, "quorum: offset=%" PRIu64 " bytes=%" PRIu64 " ",
28
- acb->offset, acb->bytes);
29
- vfprintf(stderr, fmt, ap);
30
- fprintf(stderr, "\n");
31
- va_end(ap);
32
- exit(1);
55
-}
33
-}
56
-
34
-
57
-int coroutine_fn bdrv_co_readv(BdrvChild *child, int64_t sector_num,
35
-static bool quorum_compare(QuorumAIOCB *acb,
58
- int nb_sectors, QEMUIOVector *qiov)
36
- QEMUIOVector *a,
59
-{
37
- QEMUIOVector *b)
60
- return bdrv_co_do_readv(child, sector_num, nb_sectors, qiov, 0);
38
+static bool quorum_compare(QuorumAIOCB *acb, QEMUIOVector *a, QEMUIOVector *b)
61
-}
62
-
63
static int coroutine_fn bdrv_co_do_pwrite_zeroes(BlockDriverState *bs,
64
int64_t offset, int bytes, BdrvRequestFlags flags)
65
{
39
{
66
@@ -XXX,XX +XXX,XX @@ out:
40
BDRVQuorumState *s = acb->bs->opaque;
67
return ret;
41
ssize_t offset;
68
}
42
@@ -XXX,XX +XXX,XX @@ static bool quorum_compare(QuorumAIOCB *acb,
69
43
if (s->is_blkverify) {
70
-static int coroutine_fn bdrv_co_do_writev(BdrvChild *child,
44
offset = qemu_iovec_compare(a, b);
71
- int64_t sector_num, int nb_sectors, QEMUIOVector *qiov,
45
if (offset != -1) {
72
- BdrvRequestFlags flags)
46
- quorum_err(acb, "contents mismatch at offset %" PRIu64,
73
-{
47
- acb->offset + offset);
74
- if (nb_sectors < 0 || nb_sectors > BDRV_REQUEST_MAX_SECTORS) {
48
+ fprintf(stderr, "quorum: offset=%" PRIu64 " bytes=%" PRIu64
75
- return -EINVAL;
49
+ " contents mismatch at offset %" PRIu64 "\n",
76
- }
50
+ acb->offset, acb->bytes, acb->offset + offset);
77
-
51
+ exit(1);
78
- return bdrv_co_pwritev(child, sector_num << BDRV_SECTOR_BITS,
52
}
79
- nb_sectors << BDRV_SECTOR_BITS, qiov, flags);
53
return true;
80
-}
54
}
81
-
82
-int coroutine_fn bdrv_co_writev(BdrvChild *child, int64_t sector_num,
83
- int nb_sectors, QEMUIOVector *qiov)
84
-{
85
- return bdrv_co_do_writev(child, sector_num, nb_sectors, qiov, 0);
86
-}
87
-
88
int coroutine_fn bdrv_co_pwrite_zeroes(BdrvChild *child, int64_t offset,
89
int bytes, BdrvRequestFlags flags)
90
{
91
--
55
--
92
2.13.6
56
2.19.1
93
57
94
58
diff view generated by jsdifflib
1
From: Eric Blake <eblake@redhat.com>
1
From: Alberto Garcia <berto@igalia.com>
2
2
3
We are gradually moving away from sector-based interfaces, towards
3
The blkverify mode of Quorum can only be enabled if the number of
4
byte-based. Make the change for the last few sector-based calls
4
children is exactly two and the value of vote-threshold is also two.
5
into the block layer from the parallels driver.
6
5
7
Ideally, the parallels driver should switch to doing everything
6
If the user tries to enable it but the other settings are incorrect
8
byte-based, but that's a more invasive change that requires a
7
then QEMU simply prints an error message to stderr and carries on
9
bit more auditing.
8
disabling the blkverify setting.
10
9
11
Signed-off-by: Eric Blake <eblake@redhat.com>
10
This patch makes quorum_open() fail and return an error in this case.
12
Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
11
13
Reviewed-by: Denis V. Lunev <den@openvz.org>
12
Signed-off-by: Alberto Garcia <berto@igalia.com>
14
Reviewed-by: Jeff Cody <jcody@redhat.com>
13
Reported-by: Markus Armbruster <armbru@redhat.com>
15
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
14
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
16
---
15
---
17
block/parallels.c | 16 ++++++++++------
16
block/quorum.c | 13 ++++++-------
18
1 file changed, 10 insertions(+), 6 deletions(-)
17
1 file changed, 6 insertions(+), 7 deletions(-)
19
18
20
diff --git a/block/parallels.c b/block/parallels.c
19
diff --git a/block/quorum.c b/block/quorum.c
21
index XXXXXXX..XXXXXXX 100644
20
index XXXXXXX..XXXXXXX 100644
22
--- a/block/parallels.c
21
--- a/block/quorum.c
23
+++ b/block/parallels.c
22
+++ b/block/quorum.c
24
@@ -XXX,XX +XXX,XX @@ static int64_t allocate_clusters(BlockDriverState *bs, int64_t sector_num,
23
@@ -XXX,XX +XXX,XX @@ static int quorum_open(BlockDriverState *bs, QDict *options, int flags,
25
};
24
s->read_pattern = ret;
26
qemu_iovec_init_external(&qiov, &iov, 1);
25
27
26
if (s->read_pattern == QUORUM_READ_PATTERN_QUORUM) {
28
- ret = bdrv_co_readv(bs->backing, idx * s->tracks, nb_cow_sectors,
27
- /* is the driver in blkverify mode */
29
- &qiov);
28
- if (qemu_opt_get_bool(opts, QUORUM_OPT_BLKVERIFY, false) &&
30
+ ret = bdrv_co_preadv(bs->backing, idx * s->tracks * BDRV_SECTOR_SIZE,
29
- s->num_children == 2 && s->threshold == 2) {
31
+ nb_cow_bytes, &qiov, 0);
30
- s->is_blkverify = true;
32
if (ret < 0) {
31
- } else if (qemu_opt_get_bool(opts, QUORUM_OPT_BLKVERIFY, false)) {
33
qemu_vfree(iov.iov_base);
32
- fprintf(stderr, "blkverify mode is set by setting blkverify=on "
34
return ret;
33
- "and using two files with vote_threshold=2\n");
34
+ s->is_blkverify = qemu_opt_get_bool(opts, QUORUM_OPT_BLKVERIFY, false);
35
+ if (s->is_blkverify && (s->num_children != 2 || s->threshold != 2)) {
36
+ error_setg(&local_err, "blkverify=on can only be set if there are "
37
+ "exactly two files and vote-threshold is 2");
38
+ ret = -EINVAL;
39
+ goto exit;
35
}
40
}
36
41
37
- ret = bdrv_co_writev(bs->file, s->data_end, nb_cow_sectors, &qiov);
42
s->rewrite_corrupted = qemu_opt_get_bool(opts, QUORUM_OPT_REWRITE,
38
+ ret = bdrv_co_pwritev(bs->file, s->data_end * BDRV_SECTOR_SIZE,
39
+ nb_cow_bytes, &qiov, 0);
40
qemu_vfree(iov.iov_base);
41
if (ret < 0) {
42
return ret;
43
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int parallels_co_writev(BlockDriverState *bs,
44
qemu_iovec_reset(&hd_qiov);
45
qemu_iovec_concat(&hd_qiov, qiov, bytes_done, nbytes);
46
47
- ret = bdrv_co_writev(bs->file, position, n, &hd_qiov);
48
+ ret = bdrv_co_pwritev(bs->file, position * BDRV_SECTOR_SIZE, nbytes,
49
+ &hd_qiov, 0);
50
if (ret < 0) {
51
break;
52
}
53
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int parallels_co_readv(BlockDriverState *bs,
54
55
if (position < 0) {
56
if (bs->backing) {
57
- ret = bdrv_co_readv(bs->backing, sector_num, n, &hd_qiov);
58
+ ret = bdrv_co_preadv(bs->backing, sector_num * BDRV_SECTOR_SIZE,
59
+ nbytes, &hd_qiov, 0);
60
if (ret < 0) {
61
break;
62
}
63
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int parallels_co_readv(BlockDriverState *bs,
64
qemu_iovec_memset(&hd_qiov, 0, 0, nbytes);
65
}
66
} else {
67
- ret = bdrv_co_readv(bs->file, position, n, &hd_qiov);
68
+ ret = bdrv_co_preadv(bs->file, position * BDRV_SECTOR_SIZE, nbytes,
69
+ &hd_qiov, 0);
70
if (ret < 0) {
71
break;
72
}
73
--
43
--
74
2.13.6
44
2.19.1
75
45
76
46
diff view generated by jsdifflib
1
From: Fam Zheng <famz@redhat.com>
1
From: Alberto Garcia <berto@igalia.com>
2
2
3
Not updating src_offset will result in wrong data being written to dst
3
Signed-off-by: Alberto Garcia <berto@igalia.com>
4
image.
5
6
Reported-by: Max Reitz <mreitz@redhat.com>
7
Signed-off-by: Fam Zheng <famz@redhat.com>
8
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
4
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
9
---
5
---
10
block/qcow2.c | 1 +
6
tests/qemu-iotests/081 | 30 ++++++++++++++++++++++++++++++
11
tests/qemu-iotests/063 | 9 +++++++++
7
tests/qemu-iotests/081.out | 16 ++++++++++++++++
12
tests/qemu-iotests/063.out | 12 ++++++++++++
8
2 files changed, 46 insertions(+)
13
3 files changed, 22 insertions(+)
14
9
15
diff --git a/block/qcow2.c b/block/qcow2.c
10
diff --git a/tests/qemu-iotests/081 b/tests/qemu-iotests/081
16
index XXXXXXX..XXXXXXX 100644
17
--- a/block/qcow2.c
18
+++ b/block/qcow2.c
19
@@ -XXX,XX +XXX,XX @@ qcow2_co_copy_range_to(BlockDriverState *bs,
20
}
21
22
bytes -= cur_bytes;
23
+ src_offset += cur_bytes;
24
dst_offset += cur_bytes;
25
}
26
ret = 0;
27
diff --git a/tests/qemu-iotests/063 b/tests/qemu-iotests/063
28
index XXXXXXX..XXXXXXX 100755
11
index XXXXXXX..XXXXXXX 100755
29
--- a/tests/qemu-iotests/063
12
--- a/tests/qemu-iotests/081
30
+++ b/tests/qemu-iotests/063
13
+++ b/tests/qemu-iotests/081
31
@@ -XXX,XX +XXX,XX @@ if $QEMU_IMG convert -f $IMGFMT -O $IMGFMT -n "$TEST_IMG.orig" "$TEST_IMG" >/dev
14
@@ -XXX,XX +XXX,XX @@ echo "== checking that quorum is broken =="
32
exit 1
15
33
fi
16
$QEMU_IO -c "open -o $quorum" -c "read -P 0x32 0 $size" | _filter_qemu_io
34
17
35
+echo "== Regression testing for copy offloading bug =="
18
+echo
19
+echo "== checking the blkverify mode with broken content =="
36
+
20
+
37
+_make_test_img 1M
21
+quorum="driver=raw,file.driver=quorum,file.vote-threshold=2,file.blkverify=on"
38
+TEST_IMG="$TEST_IMG.target" _make_test_img 1M
22
+quorum="$quorum,file.children.0.file.filename=$TEST_DIR/1.raw"
39
+$QEMU_IO -c 'write -P 1 0 512k' -c 'write -P 2 512k 512k' "$TEST_IMG" | _filter_qemu_io
23
+quorum="$quorum,file.children.1.file.filename=$TEST_DIR/2.raw"
40
+$QEMU_IO -c 'write -P 4 512k 512k' -c 'write -P 3 0 512k' "$TEST_IMG.target" | _filter_qemu_io
24
+quorum="$quorum,file.children.0.driver=raw"
41
+$QEMU_IMG convert -n -O $IMGFMT "$TEST_IMG" "$TEST_IMG.target"
25
+quorum="$quorum,file.children.1.driver=raw"
42
+$QEMU_IMG compare "$TEST_IMG" "$TEST_IMG.target"
43
+
26
+
27
+$QEMU_IO -c "open -o $quorum" -c "read -P 0x32 0 $size" | _filter_qemu_io
28
+
29
+echo
30
+echo "== writing the same data to both files =="
31
+
32
+$QEMU_IO -c "write -P 0x32 0 $size" "$TEST_DIR/1.raw" | _filter_qemu_io
33
+$QEMU_IO -c "write -P 0x32 0 $size" "$TEST_DIR/2.raw" | _filter_qemu_io
34
+
35
+echo
36
+echo "== checking the blkverify mode with valid content =="
37
+
38
+$QEMU_IO -c "open -o $quorum" -c "read -P 0x32 0 $size" | _filter_qemu_io
39
+
40
+echo
41
+echo "== checking the blkverify mode with invalid settings =="
42
+
43
+quorum="$quorum,file.children.2.file.filename=$TEST_DIR/3.raw"
44
+quorum="$quorum,file.children.2.driver=raw"
45
+
46
+$QEMU_IO -c "open -o $quorum" | _filter_qemu_io
47
+
48
# success, all done
44
echo "*** done"
49
echo "*** done"
45
rm -f $seq.full
50
rm -f $seq.full
46
status=0
51
diff --git a/tests/qemu-iotests/081.out b/tests/qemu-iotests/081.out
47
diff --git a/tests/qemu-iotests/063.out b/tests/qemu-iotests/063.out
48
index XXXXXXX..XXXXXXX 100644
52
index XXXXXXX..XXXXXXX 100644
49
--- a/tests/qemu-iotests/063.out
53
--- a/tests/qemu-iotests/081.out
50
+++ b/tests/qemu-iotests/063.out
54
+++ b/tests/qemu-iotests/081.out
51
@@ -XXX,XX +XXX,XX @@ Formatting 'TEST_DIR/t.IMGFMT', fmt=IMGFMT size=4194304
55
@@ -XXX,XX +XXX,XX @@ wrote 10485760/10485760 bytes at offset 0
52
No errors were found on the image.
56
53
== Testing conversion to a smaller file fails ==
57
== checking that quorum is broken ==
54
Formatting 'TEST_DIR/t.IMGFMT', fmt=IMGFMT size=2097152
58
read failed: Input/output error
55
+== Regression testing for copy offloading bug ==
59
+
56
+Formatting 'TEST_DIR/t.IMGFMT', fmt=IMGFMT size=1048576
60
+== checking the blkverify mode with broken content ==
57
+Formatting 'TEST_DIR/t.IMGFMT.target', fmt=IMGFMT size=1048576
61
+quorum: offset=0 bytes=10485760 contents mismatch at offset 0
58
+wrote 524288/524288 bytes at offset 0
62
+
59
+512 KiB, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
63
+== writing the same data to both files ==
60
+wrote 524288/524288 bytes at offset 524288
64
+wrote 10485760/10485760 bytes at offset 0
61
+512 KiB, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
65
+10 MiB, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
62
+wrote 524288/524288 bytes at offset 524288
66
+wrote 10485760/10485760 bytes at offset 0
63
+512 KiB, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
67
+10 MiB, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
64
+wrote 524288/524288 bytes at offset 0
68
+
65
+512 KiB, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
69
+== checking the blkverify mode with valid content ==
66
+Images are identical.
70
+read 10485760/10485760 bytes at offset 0
71
+10 MiB, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
72
+
73
+== checking the blkverify mode with invalid settings ==
74
+can't open: blkverify=on can only be set if there are exactly two files and vote-threshold is 2
67
*** done
75
*** done
68
--
76
--
69
2.13.6
77
2.19.1
70
78
71
79
diff view generated by jsdifflib
1
From: Eric Blake <eblake@redhat.com>
1
From: Alberto Garcia <berto@igalia.com>
2
2
3
We are gradually moving away from sector-based interfaces, towards
3
The blkverify mode of Quorum only works when the number of children is
4
byte-based. Make the change for the internals of the qcow
4
exactly two, so any attempt to add a new one must return an error.
5
driver read function, by iterating over offset/bytes instead of
6
sector_num/nb_sectors, and with a rename of index_in_cluster and
7
repurposing of n to track bytes instead of sectors.
8
5
9
A later patch will then switch the qcow driver as a whole over
6
quorum_del_child() on the other hand doesn't need any additional check
10
to byte-based operation.
7
because decreasing the number of children would make it go under the
8
vote threshold.
11
9
12
Signed-off-by: Eric Blake <eblake@redhat.com>
10
Signed-off-by: Alberto Garcia <berto@igalia.com>
13
Reviewed-by: Jeff Cody <jcody@redhat.com>
11
Reported-by: Kevin Wolf <kwolf@redhat.com>
14
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
12
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
15
---
13
---
16
block/qcow.c | 42 ++++++++++++++++++++----------------------
14
block/quorum.c | 8 ++++++++
17
1 file changed, 20 insertions(+), 22 deletions(-)
15
1 file changed, 8 insertions(+)
18
16
19
diff --git a/block/qcow.c b/block/qcow.c
17
diff --git a/block/quorum.c b/block/quorum.c
20
index XXXXXXX..XXXXXXX 100644
18
index XXXXXXX..XXXXXXX 100644
21
--- a/block/qcow.c
19
--- a/block/quorum.c
22
+++ b/block/qcow.c
20
+++ b/block/quorum.c
23
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int qcow_co_readv(BlockDriverState *bs, int64_t sector_num,
21
@@ -XXX,XX +XXX,XX @@ static void quorum_add_child(BlockDriverState *bs, BlockDriverState *child_bs,
24
int nb_sectors, QEMUIOVector *qiov)
22
char indexstr[32];
25
{
23
int ret;
26
BDRVQcowState *s = bs->opaque;
24
27
- int index_in_cluster;
25
+ if (s->is_blkverify) {
28
+ int offset_in_cluster;
26
+ error_setg(errp, "Cannot add a child to a quorum in blkverify mode");
29
int ret = 0, n;
27
+ return;
30
uint64_t cluster_offset;
28
+ }
31
struct iovec hd_iov;
29
+
32
QEMUIOVector hd_qiov;
30
assert(s->num_children <= INT_MAX / sizeof(BdrvChild *));
33
uint8_t *buf;
31
if (s->num_children == INT_MAX / sizeof(BdrvChild *) ||
34
void *orig_buf;
32
s->next_child_index == UINT_MAX) {
35
+ int64_t offset = sector_num * BDRV_SECTOR_SIZE;
33
@@ -XXX,XX +XXX,XX @@ static void quorum_del_child(BlockDriverState *bs, BdrvChild *child,
36
+ int64_t bytes = nb_sectors * BDRV_SECTOR_SIZE;
34
return;
37
38
if (qiov->niov > 1) {
39
buf = orig_buf = qemu_try_blockalign(bs, qiov->size);
40
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int qcow_co_readv(BlockDriverState *bs, int64_t sector_num,
41
42
qemu_co_mutex_lock(&s->lock);
43
44
- while (nb_sectors != 0) {
45
+ while (bytes != 0) {
46
/* prepare next request */
47
- ret = get_cluster_offset(bs, sector_num << 9,
48
- 0, 0, 0, 0, &cluster_offset);
49
+ ret = get_cluster_offset(bs, offset, 0, 0, 0, 0, &cluster_offset);
50
if (ret < 0) {
51
break;
52
}
53
- index_in_cluster = sector_num & (s->cluster_sectors - 1);
54
- n = s->cluster_sectors - index_in_cluster;
55
- if (n > nb_sectors) {
56
- n = nb_sectors;
57
+ offset_in_cluster = offset & (s->cluster_size - 1);
58
+ n = s->cluster_size - offset_in_cluster;
59
+ if (n > bytes) {
60
+ n = bytes;
61
}
62
63
if (!cluster_offset) {
64
if (bs->backing) {
65
/* read from the base image */
66
hd_iov.iov_base = (void *)buf;
67
- hd_iov.iov_len = n * 512;
68
+ hd_iov.iov_len = n;
69
qemu_iovec_init_external(&hd_qiov, &hd_iov, 1);
70
qemu_co_mutex_unlock(&s->lock);
71
/* qcow2 emits this on bs->file instead of bs->backing */
72
BLKDBG_EVENT(bs->file, BLKDBG_READ_BACKING_AIO);
73
- ret = bdrv_co_readv(bs->backing, sector_num, n, &hd_qiov);
74
+ ret = bdrv_co_preadv(bs->backing, offset, n, &hd_qiov, 0);
75
qemu_co_mutex_lock(&s->lock);
76
if (ret < 0) {
77
break;
78
}
79
} else {
80
/* Note: in this case, no need to wait */
81
- memset(buf, 0, 512 * n);
82
+ memset(buf, 0, n);
83
}
84
} else if (cluster_offset & QCOW_OFLAG_COMPRESSED) {
85
/* add AIO support for compressed blocks ? */
86
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int qcow_co_readv(BlockDriverState *bs, int64_t sector_num,
87
ret = -EIO;
88
break;
89
}
90
- memcpy(buf,
91
- s->cluster_cache + index_in_cluster * 512, 512 * n);
92
+ memcpy(buf, s->cluster_cache + offset_in_cluster, n);
93
} else {
94
if ((cluster_offset & 511) != 0) {
95
ret = -EIO;
96
break;
97
}
98
hd_iov.iov_base = (void *)buf;
99
- hd_iov.iov_len = n * 512;
100
+ hd_iov.iov_len = n;
101
qemu_iovec_init_external(&hd_qiov, &hd_iov, 1);
102
qemu_co_mutex_unlock(&s->lock);
103
BLKDBG_EVENT(bs->file, BLKDBG_READ_AIO);
104
- ret = bdrv_co_readv(bs->file,
105
- (cluster_offset >> 9) + index_in_cluster,
106
- n, &hd_qiov);
107
+ ret = bdrv_co_preadv(bs->file, cluster_offset + offset_in_cluster,
108
+ n, &hd_qiov, 0);
109
qemu_co_mutex_lock(&s->lock);
110
if (ret < 0) {
111
break;
112
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int qcow_co_readv(BlockDriverState *bs, int64_t sector_num,
113
if (bs->encrypted) {
114
assert(s->crypto);
115
if (qcrypto_block_decrypt(s->crypto,
116
- sector_num * BDRV_SECTOR_SIZE, buf,
117
- n * BDRV_SECTOR_SIZE, NULL) < 0) {
118
+ offset, buf, n, NULL) < 0) {
119
ret = -EIO;
120
break;
121
}
122
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int qcow_co_readv(BlockDriverState *bs, int64_t sector_num,
123
}
124
ret = 0;
125
126
- nb_sectors -= n;
127
- sector_num += n;
128
- buf += n * 512;
129
+ bytes -= n;
130
+ offset += n;
131
+ buf += n;
132
}
35
}
133
36
134
qemu_co_mutex_unlock(&s->lock);
37
+ /* We know now that num_children > threshold, so blkverify must be false */
38
+ assert(!s->is_blkverify);
39
+
40
bdrv_drained_begin(bs);
41
42
/* We can safely remove this child now */
135
--
43
--
136
2.13.6
44
2.19.1
137
45
138
46
diff view generated by jsdifflib
1
This adds a test for a temporary write failure, which simulates the
1
From: Alberto Garcia <berto@igalia.com>
2
situation after werror=stop/enospc has stopped the VM. We shouldn't
3
leave leaked clusters behind in such cases.
4
2
3
This patch tests that you can add and remove drives from a Quorum
4
using the x-blockdev-change command.
5
6
Signed-off-by: Alberto Garcia <berto@igalia.com>
5
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
7
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
6
Reviewed-by: Max Reitz <mreitz@redhat.com>
7
---
8
---
8
tests/qemu-iotests/026 | 17 +++++++++++++++++
9
tests/qemu-iotests/081 | 86 ++++++++++++++++++++++++++++++++++++++
9
tests/qemu-iotests/026.out | 8 ++++++++
10
tests/qemu-iotests/081.out | 54 ++++++++++++++++++++++++
10
tests/qemu-iotests/026.out.nocache | 8 ++++++++
11
2 files changed, 140 insertions(+)
11
3 files changed, 33 insertions(+)
12
12
13
diff --git a/tests/qemu-iotests/026 b/tests/qemu-iotests/026
13
diff --git a/tests/qemu-iotests/081 b/tests/qemu-iotests/081
14
index XXXXXXX..XXXXXXX 100755
14
index XXXXXXX..XXXXXXX 100755
15
--- a/tests/qemu-iotests/026
15
--- a/tests/qemu-iotests/081
16
+++ b/tests/qemu-iotests/026
16
+++ b/tests/qemu-iotests/081
17
@@ -XXX,XX +XXX,XX @@ done
17
@@ -XXX,XX +XXX,XX @@ quorum="$quorum,file.children.2.driver=raw"
18
done
18
19
done
19
$QEMU_IO -c "open -o $quorum" | _filter_qemu_io
20
20
21
+echo
21
+echo
22
+echo === Avoid cluster leaks after temporary failure ===
22
+echo "== dynamically adding a child to a quorum =="
23
+
24
+for verify in false true; do
25
+ run_qemu <<EOF
26
+ { "execute": "qmp_capabilities" }
27
+ { "execute": "blockdev-add",
28
+ "arguments": {
29
+ "driver": "quorum",
30
+ "node-name": "drive0-quorum",
31
+ "vote-threshold": 2,
32
+ "blkverify": ${verify},
33
+ "children": [
34
+ {
35
+ "driver": "$IMGFMT",
36
+ "file": {
37
+ "driver": "file",
38
+ "filename": "$TEST_DIR/1.raw"
39
+ }
40
+ },
41
+ {
42
+ "driver": "$IMGFMT",
43
+ "file": {
44
+ "driver": "file",
45
+ "filename": "$TEST_DIR/2.raw"
46
+ }
47
+ }
48
+ ]
49
+ }
50
+ }
51
+ { "execute": "blockdev-add",
52
+ "arguments": {
53
+ "node-name": "drive3",
54
+ "driver": "$IMGFMT",
55
+ "file": {
56
+ "driver": "file",
57
+ "filename": "$TEST_DIR/2.raw"
58
+ }
59
+ }
60
+ }
61
+ { "execute": "x-blockdev-change",
62
+ "arguments": { "parent": "drive0-quorum",
63
+ "node": "drive3" } }
64
+ { "execute": "quit" }
65
+EOF
66
+done
67
+
23
+echo
68
+echo
69
+echo "== dynamically removing a child from a quorum =="
24
+
70
+
25
+cat > "$TEST_DIR/blkdebug.conf" <<EOF
71
+for verify in false true; do
26
+[inject-error]
72
+ for vote_threshold in 1 2; do
27
+event = "write_aio"
73
+ run_qemu <<EOF
28
+errno = "5"
74
+ { "execute": "qmp_capabilities" }
29
+once = "on"
75
+ { "execute": "blockdev-add",
76
+ "arguments": {
77
+ "driver": "quorum",
78
+ "node-name": "drive0-quorum",
79
+ "vote-threshold": ${vote_threshold},
80
+ "blkverify": ${verify},
81
+ "children": [
82
+ {
83
+ "driver": "$IMGFMT",
84
+ "file": {
85
+ "driver": "file",
86
+ "filename": "$TEST_DIR/1.raw"
87
+ }
88
+ },
89
+ {
90
+ "driver": "$IMGFMT",
91
+ "file": {
92
+ "driver": "file",
93
+ "filename": "$TEST_DIR/2.raw"
94
+ }
95
+ }
96
+ ]
97
+ }
98
+ }
99
+ { "execute": "x-blockdev-change",
100
+ "arguments": { "parent": "drive0-quorum",
101
+ "child": "children.1" } }
102
+ { "execute": "quit" }
30
+EOF
103
+EOF
31
+
104
+ done
32
+# After the failed first write, do a second write so that the updated refcount
105
+done
33
+# block is actually written back
34
+_make_test_img 64M
35
+$QEMU_IO -c "write 0 1M" -c "write 0 1M" "$BLKDBG_TEST_IMG" | _filter_qemu_io
36
+_check_test_img
37
+
106
+
38
# success, all done
107
# success, all done
39
echo "*** done"
108
echo "*** done"
40
rm -f $seq.full
109
rm -f $seq.full
41
diff --git a/tests/qemu-iotests/026.out b/tests/qemu-iotests/026.out
110
diff --git a/tests/qemu-iotests/081.out b/tests/qemu-iotests/081.out
42
index XXXXXXX..XXXXXXX 100644
111
index XXXXXXX..XXXXXXX 100644
43
--- a/tests/qemu-iotests/026.out
112
--- a/tests/qemu-iotests/081.out
44
+++ b/tests/qemu-iotests/026.out
113
+++ b/tests/qemu-iotests/081.out
45
@@ -XXX,XX +XXX,XX @@ write failed: No space left on device
114
@@ -XXX,XX +XXX,XX @@ read 10485760/10485760 bytes at offset 0
46
115
47
96 leaked clusters were found on the image.
116
== checking the blkverify mode with invalid settings ==
48
This means waste of disk space, but no harm to data.
117
can't open: blkverify=on can only be set if there are exactly two files and vote-threshold is 2
49
+
118
+
50
+=== Avoid cluster leaks after temporary failure ===
119
+== dynamically adding a child to a quorum ==
120
+Testing:
121
+QMP_VERSION
122
+{"return": {}}
123
+{"return": {}}
124
+{"return": {}}
125
+{"return": {}}
126
+{"return": {}}
127
+{"timestamp": {"seconds": TIMESTAMP, "microseconds": TIMESTAMP}, "event": "SHUTDOWN", "data": {"guest": false}}
51
+
128
+
52
+Formatting 'TEST_DIR/t.IMGFMT', fmt=IMGFMT size=67108864
129
+Testing:
53
+write failed: Input/output error
130
+QMP_VERSION
54
+wrote 1048576/1048576 bytes at offset 0
131
+{"return": {}}
55
+1 MiB, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
132
+{"return": {}}
56
+No errors were found on the image.
133
+{"return": {}}
57
*** done
134
+{"error": {"class": "GenericError", "desc": "Cannot add a child to a quorum in blkverify mode"}}
58
diff --git a/tests/qemu-iotests/026.out.nocache b/tests/qemu-iotests/026.out.nocache
135
+{"return": {}}
59
index XXXXXXX..XXXXXXX 100644
136
+{"timestamp": {"seconds": TIMESTAMP, "microseconds": TIMESTAMP}, "event": "SHUTDOWN", "data": {"guest": false}}
60
--- a/tests/qemu-iotests/026.out.nocache
61
+++ b/tests/qemu-iotests/026.out.nocache
62
@@ -XXX,XX +XXX,XX @@ write failed: No space left on device
63
64
96 leaked clusters were found on the image.
65
This means waste of disk space, but no harm to data.
66
+
137
+
67
+=== Avoid cluster leaks after temporary failure ===
68
+
138
+
69
+Formatting 'TEST_DIR/t.IMGFMT', fmt=IMGFMT size=67108864
139
+== dynamically removing a child from a quorum ==
70
+write failed: Input/output error
140
+Testing:
71
+wrote 1048576/1048576 bytes at offset 0
141
+QMP_VERSION
72
+1 MiB, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
142
+{"return": {}}
73
+No errors were found on the image.
143
+{"return": {}}
144
+{"return": {}}
145
+{"return": {}}
146
+{"timestamp": {"seconds": TIMESTAMP, "microseconds": TIMESTAMP}, "event": "SHUTDOWN", "data": {"guest": false}}
147
+
148
+Testing:
149
+QMP_VERSION
150
+{"return": {}}
151
+{"return": {}}
152
+{"error": {"class": "GenericError", "desc": "The number of children cannot be lower than the vote threshold 2"}}
153
+{"return": {}}
154
+{"timestamp": {"seconds": TIMESTAMP, "microseconds": TIMESTAMP}, "event": "SHUTDOWN", "data": {"guest": false}}
155
+
156
+Testing:
157
+QMP_VERSION
158
+{"return": {}}
159
+{"error": {"class": "GenericError", "desc": "blkverify=on can only be set if there are exactly two files and vote-threshold is 2"}}
160
+{"error": {"class": "GenericError", "desc": "Cannot find device=drive0-quorum nor node_name=drive0-quorum"}}
161
+{"return": {}}
162
+{"timestamp": {"seconds": TIMESTAMP, "microseconds": TIMESTAMP}, "event": "SHUTDOWN", "data": {"guest": false}}
163
+
164
+Testing:
165
+QMP_VERSION
166
+{"return": {}}
167
+{"return": {}}
168
+{"error": {"class": "GenericError", "desc": "The number of children cannot be lower than the vote threshold 2"}}
169
+{"return": {}}
170
+{"timestamp": {"seconds": TIMESTAMP, "microseconds": TIMESTAMP}, "event": "SHUTDOWN", "data": {"guest": false}}
171
+
74
*** done
172
*** done
75
--
173
--
76
2.13.6
174
2.19.1
77
175
78
176
diff view generated by jsdifflib
1
When growing an image, block drivers (especially protocol drivers) may
1
To fully change the read-only state of a node, we must not only change
2
initialise the newly added area. I/O requests to the same area need to
2
bs->read_only, but also update bs->open_flags.
3
wait for this initialisation to be completed so that data writes don't
4
get overwritten and reads don't read uninitialised data.
5
6
To avoid overhead in the fast I/O path by adding new locking in the
7
protocol drivers and to restrict the impact to requests that actually
8
touch the new area, reuse the existing tracked request infrastructure in
9
block/io.c and mark all discard requests as serialising.
10
11
With this change, it is safe for protocol drivers to make
12
.bdrv_co_truncate actually asynchronous.
13
3
14
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
4
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
15
Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
5
Reviewed-by: Eric Blake <eblake@redhat.com>
6
Reviewed-by: Alberto Garcia <berto@igalia.com>
16
---
7
---
17
include/block/block_int.h | 1 +
8
block.c | 7 +++++++
18
block/io.c | 25 +++++++++++++++++++++++++
9
1 file changed, 7 insertions(+)
19
2 files changed, 26 insertions(+)
20
10
21
diff --git a/include/block/block_int.h b/include/block/block_int.h
11
diff --git a/block.c b/block.c
22
index XXXXXXX..XXXXXXX 100644
12
index XXXXXXX..XXXXXXX 100644
23
--- a/include/block/block_int.h
13
--- a/block.c
24
+++ b/include/block/block_int.h
14
+++ b/block.c
25
@@ -XXX,XX +XXX,XX @@ enum BdrvTrackedRequestType {
15
@@ -XXX,XX +XXX,XX @@ int bdrv_set_read_only(BlockDriverState *bs, bool read_only, Error **errp)
26
BDRV_TRACKED_READ,
27
BDRV_TRACKED_WRITE,
28
BDRV_TRACKED_DISCARD,
29
+ BDRV_TRACKED_TRUNCATE,
30
};
31
32
typedef struct BdrvTrackedRequest {
33
diff --git a/block/io.c b/block/io.c
34
index XXXXXXX..XXXXXXX 100644
35
--- a/block/io.c
36
+++ b/block/io.c
37
@@ -XXX,XX +XXX,XX @@ int coroutine_fn bdrv_co_truncate(BdrvChild *child, int64_t offset,
38
{
39
BlockDriverState *bs = child->bs;
40
BlockDriver *drv = bs->drv;
41
+ BdrvTrackedRequest req;
42
+ int64_t old_size, new_bytes;
43
int ret;
44
45
assert(child->perm & BLK_PERM_RESIZE);
46
@@ -XXX,XX +XXX,XX @@ int coroutine_fn bdrv_co_truncate(BdrvChild *child, int64_t offset,
47
return -EINVAL;
48
}
16
}
49
17
50
+ old_size = bdrv_getlength(bs);
18
bs->read_only = read_only;
51
+ if (old_size < 0) {
19
+
52
+ error_setg_errno(errp, -old_size, "Failed to get old image size");
20
+ if (read_only) {
53
+ return old_size;
21
+ bs->open_flags &= ~BDRV_O_RDWR;
22
+ } else {
23
+ bs->open_flags |= BDRV_O_RDWR;
54
+ }
24
+ }
55
+
25
+
56
+ if (offset > old_size) {
26
return 0;
57
+ new_bytes = offset - old_size;
58
+ } else {
59
+ new_bytes = 0;
60
+ }
61
+
62
bdrv_inc_in_flight(bs);
63
+ tracked_request_begin(&req, bs, offset, new_bytes, BDRV_TRACKED_TRUNCATE);
64
+
65
+ /* If we are growing the image and potentially using preallocation for the
66
+ * new area, we need to make sure that no write requests are made to it
67
+ * concurrently or they might be overwritten by preallocation. */
68
+ if (new_bytes) {
69
+ mark_request_serialising(&req, 1);
70
+ wait_serialising_requests(&req);
71
+ }
72
73
if (!drv->bdrv_co_truncate) {
74
if (bs->file && drv->is_filter) {
75
@@ -XXX,XX +XXX,XX @@ int coroutine_fn bdrv_co_truncate(BdrvChild *child, int64_t offset,
76
atomic_inc(&bs->write_gen);
77
78
out:
79
+ tracked_request_end(&req);
80
bdrv_dec_in_flight(bs);
81
+
82
return ret;
83
}
27
}
84
28
85
--
29
--
86
2.13.6
30
2.19.1
87
31
88
32
diff view generated by jsdifflib
1
This moves the bdrv_truncate() implementation from block.c to block/io.c
1
If a management application builds the block graph node by node, the
2
so it can have access to the tracked requests infrastructure.
2
protocol layer doesn't inherit its read-only option from the format
3
layer any more, so it must be set explicitly.
3
4
4
This involves making refresh_total_sectors() public (in block_int.h).
5
Backing files should work on read-only storage, but at the same time, a
6
block job like commit should be able to reopen them read-write if they
7
are on read-write storage. However, without option inheritance, reopen
8
only changes the read-only option for the root node (typically the
9
format layer), but not the protocol layer, so reopening fails (the
10
format layer wants to get write permissions, but the protocol layer is
11
still read-only).
12
13
A simple workaround for the problem in the management tool would be to
14
open the protocol layer always read-write and to make only the format
15
layer read-only for backing files. However, sometimes the file is
16
actually stored on read-only storage and we don't know whether the image
17
can be opened read-write (for example, for NBD it depends on the server
18
we're trying to connect to). This adds an option that makes QEMU try to
19
open the image read-write, but allows it to degrade to a read-only mode
20
without returning an error.
21
22
The documentation for this option is consciously phrased in a way that
23
allows QEMU to switch to a better model eventually: Instead of trying
24
when the image is first opened, making the read-only flag dynamic and
25
changing it automatically whenever the first BLK_PERM_WRITE user is
26
attached or the last one is detached would be much more useful
27
behaviour.
28
29
Unfortunately, this more useful behaviour is also a lot harder to
30
implement, and libvirt needs a solution now before it can switch to
31
-blockdev, so let's start with this easier approach for now.
32
33
Instead of adding a new auto-read-only option, turning the existing
34
read-only into an enum (with a bool alternate for compatibility) was
35
considered, but it complicated the implementation to the point that it
36
didn't seem to be worth it.
5
37
6
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
38
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
7
Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
39
Reviewed-by: Eric Blake <eblake@redhat.com>
8
---
40
---
9
include/block/block_int.h | 2 +
41
qapi/block-core.json | 7 +++++++
10
block.c | 111 +---------------------------------------------
42
include/block/block.h | 2 ++
11
block/io.c | 109 +++++++++++++++++++++++++++++++++++++++++++++
43
block.c | 17 +++++++++++++++++
12
3 files changed, 112 insertions(+), 110 deletions(-)
44
block/vvfat.c | 1 +
45
blockdev.c | 2 +-
46
5 files changed, 28 insertions(+), 1 deletion(-)
13
47
14
diff --git a/include/block/block_int.h b/include/block/block_int.h
48
diff --git a/qapi/block-core.json b/qapi/block-core.json
15
index XXXXXXX..XXXXXXX 100644
49
index XXXXXXX..XXXXXXX 100644
16
--- a/include/block/block_int.h
50
--- a/qapi/block-core.json
17
+++ b/include/block/block_int.h
51
+++ b/qapi/block-core.json
18
@@ -XXX,XX +XXX,XX @@ int coroutine_fn bdrv_co_copy_range_to(BdrvChild *src, uint64_t src_offset,
52
@@ -XXX,XX +XXX,XX @@
19
BdrvChild *dst, uint64_t dst_offset,
53
# either generally or in certain configurations. In this case,
20
uint64_t bytes, BdrvRequestFlags flags);
54
# the default value does not work and the option must be
21
55
# specified explicitly.
22
+int refresh_total_sectors(BlockDriverState *bs, int64_t hint);
56
+# @auto-read-only: if true and @read-only is false, QEMU may automatically
23
+
57
+# decide not to open the image read-write as requested, but
24
#endif /* BLOCK_INT_H */
58
+# fall back to read-only instead (and switch between the modes
59
+# later), e.g. depending on whether the image file is writable
60
+# or whether a writing user is attached to the node
61
+# (default: false, since 3.1)
62
# @detect-zeroes: detect and optimize zero writes (Since 2.1)
63
# (default: off)
64
# @force-share: force share all permission on added nodes.
65
@@ -XXX,XX +XXX,XX @@
66
'*discard': 'BlockdevDiscardOptions',
67
'*cache': 'BlockdevCacheOptions',
68
'*read-only': 'bool',
69
+ '*auto-read-only': 'bool',
70
'*force-share': 'bool',
71
'*detect-zeroes': 'BlockdevDetectZeroesOptions' },
72
'discriminator': 'driver',
73
diff --git a/include/block/block.h b/include/block/block.h
74
index XXXXXXX..XXXXXXX 100644
75
--- a/include/block/block.h
76
+++ b/include/block/block.h
77
@@ -XXX,XX +XXX,XX @@ typedef struct HDGeometry {
78
select an appropriate protocol driver,
79
ignoring the format layer */
80
#define BDRV_O_NO_IO 0x10000 /* don't initialize for I/O */
81
+#define BDRV_O_AUTO_RDONLY 0x20000 /* degrade to read-only if opening read-write fails */
82
83
#define BDRV_O_CACHE_MASK (BDRV_O_NOCACHE | BDRV_O_NO_FLUSH)
84
85
@@ -XXX,XX +XXX,XX @@ typedef struct HDGeometry {
86
#define BDRV_OPT_CACHE_DIRECT "cache.direct"
87
#define BDRV_OPT_CACHE_NO_FLUSH "cache.no-flush"
88
#define BDRV_OPT_READ_ONLY "read-only"
89
+#define BDRV_OPT_AUTO_READ_ONLY "auto-read-only"
90
#define BDRV_OPT_DISCARD "discard"
91
#define BDRV_OPT_FORCE_SHARE "force-share"
92
25
diff --git a/block.c b/block.c
93
diff --git a/block.c b/block.c
26
index XXXXXXX..XXXXXXX 100644
94
index XXXXXXX..XXXXXXX 100644
27
--- a/block.c
95
--- a/block.c
28
+++ b/block.c
96
+++ b/block.c
29
@@ -XXX,XX +XXX,XX @@ static int find_image_format(BlockBackend *file, const char *filename,
97
@@ -XXX,XX +XXX,XX @@ static void bdrv_inherited_options(int *child_flags, QDict *child_options,
30
* Set the current 'total_sectors' value
98
31
* Return 0 on success, -errno on error.
99
/* Inherit the read-only option from the parent if it's not set */
32
*/
100
qdict_copy_default(child_options, parent_options, BDRV_OPT_READ_ONLY);
33
-static int refresh_total_sectors(BlockDriverState *bs, int64_t hint)
101
+ qdict_copy_default(child_options, parent_options, BDRV_OPT_AUTO_READ_ONLY);
34
+int refresh_total_sectors(BlockDriverState *bs, int64_t hint)
102
103
/* Our block drivers take care to send flushes and respect unmap policy,
104
* so we can default to enable both on lower layers regardless of the
105
@@ -XXX,XX +XXX,XX @@ static void bdrv_backing_options(int *child_flags, QDict *child_options,
106
107
/* backing files always opened read-only */
108
qdict_set_default_str(child_options, BDRV_OPT_READ_ONLY, "on");
109
+ qdict_set_default_str(child_options, BDRV_OPT_AUTO_READ_ONLY, "off");
110
flags &= ~BDRV_O_COPY_ON_READ;
111
112
/* snapshot=on is handled on the top layer */
113
@@ -XXX,XX +XXX,XX @@ static void update_flags_from_options(int *flags, QemuOpts *opts)
114
*flags |= BDRV_O_RDWR;
115
}
116
117
+ assert(qemu_opt_find(opts, BDRV_OPT_AUTO_READ_ONLY));
118
+ if (qemu_opt_get_bool_del(opts, BDRV_OPT_AUTO_READ_ONLY, false)) {
119
+ *flags |= BDRV_O_AUTO_RDONLY;
120
+ }
121
}
122
123
static void update_options_from_flags(QDict *options, int flags)
124
@@ -XXX,XX +XXX,XX @@ static void update_options_from_flags(QDict *options, int flags)
125
if (!qdict_haskey(options, BDRV_OPT_READ_ONLY)) {
126
qdict_put_bool(options, BDRV_OPT_READ_ONLY, !(flags & BDRV_O_RDWR));
127
}
128
+ if (!qdict_haskey(options, BDRV_OPT_AUTO_READ_ONLY)) {
129
+ qdict_put_bool(options, BDRV_OPT_AUTO_READ_ONLY,
130
+ flags & BDRV_O_AUTO_RDONLY);
131
+ }
132
}
133
134
static void bdrv_assign_node_name(BlockDriverState *bs,
135
@@ -XXX,XX +XXX,XX @@ QemuOptsList bdrv_runtime_opts = {
136
.type = QEMU_OPT_BOOL,
137
.help = "Node is opened in read-only mode",
138
},
139
+ {
140
+ .name = BDRV_OPT_AUTO_READ_ONLY,
141
+ .type = QEMU_OPT_BOOL,
142
+ .help = "Node can become read-only if opening read-write fails",
143
+ },
144
{
145
.name = "detect-zeroes",
146
.type = QEMU_OPT_STRING,
147
@@ -XXX,XX +XXX,XX @@ BlockDriverState *bdrv_open_blockdev_ref(BlockdevRef *ref, Error **errp)
148
qdict_set_default_str(qdict, BDRV_OPT_CACHE_DIRECT, "off");
149
qdict_set_default_str(qdict, BDRV_OPT_CACHE_NO_FLUSH, "off");
150
qdict_set_default_str(qdict, BDRV_OPT_READ_ONLY, "off");
151
+ qdict_set_default_str(qdict, BDRV_OPT_AUTO_READ_ONLY, "off");
152
+
153
}
154
155
bs = bdrv_open_inherit(NULL, reference, qdict, 0, NULL, NULL, errp);
156
diff --git a/block/vvfat.c b/block/vvfat.c
157
index XXXXXXX..XXXXXXX 100644
158
--- a/block/vvfat.c
159
+++ b/block/vvfat.c
160
@@ -XXX,XX +XXX,XX @@ static void vvfat_qcow_options(int *child_flags, QDict *child_options,
161
int parent_flags, QDict *parent_options)
35
{
162
{
36
BlockDriver *drv = bs->drv;
163
qdict_set_default_str(child_options, BDRV_OPT_READ_ONLY, "off");
37
164
+ qdict_set_default_str(child_options, BDRV_OPT_AUTO_READ_ONLY, "off");
38
@@ -XXX,XX +XXX,XX @@ static void bdrv_parent_cb_change_media(BlockDriverState *bs, bool load)
165
qdict_set_default_str(child_options, BDRV_OPT_CACHE_NO_FLUSH, "on");
39
}
40
}
166
}
41
167
42
-static void bdrv_parent_cb_resize(BlockDriverState *bs)
168
diff --git a/blockdev.c b/blockdev.c
43
-{
44
- BdrvChild *c;
45
- QLIST_FOREACH(c, &bs->parents, next_parent) {
46
- if (c->role->resize) {
47
- c->role->resize(c);
48
- }
49
- }
50
-}
51
-
52
/*
53
* Sets the backing file link of a BDS. A new reference is created; callers
54
* which don't need their own reference any more must call bdrv_unref().
55
@@ -XXX,XX +XXX,XX @@ exit:
56
}
57
58
/**
59
- * Truncate file to 'offset' bytes (needed only for file protocols)
60
- */
61
-int coroutine_fn bdrv_co_truncate(BdrvChild *child, int64_t offset,
62
- PreallocMode prealloc, Error **errp)
63
-{
64
- BlockDriverState *bs = child->bs;
65
- BlockDriver *drv = bs->drv;
66
- int ret;
67
-
68
- assert(child->perm & BLK_PERM_RESIZE);
69
-
70
- /* if bs->drv == NULL, bs is closed, so there's nothing to do here */
71
- if (!drv) {
72
- error_setg(errp, "No medium inserted");
73
- return -ENOMEDIUM;
74
- }
75
- if (offset < 0) {
76
- error_setg(errp, "Image size cannot be negative");
77
- return -EINVAL;
78
- }
79
-
80
- bdrv_inc_in_flight(bs);
81
-
82
- if (!drv->bdrv_co_truncate) {
83
- if (bs->file && drv->is_filter) {
84
- ret = bdrv_co_truncate(bs->file, offset, prealloc, errp);
85
- goto out;
86
- }
87
- error_setg(errp, "Image format driver does not support resize");
88
- ret = -ENOTSUP;
89
- goto out;
90
- }
91
- if (bs->read_only) {
92
- error_setg(errp, "Image is read-only");
93
- ret = -EACCES;
94
- goto out;
95
- }
96
-
97
- assert(!(bs->open_flags & BDRV_O_INACTIVE));
98
-
99
- ret = drv->bdrv_co_truncate(bs, offset, prealloc, errp);
100
- if (ret < 0) {
101
- goto out;
102
- }
103
- ret = refresh_total_sectors(bs, offset >> BDRV_SECTOR_BITS);
104
- if (ret < 0) {
105
- error_setg_errno(errp, -ret, "Could not refresh total sector count");
106
- } else {
107
- offset = bs->total_sectors * BDRV_SECTOR_SIZE;
108
- }
109
- bdrv_dirty_bitmap_truncate(bs, offset);
110
- bdrv_parent_cb_resize(bs);
111
- atomic_inc(&bs->write_gen);
112
-
113
-out:
114
- bdrv_dec_in_flight(bs);
115
- return ret;
116
-}
117
-
118
-typedef struct TruncateCo {
119
- BdrvChild *child;
120
- int64_t offset;
121
- PreallocMode prealloc;
122
- Error **errp;
123
- int ret;
124
-} TruncateCo;
125
-
126
-static void coroutine_fn bdrv_truncate_co_entry(void *opaque)
127
-{
128
- TruncateCo *tco = opaque;
129
- tco->ret = bdrv_co_truncate(tco->child, tco->offset, tco->prealloc,
130
- tco->errp);
131
-}
132
-
133
-int bdrv_truncate(BdrvChild *child, int64_t offset, PreallocMode prealloc,
134
- Error **errp)
135
-{
136
- Coroutine *co;
137
- TruncateCo tco = {
138
- .child = child,
139
- .offset = offset,
140
- .prealloc = prealloc,
141
- .errp = errp,
142
- .ret = NOT_DONE,
143
- };
144
-
145
- if (qemu_in_coroutine()) {
146
- /* Fast-path if already in coroutine context */
147
- bdrv_truncate_co_entry(&tco);
148
- } else {
149
- co = qemu_coroutine_create(bdrv_truncate_co_entry, &tco);
150
- qemu_coroutine_enter(co);
151
- BDRV_POLL_WHILE(child->bs, tco.ret == NOT_DONE);
152
- }
153
-
154
- return tco.ret;
155
-}
156
-
157
-/**
158
* Length of a allocated file in bytes. Sparse files are counted by actual
159
* allocated space. Return < 0 if error or unknown.
160
*/
161
diff --git a/block/io.c b/block/io.c
162
index XXXXXXX..XXXXXXX 100644
169
index XXXXXXX..XXXXXXX 100644
163
--- a/block/io.c
170
--- a/blockdev.c
164
+++ b/block/io.c
171
+++ b/blockdev.c
165
@@ -XXX,XX +XXX,XX @@ int coroutine_fn bdrv_co_copy_range(BdrvChild *src, uint64_t src_offset,
172
@@ -XXX,XX +XXX,XX @@ void qmp_blockdev_change_medium(bool has_device, const char *device,
166
bdrv_dec_in_flight(dst_bs);
173
167
return ret;
174
bdrv_flags = blk_get_open_flags_from_root_state(blk);
168
}
175
bdrv_flags &= ~(BDRV_O_TEMPORARY | BDRV_O_SNAPSHOT | BDRV_O_NO_BACKING |
169
+
176
- BDRV_O_PROTOCOL);
170
+static void bdrv_parent_cb_resize(BlockDriverState *bs)
177
+ BDRV_O_PROTOCOL | BDRV_O_AUTO_RDONLY);
171
+{
178
172
+ BdrvChild *c;
179
if (!has_read_only) {
173
+ QLIST_FOREACH(c, &bs->parents, next_parent) {
180
read_only = BLOCKDEV_CHANGE_READ_ONLY_MODE_RETAIN;
174
+ if (c->role->resize) {
175
+ c->role->resize(c);
176
+ }
177
+ }
178
+}
179
+
180
+/**
181
+ * Truncate file to 'offset' bytes (needed only for file protocols)
182
+ */
183
+int coroutine_fn bdrv_co_truncate(BdrvChild *child, int64_t offset,
184
+ PreallocMode prealloc, Error **errp)
185
+{
186
+ BlockDriverState *bs = child->bs;
187
+ BlockDriver *drv = bs->drv;
188
+ int ret;
189
+
190
+ assert(child->perm & BLK_PERM_RESIZE);
191
+
192
+ /* if bs->drv == NULL, bs is closed, so there's nothing to do here */
193
+ if (!drv) {
194
+ error_setg(errp, "No medium inserted");
195
+ return -ENOMEDIUM;
196
+ }
197
+ if (offset < 0) {
198
+ error_setg(errp, "Image size cannot be negative");
199
+ return -EINVAL;
200
+ }
201
+
202
+ bdrv_inc_in_flight(bs);
203
+
204
+ if (!drv->bdrv_co_truncate) {
205
+ if (bs->file && drv->is_filter) {
206
+ ret = bdrv_co_truncate(bs->file, offset, prealloc, errp);
207
+ goto out;
208
+ }
209
+ error_setg(errp, "Image format driver does not support resize");
210
+ ret = -ENOTSUP;
211
+ goto out;
212
+ }
213
+ if (bs->read_only) {
214
+ error_setg(errp, "Image is read-only");
215
+ ret = -EACCES;
216
+ goto out;
217
+ }
218
+
219
+ assert(!(bs->open_flags & BDRV_O_INACTIVE));
220
+
221
+ ret = drv->bdrv_co_truncate(bs, offset, prealloc, errp);
222
+ if (ret < 0) {
223
+ goto out;
224
+ }
225
+ ret = refresh_total_sectors(bs, offset >> BDRV_SECTOR_BITS);
226
+ if (ret < 0) {
227
+ error_setg_errno(errp, -ret, "Could not refresh total sector count");
228
+ } else {
229
+ offset = bs->total_sectors * BDRV_SECTOR_SIZE;
230
+ }
231
+ bdrv_dirty_bitmap_truncate(bs, offset);
232
+ bdrv_parent_cb_resize(bs);
233
+ atomic_inc(&bs->write_gen);
234
+
235
+out:
236
+ bdrv_dec_in_flight(bs);
237
+ return ret;
238
+}
239
+
240
+typedef struct TruncateCo {
241
+ BdrvChild *child;
242
+ int64_t offset;
243
+ PreallocMode prealloc;
244
+ Error **errp;
245
+ int ret;
246
+} TruncateCo;
247
+
248
+static void coroutine_fn bdrv_truncate_co_entry(void *opaque)
249
+{
250
+ TruncateCo *tco = opaque;
251
+ tco->ret = bdrv_co_truncate(tco->child, tco->offset, tco->prealloc,
252
+ tco->errp);
253
+}
254
+
255
+int bdrv_truncate(BdrvChild *child, int64_t offset, PreallocMode prealloc,
256
+ Error **errp)
257
+{
258
+ Coroutine *co;
259
+ TruncateCo tco = {
260
+ .child = child,
261
+ .offset = offset,
262
+ .prealloc = prealloc,
263
+ .errp = errp,
264
+ .ret = NOT_DONE,
265
+ };
266
+
267
+ if (qemu_in_coroutine()) {
268
+ /* Fast-path if already in coroutine context */
269
+ bdrv_truncate_co_entry(&tco);
270
+ } else {
271
+ co = qemu_coroutine_create(bdrv_truncate_co_entry, &tco);
272
+ qemu_coroutine_enter(co);
273
+ BDRV_POLL_WHILE(child->bs, tco.ret == NOT_DONE);
274
+ }
275
+
276
+ return tco.ret;
277
+}
278
--
181
--
279
2.13.6
182
2.19.1
280
183
281
184
diff view generated by jsdifflib
1
If we managed to allocate the clusters, but then failed to write the
1
Commit e2b8247a322 introduced an error path in qemu_rbd_open() after
2
data, there's a good chance that we'll still be able to free the
2
calling rbd_open(), but neglected to close the image again in this error
3
clusters again in order to avoid cluster leaks (the refcounts are
3
path. The error path should contain everything that the regular close
4
cached, so even if we can't write them out right now, we may be able to
4
function qemu_rbd_close() contains.
5
do so when the VM is resumed after a werror=stop/enospc pause).
5
6
This adds the missing rbd_close() call.
6
7
7
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
8
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
8
Reviewed-by: Max Reitz <mreitz@redhat.com>
9
Reviewed-by: Eric Blake <eblake@redhat.com>
9
Reviewed-by: Eric Blake <eblake@redhat.com>
10
Tested-by: Eric Blake <eblake@redhat.com>
11
---
10
---
12
block/qcow2.h | 1 +
11
block/rbd.c | 1 +
13
block/qcow2-cluster.c | 11 +++++++++++
12
1 file changed, 1 insertion(+)
14
block/qcow2.c | 2 ++
15
3 files changed, 14 insertions(+)
16
13
17
diff --git a/block/qcow2.h b/block/qcow2.h
14
diff --git a/block/rbd.c b/block/rbd.c
18
index XXXXXXX..XXXXXXX 100644
15
index XXXXXXX..XXXXXXX 100644
19
--- a/block/qcow2.h
16
--- a/block/rbd.c
20
+++ b/block/qcow2.h
17
+++ b/block/rbd.c
21
@@ -XXX,XX +XXX,XX @@ uint64_t qcow2_alloc_compressed_cluster_offset(BlockDriverState *bs,
18
@@ -XXX,XX +XXX,XX @@ static int qemu_rbd_open(BlockDriverState *bs, QDict *options, int flags,
22
int compressed_size);
19
"automatically marking the image read-only.");
23
20
r = bdrv_set_read_only(bs, true, &local_err);
24
int qcow2_alloc_cluster_link_l2(BlockDriverState *bs, QCowL2Meta *m);
21
if (r < 0) {
25
+void qcow2_alloc_cluster_abort(BlockDriverState *bs, QCowL2Meta *m);
22
+ rbd_close(s->image);
26
int qcow2_cluster_discard(BlockDriverState *bs, uint64_t offset,
23
error_propagate(errp, local_err);
27
uint64_t bytes, enum qcow2_discard_type type,
24
goto failed_open;
28
bool full_discard);
29
diff --git a/block/qcow2-cluster.c b/block/qcow2-cluster.c
30
index XXXXXXX..XXXXXXX 100644
31
--- a/block/qcow2-cluster.c
32
+++ b/block/qcow2-cluster.c
33
@@ -XXX,XX +XXX,XX @@ err:
34
return ret;
35
}
36
37
+/**
38
+ * Frees the allocated clusters because the request failed and they won't
39
+ * actually be linked.
40
+ */
41
+void qcow2_alloc_cluster_abort(BlockDriverState *bs, QCowL2Meta *m)
42
+{
43
+ BDRVQcow2State *s = bs->opaque;
44
+ qcow2_free_clusters(bs, m->alloc_offset, m->nb_clusters << s->cluster_bits,
45
+ QCOW2_DISCARD_NEVER);
46
+}
47
+
48
/*
49
* Returns the number of contiguous clusters that can be used for an allocating
50
* write, but require COW to be performed (this includes yet unallocated space,
51
diff --git a/block/qcow2.c b/block/qcow2.c
52
index XXXXXXX..XXXXXXX 100644
53
--- a/block/qcow2.c
54
+++ b/block/qcow2.c
55
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int qcow2_handle_l2meta(BlockDriverState *bs,
56
if (ret) {
57
goto out;
58
}
25
}
59
+ } else {
60
+ qcow2_alloc_cluster_abort(bs, l2meta);
61
}
62
63
/* Take the request off the list of running requests */
64
--
26
--
65
2.13.6
27
2.19.1
66
28
67
29
diff view generated by jsdifflib
1
bdrv_truncate() is an operation that can block (even for a quite long
1
Some block drivers have traditionally changed their node to read-only
2
time, depending on the PreallocMode) in I/O paths that shouldn't block.
2
mode without asking the user. This behaviour has been marked deprecated
3
Convert it to a coroutine_fn so that we have the infrastructure for
3
since 2.11, expecting users to provide an explicit read-only=on option.
4
drivers to make their .bdrv_co_truncate implementation asynchronous.
4
5
5
Now that we have auto-read-only=on, enable these drivers to make use of
6
This change could potentially introduce new race conditions because
6
the option.
7
bdrv_truncate() isn't necessarily executed atomically any more. Whether
7
8
this is a problem needs to be evaluated for each block driver that
8
This is the only use of bdrv_set_read_only(), so we can make it a bit
9
supports truncate:
9
more specific and turn it into a bdrv_apply_auto_read_only() that is
10
10
more convenient for drivers to use.
11
* file-posix/win32, gluster, iscsi, nfs, rbd, ssh, sheepdog: The
12
protocol drivers are trivially safe because they don't actually yield
13
yet, so there is no change in behaviour.
14
15
* copy-on-read, crypto, raw-format: Essentially just filter drivers that
16
pass the request to a child node, no problem.
17
18
* qcow2: The implementation modifies metadata, so it needs to hold
19
s->lock to be safe with concurrent I/O requests. In order to avoid
20
double locking, this requires pulling the locking out into
21
preallocate_co() and using qcow2_write_caches() instead of
22
bdrv_flush().
23
24
* qed: Does a single header update, this is fine without locking.
25
11
26
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
12
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
27
Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
13
Reviewed-by: Eric Blake <eblake@redhat.com>
28
---
14
---
29
include/block/block.h | 4 +++
15
include/block/block.h | 3 ++-
30
include/block/block_int.h | 4 +--
16
block.c | 42 +++++++++++++++++++++++++++---------------
31
block.c | 63 +++++++++++++++++++++++++++++++++++-----
17
block/bochs.c | 17 ++++++-----------
32
block/copy-on-read.c | 8 ++---
18
block/cloop.c | 16 +++++-----------
33
block/crypto.c | 9 +++---
19
block/dmg.c | 16 +++++-----------
34
block/file-posix.c | 12 ++++----
20
block/rbd.c | 15 ++++-----------
35
block/file-win32.c | 6 ++--
21
block/vvfat.c | 10 ++--------
36
block/gluster.c | 14 +++++----
22
7 files changed, 51 insertions(+), 68 deletions(-)
37
block/iscsi.c | 8 ++---
38
block/nfs.c | 7 +++--
39
block/qcow2.c | 74 ++++++++++++++++++++++++++++-------------------
40
block/qed.c | 8 +++--
41
block/raw-format.c | 8 ++---
42
block/rbd.c | 8 +++--
43
block/sheepdog.c | 12 ++++----
44
block/ssh.c | 6 ++--
45
16 files changed, 162 insertions(+), 89 deletions(-)
46
23
47
diff --git a/include/block/block.h b/include/block/block.h
24
diff --git a/include/block/block.h b/include/block/block.h
48
index XXXXXXX..XXXXXXX 100644
25
index XXXXXXX..XXXXXXX 100644
49
--- a/include/block/block.h
26
--- a/include/block/block.h
50
+++ b/include/block/block.h
27
+++ b/include/block/block.h
51
@@ -XXX,XX +XXX,XX @@ int coroutine_fn bdrv_co_pwrite_zeroes(BdrvChild *child, int64_t offset,
28
@@ -XXX,XX +XXX,XX @@ int bdrv_is_allocated_above(BlockDriverState *top, BlockDriverState *base,
52
BlockDriverState *bdrv_find_backing_image(BlockDriverState *bs,
29
bool bdrv_is_read_only(BlockDriverState *bs);
53
const char *backing_file);
30
int bdrv_can_set_read_only(BlockDriverState *bs, bool read_only,
54
void bdrv_refresh_filename(BlockDriverState *bs);
31
bool ignore_allow_rdw, Error **errp);
55
+
32
-int bdrv_set_read_only(BlockDriverState *bs, bool read_only, Error **errp);
56
+int coroutine_fn bdrv_co_truncate(BdrvChild *child, int64_t offset,
33
+int bdrv_apply_auto_read_only(BlockDriverState *bs, const char *errmsg,
57
+ PreallocMode prealloc, Error **errp);
34
+ Error **errp);
58
int bdrv_truncate(BdrvChild *child, int64_t offset, PreallocMode prealloc,
35
bool bdrv_is_writable(BlockDriverState *bs);
59
Error **errp);
36
bool bdrv_is_sg(BlockDriverState *bs);
60
+
37
bool bdrv_is_inserted(BlockDriverState *bs);
61
int64_t bdrv_nb_sectors(BlockDriverState *bs);
62
int64_t bdrv_getlength(BlockDriverState *bs);
63
int64_t bdrv_get_allocated_file_size(BlockDriverState *bs);
64
diff --git a/include/block/block_int.h b/include/block/block_int.h
65
index XXXXXXX..XXXXXXX 100644
66
--- a/include/block/block_int.h
67
+++ b/include/block/block_int.h
68
@@ -XXX,XX +XXX,XX @@ struct BlockDriver {
69
* bdrv_parse_filename.
70
*/
71
const char *protocol_name;
72
- int (*bdrv_truncate)(BlockDriverState *bs, int64_t offset,
73
- PreallocMode prealloc, Error **errp);
74
+ int coroutine_fn (*bdrv_co_truncate)(BlockDriverState *bs, int64_t offset,
75
+ PreallocMode prealloc, Error **errp);
76
77
int64_t (*bdrv_getlength)(BlockDriverState *bs);
78
bool has_variable_length;
79
diff --git a/block.c b/block.c
38
diff --git a/block.c b/block.c
80
index XXXXXXX..XXXXXXX 100644
39
index XXXXXXX..XXXXXXX 100644
81
--- a/block.c
40
--- a/block.c
82
+++ b/block.c
41
+++ b/block.c
83
@@ -XXX,XX +XXX,XX @@ exit:
42
@@ -XXX,XX +XXX,XX @@ int bdrv_can_set_read_only(BlockDriverState *bs, bool read_only,
84
/**
43
return 0;
85
* Truncate file to 'offset' bytes (needed only for file protocols)
44
}
86
*/
45
87
-int bdrv_truncate(BdrvChild *child, int64_t offset, PreallocMode prealloc,
46
-/* TODO Remove (deprecated since 2.11)
88
- Error **errp)
47
- * Block drivers are not supposed to automatically change bs->read_only.
89
+int coroutine_fn bdrv_co_truncate(BdrvChild *child, int64_t offset,
48
- * Instead, they should just check whether they can provide what the user
90
+ PreallocMode prealloc, Error **errp)
49
- * explicitly requested and error out if read-write is requested, but they can
50
- * only provide read-only access. */
51
-int bdrv_set_read_only(BlockDriverState *bs, bool read_only, Error **errp)
52
+/*
53
+ * Called by a driver that can only provide a read-only image.
54
+ *
55
+ * Returns 0 if the node is already read-only or it could switch the node to
56
+ * read-only because BDRV_O_AUTO_RDONLY is set.
57
+ *
58
+ * Returns -EACCES if the node is read-write and BDRV_O_AUTO_RDONLY is not set
59
+ * or bdrv_can_set_read_only() forbids making the node read-only. If @errmsg
60
+ * is not NULL, it is used as the error message for the Error object.
61
+ */
62
+int bdrv_apply_auto_read_only(BlockDriverState *bs, const char *errmsg,
63
+ Error **errp)
91
{
64
{
92
BlockDriverState *bs = child->bs;
65
int ret = 0;
93
BlockDriver *drv = bs->drv;
66
94
@@ -XXX,XX +XXX,XX @@ int bdrv_truncate(BdrvChild *child, int64_t offset, PreallocMode prealloc,
67
- ret = bdrv_can_set_read_only(bs, read_only, false, errp);
68
- if (ret < 0) {
69
- return ret;
70
+ if (!(bs->open_flags & BDRV_O_RDWR)) {
71
+ return 0;
72
+ }
73
+ if (!(bs->open_flags & BDRV_O_AUTO_RDONLY)) {
74
+ goto fail;
75
}
76
77
- bs->read_only = read_only;
78
-
79
- if (read_only) {
80
- bs->open_flags &= ~BDRV_O_RDWR;
81
- } else {
82
- bs->open_flags |= BDRV_O_RDWR;
83
+ ret = bdrv_can_set_read_only(bs, true, false, NULL);
84
+ if (ret < 0) {
85
+ goto fail;
86
}
87
88
+ bs->read_only = true;
89
+ bs->open_flags &= ~BDRV_O_RDWR;
90
+
91
return 0;
92
+
93
+fail:
94
+ error_setg(errp, "%s", errmsg ?: "Image is read-only");
95
+ return -EACCES;
96
}
97
98
void bdrv_get_full_backing_filename_from_filename(const char *backed,
99
diff --git a/block/bochs.c b/block/bochs.c
100
index XXXXXXX..XXXXXXX 100644
101
--- a/block/bochs.c
102
+++ b/block/bochs.c
103
@@ -XXX,XX +XXX,XX @@ static int bochs_open(BlockDriverState *bs, QDict *options, int flags,
104
struct bochs_header bochs;
105
int ret;
106
107
+ /* No write support yet */
108
+ ret = bdrv_apply_auto_read_only(bs, NULL, errp);
109
+ if (ret < 0) {
110
+ return ret;
111
+ }
112
+
113
bs->file = bdrv_open_child(NULL, options, "file", bs, &child_file,
114
false, errp);
115
if (!bs->file) {
95
return -EINVAL;
116
return -EINVAL;
96
}
117
}
97
118
98
- if (!drv->bdrv_truncate) {
119
- if (!bdrv_is_read_only(bs)) {
99
+ bdrv_inc_in_flight(bs);
120
- error_report("Opening bochs images without an explicit read-only=on "
100
+
121
- "option is deprecated. Future versions will refuse to "
101
+ if (!drv->bdrv_co_truncate) {
122
- "open the image instead of automatically marking the "
102
if (bs->file && drv->is_filter) {
123
- "image read-only.");
103
- return bdrv_truncate(bs->file, offset, prealloc, errp);
124
- ret = bdrv_set_read_only(bs, true, errp); /* no write support yet */
104
+ ret = bdrv_co_truncate(bs->file, offset, prealloc, errp);
125
- if (ret < 0) {
105
+ goto out;
126
- return ret;
106
}
127
- }
107
error_setg(errp, "Image format driver does not support resize");
128
- }
108
- return -ENOTSUP;
129
-
109
+ ret = -ENOTSUP;
130
ret = bdrv_pread(bs->file, 0, &bochs, sizeof(bochs));
110
+ goto out;
111
}
112
if (bs->read_only) {
113
error_setg(errp, "Image is read-only");
114
- return -EACCES;
115
+ ret = -EACCES;
116
+ goto out;
117
}
118
119
assert(!(bs->open_flags & BDRV_O_INACTIVE));
120
121
- ret = drv->bdrv_truncate(bs, offset, prealloc, errp);
122
+ ret = drv->bdrv_co_truncate(bs, offset, prealloc, errp);
123
if (ret < 0) {
131
if (ret < 0) {
124
- return ret;
132
return ret;
125
+ goto out;
133
diff --git a/block/cloop.c b/block/cloop.c
126
}
134
index XXXXXXX..XXXXXXX 100644
127
ret = refresh_total_sectors(bs, offset >> BDRV_SECTOR_BITS);
135
--- a/block/cloop.c
136
+++ b/block/cloop.c
137
@@ -XXX,XX +XXX,XX @@ static int cloop_open(BlockDriverState *bs, QDict *options, int flags,
138
uint32_t offsets_size, max_compressed_block_size = 1, i;
139
int ret;
140
141
+ ret = bdrv_apply_auto_read_only(bs, NULL, errp);
142
+ if (ret < 0) {
143
+ return ret;
144
+ }
145
+
146
bs->file = bdrv_open_child(NULL, options, "file", bs, &child_file,
147
false, errp);
148
if (!bs->file) {
149
return -EINVAL;
150
}
151
152
- if (!bdrv_is_read_only(bs)) {
153
- error_report("Opening cloop images without an explicit read-only=on "
154
- "option is deprecated. Future versions will refuse to "
155
- "open the image instead of automatically marking the "
156
- "image read-only.");
157
- ret = bdrv_set_read_only(bs, true, errp);
158
- if (ret < 0) {
159
- return ret;
160
- }
161
- }
162
-
163
/* read header */
164
ret = bdrv_pread(bs->file, 128, &s->block_size, 4);
128
if (ret < 0) {
165
if (ret < 0) {
129
@@ -XXX,XX +XXX,XX @@ int bdrv_truncate(BdrvChild *child, int64_t offset, PreallocMode prealloc,
166
diff --git a/block/dmg.c b/block/dmg.c
130
bdrv_dirty_bitmap_truncate(bs, offset);
167
index XXXXXXX..XXXXXXX 100644
131
bdrv_parent_cb_resize(bs);
168
--- a/block/dmg.c
132
atomic_inc(&bs->write_gen);
169
+++ b/block/dmg.c
133
+
170
@@ -XXX,XX +XXX,XX @@ static int dmg_open(BlockDriverState *bs, QDict *options, int flags,
134
+out:
171
int64_t offset;
135
+ bdrv_dec_in_flight(bs);
136
return ret;
137
}
138
139
+typedef struct TruncateCo {
140
+ BdrvChild *child;
141
+ int64_t offset;
142
+ PreallocMode prealloc;
143
+ Error **errp;
144
+ int ret;
145
+} TruncateCo;
146
+
147
+static void coroutine_fn bdrv_truncate_co_entry(void *opaque)
148
+{
149
+ TruncateCo *tco = opaque;
150
+ tco->ret = bdrv_co_truncate(tco->child, tco->offset, tco->prealloc,
151
+ tco->errp);
152
+}
153
+
154
+int bdrv_truncate(BdrvChild *child, int64_t offset, PreallocMode prealloc,
155
+ Error **errp)
156
+{
157
+ Coroutine *co;
158
+ TruncateCo tco = {
159
+ .child = child,
160
+ .offset = offset,
161
+ .prealloc = prealloc,
162
+ .errp = errp,
163
+ .ret = NOT_DONE,
164
+ };
165
+
166
+ if (qemu_in_coroutine()) {
167
+ /* Fast-path if already in coroutine context */
168
+ bdrv_truncate_co_entry(&tco);
169
+ } else {
170
+ co = qemu_coroutine_create(bdrv_truncate_co_entry, &tco);
171
+ qemu_coroutine_enter(co);
172
+ BDRV_POLL_WHILE(child->bs, tco.ret == NOT_DONE);
173
+ }
174
+
175
+ return tco.ret;
176
+}
177
+
178
/**
179
* Length of a allocated file in bytes. Sparse files are counted by actual
180
* allocated space. Return < 0 if error or unknown.
181
diff --git a/block/copy-on-read.c b/block/copy-on-read.c
182
index XXXXXXX..XXXXXXX 100644
183
--- a/block/copy-on-read.c
184
+++ b/block/copy-on-read.c
185
@@ -XXX,XX +XXX,XX @@ static int64_t cor_getlength(BlockDriverState *bs)
186
}
187
188
189
-static int cor_truncate(BlockDriverState *bs, int64_t offset,
190
- PreallocMode prealloc, Error **errp)
191
+static int coroutine_fn cor_co_truncate(BlockDriverState *bs, int64_t offset,
192
+ PreallocMode prealloc, Error **errp)
193
{
194
- return bdrv_truncate(bs->file, offset, prealloc, errp);
195
+ return bdrv_co_truncate(bs->file, offset, prealloc, errp);
196
}
197
198
199
@@ -XXX,XX +XXX,XX @@ BlockDriver bdrv_copy_on_read = {
200
.bdrv_child_perm = cor_child_perm,
201
202
.bdrv_getlength = cor_getlength,
203
- .bdrv_truncate = cor_truncate,
204
+ .bdrv_co_truncate = cor_co_truncate,
205
206
.bdrv_co_preadv = cor_co_preadv,
207
.bdrv_co_pwritev = cor_co_pwritev,
208
diff --git a/block/crypto.c b/block/crypto.c
209
index XXXXXXX..XXXXXXX 100644
210
--- a/block/crypto.c
211
+++ b/block/crypto.c
212
@@ -XXX,XX +XXX,XX @@ static int block_crypto_co_create_generic(BlockDriverState *bs,
213
return ret;
214
}
215
216
-static int block_crypto_truncate(BlockDriverState *bs, int64_t offset,
217
- PreallocMode prealloc, Error **errp)
218
+static int coroutine_fn
219
+block_crypto_co_truncate(BlockDriverState *bs, int64_t offset,
220
+ PreallocMode prealloc, Error **errp)
221
{
222
BlockCrypto *crypto = bs->opaque;
223
uint64_t payload_offset =
224
@@ -XXX,XX +XXX,XX @@ static int block_crypto_truncate(BlockDriverState *bs, int64_t offset,
225
226
offset += payload_offset;
227
228
- return bdrv_truncate(bs->file, offset, prealloc, errp);
229
+ return bdrv_co_truncate(bs->file, offset, prealloc, errp);
230
}
231
232
static void block_crypto_close(BlockDriverState *bs)
233
@@ -XXX,XX +XXX,XX @@ BlockDriver bdrv_crypto_luks = {
234
.bdrv_child_perm = bdrv_format_default_perms,
235
.bdrv_co_create = block_crypto_co_create_luks,
236
.bdrv_co_create_opts = block_crypto_co_create_opts_luks,
237
- .bdrv_truncate = block_crypto_truncate,
238
+ .bdrv_co_truncate = block_crypto_co_truncate,
239
.create_opts = &block_crypto_create_opts_luks,
240
241
.bdrv_reopen_prepare = block_crypto_reopen_prepare,
242
diff --git a/block/file-posix.c b/block/file-posix.c
243
index XXXXXXX..XXXXXXX 100644
244
--- a/block/file-posix.c
245
+++ b/block/file-posix.c
246
@@ -XXX,XX +XXX,XX @@ out:
247
return result;
248
}
249
250
-static int raw_truncate(BlockDriverState *bs, int64_t offset,
251
- PreallocMode prealloc, Error **errp)
252
+static int coroutine_fn raw_co_truncate(BlockDriverState *bs, int64_t offset,
253
+ PreallocMode prealloc, Error **errp)
254
{
255
BDRVRawState *s = bs->opaque;
256
struct stat st;
257
@@ -XXX,XX +XXX,XX @@ BlockDriver bdrv_file = {
258
.bdrv_io_unplug = raw_aio_unplug,
259
.bdrv_attach_aio_context = raw_aio_attach_aio_context,
260
261
- .bdrv_truncate = raw_truncate,
262
+ .bdrv_co_truncate = raw_co_truncate,
263
.bdrv_getlength = raw_getlength,
264
.bdrv_get_info = raw_get_info,
265
.bdrv_get_allocated_file_size
266
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_host_device = {
267
.bdrv_io_plug = raw_aio_plug,
268
.bdrv_io_unplug = raw_aio_unplug,
269
270
- .bdrv_truncate = raw_truncate,
271
+ .bdrv_co_truncate = raw_co_truncate,
272
.bdrv_getlength    = raw_getlength,
273
.bdrv_get_info = raw_get_info,
274
.bdrv_get_allocated_file_size
275
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_host_cdrom = {
276
.bdrv_io_plug = raw_aio_plug,
277
.bdrv_io_unplug = raw_aio_unplug,
278
279
- .bdrv_truncate = raw_truncate,
280
+ .bdrv_co_truncate = raw_co_truncate,
281
.bdrv_getlength = raw_getlength,
282
.has_variable_length = true,
283
.bdrv_get_allocated_file_size
284
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_host_cdrom = {
285
.bdrv_io_plug = raw_aio_plug,
286
.bdrv_io_unplug = raw_aio_unplug,
287
288
- .bdrv_truncate = raw_truncate,
289
+ .bdrv_co_truncate = raw_co_truncate,
290
.bdrv_getlength = raw_getlength,
291
.has_variable_length = true,
292
.bdrv_get_allocated_file_size
293
diff --git a/block/file-win32.c b/block/file-win32.c
294
index XXXXXXX..XXXXXXX 100644
295
--- a/block/file-win32.c
296
+++ b/block/file-win32.c
297
@@ -XXX,XX +XXX,XX @@ static void raw_close(BlockDriverState *bs)
298
}
299
}
300
301
-static int raw_truncate(BlockDriverState *bs, int64_t offset,
302
- PreallocMode prealloc, Error **errp)
303
+static int coroutine_fn raw_co_truncate(BlockDriverState *bs, int64_t offset,
304
+ PreallocMode prealloc, Error **errp)
305
{
306
BDRVRawState *s = bs->opaque;
307
LONG low, high;
308
@@ -XXX,XX +XXX,XX @@ BlockDriver bdrv_file = {
309
.bdrv_aio_pwritev = raw_aio_pwritev,
310
.bdrv_aio_flush = raw_aio_flush,
311
312
- .bdrv_truncate    = raw_truncate,
313
+ .bdrv_co_truncate = raw_co_truncate,
314
.bdrv_getlength    = raw_getlength,
315
.bdrv_get_allocated_file_size
316
= raw_get_allocated_file_size,
317
diff --git a/block/gluster.c b/block/gluster.c
318
index XXXXXXX..XXXXXXX 100644
319
--- a/block/gluster.c
320
+++ b/block/gluster.c
321
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int qemu_gluster_co_rw(BlockDriverState *bs,
322
return acb.ret;
323
}
324
325
-static int qemu_gluster_truncate(BlockDriverState *bs, int64_t offset,
326
- PreallocMode prealloc, Error **errp)
327
+static coroutine_fn int qemu_gluster_co_truncate(BlockDriverState *bs,
328
+ int64_t offset,
329
+ PreallocMode prealloc,
330
+ Error **errp)
331
{
332
BDRVGlusterState *s = bs->opaque;
333
return qemu_gluster_do_truncate(s->fd, offset, prealloc, errp);
334
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_gluster = {
335
.bdrv_co_create_opts = qemu_gluster_co_create_opts,
336
.bdrv_getlength = qemu_gluster_getlength,
337
.bdrv_get_allocated_file_size = qemu_gluster_allocated_file_size,
338
- .bdrv_truncate = qemu_gluster_truncate,
339
+ .bdrv_co_truncate = qemu_gluster_co_truncate,
340
.bdrv_co_readv = qemu_gluster_co_readv,
341
.bdrv_co_writev = qemu_gluster_co_writev,
342
.bdrv_co_flush_to_disk = qemu_gluster_co_flush_to_disk,
343
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_gluster_tcp = {
344
.bdrv_co_create_opts = qemu_gluster_co_create_opts,
345
.bdrv_getlength = qemu_gluster_getlength,
346
.bdrv_get_allocated_file_size = qemu_gluster_allocated_file_size,
347
- .bdrv_truncate = qemu_gluster_truncate,
348
+ .bdrv_co_truncate = qemu_gluster_co_truncate,
349
.bdrv_co_readv = qemu_gluster_co_readv,
350
.bdrv_co_writev = qemu_gluster_co_writev,
351
.bdrv_co_flush_to_disk = qemu_gluster_co_flush_to_disk,
352
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_gluster_unix = {
353
.bdrv_co_create_opts = qemu_gluster_co_create_opts,
354
.bdrv_getlength = qemu_gluster_getlength,
355
.bdrv_get_allocated_file_size = qemu_gluster_allocated_file_size,
356
- .bdrv_truncate = qemu_gluster_truncate,
357
+ .bdrv_co_truncate = qemu_gluster_co_truncate,
358
.bdrv_co_readv = qemu_gluster_co_readv,
359
.bdrv_co_writev = qemu_gluster_co_writev,
360
.bdrv_co_flush_to_disk = qemu_gluster_co_flush_to_disk,
361
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_gluster_rdma = {
362
.bdrv_co_create_opts = qemu_gluster_co_create_opts,
363
.bdrv_getlength = qemu_gluster_getlength,
364
.bdrv_get_allocated_file_size = qemu_gluster_allocated_file_size,
365
- .bdrv_truncate = qemu_gluster_truncate,
366
+ .bdrv_co_truncate = qemu_gluster_co_truncate,
367
.bdrv_co_readv = qemu_gluster_co_readv,
368
.bdrv_co_writev = qemu_gluster_co_writev,
369
.bdrv_co_flush_to_disk = qemu_gluster_co_flush_to_disk,
370
diff --git a/block/iscsi.c b/block/iscsi.c
371
index XXXXXXX..XXXXXXX 100644
372
--- a/block/iscsi.c
373
+++ b/block/iscsi.c
374
@@ -XXX,XX +XXX,XX @@ static void iscsi_reopen_commit(BDRVReopenState *reopen_state)
375
}
376
}
377
378
-static int iscsi_truncate(BlockDriverState *bs, int64_t offset,
379
- PreallocMode prealloc, Error **errp)
380
+static int coroutine_fn iscsi_co_truncate(BlockDriverState *bs, int64_t offset,
381
+ PreallocMode prealloc, Error **errp)
382
{
383
IscsiLun *iscsilun = bs->opaque;
384
Error *local_err = NULL;
385
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_iscsi = {
386
387
.bdrv_getlength = iscsi_getlength,
388
.bdrv_get_info = iscsi_get_info,
389
- .bdrv_truncate = iscsi_truncate,
390
+ .bdrv_co_truncate = iscsi_co_truncate,
391
.bdrv_refresh_limits = iscsi_refresh_limits,
392
393
.bdrv_co_block_status = iscsi_co_block_status,
394
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_iser = {
395
396
.bdrv_getlength = iscsi_getlength,
397
.bdrv_get_info = iscsi_get_info,
398
- .bdrv_truncate = iscsi_truncate,
399
+ .bdrv_co_truncate = iscsi_co_truncate,
400
.bdrv_refresh_limits = iscsi_refresh_limits,
401
402
.bdrv_co_block_status = iscsi_co_block_status,
403
diff --git a/block/nfs.c b/block/nfs.c
404
index XXXXXXX..XXXXXXX 100644
405
--- a/block/nfs.c
406
+++ b/block/nfs.c
407
@@ -XXX,XX +XXX,XX @@ static int64_t nfs_get_allocated_file_size(BlockDriverState *bs)
408
return (task.ret < 0 ? task.ret : st.st_blocks * 512);
409
}
410
411
-static int nfs_file_truncate(BlockDriverState *bs, int64_t offset,
412
- PreallocMode prealloc, Error **errp)
413
+static int coroutine_fn
414
+nfs_file_co_truncate(BlockDriverState *bs, int64_t offset,
415
+ PreallocMode prealloc, Error **errp)
416
{
417
NFSClient *client = bs->opaque;
418
int ret;
172
int ret;
419
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_nfs = {
173
420
174
+ ret = bdrv_apply_auto_read_only(bs, NULL, errp);
421
.bdrv_has_zero_init = nfs_has_zero_init,
175
+ if (ret < 0) {
422
.bdrv_get_allocated_file_size = nfs_get_allocated_file_size,
176
+ return ret;
423
- .bdrv_truncate = nfs_file_truncate,
177
+ }
424
+ .bdrv_co_truncate = nfs_file_co_truncate,
178
+
425
179
bs->file = bdrv_open_child(NULL, options, "file", bs, &child_file,
426
.bdrv_file_open = nfs_file_open,
180
false, errp);
427
.bdrv_close = nfs_file_close,
181
if (!bs->file) {
428
diff --git a/block/qcow2.c b/block/qcow2.c
429
index XXXXXXX..XXXXXXX 100644
430
--- a/block/qcow2.c
431
+++ b/block/qcow2.c
432
@@ -XXX,XX +XXX,XX @@ static void coroutine_fn preallocate_co(void *opaque)
433
BlockDriverState *bs = params->bs;
434
uint64_t offset = params->offset;
435
uint64_t new_length = params->new_length;
436
- BDRVQcow2State *s = bs->opaque;
437
uint64_t bytes;
438
uint64_t host_offset = 0;
439
unsigned int cur_bytes;
440
int ret;
441
QCowL2Meta *meta;
442
443
- qemu_co_mutex_lock(&s->lock);
444
-
445
assert(offset <= new_length);
446
bytes = new_length - offset;
447
448
@@ -XXX,XX +XXX,XX @@ static void coroutine_fn preallocate_co(void *opaque)
449
ret = 0;
450
451
done:
452
- qemu_co_mutex_unlock(&s->lock);
453
params->ret = ret;
454
}
455
456
@@ -XXX,XX +XXX,XX @@ qcow2_co_create(BlockdevCreateOptions *create_options, Error **errp)
457
458
/* And if we're supposed to preallocate metadata, do that now */
459
if (qcow2_opts->preallocation != PREALLOC_MODE_OFF) {
460
+ BDRVQcow2State *s = blk_bs(blk)->opaque;
461
+ qemu_co_mutex_lock(&s->lock);
462
ret = preallocate(blk_bs(blk), 0, qcow2_opts->size);
463
+ qemu_co_mutex_unlock(&s->lock);
464
+
465
if (ret < 0) {
466
error_setg_errno(errp, -ret, "Could not preallocate metadata");
467
goto out;
468
@@ -XXX,XX +XXX,XX @@ fail:
469
return ret;
470
}
471
472
-static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
473
- PreallocMode prealloc, Error **errp)
474
+static int coroutine_fn qcow2_co_truncate(BlockDriverState *bs, int64_t offset,
475
+ PreallocMode prealloc, Error **errp)
476
{
477
BDRVQcow2State *s = bs->opaque;
478
uint64_t old_length;
479
@@ -XXX,XX +XXX,XX @@ static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
480
return -EINVAL;
182
return -EINVAL;
481
}
183
}
482
184
483
+ qemu_co_mutex_lock(&s->lock);
185
- if (!bdrv_is_read_only(bs)) {
484
+
186
- error_report("Opening dmg images without an explicit read-only=on "
485
/* cannot proceed if image has snapshots */
187
- "option is deprecated. Future versions will refuse to "
486
if (s->nb_snapshots) {
188
- "open the image instead of automatically marking the "
487
error_setg(errp, "Can't resize an image which has snapshots");
189
- "image read-only.");
488
- return -ENOTSUP;
190
- ret = bdrv_set_read_only(bs, true, errp);
489
+ ret = -ENOTSUP;
191
- if (ret < 0) {
490
+ goto fail;
491
}
492
493
/* cannot proceed if image has bitmaps */
494
if (s->nb_bitmaps) {
495
/* TODO: resize bitmaps in the image */
496
error_setg(errp, "Can't resize an image which has bitmaps");
497
- return -ENOTSUP;
498
+ ret = -ENOTSUP;
499
+ goto fail;
500
}
501
502
old_length = bs->total_sectors * 512;
503
@@ -XXX,XX +XXX,XX @@ static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
504
if (prealloc != PREALLOC_MODE_OFF) {
505
error_setg(errp,
506
"Preallocation can't be used for shrinking an image");
507
- return -EINVAL;
508
+ ret = -EINVAL;
509
+ goto fail;
510
}
511
512
ret = qcow2_cluster_discard(bs, ROUND_UP(offset, s->cluster_size),
513
@@ -XXX,XX +XXX,XX @@ static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
514
QCOW2_DISCARD_ALWAYS, true);
515
if (ret < 0) {
516
error_setg_errno(errp, -ret, "Failed to discard cropped clusters");
517
- return ret;
192
- return ret;
518
+ goto fail;
193
- }
519
}
194
- }
520
195
-
521
ret = qcow2_shrink_l1_table(bs, new_l1_size);
196
block_module_load_one("dmg-bz2");
522
if (ret < 0) {
197
523
error_setg_errno(errp, -ret,
198
s->n_chunks = 0;
524
"Failed to reduce the number of L2 tables");
525
- return ret;
526
+ goto fail;
527
}
528
529
ret = qcow2_shrink_reftable(bs);
530
if (ret < 0) {
531
error_setg_errno(errp, -ret,
532
"Failed to discard unused refblocks");
533
- return ret;
534
+ goto fail;
535
}
536
537
old_file_size = bdrv_getlength(bs->file->bs);
538
if (old_file_size < 0) {
539
error_setg_errno(errp, -old_file_size,
540
"Failed to inquire current file length");
541
- return old_file_size;
542
+ ret = old_file_size;
543
+ goto fail;
544
}
545
last_cluster = qcow2_get_last_cluster(bs, old_file_size);
546
if (last_cluster < 0) {
547
error_setg_errno(errp, -last_cluster,
548
"Failed to find the last cluster");
549
- return last_cluster;
550
+ ret = last_cluster;
551
+ goto fail;
552
}
553
if ((last_cluster + 1) * s->cluster_size < old_file_size) {
554
Error *local_err = NULL;
555
556
- bdrv_truncate(bs->file, (last_cluster + 1) * s->cluster_size,
557
- PREALLOC_MODE_OFF, &local_err);
558
+ bdrv_co_truncate(bs->file, (last_cluster + 1) * s->cluster_size,
559
+ PREALLOC_MODE_OFF, &local_err);
560
if (local_err) {
561
warn_reportf_err(local_err,
562
"Failed to truncate the tail of the image: ");
563
@@ -XXX,XX +XXX,XX @@ static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
564
ret = qcow2_grow_l1_table(bs, new_l1_size, true);
565
if (ret < 0) {
566
error_setg_errno(errp, -ret, "Failed to grow the L1 table");
567
- return ret;
568
+ goto fail;
569
}
570
}
571
572
@@ -XXX,XX +XXX,XX @@ static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
573
ret = preallocate(bs, old_length, offset);
574
if (ret < 0) {
575
error_setg_errno(errp, -ret, "Preallocation failed");
576
- return ret;
577
+ goto fail;
578
}
579
break;
580
581
@@ -XXX,XX +XXX,XX @@ static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
582
if (old_file_size < 0) {
583
error_setg_errno(errp, -old_file_size,
584
"Failed to inquire current file length");
585
- return old_file_size;
586
+ ret = old_file_size;
587
+ goto fail;
588
}
589
old_file_size = ROUND_UP(old_file_size, s->cluster_size);
590
591
@@ -XXX,XX +XXX,XX @@ static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
592
if (allocation_start < 0) {
593
error_setg_errno(errp, -allocation_start,
594
"Failed to resize refcount structures");
595
- return allocation_start;
596
+ ret = allocation_start;
597
+ goto fail;
598
}
599
600
clusters_allocated = qcow2_alloc_clusters_at(bs, allocation_start,
601
@@ -XXX,XX +XXX,XX @@ static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
602
if (clusters_allocated < 0) {
603
error_setg_errno(errp, -clusters_allocated,
604
"Failed to allocate data clusters");
605
- return clusters_allocated;
606
+ ret = clusters_allocated;
607
+ goto fail;
608
}
609
610
assert(clusters_allocated == nb_new_data_clusters);
611
@@ -XXX,XX +XXX,XX @@ static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
612
/* Allocate the data area */
613
new_file_size = allocation_start +
614
nb_new_data_clusters * s->cluster_size;
615
- ret = bdrv_truncate(bs->file, new_file_size, prealloc, errp);
616
+ ret = bdrv_co_truncate(bs->file, new_file_size, prealloc, errp);
617
if (ret < 0) {
618
error_prepend(errp, "Failed to resize underlying file: ");
619
qcow2_free_clusters(bs, allocation_start,
620
nb_new_data_clusters * s->cluster_size,
621
QCOW2_DISCARD_OTHER);
622
- return ret;
623
+ goto fail;
624
}
625
626
/* Create the necessary L2 entries */
627
@@ -XXX,XX +XXX,XX @@ static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
628
qcow2_free_clusters(bs, host_offset,
629
nb_new_data_clusters * s->cluster_size,
630
QCOW2_DISCARD_OTHER);
631
- return ret;
632
+ goto fail;
633
}
634
635
guest_offset += nb_clusters * s->cluster_size;
636
@@ -XXX,XX +XXX,XX @@ static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
637
638
if (prealloc != PREALLOC_MODE_OFF) {
639
/* Flush metadata before actually changing the image size */
640
- ret = bdrv_flush(bs);
641
+ ret = qcow2_write_caches(bs);
642
if (ret < 0) {
643
error_setg_errno(errp, -ret,
644
"Failed to flush the preallocated area to disk");
645
- return ret;
646
+ goto fail;
647
}
648
}
649
650
@@ -XXX,XX +XXX,XX @@ static int qcow2_truncate(BlockDriverState *bs, int64_t offset,
651
&offset, sizeof(uint64_t));
652
if (ret < 0) {
653
error_setg_errno(errp, -ret, "Failed to update the image size");
654
- return ret;
655
+ goto fail;
656
}
657
658
s->l1_vm_state_index = new_l1_size;
659
- return 0;
660
+ ret = 0;
661
+fail:
662
+ qemu_co_mutex_unlock(&s->lock);
663
+ return ret;
664
}
665
666
/* XXX: put compressed sectors first, then all the cluster aligned
667
@@ -XXX,XX +XXX,XX @@ qcow2_co_pwritev_compressed(BlockDriverState *bs, uint64_t offset,
668
if (cluster_offset < 0) {
669
return cluster_offset;
670
}
671
- return bdrv_truncate(bs->file, cluster_offset, PREALLOC_MODE_OFF, NULL);
672
+ return bdrv_co_truncate(bs->file, cluster_offset, PREALLOC_MODE_OFF,
673
+ NULL);
674
}
675
676
if (offset_into_cluster(s, offset)) {
677
@@ -XXX,XX +XXX,XX @@ BlockDriver bdrv_qcow2 = {
678
.bdrv_co_pdiscard = qcow2_co_pdiscard,
679
.bdrv_co_copy_range_from = qcow2_co_copy_range_from,
680
.bdrv_co_copy_range_to = qcow2_co_copy_range_to,
681
- .bdrv_truncate = qcow2_truncate,
682
+ .bdrv_co_truncate = qcow2_co_truncate,
683
.bdrv_co_pwritev_compressed = qcow2_co_pwritev_compressed,
684
.bdrv_make_empty = qcow2_make_empty,
685
686
diff --git a/block/qed.c b/block/qed.c
687
index XXXXXXX..XXXXXXX 100644
688
--- a/block/qed.c
689
+++ b/block/qed.c
690
@@ -XXX,XX +XXX,XX @@ static int coroutine_fn bdrv_qed_co_pwrite_zeroes(BlockDriverState *bs,
691
QED_AIOCB_WRITE | QED_AIOCB_ZERO);
692
}
693
694
-static int bdrv_qed_truncate(BlockDriverState *bs, int64_t offset,
695
- PreallocMode prealloc, Error **errp)
696
+static int coroutine_fn bdrv_qed_co_truncate(BlockDriverState *bs,
697
+ int64_t offset,
698
+ PreallocMode prealloc,
699
+ Error **errp)
700
{
701
BDRVQEDState *s = bs->opaque;
702
uint64_t old_image_size;
703
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_qed = {
704
.bdrv_co_readv = bdrv_qed_co_readv,
705
.bdrv_co_writev = bdrv_qed_co_writev,
706
.bdrv_co_pwrite_zeroes = bdrv_qed_co_pwrite_zeroes,
707
- .bdrv_truncate = bdrv_qed_truncate,
708
+ .bdrv_co_truncate = bdrv_qed_co_truncate,
709
.bdrv_getlength = bdrv_qed_getlength,
710
.bdrv_get_info = bdrv_qed_get_info,
711
.bdrv_refresh_limits = bdrv_qed_refresh_limits,
712
diff --git a/block/raw-format.c b/block/raw-format.c
713
index XXXXXXX..XXXXXXX 100644
714
--- a/block/raw-format.c
715
+++ b/block/raw-format.c
716
@@ -XXX,XX +XXX,XX @@ static void raw_refresh_limits(BlockDriverState *bs, Error **errp)
717
}
718
}
719
720
-static int raw_truncate(BlockDriverState *bs, int64_t offset,
721
- PreallocMode prealloc, Error **errp)
722
+static int coroutine_fn raw_co_truncate(BlockDriverState *bs, int64_t offset,
723
+ PreallocMode prealloc, Error **errp)
724
{
725
BDRVRawState *s = bs->opaque;
726
727
@@ -XXX,XX +XXX,XX @@ static int raw_truncate(BlockDriverState *bs, int64_t offset,
728
729
s->size = offset;
730
offset += s->offset;
731
- return bdrv_truncate(bs->file, offset, prealloc, errp);
732
+ return bdrv_co_truncate(bs->file, offset, prealloc, errp);
733
}
734
735
static void raw_eject(BlockDriverState *bs, bool eject_flag)
736
@@ -XXX,XX +XXX,XX @@ BlockDriver bdrv_raw = {
737
.bdrv_co_block_status = &raw_co_block_status,
738
.bdrv_co_copy_range_from = &raw_co_copy_range_from,
739
.bdrv_co_copy_range_to = &raw_co_copy_range_to,
740
- .bdrv_truncate = &raw_truncate,
741
+ .bdrv_co_truncate = &raw_co_truncate,
742
.bdrv_getlength = &raw_getlength,
743
.has_variable_length = true,
744
.bdrv_measure = &raw_measure,
745
diff --git a/block/rbd.c b/block/rbd.c
199
diff --git a/block/rbd.c b/block/rbd.c
746
index XXXXXXX..XXXXXXX 100644
200
index XXXXXXX..XXXXXXX 100644
747
--- a/block/rbd.c
201
--- a/block/rbd.c
748
+++ b/block/rbd.c
202
+++ b/block/rbd.c
749
@@ -XXX,XX +XXX,XX @@ static int64_t qemu_rbd_getlength(BlockDriverState *bs)
203
@@ -XXX,XX +XXX,XX @@ static int qemu_rbd_open(BlockDriverState *bs, QDict *options, int flags,
750
return info.size;
204
/* If we are using an rbd snapshot, we must be r/o, otherwise
751
}
205
* leave as-is */
752
206
if (s->snap != NULL) {
753
-static int qemu_rbd_truncate(BlockDriverState *bs, int64_t offset,
207
- if (!bdrv_is_read_only(bs)) {
754
- PreallocMode prealloc, Error **errp)
208
- error_report("Opening rbd snapshots without an explicit "
755
+static int coroutine_fn qemu_rbd_co_truncate(BlockDriverState *bs,
209
- "read-only=on option is deprecated. Future versions "
756
+ int64_t offset,
210
- "will refuse to open the image instead of "
757
+ PreallocMode prealloc,
211
- "automatically marking the image read-only.");
758
+ Error **errp)
212
- r = bdrv_set_read_only(bs, true, &local_err);
759
{
213
- if (r < 0) {
760
BDRVRBDState *s = bs->opaque;
214
- rbd_close(s->image);
761
int r;
215
- error_propagate(errp, local_err);
762
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_rbd = {
216
- goto failed_open;
763
.bdrv_get_info = qemu_rbd_getinfo,
217
- }
764
.create_opts = &qemu_rbd_create_opts,
218
+ r = bdrv_apply_auto_read_only(bs, "rbd snapshots are read-only", errp);
765
.bdrv_getlength = qemu_rbd_getlength,
219
+ if (r < 0) {
766
- .bdrv_truncate = qemu_rbd_truncate,
220
+ rbd_close(s->image);
767
+ .bdrv_co_truncate = qemu_rbd_co_truncate,
221
+ goto failed_open;
768
.protocol_name = "rbd",
222
}
769
223
}
770
.bdrv_aio_preadv = qemu_rbd_aio_preadv,
224
771
diff --git a/block/sheepdog.c b/block/sheepdog.c
225
diff --git a/block/vvfat.c b/block/vvfat.c
772
index XXXXXXX..XXXXXXX 100644
226
index XXXXXXX..XXXXXXX 100644
773
--- a/block/sheepdog.c
227
--- a/block/vvfat.c
774
+++ b/block/sheepdog.c
228
+++ b/block/vvfat.c
775
@@ -XXX,XX +XXX,XX @@ static int64_t sd_getlength(BlockDriverState *bs)
229
@@ -XXX,XX +XXX,XX @@ static int vvfat_open(BlockDriverState *bs, QDict *options, int flags,
776
return s->inode.vdi_size;
230
"Unable to set VVFAT to 'rw' when drive is read-only");
777
}
231
goto fail;
778
232
}
779
-static int sd_truncate(BlockDriverState *bs, int64_t offset,
233
- } else if (!bdrv_is_read_only(bs)) {
780
- PreallocMode prealloc, Error **errp)
234
- error_report("Opening non-rw vvfat images without an explicit "
781
+static int coroutine_fn sd_co_truncate(BlockDriverState *bs, int64_t offset,
235
- "read-only=on option is deprecated. Future versions "
782
+ PreallocMode prealloc, Error **errp)
236
- "will refuse to open the image instead of "
783
{
237
- "automatically marking the image read-only.");
784
BDRVSheepdogState *s = bs->opaque;
238
- /* read only is the default for safety */
785
int ret, fd;
239
- ret = bdrv_set_read_only(bs, true, &local_err);
786
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int sd_co_writev(BlockDriverState *bs, int64_t sector_num,
240
+ } else {
787
241
+ ret = bdrv_apply_auto_read_only(bs, NULL, errp);
788
assert(!flags);
789
if (offset > s->inode.vdi_size) {
790
- ret = sd_truncate(bs, offset, PREALLOC_MODE_OFF, NULL);
791
+ ret = sd_co_truncate(bs, offset, PREALLOC_MODE_OFF, NULL);
792
if (ret < 0) {
242
if (ret < 0) {
793
return ret;
243
- error_propagate(errp, local_err);
244
goto fail;
794
}
245
}
795
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_sheepdog = {
246
}
796
.bdrv_has_zero_init = bdrv_has_zero_init_1,
797
.bdrv_getlength = sd_getlength,
798
.bdrv_get_allocated_file_size = sd_get_allocated_file_size,
799
- .bdrv_truncate = sd_truncate,
800
+ .bdrv_co_truncate = sd_co_truncate,
801
802
.bdrv_co_readv = sd_co_readv,
803
.bdrv_co_writev = sd_co_writev,
804
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_sheepdog_tcp = {
805
.bdrv_has_zero_init = bdrv_has_zero_init_1,
806
.bdrv_getlength = sd_getlength,
807
.bdrv_get_allocated_file_size = sd_get_allocated_file_size,
808
- .bdrv_truncate = sd_truncate,
809
+ .bdrv_co_truncate = sd_co_truncate,
810
811
.bdrv_co_readv = sd_co_readv,
812
.bdrv_co_writev = sd_co_writev,
813
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_sheepdog_unix = {
814
.bdrv_has_zero_init = bdrv_has_zero_init_1,
815
.bdrv_getlength = sd_getlength,
816
.bdrv_get_allocated_file_size = sd_get_allocated_file_size,
817
- .bdrv_truncate = sd_truncate,
818
+ .bdrv_co_truncate = sd_co_truncate,
819
820
.bdrv_co_readv = sd_co_readv,
821
.bdrv_co_writev = sd_co_writev,
822
diff --git a/block/ssh.c b/block/ssh.c
823
index XXXXXXX..XXXXXXX 100644
824
--- a/block/ssh.c
825
+++ b/block/ssh.c
826
@@ -XXX,XX +XXX,XX @@ static int64_t ssh_getlength(BlockDriverState *bs)
827
return length;
828
}
829
830
-static int ssh_truncate(BlockDriverState *bs, int64_t offset,
831
- PreallocMode prealloc, Error **errp)
832
+static int coroutine_fn ssh_co_truncate(BlockDriverState *bs, int64_t offset,
833
+ PreallocMode prealloc, Error **errp)
834
{
835
BDRVSSHState *s = bs->opaque;
836
837
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_ssh = {
838
.bdrv_co_readv = ssh_co_readv,
839
.bdrv_co_writev = ssh_co_writev,
840
.bdrv_getlength = ssh_getlength,
841
- .bdrv_truncate = ssh_truncate,
842
+ .bdrv_co_truncate = ssh_co_truncate,
843
.bdrv_co_flush_to_disk = ssh_co_flush,
844
.create_opts = &ssh_create_opts,
845
};
846
--
247
--
847
2.13.6
248
2.19.1
848
249
849
250
diff view generated by jsdifflib
1
Commit abf754fe406 updated 026.out, but forgot to also update
1
If read-only=off, but auto-read-only=on is given, open a read-write NBD
2
026.out.nocache.
2
connection if the server provides a read-write export, but instead of
3
erroring out for read-only exports, just degrade to read-only.
3
4
4
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
5
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
5
Reviewed-by: Max Reitz <mreitz@redhat.com>
6
Reviewed-by: Eric Blake <eblake@redhat.com>
6
---
7
---
7
tests/qemu-iotests/026.out.nocache | 6 +++---
8
block/nbd-client.c | 10 +++++-----
8
1 file changed, 3 insertions(+), 3 deletions(-)
9
1 file changed, 5 insertions(+), 5 deletions(-)
9
10
10
diff --git a/tests/qemu-iotests/026.out.nocache b/tests/qemu-iotests/026.out.nocache
11
diff --git a/block/nbd-client.c b/block/nbd-client.c
11
index XXXXXXX..XXXXXXX 100644
12
index XXXXXXX..XXXXXXX 100644
12
--- a/tests/qemu-iotests/026.out.nocache
13
--- a/block/nbd-client.c
13
+++ b/tests/qemu-iotests/026.out.nocache
14
+++ b/block/nbd-client.c
14
@@ -XXX,XX +XXX,XX @@ Failed to flush the L2 table cache: No space left on device
15
@@ -XXX,XX +XXX,XX @@ int nbd_client_init(BlockDriverState *bs,
15
Failed to flush the refcount block cache: No space left on device
16
logout("Failed to negotiate with the NBD server\n");
16
write failed: No space left on device
17
return ret;
17
18
}
18
-11 leaked clusters were found on the image.
19
- if (client->info.flags & NBD_FLAG_READ_ONLY &&
19
+10 leaked clusters were found on the image.
20
- !bdrv_is_read_only(bs)) {
20
This means waste of disk space, but no harm to data.
21
- error_setg(errp,
21
Formatting 'TEST_DIR/t.IMGFMT', fmt=IMGFMT size=1073741824
22
- "request for write access conflicts with read-only export");
22
23
- return -EACCES;
23
@@ -XXX,XX +XXX,XX @@ Failed to flush the L2 table cache: No space left on device
24
+ if (client->info.flags & NBD_FLAG_READ_ONLY) {
24
Failed to flush the refcount block cache: No space left on device
25
+ ret = bdrv_apply_auto_read_only(bs, "NBD export is read-only", errp);
25
write failed: No space left on device
26
+ if (ret < 0) {
26
27
+ return ret;
27
-11 leaked clusters were found on the image.
28
+ }
28
+10 leaked clusters were found on the image.
29
}
29
This means waste of disk space, but no harm to data.
30
if (client->info.flags & NBD_FLAG_SEND_FUA) {
30
Formatting 'TEST_DIR/t.IMGFMT', fmt=IMGFMT size=1073741824
31
bs->supported_write_flags = BDRV_REQ_FUA;
31
32
@@ -XXX,XX +XXX,XX @@ Failed to flush the L2 table cache: No space left on device
33
Failed to flush the refcount block cache: No space left on device
34
write failed: No space left on device
35
36
-11 leaked clusters were found on the image.
37
+10 leaked clusters were found on the image.
38
This means waste of disk space, but no harm to data.
39
Formatting 'TEST_DIR/t.IMGFMT', fmt=IMGFMT size=1073741824
40
41
--
32
--
42
2.13.6
33
2.19.1
43
34
44
35
diff view generated by jsdifflib
1
This moves the code to resize an image file to the thread pool to avoid
1
If read-only=off, but auto-read-only=on is given, open the file
2
blocking.
2
read-write if we have the permissions, but instead of erroring out for
3
3
read-only files, just degrade to read-only.
4
Creating large images with preallocation with blockdev-create is now
5
actually a background job instead of blocking the monitor (and most
6
other things) until the preallocation has completed.
7
4
8
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
5
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
9
Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
6
Reviewed-by: Eric Blake <eblake@redhat.com>
10
---
7
---
11
include/block/raw-aio.h | 4 +-
8
block/file-posix.c | 19 ++++++++++++++++---
12
block/file-posix.c | 266 +++++++++++++++++++++++++++---------------------
9
1 file changed, 16 insertions(+), 3 deletions(-)
13
2 files changed, 154 insertions(+), 116 deletions(-)
14
10
15
diff --git a/include/block/raw-aio.h b/include/block/raw-aio.h
16
index XXXXXXX..XXXXXXX 100644
17
--- a/include/block/raw-aio.h
18
+++ b/include/block/raw-aio.h
19
@@ -XXX,XX +XXX,XX @@
20
#define QEMU_AIO_DISCARD 0x0010
21
#define QEMU_AIO_WRITE_ZEROES 0x0020
22
#define QEMU_AIO_COPY_RANGE 0x0040
23
+#define QEMU_AIO_TRUNCATE 0x0080
24
#define QEMU_AIO_TYPE_MASK \
25
(QEMU_AIO_READ | \
26
QEMU_AIO_WRITE | \
27
@@ -XXX,XX +XXX,XX @@
28
QEMU_AIO_FLUSH | \
29
QEMU_AIO_DISCARD | \
30
QEMU_AIO_WRITE_ZEROES | \
31
- QEMU_AIO_COPY_RANGE)
32
+ QEMU_AIO_COPY_RANGE | \
33
+ QEMU_AIO_TRUNCATE)
34
35
/* AIO flags */
36
#define QEMU_AIO_MISALIGNED 0x1000
37
diff --git a/block/file-posix.c b/block/file-posix.c
11
diff --git a/block/file-posix.c b/block/file-posix.c
38
index XXXXXXX..XXXXXXX 100644
12
index XXXXXXX..XXXXXXX 100644
39
--- a/block/file-posix.c
13
--- a/block/file-posix.c
40
+++ b/block/file-posix.c
14
+++ b/block/file-posix.c
41
@@ -XXX,XX +XXX,XX @@ typedef struct RawPosixAIOData {
15
@@ -XXX,XX +XXX,XX @@ static int raw_open_common(BlockDriverState *bs, QDict *options,
42
#define aio_ioctl_cmd aio_nbytes /* for QEMU_AIO_IOCTL */
16
43
off_t aio_offset;
17
s->fd = -1;
44
int aio_type;
18
fd = qemu_open(filename, s->open_flags, 0644);
45
- int aio_fd2;
19
- if (fd < 0) {
46
- off_t aio_offset2;
20
- ret = -errno;
47
+ union {
21
- error_setg_errno(errp, errno, "Could not open '%s'", filename);
48
+ struct {
22
+ ret = fd < 0 ? -errno : 0;
49
+ int aio_fd2;
50
+ off_t aio_offset2;
51
+ };
52
+ struct {
53
+ PreallocMode prealloc;
54
+ Error **errp;
55
+ };
56
+ };
57
} RawPosixAIOData;
58
59
#if defined(__FreeBSD__) || defined(__FreeBSD_kernel__)
60
@@ -XXX,XX +XXX,XX @@ static ssize_t handle_aiocb_discard(RawPosixAIOData *aiocb)
61
return ret;
62
}
63
64
+static int handle_aiocb_truncate(RawPosixAIOData *aiocb)
65
+{
66
+ int result = 0;
67
+ int64_t current_length = 0;
68
+ char *buf = NULL;
69
+ struct stat st;
70
+ int fd = aiocb->aio_fildes;
71
+ int64_t offset = aiocb->aio_offset;
72
+ Error **errp = aiocb->errp;
73
+
23
+
74
+ if (fstat(fd, &st) < 0) {
24
+ if (ret == -EACCES || ret == -EROFS) {
75
+ result = -errno;
25
+ /* Try to degrade to read-only, but if it doesn't work, still use the
76
+ error_setg_errno(errp, -result, "Could not stat file");
26
+ * normal error message. */
77
+ return result;
27
+ if (bdrv_apply_auto_read_only(bs, NULL, NULL) == 0) {
78
+ }
28
+ bdrv_flags &= ~BDRV_O_RDWR;
79
+
29
+ raw_parse_flags(bdrv_flags, &s->open_flags);
80
+ current_length = st.st_size;
30
+ assert(!(s->open_flags & O_CREAT));
81
+ if (current_length > offset && aiocb->prealloc != PREALLOC_MODE_OFF) {
31
+ fd = qemu_open(filename, s->open_flags);
82
+ error_setg(errp, "Cannot use preallocation for shrinking files");
32
+ ret = fd < 0 ? -errno : 0;
83
+ return -ENOTSUP;
84
+ }
85
+
86
+ switch (aiocb->prealloc) {
87
+#ifdef CONFIG_POSIX_FALLOCATE
88
+ case PREALLOC_MODE_FALLOC:
89
+ /*
90
+ * Truncating before posix_fallocate() makes it about twice slower on
91
+ * file systems that do not support fallocate(), trying to check if a
92
+ * block is allocated before allocating it, so don't do that here.
93
+ */
94
+ if (offset != current_length) {
95
+ result = -posix_fallocate(fd, current_length,
96
+ offset - current_length);
97
+ if (result != 0) {
98
+ /* posix_fallocate() doesn't set errno. */
99
+ error_setg_errno(errp, -result,
100
+ "Could not preallocate new data");
101
+ }
102
+ } else {
103
+ result = 0;
104
+ }
105
+ goto out;
106
+#endif
107
+ case PREALLOC_MODE_FULL:
108
+ {
109
+ int64_t num = 0, left = offset - current_length;
110
+ off_t seek_result;
111
+
112
+ /*
113
+ * Knowing the final size from the beginning could allow the file
114
+ * system driver to do less allocations and possibly avoid
115
+ * fragmentation of the file.
116
+ */
117
+ if (ftruncate(fd, offset) != 0) {
118
+ result = -errno;
119
+ error_setg_errno(errp, -result, "Could not resize file");
120
+ goto out;
121
+ }
122
+
123
+ buf = g_malloc0(65536);
124
+
125
+ seek_result = lseek(fd, current_length, SEEK_SET);
126
+ if (seek_result < 0) {
127
+ result = -errno;
128
+ error_setg_errno(errp, -result,
129
+ "Failed to seek to the old end of file");
130
+ goto out;
131
+ }
132
+
133
+ while (left > 0) {
134
+ num = MIN(left, 65536);
135
+ result = write(fd, buf, num);
136
+ if (result < 0) {
137
+ result = -errno;
138
+ error_setg_errno(errp, -result,
139
+ "Could not write zeros for preallocation");
140
+ goto out;
141
+ }
142
+ left -= result;
143
+ }
144
+ if (result >= 0) {
145
+ result = fsync(fd);
146
+ if (result < 0) {
147
+ result = -errno;
148
+ error_setg_errno(errp, -result,
149
+ "Could not flush file to disk");
150
+ goto out;
151
+ }
152
+ }
153
+ goto out;
154
+ }
155
+ case PREALLOC_MODE_OFF:
156
+ if (ftruncate(fd, offset) != 0) {
157
+ result = -errno;
158
+ error_setg_errno(errp, -result, "Could not resize file");
159
+ }
160
+ return result;
161
+ default:
162
+ result = -ENOTSUP;
163
+ error_setg(errp, "Unsupported preallocation mode: %s",
164
+ PreallocMode_str(aiocb->prealloc));
165
+ return result;
166
+ }
167
+
168
+out:
169
+ if (result < 0) {
170
+ if (ftruncate(fd, current_length) < 0) {
171
+ error_report("Failed to restore old file length: %s",
172
+ strerror(errno));
173
+ }
33
+ }
174
+ }
34
+ }
175
+
35
+
176
+ g_free(buf);
36
+ if (ret < 0) {
177
+ return result;
37
+ error_setg_errno(errp, -ret, "Could not open '%s'", filename);
178
+}
38
if (ret == -EROFS) {
179
+
39
ret = -EACCES;
180
static int aio_worker(void *arg)
40
}
181
{
182
RawPosixAIOData *aiocb = arg;
183
@@ -XXX,XX +XXX,XX @@ static int aio_worker(void *arg)
184
case QEMU_AIO_COPY_RANGE:
185
ret = handle_aiocb_copy_range(aiocb);
186
break;
187
+ case QEMU_AIO_TRUNCATE:
188
+ ret = handle_aiocb_truncate(aiocb);
189
+ break;
190
default:
191
fprintf(stderr, "invalid aio request (0x%x)\n", aiocb->aio_type);
192
ret = -EINVAL;
193
@@ -XXX,XX +XXX,XX @@ static void raw_close(BlockDriverState *bs)
194
*
195
* Returns: 0 on success, -errno on failure.
196
*/
197
-static int raw_regular_truncate(int fd, int64_t offset, PreallocMode prealloc,
198
- Error **errp)
199
+static int coroutine_fn
200
+raw_regular_truncate(BlockDriverState *bs, int fd, int64_t offset,
201
+ PreallocMode prealloc, Error **errp)
202
{
203
- int result = 0;
204
- int64_t current_length = 0;
205
- char *buf = NULL;
206
- struct stat st;
207
-
208
- if (fstat(fd, &st) < 0) {
209
- result = -errno;
210
- error_setg_errno(errp, -result, "Could not stat file");
211
- return result;
212
- }
213
-
214
- current_length = st.st_size;
215
- if (current_length > offset && prealloc != PREALLOC_MODE_OFF) {
216
- error_setg(errp, "Cannot use preallocation for shrinking files");
217
- return -ENOTSUP;
218
- }
219
-
220
- switch (prealloc) {
221
-#ifdef CONFIG_POSIX_FALLOCATE
222
- case PREALLOC_MODE_FALLOC:
223
- /*
224
- * Truncating before posix_fallocate() makes it about twice slower on
225
- * file systems that do not support fallocate(), trying to check if a
226
- * block is allocated before allocating it, so don't do that here.
227
- */
228
- if (offset != current_length) {
229
- result = -posix_fallocate(fd, current_length, offset - current_length);
230
- if (result != 0) {
231
- /* posix_fallocate() doesn't set errno. */
232
- error_setg_errno(errp, -result,
233
- "Could not preallocate new data");
234
- }
235
- } else {
236
- result = 0;
237
- }
238
- goto out;
239
-#endif
240
- case PREALLOC_MODE_FULL:
241
- {
242
- int64_t num = 0, left = offset - current_length;
243
- off_t seek_result;
244
-
245
- /*
246
- * Knowing the final size from the beginning could allow the file
247
- * system driver to do less allocations and possibly avoid
248
- * fragmentation of the file.
249
- */
250
- if (ftruncate(fd, offset) != 0) {
251
- result = -errno;
252
- error_setg_errno(errp, -result, "Could not resize file");
253
- goto out;
254
- }
255
-
256
- buf = g_malloc0(65536);
257
-
258
- seek_result = lseek(fd, current_length, SEEK_SET);
259
- if (seek_result < 0) {
260
- result = -errno;
261
- error_setg_errno(errp, -result,
262
- "Failed to seek to the old end of file");
263
- goto out;
264
- }
265
-
266
- while (left > 0) {
267
- num = MIN(left, 65536);
268
- result = write(fd, buf, num);
269
- if (result < 0) {
270
- result = -errno;
271
- error_setg_errno(errp, -result,
272
- "Could not write zeros for preallocation");
273
- goto out;
274
- }
275
- left -= result;
276
- }
277
- if (result >= 0) {
278
- result = fsync(fd);
279
- if (result < 0) {
280
- result = -errno;
281
- error_setg_errno(errp, -result,
282
- "Could not flush file to disk");
283
- goto out;
284
- }
285
- }
286
- goto out;
287
- }
288
- case PREALLOC_MODE_OFF:
289
- if (ftruncate(fd, offset) != 0) {
290
- result = -errno;
291
- error_setg_errno(errp, -result, "Could not resize file");
292
- }
293
- return result;
294
- default:
295
- result = -ENOTSUP;
296
- error_setg(errp, "Unsupported preallocation mode: %s",
297
- PreallocMode_str(prealloc));
298
- return result;
299
- }
300
+ RawPosixAIOData *acb = g_new(RawPosixAIOData, 1);
301
+ ThreadPool *pool;
302
303
-out:
304
- if (result < 0) {
305
- if (ftruncate(fd, current_length) < 0) {
306
- error_report("Failed to restore old file length: %s",
307
- strerror(errno));
308
- }
309
- }
310
+ *acb = (RawPosixAIOData) {
311
+ .bs = bs,
312
+ .aio_fildes = fd,
313
+ .aio_type = QEMU_AIO_TRUNCATE,
314
+ .aio_offset = offset,
315
+ .prealloc = prealloc,
316
+ .errp = errp,
317
+ };
318
319
- g_free(buf);
320
- return result;
321
+ /* @bs can be NULL, bdrv_get_aio_context() returns the main context then */
322
+ pool = aio_get_thread_pool(bdrv_get_aio_context(bs));
323
+ return thread_pool_submit_co(pool, aio_worker, acb);
324
}
325
326
static int coroutine_fn raw_co_truncate(BlockDriverState *bs, int64_t offset,
327
@@ -XXX,XX +XXX,XX @@ static int coroutine_fn raw_co_truncate(BlockDriverState *bs, int64_t offset,
328
}
329
330
if (S_ISREG(st.st_mode)) {
331
- return raw_regular_truncate(s->fd, offset, prealloc, errp);
332
+ return raw_regular_truncate(bs, s->fd, offset, prealloc, errp);
333
}
334
335
if (prealloc != PREALLOC_MODE_OFF) {
336
@@ -XXX,XX +XXX,XX @@ static int64_t raw_get_allocated_file_size(BlockDriverState *bs)
337
return (int64_t)st.st_blocks * 512;
338
}
339
340
-static int raw_co_create(BlockdevCreateOptions *options, Error **errp)
341
+static int coroutine_fn
342
+raw_co_create(BlockdevCreateOptions *options, Error **errp)
343
{
344
BlockdevCreateOptionsFile *file_opts;
345
int fd;
346
@@ -XXX,XX +XXX,XX @@ static int raw_co_create(BlockdevCreateOptions *options, Error **errp)
347
}
348
349
/* Clear the file by truncating it to 0 */
350
- result = raw_regular_truncate(fd, 0, PREALLOC_MODE_OFF, errp);
351
+ result = raw_regular_truncate(NULL, fd, 0, PREALLOC_MODE_OFF, errp);
352
if (result < 0) {
353
goto out_close;
354
}
355
@@ -XXX,XX +XXX,XX @@ static int raw_co_create(BlockdevCreateOptions *options, Error **errp)
356
357
/* Resize and potentially preallocate the file to the desired
358
* final size */
359
- result = raw_regular_truncate(fd, file_opts->size, file_opts->preallocation,
360
- errp);
361
+ result = raw_regular_truncate(NULL, fd, file_opts->size,
362
+ file_opts->preallocation, errp);
363
if (result < 0) {
364
goto out_close;
365
}
366
--
41
--
367
2.13.6
42
2.19.1
368
43
369
44
diff view generated by jsdifflib
1
This simplifies file-posix by implementing the coroutine variants of
1
If read-only=off, but auto-read-only=on is given, just degrade to
2
the discard and flush BlockDriver callbacks. These were the last
2
read-only.
3
remaining users of paio_submit(), which can be removed now.
4
3
5
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
4
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
6
Reviewed-by: Eric Blake <eblake@redhat.com>
5
Reviewed-by: Eric Blake <eblake@redhat.com>
7
---
6
---
8
block/file-posix.c | 72 ++++++++++++++++++------------------------------------
7
block/curl.c | 8 ++++----
9
1 file changed, 24 insertions(+), 48 deletions(-)
8
1 file changed, 4 insertions(+), 4 deletions(-)
10
9
11
diff --git a/block/file-posix.c b/block/file-posix.c
10
diff --git a/block/curl.c b/block/curl.c
12
index XXXXXXX..XXXXXXX 100644
11
index XXXXXXX..XXXXXXX 100644
13
--- a/block/file-posix.c
12
--- a/block/curl.c
14
+++ b/block/file-posix.c
13
+++ b/block/curl.c
15
@@ -XXX,XX +XXX,XX @@ static inline int paio_submit_co(BlockDriverState *bs, int fd,
14
@@ -XXX,XX +XXX,XX @@ static int curl_open(BlockDriverState *bs, QDict *options, int flags,
16
return paio_submit_co_full(bs, fd, offset, -1, 0, qiov, bytes, type);
15
const char *protocol_delimiter;
17
}
16
int ret;
18
17
19
-static BlockAIOCB *paio_submit(BlockDriverState *bs, int fd,
20
- int64_t offset, QEMUIOVector *qiov, int bytes,
21
- BlockCompletionFunc *cb, void *opaque, int type)
22
-{
23
- RawPosixAIOData *acb = g_new(RawPosixAIOData, 1);
24
- ThreadPool *pool;
25
-
18
-
26
- acb->bs = bs;
19
- if (flags & BDRV_O_RDWR) {
27
- acb->aio_type = type;
20
- error_setg(errp, "curl block device does not support writes");
28
- acb->aio_fildes = fd;
21
- return -EROFS;
29
-
22
+ ret = bdrv_apply_auto_read_only(bs, "curl driver does not support writes",
30
- acb->aio_nbytes = bytes;
23
+ errp);
31
- acb->aio_offset = offset;
32
-
33
- if (qiov) {
34
- acb->aio_iov = qiov->iov;
35
- acb->aio_niov = qiov->niov;
36
- assert(qiov->size == acb->aio_nbytes);
37
- }
38
-
39
- trace_paio_submit(acb, opaque, offset, bytes, type);
40
- pool = aio_get_thread_pool(bdrv_get_aio_context(bs));
41
- return thread_pool_submit_aio(pool, aio_worker, acb, cb, opaque);
42
-}
43
-
44
static int coroutine_fn raw_co_prw(BlockDriverState *bs, uint64_t offset,
45
uint64_t bytes, QEMUIOVector *qiov, int type)
46
{
47
@@ -XXX,XX +XXX,XX @@ static void raw_aio_unplug(BlockDriverState *bs)
48
#endif
49
}
50
51
-static BlockAIOCB *raw_aio_flush(BlockDriverState *bs,
52
- BlockCompletionFunc *cb, void *opaque)
53
+static int raw_co_flush_to_disk(BlockDriverState *bs)
54
{
55
BDRVRawState *s = bs->opaque;
56
+ int ret;
57
58
- if (fd_open(bs) < 0)
59
- return NULL;
60
+ ret = fd_open(bs);
61
+ if (ret < 0) {
62
+ return ret;
63
+ }
64
65
- return paio_submit(bs, s->fd, 0, NULL, 0, cb, opaque, QEMU_AIO_FLUSH);
66
+ return paio_submit_co(bs, s->fd, 0, NULL, 0, QEMU_AIO_FLUSH);
67
}
68
69
static void raw_aio_attach_aio_context(BlockDriverState *bs,
70
@@ -XXX,XX +XXX,XX @@ static void coroutine_fn raw_co_invalidate_cache(BlockDriverState *bs,
71
#endif /* !__linux__ */
72
}
73
74
-static coroutine_fn BlockAIOCB *raw_aio_pdiscard(BlockDriverState *bs,
75
- int64_t offset, int bytes,
76
- BlockCompletionFunc *cb, void *opaque)
77
+static coroutine_fn int
78
+raw_co_pdiscard(BlockDriverState *bs, int64_t offset, int bytes)
79
{
80
BDRVRawState *s = bs->opaque;
81
82
- return paio_submit(bs, s->fd, offset, NULL, bytes,
83
- cb, opaque, QEMU_AIO_DISCARD);
84
+ return paio_submit_co(bs, s->fd, offset, NULL, bytes, QEMU_AIO_DISCARD);
85
}
86
87
static int coroutine_fn raw_co_pwrite_zeroes(
88
@@ -XXX,XX +XXX,XX @@ BlockDriver bdrv_file = {
89
90
.bdrv_co_preadv = raw_co_preadv,
91
.bdrv_co_pwritev = raw_co_pwritev,
92
- .bdrv_aio_flush = raw_aio_flush,
93
- .bdrv_aio_pdiscard = raw_aio_pdiscard,
94
+ .bdrv_co_flush_to_disk = raw_co_flush_to_disk,
95
+ .bdrv_co_pdiscard = raw_co_pdiscard,
96
.bdrv_co_copy_range_from = raw_co_copy_range_from,
97
.bdrv_co_copy_range_to = raw_co_copy_range_to,
98
.bdrv_refresh_limits = raw_refresh_limits,
99
@@ -XXX,XX +XXX,XX @@ static int fd_open(BlockDriverState *bs)
100
return -EIO;
101
}
102
103
-static coroutine_fn BlockAIOCB *hdev_aio_pdiscard(BlockDriverState *bs,
104
- int64_t offset, int bytes,
105
- BlockCompletionFunc *cb, void *opaque)
106
+static coroutine_fn int
107
+hdev_co_pdiscard(BlockDriverState *bs, int64_t offset, int bytes)
108
{
109
BDRVRawState *s = bs->opaque;
110
+ int ret;
111
112
- if (fd_open(bs) < 0) {
113
- return NULL;
114
+ ret = fd_open(bs);
115
+ if (ret < 0) {
24
+ if (ret < 0) {
116
+ return ret;
25
+ return ret;
117
}
26
}
118
- return paio_submit(bs, s->fd, offset, NULL, bytes,
27
119
- cb, opaque, QEMU_AIO_DISCARD|QEMU_AIO_BLKDEV);
28
if (!libcurl_initialized) {
120
+ return paio_submit_co(bs, s->fd, offset, NULL, bytes,
121
+ QEMU_AIO_DISCARD | QEMU_AIO_BLKDEV);
122
}
123
124
static coroutine_fn int hdev_co_pwrite_zeroes(BlockDriverState *bs,
125
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_host_device = {
126
127
.bdrv_co_preadv = raw_co_preadv,
128
.bdrv_co_pwritev = raw_co_pwritev,
129
- .bdrv_aio_flush    = raw_aio_flush,
130
- .bdrv_aio_pdiscard = hdev_aio_pdiscard,
131
+ .bdrv_co_flush_to_disk = raw_co_flush_to_disk,
132
+ .bdrv_co_pdiscard = hdev_co_pdiscard,
133
.bdrv_co_copy_range_from = raw_co_copy_range_from,
134
.bdrv_co_copy_range_to = raw_co_copy_range_to,
135
.bdrv_refresh_limits = raw_refresh_limits,
136
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_host_cdrom = {
137
138
.bdrv_co_preadv = raw_co_preadv,
139
.bdrv_co_pwritev = raw_co_pwritev,
140
- .bdrv_aio_flush    = raw_aio_flush,
141
+ .bdrv_co_flush_to_disk = raw_co_flush_to_disk,
142
.bdrv_refresh_limits = raw_refresh_limits,
143
.bdrv_io_plug = raw_aio_plug,
144
.bdrv_io_unplug = raw_aio_unplug,
145
@@ -XXX,XX +XXX,XX @@ static BlockDriver bdrv_host_cdrom = {
146
147
.bdrv_co_preadv = raw_co_preadv,
148
.bdrv_co_pwritev = raw_co_pwritev,
149
- .bdrv_aio_flush    = raw_aio_flush,
150
+ .bdrv_co_flush_to_disk = raw_co_flush_to_disk,
151
.bdrv_refresh_limits = raw_refresh_limits,
152
.bdrv_io_plug = raw_aio_plug,
153
.bdrv_io_unplug = raw_aio_unplug,
154
--
29
--
155
2.13.6
30
2.19.1
156
31
157
32
diff view generated by jsdifflib
1
The error handling policy was traditionally set with -drive, but with
1
If read-only=off, but auto-read-only=on is given, open the file
2
-blockdev it is no longer possible to set frontend options. scsi-disk
2
read-write if we have the permissions, but instead of erroring out for
3
(and other block devices) have long supported qdev properties to
3
read-only files, just degrade to read-only.
4
configure the error handling policy, so let's add these options to
5
usb-storage as well and just forward them to the internal scsi-disk
6
instance.
7
4
8
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
5
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
9
Reviewed-by: Markus Armbruster <armbru@redhat.com>
6
Reviewed-by: Niels de Vos <ndevos@redhat.com>
10
---
7
---
11
include/hw/scsi/scsi.h | 2 ++
8
block/gluster.c | 12 ++++++++++--
12
hw/scsi/scsi-bus.c | 11 ++++++++++-
9
1 file changed, 10 insertions(+), 2 deletions(-)
13
hw/usb/dev-storage.c | 2 ++
14
3 files changed, 14 insertions(+), 1 deletion(-)
15
10
16
diff --git a/include/hw/scsi/scsi.h b/include/hw/scsi/scsi.h
11
diff --git a/block/gluster.c b/block/gluster.c
17
index XXXXXXX..XXXXXXX 100644
12
index XXXXXXX..XXXXXXX 100644
18
--- a/include/hw/scsi/scsi.h
13
--- a/block/gluster.c
19
+++ b/include/hw/scsi/scsi.h
14
+++ b/block/gluster.c
20
@@ -XXX,XX +XXX,XX @@ static inline SCSIBus *scsi_bus_from_device(SCSIDevice *d)
15
@@ -XXX,XX +XXX,XX @@ static int qemu_gluster_open(BlockDriverState *bs, QDict *options,
21
SCSIDevice *scsi_bus_legacy_add_drive(SCSIBus *bus, BlockBackend *blk,
16
qemu_gluster_parse_flags(bdrv_flags, &open_flags);
22
int unit, bool removable, int bootindex,
17
23
bool share_rw,
18
s->fd = glfs_open(s->glfs, gconf->path, open_flags);
24
+ BlockdevOnError rerror,
19
- if (!s->fd) {
25
+ BlockdevOnError werror,
20
- ret = -errno;
26
const char *serial, Error **errp);
21
+ ret = s->fd ? 0 : -errno;
27
void scsi_bus_legacy_handle_cmdline(SCSIBus *bus);
22
+
28
void scsi_legacy_handle_cmdline(void);
23
+ if (ret == -EACCES || ret == -EROFS) {
29
diff --git a/hw/scsi/scsi-bus.c b/hw/scsi/scsi-bus.c
24
+ /* Try to degrade to read-only, but if it doesn't work, still use the
30
index XXXXXXX..XXXXXXX 100644
25
+ * normal error message. */
31
--- a/hw/scsi/scsi-bus.c
26
+ if (bdrv_apply_auto_read_only(bs, NULL, NULL) == 0) {
32
+++ b/hw/scsi/scsi-bus.c
27
+ open_flags = (open_flags & ~O_RDWR) | O_RDONLY;
33
@@ -XXX,XX +XXX,XX @@ static void scsi_qdev_unrealize(DeviceState *qdev, Error **errp)
28
+ s->fd = glfs_open(s->glfs, gconf->path, open_flags);
34
SCSIDevice *scsi_bus_legacy_add_drive(SCSIBus *bus, BlockBackend *blk,
29
+ ret = s->fd ? 0 : -errno;
35
int unit, bool removable, int bootindex,
30
+ }
36
bool share_rw,
37
+ BlockdevOnError rerror,
38
+ BlockdevOnError werror,
39
const char *serial, Error **errp)
40
{
41
const char *driver;
42
@@ -XXX,XX +XXX,XX @@ SCSIDevice *scsi_bus_legacy_add_drive(SCSIBus *bus, BlockBackend *blk,
43
object_unparent(OBJECT(dev));
44
return NULL;
45
}
31
}
46
+
32
47
+ qdev_prop_set_enum(dev, "rerror", rerror);
33
s->supports_seek_data = qemu_gluster_test_seek(s->fd);
48
+ qdev_prop_set_enum(dev, "werror", werror);
49
+
50
object_property_set_bool(OBJECT(dev), true, "realized", &err);
51
if (err != NULL) {
52
error_propagate(errp, err);
53
@@ -XXX,XX +XXX,XX @@ void scsi_bus_legacy_handle_cmdline(SCSIBus *bus)
54
}
55
qemu_opts_loc_restore(dinfo->opts);
56
scsi_bus_legacy_add_drive(bus, blk_by_legacy_dinfo(dinfo),
57
- unit, false, -1, false, NULL, &error_fatal);
58
+ unit, false, -1, false,
59
+ BLOCKDEV_ON_ERROR_AUTO,
60
+ BLOCKDEV_ON_ERROR_AUTO,
61
+ NULL, &error_fatal);
62
}
63
loc_pop(&loc);
64
}
65
diff --git a/hw/usb/dev-storage.c b/hw/usb/dev-storage.c
66
index XXXXXXX..XXXXXXX 100644
67
--- a/hw/usb/dev-storage.c
68
+++ b/hw/usb/dev-storage.c
69
@@ -XXX,XX +XXX,XX @@ static void usb_msd_storage_realize(USBDevice *dev, Error **errp)
70
&usb_msd_scsi_info_storage, NULL);
71
scsi_dev = scsi_bus_legacy_add_drive(&s->bus, blk, 0, !!s->removable,
72
s->conf.bootindex, s->conf.share_rw,
73
+ s->conf.rerror, s->conf.werror,
74
dev->serial,
75
errp);
76
blk_unref(blk);
77
@@ -XXX,XX +XXX,XX @@ static const VMStateDescription vmstate_usb_msd = {
78
79
static Property msd_properties[] = {
80
DEFINE_BLOCK_PROPERTIES(MSDState, conf),
81
+ DEFINE_BLOCK_ERROR_PROPERTIES(MSDState, conf),
82
DEFINE_PROP_BIT("removable", MSDState, removable, 0, false),
83
DEFINE_PROP_END_OF_LIST(),
84
};
85
--
34
--
86
2.13.6
35
2.19.1
87
36
88
37
diff view generated by jsdifflib
1
From: Fam Zheng <famz@redhat.com>
1
If read-only=off, but auto-read-only=on is given, open the volume
2
read-write if we have the permissions, but instead of erroring out for
3
read-only volumes, just degrade to read-only.
2
4
3
Per SCSI definition the designator_length we receive from INQUIRY is 8,
4
12 or at most 16, but we should be careful because the remote iscsi
5
target may misbehave, otherwise we could have a buffer overflow.
6
7
Reported-by: Max Reitz <mreitz@redhat.com>
8
Signed-off-by: Fam Zheng <famz@redhat.com>
9
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
5
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
6
Reviewed-by: Eric Blake <eblake@redhat.com>
10
---
7
---
11
block/iscsi.c | 2 +-
8
block/iscsi.c | 8 +++++---
12
1 file changed, 1 insertion(+), 1 deletion(-)
9
1 file changed, 5 insertions(+), 3 deletions(-)
13
10
14
diff --git a/block/iscsi.c b/block/iscsi.c
11
diff --git a/block/iscsi.c b/block/iscsi.c
15
index XXXXXXX..XXXXXXX 100644
12
index XXXXXXX..XXXXXXX 100644
16
--- a/block/iscsi.c
13
--- a/block/iscsi.c
17
+++ b/block/iscsi.c
14
+++ b/block/iscsi.c
18
@@ -XXX,XX +XXX,XX @@ static void iscsi_populate_target_desc(unsigned char *desc, IscsiLun *lun)
15
@@ -XXX,XX +XXX,XX @@ static int iscsi_open(BlockDriverState *bs, QDict *options, int flags,
19
desc[5] = (dd->designator_type & 0xF)
16
/* Check the write protect flag of the LUN if we want to write */
20
| ((dd->association & 3) << 4);
17
if (iscsilun->type == TYPE_DISK && (flags & BDRV_O_RDWR) &&
21
desc[7] = dd->designator_length;
18
iscsilun->write_protected) {
22
- memcpy(desc + 8, dd->designator, dd->designator_length);
19
- error_setg(errp, "Cannot open a write protected LUN as read-write");
23
+ memcpy(desc + 8, dd->designator, MIN(dd->designator_length, 20));
20
- ret = -EACCES;
24
21
- goto out;
25
desc[28] = 0;
22
+ ret = bdrv_apply_auto_read_only(bs, "LUN is write protected", errp);
26
desc[29] = (lun->block_size >> 16) & 0xFF;
23
+ if (ret < 0) {
24
+ goto out;
25
+ }
26
+ flags &= ~BDRV_O_RDWR;
27
}
28
29
iscsi_readcapacity_sync(iscsilun, &local_err);
27
--
30
--
28
2.13.6
31
2.19.1
29
32
30
33
diff view generated by jsdifflib
1
Commit 51f63ec7d tried to change all references to 2.13 into 3.0, but
1
While we want machine interfaces like -blockdev and QMP blockdev-add to
2
it failed to achieve this because it was not properly rebased on top of
2
add as little auto-detection as possible so that management tools are
3
the series introducing qapi/job.json. Change the references now.
3
explicit about their needs, -drive is a convenience option for human
4
users. Enabling auto-read-only=on by default there enables users to use
5
read-only images for read-only guest devices without having to specify
6
read-only=on explicitly. If they try to attach the image to a read-write
7
device, they will still get an error message.
4
8
5
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
9
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
6
Reviewed-by: Markus Armbruster <armbru@redhat.com>
7
Reviewed-by: Eric Blake <eblake@redhat.com>
10
Reviewed-by: Eric Blake <eblake@redhat.com>
8
---
11
---
9
qapi/job.json | 18 +++++++++---------
12
blockdev.c | 1 +
10
1 file changed, 9 insertions(+), 9 deletions(-)
13
1 file changed, 1 insertion(+)
11
14
12
diff --git a/qapi/job.json b/qapi/job.json
15
diff --git a/blockdev.c b/blockdev.c
13
index XXXXXXX..XXXXXXX 100644
16
index XXXXXXX..XXXXXXX 100644
14
--- a/qapi/job.json
17
--- a/blockdev.c
15
+++ b/qapi/job.json
18
+++ b/blockdev.c
16
@@ -XXX,XX +XXX,XX @@
19
@@ -XXX,XX +XXX,XX @@ static BlockBackend *blockdev_init(const char *file, QDict *bs_opts,
17
# @id: The job identifier
20
qdict_set_default_str(bs_opts, BDRV_OPT_CACHE_NO_FLUSH, "off");
18
# @status: The new job status
21
qdict_set_default_str(bs_opts, BDRV_OPT_READ_ONLY,
19
#
22
read_only ? "on" : "off");
20
-# Since: 2.13
23
+ qdict_set_default_str(bs_opts, BDRV_OPT_AUTO_READ_ONLY, "on");
21
+# Since: 3.0
24
assert((bdrv_flags & BDRV_O_CACHE_MASK) == 0);
22
##
25
23
{ 'event': 'JOB_STATUS_CHANGE',
26
if (runstate_check(RUN_STATE_INMIGRATE)) {
24
'data': { 'id': 'str',
25
@@ -XXX,XX +XXX,XX @@
26
#
27
# @id: The job identifier.
28
#
29
-# Since: 2.13
30
+# Since: 3.0
31
##
32
{ 'command': 'job-pause', 'data': { 'id': 'str' } }
33
34
@@ -XXX,XX +XXX,XX @@
35
#
36
# @id : The job identifier.
37
#
38
-# Since: 2.13
39
+# Since: 3.0
40
##
41
{ 'command': 'job-resume', 'data': { 'id': 'str' } }
42
43
@@ -XXX,XX +XXX,XX @@
44
#
45
# @id: The job identifier.
46
#
47
-# Since: 2.13
48
+# Since: 3.0
49
##
50
{ 'command': 'job-cancel', 'data': { 'id': 'str' } }
51
52
@@ -XXX,XX +XXX,XX @@
53
#
54
# @id: The job identifier.
55
#
56
-# Since: 2.13
57
+# Since: 3.0
58
##
59
{ 'command': 'job-complete', 'data': { 'id': 'str' } }
60
61
@@ -XXX,XX +XXX,XX @@
62
#
63
# @id: The job identifier.
64
#
65
-# Since: 2.13
66
+# Since: 3.0
67
##
68
{ 'command': 'job-dismiss', 'data': { 'id': 'str' } }
69
70
@@ -XXX,XX +XXX,XX @@
71
# @id: The identifier of any job in the transaction, or of a job that is not
72
# part of any transaction.
73
#
74
-# Since: 2.13
75
+# Since: 3.0
76
##
77
{ 'command': 'job-finalize', 'data': { 'id': 'str' } }
78
79
@@ -XXX,XX +XXX,XX @@
80
# the reason for the job failure. It should not be parsed
81
# by applications.
82
#
83
-# Since: 2.13
84
+# Since: 3.0
85
##
86
{ 'struct': 'JobInfo',
87
'data': { 'id': 'str', 'type': 'JobType', 'status': 'JobStatus',
88
@@ -XXX,XX +XXX,XX @@
89
#
90
# Returns: a list with a @JobInfo for each active job
91
#
92
-# Since: 2.13
93
+# Since: 3.0
94
##
95
{ 'command': 'query-jobs', 'returns': ['JobInfo'] }
96
--
27
--
97
2.13.6
28
2.19.1
98
29
99
30
diff view generated by jsdifflib
New patch
1
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
2
Reviewed-by: Eric Blake <eblake@redhat.com>
3
---
4
tests/qemu-iotests/232 | 147 +++++++++++++++++++++++++++++++++++++
5
tests/qemu-iotests/232.out | 59 +++++++++++++++
6
tests/qemu-iotests/group | 1 +
7
3 files changed, 207 insertions(+)
8
create mode 100755 tests/qemu-iotests/232
9
create mode 100644 tests/qemu-iotests/232.out
1
10
11
diff --git a/tests/qemu-iotests/232 b/tests/qemu-iotests/232
12
new file mode 100755
13
index XXXXXXX..XXXXXXX
14
--- /dev/null
15
+++ b/tests/qemu-iotests/232
16
@@ -XXX,XX +XXX,XX @@
17
+#!/bin/bash
18
+#
19
+# Test for auto-read-only
20
+#
21
+# Copyright (C) 2018 Red Hat, Inc.
22
+#
23
+# This program is free software; you can redistribute it and/or modify
24
+# it under the terms of the GNU General Public License as published by
25
+# the Free Software Foundation; either version 2 of the License, or
26
+# (at your option) any later version.
27
+#
28
+# This program is distributed in the hope that it will be useful,
29
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
30
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
31
+# GNU General Public License for more details.
32
+#
33
+# You should have received a copy of the GNU General Public License
34
+# along with this program. If not, see <http://www.gnu.org/licenses/>.
35
+#
36
+
37
+# creator
38
+owner=kwolf@redhat.com
39
+
40
+seq=`basename $0`
41
+echo "QA output created by $seq"
42
+
43
+here=`pwd`
44
+status=1    # failure is the default!
45
+
46
+_cleanup()
47
+{
48
+ _cleanup_test_img
49
+ rm -f $TEST_IMG.snap
50
+}
51
+trap "_cleanup; exit \$status" 0 1 2 3 15
52
+
53
+# get standard environment, filters and checks
54
+. ./common.rc
55
+. ./common.filter
56
+
57
+_supported_fmt generic
58
+_supported_proto file
59
+_supported_os Linux
60
+
61
+function do_run_qemu()
62
+{
63
+ echo Testing: "$@"
64
+ (
65
+ if ! test -t 0; then
66
+ while read cmd; do
67
+ echo $cmd
68
+ done
69
+ fi
70
+ echo quit
71
+ ) | $QEMU -nographic -monitor stdio -nodefaults "$@"
72
+ echo
73
+}
74
+
75
+function run_qemu()
76
+{
77
+ do_run_qemu "$@" 2>&1 | _filter_testdir | _filter_qemu | _filter_hmp |
78
+ _filter_generated_node_ids | _filter_imgfmt
79
+}
80
+
81
+function run_qemu_info_block()
82
+{
83
+ echo "info block -n" | run_qemu "$@" | grep -e "(file" -e "QEMU_PROG"
84
+}
85
+
86
+size=128M
87
+
88
+_make_test_img $size
89
+
90
+echo
91
+echo "=== -drive with read-write image: read-only/auto-read-only combinations ==="
92
+echo
93
+
94
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,read-only=on,auto-read-only=off
95
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,read-only=on,auto-read-only=on
96
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,read-only=on
97
+echo
98
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,read-only=off,auto-read-only=off
99
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,read-only=off,auto-read-only=on
100
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,read-only=off
101
+echo
102
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,auto-read-only=off
103
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,auto-read-only=on
104
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none
105
+
106
+echo
107
+echo "=== -drive with read-only image: read-only/auto-read-only combinations ==="
108
+echo
109
+
110
+chmod a-w $TEST_IMG
111
+
112
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,read-only=on,auto-read-only=off
113
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,read-only=on,auto-read-only=on
114
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,read-only=on
115
+echo
116
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,read-only=off,auto-read-only=off
117
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,read-only=off,auto-read-only=on
118
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,read-only=off
119
+echo
120
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,auto-read-only=off
121
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none,auto-read-only=on
122
+run_qemu_info_block -drive driver=file,file="$TEST_IMG",if=none
123
+
124
+echo
125
+echo "=== -blockdev with read-write image: read-only/auto-read-only combinations ==="
126
+echo
127
+
128
+chmod a+w $TEST_IMG
129
+
130
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,read-only=on,auto-read-only=off
131
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,read-only=on,auto-read-only=on
132
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,read-only=on
133
+echo
134
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,read-only=off,auto-read-only=off
135
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,read-only=off,auto-read-only=on
136
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,read-only=off
137
+echo
138
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,auto-read-only=off
139
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,auto-read-only=on
140
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0
141
+
142
+echo
143
+echo "=== -blockdev with read-only image: read-only/auto-read-only combinations ==="
144
+echo
145
+
146
+chmod a-w $TEST_IMG
147
+
148
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,read-only=on,auto-read-only=off
149
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,read-only=on,auto-read-only=on
150
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,read-only=on
151
+echo
152
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,read-only=off,auto-read-only=off
153
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,read-only=off,auto-read-only=on
154
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,read-only=off
155
+echo
156
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,auto-read-only=off
157
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0,auto-read-only=on
158
+run_qemu_info_block -blockdev driver=file,filename="$TEST_IMG",node-name=node0
159
+
160
+# success, all done
161
+echo "*** done"
162
+rm -f $seq.full
163
+status=0
164
diff --git a/tests/qemu-iotests/232.out b/tests/qemu-iotests/232.out
165
new file mode 100644
166
index XXXXXXX..XXXXXXX
167
--- /dev/null
168
+++ b/tests/qemu-iotests/232.out
169
@@ -XXX,XX +XXX,XX @@
170
+QA output created by 232
171
+Formatting 'TEST_DIR/t.IMGFMT', fmt=IMGFMT size=134217728
172
+
173
+=== -drive with read-write image: read-only/auto-read-only combinations ===
174
+
175
+NODE_NAME: TEST_DIR/t.IMGFMT (file, read-only)
176
+NODE_NAME: TEST_DIR/t.IMGFMT (file, read-only)
177
+NODE_NAME: TEST_DIR/t.IMGFMT (file, read-only)
178
+
179
+NODE_NAME: TEST_DIR/t.IMGFMT (file)
180
+NODE_NAME: TEST_DIR/t.IMGFMT (file)
181
+NODE_NAME: TEST_DIR/t.IMGFMT (file)
182
+
183
+NODE_NAME: TEST_DIR/t.IMGFMT (file)
184
+NODE_NAME: TEST_DIR/t.IMGFMT (file)
185
+NODE_NAME: TEST_DIR/t.IMGFMT (file)
186
+
187
+=== -drive with read-only image: read-only/auto-read-only combinations ===
188
+
189
+NODE_NAME: TEST_DIR/t.IMGFMT (file, read-only)
190
+NODE_NAME: TEST_DIR/t.IMGFMT (file, read-only)
191
+NODE_NAME: TEST_DIR/t.IMGFMT (file, read-only)
192
+
193
+QEMU_PROG: -drive driver=file,file=TEST_DIR/t.IMGFMT,if=none,read-only=off,auto-read-only=off: Could not open 'TEST_DIR/t.IMGFMT': Permission denied
194
+NODE_NAME: TEST_DIR/t.IMGFMT (file, read-only)
195
+NODE_NAME: TEST_DIR/t.IMGFMT (file, read-only)
196
+
197
+QEMU_PROG: -drive driver=file,file=TEST_DIR/t.IMGFMT,if=none,auto-read-only=off: Could not open 'TEST_DIR/t.IMGFMT': Permission denied
198
+NODE_NAME: TEST_DIR/t.IMGFMT (file, read-only)
199
+NODE_NAME: TEST_DIR/t.IMGFMT (file, read-only)
200
+
201
+=== -blockdev with read-write image: read-only/auto-read-only combinations ===
202
+
203
+node0: TEST_DIR/t.IMGFMT (file, read-only)
204
+node0: TEST_DIR/t.IMGFMT (file, read-only)
205
+node0: TEST_DIR/t.IMGFMT (file, read-only)
206
+
207
+node0: TEST_DIR/t.IMGFMT (file)
208
+node0: TEST_DIR/t.IMGFMT (file)
209
+node0: TEST_DIR/t.IMGFMT (file)
210
+
211
+node0: TEST_DIR/t.IMGFMT (file)
212
+node0: TEST_DIR/t.IMGFMT (file)
213
+node0: TEST_DIR/t.IMGFMT (file)
214
+
215
+=== -blockdev with read-only image: read-only/auto-read-only combinations ===
216
+
217
+node0: TEST_DIR/t.IMGFMT (file, read-only)
218
+node0: TEST_DIR/t.IMGFMT (file, read-only)
219
+node0: TEST_DIR/t.IMGFMT (file, read-only)
220
+
221
+QEMU_PROG: -blockdev driver=file,filename=TEST_DIR/t.IMGFMT,node-name=node0,read-only=off,auto-read-only=off: Could not open 'TEST_DIR/t.IMGFMT': Permission denied
222
+node0: TEST_DIR/t.IMGFMT (file, read-only)
223
+QEMU_PROG: -blockdev driver=file,filename=TEST_DIR/t.IMGFMT,node-name=node0,read-only=off: Could not open 'TEST_DIR/t.IMGFMT': Permission denied
224
+
225
+QEMU_PROG: -blockdev driver=file,filename=TEST_DIR/t.IMGFMT,node-name=node0,auto-read-only=off: Could not open 'TEST_DIR/t.IMGFMT': Permission denied
226
+node0: TEST_DIR/t.IMGFMT (file, read-only)
227
+QEMU_PROG: -blockdev driver=file,filename=TEST_DIR/t.IMGFMT,node-name=node0: Could not open 'TEST_DIR/t.IMGFMT': Permission denied
228
+*** done
229
diff --git a/tests/qemu-iotests/group b/tests/qemu-iotests/group
230
index XXXXXXX..XXXXXXX 100644
231
--- a/tests/qemu-iotests/group
232
+++ b/tests/qemu-iotests/group
233
@@ -XXX,XX +XXX,XX @@
234
227 auto quick
235
229 auto quick
236
231 auto quick
237
+232 auto quick
238
--
239
2.19.1
240
241
diff view generated by jsdifflib
1
From: Markus Armbruster <armbru@redhat.com>
1
From: Max Reitz <mreitz@redhat.com>
2
2
3
Coverity can't see that qobject_input_visitor_new_flat_confused()
3
This adds some whitespace into the option help (including indentation)
4
returns non-null when it doesn't set @local_err. Check the return
4
and puts angle brackets around the type names. Furthermore, the list
5
value instead, like all the other callers do.
5
name is no longer printed as part of every line, but only once in
6
advance, and only if the caller did not print a caption already.
6
7
7
Fixes: CID 1393615
8
This patch also restores the description alignment we had before commit
8
Fixes: CID 1393616
9
9cbef9d68ee1d8d0, just at 24 instead of 16 characters like we used to.
9
Signed-off-by: Markus Armbruster <armbru@redhat.com>
10
This increase is because now we have the type and two spaces of
11
indentation before the description, and with a usual type name length of
12
three chracters, this sums up to eight additional characters -- which
13
means that we now need 24 characters to get the same amount of padding
14
for most options. Also, 24 is a third of 80, which makes it kind of a
15
round number in terminal terms.
16
17
Finally, this patch amends the reference output of iotest 082 to match
18
the changes (and thus makes it pass again).
19
20
Signed-off-by: Max Reitz <mreitz@redhat.com>
21
Reviewed-by: Marc-André Lureau <marcandre.lureau@redhat.com>
10
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
22
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
11
---
23
---
12
block/crypto.c | 4 ++--
24
include/qemu/option.h | 2 +-
13
1 file changed, 2 insertions(+), 2 deletions(-)
25
qemu-img.c | 4 +-
26
util/qemu-option.c | 32 +-
27
tests/qemu-iotests/082.out | 956 ++++++++++++++++++-------------------
28
4 files changed, 507 insertions(+), 487 deletions(-)
14
29
15
diff --git a/block/crypto.c b/block/crypto.c
30
diff --git a/include/qemu/option.h b/include/qemu/option.h
16
index XXXXXXX..XXXXXXX 100644
31
index XXXXXXX..XXXXXXX 100644
17
--- a/block/crypto.c
32
--- a/include/qemu/option.h
18
+++ b/block/crypto.c
33
+++ b/include/qemu/option.h
19
@@ -XXX,XX +XXX,XX @@ block_crypto_open_opts_init(QCryptoBlockFormat format,
34
@@ -XXX,XX +XXX,XX @@ typedef int (*qemu_opts_loopfunc)(void *opaque, QemuOpts *opts, Error **errp);
20
ret->format = format;
35
int qemu_opts_foreach(QemuOptsList *list, qemu_opts_loopfunc func,
21
36
void *opaque, Error **errp);
22
v = qobject_input_visitor_new_flat_confused(opts, &local_err);
37
void qemu_opts_print(QemuOpts *opts, const char *sep);
23
- if (local_err) {
38
-void qemu_opts_print_help(QemuOptsList *list);
24
+ if (!v) {
39
+void qemu_opts_print_help(QemuOptsList *list, bool print_caption);
25
goto out;
40
void qemu_opts_free(QemuOptsList *list);
41
QemuOptsList *qemu_opts_append(QemuOptsList *dst, QemuOptsList *list);
42
43
diff --git a/qemu-img.c b/qemu-img.c
44
index XXXXXXX..XXXXXXX 100644
45
--- a/qemu-img.c
46
+++ b/qemu-img.c
47
@@ -XXX,XX +XXX,XX @@ static int print_block_option_help(const char *filename, const char *fmt)
26
}
48
}
27
49
28
@@ -XXX,XX +XXX,XX @@ block_crypto_create_opts_init(QCryptoBlockFormat format,
50
printf("Supported options:\n");
29
ret->format = format;
51
- qemu_opts_print_help(create_opts);
30
52
+ qemu_opts_print_help(create_opts, false);
31
v = qobject_input_visitor_new_flat_confused(opts, &local_err);
53
qemu_opts_free(create_opts);
32
- if (local_err) {
54
return 0;
33
+ if (!v) {
55
}
34
goto out;
56
@@ -XXX,XX +XXX,XX @@ static int print_amend_option_help(const char *format)
57
assert(drv->create_opts);
58
59
printf("Creation options for '%s':\n", format);
60
- qemu_opts_print_help(drv->create_opts);
61
+ qemu_opts_print_help(drv->create_opts, false);
62
printf("\nNote that not all of these options may be amendable.\n");
63
return 0;
64
}
65
diff --git a/util/qemu-option.c b/util/qemu-option.c
66
index XXXXXXX..XXXXXXX 100644
67
--- a/util/qemu-option.c
68
+++ b/util/qemu-option.c
69
@@ -XXX,XX +XXX,XX @@ static const char *opt_type_to_string(enum QemuOptType type)
70
g_assert_not_reached();
71
}
72
73
-void qemu_opts_print_help(QemuOptsList *list)
74
+/**
75
+ * Print the list of options available in the given list. If
76
+ * @print_caption is true, a caption (including the list name, if it
77
+ * exists) is printed. The options itself will be indented, so
78
+ * @print_caption should only be set to false if the caller prints its
79
+ * own custom caption (so that the indentation makes sense).
80
+ */
81
+void qemu_opts_print_help(QemuOptsList *list, bool print_caption)
82
{
83
QemuOptDesc *desc;
84
int i;
85
@@ -XXX,XX +XXX,XX @@ void qemu_opts_print_help(QemuOptsList *list)
86
desc = list->desc;
87
while (desc && desc->name) {
88
GString *str = g_string_new(NULL);
89
- if (list->name) {
90
- g_string_append_printf(str, "%s.", list->name);
91
- }
92
- g_string_append_printf(str, "%s=%s", desc->name,
93
+ g_string_append_printf(str, " %s=<%s>", desc->name,
94
opt_type_to_string(desc->type));
95
if (desc->help) {
96
+ if (str->len < 24) {
97
+ g_string_append_printf(str, "%*s", 24 - (int)str->len, "");
98
+ }
99
g_string_append_printf(str, " - %s", desc->help);
100
}
101
g_ptr_array_add(array, g_string_free(str, false));
102
@@ -XXX,XX +XXX,XX @@ void qemu_opts_print_help(QemuOptsList *list)
35
}
103
}
36
104
105
g_ptr_array_sort(array, (GCompareFunc)qemu_pstrcmp0);
106
+ if (print_caption && array->len > 0) {
107
+ if (list->name) {
108
+ printf("%s options:\n", list->name);
109
+ } else {
110
+ printf("Options:\n");
111
+ }
112
+ } else if (array->len == 0) {
113
+ if (list->name) {
114
+ printf("There are no options for %s.\n", list->name);
115
+ } else {
116
+ printf("No options available.\n");
117
+ }
118
+ }
119
for (i = 0; i < array->len; i++) {
120
printf("%s\n", (char *)array->pdata[i]);
121
}
122
@@ -XXX,XX +XXX,XX @@ QemuOpts *qemu_opts_parse_noisily(QemuOptsList *list, const char *params,
123
opts = opts_parse(list, params, permit_abbrev, false, &invalidp, &err);
124
if (err) {
125
if (invalidp && has_help_option(params)) {
126
- qemu_opts_print_help(list);
127
+ qemu_opts_print_help(list, true);
128
error_free(err);
129
} else {
130
error_report_err(err);
131
diff --git a/tests/qemu-iotests/082.out b/tests/qemu-iotests/082.out
132
index XXXXXXX..XXXXXXX 100644
133
--- a/tests/qemu-iotests/082.out
134
+++ b/tests/qemu-iotests/082.out
135
@@ -XXX,XX +XXX,XX @@ cluster_size: 8192
136
137
Testing: create -f qcow2 -o help TEST_DIR/t.qcow2 128M
138
Supported options:
139
-size Virtual disk size
140
-compat Compatibility level (0.10 or 1.1)
141
-backing_file File name of a base image
142
-backing_fmt Image format of the base image
143
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
144
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
145
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
146
-encrypt.cipher-alg Name of encryption cipher algorithm
147
-encrypt.cipher-mode Name of encryption cipher mode
148
-encrypt.ivgen-alg Name of IV generator algorithm
149
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
150
-encrypt.hash-alg Name of encryption hash algorithm
151
-encrypt.iter-time Time to spend in PBKDF in milliseconds
152
-cluster_size qcow2 cluster size
153
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
154
-lazy_refcounts Postpone refcount updates
155
-refcount_bits Width of a reference count entry in bits
156
-nocow Turn off copy-on-write (valid only on btrfs)
157
+ backing_file=<str> - File name of a base image
158
+ backing_fmt=<str> - Image format of the base image
159
+ cluster_size=<size> - qcow2 cluster size
160
+ compat=<str> - Compatibility level (0.10 or 1.1)
161
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
162
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
163
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
164
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
165
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
166
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
167
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
168
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
169
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
170
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
171
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
172
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
173
+ refcount_bits=<num> - Width of a reference count entry in bits
174
+ size=<size> - Virtual disk size
175
176
Testing: create -f qcow2 -o ? TEST_DIR/t.qcow2 128M
177
Supported options:
178
-size Virtual disk size
179
-compat Compatibility level (0.10 or 1.1)
180
-backing_file File name of a base image
181
-backing_fmt Image format of the base image
182
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
183
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
184
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
185
-encrypt.cipher-alg Name of encryption cipher algorithm
186
-encrypt.cipher-mode Name of encryption cipher mode
187
-encrypt.ivgen-alg Name of IV generator algorithm
188
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
189
-encrypt.hash-alg Name of encryption hash algorithm
190
-encrypt.iter-time Time to spend in PBKDF in milliseconds
191
-cluster_size qcow2 cluster size
192
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
193
-lazy_refcounts Postpone refcount updates
194
-refcount_bits Width of a reference count entry in bits
195
-nocow Turn off copy-on-write (valid only on btrfs)
196
+ backing_file=<str> - File name of a base image
197
+ backing_fmt=<str> - Image format of the base image
198
+ cluster_size=<size> - qcow2 cluster size
199
+ compat=<str> - Compatibility level (0.10 or 1.1)
200
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
201
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
202
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
203
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
204
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
205
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
206
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
207
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
208
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
209
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
210
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
211
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
212
+ refcount_bits=<num> - Width of a reference count entry in bits
213
+ size=<size> - Virtual disk size
214
215
Testing: create -f qcow2 -o cluster_size=4k,help TEST_DIR/t.qcow2 128M
216
Supported options:
217
-size Virtual disk size
218
-compat Compatibility level (0.10 or 1.1)
219
-backing_file File name of a base image
220
-backing_fmt Image format of the base image
221
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
222
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
223
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
224
-encrypt.cipher-alg Name of encryption cipher algorithm
225
-encrypt.cipher-mode Name of encryption cipher mode
226
-encrypt.ivgen-alg Name of IV generator algorithm
227
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
228
-encrypt.hash-alg Name of encryption hash algorithm
229
-encrypt.iter-time Time to spend in PBKDF in milliseconds
230
-cluster_size qcow2 cluster size
231
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
232
-lazy_refcounts Postpone refcount updates
233
-refcount_bits Width of a reference count entry in bits
234
-nocow Turn off copy-on-write (valid only on btrfs)
235
+ backing_file=<str> - File name of a base image
236
+ backing_fmt=<str> - Image format of the base image
237
+ cluster_size=<size> - qcow2 cluster size
238
+ compat=<str> - Compatibility level (0.10 or 1.1)
239
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
240
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
241
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
242
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
243
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
244
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
245
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
246
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
247
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
248
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
249
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
250
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
251
+ refcount_bits=<num> - Width of a reference count entry in bits
252
+ size=<size> - Virtual disk size
253
254
Testing: create -f qcow2 -o cluster_size=4k,? TEST_DIR/t.qcow2 128M
255
Supported options:
256
-size Virtual disk size
257
-compat Compatibility level (0.10 or 1.1)
258
-backing_file File name of a base image
259
-backing_fmt Image format of the base image
260
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
261
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
262
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
263
-encrypt.cipher-alg Name of encryption cipher algorithm
264
-encrypt.cipher-mode Name of encryption cipher mode
265
-encrypt.ivgen-alg Name of IV generator algorithm
266
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
267
-encrypt.hash-alg Name of encryption hash algorithm
268
-encrypt.iter-time Time to spend in PBKDF in milliseconds
269
-cluster_size qcow2 cluster size
270
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
271
-lazy_refcounts Postpone refcount updates
272
-refcount_bits Width of a reference count entry in bits
273
-nocow Turn off copy-on-write (valid only on btrfs)
274
+ backing_file=<str> - File name of a base image
275
+ backing_fmt=<str> - Image format of the base image
276
+ cluster_size=<size> - qcow2 cluster size
277
+ compat=<str> - Compatibility level (0.10 or 1.1)
278
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
279
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
280
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
281
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
282
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
283
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
284
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
285
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
286
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
287
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
288
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
289
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
290
+ refcount_bits=<num> - Width of a reference count entry in bits
291
+ size=<size> - Virtual disk size
292
293
Testing: create -f qcow2 -o help,cluster_size=4k TEST_DIR/t.qcow2 128M
294
Supported options:
295
-size Virtual disk size
296
-compat Compatibility level (0.10 or 1.1)
297
-backing_file File name of a base image
298
-backing_fmt Image format of the base image
299
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
300
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
301
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
302
-encrypt.cipher-alg Name of encryption cipher algorithm
303
-encrypt.cipher-mode Name of encryption cipher mode
304
-encrypt.ivgen-alg Name of IV generator algorithm
305
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
306
-encrypt.hash-alg Name of encryption hash algorithm
307
-encrypt.iter-time Time to spend in PBKDF in milliseconds
308
-cluster_size qcow2 cluster size
309
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
310
-lazy_refcounts Postpone refcount updates
311
-refcount_bits Width of a reference count entry in bits
312
-nocow Turn off copy-on-write (valid only on btrfs)
313
+ backing_file=<str> - File name of a base image
314
+ backing_fmt=<str> - Image format of the base image
315
+ cluster_size=<size> - qcow2 cluster size
316
+ compat=<str> - Compatibility level (0.10 or 1.1)
317
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
318
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
319
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
320
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
321
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
322
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
323
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
324
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
325
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
326
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
327
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
328
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
329
+ refcount_bits=<num> - Width of a reference count entry in bits
330
+ size=<size> - Virtual disk size
331
332
Testing: create -f qcow2 -o ?,cluster_size=4k TEST_DIR/t.qcow2 128M
333
Supported options:
334
-size Virtual disk size
335
-compat Compatibility level (0.10 or 1.1)
336
-backing_file File name of a base image
337
-backing_fmt Image format of the base image
338
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
339
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
340
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
341
-encrypt.cipher-alg Name of encryption cipher algorithm
342
-encrypt.cipher-mode Name of encryption cipher mode
343
-encrypt.ivgen-alg Name of IV generator algorithm
344
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
345
-encrypt.hash-alg Name of encryption hash algorithm
346
-encrypt.iter-time Time to spend in PBKDF in milliseconds
347
-cluster_size qcow2 cluster size
348
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
349
-lazy_refcounts Postpone refcount updates
350
-refcount_bits Width of a reference count entry in bits
351
-nocow Turn off copy-on-write (valid only on btrfs)
352
+ backing_file=<str> - File name of a base image
353
+ backing_fmt=<str> - Image format of the base image
354
+ cluster_size=<size> - qcow2 cluster size
355
+ compat=<str> - Compatibility level (0.10 or 1.1)
356
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
357
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
358
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
359
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
360
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
361
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
362
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
363
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
364
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
365
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
366
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
367
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
368
+ refcount_bits=<num> - Width of a reference count entry in bits
369
+ size=<size> - Virtual disk size
370
371
Testing: create -f qcow2 -o cluster_size=4k -o help TEST_DIR/t.qcow2 128M
372
Supported options:
373
-size Virtual disk size
374
-compat Compatibility level (0.10 or 1.1)
375
-backing_file File name of a base image
376
-backing_fmt Image format of the base image
377
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
378
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
379
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
380
-encrypt.cipher-alg Name of encryption cipher algorithm
381
-encrypt.cipher-mode Name of encryption cipher mode
382
-encrypt.ivgen-alg Name of IV generator algorithm
383
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
384
-encrypt.hash-alg Name of encryption hash algorithm
385
-encrypt.iter-time Time to spend in PBKDF in milliseconds
386
-cluster_size qcow2 cluster size
387
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
388
-lazy_refcounts Postpone refcount updates
389
-refcount_bits Width of a reference count entry in bits
390
-nocow Turn off copy-on-write (valid only on btrfs)
391
+ backing_file=<str> - File name of a base image
392
+ backing_fmt=<str> - Image format of the base image
393
+ cluster_size=<size> - qcow2 cluster size
394
+ compat=<str> - Compatibility level (0.10 or 1.1)
395
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
396
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
397
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
398
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
399
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
400
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
401
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
402
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
403
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
404
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
405
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
406
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
407
+ refcount_bits=<num> - Width of a reference count entry in bits
408
+ size=<size> - Virtual disk size
409
410
Testing: create -f qcow2 -o cluster_size=4k -o ? TEST_DIR/t.qcow2 128M
411
Supported options:
412
-size Virtual disk size
413
-compat Compatibility level (0.10 or 1.1)
414
-backing_file File name of a base image
415
-backing_fmt Image format of the base image
416
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
417
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
418
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
419
-encrypt.cipher-alg Name of encryption cipher algorithm
420
-encrypt.cipher-mode Name of encryption cipher mode
421
-encrypt.ivgen-alg Name of IV generator algorithm
422
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
423
-encrypt.hash-alg Name of encryption hash algorithm
424
-encrypt.iter-time Time to spend in PBKDF in milliseconds
425
-cluster_size qcow2 cluster size
426
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
427
-lazy_refcounts Postpone refcount updates
428
-refcount_bits Width of a reference count entry in bits
429
-nocow Turn off copy-on-write (valid only on btrfs)
430
+ backing_file=<str> - File name of a base image
431
+ backing_fmt=<str> - Image format of the base image
432
+ cluster_size=<size> - qcow2 cluster size
433
+ compat=<str> - Compatibility level (0.10 or 1.1)
434
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
435
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
436
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
437
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
438
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
439
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
440
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
441
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
442
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
443
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
444
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
445
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
446
+ refcount_bits=<num> - Width of a reference count entry in bits
447
+ size=<size> - Virtual disk size
448
449
Testing: create -f qcow2 -u -o backing_file=TEST_DIR/t.qcow2,,help TEST_DIR/t.qcow2 128M
450
Formatting 'TEST_DIR/t.qcow2', fmt=qcow2 size=134217728 backing_file=TEST_DIR/t.qcow2,,help cluster_size=65536 lazy_refcounts=off refcount_bits=16
451
@@ -XXX,XX +XXX,XX @@ qemu-img: Invalid option list: ,,
452
453
Testing: create -f qcow2 -o help
454
Supported options:
455
-size Virtual disk size
456
-compat Compatibility level (0.10 or 1.1)
457
-backing_file File name of a base image
458
-backing_fmt Image format of the base image
459
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
460
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
461
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
462
-encrypt.cipher-alg Name of encryption cipher algorithm
463
-encrypt.cipher-mode Name of encryption cipher mode
464
-encrypt.ivgen-alg Name of IV generator algorithm
465
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
466
-encrypt.hash-alg Name of encryption hash algorithm
467
-encrypt.iter-time Time to spend in PBKDF in milliseconds
468
-cluster_size qcow2 cluster size
469
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
470
-lazy_refcounts Postpone refcount updates
471
-refcount_bits Width of a reference count entry in bits
472
+ backing_file=<str> - File name of a base image
473
+ backing_fmt=<str> - Image format of the base image
474
+ cluster_size=<size> - qcow2 cluster size
475
+ compat=<str> - Compatibility level (0.10 or 1.1)
476
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
477
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
478
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
479
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
480
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
481
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
482
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
483
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
484
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
485
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
486
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
487
+ refcount_bits=<num> - Width of a reference count entry in bits
488
+ size=<size> - Virtual disk size
489
490
Testing: create -o help
491
Supported options:
492
-size Virtual disk size
493
+ size=<size> - Virtual disk size
494
495
Testing: create -f bochs -o help
496
qemu-img: Format driver 'bochs' does not support image creation
497
@@ -XXX,XX +XXX,XX @@ cluster_size: 8192
498
499
Testing: convert -O qcow2 -o help TEST_DIR/t.qcow2 TEST_DIR/t.qcow2.base
500
Supported options:
501
-size Virtual disk size
502
-compat Compatibility level (0.10 or 1.1)
503
-backing_file File name of a base image
504
-backing_fmt Image format of the base image
505
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
506
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
507
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
508
-encrypt.cipher-alg Name of encryption cipher algorithm
509
-encrypt.cipher-mode Name of encryption cipher mode
510
-encrypt.ivgen-alg Name of IV generator algorithm
511
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
512
-encrypt.hash-alg Name of encryption hash algorithm
513
-encrypt.iter-time Time to spend in PBKDF in milliseconds
514
-cluster_size qcow2 cluster size
515
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
516
-lazy_refcounts Postpone refcount updates
517
-refcount_bits Width of a reference count entry in bits
518
-nocow Turn off copy-on-write (valid only on btrfs)
519
+ backing_file=<str> - File name of a base image
520
+ backing_fmt=<str> - Image format of the base image
521
+ cluster_size=<size> - qcow2 cluster size
522
+ compat=<str> - Compatibility level (0.10 or 1.1)
523
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
524
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
525
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
526
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
527
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
528
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
529
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
530
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
531
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
532
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
533
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
534
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
535
+ refcount_bits=<num> - Width of a reference count entry in bits
536
+ size=<size> - Virtual disk size
537
538
Testing: convert -O qcow2 -o ? TEST_DIR/t.qcow2 TEST_DIR/t.qcow2.base
539
Supported options:
540
-size Virtual disk size
541
-compat Compatibility level (0.10 or 1.1)
542
-backing_file File name of a base image
543
-backing_fmt Image format of the base image
544
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
545
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
546
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
547
-encrypt.cipher-alg Name of encryption cipher algorithm
548
-encrypt.cipher-mode Name of encryption cipher mode
549
-encrypt.ivgen-alg Name of IV generator algorithm
550
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
551
-encrypt.hash-alg Name of encryption hash algorithm
552
-encrypt.iter-time Time to spend in PBKDF in milliseconds
553
-cluster_size qcow2 cluster size
554
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
555
-lazy_refcounts Postpone refcount updates
556
-refcount_bits Width of a reference count entry in bits
557
-nocow Turn off copy-on-write (valid only on btrfs)
558
+ backing_file=<str> - File name of a base image
559
+ backing_fmt=<str> - Image format of the base image
560
+ cluster_size=<size> - qcow2 cluster size
561
+ compat=<str> - Compatibility level (0.10 or 1.1)
562
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
563
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
564
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
565
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
566
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
567
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
568
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
569
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
570
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
571
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
572
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
573
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
574
+ refcount_bits=<num> - Width of a reference count entry in bits
575
+ size=<size> - Virtual disk size
576
577
Testing: convert -O qcow2 -o cluster_size=4k,help TEST_DIR/t.qcow2 TEST_DIR/t.qcow2.base
578
Supported options:
579
-size Virtual disk size
580
-compat Compatibility level (0.10 or 1.1)
581
-backing_file File name of a base image
582
-backing_fmt Image format of the base image
583
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
584
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
585
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
586
-encrypt.cipher-alg Name of encryption cipher algorithm
587
-encrypt.cipher-mode Name of encryption cipher mode
588
-encrypt.ivgen-alg Name of IV generator algorithm
589
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
590
-encrypt.hash-alg Name of encryption hash algorithm
591
-encrypt.iter-time Time to spend in PBKDF in milliseconds
592
-cluster_size qcow2 cluster size
593
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
594
-lazy_refcounts Postpone refcount updates
595
-refcount_bits Width of a reference count entry in bits
596
-nocow Turn off copy-on-write (valid only on btrfs)
597
+ backing_file=<str> - File name of a base image
598
+ backing_fmt=<str> - Image format of the base image
599
+ cluster_size=<size> - qcow2 cluster size
600
+ compat=<str> - Compatibility level (0.10 or 1.1)
601
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
602
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
603
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
604
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
605
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
606
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
607
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
608
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
609
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
610
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
611
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
612
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
613
+ refcount_bits=<num> - Width of a reference count entry in bits
614
+ size=<size> - Virtual disk size
615
616
Testing: convert -O qcow2 -o cluster_size=4k,? TEST_DIR/t.qcow2 TEST_DIR/t.qcow2.base
617
Supported options:
618
-size Virtual disk size
619
-compat Compatibility level (0.10 or 1.1)
620
-backing_file File name of a base image
621
-backing_fmt Image format of the base image
622
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
623
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
624
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
625
-encrypt.cipher-alg Name of encryption cipher algorithm
626
-encrypt.cipher-mode Name of encryption cipher mode
627
-encrypt.ivgen-alg Name of IV generator algorithm
628
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
629
-encrypt.hash-alg Name of encryption hash algorithm
630
-encrypt.iter-time Time to spend in PBKDF in milliseconds
631
-cluster_size qcow2 cluster size
632
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
633
-lazy_refcounts Postpone refcount updates
634
-refcount_bits Width of a reference count entry in bits
635
-nocow Turn off copy-on-write (valid only on btrfs)
636
+ backing_file=<str> - File name of a base image
637
+ backing_fmt=<str> - Image format of the base image
638
+ cluster_size=<size> - qcow2 cluster size
639
+ compat=<str> - Compatibility level (0.10 or 1.1)
640
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
641
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
642
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
643
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
644
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
645
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
646
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
647
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
648
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
649
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
650
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
651
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
652
+ refcount_bits=<num> - Width of a reference count entry in bits
653
+ size=<size> - Virtual disk size
654
655
Testing: convert -O qcow2 -o help,cluster_size=4k TEST_DIR/t.qcow2 TEST_DIR/t.qcow2.base
656
Supported options:
657
-size Virtual disk size
658
-compat Compatibility level (0.10 or 1.1)
659
-backing_file File name of a base image
660
-backing_fmt Image format of the base image
661
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
662
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
663
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
664
-encrypt.cipher-alg Name of encryption cipher algorithm
665
-encrypt.cipher-mode Name of encryption cipher mode
666
-encrypt.ivgen-alg Name of IV generator algorithm
667
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
668
-encrypt.hash-alg Name of encryption hash algorithm
669
-encrypt.iter-time Time to spend in PBKDF in milliseconds
670
-cluster_size qcow2 cluster size
671
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
672
-lazy_refcounts Postpone refcount updates
673
-refcount_bits Width of a reference count entry in bits
674
-nocow Turn off copy-on-write (valid only on btrfs)
675
+ backing_file=<str> - File name of a base image
676
+ backing_fmt=<str> - Image format of the base image
677
+ cluster_size=<size> - qcow2 cluster size
678
+ compat=<str> - Compatibility level (0.10 or 1.1)
679
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
680
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
681
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
682
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
683
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
684
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
685
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
686
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
687
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
688
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
689
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
690
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
691
+ refcount_bits=<num> - Width of a reference count entry in bits
692
+ size=<size> - Virtual disk size
693
694
Testing: convert -O qcow2 -o ?,cluster_size=4k TEST_DIR/t.qcow2 TEST_DIR/t.qcow2.base
695
Supported options:
696
-size Virtual disk size
697
-compat Compatibility level (0.10 or 1.1)
698
-backing_file File name of a base image
699
-backing_fmt Image format of the base image
700
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
701
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
702
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
703
-encrypt.cipher-alg Name of encryption cipher algorithm
704
-encrypt.cipher-mode Name of encryption cipher mode
705
-encrypt.ivgen-alg Name of IV generator algorithm
706
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
707
-encrypt.hash-alg Name of encryption hash algorithm
708
-encrypt.iter-time Time to spend in PBKDF in milliseconds
709
-cluster_size qcow2 cluster size
710
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
711
-lazy_refcounts Postpone refcount updates
712
-refcount_bits Width of a reference count entry in bits
713
-nocow Turn off copy-on-write (valid only on btrfs)
714
+ backing_file=<str> - File name of a base image
715
+ backing_fmt=<str> - Image format of the base image
716
+ cluster_size=<size> - qcow2 cluster size
717
+ compat=<str> - Compatibility level (0.10 or 1.1)
718
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
719
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
720
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
721
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
722
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
723
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
724
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
725
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
726
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
727
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
728
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
729
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
730
+ refcount_bits=<num> - Width of a reference count entry in bits
731
+ size=<size> - Virtual disk size
732
733
Testing: convert -O qcow2 -o cluster_size=4k -o help TEST_DIR/t.qcow2 TEST_DIR/t.qcow2.base
734
Supported options:
735
-size Virtual disk size
736
-compat Compatibility level (0.10 or 1.1)
737
-backing_file File name of a base image
738
-backing_fmt Image format of the base image
739
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
740
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
741
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
742
-encrypt.cipher-alg Name of encryption cipher algorithm
743
-encrypt.cipher-mode Name of encryption cipher mode
744
-encrypt.ivgen-alg Name of IV generator algorithm
745
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
746
-encrypt.hash-alg Name of encryption hash algorithm
747
-encrypt.iter-time Time to spend in PBKDF in milliseconds
748
-cluster_size qcow2 cluster size
749
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
750
-lazy_refcounts Postpone refcount updates
751
-refcount_bits Width of a reference count entry in bits
752
-nocow Turn off copy-on-write (valid only on btrfs)
753
+ backing_file=<str> - File name of a base image
754
+ backing_fmt=<str> - Image format of the base image
755
+ cluster_size=<size> - qcow2 cluster size
756
+ compat=<str> - Compatibility level (0.10 or 1.1)
757
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
758
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
759
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
760
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
761
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
762
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
763
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
764
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
765
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
766
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
767
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
768
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
769
+ refcount_bits=<num> - Width of a reference count entry in bits
770
+ size=<size> - Virtual disk size
771
772
Testing: convert -O qcow2 -o cluster_size=4k -o ? TEST_DIR/t.qcow2 TEST_DIR/t.qcow2.base
773
Supported options:
774
-size Virtual disk size
775
-compat Compatibility level (0.10 or 1.1)
776
-backing_file File name of a base image
777
-backing_fmt Image format of the base image
778
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
779
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
780
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
781
-encrypt.cipher-alg Name of encryption cipher algorithm
782
-encrypt.cipher-mode Name of encryption cipher mode
783
-encrypt.ivgen-alg Name of IV generator algorithm
784
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
785
-encrypt.hash-alg Name of encryption hash algorithm
786
-encrypt.iter-time Time to spend in PBKDF in milliseconds
787
-cluster_size qcow2 cluster size
788
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
789
-lazy_refcounts Postpone refcount updates
790
-refcount_bits Width of a reference count entry in bits
791
-nocow Turn off copy-on-write (valid only on btrfs)
792
+ backing_file=<str> - File name of a base image
793
+ backing_fmt=<str> - Image format of the base image
794
+ cluster_size=<size> - qcow2 cluster size
795
+ compat=<str> - Compatibility level (0.10 or 1.1)
796
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
797
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
798
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
799
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
800
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
801
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
802
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
803
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
804
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
805
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
806
+ nocow=<bool (on/off)> - Turn off copy-on-write (valid only on btrfs)
807
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
808
+ refcount_bits=<num> - Width of a reference count entry in bits
809
+ size=<size> - Virtual disk size
810
811
Testing: convert -O qcow2 -o backing_file=TEST_DIR/t.qcow2,,help TEST_DIR/t.qcow2 TEST_DIR/t.qcow2.base
812
qemu-img: Could not open 'TEST_DIR/t.qcow2.base': Could not open backing file: Could not open 'TEST_DIR/t.qcow2,help': No such file or directory
813
@@ -XXX,XX +XXX,XX @@ qemu-img: Invalid option list: ,,
814
815
Testing: convert -O qcow2 -o help
816
Supported options:
817
-size Virtual disk size
818
-compat Compatibility level (0.10 or 1.1)
819
-backing_file File name of a base image
820
-backing_fmt Image format of the base image
821
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
822
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
823
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
824
-encrypt.cipher-alg Name of encryption cipher algorithm
825
-encrypt.cipher-mode Name of encryption cipher mode
826
-encrypt.ivgen-alg Name of IV generator algorithm
827
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
828
-encrypt.hash-alg Name of encryption hash algorithm
829
-encrypt.iter-time Time to spend in PBKDF in milliseconds
830
-cluster_size qcow2 cluster size
831
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
832
-lazy_refcounts Postpone refcount updates
833
-refcount_bits Width of a reference count entry in bits
834
+ backing_file=<str> - File name of a base image
835
+ backing_fmt=<str> - Image format of the base image
836
+ cluster_size=<size> - qcow2 cluster size
837
+ compat=<str> - Compatibility level (0.10 or 1.1)
838
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
839
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
840
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
841
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
842
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
843
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
844
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
845
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
846
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
847
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
848
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
849
+ refcount_bits=<num> - Width of a reference count entry in bits
850
+ size=<size> - Virtual disk size
851
852
Testing: convert -o help
853
Supported options:
854
-size Virtual disk size
855
+ size=<size> - Virtual disk size
856
857
Testing: convert -O bochs -o help
858
qemu-img: Format driver 'bochs' does not support image creation
859
@@ -XXX,XX +XXX,XX @@ cluster_size: 65536
860
861
Testing: amend -f qcow2 -o help TEST_DIR/t.qcow2
862
Creation options for 'qcow2':
863
-size Virtual disk size
864
-compat Compatibility level (0.10 or 1.1)
865
-backing_file File name of a base image
866
-backing_fmt Image format of the base image
867
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
868
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
869
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
870
-encrypt.cipher-alg Name of encryption cipher algorithm
871
-encrypt.cipher-mode Name of encryption cipher mode
872
-encrypt.ivgen-alg Name of IV generator algorithm
873
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
874
-encrypt.hash-alg Name of encryption hash algorithm
875
-encrypt.iter-time Time to spend in PBKDF in milliseconds
876
-cluster_size qcow2 cluster size
877
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
878
-lazy_refcounts Postpone refcount updates
879
-refcount_bits Width of a reference count entry in bits
880
+ backing_file=<str> - File name of a base image
881
+ backing_fmt=<str> - Image format of the base image
882
+ cluster_size=<size> - qcow2 cluster size
883
+ compat=<str> - Compatibility level (0.10 or 1.1)
884
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
885
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
886
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
887
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
888
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
889
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
890
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
891
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
892
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
893
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
894
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
895
+ refcount_bits=<num> - Width of a reference count entry in bits
896
+ size=<size> - Virtual disk size
897
898
Note that not all of these options may be amendable.
899
900
Testing: amend -f qcow2 -o ? TEST_DIR/t.qcow2
901
Creation options for 'qcow2':
902
-size Virtual disk size
903
-compat Compatibility level (0.10 or 1.1)
904
-backing_file File name of a base image
905
-backing_fmt Image format of the base image
906
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
907
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
908
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
909
-encrypt.cipher-alg Name of encryption cipher algorithm
910
-encrypt.cipher-mode Name of encryption cipher mode
911
-encrypt.ivgen-alg Name of IV generator algorithm
912
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
913
-encrypt.hash-alg Name of encryption hash algorithm
914
-encrypt.iter-time Time to spend in PBKDF in milliseconds
915
-cluster_size qcow2 cluster size
916
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
917
-lazy_refcounts Postpone refcount updates
918
-refcount_bits Width of a reference count entry in bits
919
+ backing_file=<str> - File name of a base image
920
+ backing_fmt=<str> - Image format of the base image
921
+ cluster_size=<size> - qcow2 cluster size
922
+ compat=<str> - Compatibility level (0.10 or 1.1)
923
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
924
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
925
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
926
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
927
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
928
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
929
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
930
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
931
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
932
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
933
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
934
+ refcount_bits=<num> - Width of a reference count entry in bits
935
+ size=<size> - Virtual disk size
936
937
Note that not all of these options may be amendable.
938
939
Testing: amend -f qcow2 -o cluster_size=4k,help TEST_DIR/t.qcow2
940
Creation options for 'qcow2':
941
-size Virtual disk size
942
-compat Compatibility level (0.10 or 1.1)
943
-backing_file File name of a base image
944
-backing_fmt Image format of the base image
945
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
946
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
947
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
948
-encrypt.cipher-alg Name of encryption cipher algorithm
949
-encrypt.cipher-mode Name of encryption cipher mode
950
-encrypt.ivgen-alg Name of IV generator algorithm
951
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
952
-encrypt.hash-alg Name of encryption hash algorithm
953
-encrypt.iter-time Time to spend in PBKDF in milliseconds
954
-cluster_size qcow2 cluster size
955
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
956
-lazy_refcounts Postpone refcount updates
957
-refcount_bits Width of a reference count entry in bits
958
+ backing_file=<str> - File name of a base image
959
+ backing_fmt=<str> - Image format of the base image
960
+ cluster_size=<size> - qcow2 cluster size
961
+ compat=<str> - Compatibility level (0.10 or 1.1)
962
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
963
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
964
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
965
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
966
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
967
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
968
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
969
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
970
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
971
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
972
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
973
+ refcount_bits=<num> - Width of a reference count entry in bits
974
+ size=<size> - Virtual disk size
975
976
Note that not all of these options may be amendable.
977
978
Testing: amend -f qcow2 -o cluster_size=4k,? TEST_DIR/t.qcow2
979
Creation options for 'qcow2':
980
-size Virtual disk size
981
-compat Compatibility level (0.10 or 1.1)
982
-backing_file File name of a base image
983
-backing_fmt Image format of the base image
984
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
985
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
986
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
987
-encrypt.cipher-alg Name of encryption cipher algorithm
988
-encrypt.cipher-mode Name of encryption cipher mode
989
-encrypt.ivgen-alg Name of IV generator algorithm
990
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
991
-encrypt.hash-alg Name of encryption hash algorithm
992
-encrypt.iter-time Time to spend in PBKDF in milliseconds
993
-cluster_size qcow2 cluster size
994
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
995
-lazy_refcounts Postpone refcount updates
996
-refcount_bits Width of a reference count entry in bits
997
+ backing_file=<str> - File name of a base image
998
+ backing_fmt=<str> - Image format of the base image
999
+ cluster_size=<size> - qcow2 cluster size
1000
+ compat=<str> - Compatibility level (0.10 or 1.1)
1001
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
1002
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
1003
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
1004
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
1005
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
1006
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
1007
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
1008
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
1009
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
1010
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
1011
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
1012
+ refcount_bits=<num> - Width of a reference count entry in bits
1013
+ size=<size> - Virtual disk size
1014
1015
Note that not all of these options may be amendable.
1016
1017
Testing: amend -f qcow2 -o help,cluster_size=4k TEST_DIR/t.qcow2
1018
Creation options for 'qcow2':
1019
-size Virtual disk size
1020
-compat Compatibility level (0.10 or 1.1)
1021
-backing_file File name of a base image
1022
-backing_fmt Image format of the base image
1023
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
1024
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
1025
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
1026
-encrypt.cipher-alg Name of encryption cipher algorithm
1027
-encrypt.cipher-mode Name of encryption cipher mode
1028
-encrypt.ivgen-alg Name of IV generator algorithm
1029
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
1030
-encrypt.hash-alg Name of encryption hash algorithm
1031
-encrypt.iter-time Time to spend in PBKDF in milliseconds
1032
-cluster_size qcow2 cluster size
1033
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
1034
-lazy_refcounts Postpone refcount updates
1035
-refcount_bits Width of a reference count entry in bits
1036
+ backing_file=<str> - File name of a base image
1037
+ backing_fmt=<str> - Image format of the base image
1038
+ cluster_size=<size> - qcow2 cluster size
1039
+ compat=<str> - Compatibility level (0.10 or 1.1)
1040
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
1041
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
1042
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
1043
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
1044
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
1045
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
1046
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
1047
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
1048
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
1049
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
1050
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
1051
+ refcount_bits=<num> - Width of a reference count entry in bits
1052
+ size=<size> - Virtual disk size
1053
1054
Note that not all of these options may be amendable.
1055
1056
Testing: amend -f qcow2 -o ?,cluster_size=4k TEST_DIR/t.qcow2
1057
Creation options for 'qcow2':
1058
-size Virtual disk size
1059
-compat Compatibility level (0.10 or 1.1)
1060
-backing_file File name of a base image
1061
-backing_fmt Image format of the base image
1062
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
1063
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
1064
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
1065
-encrypt.cipher-alg Name of encryption cipher algorithm
1066
-encrypt.cipher-mode Name of encryption cipher mode
1067
-encrypt.ivgen-alg Name of IV generator algorithm
1068
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
1069
-encrypt.hash-alg Name of encryption hash algorithm
1070
-encrypt.iter-time Time to spend in PBKDF in milliseconds
1071
-cluster_size qcow2 cluster size
1072
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
1073
-lazy_refcounts Postpone refcount updates
1074
-refcount_bits Width of a reference count entry in bits
1075
+ backing_file=<str> - File name of a base image
1076
+ backing_fmt=<str> - Image format of the base image
1077
+ cluster_size=<size> - qcow2 cluster size
1078
+ compat=<str> - Compatibility level (0.10 or 1.1)
1079
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
1080
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
1081
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
1082
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
1083
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
1084
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
1085
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
1086
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
1087
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
1088
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
1089
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
1090
+ refcount_bits=<num> - Width of a reference count entry in bits
1091
+ size=<size> - Virtual disk size
1092
1093
Note that not all of these options may be amendable.
1094
1095
Testing: amend -f qcow2 -o cluster_size=4k -o help TEST_DIR/t.qcow2
1096
Creation options for 'qcow2':
1097
-size Virtual disk size
1098
-compat Compatibility level (0.10 or 1.1)
1099
-backing_file File name of a base image
1100
-backing_fmt Image format of the base image
1101
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
1102
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
1103
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
1104
-encrypt.cipher-alg Name of encryption cipher algorithm
1105
-encrypt.cipher-mode Name of encryption cipher mode
1106
-encrypt.ivgen-alg Name of IV generator algorithm
1107
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
1108
-encrypt.hash-alg Name of encryption hash algorithm
1109
-encrypt.iter-time Time to spend in PBKDF in milliseconds
1110
-cluster_size qcow2 cluster size
1111
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
1112
-lazy_refcounts Postpone refcount updates
1113
-refcount_bits Width of a reference count entry in bits
1114
+ backing_file=<str> - File name of a base image
1115
+ backing_fmt=<str> - Image format of the base image
1116
+ cluster_size=<size> - qcow2 cluster size
1117
+ compat=<str> - Compatibility level (0.10 or 1.1)
1118
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
1119
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
1120
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
1121
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
1122
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
1123
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
1124
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
1125
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
1126
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
1127
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
1128
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
1129
+ refcount_bits=<num> - Width of a reference count entry in bits
1130
+ size=<size> - Virtual disk size
1131
1132
Note that not all of these options may be amendable.
1133
1134
Testing: amend -f qcow2 -o cluster_size=4k -o ? TEST_DIR/t.qcow2
1135
Creation options for 'qcow2':
1136
-size Virtual disk size
1137
-compat Compatibility level (0.10 or 1.1)
1138
-backing_file File name of a base image
1139
-backing_fmt Image format of the base image
1140
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
1141
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
1142
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
1143
-encrypt.cipher-alg Name of encryption cipher algorithm
1144
-encrypt.cipher-mode Name of encryption cipher mode
1145
-encrypt.ivgen-alg Name of IV generator algorithm
1146
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
1147
-encrypt.hash-alg Name of encryption hash algorithm
1148
-encrypt.iter-time Time to spend in PBKDF in milliseconds
1149
-cluster_size qcow2 cluster size
1150
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
1151
-lazy_refcounts Postpone refcount updates
1152
-refcount_bits Width of a reference count entry in bits
1153
+ backing_file=<str> - File name of a base image
1154
+ backing_fmt=<str> - Image format of the base image
1155
+ cluster_size=<size> - qcow2 cluster size
1156
+ compat=<str> - Compatibility level (0.10 or 1.1)
1157
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
1158
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
1159
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
1160
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
1161
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
1162
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
1163
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
1164
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
1165
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
1166
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
1167
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
1168
+ refcount_bits=<num> - Width of a reference count entry in bits
1169
+ size=<size> - Virtual disk size
1170
1171
Note that not all of these options may be amendable.
1172
1173
@@ -XXX,XX +XXX,XX @@ qemu-img: Invalid option list: ,,
1174
1175
Testing: amend -f qcow2 -o help
1176
Creation options for 'qcow2':
1177
-size Virtual disk size
1178
-compat Compatibility level (0.10 or 1.1)
1179
-backing_file File name of a base image
1180
-backing_fmt Image format of the base image
1181
-encryption Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
1182
-encrypt.format Encrypt the image, format choices: 'aes', 'luks'
1183
-encrypt.key-secret ID of secret providing qcow AES key or LUKS passphrase
1184
-encrypt.cipher-alg Name of encryption cipher algorithm
1185
-encrypt.cipher-mode Name of encryption cipher mode
1186
-encrypt.ivgen-alg Name of IV generator algorithm
1187
-encrypt.ivgen-hash-alg Name of IV generator hash algorithm
1188
-encrypt.hash-alg Name of encryption hash algorithm
1189
-encrypt.iter-time Time to spend in PBKDF in milliseconds
1190
-cluster_size qcow2 cluster size
1191
-preallocation Preallocation mode (allowed values: off, metadata, falloc, full)
1192
-lazy_refcounts Postpone refcount updates
1193
-refcount_bits Width of a reference count entry in bits
1194
+ backing_file=<str> - File name of a base image
1195
+ backing_fmt=<str> - Image format of the base image
1196
+ cluster_size=<size> - qcow2 cluster size
1197
+ compat=<str> - Compatibility level (0.10 or 1.1)
1198
+ encrypt.cipher-alg=<str> - Name of encryption cipher algorithm
1199
+ encrypt.cipher-mode=<str> - Name of encryption cipher mode
1200
+ encrypt.format=<str> - Encrypt the image, format choices: 'aes', 'luks'
1201
+ encrypt.hash-alg=<str> - Name of encryption hash algorithm
1202
+ encrypt.iter-time=<num> - Time to spend in PBKDF in milliseconds
1203
+ encrypt.ivgen-alg=<str> - Name of IV generator algorithm
1204
+ encrypt.ivgen-hash-alg=<str> - Name of IV generator hash algorithm
1205
+ encrypt.key-secret=<str> - ID of secret providing qcow AES key or LUKS passphrase
1206
+ encryption=<bool (on/off)> - Encrypt the image with format 'aes'. (Deprecated in favor of encrypt.format=aes)
1207
+ lazy_refcounts=<bool (on/off)> - Postpone refcount updates
1208
+ preallocation=<str> - Preallocation mode (allowed values: off, metadata, falloc, full)
1209
+ refcount_bits=<num> - Width of a reference count entry in bits
1210
+ size=<size> - Virtual disk size
1211
1212
Note that not all of these options may be amendable.
1213
1214
Testing: convert -o help
1215
Supported options:
1216
-size Virtual disk size
1217
+ size=<size> - Virtual disk size
1218
1219
Testing: amend -f bochs -o help
1220
qemu-img: Format driver 'bochs' does not support option amendment
37
--
1221
--
38
2.13.6
1222
2.19.1
39
1223
40
1224
diff view generated by jsdifflib
New patch
1
From: Max Reitz <mreitz@redhat.com>
1
2
3
Following the example of qemu_opts_print_help(), indent all entries in
4
the list of character devices.
5
6
Signed-off-by: Max Reitz <mreitz@redhat.com>
7
Reviewed-by: Marc-André Lureau <marcandre.lureau@redhat.com>
8
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
9
---
10
chardev/char.c | 2 +-
11
1 file changed, 1 insertion(+), 1 deletion(-)
12
13
diff --git a/chardev/char.c b/chardev/char.c
14
index XXXXXXX..XXXXXXX 100644
15
--- a/chardev/char.c
16
+++ b/chardev/char.c
17
@@ -XXX,XX +XXX,XX @@ help_string_append(const char *name, void *opaque)
18
{
19
GString *str = opaque;
20
21
- g_string_append_printf(str, "\n%s", name);
22
+ g_string_append_printf(str, "\n %s", name);
23
}
24
25
static const char *chardev_alias_translate(const char *name)
26
--
27
2.19.1
28
29
diff view generated by jsdifflib
1
From: Eric Blake <eblake@redhat.com>
1
From: Max Reitz <mreitz@redhat.com>
2
2
3
We are gradually moving away from sector-based interfaces, towards
3
Just like in qemu_opts_print_help(), print the device name as a caption
4
byte-based. Make the change for the last few sector-based calls
4
instead of on every single line, indent all options, add angle brackets
5
into the block layer from the replication driver.
5
around types, and align the descriptions after 24 characters. Also,
6
separate the descriptions with " - " instead of putting them in
7
parentheses, because that is what we do everywhere else. This does look
8
a bit funny here because basically all bits have the description
9
"on/off", but funny does not mean it is less readable.
6
10
7
Ideally, the replication driver should switch to doing everything
11
Signed-off-by: Max Reitz <mreitz@redhat.com>
8
byte-based, but that's a more invasive change that requires a
12
Reviewed-by: Marc-André Lureau <marcandre.lureau@redhat.com>
9
bit more auditing.
10
11
Signed-off-by: Eric Blake <eblake@redhat.com>
12
Reviewed-by: Jeff Cody <jcody@redhat.com>
13
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
13
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
14
---
14
---
15
block/replication.c | 14 ++++++++------
15
qdev-monitor.c | 13 +++++++++++--
16
1 file changed, 8 insertions(+), 6 deletions(-)
16
1 file changed, 11 insertions(+), 2 deletions(-)
17
17
18
diff --git a/block/replication.c b/block/replication.c
18
diff --git a/qdev-monitor.c b/qdev-monitor.c
19
index XXXXXXX..XXXXXXX 100644
19
index XXXXXXX..XXXXXXX 100644
20
--- a/block/replication.c
20
--- a/qdev-monitor.c
21
+++ b/block/replication.c
21
+++ b/qdev-monitor.c
22
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int replication_co_readv(BlockDriverState *bs,
22
@@ -XXX,XX +XXX,XX @@ int qdev_device_help(QemuOpts *opts)
23
backup_cow_request_begin(&req, child->bs->job,
23
goto error;
24
sector_num * BDRV_SECTOR_SIZE,
25
remaining_bytes);
26
- ret = bdrv_co_readv(bs->file, sector_num, remaining_sectors,
27
- qiov);
28
+ ret = bdrv_co_preadv(bs->file, sector_num * BDRV_SECTOR_SIZE,
29
+ remaining_bytes, qiov, 0);
30
backup_cow_request_end(&req);
31
goto out;
32
}
24
}
33
25
34
- ret = bdrv_co_readv(bs->file, sector_num, remaining_sectors, qiov);
26
+ if (prop_list) {
35
+ ret = bdrv_co_preadv(bs->file, sector_num * BDRV_SECTOR_SIZE,
27
+ out_printf("%s options:\n", driver);
36
+ remaining_sectors * BDRV_SECTOR_SIZE, qiov, 0);
28
+ } else {
37
out:
29
+ out_printf("There are no options for %s.\n", driver);
38
return replication_return_value(s, ret);
30
+ }
39
}
31
for (prop = prop_list; prop; prop = prop->next) {
40
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int replication_co_writev(BlockDriverState *bs,
32
- out_printf("%s.%s=%s", driver, prop->value->name, prop->value->type);
41
}
33
+ int len;
42
34
+ out_printf(" %s=<%s>%n", prop->value->name, prop->value->type, &len);
43
if (ret == 0) {
35
if (prop->value->has_description) {
44
- ret = bdrv_co_writev(top, sector_num,
36
- out_printf(" (%s)\n", prop->value->description);
45
- remaining_sectors, qiov);
37
+ if (len < 24) {
46
+ ret = bdrv_co_pwritev(top, sector_num * BDRV_SECTOR_SIZE,
38
+ out_printf("%*s", 24 - len, "");
47
+ remaining_sectors * BDRV_SECTOR_SIZE, qiov, 0);
39
+ }
48
return replication_return_value(s, ret);
40
+ out_printf(" - %s\n", prop->value->description);
49
}
41
} else {
50
42
out_printf("\n");
51
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int replication_co_writev(BlockDriverState *bs,
52
qemu_iovec_concat(&hd_qiov, qiov, bytes_done, count);
53
54
target = ret ? top : base;
55
- ret = bdrv_co_writev(target, sector_num, n, &hd_qiov);
56
+ ret = bdrv_co_pwritev(target, sector_num * BDRV_SECTOR_SIZE,
57
+ n * BDRV_SECTOR_SIZE, &hd_qiov, 0);
58
if (ret < 0) {
59
goto out1;
60
}
43
}
61
--
44
--
62
2.13.6
45
2.19.1
63
46
64
47
diff view generated by jsdifflib
1
From: Eric Blake <eblake@redhat.com>
1
From: Max Reitz <mreitz@redhat.com>
2
2
3
We are gradually moving away from sector-based interfaces, towards
3
Just like in qemu_opts_print_help(), print the object name as a caption
4
byte-based. Make the change for the internal helper function
4
instead of on every single line, indent all options, add angle brackets
5
get_cluster_offset(), by changing n_start and n_end to be byte
5
around types, and align the descriptions after 24 characters.
6
offsets rather than sector indices within the cluster being
7
allocated. However, assert that these values are still
8
sector-aligned (at least qcrypto_block_encrypt() still wants that).
9
For now we get that alignment for free because we still use
10
sector-based driver callbacks.
11
6
12
A later patch will then switch the qcow driver as a whole over
7
Also, indent every object name in the list of available objects.
13
to byte-based operation; but will still leave things at sector
14
alignments as it is not worth auditing the qcow image format
15
to worry about sub-sector requests.
16
8
17
Signed-off-by: Eric Blake <eblake@redhat.com>
9
Signed-off-by: Max Reitz <mreitz@redhat.com>
18
Reviewed-by: Jeff Cody <jcody@redhat.com>
10
Reviewed-by: Marc-André Lureau <marcandre.lureau@redhat.com>
19
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
11
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
20
---
12
---
21
block/qcow.c | 29 +++++++++++++++--------------
13
vl.c | 13 ++++++++++---
22
1 file changed, 15 insertions(+), 14 deletions(-)
14
1 file changed, 10 insertions(+), 3 deletions(-)
23
15
24
diff --git a/block/qcow.c b/block/qcow.c
16
diff --git a/vl.c b/vl.c
25
index XXXXXXX..XXXXXXX 100644
17
index XXXXXXX..XXXXXXX 100644
26
--- a/block/qcow.c
18
--- a/vl.c
27
+++ b/block/qcow.c
19
+++ b/vl.c
28
@@ -XXX,XX +XXX,XX @@ static int qcow_reopen_prepare(BDRVReopenState *state,
20
@@ -XXX,XX +XXX,XX @@ static bool object_create_initial(const char *type, QemuOpts *opts)
29
*
21
list = object_class_get_list_sorted(TYPE_USER_CREATABLE, false);
30
* 0 to not allocate.
22
for (l = list; l != NULL; l = l->next) {
31
*
23
ObjectClass *oc = OBJECT_CLASS(l->data);
32
- * 1 to allocate a normal cluster (for sector indexes 'n_start' to
24
- printf("%s\n", object_class_get_name(oc));
33
- * 'n_end')
25
+ printf(" %s\n", object_class_get_name(oc));
34
+ * 1 to allocate a normal cluster (for sector-aligned byte offsets 'n_start'
35
+ * to 'n_end' within the cluster)
36
*
37
* 2 to allocate a compressed cluster of size
38
* 'compressed_size'. 'compressed_size' must be > 0 and <
39
@@ -XXX,XX +XXX,XX @@ static int get_cluster_offset(BlockDriverState *bs,
40
if (!allocate)
41
return 0;
42
BLKDBG_EVENT(bs->file, BLKDBG_CLUSTER_ALLOC);
43
+ assert(QEMU_IS_ALIGNED(n_start | n_end, BDRV_SECTOR_SIZE));
44
/* allocate a new cluster */
45
if ((cluster_offset & QCOW_OFLAG_COMPRESSED) &&
46
- (n_end - n_start) < s->cluster_sectors) {
47
+ (n_end - n_start) < s->cluster_size) {
48
/* if the cluster is already compressed, we must
49
decompress it in the case it is not completely
50
overwritten */
51
@@ -XXX,XX +XXX,XX @@ static int get_cluster_offset(BlockDriverState *bs,
52
/* if encrypted, we must initialize the cluster
53
content which won't be written */
54
if (bs->encrypted &&
55
- (n_end - n_start) < s->cluster_sectors) {
56
- uint64_t start_sect;
57
+ (n_end - n_start) < s->cluster_size) {
58
+ uint64_t start_offset;
59
assert(s->crypto);
60
- start_sect = (offset & ~(s->cluster_size - 1)) >> 9;
61
- for(i = 0; i < s->cluster_sectors; i++) {
62
+ start_offset = offset & ~(s->cluster_size - 1);
63
+ for (i = 0; i < s->cluster_size; i += BDRV_SECTOR_SIZE) {
64
if (i < n_start || i >= n_end) {
65
- memset(s->cluster_data, 0x00, 512);
66
+ memset(s->cluster_data, 0x00, BDRV_SECTOR_SIZE);
67
if (qcrypto_block_encrypt(s->crypto,
68
- (start_sect + i) *
69
- BDRV_SECTOR_SIZE,
70
+ start_offset + i,
71
s->cluster_data,
72
BDRV_SECTOR_SIZE,
73
NULL) < 0) {
74
@@ -XXX,XX +XXX,XX @@ static int get_cluster_offset(BlockDriverState *bs,
75
}
76
BLKDBG_EVENT(bs->file, BLKDBG_WRITE_AIO);
77
ret = bdrv_pwrite(bs->file,
78
- cluster_offset + i * 512,
79
- s->cluster_data, 512);
80
+ cluster_offset + i,
81
+ s->cluster_data,
82
+ BDRV_SECTOR_SIZE);
83
if (ret < 0) {
84
return ret;
85
}
86
@@ -XXX,XX +XXX,XX @@ static coroutine_fn int qcow_co_writev(BlockDriverState *bs, int64_t sector_num,
87
n = nb_sectors;
88
}
26
}
89
ret = get_cluster_offset(bs, sector_num << 9, 1, 0,
27
g_slist_free(list);
90
- index_in_cluster,
28
exit(0);
91
- index_in_cluster + n, &cluster_offset);
29
@@ -XXX,XX +XXX,XX @@ static bool object_create_initial(const char *type, QemuOpts *opts)
92
+ index_in_cluster << 9,
30
}
93
+ (index_in_cluster + n) << 9, &cluster_offset);
31
94
if (ret < 0) {
32
str = g_string_new(NULL);
95
break;
33
- g_string_append_printf(str, "%s.%s=%s", type,
34
- prop->name, prop->type);
35
+ g_string_append_printf(str, " %s=<%s>", prop->name, prop->type);
36
if (prop->description) {
37
+ if (str->len < 24) {
38
+ g_string_append_printf(str, "%*s", 24 - (int)str->len, "");
39
+ }
40
g_string_append_printf(str, " - %s", prop->description);
41
}
42
g_ptr_array_add(array, g_string_free(str, false));
43
}
44
g_ptr_array_sort(array, (GCompareFunc)qemu_pstrcmp0);
45
+ if (array->len > 0) {
46
+ printf("%s options:\n", type);
47
+ } else {
48
+ printf("There are no options for %s.\n", type);
49
+ }
50
for (i = 0; i < array->len; i++) {
51
printf("%s\n", (char *)array->pdata[i]);
96
}
52
}
97
--
53
--
98
2.13.6
54
2.19.1
99
55
100
56
diff view generated by jsdifflib
1
From: Fam Zheng <famz@redhat.com>
1
From: Max Reitz <mreitz@redhat.com>
2
2
3
EINTR should be checked against errno, not ret. While fixing the bug,
3
There is no good reason why there should be a newline in this
4
collect the branches with a switch block.
4
description, so remove it.
5
5
6
Also, change the return value from -ENOSTUP to -ENOSPC when the actual
6
Signed-off-by: Max Reitz <mreitz@redhat.com>
7
issue is request range passes EOF, which should be distinguishable from
7
Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
8
the case of error == ENOSYS by the caller, so that it could still retry
8
Reviewed-by: Marc-André Lureau <marcandre.lureau@redhat.com>
9
with other byte ranges, whereas it shouldn't retry anymore upon ENOSYS.
10
11
Signed-off-by: Fam Zheng <famz@redhat.com>
12
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
9
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
13
---
10
---
14
block/file-posix.c | 17 +++++++++--------
11
vl.c | 2 +-
15
1 file changed, 9 insertions(+), 8 deletions(-)
12
1 file changed, 1 insertion(+), 1 deletion(-)
16
13
17
diff --git a/block/file-posix.c b/block/file-posix.c
14
diff --git a/vl.c b/vl.c
18
index XXXXXXX..XXXXXXX 100644
15
index XXXXXXX..XXXXXXX 100644
19
--- a/block/file-posix.c
16
--- a/vl.c
20
+++ b/block/file-posix.c
17
+++ b/vl.c
21
@@ -XXX,XX +XXX,XX @@ static ssize_t handle_aiocb_copy_range(RawPosixAIOData *aiocb)
18
@@ -XXX,XX +XXX,XX @@ static QemuOptsList qemu_fw_cfg_opts = {
22
ssize_t ret = copy_file_range(aiocb->aio_fildes, &in_off,
19
}, {
23
aiocb->aio_fd2, &out_off,
20
.name = "file",
24
bytes, 0);
21
.type = QEMU_OPT_STRING,
25
- if (ret == -EINTR) {
22
- .help = "Sets the name of the file from which\n"
26
- continue;
23
+ .help = "Sets the name of the file from which "
27
+ if (ret == 0) {
24
"the fw_cfg blob will be loaded",
28
+ /* No progress (e.g. when beyond EOF), let the caller fall back to
25
}, {
29
+ * buffer I/O. */
26
.name = "string",
30
+ return -ENOSPC;
31
}
32
if (ret < 0) {
33
- if (errno == ENOSYS) {
34
+ switch (errno) {
35
+ case ENOSYS:
36
return -ENOTSUP;
37
- } else {
38
+ case EINTR:
39
+ continue;
40
+ default:
41
return -errno;
42
}
43
}
44
- if (!ret) {
45
- /* No progress (e.g. when beyond EOF), fall back to buffer I/O. */
46
- return -ENOTSUP;
47
- }
48
bytes -= ret;
49
}
50
return 0;
51
--
27
--
52
2.13.6
28
2.19.1
53
29
54
30
diff view generated by jsdifflib
1
From: Weiping Zhang <zhangweiping@didichuxing.com>
1
From: Leonid Bloch <lbloch@janustech.com>
2
2
3
Add an optional paramter num_queues for device, and set it
3
If an expression is used to define DEFAULT_CLUSTER_SIZE, when compiled,
4
to 64 by default.
4
it will be embedded as a literal expression in the binary (as the
5
default value) because it is stringified to mark the size of the default
6
value. Now this is fixed by using a defined number to define this value.
5
7
6
Signed-off-by: Weiping Zhang <zhangweiping@didichuxing.com>
8
Signed-off-by: Leonid Bloch <lbloch@janustech.com>
7
Acked-by: Keith Busch <keith.busch@intel.com>
9
Reviewed-by: Stefan Weil <sw@weilnetz.de>
8
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
10
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
9
---
11
---
10
hw/block/nvme.c | 5 +++--
12
block/vdi.c | 4 ++--
11
1 file changed, 3 insertions(+), 2 deletions(-)
13
1 file changed, 2 insertions(+), 2 deletions(-)
12
14
13
diff --git a/hw/block/nvme.c b/hw/block/nvme.c
15
diff --git a/block/vdi.c b/block/vdi.c
14
index XXXXXXX..XXXXXXX 100644
16
index XXXXXXX..XXXXXXX 100644
15
--- a/hw/block/nvme.c
17
--- a/block/vdi.c
16
+++ b/hw/block/nvme.c
18
+++ b/block/vdi.c
17
@@ -XXX,XX +XXX,XX @@
19
@@ -XXX,XX +XXX,XX @@
18
* Usage: add options:
20
#define BLOCK_OPT_STATIC "static"
19
* -drive file=<file>,if=none,id=<drive_id>
21
20
* -device nvme,drive=<drive_id>,serial=<serial>,id=<id[optional]>, \
22
#define SECTOR_SIZE 512
21
- * cmb_size_mb=<cmb_size_mb[optional]>
23
-#define DEFAULT_CLUSTER_SIZE (1 * MiB)
22
+ * cmb_size_mb=<cmb_size_mb[optional]>, \
24
+#define DEFAULT_CLUSTER_SIZE S_1MiB
23
+ * num_queues=<N[optional]>
25
24
*
26
#if defined(CONFIG_VDI_DEBUG)
25
* Note cmb_size_mb denotes size of CMB in MB. CMB is assumed to be at
27
#define VDI_DEBUG 1
26
* offset 0 in BAR2 and supports only WDS, RDS and SQS for now.
28
@@ -XXX,XX +XXX,XX @@ static int vdi_open(BlockDriverState *bs, QDict *options, int flags,
27
@@ -XXX,XX +XXX,XX @@ static void nvme_realize(PCIDevice *pci_dev, Error **errp)
29
goto fail;
28
pcie_endpoint_cap_init(&n->parent_obj, 0x80);
30
} else if (header.block_size != DEFAULT_CLUSTER_SIZE) {
29
31
error_setg(errp, "unsupported VDI image (block size %" PRIu32
30
n->num_namespaces = 1;
32
- " is not %" PRIu64 ")",
31
- n->num_queues = 64;
33
+ " is not %" PRIu32 ")",
32
n->reg_size = pow2ceil(0x1004 + 2 * (n->num_queues + 1) * 4);
34
header.block_size, DEFAULT_CLUSTER_SIZE);
33
n->ns_size = bs_size / (uint64_t)n->num_namespaces;
35
ret = -ENOTSUP;
34
36
goto fail;
35
@@ -XXX,XX +XXX,XX @@ static Property nvme_props[] = {
36
DEFINE_BLOCK_PROPERTIES(NvmeCtrl, conf),
37
DEFINE_PROP_STRING("serial", NvmeCtrl, serial),
38
DEFINE_PROP_UINT32("cmb_size_mb", NvmeCtrl, cmb_size_mb, 0),
39
+ DEFINE_PROP_UINT32("num_queues", NvmeCtrl, num_queues, 64),
40
DEFINE_PROP_END_OF_LIST(),
41
};
42
43
--
37
--
44
2.13.6
38
2.19.1
45
39
46
40
diff view generated by jsdifflib
1
From: Markus Armbruster <armbru@redhat.com>
1
From: Leonid Bloch <lbloch@janustech.com>
2
2
3
Commit f1b34a248e9 replaced less-than-obvious test in
3
The lookup table for power-of-two sizes was added in commit 540b8492618eb
4
qdict_flatten_qdict() by the obvious one. Sadly, it made something
4
for the purpose of having convenient shortcuts for these sizes in cases
5
else non-obvious: the fact that @new_key passed to qdict_put_obj()
5
when the literal number has to be present at compile time, and
6
can't be null, because that depends on the function's precondition
6
expressions as '(1 * KiB)' can not be used. One such case is the
7
(target == qdict) == !prefix.
7
stringification of sizes. Beyond that, it is convenient to use these
8
shortcuts for all power-of-two sizes, even if they don't have to be
9
literal numbers.
8
10
9
Tweak the function some more to help Coverity and human readers alike.
11
Despite its convenience, this table introduced 55 lines of "dumb" code,
12
the purpose and origin of which are obscure without reading the message
13
of the commit which introduced it. This patch fixes that by adding a
14
comment to the code itself with a brief explanation for the reasoning
15
behind this table. This comment includes the short AWK script that
16
generated the table, so that anyone who's interested could make sure
17
that the values in it are correct (otherwise these values look as if
18
they were typed manually).
10
19
11
Fixes: CID 1393620
20
Signed-off-by: Leonid Bloch <lbloch@janustech.com>
12
Signed-off-by: Markus Armbruster <armbru@redhat.com>
13
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
21
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
14
---
22
---
15
qobject/block-qdict.c | 16 ++++++++--------
23
include/qemu/units.h | 18 ++++++++++++++++++
16
1 file changed, 8 insertions(+), 8 deletions(-)
24
1 file changed, 18 insertions(+)
17
25
18
diff --git a/qobject/block-qdict.c b/qobject/block-qdict.c
26
diff --git a/include/qemu/units.h b/include/qemu/units.h
19
index XXXXXXX..XXXXXXX 100644
27
index XXXXXXX..XXXXXXX 100644
20
--- a/qobject/block-qdict.c
28
--- a/include/qemu/units.h
21
+++ b/qobject/block-qdict.c
29
+++ b/include/qemu/units.h
22
@@ -XXX,XX +XXX,XX @@ static void qdict_flatten_qdict(QDict *qdict, QDict *target, const char *prefix)
30
@@ -XXX,XX +XXX,XX @@
23
const QDictEntry *entry, *next;
31
#define PiB (INT64_C(1) << 50)
24
QDict *dict_val;
32
#define EiB (INT64_C(1) << 60)
25
QList *list_val;
33
26
- char *new_key;
34
+/*
27
+ char *key, *new_key;
35
+ * The following lookup table is intended to be used when a literal string of
28
36
+ * the number of bytes is required (for example if it needs to be stringified).
29
entry = qdict_first(qdict);
37
+ * It can also be used for generic shortcuts of power-of-two sizes.
30
38
+ * This table is generated using the AWK script below:
31
@@ -XXX,XX +XXX,XX @@ static void qdict_flatten_qdict(QDict *qdict, QDict *target, const char *prefix)
39
+ *
32
value = qdict_entry_value(entry);
40
+ * BEGIN {
33
dict_val = qobject_to(QDict, value);
41
+ * suffix="KMGTPE";
34
list_val = qobject_to(QList, value);
42
+ * for(i=10; i<64; i++) {
35
- new_key = NULL;
43
+ * val=2**i;
36
44
+ * s=substr(suffix, int(i/10), 1);
37
if (prefix) {
45
+ * n=2**(i%10);
38
- new_key = g_strdup_printf("%s.%s", prefix, entry->key);
46
+ * pad=21-int(log(n)/log(10));
39
+ key = new_key = g_strdup_printf("%s.%s", prefix, entry->key);
47
+ * printf("#define S_%d%siB %*d\n", n, s, pad, val);
40
+ } else {
48
+ * }
41
+ key = entry->key;
49
+ * }
42
+ new_key = NULL;
50
+ */
43
}
51
+
44
52
#define S_1KiB 1024
45
/*
53
#define S_2KiB 2048
46
@@ -XXX,XX +XXX,XX @@ static void qdict_flatten_qdict(QDict *qdict, QDict *target, const char *prefix)
54
#define S_4KiB 4096
47
* well advised not to modify them altogether.)
48
*/
49
if (dict_val && qdict_size(dict_val)) {
50
- qdict_flatten_qdict(dict_val, target,
51
- new_key ? new_key : entry->key);
52
+ qdict_flatten_qdict(dict_val, target, key);
53
if (target == qdict) {
54
qdict_del(qdict, entry->key);
55
}
56
} else if (list_val && !qlist_empty(list_val)) {
57
- qdict_flatten_qlist(list_val, target,
58
- new_key ? new_key : entry->key);
59
+ qdict_flatten_qlist(list_val, target, key);
60
if (target == qdict) {
61
qdict_del(qdict, entry->key);
62
}
63
} else if (target != qdict) {
64
- qdict_put_obj(target, new_key, qobject_ref(value));
65
+ qdict_put_obj(target, key, qobject_ref(value));
66
}
67
68
g_free(new_key);
69
--
55
--
70
2.13.6
56
2.19.1
71
57
72
58
diff view generated by jsdifflib