Class MetadataWriter
Writes CHD metadata entries (linked list at the end of the file, before the map).
The on-disk format mirrors MAME's chd_file::write_metadata (src/lib/util/chd.cpp):
each entry is a 16-byte header (tag, flags, 24-bit length, 64-bit next) followed by the
payload. The first entry's file offset is stored in the CHD header's metaoffset field.
public static class MetadataWriter
- Inheritance
-
MetadataWriter
- Inherited Members
Fields
AvLdMetadataTag
'AVLD' laserdisc VBI metadata tag (big-endian), MAME's AV_LD_METADATA_TAG.
public const uint AvLdMetadataTag = 1096174660
Field Value
AvMetadataTag
'AVAV' A/V metadata tag (big-endian), MAME's AV_METADATA_TAG.
public const uint AvMetadataTag = 1096171862
Field Value
CdRomOldMetadataTag
'CHCD' legacy CD-ROM track metadata tag (big-endian, binary format).
public const uint CdRomOldMetadataTag = 1128809284
Field Value
CdRomTrackMetadata2Tag
'CHT2' CD-ROM track metadata v2 tag (big-endian).
public const uint CdRomTrackMetadata2Tag = 1128813618
Field Value
CdRomTrackMetadataTag
'CHTR' CD-ROM track metadata v1 tag (big-endian, text format, 4 fields).
public const uint CdRomTrackMetadataTag = 1128813650
Field Value
ChdMdflagsChecksum
CHD_MDFLAGS_CHECKSUM: the entry is covered by the combined SHA-1 verification.
public const byte ChdMdflagsChecksum = 1
Field Value
DvdMetadataTag
'DVD ' DVD-ROM metadata tag (big-endian).
public const uint DvdMetadataTag = 1146504224
Field Value
GdRomOldMetadataTag
'CHGT' legacy GD-ROM track metadata tag (big-endian, LE CDDA).
public const uint GdRomOldMetadataTag = 1128810324
Field Value
GdRomTrackMetadataTag
'CHGD' GD-ROM track metadata tag (big-endian).
public const uint GdRomTrackMetadataTag = 1128810308
Field Value
HardDiskMetadataTag
'GDDD' hard-disk geometry metadata tag (big-endian).
public const uint HardDiskMetadataTag = 1195656260
Field Value
IdentMetadataTag
'IDNT' hard disk ATA IDENTIFY DEVICE metadata tag (big-endian).
public const uint IdentMetadataTag = 1229213268
Field Value
KeyMetadataTag
'KEY ' hard disk encryption key metadata tag (big-endian).
public const uint KeyMetadataTag = 1262836000
Field Value
MetadataHeaderSize
The metadata entry header size in bytes.
public const int MetadataHeaderSize = 16
Field Value
PcmciaCisMetadataTag
'CIS ' PCMCIA Card Information Structure metadata tag (big-endian).
public const uint PcmciaCisMetadataTag = 1128878880
Field Value
Methods
BuildAvLdMetadata(byte[])
Builds the 'AVLD' laserdisc VBI metadata entry from packed per-frame records
(16 bytes each, see MetadataPack(Span<byte>, uint, VbiMetadata)). Matches chdman
createld's post-compression write with flags 0 (not covered by the SHA-1).
public static MetadataEntry BuildAvLdMetadata(byte[] packedFrames)
Parameters
packedFramesbyte[]The concatenated per-frame VBI records.
Returns
BuildAvMetadata(ulong, uint, uint, bool, uint, uint)
Builds the 'AVAV' A/V metadata entry for a laserdisc image, matching chdman
createld and MAME's AV_METADATA_FORMAT:
FPS:%d.%06d WIDTH:%d HEIGHT:%d INTERLACED:%d CHANNELS:%d SAMPLERATE:%d
(null-terminated, checksummed).
public static MetadataEntry BuildAvMetadata(ulong fpsTimes1Million, uint width, uint height, bool interlaced, uint channels, uint sampleRate)
Parameters
fpsTimes1MillionulongFrame rate in frames per 1,000,000 seconds.
widthuintVideo width in pixels.
heightuintVideo height in lines (field height for interlaced sources).
interlacedboolWhether the source is interlaced.
channelsuintAudio channel count.
sampleRateuintAudio sample rate in Hz.
Returns
BuildCdMetadataEntries(CdToc)
Builds the metadata entries (tag, checksum flag, null-terminated payload) for a CD or GD-ROM table of contents, in track order: 'CHT2' entries for CDs, 'CHGD' entries (with the PAD field) for GD-ROMs.
public static List<MetadataEntry> BuildCdMetadataEntries(CdToc toc)
Parameters
tocCdToc
Returns
BuildChd2String(CdTrack)
Builds the CHT2 metadata string for a track, matching MAME's
CDROM_TRACK_METADATA2_FORMAT:
TRACK:%d TYPE:%s SUBTYPE:%s FRAMES:%d PREGAP:%d PGTYPE:%s PGSUB:%s POSTGAP:%d.
When the track has pregap data (PgDataSize > 0), the pregap type is prefixed
with 'V' to indicate the pregap sectors are physically present.
public static string BuildChd2String(CdTrack track)
Parameters
trackCdTrack
Returns
BuildDvdMetadata()
Builds the 'DVD ' metadata entry for a DVD-ROM image, matching chdman createdvd
(chd->write_metadata(DVD_METADATA_TAG, 0, "")). The std::string overload in
chd.h:351 passes input.length() + 1, so the payload written for an empty string
is exactly one NUL byte (length 1), not an empty payload.
public static MetadataEntry BuildDvdMetadata()
Returns
BuildGdRomString(CdTrack)
Builds the GD-ROM metadata string for a track, matching MAME's
GDROM_TRACK_METADATA_FORMAT:
TRACK:%d TYPE:%s SUBTYPE:%s FRAMES:%d PAD:%d PREGAP:%d PGTYPE:%s PGSUB:%s POSTGAP:%d.
public static string BuildGdRomString(CdTrack track)
Parameters
trackCdTrack
Returns
BuildHardDiskMetadata(uint, uint, uint, uint)
Builds the 'GDDD' hard-disk geometry metadata entry with explicit CHS values.
Used when a template (HardDiskTemplates) supplies the geometry instead
of guessing from the file size. Matches MAME's HARD_DISK_METADATA_FORMAT.
public static MetadataEntry BuildHardDiskMetadata(uint cylinders, uint heads, uint sectors, uint bytesPerSector)
Parameters
cylindersuintNumber of cylinders.
headsuintNumber of heads.
sectorsuintSectors per track.
bytesPerSectoruintBytes per sector (BPS).
Returns
BuildHardDiskMetadata(ulong, uint)
Builds the 'GDDD' hard-disk geometry metadata entry, matching MAME's
HARD_DISK_METADATA_FORMAT ("%u/%u/%u/%u", written by
chdman createhd). Uses fixed 16 heads and 63 sectors/track to compute
the cylinder count from totalBytes, exactly like MAME.
public static MetadataEntry BuildHardDiskMetadata(ulong totalBytes, uint bytesPerSector)
Parameters
totalBytesulongThe logical image size in bytes.
bytesPerSectoruintThe sector size in bytes (BPS; normally the unit size).
Returns
BuildIdentMetadata(byte[])
Builds the 'IDNT' metadata entry for an ATA IDENTIFY DEVICE response (512 bytes). Used by OG Xbox and other platforms that need to preserve the original drive's model, serial, CHS geometry, and firmware revision.
public static MetadataEntry BuildIdentMetadata(byte[] identData)
Parameters
identDatabyte[]The 512-byte ATA IDENTIFY DEVICE response data.
Returns
Exceptions
- ArgumentNullException
identDatais null.- ArgumentException
identDatais not exactly 512 bytes.
ComputeCombinedSha1(byte[], IEnumerable<MetadataEntry>)
Computes the combined SHA-1 of a compressed CHD: SHA1(rawsha1 ‖ sorted hashes)
where each hash is the big-endian 4-byte metadata tag followed by the SHA-1 of the
entry payload (checksummed entries only, sorted byte-wise). Matches MAME's
compute_overall_sha1 (src/lib/util/chd.cpp) and the CHDSharpLib reader.
public static byte[] ComputeCombinedSha1(byte[] rawSha1, IEnumerable<MetadataEntry> entries)
Parameters
rawSha1byte[]entriesIEnumerable<MetadataEntry>
Returns
- byte[]
GetSubtypeString(int)
Returns the metadata string for a subcode type (MAME's get_subtype_string).
public static string GetSubtypeString(int subtype)
Parameters
subtypeint
Returns
GetTypeString(int)
Returns the metadata string for a track type (MAME's get_type_string).
public static string GetTypeString(int trackType)
Parameters
trackTypeint
Returns
GuessChs(ulong, uint)
Replicates chdman's guess_chs (chdman.cpp:1119): given a byte count and sector
size, finds the smallest sector-count ≥ totalBytes/bps that is
expressible as cylinders × heads × sectors, preferring the largest sectors per track
(63 down to 2) and the largest heads (16 down to 2). Returns the guessed geometry.
public static MetadataWriter.ChsGeometry GuessChs(ulong totalBytes, uint bytesPerSector)
Parameters
Returns
IsLegacyCdMetadata(uint)
Returns true if the tag is a legacy CD/GD-ROM metadata tag
(CHCD, CHTR, or CHGT) that should be upgraded during copy.
public static bool IsLegacyCdMetadata(uint tag)
Parameters
taguint
Returns
IsLegacyGdRomMetadata(uint)
Returns true if the tag is a legacy GD-ROM metadata tag (CHGT)
whose CDDA audio is stored in little-endian byte order.
public static bool IsLegacyGdRomMetadata(uint tag)
Parameters
taguint
Returns
TagFromString(string)
Converts a four-character metadata tag string ("CHT2", "GDDD", ...) to its big-endian Tag value.
public static uint TagFromString(string tag)
Parameters
tagstringThe four-character tag.
Returns
Exceptions
- ArgumentException
tagis not exactly 4 characters.
WriteCdMetadata(Stream, CdToc)
Appends one CHT2 metadata entry per track at the current stream position, linking them
into a forward linked list (each entry's next points at the following entry; the
last entry has next = 0).
public static long WriteCdMetadata(Stream stream, CdToc toc)
Parameters
streamStreamThe output stream; entries are appended at the current position.
tocCdTocThe CD table of contents to serialize.
Returns
- long
The byte offset of the first metadata entry (for the header's
metaoffset).
WriteCdMetadata(Stream, IEnumerable<MetadataEntry>)
Appends the given metadata entries at the current stream position, linking them into a
forward linked list (each entry's next points at the following entry; the last
entry has next = 0).
public static long WriteCdMetadata(Stream stream, IEnumerable<MetadataEntry> entries)
Parameters
streamStreamThe output stream; entries are appended at the current position.
entriesIEnumerable<MetadataEntry>The metadata entries to write.
Returns
- long
The byte offset of the first metadata entry (for the header's
metaoffset).