www.pudn.com > ampegsrc.zip > DECODE.C
/**********************************************************************
Copyright (c) 1991 MPEG/audio software simulation group, All Rights Reserved
decode.c
**********************************************************************/
/**********************************************************************
* MPEG/audio coding/decoding software, work in progress *
* NOT for public distribution until verified and approved by the *
* MPEG/audio committee. For further information, please contact *
* Davis Pan, 708-538-5671, e-mail: pan@ukraine.corp.mot.com *
* *
* VERSION 4.3 *
* changes made since last update: *
* date programmers comment *
* 2/25/91 Douglas Wong, start of version 1.0 records *
* Davis Pan *
* 3/06/91 Douglas Wong rename: setup.h to dedef.h *
* dfilter to defilter *
* dwindow to dewindow *
* integrated "quantizer", "scalefactor" *
* combined window_samples routine into *
* filter samples *
* 3/31/91 Bill Aspromonte replaced read_filter by *
* create_syn_filter and introduced a *
* new Sub-Band Synthesis routine called *
* SubBandSynthesis() *
* 5/10/91 Vish (PRISM) Ported to Macintosh and Unix. *
* Changed "out_fifo()" so that last *
* unfilled block is also written out. *
* "create_syn_filter()" was modified so *
* that calculation precision is same as *
* in specification tables. *
* Changed "decode_scale()" to reflect *
* specifications. *
* Removed all routines used by *
* "synchronize_buffer()". This is now *
* replaced by "seek_sync()". *
* Incorporated Jean-Georges Fritsch's *
* "bitstream.c" package. *
* Deleted "reconstruct_sample()". *
* 27jun91 dpwe (Aware) Passed outFile and &sampFrames as *
* args to out_fifo() - were global. *
* Moved "alloc_*" reader to common.c. *
* alloc, sblimit, stereo passed via new *
* 'frame_params struct (were globals). *
* Added JOINT STEREO decoding, lyrs I&II*
* Affects: decode_bitalloc,buffer_samps *
* Plus a few other cleanups. *
* 6/10/91 Earle Jennings conditional expansion added in *
* II_dequantize_sample to handle range *
* problems in MSDOS version *
* 8/8/91 Jens Spille Change for MS-C6.00 *
*10/1/91 S.I. Sudharsanan, Ported to IBM AIX platform. *
* Don H. Lee, *
* Peter W. Farrett *
*10/3/91 Don H. Lee implemented CRC-16 error protection *
* newly introduced functions are *
* buffer_CRC and recover_CRC_error. *
* 2/11/92 W. Joseph Carter Ported new code to Macintosh. Most *
* important fixes involved changing *
* 16-bit ints to long or unsigned in *
* bit alloc routines for quant of 65535 *
* and passing proper function args. *
* Removed "Other Joint Stereo" option *
* and made bitrate be total channel *
* bitrate, irrespective of the mode. *
* Fixed many small bugs & reorganized. *
* 7/27/92 Juan Pineda Bug fix in SubBandSynthesis() *
*--------------------------------------------------------------------*
* 6/14/92 Juan Pineda Layer III decoding routines added. *
* Amit Gulati Follows CD 3-11172 rev2. Contains *
* hacks deal with evolving available *
* layerIII bitstreams. Some (minor) *
* modification of prior LI&II code. *
* 10/25/92 Amit Gulati Updated layerIII routines. Added code *
* for subblock_gain, switched block *
* modes, stereo pre-processing. *
* Corrected sign bits for huffman *
* decoding of quadruples region and *
* adjusted gain factor in III_dequant. *
* 11/21/92 Amit Gulati Several layerIII bugs fixed. *
* 12/15/92 Amit Gulati Corrected reordering (indexing) *
* Stan Searing within IMDCT routine. *
* 8/24/93 Masahiro Iwadare Included IS modification in Layer III.*
* Changed for 1 pass decoding. *
* 9/07/93 Toshiyuki Ishino Integrated Layer III with Ver 3.9. *
*--------------------------------------------------------------------*
* 11/20/93 Masahiro Iwadare Integrated Layer III with Ver 4.0. *
*--------------------------------------------------------------------*
* 7/14/94 Juergen Koller Bug fixes in Layer III code *
*--------------------------------------------------------------------*
* 08/11/94 IIS Bug fixes in Layer III code *
*--------------------------------------------------------------------*
* 9/20/94 Davis Pan Modification to avoid premature *
* synchword detection *
*--------------------------------------------------------------------*
* 11/09/94 Jon Rowlands Merged premature synchword detection *
* fix into layer III code version *
**********************************************************************/
#include "common.h"
#include "decoder.h"
#include "huffman.h"
/***************************************************************
/*
/* This module contains the core of the decoder ie all the
/* computational routines. (Layer I and II only)
/* Functions are common to both layer unless
/* otherwise specified.
/*
/***************************************************************/
/*****************************************************************
/*
/* The following routines decode the system information
/*
/****************************************************************/
/************ Layer I, Layer II & Layer III ******************/
void decode_info(bs, fr_ps)
Bit_stream_struc *bs;
frame_params *fr_ps;
{
unsigned int bits;
layer *hdr = fr_ps->header;
while( (bits=getbits(bs,8)) == 255); /*discard leading 0xFF's of syncword*/
hdr->bitrate_index = bits & 0xF;
bits = bits >> 4;
switch(bits) {
case 0:
hdr->version = 0;
hdr->lay = 4;
hdr->error_protection = 1;
break;
case 1:
hdr->version = 0;
hdr->lay = 4;
hdr->error_protection = 0;
break;
case 2:
hdr->version = 0;
hdr->lay = 3;
hdr->error_protection = 1;
break;
case 3:
hdr->version = 0;
hdr->lay = 3;
hdr->error_protection = 0;
break;
case 4:
hdr->version = 0;
hdr->lay = 2;
hdr->error_protection = 1;
break;
case 5:
hdr->version = 0;
hdr->lay = 2;
hdr->error_protection = 0;
break;
case 6:
hdr->version = 0;
hdr->lay = 1;
hdr->error_protection = 1;
break;
case 7:
hdr->version = 0;
hdr->lay = 1;
hdr->error_protection = 0;
break;
case 8:
hdr->version = 1;
hdr->lay = 4;
hdr->error_protection = 1;
break;
case 9:
hdr->version = 1;
hdr->lay = 4;
hdr->error_protection = 0;
break;
case 10:
hdr->version = 1;
hdr->lay = 3;
hdr->error_protection = 1;
break;
case 11:
hdr->version = 1;
hdr->lay = 3;
hdr->error_protection = 0;
break;
case 12:
hdr->version = 1;
hdr->lay = 2;
hdr->error_protection = 1;
break;
case 13:
hdr->version = 1;
hdr->lay = 2;
hdr->error_protection = 0;
break;
case 14:
hdr->version = 1;
hdr->lay = 1;
hdr->error_protection = 1;
break;
default:
hdr->version = 1;
hdr->lay = 1;
hdr->error_protection = 0;
}
hdr->sampling_frequency = getbits(bs,2);
hdr->padding = get1bit(bs);
hdr->extension = get1bit(bs);
hdr->mode = getbits(bs,2);
hdr->mode_ext = getbits(bs,2);
hdr->copyright = get1bit(bs);
hdr->original = get1bit(bs);
hdr->emphasis = getbits(bs,2);
}
/*******************************************************************
/*
/* The bit allocation information is decoded. Layer I
/* has 4 bit per subband whereas Layer II is Ws and bit rate
/* dependent.
/*
/********************************************************************/
/**************************** Layer II *************/
void II_decode_bitalloc(bs, bit_alloc, fr_ps)
Bit_stream_struc *bs;
unsigned int bit_alloc[2][SBLIMIT];
frame_params *fr_ps;
{
int i,j;
int stereo = fr_ps->stereo;
int sblimit = fr_ps->sblimit;
int jsbound = fr_ps->jsbound;
al_table *alloc = fr_ps->alloc;
for (i=0;istereo;
int sblimit = fr_ps->sblimit;
int jsbound = fr_ps->jsbound;
int b;
for (i=0;istereo;
int sblimit = fr_ps->sblimit;
for (i=0;istereo;
int sblimit = fr_ps->sblimit;
for (i=0;istereo;
int sblimit = fr_ps->sblimit;
int jsbound = fr_ps->jsbound;
unsigned int s;
for (i=0;istereo;
int sblimit = fr_ps->sblimit;
int jsbound = fr_ps->jsbound;
al_table *alloc = fr_ps->alloc;
for (i=0;i= jsbound) /* joint stereo : copy L to R */
for (k=0;k<3;k++) sample[1][k][i] = sample[0][k][i];
}
for (i=sblimit;istereo;
int sblimit = fr_ps->sblimit;
al_table *alloc = fr_ps->alloc;
for (i=0;i> x-1) & 1) == 1)
fraction[k][j][i] = 0.0;
else fraction[k][j][i] = -1.0;
/* Form a 2's complement sample */
fraction[k][j][i] += (double) (sample[k][j][i] & ((1<stereo;
int sblimit = fr_ps->sblimit;
for (i=0;i> nb-1) & 1) == 1) fraction[k][0][i] = 0.0;
else fraction[k][0][i] = -1.0;
fraction[k][0][i] += (double) (sample[k][0][i] & ((1<stereo;
int sblimit = fr_ps->sblimit;
for (i=0;istereo;
int sblimit = fr_ps->sblimit;
for (i=0;i= 0)
modf(filter[i][k]+0.5, &filter[i][k]);
else
modf(filter[i][k]-0.5, &filter[i][k]);
filter[i][k] *= 1e-9;
}
}
/***************************************************************
/*
/* Window the restored sample
/*
/***************************************************************/
/* read in synthesis window */
void read_syn_window(window)
double FAR window[HAN_SIZE];
{
int i,j[4];
FILE *fp;
double f[4];
char t[150];
if (!(fp = OpenTableFile("dewindow") )) {
printf("Please check synthesis window table 'dewindow'\n");
exit(1);
}
for (i=0;i<512;i+=4) {
fgets(t, 150, fp);
sscanf(t,"D[%d] = %lf D[%d] = %lf D[%d] = %lf D[%d] = %lf\n",
j, f,j+1,f+1,j+2,f+2,j+3,f+3);
if (i==j[0]) {
window[i] = f[0];
window[i+1] = f[1];
window[i+2] = f[2];
window[i+3] = f[3];
}
else {
printf("Check index in synthesis window table\n");
exit(1);
}
fgets(t,150,fp);
}
fclose(fp);
}
int SubBandSynthesis (bandPtr, channel, samples)
double *bandPtr;
int channel;
short *samples;
{
register int i,j,k;
register double *bufOffsetPtr, sum;
static int init = 1;
typedef double NN[64][32];
static NN FAR *filter;
typedef double BB[2][2*HAN_SIZE];
static BB FAR *buf;
static int bufOffset[2] = {64,64};
static double FAR *window;
int clip = 0; /* count & return how many samples clipped */
if (init) {
buf = (BB FAR *) mem_alloc(sizeof(BB),"BB");
filter = (NN FAR *) mem_alloc(sizeof(NN), "NN");
create_syn_filter(*filter);
window = (double FAR *) mem_alloc(sizeof(double) * HAN_SIZE, "WIN");
read_syn_window(window);
init = 0;
}
/* if (channel == 0) */
bufOffset[channel] = (bufOffset[channel] - 64) & 0x3ff;
bufOffsetPtr = &((*buf)[channel][bufOffset[channel]]);
for (i=0; i<64; i++) {
sum = 0;
for (k=0; k<32; k++)
sum += bandPtr[k] * (*filter)[i][k];
bufOffsetPtr[i] = sum;
}
/* S(i,j) = D(j+32i) * U(j+32i+((i+1)>>1)*64) */
/* samples(i,j) = MWindow(j+32i) * bufPtr(j+32i+((i+1)>>1)*64) */
for (j=0; j<32; j++) {
sum = 0;
for (i=0; i<16; i++) {
k = j + (i<<5);
sum += window[k] * (*buf) [channel] [( (k + ( ((i+1)>>1) <<6) ) +
bufOffset[channel]) & 0x3ff];
}
/* {long foo = (sum > 0) ? sum * SCALE + 0.5 : sum * SCALE - 0.5; */
{long foo = sum * SCALE;
if (foo >= (long) SCALE) {samples[j] = SCALE-1; ++clip;}
else if (foo < (long) -SCALE) {samples[j] = -SCALE; ++clip;}
else samples[j] = foo;
}
}
return(clip);
}
void out_fifo(pcm_sample, num, fr_ps, done, outFile, psampFrames)
short FAR pcm_sample[2][SSLIMIT][SBLIMIT];
int num;
frame_params *fr_ps;
int done;
FILE *outFile;
unsigned long *psampFrames;
{
int i,j,l;
int stereo = fr_ps->stereo;
int sblimit = fr_ps->sblimit;
static short int outsamp[1600];
static long k = 0;
if (!done)
for (i=0;istereo;
int num, done, i;
int samplesPerFrame, samplesPerSlot;
layer *hdr = fr_ps->header;
long offset;
short *temp;
num = 3;
if (hdr->lay == 1) num = 1;
samplesPerSlot = SBLIMIT * num * stereo;
samplesPerFrame = samplesPerSlot * 32;
if (error_count == 1) { /* replicate previous error_free frame */
done = 1;
/* flush out fifo */
out_fifo(pcm_sample, num, fr_ps, done, outFile, psampFrames);
/* go back to the beginning of the previous frame */
offset = sizeof(short int) * samplesPerFrame;
fseek(outFile, -offset, SEEK_CUR);
done = 0;
for (i = 0; i < SCALE_BLOCK; i++) {
fread(pcm_sample, 2, samplesPerSlot, outFile);
out_fifo(pcm_sample, num, fr_ps, done, outFile, psampFrames);
}
}
else{ /* mute the frame */
temp = (short*) pcm_sample;
done = 0;
for (i = 0; i < 2*3*SBLIMIT; i++)
*temp++ = MUTE; /* MUTE value is in decoder.h */
for (i = 0; i < SCALE_BLOCK; i++)
out_fifo(pcm_sample, num, fr_ps, done, outFile, psampFrames);
}
}
/************************* Layer III routines **********************/
void III_get_side_info(bs, si, fr_ps)
Bit_stream_struc *bs;
III_side_info_t *si;
frame_params *fr_ps;
{
int ch, gr, i;
int stereo = fr_ps->stereo;
si->main_data_begin = getbits(bs, 9);
if (stereo == 1)
si->private_bits = getbits(bs,5);
else si->private_bits = getbits(bs,3);
for (ch=0; chch[ch].scfsi[i] = get1bit(bs);
for (gr=0; gr<2; gr++) {
for (ch=0; chch[ch].gr[gr].part2_3_length = getbits(bs, 12);
si->ch[ch].gr[gr].big_values = getbits(bs, 9);
si->ch[ch].gr[gr].global_gain = getbits(bs, 8);
si->ch[ch].gr[gr].scalefac_compress = getbits(bs, 4);
si->ch[ch].gr[gr].window_switching_flag = get1bit(bs);
if (si->ch[ch].gr[gr].window_switching_flag) {
si->ch[ch].gr[gr].block_type = getbits(bs, 2);
si->ch[ch].gr[gr].mixed_block_flag = get1bit(bs);
for (i=0; i<2; i++)
si->ch[ch].gr[gr].table_select[i] = getbits(bs, 5);
for (i=0; i<3; i++)
si->ch[ch].gr[gr].subblock_gain[i] = getbits(bs, 3);
/* Set region_count parameters since they are implicit in this case. */
if (si->ch[ch].gr[gr].block_type == 0) {
printf("Side info bad: block_type == 0 in split block.\n");
exit(0);
}
else if (si->ch[ch].gr[gr].block_type == 2
&& si->ch[ch].gr[gr].mixed_block_flag == 0)
si->ch[ch].gr[gr].region0_count = 8; /* MI 9; */
else si->ch[ch].gr[gr].region0_count = 7; /* MI 8; */
si->ch[ch].gr[gr].region1_count = 20 -
si->ch[ch].gr[gr].region0_count;
}
else {
for (i=0; i<3; i++)
si->ch[ch].gr[gr].table_select[i] = getbits(bs, 5);
si->ch[ch].gr[gr].region0_count = getbits(bs, 4);
si->ch[ch].gr[gr].region1_count = getbits(bs, 3);
si->ch[ch].gr[gr].block_type = 0;
}
si->ch[ch].gr[gr].preflag = get1bit(bs);
si->ch[ch].gr[gr].scalefac_scale = get1bit(bs);
si->ch[ch].gr[gr].count1table_select = get1bit(bs);
}
}
}
void III_put_side_info(bs, si, fr_ps)
frame_params *fr_ps;
Bit_stream_struc *bs;
III_side_info_t *si;
{
int ch, gr, i;
int stereo = fr_ps->stereo;
putbits(bs, si->main_data_begin,9);
if (stereo == 1)
putbits(bs, si->private_bits, 5);
else putbits(bs, si->private_bits, 3);
for (ch=0; chch[ch].scfsi[i]);
for (gr=0; gr<2; gr++) {
for (ch=0; chch[ch].gr[gr].part2_3_length, 12);
putbits(bs, si->ch[ch].gr[gr].big_values, 9);
putbits(bs, si->ch[ch].gr[gr].global_gain, 8);
putbits(bs, si->ch[ch].gr[gr].scalefac_compress, 4);
put1bit(bs, si->ch[ch].gr[gr].window_switching_flag);
if (si->ch[ch].gr[gr].window_switching_flag) {
putbits(bs, si->ch[ch].gr[gr].block_type, 2);
put1bit(bs, si->ch[ch].gr[gr].mixed_block_flag);
for (i=0; i<2; i++)
putbits(bs, si->ch[ch].gr[gr].table_select[i], 5);
for (i=0; i<3; i++)
putbits(bs, si->ch[ch].gr[gr].subblock_gain[i], 3);
}
else {
for (i=0; i<3; i++)
putbits(bs, si->ch[ch].gr[gr].table_select[i], 5);
putbits(bs, si->ch[ch].gr[gr].region0_count, 4);
putbits(bs, si->ch[ch].gr[gr].region1_count, 3);
}
put1bit(bs, si->ch[ch].gr[gr].preflag);
put1bit(bs, si->ch[ch].gr[gr].scalefac_scale);
put1bit(bs, si->ch[ch].gr[gr].count1table_select);
}
}
}
struct {
int l[5];
int s[3];} sfbtable = {{0, 6, 11, 16, 21},
{0, 6, 12}};
int slen[2][16] = {{0, 0, 0, 0, 3, 1, 1, 1, 2, 2, 2, 3, 3, 3, 4, 4},
{0, 1, 2, 3, 0, 1, 2, 3, 1, 2, 3, 1, 2, 3, 2, 3}};
struct {
int l[23];
int s[14];} sfBandIndex[3] =
{{{0,4,8,12,16,20,24,30,36,44,52,62,74,90,110,134,162,196,238,288,342,418,576},
{0,4,8,12,16,22,30,40,52,66,84,106,136,192}},
{{0,4,8,12,16,20,24,30,36,42,50,60,72,88,106,128,156,190,230,276,330,384,576},
{0,4,8,12,16,22,28,38,50,64,80,100,126,192}},
{{0,4,8,12,16,20,24,30,36,44,54,66,82,102,126,156,194,240,296,364,448,550,576},
{0,4,8,12,16,22,30,42,58,78,104,138,180,192}}};
void III_get_scale_factors(scalefac, si, gr, ch, fr_ps)
III_scalefac_t *scalefac;
III_side_info_t *si;
int gr, ch;
frame_params *fr_ps;
{
int sfb, i, window;
struct gr_info_s *gr_info = &(si->ch[ch].gr[gr]);
if (gr_info->window_switching_flag && (gr_info->block_type == 2)) {
if (gr_info->mixed_block_flag) { /* MIXED */ /* NEW - ag 11/25 */
for (sfb = 0; sfb < 8; sfb++)
(*scalefac)[ch].l[sfb] = hgetbits(
slen[0][gr_info->scalefac_compress]);
for (sfb = 3; sfb < 6; sfb++)
for (window=0; window<3; window++)
(*scalefac)[ch].s[window][sfb] = hgetbits(
slen[0][gr_info->scalefac_compress]);
for (sfb = 6; sfb < 12; sfb++)
for (window=0; window<3; window++)
(*scalefac)[ch].s[window][sfb] = hgetbits(
slen[1][gr_info->scalefac_compress]);
for (sfb=12,window=0; window<3; window++)
(*scalefac)[ch].s[window][sfb] = 0;
}
else { /* SHORT*/
for (i=0; i<2; i++)
for (sfb = sfbtable.s[i]; sfb < sfbtable.s[i+1]; sfb++)
for (window=0; window<3; window++)
(*scalefac)[ch].s[window][sfb] = hgetbits(
slen[i][gr_info->scalefac_compress]);
for (sfb=12,window=0; window<3; window++)
(*scalefac)[ch].s[window][sfb] = 0;
}
}
else { /* LONG types 0,1,3 */
for (i=0; i<4; i++) {
if ((si->ch[ch].scfsi[i] == 0) || (gr == 0))
for (sfb = sfbtable.l[i]; sfb < sfbtable.l[i+1]; sfb++)
(*scalefac)[ch].l[sfb] = hgetbits(
slen[(i<2)?0:1][gr_info->scalefac_compress]);
}
(*scalefac)[ch].l[22] = 0;
}
}
/* Already declared in huffman.c
struct huffcodetab ht[HTN];
*/
int huffman_initialized = FALSE;
void initialize_huffman() {
FILE *fi;
if (huffman_initialized) return;
if (!(fi = OpenTableFile("huffdec") )) {
printf("Please check huffman table 'huffdec'\n");
exit(1);
}
if (fi==NULL) {
fprintf(stderr,"decoder table open error\n");
exit(3);
}
if (read_decoder_table(fi) != HTN) {
fprintf(stderr,"decoder table read error\n");
exit(4);
}
huffman_initialized = TRUE;
}
III_hufman_decode(is, si, ch, gr, part2_start, fr_ps)
long int is[SBLIMIT][SSLIMIT];
III_side_info_t *si;
int gr, ch, part2_start;
frame_params *fr_ps;
{
int i, x, y;
int v, w;
struct huffcodetab *h;
int region1Start;
int region2Start;
int bt = (*si).ch[ch].gr[gr].window_switching_flag && ((*si).ch[ch].gr[gr].block_type == 2);
initialize_huffman();
/* Find region boundary for short block case. */
if ( ((*si).ch[ch].gr[gr].window_switching_flag) &&
((*si).ch[ch].gr[gr].block_type == 2) ) {
/* Region2. */
region1Start = 36; /* sfb[9/3]*3=36 */
region2Start = 576; /* No Region2 for short block case. */
}
else { /* Find region boundary for long block case. */
region1Start = sfBandIndex[fr_ps->header->sampling_frequency]
.l[(*si).ch[ch].gr[gr].region0_count + 1]; /* MI */
region2Start = sfBandIndex[fr_ps->header->sampling_frequency]
.l[(*si).ch[ch].gr[gr].region0_count +
(*si).ch[ch].gr[gr].region1_count + 2]; /* MI */
}
/* Read bigvalues area. */
for (i=0; i<(*si).ch[ch].gr[gr].big_values*2; i+=2) {
if (i part2_start + (*si).ch[ch].gr[gr].part2_3_length)
{ i -=4;
rewindNbits(hsstell()-part2_start - (*si).ch[ch].gr[gr].part2_3_length);
}
/* Dismiss stuffing Bits */
if ( hsstell() < part2_start + (*si).ch[ch].gr[gr].part2_3_length )
hgetbits( part2_start + (*si).ch[ch].gr[gr].part2_3_length - hsstell());
/* Zero out rest. */
for (; iheader->sampling_frequency;
int stereo = fr_ps->stereo;
int next_cb_boundary, cb_begin, cb_width, sign;
/* choose correct scalefactor band per block type, initalize boundary */
if (gr_info->window_switching_flag && (gr_info->block_type == 2) )
if (gr_info->mixed_block_flag)
next_cb_boundary=sfBandIndex[sfreq].l[1]; /* LONG blocks: 0,1,3 */
else {
next_cb_boundary=sfBandIndex[sfreq].s[1]*3; /* pure SHORT block */
cb_width = sfBandIndex[sfreq].s[1];
cb_begin = 0;
}
else
next_cb_boundary=sfBandIndex[sfreq].l[1]; /* LONG blocks: 0,1,3 */
/* apply formula per block type */
for (sb=0 ; sb < SBLIMIT ; sb++)
for (ss=0 ; ss < SSLIMIT ; ss++) {
if ( (sb*18)+ss == next_cb_boundary) { /* Adjust critical band boundary */
if (gr_info->window_switching_flag && (gr_info->block_type == 2)) {
if (gr_info->mixed_block_flag) {
if (((sb*18)+ss) == sfBandIndex[sfreq].l[8]) {
next_cb_boundary=sfBandIndex[sfreq].s[4]*3;
cb = 3;
cb_width = sfBandIndex[sfreq].s[cb+1] -
sfBandIndex[sfreq].s[cb];
cb_begin = sfBandIndex[sfreq].s[cb]*3;
}
else if (((sb*18)+ss) < sfBandIndex[sfreq].l[8])
next_cb_boundary = sfBandIndex[sfreq].l[(++cb)+1];
else {
next_cb_boundary = sfBandIndex[sfreq].s[(++cb)+1]*3;
cb_width = sfBandIndex[sfreq].s[cb+1] -
sfBandIndex[sfreq].s[cb];
cb_begin = sfBandIndex[sfreq].s[cb]*3;
}
}
else {
next_cb_boundary = sfBandIndex[sfreq].s[(++cb)+1]*3;
cb_width = sfBandIndex[sfreq].s[cb+1] -
sfBandIndex[sfreq].s[cb];
cb_begin = sfBandIndex[sfreq].s[cb]*3;
}
}
else /* long blocks */
next_cb_boundary = sfBandIndex[sfreq].l[(++cb)+1];
}
/* Compute overall (global) scaling. */
xr[sb][ss] = pow( 2.0 , (0.25 * (gr_info->global_gain - 210.0)));
/* Do long/short dependent scaling operations. */
if (gr_info->window_switching_flag && (
((gr_info->block_type == 2) && (gr_info->mixed_block_flag == 0)) ||
((gr_info->block_type == 2) && gr_info->mixed_block_flag && (sb >= 2)) )) {
xr[sb][ss] *= pow(2.0, 0.25 * -8.0 *
gr_info->subblock_gain[(((sb*18)+ss) - cb_begin)/cb_width]);
xr[sb][ss] *= pow(2.0, 0.25 * -2.0 * (1.0+gr_info->scalefac_scale)
* (*scalefac)[ch].s[(((sb*18)+ss) - cb_begin)/cb_width][cb]);
}
else { /* LONG block types 0,1,3 & 1st 2 subbands of switched blocks */
xr[sb][ss] *= pow(2.0, -0.5 * (1.0+gr_info->scalefac_scale)
* ((*scalefac)[ch].l[cb]
+ gr_info->preflag * pretab[cb]));
}
/* Scale quantized value. */
sign = (is[sb][ss]<0) ? 1 : 0;
xr[sb][ss] *= pow( (double) abs(is[sb][ss]), ((double)4.0/3.0) );
if (sign) xr[sb][ss] = -xr[sb][ss];
}
}
III_reorder (xr, ro, gr_info, fr_ps)
double xr[SBLIMIT][SSLIMIT];
double ro[SBLIMIT][SSLIMIT];
struct gr_info_s *gr_info;
frame_params *fr_ps;
{
int sfreq=fr_ps->header->sampling_frequency;
int sfb, sfb_start, sfb_lines;
int sb, ss, window, freq, src_line, des_line;
for(sb=0;sbwindow_switching_flag && (gr_info->block_type == 2)) {
if (gr_info->mixed_block_flag) {
/* NO REORDER FOR LOW 2 SUBBANDS */
for (sb=0 ; sb < 2 ; sb++)
for (ss=0 ; ss < SSLIMIT ; ss++) {
ro[sb][ss] = xr[sb][ss];
}
/* REORDERING FOR REST SWITCHED SHORT */
for(sfb=3,sfb_start=sfBandIndex[sfreq].s[3],
sfb_lines=sfBandIndex[sfreq].s[4] - sfb_start;
sfb < 13; sfb++,sfb_start=sfBandIndex[sfreq].s[sfb],
(sfb_lines=sfBandIndex[sfreq].s[sfb+1] - sfb_start))
for(window=0; window<3; window++)
for(freq=0;freqheader->sampling_frequency;
int stereo = fr_ps->stereo;
int ms_stereo = (fr_ps->header->mode == MPG_MD_JOINT_STEREO) &&
(fr_ps->header->mode_ext & 0x2);
int i_stereo = (fr_ps->header->mode == MPG_MD_JOINT_STEREO) &&
(fr_ps->header->mode_ext & 0x1);
int js_bound; /* frequency line that marks the beggining of the zero part */
int sfb,next_sfb_boundary;
int i,j,sb,ss,ch,is_pos[576];
double is_ratio[576];
/* intialization */
for ( i=0; i<576; i++ )
is_pos[i] = 7;
if ((stereo == 2) && i_stereo )
{ if (gr_info->window_switching_flag && (gr_info->block_type == 2))
{ if( gr_info->mixed_block_flag )
{ int max_sfb = 0;
for ( j=0; j<3; j++ )
{ int sfbcnt;
sfbcnt = 2;
for( sfb=12; sfb >=3; sfb-- )
{ int lines;
lines = sfBandIndex[sfreq].s[sfb+1]-sfBandIndex[sfreq].s[sfb];
i = 3*sfBandIndex[sfreq].s[sfb] + (j+1) * lines - 1;
while ( lines > 0 )
{ if ( xr[1][i/SSLIMIT][i%SSLIMIT] != 0.0 )
{ sfbcnt = sfb;
sfb = -10;
lines = -10;
}
lines--;
i--;
}
}
sfb = sfbcnt + 1;
if ( sfb > max_sfb )
max_sfb = sfb;
while( sfb<12 )
{ sb = sfBandIndex[sfreq].s[sfb+1]-sfBandIndex[sfreq].s[sfb];
i = 3*sfBandIndex[sfreq].s[sfb] + j * sb;
for ( ; sb > 0; sb--)
{ is_pos[i] = (*scalefac)[1].s[j][sfb];
if ( is_pos[i] != 7 )
is_ratio[i] = tan( is_pos[i] * (PI / 12));
i++;
}
sfb++;
}
sb = sfBandIndex[sfreq].s[11]-sfBandIndex[sfreq].s[10];
sfb = 3*sfBandIndex[sfreq].s[10] + j * sb;
sb = sfBandIndex[sfreq].s[12]-sfBandIndex[sfreq].s[11];
i = 3*sfBandIndex[sfreq].s[11] + j * sb;
for ( ; sb > 0; sb-- )
{ is_pos[i] = is_pos[sfb];
is_ratio[i] = is_ratio[sfb];
i++;
}
}
if ( max_sfb <= 3 )
{ i = 2;
ss = 17;
sb = -1;
while ( i >= 0 )
{ if ( xr[1][i][ss] != 0.0 )
{ sb = i*18+ss;
i = -1;
} else
{ ss--;
if ( ss < 0 )
{ i--;
ss = 17;
}
}
}
i = 0;
while ( sfBandIndex[sfreq].l[i] <= sb )
i++;
sfb = i;
i = sfBandIndex[sfreq].l[i];
for ( ; sfb<8; sfb++ )
{ sb = sfBandIndex[sfreq].l[sfb+1]-sfBandIndex[sfreq].l[sfb];
for ( ; sb > 0; sb--)
{ is_pos[i] = (*scalefac)[1].l[sfb];
if ( is_pos[i] != 7 )
is_ratio[i] = tan( is_pos[i] * (PI / 12));
i++;
}
}
}
} else
{ for ( j=0; j<3; j++ )
{ int sfbcnt;
sfbcnt = -1;
for( sfb=12; sfb >=0; sfb-- )
{ int lines;
lines = sfBandIndex[sfreq].s[sfb+1]-sfBandIndex[sfreq].s[sfb];
i = 3*sfBandIndex[sfreq].s[sfb] + (j+1) * lines - 1;
while ( lines > 0 )
{ if ( xr[1][i/SSLIMIT][i%SSLIMIT] != 0.0 )
{ sfbcnt = sfb;
sfb = -10;
lines = -10;
}
lines--;
i--;
}
}
sfb = sfbcnt + 1;
while( sfb<12 )
{ sb = sfBandIndex[sfreq].s[sfb+1]-sfBandIndex[sfreq].s[sfb];
i = 3*sfBandIndex[sfreq].s[sfb] + j * sb;
for ( ; sb > 0; sb--)
{ is_pos[i] = (*scalefac)[1].s[j][sfb];
if ( is_pos[i] != 7 )
is_ratio[i] = tan( is_pos[i] * (PI / 12));
i++;
}
sfb++;
}
sb = sfBandIndex[sfreq].s[11]-sfBandIndex[sfreq].s[10];
sfb = 3*sfBandIndex[sfreq].s[10] + j * sb;
sb = sfBandIndex[sfreq].s[12]-sfBandIndex[sfreq].s[11];
i = 3*sfBandIndex[sfreq].s[11] + j * sb;
for ( ; sb > 0; sb-- )
{ is_pos[i] = is_pos[sfb];
is_ratio[i] = is_ratio[sfb];
i++;
}
}
}
} else
{ i = 31;
ss = 17;
sb = 0;
while ( i >= 0 )
{ if ( xr[1][i][ss] != 0.0 )
{ sb = i*18+ss;
i = -1;
} else
{ ss--;
if ( ss < 0 )
{ i--;
ss = 17;
}
}
}
i = 0;
while ( sfBandIndex[sfreq].l[i] <= sb )
i++;
sfb = i;
i = sfBandIndex[sfreq].l[i];
for ( ; sfb<21; sfb++ )
{ sb = sfBandIndex[sfreq].l[sfb+1] - sfBandIndex[sfreq].l[sfb];
for ( ; sb > 0; sb--)
{ is_pos[i] = (*scalefac)[1].l[sfb];
if ( is_pos[i] != 7 )
is_ratio[i] = tan( is_pos[i] * (PI / 12));
i++;
}
}
sfb = sfBandIndex[sfreq].l[20];
for ( sb = 576 - sfBandIndex[sfreq].l[21]; sb > 0; sb-- )
{ is_pos[i] = is_pos[sfb];
is_ratio[i] = is_ratio[sfb];
i++;
}
}
}
for(ch=0;ch<2;ch++)
for(sb=0;sbwindow_switching_flag && (gr_info->block_type == 2) &&
!gr_info->mixed_block_flag ) return;
if ( gr_info->window_switching_flag && gr_info->mixed_block_flag &&
(gr_info->block_type == 2))
sblim = 1;
else
sblim = SBLIMIT-1;
/* 31 alias-reduction operations between each pair of sub-bands */
/* with 8 butterflies between each pair */
for(sb=0;sbwindow_switching_flag && gr_info->mixed_block_flag &&
(sb < 2)) ? 0 : gr_info->block_type;
inv_mdct( fsIn, rawout, bt);
/* overlap addition */
for(ss=0; ssbitrate_index])
/ s_freq[fr_ps.header->sampling_frequency];
if (fr_ps.header->padding) nSlots++;
nSlots -= 4;
if (fr_ps.header->error_protection) nSlots -= 2;
if (fr_ps.stereo == 1) nSlots -= 17; else nSlots -=32;
return(nSlots);
}