Updated vgmstream with experimental BFWAV support

CQTexperiment
Chris Moeller 2014-08-02 21:22:09 -07:00
parent 3b5b53ca26
commit cc0f04d8f9
5 changed files with 181 additions and 18 deletions

View File

@ -322,6 +322,7 @@
836F705718BDC2190095E648 /* util.h in Headers */ = {isa = PBXBuildFile; fileRef = 836F6F1B18BDC2190095E648 /* util.h */; };
836F705818BDC2190095E648 /* vgmstream.c in Sources */ = {isa = PBXBuildFile; fileRef = 836F6F1C18BDC2190095E648 /* vgmstream.c */; };
836F705918BDC2190095E648 /* vgmstream.h in Headers */ = {isa = PBXBuildFile; fileRef = 836F6F1D18BDC2190095E648 /* vgmstream.h */; settings = {ATTRIBUTES = (Public, ); }; };
83A5F75F198DF021009AF94C /* bfwav.c in Sources */ = {isa = PBXBuildFile; fileRef = 83A5F75E198DF021009AF94C /* bfwav.c */; };
83F5F8831908D0A400C8E65F /* fsb5.c in Sources */ = {isa = PBXBuildFile; fileRef = 83F5F8821908D0A400C8E65F /* fsb5.c */; };
/* End PBXBuildFile section */
@ -686,6 +687,7 @@
836F6F1B18BDC2190095E648 /* util.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = util.h; sourceTree = "<group>"; };
836F6F1C18BDC2190095E648 /* vgmstream.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = vgmstream.c; sourceTree = "<group>"; };
836F6F1D18BDC2190095E648 /* vgmstream.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = vgmstream.h; sourceTree = "<group>"; };
83A5F75E198DF021009AF94C /* bfwav.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bfwav.c; sourceTree = "<group>"; };
83F5F8821908D0A400C8E65F /* fsb5.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = fsb5.c; sourceTree = "<group>"; };
/* End PBXFileReference section */
@ -869,6 +871,7 @@
836F6E2718BDC2180095E648 /* meta */ = {
isa = PBXGroup;
children = (
83A5F75E198DF021009AF94C /* bfwav.c */,
83F5F8821908D0A400C8E65F /* fsb5.c */,
836F6E2918BDC2180095E648 /* 2dx9.c */,
836F6E2A18BDC2180095E648 /* aax.c */,
@ -1243,6 +1246,7 @@
836F700C18BDC2190095E648 /* ps2_wb.c in Sources */,
836F6F7D18BDC2190095E648 /* dc_str.c in Sources */,
836F701718BDC2190095E648 /* ps3_vawx.c in Sources */,
83A5F75F198DF021009AF94C /* bfwav.c in Sources */,
836F702018BDC2190095E648 /* rkv.c in Sources */,
836F703218BDC2190095E648 /* str_asr.c in Sources */,
836F6FB218BDC2190095E648 /* ngc_gcub.c in Sources */,

View File

@ -0,0 +1,171 @@
#include "meta.h"
#include "../util.h"
VGMSTREAM * init_vgmstream_bfwav(STREAMFILE *streamFile) {
VGMSTREAM * vgmstream = NULL;
char filename[PATH_LIMIT];
coding_t coding_type;
off_t head_offset;
/*off_t seek_offset;*/
int codec_number;
int channel_count;
int loop_flag;
off_t start_offset;
int big_endian = 1;
int ima = 0;
int32_t(*read_32bit)(off_t, STREAMFILE*) = NULL;
int16_t(*read_16bit)(off_t, STREAMFILE*) = NULL;
read_16bit = read_16bitBE;
read_32bit = read_32bitBE;
/* check extension, case insensitive */
streamFile->get_name(streamFile, filename, sizeof(filename));
if (strcasecmp("bfwav", filename_extension(filename)))
goto fail;
/* check header */
if ((uint32_t)read_32bitBE(0, streamFile) != 0x46574156) /* "FWAV" */
goto fail;
if ((uint32_t)read_32bitBE(4, streamFile) != 0xFEFF0040) /* "FWAV" */
goto fail;
/* get head offset, check */
if (big_endian)
head_offset = read_32bit(0x18, streamFile);
if ((uint32_t)read_32bitBE(head_offset, streamFile) != 0x494E464F) /* "INFO" (FWAV)*/
goto fail;
/* check type details */
codec_number = read_8bit(head_offset + 0x8, streamFile);
loop_flag = read_8bit(head_offset + 0x9, streamFile);
channel_count = read_8bit(head_offset + 0x1F, streamFile);
switch (codec_number) {
case 0:
coding_type = coding_PCM8;
break;
case 1:
if (big_endian)
coding_type = coding_PCM16BE;
else
coding_type = coding_PCM16LE;
break;
case 2:
coding_type = coding_NGC_DSP;
break;
default:
goto fail;
}
if (channel_count < 1) goto fail;
/* build the VGMSTREAM */
vgmstream = allocate_vgmstream(channel_count, loop_flag);
if (!vgmstream) goto fail;
/* fill in the vital statistics */
vgmstream->num_samples = read_32bit(head_offset + 0x14, streamFile);
vgmstream->sample_rate = (uint16_t)read_16bit(head_offset + 0xE, streamFile);
/* channels and loop flag are set by allocate_vgmstream */
vgmstream->loop_start_sample = read_32bit(head_offset + 0x10, streamFile);
vgmstream->loop_end_sample = vgmstream->num_samples;
vgmstream->coding_type = coding_type;
if (channel_count == 1)
vgmstream->layout_type = layout_none;
else
{
if (ima)
vgmstream->layout_type = layout_interleave;
else
vgmstream->layout_type = layout_interleave_shortblock;
}
if (big_endian)
vgmstream->meta_type = meta_FWAV;
if (big_endian)
{
// vgmstream->interleave_block_size = read_32bit(head_offset + 0x38, streamFile);
// vgmstream->interleave_smallblock_size = read_32bit(head_offset + 0x48, streamFile);
vgmstream->interleave_block_size = 0x200;
vgmstream->interleave_smallblock_size = 0x20;
}
if (big_endian)
start_offset = read_32bitBE(0x24, streamFile) + 0x20;
if (vgmstream->coding_type == coding_NGC_DSP) {
off_t coef_offset;
/*off_t coef_offset1;
off_t coef_offset2;*/
int coef_spacing;
int i, j;
off_t coeffheader;
int foundcoef;
coef_spacing = 0x2E;
coeffheader = head_offset + 0x28;
foundcoef = 0;
while (!(foundcoef))
{
if ((uint32_t)read_32bit(coeffheader, streamFile) == 0x1F000000)
{
coef_offset = read_32bit(coeffheader + 0xC, streamFile) + coeffheader;
foundcoef = 1;
break;
}
coeffheader++;
}
for (j = 0; j<vgmstream->channels; j++) {
for (i = 0; i<16; i++) {
vgmstream->ch[j].adpcm_coef[i] = read_16bit(coef_offset + j*coef_spacing + i * 2, streamFile);
}
}
}
/* open the file for reading by each channel */
{
int i;
for (i = 0; i<channel_count; i++) {
if (vgmstream->layout_type == layout_interleave_shortblock)
vgmstream->ch[i].streamfile = streamFile->open(streamFile, filename,
vgmstream->interleave_block_size);
else if (vgmstream->layout_type == layout_interleave)
vgmstream->ch[i].streamfile = streamFile->open(streamFile, filename,
STREAMFILE_DEFAULT_BUFFER_SIZE);
else
vgmstream->ch[i].streamfile = streamFile->open(streamFile, filename,
0x1000);
if (!vgmstream->ch[i].streamfile) goto fail;
vgmstream->ch[i].channel_start_offset =
vgmstream->ch[i].offset =
start_offset + i*vgmstream->interleave_block_size;
}
}
return vgmstream;
/* clean up anything we may have opened */
fail:
if (vgmstream) close_vgmstream(vgmstream);
return NULL;
}

View File

@ -1,6 +1,7 @@
#ifndef _MSC_VER
#include <unistd.h>
#endif
#include "vgmstream.h"
#include "streamfile.h"
#include "util.h"
@ -11,7 +12,7 @@ typedef struct {
size_t validsize;
uint8_t * buffer;
size_t buffersize;
char name[260];
char name[PATH_LIMIT];
#ifdef PROFILE_STREAMFILE
size_t bytes_read;
int error_count;

View File

@ -16,23 +16,14 @@ enum { PATH_LIMIT = 32768 };
#define VGM_USE_MPEG
/* disabled by default, defined for builds that support it */
//#define VGM_USE_G7221
//#define VGM_USE_MP4V2
//#define VGM_USE_FDKAAC
#include "streamfile.h"
#ifdef BUILD_VGMSTREAM
#include "coding/g72x_state.h"
#else
#include "g72x_state.h"
#endif
#ifdef VGM_USE_VORBIS
#ifdef __APPLE__
#define __MACOSX__
#endif
#include <vorbis/vorbisfile.h>
#endif
#ifdef VGM_USE_MPEG
#include <mpg123/mpg123.h>
#include <mpg123.h>
#endif
#ifdef VGM_USE_G7221
#include "g7221.h"
@ -51,13 +42,8 @@ enum { PATH_LIMIT = 32768 };
#include <maiatrac3plus.h>
#endif
#ifdef BUILD_VGMSTREAM
#include "coding/acm_decoder.h"
#include "coding/nwa_decoder.h"
#else
#include "acm_decoder.h"
#include "nwa_decoder.h"
#endif
/* The encoding type specifies the format the sound data itself takes */
typedef enum {
@ -254,7 +240,8 @@ typedef enum {
meta_RWSD, /* single-stream RWSD */
meta_RWAR, /* single-stream RWAR */
meta_RWAV, /* contents of RWAR */
meta_CWAV, /* */
meta_CWAV, /* contents of CWAR */
meta_FWAV, /* contents of FWAR */
meta_RSTM_SPM, /* RSTM with 44->22khz hack */
meta_THP,
meta_RSTM_shrunken, /* Atlus' mutant shortened RSTM */

View File

@ -211,7 +211,7 @@ err1:
+ (NSArray *)fileTypes
{
return [NSArray arrayWithObjects:@"2dx9", @"aaap", @"aax", @"acm", @"adp", @"adpcm", @"ads", @"adx", @"afc", @"agsc", @"ahx",@"aifc", @"aiff", @"aix", @"amts", @"as4", @"asd", @"asf", @"asr", @"ass", @"ast", @"aud", @"aus", @"baf", @"baka", @"bar", @"bcstm", @"bcwav", @"bg00", @"bgw", @"bh2pcm", @"bmdx", @"bns", @"bnsf", @"bo2", @"brstm", @"caf", @"capdsp", @"ccc", @"cfn", @"cnk", @"dcs", @"dcsw", @"ddsp", @"de2", @"dmsg", @"dsp", @"dvi", @"dxh", @"eam", @"emff", @"enth", @"fag", @"filp", @"fsb", @"gca", @"gcm", @"gcsw", @"gcw", @"genh", @"gms", @"gsp", @"hgc1", @"his", @"hps", @"hwas", @"idsp", @"idvi", @"ikm", @"ild", @"int", @"isd", @"ish", @"ivaud", @"ivb", @"joe", @"kces", @"kcey", @"khv", @"kraw", @"leg", @"logg", @"lps", @"lsf", @"lwav", @"matx", @"mcg", @"mi4", @"mib", @"mic", @"mihb", @"mpdsp", @"msa", @"mss", @"msvp", @"mus", @"musc", @"musx", @"mwv", @"myspd", @"ndp", @"npsf", @"nwa", @"omu", @"otm", @"p3d", @"pcm", @"pdt", @"pnb", @"pos", @"psh", @"psw", @"raw", @"rkv", @"rnd", @"rrds", @"rsd", @"rsf", @"rstm", @"rwar", @"rwav", @"rws", @"rwsd", @"rwx", @"rxw", @"s14", @"sab", @"sad", @"sap", @"sc", @"scd", @"sd9", @"sdt", @"seg", @"sfl", @"sfs", @"sl3", @"sli", @"smp", @"smpl", @"snd", @"sng", @"sns", @"spd", @"sps", @"spsd", @"spt", @"spw", @"ss2", @"ss7", @"ssm", @"sss", @"ster", @"sth", @"stm", @"stma", @"str", @"strm", @"sts", @"stx", @"svag", @"svs", @"swav", @"swd", @"tec", @"thp", @"tk5", @"tydsp", @"um3", @"vag", @"vas", @"vgs", @"vig", @"vjdsp", @"voi", @"vpk", @"vs", @"vsf", @"waa", @"wac", @"wad", @"wam", @"was", @"wavm", @"wb", @"wii", @"wp2", @"wsd", @"wsi", @"wvs", @"xa", @"xa2", @"xa30", @"xmu", @"xss", @"xvas", @"xwav", @"xwb", @"ydsp", @"ymf", @"zsd", @"zwdsp", nil];
return [NSArray arrayWithObjects:@"2dx9", @"aaap", @"aax", @"acm", @"adp", @"adpcm", @"ads", @"adx", @"afc", @"agsc", @"ahx",@"aifc", @"aiff", @"aix", @"amts", @"as4", @"asd", @"asf", @"asr", @"ass", @"ast", @"aud", @"aus", @"baf", @"baka", @"bar", @"bcstm", @"bcwav", @"bfwav", @"bg00", @"bgw", @"bh2pcm", @"bmdx", @"bns", @"bnsf", @"bo2", @"brstm", @"caf", @"capdsp", @"ccc", @"cfn", @"cnk", @"dcs", @"dcsw", @"ddsp", @"de2", @"dmsg", @"dsp", @"dvi", @"dxh", @"eam", @"emff", @"enth", @"fag", @"filp", @"fsb", @"gca", @"gcm", @"gcsw", @"gcw", @"genh", @"gms", @"gsp", @"hgc1", @"his", @"hps", @"hwas", @"idsp", @"idvi", @"ikm", @"ild", @"int", @"isd", @"ish", @"ivaud", @"ivb", @"joe", @"kces", @"kcey", @"khv", @"kraw", @"leg", @"logg", @"lps", @"lsf", @"lwav", @"matx", @"mcg", @"mi4", @"mib", @"mic", @"mihb", @"mpdsp", @"msa", @"mss", @"msvp", @"mus", @"musc", @"musx", @"mwv", @"myspd", @"ndp", @"npsf", @"nwa", @"omu", @"otm", @"p3d", @"pcm", @"pdt", @"pnb", @"pos", @"psh", @"psw", @"raw", @"rkv", @"rnd", @"rrds", @"rsd", @"rsf", @"rstm", @"rwar", @"rwav", @"rws", @"rwsd", @"rwx", @"rxw", @"s14", @"sab", @"sad", @"sap", @"sc", @"scd", @"sd9", @"sdt", @"seg", @"sfl", @"sfs", @"sl3", @"sli", @"smp", @"smpl", @"snd", @"sng", @"sns", @"spd", @"sps", @"spsd", @"spt", @"spw", @"ss2", @"ss7", @"ssm", @"sss", @"ster", @"sth", @"stm", @"stma", @"str", @"strm", @"sts", @"stx", @"svag", @"svs", @"swav", @"swd", @"tec", @"thp", @"tk5", @"tydsp", @"um3", @"vag", @"vas", @"vgs", @"vig", @"vjdsp", @"voi", @"vpk", @"vs", @"vsf", @"waa", @"wac", @"wad", @"wam", @"was", @"wavm", @"wb", @"wii", @"wp2", @"wsd", @"wsi", @"wvs", @"xa", @"xa2", @"xa30", @"xmu", @"xss", @"xvas", @"xwav", @"xwb", @"ydsp", @"ymf", @"zsd", @"zwdsp", nil];
}
+ (NSArray *)mimeTypes