]> git.sesse.net Git - ffmpeg/blobdiff - libavcodec/ac3dec.c
const
[ffmpeg] / libavcodec / ac3dec.c
index 438cc65a42ae91e6969b98deca322b720b0d67b9..0ce75e7699167f8d01147c45afa59749568f5f56 100644 (file)
@@ -135,7 +135,6 @@ typedef struct {
     int phase_flags_in_use;                 ///< phase flags in use
     int phase_flags[18];                    ///< phase flags
     int cpl_band_struct[18];                ///< coupling band structure
-    int rematrixing_strategy;               ///< rematrixing strategy
     int num_rematrixing_bands;              ///< number of rematrixing bands
     int rematrixing_flags[4];               ///< rematrixing flags
     int exp_strategy[AC3_MAX_CHANNELS];     ///< exponent strategies
@@ -158,6 +157,8 @@ typedef struct {
     int output_mode;                        ///< output channel configuration
     int out_channels;                       ///< number of output channels
 
+    int center_mix_level;                   ///< Center mix level index
+    int surround_mix_level;                 ///< Surround mix level index
     float downmix_coeffs[AC3_MAX_CHANNELS][2];  ///< stereo downmix coefficients
     float dynamic_range[2];                 ///< dynamic range
     float cpl_coords[AC3_MAX_CHANNELS][18]; ///< coupling coordinates
@@ -195,30 +196,6 @@ typedef struct {
     AVCodecContext *avctx;                  ///< parent context
 } AC3DecodeContext;
 
-/**
- * Generate a Kaiser-Bessel Derived Window.
- */
-static void ac3_window_init(float *window)
-{
-   int i, j;
-   double sum = 0.0, bessel, tmp;
-   double local_window[256];
-   double alpha2 = (5.0 * M_PI / 256.0) * (5.0 * M_PI / 256.0);
-
-   for (i = 0; i < 256; i++) {
-       tmp = i * (256 - i) * alpha2;
-       bessel = 1.0;
-       for (j = 100; j > 0; j--) /* default to 100 iterations */
-           bessel = bessel * tmp / (j * j) + 1;
-       sum += bessel;
-       local_window[i] = sum;
-   }
-
-   sum++;
-   for (i = 0; i < 256; i++)
-       window[i] = sqrt(local_window[i] / sum);
-}
-
 /**
  * Symmetrical Dequantization
  * reference: Section 7.3.3 Expansion of Mantissas for Symmetrical Quantization
@@ -300,7 +277,7 @@ static int ac3_decode_init(AVCodecContext *avctx)
     ac3_tables_init();
     ff_mdct_init(&s->imdct_256, 8, 1);
     ff_mdct_init(&s->imdct_512, 9, 1);
-    ac3_window_init(s->window);
+    ff_kbd_window_init(s->window, 5.0, 256);
     dsputil_init(&s->dsp, avctx);
     av_init_random(0, &s->dith_state);
 
@@ -332,7 +309,6 @@ static int ac3_parse_header(AC3DecodeContext *s)
 {
     AC3HeaderInfo hdr;
     GetBitContext *gbc = &s->gbc;
-    float center_mix_level, surround_mix_level;
     int err, i;
 
     err = ff_ac3_parse_header(gbc->buffer, &hdr);
@@ -360,6 +336,10 @@ static int ac3_parse_header(AC3DecodeContext *s)
     if(s->lfe_on)
         s->output_mode |= AC3_OUTPUT_LFEON;
 
+    /* set default mix levels */
+    s->center_mix_level   = 3;  // -4.5dB
+    s->surround_mix_level = 4;  // -6.0dB
+
     /* skip over portion of header which has already been read */
     skip_bits(gbc, 16); // skip the sync_word
     skip_bits(gbc, 16); // skip crc1
@@ -369,9 +349,9 @@ static int ac3_parse_header(AC3DecodeContext *s)
         skip_bits(gbc, 2); // skip dsurmod
     } else {
         if((s->channel_mode & 1) && s->channel_mode != AC3_CHMODE_MONO)
-            center_mix_level = gain_levels[center_levels[get_bits(gbc, 2)]];
+            s->center_mix_level = center_levels[get_bits(gbc, 2)];
         if(s->channel_mode & 4)
-            surround_mix_level = gain_levels[surround_levels[get_bits(gbc, 2)]];
+            s->surround_mix_level = surround_levels[get_bits(gbc, 2)];
     }
     skip_bits1(gbc); // skip lfeon
 
@@ -404,25 +384,34 @@ static int ac3_parse_header(AC3DecodeContext *s)
         } while(i--);
     }
 
-    /* set stereo downmixing coefficients
-       reference: Section 7.8.2 Downmixing Into Two Channels */
+    return 0;
+}
+
+/**
+ * Set stereo downmixing coefficients based on frame header info.
+ * reference: Section 7.8.2 Downmixing Into Two Channels
+ */
+static void set_downmix_coeffs(AC3DecodeContext *s)
+{
+    int i;
+    float cmix = gain_levels[s->center_mix_level];
+    float smix = gain_levels[s->surround_mix_level];
+
     for(i=0; i<s->fbw_channels; i++) {
         s->downmix_coeffs[i][0] = gain_levels[ac3_default_coeffs[s->channel_mode][i][0]];
         s->downmix_coeffs[i][1] = gain_levels[ac3_default_coeffs[s->channel_mode][i][1]];
     }
     if(s->channel_mode > 1 && s->channel_mode & 1) {
-        s->downmix_coeffs[1][0] = s->downmix_coeffs[1][1] = center_mix_level;
+        s->downmix_coeffs[1][0] = s->downmix_coeffs[1][1] = cmix;
     }
     if(s->channel_mode == AC3_CHMODE_2F1R || s->channel_mode == AC3_CHMODE_3F1R) {
         int nf = s->channel_mode - 2;
-        s->downmix_coeffs[nf][0] = s->downmix_coeffs[nf][1] = surround_mix_level * LEVEL_MINUS_3DB;
+        s->downmix_coeffs[nf][0] = s->downmix_coeffs[nf][1] = smix * LEVEL_MINUS_3DB;
     }
     if(s->channel_mode == AC3_CHMODE_2F2R || s->channel_mode == AC3_CHMODE_3F2R) {
         int nf = s->channel_mode - 4;
-        s->downmix_coeffs[nf][0] = s->downmix_coeffs[nf+1][1] = surround_mix_level;
+        s->downmix_coeffs[nf][0] = s->downmix_coeffs[nf+1][1] = smix;
     }
-
-    return 0;
 }
 
 /**
@@ -840,6 +829,7 @@ static int ac3_parse_audio_block(AC3DecodeContext *s, int blk)
                     s->num_cpl_bands--;
                 }
             }
+            s->cpl_band_struct[s->num_cpl_subbands-1] = 0;
         } else {
             /* coupling not in use */
             for (ch = 1; ch <= fbw_channels; ch++)
@@ -879,8 +869,7 @@ static int ac3_parse_audio_block(AC3DecodeContext *s, int blk)
 
     /* stereo rematrixing strategy and band structure */
     if (channel_mode == AC3_CHMODE_STEREO) {
-        s->rematrixing_strategy = get_bits1(gbc);
-        if (s->rematrixing_strategy) {
+        if (get_bits1(gbc)) {
             s->num_rematrixing_bands = 4;
             if(s->cpl_in_use && s->start_freq[CPL_CH] <= 61)
                 s->num_rematrixing_bands -= 1 + (s->start_freq[CPL_CH] == 37);
@@ -1120,7 +1109,7 @@ static int ac3_decode_frame(AVCodecContext * avctx, void *data, int *data_size,
     }
 
     /* check for crc mismatch */
-    if(avctx->error_resilience > 0) {
+    if(avctx->error_resilience >= FF_ER_CAREFUL) {
         if(av_crc(av_crc_get_table(AV_CRC_16_ANSI), 0, &buf[2], s->frame_size-2)) {
             av_log(avctx, AV_LOG_ERROR, "frame CRC mismatch\n");
             return -1;
@@ -1140,6 +1129,12 @@ static int ac3_decode_frame(AVCodecContext * avctx, void *data, int *data_size,
     }
     avctx->channels = s->out_channels;
 
+    /* set downmixing coefficients if needed */
+    if(s->channels != s->out_channels && !((s->output_mode & AC3_OUTPUT_LFEON) &&
+            s->fbw_channels == s->out_channels)) {
+        set_downmix_coeffs(s);
+    }
+
     /* parse the audio blocks */
     for (blk = 0; blk < NB_BLOCKS; blk++) {
         if (ac3_parse_audio_block(s, blk)) {