diff mbox series

[FFmpeg-devel,6/6] aacdec_usac, aacsbr: implement SBR support for USAC

Message ID 20240616085454.2560973-6-dev@lynne.ee
State New
Headers show
Series [FFmpeg-devel,1/6] aacdec_usac: apply specification fix M55715 | expand

Checks

Context Check Description
yinshiyou/make_fate_loongarch64 success Make fate finished
yinshiyou/make_loongarch64 warning New warnings during build
andriy/make_fate_x86 success Make fate finished
andriy/make_x86 warning New warnings during build

Commit Message

Lynne June 16, 2024, 8:54 a.m. UTC
Currently, no eSBR features are supported.
Thankfully, no encoders exist for it yet.
---
 libavcodec/aac/aacdec_usac.c | 119 +++++++++++++++---
 libavcodec/aacsbr.h          |  11 ++
 libavcodec/aacsbr_template.c | 232 ++++++++++++++++++++++++++++++++---
 libavcodec/sbr.h             |  32 +++--
 4 files changed, 351 insertions(+), 43 deletions(-)

Comments

Anton Khirnov June 17, 2024, 7:35 a.m. UTC | #1
No tests?
Lynne June 17, 2024, 7:01 p.m. UTC | #2
On 17/06/2024 09:35, Anton Khirnov wrote:
> No tests?

Tests for this particular part are tricky. We still have the SBR issue 
where we add a single sample of delay to the output, which the reference 
samples and their decodings do not. Adding a test would mean modifying 
the samples in a way where we would not be able to use them after fixing 
this (in addition to all the other regular AAC samples with SBR we have 
that would become irrelevant).

My plan is to fix this after this patch, as its a troublesome topic.
Lynne June 17, 2024, 7:04 p.m. UTC | #3
On 17/06/2024 21:01, Lynne wrote:
> On 17/06/2024 09:35, Anton Khirnov wrote:
>> No tests?
> 
> Tests for this particular part are tricky. We still have the SBR issue 
> where we add a single sample of delay to the output, which the reference 
> samples and their decodings do not. Adding a test would mean modifying 
> the samples in a way where we would not be able to use them after fixing 
> this (in addition to all the other regular AAC samples with SBR we have 
> that would become irrelevant).
> 
> My plan is to fix this after this patch, as its a troublesome topic.

Additionally, we also don't correctly take into account encoder SBR 
delay signalled via MP4.
Lynne June 20, 2024, 2:12 a.m. UTC | #4
On 16/06/2024 10:54, Lynne wrote:
> Currently, no eSBR features are supported.
> Thankfully, no encoders exist for it yet.
> ---
>   libavcodec/aac/aacdec_usac.c | 119 +++++++++++++++---
>   libavcodec/aacsbr.h          |  11 ++
>   libavcodec/aacsbr_template.c | 232 ++++++++++++++++++++++++++++++++---
>   libavcodec/sbr.h             |  32 +++--
>   4 files changed, 351 insertions(+), 43 deletions(-)
> 
> diff --git a/libavcodec/aac/aacdec_usac.c b/libavcodec/aac/aacdec_usac.c
> index e5504117d0..132ffee9c2 100644
> --- a/libavcodec/aac/aacdec_usac.c
> +++ b/libavcodec/aac/aacdec_usac.c
> @@ -23,6 +23,8 @@
>   #include "aacdec_lpd.h"
>   #include "aacdec_ac.h"
>   
> +#include "libavcodec/aacsbr.h"
> +
>   #include "libavcodec/aactab.h"
>   #include "libavutil/mem.h"
>   #include "libavcodec/mpeg4audio.h"
> @@ -145,7 +147,8 @@ static int decode_loudness_set(AACDecContext *ac, AACUSACConfig *usac,
>       return 0;
>   }
>   
> -static void decode_usac_sbr_data(AACUsacElemConfig *e, GetBitContext *gb)
> +static int decode_usac_sbr_data(AACDecContext *ac,
> +                                AACUsacElemConfig *e, GetBitContext *gb)
>   {
>       uint8_t header_extra1;
>       uint8_t header_extra2;
> @@ -153,6 +156,10 @@ static void decode_usac_sbr_data(AACUsacElemConfig *e, GetBitContext *gb)
>       e->sbr.harmonic_sbr = get_bits1(gb); /* harmonicSBR */
>       e->sbr.bs_intertes = get_bits1(gb); /* bs_interTes */
>       e->sbr.bs_pvc = get_bits1(gb); /* bs_pvc */
> +    if (e->sbr.harmonic_sbr || e->sbr.bs_intertes || e->sbr.bs_pvc) {
> +        avpriv_report_missing_feature(ac->avctx, "AAC USAC eSBR");
> +        return AVERROR_PATCHWELCOME;
> +    }
>   
>       e->sbr.dflt.start_freq = get_bits(gb, 4); /* dflt_start_freq */
>       e->sbr.dflt.stop_freq = get_bits(gb, 4); /* dflt_stop_freq */
> @@ -179,6 +186,8 @@ static void decode_usac_sbr_data(AACUsacElemConfig *e, GetBitContext *gb)
>           e->sbr.dflt.interpol_freq = get_bits1(gb); /* dflt_interpol_freq */
>           e->sbr.dflt.smoothing_mode = get_bits1(gb); /* dflt_smoothing_mode */
>       }
> +
> +    return 0;
>   }
>   
>   static void decode_usac_element_core(AACUsacElemConfig *e,
> @@ -190,13 +199,17 @@ static void decode_usac_element_core(AACUsacElemConfig *e,
>       e->sbr.ratio = sbr_ratio;
>   }
>   
> -static void decode_usac_element_pair(AACUsacElemConfig *e, GetBitContext *gb)
> +static int decode_usac_element_pair(AACDecContext *ac,
> +                                    AACUsacElemConfig *e, GetBitContext *gb)
>   {
>       e->stereo_config_index = 0;
>       if (e->sbr.ratio) {
> -        decode_usac_sbr_data(e, gb);
> +        int ret = decode_usac_sbr_data(ac, e, gb);
> +        if (ret < 0)
> +            return ret;
>           e->stereo_config_index = get_bits(gb, 2);
>       }
> +
>       if (e->stereo_config_index) {
>           e->mps.freq_res = get_bits(gb, 3); /* bsFreqRes */
>           e->mps.fixed_gain = get_bits(gb, 3); /* bsFixedGainDMX */
> @@ -216,6 +229,8 @@ static void decode_usac_element_pair(AACUsacElemConfig *e, GetBitContext *gb)
>           if (e->mps.temp_shape_config == 2)
>               e->mps.env_quant_mode = get_bits1(gb); /* bsEnvQuantMode */
>       }
> +
> +    return 0;
>   }
>   
>   static int decode_usac_extension(AACDecContext *ac, AACUsacElemConfig *e,
> @@ -294,6 +309,9 @@ int ff_aac_usac_reset_state(AACDecContext *ac, OutputConfiguration *oc)
>               AACUsacStereo *us = &che->us;
>               memset(us, 0, sizeof(*us));
>   
> +            if (e->sbr.ratio)
> +                ff_aac_sbr_config_usac(ac, che, e);
> +
>               for (int j = 0; j < ch; j++) {
>                   SingleChannelElement *sce = &che->ch[ch];
>                   AACUsacElemData *ue = &sce->ue;
> @@ -320,6 +338,7 @@ int ff_aac_usac_config_decode(AACDecContext *ac, AVCodecContext *avctx,
>       uint8_t freq_idx;
>       uint8_t channel_config_idx;
>       int nb_channels = 0;
> +    int ratio_mult, ratio_dec;
>       int samplerate;
>       int sbr_ratio;
>       MPEG4AudioConfig *m4ac = &oc->m4ac;
> @@ -340,8 +359,6 @@ int ff_aac_usac_config_decode(AACDecContext *ac, AVCodecContext *avctx,
>               return AVERROR(EINVAL);
>       }
>   
> -    m4ac->sample_rate = avctx->sample_rate = samplerate;
> -
>       usac->core_sbr_frame_len_idx = get_bits(gb, 3); /* coreSbrFrameLengthIndex */
>       m4ac->frame_length_short = usac->core_sbr_frame_len_idx == 0 ||
>                                  usac->core_sbr_frame_len_idx == 2;
> @@ -354,7 +371,26 @@ int ff_aac_usac_config_decode(AACDecContext *ac, AVCodecContext *avctx,
>                   usac->core_sbr_frame_len_idx == 4 ? 1 :
>                   0;
>   
> +    if (sbr_ratio == 2) {
> +        ratio_mult = 8;
> +        ratio_dec = 3;
> +    } else if (sbr_ratio == 3) {
> +        ratio_mult = 2;
> +        ratio_dec = 1;
> +    } else if (sbr_ratio == 4) {
> +        ratio_mult = 4;
> +        ratio_dec = 1;
> +    } else {
> +        ratio_mult = 1;
> +        ratio_dec = 1;
> +    }
> +
> +    avctx->sample_rate = samplerate;
> +    m4ac->ext_sample_rate = samplerate;
> +    m4ac->sample_rate = (samplerate * ratio_dec) / ratio_mult;
> +
>       m4ac->sampling_index = ff_aac_sample_rate_idx(m4ac->sample_rate);
> +    m4ac->sbr = sbr_ratio > 0;
>   
>       channel_config_idx = get_bits(gb, 5); /* channelConfigurationIndex */
>       if (!channel_config_idx) {
> @@ -426,8 +462,11 @@ int ff_aac_usac_config_decode(AACDecContext *ac, AVCodecContext *avctx,
>           case ID_USAC_SCE: /* SCE */
>               /* UsacCoreConfig */
>               decode_usac_element_core(e, gb, sbr_ratio);
> -            if (e->sbr.ratio > 0)
> -                decode_usac_sbr_data(e, gb);
> +            if (e->sbr.ratio > 0) {
> +                ret = decode_usac_sbr_data(ac, e, gb);
> +                if (ret < 0)
> +                    return ret;
> +            }
>               layout_map[map_count][0] = TYPE_SCE;
>               layout_map[map_count][1] = elem_id[0]++;
>               if (!map_pos_set)
> @@ -437,7 +476,9 @@ int ff_aac_usac_config_decode(AACDecContext *ac, AVCodecContext *avctx,
>           case ID_USAC_CPE: /* UsacChannelPairElementConf */
>               /* UsacCoreConfig */
>               decode_usac_element_core(e, gb, sbr_ratio);
> -            decode_usac_element_pair(e, gb);
> +            ret = decode_usac_element_pair(ac, e, gb);
> +            if (ret < 0)
> +                return ret;
>               layout_map[map_count][0] = TYPE_CPE;
>               layout_map[map_count][1] = elem_id[1]++;
>               if (!map_pos_set)
> @@ -1307,13 +1348,14 @@ static int decode_usac_core_coder(AACDecContext *ac, AACUSACConfig *usac,
>       int ret;
>       int arith_reset_flag;
>       AACUsacStereo *us = &che->us;
> +    int core_nb_channels = nb_channels;
>   
>       /* Local symbols */
>       uint8_t global_gain;
>   
>       us->common_window = 0;
>   
> -    for (int ch = 0; ch < nb_channels; ch++) {
> +    for (int ch = 0; ch < core_nb_channels; ch++) {
>           SingleChannelElement *sce = &che->ch[ch];
>           AACUsacElemData *ue = &sce->ue;
>   
> @@ -1323,13 +1365,16 @@ static int decode_usac_core_coder(AACDecContext *ac, AACUSACConfig *usac,
>           ue->core_mode = get_bits1(gb);
>       }
>   
> -    if (nb_channels == 2) {
> +    if (nb_channels > 1 && ec->stereo_config_index == 1)
> +        core_nb_channels = 1;
> +
> +    if (core_nb_channels == 2) {
>           ret = decode_usac_stereo_info(ac, usac, ec, che, gb, indep_flag);
>           if (ret)
>               return ret;
>       }
>   
> -    for (int ch = 0; ch < nb_channels; ch++) {
> +    for (int ch = 0; ch < core_nb_channels; ch++) {
>           SingleChannelElement *sce = &che->ch[ch];
>           IndividualChannelStream *ics = &sce->ics;
>           AACUsacElemData *ue = &sce->ue;
> @@ -1341,7 +1386,7 @@ static int decode_usac_core_coder(AACDecContext *ac, AACUSACConfig *usac,
>               continue;
>           }
>   
> -        if ((nb_channels == 1) ||
> +        if ((core_nb_channels == 1) ||
>               (che->ch[0].ue.core_mode != che->ch[1].ue.core_mode))
>               ue->tns_data_present = get_bits1(gb);
>   
> @@ -1424,7 +1469,29 @@ static int decode_usac_core_coder(AACDecContext *ac, AACUSACConfig *usac,
>           }
>       }
>   
> -    spectrum_decode(ac, usac, che, nb_channels);
> +    if (ec->sbr.ratio) {
> +        int sbr_ch = nb_channels;
> +        if (nb_channels == 2 &&
> +            !(ec->stereo_config_index == 0 || ec->stereo_config_index == 3))
> +            sbr_ch = 1;
> +
> +        ret = ff_aac_sbr_decode_usac_data(ac, che, ec, gb, sbr_ch, indep_flag);
> +        if (ret < 0)
> +            return ret;
> +
> +        if (ec->stereo_config_index) {
> +            avpriv_report_missing_feature(ac->avctx, "AAC USAC Mps212");
> +            return AVERROR_PATCHWELCOME;
> +        }
> +    }
> +
> +    spectrum_decode(ac, usac, che, core_nb_channels);
> +
> +    if (ac->oc[1].m4ac.sbr > 0) {
> +        ac->proc.sbr_apply(ac, che, nb_channels == 2 ? TYPE_CPE : TYPE_SCE,
> +                           che->ch[0].output,
> +                           che->ch[1].output);
> +    }
>   
>       return 0;
>   }
> @@ -1591,9 +1658,29 @@ int ff_aac_usac_decode_frame(AVCodecContext *avctx, AACDecContext *ac,
>       int indep_flag, samples = 0;
>       int audio_found = 0;
>       int elem_id[3 /* SCE, CPE, LFE */] = { 0, 0, 0 };
> -
>       AVFrame *frame = ac->frame;
>   
> +    int ratio_mult, ratio_dec;
> +    AACUSACConfig *usac = &ac->oc[1].usac;
> +    int sbr_ratio = usac->core_sbr_frame_len_idx == 2 ? 2 :
> +                    usac->core_sbr_frame_len_idx == 3 ? 3 :
> +                    usac->core_sbr_frame_len_idx == 4 ? 1 :
> +                    0;
> +
> +    if (sbr_ratio == 2) {
> +        ratio_mult = 8;
> +        ratio_dec = 3;
> +    } else if (sbr_ratio == 3) {
> +        ratio_mult = 2;
> +        ratio_dec = 1;
> +    } else if (sbr_ratio == 4) {
> +        ratio_mult = 4;
> +        ratio_dec = 1;
> +    } else {
> +        ratio_mult = 1;
> +        ratio_dec = 1;
> +    }
> +
>       ff_aac_output_configure(ac, ac->oc[1].layout_map, ac->oc[1].layout_map_tags,
>                               ac->oc[1].status, 0);
>   
> @@ -1660,8 +1747,10 @@ int ff_aac_usac_decode_frame(AVCodecContext *avctx, AACDecContext *ac,
>       if (audio_found)
>           samples = ac->oc[1].m4ac.frame_length_short ? 768 : 1024;
>   
> +    samples = (samples * ratio_mult) / ratio_dec;
> +
>       if (ac->oc[1].status && audio_found) {
> -        avctx->sample_rate = ac->oc[1].m4ac.sample_rate;
> +        avctx->sample_rate = ac->oc[1].m4ac.ext_sample_rate;
>           avctx->frame_size = samples;
>           ac->oc[1].status = OC_LOCKED;
>       }
> diff --git a/libavcodec/aacsbr.h b/libavcodec/aacsbr.h
> index d4582d1100..3958b43b91 100644
> --- a/libavcodec/aacsbr.h
> +++ b/libavcodec/aacsbr.h
> @@ -88,6 +88,17 @@ int ff_aac_sbr_decode_extension(AACDecContext *ac, ChannelElement *che,
>   int ff_aac_sbr_decode_extension_fixed(AACDecContext *ac, ChannelElement *che,
>                                         GetBitContext *gb, int crc, int cnt, int id_aac);
>   
> +/** Due to channel allocation not being known upon SBR parameter transmission,
> + * supply the parameters separately.
> + * Functionally identical to ff_aac_sbr_decode_extension() */
> +int ff_aac_sbr_config_usac(AACDecContext *ac, ChannelElement *che,
> +                           AACUsacElemConfig *ue);
> +
> +/** Decode frame SBR data, USAC. */
> +int ff_aac_sbr_decode_usac_data(AACDecContext *ac, ChannelElement *che,
> +                                AACUsacElemConfig *ue, GetBitContext *gb,
> +                                int sbr_ch, int indep_flag);
> +
>   /** Apply one SBR element to one AAC element. */
>   void ff_aac_sbr_apply(AACDecContext *ac, ChannelElement *che,
>                         int id_aac, void /* float */ *L, void /* float */ *R);
> diff --git a/libavcodec/aacsbr_template.c b/libavcodec/aacsbr_template.c
> index 86f4d8c26e..e5bc4d4659 100644
> --- a/libavcodec/aacsbr_template.c
> +++ b/libavcodec/aacsbr_template.c
> @@ -57,6 +57,7 @@ av_cold void AAC_RENAME(ff_aac_sbr_init)(void)
>   /** Places SBR in pure upsampling mode. */
>   static void sbr_turnoff(SpectralBandReplication *sbr) {
>       sbr->start = 0;
> +    sbr->usac = 0;
>       sbr->ready_for_dequant = 0;
>       // Init defults used in pure upsampling mode
>       sbr->kx[1] = 32; //Typo in spec, kx' inits to 32
> @@ -184,7 +185,8 @@ static void sbr_make_f_tablelim(SpectralBandReplication *sbr)
>       }
>   }
>   
> -static unsigned int read_sbr_header(SpectralBandReplication *sbr, GetBitContext *gb)
> +static unsigned int read_sbr_header(SpectralBandReplication *sbr,
> +                                    GetBitContext *gb, int is_usac)
>   {
>       unsigned int cnt = get_bits_count(gb);
>       uint8_t bs_header_extra_1;
> @@ -194,15 +196,20 @@ static unsigned int read_sbr_header(SpectralBandReplication *sbr, GetBitContext
>   
>       sbr->start = 1;
>       sbr->ready_for_dequant = 0;
> +    sbr->usac = is_usac;
>   
>       // Save last spectrum parameters variables to compare to new ones
>       memcpy(&old_spectrum_params, &sbr->spectrum_params, sizeof(SpectrumParameters));
>   
> -    sbr->bs_amp_res_header              = get_bits1(gb);
> +    if (!is_usac)
> +        sbr->bs_amp_res_header          = get_bits1(gb);
> +
>       sbr->spectrum_params.bs_start_freq  = get_bits(gb, 4);
>       sbr->spectrum_params.bs_stop_freq   = get_bits(gb, 4);
> -    sbr->spectrum_params.bs_xover_band  = get_bits(gb, 3);
> -                                          skip_bits(gb, 2); // bs_reserved
> +
> +    if (!is_usac)
> +        sbr->spectrum_params.bs_xover_band = get_bits(gb, 3);
> +                                             skip_bits(gb, 2); // bs_reserved
>   
>       bs_header_extra_1 = get_bits1(gb);
>       bs_header_extra_2 = get_bits1(gb);
> @@ -645,7 +652,7 @@ static int read_sbr_grid(AACDecContext *ac, SpectralBandReplication *sbr,
>       switch (bs_frame_class = get_bits(gb, 2)) {
>       case FIXFIX:
>           bs_num_env = 1 << get_bits(gb, 2);
> -        if (bs_num_env > 4) {
> +        if (bs_num_env > (sbr->usac ? 8 : 5)) {
>               av_log(ac->avctx, AV_LOG_ERROR,
>                      "Invalid bitstream, too many SBR envelopes in FIXFIX type SBR frame: %d\n",
>                      bs_num_env);
> @@ -793,10 +800,26 @@ static void copy_sbr_grid(SBRData *dst, const SBRData *src) {
>   
>   /// Read how the envelope and noise floor data is delta coded
>   static void read_sbr_dtdf(SpectralBandReplication *sbr, GetBitContext *gb,
> -                          SBRData *ch_data)
> +                          SBRData *ch_data, int indep_flag)
>   {
> -    get_bits1_vector(gb, ch_data->bs_df_env,   ch_data->bs_num_env);
> -    get_bits1_vector(gb, ch_data->bs_df_noise, ch_data->bs_num_noise);
> +    if (sbr->usac) {
> +        if (indep_flag) {
> +            ch_data->bs_df_env[0] = 0;
> +            get_bits1_vector(gb, &ch_data->bs_df_env[1], ch_data->bs_num_env - 1);
> +        } else {
> +            get_bits1_vector(gb, ch_data->bs_df_env, ch_data->bs_num_env);
> +        }
> +
> +        if (indep_flag) {
> +            ch_data->bs_df_noise[0] = 0;
> +            get_bits1_vector(gb, &ch_data->bs_df_noise[1], ch_data->bs_num_noise - 1);
> +        } else {
> +            get_bits1_vector(gb, ch_data->bs_df_noise, ch_data->bs_num_noise);
> +        }
> +    } else {
> +        get_bits1_vector(gb, ch_data->bs_df_env,   ch_data->bs_num_env);
> +        get_bits1_vector(gb, ch_data->bs_df_noise, ch_data->bs_num_noise);
> +    }
>   }
>   
>   /// Read inverse filtering data
> @@ -811,7 +834,7 @@ static void read_sbr_invf(SpectralBandReplication *sbr, GetBitContext *gb,
>   }
>   
>   static int read_sbr_envelope(AACDecContext *ac, SpectralBandReplication *sbr, GetBitContext *gb,
> -                              SBRData *ch_data, int ch)
> +                             SBRData *ch_data, int ch)
>   {
>       int bits;
>       int i, j, k;
> @@ -881,6 +904,13 @@ static int read_sbr_envelope(AACDecContext *ac, SpectralBandReplication *sbr, Ge
>                   }
>               }
>           }
> +        if (sbr->usac) {
> +            if (sbr->inter_tes) {
> +                ch_data->temp_shape[i] = get_bits(gb, 1);
> +                if (ch_data->temp_shape[i])
> +                    ch_data->temp_shape_mode[i] = get_bits(gb, 2);
> +            }
> +        }
>       }
>   
>       //assign 0th elements of env_facs_q from last elements
> @@ -970,7 +1000,7 @@ static int read_sbr_single_channel_element(AACDecContext *ac,
>   
>       if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]))
>           return -1;
> -    read_sbr_dtdf(sbr, gb, &sbr->data[0]);
> +    read_sbr_dtdf(sbr, gb, &sbr->data[0], 0);
>       read_sbr_invf(sbr, gb, &sbr->data[0]);
>       if((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[0], 0)) < 0)
>           return ret;
> @@ -996,8 +1026,8 @@ static int read_sbr_channel_pair_element(AACDecContext *ac,
>           if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]))
>               return -1;
>           copy_sbr_grid(&sbr->data[1], &sbr->data[0]);
> -        read_sbr_dtdf(sbr, gb, &sbr->data[0]);
> -        read_sbr_dtdf(sbr, gb, &sbr->data[1]);
> +        read_sbr_dtdf(sbr, gb, &sbr->data[0], 0);
> +        read_sbr_dtdf(sbr, gb, &sbr->data[1], 0);
>           read_sbr_invf(sbr, gb, &sbr->data[0]);
>           memcpy(sbr->data[1].bs_invf_mode[1], sbr->data[1].bs_invf_mode[0], sizeof(sbr->data[1].bs_invf_mode[0]));
>           memcpy(sbr->data[1].bs_invf_mode[0], sbr->data[0].bs_invf_mode[0], sizeof(sbr->data[1].bs_invf_mode[0]));
> @@ -1013,8 +1043,8 @@ static int read_sbr_channel_pair_element(AACDecContext *ac,
>           if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]) ||
>               read_sbr_grid(ac, sbr, gb, &sbr->data[1]))
>               return -1;
> -        read_sbr_dtdf(sbr, gb, &sbr->data[0]);
> -        read_sbr_dtdf(sbr, gb, &sbr->data[1]);
> +        read_sbr_dtdf(sbr, gb, &sbr->data[0], 0);
> +        read_sbr_dtdf(sbr, gb, &sbr->data[1], 0);
>           read_sbr_invf(sbr, gb, &sbr->data[0]);
>           read_sbr_invf(sbr, gb, &sbr->data[1]);
>           if((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[0], 0)) < 0)
> @@ -1129,7 +1159,7 @@ int AAC_RENAME(ff_aac_sbr_decode_extension)(AACDecContext *ac, ChannelElement *c
>   
>       num_sbr_bits++;
>       if (get_bits1(gb)) // bs_header_flag
> -        num_sbr_bits += read_sbr_header(sbr, gb);
> +        num_sbr_bits += read_sbr_header(sbr, gb, 0);
>   
>       if (sbr->reset)
>           sbr_reset(ac, sbr);
> @@ -1148,6 +1178,178 @@ int AAC_RENAME(ff_aac_sbr_decode_extension)(AACDecContext *ac, ChannelElement *c
>       return cnt;
>   }
>   
> +#if !USE_FIXED
> +static void copy_usac_default_header(SpectralBandReplication *sbr,
> +                                     AACUsacElemConfig *ue)
> +{
> +    sbr->inter_tes = ue->sbr.bs_intertes;
> +
> +    sbr->spectrum_params.bs_start_freq = ue->sbr.dflt.start_freq;
> +    sbr->spectrum_params.bs_stop_freq = ue->sbr.dflt.stop_freq;
> +
> +    sbr->spectrum_params.bs_freq_scale = ue->sbr.dflt.freq_scale;
> +    sbr->spectrum_params.bs_alter_scale = ue->sbr.dflt.alter_scale;
> +    sbr->spectrum_params.bs_noise_bands = ue->sbr.dflt.noise_bands;
> +
> +    sbr->bs_limiter_bands = ue->sbr.dflt.limiter_bands;
> +    sbr->bs_limiter_gains = ue->sbr.dflt.limiter_gains;
> +    sbr->bs_interpol_freq = ue->sbr.dflt.interpol_freq;
> +    sbr->bs_smoothing_mode = ue->sbr.dflt.smoothing_mode;
> +}
> +
> +int ff_aac_sbr_config_usac(AACDecContext *ac, ChannelElement *che,
> +                           AACUsacElemConfig *ue)
> +{
> +    SpectralBandReplication *sbr = get_sbr(che);
> +    sbr_turnoff(sbr);
> +    return 0;
> +}
> +
> +int ff_aac_sbr_decode_usac_data(AACDecContext *ac, ChannelElement *che,
> +                                AACUsacElemConfig *ue, GetBitContext *gb,
> +                                int sbr_ch, int indep_flag)
> +{
> +    int ret;
> +    SpectralBandReplication *sbr = get_sbr(che);
> +    int info_present = 1;
> +    int header_present = 1;
> +
> +    sbr->reset = 0;
> +    sbr->usac = 1;
> +
> +    sbr->sample_rate = ac->oc[1].m4ac.ext_sample_rate;
> +    sbr->id_aac = sbr_ch == 2 ? TYPE_CPE : TYPE_SCE;
> +
> +    if (!indep_flag) {
> +        info_present = get_bits1(gb);
> +        if (info_present)
> +            header_present = get_bits1(gb);
> +        else
> +            header_present = 0;
> +    }
> +
> +    if (info_present) {
> +        /* SbrInfo() */
> +        sbr->bs_amp_res_header = get_bits1(gb);
> +        sbr->spectrum_params.bs_xover_band = get_bits(gb, 4);
> +        sbr->bs_sbr_preprocessing = get_bits1(gb);
> +        /* if (bs_pvc) ... */
> +    }
> +
> +    if (header_present) {
> +        if (get_bits1(gb)) {
> +            int old_bs_limiter_bands = sbr->bs_limiter_bands;
> +            SpectrumParameters old_spectrum_params;
> +            memcpy(&old_spectrum_params, &sbr->spectrum_params,
> +                   sizeof(SpectrumParameters));
> +
> +            copy_usac_default_header(sbr, ue);
> +            // Check if spectrum parameters changed
> +            if (memcmp(&old_spectrum_params, &sbr->spectrum_params,
> +                       sizeof(SpectrumParameters)))
> +                sbr->reset = 1;
> +
> +            if (sbr->bs_limiter_bands != old_bs_limiter_bands && !sbr->reset)
> +                sbr_make_f_tablelim(sbr);
> +        } else {
> +            read_sbr_header(sbr, gb, 1);
> +        }
> +
> +        sbr->start = 1;
> +    }
> +
> +    //Save some state from the previous frame.
> +    sbr->kx[0] = sbr->kx[1];
> +    sbr->m[0] = sbr->m[1];
> +    sbr->kx_and_m_pushed = 1;
> +
> +    if (sbr->reset)
> +        sbr_reset(ac, sbr);
> +
> +    sbr->ready_for_dequant = 1;
> +
> +    int start = get_bits_count(gb);
> +
> +    if (sbr_ch == 1) { /* sbr_single_channel_element */
> +        /* if (harmonicSBR) ... */
> +
> +        if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]))
> +            return -1;
> +
> +        read_sbr_dtdf(sbr, gb, &sbr->data[0], indep_flag);
> +        read_sbr_invf(sbr, gb, &sbr->data[0]);
> +
> +        if ((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[0], 0)) < 0)
> +            return ret;
> +
> +        if ((ret = read_sbr_noise(ac, sbr, gb, &sbr->data[0], 0)) < 0)
> +            return ret;
> +
> +        if ((sbr->data[0].bs_add_harmonic_flag = get_bits1(gb)))
> +            get_bits1_vector(gb, sbr->data[0].bs_add_harmonic, sbr->n[1]);
> +    } else if (get_bits1(gb)) { /* bs_coupling == 1 */
> +        /* if (harmonicSBR) ... */
> +
> +        if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]))
> +            return -1;
> +        copy_sbr_grid(&sbr->data[1], &sbr->data[0]);
> +
> +        read_sbr_dtdf(sbr, gb, &sbr->data[0], indep_flag);
> +        read_sbr_dtdf(sbr, gb, &sbr->data[1], indep_flag);
> +
> +        read_sbr_invf(sbr, gb, &sbr->data[0]);
> +        memcpy(sbr->data[1].bs_invf_mode[1], sbr->data[1].bs_invf_mode[0],
> +               sizeof(sbr->data[1].bs_invf_mode[0]));
> +        memcpy(sbr->data[1].bs_invf_mode[0], sbr->data[0].bs_invf_mode[0],
> +               sizeof(sbr->data[1].bs_invf_mode[0]));
> +
> +        if ((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[0], 0)) < 0)
> +            return ret;
> +        if ((ret = read_sbr_noise(ac, sbr, gb, &sbr->data[0], 0)) < 0)
> +            return ret;
> +
> +        if ((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[1], 1)) < 0)
> +            return ret;
> +        if ((ret = read_sbr_noise(ac, sbr, gb, &sbr->data[1], 1)) < 0)
> +            return ret;
> +
> +        if ((sbr->data[0].bs_add_harmonic_flag = get_bits1(gb)))
> +            get_bits1_vector(gb, sbr->data[0].bs_add_harmonic, sbr->n[1]);
> +        if ((sbr->data[1].bs_add_harmonic_flag = get_bits1(gb)))
> +            get_bits1_vector(gb, sbr->data[1].bs_add_harmonic, sbr->n[1]);
> +    } else { /* bs_coupling == 0 */
> +        /* if (harmonicSBR) ... */
> +        if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]))
> +            return -1;
> +        if (read_sbr_grid(ac, sbr, gb, &sbr->data[1]))
> +            return -1;
> +
> +        read_sbr_dtdf(sbr, gb, &sbr->data[0], indep_flag);
> +        read_sbr_dtdf(sbr, gb, &sbr->data[1], indep_flag);
> +
> +        read_sbr_invf(sbr, gb, &sbr->data[0]);
> +        read_sbr_invf(sbr, gb, &sbr->data[1]);
> +
> +        if ((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[0], 0)) < 0)
> +            return ret;
> +        if ((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[1], 1)) < 0)
> +            return ret;
> +
> +        if ((ret = read_sbr_noise(ac, sbr, gb, &sbr->data[0], 0)) < 0)
> +            return ret;
> +        if ((ret = read_sbr_noise(ac, sbr, gb, &sbr->data[1], 1)) < 0)
> +            return ret;
> +
> +        if ((sbr->data[0].bs_add_harmonic_flag = get_bits1(gb)))
> +            get_bits1_vector(gb, sbr->data[0].bs_add_harmonic, sbr->n[1]);
> +        if ((sbr->data[1].bs_add_harmonic_flag = get_bits1(gb)))
> +            get_bits1_vector(gb, sbr->data[1].bs_add_harmonic, sbr->n[1]);
> +    }
> +
> +    return 0;
> +}
> +#endif
> +
>   /**
>    * Analysis QMF Bank (14496-3 sp04 p206)
>    *
> diff --git a/libavcodec/sbr.h b/libavcodec/sbr.h
> index fe3a39603a..40bb30e04d 100644
> --- a/libavcodec/sbr.h
> +++ b/libavcodec/sbr.h
> @@ -68,9 +68,9 @@ typedef struct SBRData {
>       unsigned           bs_frame_class;
>       unsigned           bs_add_harmonic_flag;
>       AAC_SIGNE          bs_num_env;
> -    uint8_t            bs_freq_res[7];
> +    uint8_t            bs_freq_res[9];
>       AAC_SIGNE          bs_num_noise;
> -    uint8_t            bs_df_env[5];
> +    uint8_t            bs_df_env[9];
>       uint8_t            bs_df_noise[2];
>       uint8_t            bs_invf_mode[2][5];
>       uint8_t            bs_add_harmonic[48];
> @@ -95,21 +95,24 @@ typedef struct SBRData {
>       DECLARE_ALIGNED(16, INTFLOAT, Y)[2][38][64][2];
>       DECLARE_ALIGNED(16, AAC_FLOAT, g_temp)[42][48];
>       AAC_FLOAT          q_temp[42][48];
> -    uint8_t            s_indexmapped[8][48];
> +    uint8_t            s_indexmapped[9][48];
>       ///Envelope scalefactors
> -    uint8_t            env_facs_q[6][48];
> -    AAC_FLOAT          env_facs[6][48];
> +    uint8_t            env_facs_q[9][48];
> +    AAC_FLOAT          env_facs[9][48];
>       ///Noise scalefactors
>       uint8_t            noise_facs_q[3][5];
>       AAC_FLOAT          noise_facs[3][5];
>       ///Envelope time borders
> -    uint8_t            t_env[8];
> +    uint8_t            t_env[9];
>       ///Envelope time border of the last envelope of the previous frame
>       uint8_t            t_env_num_env_old;
>       ///Noise time borders
>       uint8_t            t_q[3];
>       unsigned           f_indexnoise;
>       unsigned           f_indexsine;
> +    //inter_tes (USAC)
> +    uint8_t            temp_shape[6];
> +    uint8_t            temp_shape_mode[6];
>       /** @} */
>   } SBRData;
>   
> @@ -142,9 +145,12 @@ struct SpectralBandReplication {
>       int                start;
>       int                ready_for_dequant;
>       int                id_aac;
> +    int                usac;
> +    int                inter_tes; // USAC-only
>       int                reset;
>       SpectrumParameters spectrum_params;
>       int                bs_amp_res_header;
> +    int                bs_sbr_preprocessing; // USAC-only
>       /**
>        * @name Variables associated with bs_header_extra_2
>        * @{
> @@ -196,18 +202,18 @@ struct SpectralBandReplication {
>       ///First coefficient used to filter the subband signals
>       DECLARE_ALIGNED(16, INTFLOAT, alpha1)[64][2];
>       ///Dequantized envelope scalefactors, remapped
> -    AAC_FLOAT          e_origmapped[7][48];
> +    AAC_FLOAT          e_origmapped[8][48];
>       ///Dequantized noise scalefactors, remapped
> -    AAC_FLOAT          q_mapped[7][48];
> +    AAC_FLOAT          q_mapped[8][48];
>       ///Sinusoidal presence, remapped
> -    uint8_t            s_mapped[7][48];
> +    uint8_t            s_mapped[8][48];
>       ///Estimated envelope
> -    AAC_FLOAT          e_curr[7][48];
> +    AAC_FLOAT          e_curr[8][48];
>       ///Amplitude adjusted noise scalefactors
> -    AAC_FLOAT          q_m[7][48];
> +    AAC_FLOAT          q_m[8][48];
>       ///Sinusoidal levels
> -    AAC_FLOAT          s_m[7][48];
> -    AAC_FLOAT          gain[7][48];
> +    AAC_FLOAT          s_m[8][48];
> +    AAC_FLOAT          gain[8][48];
>       DECLARE_ALIGNED(32, INTFLOAT, qmf_filter_scratch)[5][64];
>       AVTXContext       *mdct_ana;
>       av_tx_fn           mdct_ana_fn;

I'll wait 2 more days before merging this patch, but I'll push the other 
5 fix/prep patches tomorrow.
Lynne June 23, 2024, 7:11 a.m. UTC | #5
On 20/06/2024 04:12, Lynne wrote:
> On 16/06/2024 10:54, Lynne wrote:
>> Currently, no eSBR features are supported.
>> Thankfully, no encoders exist for it yet.
>> ---
>>   libavcodec/aac/aacdec_usac.c | 119 +++++++++++++++---
>>   libavcodec/aacsbr.h          |  11 ++
>>   libavcodec/aacsbr_template.c | 232 ++++++++++++++++++++++++++++++++---
>>   libavcodec/sbr.h             |  32 +++--
>>   4 files changed, 351 insertions(+), 43 deletions(-)
>>
>> diff --git a/libavcodec/aac/aacdec_usac.c b/libavcodec/aac/aacdec_usac.c
>> index e5504117d0..132ffee9c2 100644
>> --- a/libavcodec/aac/aacdec_usac.c
>> +++ b/libavcodec/aac/aacdec_usac.c
>> @@ -23,6 +23,8 @@
>>   #include "aacdec_lpd.h"
>>   #include "aacdec_ac.h"
>> +#include "libavcodec/aacsbr.h"
>> +
>>   #include "libavcodec/aactab.h"
>>   #include "libavutil/mem.h"
>>   #include "libavcodec/mpeg4audio.h"
>> @@ -145,7 +147,8 @@ static int decode_loudness_set(AACDecContext *ac, 
>> AACUSACConfig *usac,
>>       return 0;
>>   }
>> -static void decode_usac_sbr_data(AACUsacElemConfig *e, GetBitContext 
>> *gb)
>> +static int decode_usac_sbr_data(AACDecContext *ac,
>> +                                AACUsacElemConfig *e, GetBitContext *gb)
>>   {
>>       uint8_t header_extra1;
>>       uint8_t header_extra2;
>> @@ -153,6 +156,10 @@ static void 
>> decode_usac_sbr_data(AACUsacElemConfig *e, GetBitContext *gb)
>>       e->sbr.harmonic_sbr = get_bits1(gb); /* harmonicSBR */
>>       e->sbr.bs_intertes = get_bits1(gb); /* bs_interTes */
>>       e->sbr.bs_pvc = get_bits1(gb); /* bs_pvc */
>> +    if (e->sbr.harmonic_sbr || e->sbr.bs_intertes || e->sbr.bs_pvc) {
>> +        avpriv_report_missing_feature(ac->avctx, "AAC USAC eSBR");
>> +        return AVERROR_PATCHWELCOME;
>> +    }
>>       e->sbr.dflt.start_freq = get_bits(gb, 4); /* dflt_start_freq */
>>       e->sbr.dflt.stop_freq = get_bits(gb, 4); /* dflt_stop_freq */
>> @@ -179,6 +186,8 @@ static void decode_usac_sbr_data(AACUsacElemConfig 
>> *e, GetBitContext *gb)
>>           e->sbr.dflt.interpol_freq = get_bits1(gb); /* 
>> dflt_interpol_freq */
>>           e->sbr.dflt.smoothing_mode = get_bits1(gb); /* 
>> dflt_smoothing_mode */
>>       }
>> +
>> +    return 0;
>>   }
>>   static void decode_usac_element_core(AACUsacElemConfig *e,
>> @@ -190,13 +199,17 @@ static void 
>> decode_usac_element_core(AACUsacElemConfig *e,
>>       e->sbr.ratio = sbr_ratio;
>>   }
>> -static void decode_usac_element_pair(AACUsacElemConfig *e, 
>> GetBitContext *gb)
>> +static int decode_usac_element_pair(AACDecContext *ac,
>> +                                    AACUsacElemConfig *e, 
>> GetBitContext *gb)
>>   {
>>       e->stereo_config_index = 0;
>>       if (e->sbr.ratio) {
>> -        decode_usac_sbr_data(e, gb);
>> +        int ret = decode_usac_sbr_data(ac, e, gb);
>> +        if (ret < 0)
>> +            return ret;
>>           e->stereo_config_index = get_bits(gb, 2);
>>       }
>> +
>>       if (e->stereo_config_index) {
>>           e->mps.freq_res = get_bits(gb, 3); /* bsFreqRes */
>>           e->mps.fixed_gain = get_bits(gb, 3); /* bsFixedGainDMX */
>> @@ -216,6 +229,8 @@ static void 
>> decode_usac_element_pair(AACUsacElemConfig *e, GetBitContext *gb)
>>           if (e->mps.temp_shape_config == 2)
>>               e->mps.env_quant_mode = get_bits1(gb); /* bsEnvQuantMode */
>>       }
>> +
>> +    return 0;
>>   }
>>   static int decode_usac_extension(AACDecContext *ac, 
>> AACUsacElemConfig *e,
>> @@ -294,6 +309,9 @@ int ff_aac_usac_reset_state(AACDecContext *ac, 
>> OutputConfiguration *oc)
>>               AACUsacStereo *us = &che->us;
>>               memset(us, 0, sizeof(*us));
>> +            if (e->sbr.ratio)
>> +                ff_aac_sbr_config_usac(ac, che, e);
>> +
>>               for (int j = 0; j < ch; j++) {
>>                   SingleChannelElement *sce = &che->ch[ch];
>>                   AACUsacElemData *ue = &sce->ue;
>> @@ -320,6 +338,7 @@ int ff_aac_usac_config_decode(AACDecContext *ac, 
>> AVCodecContext *avctx,
>>       uint8_t freq_idx;
>>       uint8_t channel_config_idx;
>>       int nb_channels = 0;
>> +    int ratio_mult, ratio_dec;
>>       int samplerate;
>>       int sbr_ratio;
>>       MPEG4AudioConfig *m4ac = &oc->m4ac;
>> @@ -340,8 +359,6 @@ int ff_aac_usac_config_decode(AACDecContext *ac, 
>> AVCodecContext *avctx,
>>               return AVERROR(EINVAL);
>>       }
>> -    m4ac->sample_rate = avctx->sample_rate = samplerate;
>> -
>>       usac->core_sbr_frame_len_idx = get_bits(gb, 3); /* 
>> coreSbrFrameLengthIndex */
>>       m4ac->frame_length_short = usac->core_sbr_frame_len_idx == 0 ||
>>                                  usac->core_sbr_frame_len_idx == 2;
>> @@ -354,7 +371,26 @@ int ff_aac_usac_config_decode(AACDecContext *ac, 
>> AVCodecContext *avctx,
>>                   usac->core_sbr_frame_len_idx == 4 ? 1 :
>>                   0;
>> +    if (sbr_ratio == 2) {
>> +        ratio_mult = 8;
>> +        ratio_dec = 3;
>> +    } else if (sbr_ratio == 3) {
>> +        ratio_mult = 2;
>> +        ratio_dec = 1;
>> +    } else if (sbr_ratio == 4) {
>> +        ratio_mult = 4;
>> +        ratio_dec = 1;
>> +    } else {
>> +        ratio_mult = 1;
>> +        ratio_dec = 1;
>> +    }
>> +
>> +    avctx->sample_rate = samplerate;
>> +    m4ac->ext_sample_rate = samplerate;
>> +    m4ac->sample_rate = (samplerate * ratio_dec) / ratio_mult;
>> +
>>       m4ac->sampling_index = ff_aac_sample_rate_idx(m4ac->sample_rate);
>> +    m4ac->sbr = sbr_ratio > 0;
>>       channel_config_idx = get_bits(gb, 5); /* 
>> channelConfigurationIndex */
>>       if (!channel_config_idx) {
>> @@ -426,8 +462,11 @@ int ff_aac_usac_config_decode(AACDecContext *ac, 
>> AVCodecContext *avctx,
>>           case ID_USAC_SCE: /* SCE */
>>               /* UsacCoreConfig */
>>               decode_usac_element_core(e, gb, sbr_ratio);
>> -            if (e->sbr.ratio > 0)
>> -                decode_usac_sbr_data(e, gb);
>> +            if (e->sbr.ratio > 0) {
>> +                ret = decode_usac_sbr_data(ac, e, gb);
>> +                if (ret < 0)
>> +                    return ret;
>> +            }
>>               layout_map[map_count][0] = TYPE_SCE;
>>               layout_map[map_count][1] = elem_id[0]++;
>>               if (!map_pos_set)
>> @@ -437,7 +476,9 @@ int ff_aac_usac_config_decode(AACDecContext *ac, 
>> AVCodecContext *avctx,
>>           case ID_USAC_CPE: /* UsacChannelPairElementConf */
>>               /* UsacCoreConfig */
>>               decode_usac_element_core(e, gb, sbr_ratio);
>> -            decode_usac_element_pair(e, gb);
>> +            ret = decode_usac_element_pair(ac, e, gb);
>> +            if (ret < 0)
>> +                return ret;
>>               layout_map[map_count][0] = TYPE_CPE;
>>               layout_map[map_count][1] = elem_id[1]++;
>>               if (!map_pos_set)
>> @@ -1307,13 +1348,14 @@ static int 
>> decode_usac_core_coder(AACDecContext *ac, AACUSACConfig *usac,
>>       int ret;
>>       int arith_reset_flag;
>>       AACUsacStereo *us = &che->us;
>> +    int core_nb_channels = nb_channels;
>>       /* Local symbols */
>>       uint8_t global_gain;
>>       us->common_window = 0;
>> -    for (int ch = 0; ch < nb_channels; ch++) {
>> +    for (int ch = 0; ch < core_nb_channels; ch++) {
>>           SingleChannelElement *sce = &che->ch[ch];
>>           AACUsacElemData *ue = &sce->ue;
>> @@ -1323,13 +1365,16 @@ static int 
>> decode_usac_core_coder(AACDecContext *ac, AACUSACConfig *usac,
>>           ue->core_mode = get_bits1(gb);
>>       }
>> -    if (nb_channels == 2) {
>> +    if (nb_channels > 1 && ec->stereo_config_index == 1)
>> +        core_nb_channels = 1;
>> +
>> +    if (core_nb_channels == 2) {
>>           ret = decode_usac_stereo_info(ac, usac, ec, che, gb, 
>> indep_flag);
>>           if (ret)
>>               return ret;
>>       }
>> -    for (int ch = 0; ch < nb_channels; ch++) {
>> +    for (int ch = 0; ch < core_nb_channels; ch++) {
>>           SingleChannelElement *sce = &che->ch[ch];
>>           IndividualChannelStream *ics = &sce->ics;
>>           AACUsacElemData *ue = &sce->ue;
>> @@ -1341,7 +1386,7 @@ static int decode_usac_core_coder(AACDecContext 
>> *ac, AACUSACConfig *usac,
>>               continue;
>>           }
>> -        if ((nb_channels == 1) ||
>> +        if ((core_nb_channels == 1) ||
>>               (che->ch[0].ue.core_mode != che->ch[1].ue.core_mode))
>>               ue->tns_data_present = get_bits1(gb);
>> @@ -1424,7 +1469,29 @@ static int decode_usac_core_coder(AACDecContext 
>> *ac, AACUSACConfig *usac,
>>           }
>>       }
>> -    spectrum_decode(ac, usac, che, nb_channels);
>> +    if (ec->sbr.ratio) {
>> +        int sbr_ch = nb_channels;
>> +        if (nb_channels == 2 &&
>> +            !(ec->stereo_config_index == 0 || ec->stereo_config_index 
>> == 3))
>> +            sbr_ch = 1;
>> +
>> +        ret = ff_aac_sbr_decode_usac_data(ac, che, ec, gb, sbr_ch, 
>> indep_flag);
>> +        if (ret < 0)
>> +            return ret;
>> +
>> +        if (ec->stereo_config_index) {
>> +            avpriv_report_missing_feature(ac->avctx, "AAC USAC Mps212");
>> +            return AVERROR_PATCHWELCOME;
>> +        }
>> +    }
>> +
>> +    spectrum_decode(ac, usac, che, core_nb_channels);
>> +
>> +    if (ac->oc[1].m4ac.sbr > 0) {
>> +        ac->proc.sbr_apply(ac, che, nb_channels == 2 ? TYPE_CPE : 
>> TYPE_SCE,
>> +                           che->ch[0].output,
>> +                           che->ch[1].output);
>> +    }
>>       return 0;
>>   }
>> @@ -1591,9 +1658,29 @@ int ff_aac_usac_decode_frame(AVCodecContext 
>> *avctx, AACDecContext *ac,
>>       int indep_flag, samples = 0;
>>       int audio_found = 0;
>>       int elem_id[3 /* SCE, CPE, LFE */] = { 0, 0, 0 };
>> -
>>       AVFrame *frame = ac->frame;
>> +    int ratio_mult, ratio_dec;
>> +    AACUSACConfig *usac = &ac->oc[1].usac;
>> +    int sbr_ratio = usac->core_sbr_frame_len_idx == 2 ? 2 :
>> +                    usac->core_sbr_frame_len_idx == 3 ? 3 :
>> +                    usac->core_sbr_frame_len_idx == 4 ? 1 :
>> +                    0;
>> +
>> +    if (sbr_ratio == 2) {
>> +        ratio_mult = 8;
>> +        ratio_dec = 3;
>> +    } else if (sbr_ratio == 3) {
>> +        ratio_mult = 2;
>> +        ratio_dec = 1;
>> +    } else if (sbr_ratio == 4) {
>> +        ratio_mult = 4;
>> +        ratio_dec = 1;
>> +    } else {
>> +        ratio_mult = 1;
>> +        ratio_dec = 1;
>> +    }
>> +
>>       ff_aac_output_configure(ac, ac->oc[1].layout_map, ac- 
>> >oc[1].layout_map_tags,
>>                               ac->oc[1].status, 0);
>> @@ -1660,8 +1747,10 @@ int ff_aac_usac_decode_frame(AVCodecContext 
>> *avctx, AACDecContext *ac,
>>       if (audio_found)
>>           samples = ac->oc[1].m4ac.frame_length_short ? 768 : 1024;
>> +    samples = (samples * ratio_mult) / ratio_dec;
>> +
>>       if (ac->oc[1].status && audio_found) {
>> -        avctx->sample_rate = ac->oc[1].m4ac.sample_rate;
>> +        avctx->sample_rate = ac->oc[1].m4ac.ext_sample_rate;
>>           avctx->frame_size = samples;
>>           ac->oc[1].status = OC_LOCKED;
>>       }
>> diff --git a/libavcodec/aacsbr.h b/libavcodec/aacsbr.h
>> index d4582d1100..3958b43b91 100644
>> --- a/libavcodec/aacsbr.h
>> +++ b/libavcodec/aacsbr.h
>> @@ -88,6 +88,17 @@ int ff_aac_sbr_decode_extension(AACDecContext *ac, 
>> ChannelElement *che,
>>   int ff_aac_sbr_decode_extension_fixed(AACDecContext *ac, 
>> ChannelElement *che,
>>                                         GetBitContext *gb, int crc, 
>> int cnt, int id_aac);
>> +/** Due to channel allocation not being known upon SBR parameter 
>> transmission,
>> + * supply the parameters separately.
>> + * Functionally identical to ff_aac_sbr_decode_extension() */
>> +int ff_aac_sbr_config_usac(AACDecContext *ac, ChannelElement *che,
>> +                           AACUsacElemConfig *ue);
>> +
>> +/** Decode frame SBR data, USAC. */
>> +int ff_aac_sbr_decode_usac_data(AACDecContext *ac, ChannelElement *che,
>> +                                AACUsacElemConfig *ue, GetBitContext 
>> *gb,
>> +                                int sbr_ch, int indep_flag);
>> +
>>   /** Apply one SBR element to one AAC element. */
>>   void ff_aac_sbr_apply(AACDecContext *ac, ChannelElement *che,
>>                         int id_aac, void /* float */ *L, void /* float 
>> */ *R);
>> diff --git a/libavcodec/aacsbr_template.c b/libavcodec/aacsbr_template.c
>> index 86f4d8c26e..e5bc4d4659 100644
>> --- a/libavcodec/aacsbr_template.c
>> +++ b/libavcodec/aacsbr_template.c
>> @@ -57,6 +57,7 @@ av_cold void AAC_RENAME(ff_aac_sbr_init)(void)
>>   /** Places SBR in pure upsampling mode. */
>>   static void sbr_turnoff(SpectralBandReplication *sbr) {
>>       sbr->start = 0;
>> +    sbr->usac = 0;
>>       sbr->ready_for_dequant = 0;
>>       // Init defults used in pure upsampling mode
>>       sbr->kx[1] = 32; //Typo in spec, kx' inits to 32
>> @@ -184,7 +185,8 @@ static void 
>> sbr_make_f_tablelim(SpectralBandReplication *sbr)
>>       }
>>   }
>> -static unsigned int read_sbr_header(SpectralBandReplication *sbr, 
>> GetBitContext *gb)
>> +static unsigned int read_sbr_header(SpectralBandReplication *sbr,
>> +                                    GetBitContext *gb, int is_usac)
>>   {
>>       unsigned int cnt = get_bits_count(gb);
>>       uint8_t bs_header_extra_1;
>> @@ -194,15 +196,20 @@ static unsigned int 
>> read_sbr_header(SpectralBandReplication *sbr, GetBitContext
>>       sbr->start = 1;
>>       sbr->ready_for_dequant = 0;
>> +    sbr->usac = is_usac;
>>       // Save last spectrum parameters variables to compare to new ones
>>       memcpy(&old_spectrum_params, &sbr->spectrum_params, 
>> sizeof(SpectrumParameters));
>> -    sbr->bs_amp_res_header              = get_bits1(gb);
>> +    if (!is_usac)
>> +        sbr->bs_amp_res_header          = get_bits1(gb);
>> +
>>       sbr->spectrum_params.bs_start_freq  = get_bits(gb, 4);
>>       sbr->spectrum_params.bs_stop_freq   = get_bits(gb, 4);
>> -    sbr->spectrum_params.bs_xover_band  = get_bits(gb, 3);
>> -                                          skip_bits(gb, 2); // 
>> bs_reserved
>> +
>> +    if (!is_usac)
>> +        sbr->spectrum_params.bs_xover_band = get_bits(gb, 3);
>> +                                             skip_bits(gb, 2); // 
>> bs_reserved
>>       bs_header_extra_1 = get_bits1(gb);
>>       bs_header_extra_2 = get_bits1(gb);
>> @@ -645,7 +652,7 @@ static int read_sbr_grid(AACDecContext *ac, 
>> SpectralBandReplication *sbr,
>>       switch (bs_frame_class = get_bits(gb, 2)) {
>>       case FIXFIX:
>>           bs_num_env = 1 << get_bits(gb, 2);
>> -        if (bs_num_env > 4) {
>> +        if (bs_num_env > (sbr->usac ? 8 : 5)) {
>>               av_log(ac->avctx, AV_LOG_ERROR,
>>                      "Invalid bitstream, too many SBR envelopes in 
>> FIXFIX type SBR frame: %d\n",
>>                      bs_num_env);
>> @@ -793,10 +800,26 @@ static void copy_sbr_grid(SBRData *dst, const 
>> SBRData *src) {
>>   /// Read how the envelope and noise floor data is delta coded
>>   static void read_sbr_dtdf(SpectralBandReplication *sbr, 
>> GetBitContext *gb,
>> -                          SBRData *ch_data)
>> +                          SBRData *ch_data, int indep_flag)
>>   {
>> -    get_bits1_vector(gb, ch_data->bs_df_env,   ch_data->bs_num_env);
>> -    get_bits1_vector(gb, ch_data->bs_df_noise, ch_data->bs_num_noise);
>> +    if (sbr->usac) {
>> +        if (indep_flag) {
>> +            ch_data->bs_df_env[0] = 0;
>> +            get_bits1_vector(gb, &ch_data->bs_df_env[1], ch_data- 
>> >bs_num_env - 1);
>> +        } else {
>> +            get_bits1_vector(gb, ch_data->bs_df_env, ch_data- 
>> >bs_num_env);
>> +        }
>> +
>> +        if (indep_flag) {
>> +            ch_data->bs_df_noise[0] = 0;
>> +            get_bits1_vector(gb, &ch_data->bs_df_noise[1], ch_data- 
>> >bs_num_noise - 1);
>> +        } else {
>> +            get_bits1_vector(gb, ch_data->bs_df_noise, ch_data- 
>> >bs_num_noise);
>> +        }
>> +    } else {
>> +        get_bits1_vector(gb, ch_data->bs_df_env,   ch_data->bs_num_env);
>> +        get_bits1_vector(gb, ch_data->bs_df_noise, ch_data- 
>> >bs_num_noise);
>> +    }
>>   }
>>   /// Read inverse filtering data
>> @@ -811,7 +834,7 @@ static void read_sbr_invf(SpectralBandReplication 
>> *sbr, GetBitContext *gb,
>>   }
>>   static int read_sbr_envelope(AACDecContext *ac, 
>> SpectralBandReplication *sbr, GetBitContext *gb,
>> -                              SBRData *ch_data, int ch)
>> +                             SBRData *ch_data, int ch)
>>   {
>>       int bits;
>>       int i, j, k;
>> @@ -881,6 +904,13 @@ static int read_sbr_envelope(AACDecContext *ac, 
>> SpectralBandReplication *sbr, Ge
>>                   }
>>               }
>>           }
>> +        if (sbr->usac) {
>> +            if (sbr->inter_tes) {
>> +                ch_data->temp_shape[i] = get_bits(gb, 1);
>> +                if (ch_data->temp_shape[i])
>> +                    ch_data->temp_shape_mode[i] = get_bits(gb, 2);
>> +            }
>> +        }
>>       }
>>       //assign 0th elements of env_facs_q from last elements
>> @@ -970,7 +1000,7 @@ static int 
>> read_sbr_single_channel_element(AACDecContext *ac,
>>       if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]))
>>           return -1;
>> -    read_sbr_dtdf(sbr, gb, &sbr->data[0]);
>> +    read_sbr_dtdf(sbr, gb, &sbr->data[0], 0);
>>       read_sbr_invf(sbr, gb, &sbr->data[0]);
>>       if((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[0], 0)) < 0)
>>           return ret;
>> @@ -996,8 +1026,8 @@ static int 
>> read_sbr_channel_pair_element(AACDecContext *ac,
>>           if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]))
>>               return -1;
>>           copy_sbr_grid(&sbr->data[1], &sbr->data[0]);
>> -        read_sbr_dtdf(sbr, gb, &sbr->data[0]);
>> -        read_sbr_dtdf(sbr, gb, &sbr->data[1]);
>> +        read_sbr_dtdf(sbr, gb, &sbr->data[0], 0);
>> +        read_sbr_dtdf(sbr, gb, &sbr->data[1], 0);
>>           read_sbr_invf(sbr, gb, &sbr->data[0]);
>>           memcpy(sbr->data[1].bs_invf_mode[1], sbr- 
>> >data[1].bs_invf_mode[0], sizeof(sbr->data[1].bs_invf_mode[0]));
>>           memcpy(sbr->data[1].bs_invf_mode[0], sbr- 
>> >data[0].bs_invf_mode[0], sizeof(sbr->data[1].bs_invf_mode[0]));
>> @@ -1013,8 +1043,8 @@ static int 
>> read_sbr_channel_pair_element(AACDecContext *ac,
>>           if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]) ||
>>               read_sbr_grid(ac, sbr, gb, &sbr->data[1]))
>>               return -1;
>> -        read_sbr_dtdf(sbr, gb, &sbr->data[0]);
>> -        read_sbr_dtdf(sbr, gb, &sbr->data[1]);
>> +        read_sbr_dtdf(sbr, gb, &sbr->data[0], 0);
>> +        read_sbr_dtdf(sbr, gb, &sbr->data[1], 0);
>>           read_sbr_invf(sbr, gb, &sbr->data[0]);
>>           read_sbr_invf(sbr, gb, &sbr->data[1]);
>>           if((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[0], 0)) 
>> < 0)
>> @@ -1129,7 +1159,7 @@ int AAC_RENAME(ff_aac_sbr_decode_extension) 
>> (AACDecContext *ac, ChannelElement *c
>>       num_sbr_bits++;
>>       if (get_bits1(gb)) // bs_header_flag
>> -        num_sbr_bits += read_sbr_header(sbr, gb);
>> +        num_sbr_bits += read_sbr_header(sbr, gb, 0);
>>       if (sbr->reset)
>>           sbr_reset(ac, sbr);
>> @@ -1148,6 +1178,178 @@ int AAC_RENAME(ff_aac_sbr_decode_extension) 
>> (AACDecContext *ac, ChannelElement *c
>>       return cnt;
>>   }
>> +#if !USE_FIXED
>> +static void copy_usac_default_header(SpectralBandReplication *sbr,
>> +                                     AACUsacElemConfig *ue)
>> +{
>> +    sbr->inter_tes = ue->sbr.bs_intertes;
>> +
>> +    sbr->spectrum_params.bs_start_freq = ue->sbr.dflt.start_freq;
>> +    sbr->spectrum_params.bs_stop_freq = ue->sbr.dflt.stop_freq;
>> +
>> +    sbr->spectrum_params.bs_freq_scale = ue->sbr.dflt.freq_scale;
>> +    sbr->spectrum_params.bs_alter_scale = ue->sbr.dflt.alter_scale;
>> +    sbr->spectrum_params.bs_noise_bands = ue->sbr.dflt.noise_bands;
>> +
>> +    sbr->bs_limiter_bands = ue->sbr.dflt.limiter_bands;
>> +    sbr->bs_limiter_gains = ue->sbr.dflt.limiter_gains;
>> +    sbr->bs_interpol_freq = ue->sbr.dflt.interpol_freq;
>> +    sbr->bs_smoothing_mode = ue->sbr.dflt.smoothing_mode;
>> +}
>> +
>> +int ff_aac_sbr_config_usac(AACDecContext *ac, ChannelElement *che,
>> +                           AACUsacElemConfig *ue)
>> +{
>> +    SpectralBandReplication *sbr = get_sbr(che);
>> +    sbr_turnoff(sbr);
>> +    return 0;
>> +}
>> +
>> +int ff_aac_sbr_decode_usac_data(AACDecContext *ac, ChannelElement *che,
>> +                                AACUsacElemConfig *ue, GetBitContext 
>> *gb,
>> +                                int sbr_ch, int indep_flag)
>> +{
>> +    int ret;
>> +    SpectralBandReplication *sbr = get_sbr(che);
>> +    int info_present = 1;
>> +    int header_present = 1;
>> +
>> +    sbr->reset = 0;
>> +    sbr->usac = 1;
>> +
>> +    sbr->sample_rate = ac->oc[1].m4ac.ext_sample_rate;
>> +    sbr->id_aac = sbr_ch == 2 ? TYPE_CPE : TYPE_SCE;
>> +
>> +    if (!indep_flag) {
>> +        info_present = get_bits1(gb);
>> +        if (info_present)
>> +            header_present = get_bits1(gb);
>> +        else
>> +            header_present = 0;
>> +    }
>> +
>> +    if (info_present) {
>> +        /* SbrInfo() */
>> +        sbr->bs_amp_res_header = get_bits1(gb);
>> +        sbr->spectrum_params.bs_xover_band = get_bits(gb, 4);
>> +        sbr->bs_sbr_preprocessing = get_bits1(gb);
>> +        /* if (bs_pvc) ... */
>> +    }
>> +
>> +    if (header_present) {
>> +        if (get_bits1(gb)) {
>> +            int old_bs_limiter_bands = sbr->bs_limiter_bands;
>> +            SpectrumParameters old_spectrum_params;
>> +            memcpy(&old_spectrum_params, &sbr->spectrum_params,
>> +                   sizeof(SpectrumParameters));
>> +
>> +            copy_usac_default_header(sbr, ue);
>> +            // Check if spectrum parameters changed
>> +            if (memcmp(&old_spectrum_params, &sbr->spectrum_params,
>> +                       sizeof(SpectrumParameters)))
>> +                sbr->reset = 1;
>> +
>> +            if (sbr->bs_limiter_bands != old_bs_limiter_bands && ! 
>> sbr->reset)
>> +                sbr_make_f_tablelim(sbr);
>> +        } else {
>> +            read_sbr_header(sbr, gb, 1);
>> +        }
>> +
>> +        sbr->start = 1;
>> +    }
>> +
>> +    //Save some state from the previous frame.
>> +    sbr->kx[0] = sbr->kx[1];
>> +    sbr->m[0] = sbr->m[1];
>> +    sbr->kx_and_m_pushed = 1;
>> +
>> +    if (sbr->reset)
>> +        sbr_reset(ac, sbr);
>> +
>> +    sbr->ready_for_dequant = 1;
>> +
>> +    int start = get_bits_count(gb);
>> +
>> +    if (sbr_ch == 1) { /* sbr_single_channel_element */
>> +        /* if (harmonicSBR) ... */
>> +
>> +        if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]))
>> +            return -1;
>> +
>> +        read_sbr_dtdf(sbr, gb, &sbr->data[0], indep_flag);
>> +        read_sbr_invf(sbr, gb, &sbr->data[0]);
>> +
>> +        if ((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[0], 0)) 
>> < 0)
>> +            return ret;
>> +
>> +        if ((ret = read_sbr_noise(ac, sbr, gb, &sbr->data[0], 0)) < 0)
>> +            return ret;
>> +
>> +        if ((sbr->data[0].bs_add_harmonic_flag = get_bits1(gb)))
>> +            get_bits1_vector(gb, sbr->data[0].bs_add_harmonic, sbr- 
>> >n[1]);
>> +    } else if (get_bits1(gb)) { /* bs_coupling == 1 */
>> +        /* if (harmonicSBR) ... */
>> +
>> +        if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]))
>> +            return -1;
>> +        copy_sbr_grid(&sbr->data[1], &sbr->data[0]);
>> +
>> +        read_sbr_dtdf(sbr, gb, &sbr->data[0], indep_flag);
>> +        read_sbr_dtdf(sbr, gb, &sbr->data[1], indep_flag);
>> +
>> +        read_sbr_invf(sbr, gb, &sbr->data[0]);
>> +        memcpy(sbr->data[1].bs_invf_mode[1], sbr- 
>> >data[1].bs_invf_mode[0],
>> +               sizeof(sbr->data[1].bs_invf_mode[0]));
>> +        memcpy(sbr->data[1].bs_invf_mode[0], sbr- 
>> >data[0].bs_invf_mode[0],
>> +               sizeof(sbr->data[1].bs_invf_mode[0]));
>> +
>> +        if ((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[0], 0)) 
>> < 0)
>> +            return ret;
>> +        if ((ret = read_sbr_noise(ac, sbr, gb, &sbr->data[0], 0)) < 0)
>> +            return ret;
>> +
>> +        if ((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[1], 1)) 
>> < 0)
>> +            return ret;
>> +        if ((ret = read_sbr_noise(ac, sbr, gb, &sbr->data[1], 1)) < 0)
>> +            return ret;
>> +
>> +        if ((sbr->data[0].bs_add_harmonic_flag = get_bits1(gb)))
>> +            get_bits1_vector(gb, sbr->data[0].bs_add_harmonic, sbr- 
>> >n[1]);
>> +        if ((sbr->data[1].bs_add_harmonic_flag = get_bits1(gb)))
>> +            get_bits1_vector(gb, sbr->data[1].bs_add_harmonic, sbr- 
>> >n[1]);
>> +    } else { /* bs_coupling == 0 */
>> +        /* if (harmonicSBR) ... */
>> +        if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]))
>> +            return -1;
>> +        if (read_sbr_grid(ac, sbr, gb, &sbr->data[1]))
>> +            return -1;
>> +
>> +        read_sbr_dtdf(sbr, gb, &sbr->data[0], indep_flag);
>> +        read_sbr_dtdf(sbr, gb, &sbr->data[1], indep_flag);
>> +
>> +        read_sbr_invf(sbr, gb, &sbr->data[0]);
>> +        read_sbr_invf(sbr, gb, &sbr->data[1]);
>> +
>> +        if ((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[0], 0)) 
>> < 0)
>> +            return ret;
>> +        if ((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[1], 1)) 
>> < 0)
>> +            return ret;
>> +
>> +        if ((ret = read_sbr_noise(ac, sbr, gb, &sbr->data[0], 0)) < 0)
>> +            return ret;
>> +        if ((ret = read_sbr_noise(ac, sbr, gb, &sbr->data[1], 1)) < 0)
>> +            return ret;
>> +
>> +        if ((sbr->data[0].bs_add_harmonic_flag = get_bits1(gb)))
>> +            get_bits1_vector(gb, sbr->data[0].bs_add_harmonic, sbr- 
>> >n[1]);
>> +        if ((sbr->data[1].bs_add_harmonic_flag = get_bits1(gb)))
>> +            get_bits1_vector(gb, sbr->data[1].bs_add_harmonic, sbr- 
>> >n[1]);
>> +    }
>> +
>> +    return 0;
>> +}
>> +#endif
>> +
>>   /**
>>    * Analysis QMF Bank (14496-3 sp04 p206)
>>    *
>> diff --git a/libavcodec/sbr.h b/libavcodec/sbr.h
>> index fe3a39603a..40bb30e04d 100644
>> --- a/libavcodec/sbr.h
>> +++ b/libavcodec/sbr.h
>> @@ -68,9 +68,9 @@ typedef struct SBRData {
>>       unsigned           bs_frame_class;
>>       unsigned           bs_add_harmonic_flag;
>>       AAC_SIGNE          bs_num_env;
>> -    uint8_t            bs_freq_res[7];
>> +    uint8_t            bs_freq_res[9];
>>       AAC_SIGNE          bs_num_noise;
>> -    uint8_t            bs_df_env[5];
>> +    uint8_t            bs_df_env[9];
>>       uint8_t            bs_df_noise[2];
>>       uint8_t            bs_invf_mode[2][5];
>>       uint8_t            bs_add_harmonic[48];
>> @@ -95,21 +95,24 @@ typedef struct SBRData {
>>       DECLARE_ALIGNED(16, INTFLOAT, Y)[2][38][64][2];
>>       DECLARE_ALIGNED(16, AAC_FLOAT, g_temp)[42][48];
>>       AAC_FLOAT          q_temp[42][48];
>> -    uint8_t            s_indexmapped[8][48];
>> +    uint8_t            s_indexmapped[9][48];
>>       ///Envelope scalefactors
>> -    uint8_t            env_facs_q[6][48];
>> -    AAC_FLOAT          env_facs[6][48];
>> +    uint8_t            env_facs_q[9][48];
>> +    AAC_FLOAT          env_facs[9][48];
>>       ///Noise scalefactors
>>       uint8_t            noise_facs_q[3][5];
>>       AAC_FLOAT          noise_facs[3][5];
>>       ///Envelope time borders
>> -    uint8_t            t_env[8];
>> +    uint8_t            t_env[9];
>>       ///Envelope time border of the last envelope of the previous frame
>>       uint8_t            t_env_num_env_old;
>>       ///Noise time borders
>>       uint8_t            t_q[3];
>>       unsigned           f_indexnoise;
>>       unsigned           f_indexsine;
>> +    //inter_tes (USAC)
>> +    uint8_t            temp_shape[6];
>> +    uint8_t            temp_shape_mode[6];
>>       /** @} */
>>   } SBRData;
>> @@ -142,9 +145,12 @@ struct SpectralBandReplication {
>>       int                start;
>>       int                ready_for_dequant;
>>       int                id_aac;
>> +    int                usac;
>> +    int                inter_tes; // USAC-only
>>       int                reset;
>>       SpectrumParameters spectrum_params;
>>       int                bs_amp_res_header;
>> +    int                bs_sbr_preprocessing; // USAC-only
>>       /**
>>        * @name Variables associated with bs_header_extra_2
>>        * @{
>> @@ -196,18 +202,18 @@ struct SpectralBandReplication {
>>       ///First coefficient used to filter the subband signals
>>       DECLARE_ALIGNED(16, INTFLOAT, alpha1)[64][2];
>>       ///Dequantized envelope scalefactors, remapped
>> -    AAC_FLOAT          e_origmapped[7][48];
>> +    AAC_FLOAT          e_origmapped[8][48];
>>       ///Dequantized noise scalefactors, remapped
>> -    AAC_FLOAT          q_mapped[7][48];
>> +    AAC_FLOAT          q_mapped[8][48];
>>       ///Sinusoidal presence, remapped
>> -    uint8_t            s_mapped[7][48];
>> +    uint8_t            s_mapped[8][48];
>>       ///Estimated envelope
>> -    AAC_FLOAT          e_curr[7][48];
>> +    AAC_FLOAT          e_curr[8][48];
>>       ///Amplitude adjusted noise scalefactors
>> -    AAC_FLOAT          q_m[7][48];
>> +    AAC_FLOAT          q_m[8][48];
>>       ///Sinusoidal levels
>> -    AAC_FLOAT          s_m[7][48];
>> -    AAC_FLOAT          gain[7][48];
>> +    AAC_FLOAT          s_m[8][48];
>> +    AAC_FLOAT          gain[8][48];
>>       DECLARE_ALIGNED(32, INTFLOAT, qmf_filter_scratch)[5][64];
>>       AVTXContext       *mdct_ana;
>>       av_tx_fn           mdct_ana_fn;
> 
> I'll wait 2 more days before merging this patch, but I'll push the other 
> 5 fix/prep patches tomorrow.

Last patch pushed.
diff mbox series

Patch

diff --git a/libavcodec/aac/aacdec_usac.c b/libavcodec/aac/aacdec_usac.c
index e5504117d0..132ffee9c2 100644
--- a/libavcodec/aac/aacdec_usac.c
+++ b/libavcodec/aac/aacdec_usac.c
@@ -23,6 +23,8 @@ 
 #include "aacdec_lpd.h"
 #include "aacdec_ac.h"
 
+#include "libavcodec/aacsbr.h"
+
 #include "libavcodec/aactab.h"
 #include "libavutil/mem.h"
 #include "libavcodec/mpeg4audio.h"
@@ -145,7 +147,8 @@  static int decode_loudness_set(AACDecContext *ac, AACUSACConfig *usac,
     return 0;
 }
 
-static void decode_usac_sbr_data(AACUsacElemConfig *e, GetBitContext *gb)
+static int decode_usac_sbr_data(AACDecContext *ac,
+                                AACUsacElemConfig *e, GetBitContext *gb)
 {
     uint8_t header_extra1;
     uint8_t header_extra2;
@@ -153,6 +156,10 @@  static void decode_usac_sbr_data(AACUsacElemConfig *e, GetBitContext *gb)
     e->sbr.harmonic_sbr = get_bits1(gb); /* harmonicSBR */
     e->sbr.bs_intertes = get_bits1(gb); /* bs_interTes */
     e->sbr.bs_pvc = get_bits1(gb); /* bs_pvc */
+    if (e->sbr.harmonic_sbr || e->sbr.bs_intertes || e->sbr.bs_pvc) {
+        avpriv_report_missing_feature(ac->avctx, "AAC USAC eSBR");
+        return AVERROR_PATCHWELCOME;
+    }
 
     e->sbr.dflt.start_freq = get_bits(gb, 4); /* dflt_start_freq */
     e->sbr.dflt.stop_freq = get_bits(gb, 4); /* dflt_stop_freq */
@@ -179,6 +186,8 @@  static void decode_usac_sbr_data(AACUsacElemConfig *e, GetBitContext *gb)
         e->sbr.dflt.interpol_freq = get_bits1(gb); /* dflt_interpol_freq */
         e->sbr.dflt.smoothing_mode = get_bits1(gb); /* dflt_smoothing_mode */
     }
+
+    return 0;
 }
 
 static void decode_usac_element_core(AACUsacElemConfig *e,
@@ -190,13 +199,17 @@  static void decode_usac_element_core(AACUsacElemConfig *e,
     e->sbr.ratio = sbr_ratio;
 }
 
-static void decode_usac_element_pair(AACUsacElemConfig *e, GetBitContext *gb)
+static int decode_usac_element_pair(AACDecContext *ac,
+                                    AACUsacElemConfig *e, GetBitContext *gb)
 {
     e->stereo_config_index = 0;
     if (e->sbr.ratio) {
-        decode_usac_sbr_data(e, gb);
+        int ret = decode_usac_sbr_data(ac, e, gb);
+        if (ret < 0)
+            return ret;
         e->stereo_config_index = get_bits(gb, 2);
     }
+
     if (e->stereo_config_index) {
         e->mps.freq_res = get_bits(gb, 3); /* bsFreqRes */
         e->mps.fixed_gain = get_bits(gb, 3); /* bsFixedGainDMX */
@@ -216,6 +229,8 @@  static void decode_usac_element_pair(AACUsacElemConfig *e, GetBitContext *gb)
         if (e->mps.temp_shape_config == 2)
             e->mps.env_quant_mode = get_bits1(gb); /* bsEnvQuantMode */
     }
+
+    return 0;
 }
 
 static int decode_usac_extension(AACDecContext *ac, AACUsacElemConfig *e,
@@ -294,6 +309,9 @@  int ff_aac_usac_reset_state(AACDecContext *ac, OutputConfiguration *oc)
             AACUsacStereo *us = &che->us;
             memset(us, 0, sizeof(*us));
 
+            if (e->sbr.ratio)
+                ff_aac_sbr_config_usac(ac, che, e);
+
             for (int j = 0; j < ch; j++) {
                 SingleChannelElement *sce = &che->ch[ch];
                 AACUsacElemData *ue = &sce->ue;
@@ -320,6 +338,7 @@  int ff_aac_usac_config_decode(AACDecContext *ac, AVCodecContext *avctx,
     uint8_t freq_idx;
     uint8_t channel_config_idx;
     int nb_channels = 0;
+    int ratio_mult, ratio_dec;
     int samplerate;
     int sbr_ratio;
     MPEG4AudioConfig *m4ac = &oc->m4ac;
@@ -340,8 +359,6 @@  int ff_aac_usac_config_decode(AACDecContext *ac, AVCodecContext *avctx,
             return AVERROR(EINVAL);
     }
 
-    m4ac->sample_rate = avctx->sample_rate = samplerate;
-
     usac->core_sbr_frame_len_idx = get_bits(gb, 3); /* coreSbrFrameLengthIndex */
     m4ac->frame_length_short = usac->core_sbr_frame_len_idx == 0 ||
                                usac->core_sbr_frame_len_idx == 2;
@@ -354,7 +371,26 @@  int ff_aac_usac_config_decode(AACDecContext *ac, AVCodecContext *avctx,
                 usac->core_sbr_frame_len_idx == 4 ? 1 :
                 0;
 
+    if (sbr_ratio == 2) {
+        ratio_mult = 8;
+        ratio_dec = 3;
+    } else if (sbr_ratio == 3) {
+        ratio_mult = 2;
+        ratio_dec = 1;
+    } else if (sbr_ratio == 4) {
+        ratio_mult = 4;
+        ratio_dec = 1;
+    } else {
+        ratio_mult = 1;
+        ratio_dec = 1;
+    }
+
+    avctx->sample_rate = samplerate;
+    m4ac->ext_sample_rate = samplerate;
+    m4ac->sample_rate = (samplerate * ratio_dec) / ratio_mult;
+
     m4ac->sampling_index = ff_aac_sample_rate_idx(m4ac->sample_rate);
+    m4ac->sbr = sbr_ratio > 0;
 
     channel_config_idx = get_bits(gb, 5); /* channelConfigurationIndex */
     if (!channel_config_idx) {
@@ -426,8 +462,11 @@  int ff_aac_usac_config_decode(AACDecContext *ac, AVCodecContext *avctx,
         case ID_USAC_SCE: /* SCE */
             /* UsacCoreConfig */
             decode_usac_element_core(e, gb, sbr_ratio);
-            if (e->sbr.ratio > 0)
-                decode_usac_sbr_data(e, gb);
+            if (e->sbr.ratio > 0) {
+                ret = decode_usac_sbr_data(ac, e, gb);
+                if (ret < 0)
+                    return ret;
+            }
             layout_map[map_count][0] = TYPE_SCE;
             layout_map[map_count][1] = elem_id[0]++;
             if (!map_pos_set)
@@ -437,7 +476,9 @@  int ff_aac_usac_config_decode(AACDecContext *ac, AVCodecContext *avctx,
         case ID_USAC_CPE: /* UsacChannelPairElementConf */
             /* UsacCoreConfig */
             decode_usac_element_core(e, gb, sbr_ratio);
-            decode_usac_element_pair(e, gb);
+            ret = decode_usac_element_pair(ac, e, gb);
+            if (ret < 0)
+                return ret;
             layout_map[map_count][0] = TYPE_CPE;
             layout_map[map_count][1] = elem_id[1]++;
             if (!map_pos_set)
@@ -1307,13 +1348,14 @@  static int decode_usac_core_coder(AACDecContext *ac, AACUSACConfig *usac,
     int ret;
     int arith_reset_flag;
     AACUsacStereo *us = &che->us;
+    int core_nb_channels = nb_channels;
 
     /* Local symbols */
     uint8_t global_gain;
 
     us->common_window = 0;
 
-    for (int ch = 0; ch < nb_channels; ch++) {
+    for (int ch = 0; ch < core_nb_channels; ch++) {
         SingleChannelElement *sce = &che->ch[ch];
         AACUsacElemData *ue = &sce->ue;
 
@@ -1323,13 +1365,16 @@  static int decode_usac_core_coder(AACDecContext *ac, AACUSACConfig *usac,
         ue->core_mode = get_bits1(gb);
     }
 
-    if (nb_channels == 2) {
+    if (nb_channels > 1 && ec->stereo_config_index == 1)
+        core_nb_channels = 1;
+
+    if (core_nb_channels == 2) {
         ret = decode_usac_stereo_info(ac, usac, ec, che, gb, indep_flag);
         if (ret)
             return ret;
     }
 
-    for (int ch = 0; ch < nb_channels; ch++) {
+    for (int ch = 0; ch < core_nb_channels; ch++) {
         SingleChannelElement *sce = &che->ch[ch];
         IndividualChannelStream *ics = &sce->ics;
         AACUsacElemData *ue = &sce->ue;
@@ -1341,7 +1386,7 @@  static int decode_usac_core_coder(AACDecContext *ac, AACUSACConfig *usac,
             continue;
         }
 
-        if ((nb_channels == 1) ||
+        if ((core_nb_channels == 1) ||
             (che->ch[0].ue.core_mode != che->ch[1].ue.core_mode))
             ue->tns_data_present = get_bits1(gb);
 
@@ -1424,7 +1469,29 @@  static int decode_usac_core_coder(AACDecContext *ac, AACUSACConfig *usac,
         }
     }
 
-    spectrum_decode(ac, usac, che, nb_channels);
+    if (ec->sbr.ratio) {
+        int sbr_ch = nb_channels;
+        if (nb_channels == 2 &&
+            !(ec->stereo_config_index == 0 || ec->stereo_config_index == 3))
+            sbr_ch = 1;
+
+        ret = ff_aac_sbr_decode_usac_data(ac, che, ec, gb, sbr_ch, indep_flag);
+        if (ret < 0)
+            return ret;
+
+        if (ec->stereo_config_index) {
+            avpriv_report_missing_feature(ac->avctx, "AAC USAC Mps212");
+            return AVERROR_PATCHWELCOME;
+        }
+    }
+
+    spectrum_decode(ac, usac, che, core_nb_channels);
+
+    if (ac->oc[1].m4ac.sbr > 0) {
+        ac->proc.sbr_apply(ac, che, nb_channels == 2 ? TYPE_CPE : TYPE_SCE,
+                           che->ch[0].output,
+                           che->ch[1].output);
+    }
 
     return 0;
 }
@@ -1591,9 +1658,29 @@  int ff_aac_usac_decode_frame(AVCodecContext *avctx, AACDecContext *ac,
     int indep_flag, samples = 0;
     int audio_found = 0;
     int elem_id[3 /* SCE, CPE, LFE */] = { 0, 0, 0 };
-
     AVFrame *frame = ac->frame;
 
+    int ratio_mult, ratio_dec;
+    AACUSACConfig *usac = &ac->oc[1].usac;
+    int sbr_ratio = usac->core_sbr_frame_len_idx == 2 ? 2 :
+                    usac->core_sbr_frame_len_idx == 3 ? 3 :
+                    usac->core_sbr_frame_len_idx == 4 ? 1 :
+                    0;
+
+    if (sbr_ratio == 2) {
+        ratio_mult = 8;
+        ratio_dec = 3;
+    } else if (sbr_ratio == 3) {
+        ratio_mult = 2;
+        ratio_dec = 1;
+    } else if (sbr_ratio == 4) {
+        ratio_mult = 4;
+        ratio_dec = 1;
+    } else {
+        ratio_mult = 1;
+        ratio_dec = 1;
+    }
+
     ff_aac_output_configure(ac, ac->oc[1].layout_map, ac->oc[1].layout_map_tags,
                             ac->oc[1].status, 0);
 
@@ -1660,8 +1747,10 @@  int ff_aac_usac_decode_frame(AVCodecContext *avctx, AACDecContext *ac,
     if (audio_found)
         samples = ac->oc[1].m4ac.frame_length_short ? 768 : 1024;
 
+    samples = (samples * ratio_mult) / ratio_dec;
+
     if (ac->oc[1].status && audio_found) {
-        avctx->sample_rate = ac->oc[1].m4ac.sample_rate;
+        avctx->sample_rate = ac->oc[1].m4ac.ext_sample_rate;
         avctx->frame_size = samples;
         ac->oc[1].status = OC_LOCKED;
     }
diff --git a/libavcodec/aacsbr.h b/libavcodec/aacsbr.h
index d4582d1100..3958b43b91 100644
--- a/libavcodec/aacsbr.h
+++ b/libavcodec/aacsbr.h
@@ -88,6 +88,17 @@  int ff_aac_sbr_decode_extension(AACDecContext *ac, ChannelElement *che,
 int ff_aac_sbr_decode_extension_fixed(AACDecContext *ac, ChannelElement *che,
                                       GetBitContext *gb, int crc, int cnt, int id_aac);
 
+/** Due to channel allocation not being known upon SBR parameter transmission,
+ * supply the parameters separately.
+ * Functionally identical to ff_aac_sbr_decode_extension() */
+int ff_aac_sbr_config_usac(AACDecContext *ac, ChannelElement *che,
+                           AACUsacElemConfig *ue);
+
+/** Decode frame SBR data, USAC. */
+int ff_aac_sbr_decode_usac_data(AACDecContext *ac, ChannelElement *che,
+                                AACUsacElemConfig *ue, GetBitContext *gb,
+                                int sbr_ch, int indep_flag);
+
 /** Apply one SBR element to one AAC element. */
 void ff_aac_sbr_apply(AACDecContext *ac, ChannelElement *che,
                       int id_aac, void /* float */ *L, void /* float */ *R);
diff --git a/libavcodec/aacsbr_template.c b/libavcodec/aacsbr_template.c
index 86f4d8c26e..e5bc4d4659 100644
--- a/libavcodec/aacsbr_template.c
+++ b/libavcodec/aacsbr_template.c
@@ -57,6 +57,7 @@  av_cold void AAC_RENAME(ff_aac_sbr_init)(void)
 /** Places SBR in pure upsampling mode. */
 static void sbr_turnoff(SpectralBandReplication *sbr) {
     sbr->start = 0;
+    sbr->usac = 0;
     sbr->ready_for_dequant = 0;
     // Init defults used in pure upsampling mode
     sbr->kx[1] = 32; //Typo in spec, kx' inits to 32
@@ -184,7 +185,8 @@  static void sbr_make_f_tablelim(SpectralBandReplication *sbr)
     }
 }
 
-static unsigned int read_sbr_header(SpectralBandReplication *sbr, GetBitContext *gb)
+static unsigned int read_sbr_header(SpectralBandReplication *sbr,
+                                    GetBitContext *gb, int is_usac)
 {
     unsigned int cnt = get_bits_count(gb);
     uint8_t bs_header_extra_1;
@@ -194,15 +196,20 @@  static unsigned int read_sbr_header(SpectralBandReplication *sbr, GetBitContext
 
     sbr->start = 1;
     sbr->ready_for_dequant = 0;
+    sbr->usac = is_usac;
 
     // Save last spectrum parameters variables to compare to new ones
     memcpy(&old_spectrum_params, &sbr->spectrum_params, sizeof(SpectrumParameters));
 
-    sbr->bs_amp_res_header              = get_bits1(gb);
+    if (!is_usac)
+        sbr->bs_amp_res_header          = get_bits1(gb);
+
     sbr->spectrum_params.bs_start_freq  = get_bits(gb, 4);
     sbr->spectrum_params.bs_stop_freq   = get_bits(gb, 4);
-    sbr->spectrum_params.bs_xover_band  = get_bits(gb, 3);
-                                          skip_bits(gb, 2); // bs_reserved
+
+    if (!is_usac)
+        sbr->spectrum_params.bs_xover_band = get_bits(gb, 3);
+                                             skip_bits(gb, 2); // bs_reserved
 
     bs_header_extra_1 = get_bits1(gb);
     bs_header_extra_2 = get_bits1(gb);
@@ -645,7 +652,7 @@  static int read_sbr_grid(AACDecContext *ac, SpectralBandReplication *sbr,
     switch (bs_frame_class = get_bits(gb, 2)) {
     case FIXFIX:
         bs_num_env = 1 << get_bits(gb, 2);
-        if (bs_num_env > 4) {
+        if (bs_num_env > (sbr->usac ? 8 : 5)) {
             av_log(ac->avctx, AV_LOG_ERROR,
                    "Invalid bitstream, too many SBR envelopes in FIXFIX type SBR frame: %d\n",
                    bs_num_env);
@@ -793,10 +800,26 @@  static void copy_sbr_grid(SBRData *dst, const SBRData *src) {
 
 /// Read how the envelope and noise floor data is delta coded
 static void read_sbr_dtdf(SpectralBandReplication *sbr, GetBitContext *gb,
-                          SBRData *ch_data)
+                          SBRData *ch_data, int indep_flag)
 {
-    get_bits1_vector(gb, ch_data->bs_df_env,   ch_data->bs_num_env);
-    get_bits1_vector(gb, ch_data->bs_df_noise, ch_data->bs_num_noise);
+    if (sbr->usac) {
+        if (indep_flag) {
+            ch_data->bs_df_env[0] = 0;
+            get_bits1_vector(gb, &ch_data->bs_df_env[1], ch_data->bs_num_env - 1);
+        } else {
+            get_bits1_vector(gb, ch_data->bs_df_env, ch_data->bs_num_env);
+        }
+
+        if (indep_flag) {
+            ch_data->bs_df_noise[0] = 0;
+            get_bits1_vector(gb, &ch_data->bs_df_noise[1], ch_data->bs_num_noise - 1);
+        } else {
+            get_bits1_vector(gb, ch_data->bs_df_noise, ch_data->bs_num_noise);
+        }
+    } else {
+        get_bits1_vector(gb, ch_data->bs_df_env,   ch_data->bs_num_env);
+        get_bits1_vector(gb, ch_data->bs_df_noise, ch_data->bs_num_noise);
+    }
 }
 
 /// Read inverse filtering data
@@ -811,7 +834,7 @@  static void read_sbr_invf(SpectralBandReplication *sbr, GetBitContext *gb,
 }
 
 static int read_sbr_envelope(AACDecContext *ac, SpectralBandReplication *sbr, GetBitContext *gb,
-                              SBRData *ch_data, int ch)
+                             SBRData *ch_data, int ch)
 {
     int bits;
     int i, j, k;
@@ -881,6 +904,13 @@  static int read_sbr_envelope(AACDecContext *ac, SpectralBandReplication *sbr, Ge
                 }
             }
         }
+        if (sbr->usac) {
+            if (sbr->inter_tes) {
+                ch_data->temp_shape[i] = get_bits(gb, 1);
+                if (ch_data->temp_shape[i])
+                    ch_data->temp_shape_mode[i] = get_bits(gb, 2);
+            }
+        }
     }
 
     //assign 0th elements of env_facs_q from last elements
@@ -970,7 +1000,7 @@  static int read_sbr_single_channel_element(AACDecContext *ac,
 
     if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]))
         return -1;
-    read_sbr_dtdf(sbr, gb, &sbr->data[0]);
+    read_sbr_dtdf(sbr, gb, &sbr->data[0], 0);
     read_sbr_invf(sbr, gb, &sbr->data[0]);
     if((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[0], 0)) < 0)
         return ret;
@@ -996,8 +1026,8 @@  static int read_sbr_channel_pair_element(AACDecContext *ac,
         if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]))
             return -1;
         copy_sbr_grid(&sbr->data[1], &sbr->data[0]);
-        read_sbr_dtdf(sbr, gb, &sbr->data[0]);
-        read_sbr_dtdf(sbr, gb, &sbr->data[1]);
+        read_sbr_dtdf(sbr, gb, &sbr->data[0], 0);
+        read_sbr_dtdf(sbr, gb, &sbr->data[1], 0);
         read_sbr_invf(sbr, gb, &sbr->data[0]);
         memcpy(sbr->data[1].bs_invf_mode[1], sbr->data[1].bs_invf_mode[0], sizeof(sbr->data[1].bs_invf_mode[0]));
         memcpy(sbr->data[1].bs_invf_mode[0], sbr->data[0].bs_invf_mode[0], sizeof(sbr->data[1].bs_invf_mode[0]));
@@ -1013,8 +1043,8 @@  static int read_sbr_channel_pair_element(AACDecContext *ac,
         if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]) ||
             read_sbr_grid(ac, sbr, gb, &sbr->data[1]))
             return -1;
-        read_sbr_dtdf(sbr, gb, &sbr->data[0]);
-        read_sbr_dtdf(sbr, gb, &sbr->data[1]);
+        read_sbr_dtdf(sbr, gb, &sbr->data[0], 0);
+        read_sbr_dtdf(sbr, gb, &sbr->data[1], 0);
         read_sbr_invf(sbr, gb, &sbr->data[0]);
         read_sbr_invf(sbr, gb, &sbr->data[1]);
         if((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[0], 0)) < 0)
@@ -1129,7 +1159,7 @@  int AAC_RENAME(ff_aac_sbr_decode_extension)(AACDecContext *ac, ChannelElement *c
 
     num_sbr_bits++;
     if (get_bits1(gb)) // bs_header_flag
-        num_sbr_bits += read_sbr_header(sbr, gb);
+        num_sbr_bits += read_sbr_header(sbr, gb, 0);
 
     if (sbr->reset)
         sbr_reset(ac, sbr);
@@ -1148,6 +1178,178 @@  int AAC_RENAME(ff_aac_sbr_decode_extension)(AACDecContext *ac, ChannelElement *c
     return cnt;
 }
 
+#if !USE_FIXED
+static void copy_usac_default_header(SpectralBandReplication *sbr,
+                                     AACUsacElemConfig *ue)
+{
+    sbr->inter_tes = ue->sbr.bs_intertes;
+
+    sbr->spectrum_params.bs_start_freq = ue->sbr.dflt.start_freq;
+    sbr->spectrum_params.bs_stop_freq = ue->sbr.dflt.stop_freq;
+
+    sbr->spectrum_params.bs_freq_scale = ue->sbr.dflt.freq_scale;
+    sbr->spectrum_params.bs_alter_scale = ue->sbr.dflt.alter_scale;
+    sbr->spectrum_params.bs_noise_bands = ue->sbr.dflt.noise_bands;
+
+    sbr->bs_limiter_bands = ue->sbr.dflt.limiter_bands;
+    sbr->bs_limiter_gains = ue->sbr.dflt.limiter_gains;
+    sbr->bs_interpol_freq = ue->sbr.dflt.interpol_freq;
+    sbr->bs_smoothing_mode = ue->sbr.dflt.smoothing_mode;
+}
+
+int ff_aac_sbr_config_usac(AACDecContext *ac, ChannelElement *che,
+                           AACUsacElemConfig *ue)
+{
+    SpectralBandReplication *sbr = get_sbr(che);
+    sbr_turnoff(sbr);
+    return 0;
+}
+
+int ff_aac_sbr_decode_usac_data(AACDecContext *ac, ChannelElement *che,
+                                AACUsacElemConfig *ue, GetBitContext *gb,
+                                int sbr_ch, int indep_flag)
+{
+    int ret;
+    SpectralBandReplication *sbr = get_sbr(che);
+    int info_present = 1;
+    int header_present = 1;
+
+    sbr->reset = 0;
+    sbr->usac = 1;
+
+    sbr->sample_rate = ac->oc[1].m4ac.ext_sample_rate;
+    sbr->id_aac = sbr_ch == 2 ? TYPE_CPE : TYPE_SCE;
+
+    if (!indep_flag) {
+        info_present = get_bits1(gb);
+        if (info_present)
+            header_present = get_bits1(gb);
+        else
+            header_present = 0;
+    }
+
+    if (info_present) {
+        /* SbrInfo() */
+        sbr->bs_amp_res_header = get_bits1(gb);
+        sbr->spectrum_params.bs_xover_band = get_bits(gb, 4);
+        sbr->bs_sbr_preprocessing = get_bits1(gb);
+        /* if (bs_pvc) ... */
+    }
+
+    if (header_present) {
+        if (get_bits1(gb)) {
+            int old_bs_limiter_bands = sbr->bs_limiter_bands;
+            SpectrumParameters old_spectrum_params;
+            memcpy(&old_spectrum_params, &sbr->spectrum_params,
+                   sizeof(SpectrumParameters));
+
+            copy_usac_default_header(sbr, ue);
+            // Check if spectrum parameters changed
+            if (memcmp(&old_spectrum_params, &sbr->spectrum_params,
+                       sizeof(SpectrumParameters)))
+                sbr->reset = 1;
+
+            if (sbr->bs_limiter_bands != old_bs_limiter_bands && !sbr->reset)
+                sbr_make_f_tablelim(sbr);
+        } else {
+            read_sbr_header(sbr, gb, 1);
+        }
+
+        sbr->start = 1;
+    }
+
+    //Save some state from the previous frame.
+    sbr->kx[0] = sbr->kx[1];
+    sbr->m[0] = sbr->m[1];
+    sbr->kx_and_m_pushed = 1;
+
+    if (sbr->reset)
+        sbr_reset(ac, sbr);
+
+    sbr->ready_for_dequant = 1;
+
+    int start = get_bits_count(gb);
+
+    if (sbr_ch == 1) { /* sbr_single_channel_element */
+        /* if (harmonicSBR) ... */
+
+        if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]))
+            return -1;
+
+        read_sbr_dtdf(sbr, gb, &sbr->data[0], indep_flag);
+        read_sbr_invf(sbr, gb, &sbr->data[0]);
+
+        if ((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[0], 0)) < 0)
+            return ret;
+
+        if ((ret = read_sbr_noise(ac, sbr, gb, &sbr->data[0], 0)) < 0)
+            return ret;
+
+        if ((sbr->data[0].bs_add_harmonic_flag = get_bits1(gb)))
+            get_bits1_vector(gb, sbr->data[0].bs_add_harmonic, sbr->n[1]);
+    } else if (get_bits1(gb)) { /* bs_coupling == 1 */
+        /* if (harmonicSBR) ... */
+
+        if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]))
+            return -1;
+        copy_sbr_grid(&sbr->data[1], &sbr->data[0]);
+
+        read_sbr_dtdf(sbr, gb, &sbr->data[0], indep_flag);
+        read_sbr_dtdf(sbr, gb, &sbr->data[1], indep_flag);
+
+        read_sbr_invf(sbr, gb, &sbr->data[0]);
+        memcpy(sbr->data[1].bs_invf_mode[1], sbr->data[1].bs_invf_mode[0],
+               sizeof(sbr->data[1].bs_invf_mode[0]));
+        memcpy(sbr->data[1].bs_invf_mode[0], sbr->data[0].bs_invf_mode[0],
+               sizeof(sbr->data[1].bs_invf_mode[0]));
+
+        if ((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[0], 0)) < 0)
+            return ret;
+        if ((ret = read_sbr_noise(ac, sbr, gb, &sbr->data[0], 0)) < 0)
+            return ret;
+
+        if ((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[1], 1)) < 0)
+            return ret;
+        if ((ret = read_sbr_noise(ac, sbr, gb, &sbr->data[1], 1)) < 0)
+            return ret;
+
+        if ((sbr->data[0].bs_add_harmonic_flag = get_bits1(gb)))
+            get_bits1_vector(gb, sbr->data[0].bs_add_harmonic, sbr->n[1]);
+        if ((sbr->data[1].bs_add_harmonic_flag = get_bits1(gb)))
+            get_bits1_vector(gb, sbr->data[1].bs_add_harmonic, sbr->n[1]);
+    } else { /* bs_coupling == 0 */
+        /* if (harmonicSBR) ... */
+        if (read_sbr_grid(ac, sbr, gb, &sbr->data[0]))
+            return -1;
+        if (read_sbr_grid(ac, sbr, gb, &sbr->data[1]))
+            return -1;
+
+        read_sbr_dtdf(sbr, gb, &sbr->data[0], indep_flag);
+        read_sbr_dtdf(sbr, gb, &sbr->data[1], indep_flag);
+
+        read_sbr_invf(sbr, gb, &sbr->data[0]);
+        read_sbr_invf(sbr, gb, &sbr->data[1]);
+
+        if ((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[0], 0)) < 0)
+            return ret;
+        if ((ret = read_sbr_envelope(ac, sbr, gb, &sbr->data[1], 1)) < 0)
+            return ret;
+
+        if ((ret = read_sbr_noise(ac, sbr, gb, &sbr->data[0], 0)) < 0)
+            return ret;
+        if ((ret = read_sbr_noise(ac, sbr, gb, &sbr->data[1], 1)) < 0)
+            return ret;
+
+        if ((sbr->data[0].bs_add_harmonic_flag = get_bits1(gb)))
+            get_bits1_vector(gb, sbr->data[0].bs_add_harmonic, sbr->n[1]);
+        if ((sbr->data[1].bs_add_harmonic_flag = get_bits1(gb)))
+            get_bits1_vector(gb, sbr->data[1].bs_add_harmonic, sbr->n[1]);
+    }
+
+    return 0;
+}
+#endif
+
 /**
  * Analysis QMF Bank (14496-3 sp04 p206)
  *
diff --git a/libavcodec/sbr.h b/libavcodec/sbr.h
index fe3a39603a..40bb30e04d 100644
--- a/libavcodec/sbr.h
+++ b/libavcodec/sbr.h
@@ -68,9 +68,9 @@  typedef struct SBRData {
     unsigned           bs_frame_class;
     unsigned           bs_add_harmonic_flag;
     AAC_SIGNE          bs_num_env;
-    uint8_t            bs_freq_res[7];
+    uint8_t            bs_freq_res[9];
     AAC_SIGNE          bs_num_noise;
-    uint8_t            bs_df_env[5];
+    uint8_t            bs_df_env[9];
     uint8_t            bs_df_noise[2];
     uint8_t            bs_invf_mode[2][5];
     uint8_t            bs_add_harmonic[48];
@@ -95,21 +95,24 @@  typedef struct SBRData {
     DECLARE_ALIGNED(16, INTFLOAT, Y)[2][38][64][2];
     DECLARE_ALIGNED(16, AAC_FLOAT, g_temp)[42][48];
     AAC_FLOAT          q_temp[42][48];
-    uint8_t            s_indexmapped[8][48];
+    uint8_t            s_indexmapped[9][48];
     ///Envelope scalefactors
-    uint8_t            env_facs_q[6][48];
-    AAC_FLOAT          env_facs[6][48];
+    uint8_t            env_facs_q[9][48];
+    AAC_FLOAT          env_facs[9][48];
     ///Noise scalefactors
     uint8_t            noise_facs_q[3][5];
     AAC_FLOAT          noise_facs[3][5];
     ///Envelope time borders
-    uint8_t            t_env[8];
+    uint8_t            t_env[9];
     ///Envelope time border of the last envelope of the previous frame
     uint8_t            t_env_num_env_old;
     ///Noise time borders
     uint8_t            t_q[3];
     unsigned           f_indexnoise;
     unsigned           f_indexsine;
+    //inter_tes (USAC)
+    uint8_t            temp_shape[6];
+    uint8_t            temp_shape_mode[6];
     /** @} */
 } SBRData;
 
@@ -142,9 +145,12 @@  struct SpectralBandReplication {
     int                start;
     int                ready_for_dequant;
     int                id_aac;
+    int                usac;
+    int                inter_tes; // USAC-only
     int                reset;
     SpectrumParameters spectrum_params;
     int                bs_amp_res_header;
+    int                bs_sbr_preprocessing; // USAC-only
     /**
      * @name Variables associated with bs_header_extra_2
      * @{
@@ -196,18 +202,18 @@  struct SpectralBandReplication {
     ///First coefficient used to filter the subband signals
     DECLARE_ALIGNED(16, INTFLOAT, alpha1)[64][2];
     ///Dequantized envelope scalefactors, remapped
-    AAC_FLOAT          e_origmapped[7][48];
+    AAC_FLOAT          e_origmapped[8][48];
     ///Dequantized noise scalefactors, remapped
-    AAC_FLOAT          q_mapped[7][48];
+    AAC_FLOAT          q_mapped[8][48];
     ///Sinusoidal presence, remapped
-    uint8_t            s_mapped[7][48];
+    uint8_t            s_mapped[8][48];
     ///Estimated envelope
-    AAC_FLOAT          e_curr[7][48];
+    AAC_FLOAT          e_curr[8][48];
     ///Amplitude adjusted noise scalefactors
-    AAC_FLOAT          q_m[7][48];
+    AAC_FLOAT          q_m[8][48];
     ///Sinusoidal levels
-    AAC_FLOAT          s_m[7][48];
-    AAC_FLOAT          gain[7][48];
+    AAC_FLOAT          s_m[8][48];
+    AAC_FLOAT          gain[8][48];
     DECLARE_ALIGNED(32, INTFLOAT, qmf_filter_scratch)[5][64];
     AVTXContext       *mdct_ana;
     av_tx_fn           mdct_ana_fn;