Features/QED: Difference between revisions
(→Header) |
|||
Line 3: | Line 3: | ||
The file format looks like this: | The file format looks like this: | ||
+--------+ | +--------+----------+---------+---------+-----+ | ||
| header | | | header | L1 table | extent0 | extent1 | ... | | ||
+--------+ | +--------+----------+---------+---------+-----+ | ||
==Header== | ==Header== | ||
Line 14: | Line 14: | ||
uint32_t cluster_size; /* in bytes */ | uint32_t cluster_size; /* in bytes */ | ||
uint32_t table_size; /* table size, in clusters */ | uint32_t table_size; /* table size, in clusters */ | ||
uint64_t l1_table_offset; /* L1 table offset, in | uint64_t l1_table_offset; /* L1 table offset, in clusters */ | ||
uint64_t image_size; /* total image size, in clusters */ | uint64_t image_size; /* total image size, in clusters */ | ||
Revision as of 15:45, 24 August 2010
Specification
The file format looks like this:
+--------+----------+---------+---------+-----+ | header | L1 table | extent0 | extent1 | ... | +--------+----------+---------+---------+-----+
Header
Header { uint32_t magic; /* COW2 */ uint32_t features; /* format feature bits */ uint32_t cluster_size; /* in bytes */ uint32_t table_size; /* table size, in clusters */ uint64_t l1_table_offset; /* L1 table offset, in clusters */ uint64_t image_size; /* total image size, in clusters */ uint32_t backing_file_offset; /* in bytes from start of header */ uint32_t backing_file_size; /* in bytes */ }
Extent table
#define TABLE_NOFFSETS (table_size * cluster_size / sizeof(uint64_t)) Table { uint64_t offsets[TABLE_NOFFSETS]; }
The extent tables are organized as follows:
+----------+ | L1 table | +----------+ ,------' | '------. +----------+ | +----------+ | L2 table | ... | L2 table | +----------+ +----------+ ,------' | '------. +----------+ | +----------+ | Data | ... | Data | +----------+ +----------+
The table_size field allows tables to be multiples of the cluster size. For example, cluster_size=64 KB and table_size=4 results in 256 KB tables.
Operations
Read
- If L2 table is not present in L1, read from backing image.
- If data cluster is not present in L2, read from backing image.
- Otherwise read data from cluster.
Write
- If L2 table is not present in L1, allocate new cluster and L2. Perform L2 and L1 link after writing data.
- If data cluster is not present in L2, allocate new cluster. Perform L1 link after writing data.
- Otherwise overwrite data cluster.
Grow
- If table_size * TABLE_NOFFSETS < new_image_size, fail -EOVERFLOW. The L1 table is not big enough.
- Write new image_size header field.