added blocked format for Future Cop L.A.P.D.

added new IDSP format
added various stuff to MUSX
rewritten FSB3 meta (still WIP)
added .bo2 (Blood Omen 2 NGC)
added .mpds (Big Air Freestyle NGC)
added .khv (Kingdom Hearts 2 PS2)
added .voi (Raw Danger 2 PS2)
added .ddsp and a new dsp meta to ngc_dsp_std.c
moved source from wii_was.c to ngc_dsp_std.c
rewritten PDT meta (Mario Party games)


git-svn-id: https://vgmstream.svn.sourceforge.net/svnroot/vgmstream@782 51a99a44-fe44-0410-b1ba-c3e57ba2b86b
This commit is contained in:
manakoAT 2010-04-20 20:26:10 +00:00
parent 2439a59e42
commit 8a8d77149f
27 changed files with 1501 additions and 520 deletions

View File

@ -45,7 +45,8 @@ LAYOUT_OBJS=layout/ast_blocked.o \
layout/filp_blocked.o \
layout/aax_layout.o \
layout/ivaud_layout.o \
layout/mxch_blocked.o
layout/mxch_blocked.o \
layout/mgav_blocked.o
META_OBJS=meta/adx_header.o \
meta/afc_header.o \
@ -212,7 +213,6 @@ META_OBJS=meta/adx_header.o \
meta/pc_sob.o \
meta/exakt_sc.o \
meta/wii_bns.o \
meta/wii_was.o \
meta/pona.o \
meta/fsb_test.o \
meta/xbox_hlwav.o \
@ -233,7 +233,12 @@ META_OBJS=meta/adx_header.o \
meta/ps2_msa.o \
meta/pc_smp.o \
meta/p3d.o \
meta/ps2_adsc.o
meta/ps2_adsc.o \
meta/psx_str_mgav.o \
meta/ngc_bo2.o \
meta/ngc_dsp_mpds.o \
meta/ps2_khv.o \
meta/ps2_voi.o
OBJECTS=vgmstream.o streamfile.o util.o $(CODING_OBJS) $(LAYOUT_OBJS) $(META_OBJS)

View File

@ -30,5 +30,6 @@ liblayout_la_SOURCES += filp_blocked.c
liblayout_la_SOURCES += aax_layout.c
liblayout_la_SOURCES += ivaud_layout.c
liblayout_la_SOURCES += mxch_blocked.c
liblayout_la_SOURCES += psx_mgav_blocked.c
EXTRA_DIST = layout.h

View File

@ -112,6 +112,9 @@ void render_vgmstream_blocked(sample * buffer, int32_t sample_count, VGMSTREAM *
case layout_ivaud_blocked:
ivaud_block_update(vgmstream->next_block_offset,vgmstream);
break;
case layout_psx_mgav_blocked:
psx_mgav_block_update(vgmstream->next_block_offset,vgmstream);
break;
default:
break;
}

View File

@ -58,4 +58,6 @@ void render_vgmstream_aix(sample * buffer, int32_t sample_count, VGMSTREAM * vgm
void render_vgmstream_aax(sample * buffer, int32_t sample_count, VGMSTREAM * vgmstream);
void psx_mgav_block_update(off_t block_offset, VGMSTREAM * vgmstream);
#endif

View File

@ -0,0 +1,17 @@
#include "layout.h"
#include "../vgmstream.h"
/* set up for the block at the given offset */
void psx_mgav_block_update(off_t block_offset, VGMSTREAM * vgmstream) {
int i;
vgmstream->current_block_offset = block_offset;
vgmstream->current_block_size = read_32bitLE(vgmstream->current_block_offset+0x04,vgmstream->ch[0].streamfile)-0x1C;
vgmstream->next_block_offset = vgmstream->current_block_offset+vgmstream->current_block_size+0x1C;
vgmstream->current_block_size/=vgmstream->channels;
for (i=0;i<vgmstream->channels;i++) {
vgmstream->ch[i].offset = vgmstream->current_block_offset+0x1C+(vgmstream->current_block_size*i);
}
}

View File

@ -1,7 +1,7 @@
<?xml version="1.0" encoding="UTF-8"?>
<VisualStudioProject
ProjectType="Visual C++"
Version="9.00"
Version="9,00"
Name="libvgmstream"
ProjectGUID="{54A6AD11-5369-4895-A06F-E255ABB99B11}"
RootNamespace="libvgmstream"
@ -196,6 +196,10 @@
<Filter
Name="Source Files"
>
<File
RelativePath=".\meta\#dsp_test.c"
>
</File>
<File
RelativePath=".\meta\2dx.c"
>
@ -442,10 +446,18 @@
RelativePath=".\meta\ngc_bh2pcm.c"
>
</File>
<File
RelativePath=".\meta\ngc_bo2.c"
>
</File>
<File
RelativePath=".\meta\ngc_caf.c"
>
</File>
<File
RelativePath=".\meta\ngc_dsp_mpds.c"
>
</File>
<File
RelativePath=".\meta\ngc_dsp_std.c"
>
@ -610,6 +622,10 @@
RelativePath=".\meta\ps2_kces.c"
>
</File>
<File
RelativePath=".\meta\ps2_khv.c"
>
</File>
<File
RelativePath=".\meta\ps2_leg.c"
>
@ -734,6 +750,10 @@
RelativePath=".\meta\ps2_vgv.c"
>
</File>
<File
RelativePath=".\meta\ps2_voi.c"
>
</File>
<File
RelativePath=".\meta\ps2_vpk.c"
>
@ -762,6 +782,10 @@
RelativePath=".\meta\psx_gms.c"
>
</File>
<File
RelativePath=".\meta\psx_str_mgav.c"
>
</File>
<File
RelativePath=".\meta\raw.c"
>
@ -898,10 +922,6 @@
RelativePath=".\meta\wii_sts.c"
>
</File>
<File
RelativePath=".\meta\wii_was.c"
>
</File>
<File
RelativePath=".\meta\ws_aud.c"
>
@ -1162,6 +1182,10 @@
RelativePath=".\layout\nolayout.c"
>
</File>
<File
RelativePath=".\layout\psx_mgav_blocked.c"
>
</File>
<File
RelativePath=".\layout\str_snds_blocked.c"
>

View File

@ -168,7 +168,6 @@ libmeta_la_SOURCES += pc_mxst.c
libmeta_la_SOURCES += pc_sob.c
libmeta_la_SOURCES += exakt_sc.c
libmeta_la_SOURCES += wii_bns.c
libmeta_la_SOURCES += wii_was.c
libmeta_la_SOURCES += pona.c
libmeta_la_SOURCES += fsb_test.c
libmeta_la_SOURCES += xbox_hlwav.c
@ -190,5 +189,10 @@ libmeta_la_SOURCES += ps2_msa.c
libmeta_la_SOURCES += pc_smp.c
libmeta_la_SOURCES += p3d.c
libmeta_la_SOURCES += ps2_adsc.c
libmeta_la_SOURCES += psx_str_mgav.c
libmeta_la_SOURCES += ngc_bo2.c
libmeta_la_SOURCES += ngc_dsp_mpds.c
libmeta_la_SOURCES += ps2_khv.c
libmeta_la_SOURCES += ps2_voi.c
EXTRA_DIST = meta.h

View File

@ -60,7 +60,7 @@ VGMSTREAM * init_vgmstream_emff_ps2(STREAMFILE *streamFile) {
/* Calc num_samples */
emff_ps2_block_update(start_offset,vgmstream);
vgmstream->num_samples = read_32bitLE(0x8,streamFile);;
vgmstream->num_samples = read_32bitLE(0x8,streamFile);
if (loop_flag) {
vgmstream->loop_start_sample = (read_32bitLE(0x28,streamFile)-start_offset)*28/16/channel_count;
vgmstream->loop_end_sample = read_32bitLE(0x8,streamFile);

View File

@ -1,120 +1,96 @@
#include "meta.h"
#include "../util.h"
/* FSB3.0 & FSB3.1*/
/* FSB3.0 */
VGMSTREAM * init_vgmstream_fsb3(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
int fsb_headerlen;
int loop_flag;
int channel_count;
int channel_count;
int loop_flag = 0;
int FSBFlag = 0;
int i, c;
off_t start_offset;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("fsb",filename_extension(filename)) &&
strcasecmp("lfsb",filename_extension(filename)))
goto fail;
/* check header */
if (read_32bitBE(0x00,streamFile) != 0x46534233) goto fail; /* "FSB3" */
/* "Check if the FSB is used as conatiner or as single file" */
if (read_32bitLE(0x04,streamFile) != 0x1) goto fail;
/* Check if we're dealing with a FSB3.0 or FSB3.1 file */
if ((read_32bitBE(0x10,streamFile) != 0x00000300) &&
(read_32bitBE(0x10,streamFile) != 0x01000300))
if (strcasecmp("fsb",filename_extension(filename)))
goto fail;
/* check header for "FSB3" string */
if (read_32bitBE(0x00,streamFile) != 0x46534233)
goto fail;
/* "Check if the FSB is used as conatiner or as single file" */
if (read_32bitLE(0x04,streamFile) != 0x1)
goto fail;
/* Check if we're dealing with a FSB3.0 file */
if ((read_32bitBE(0x10,streamFile) != 0x00000300) &&
((read_32bitBE(0x10,streamFile) != 0x01000300)))
goto fail;
if (read_32bitBE(0x48,streamFile) == 0x02000806) { // Metroid Prime 3
loop_flag = 1;
} else {
loop_flag = 0;
}
channel_count = read_16bitLE(0x56,streamFile);
fsb_headerlen = read_32bitLE(0x08,streamFile);
channel_count = read_16bitLE(0x56,streamFile);
fsb_headerlen = read_32bitLE(0x08,streamFile);
FSBFlag = read_32bitLE(0x48,streamFile);
if (FSBFlag&0x2 || FSBFlag&0x4 || FSBFlag&0x6)
loop_flag = 1;
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
// fsb_format = ;
switch (((uint8_t)read_8bit(0x4A, streamFile)) >> 4) {
case 0x0: // Nintendo DSP
// Hack to support an illegal coding flag
if (read_32bitBE(0x48,streamFile) == 0x50010000) { // Fantastic 4: Rise of the Silver Surfer
vgmstream->coding_type = coding_PCM16LE;
vgmstream->num_samples = (read_32bitLE(0x0C,streamFile))/2/channel_count;
if (loop_flag) {
vgmstream->loop_start_sample = 0;
vgmstream->loop_end_sample = (read_32bitLE(0x0C,streamFile))/2/channel_count;
}
if (channel_count == 1) {
vgmstream->layout_type = layout_none;
} else if (channel_count > 1) {
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = 2;
}
} else {
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->num_samples = (read_32bitLE(0x0C,streamFile))*14/8/channel_count;
if (loop_flag) {
vgmstream->loop_start_sample = 0;
vgmstream->loop_end_sample = (read_32bitLE(0x0C,streamFile))*14/8/channel_count;
}
if (channel_count == 1) {
vgmstream->layout_type = layout_none;
} else if (channel_count > 1) {
vgmstream->layout_type = layout_interleave_byte;
vgmstream->interleave_block_size = 2;
}
}
break;
case 0x4: // XBOX IMA ADPCM
vgmstream->coding_type = coding_XBOX;
vgmstream->layout_type = layout_none;
vgmstream->num_samples = read_32bitLE(0x0C,streamFile)*64/36/channel_count;
if (loop_flag) {
vgmstream->loop_start_sample = 0;
vgmstream->loop_end_sample = read_32bitLE(0x0C,streamFile)*64/36/channel_count;
}
break;
case 0x8: // PS2 APDCM
vgmstream->coding_type = coding_PSX;
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = 0x10;
vgmstream->num_samples = (read_32bitLE(0x0C,streamFile))*28/16/channel_count;
if (loop_flag) {
vgmstream->loop_start_sample = 0;
vgmstream->loop_end_sample = (read_32bitLE(0x0C,streamFile))*28/16/channel_count;
}
break;
default:
goto fail;
}
/* fill in the vital statistics */
start_offset = fsb_headerlen+0x18;
vgmstream->sample_rate = (read_32bitLE(0x4C, streamFile));
if (read_32bitBE(0x10,streamFile) == 0x00000300) {
vgmstream->meta_type = meta_FSB3_0;
} else if (read_32bitBE(0x10,streamFile) == 0x01000300) {
vgmstream->meta_type = meta_FSB3_1;
// XBOX IMA
if (FSBFlag&0x00400000) {
vgmstream->coding_type = coding_XBOX;
vgmstream->layout_type = layout_none;
}
if (vgmstream->coding_type == coding_NGC_DSP) {
int i,c;
// PS2 ADPCM
else if (FSBFlag&0x00800000) {
vgmstream->coding_type = coding_PSX;
if (channel_count == 1) {
vgmstream->layout_type = layout_none;
} else if (channel_count > 1) {
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = 0x10;
}
}
// Nintendo DSP
else if (FSBFlag&0x02000000) {
vgmstream->coding_type = coding_NGC_DSP;
if (channel_count == 1) {
vgmstream->layout_type = layout_none;
} else if (channel_count > 1) {
vgmstream->layout_type = layout_interleave_byte;
vgmstream->interleave_block_size = 2;
}
for (c=0;c<channel_count;c++) {
for (i=0;i<16;i++) {
vgmstream->ch[c].adpcm_coef[i] =
read_16bitBE(0x68+c*0x2e +i*2,streamFile);
}
}
}
vgmstream->num_samples = read_32bitLE(0x38,streamFile);
if (loop_flag) {
vgmstream->loop_start_sample = read_32bitLE(0x40,streamFile);
vgmstream->loop_end_sample = read_32bitLE(0x44,streamFile);
}
vgmstream->meta_type = meta_FSB3_0;
/* open the file for reading */
{
int i;

View File

@ -5,11 +5,10 @@
VGMSTREAM * init_vgmstream_idsp(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
int loop_flag = 0;
int channel_count;
off_t start_offset;
int loop_flag;
int channel_count;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("idsp",filename_extension(filename))) goto fail;
@ -18,17 +17,20 @@ VGMSTREAM * init_vgmstream_idsp(STREAMFILE *streamFile) {
if (read_32bitBE(0x00,streamFile) != 0x49445350) /* "IDSP" */
goto fail;
loop_flag = 0;
channel_count = read_32bitBE(0x04,streamFile);
/* build the VGMSTREAM */
if (channel_count > 8)
{
goto fail;
}
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
/* fill in the vital statistics */
start_offset = 0xD0;
vgmstream->channels = channel_count;
vgmstream->channels = channel_count;
vgmstream->sample_rate = read_32bitBE(0x28,streamFile);
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->num_samples = read_32bitBE(0x20,streamFile);
@ -41,7 +43,6 @@ VGMSTREAM * init_vgmstream_idsp(STREAMFILE *streamFile) {
vgmstream->interleave_block_size = read_32bitBE(0x0C,streamFile);
vgmstream->meta_type = meta_IDSP;
if (vgmstream->coding_type == coding_NGC_DSP) {
int i;
for (i=0;i<16;i++) {
@ -78,8 +79,6 @@ fail:
return NULL;
}
/* "idsp/IDSP"
Soul Calibur Legends (Wii)
Sky Crawlers: Innocent Aces (Wii)
@ -87,10 +86,10 @@ fail:
VGMSTREAM * init_vgmstream_idsp2(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
off_t start_offset;
int loop_flag;
int channel_count;
int i, j;
int channel_count;
int i, j;
off_t start_offset;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
@ -104,11 +103,16 @@ VGMSTREAM * init_vgmstream_idsp2(STREAMFILE *streamFile) {
loop_flag = read_32bitBE(0x20,streamFile);
channel_count = read_32bitBE(0xC4,streamFile);
/* build the VGMSTREAM */
if (channel_count > 8)
{
goto fail;
}
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
/* fill in the vital statistics */
start_offset = (channel_count * 0x60) + 0x100;
vgmstream->channels = channel_count;
vgmstream->sample_rate = read_32bitBE(0xC8,streamFile);
@ -119,30 +123,36 @@ VGMSTREAM * init_vgmstream_idsp2(STREAMFILE *streamFile) {
vgmstream->loop_end_sample = (read_32bitBE(0xD4,streamFile));
}
if (channel_count == 1) {
if (channel_count == 1)
{
vgmstream->layout_type = layout_none;
} else if (channel_count > 1) {
if (read_32bitBE(0xD8,streamFile) == 0) {
vgmstream->layout_type = layout_none;
vgmstream->interleave_block_size = (get_streamfile_size(streamFile)-start_offset)/2;
} else if (read_32bitBE(0xD8,streamFile) > 0) {
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = read_32bitBE(0xD8,streamFile);
}
}
}
else if (channel_count > 1)
{
if (read_32bitBE(0xD8,streamFile) == 0)
{
vgmstream->layout_type = layout_none;
vgmstream->interleave_block_size = (get_streamfile_size(streamFile)-start_offset)/2;
}
else if (read_32bitBE(0xD8,streamFile) > 0)
{
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = read_32bitBE(0xD8,streamFile);
}
}
vgmstream->meta_type = meta_IDSP2;
vgmstream->meta_type = meta_IDSP;
{
if (vgmstream->coding_type == coding_NGC_DSP) {
off_t coef_table[8] = {0x118,0x178,0x1D8,0x238,0x298,0x2F8,0x358,0x3B8};
for (j=0;j<vgmstream->channels;j++) {
for (i=0;i<16;i++) {
vgmstream->ch[j].adpcm_coef[i] = read_16bitBE(coef_table[j]+i*2,streamFile);
}
}
}
}
{
if (vgmstream->coding_type == coding_NGC_DSP) {
off_t coef_table[8] = {0x118,0x178,0x1D8,0x238,0x298,0x2F8,0x358,0x3B8};
for (j=0;j<vgmstream->channels;j++) {
for (i=0;i<16;i++) {
vgmstream->ch[j].adpcm_coef[i] = read_16bitBE(coef_table[j]+i*2,streamFile);
}
}
}
}
/* open the file for reading */
{
@ -175,10 +185,9 @@ fail:
VGMSTREAM * init_vgmstream_idsp3(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
off_t start_offset;
int loop_flag = 1;
int channel_count;
int channel_count;
off_t start_offset;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
@ -188,17 +197,20 @@ VGMSTREAM * init_vgmstream_idsp3(STREAMFILE *streamFile) {
if (read_32bitBE(0x00,streamFile) != 0x49445350) /* IDSP */
goto fail;
// loop_flag = read_32bitBE(0x08,streamFile);
channel_count = read_32bitBE(0x24,streamFile);
/* build the VGMSTREAM */
if (channel_count > 8)
{
goto fail;
}
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
/* fill in the vital statistics */
start_offset = 0xD4;
vgmstream->channels = channel_count;
vgmstream->channels = channel_count;
vgmstream->sample_rate = read_32bitBE(0x14,streamFile);
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->num_samples = read_32bitBE(0x0C,streamFile);
@ -207,10 +219,9 @@ VGMSTREAM * init_vgmstream_idsp3(STREAMFILE *streamFile) {
vgmstream->loop_end_sample = (read_32bitBE(0x0C,streamFile));
}
vgmstream->layout_type = layout_interleave;
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = read_32bitBE(0x04,streamFile);
vgmstream->meta_type = meta_IDSP3;
vgmstream->meta_type = meta_IDSP;
if (vgmstream->coding_type == coding_NGC_DSP) {
int i;
@ -249,4 +260,86 @@ fail:
}
/* IDSP (Defender NGC) */
VGMSTREAM * init_vgmstream_idsp4(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
int loop_flag = 0;
int channel_count;
off_t start_offset;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("idsp",filename_extension(filename))) goto fail;
/* check header */
if (read_32bitBE(0x00,streamFile) != 0x49445350) /* "IDSP" */
goto fail;
channel_count = read_32bitBE(0x0C,streamFile);
if (channel_count > 2) // Refuse everything else for now
{
goto fail;
}
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
start_offset = 0x70;
vgmstream->channels = channel_count;
vgmstream->sample_rate = read_32bitBE(0x08,streamFile);
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->num_samples = read_32bitBE(0x04,streamFile)/channel_count/8*14;
if (loop_flag) {
vgmstream->loop_start_sample = 0;
vgmstream->loop_end_sample = read_32bitBE(0x04,streamFile)/channel_count/8*14;
}
if (channel_count == 1)
{
vgmstream->layout_type = layout_none;
}
else
{
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = read_32bitBE(0x10,streamFile);
}
vgmstream->meta_type = meta_IDSP;
{
int i;
for (i=0;i<16;i++)
vgmstream->ch[0].adpcm_coef[i] = read_16bitBE(0x14+i*2,streamFile);
if (channel_count == 2) {
for (i=0;i<16;i++)
vgmstream->ch[1].adpcm_coef[i] = read_16bitBE(0x42+i*2,streamFile);
}
}
/* open the file for reading */
{
int i;
STREAMFILE * file;
file = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!file) goto fail;
for (i=0;i<channel_count;i++) {
vgmstream->ch[i].streamfile = file;
vgmstream->ch[i].channel_start_offset=
vgmstream->ch[i].offset=start_offset+
vgmstream->interleave_block_size*i;
}
}
return vgmstream;
/* clean up anything we may have opened */
fail:
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}

View File

@ -251,6 +251,8 @@ VGMSTREAM * init_vgmstream_idsp2(STREAMFILE * streamFile);
VGMSTREAM * init_vgmstream_idsp3(STREAMFILE * streamFile);
VGMSTREAM * init_vgmstream_idsp4(STREAMFILE * streamFile);
VGMSTREAM * init_vgmstream_ngc_ymf(STREAMFILE * streamFile);
VGMSTREAM * init_vgmstream_sadl(STREAMFILE * streamFile);
@ -459,12 +461,26 @@ VGMSTREAM * init_vgmstream_ps2_smpl(STREAMFILE* streamFile);
VGMSTREAM * init_vgmstream_ps2_msa(STREAMFILE* streamFile);
VGMSTREAM * init_vgmstream_ps2_voi(STREAMFILE* streamFile);
VGMSTREAM * init_vgmstream_ps2_khv(STREAMFILE* streamFile);
VGMSTREAM * init_vgmstream_pc_smp(STREAMFILE* streamFile);
VGMSTREAM * init_vgmstream_ngc_bo2(STREAMFILE* streamFile);
VGMSTREAM * init_vgmstream_dsp_ddsp(STREAMFILE* streamFile);
VGMSTREAM * init_vgmstream_p3d(STREAMFILE* streamFile);
VGMSTREAM * init_vgmstream_ps2_tk1(STREAMFILE* streamFile);
VGMSTREAM * init_vgmstream_ps2_adsc(STREAMFILE* streamFile);
VGMSTREAM * init_vgmstream_ngc_dsp_mpds(STREAMFILE* streamFile);
VGMSTREAM * init_vgmstream_dsp_str_ig(STREAMFILE* streamFile);
VGMSTREAM * init_vgmstream_psx_mgav(STREAMFILE* streamFile);
#endif

View File

@ -6,11 +6,9 @@
VGMSTREAM * init_vgmstream_musx_v004(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
int loop_flag = 0;
int channel_count;
off_t start_offset;
int musx_type; /* determining the decoder by strings like "PS2_", "GC__" and so on */
//int musx_version; /* 0x08 provides a "version" byte */
int loop_flag = 0;
int channel_count;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
@ -18,57 +16,68 @@ VGMSTREAM * init_vgmstream_musx_v004(STREAMFILE *streamFile) {
/* check header */
if (read_32bitBE(0x00,streamFile) != 0x4D555358) /* "MUSX" */
goto fail;
if (read_32bitBE(0x08,streamFile) != 0x04000000) /* "0x04000000" */
goto fail;
/* This is tricky, the header changes it's layout if the file is unlooped */
goto fail;
if (read_32bitBE(0x08,streamFile) != 0x04000000) /* "0x04000000" */
goto fail;
/* This is tricky, the header changes it's layout if the file is unlooped */
loop_flag = (read_32bitLE(0x840,streamFile)!=0xFFFFFFFF);
channel_count = 2;
/* build the VGMSTREAM */
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
musx_type=(read_32bitBE(0x10,streamFile));
switch (musx_type) {
case 0x5053325F: /* PS2_ */
switch (read_32bitBE(0x10,streamFile))
{
case 0x5053325F: /* PS2_ */
start_offset = read_32bitLE(0x28,streamFile);
vgmstream->channels = channel_count;
vgmstream->sample_rate = 32000;
vgmstream->coding_type = coding_PSX;
vgmstream->num_samples = (read_32bitLE(0x0C,streamFile))*28/16/channel_count;
vgmstream->coding_type = coding_PSX; // PS2 ADPCM
vgmstream->num_samples = (read_32bitLE(0x0C,streamFile))/16/channel_count*28;
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = 0x80;
vgmstream->meta_type = meta_MUSX_V004;
if (loop_flag) {
vgmstream->loop_start_sample = (read_32bitLE(0x890,streamFile))*28/16/channel_count;
vgmstream->loop_end_sample = (read_32bitLE(0x89C,streamFile))*28/16/channel_count;
}
break;
/* seems to not work for Spyro, maybe i find other games for testing
case 0x58425F5F: XB__
start_offset = read_32bitLE(0x28,streamFile);
if (loop_flag)
{
vgmstream->loop_start_sample = (read_32bitLE(0x890,streamFile))/16/channel_count*28;
vgmstream->loop_end_sample = (read_32bitLE(0x89C,streamFile))/16/channel_count*28;
}
break;
case 0x47435F5F: /* GC__ */
start_offset = read_32bitBE(0x28,streamFile);
vgmstream->channels = channel_count;
vgmstream->sample_rate = 32000;
vgmstream->coding_type = coding_XBOX;
vgmstream->num_samples = (read_32bitLE(0x0C,streamFile))*64/36/channel_count;
vgmstream->layout_type = layout_none;
vgmstream->meta_type = meta_MUSX_V004;
if (loop_flag) {
vgmstream->loop_start_sample = (read_32bitLE(0x890,streamFile))*64/36/channel_count;
vgmstream->loop_end_sample = (read_32bitLE(0x89C,streamFile))*64/36/channel_count;
}
break;
*/
default:
goto fail;
}
vgmstream->coding_type = coding_DAT4_IMA; // Eurocom DAT4 4-bit IMA ADPCM
vgmstream->num_samples = (read_32bitBE(0x2C,streamFile))/16/channel_count*28;
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = 0x20;
if (loop_flag)
{
vgmstream->loop_start_sample = (read_32bitBE(0x890,streamFile))/16/channel_count*28;
vgmstream->loop_end_sample = (read_32bitBE(0x89C,streamFile))/16/channel_count*28;
}
break;
case 0x58425F5F: /* XB__ */
start_offset = read_32bitLE(0x28,streamFile);
vgmstream->channels = channel_count;
vgmstream->sample_rate = 44100;
vgmstream->coding_type = coding_DAT4_IMA; // Eurocom DAT4 4-bit IMA ADPCM
vgmstream->num_samples = (read_32bitLE(0x2C,streamFile))/16/channel_count*28;
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = 0x20;
if (loop_flag)
{
vgmstream->loop_start_sample = (read_32bitLE(0x890,streamFile))/16/channel_count*28;
vgmstream->loop_end_sample = (read_32bitLE(0x89C,streamFile))/16/channel_count*28;
}
break;
default:
goto fail;
}
vgmstream->meta_type = meta_MUSX_V004;
/* open the file for reading */
{
int i;
@ -78,15 +87,9 @@ VGMSTREAM * init_vgmstream_musx_v004(STREAMFILE *streamFile) {
for (i=0;i<channel_count;i++) {
vgmstream->ch[i].streamfile = file;
if (vgmstream->coding_type == coding_XBOX) {
/* xbox interleaving is a little odd */
vgmstream->ch[i].channel_start_offset=start_offset;
} else {
vgmstream->ch[i].channel_start_offset=
start_offset+vgmstream->interleave_block_size*i;
}
vgmstream->ch[i].offset = vgmstream->ch[i].channel_start_offset;
vgmstream->ch[i].channel_start_offset=
vgmstream->ch[i].offset=start_offset+
vgmstream->interleave_block_size*i;
}
}
@ -146,6 +149,20 @@ VGMSTREAM * init_vgmstream_musx_v006(STREAMFILE *streamFile) {
vgmstream->loop_start_sample = (read_32bitLE(0x890,streamFile))*28/16/channel_count;
vgmstream->loop_end_sample = (read_32bitLE(0x89C,streamFile))*28/16/channel_count;
}
break;
case 0x47435F5F: /* GC__ */
start_offset = read_32bitBE(0x28,streamFile);
vgmstream->channels = channel_count;
vgmstream->sample_rate = 32000;
vgmstream->coding_type = coding_DAT4_IMA;
vgmstream->num_samples = (read_32bitBE(0x2C,streamFile))*28/16/channel_count;
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = 0x20;
vgmstream->meta_type = meta_MUSX_V006;
if (loop_flag) {
vgmstream->loop_start_sample = (read_32bitBE(0x890,streamFile))*28/16/channel_count;
vgmstream->loop_end_sample = (read_32bitBE(0x89C,streamFile))*28/16/channel_count;
}
break;
default:
goto fail;
@ -302,7 +319,8 @@ VGMSTREAM * init_vgmstream_musx_v201(STREAMFILE *streamFile) {
/* check header */
if (read_32bitBE(0x00,streamFile) != 0x4D555358) /* "MUSX" */
goto fail;
if (read_32bitBE(0x08,streamFile) != 0xC9000000) /* "0xC9000000" */
if ((read_32bitBE(0x08,streamFile) != 0xC9000000) &&
(read_32bitLE(0x08,streamFile) != 0xC9000000)) /* "0xC9000000" */
goto fail;
channel_count = 2;

100
src/meta/ngc_bo2.c Normal file
View File

@ -0,0 +1,100 @@
#include "meta.h"
#include "../util.h"
/* BO2 (Blood Omen 2 NGC) */
VGMSTREAM * init_vgmstream_ngc_bo2(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
int loop_flag;
int channels;
int channel_count;
off_t start_offset;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("bo2",filename_extension(filename))) goto fail;
/* check header */
if (read_32bitBE(0x00,streamFile) != 0x0) /* "IDSP" */
goto fail;
switch (read_32bitBE(0x10,streamFile))
{
case 0x0:
channels = 1;
break;
case 0x1:
channels = 2;
break;
default:
goto fail;
}
if ((get_streamfile_size(streamFile)) < ((read_32bitBE(0x0C,streamFile)/14*8*channels)+0x800))
{
goto fail;
}
channel_count = channels;
loop_flag = (read_32bitBE(0x08,streamFile) != 0xFFFFFFFF);
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
start_offset = 0x800;
vgmstream->channels = channel_count;
vgmstream->sample_rate = read_32bitBE(0x04,streamFile);
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->num_samples = read_32bitBE(0x0C,streamFile);
if (loop_flag) {
vgmstream->loop_start_sample = read_32bitBE(0x08,streamFile);
vgmstream->loop_end_sample = read_32bitBE(0x0C,streamFile);
}
if (channel_count == 1)
{
vgmstream->layout_type = layout_none;
}
else
{
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = 0x400;
}
vgmstream->meta_type = meta_NGC_BO2;
{
int i;
for (i=0;i<16;i++)
vgmstream->ch[0].adpcm_coef[i] = read_16bitBE(0x24+i*2,streamFile);
if (channel_count == 2) {
for (i=0;i<16;i++)
vgmstream->ch[1].adpcm_coef[i] = read_16bitBE(0x52+i*2,streamFile);
}
}
/* open the file for reading */
{
int i;
STREAMFILE * file;
file = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!file) goto fail;
for (i=0;i<channel_count;i++) {
vgmstream->ch[i].streamfile = file;
vgmstream->ch[i].channel_start_offset=
vgmstream->ch[i].offset=start_offset+
vgmstream->interleave_block_size*i;
}
}
return vgmstream;
/* clean up anything we may have opened */
fail:
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}

100
src/meta/ngc_dsp_mpds.c Normal file
View File

@ -0,0 +1,100 @@
#include "meta.h"
#include "../util.h"
/* MPDS - found in Big Air Freestyle, Terminator 3 (no coeffs), etc */
VGMSTREAM * init_vgmstream_ngc_dsp_mpds(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
int loop_flag = 0;
int channel_count;
off_t start_offset;
int ch1_header_start, ch2_header_start, ch1_start, ch2_start;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("dsp",filename_extension(filename))) goto fail;
/* check header */
if (read_32bitBE(0x00,streamFile) != 0x4D504453) /* "MPDS" */
goto fail;
/* Version byte ??? */
if (read_32bitBE(0x04,streamFile) != 0x00010000) /* "0x10000" */
goto fail;
/* compare sample count with body size */
if (((read_32bitBE(0x08,streamFile)/7*8)) != (read_32bitBE(0x0C,streamFile)))
goto fail;
channel_count = read_32bitBE(0x14,streamFile);
if (channel_count > 2)
{
goto fail;
}
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
vgmstream->channels = channel_count;
if (channel_count == 1)
{
vgmstream->layout_type = layout_none;
ch1_start = 0x80;
}
else if (channel_count == 2)
{
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = read_32bitBE(0x18,streamFile);
ch1_start = 0x80;
ch2_start = 0x80 + vgmstream->interleave_block_size;
}
else
{
goto fail;
}
vgmstream->sample_rate = read_32bitBE(0x10,streamFile);
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->num_samples = read_32bitBE(0x08,streamFile);
if (loop_flag) {
vgmstream->loop_start_sample = 0;
vgmstream->loop_end_sample = read_32bitBE(0x08,streamFile);
}
vgmstream->meta_type = meta_NGC_DSP_MPDS;
{
int i;
for (i=0;i<16;i++)
vgmstream->ch[0].adpcm_coef[i] = read_16bitBE(0x24+i*2,streamFile);
if (channel_count == 2)
{
for (i=0;i<16;i++)
vgmstream->ch[1].adpcm_coef[i] = read_16bitBE(0x4C+i*2,streamFile);
}
}
/* open the file for reading */
vgmstream->ch[0].streamfile = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!vgmstream->ch[0].streamfile) goto fail;
vgmstream->ch[0].channel_start_offset =
vgmstream->ch[0].offset=ch1_start;
if (channel_count == 2)
{
vgmstream->ch[1].streamfile = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!vgmstream->ch[1].streamfile) goto fail;
vgmstream->ch[1].channel_start_offset =
vgmstream->ch[1].offset=ch2_start;
}
return vgmstream;
/* clean up anything we may have opened */
fail:
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}

View File

@ -1365,3 +1365,423 @@ fail:
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}
/* .ddsp files, two DSP files stuck together, without additional header */
VGMSTREAM * init_vgmstream_dsp_ddsp(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
off_t channel_1_start, channel_2_start, channel_1_size, channel_2_size;
struct dsp_header ch0_header,ch1_header;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("ddsp",filename_extension(filename))) goto fail;
/* read .wsd header */
channel_1_start = 0;
channel_2_start = (get_streamfile_size(streamFile)/2);
channel_1_size = (get_streamfile_size(streamFile)/2)-0x60;
channel_2_size = (get_streamfile_size(streamFile)/2)-0x60;
/* check header */
if (channel_1_size != channel_2_size) goto fail;
if (channel_1_start != 0x0) goto fail;
if (channel_1_size < 0x20 || channel_2_size < 0x20) goto fail;
if (channel_1_start + channel_1_size > channel_2_start) goto fail;
if (channel_2_start + channel_2_size > get_streamfile_size(streamFile))
goto fail;
/* get DSP headers */
if (read_dsp_header(&ch0_header, channel_1_start, streamFile)) goto fail;
if (read_dsp_header(&ch1_header, channel_2_start, streamFile)) goto fail;
/* check initial predictor/scale */
if (ch0_header.initial_ps !=
(uint8_t)read_8bit(channel_1_start + 0x60, streamFile))
goto fail;
if (ch1_header.initial_ps !=
(uint8_t)read_8bit(channel_2_start + 0x60, streamFile))
goto fail;
/* check type==0 and gain==0 */
if (ch0_header.format || ch0_header.gain ||
ch1_header.format || ch1_header.gain)
goto fail;
/* check for agreement */
if (
ch0_header.sample_count != ch1_header.sample_count ||
ch0_header.nibble_count != ch1_header.nibble_count ||
ch0_header.sample_rate != ch1_header.sample_rate ||
ch0_header.loop_flag != ch1_header.loop_flag ||
ch0_header.loop_start_offset != ch1_header.loop_start_offset ||
ch0_header.loop_end_offset != ch1_header.loop_end_offset
) goto fail;
if (ch0_header.loop_flag) {
off_t loop_off;
/* check loop predictor/scale */
loop_off = ch0_header.loop_start_offset/16*8;
if (ch0_header.loop_ps !=
(uint8_t)read_8bit(channel_1_start+0x60+loop_off,streamFile))
goto fail;
if (ch1_header.loop_ps !=
(uint8_t)read_8bit(channel_2_start+0x60+loop_off,streamFile))
goto fail;
}
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(2,ch0_header.loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
vgmstream->num_samples = ch0_header.sample_count;
vgmstream->sample_rate = ch0_header.sample_rate;
vgmstream->loop_start_sample = dsp_nibbles_to_samples(
ch0_header.loop_start_offset);
vgmstream->loop_end_sample = dsp_nibbles_to_samples(
ch0_header.loop_end_offset)+1;
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->layout_type = layout_none;
vgmstream->meta_type = meta_DSP_DDSP;
/* coeffs */
{
int i;
for (i=0;i<16;i++) {
vgmstream->ch[0].adpcm_coef[i] = ch0_header.coef[i];
vgmstream->ch[1].adpcm_coef[i] = ch1_header.coef[i];
}
}
/* initial history */
/* always 0 that I've ever seen, but for completeness... */
vgmstream->ch[0].adpcm_history1_16 = ch0_header.initial_hist1;
vgmstream->ch[0].adpcm_history2_16 = ch0_header.initial_hist2;
vgmstream->ch[1].adpcm_history1_16 = ch1_header.initial_hist1;
vgmstream->ch[1].adpcm_history2_16 = ch1_header.initial_hist2;
/* open the file for reading */
vgmstream->ch[0].streamfile = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!vgmstream->ch[0].streamfile) goto fail;
vgmstream->ch[1].streamfile = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!vgmstream->ch[1].streamfile) goto fail;
vgmstream->ch[0].channel_start_offset =
vgmstream->ch[0].offset=channel_1_start+0x60;
vgmstream->ch[1].channel_start_offset =
vgmstream->ch[1].offset=channel_2_start+0x60;
return vgmstream;
fail:
/* clean up anything we may have opened */
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}
/* .was files, DSP file(s), with additional iSWS header */
VGMSTREAM * init_vgmstream_wii_was(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
struct dsp_header ch0_header,ch1_header;
off_t ch1_header_start, ch2_header_start, ch1_start, ch2_start;
int channel_count;
int i;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if ((strcasecmp("dsp",filename_extension(filename))) &&
(strcasecmp("isws",filename_extension(filename))) &&
(strcasecmp("was",filename_extension(filename))))
goto fail;
/* read iSWS header */
if (read_32bitBE(0x0,streamFile) != 0x69535753)
goto fail;
channel_count = read_32bitBE(0x08,streamFile);
if (channel_count == 1)
{
ch1_header_start = 0x20;
ch1_start = 0x80;
/* get DSP headers */
if (read_dsp_header(&ch0_header, ch1_header_start, streamFile)) goto fail;
/* check initial predictor/scale */
if (ch0_header.initial_ps != (uint8_t)read_8bit(ch1_start, streamFile))
goto fail;
/* check type==0 and gain==0 */
if (ch0_header.format || ch0_header.gain)
goto fail;
if (ch0_header.loop_flag)
{
off_t loop_off;
/* check loop predictor/scale */
loop_off = ch0_header.loop_start_offset/16*8;
if (ch0_header.loop_ps != (uint8_t)read_8bit(ch1_start+loop_off,streamFile))
goto fail;
}
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(1,ch0_header.loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
vgmstream->num_samples = ch0_header.sample_count;
vgmstream->sample_rate = ch0_header.sample_rate;
vgmstream->loop_start_sample = dsp_nibbles_to_samples(
ch0_header.loop_start_offset);
vgmstream->loop_end_sample = dsp_nibbles_to_samples(
ch0_header.loop_end_offset)+1;
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->layout_type = layout_none;
vgmstream->meta_type = meta_WII_WAS;
/* coeffs */
for (i=0;i<16;i++) {
vgmstream->ch[0].adpcm_coef[i] = ch0_header.coef[i];
}
/* initial history */
/* always 0 that I've ever seen, but for completeness... */
vgmstream->ch[0].adpcm_history1_16 = ch0_header.initial_hist1;
vgmstream->ch[0].adpcm_history2_16 = ch0_header.initial_hist2;
/* open the file for reading */
vgmstream->ch[0].streamfile = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!vgmstream->ch[0].streamfile)
goto fail;
vgmstream->ch[0].channel_start_offset = vgmstream->ch[0].offset=ch1_start;
}
else if (channel_count == 2)
{
ch1_header_start = 0x20;
ch2_header_start = 0x80;
ch1_start = 0xE0;
ch2_start = 0xE0 + (read_32bitBE(0x10,streamFile));
/* get DSP headers */
if (read_dsp_header(&ch0_header, ch1_header_start, streamFile)) goto fail;
if (read_dsp_header(&ch1_header, ch2_header_start, streamFile)) goto fail;
/* check initial predictor/scale */
if (ch0_header.initial_ps != (uint8_t)read_8bit(ch1_start, streamFile))
goto fail;
if (ch1_header.initial_ps != (uint8_t)read_8bit(ch2_start, streamFile))
goto fail;
/* check type==0 and gain==0 */
if (ch0_header.format || ch0_header.gain)
goto fail;
if (ch1_header.format || ch1_header.gain)
goto fail;
/* check for agreement */
if (
ch0_header.sample_count != ch1_header.sample_count ||
ch0_header.nibble_count != ch1_header.nibble_count ||
ch0_header.sample_rate != ch1_header.sample_rate ||
ch0_header.loop_flag != ch1_header.loop_flag ||
ch0_header.loop_start_offset != ch1_header.loop_start_offset ||
ch0_header.loop_end_offset != ch1_header.loop_end_offset
) goto fail;
if (ch0_header.loop_flag)
{
off_t loop_off;
/* check loop predictor/scale */
loop_off = ch0_header.loop_start_offset/16*8;
if (ch0_header.loop_ps != (uint8_t)read_8bit(ch1_start+loop_off,streamFile))
goto fail;
if (ch1_header.loop_ps != (uint8_t)read_8bit(ch2_start+loop_off,streamFile))
goto fail;
}
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(2,ch0_header.loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
vgmstream->num_samples = ch0_header.sample_count;
vgmstream->sample_rate = ch0_header.sample_rate;
vgmstream->loop_start_sample = dsp_nibbles_to_samples(
ch0_header.loop_start_offset);
vgmstream->loop_end_sample = dsp_nibbles_to_samples(
ch0_header.loop_end_offset)+1;
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = read_32bitBE(0x10,streamFile);
vgmstream->meta_type = meta_WII_WAS;
/* coeffs */
for (i=0;i<16;i++) {
vgmstream->ch[0].adpcm_coef[i] = ch0_header.coef[i];
vgmstream->ch[1].adpcm_coef[i] = ch1_header.coef[i];
}
/* initial history */
/* always 0 that I've ever seen, but for completeness... */
vgmstream->ch[0].adpcm_history1_16 = ch0_header.initial_hist1;
vgmstream->ch[0].adpcm_history2_16 = ch0_header.initial_hist2;
vgmstream->ch[1].adpcm_history1_16 = ch1_header.initial_hist1;
vgmstream->ch[1].adpcm_history2_16 = ch1_header.initial_hist2;
/* open the file for reading */
vgmstream->ch[0].streamfile = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!vgmstream->ch[0].streamfile)
goto fail;
vgmstream->ch[0].channel_start_offset = vgmstream->ch[0].offset=ch1_start;
vgmstream->ch[1].streamfile = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!vgmstream->ch[1].streamfile)
goto fail;
vgmstream->ch[1].channel_start_offset = vgmstream->ch[1].offset=ch2_start;
}
else
{
goto fail;
}
return vgmstream;
fail:
/* clean up anything we may have opened */
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}
/* .str found in Micro Machines, Superman: Shadow of Apokolips */
VGMSTREAM * init_vgmstream_dsp_str_ig(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
struct dsp_header ch0_header,ch1_header;
off_t ch1_header_start, ch2_header_start, ch1_start, ch2_start;
int channel_count;
int i;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("str",filename_extension(filename)))
goto fail;
channel_count = 2;
ch1_header_start = 0x00;
ch2_header_start = 0x80;
ch1_start = 0x800;
ch2_start = 0x4800;
/* get DSP headers */
if (read_dsp_header(&ch0_header, ch1_header_start, streamFile)) goto fail;
if (read_dsp_header(&ch1_header, ch2_header_start, streamFile)) goto fail;
/* check initial predictor/scale */
if (ch0_header.initial_ps != (uint8_t)read_8bit(ch1_start, streamFile))
goto fail;
if (ch1_header.initial_ps != (uint8_t)read_8bit(ch2_start, streamFile))
goto fail;
/* check type==0 and gain==0 */
if (ch0_header.format || ch0_header.gain)
goto fail;
if (ch1_header.format || ch1_header.gain)
goto fail;
/* check for agreement */
if (
ch0_header.sample_count != ch1_header.sample_count ||
ch0_header.nibble_count != ch1_header.nibble_count ||
ch0_header.sample_rate != ch1_header.sample_rate ||
ch0_header.loop_flag != ch1_header.loop_flag ||
ch0_header.loop_start_offset != ch1_header.loop_start_offset ||
ch0_header.loop_end_offset != ch1_header.loop_end_offset
) goto fail;
if (ch0_header.loop_flag)
{
off_t loop_off;
/* check loop predictor/scale */
loop_off = ch0_header.loop_start_offset/16*8;
if (ch0_header.loop_ps != (uint8_t)read_8bit(ch1_start+loop_off,streamFile))
goto fail;
if (ch1_header.loop_ps != (uint8_t)read_8bit(ch2_start+loop_off,streamFile))
goto fail;
}
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(2,ch0_header.loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
vgmstream->num_samples = ch0_header.sample_count;
vgmstream->sample_rate = ch0_header.sample_rate;
vgmstream->loop_start_sample = dsp_nibbles_to_samples(
ch0_header.loop_start_offset);
vgmstream->loop_end_sample = dsp_nibbles_to_samples(
ch0_header.loop_end_offset)+1;
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = 0x4000;
vgmstream->meta_type = meta_DSP_STR_IG;
/* coeffs */
for (i=0;i<16;i++) {
vgmstream->ch[0].adpcm_coef[i] = ch0_header.coef[i];
vgmstream->ch[1].adpcm_coef[i] = ch1_header.coef[i];
}
/* initial history */
/* always 0 that I've ever seen, but for completeness... */
vgmstream->ch[0].adpcm_history1_16 = ch0_header.initial_hist1;
vgmstream->ch[0].adpcm_history2_16 = ch0_header.initial_hist2;
vgmstream->ch[1].adpcm_history1_16 = ch1_header.initial_hist1;
vgmstream->ch[1].adpcm_history2_16 = ch1_header.initial_hist2;
/* open the file for reading */
vgmstream->ch[0].streamfile = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!vgmstream->ch[0].streamfile)
goto fail;
vgmstream->ch[0].channel_start_offset = vgmstream->ch[0].offset=ch1_start;
vgmstream->ch[1].streamfile = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!vgmstream->ch[1].streamfile)
goto fail;
vgmstream->ch[1].channel_start_offset = vgmstream->ch[1].offset=ch2_start;
return vgmstream;
fail:
/* clean up anything we may have opened */
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}

View File

@ -1,79 +1,101 @@
#include "meta.h"
#include "../util.h"
/* PDT - Custom Generated File (Mario Party) */
VGMSTREAM * init_vgmstream_ngc_pdt(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
off_t start_offset;
int loop_flag;
int channel_count;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("pdt",filename_extension(filename))) goto fail;
#if 0
/* check header */
if (read_32bitBE(0x00,streamFile) != 0x00000000) /* 0x0 */
goto fail;
#endif
loop_flag = (read_32bitBE(0x0C,streamFile)!=2); /* not sure, but it seems unlooped = 2 */
channel_count = 2;
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
start_offset = 0x60;
vgmstream->channels = channel_count;
vgmstream->sample_rate = read_32bitBE(0x04,streamFile);
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->num_samples = read_32bitBE(0x08,streamFile)*14/8/channel_count;
if (loop_flag) {
vgmstream->loop_start_sample = read_32bitBE(0x0C,streamFile)*14/8/channel_count;
vgmstream->loop_end_sample = read_32bitBE(0x08,streamFile)*14/8/channel_count;
}
/* dealing with no interleave, 'cause the interleave
for 2 channels is larger than the sample count/2 */
vgmstream->layout_type = layout_none;
vgmstream->meta_type = meta_NGC_PDT;
if (vgmstream->coding_type == coding_NGC_DSP) {
int i;
for (i=0;i<16;i++) {
vgmstream->ch[0].adpcm_coef[i] = read_16bitBE(0x20+i*2,streamFile);
}
if (vgmstream->channels == 2) {
for (i=0;i<16;i++) {
vgmstream->ch[1].adpcm_coef[i] = read_16bitBE(0x40+i*2,streamFile);
}
}
}
/* open the file for reading */
{
int i;
STREAMFILE * file;
file = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!file) goto fail;
for (i=0;i<channel_count;i++) {
vgmstream->ch[i].streamfile = file;
vgmstream->ch[i].channel_start_offset=
vgmstream->ch[i].offset=(get_streamfile_size(streamFile)+start_offset)/2*i;
}
}
return vgmstream;
/* clean up anything we may have opened */
fail:
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}
#include "meta.h"
#include "../util.h"
/* PDT - Custom Generated File (Mario Party) */
VGMSTREAM * init_vgmstream_ngc_pdt(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
int loop_flag;
int channel_count;
off_t start_offset;
int second_channel_start;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("pdt",filename_extension(filename))) goto fail;
/* check header */
if (read_32bitBE(0x00,streamFile) != 0x50445420) /* "PDT " */
goto fail;
if (read_32bitBE(0x04,streamFile) != 0x44535020) /* "DSP " */
goto fail;
if (read_32bitBE(0x08,streamFile) != 0x48454144) /* "HEAD " */
goto fail;
if (read_16bitBE(0x0C,streamFile) != 0x4552) /* "ER " */
goto fail;
loop_flag = (read_32bitBE(0x1C,streamFile)!=2);
channel_count = (uint16_t)(read_16bitLE(0x0E,streamFile));
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
start_offset = 0x800;
vgmstream->channels = channel_count;
vgmstream->sample_rate = read_32bitBE(0x14,streamFile);
vgmstream->coding_type = coding_NGC_DSP;
if (channel_count == 1)
{
vgmstream->num_samples = read_32bitBE(0x18,streamFile)*14/8/channel_count/2;
if (loop_flag) {
vgmstream->loop_start_sample = read_32bitBE(0x1C,streamFile)*14/8/channel_count/2;
vgmstream->loop_end_sample = read_32bitBE(0x18,streamFile)*14/8/channel_count/2;
}
}
else if (channel_count == 2)
{
vgmstream->num_samples = read_32bitBE(0x18,streamFile)*14/8/channel_count;
if (loop_flag) {
vgmstream->loop_start_sample = read_32bitBE(0x1C,streamFile)*14/8/channel_count;
vgmstream->loop_end_sample = read_32bitBE(0x18,streamFile)*14/8/channel_count;
}
second_channel_start = (get_streamfile_size(streamFile)+start_offset)/2;
}
else
{
goto fail;
}
vgmstream->layout_type = layout_none;
vgmstream->meta_type = meta_NGC_PDT;
if (vgmstream->coding_type == coding_NGC_DSP) {
int i;
for (i=0;i<16;i++) {
vgmstream->ch[0].adpcm_coef[i] = read_16bitBE(0x50+i*2,streamFile);
}
if (vgmstream->channels == 2) {
for (i=0;i<16;i++) {
vgmstream->ch[1].adpcm_coef[i] = read_16bitBE(0x70+i*2,streamFile);
}
}
}
/* open the file for reading */
{
int i;
STREAMFILE * file;
file = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!file) goto fail;
for (i=0;i<channel_count;i++) {
vgmstream->ch[i].streamfile = file;
vgmstream->ch[0].channel_start_offset=start_offset;
if (channel_count == 2) {
if (second_channel_start == -1) goto fail;
vgmstream->ch[1].channel_start_offset=second_channel_start;
}
vgmstream->ch[i].offset = vgmstream->ch[i].channel_start_offset;
}
}
return vgmstream;
/* clean up anything we may have opened */
fail:
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}

View File

@ -82,7 +82,7 @@ VGMSTREAM * init_vgmstream_ngc_ssm(STREAMFILE *streamFile) {
}
}
}
}
return vgmstream;

65
src/meta/ps2_khv.c Normal file
View File

@ -0,0 +1,65 @@
#include "meta.h"
#include "../util.h"
/* KHV (from Kingdom Hearts 2) */
/* VAG files with custom headers */
VGMSTREAM * init_vgmstream_ps2_khv(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
int loop_flag = 0;
int channel_count;
off_t start_offset;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("khv",filename_extension(filename))) goto fail;
/* check header */
if (read_32bitBE(0x00,streamFile) != 0x56414770) /* "VAGp" */
goto fail;
loop_flag = (read_32bitBE(0x14,streamFile)!=0);
channel_count = 2;
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
start_offset = 0x60;
vgmstream->channels = channel_count;
vgmstream->sample_rate = read_32bitBE(0x10,streamFile);
vgmstream->coding_type = coding_PSX;
vgmstream->num_samples = read_32bitBE(0x0C,streamFile);
if (loop_flag) {
vgmstream->loop_start_sample = read_32bitBE(0x14,streamFile);
vgmstream->loop_end_sample = read_32bitBE(0x18,streamFile);
}
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = 0x10;
vgmstream->meta_type = meta_PS2_KHV;
/* open the file for reading */
{
int i;
STREAMFILE * file;
file = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!file) goto fail;
for (i=0;i<channel_count;i++) {
vgmstream->ch[i].streamfile = file;
vgmstream->ch[i].channel_start_offset=
vgmstream->ch[i].offset=start_offset+
vgmstream->interleave_block_size*i;
}
}
return vgmstream;
/* clean up anything we may have opened */
fail:
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}

81
src/meta/ps2_voi.c Normal file
View File

@ -0,0 +1,81 @@
#include "meta.h"
#include "../util.h"
/* VOI - found in "RAW Danger" (PS2) */
VGMSTREAM * init_vgmstream_ps2_voi(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
int loop_flag = 0;
int channel_count;
off_t start_offset;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("voi",filename_extension(filename))) goto fail;
/* check header */
if (((read_32bitLE(0x04,streamFile)*2)+0x800) != (get_streamfile_size(streamFile)))
{
goto fail;
}
loop_flag = 0;
channel_count = read_32bitLE(0x00,streamFile);
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
start_offset = 0x800;
vgmstream->channels = channel_count;
vgmstream->coding_type = coding_PCM16LE;
vgmstream->num_samples = (get_streamfile_size(streamFile)-start_offset)/channel_count/2;
if (loop_flag)
{
vgmstream->loop_start_sample = 0;
vgmstream->loop_end_sample = (read_32bitLE(0x04,streamFile)/2);
}
if (read_32bitLE(0x08,streamFile) == 0)
{
vgmstream->sample_rate = 48000;
vgmstream->interleave_block_size = 0x200;
}
else if (read_32bitLE(0x08,streamFile) == 1)
{
vgmstream->sample_rate = 24000;
vgmstream->interleave_block_size = 0x100;
}
else
{
goto fail;
}
vgmstream->layout_type = layout_interleave;
vgmstream->meta_type = meta_PS2_VOI;
/* open the file for reading */
{
int i;
STREAMFILE * file;
file = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!file) goto fail;
for (i=0;i<channel_count;i++) {
vgmstream->ch[i].streamfile = file;
vgmstream->ch[i].channel_start_offset=
vgmstream->ch[i].offset=start_offset+
vgmstream->interleave_block_size*i;
}
}
return vgmstream;
/* clean up anything we may have opened */
fail:
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}

77
src/meta/psx_str_mgav.c Normal file
View File

@ -0,0 +1,77 @@
#include "meta.h"
#include "../layout/layout.h"
#include "../util.h"
/* STR (Future Cop L.A.P.D.) */
VGMSTREAM * init_vgmstream_psx_mgav(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
off_t start_offset;
off_t current_chunk;
char filename[260];
int loop_flag = 0;
int channel_count;
int dataBuffer = 0;
int i;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("str",filename_extension(filename))) goto fail;
/* check header */
if (read_32bitBE(0x00,streamFile) != 0x52565753) /* "RVWS" */
goto fail;
loop_flag = 1;
channel_count = 2;
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
start_offset = read_32bitLE(0x4,streamFile);
vgmstream->channels = channel_count;
vgmstream->sample_rate = 16000;
vgmstream->coding_type = coding_PSX;
vgmstream->layout_type = layout_psx_mgav_blocked;
vgmstream->meta_type = meta_PSX_MGAV;
/* open the file for reading */
{
STREAMFILE * file;
file = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!file) goto fail;
for (i=0;i<channel_count;i++) {
vgmstream->ch[i].streamfile = file;
}
}
// calculate samples
current_chunk = start_offset;
vgmstream->num_samples = 0;
while ((current_chunk + start_offset) < (get_streamfile_size(streamFile)))
{
dataBuffer = (read_32bitBE(current_chunk,streamFile));
if (dataBuffer == 0x4D474156) /* "MGAV" */
{
psx_mgav_block_update(start_offset,vgmstream);
vgmstream->num_samples += vgmstream->current_block_size/16*28;
current_chunk += vgmstream->current_block_size + 0x1C;
}
current_chunk += 0x10;
}
if (loop_flag) {
vgmstream->loop_start_sample = 0;
vgmstream->loop_end_sample = vgmstream->num_samples;
}
return vgmstream;
/* clean up anything we may have opened */
fail:
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}

View File

@ -7,64 +7,68 @@
*/
VGMSTREAM * init_vgmstream_spt_spd(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
STREAMFILE * streamFileSPT = NULL;
char filename[260];
VGMSTREAM * vgmstream = NULL;
STREAMFILE * streamFileSPT = NULL;
char filename[260];
char filenameSPT[260];
int i;
int channel_count;
int loop_flag;
int i;
/* check extension, case insensitive */
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("spd",filename_extension(filename))) goto fail;
strcpy(filenameSPT,filename);
strcpy(filenameSPT+strlen(filenameSPT)-3,"spt");
strcpy(filenameSPT,filename);
strcpy(filenameSPT+strlen(filenameSPT)-3,"spt");
streamFileSPT = streamFile->open(streamFile,filenameSPT,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!streamFileSPT)
goto fail;
if (read_32bitBE(0x0,streamFileSPT) != 0x1) // make sure that it's not a container
goto fail;
streamFileSPT = streamFile->open(streamFile,filenameSPT,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!streamFileSPT) goto fail;
channel_count = read_32bitBE(0x00,streamFileSPT);
loop_flag = read_32bitBE(0x04,streamFileSPT);
channel_count = 1;
loop_flag = (read_32bitBE(0x0C,streamFileSPT) == 0x2);
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
vgmstream->channels = channel_count;
vgmstream->sample_rate = read_32bitBE(0x08,streamFileSPT);
vgmstream->num_samples=read_32bitBE(0x14,streamFileSPT)*14/16/channel_count;
switch ((read_32bitBE(0x0,streamFileSPT))) {
case 1:
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->channels = channel_count;
vgmstream->sample_rate = read_32bitBE(0x08,streamFileSPT);
switch ((read_32bitBE(0x4,streamFileSPT))) {
case 0:
case 1:
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->num_samples=read_32bitBE(0x14,streamFileSPT)*14/16/channel_count;
if(loop_flag) {
vgmstream->loop_start_sample = 0;
vgmstream->loop_end_sample = read_32bitBE(0x14,streamFileSPT)*14/16/channel_count;
}
break;
case 2:
vgmstream->coding_type = coding_PCM16BE;
vgmstream->num_samples=read_32bitBE(0x14,streamFileSPT)/channel_count;
if(loop_flag) {
vgmstream->loop_start_sample = 0;
vgmstream->loop_end_sample = read_32bitBE(0x14,streamFileSPT)/channel_count;
}
break;
case 2:
vgmstream->coding_type = coding_PCM16BE;
break;
default:
goto fail;
}
if(loop_flag) {
vgmstream->loop_start_sample = 0;
vgmstream->loop_end_sample = read_32bitBE(0x14,streamFileSPT)*14/16/channel_count;
}
if (channel_count == 1) {
vgmstream->layout_type = layout_none;
} else if (channel_count == 2) {
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size=(read_32bitBE(0x34,streamFileSPT)*channel_count)/2;
}
default:
goto fail;
}
if (channel_count == 1) {
vgmstream->layout_type = layout_none;
} else if (channel_count == 2) {
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size=(read_32bitBE(0x34,streamFileSPT)*channel_count)/2;
}
vgmstream->meta_type = meta_SPT_SPD;
@ -74,7 +78,6 @@ VGMSTREAM * init_vgmstream_spt_spd(STREAMFILE *streamFile) {
/* Not sure, i'll put a fake value here for now */
vgmstream->ch[i].streamfile = streamFile->open(streamFile,filename,0x8000);
vgmstream->ch[i].offset = 0;
if (!vgmstream->ch[i].streamfile) goto fail;
}
}

View File

@ -117,8 +117,9 @@ VGMSTREAM * init_vgmstream_ss_stream(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
int loop_flag=0;
int channels;
int channels;
int channel_count;
int freq_flag;
off_t start_offset;
int i;
@ -128,6 +129,7 @@ VGMSTREAM * init_vgmstream_ss_stream(STREAMFILE *streamFile) {
strcasecmp("ss7",filename_extension(filename))) goto fail;
loop_flag = 0;
freq_flag = read_8bit(0x08,streamFile);
if (read_8bit(0x0C,streamFile) == 0) {
channels = 1;
@ -143,17 +145,19 @@ VGMSTREAM * init_vgmstream_ss_stream(STREAMFILE *streamFile) {
if (!vgmstream) goto fail;
/* fill in the vital statistics */
vgmstream->channels = channel_count;
vgmstream->channels = channel_count;
vgmstream->sample_rate = 48000;
#if 0
if (!strcasecmp("ss3",filename_extension(filename))) {
vgmstream->sample_rate = 32000;
} else if (!strcasecmp("ss7",filename_extension(filename))) {
vgmstream->sample_rate = 48000;
}
#endif
start_offset = (read_8bit(0x07,streamFile)+5);
if (channel_count == 1){
start_offset = 0x3C;

View File

@ -1,85 +0,0 @@
#include "meta.h"
#include "../util.h"
/* WAS / ISWS
found in: DiRT 2 (Wii)
Formula 1 2009 (Wii)
Sega Superstars Tennis (Wii)
*/
VGMSTREAM * init_vgmstream_wii_was(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
off_t start_offset;
int loop_flag;
int channel_count;
int i, j;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("was",filename_extension(filename)) &&
(strcasecmp("isws",filename_extension(filename)))) goto fail;
/* check header */
if (read_32bitBE(0x0,streamFile) != 0x69535753) /* iSWS */
goto fail;
loop_flag = 0;
channel_count = read_32bitBE(0x8,streamFile);
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
start_offset = (channel_count * 0x60) + 0x20;
vgmstream->channels = channel_count;
vgmstream->sample_rate = read_32bitBE(0x28,streamFile);
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->num_samples = read_32bitBE(0x20,streamFile);
vgmstream->layout_type = layout_interleave;
if (channel_count == 1) {
vgmstream->layout_type = layout_none;
} else if (channel_count > 1) {
vgmstream->layout_type = layout_interleave;
vgmstream->interleave_block_size = read_32bitBE(0x10,streamFile);
}
vgmstream->meta_type = meta_WII_WAS;
{
off_t coef_table[8] = {0x3C,0x9C,0xFC,0x15C,0x1BC,0x21C,0x27C,0x2DC};
for (j=0;j<vgmstream->channels;j++) {
for (i=0;i<16;i++) {
vgmstream->ch[j].adpcm_coef[i] = read_16bitBE(coef_table[j]+i*2,streamFile);
}
}
}
/* open the file for reading */
{
int i;
STREAMFILE * file;
file = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!file) goto fail;
for (i=0;i<channel_count;i++) {
vgmstream->ch[i].streamfile = file;
vgmstream->ch[i].channel_start_offset=
vgmstream->ch[i].offset=start_offset+
vgmstream->interleave_block_size*i;
}
}
return vgmstream;
fail:
/* clean up anything we may have opened */
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}

View File

@ -1,86 +1,88 @@
#include "meta.h"
#include "../util.h"
/* ZWDSP (hcs' custom DSP files from Zack & Wiki) */
VGMSTREAM * init_vgmstream_zwdsp(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
off_t start_offset;
int loop_flag;
int channel_count = 2;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("zwdsp",filename_extension(filename))) goto fail;
/* check header */
if (read_32bitBE(0x00,streamFile) != 0x00000000) /* 0x0 */
goto fail;
/* Retrieve the loop flag, some files have 0x0 and some 0x02 as "no loop" */
switch (read_32bitBE(0x10, streamFile)) {
case 0:
case 2:
loop_flag = 0;
break;
default:
loop_flag = 1;
}
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
start_offset = 0x90;
vgmstream->channels = channel_count;
vgmstream->sample_rate = read_32bitBE(0x08,streamFile);
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->num_samples = read_32bitBE(0x18,streamFile)*14/8/channel_count;
if (loop_flag) {
vgmstream->loop_start_sample = read_32bitBE(0x10,streamFile)*14/8/channel_count;
vgmstream->loop_end_sample = read_32bitBE(0x14,streamFile)*14/8/channel_count;
}
vgmstream->layout_type = layout_none;
vgmstream->meta_type = meta_ZWDSP;
if (vgmstream->coding_type == coding_NGC_DSP) {
int i;
for (i=0;i<16;i++) {
vgmstream->ch[0].adpcm_coef[i] = read_16bitBE(0x20+i*2,streamFile);
}
if (vgmstream->channels == 2) {
for (i=0;i<16;i++) {
vgmstream->ch[1].adpcm_coef[i] = read_16bitBE(0x60+i*2,streamFile);
}
}
}
/* open the file for reading */
{
int i;
STREAMFILE * file;
file = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!file) goto fail;
for (i=0;i<channel_count;i++) {
vgmstream->ch[i].streamfile = file;
vgmstream->ch[i].channel_start_offset=
vgmstream->ch[i].offset=start_offset+
((get_streamfile_size(streamFile)-start_offset)/2)*i;
}
}
return vgmstream;
/* clean up anything we may have opened */
fail:
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}
#include "meta.h"
#include "../util.h"
/* ZWDSP (hcs' custom DSP files from Zack & Wiki) */
VGMSTREAM * init_vgmstream_zwdsp(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[260];
int second_channel_start;
int loop_flag;
int channel_count = 2;
off_t start_offset;
/* check extension, case insensitive */
streamFile->get_name(streamFile,filename,sizeof(filename));
if (strcasecmp("zwdsp",filename_extension(filename))) goto fail;
/* check header */
if (read_32bitBE(0x00,streamFile) != 0x00000000) /* 0x0 */
goto fail;
/* Retrieve the loop flag, some files have 0x0 and some 0x02 as "no loop" */
switch (read_32bitBE(0x10, streamFile)) {
case 0:
case 2:
loop_flag = 0;
break;
default:
loop_flag = 1;
}
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count,loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
start_offset = 0x90;
vgmstream->channels = channel_count;
vgmstream->sample_rate = read_32bitBE(0x08,streamFile);
vgmstream->coding_type = coding_NGC_DSP;
vgmstream->num_samples = read_32bitBE(0x18,streamFile)*14/8/channel_count;
if (loop_flag) {
vgmstream->loop_start_sample = read_32bitBE(0x10,streamFile)*14/8/channel_count;
vgmstream->loop_end_sample = read_32bitBE(0x14,streamFile)*14/8/channel_count;
}
vgmstream->layout_type = layout_none;
vgmstream->meta_type = meta_ZWDSP;
if (vgmstream->coding_type == coding_NGC_DSP) {
int i;
for (i=0;i<16;i++) {
vgmstream->ch[0].adpcm_coef[i] = read_16bitBE(0x20+i*2,streamFile);
}
if (vgmstream->channels == 2) {
for (i=0;i<16;i++) {
vgmstream->ch[1].adpcm_coef[i] = read_16bitBE(0x60+i*2,streamFile);
}
}
}
second_channel_start = (get_streamfile_size(streamFile)+start_offset)/2;
{
int i;
STREAMFILE * file;
file = streamFile->open(streamFile,filename,STREAMFILE_DEFAULT_BUFFER_SIZE);
if (!file) goto fail;
for (i=0;i<channel_count;i++) {
vgmstream->ch[i].streamfile = file;
vgmstream->ch[0].channel_start_offset=start_offset;
if (channel_count == 2) {
if (second_channel_start == -1) goto fail;
vgmstream->ch[1].channel_start_offset=second_channel_start;
}
vgmstream->ch[i].offset = vgmstream->ch[i].channel_start_offset;
}
}
return vgmstream;
/* clean up anything we may have opened */
fail:
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}

View File

@ -143,6 +143,7 @@ VGMSTREAM * (*init_vgmstream_fcns[])(STREAMFILE *streamFile) = {
init_vgmstream_idsp,
init_vgmstream_idsp2,
init_vgmstream_idsp3,
init_vgmstream_idsp4,
init_vgmstream_ngc_ymf,
init_vgmstream_sadl,
init_vgmstream_ps2_ccc,
@ -243,19 +244,26 @@ VGMSTREAM * (*init_vgmstream_fcns[])(STREAMFILE *streamFile) = {
init_vgmstream_dmsg,
init_vgmstream_ngc_aaap,
init_vgmstream_ngc_dsp_tmnt2,
init_vgmstream_ps2_ster,
init_vgmstream_ps2_wb,
init_vgmstream_ps2_ster,
init_vgmstream_ps2_wb,
init_vgmstream_bnsf,
#ifdef VGM_USE_G7221
init_vgmstream_s14_sss,
#endif
init_vgmstream_ps2_gcm,
init_vgmstream_ps2_smpl,
init_vgmstream_ps2_msa,
init_vgmstream_ps2_smpl,
init_vgmstream_ps2_msa,
init_vgmstream_ps2_voi,
init_vgmstream_ps2_khv,
init_vgmstream_pc_smp,
init_vgmstream_ngc_bo2,
init_vgmstream_dsp_ddsp,
init_vgmstream_p3d,
init_vgmstream_ps2_tk1,
init_vgmstream_ps2_adsc,
init_vgmstream_ps2_tk1,
init_vgmstream_ps2_adsc,
init_vgmstream_ngc_dsp_mpds,
init_vgmstream_dsp_str_ig,
init_vgmstream_psx_mgav,
};
#define INIT_VGMSTREAM_FCNS (sizeof(init_vgmstream_fcns)/sizeof(init_vgmstream_fcns[0]))
@ -288,9 +296,10 @@ VGMSTREAM * init_vgmstream_internal(STREAMFILE *streamFile, int do_dfs) {
(vgmstream->meta_type == meta_KRAW) ||
(vgmstream->meta_type == meta_PS2_MIB) ||
(vgmstream->meta_type == meta_NGC_LPS) ||
(vgmstream->meta_type == meta_DSP_YGO) ||
(vgmstream->meta_type == meta_DSP_YGO) ||
(vgmstream->meta_type == meta_DSP_AGSC) ||
(vgmstream->meta_type == meta_PS2_SMPL)
(vgmstream->meta_type == meta_PS2_SMPL) ||
(vgmstream->meta_type == meta_SPT_SPD)
) && vgmstream->channels == 1) {
try_dual_file_stereo(vgmstream, streamFile);
}
@ -691,6 +700,7 @@ void render_vgmstream(sample * buffer, int32_t sample_count, VGMSTREAM * vgmstre
case layout_thp_blocked:
case layout_filp_blocked:
case layout_ivaud_blocked:
case layout_psx_mgav_blocked:
render_vgmstream_blocked(buffer,sample_count,vgmstream);
break;
case layout_interleave_byte:
@ -1737,6 +1747,9 @@ void describe_vgmstream(VGMSTREAM * vgmstream, char * desc, int length) {
case layout_filp_blocked:
snprintf(temp,TEMPSIZE,"FILp blocked");
break;
case layout_psx_mgav_blocked:
snprintf(temp,TEMPSIZE,"MGAV blocked");
break;
#ifdef VGM_USE_MPEG
case layout_fake_mpeg:
snprintf(temp,TEMPSIZE,"MPEG Audio stream with incorrect frame headers");
@ -2283,12 +2296,6 @@ void describe_vgmstream(VGMSTREAM * vgmstream, char * desc, int length) {
case meta_IDSP:
snprintf(temp,TEMPSIZE,"IDSP Header");
break;
case meta_IDSP2:
snprintf(temp,TEMPSIZE,"IDSP Header");
break;
case meta_IDSP3:
snprintf(temp,TEMPSIZE,"IDSP Header");
break;
case meta_WAA_WAC_WAD_WAM:
snprintf(temp,TEMPSIZE,"WAA/WAC/WAD/WAM RIFF Header");
break;
@ -2528,14 +2535,29 @@ void describe_vgmstream(VGMSTREAM * vgmstream, char * desc, int length) {
case meta_PC_SMP:
snprintf(temp,TEMPSIZE,"Ghostbusters .smp Header");
break;
case meta_NGC_PDT:
snprintf(temp,TEMPSIZE,"PDT DSP header");
break;
case meta_NGC_BO2:
snprintf(temp,TEMPSIZE,"Blood Omen 2 DSP header");
break;
case meta_P3D:
snprintf(temp,TEMPSIZE,"Prototype P3D Header");
break;
case meta_PS2_TK1:
case meta_PS2_TK1:
snprintf(temp,TEMPSIZE,"Tekken TK5STRM1 Header");
break;
case meta_PS2_ADSC:
case meta_PS2_ADSC:
snprintf(temp,TEMPSIZE,"ADSC Header");
break;
case meta_NGC_DSP_MPDS:
snprintf(temp,TEMPSIZE,"MPDS DSP header");
break;
case meta_DSP_STR_IG:
snprintf(temp,TEMPSIZE,"Infogrames dual dsp header");
break;
case meta_PSX_MGAV:
snprintf(temp,TEMPSIZE,"Electronic Arts RVWS header");
break;
default:
snprintf(temp,TEMPSIZE,"THEY SHOULD HAVE SENT A POET");

View File

@ -147,8 +147,8 @@ typedef enum {
layout_gsb_blocked,
layout_thp_blocked,
layout_filp_blocked,
layout_mxch_blocked,
layout_mxch_blocked,
layout_psx_mgav_blocked,
#if 0
layout_strm_blocked, /* */
#endif
@ -295,9 +295,7 @@ typedef enum {
meta_KRAW, /* Geometry Wars - Galaxies */
meta_PS2_OMU, /* PS2 Int file with Header */
meta_PS2_XA2, /* XG3 Extreme-G Racing */
meta_IDSP, /* Chronicles of Narnia */
meta_IDSP2, /* Soul Calibur */
meta_IDSP3, /* Mario Strikers Charged */
meta_IDSP, /* Chronicles of Narnia, Soul Calibur Legends, Mario Strikers Charged */
meta_SPT_SPD, /* Variouis */
meta_ISH_ISD, /* Various */
meta_GSP_GSB, /* Various */
@ -444,17 +442,24 @@ typedef enum {
meta_PS2_AST, /* Some KOEI game (PS2) */
meta_DMSG, /* Nightcaster II - Equinox (XBOX) */
meta_NGC_AAAP, /* Turok: Evolution (NGC) */
meta_PS2_STER, /* Juuni Kokuki: Kakukaku Taru Ou Michi Beni Midori no Uka */
meta_PS2_WB, /* Shooting Love. ~TRIZEAL~ */
meta_PS2_STER, /* Juuni Kokuki: Kakukaku Taru Ou Michi Beni Midori no Uka */
meta_PS2_WB, /* Shooting Love. ~TRIZEAL~ */
meta_S14, /* raw Siren 14, 24kbit mono */
meta_SSS, /* raw Siren 14, 48kbit stereo */
meta_PS2_GCM, /* NamCollection */
meta_PS2_SMPL, /* Homura */
meta_PS2_MSA, /* Psyvariar -Complete Edition- */
meta_PS2_GCM, /* NamCollection */
meta_PS2_SMPL, /* Homura */
meta_PS2_MSA, /* Psyvariar -Complete Edition- */
meta_PS2_VOI, /* RAW Danger (Zettaizetsumei Toshi 2 - Itetsuita Kiokutachi) [PS2] */
meta_PS2_KHV, /* Kingdom Hearts 2 VAG streams */
meta_PC_SMP, /* Ghostbusters PC .smp */
meta_P3D, /* Prototype P3D */
meta_PS2_TK1, /* Tekken (NamCollection) */
meta_PS2_TK1, /* Tekken (NamCollection) */
meta_PS2_ADSC, /* Kenka Bancho 2: Full Throttle */
meta_NGC_BO2, /* Blood Omen 2 (NGC) */
meta_DSP_DDSP, /* Various (2 dsp files stuck together */
meta_NGC_DSP_MPDS, /* Big Air Freestyle, Terminator 3 */
meta_DSP_STR_IG, /* Micro Machines, Superman Superman: Shadow of Apokolis */
meta_PSX_MGAV, /* Future Cop L.A.P.D. */
} meta_t;
typedef struct {

View File

@ -111,6 +111,7 @@ char * extension_list[] = {
"bmdx\0BMDX Audio File (*.BMDX)\0",
"bns\0BNS Audio File (*.BNS)\0",
"bnsf\0BNSF Audio File (*.BNSF)\0",
"bo2\0BO2 Audio File (*.BO2)\0",
"brstm;brstmspm\0BRSTM Audio File (*.BRSTM)\0",
"caf\0CAF Audio File (*.CAF)\0",
@ -121,6 +122,7 @@ char * extension_list[] = {
"dcs\0DCS Audio File (*.DCS)\0",
"de2\0DE2 Audio File (*.DE2)\0",
"ddsp\0DDSP Audio File (*.DDSP)\0",
"dmsg\0DMSG Audio File (*.DMSG)\0",
"dsp\0DSP Audio File (*.DSP)\0",
"dtk\0DTK Audio File (*.DTK)\0",
@ -164,6 +166,7 @@ char * extension_list[] = {
"kces\0KCES Audio File (*.KCES)\0",
"kcey\0KCEY Audio File (*.KCEY)\0",
"khv\0KHV Audio File (*.KHV)\0",
"kraw\0KRAW Audio File (*.KRAW)\0",
"leg\0LEG Audio File (*.LEG)\0",
@ -178,6 +181,7 @@ char * extension_list[] = {
"mic\0PS2 MIC Audio File (*.MIC)\0",
"mihb\0MIHB Audio File (*.MIHB)\0",
"mpdsp\0MPDSP Audio File (*.MPDSP)\0",
"mpds\0MPDS Audio File (*.MPDS)\0",
"msa\0MSA Audio File (*.MSA)\0",
"mss\0MSS Audio File (*.MSS)\0",
"msvp\0MSVP Audio File (*.MSVP)\0",
@ -212,6 +216,7 @@ char * extension_list[] = {
"rsd\0RSD Audio File (*.RSD)\0",
"rsf\0RSF Audio File (*.RSF)\0",
"rstm\0RSTM Audio File (*.RSTM)\0",
"rvws\0RVWS Audio File (*.RVWS)\0",
"rwar\0RWAR Audio File (*.RWSD)\0",
"rwav\0RWAV Audio File (*.RWAV)\0",
"rws\0RWS Audio File (*.RWS)\0",
@ -233,7 +238,7 @@ char * extension_list[] = {
"sl3\0SL3 Audio File (*.SL3)\0",
"sli\0SLI Audio File (*.SLI)\0",
"smp\0SMP Audio File (*.SMP)\0",
"smpl\0SMPL Audio File (*.SMPL)\0",
"smpl\0SMPL Audio File (*.SMPL)\0",
"snd\0SND Audio File (*.SND)\0",
"sng\0SNG Audio File (*.SNG)\0",
"sns\0SNS Audio File (*.SNS)\0",
@ -274,6 +279,7 @@ char * extension_list[] = {
"vs\0VS Audio File (*.VS)\0",
"vsf\0VSF Audio File (*.VSF)\0",
"vgv\0VGV Audio File (*.VGV)\0",
"voi\0VOI Audio File (*.VOI)\0",
"waa\0WAA Audio File (*.WAA)\0",
"wac\0WAC Audio File (*.WAC)\0",
@ -281,7 +287,7 @@ char * extension_list[] = {
"wam\0WAM Audio File (*.WAM)\0",
"wavm\0WAVM Audio File (*.WAVM)\0",
"was\0WAS Audio File (*.WAS)\0",
"wb\0WB Audio File (*.WB)\0",
"wb\0WB Audio File (*.WB)\0",
"wii\0WII Audio File (*.WII)\0",
"wp2\0WP2 Audio File (*.WP2)\0",
"wsd\0WSD Audio File (*.WSD)\0",