diff --git a/libavcodec/avcodec.h b/libavcodec/avcodec.h index eee56351f597f90b0328e30104957f4901897190..4bddbaa4aa88316e0ebeaf706eb0bb1244f8bb6a 100644 --- a/libavcodec/avcodec.h +++ b/libavcodec/avcodec.h @@ -703,6 +703,11 @@ typedef struct RcOverride{ * encoders */ #define CODEC_CAP_EXPERIMENTAL 0x0200 +/** + * Codec should fill in channel configuration and samplerate instead of container + */ +#define CODEC_CAP_CHANNEL_CONF 0x0400 + //The following defines may change, don't expect compatibility if you use them. #define MB_TYPE_INTRA4x4 0x0001 diff --git a/libavcodec/dca.c b/libavcodec/dca.c index e8627a23d95830872d3cb867b4eb31b35b6ccfcc..afd55bb075b3518b58b39b18ddcedccf28796020 100644 --- a/libavcodec/dca.c +++ b/libavcodec/dca.c @@ -1500,4 +1500,5 @@ AVCodec dca_decoder = { .decode = dca_decode_frame, .close = dca_decode_end, .long_name = NULL_IF_CONFIG_SMALL("DCA (DTS Coherent Acoustics)"), + .capabilities = CODEC_CAP_CHANNEL_CONF, }; diff --git a/libavformat/utils.c b/libavformat/utils.c index 24dbd88feb4429bafc9cda02d0a948b4071197aa..598551178cb0078652fe5ae704fa335d61ff36e0 100644 --- a/libavformat/utils.c +++ b/libavformat/utils.c @@ -2167,6 +2167,7 @@ int av_find_stream_info(AVFormatContext *ic) } info[MAX_STREAMS] = {{0}}; for(i=0;i<ic->nb_streams;i++) { + AVCodec *codec; st = ic->streams[i]; if (st->codec->codec_id == CODEC_ID_AAC) { st->codec->sample_rate = 0; @@ -2187,9 +2188,17 @@ int av_find_stream_info(AVFormatContext *ic) } } assert(!st->codec->codec); + codec = avcodec_find_decoder(st->codec->codec_id); + + /* Force decoding of at least one frame of codec data + * this makes sure the codec initializes the channel configuration + * and does not trust the values from the container. + */ + if (codec && codec->capabilities & CODEC_CAP_CHANNEL_CONF) + st->codec->channels = 0; + //try to just open decoders, in case this is enough to get parameters if(!has_codec_parameters(st->codec)){ - AVCodec *codec = avcodec_find_decoder(st->codec->codec_id); if (codec) avcodec_open(st->codec, codec); }