ESO Mod:RIFF File Format
Although RIFF files are a very popular data type used for saving WAV files, those used in the game files have modified, shortened headers which cannot be interpreted by media players. This page describes the relatively simple procedure required to make these otherwise-normal WAV files readable by any media player.
Contents
EsoAudioSoundSets.mnf Format[edit]
The sound files are in the WAVE_FORMAT_EXTENSIBLE structure. All numerical values are little endian.
Original Format[edit]
The original header format for WAV files is as such:
byte RIFF[4] = "RIFF" dword fileSize byte WAVE[4] = "WAVE" byte fmt_[4] = "fmt " dword fmtSize = 0x28000000 //40 bytes word fmtTag = 0xFEFF //WAVE_FORMAT_EXTENSIBLE word nChannels dword nSamplesPerSec dword nAvgBytesPerSec word nBlockAlign word nBitsPerSample word cbSize = 0x1600 //22 extra bytes of format info word nValidBitsPerSample dword channelMask //See below byte subFormat[16] = 0x0100000000001000800000AA00389B71 byte DATA[4] = "DATA" //Might be "cue " in later versions dword dataSize
For more info on ChannelMask, refer to this site.
Game Format[edit]
The header format for the extracted audio is slightly different:
byte RIFF[4] = "RIFF" dword fileSize byte WAVE[4] = "WAVE" byte fmt_[4] = "fmt " dword fmtSize = 0x18000000 //24 bytes, not 40 word fmtTag = 0xFEFF //WAVE_FORMAT_EXTENSIBLE word nChannels dword nSamplesPerSec dword nAvgBytesPerSec word nBlockAlign word nBitsPerSample word cbSize = 0x0600 //6 extra bytes of format info, not 22 word null1 = 0x0000 dword channelMask //Same as above byte JUNK[4] = "JUNK" dword junkSize = 0x04000000 dword null2 = 0x00000000 byte DATA[4] = "DATA" dword dataSize
Changing Format[edit]
In order to modify the header of the sound file, a hex editor has to be used. HxD is recommended, but you can use the one of your preference. Do NOT try using Notepad.
For this example we will examine 164171.riff, which can be extracted from depot\version\eso0028.dat.
Below, the first 64 bytes are listed in the unmodified header. The bytes that will be modified are indicated below:
52 49 46 46C4 09 AF 0157 41 56 45 66 6D 74 20 RIFFÄ.¯.WAVEfmt1800 00 00 FE FF 02 00 C0 5D 00 00 00 77 01 00 ....þÿ..À]...w.. 04 00 10 00060000 0003 00 00 004A 55 4E 4B............JUNK04 00 00 00 00 00 00 0064 61 74 61 8C 09 AF 01 ........dataŒ.¯.
The modified version of this will be 68 bytes long:
52 49 46 46 C8 09 AF 01 57 41 56 45 66 6D 74 20 RIFFÄ.¯.WAVEfmt Size increased by 4 bytes 28 00 00 00 FE FF 02 00 C0 5D 00 00 00 77 01 00 (...þÿ..À]...w.. fmtSize increased from 0x18 to 0x28 04 00 10 00 16 00 10 00 03 00 00 00 01 00 00 00 ................ cbSize increased from 0x06 to 0x16, null1 replaced with nValidBitsPerSample; 00 00 10 00 80 00 00 AA 00 38 9B 71 64 61 74 61 ....€..ª.8›qdata JUNK block replaced with subFormat 8C 09 AF 01 Œ.¯.
Finally, rename the file "164171.wav". Now you're good to go!
EsoAudioEn.mnf Format[edit]
The voice over sound files (vo_en) are similarly RIFF format but have a different header format and the previous method doesn't work. You can instead use the ww2ogg utility to convert the RIFF files to OGG with the following comand:
ww2ogg 000011.riff --pcb packed_codebooks_aoTuV_603.bin
Notes[edit]
- This conversion process is very crude, but it works for at least some files. Some files do not seem to work with this process, but it's possible that the header can be tweaked to fix these.