From 770a27d0b41c58bfd57ebe6d17f5939887eed795 Mon Sep 17 00:00:00 2001 From: bnnm Date: Sun, 26 Nov 2017 01:54:33 +0100 Subject: [PATCH] Add dual extension in try_dual_file_stereo for Homura (PS2) --- src/formats.c | 1 + src/meta/ps2_smpl.c | 35 ++++++------------------------ src/vgmstream.c | 52 +++++++++++++++++++++++++++++++-------------- 3 files changed, 43 insertions(+), 45 deletions(-) diff --git a/src/formats.c b/src/formats.c index 7f44b732..cf77b8ce 100644 --- a/src/formats.c +++ b/src/formats.c @@ -310,6 +310,7 @@ static const char* extension_list[] = { "um3", "v0", + //"v1", //dual channel with v0 "vag", "vas", "vawx", diff --git a/src/meta/ps2_smpl.c b/src/meta/ps2_smpl.c index 57e2ec5b..e44bd7ed 100644 --- a/src/meta/ps2_smpl.c +++ b/src/meta/ps2_smpl.c @@ -1,26 +1,23 @@ #include "meta.h" #include "../coding/coding.h" -/* SMPL - from Homura */ +/* SMPL - from Homura (PS2) */ VGMSTREAM * init_vgmstream_ps2_smpl(STREAMFILE *streamFile) { VGMSTREAM * vgmstream = NULL; - STREAMFILE * streamRch = NULL; off_t start_offset; int loop_flag, channel_count; size_t channel_size; /* check extension (.v0: left channel, .v1: right channel, .smpl: header id) */ - if ( !check_extensions(streamFile,"v0,smpl") ) + if ( !check_extensions(streamFile,"v0,v1,smpl") ) goto fail; /* check header */ if (read_32bitBE(0x00,streamFile) != 0x534D504C) /* "SMPL" */ goto fail; - /* right channel is in .V1 and doesn't have loop points; manually parse as dual_stereo would fail */ - streamRch = open_stream_ext(streamFile, "V1"); - channel_count = streamRch != NULL ? 2 : 1; - loop_flag = (read_32bitLE(0x30,streamFile) != 0); + channel_count = 1; + loop_flag = (read_32bitLE(0x30,streamFile) != 0); /* .v1 doesn't have loop points */ start_offset = 0x40; channel_size = read_32bitBE(0x0c,streamFile) - 0x10; @@ -41,31 +38,11 @@ VGMSTREAM * init_vgmstream_ps2_smpl(STREAMFILE *streamFile) { read_string(vgmstream->stream_name,0x10+1, 0x20,streamFile); /* open the file for reading */ - //if ( !vgmstream_open_stream(vgmstream, streamFile, start_offset) ) - // goto fail; - - /* custom dual channel */ // todo improve dual_stereo - { - int i; - char filename[PATH_LIMIT]; - - streamFile->get_name(streamFile,filename,sizeof(filename)); - vgmstream->ch[0].streamfile = streamFile->open(streamFile,filename, STREAMFILE_DEFAULT_BUFFER_SIZE); - if (!vgmstream->ch[0].streamfile) goto fail; - - if (channel_count == 2) - vgmstream->ch[1].streamfile = streamRch; - - for (i = 0; i < channel_count; i++) { - vgmstream->ch[i].channel_start_offset = - vgmstream->ch[i].offset = start_offset; - } - } - + if ( !vgmstream_open_stream(vgmstream, streamFile, start_offset) ) + goto fail; return vgmstream; fail: - if (streamRch) close_streamfile(streamRch); close_vgmstream(vgmstream); return NULL; } diff --git a/src/vgmstream.c b/src/vgmstream.c index b27b52b5..a09dd3c8 100644 --- a/src/vgmstream.c +++ b/src/vgmstream.c @@ -2157,9 +2157,10 @@ static void try_dual_file_stereo(VGMSTREAM * opened_vgmstream, STREAMFILE *strea static const char * const dfs_pairs[][2] = { {"L","R"}, {"l","r"}, - {"_0","_1"}, {"left","right"}, {"Left","Right"}, + {".V0",".V1"}, + {"_0","_1"}, //unneeded? }; char new_filename[PATH_LIMIT]; char * ext; @@ -2180,7 +2181,7 @@ static void try_dual_file_stereo(VGMSTREAM * opened_vgmstream, STREAMFILE *strea if (strlen(new_filename)<2) return; /* we need at least a base and a name ending to replace */ ext = (char *)filename_extension(new_filename); - if (ext-new_filename >= 1 && ext[-1]=='.') ext--; /* excluding "." */ + if (ext-new_filename >= 1 && ext[-1]=='.') ext--; /* including "." */ /* find pair from base name and modify new_filename with the opposite */ dfs_pair_count = (sizeof(dfs_pairs)/sizeof(dfs_pairs[0])); @@ -2188,16 +2189,24 @@ static void try_dual_file_stereo(VGMSTREAM * opened_vgmstream, STREAMFILE *strea for (j=0; dfs_pair==-1 && j<2; j++) { const char * this_suffix = dfs_pairs[i][j]; size_t this_suffix_len = strlen(dfs_pairs[i][j]); + const char * other_suffix = dfs_pairs[i][j^1]; + size_t other_suffix_len = strlen(dfs_pairs[i][j^1]); /* if suffix matches copy opposite to ext pointer (thus to new_filename) */ - if ( !memcmp(ext - this_suffix_len,this_suffix,this_suffix_len) ) { - const char * other_suffix = dfs_pairs[i][j^1]; - size_t other_suffix_len = strlen(dfs_pairs[i][j^1]); - - dfs_pair = j; - memmove(ext + other_suffix_len - this_suffix_len, ext,strlen(ext)+1); /* move the extension and terminator, too */ - memcpy (ext - this_suffix_len, other_suffix,other_suffix_len); /* make the new name */ + if (this_suffix[0] == '.' && strlen(ext) == this_suffix_len) { /* dual extension (ex. Homura PS2) */ + if ( !memcmp(ext,this_suffix,this_suffix_len) ) { + dfs_pair = j; + memcpy (ext, other_suffix,other_suffix_len); /* overwrite with new extension */ + } } + else { /* dual suffix */ + if ( !memcmp(ext - this_suffix_len,this_suffix,this_suffix_len) ) { + dfs_pair = j; + memmove(ext + other_suffix_len - this_suffix_len, ext,strlen(ext)+1); /* move the extension and terminator, too */ + memcpy (ext - this_suffix_len, other_suffix,other_suffix_len); /* overwrite with new suffix */ + } + } + } } @@ -2205,6 +2214,7 @@ static void try_dual_file_stereo(VGMSTREAM * opened_vgmstream, STREAMFILE *strea if (dfs_pair == -1) goto fail; + /* try to init other channel (new_filename now has the opposite name) */ dual_streamFile = streamFile->open(streamFile,new_filename,STREAMFILE_DEFAULT_BUFFER_SIZE); if (!dual_streamFile) goto fail; @@ -2213,7 +2223,7 @@ static void try_dual_file_stereo(VGMSTREAM * opened_vgmstream, STREAMFILE *strea close_streamfile(dual_streamFile); /* see if we were able to open the file, and if everything matched nicely */ - if (new_vgmstream && + if (!(new_vgmstream && new_vgmstream->channels == 1 && /* we have seen legitimate pairs where these are off by one... * but leaving it commented out until I can find those and recheck */ @@ -2223,15 +2233,24 @@ static void try_dual_file_stereo(VGMSTREAM * opened_vgmstream, STREAMFILE *strea new_vgmstream->meta_type == opened_vgmstream->meta_type && new_vgmstream->coding_type == opened_vgmstream->coding_type && new_vgmstream->layout_type == opened_vgmstream->layout_type && - new_vgmstream->loop_flag == opened_vgmstream->loop_flag && - /* check these even if there is no loop, because they should then be zero in both */ - new_vgmstream->loop_start_sample == opened_vgmstream->loop_start_sample && - new_vgmstream->loop_end_sample == opened_vgmstream->loop_end_sample && /* check even if the layout doesn't use them, because it is * difficult to determine when it does, and they should be zero otherwise, anyway */ new_vgmstream->interleave_block_size == opened_vgmstream->interleave_block_size && - new_vgmstream->interleave_smallblock_size == opened_vgmstream->interleave_smallblock_size) { - /* We seem to have a usable, matching file. Merge in the second channel. */ + new_vgmstream->interleave_smallblock_size == opened_vgmstream->interleave_smallblock_size)) { + goto fail; + } + + /* check these even if there is no loop, because they should then be zero in both + * Homura PS2 right channel doesn't have loop points so it's ignored */ + if (new_vgmstream->meta_type != meta_PS2_SMPL && + !(new_vgmstream->loop_flag == opened_vgmstream->loop_flag && + new_vgmstream->loop_start_sample== opened_vgmstream->loop_start_sample && + new_vgmstream->loop_end_sample == opened_vgmstream->loop_end_sample)) { + goto fail; + } + + /* We seem to have a usable, matching file. Merge in the second channel. */ + { VGMSTREAMCHANNEL * new_chans; VGMSTREAMCHANNEL * new_loop_chans = NULL; VGMSTREAMCHANNEL * new_start_chans = NULL; @@ -2283,6 +2302,7 @@ static void try_dual_file_stereo(VGMSTREAM * opened_vgmstream, STREAMFILE *strea /* discard the second VGMSTREAM */ free(new_vgmstream); } + fail: return; }