Redesign of buffer length calculation

git-svn-id: svn://svn.mplayerhq.hu/mplayer/trunk@7590 b3059339-0415-0410-9bf9-f77b7e298cf2
This commit is contained in:
anders 2002-10-03 12:02:46 +00:00
parent f1f0dbdba3
commit 7ca1ef4974
3 changed files with 28 additions and 21 deletions

View File

@ -366,41 +366,46 @@ af_data_t* af_play(af_stream_t* s, af_data_t* data)
}
/* Helper function used to calculate the exact buffer length needed
when buffers are resized */
inline int af_lencalc(frac_t mul, int len){
register int q = len*mul.n;
return q/mul.d + q%mul.d;
when buffers are resized. The returned length is >= than what is
needed */
inline int af_lencalc(frac_t mul, af_data_t* d){
register int t = d->bps*d->nch;
return t*(((d->len/t)*mul.n + 1)/mul.d);
}
/* Calculate how long the output from the filters will be given the
input length "len" */
input length "len". The calculated length is >= the actual
length. */
int af_outputlen(af_stream_t* s, int len)
{
int t = s->input.bps*s->input.nch;
af_instance_t* af=s->first;
frac_t mul = {1,1};
register frac_t mul = {1,1};
// Iterate through all filters
do{
mul.n *= af->mul.n;
mul.d *= af->mul.d;
af=af->next;
}while(af);
return af_lencalc(mul,len);
return t * (((len/t)*mul.n + 1)/mul.d);
}
/* Calculate how long the input to the filters should be to produce a
certain output length, i.e. the return value of this function is
the input length required to produce the output length "len". */
the input length required to produce the output length "len". The
calculated length is <= the actual length */
int af_inputlen(af_stream_t* s, int len)
{
int t = s->input.bps*s->input.nch;
af_instance_t* af=s->first;
frac_t mul = {1,1};
register frac_t mul = {1,1};
// Iterate through all filters
do{
mul.d *= af->mul.n;
mul.n *= af->mul.d;
mul.n *= af->mul.n;
mul.d *= af->mul.d;
af=af->next;
}while(af);
return af_lencalc(mul,len);
return t * (((len/t) * mul.d - 1)/mul.n);
}
/* Helper function called by the macro with the same name this
@ -408,8 +413,7 @@ int af_inputlen(af_stream_t* s, int len)
inline int af_resize_local_buffer(af_instance_t* af, af_data_t* data)
{
// Calculate new length
register int len = af_lencalc(af->mul,data->len/(data->nch*data->bps)) *
data->nch * data->bps;
register int len = af_lencalc(af->mul,data);
mp_msg(MSGT_AFILTER,MSGL_V,"Reallocating memory in module %s, old len = %i, new len = %i\n",af->info->name,af->data->len,len);
// If there is a buffer free it
if(af->data->audio)

View File

@ -138,11 +138,13 @@ void af_uninit(af_stream_t* s);
// Filter data chunk through the filters in the list
af_data_t* af_play(af_stream_t* s, af_data_t* data);
/* Calculate how long the output from the filters will be given the
input length "len" */
input length "len". The calculated length is >= the actual
length */
int af_outputlen(af_stream_t* s, int len);
/* Calculate how long the input to the filters should be to produce a
certain output length, i.e. the return value of this function is
the input length required to produce the output length "len". */
the input length required to produce the output length "len". The
calculated length is <= the actual length */
int af_inputlen(af_stream_t* s, int len);
@ -154,14 +156,15 @@ int af_inputlen(af_stream_t* s, int len);
int af_resize_local_buffer(af_instance_t* af, af_data_t* data);
/* Helper function used to calculate the exact buffer length needed
when buffers are resized */
int af_lencalc(frac_t mul, int len);
when buffers are resized. The returned length is >= than what is
needed */
int af_lencalc(frac_t mul, af_data_t* data);
/* Memory reallocation macro: if a local buffer is used (i.e. if the
filter doesn't operate on the incoming buffer this macro must be
called to ensure the buffer is big enough. */
#define RESIZE_LOCAL_BUFFER(a,d)\
((af->data->len < af_lencalc(af->mul,data->len))?af_resize_local_buffer(af,data):AF_OK)
((af->data->len < af_lencalc(af->mul,data))?af_resize_local_buffer(af,data):AF_OK)
#ifndef min
#define min(a,b)(((a)>(b))?(b):(a))

View File

@ -122,7 +122,7 @@ static af_data_t* play(struct af_instance_s* af, af_data_t* data)
// Reset unused channels if nch in < nch out
if(af->mul.n > af->mul.d)
memset(l->audio,0,af_lencalc(af->mul, c->len));
memset(l->audio,0,af_lencalc(af->mul, c));
// Special case always output L & R
if(c->nch == 1){
@ -143,7 +143,7 @@ static af_data_t* play(struct af_instance_s* af, af_data_t* data)
// Set output data
c->audio = l->audio;
c->len = af_lencalc(af->mul, c->len);
c->len = af_lencalc(af->mul, c);
c->nch = l->nch;
return c;