📄 chan_enc.c
字号:
static void Line_Pack_Channel( LINEDEF *Line, char *Vout, Word16 FrType)
{
int i ;
int BitCount ;
Word16 InfoBitStream_tmp[195] ;
Word16 *Bsp = InfoBitStream_tmp ;
Word32 Temp ;
static Word16 MapIndexMamp[24]={0,1,2,3,4,5,6, 7, 8, 9,10,11,12,13,
14,15,16,17,18,19,20,21,22,23};
/* Clear the output vector */
for ( i = 0 ; i < 25 ; i ++ )
Vout[i] = 0 ;
/*
Add the coder rate info and the VAD status to the 2 msb
of the first word of the frame.
The signalling is as follows:
00 : High Rate
01 : Low Rate
10 : Silence frame
11 : Reserved for future use
*/
Temp = 2L ;
if ( FrType < 2 ) {
if ( FrType == 0)
Temp = 0x00000000L ;
else
Temp = 0x00000001L ;
}
/* Serialize Control info */
Bsp = Par2Ser( Temp, Bsp, 2 ) ;
/* 24 bit LspId */
Temp = (*Line).LspId ;
Bsp = Par2Ser( Temp, Bsp, 24 ) ;
/* Check for Speech/NonSpeech case */
if ( FrType < 2 ) {
/*
Do the part common to both rates
*/
/* Adaptive code book lags */
Temp = (Word32) (*Line).Olp[0] - (Word32) PitchMin ;
Bsp = Par2Ser( Temp, Bsp, 7 ) ;
Temp = (Word32) (*Line).Sfs[1].AcLg ;
Bsp = Par2Ser( Temp, Bsp, 2 ) ;
Temp = (Word32) (*Line).Olp[1] - (Word32) PitchMin ;
Bsp = Par2Ser( Temp, Bsp, 7 ) ;
Temp = (Word32) (*Line).Sfs[3].AcLg ;
Bsp = Par2Ser( Temp, Bsp, 2 ) ;
/* Write 8 bit index of adaptive gains */
/* ----------------------------------- */
for ( i = 0 ; i < SubFrames ; i ++ ) {
Temp = (*Line).Sfs[i].AcGn;
if ((FrType == 0 )&&((*Line).Olp[i>>1] < (SubFrLen-2) )) {
Temp += (Word32) (*Line).Sfs[i].Tran << 7 ;
}
Bsp = Par2Ser( Temp, Bsp, 8 ) ;
}
/* Write 5 bit index of fixed gains */
/* -------------------------------- */
for ( i = 0 ; i < SubFrames ; i ++ ) {
Temp = (*Line).Sfs[i].Mamp ;
Temp = MapIndexMamp[Temp]; /* map the index to take maximum
advantage of error detection */
Bsp = Par2Ser( Temp, Bsp, 5 ) ;
}
/* Write all the Grid indices */
for ( i = 0 ; i < SubFrames ; i ++ )
*Bsp ++ = (*Line).Sfs[i].Grid ;
/* High rate only part */
if ( FrType == 0 ) {
/* Write 13 bit combined position index */
Temp = (*Line).Sfs[0].Ppos >> 16 ;
Temp = Temp * 9 + ( (*Line).Sfs[1].Ppos >> 14) ;
Temp *= 90 ;
Temp += ((*Line).Sfs[2].Ppos >> 16) * 9 + ( (*Line).Sfs[3].Ppos >> 14 ) ;
Bsp = Par2Ser( Temp, Bsp, 13 ) ;
/* Write all the pulse positions */
Temp = (*Line).Sfs[0].Ppos & 0x0000ffffL ;
Bsp = Par2Ser( Temp, Bsp, 16 ) ;
Temp = (*Line).Sfs[1].Ppos & 0x00003fffL ;
Bsp = Par2Ser( Temp, Bsp, 14 ) ;
Temp = (*Line).Sfs[2].Ppos & 0x0000ffffL ;
Bsp = Par2Ser( Temp, Bsp, 16 ) ;
Temp = (*Line).Sfs[3].Ppos & 0x00003fffL ;
Bsp = Par2Ser( Temp, Bsp, 14 ) ;
/* Write pulse amplitudes */
Temp = (Word32) (*Line).Sfs[0].Pamp ;
Bsp = Par2Ser( Temp, Bsp, 6 ) ;
Temp = (Word32) (*Line).Sfs[1].Pamp ;
Bsp = Par2Ser( Temp, Bsp, 5 ) ;
Temp = (Word32) (*Line).Sfs[2].Pamp ;
Bsp = Par2Ser( Temp, Bsp, 6 ) ;
Temp = (Word32) (*Line).Sfs[3].Pamp ;
Bsp = Par2Ser( Temp, Bsp, 5 ) ;
}
/* Low rate only part */
else {
/* Write 12 bits of positions */
for ( i = 0 ; i < SubFrames ; i ++ ) {
Temp = (*Line).Sfs[i].Ppos ;
Bsp = Par2Ser( Temp, Bsp, 12 ) ;
}
/* Write 4 bit Pamps */
for ( i = 0 ; i < SubFrames ; i ++ ) {
Temp = (*Line).Sfs[i].Pamp ;
Bsp = Par2Ser( Temp, Bsp, 4 ) ;
}
}
}
else {
/* Do Sid frame gain */
}
/* Write out voiced frames */
if ( FrType == 0 ) BitCount = 192+3 ;
if ( FrType == 1 ) BitCount = 160+4 ;
if ( FrType == 2 ) BitCount = 32 ;
for ( i = 0 ; i < BitCount ; i ++ )
Vout[i>>3] ^= InfoBitStream_tmp[i] << (i & 0x0007) ;
}
/*__________________________________________________________________________
| |
| Channel encoder functions |
| (section 2) |
|__________________________________________________________________________|
*/
static void ChannelEncoder( char InfoBitStream[], char ChannelBitStream[],
Word16 ChannelBitrate, Word16 *NumChannelBytes)
{
/* Definition of BCH Code for configuration bits (see section 2.5.4) */
/* ----------------------------------------------------------------- */
static const Word16 ConfigGenMatrix[NumBCHWords][BCHLen] = {
{ 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127, 127},
{-127,-127,-127, 127,-127,-127, 127, 127,-127, 127,-127, 127, 127},
{ 127,-127,-127,-127, 127,-127,-127, 127, 127,-127, 127,-127, 127},
{-127, 127, 127,-127,-127, 127,-127, 127,-127,-127,-127,-127, 127},
{ 127, 127,-127,-127,-127, 127,-127,-127, 127, 127,-127, 127,-127},
{-127,-127, 127,-127, 127,-127,-127,-127,-127, 127, 127, 127,-127},
{ 127,-127, 127, 127,-127,-127, 127,-127, 127,-127,-127,-127,-127},
{-127, 127,-127, 127, 127, 127, 127,-127,-127,-127, 127,-127,-127}};
static Word16 LastMode = {-1};
static Word16 bit_class[5],punctur[5][3];
Word16 info_bit[210], i, mode, G723_mode, CC_mode;
Word16 chan_bit[700], SysChannelBitrate;
char CInfoBitStream[25];
G723_mode = InfoBitStream[0] & 3;
if (TESTSEQUENCE == True) {
/* This is only for processing the test sequences and not an allowed */
/* operational mode: */
/* The requested channel bitrate is not mapped to the allowed channel */
/* bitrates. This enables to exercise all possible channel bitrates */
/* and to verify the channel bitrate allocation algorithm */
/* ------------------------------------------------------------------ */
SysChannelBitrate = ChannelBitrate;
CC_mode = 0;
/* Limit channel bitrate to maximum */
/* -------------------------------- */
if ((G723_mode == 0) && (SysChannelBitrate > 20634)) SysChannelBitrate = 20634;
if ((G723_mode == 1) && (SysChannelBitrate > 17534)) SysChannelBitrate = 17534;
if ((G723_mode == 2) && (SysChannelBitrate > 4334)) SysChannelBitrate = 4334;
}else{
/* This is the normal operational mode: */
/* Get allowed channel bitrate from channel bitrate table (section 2.5.4) */
/* ---------------------------------------------------------------------- */
SelectChannelBitrate(ChannelBitrate,&SysChannelBitrate,&CC_mode,G723_mode);
}
mode = (CC_mode << 2) + G723_mode;
if (mode != LastMode){
/* (Re-)Initialise Channel Codec (section 2.5.1) */
/* --------------------------------------------- */
ChannelCodecInit(G723_mode,SysChannelBitrate,bit_class,punctur);
LastMode = mode;
}
/* Increase robustness by separating gain indexes and reordering LSP's (section 2.1) */
/* --------------------------------------------------------------------------------- */
channel_encoder_adaptation(InfoBitStream,CInfoBitStream);
/* Allocate information bits to protection classes (sections 2.2 and 2.3) */
/* ---------------------------------------------------------------------- */
bit_allocation(CInfoBitStream, &info_bit[4] );
/* Calculate CRC for class 0 and add to infobit-stream (section 2.4) */
/* ----------------------------------------------------------------- */
CrcEncoder(&info_bit[4],CInfoBitStream[0]);
/* Consider low residual error probability at the end of the trellis (section 2.5.2) */
/* --------------------------------------------------------------------------------- */
EndTrellisReorderEnc (&info_bit[4], bit_class, punctur, CInfoBitStream[0]);
/* Convolutionally encode (section 2.5.3) */
/* -------------------------------------- */
conv_encoder(bit_class, punctur, &info_bit[4], chan_bit, CInfoBitStream[0]);
/* Encode configuration bits (section 2.5.4) */
/* ----------------------------------------- */
for (i=0;i<BCHLen;i++)
chan_bit[i] = (ConfigGenMatrix[mode][i] & 0x0080) >> 7;
/* Pack channel bits (section 2.5.4) */
/* --------------------------------- */
Channel_Pack(chan_bit,ChannelBitStream,SysChannelBitrate,NumChannelBytes);
return;
}
/*__________________________________________________________________________
| |
| Convolutional encoder |
| (section 2.5.3) |
|__________________________________________________________________________|
*/
static void conv_encoder( Word16 nbit_class[], Word16 punctur[5][3],
Word16 info_bit[], Word16 chan_bit[], char mode)
{
Word16 i, j, k, ptr0, ptr1, temp, ninfo_bits, cnt, out[3], last, n0;
Word16 tmp[193];
static const Word16 mask[16] = { 0X0001, 0X0002, 0X0004, 0X0008,
0X0010, 0X0020, 0X0040, 0X0080,
0X0100, 0X0200, 0X0400, 0X0800,
0X1000, 0X2000, 0X4000, -32768 };
if( (mode & 0x3) == 0) {
ninfo_bits = NInfoBits6_3+CrcLen;
if ((nbit_class[0]+nbit_class[1]+
nbit_class[2]+nbit_class[3]+nbit_class[4]) > (NInfoBits6_3+CrcLen+4)){
printf ("\n\n\nNumber of info bits incorrect! \n");
exit(1);
}
}
if( (mode & 0x3) == 1) {
ninfo_bits = NInfoBits5_3+CrcLen;
if ((nbit_class[0]+nbit_class[1]+
nbit_class[2]+nbit_class[3]+nbit_class[4]) > (NInfoBits5_3+CrcLen+4)){
printf ("\n\n\nNumber of info bits incorrect! \n");
exit(1);
}
}
if( (mode & 0x3) == 2) {
ninfo_bits = NInfoBitsSID+CrcLen;
if ((nbit_class[0]+nbit_class[1]+
nbit_class[2]+nbit_class[3]+nbit_class[4]) > (NInfoBitsSID+CrcLen+4)){
printf ("\n\n\nNumber of info bits incorrect! \n");
exit(1);
}
}
if (punctur[0][0] != 0) {
for( i = -4; i < 0; ++i ) info_bit[i] = 0;
/* Check which class is the last protected one */
/* ------------------------------------------- */
last = 0;
for (i=1;i<5;i++){
if (punctur[i][0] != 0) last=i;
}
/* save not protected bits: */
/* ------------------------ */
for (n0=0,i=last+1;i<5;i++) n0 += nbit_class[i];
ptr0 = 0;
for( i = ninfo_bits - n0; i < ninfo_bits; ++i ) {
tmp[ptr0++] = info_bit[i];
}
/* Clear tailbits: */
/* --------------- */
for( i = ninfo_bits - n0; i < ninfo_bits - n0 + 4; ++i ) {
info_bit[i] = 0;
}
/* Encode protected classes: */
/* ------------------------- */
ptr1 = 0;
ptr0 = BCHLen;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -