From 54cf2e04fcb6b1db1aa948a8f1ec7fd222fe097e Mon Sep 17 00:00:00 2001 From: NicknineTheEagle Date: Thu, 27 Dec 2018 21:20:28 +0300 Subject: [PATCH] EA SCHl: Calculate stream size for bitrate --- src/meta/ea_schl.c | 39 +++++++++++++++++++++++++++++++++++---- 1 file changed, 35 insertions(+), 4 deletions(-) diff --git a/src/meta/ea_schl.c b/src/meta/ea_schl.c index 5e5b6c32..e71162e3 100644 --- a/src/meta/ea_schl.c +++ b/src/meta/ea_schl.c @@ -103,6 +103,7 @@ static int parse_variable_header(STREAMFILE* streamFile, ea_header* ea, off_t be static uint32_t read_patch(STREAMFILE* streamFile, off_t* offset); static off_t get_ea_stream_mpeg_start_offset(STREAMFILE* streamFile, off_t start_offset, const ea_header* ea); static VGMSTREAM * init_vgmstream_ea_variable_header(STREAMFILE *streamFile, ea_header *ea, off_t start_offset, int is_bnk); +static int get_ea_stream_size(STREAMFILE* streamFile, off_t start_offset, VGMSTREAM *vgmstream); /* EA SCHl with variable header - from EA games (roughly 1997~2010); generated by EA Canada's sx.exe/Sound eXchange */ VGMSTREAM * init_vgmstream_ea_schl(STREAMFILE *streamFile) { @@ -378,10 +379,10 @@ VGMSTREAM * init_vgmstream_ea_map_mus(STREAMFILE *streamFile) { * 0x07: userdata entry size (incorrect?) * 0x08: three zeroes * 0x0b: number of userdata entries + * 0x0c: section 1 start */ num_sounds = read_8bit(0x06, streamFile); num_userdata = read_8bit(0x0b, streamFile); - section_offset = 0x0c; /* section 1: contains information about segment playback order */ @@ -456,7 +457,7 @@ VGMSTREAM * init_vgmstream_ea_mpf_mus(STREAMFILE *streamFile) { section_offset = 0x20; entry_offset = read_16bit(section_offset + (sec1_num - 1) * 0x02, streamFile) * 0x04; - /* HACK: there's some weird bitstream here that's store differently in LE and BE */ + /* HACK: there's some weird bitstream here that's stored differently in LE and BE */ /* I can't figure it out, so let's just use a workaround for now */ if (read_32bitBE(0x00, streamFile) == 0x50464478) { subentry_num = (read_32bitBE(entry_offset + 0x04, streamFile) >> 15) & 0xFF; @@ -673,8 +674,6 @@ static VGMSTREAM * init_vgmstream_ea_variable_header(STREAMFILE *streamFile, ea_ vgmstream->layout_type = layout_blocked_ea_schl; } - //vgmstream->stream_size = ; //todo needed for kbps info - /* EA usually implements their codecs in all platforms (PS2/WII do EAXA/MT/EALAYER3) and * favors them over platform's natives (ex. EAXA vs VAG/DSP). * Unneeded codecs are removed over time (ex. LAYER3 when EALAYER3 was introduced). */ @@ -856,6 +855,11 @@ static VGMSTREAM * init_vgmstream_ea_variable_header(STREAMFILE *streamFile, ea_ vgmstream->ch[i].offset = ea->offsets[i]; } } + + /* TODO: Figure out how to get stream size for BNK sounds */ + } + else { + vgmstream->stream_size = get_ea_stream_size(streamFile, start_offset, vgmstream); } return vgmstream; @@ -1245,6 +1249,33 @@ fail: return 0; } +/* Stream size is almost never provided in bank files so we have to calc it manually */ +static int get_ea_stream_size(STREAMFILE* streamFile, off_t start_offset, VGMSTREAM *vgmstream) { + size_t stream_size, block_size; + uint32_t block_id; + off_t block_offset; + + stream_size = 0; + block_offset = start_offset; + + + while (1) { + block_id = read_32bitBE(block_offset + 0x00, streamFile); + if (block_id == EA_BLOCKID_END) + break; + + if (vgmstream->codec_config & 0x02) /* size is always LE, except in early SS/MAC */ + block_size = read_32bitBE(block_offset + 0x04, streamFile); + else + block_size = read_32bitLE(block_offset + 0x04, streamFile); + + stream_size += block_size - 0x08; + block_offset += block_size; + } + + return stream_size; +} + /* find data start offset inside the first SCDl; not very elegant but oh well */ static off_t get_ea_stream_mpeg_start_offset(STREAMFILE* streamFile, off_t start_offset, const ea_header* ea) { size_t file_size = get_streamfile_size(streamFile);