summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPeter Wu <peter@lekensteyn.nl>2015-01-05 18:45:07 +0100
committerPeter Wu <peter@lekensteyn.nl>2015-01-06 17:28:24 +0100
commit8c49a210b850d59edcc20b400c4fad48edf8a7b7 (patch)
treedad1d13caa7c79e27216a6599fee01785db6ab72
parent7bc66dcb3c62375675d66fa03ea3f69a3304e26b (diff)
downloadqemu-8c49a210b850d59edcc20b400c4fad48edf8a7b7.tar.gz
block/dmg: factor out block type check
In preparation for adding bzip2 support, split the type check into a separate function. Make all offsets relative to the begin of a chunk such that it is easier to recognize the position without having to add up all offsets. Some comments are added to describe the fields. There is no functional change. Signed-off-by: Peter Wu <peter@lekensteyn.nl>
-rw-r--r--block/dmg.c36
1 files changed, 23 insertions, 13 deletions
diff --git a/block/dmg.c b/block/dmg.c
index 57922c579a..b1d0930d17 100644
--- a/block/dmg.c
+++ b/block/dmg.c
@@ -194,6 +194,18 @@ typedef struct DmgHeaderState {
uint32_t max_sectors_per_chunk;
} DmgHeaderState;
+static bool dmg_is_known_block_type(uint32_t entry_type)
+{
+ switch (entry_type) {
+ case 0x00000001: /* uncompressed */
+ case 0x00000002: /* zeroes */
+ case 0x80000005: /* zlib */
+ return true;
+ default:
+ return false;
+ }
+}
+
static int dmg_read_mish_block(BDRVDMGState *s, DmgHeaderState *ds,
uint8_t *buffer, uint32_t count)
{
@@ -233,22 +245,19 @@ static int dmg_read_mish_block(BDRVDMGState *s, DmgHeaderState *ds,
for (i = s->n_chunks; i < s->n_chunks + chunk_count; i++) {
s->types[i] = buff_read_uint32(buffer, offset);
- offset += 4;
- if (s->types[i] != 0x80000005 && s->types[i] != 1 &&
- s->types[i] != 2) {
+ if (!dmg_is_known_block_type(s->types[i])) {
chunk_count--;
i--;
- offset += 36;
+ offset += 40;
continue;
}
- offset += 4;
- s->sectors[i] = buff_read_uint64(buffer, offset);
+ /* sector number */
+ s->sectors[i] = buff_read_uint64(buffer, offset + 8);
s->sectors[i] += out_offset;
- offset += 8;
- s->sectorcounts[i] = buff_read_uint64(buffer, offset);
- offset += 8;
+ /* sector count */
+ s->sectorcounts[i] = buff_read_uint64(buffer, offset + 0x10);
if (s->sectorcounts[i] > DMG_SECTORCOUNTS_MAX) {
error_report("sector count %" PRIu64 " for chunk %" PRIu32
@@ -258,12 +267,12 @@ static int dmg_read_mish_block(BDRVDMGState *s, DmgHeaderState *ds,
goto fail;
}
- s->offsets[i] = buff_read_uint64(buffer, offset);
+ /* offset in (compressed) data fork */
+ s->offsets[i] = buff_read_uint64(buffer, offset + 0x18);
s->offsets[i] += in_offset;
- offset += 8;
- s->lengths[i] = buff_read_uint64(buffer, offset);
- offset += 8;
+ /* length in (compressed) data fork */
+ s->lengths[i] = buff_read_uint64(buffer, offset + 0x20);
if (s->lengths[i] > DMG_LENGTHS_MAX) {
error_report("length %" PRIu64 " for chunk %" PRIu32
@@ -275,6 +284,7 @@ static int dmg_read_mish_block(BDRVDMGState *s, DmgHeaderState *ds,
update_max_chunk_size(s, i, &ds->max_compressed_size,
&ds->max_sectors_per_chunk);
+ offset += 40;
}
s->n_chunks += chunk_count;
return 0;