From 59297ad63dbd7f9a587e742e1d5b0e94ae125fff Mon Sep 17 00:00:00 2001 From: Janne Grunau Date: Wed, 18 Jan 2012 20:32:32 +0100 Subject: lavf: force single-threaded decoding in avformat_find_stream_info The H.264 decoder needs SPS and PPS for initialization during multi-threaded decoding. When probed single-threaded SPS and PPS are copied to extradata and are available for proper initialization of the decoder before the first frame is decoded. --- libavformat/utils.c | 23 ++++++++++++++++++++--- 1 file changed, 20 insertions(+), 3 deletions(-) (limited to 'libavformat') diff --git a/libavformat/utils.c b/libavformat/utils.c index b1832ba717..22ee13b51f 100644 --- a/libavformat/utils.c +++ b/libavformat/utils.c @@ -2138,10 +2138,18 @@ static int try_decode_frame(AVStream *st, AVPacket *avpkt, AVDictionary **option AVPacket pkt = *avpkt; if(!st->codec->codec){ + AVDictionary *thread_opt = NULL; + codec = avcodec_find_decoder(st->codec->codec_id); if (!codec) return -1; - ret = avcodec_open2(st->codec, codec, options); + + /* force thread count to 1 since the h264 decoder will not extract SPS + * and PPS to extradata during multi-threaded decoding */ + av_dict_set(options ? options : &thread_opt, "threads", "1", 0); + ret = avcodec_open2(st->codec, codec, options ? options : &thread_opt); + if (!options) + av_dict_free(&thread_opt); if (ret < 0) return ret; } @@ -2281,6 +2289,7 @@ int avformat_find_stream_info(AVFormatContext *ic, AVDictionary **options) for(i=0;inb_streams;i++) { AVCodec *codec; + AVDictionary *thread_opt = NULL; st = ic->streams[i]; if (st->codec->codec_type == AVMEDIA_TYPE_VIDEO || @@ -2300,16 +2309,24 @@ int avformat_find_stream_info(AVFormatContext *ic, AVDictionary **options) assert(!st->codec->codec); codec = avcodec_find_decoder(st->codec->codec_id); + /* force thread count to 1 since the h264 decoder will not extract SPS + * and PPS to extradata during multi-threaded decoding */ + av_dict_set(options ? &options[i] : &thread_opt, "threads", "1", 0); + /* Ensure that subtitle_header is properly set. */ if (st->codec->codec_type == AVMEDIA_TYPE_SUBTITLE && codec && !st->codec->codec) - avcodec_open2(st->codec, codec, options ? &options[i] : NULL); + avcodec_open2(st->codec, codec, options ? &options[i] + : &thread_opt); //try to just open decoders, in case this is enough to get parameters if(!has_codec_parameters(st->codec)){ if (codec && !st->codec->codec) - avcodec_open2(st->codec, codec, options ? &options[i] : NULL); + avcodec_open2(st->codec, codec, options ? &options[i] + : &thread_opt); } + if (!options) + av_dict_free(&thread_opt); } for (i=0; inb_streams; i++) { -- cgit v1.2.3