mirror of
https://github.com/vgmstream/vgmstream.git
synced 2025-01-31 04:13:47 +01:00
cleanup: atx > apa3
This commit is contained in:
parent
4168673bbd
commit
9631e02689
@ -126,6 +126,7 @@
|
||||
<ClInclude Include="meta\adx_keys.h" />
|
||||
<ClInclude Include="meta\ahx_keys.h" />
|
||||
<ClInclude Include="meta\aix_streamfile.h" />
|
||||
<ClInclude Include="meta\apa3_streamfile.h" />
|
||||
<ClInclude Include="meta\awc_decryption_streamfile.h" />
|
||||
<ClInclude Include="meta\awc_streamfile.h" />
|
||||
<ClInclude Include="meta\bar_streamfile.h" />
|
||||
@ -395,6 +396,7 @@
|
||||
<ClCompile Include="meta\akb.c" />
|
||||
<ClCompile Include="meta\alp.c" />
|
||||
<ClCompile Include="meta\ao.c" />
|
||||
<ClCompile Include="meta\apa3.c" />
|
||||
<ClCompile Include="meta\apc.c" />
|
||||
<ClCompile Include="meta\apple_caff.c" />
|
||||
<ClCompile Include="meta\asd_naxat.c" />
|
||||
@ -404,7 +406,6 @@
|
||||
<ClCompile Include="meta\ast_mmv.c" />
|
||||
<ClCompile Include="meta\ast_mv.c" />
|
||||
<ClCompile Include="meta\atsl.c" />
|
||||
<ClCompile Include="meta\atx.c" />
|
||||
<ClCompile Include="meta\aus.c" />
|
||||
<ClCompile Include="meta\awb.c" />
|
||||
<ClCompile Include="meta\awc.c" />
|
||||
@ -610,7 +611,6 @@
|
||||
<ClCompile Include="meta\ppst.c" />
|
||||
<ClCompile Include="meta\ps2_adm.c" />
|
||||
<ClCompile Include="meta\ps2_ass.c" />
|
||||
<ClCompile Include="meta\ps2_b1s.c" />
|
||||
<ClCompile Include="meta\ps2_bmdx.c" />
|
||||
<ClCompile Include="meta\ps2_gcm.c" />
|
||||
<ClCompile Include="meta\ps2_hsf.c" />
|
||||
|
@ -212,6 +212,9 @@
|
||||
<ClInclude Include="meta\aix_streamfile.h">
|
||||
<Filter>meta\Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="meta\apa3_streamfile.h">
|
||||
<Filter>meta\Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="meta\awc_decryption_streamfile.h">
|
||||
<Filter>meta\Header Files</Filter>
|
||||
</ClInclude>
|
||||
@ -1015,6 +1018,9 @@
|
||||
<ClCompile Include="meta\ao.c">
|
||||
<Filter>meta\Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="meta\apa3.c">
|
||||
<Filter>meta\Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="meta\apc.c">
|
||||
<Filter>meta\Source Files</Filter>
|
||||
</ClCompile>
|
||||
@ -1042,9 +1048,6 @@
|
||||
<ClCompile Include="meta\atsl.c">
|
||||
<Filter>meta\Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="meta\atx.c">
|
||||
<Filter>meta\Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="meta\aus.c">
|
||||
<Filter>meta\Source Files</Filter>
|
||||
</ClCompile>
|
||||
@ -1660,9 +1663,6 @@
|
||||
<ClCompile Include="meta\ps2_ass.c">
|
||||
<Filter>meta\Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="meta\ps2_b1s.c">
|
||||
<Filter>meta\Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="meta\ps2_bmdx.c">
|
||||
<Filter>meta\Source Files</Filter>
|
||||
</ClCompile>
|
||||
|
34
src/meta/apa3.c
Normal file
34
src/meta/apa3.c
Normal file
@ -0,0 +1,34 @@
|
||||
#include "meta.h"
|
||||
#include "../coding/coding.h"
|
||||
#include "apa3_streamfile.h"
|
||||
|
||||
|
||||
/* .ATX - Media.Vision's segmented RIFF AT3 wrapper [Senjo no Valkyria 3 (PSP), Shining Blade (PSP)] */
|
||||
VGMSTREAM* init_vgmstream_apa3(STREAMFILE* sf) {
|
||||
VGMSTREAM* vgmstream = NULL;
|
||||
STREAMFILE* temp_sf = NULL;
|
||||
|
||||
|
||||
/* checks */
|
||||
if (!is_id32be(0x00, sf, "APA3"))
|
||||
return NULL;
|
||||
if (!check_extensions(sf,"atx"))
|
||||
return NULL;
|
||||
|
||||
/* .ATX is made of subfile segments, handled by a custom SF.
|
||||
* Each segment has a header/footer, and part of the full AT3 data
|
||||
* (i.e. ATRAC3 data ends in a subfile and continues in the next) */
|
||||
temp_sf = setup_apa3_streamfile(sf);
|
||||
if (!temp_sf) goto fail;
|
||||
|
||||
vgmstream = init_vgmstream_riff(temp_sf);
|
||||
if (!vgmstream) goto fail;
|
||||
|
||||
close_streamfile(temp_sf);
|
||||
return vgmstream;
|
||||
|
||||
fail:
|
||||
close_streamfile(temp_sf);
|
||||
close_vgmstream(vgmstream);
|
||||
return NULL;
|
||||
}
|
81
src/meta/apa3_streamfile.h
Normal file
81
src/meta/apa3_streamfile.h
Normal file
@ -0,0 +1,81 @@
|
||||
#ifndef _APA3_STREAMFILE_H_
|
||||
#define _APA3_STREAMFILE_H_
|
||||
#include "meta.h"
|
||||
|
||||
|
||||
#define ATX_MAX_SEGMENTS 2
|
||||
|
||||
|
||||
static STREAMFILE* setup_apa3_streamfile(STREAMFILE* sf) {
|
||||
STREAMFILE* new_sf = NULL;
|
||||
STREAMFILE* segments_sf[ATX_MAX_SEGMENTS] = {0};
|
||||
char filename[PATH_LIMIT];
|
||||
size_t riff_size;
|
||||
|
||||
|
||||
/* this must be first segment */
|
||||
if (read_u16le(0x1c,sf) != 0)
|
||||
return NULL;
|
||||
int total_segments = read_u16le(0x1e,sf);
|
||||
if (total_segments < 1 || total_segments > ATX_MAX_SEGMENTS)
|
||||
return NULL;
|
||||
|
||||
/* expected segment name: X_XXX_XXX_0n.ATX, starting from n=1 */
|
||||
get_streamfile_filename(sf, filename, PATH_LIMIT);
|
||||
size_t filename_len = strlen(filename);
|
||||
if (filename_len < 7 || filename[filename_len - 5] != '1')
|
||||
return NULL;
|
||||
|
||||
/* setup segments (could avoid reopening first segment but meh) */
|
||||
for (int i = 0; i < total_segments; i++) {
|
||||
off_t subfile_offset;
|
||||
size_t subfile_size;
|
||||
|
||||
filename[filename_len - 5] = ('0' + i + 1); /* digit conversion */
|
||||
|
||||
segments_sf[i] = open_streamfile_by_filename(sf, filename);
|
||||
if (!segments_sf[i]) goto fail;
|
||||
|
||||
if (!is_id32be(0x00, segments_sf[i], "APA3"))
|
||||
goto fail;
|
||||
|
||||
/* parse block/segment header (other Media.Vision's files use it too) */
|
||||
subfile_offset = read_32bitLE(0x08, segments_sf[i]); /* header size */
|
||||
subfile_size = read_32bitLE(0x14, segments_sf[i]); /* can be 0 in other containers */
|
||||
|
||||
if (read_u16le(0x1c,segments_sf[i]) != i)
|
||||
goto fail; /* segment sequence */
|
||||
// 0x04: block size (should match subfile_size in .ATX)
|
||||
// 0x0c: flags? also in other files
|
||||
// 0x10/18: null
|
||||
// 0x1e: total segments
|
||||
|
||||
/* clamp to ignore header/footer during next reads */
|
||||
segments_sf[i] = open_clamp_streamfile_f(segments_sf[i], subfile_offset, subfile_size);
|
||||
if (!segments_sf[i]) goto fail;
|
||||
}
|
||||
|
||||
/* setup with all segments and clamp further using riff_size (last segment has padding) */
|
||||
riff_size = read_32bitLE(read_32bitLE(0x08,sf) + 0x04,sf) + 0x08;
|
||||
|
||||
new_sf = open_multifile_streamfile_f(segments_sf, total_segments);
|
||||
new_sf = open_clamp_streamfile_f(new_sf, 0, riff_size);
|
||||
new_sf = open_fakename_streamfile_f(new_sf, NULL, "at3");
|
||||
|
||||
/* if all this worked we'll have this frankenstein streamfile:
|
||||
* fakename( clamp( multifile( segment0=clamp(standard(FILE)), segment1=clamp(standard(FILE)) ) ) ) */
|
||||
|
||||
return new_sf;
|
||||
fail:
|
||||
if (!new_sf) {
|
||||
for (int i = 0; i < total_segments; i++) {
|
||||
close_streamfile(segments_sf[i]);
|
||||
}
|
||||
} else {
|
||||
close_streamfile(new_sf); /* closes all segments */
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
#endif
|
113
src/meta/atx.c
113
src/meta/atx.c
@ -1,113 +0,0 @@
|
||||
#include "meta.h"
|
||||
#include "../coding/coding.h"
|
||||
|
||||
#define ATX_MAX_SEGMENTS 2
|
||||
|
||||
static STREAMFILE* setup_atx_streamfile(STREAMFILE *streamFile);
|
||||
|
||||
/* .ATX - Media.Vision's segmented RIFF AT3 wrapper [Senjo no Valkyria 3 (PSP), Shining Blade (PSP)] */
|
||||
VGMSTREAM * init_vgmstream_atx(STREAMFILE *streamFile) {
|
||||
VGMSTREAM *vgmstream = NULL;
|
||||
STREAMFILE *temp_streamFile = NULL;
|
||||
|
||||
|
||||
/* check extensions */
|
||||
if ( !check_extensions(streamFile,"atx"))
|
||||
goto fail;
|
||||
if (read_32bitBE(0x00,streamFile) != 0x41504133) /* "APA3" */
|
||||
goto fail;
|
||||
|
||||
/* .ATX is made of subfile segments, handled by the streamFile.
|
||||
* Each segment has a header/footer, and part of the whole data
|
||||
* (i.e. ATRAC3 data ends in a subfile and continues in the next) */
|
||||
temp_streamFile = setup_atx_streamfile(streamFile);
|
||||
if (!temp_streamFile) goto fail;
|
||||
|
||||
vgmstream = init_vgmstream_riff(temp_streamFile);
|
||||
if (!vgmstream) goto fail;
|
||||
|
||||
close_streamfile(temp_streamFile);
|
||||
return vgmstream;
|
||||
|
||||
fail:
|
||||
close_streamfile(temp_streamFile);
|
||||
close_vgmstream(vgmstream);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static STREAMFILE* setup_atx_streamfile(STREAMFILE *streamFile) {
|
||||
STREAMFILE *temp_streamFile = NULL, *new_streamFile = NULL;
|
||||
STREAMFILE *segment_streamFiles[ATX_MAX_SEGMENTS] = {0};
|
||||
char filename[PATH_LIMIT];
|
||||
size_t filename_len;
|
||||
int i, num_segments = 0;
|
||||
size_t riff_size;
|
||||
|
||||
|
||||
if (read_16bitLE(0x1c,streamFile) != 0) goto fail; /* this must be first segment */
|
||||
if (read_16bitLE(0x1e,streamFile) < 1 || read_16bitLE(0x1e,streamFile) > ATX_MAX_SEGMENTS) goto fail;
|
||||
num_segments = read_16bitLE(0x1e,streamFile);
|
||||
|
||||
/* expected segment name: X_XXX_XXX_0n.ATX, starting from n=1 */
|
||||
get_streamfile_filename(streamFile, filename,PATH_LIMIT);
|
||||
filename_len = strlen(filename);
|
||||
if (filename_len < 7 || filename[filename_len - 5] != '1') goto fail;
|
||||
|
||||
/* setup segments (could avoid reopening first segment but meh) */
|
||||
for (i = 0; i < num_segments; i++) {
|
||||
off_t subfile_offset;
|
||||
size_t subfile_size;
|
||||
|
||||
filename[filename_len - 5] = ('0'+i+1); /* ghetto digit conversion */
|
||||
new_streamFile = open_streamfile_by_filename(streamFile, filename);
|
||||
if (!new_streamFile) goto fail;
|
||||
segment_streamFiles[i] = new_streamFile;
|
||||
|
||||
if (read_32bitBE(0x00,segment_streamFiles[i]) != 0x41504133) /* "APA3" */
|
||||
goto fail;
|
||||
|
||||
/* parse block/segment header (other Media.Vision's files use it too) */
|
||||
subfile_offset = read_32bitLE(0x08,segment_streamFiles[i]); /* header size */
|
||||
subfile_size = read_32bitLE(0x14,segment_streamFiles[i]); /* can be 0 in other containers */
|
||||
|
||||
if (read_16bitLE(0x1c,segment_streamFiles[i]) != i)
|
||||
goto fail; /* segment sequence */
|
||||
/* 0x04: block size (should match subfile_size in .ATX) */
|
||||
/* 0x0c: flags? also in other files, 0x10/18: null, 0x1e: segments */
|
||||
|
||||
/* clamp to ignore header/footer during next reads */
|
||||
new_streamFile = open_clamp_streamfile(segment_streamFiles[i], subfile_offset,subfile_size);
|
||||
if (!new_streamFile) goto fail;
|
||||
segment_streamFiles[i] = new_streamFile;
|
||||
}
|
||||
|
||||
/* setup with all segments and clamp further using riff_size (last segment has padding) */
|
||||
riff_size = read_32bitLE(read_32bitLE(0x08,streamFile) + 0x04,streamFile) + 0x08;
|
||||
|
||||
new_streamFile = open_multifile_streamfile(segment_streamFiles, num_segments);
|
||||
if (!new_streamFile) goto fail;
|
||||
temp_streamFile = new_streamFile;
|
||||
|
||||
new_streamFile = open_clamp_streamfile(temp_streamFile, 0,riff_size);
|
||||
if (!new_streamFile) goto fail;
|
||||
temp_streamFile = new_streamFile;
|
||||
|
||||
new_streamFile = open_fakename_streamfile(temp_streamFile, NULL, "at3");
|
||||
if (!new_streamFile) goto fail;
|
||||
temp_streamFile = new_streamFile;
|
||||
|
||||
/* if all this worked we'll have this frankenstein streamfile:
|
||||
* fakename( clamp( multifile( segment0=clamp(standard(FILE)), segment1=clamp(standard(FILE)) ) ) ) */
|
||||
|
||||
return temp_streamFile;
|
||||
|
||||
fail:
|
||||
if (!temp_streamFile) {
|
||||
for (i = 0; i < num_segments; i++) {
|
||||
close_streamfile(segment_streamFiles[i]);
|
||||
}
|
||||
} else {
|
||||
close_streamfile(temp_streamFile); /* closes all segments */
|
||||
}
|
||||
return NULL;
|
||||
}
|
@ -688,7 +688,7 @@ VGMSTREAM * init_vgmstream_atsl(STREAMFILE *streamFile);
|
||||
VGMSTREAM * init_vgmstream_sps_n1(STREAMFILE *streamFile);
|
||||
VGMSTREAM * init_vgmstream_sps_n1_segmented(STREAMFILE *streamFile);
|
||||
|
||||
VGMSTREAM * init_vgmstream_atx(STREAMFILE *streamFile);
|
||||
VGMSTREAM* init_vgmstream_apa3(STREAMFILE *streamFile);
|
||||
|
||||
VGMSTREAM * init_vgmstream_sqex_sead(STREAMFILE * streamFile);
|
||||
|
||||
|
@ -334,7 +334,7 @@ init_vgmstream_t init_vgmstream_functions[] = {
|
||||
init_vgmstream_xwc,
|
||||
init_vgmstream_atsl,
|
||||
init_vgmstream_sps_n1,
|
||||
init_vgmstream_atx,
|
||||
init_vgmstream_apa3,
|
||||
init_vgmstream_sqex_sead,
|
||||
init_vgmstream_waf,
|
||||
init_vgmstream_wave,
|
||||
|
Loading…
x
Reference in New Issue
Block a user