summaryrefslogtreecommitdiff
path: root/libavcodec
diff options
context:
space:
mode:
authorJustin Ruggles <justin.ruggles@gmail.com>2010-12-16 22:47:00 +0000
committerJustin Ruggles <justin.ruggles@gmail.com>2010-12-16 22:47:00 +0000
commite7536ac567f7f0edcd49a5ffb8de2f11012be908 (patch)
tree908fb72d62e3e87ad52cce424816855af2a043dd /libavcodec
parente86ea34daddbc46ae06c1d4868eeb2750c0ad1b9 (diff)
Count bits for fixed parameters at start of encoding rather than in every
frame. Originally committed as revision 26038 to svn://svn.ffmpeg.org/ffmpeg/trunk
Diffstat (limited to 'libavcodec')
-rw-r--r--libavcodec/ac3enc.c100
1 files changed, 66 insertions, 34 deletions
diff --git a/libavcodec/ac3enc.c b/libavcodec/ac3enc.c
index 5d00dfdf64..61f464b126 100644
--- a/libavcodec/ac3enc.c
+++ b/libavcodec/ac3enc.c
@@ -122,6 +122,7 @@ typedef struct AC3EncodeContext {
int coarse_snr_offset; ///< coarse SNR offsets (csnroffst)
int fast_gain_code[AC3_MAX_CHANNELS]; ///< fast gain codes (signal-to-mask ratio) (fgaincod)
int fine_snr_offset[AC3_MAX_CHANNELS]; ///< fine SNR offsets (fsnroffst)
+ int frame_bits_fixed; ///< number of non-coefficient bits for fixed parameters
int frame_bits; ///< all frame bits except exponents and mantissas
int exponent_bits; ///< number of bits used for exponents
@@ -801,6 +802,63 @@ static void process_exponents(AC3EncodeContext *s)
/**
+ * Count frame bits that are based solely on fixed parameters.
+ * This only has to be run once when the encoder is initialized.
+ */
+static void count_frame_bits_fixed(AC3EncodeContext *s)
+{
+ static const int frame_bits_inc[8] = { 0, 0, 2, 2, 2, 4, 2, 4 };
+ int blk;
+ int frame_bits;
+
+ /* assumptions:
+ * no dynamic range codes
+ * no channel coupling
+ * no rematrixing
+ * bit allocation parameters do not change between blocks
+ * SNR offsets do not change between blocks
+ * no delta bit allocation
+ * no skipped data
+ * no auxilliary data
+ */
+
+ /* header size */
+ frame_bits = 65;
+ frame_bits += frame_bits_inc[s->channel_mode];
+
+ /* audio blocks */
+ for (blk = 0; blk < AC3_MAX_BLOCKS; blk++) {
+ frame_bits += s->fbw_channels * 2 + 2; /* blksw * c, dithflag * c, dynrnge, cplstre */
+ if (s->channel_mode == AC3_CHMODE_STEREO) {
+ frame_bits++; /* rematstr */
+ if (!blk)
+ frame_bits += 4;
+ }
+ frame_bits += 2 * s->fbw_channels; /* chexpstr[2] * c */
+ if (s->lfe_on)
+ frame_bits++; /* lfeexpstr */
+ frame_bits++; /* baie */
+ frame_bits++; /* snr */
+ frame_bits += 2; /* delta / skip */
+ }
+ frame_bits++; /* cplinu for block 0 */
+ /* bit alloc info */
+ /* sdcycod[2], fdcycod[2], sgaincod[2], dbpbcod[2], floorcod[3] */
+ /* csnroffset[6] */
+ /* (fsnoffset[4] + fgaincod[4]) * c */
+ frame_bits += 2*4 + 3 + 6 + s->channels * (4 + 3);
+
+ /* auxdatae, crcrsv */
+ frame_bits += 2;
+
+ /* CRC */
+ frame_bits += 16;
+
+ s->frame_bits_fixed = frame_bits;
+}
+
+
+/**
* Initialize bit allocation.
* Set default parameter codes and calculate parameter values.
*/
@@ -828,55 +886,29 @@ static void bit_alloc_init(AC3EncodeContext *s)
s->bit_alloc.slow_gain = ff_ac3_slow_gain_tab[s->slow_gain_code];
s->bit_alloc.db_per_bit = ff_ac3_db_per_bit_tab[s->db_per_bit_code];
s->bit_alloc.floor = ff_ac3_floor_tab[s->floor_code];
+
+ count_frame_bits_fixed(s);
}
/**
* Count the bits used to encode the frame, minus exponents and mantissas.
+ * Bits based on fixed parameters have already been counted, so now we just
+ * have to add the bits based on parameters that change during encoding.
*/
static void count_frame_bits(AC3EncodeContext *s)
{
- static const int frame_bits_inc[8] = { 0, 0, 2, 2, 2, 4, 2, 4 };
int blk, ch;
- int frame_bits;
+ int frame_bits = 0;
- /* header size */
- frame_bits = 65;
- frame_bits += frame_bits_inc[s->channel_mode];
-
- /* audio blocks */
for (blk = 0; blk < AC3_MAX_BLOCKS; blk++) {
- frame_bits += s->fbw_channels * 2 + 2; /* blksw * c, dithflag * c, dynrnge, cplstre */
- if (s->channel_mode == AC3_CHMODE_STEREO) {
- frame_bits++; /* rematstr */
- if (!blk)
- frame_bits += 4;
- }
- frame_bits += 2 * s->fbw_channels; /* chexpstr[2] * c */
- if (s->lfe_on)
- frame_bits++; /* lfeexpstr */
+ uint8_t *exp_strategy = s->blocks[blk].exp_strategy;
for (ch = 0; ch < s->fbw_channels; ch++) {
- if (s->blocks[blk].exp_strategy[ch] != EXP_REUSE)
+ if (exp_strategy[ch] != EXP_REUSE)
frame_bits += 6 + 2; /* chbwcod[6], gainrng[2] */
}
- frame_bits++; /* baie */
- frame_bits++; /* snr */
- frame_bits += 2; /* delta / skip */
}
- frame_bits++; /* cplinu for block 0 */
- /* bit alloc info */
- /* sdcycod[2], fdcycod[2], sgaincod[2], dbpbcod[2], floorcod[3] */
- /* csnroffset[6] */
- /* (fsnoffset[4] + fgaincod[4]) * c */
- frame_bits += 2*4 + 3 + 6 + s->channels * (4 + 3);
-
- /* auxdatae, crcrsv */
- frame_bits += 2;
-
- /* CRC */
- frame_bits += 16;
-
- s->frame_bits = frame_bits;
+ s->frame_bits = s->frame_bits_fixed + frame_bits;
}