Patchwork [2/5] block: Virtual Bridges VERDE GOW disk image format data structures and common MACROs

login
register
mail settings
Submitter Leonardo E. Reiter
Date March 8, 2012, 10:14 p.m.
Message ID <CA+BHXkLdm7kaS97UPKurVWXSvrADQcAAfE8=0-H9RET8fMRcHA@mail.gmail.com>
Download mbox | patch
Permalink /patch/145664/
State New
Headers show

Comments

Leonardo E. Reiter - March 8, 2012, 10:14 p.m.
commit 2947e89cc581285eb74badc80a30300ee9b9a96b
Author: Leonardo E. Reiter <lreiter@vbridges.com>
Date:   Thu Mar 8 16:00:44 2012 -0600

    define data structures and common MACROs for GOW disk image format
implementation
    Signed-off-by: Leonardo E. Reiter <lreiter@vbridges.com>

+#define BLOCK_NUM(s)        ((s << 9) / GOW_BLOCKSIZE)
+#define BLOCK_OFFSET(s)     ((s << 9) % GOW_BLOCKSIZE)
+#define BLOCK_SECTORS(o)    ((GOW_BLOCKSIZE - o) >> 9)
+#define IMG_OFFSET(b, o) \
+    ((int64_t) ((int64_t) le32_to_cpu(s->header->map[b]) * \
+        (int64_t) GOW_BLOCKSIZE) + (int64_t) o + s->base)
+
+#endif  /* BLOCK_GOW_INT_H */
+
Stefan Hajnoczi - March 9, 2012, 11:02 a.m.
On Thu, Mar 8, 2012 at 10:14 PM, Leonardo E. Reiter
<lreiter@vbridges.com> wrote:
> +#if defined(BLOCK_GOW1)
> +#define GOW_MAGIC       GOW1_MAGIC
> +#define GOW_MAXBLOCKS   1048576
> +
> +/* GOW1: header is not padded */
> +/* header type, contains map */
> +typedef struct {
> +    uint32_t magic;
> +    uint32_t size;
> +    uint32_t allocated;
> +    uint32_t map[GOW_MAXBLOCKS];
> +} gow_header_t;
> +
> +/* block type, contains data */
> +typedef struct {
> +    uint8_t data[GOW_BLOCKSIZE];
> +} gow_block_t;
> +#else /* GOW2, GOW3 below */
> +
> +
> +/* GOW2: approximately 16MB header size, and up to 256GB image size
> + * GOW3: approximately 32MB header size, and up to 256GB image size */
> +
> +#define GOW_MAXBLOCKS   4194304
> +
> +typedef struct {
> +    uint32_t magic;
> +    uint32_t size;
> +    uint32_t allocated;
> +    uint32_t map[GOW_MAXBLOCKS];
> +} gow2_header_t;
> +
> +typedef struct {
> +    uint32_t magic;
> +    uint32_t size;
> +    uint32_t allocated;
> +    uint32_t map[GOW_MAXBLOCKS];
> +    uint32_t ver[GOW_MAXBLOCKS];
> +    uint32_t carry;
> +    uint8_t  signature[32];
> +    uint32_t maint;
> +} gow3_header_t;
> +
> +/* header is padded to 512-bytes so image can be indexed in sectors */
> +#define GOW2_HEADER_SIZE (((sizeof(gow2_header_t) + 511) >> 9) << 9)
> +#define GOW3_HEADER_SIZE (((sizeof(gow3_header_t) + 511) >> 9) << 9)
> +
> +#endif /* GOW2, GOW3 */
> +
> +#if defined(BLOCK_GOW1)
> +
> +#define GOW_HEADER_SIZE (sizeof(gow_header_t))
> +
> +#elif defined(BLOCK_GOW2)
> +
> +#define GOW_MAGIC       GOW2_MAGIC
> +#define GOW_HEADER_SIZE GOW2_HEADER_SIZE
> +#define gow_header_t gow2_header_t
> +
> +#elif defined(BLOCK_GOW3)
> +
> +#define GOW_MAGIC       GOW3_MAGIC
> +#define gow_header_t gow3_header_t
> +#define GOW_HEADER_SIZE GOW3_HEADER_SIZE
> +
> +#endif

This #ifdef approach is ugly.  All three headers have the same
starting common fields.

I bet you could have clean C code without reincluding this header and
using macro tricks.  Just use the common header fields and
parameterize the size, if needed.

Stefan

Patch

diff --git a/block/gow_int.h b/block/gow_int.h
new file mode 100644
index 0000000..ca5dd8a
--- /dev/null
+++ b/block/gow_int.h
@@ -0,0 +1,115 @@ 
+/*
+ * Virtual Bridges Grow-on-Write block driver for QEMU, common definitions
+ *
+ * Copyright (c) 2008-2009 Leonardo E. Reiter
+ * Copyright (c) 1984-2012 Virtual Bridges, Inc.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
copy
+ * of this software and associated documentation files (the "Software"),
to deal
+ * in the Software without restriction, including without limitation the
rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or
sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included
in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
IN
+ * THE SOFTWARE.
+ */
+#ifndef BLOCK_GOW_INT_H
+#define BLOCK_GOW_INT_H
+
+/* GOW1: approximately 4MB header size, and up to 64GB image size */
+#define GOW_BLOCKSIZE   65536
+
+#define GOW_MAXSIZE     ((int64_t) GOW_MAXBLOCKS * (int64_t) GOW_BLOCKSIZE)
+#define GOW_FREE_BLOCK  (0xffffffff)
+
+#define GOW1_MAGIC      ('G' | ('O' << 8) | ('W' << 16) | ('1' << 24))
+#define GOW2_MAGIC      ('G' | ('O' << 8) | ('W' << 16) | ('2' << 24))
+#define GOW3_MAGIC      ('G' | ('O' << 8) | ('W' << 16) | ('3' << 24))
+
+#if defined(BLOCK_GOW1)
+#define GOW_MAGIC       GOW1_MAGIC
+#define GOW_MAXBLOCKS   1048576
+
+/* GOW1: header is not padded */
+/* header type, contains map */
+typedef struct {
+    uint32_t magic;
+    uint32_t size;
+    uint32_t allocated;
+    uint32_t map[GOW_MAXBLOCKS];
+} gow_header_t;
+
+/* block type, contains data */
+typedef struct {
+    uint8_t data[GOW_BLOCKSIZE];
+} gow_block_t;
+#else /* GOW2, GOW3 below */
+
+
+/* GOW2: approximately 16MB header size, and up to 256GB image size
+ * GOW3: approximately 32MB header size, and up to 256GB image size */
+
+#define GOW_MAXBLOCKS   4194304
+
+typedef struct {
+    uint32_t magic;
+    uint32_t size;
+    uint32_t allocated;
+    uint32_t map[GOW_MAXBLOCKS];
+} gow2_header_t;
+
+typedef struct {
+    uint32_t magic;
+    uint32_t size;
+    uint32_t allocated;
+    uint32_t map[GOW_MAXBLOCKS];
+    uint32_t ver[GOW_MAXBLOCKS];
+    uint32_t carry;
+    uint8_t  signature[32];
+    uint32_t maint;
+} gow3_header_t;
+
+/* header is padded to 512-bytes so image can be indexed in sectors */
+#define GOW2_HEADER_SIZE (((sizeof(gow2_header_t) + 511) >> 9) << 9)
+#define GOW3_HEADER_SIZE (((sizeof(gow3_header_t) + 511) >> 9) << 9)
+
+#endif /* GOW2, GOW3 */
+
+#if defined(BLOCK_GOW1)
+
+#define GOW_HEADER_SIZE (sizeof(gow_header_t))
+
+#elif defined(BLOCK_GOW2)
+
+#define GOW_MAGIC       GOW2_MAGIC
+#define GOW_HEADER_SIZE GOW2_HEADER_SIZE
+#define gow_header_t gow2_header_t
+
+#elif defined(BLOCK_GOW3)
+
+#define GOW_MAGIC       GOW3_MAGIC
+#define gow_header_t gow3_header_t
+#define GOW_HEADER_SIZE GOW3_HEADER_SIZE
+
+#endif
+
+
+/* block helper MACROs */