summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorMiguel Freitas <miguelfreitas@users.sourceforge.net>2001-11-15 00:41:28 +0000
committerMiguel Freitas <miguelfreitas@users.sourceforge.net>2001-11-15 00:41:28 +0000
commit2c82a5b3b2398de419ec33297fabf2a752539d80 (patch)
tree47dc944bc9e1fd0d44e0e61e5f0a508aa0901d8a /src
parentd731e04a7ffc2bac45e975c9b35a16d3e632a91c (diff)
downloadxine-lib-2c82a5b3b2398de419ec33297fabf2a752539d80.tar.gz
xine-lib-2c82a5b3b2398de419ec33297fabf2a752539d80.tar.bz2
- audio bugfixes (dynamic buffers and Direct Show support). it show play
about any working audio codec now, no matter the rate and number of channels. unfortunately sync and seek might be broken. CVS patchset: 1041 CVS date: 2001/11/15 00:41:28
Diffstat (limited to 'src')
-rw-r--r--src/libw32dll/Makefile.am7
-rw-r--r--src/libw32dll/libwin32.h38
-rw-r--r--src/libw32dll/w32codec.c381
3 files changed, 337 insertions, 89 deletions
diff --git a/src/libw32dll/Makefile.am b/src/libw32dll/Makefile.am
index 5012c03f4..358dab4a2 100644
--- a/src/libw32dll/Makefile.am
+++ b/src/libw32dll/Makefile.am
@@ -1,6 +1,7 @@
CFLAGS = @GLOBAL_CFLAGS@
-SUBDIRS = wine
+SUBDIRS = wine DirectShow
+# SUBDIRS = wine dshow_cpp
if HAVE_W32DLL
w32dll_codec = xineplug_decode_w32dll.la
@@ -19,7 +20,9 @@ lib_LTLIBRARIES = $(w32dll_codec)
xineplug_decode_w32dll_la_SOURCES = w32codec.c
xineplug_decode_w32dll_la_LDFLAGS = -avoid-version -module
-xineplug_decode_w32dll_la_LIBADD = $(top_builddir)/src/libw32dll/wine/libwine.la @KSTAT_LIBS@
+xineplug_decode_w32dll_la_LIBADD = $(top_builddir)/src/libw32dll/wine/libwine.la \
+ $(top_builddir)/src/libw32dll/DirectShow/libds_filter.la @KSTAT_LIBS@
+# $(top_builddir)/src/libw32dll/dshow_cpp/libds_filter.la @KSTAT_LIBS@
noinst_HEADERS = w32codec.h
diff --git a/src/libw32dll/libwin32.h b/src/libw32dll/libwin32.h
index 2155f9adf..cf57b2f88 100644
--- a/src/libw32dll/libwin32.h
+++ b/src/libw32dll/libwin32.h
@@ -34,21 +34,23 @@ typedef struct _CodecInfo
GUID guid;
}CodecInfo;
-/*
+
typedef struct _CImage // public your_libvo_mem
{
+ char* ptr;
+
char* (*Data)();
- {
+ /*{
return 0;
// pointer to memory block
- }
- bool (*Supported)(fourcc_t csp, int bits);
- {
+ }*/
+ int (*Supported)(fourcc_t csp, int bits);
+ /*{
return true;
// if you support such surface
- }
+ }*/
}CImage;
-*/
+
#if 0
struct BitmapInfo : public BITMAPINFOHEADER
@@ -77,14 +79,6 @@ struct IAudioEncoder
};
*/
-typedef struct _IVideoDecoder
-{
- int VBUFSIZE;
- int QMARKHI;
- int QMARKLO;
- int DMARKHI;
- int DMARKLO;
-
enum CAPS
{
CAP_NONE = 0,
@@ -106,6 +100,16 @@ typedef struct _IVideoDecoder
STOP = 0,
START,
};
+
+
+typedef struct _IVideoDecoder
+{
+ int VBUFSIZE;
+ int QMARKHI;
+ int QMARKLO;
+ int DMARKHI;
+ int DMARKLO;
+
/*
IVideoDecoder(CodecInfo& info, const BITMAPINFOHEADER& format) : record(info)
{
@@ -120,8 +124,8 @@ typedef struct _IVideoDecoder
}
*/
const CodecInfo record;
- //DecodingMode m_Mode; // should we do precaching (or even change Quality on the fly)
- //DecodingState m_State;
+ int m_Mode; // should we do precaching (or even change Quality on the fly)
+ int m_State;
int m_iDecpos;
int m_iPlaypos;
float m_fQuality; // quality for the progress bar 0..1(best)
diff --git a/src/libw32dll/w32codec.c b/src/libw32dll/w32codec.c
index 9d93508ff..7067b097e 100644
--- a/src/libw32dll/w32codec.c
+++ b/src/libw32dll/w32codec.c
@@ -17,9 +17,10 @@
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
*
- * $Id: w32codec.c,v 1.41 2001/11/13 21:47:59 heikos Exp $
+ * $Id: w32codec.c,v 1.42 2001/11/15 00:41:28 miguelfreitas Exp $
*
* routines for using w32 codecs
+ * DirectShow support by Miguel Freitas
*
*/
@@ -35,12 +36,42 @@
#include "wine/mmreg.h"
#include "wine/ldt_keeper.h"
+#define NOAVIFILE_HEADERS
+#include "DirectShow/guids.h"
+#include "DirectShow/DS_AudioDecoder.h"
+//#include "DirectShow/DS_VideoDecoder.h"
+//#include "dshow_cpp/DS_AudioDec.h"
+
#include "video_out.h"
#include "audio_out.h"
#include "buffer.h"
#include "monitor.h"
#include "xine_internal.h"
#include "memcpy.h"
+
+static GUID CLSID_Voxware =
+{
+ 0x73f7a062, 0x8829, 0x11d1,
+ { 0xb5, 0x50, 0x00, 0x60, 0x97, 0x24, 0x2d, 0x8d }
+};
+
+static GUID CLSID_Acelp =
+{
+ 0x4009f700, 0xaeba, 0x11d1,
+ { 0x83, 0x44, 0x00, 0xc0, 0x4f, 0xb9, 0x2e, 0xb7 }
+};
+
+static GUID wmv1_clsid =
+{
+ 0x4facbba1, 0xffd8, 0x4cd7,
+ {0x82, 0x28, 0x61, 0xe2, 0xf6, 0x5c, 0xb1, 0xae}
+};
+
+static GUID wmv2_clsid =
+{
+ 0x521fb373, 0x7654, 0x49f2,
+ {0xbd, 0xb1, 0x0c, 0x6e, 0x66, 0x60, 0x71, 0x4f}
+};
extern char* win32_codec_name;
extern char* win32_def_path;
@@ -64,7 +95,12 @@ typedef struct w32v_decoder_s {
/* profiler */
int prof_rgb2yuv;
-
+
+ int ds_driver;
+ GUID *guid;
+ //DS_VideoDecoder *ds_dec;
+
+
LDT_FS *ldt_fs;
} w32v_decoder_t;
@@ -77,9 +113,21 @@ typedef struct w32a_decoder_s {
unsigned char *buf;
int size;
+ uint32_t pts;
+ uint32_t scr;
+
+ unsigned char *outbuf;
+ int outsize;
+
HACMSTREAM srcstream;
int rec_audio_src_size;
+ int max_audio_src_size;
int num_channels;
+ int rate;
+
+ int ds_driver;
+ GUID *guid;
+ DS_AudioDecoder *ds_dec;
LDT_FS *ldt_fs;
} w32a_decoder_t;
@@ -181,6 +229,7 @@ static char* get_vids_codec_name(w32v_decoder_t *this,
this->yuv_supported=0;
this->yuv_hack_needed=0;
this->flipped=0;
+ this->ds_driver = 0;
buf_type &= 0xffff0000;
@@ -253,6 +302,12 @@ static char* get_vids_codec_name(w32v_decoder_t *this,
/* MainConcept DV Codec */
this->yuv_supported=1;
return "mcdvd_32.dll";
+
+ case BUF_VIDEO_WMV7:
+ this->yuv_supported=1;
+ this->ds_driver = 1;
+ this->guid=&wmv1_clsid;
+ return "wmvds32.ax";
}
@@ -287,6 +342,7 @@ static int w32v_can_handle (video_decoder_t *this_gen, int buf_type) {
buf_type == BUF_VIDEO_I263 ||
buf_type == BUF_VIDEO_MSVC ||
buf_type == BUF_VIDEO_DV );
+ //buf_type == BUF_VIDEO_WMV7 );
}
static void w32v_init (video_decoder_t *this_gen, vo_instance_t *video_out) {
@@ -313,8 +369,6 @@ static void w32v_init_codec (w32v_decoder_t *this, int buf_type) {
this->ldt_fs = Setup_LDT_Keeper();
- win32_codec_name = get_vids_codec_name (this, buf_type);
-
outfmt = IMGFMT_15RGB;
if (this->yuv_supported) {
vo_cap = this->video_out->get_capabilities (this->video_out);
@@ -343,7 +397,7 @@ static void w32v_init_codec (w32v_decoder_t *this, int buf_type) {
this->decoder_ok = 0;
return;
}
-
+
printf ("w32codec: video output format: %.4s %08lx\n",
(char*)&this->o_bih.biCompression,
this->o_bih.biCompression);
@@ -392,6 +446,66 @@ static void w32v_init_codec (w32v_decoder_t *this, int buf_type) {
this->decoder_ok = 1;
}
+static void w32v_init_ds_codec (w32v_decoder_t *this, int buf_type) {
+ /*HRESULT ret;
+ uint32_t vo_cap;
+ int outfmt;
+ CodecInfo ci;
+
+ printf ("w32codec: init DS codec...\n");
+
+ memset(&this->o_bih, 0, sizeof(BITMAPINFOHEADER));
+ this->o_bih.biSize = sizeof(BITMAPINFOHEADER);
+
+ this->ldt_fs = Setup_LDT_Keeper();
+
+ outfmt = IMGFMT_15RGB;
+ if (this->yuv_supported) {
+ outfmt = IMGFMT_YUY2;
+ }
+
+
+ ci.dll=win32_codec_name;
+ memcpy(&ci.guid,this->guid,sizeof(ci.guid));
+
+ this->ds_dec = DS_VideoDecoder_Create(&ci, &this->bih, this->flipped, 0);
+
+
+ if(outfmt==IMGFMT_YUY2 || outfmt==IMGFMT_15RGB)
+ this->o_bih.biBitCount=16;
+ else
+ this->o_bih.biBitCount=outfmt&0xFF;
+
+ this->o_bih.biSizeImage = this->o_bih.biWidth * this->o_bih.biHeight
+ * this->o_bih.biBitCount / 8;
+
+ if (this->flipped)
+ this->o_bih.biHeight=-this->bih.biHeight;
+
+ if(outfmt==IMGFMT_YUY2 && !this->yuv_hack_needed)
+ this->o_bih.biCompression = mmioFOURCC('Y','U','Y','2');
+ else
+ this->o_bih.biCompression = 0;
+
+
+ if (outfmt==IMGFMT_YUY2 && this->yuv_hack_needed)
+ this->o_bih.biCompression = mmioFOURCC('Y','U','Y','2');
+
+ DS_VideoDecoder_SetDestFmt(this->ds_dec, this->o_bih.biBitCount,this->o_bih.biCompression);
+
+ DS_VideoDecoder_StartInternal(this->ds_dec);
+
+ this->size = 0;
+
+ this->img_buffer = malloc (this->o_bih.biSizeImage);
+
+ this->video_out->open (this->video_out);
+
+ this->outfmt = outfmt;
+ this->decoder_ok = 1;*/
+}
+
+
static void w32v_decode_data (video_decoder_t *this_gen, buf_element_t *buf) {
w32v_decoder_t *this = (w32v_decoder_t *) this_gen;
@@ -408,7 +522,12 @@ static void w32v_decode_data (video_decoder_t *this_gen, buf_element_t *buf) {
memcpy ( &this->bih, buf->content, sizeof (BITMAPINFOHEADER));
this->video_step = buf->decoder_info[1];
- w32v_init_codec (this, buf->type);
+ win32_codec_name = get_vids_codec_name (this, buf->type);
+
+ if( !this->ds_driver )
+ w32v_init_codec (this, buf->type);
+ else
+ w32v_init_ds_codec (this, buf->type);
} else if (this->decoder_ok) {
@@ -440,10 +559,17 @@ static void w32v_decode_data (video_decoder_t *this_gen, buf_element_t *buf) {
&this->bih, this->buf,
&this->o_bih, img->base[0]);
*/
+ if( !this->ds_driver )
ret = ICDecompress(this->hic, ICDECOMPRESS_NOTKEYFRAME,
&this->bih, this->buf,
&this->o_bih, this->img_buffer);
-
+ else {
+ /* CImage image;
+ image.ptr=this->img_buffer;
+ ret = DS_VideoDecoder_DecodeInternal(this->ds_dec, this->buf,
+ this->size, 0, &image);*/
+ }
+
if (this->outfmt==IMGFMT_YUY2) {
/* already decoded into YUY2 format by DLL */
fast_memcpy(img->base[0], this->img_buffer, this->bih.biHeight*this->bih.biWidth*2);
@@ -564,12 +690,15 @@ static int w32a_can_handle (audio_decoder_t *this_gen, int buf_type) {
(codec == BUF_AUDIO_IMAADPCM) ||
(codec == BUF_AUDIO_MSGSM) ||
(codec == BUF_AUDIO_IMC) ||
- (codec == BUF_AUDIO_LH) );
+ (codec == BUF_AUDIO_LH) ||
+ (codec == BUF_AUDIO_VOXWARE) ||
+ (codec == BUF_AUDIO_ACELPNET) );
}
static char* get_auds_codec_name(w32a_decoder_t *this, int buf_type) {
buf_type = buf_type & 0xFFFF0000;
+ this->ds_driver=0;
switch (buf_type) {
case BUF_AUDIO_DIVXA:
@@ -584,6 +713,15 @@ static char* get_auds_codec_name(w32a_decoder_t *this, int buf_type) {
return "imc32.acm";
case BUF_AUDIO_LH:
return "lhacm.acm";
+ case BUF_AUDIO_VOXWARE:
+ this->ds_driver=1;
+ this->guid=&CLSID_Voxware;
+ return "voxmsdec.ax";
+ case BUF_AUDIO_ACELPNET:
+ /* acelpnet is not working yet */
+ this->ds_driver=1;
+ this->guid=&CLSID_Acelp;
+ return "acelpdec.ax";
}
printf ("w32codec: this didn't happen: unknown audio buf type %08x\n",
buf_type);
@@ -599,6 +737,7 @@ static void w32a_init (audio_decoder_t *this_gen, ao_instance_t *audio_out) {
this->decoder_ok = 0;
this->buf = NULL;
+ this->outbuf = NULL;
}
static int w32a_init_audio (w32a_decoder_t *this,
@@ -607,9 +746,10 @@ static int w32a_init_audio (w32a_decoder_t *this,
HRESULT ret;
static WAVEFORMATEX wf;
- long in_size=in_fmt_->nBlockAlign;
static WAVEFORMATEX *in_fmt;
- unsigned long srcsize;
+ unsigned long in_size=in_fmt_->nBlockAlign;
+ unsigned long out_size;
+ audio_buffer_t *audio_buffer;
in_fmt = (WAVEFORMATEX *) malloc (64);
@@ -617,6 +757,7 @@ static int w32a_init_audio (w32a_decoder_t *this,
this->srcstream = 0;
this->num_channels = in_fmt->nChannels;
+ this->rate = in_fmt->nSamplesPerSec;
if (this->output_open)
this->audio_out->close (this->audio_out);
@@ -628,6 +769,7 @@ static int w32a_init_audio (w32a_decoder_t *this,
printf("w32codec: (ACM_Decoder) Cannot open audio output device\n");
return 0;
}
+ audio_buffer = this->audio_out->get_buffer (this->audio_out);
this->ldt_fs = Setup_LDT_Keeper();
@@ -640,39 +782,75 @@ static int w32a_init_audio (w32a_decoder_t *this,
wf.cbSize = 0;
win32_codec_name = get_auds_codec_name (this, buf_type);
- ret=acmStreamOpen(&this->srcstream,(HACMDRIVER)NULL,
- in_fmt,
- &wf,
- NULL,0,0,0);
- if(ret){
- if(ret==ACMERR_NOTPOSSIBLE)
- printf("w32codec: (ACM_Decoder) Unappropriate audio format\n");
- else
- printf("w32codec: (ACM_Decoder) acmStreamOpen error %d", (int) ret);
- this->srcstream = 0;
- return 0;
- }
+
+ if( !this->ds_driver ) {
+ ret=acmStreamOpen(&this->srcstream,(HACMDRIVER)NULL,
+ in_fmt,
+ &wf,
+ NULL,0,0,0);
+ if(ret){
+ if(ret==ACMERR_NOTPOSSIBLE)
+ printf("w32codec: (ACM_Decoder) Unappropriate audio format\n");
+ else
+ printf("w32codec: (ACM_Decoder) acmStreamOpen error %d", (int) ret);
+ this->srcstream = 0;
+ return 0;
+ }
- acmStreamSize(this->srcstream, in_size, &srcsize, ACM_STREAMSIZEF_SOURCE);
- printf("w32codec: Audio buffer min. size: %d\n",(int)srcsize);
- srcsize*=2;
- if(srcsize<16384)
- srcsize=16384;
+ acmStreamSize(this->srcstream, in_size, &out_size, ACM_STREAMSIZEF_SOURCE);
+ out_size*=2;
+ if(out_size < audio_buffer->mem_size)
+ out_size=audio_buffer->mem_size;
+ printf("w32codec: Audio buffer min. size: %d\n",(int)out_size);
+
+ acmStreamSize(this->srcstream, out_size, (LPDWORD) &this->rec_audio_src_size,
+ ACM_STREAMSIZEF_DESTINATION);
+ } else {
+ CodecInfo ci;
+
+ ci.dll=win32_codec_name;
+ memcpy(&ci.guid,this->guid,sizeof(GUID));
+
+ /*__asm__ __volatile__(
+ "int $0x3\n" : :
+ );*/
+
+ if( (this->ds_dec=DS_AudioDecoder_Create(&ci, in_fmt)) == NULL ) {
+ printf("w32codec: Error initializing DirectShow Audio\n");
+ this->srcstream = 0;
+ return 0;
+ }
+
+ out_size = audio_buffer->mem_size;
+ printf("w32codec: output buffer size: %d\n",(int)out_size);
+ this->rec_audio_src_size=DS_AudioDecoder_GetSrcSize(this->ds_dec,out_size);
- acmStreamSize(this->srcstream, srcsize, (LPDWORD) &this->rec_audio_src_size,
- ACM_STREAMSIZEF_DESTINATION);
+ /* somehow DS_Filters seems to eat more than rec_audio_src_size if the output
+ buffer is big enough. Doubling rec_audio_src_size should make this
+ impossible */
+ this->rec_audio_src_size*=2;
+ }
printf("w32codec: Recommended source buffer size: %d\n", this->rec_audio_src_size);
if( this->buf )
free(this->buf);
- if( this->rec_audio_src_size < 2 * in_fmt->nBlockAlign ) {
- this->rec_audio_src_size = 2 * in_fmt->nBlockAlign;
- srcsize *= 2;
+ if( this->outbuf )
+ free(this->outbuf);
+
+ if( this->rec_audio_src_size < in_fmt->nBlockAlign ) {
+ this->rec_audio_src_size = in_fmt->nBlockAlign;
printf("w32codec: adjusting source buffer size to %d\n", this->rec_audio_src_size);
}
- this->buf = malloc( 2 * this->rec_audio_src_size );
-
+
+ this->max_audio_src_size = 2 * this->rec_audio_src_size;
+
+ this->buf = malloc( this->max_audio_src_size );
+
+ out_size += 32768;
+ this->outbuf = malloc( out_size );
+ this->outsize = out_size;
+
this->size = 0;
return 1;
@@ -688,76 +866,132 @@ static void w32a_decode_audio (w32a_decoder_t *this,
static ACMSTREAMHEADER ash;
HRESULT hr;
+ int size_read, size_written;
/* DWORD srcsize=0; */
+ int in_avg_pts_kbyte = 0;
+
+ /* FIXME: the current code for estimating output pts don't work
+ on wraps and seeks!!!
+ also there might be serious sync problems. in short: it's
+ somewhat broken and need fix.
+ */
+
+ if( !this->size || pts < this->pts || scr < this->scr ) {
+ this->pts = pts;
+ this->scr = scr;
+ } else {
+ /* input based estimation disabled -> bad results */
+ /* in_avg_pts_kbyte = (pts - this->pts) * 1024 / this->size; */
+ }
+
+
+ if( this->size + size > this->max_audio_src_size ) {
+ this->max_audio_src_size = this->size + size;
+ printf("w32codec: increasing source buffer to %d to avoid overflow.\n",
+ this->max_audio_src_size);
+ this->buf = realloc( this->buf, this->max_audio_src_size );
+ }
+
fast_memcpy (&this->buf[this->size], data, size);
-
+
this->size += size;
- if( this->size > 2 * this->rec_audio_src_size )
- printf("w32codec: buffer overflow on w32a_decode_audio\n");
-
- while (this->size >= this->rec_audio_src_size) {
-
- audio_buffer_t *audio_buffer = this->audio_out->get_buffer (this->audio_out);
+ while (this->size >= this->rec_audio_src_size) {
memset(&ash, 0, sizeof(ash));
ash.cbStruct=sizeof(ash);
ash.fdwStatus=0;
ash.dwUser=0;
ash.pbSrc=this->buf;
ash.cbSrcLength=this->rec_audio_src_size;
- ash.pbDst=(uint8_t *)audio_buffer->mem;
- ash.cbDstLength=audio_buffer->mem_size;
- hr=acmStreamPrepareHeader(this->srcstream,&ash,0);
- if(hr){
- printf("w32codec: (ACM_Decoder) acmStreamPrepareHeader error %d\n",(int)hr);
-
- audio_buffer->num_frames = 0;
- this->audio_out->put_buffer (this->audio_out, audio_buffer);
-
- return;
- }
-
+ ash.pbDst=this->outbuf;
+ ash.cbDstLength=this->outsize;
+
/*
printf ("decoding %d of %d bytes (%02x %02x %02x %02x ... %02x %02x)\n",
this->rec_audio_src_size, this->size,
this->buf[0], this->buf[1], this->buf[2], this->buf[3],
this->buf[this->rec_audio_src_size-2], this->buf[this->rec_audio_src_size-1]);
*/
+
+ if( !this->ds_driver ) {
+ hr=acmStreamPrepareHeader(this->srcstream,&ash,0);
+ if(hr){
+ printf("w32codec: (ACM_Decoder) acmStreamPrepareHeader error %d\n",(int)hr);
- hr=acmStreamConvert(this->srcstream,&ash,0);
+ return;
+ }
+
+ hr=acmStreamConvert(this->srcstream,&ash,0);
+ } else {
+ hr=DS_AudioDecoder_Convert(this->ds_dec, ash.pbSrc, ash.cbSrcLength,
+ ash.pbDst, ash.cbDstLength,
+ &size_read, &size_written );
+ ash.cbSrcLengthUsed = size_read;
+ ash.cbDstLengthUsed = size_written;
+ }
+
if(hr){
- printf("w32codec: acmStreamConvert error %d, used %d bytes\n",(int)hr,(int)ash.cbSrcLengthUsed);
- ash.cbSrcLengthUsed = this->rec_audio_src_size;
-
- audio_buffer->num_frames = 0;
- this->audio_out->put_buffer (this->audio_out, audio_buffer);
-
+ printf("w32codec: stream convert error %d, used %d bytes\n",(int)hr,(int)ash.cbSrcLengthUsed);
+ this->size-=ash.cbSrcLength;
} else {
+ int DstLengthUsed, bufsize;
+ audio_buffer_t *audio_buffer;
+ char *p;
/*
printf ("acmStreamConvert worked, used %d bytes, generated %d bytes\n",
ash.cbSrcLengthUsed, ash.cbDstLengthUsed);
*/
- if (ash.cbDstLengthUsed>0) {
-
- audio_buffer->num_frames = ash.cbDstLengthUsed / (this->num_channels*2);
+ DstLengthUsed = ash.cbDstLengthUsed;
+ pts = this->pts;
+ scr = this->scr;
+ p = this->outbuf;
+
+ while( DstLengthUsed )
+ {
+ audio_buffer = this->audio_out->get_buffer (this->audio_out);
+
+ if( DstLengthUsed < audio_buffer->mem_size )
+ bufsize = DstLengthUsed;
+ else
+ bufsize = audio_buffer->mem_size;
+
+ fast_memcpy( audio_buffer->mem, p, bufsize );
+ /*
+ printf(" outputing %d bytes, pts = %d\n", bufsize, pts );
+ */
+ audio_buffer->num_frames = bufsize / (this->num_channels*2);
audio_buffer->vpts = pts;
audio_buffer->scr = scr;
this->audio_out->put_buffer (this->audio_out, audio_buffer);
-
+
+ pts += bufsize / (this->num_channels*2) * 90000 / this->rate;
+ scr += bufsize / (this->num_channels*2) * 90000 / this->rate;
+ DstLengthUsed -= bufsize;
+ p += bufsize;
}
}
if(ash.cbSrcLengthUsed>=this->size){
this->size=0;
} else {
this->size-=ash.cbSrcLengthUsed;
- memmove( this->buf, &this->buf [ash.cbSrcLengthUsed], this->size);
+ fast_memcpy( this->buf, &this->buf [ash.cbSrcLengthUsed], this->size);
+
+ if( in_avg_pts_kbyte ) {
+ this->pts += ash.cbSrcLengthUsed * in_avg_pts_kbyte / 1024;
+ this->scr += ash.cbSrcLengthUsed * in_avg_pts_kbyte / 1024;
+ } else {
+ this->pts += ash.cbDstLengthUsed / (this->num_channels*2) * 90000 / this->rate;
+ this->scr += ash.cbDstLengthUsed / (this->num_channels*2) * 90000 / this->rate;
+ }
}
- hr=acmStreamUnprepareHeader(this->srcstream,&ash,0);
- if(hr){
- printf("w32codec: (ACM_Decoder) acmStreamUnprepareHeader error %d\n",(int)hr);
+ if( !this->ds_driver ) {
+ hr=acmStreamUnprepareHeader(this->srcstream,&ash,0);
+ if(hr){
+ printf("w32codec: (ACM_Decoder) acmStreamUnprepareHeader error %d\n",(int)hr);
+ }
}
}
}
@@ -779,12 +1013,15 @@ static void w32a_decode_data (audio_decoder_t *this_gen, buf_element_t *buf) {
}
-
static void w32a_close (audio_decoder_t *this_gen) {
w32a_decoder_t *this = (w32a_decoder_t *) this_gen;
- acmStreamClose(this->srcstream, 0);
+ if( !this->ds_driver ) {
+ acmStreamClose(this->srcstream, 0);
+ } else {
+ DS_AudioDecoder_Destroy(this->ds_dec);
+ }
Restore_LDT_Keeper(this->ldt_fs);
@@ -796,6 +1033,10 @@ static void w32a_close (audio_decoder_t *this_gen) {
free(this->buf);
this->buf = NULL;
}
+ if( this->outbuf ) {
+ free(this->outbuf);
+ this->outbuf = NULL;
+ }
}
static char *w32a_get_id(void) {