The fmt chunk says how the samples in the data chunk are encoded. Its
fields are those of the ordinary WAV format chunk, each stored big-endian. It has grown
over the years, each form adding fields at the end, and its first field decides how the
rest of the file is read. It must come before the data chunk.
Fields
Offsets are from the start of the chunk’s data, after the eight-byte chunk header. All numbers are big-endian.
| Offset | Size | Type | Name | Description |
|---|---|---|---|---|
| 0 | 2 | u16 | wFormatTag | the format code: 1 for PCM (00 01), 3 for float, 0xFFFE for extensible (FF FE) |
| 2 | 2 | u16 | nChannels | the number of channels |
| 4 | 4 | u32 | nSamplesPerSec | sample frames per second, such as 44,100 (00 00 AC 44) or 48,000 |
| 8 | 4 | u32 | nAvgBytesPerSec | bytes per second, for buffering: nSamplesPerSec × nBlockAlign for PCM |
| 12 | 2 | u16 | nBlockAlign | bytes per frame for PCM (nChannels × bytes per sample), or the size of one block for ADPCM and other codecs |
| 14 | 2 | u16 | wBitsPerSample | bits per sample: the container size for PCM (8, 16, 24, 32), 32 or 64 for float, 4 for both ADPCMs, 0 for some codecs such as GSM and MP3 |
| 16 | 2 | u16 | cbSize | the number of bytes of format-specific data that follow (WAVEFORMATEX) |
| 18 | cbSize | bytes | extension | depends on the format code: see extensible, Microsoft ADPCM, IMA ADPCM and MPEG |
The format chunk of the SciPy float file on the
RIFX chunks page reads
00 03 (float), 00 02 (2 channels), 00 00 AC 44
(44,100 Hz), 00 05 62 20 (352,800 bytes a second), 00 08,
00 20 (32 bits) and 00 00 (cbSize 0). The explorer
checks the block align and byte rate of PCM, float and G.711 files against the other
fields, and reports a channel count or sample rate of 0.
Sizes
The chunk size tells which form a file uses.
| Size | Structure | Used for |
|---|---|---|
| 14 | WAVEFORMAT | the 1991 form for formats other than PCM, without wBitsPerSample; rare |
| 16 | PCMWAVEFORMAT | plain PCM: the six fields up to wBitsPerSample, which the 1991 specification calls “PCM-specific” |
18 + cbSize | WAVEFORMATEX | from Microsoft’s 1994 revision: adds cbSize, and codecs put their own data after it |
| 40 | WAVEFORMATEXTENSIBLE | wFormatTag is 0xFFFE and cbSize is 22 |
The 1994 revision says every format other than PCM must use the extended chunk, with
cbSize present even when it is 0, and must have a
fact chunk;
SciPy’s float file follows this. Readers should accept every size, read
cbSize only when the chunk is long enough to hold it, and not trust a
cbSize larger than the chunk.
Format codes
The format codes are Microsoft’s, listed in its mmreg.h header and, as of
1998, in RFC 2361. They mean the same in a RIFX file, stored big-endian. These are the
ones commonly met in WAV files; in practice RIFX files hold PCM or float.
| Code | Name | Audio |
|---|---|---|
| 0x0000 | WAVE_FORMAT_UNKNOWN | unknown |
| 0x0001 (1) | WAVE_FORMAT_PCM | integer PCM |
| 0x0002 (2) | WAVE_FORMAT_ADPCM | Microsoft ADPCM |
| 0x0003 (3) | WAVE_FORMAT_IEEE_FLOAT | 32- or 64-bit floating point, full scale 1.0 |
| 0x0006 (6) | WAVE_FORMAT_ALAW | G.711 A-law, 8-bit codes |
| 0x0007 (7) | WAVE_FORMAT_MULAW | G.711 µ-law, 8-bit codes |
| 0x0011 (17) | WAVE_FORMAT_DVI_ADPCM | IMA ADPCM (Intel DVI), 4 bits per sample |
| 0x0031 (49) | WAVE_FORMAT_GSM610 | GSM 6.10 speech |
| 0x0050 (80) | WAVE_FORMAT_MPEG | MPEG-1 audio layer 1 or 2 |
| 0x0055 (85) | WAVE_FORMAT_MPEGLAYER3 | MP3 |
| 0x0092 | WAVE_FORMAT_DOLBY_AC3_SPDIF | AC-3 packed for S/PDIF |
| 0x00FF | WAVE_FORMAT_RAW_AAC1 | raw AAC |
| 0x0160 to 0x0163 | WAVE_FORMAT_MSAUDIO1, WMAUDIO2, WMAUDIO3, WMAUDIO_LOSSLESS | Windows Media Audio |
| 0x1600 | WAVE_FORMAT_MPEG_ADTS_AAC | AAC in ADTS frames |
| 0x1610 | WAVE_FORMAT_MPEG_HEAAC | HE-AAC |
| 0x674F to 0x6751 | WAVE_FORMAT_OGG_VORBIS_MODE_1, _2, _3 | Ogg Vorbis, the whole Ogg stream in the data chunk |
| 0x676F to 0x6771 | WAVE_FORMAT_OGG_VORBIS_MODE_1_PLUS, _2_PLUS, _3_PLUS | Ogg Vorbis |
| 0xF1AC | WAVE_FORMAT_FLAC | FLAC |
| 0xFFFE (65534) | WAVE_FORMAT_EXTENSIBLE | see SubFormat |
| 0xFFFF | WAVE_FORMAT_DEVELOPMENT | for codecs in development |
The values of the Ogg Vorbis modes 1 and 3 plus are confirmed in Microsoft’s headers as published in the winapi bindings; the others follow in sequence.
The other registered codes
RFC 2361 lists these as well. Each name starts WAVE_FORMAT_. Few of them
are met today.
| Code | Name | Code | Name |
|---|---|---|---|
| 0x0004 | VSELP (Compaq) | 0x0005 | IBM_CVSD |
| 0x0010 | OKI_ADPCM | 0x0012 | MEDIASPACE_ADPCM |
| 0x0013 | SIERRA_ADPCM | 0x0014 | G723_ADPCM (Antex) |
| 0x0015 | DIGISTD | 0x0016 | DIGIFIX |
| 0x0017 | DIALOGIC_OKI_ADPCM | 0x0018 | MEDIAVISION_ADPCM |
| 0x0019 | CU_CODEC (HP) | 0x0020 | YAMAHA_ADPCM |
| 0x0021 | SONARC | 0x0022 | DSPGROUP_TRUESPEECH |
| 0x0023 | ECHOSC1 | 0x0024 | AUDIOFILE_AF36 |
| 0x0025 | APTX | 0x0026 | AUDIOFILE_AF10 |
| 0x0027 | PROSODY_1612 | 0x0028 | LRC |
| 0x0030 | DOLBY_AC2 | 0x0032 | MSNAUDIO |
| 0x0033 | ANTEX_ADPCME | 0x0034 | CONTROL_RES_VQLPC |
| 0x0035 | DIGIREAL | 0x0036 | DIGIADPCM |
| 0x0037 | CONTROL_RES_CR10 | 0x0038 | NMS_VBXADPCM |
| 0x0039 | ROLAND_RDAC | 0x003A | ECHOSC3 |
| 0x003B | ROCKWELL_ADPCM | 0x003C | ROCKWELL_DIGITALK |
| 0x003D | XEBEC | 0x0040 | G721_ADPCM |
| 0x0041 | G728_CELP | 0x0042 | MSG723 |
| 0x0052 | RT24 | 0x0053 | PAC |
| 0x0059 | LUCENT_G723 | 0x0060 | CIRRUS |
| 0x0061 | ESPCM | 0x0062 | VOXWARE |
| 0x0063 | CANOPUS_ATRAC | 0x0064 | G726_ADPCM |
| 0x0065 | G722_ADPCM | 0x0066 | DSAT |
| 0x0067 | DSAT_DISPLAY | 0x0069 to 0x0081 | mostly Voxware codecs |
| 0x0080 | SOFTSOUND | 0x0082 | MSRT24 |
| 0x0083 | G729A | 0x0084 | MVI_MV12 |
| 0x0085 | DF_G726 | 0x0086 | DF_GSM610 |
| 0x0088 | ISIAUDIO | 0x0089 | ONLIVE |
| 0x0091 | SBC24 | 0x0097 | ZYXEL_ADPCM |
| 0x0098 | PHILIPS_LPCBB | 0x0099 | PACKED |
| 0x0100 | RHETOREX_ADPCM | 0x0101 | IRAT |
| 0x0112 | VIVO_SIREN | 0x0123 | DIGITAL_G723 |
| 0x0200 | CREATIVE_ADPCM | 0x0202 | CREATIVE_FASTSPEECH8 |
| 0x0203 | CREATIVE_FASTSPEECH10 | 0x0220 | QUARTERDECK |
| 0x0300 | FM_TOWNS_SND | 0x0400 | BTV_DIGITAL |
| 0x0680 | VME_VMPCM | 0x1000 to 0x1004 | Olivetti codecs |
| 0x1100 | LH_CODEC | 0x1400 | NORRIS |
| 0x1401 | ISIAUDIO (AT&T) | 0x1500 | SOUNDSPACE_MUSICOMPRESS |
| 0x2000 | DVM |
WAVE_FORMAT_EXTENSIBLE
With the format code 0xFFFE, cbSize is 22 and three fields
follow. The real format is then the SubFormat GUID.
| Offset | Size | Type | Name | Description |
|---|---|---|---|---|
| 18 | 2 | u16 | wValidBitsPerSample | how many bits of each sample carry the signal, such as 20 in a 24-bit container; for a compressed subformat the same field is wSamplesPerBlock |
| 20 | 4 | u32 | dwChannelMask | which speaker each channel feeds, see channel mask |
| 24 | 16 | GUID | SubFormat | the real format, see SubFormat |
McGill’s notes give the rules: wBitsPerSample must be the container size,
8 × nBlockAlign / nChannels, and a multiple of 8;
wValidBitsPerSample is for information, from 1 to the container size. The
extensible form should be used for PCM above 16 bits, for more than two channels, for a
container larger than the bit depth, and whenever the speakers need naming. No
extensible RIFX file was among the files examined for this site.
Channel mask
Each set bit of dwChannelMask, a big-endian u32, names a speaker. The
channels in each frame appear in the order of the set bits, lowest first. A mask of 0
means the channels have no particular speaker. The explorer reports a mask whose number
of set bits differs from the channel count.
| Bit | Speaker | Bit | Speaker |
|---|---|---|---|
0x1 | front left (L) | 0x200 | side left (Sl) |
0x2 | front right (R) | 0x400 | side right (Sr) |
0x4 | front centre (C) | 0x800 | top centre (Tc) |
0x8 | low frequency (LFE) | 0x1000 | top front left (Tfl) |
0x10 | back left (Ls) | 0x2000 | top front centre (Tfc) |
0x20 | back right (Rs) | 0x4000 | top front right (Tfr) |
0x40 | front left of centre (Lc) | 0x8000 | top back left (Trl) |
0x80 | front right of centre (Rc) | 0x10000 | top back centre (Trc) |
0x100 | back centre (Cs) | 0x20000 | top back right (Trr) |
The short names are libsndfile’s. Common masks are 0x4 for mono,
0x3 for stereo, 0x3F for 5.1 (front left, front right, centre,
LFE, back left, back right) and 0x63F for 7.1 with side speakers. In a RIFX
file the 5.1 mask is stored 00 00 00 3F.
SubFormat
An extensible chunk carries its real format as a GUID. For the classic formats the
first field is the old format code and the rest is fixed:
0000xxxx-0000-0010-8000-00AA00389B71. Microsoft names them
KSDATAFORMAT_SUBTYPE_PCM (1), _IEEE_FLOAT (3),
_ALAW (6), _MULAW (7) and _ADPCM (2).
A GUID is a 32-bit field, two 16-bit fields and eight single bytes. In a RIFF file the
first three fields are little-endian. In a RIFX file libsndfile reads them in the file’s
byte order, big-endian, and the explorer does the same, so PCM is stored
00 00 00 01 00 00 00 10 80 00 00 AA 00 38 9B 71. No RIFX file with an
extensible format chunk was seen, so this follows libsndfile rather than files.
Ambisonic B-format, as libsndfile names it, uses
00000001-0721-11D3-8644-C8C1CA000000 for PCM and
00000003-0721-11D3-8644-C8C1CA000000 for float.
Microsoft ADPCM
Format code 2. cbSize is 32 with the usual seven coefficient pairs.
| Offset | Size | Type | Name | Description |
|---|---|---|---|---|
| 18 | 2 | u16 | wSamplesPerBlock | frames each block decodes to: 2 × (nBlockAlign − 7 × nChannels) / nChannels + 2 |
| 20 | 2 | u16 | wNumCoef | the number of coefficient pairs, 7 as a rule |
| 22 | 4 each | i16, i16 | aCoef | the pairs (iCoef1, iCoef2), in 256ths |
The standard pairs are (256, 0), (512, −256), (0, 0), (192, 64), (240, 0), (460, −208) and (392, −232). How a block uses them is on Sample data. Here is the format chunk of a mono 8,000 Hz Microsoft ADPCM sample with 256-byte blocks, written in RIFX byte order for this page; no RIFX ADPCM file was seen.
00000000 66 6D 74 20 00 00 00 32 00 02 00 01 00 00 1F 40 fmt ...2.......@
00000010 00 00 10 00 01 00 00 04 00 20 01 F4 00 07 01 00 ......... ......
00000020 00 00 02 00 FF 00 00 00 00 00 00 C0 00 40 00 F0 .............@..
00000030 00 00 01 CC FF 30 01 88 FF 18 .....0....
IMA ADPCM
Format code 0x11. cbSize is 2, and the one field is
wSamplesPerBlock at offset 18: the frames each block decodes to, which
must be 2 × (nBlockAlign − 4 × nChannels) / nChannels
+ 1. libsndfile refuses a file where it is not. A 256-byte mono block gives 505 frames
(01 F9), a 512-byte mono block 1,017 and a 1,024-byte stereo block 1,017.
wBitsPerSample is 4. The blocks are described on
Sample data.
MPEG
For MP3, format code 0x55, Microsoft’s MPEGLAYER3WAVEFORMAT
has cbSize 12 or more. Its fields are big-endian in a RIFX file, as the
explorer reads them:
| Offset | Size | Type | Name | Description |
|---|---|---|---|---|
| 18 | 2 | u16 | wID | MPEGLAYER3_ID_MPEG, 1 |
| 20 | 4 | u32 | fdwFlags | padding: 0 as ISO decides, 1 always, 2 never |
| 24 | 2 | u16 | nBlockSize | the block size in bytes: the frame length × nFramesPerBlock |
| 26 | 2 | u16 | nFramesPerBlock | MP3 frames a block, usually 1 |
| 28 | 2 | u16 | nCodecDelay | the encoder delay in samples, or 0 when unknown |
For MPEG-1 layers 1 and 2, format code 0x50, MPEG1WAVEFORMAT
has cbSize 22; wBitsPerSample is 0:
| Offset | Size | Type | Name | Description |
|---|---|---|---|---|
| 18 | 2 | u16 | fwHeadLayer | the layer, as flags ACM_MPEG_LAYER1, LAYER2 and LAYER3 (1, 2 and 4), combined when a stream mixes layers |
| 20 | 4 | u32 | dwHeadBitrate | the bit rate in bits a second, or 0 when it varies |
| 24 | 2 | u16 | fwHeadMode | flags for stereo, joint stereo, dual channel and single channel |
| 26 | 2 | u16 | fwHeadModeExt | the joint stereo mode extensions allowed, 0x01 to 0x08; 0x0F for all |
| 28 | 2 | u16 | wHeadEmphasis | de-emphasis: 1 none, 2 50/15 ms, 3 reserved, 4 CCITT J.17 |
| 30 | 2 | u16 | fwHeadFlags | private, copyright, original, protection and MPEG-1 ID bits |
| 32 | 4 | u32 | dwPTSLow | the low 32 bits of the first frame’s presentation time stamp |
| 36 | 4 | u32 | dwPTSHigh | its top bit |
An example
The format chunk of a 24-bit, 48 kHz, 5.1 surround file, written in RIFX byte order for this page.
00000000 66 6D 74 20 00 00 00 28 FF FE 00 06 00 00 BB 80 fmt ...(........
00000010 00 0D 2F 00 00 12 00 18 00 16 00 18 00 00 00 3F ../............?
00000020 00 00 00 01 00 00 00 10 80 00 00 AA 00 38 9B 71 .............8.q
| Field | Bytes | Value |
|---|---|---|
ckSize | 00 00 00 28 | 40 |
wFormatTag | FF FE | 0xFFFE, extensible |
nChannels | 00 06 | 6 |
nSamplesPerSec | 00 00 BB 80 | 48,000 |
nAvgBytesPerSec | 00 0D 2F 00 | 864,000 |
nBlockAlign | 00 12 | 18 bytes per frame: 6 channels × 3 bytes |
wBitsPerSample | 00 18 | 24 |
cbSize | 00 16 | 22 |
wValidBitsPerSample | 00 18 | 24 |
dwChannelMask | 00 00 00 3F | 5.1 |
SubFormat | 16 bytes | PCM, its first three fields big-endian |