[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: [Qemu-devel] [PATCH V13 5/6] add-cow file format core code.
From: |
Stefan Hajnoczi |
Subject: |
Re: [Qemu-devel] [PATCH V13 5/6] add-cow file format core code. |
Date: |
Mon, 22 Oct 2012 11:29:51 +0200 |
User-agent: |
Mutt/1.5.21 (2010-09-15) |
On Thu, Oct 18, 2012 at 05:51:34PM +0800, Dong Xu Wang wrote:
> +static void add_cow_header_cpu_to_le(const AddCowHeader *cpu, AddCowHeader
> *le)
> +{
> + le->magic = cpu_to_le64(cpu->magic);
> + le->version = cpu_to_le32(cpu->version);
> +
> + le->backing_filename_offset =
> cpu_to_le32(cpu->backing_filename_offset);
> + le->backing_filename_size =
> cpu_to_le32(cpu->backing_filename_size);
> +
> + le->image_filename_offset =
> cpu_to_le32(cpu->image_filename_offset);
> + le->image_filename_size = cpu_to_le32(cpu->image_filename_size);
> +
> + le->cluster_bits = cpu_to_le32(cpu->cluster_bits);
> + le->features = cpu_to_le64(cpu->features);
> + le->optional_features = cpu_to_le64(cpu->optional_features);
> + le->header_pages_size = cpu_to_le32(cpu->header_pages_size);
> + memcpy(le->backing_fmt, cpu->backing_fmt, sizeof(cpu->backing_fmt));
> + memcpy(le->image_fmt, cpu->image_fmt, sizeof(cpu->image_fmt));
Minor style issue: sizeof(le->backing_fmt) is safer than
sizeof(cpu->image_fmt) in case the types change or this code is
copy-pasted elsewhere. Always use the size of the destination buffer.
> +}
> +
> +static int add_cow_probe(const uint8_t *buf, int buf_size, const char
> *filename)
> +{
> + const AddCowHeader *header = (const AddCowHeader *)buf;
> +
In case .bdrv_probe() is exposed in a future stand-alone block libary
like libqblock.so where we cannot make assumptions about buf_size:
if (buf_size < sizeof(*header)) {
return 0;
}
> + ret = bdrv_file_open(&bs, filename, BDRV_O_RDWR);
> + if (ret < 0) {
> + return ret;
> + }
> + snprintf(header.backing_fmt, sizeof(header.backing_fmt),
> + "%s", backing_fmt ? backing_fmt : "");
> + snprintf(header.image_fmt, sizeof(header.image_fmt),
> + "%s", image_format ? image_format : "raw");
> + add_cow_header_cpu_to_le(&header, &le_header);
> + ret = bdrv_pwrite(bs, 0, &le_header, sizeof(le_header));
> + if (ret < 0) {
> + bdrv_delete(bs);
> + return ret;
> + }
Once...
> + if (ret < 0) {
> + bdrv_delete(bs);
> + return ret;
> + }
...twice. This can be dropped.
> +
> + if (backing_filename) {
> + ret = bdrv_pwrite(bs, header.backing_filename_offset,
> + backing_filename, header.backing_filename_size);
> + if (ret < 0) {
> + bdrv_delete(bs);
> + return ret;
> + }
> + }
> +
> + ret = bdrv_pwrite(bs, header.image_filename_offset,
> + image_filename, header.image_filename_size);
> + if (ret < 0) {
> + bdrv_delete(bs);
> + return ret;
> + }
I suggest writing the image filename before the backing filename so it's
easier to implement .bdrv_change_backing_file() in the future.
> +
> + ret = bdrv_open(bs, filename, BDRV_O_RDWR | BDRV_O_NO_FLUSH, drv);
Forgot to bdrv_close(bs) before opening as add-cow.
> + if ((s->header.features & ADD_COW_F_ALL_ALLOCATED) == 0) {
> + ret = bdrv_read_string(bs->file, sizeof(s->header),
> + sizeof(bs->backing_format) - 1,
> + bs->backing_format,
> + sizeof(bs->backing_format));
This looks wrong:
1. The header contains the backing format field, we've already read it.
Now we just need to put a NUL-terminated string into
bs->backing_format. No need for bdrv_read_string().
2. offset = sizeof(s->header) does not make sense because the
backing_format field is part of the header.
3. n = sizeof(bs->backing_format) - 1 should be the size of the header
backing_format field, not the destination buffer.
I'm wondering if I missed something or why add-cow files open
successfully in your testing, because I think this line of code would
cause it to use a junk bs->backing_format.
> + s->image_hd = bdrv_new("");
> + if (path_has_protocol(image_filename)) {
image_filename[] is uninitialized. Did you mean tmp_name?
> + pstrcpy(image_filename, sizeof(image_filename), tmp_name);
> + } else {
> + path_combine(image_filename, sizeof(image_filename),
> + bs->filename, tmp_name);
> + }
> +
> + ret = bdrv_open(s->image_hd, image_filename, flags, NULL);
What about header->image_format?
> + if (ret < 0) {
> + bdrv_delete(s->image_hd);
> + goto fail;
> + }
> +
> + bs->total_sectors = bdrv_getlength(s->image_hd) >> 9;
/ BDRV_SECTOR_SIZE
> + s->cluster_size = 1 << s->header.cluster_bits;
> + sector_per_byte = SECTORS_PER_CLUSTER * 8;
SECTORS_PER_CLUSTER does not take s->cluster_size into account.
The add_cow_open() issues should have been visible during
development/testing (backing_format, unitialized image_filename[],
unused header->image_format, SECTORS_PER_CLUSTER). It looks like not
much testing of image creation options has been done. I'll review more
of this series in the next version, please test more.
Stefan
- [Qemu-devel] [PATCH V13 2/6] make path_has_protocol non static, (continued)
- [Qemu-devel] [PATCH V13 2/6] make path_has_protocol non static, Dong Xu Wang, 2012/10/18
- [Qemu-devel] [PATCH V13 1/6] docs: document for add-cow file format, Dong Xu Wang, 2012/10/18
- [Qemu-devel] [PATCH V13 3/6] qed_read_string to bdrv_read_string, Dong Xu Wang, 2012/10/18
- [Qemu-devel] [PATCH V13 6/6] qemu-iotests: add add-cow iotests support., Dong Xu Wang, 2012/10/18
- [Qemu-devel] [PATCH V13 4/6] rename qcow2-cache.c to block-cache.c, Dong Xu Wang, 2012/10/18
- [Qemu-devel] [PATCH V13 5/6] add-cow file format core code., Dong Xu Wang, 2012/10/18
- Re: [Qemu-devel] [PATCH V13 5/6] add-cow file format core code.,
Stefan Hajnoczi <=