michael@0: /* Copyright (c) 2007-2008 CSIRO michael@0: Copyright (c) 2007-2009 Xiph.Org Foundation michael@0: Copyright (c) 2008-2009 Gregory Maxwell michael@0: Written by Jean-Marc Valin and Gregory Maxwell */ michael@0: /* michael@0: Redistribution and use in source and binary forms, with or without michael@0: modification, are permitted provided that the following conditions michael@0: are met: michael@0: michael@0: - Redistributions of source code must retain the above copyright michael@0: notice, this list of conditions and the following disclaimer. michael@0: michael@0: - Redistributions in binary form must reproduce the above copyright michael@0: notice, this list of conditions and the following disclaimer in the michael@0: documentation and/or other materials provided with the distribution. michael@0: michael@0: THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS michael@0: ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT michael@0: LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR michael@0: A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER michael@0: OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, michael@0: EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, michael@0: PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR michael@0: PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF michael@0: LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING michael@0: NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS michael@0: SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. michael@0: */ michael@0: michael@0: #ifdef HAVE_CONFIG_H michael@0: #include "config.h" michael@0: #endif michael@0: michael@0: #include michael@0: #include "bands.h" michael@0: #include "modes.h" michael@0: #include "vq.h" michael@0: #include "cwrs.h" michael@0: #include "stack_alloc.h" michael@0: #include "os_support.h" michael@0: #include "mathops.h" michael@0: #include "rate.h" michael@0: #include "quant_bands.h" michael@0: #include "pitch.h" michael@0: michael@0: int hysteresis_decision(opus_val16 val, const opus_val16 *thresholds, const opus_val16 *hysteresis, int N, int prev) michael@0: { michael@0: int i; michael@0: for (i=0;iprev && val < thresholds[prev]+hysteresis[prev]) michael@0: i=prev; michael@0: if (i thresholds[prev-1]-hysteresis[prev-1]) michael@0: i=prev; michael@0: return i; michael@0: } michael@0: michael@0: opus_uint32 celt_lcg_rand(opus_uint32 seed) michael@0: { michael@0: return 1664525 * seed + 1013904223; michael@0: } michael@0: michael@0: /* This is a cos() approximation designed to be bit-exact on any platform. Bit exactness michael@0: with this approximation is important because it has an impact on the bit allocation */ michael@0: static opus_int16 bitexact_cos(opus_int16 x) michael@0: { michael@0: opus_int32 tmp; michael@0: opus_int16 x2; michael@0: tmp = (4096+((opus_int32)(x)*(x)))>>13; michael@0: celt_assert(tmp<=32767); michael@0: x2 = tmp; michael@0: x2 = (32767-x2) + FRAC_MUL16(x2, (-7651 + FRAC_MUL16(x2, (8277 + FRAC_MUL16(-626, x2))))); michael@0: celt_assert(x2<=32766); michael@0: return 1+x2; michael@0: } michael@0: michael@0: static int bitexact_log2tan(int isin,int icos) michael@0: { michael@0: int lc; michael@0: int ls; michael@0: lc=EC_ILOG(icos); michael@0: ls=EC_ILOG(isin); michael@0: icos<<=15-lc; michael@0: isin<<=15-ls; michael@0: return (ls-lc)*(1<<11) michael@0: +FRAC_MUL16(isin, FRAC_MUL16(isin, -2597) + 7932) michael@0: -FRAC_MUL16(icos, FRAC_MUL16(icos, -2597) + 7932); michael@0: } michael@0: michael@0: #ifdef FIXED_POINT michael@0: /* Compute the amplitude (sqrt energy) in each of the bands */ michael@0: void compute_band_energies(const CELTMode *m, const celt_sig *X, celt_ener *bandE, int end, int C, int M) michael@0: { michael@0: int i, c, N; michael@0: const opus_int16 *eBands = m->eBands; michael@0: N = M*m->shortMdctSize; michael@0: c=0; do { michael@0: for (i=0;i 0) michael@0: { michael@0: int shift = celt_ilog2(maxval)-10; michael@0: j=M*eBands[i]; do { michael@0: sum = MAC16_16(sum, EXTRACT16(VSHR32(X[j+c*N],shift)), michael@0: EXTRACT16(VSHR32(X[j+c*N],shift))); michael@0: } while (++jnbEBands] = EPSILON+VSHR32(EXTEND32(celt_sqrt(sum)),-shift); michael@0: } else { michael@0: bandE[i+c*m->nbEBands] = EPSILON; michael@0: } michael@0: /*printf ("%f ", bandE[i+c*m->nbEBands]);*/ michael@0: } michael@0: } while (++ceBands; michael@0: N = M*m->shortMdctSize; michael@0: c=0; do { michael@0: i=0; do { michael@0: opus_val16 g; michael@0: int j,shift; michael@0: opus_val16 E; michael@0: shift = celt_zlog2(bandE[i+c*m->nbEBands])-13; michael@0: E = VSHR32(bandE[i+c*m->nbEBands], shift); michael@0: g = EXTRACT16(celt_rcp(SHL32(E,3))); michael@0: j=M*eBands[i]; do { michael@0: X[j+c*N] = MULT16_16_Q15(VSHR32(freq[j+c*N],shift-1),g); michael@0: } while (++jeBands; michael@0: N = M*m->shortMdctSize; michael@0: c=0; do { michael@0: for (i=0;inbEBands] = celt_sqrt(sum); michael@0: /*printf ("%f ", bandE[i+c*m->nbEBands]);*/ michael@0: } michael@0: } while (++ceBands; michael@0: N = M*m->shortMdctSize; michael@0: c=0; do { michael@0: for (i=0;inbEBands]); michael@0: for (j=M*eBands[i];jeBands; michael@0: N = M*m->shortMdctSize; michael@0: celt_assert2(C<=2, "denormalise_bands() not implemented for >2 channels"); michael@0: c=0; do { michael@0: celt_sig * OPUS_RESTRICT f; michael@0: const celt_norm * OPUS_RESTRICT x; michael@0: f = freq+c*N; michael@0: x = X+c*N+M*eBands[start]; michael@0: for (i=0;inbEBands], SHL16((opus_val16)eMeans[i],6)); michael@0: #ifndef FIXED_POINT michael@0: g = celt_exp2(lg); michael@0: #else michael@0: /* Handle the integer part of the log energy */ michael@0: shift = 16-(lg>>DB_SHIFT); michael@0: if (shift>31) michael@0: { michael@0: shift=0; michael@0: g=0; michael@0: } else { michael@0: /* Handle the fractional part. */ michael@0: g = celt_exp2_frac(lg&((1<eBands[i+1]-m->eBands[i]; michael@0: /* depth in 1/8 bits */ michael@0: depth = (1+pulses[i])/((m->eBands[i+1]-m->eBands[i])<>1; michael@0: t = SHL32(t, (7-shift)<<1); michael@0: sqrt_1 = celt_rsqrt_norm(t); michael@0: } michael@0: #else michael@0: thresh = .5f*celt_exp2(-.125f*depth); michael@0: sqrt_1 = celt_rsqrt(N0<nbEBands+i]; michael@0: prev2 = prev2logE[c*m->nbEBands+i]; michael@0: if (C==1) michael@0: { michael@0: prev1 = MAX16(prev1,prev1logE[m->nbEBands+i]); michael@0: prev2 = MAX16(prev2,prev2logE[m->nbEBands+i]); michael@0: } michael@0: Ediff = EXTEND32(logE[c*m->nbEBands+i])-EXTEND32(MIN16(prev1,prev2)); michael@0: Ediff = MAX32(0, Ediff); michael@0: michael@0: #ifdef FIXED_POINT michael@0: if (Ediff < 16384) michael@0: { michael@0: opus_val32 r32 = SHR32(celt_exp2(-EXTRACT16(Ediff)),1); michael@0: r = 2*MIN16(16383,r32); michael@0: } else { michael@0: r = 0; michael@0: } michael@0: if (LM==3) michael@0: r = MULT16_16_Q14(23170, MIN32(23169, r)); michael@0: r = SHR16(MIN16(thresh, r),1); michael@0: r = SHR32(MULT16_16_Q15(sqrt_1, r),shift); michael@0: #else michael@0: /* r needs to be multiplied by 2 or 2*sqrt(2) depending on LM because michael@0: short blocks don't have the same energy as long */ michael@0: r = 2.f*celt_exp2(-Ediff); michael@0: if (LM==3) michael@0: r *= 1.41421356f; michael@0: r = MIN16(thresh, r); michael@0: r = r*sqrt_1; michael@0: #endif michael@0: X = X_+c*size+(m->eBands[i]<nbEBands]))-13; michael@0: #endif michael@0: left = VSHR32(bandE[i],shift); michael@0: right = VSHR32(bandE[i+m->nbEBands],shift); michael@0: norm = EPSILON + celt_sqrt(EPSILON+MULT16_16(left,left)+MULT16_16(right,right)); michael@0: a1 = DIV32_16(SHL32(EXTEND32(left),14),norm); michael@0: a2 = DIV32_16(SHL32(EXTEND32(right),14),norm); michael@0: for (j=0;j>1; michael@0: kr = celt_ilog2(Er)>>1; michael@0: #endif michael@0: t = VSHR32(El, (kl-7)<<1); michael@0: lgain = celt_rsqrt_norm(t); michael@0: t = VSHR32(Er, (kr-7)<<1); michael@0: rgain = celt_rsqrt_norm(t); michael@0: michael@0: #ifdef FIXED_POINT michael@0: if (kl < 7) michael@0: kl = 7; michael@0: if (kr < 7) michael@0: kr = 7; michael@0: #endif michael@0: michael@0: for (j=0;jeBands; michael@0: int decision; michael@0: int hf_sum=0; michael@0: michael@0: celt_assert(end>0); michael@0: michael@0: N0 = M*m->shortMdctSize; michael@0: michael@0: if (M*(eBands[end]-eBands[end-1]) <= 8) michael@0: return SPREAD_NONE; michael@0: c=0; do { michael@0: for (i=0;im->nbEBands-4) michael@0: hf_sum += 32*(tcount[1]+tcount[0])/N; michael@0: tmp = (2*tcount[2] >= N) + (2*tcount[1] >= N) + (2*tcount[0] >= N); michael@0: sum += tmp*256; michael@0: nbBands++; michael@0: } michael@0: } while (++cnbEBands+end); michael@0: *hf_average = (*hf_average+hf_sum)>>1; michael@0: hf_sum = *hf_average; michael@0: if (*tapset_decision==2) michael@0: hf_sum += 4; michael@0: else if (*tapset_decision==0) michael@0: hf_sum -= 4; michael@0: if (hf_sum > 22) michael@0: *tapset_decision=2; michael@0: else if (hf_sum > 18) michael@0: *tapset_decision=1; michael@0: else michael@0: *tapset_decision=0; michael@0: } michael@0: /*printf("%d %d %d\n", hf_sum, *hf_average, *tapset_decision);*/ michael@0: celt_assert(nbBands>0); /* end has to be non-zero */ michael@0: sum /= nbBands; michael@0: /* Recursive averaging */ michael@0: sum = (sum+*average)>>1; michael@0: *average = sum; michael@0: /* Hysteresis */ michael@0: sum = (3*sum + (((3-last_decision)<<7) + 64) + 2)>>2; michael@0: if (sum < 80) michael@0: { michael@0: decision = SPREAD_AGGRESSIVE; michael@0: } else if (sum < 256) michael@0: { michael@0: decision = SPREAD_NORMAL; michael@0: } else if (sum < 384) michael@0: { michael@0: decision = SPREAD_LIGHT; michael@0: } else { michael@0: decision = SPREAD_NONE; michael@0: } michael@0: #ifdef FUZZING michael@0: decision = rand()&0x3; michael@0: *tapset_decision=rand()%3; michael@0: #endif michael@0: return decision; michael@0: } michael@0: michael@0: /* Indexing table for converting from natural Hadamard to ordery Hadamard michael@0: This is essentially a bit-reversed Gray, on top of which we've added michael@0: an inversion of the order because we want the DC at the end rather than michael@0: the beginning. The lines are for N=2, 4, 8, 16 */ michael@0: static const int ordery_table[] = { michael@0: 1, 0, michael@0: 3, 0, 2, 1, michael@0: 7, 0, 4, 3, 6, 1, 5, 2, michael@0: 15, 0, 8, 7, 12, 3, 11, 4, 14, 1, 9, 6, 13, 2, 10, 5, michael@0: }; michael@0: michael@0: static void deinterleave_hadamard(celt_norm *X, int N0, int stride, int hadamard) michael@0: { michael@0: int i,j; michael@0: VARDECL(celt_norm, tmp); michael@0: int N; michael@0: SAVE_STACK; michael@0: N = N0*stride; michael@0: ALLOC(tmp, N, celt_norm); michael@0: celt_assert(stride>0); michael@0: if (hadamard) michael@0: { michael@0: const int *ordery = ordery_table+stride-2; michael@0: for (i=0;i>= 1; michael@0: for (i=0;i>1)) { michael@0: qn = 1; michael@0: } else { michael@0: qn = exp2_table8[qb&0x7]>>(14-(qb>>BITRES)); michael@0: qn = (qn+1)>>1<<1; michael@0: } michael@0: celt_assert(qn <= 256); michael@0: return qn; michael@0: } michael@0: michael@0: struct band_ctx { michael@0: int encode; michael@0: const CELTMode *m; michael@0: int i; michael@0: int intensity; michael@0: int spread; michael@0: int tf_change; michael@0: ec_ctx *ec; michael@0: opus_int32 remaining_bits; michael@0: const celt_ener *bandE; michael@0: opus_uint32 seed; michael@0: }; michael@0: michael@0: struct split_ctx { michael@0: int inv; michael@0: int imid; michael@0: int iside; michael@0: int delta; michael@0: int itheta; michael@0: int qalloc; michael@0: }; michael@0: michael@0: static void compute_theta(struct band_ctx *ctx, struct split_ctx *sctx, michael@0: celt_norm *X, celt_norm *Y, int N, int *b, int B, int B0, michael@0: int LM, michael@0: int stereo, int *fill) michael@0: { michael@0: int qn; michael@0: int itheta=0; michael@0: int delta; michael@0: int imid, iside; michael@0: int qalloc; michael@0: int pulse_cap; michael@0: int offset; michael@0: opus_int32 tell; michael@0: int inv=0; michael@0: int encode; michael@0: const CELTMode *m; michael@0: int i; michael@0: int intensity; michael@0: ec_ctx *ec; michael@0: const celt_ener *bandE; michael@0: michael@0: encode = ctx->encode; michael@0: m = ctx->m; michael@0: i = ctx->i; michael@0: intensity = ctx->intensity; michael@0: ec = ctx->ec; michael@0: bandE = ctx->bandE; michael@0: michael@0: /* Decide on the resolution to give to the split parameter theta */ michael@0: pulse_cap = m->logN[i]+LM*(1<>1) - (stereo&&N==2 ? QTHETA_OFFSET_TWOPHASE : QTHETA_OFFSET); michael@0: qn = compute_qn(N, *b, offset, pulse_cap, stereo); michael@0: if (stereo && i>=intensity) michael@0: qn = 1; michael@0: if (encode) michael@0: { michael@0: /* theta is the atan() of the ratio between the (normalized) michael@0: side and mid. With just that parameter, we can re-scale both michael@0: mid and side because we know that 1) they have unit norm and michael@0: 2) they are orthogonal. */ michael@0: itheta = stereo_itheta(X, Y, stereo, N); michael@0: } michael@0: tell = ec_tell_frac(ec); michael@0: if (qn!=1) michael@0: { michael@0: if (encode) michael@0: itheta = (itheta*qn+8192)>>14; michael@0: michael@0: /* Entropy coding of the angle. We use a uniform pdf for the michael@0: time split, a step for stereo, and a triangular one for the rest. */ michael@0: if (stereo && N>2) michael@0: { michael@0: int p0 = 3; michael@0: int x = itheta; michael@0: int x0 = qn/2; michael@0: int ft = p0*(x0+1) + x0; michael@0: /* Use a probability of p0 up to itheta=8192 and then use 1 after */ michael@0: if (encode) michael@0: { michael@0: ec_encode(ec,x<=x0?p0*x:(x-1-x0)+(x0+1)*p0,x<=x0?p0*(x+1):(x-x0)+(x0+1)*p0,ft); michael@0: } else { michael@0: int fs; michael@0: fs=ec_decode(ec,ft); michael@0: if (fs<(x0+1)*p0) michael@0: x=fs/p0; michael@0: else michael@0: x=x0+1+(fs-(x0+1)*p0); michael@0: ec_dec_update(ec,x<=x0?p0*x:(x-1-x0)+(x0+1)*p0,x<=x0?p0*(x+1):(x-x0)+(x0+1)*p0,ft); michael@0: itheta = x; michael@0: } michael@0: } else if (B0>1 || stereo) { michael@0: /* Uniform pdf */ michael@0: if (encode) michael@0: ec_enc_uint(ec, itheta, qn+1); michael@0: else michael@0: itheta = ec_dec_uint(ec, qn+1); michael@0: } else { michael@0: int fs=1, ft; michael@0: ft = ((qn>>1)+1)*((qn>>1)+1); michael@0: if (encode) michael@0: { michael@0: int fl; michael@0: michael@0: fs = itheta <= (qn>>1) ? itheta + 1 : qn + 1 - itheta; michael@0: fl = itheta <= (qn>>1) ? itheta*(itheta + 1)>>1 : michael@0: ft - ((qn + 1 - itheta)*(qn + 2 - itheta)>>1); michael@0: michael@0: ec_encode(ec, fl, fl+fs, ft); michael@0: } else { michael@0: /* Triangular pdf */ michael@0: int fl=0; michael@0: int fm; michael@0: fm = ec_decode(ec, ft); michael@0: michael@0: if (fm < ((qn>>1)*((qn>>1) + 1)>>1)) michael@0: { michael@0: itheta = (isqrt32(8*(opus_uint32)fm + 1) - 1)>>1; michael@0: fs = itheta + 1; michael@0: fl = itheta*(itheta + 1)>>1; michael@0: } michael@0: else michael@0: { michael@0: itheta = (2*(qn + 1) michael@0: - isqrt32(8*(opus_uint32)(ft - fm - 1) + 1))>>1; michael@0: fs = qn + 1 - itheta; michael@0: fl = ft - ((qn + 1 - itheta)*(qn + 2 - itheta)>>1); michael@0: } michael@0: michael@0: ec_dec_update(ec, fl, fl+fs, ft); michael@0: } michael@0: } michael@0: itheta = (opus_int32)itheta*16384/qn; michael@0: if (encode && stereo) michael@0: { michael@0: if (itheta==0) michael@0: intensity_stereo(m, X, Y, bandE, i, N); michael@0: else michael@0: stereo_split(X, Y, N); michael@0: } michael@0: /* NOTE: Renormalising X and Y *may* help fixed-point a bit at very high rate. michael@0: Let's do that at higher complexity */ michael@0: } else if (stereo) { michael@0: if (encode) michael@0: { michael@0: inv = itheta > 8192; michael@0: if (inv) michael@0: { michael@0: int j; michael@0: for (j=0;j2<remaining_bits > 2<inv = inv; michael@0: sctx->imid = imid; michael@0: sctx->iside = iside; michael@0: sctx->delta = delta; michael@0: sctx->itheta = itheta; michael@0: sctx->qalloc = qalloc; michael@0: } michael@0: static unsigned quant_band_n1(struct band_ctx *ctx, celt_norm *X, celt_norm *Y, int b, michael@0: celt_norm *lowband_out) michael@0: { michael@0: #ifdef RESYNTH michael@0: int resynth = 1; michael@0: #else michael@0: int resynth = !ctx->encode; michael@0: #endif michael@0: int c; michael@0: int stereo; michael@0: celt_norm *x = X; michael@0: int encode; michael@0: ec_ctx *ec; michael@0: michael@0: encode = ctx->encode; michael@0: ec = ctx->ec; michael@0: michael@0: stereo = Y != NULL; michael@0: c=0; do { michael@0: int sign=0; michael@0: if (ctx->remaining_bits>=1<remaining_bits -= 1<encode; michael@0: #endif michael@0: celt_norm *Y=NULL; michael@0: int encode; michael@0: const CELTMode *m; michael@0: int i; michael@0: int spread; michael@0: ec_ctx *ec; michael@0: michael@0: encode = ctx->encode; michael@0: m = ctx->m; michael@0: i = ctx->i; michael@0: spread = ctx->spread; michael@0: ec = ctx->ec; michael@0: michael@0: /* If we need 1.5 more bit than we can produce, split the band in two. */ michael@0: cache = m->cache.bits + m->cache.index[(LM+1)*m->nbEBands+i]; michael@0: if (LM != -1 && b > cache[cache[0]]+12 && N>2) michael@0: { michael@0: int mbits, sbits, delta; michael@0: int itheta; michael@0: int qalloc; michael@0: struct split_ctx sctx; michael@0: celt_norm *next_lowband2=NULL; michael@0: opus_int32 rebalance; michael@0: michael@0: N >>= 1; michael@0: Y = X+N; michael@0: LM -= 1; michael@0: if (B==1) michael@0: fill = (fill&1)|(fill<<1); michael@0: B = (B+1)>>1; michael@0: michael@0: compute_theta(ctx, &sctx, X, Y, N, &b, B, B0, michael@0: LM, 0, &fill); michael@0: imid = sctx.imid; michael@0: iside = sctx.iside; michael@0: delta = sctx.delta; michael@0: itheta = sctx.itheta; michael@0: qalloc = sctx.qalloc; michael@0: #ifdef FIXED_POINT michael@0: mid = imid; michael@0: side = iside; michael@0: #else michael@0: mid = (1.f/32768)*imid; michael@0: side = (1.f/32768)*iside; michael@0: #endif michael@0: michael@0: /* Give more bits to low-energy MDCTs than they would otherwise deserve */ michael@0: if (B0>1 && (itheta&0x3fff)) michael@0: { michael@0: if (itheta > 8192) michael@0: /* Rough approximation for pre-echo masking */ michael@0: delta -= delta>>(4-LM); michael@0: else michael@0: /* Corresponds to a forward-masking slope of 1.5 dB per 10 ms */ michael@0: delta = IMIN(0, delta + (N<>(5-LM))); michael@0: } michael@0: mbits = IMAX(0, IMIN(b, (b-delta)/2)); michael@0: sbits = b-mbits; michael@0: ctx->remaining_bits -= qalloc; michael@0: michael@0: if (lowband) michael@0: next_lowband2 = lowband+N; /* >32-bit split case */ michael@0: michael@0: rebalance = ctx->remaining_bits; michael@0: if (mbits >= sbits) michael@0: { michael@0: cm = quant_partition(ctx, X, N, mbits, B, michael@0: lowband, LM, michael@0: MULT16_16_P15(gain,mid), fill); michael@0: rebalance = mbits - (rebalance-ctx->remaining_bits); michael@0: if (rebalance > 3<>B)<<(B0>>1); michael@0: } else { michael@0: cm = quant_partition(ctx, Y, N, sbits, B, michael@0: next_lowband2, LM, michael@0: MULT16_16_P15(gain,side), fill>>B)<<(B0>>1); michael@0: rebalance = sbits - (rebalance-ctx->remaining_bits); michael@0: if (rebalance > 3<remaining_bits -= curr_bits; michael@0: michael@0: /* Ensures we can never bust the budget */ michael@0: while (ctx->remaining_bits < 0 && q > 0) michael@0: { michael@0: ctx->remaining_bits += curr_bits; michael@0: q--; michael@0: curr_bits = pulses2bits(m, i, LM, q); michael@0: ctx->remaining_bits -= curr_bits; michael@0: } michael@0: michael@0: if (q!=0) michael@0: { michael@0: int K = get_pulses(q); michael@0: michael@0: /* Finally do the actual quantization */ michael@0: if (encode) michael@0: { michael@0: cm = alg_quant(X, N, K, spread, B, ec michael@0: #ifdef RESYNTH michael@0: , gain michael@0: #endif michael@0: ); michael@0: } else { michael@0: cm = alg_unquant(X, N, K, spread, B, ec, gain); michael@0: } michael@0: } else { michael@0: /* If there's no pulse, fill the band anyway */ michael@0: int j; michael@0: if (resynth) michael@0: { michael@0: unsigned cm_mask; michael@0: /* B can be as large as 16, so this shift might overflow an int on a michael@0: 16-bit platform; use a long to get defined behavior.*/ michael@0: cm_mask = (unsigned)(1UL<seed = celt_lcg_rand(ctx->seed); michael@0: X[j] = (celt_norm)((opus_int32)ctx->seed>>20); michael@0: } michael@0: cm = cm_mask; michael@0: } else { michael@0: /* Folded spectrum */ michael@0: for (j=0;jseed = celt_lcg_rand(ctx->seed); michael@0: /* About 48 dB below the "normal" folding level */ michael@0: tmp = QCONST16(1.0f/256, 10); michael@0: tmp = (ctx->seed)&0x8000 ? tmp : -tmp; michael@0: X[j] = lowband[j]+tmp; michael@0: } michael@0: cm = fill; michael@0: } michael@0: renormalise_vector(X, N, gain); michael@0: } michael@0: } michael@0: } michael@0: } michael@0: michael@0: return cm; michael@0: } michael@0: michael@0: michael@0: /* This function is responsible for encoding and decoding a band for the mono case. */ michael@0: static unsigned quant_band(struct band_ctx *ctx, celt_norm *X, michael@0: int N, int b, int B, celt_norm *lowband, michael@0: int LM, celt_norm *lowband_out, michael@0: opus_val16 gain, celt_norm *lowband_scratch, int fill) michael@0: { michael@0: int N0=N; michael@0: int N_B=N; michael@0: int N_B0; michael@0: int B0=B; michael@0: int time_divide=0; michael@0: int recombine=0; michael@0: int longBlocks; michael@0: unsigned cm=0; michael@0: #ifdef RESYNTH michael@0: int resynth = 1; michael@0: #else michael@0: int resynth = !ctx->encode; michael@0: #endif michael@0: int k; michael@0: int encode; michael@0: int tf_change; michael@0: michael@0: encode = ctx->encode; michael@0: tf_change = ctx->tf_change; michael@0: michael@0: longBlocks = B0==1; michael@0: michael@0: N_B /= B; michael@0: michael@0: /* Special case for one sample */ michael@0: if (N==1) michael@0: { michael@0: return quant_band_n1(ctx, X, NULL, b, lowband_out); michael@0: } michael@0: michael@0: if (tf_change>0) michael@0: recombine = tf_change; michael@0: /* Band recombining to increase frequency resolution */ michael@0: michael@0: if (lowband_scratch && lowband && (recombine || ((N_B&1) == 0 && tf_change<0) || B0>1)) michael@0: { michael@0: int j; michael@0: for (j=0;j>k, 1<>k, 1<>4]<<2; michael@0: } michael@0: B>>=recombine; michael@0: N_B<<=recombine; michael@0: michael@0: /* Increasing the time resolution */ michael@0: while ((N_B&1) == 0 && tf_change<0) michael@0: { michael@0: if (encode) michael@0: haar1(X, N_B, B); michael@0: if (lowband) michael@0: haar1(lowband, N_B, B); michael@0: fill |= fill<>= 1; michael@0: time_divide++; michael@0: tf_change++; michael@0: } michael@0: B0=B; michael@0: N_B0 = N_B; michael@0: michael@0: /* Reorganize the samples in time order instead of frequency order */ michael@0: if (B0>1) michael@0: { michael@0: if (encode) michael@0: deinterleave_hadamard(X, N_B>>recombine, B0<>recombine, B0<1) michael@0: interleave_hadamard(X, N_B>>recombine, B0<>= 1; michael@0: N_B <<= 1; michael@0: cm |= cm>>B; michael@0: haar1(X, N_B, B); michael@0: } michael@0: michael@0: for (k=0;k>k, 1<encode; michael@0: #endif michael@0: int mbits, sbits, delta; michael@0: int itheta; michael@0: int qalloc; michael@0: struct split_ctx sctx; michael@0: int orig_fill; michael@0: int encode; michael@0: ec_ctx *ec; michael@0: michael@0: encode = ctx->encode; michael@0: ec = ctx->ec; michael@0: michael@0: /* Special case for one sample */ michael@0: if (N==1) michael@0: { michael@0: return quant_band_n1(ctx, X, Y, b, lowband_out); michael@0: } michael@0: michael@0: orig_fill = fill; michael@0: michael@0: compute_theta(ctx, &sctx, X, Y, N, &b, B, B, michael@0: LM, 1, &fill); michael@0: inv = sctx.inv; michael@0: imid = sctx.imid; michael@0: iside = sctx.iside; michael@0: delta = sctx.delta; michael@0: itheta = sctx.itheta; michael@0: qalloc = sctx.qalloc; michael@0: #ifdef FIXED_POINT michael@0: mid = imid; michael@0: side = iside; michael@0: #else michael@0: mid = (1.f/32768)*imid; michael@0: side = (1.f/32768)*iside; michael@0: #endif michael@0: michael@0: /* This is a special case for N=2 that only works for stereo and takes michael@0: advantage of the fact that mid and side are orthogonal to encode michael@0: the side with just one bit. */ michael@0: if (N==2) michael@0: { michael@0: int c; michael@0: int sign=0; michael@0: celt_norm *x2, *y2; michael@0: mbits = b; michael@0: sbits = 0; michael@0: /* Only need one bit for the side. */ michael@0: if (itheta != 0 && itheta != 16384) michael@0: sbits = 1< 8192; michael@0: ctx->remaining_bits -= qalloc+sbits; michael@0: michael@0: x2 = c ? Y : X; michael@0: y2 = c ? X : Y; michael@0: if (sbits) michael@0: { michael@0: if (encode) michael@0: { michael@0: /* Here we only need to encode a sign for the side. */ michael@0: sign = x2[0]*y2[1] - x2[1]*y2[0] < 0; michael@0: ec_enc_bits(ec, sign, 1); michael@0: } else { michael@0: sign = ec_dec_bits(ec, 1); michael@0: } michael@0: } michael@0: sign = 1-2*sign; michael@0: /* We use orig_fill here because we want to fold the side, but if michael@0: itheta==16384, we'll have cleared the low bits of fill. */ michael@0: cm = quant_band(ctx, x2, N, mbits, B, lowband, michael@0: LM, lowband_out, Q15ONE, lowband_scratch, orig_fill); michael@0: /* We don't split N=2 bands, so cm is either 1 or 0 (for a fold-collapse), michael@0: and there's no need to worry about mixing with the other channel. */ michael@0: y2[0] = -sign*x2[1]; michael@0: y2[1] = sign*x2[0]; michael@0: if (resynth) michael@0: { michael@0: celt_norm tmp; michael@0: X[0] = MULT16_16_Q15(mid, X[0]); michael@0: X[1] = MULT16_16_Q15(mid, X[1]); michael@0: Y[0] = MULT16_16_Q15(side, Y[0]); michael@0: Y[1] = MULT16_16_Q15(side, Y[1]); michael@0: tmp = X[0]; michael@0: X[0] = SUB16(tmp,Y[0]); michael@0: Y[0] = ADD16(tmp,Y[0]); michael@0: tmp = X[1]; michael@0: X[1] = SUB16(tmp,Y[1]); michael@0: Y[1] = ADD16(tmp,Y[1]); michael@0: } michael@0: } else { michael@0: /* "Normal" split code */ michael@0: opus_int32 rebalance; michael@0: michael@0: mbits = IMAX(0, IMIN(b, (b-delta)/2)); michael@0: sbits = b-mbits; michael@0: ctx->remaining_bits -= qalloc; michael@0: michael@0: rebalance = ctx->remaining_bits; michael@0: if (mbits >= sbits) michael@0: { michael@0: /* In stereo mode, we do not apply a scaling to the mid because we need the normalized michael@0: mid for folding later. */ michael@0: cm = quant_band(ctx, X, N, mbits, B, michael@0: lowband, LM, lowband_out, michael@0: Q15ONE, lowband_scratch, fill); michael@0: rebalance = mbits - (rebalance-ctx->remaining_bits); michael@0: if (rebalance > 3<>B); michael@0: } else { michael@0: /* For a stereo split, the high bits of fill are always zero, so no michael@0: folding will be done to the side. */ michael@0: cm = quant_band(ctx, Y, N, sbits, B, michael@0: NULL, LM, NULL, michael@0: side, NULL, fill>>B); michael@0: rebalance = sbits - (rebalance-ctx->remaining_bits); michael@0: if (rebalance > 3<eBands; michael@0: celt_norm * OPUS_RESTRICT norm, * OPUS_RESTRICT norm2; michael@0: VARDECL(celt_norm, _norm); michael@0: celt_norm *lowband_scratch; michael@0: int B; michael@0: int M; michael@0: int lowband_offset; michael@0: int update_lowband = 1; michael@0: int C = Y_ != NULL ? 2 : 1; michael@0: int norm_offset; michael@0: #ifdef RESYNTH michael@0: int resynth = 1; michael@0: #else michael@0: int resynth = !encode; michael@0: #endif michael@0: struct band_ctx ctx; michael@0: SAVE_STACK; michael@0: michael@0: M = 1<nbEBands-1]-norm_offset), celt_norm); michael@0: norm = _norm; michael@0: norm2 = norm + M*eBands[m->nbEBands-1]-norm_offset; michael@0: /* We can use the last band as scratch space because we don't need that michael@0: scratch space for the last band. */ michael@0: lowband_scratch = X_+M*eBands[m->nbEBands-1]; michael@0: michael@0: lowband_offset = 0; michael@0: ctx.bandE = bandE; michael@0: ctx.ec = ec; michael@0: ctx.encode = encode; michael@0: ctx.intensity = intensity; michael@0: ctx.m = m; michael@0: ctx.seed = *seed; michael@0: ctx.spread = spread; michael@0: for (i=start;i= M*eBands[start] && (update_lowband || lowband_offset==0)) michael@0: lowband_offset = i; michael@0: michael@0: tf_change = tf_res[i]; michael@0: ctx.tf_change = tf_change; michael@0: if (i>=m->effEBands) michael@0: { michael@0: X=norm; michael@0: if (Y_!=NULL) michael@0: Y = norm; michael@0: lowband_scratch = NULL; michael@0: } michael@0: if (i==end-1) michael@0: lowband_scratch = NULL; michael@0: michael@0: /* Get a conservative estimate of the collapse_mask's for the bands we're michael@0: going to be folding from. */ michael@0: if (lowband_offset != 0 && (spread!=SPREAD_AGGRESSIVE || B>1 || tf_change<0)) michael@0: { michael@0: int fold_start; michael@0: int fold_end; michael@0: int fold_i; michael@0: /* This ensures we never repeat spectral content within one band */ michael@0: effective_lowband = IMAX(0, M*eBands[lowband_offset]-norm_offset-N); michael@0: fold_start = lowband_offset; michael@0: while(M*eBands[--fold_start] > effective_lowband+norm_offset); michael@0: fold_end = lowband_offset-1; michael@0: while(M*eBands[++fold_end] < effective_lowband+norm_offset+N); michael@0: x_cm = y_cm = 0; michael@0: fold_i = fold_start; do { michael@0: x_cm |= collapse_masks[fold_i*C+0]; michael@0: y_cm |= collapse_masks[fold_i*C+C-1]; michael@0: } while (++fold_i(N<