📄 l3bitstream.c
字号:
/**********************************************************************
* ISO MPEG Audio Subgroup Software Simulation Group (1996)
* ISO 13818-3 MPEG-2 Audio Encoder - Lower Sampling Frequency Extension
*
**********************************************************************/
/*
Revision History:
Date Programmer Comment
========== ========================= ===============================
1995/08/06 mc@fivebats.com created
1995/09/06 mc@fivebats.com modified to use formatBitstream
*/
#include <stdlib.h>
#include "lame.h"
#include "l3bitstream.h" /* the public interface */
#include "encoder.h"
#include "quantize.h"
#include "quantize-pvt.h"
#include "formatBitstream.h"
#include "tables.h"
#include <assert.h>
#include "l3bitstream-pvt.h"
static Bit_stream_struc *bs = NULL;
BF_FrameData *frameData = NULL;
BF_FrameResults *frameResults = NULL;
int PartHoldersInitialized = 0;
BF_PartHolder *headerPH;
BF_PartHolder *frameSIPH;
BF_PartHolder *channelSIPH[ MAX_CHANNELS ];
BF_PartHolder *spectrumSIPH[ MAX_GRANULES ][ MAX_CHANNELS ];
BF_PartHolder *scaleFactorsPH[ MAX_GRANULES ][ MAX_CHANNELS ];
BF_PartHolder *codedDataPH[ MAX_GRANULES ][ MAX_CHANNELS ];
BF_PartHolder *userSpectrumPH[ MAX_GRANULES ][ MAX_CHANNELS ];
BF_PartHolder *userFrameDataPH;
void putMyBits( u_int val, u_int len )
{
putbits( bs, val, len );
}
/*
III_format_bitstream()
This is called after a frame of audio has been quantized and coded.
It will write the encoded audio to the bitstream. Note that
from a layer3 encoder's perspective the bit stream is primarily
a series of main_data() blocks, with header and side information
inserted at the proper locations to maintain framing. (See Figure A.7
in the IS).
*/
void
III_format_bitstream( lame_global_flags *gfp,
int bitsPerFrame,
int l3_enc[2][2][576],
III_side_info_t *l3_side,
III_scalefac_t scalefac[2][2],
Bit_stream_struc *in_bs)
{
int gr, ch;
bs = in_bs;
if ( frameData == NULL )
{
frameData = calloc( 1,sizeof *frameData);
assert( frameData );
}
if ( frameResults == NULL )
{
frameResults = calloc( 1,sizeof *frameResults);
assert( frameResults );
}
if ( !PartHoldersInitialized )
{
headerPH = BF_newPartHolder( 14 );
frameSIPH = BF_newPartHolder( 12 );
for ( ch = 0; ch < MAX_CHANNELS; ch++ )
channelSIPH[ch] = BF_newPartHolder( 8 );
for ( gr = 0; gr < MAX_GRANULES; gr++ )
for ( ch = 0; ch < MAX_CHANNELS; ch++ )
{
spectrumSIPH[gr][ch] = BF_newPartHolder( 32 );
scaleFactorsPH[gr][ch] = BF_newPartHolder( 64 );
codedDataPH[gr][ch] = BF_newPartHolder( 576 );
userSpectrumPH[gr][ch] = BF_newPartHolder( 4 );
}
userFrameDataPH = BF_newPartHolder( 8 );
PartHoldersInitialized = 1;
}
encodeSideInfo( gfp,l3_side );
encodeMainData( gfp,l3_enc, l3_side, scalefac );
drain_into_ancillary_data( l3_side->resvDrain );
/*
Put frameData together for the call
to BitstreamFrame()
*/
frameData->frameLength = bitsPerFrame;
frameData->nGranules = gfp->mode_gr;
frameData->nChannels = gfp->stereo;
frameData->header = headerPH->part;
frameData->frameSI = frameSIPH->part;
for ( ch = 0; ch < gfp->stereo; ch++ )
frameData->channelSI[ch] = channelSIPH[ch]->part;
for ( gr = 0; gr < gfp->mode_gr; gr++ )
for ( ch = 0; ch < gfp->stereo; ch++ )
{
frameData->spectrumSI[gr][ch] = spectrumSIPH[gr][ch]->part;
frameData->scaleFactors[gr][ch] = scaleFactorsPH[gr][ch]->part;
frameData->codedData[gr][ch] = codedDataPH[gr][ch]->part;
frameData->userSpectrum[gr][ch] = userSpectrumPH[gr][ch]->part;
}
frameData->userFrameData = userFrameDataPH->part;
BF_BitstreamFrame( frameData, frameResults );
/* we set this here -- it will be tested in the next loops iteration */
l3_side->main_data_begin = frameResults->nextBackPtr;
}
void
III_FlushBitstream(void)
{
if (PartHoldersInitialized!=0)
BF_FlushBitstream( frameData, frameResults );
}
static unsigned slen1_tab[16] = { 0, 0, 0, 0, 3, 1, 1, 1, 2, 2, 2, 3, 3, 3, 4, 4 };
static unsigned slen2_tab[16] = { 0, 1, 2, 3, 0, 1, 2, 3, 1, 2, 3, 1, 2, 3, 2, 3 };
static void
encodeMainData( lame_global_flags *gfp,
int l3_enc[2][2][576],
III_side_info_t *si,
III_scalefac_t scalefac[2][2] )
{
int i, gr, ch, sfb, window;
for ( gr = 0; gr < gfp->mode_gr; gr++ )
for ( ch = 0; ch < gfp->stereo; ch++ )
scaleFactorsPH[gr][ch]->part->nrEntries = 0;
for ( gr = 0; gr < gfp->mode_gr; gr++ )
for ( ch = 0; ch < gfp->stereo; ch++ )
codedDataPH[gr][ch]->part->nrEntries = 0;
if ( gfp->version == 1 )
{ /* MPEG 1 */
for ( gr = 0; gr < 2; gr++ )
{
for ( ch = 0; ch < gfp->stereo; ch++ )
{
BF_PartHolder **pph = &scaleFactorsPH[gr][ch];
gr_info *gi = &(si->gr[gr].ch[ch].tt);
unsigned slen1 = slen1_tab[ gi->scalefac_compress ];
unsigned slen2 = slen2_tab[ gi->scalefac_compress ];
int *ix = &l3_enc[gr][ch][0];
if (gi->block_type == SHORT_TYPE)
{
#ifdef ALLOW_MIXED
if ( gi->mixed_block_flag )
{
for ( sfb = 0; sfb < 8; sfb++ )
*pph = BF_addEntry( *pph, scalefac[gr][ch].l[sfb], slen1 );
for ( sfb = 3; sfb < 6; sfb++ )
for ( window = 0; window < 3; window++ )
*pph = BF_addEntry( *pph, scalefac[gr][ch].s[sfb][window], slen1 );
for ( sfb = 6; sfb < 12; sfb++ )
for ( window = 0; window < 3; window++ )
*pph = BF_addEntry( *pph, scalefac[gr][ch].s[sfb][window], slen2 );
}
else
#endif
{
for ( sfb = 0; sfb < 6; sfb++ )
for ( window = 0; window < 3; window++ )
*pph = BF_addEntry( *pph, scalefac[gr][ch].s[sfb][window], slen1 );
for ( sfb = 6; sfb < 12; sfb++ )
for ( window = 0; window < 3; window++ )
*pph = BF_addEntry( *pph, scalefac[gr][ch].s[sfb][window], slen2 );
}
}
else
{
if ( (gr == 0) || (si->scfsi[ch][0] == 0) )
for ( sfb = 0; sfb < 6; sfb++ )
*pph = BF_addEntry( *pph, scalefac[gr][ch].l[sfb], slen1 );
if ( (gr == 0) || (si->scfsi[ch][1] == 0) )
for ( sfb = 6; sfb < 11; sfb++ )
*pph = BF_addEntry( *pph, scalefac[gr][ch].l[sfb], slen1 );
if ( (gr == 0) || (si->scfsi[ch][2] == 0) )
for ( sfb = 11; sfb < 16; sfb++ )
*pph = BF_addEntry( *pph, scalefac[gr][ch].l[sfb], slen2 );
if ( (gr == 0) || (si->scfsi[ch][3] == 0) )
for ( sfb = 16; sfb < 21; sfb++ )
*pph = BF_addEntry( *pph, scalefac[gr][ch].l[sfb], slen2 );
}
Huffmancodebits( &codedDataPH[gr][ch], ix, gi );
} /* for ch */
} /* for gr */
}
else
{ /* MPEG 2 */
gr = 0;
for ( ch = 0; ch < gfp->stereo; ch++ )
{
BF_PartHolder **pph = &scaleFactorsPH[gr][ch];
gr_info *gi = &(si->gr[gr].ch[ch].tt);
int *ix = &l3_enc[gr][ch][0];
int sfb_partition;
assert( gi->sfb_partition_table );
if (gi->block_type == SHORT_TYPE)
{
#ifdef ALLOW_MIXED
if ( gi->mixed_block_flag )
{
sfb_partition = 0;
for ( sfb = 0; sfb < 8; sfb++ )
*pph = BF_addEntry( *pph, scalefac[gr][ch].l[sfb], gi->slen[sfb_partition] );
for ( sfb = 3, sfb_partition = 1; sfb_partition < 4; sfb_partition++ )
{
int sfbs = gi->sfb_partition_table[ sfb_partition ] / 3;
int slen = gi->slen[ sfb_partition ];
for ( i = 0; i < sfbs; i++, sfb++ )
for ( window = 0; window < 3; window++ )
*pph = BF_addEntry( *pph, scalefac[gr][ch].s[sfb][window], slen );
}
}
else
#endif
{
for ( sfb = 0, sfb_partition = 0; sfb_partition < 4; sfb_partition++ )
{
int sfbs = gi->sfb_partition_table[ sfb_partition ] / 3;
int slen = gi->slen[ sfb_partition ];
for ( i = 0; i < sfbs; i++, sfb++ )
for ( window = 0; window < 3; window++ )
*pph = BF_addEntry( *pph, scalefac[gr][ch].s[sfb][window], slen );
}
}
}
else
{
for ( sfb = 0, sfb_partition = 0; sfb_partition < 4; sfb_partition++ )
{
int sfbs = gi->sfb_partition_table[ sfb_partition ];
int slen = gi->slen[ sfb_partition ];
for ( i = 0; i < sfbs; i++, sfb++ )
*pph = BF_addEntry( *pph, scalefac[gr][ch].l[sfb], slen );
}
}
Huffmancodebits( &codedDataPH[gr][ch], ix, gi );
} /* for ch */
}
} /* main_data */
static unsigned int crc = 0; /* (jo) current crc */
/* (jo) this wrapper function for BF_addEntry() updates also the crc */
static BF_PartHolder *CRC_BF_addEntry( BF_PartHolder *thePH, u_int value, u_int length )
{
u_int bit = 1 << length;
while((bit >>= 1)){
crc <<= 1;
if (!(crc & 0x10000) ^ !(value & bit))
crc ^= CRC16_POLYNOMIAL;
}
crc &= 0xffff;
return BF_addEntry(thePH, value, length);
}
static int encodeSideInfo( lame_global_flags *gfp,III_side_info_t *si )
{
int gr, ch, scfsi_band, region, window, bits_sent;
crc = 0xffff; /* (jo) init crc16 for error_protection */
headerPH->part->nrEntries = 0;
headerPH = BF_addEntry( headerPH, 0xfff, 12 );
headerPH = BF_addEntry( headerPH, gfp->version, 1 );
headerPH = BF_addEntry( headerPH, 1, 2 );
headerPH = BF_addEntry( headerPH, !gfp->error_protection, 1 );
/* (jo) from now on call the CRC_BF_addEntry() wrapper to update crc */
headerPH = CRC_BF_addEntry( headerPH, gfp->bitrate_index, 4 );
headerPH = CRC_BF_addEntry( headerPH, gfp->samplerate_index, 2 );
headerPH = CRC_BF_addEntry( headerPH, gfp->padding, 1 );
headerPH = CRC_BF_addEntry( headerPH, gfp->extension, 1 );
headerPH = CRC_BF_addEntry( headerPH, gfp->mode, 2 );
headerPH = CRC_BF_addEntry( headerPH, gfp->mode_ext, 2 );
headerPH = CRC_BF_addEntry( headerPH, gfp->copyright, 1 );
headerPH = CRC_BF_addEntry( headerPH, gfp->original, 1 );
headerPH = CRC_BF_addEntry( headerPH, gfp->emphasis, 2 );
bits_sent = 32;
/* (jo) see below for BF_addEntry( headerPH, crc, 16 ); */
frameSIPH->part->nrEntries = 0;
for (ch = 0; ch < gfp->stereo; ch++ )
channelSIPH[ch]->part->nrEntries = 0;
for ( gr = 0; gr < gfp->mode_gr; gr++ )
for ( ch = 0; ch < gfp->stereo; ch++ )
spectrumSIPH[gr][ch]->part->nrEntries = 0;
if ( gfp->version == 1 )
{ /* MPEG1 */
frameSIPH = CRC_BF_addEntry( frameSIPH, si->main_data_begin, 9 );
if ( gfp->stereo == 2 )
frameSIPH = CRC_BF_addEntry( frameSIPH, si->private_bits, 3 );
else
frameSIPH = CRC_BF_addEntry( frameSIPH, si->private_bits, 5 );
for ( ch = 0; ch < gfp->stereo; ch++ )
for ( scfsi_band = 0; scfsi_band < 4; scfsi_band++ )
{
BF_PartHolder **pph = &channelSIPH[ch];
*pph = CRC_BF_addEntry( *pph, si->scfsi[ch][scfsi_band], 1 );
}
for ( gr = 0; gr < 2; gr++ )
for ( ch = 0; ch < gfp->stereo; ch++ )
{
BF_PartHolder **pph = &spectrumSIPH[gr][ch];
gr_info *gi = &(si->gr[gr].ch[ch].tt);
*pph = CRC_BF_addEntry( *pph, gi->part2_3_length, 12 );
*pph = CRC_BF_addEntry( *pph, gi->big_values, 9 );
*pph = CRC_BF_addEntry( *pph, gi->global_gain, 8 );
*pph = CRC_BF_addEntry( *pph, gi->scalefac_compress, 4 );
*pph = CRC_BF_addEntry( *pph, gi->window_switching_flag, 1 );
if ( gi->window_switching_flag )
{
*pph = CRC_BF_addEntry( *pph, gi->block_type, 2 );
*pph = CRC_BF_addEntry( *pph, gi->mixed_block_flag, 1 );
for ( region = 0; region < 2; region++ )
*pph = CRC_BF_addEntry( *pph, gi->table_select[region], 5 );
for ( window = 0; window < 3; window++ )
*pph = CRC_BF_addEntry( *pph, gi->subblock_gain[window], 3 );
}
else
{
assert( gi->block_type == NORM_TYPE );
for ( region = 0; region < 3; region++ )
*pph = CRC_BF_addEntry( *pph, gi->table_select[region], 5 );
*pph = CRC_BF_addEntry( *pph, gi->region0_count, 4 );
*pph = CRC_BF_addEntry( *pph, gi->region1_count, 3 );
}
*pph = CRC_BF_addEntry( *pph, gi->preflag, 1 );
*pph = CRC_BF_addEntry( *pph, gi->scalefac_scale, 1 );
*pph = CRC_BF_addEntry( *pph, gi->count1table_select, 1 );
}
if ( gfp->stereo == 2 )
bits_sent += 256;
else
bits_sent += 136;
}
else
{ /* MPEG2 */
frameSIPH = CRC_BF_addEntry( frameSIPH, si->main_data_begin, 8 );
if ( gfp->stereo == 2 )
frameSIPH = CRC_BF_addEntry( frameSIPH, si->private_bits, 2 );
else
frameSIPH = CRC_BF_addEntry( frameSIPH, si->private_bits, 1 );
gr = 0;
for ( ch = 0; ch < gfp->stereo; ch++ )
{
BF_PartHolder **pph = &spectrumSIPH[gr][ch];
gr_info *gi = &(si->gr[gr].ch[ch].tt);
*pph = CRC_BF_addEntry( *pph, gi->part2_3_length, 12 );
*pph = CRC_BF_addEntry( *pph, gi->big_values, 9 );
*pph = CRC_BF_addEntry( *pph, gi->global_gain, 8 );
*pph = CRC_BF_addEntry( *pph, gi->scalefac_compress, 9 );
*pph = CRC_BF_addEntry( *pph, gi->window_switching_flag, 1 );
if ( gi->window_switching_flag )
{
*pph = CRC_BF_addEntry( *pph, gi->block_type, 2 );
*pph = CRC_BF_addEntry( *pph, gi->mixed_block_flag, 1 );
for ( region = 0; region < 2; region++ )
*pph = CRC_BF_addEntry( *pph, gi->table_select[region], 5 );
for ( window = 0; window < 3; window++ )
*pph = CRC_BF_addEntry( *pph, gi->subblock_gain[window], 3 );
}
else
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -