ESX keeps snapshot deltas (extent type VMFSSPARSE, create type
vmfsSparse, files named -delta.vmdk) in an older sparse
format whose magic reads COWD (copy on write disk). It has a 2,048-byte
header. All numbers are little-endian and positions are in 512-byte sectors. The layout
follows the libvmdk project’s notes; several fields there are not fully understood.
Header
| Offset | Size | Type | Name | Description |
|---|---|---|---|---|
0 | 4 | text | Magic | COWD (43 4F 57 44). |
4 | 4 | uint32 | Version | 1. |
8 | 4 | uint32 | Flags | Seen as 3; meaning not established. |
12 | 4 | uint32 | Capacity | Size in sectors. |
16 | 4 | uint32 | Grain size | Sectors per grain. |
20 | 4 | uint32 | Grain directory offset | Sector of the grain directory (4, straight after the header). |
24 | 4 | uint32 | Grain directory entries | Number of grain tables. |
28 | 4 | uint32 | Next free sector | Where the next grain or table will be written. |
32 | 12 or 1028 | union | Root or child data | A root extent: cylinders, heads and sectors per track, three uint32s. A child extent: the parent’s file name (1,024 bytes) and the parent’s generation (uint32, at 1056). Recent delta files often leave the parent name empty and rely on the descriptor. |
1060 | 4 | uint32 | Generation | A counter raised as the disk changes. |
1064 | 60 | text | Name | – |
1124 | 512 | text | Description | – |
1636 | 4 | uint32 | Saved generation | – |
1640 | 8 | – | Reserved | – |
1648 | 4 | uint32 | Unclean shutdown | Non-zero if the file was not closed properly. |
1652 | 396 | – | Padding | To 2,048 bytes. |
Grain directory and tables
As in the sparse extent, a grain directory of uint32 sector numbers points to grain tables of uint32 sector numbers, one per grain, with 0 meaning the grain is not in this file (read it from the parent). Here each grain table has 4,096 entries, and the directory is stored in whole 512-byte sectors.