Commit 39710536 authored by Jean-Marc Valin's avatar Jean-Marc Valin
Browse files

This makes it possible to use the bits left after PVQ for fine energy.

parent cbc2afb1
......@@ -857,6 +857,9 @@ int celt_encode_float(CELTEncoder * restrict st, const celt_sig_t * pcm, celt_si
else
quant_bands_stereo(st->mode, X, P, NULL, has_pitch, gains, bandE, pulses, shortBlocks, has_fold, nbCompressedBytes*8, &enc);
#endif
quant_energy_finalise(st->mode, bandE, st->oldBandE, error, fine_quant, nbCompressedBytes*8-ec_enc_tell(&enc, 0), &enc);
/* Re-synthesis of the coded audio if required */
if (st->pitch_available>0 || optional_synthesis!=NULL)
{
......@@ -1404,6 +1407,8 @@ int celt_decode_float(CELTDecoder * restrict st, const unsigned char *data, int
else
unquant_bands_stereo(st->mode, X, P, has_pitch, gains, bandE, pulses, shortBlocks, has_fold, len*8, &dec);
#endif
unquant_energy_finalise(st->mode, bandE, st->oldBandE, fine_quant, len*8-ec_dec_tell(&dec, 0), &dec);
/* Synthesis */
denormalise_bands(st->mode, X, freq, bandE);
......
......@@ -169,17 +169,39 @@ static void quant_fine_energy_mono(const CELTMode *m, celt_ener_t *eBands, celt_
offset = (q2+.5f)*(1<<(14-fine_quant[i]))*(1.f/16384) - .5f;
#endif
oldEBands[i] += offset;
error[i] -= offset;
/*printf ("%f ", error[i] - offset);*/
}
for (i=0;i<m->nbEBands;i++)
eBands[i] = log2Amp(oldEBands[i]);
}
static void quant_energy_finalise_mono(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, celt_word16_t *error, int *fine_quant, int bits_left, ec_enc *enc)
{
int i;
/* Use up the remaining bits */
for (i=0;i<m->nbEBands && bits_left!=0 ;i++)
{
int q2;
celt_word16_t offset;
if (fine_quant[i] >= 7)
continue;
q2 = error[i]<0 ? 0 : 1;
ec_enc_bits(enc, q2, 1);
#ifdef FIXED_POINT
offset = SHR16(SHL16(q2,8)-QCONST16(.5,8),fine_quant[i]+1);
#else
offset = (q2-.5f)*(1<<(14-fine_quant[i]-1))*(1.f/16384);
#endif
oldEBands[i] += offset;
bits_left--;
}
for (i=0;i<m->nbEBands;i++)
{
eBands[i] = log2Amp(oldEBands[i]);
if (oldEBands[i] < -QCONST16(7.f,8))
oldEBands[i] = -QCONST16(7.f,8);
}
/*printf ("%d\n", ec_enc_tell(enc, 0)-9);*/
/*printf ("\n");*/
}
static void unquant_coarse_energy_mono(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, unsigned budget, int intra, int *prob, ec_dec *dec)
......@@ -236,17 +258,38 @@ static void unquant_fine_energy_mono(const CELTMode *m, celt_ener_t *eBands, cel
#endif
oldEBands[i] += offset;
}
for (i=0;i<m->nbEBands;i++)
eBands[i] = log2Amp(oldEBands[i]);
}
static void unquant_energy_finalise_mono(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, int *fine_quant, int bits_left, ec_dec *dec)
{
int i;
/* Use up the remaining bits */
for (i=0;i<m->nbEBands && bits_left!=0 ;i++)
{
int q2;
celt_word16_t offset;
if (fine_quant[i] >= 7)
continue;
q2 = ec_dec_bits(dec, 1);
#ifdef FIXED_POINT
offset = SHR16(SHL16(q2,8)-QCONST16(.5,8),fine_quant[i]+1);
#else
offset = (q2-.5f)*(1<<(14-fine_quant[i]-1))*(1.f/16384);
#endif
oldEBands[i] += offset;
bits_left--;
}
for (i=0;i<m->nbEBands;i++)
{
eBands[i] = log2Amp(oldEBands[i]);
if (oldEBands[i] < -QCONST16(7.f,8))
oldEBands[i] = -QCONST16(7.f,8);
}
/*printf ("\n");*/
}
unsigned quant_coarse_energy(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, int budget, int intra, int *prob, celt_word16_t *error, ec_enc *enc)
{
int C;
......@@ -300,6 +343,30 @@ void quant_fine_energy(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *ol
}
}
void quant_energy_finalise(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, celt_word16_t *error, int *fine_quant, int bits_left, ec_enc *enc)
{
int C;
C = m->nbChannels;
if (C==1)
{
quant_energy_finalise_mono(m, eBands, oldEBands, error, fine_quant, bits_left, enc);
} else {
int c;
VARDECL(celt_ener_t, E);
ALLOC(E, m->nbEBands, celt_ener_t);
for (c=0;c<C;c++)
{
int i;
SAVE_STACK;
quant_energy_finalise_mono(m, E, oldEBands+c*m->nbEBands, error+c*m->nbEBands, fine_quant, bits_left/C, enc);
for (i=0;i<m->nbEBands;i++)
eBands[C*i+c] = E[i];
RESTORE_STACK;
}
}
}
void unquant_coarse_energy(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, int budget, int intra, int *prob, ec_dec *dec)
{
......@@ -348,3 +415,29 @@ void unquant_fine_energy(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *
RESTORE_STACK;
}
}
void unquant_energy_finalise(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, int *fine_quant, int bits_left, ec_dec *dec)
{
int C;
C = m->nbChannels;
if (C==1)
{
unquant_energy_finalise_mono(m, eBands, oldEBands, fine_quant, bits_left, dec);
}
else {
int c;
VARDECL(celt_ener_t, E);
SAVE_STACK;
ALLOC(E, m->nbEBands, celt_ener_t);
for (c=0;c<C;c++)
{
int i;
unquant_energy_finalise_mono(m, E, oldEBands+c*m->nbEBands, fine_quant, bits_left/C, dec);
for (i=0;i<m->nbEBands;i++)
eBands[C*i+c] = E[i];
}
RESTORE_STACK;
}
}
......@@ -48,8 +48,12 @@ unsigned quant_coarse_energy(const CELTMode *m, celt_ener_t *eBands, celt_word16
void quant_fine_energy(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, celt_word16_t *error, int *fine_quant, ec_enc *enc);
void quant_energy_finalise(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, celt_word16_t *error, int *fine_quant, int bits_left, ec_enc *enc);
void unquant_coarse_energy(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, int budget, int intra, int *prob, ec_dec *dec);
void unquant_fine_energy(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, int *fine_quant, ec_dec *dec);
void unquant_energy_finalise(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, int *fine_quant, int bits_left, ec_dec *dec);
#endif /* QUANT_BANDS */
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment