123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207 |
- #ifdef HAVE_CONFIG_H
- #include "config.h"
- #endif
- #include "main.h"
- #include "stack_alloc.h"
- static OPUS_INLINE opus_int combine_and_check(
- opus_int *pulses_comb,
- const opus_int *pulses_in,
- opus_int max_pulses,
- opus_int len
- )
- {
- opus_int k, sum;
- for( k = 0; k < len; k++ ) {
- sum = pulses_in[ 2 * k ] + pulses_in[ 2 * k + 1 ];
- if( sum > max_pulses ) {
- return 1;
- }
- pulses_comb[ k ] = sum;
- }
- return 0;
- }
- void silk_encode_pulses(
- ec_enc *psRangeEnc,
- const opus_int signalType,
- const opus_int quantOffsetType,
- opus_int8 pulses[],
- const opus_int frame_length
- )
- {
- opus_int i, k, j, iter, bit, nLS, scale_down, RateLevelIndex = 0;
- opus_int32 abs_q, minSumBits_Q5, sumBits_Q5;
- VARDECL( opus_int, abs_pulses );
- VARDECL( opus_int, sum_pulses );
- VARDECL( opus_int, nRshifts );
- opus_int pulses_comb[ 8 ];
- opus_int *abs_pulses_ptr;
- const opus_int8 *pulses_ptr;
- const opus_uint8 *cdf_ptr;
- const opus_uint8 *nBits_ptr;
- SAVE_STACK;
- silk_memset( pulses_comb, 0, 8 * sizeof( opus_int ) );
-
-
-
-
- silk_assert( 1 << LOG2_SHELL_CODEC_FRAME_LENGTH == SHELL_CODEC_FRAME_LENGTH );
- iter = silk_RSHIFT( frame_length, LOG2_SHELL_CODEC_FRAME_LENGTH );
- if( iter * SHELL_CODEC_FRAME_LENGTH < frame_length ) {
- silk_assert( frame_length == 12 * 10 );
- iter++;
- silk_memset( &pulses[ frame_length ], 0, SHELL_CODEC_FRAME_LENGTH * sizeof(opus_int8));
- }
-
- ALLOC( abs_pulses, iter * SHELL_CODEC_FRAME_LENGTH, opus_int );
- silk_assert( !( SHELL_CODEC_FRAME_LENGTH & 3 ) );
- for( i = 0; i < iter * SHELL_CODEC_FRAME_LENGTH; i+=4 ) {
- abs_pulses[i+0] = ( opus_int )silk_abs( pulses[ i + 0 ] );
- abs_pulses[i+1] = ( opus_int )silk_abs( pulses[ i + 1 ] );
- abs_pulses[i+2] = ( opus_int )silk_abs( pulses[ i + 2 ] );
- abs_pulses[i+3] = ( opus_int )silk_abs( pulses[ i + 3 ] );
- }
-
- ALLOC( sum_pulses, iter, opus_int );
- ALLOC( nRshifts, iter, opus_int );
- abs_pulses_ptr = abs_pulses;
- for( i = 0; i < iter; i++ ) {
- nRshifts[ i ] = 0;
- while( 1 ) {
-
- scale_down = combine_and_check( pulses_comb, abs_pulses_ptr, silk_max_pulses_table[ 0 ], 8 );
-
- scale_down += combine_and_check( pulses_comb, pulses_comb, silk_max_pulses_table[ 1 ], 4 );
-
- scale_down += combine_and_check( pulses_comb, pulses_comb, silk_max_pulses_table[ 2 ], 2 );
-
- scale_down += combine_and_check( &sum_pulses[ i ], pulses_comb, silk_max_pulses_table[ 3 ], 1 );
- if( scale_down ) {
-
- nRshifts[ i ]++;
- for( k = 0; k < SHELL_CODEC_FRAME_LENGTH; k++ ) {
- abs_pulses_ptr[ k ] = silk_RSHIFT( abs_pulses_ptr[ k ], 1 );
- }
- } else {
-
- break;
- }
- }
- abs_pulses_ptr += SHELL_CODEC_FRAME_LENGTH;
- }
-
-
-
-
- minSumBits_Q5 = silk_int32_MAX;
- for( k = 0; k < N_RATE_LEVELS - 1; k++ ) {
- nBits_ptr = silk_pulses_per_block_BITS_Q5[ k ];
- sumBits_Q5 = silk_rate_levels_BITS_Q5[ signalType >> 1 ][ k ];
- for( i = 0; i < iter; i++ ) {
- if( nRshifts[ i ] > 0 ) {
- sumBits_Q5 += nBits_ptr[ SILK_MAX_PULSES + 1 ];
- } else {
- sumBits_Q5 += nBits_ptr[ sum_pulses[ i ] ];
- }
- }
- if( sumBits_Q5 < minSumBits_Q5 ) {
- minSumBits_Q5 = sumBits_Q5;
- RateLevelIndex = k;
- }
- }
- ec_enc_icdf( psRangeEnc, RateLevelIndex, silk_rate_levels_iCDF[ signalType >> 1 ], 8 );
-
-
-
- cdf_ptr = silk_pulses_per_block_iCDF[ RateLevelIndex ];
- for( i = 0; i < iter; i++ ) {
- if( nRshifts[ i ] == 0 ) {
- ec_enc_icdf( psRangeEnc, sum_pulses[ i ], cdf_ptr, 8 );
- } else {
- ec_enc_icdf( psRangeEnc, SILK_MAX_PULSES + 1, cdf_ptr, 8 );
- for( k = 0; k < nRshifts[ i ] - 1; k++ ) {
- ec_enc_icdf( psRangeEnc, SILK_MAX_PULSES + 1, silk_pulses_per_block_iCDF[ N_RATE_LEVELS - 1 ], 8 );
- }
- ec_enc_icdf( psRangeEnc, sum_pulses[ i ], silk_pulses_per_block_iCDF[ N_RATE_LEVELS - 1 ], 8 );
- }
- }
-
-
-
- for( i = 0; i < iter; i++ ) {
- if( sum_pulses[ i ] > 0 ) {
- silk_shell_encoder( psRangeEnc, &abs_pulses[ i * SHELL_CODEC_FRAME_LENGTH ] );
- }
- }
-
-
-
- for( i = 0; i < iter; i++ ) {
- if( nRshifts[ i ] > 0 ) {
- pulses_ptr = &pulses[ i * SHELL_CODEC_FRAME_LENGTH ];
- nLS = nRshifts[ i ] - 1;
- for( k = 0; k < SHELL_CODEC_FRAME_LENGTH; k++ ) {
- abs_q = (opus_int8)silk_abs( pulses_ptr[ k ] );
- for( j = nLS; j > 0; j-- ) {
- bit = silk_RSHIFT( abs_q, j ) & 1;
- ec_enc_icdf( psRangeEnc, bit, silk_lsb_iCDF, 8 );
- }
- bit = abs_q & 1;
- ec_enc_icdf( psRangeEnc, bit, silk_lsb_iCDF, 8 );
- }
- }
- }
-
-
-
- silk_encode_signs( psRangeEnc, pulses, frame_length, signalType, quantOffsetType, sum_pulses );
- RESTORE_STACK;
- }
|