+/**
+ * Decode spectral data; reference: table 4.50.
+ * Dequantize and scale spectral data; reference: 4.6.3.3.
+ *
+ * @param coef array of dequantized, scaled spectral data
+ * @param sf array of scalefactors or intensity stereo positions
+ * @param pulse_present set if pulses are present
+ * @param pulse pointer to pulse data struct
+ * @param band_type array of the used band type
+ *
+ * @return Returns error status. 0 - OK, !0 - error
+ */
+static int decode_spectrum_and_dequant(AACContext *ac, float coef[1024],
+ GetBitContext *gb, float sf[120],
+ int pulse_present, const Pulse *pulse,
+ const IndividualChannelStream *ics,
+ enum BandType band_type[120])
+{
+ int i, k, g, idx = 0;
+ const int c = 1024 / ics->num_windows;
+ const uint16_t *offsets = ics->swb_offset;
+ float *coef_base = coef;
+ static const float sign_lookup[] = { 1.0f, -1.0f };
+
+ for (g = 0; g < ics->num_windows; g++)
+ memset(coef + g * 128 + offsets[ics->max_sfb], 0, sizeof(float) * (c - offsets[ics->max_sfb]));
+
+ for (g = 0; g < ics->num_window_groups; g++) {
+ for (i = 0; i < ics->max_sfb; i++, idx++) {
+ const int cur_band_type = band_type[idx];
+ const int dim = cur_band_type >= FIRST_PAIR_BT ? 2 : 4;
+ const int is_cb_unsigned = IS_CODEBOOK_UNSIGNED(cur_band_type);
+ int group;
+ if (cur_band_type == ZERO_BT || cur_band_type == INTENSITY_BT2 || cur_band_type == INTENSITY_BT) {
+ for (group = 0; group < ics->group_len[g]; group++) {
+ memset(coef + group * 128 + offsets[i], 0, (offsets[i + 1] - offsets[i]) * sizeof(float));
+ }
+ } else if (cur_band_type == NOISE_BT) {
+ for (group = 0; group < ics->group_len[g]; group++) {
+ float scale;
+ float band_energy;
+ float *cf = coef + group * 128 + offsets[i];
+ int len = offsets[i+1] - offsets[i];
+
+ for (k = 0; k < len; k++) {
+ ac->random_state = lcg_random(ac->random_state);
+ cf[k] = ac->random_state;
+ }
+
+ band_energy = ac->dsp.scalarproduct_float(cf, cf, len);
+ scale = sf[idx] / sqrtf(band_energy);
+ ac->dsp.vector_fmul_scalar(cf, cf, scale, len);
+ }
+ } else {
+ for (group = 0; group < ics->group_len[g]; group++) {
+ const float *vq[96];
+ const float **vqp = vq;
+ float *cf = coef + (group << 7) + offsets[i];
+ int len = offsets[i + 1] - offsets[i];
+
+ for (k = offsets[i]; k < offsets[i + 1]; k += dim) {
+ const int index = get_vlc2(gb, vlc_spectral[cur_band_type - 1].table, 6, 3);
+ const int coef_tmp_idx = (group << 7) + k;
+ const float *vq_ptr;
+ int j;
+ if (index >= ff_aac_spectral_sizes[cur_band_type - 1]) {
+ av_log(ac->avccontext, AV_LOG_ERROR,
+ "Read beyond end of ff_aac_codebook_vectors[%d][]. index %d >= %d\n",
+ cur_band_type - 1, index, ff_aac_spectral_sizes[cur_band_type - 1]);
+ return -1;
+ }
+ vq_ptr = &ff_aac_codebook_vectors[cur_band_type - 1][index * dim];
+ *vqp++ = vq_ptr;
+ if (is_cb_unsigned) {
+ if (vq_ptr[0])
+ coef[coef_tmp_idx ] = sign_lookup[get_bits1(gb)];
+ if (vq_ptr[1])
+ coef[coef_tmp_idx + 1] = sign_lookup[get_bits1(gb)];
+ if (dim == 4) {
+ if (vq_ptr[2])
+ coef[coef_tmp_idx + 2] = sign_lookup[get_bits1(gb)];
+ if (vq_ptr[3])
+ coef[coef_tmp_idx + 3] = sign_lookup[get_bits1(gb)];
+ }
+ if (cur_band_type == ESC_BT) {
+ for (j = 0; j < 2; j++) {
+ if (vq_ptr[j] == 64.0f) {
+ int n = 4;
+ /* The total length of escape_sequence must be < 22 bits according
+ to the specification (i.e. max is 11111111110xxxxxxxxxx). */
+ while (get_bits1(gb) && n < 15) n++;
+ if (n == 15) {
+ av_log(ac->avccontext, AV_LOG_ERROR, "error in spectral data, ESC overflow\n");
+ return -1;
+ }
+ n = (1 << n) + get_bits(gb, n);
+ coef[coef_tmp_idx + j] *= cbrtf(n) * n;
+ } else
+ coef[coef_tmp_idx + j] *= vq_ptr[j];
+ }
+ }
+ }
+ }
+
+ if (is_cb_unsigned && cur_band_type != ESC_BT) {
+ ac->dsp.vector_fmul_sv_scalar[dim>>2](
+ cf, cf, vq, sf[idx], len);
+ } else if (cur_band_type == ESC_BT) {
+ ac->dsp.vector_fmul_scalar(cf, cf, sf[idx], len);
+ } else { /* !is_cb_unsigned */
+ ac->dsp.sv_fmul_scalar[dim>>2](cf, vq, sf[idx], len);
+ }
+ }
+ }
+ }
+ coef += ics->group_len[g] << 7;
+ }
+
+ if (pulse_present) {
+ idx = 0;
+ for (i = 0; i < pulse->num_pulse; i++) {
+ float co = coef_base[ pulse->pos[i] ];
+ while (offsets[idx + 1] <= pulse->pos[i])
+ idx++;
+ if (band_type[idx] != NOISE_BT && sf[idx]) {
+ float ico = -pulse->amp[i];
+ if (co) {
+ co /= sf[idx];
+ ico = co / sqrtf(sqrtf(fabsf(co))) + (co > 0 ? -ico : ico);
+ }
+ coef_base[ pulse->pos[i] ] = cbrtf(fabsf(ico)) * ico * sf[idx];
+ }
+ }
+ }
+ return 0;
+}
+
+static av_always_inline float flt16_round(float pf)
+{
+ union float754 tmp;
+ tmp.f = pf;
+ tmp.i = (tmp.i + 0x00008000U) & 0xFFFF0000U;
+ return tmp.f;
+}
+
+static av_always_inline float flt16_even(float pf)
+{
+ union float754 tmp;
+ tmp.f = pf;
+ tmp.i = (tmp.i + 0x00007FFFU + (tmp.i & 0x00010000U >> 16)) & 0xFFFF0000U;
+ return tmp.f;
+}
+
+static av_always_inline float flt16_trunc(float pf)
+{
+ union float754 pun;
+ pun.f = pf;
+ pun.i &= 0xFFFF0000U;
+ return pun.f;
+}
+
+static void predict(AACContext *ac, PredictorState *ps, float *coef,
+ int output_enable)
+{
+ const float a = 0.953125; // 61.0 / 64
+ const float alpha = 0.90625; // 29.0 / 32
+ float e0, e1;
+ float pv;
+ float k1, k2;
+
+ k1 = ps->var0 > 1 ? ps->cor0 * flt16_even(a / ps->var0) : 0;
+ k2 = ps->var1 > 1 ? ps->cor1 * flt16_even(a / ps->var1) : 0;
+
+ pv = flt16_round(k1 * ps->r0 + k2 * ps->r1);
+ if (output_enable)
+ *coef += pv * ac->sf_scale;
+
+ e0 = *coef / ac->sf_scale;
+ e1 = e0 - k1 * ps->r0;
+
+ ps->cor1 = flt16_trunc(alpha * ps->cor1 + ps->r1 * e1);
+ ps->var1 = flt16_trunc(alpha * ps->var1 + 0.5 * (ps->r1 * ps->r1 + e1 * e1));
+ ps->cor0 = flt16_trunc(alpha * ps->cor0 + ps->r0 * e0);
+ ps->var0 = flt16_trunc(alpha * ps->var0 + 0.5 * (ps->r0 * ps->r0 + e0 * e0));
+
+ ps->r1 = flt16_trunc(a * (ps->r0 - k1 * e0));
+ ps->r0 = flt16_trunc(a * e0);
+}
+
+/**
+ * Apply AAC-Main style frequency domain prediction.
+ */
+static void apply_prediction(AACContext *ac, SingleChannelElement *sce)
+{
+ int sfb, k;
+
+ if (!sce->ics.predictor_initialized) {
+ reset_all_predictors(sce->predictor_state);
+ sce->ics.predictor_initialized = 1;
+ }
+
+ if (sce->ics.window_sequence[0] != EIGHT_SHORT_SEQUENCE) {
+ for (sfb = 0; sfb < ff_aac_pred_sfb_max[ac->m4ac.sampling_index]; sfb++) {
+ for (k = sce->ics.swb_offset[sfb]; k < sce->ics.swb_offset[sfb + 1]; k++) {
+ predict(ac, &sce->predictor_state[k], &sce->coeffs[k],
+ sce->ics.predictor_present && sce->ics.prediction_used[sfb]);
+ }
+ }
+ if (sce->ics.predictor_reset_group)
+ reset_predictor_group(sce->predictor_state, sce->ics.predictor_reset_group);
+ } else
+ reset_all_predictors(sce->predictor_state);
+}
+