---
 libavcodec/ac3enc.c |  250 ++++++++++++++++++++++++++++++++++++++++++++++++--
 1 files changed, 240 insertions(+), 10 deletions(-)

diff --git libavcodec/ac3enc.c libavcodec/ac3enc.c
index f25bdbc..8b3bd58 100644
--- libavcodec/ac3enc.c
+++ libavcodec/ac3enc.c
@@ -31,6 +31,7 @@
 //#define DEBUG_EXPONENTS
 
 #include "libavutil/crc.h"
+#include "libavutil/opt.h"
 #include "avcodec.h"
 #include "put_bits.h"
 #include "ac3.h"
@@ -68,6 +69,32 @@
 #   define INPUT_SAMPLE_FMT SAMPLE_FMT_S16
 #endif
 
+typedef struct AC3EncOptions {
+    /* AC-3 metadata options*/
+    int dialogue_level;
+    int bitstream_mode;
+    int center_mix_level;
+    int surround_mix_level;
+    int dolby_surround_mode;
+    int audio_production_info;
+    int mixing_level;
+    int room_type;
+    int copyright;
+    int original;
+    int extended_bsi_1;
+    int preferred_stereo_downmix;
+    int lt_rt_center_mix_level;
+    int lt_rt_surround_mix_level;
+    int lo_ro_center_mix_level;
+    int lo_ro_surround_mix_level;
+    int extended_bsi_2;
+    int dolby_surround_ex_mode;
+    int dolby_headphone_mode;
+    int ad_converter_type;
+
+    /* encoding options */
+} AC3EncOptions;
+
 typedef struct IComplex {
     SampleType re,im;
 } IComplex;
@@ -95,6 +122,8 @@ typedef struct AC3Block {
 } AC3Block;
 
 typedef struct AC3EncodeContext {
+    AVClass *av_class;
+    AC3EncOptions options;
     AVCodecContext *avctx;                  ///< parent context
     PutBitContext pb;                       ///< bitstream writer
     AC3MDCTContext mdct;                    ///< MDCT context
@@ -102,7 +131,6 @@ typedef struct AC3EncodeContext {
     AC3Block blocks[AC3_MAX_BLOCKS];        ///< per-block info
 
     int bitstream_id;                       ///< bitstream id                           (bsid)
-    int bitstream_mode;                     ///< bitstream mode                         (bsmod)
 
     int bit_rate;                           ///< target bit rate, in bits-per-second
     int sample_rate;                        ///< sampling frequency, in Hz
@@ -151,6 +179,92 @@ typedef struct AC3EncodeContext {
     int16_t *mask_buffer;
 } AC3EncodeContext;
 
+#define AC3_ENCODING_PARAM (AV_OPT_FLAG_AUDIO_PARAM | AV_OPT_FLAG_ENCODING_PARAM)
+
+static const AVOption options[] = {
+/* AC-3 Metadata options
+ * These parameters are described in detail in the Dolby Metadata Guide.
+ * http://www.dolby.com/uploadedFiles/zz-_Shared_Assets/English_PDFs/Professional/18_Metadata.Guide.pdf
+ */
+{"dialnorm", "Dialogue Level (dB)", offsetof(AC3EncodeContext, options.dialogue_level), FF_OPT_TYPE_INT, 31, 1, 31, AC3_ENCODING_PARAM},
+{"bsmode", "Bitstream Mode", offsetof(AC3EncodeContext, options.bitstream_mode), FF_OPT_TYPE_INT, 0, 0, 7, AC3_ENCODING_PARAM, "bsmode"},
+    {"CM", "Complete Main (default)",  0, FF_OPT_TYPE_CONST, 0, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "bsmode"},
+    {"ME", "Music and Effects",        0, FF_OPT_TYPE_CONST, 1, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "bsmode"},
+    {"VI", "Assoc: Visually Impaired", 0, FF_OPT_TYPE_CONST, 2, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "bsmode"},
+    {"HI", "Assoc: Hearing Impaired",  0, FF_OPT_TYPE_CONST, 3, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "bsmode"},
+    {"D",  "Assoc: Dialogue",          0, FF_OPT_TYPE_CONST, 4, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "bsmode"},
+    {"C",  "Assoc: Commentary",        0, FF_OPT_TYPE_CONST, 5, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "bsmode"},
+    {"E",  "Assoc: Emergency",         0, FF_OPT_TYPE_CONST, 6, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "bsmode"},
+    {"VO", "Assoc: Voice Over (1 ch)", 0, FF_OPT_TYPE_CONST, 7, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "bsmode"},
+    {"K",  "Karaoke (2 ch or more)",   0, FF_OPT_TYPE_CONST, 7, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "bsmode"},
+{"cmixlev", "Center Mix Level", offsetof(AC3EncodeContext, options.center_mix_level), FF_OPT_TYPE_INT, 1, 0, 2, AC3_ENCODING_PARAM, "cmixlev"},
+    {"0", "-3.0 dB (0.707)",           0, FF_OPT_TYPE_CONST, 0, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "cmixlev"},
+    {"1", "-4.5 dB (0.595) (default)", 0, FF_OPT_TYPE_CONST, 1, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "cmixlev"},
+    {"2", "-6.0 dB (0.500)",           0, FF_OPT_TYPE_CONST, 2, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "cmixlev"},
+{"surmixlev", "Surround Mix Level", offsetof(AC3EncodeContext, options.surround_mix_level), FF_OPT_TYPE_INT, 1, 0, 2, AC3_ENCODING_PARAM, "surmixlev"},
+    {"0", "-3.0 dB (0.707)",           0, FF_OPT_TYPE_CONST, 0, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "surmixlev"},
+    {"1", "-6.0 dB (0.500) (default)", 0, FF_OPT_TYPE_CONST, 1, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "surmixlev"},
+    {"2", "-inf dB (0.000)",           0, FF_OPT_TYPE_CONST, 2, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "surmixlev"},
+{"dsurmode", "Dolby Surround Mode", offsetof(AC3EncodeContext, options.dolby_surround_mode), FF_OPT_TYPE_INT, 0, 0, 2, AC3_ENCODING_PARAM, "dsurmode"},
+    {"notindicated", "Not Indicated (default)",    0, FF_OPT_TYPE_CONST, 0, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "dsurmode"},
+    {"on",           "Dolby Surround Encoded",     0, FF_OPT_TYPE_CONST, 1, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "dsurmode"},
+    {"off",          "Not Dolby Surround Encoded", 0, FF_OPT_TYPE_CONST, 2, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "dsurmode"},
+{"mixlevel", "Mixing Level", offsetof(AC3EncodeContext, options.mixing_level), FF_OPT_TYPE_INT, -1, -1, 31, AC3_ENCODING_PARAM},
+{"roomtype", "Room Type", offsetof(AC3EncodeContext, options.room_type), FF_OPT_TYPE_INT, -1, -1, 2, AC3_ENCODING_PARAM, "roomtype"},
+    {"notindicated", "Not Indicated (default)", 0, FF_OPT_TYPE_CONST, 0, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "roomtype"},
+    {"large",        "Large Room",              0, FF_OPT_TYPE_CONST, 1, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "roomtype"},
+    {"small",        "Small Room",              0, FF_OPT_TYPE_CONST, 2, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "roomtype"},
+{"copyright", "Copyright Bit", offsetof(AC3EncodeContext, options.copyright), FF_OPT_TYPE_INT, 0, 0, 1, AC3_ENCODING_PARAM},
+{"original", "Original Bit Stream", offsetof(AC3EncodeContext, options.original), FF_OPT_TYPE_INT, 1, 0, 1, AC3_ENCODING_PARAM},
+{"dmixmode", "Preferred Stereo Downmix Mode", offsetof(AC3EncodeContext, options.preferred_stereo_downmix), FF_OPT_TYPE_INT, -1, -1, 2, AC3_ENCODING_PARAM, "dmixmode"},
+    {"notindicated", "not indicated (default)", 0, FF_OPT_TYPE_CONST, 0, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "dmixmode"},
+    {"ltrt", "Lt/Rt Downmix Preferred",         0, FF_OPT_TYPE_CONST, 1, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "dmixmode"},
+    {"loro", "Lo/Ro Downmix Preferred",         0, FF_OPT_TYPE_CONST, 2, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "dmixmode"},
+{"ltrtcmixlev", "Lt/Rt Center Mix Level", offsetof(AC3EncodeContext, options.lt_rt_center_mix_level), FF_OPT_TYPE_INT, -1, -1, 7, AC3_ENCODING_PARAM, "ltrtcmixlev"},
+    {"0", "+3.0 dB (1.414)",           0, FF_OPT_TYPE_CONST, 0, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "ltrtcmixlev"},
+    {"1", "+1.5 dB (1.189)",           0, FF_OPT_TYPE_CONST, 1, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "ltrtcmixlev"},
+    {"2", "+0.0 dB (1.000)",           0, FF_OPT_TYPE_CONST, 2, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "ltrtcmixlev"},
+    {"3", "-1.5 dB (0.841)",           0, FF_OPT_TYPE_CONST, 3, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "ltrtcmixlev"},
+    {"4", "-3.0 dB (0.707)",           0, FF_OPT_TYPE_CONST, 4, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "ltrtcmixlev"},
+    {"5", "-4.5 dB (0.595) (default)", 0, FF_OPT_TYPE_CONST, 5, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "ltrtcmixlev"},
+    {"6", "-6.0 dB (0.500)",           0, FF_OPT_TYPE_CONST, 6, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "ltrtcmixlev"},
+    {"7", "-inf dB (0.000)",           0, FF_OPT_TYPE_CONST, 7, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "ltrtcmixlev"},
+{"ltrtsurmixlev", "Lt/Rt Surround Mix Level", offsetof(AC3EncodeContext, options.lt_rt_surround_mix_level), FF_OPT_TYPE_INT, -1, -1, 7, AC3_ENCODING_PARAM, "ltrtsurmixlev"},
+    {"3", "-1.5 dB (0.841)",           0, FF_OPT_TYPE_CONST, 3, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "ltrtsurmixlev"},
+    {"4", "-3.0 dB (0.707)",           0, FF_OPT_TYPE_CONST, 4, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "ltrtsurmixlev"},
+    {"5", "-4.5 dB (0.595)",           0, FF_OPT_TYPE_CONST, 5, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "ltrtsurmixlev"},
+    {"6", "-6.0 dB (0.500) (default)", 0, FF_OPT_TYPE_CONST, 6, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "ltrtsurmixlev"},
+    {"7", "-inf dB (0.000)",           0, FF_OPT_TYPE_CONST, 7, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "ltrtsurmixlev"},
+{"lorocmixlev", "Lo/Ro Center Mix Level", offsetof(AC3EncodeContext, options.lo_ro_center_mix_level), FF_OPT_TYPE_INT, -1, -1, 7, AC3_ENCODING_PARAM, "lorocmixlev"},
+    {"0", "+3.0 dB (1.414)",           0, FF_OPT_TYPE_CONST, 0, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "lorocmixlev"},
+    {"1", "+1.5 dB (1.189)",           0, FF_OPT_TYPE_CONST, 1, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "lorocmixlev"},
+    {"2", "+0.0 dB (1.000)",           0, FF_OPT_TYPE_CONST, 2, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "lorocmixlev"},
+    {"3", "-1.5 dB (0.841)",           0, FF_OPT_TYPE_CONST, 3, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "lorocmixlev"},
+    {"4", "-3.0 dB (0.707)",           0, FF_OPT_TYPE_CONST, 4, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "lorocmixlev"},
+    {"5", "-4.5 dB (0.595) (default)", 0, FF_OPT_TYPE_CONST, 5, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "lorocmixlev"},
+    {"6", "-6.0 dB (0.500)",           0, FF_OPT_TYPE_CONST, 6, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "lorocmixlev"},
+    {"7", "-inf dB (0.000)",           0, FF_OPT_TYPE_CONST, 7, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "lorocmixlev"},
+{"lorosurmixlev", "Lo/Ro Surround Mix Level", offsetof(AC3EncodeContext, options.lo_ro_surround_mix_level), FF_OPT_TYPE_INT, -1, -1, 7, AC3_ENCODING_PARAM, "lorosurmixlev"},
+    {"3", "-1.5 dB (0.841)",           0, FF_OPT_TYPE_CONST, 3, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "lorosurmixlev"},
+    {"4", "-3.0 dB (0.707)",           0, FF_OPT_TYPE_CONST, 4, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "lorosurmixlev"},
+    {"5", "-4.5 dB (0.595)",           0, FF_OPT_TYPE_CONST, 5, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "lorosurmixlev"},
+    {"6", "-6.0 dB (0.500) (default)", 0, FF_OPT_TYPE_CONST, 6, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "lorosurmixlev"},
+    {"7", "-inf dB (0.000)",           0, FF_OPT_TYPE_CONST, 7, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "lorosurmixlev"},
+{"dsurexmode", "Dolby Surround EX Mode", offsetof(AC3EncodeContext, options.dolby_surround_ex_mode), FF_OPT_TYPE_INT, -1, -1, 2, AC3_ENCODING_PARAM, "dsurexmode"},
+    {"notindicated", "Not Indicated (default)",       0, FF_OPT_TYPE_CONST, 0, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "dsurexmode"},
+    {"on",           "Dolby Surround EX Encoded",     0, FF_OPT_TYPE_CONST, 1, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "dsurexmode"},
+    {"off",          "Not Dolby Surround EX Encoded", 0, FF_OPT_TYPE_CONST, 2, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "dsurexmode"},
+{"dheadphonemode", "Dolby Headphone Mode", offsetof(AC3EncodeContext, options.dolby_headphone_mode), FF_OPT_TYPE_INT, -1, -1, 2, AC3_ENCODING_PARAM, "dheadphonemode"},
+    {"notindicated", "Not Indicated (default)",     0, FF_OPT_TYPE_CONST, 0, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "dheadphonemode"},
+    {"on",           "Dolby Headphone Encoded",     0, FF_OPT_TYPE_CONST, 1, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "dheadphonemode"},
+    {"off",          "Not Dolby Headphone Encoded", 0, FF_OPT_TYPE_CONST, 2, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "dheadphonemode"},
+{"adconvtype", "A/D Converter Type", offsetof(AC3EncodeContext, options.ad_converter_type), FF_OPT_TYPE_INT, -1, -1, 1, AC3_ENCODING_PARAM, "adconvtype"},
+    {"standard", "Standard (default)", 0, FF_OPT_TYPE_CONST, 0, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "adconvtype"},
+    {"hdcd",     "HDCD",               0, FF_OPT_TYPE_CONST, 1, INT_MIN, INT_MAX, AC3_ENCODING_PARAM, "adconvtype"},
+{NULL}
+};
+static const AVClass class = { "ac3", av_default_item_name, options, LIBAVUTIL_VERSION_INT };
+
 /**
  * LUT for number of exponent groups.
  * exponent_group_tab[exponent strategy][number of coefficients]
@@ -1051,6 +1165,93 @@ static av_cold int AC3_encode_close(AVCodecContext *avctx)
     return 0;
 }
 
+static av_cold int validate_options(AC3EncodeContext *s)
+{
+    AC3EncOptions *opt = &s->options;
+
+    /* set audio production info flag */
+    if (opt->mixing_level >= 0 || opt->room_type >= 0) {
+        if (opt->mixing_level < 0) {
+            av_log(s->avctx, AV_LOG_ERROR, "mixing level (mixlevel) option "
+                   "must be set if room type is set\n");
+            return AVERROR(EINVAL);
+        }
+        /* default room type */
+        if (opt->room_type < 0)
+            opt->room_type = 0;
+        opt->audio_production_info = 1;
+    } else {
+        opt->audio_production_info = 0;
+    }
+
+    /* set extended bsi 1 flag */
+    if (opt->preferred_stereo_downmix >= 0 ||
+        opt->lt_rt_center_mix_level   >= 0 ||
+        opt->lt_rt_surround_mix_level >= 0 ||
+        opt->lo_ro_center_mix_level   >= 0 ||
+        opt->lo_ro_surround_mix_level >= 0) {
+        /* default preferred stereo downmix */
+        if (opt->preferred_stereo_downmix < 0)
+            opt->preferred_stereo_downmix = 0;
+        /* default Lt/Rt center mix level */
+        if (opt->lt_rt_center_mix_level < 0)
+            opt->lt_rt_center_mix_level = 5;
+        /* default Lt/Rt surround mix level */
+        if (opt->lt_rt_surround_mix_level < 0)
+            opt->lt_rt_surround_mix_level = 6;
+        if (opt->lt_rt_surround_mix_level < 3) {
+            av_log(s->avctx, AV_LOG_ERROR, "invalid Lt/Rt surround mix level: %d\n",
+                   opt->lt_rt_surround_mix_level);
+            return AVERROR(EINVAL);
+        }
+        /* default Lo/Ro center mix level */
+        if (opt->lo_ro_center_mix_level < 0)
+            opt->lo_ro_center_mix_level = 5;
+        /* default Lo/Ro surround mix level */
+        if (opt->lo_ro_surround_mix_level < 0)
+            opt->lo_ro_surround_mix_level = 6;
+        if (opt->lo_ro_surround_mix_level < 3) {
+            av_log(s->avctx, AV_LOG_ERROR, "invalid Lo/Ro surround mix level: %d\n",
+                   opt->lo_ro_surround_mix_level);
+            return AVERROR(EINVAL);
+        }
+        opt->extended_bsi_1 = 1;
+    } else {
+        opt->extended_bsi_1 = 0;
+    }
+
+    /* set extended bsi 2 flag */
+    if (opt->dolby_surround_ex_mode >= 0 ||
+        opt->dolby_headphone_mode   >= 0 ||
+        opt->ad_converter_type      >= 0) {
+        /* default dolby surround ex mode */
+        if (opt->dolby_surround_ex_mode < 0)
+            opt->dolby_surround_ex_mode = 0;
+        /* default dolby headphone mode */
+        if (opt->dolby_headphone_mode < 0)
+            opt->dolby_headphone_mode = 0;
+        /* default A/D converter type */
+        if (opt->ad_converter_type < 0)
+            opt->ad_converter_type = 0;
+        opt->extended_bsi_2 = 1;
+    } else {
+        opt->extended_bsi_2 = 0;
+    }
+
+    /* set bitstream id for alternate bitstream syntax */
+    if (opt->extended_bsi_1 || opt->extended_bsi_2) {
+        if (s->bitstream_id > 8) {
+            av_log(s->avctx, AV_LOG_WARNING, "alternate bitstream syntax is "
+                "not compatible with reduced samplerates. writing of extended"
+                "bitstream information will be disabled.\n");
+        } else {
+            s->bitstream_id = 6;
+        }
+    }
+
+    return 0;
+}
+
 static av_cold int AC3_encode_init(AVCodecContext *avctx)
 {
     int freq = avctx->sample_rate;
@@ -1088,7 +1289,6 @@ static av_cold int AC3_encode_init(AVCodecContext *avctx)
     s->bit_alloc.sr_shift = i;
     s->bit_alloc.sr_code  = j;
     s->bitstream_id       = 8 + s->bit_alloc.sr_shift;
-    s->bitstream_mode     = 0; /* complete main audio service */
 
     /* bitrate & frame size */
     for (i = 0; i < 19; i++) {
@@ -1130,6 +1330,11 @@ static av_cold int AC3_encode_init(AVCodecContext *avctx)
     if (s->lfe_on) {
         s->nb_coefs[s->lfe_ch] = 7; /* fixed */
     }
+
+    ret = validate_options(s);
+    if (ret)
+        return ret;
+
     /* initial snr offset */
     s->coarse_snr_offset = 40;
 
@@ -1216,6 +1421,7 @@ alloc_fail:
 /* output the AC-3 frame header */
 static void output_frame_header(AC3EncodeContext *s, unsigned char *frame)
 {
+    AC3EncOptions *opt = &s->options;
     init_put_bits(&s->pb, frame, AC3_MAX_CODED_FRAME_SIZE);
 
     put_bits(&s->pb, 16, 0x0b77);       /* frame header */
@@ -1223,23 +1429,46 @@ static void output_frame_header(AC3EncodeContext *s, unsigned char *frame)
     put_bits(&s->pb,  2, s->bit_alloc.sr_code);
     put_bits(&s->pb,  6, s->frame_size_code + (s->frame_size - s->frame_size_min)/2);
     put_bits(&s->pb,  5, s->bitstream_id);
-    put_bits(&s->pb,  3, s->bitstream_mode);
+    put_bits(&s->pb,  3, opt->bitstream_mode);
     put_bits(&s->pb,  3, s->channel_mode);
     if ((s->channel_mode & 0x01) && s->channel_mode != AC3_CHMODE_MONO)
-        put_bits(&s->pb, 2, 1);         /* XXX -4.5 dB */
+        put_bits(&s->pb, 2, opt->center_mix_level);
     if (s->channel_mode & 0x04)
-        put_bits(&s->pb, 2, 1);         /* XXX -6 dB */
+        put_bits(&s->pb, 2, opt->surround_mix_level);
     if (s->channel_mode == AC3_CHMODE_STEREO)
-        put_bits(&s->pb, 2, 0);         /* surround not indicated */
+        put_bits(&s->pb, 2, opt->dolby_surround_mode);
     put_bits(&s->pb, 1, s->lfe_on);     /* LFE */
-    put_bits(&s->pb, 5, 31);            /* dialog norm: -31 db */
+    put_bits(&s->pb, 5, opt->dialogue_level);
     put_bits(&s->pb, 1, 0);             /* no compression control word */
     put_bits(&s->pb, 1, 0);             /* no lang code */
-    put_bits(&s->pb, 1, 0);             /* no audio production info */
-    put_bits(&s->pb, 1, 0);             /* no copyright */
-    put_bits(&s->pb, 1, 1);             /* original bitstream */
+    put_bits(&s->pb, 1, opt->audio_production_info);
+    if (opt->audio_production_info) {
+        put_bits(&s->pb, 5, opt->mixing_level);
+        put_bits(&s->pb, 2, opt->room_type);
+    }
+    put_bits(&s->pb, 1, opt->copyright);
+    put_bits(&s->pb, 1, opt->original);
+    if (s->bitstream_id == 6) {
+        /* alternate bit stream syntax */
+        put_bits(&s->pb, 1, opt->extended_bsi_1);
+        if (opt->extended_bsi_1) {
+            put_bits(&s->pb, 2, opt->preferred_stereo_downmix);
+            put_bits(&s->pb, 3, opt->lt_rt_center_mix_level);
+            put_bits(&s->pb, 3, opt->lt_rt_surround_mix_level);
+            put_bits(&s->pb, 3, opt->lo_ro_center_mix_level);
+            put_bits(&s->pb, 3, opt->lo_ro_surround_mix_level);
+        }
+        put_bits(&s->pb, 1, opt->extended_bsi_2);
+        if (opt->extended_bsi_2) {
+            put_bits(&s->pb, 2, opt->dolby_surround_ex_mode);
+            put_bits(&s->pb, 2, opt->dolby_headphone_mode);
+            put_bits(&s->pb, 1, opt->ad_converter_type);
+            put_bits(&s->pb, 9, 0);     /* xbsi2 and encinfo : reserved */
+        }
+    } else {
     put_bits(&s->pb, 1, 0);             /* no time code 1 */
     put_bits(&s->pb, 1, 0);             /* no time code 2 */
+    }
     put_bits(&s->pb, 1, 0);             /* no additional bit stream info */
 }
 
@@ -1816,6 +2045,7 @@ AVCodec ac3_encoder = {
     NULL,
     .sample_fmts = (const enum SampleFormat[]){INPUT_SAMPLE_FMT,SAMPLE_FMT_NONE},
     .long_name = NULL_IF_CONFIG_SMALL("ATSC A/52A (AC-3)"),
+    .priv_class = &class,
     .channel_layouts = (const int64_t[]){
         CH_LAYOUT_MONO,
         CH_LAYOUT_STEREO,
_______________________________________________
FFmpeg-soc mailing list
[email protected]
https://lists.mplayerhq.hu/mailman/listinfo/ffmpeg-soc

Reply via email to