@ -1616,8 +1616,17 @@ static int get_buffer(AVCodecContext *s, AVFrame *frame, int flags)
static int init_input_stream ( int ist_index , char * error , int error_len )
{
int ret ;
int i , ret ;
InputStream * ist = input_streams [ ist_index ] ;
for ( i = 0 ; i < ist - > nb_filters ; i + + ) {
ret = ifilter_parameters_from_decoder ( ist - > filters [ i ] , ist - > dec_ctx ) ;
if ( ret < 0 ) {
av_log ( NULL , AV_LOG_FATAL , " Error initializing filter input \n " ) ;
return ret ;
}
}
if ( ist - > decoding_needed ) {
AVCodec * codec = ist - > dec ;
if ( ! codec ) {
@ -1872,6 +1881,136 @@ static int init_output_stream_streamcopy(OutputStream *ost)
return 0 ;
}
static void set_encoder_id ( OutputFile * of , OutputStream * ost )
{
AVDictionaryEntry * e ;
uint8_t * encoder_string ;
int encoder_string_len ;
int format_flags = 0 ;
e = av_dict_get ( of - > opts , " fflags " , NULL , 0 ) ;
if ( e ) {
const AVOption * o = av_opt_find ( of - > ctx , " fflags " , NULL , 0 , 0 ) ;
if ( ! o )
return ;
av_opt_eval_flags ( of - > ctx , o , e - > value , & format_flags ) ;
}
encoder_string_len = sizeof ( LIBAVCODEC_IDENT ) + strlen ( ost - > enc - > name ) + 2 ;
encoder_string = av_mallocz ( encoder_string_len ) ;
if ( ! encoder_string )
exit_program ( 1 ) ;
if ( ! ( format_flags & AVFMT_FLAG_BITEXACT ) )
av_strlcpy ( encoder_string , LIBAVCODEC_IDENT " " , encoder_string_len ) ;
av_strlcat ( encoder_string , ost - > enc - > name , encoder_string_len ) ;
av_dict_set ( & ost - > st - > metadata , " encoder " , encoder_string ,
AV_DICT_DONT_STRDUP_VAL | AV_DICT_DONT_OVERWRITE ) ;
}
static void parse_forced_key_frames ( char * kf , OutputStream * ost ,
AVCodecContext * avctx )
{
char * p ;
int n = 1 , i ;
int64_t t ;
for ( p = kf ; * p ; p + + )
if ( * p = = ' , ' )
n + + ;
ost - > forced_kf_count = n ;
ost - > forced_kf_pts = av_malloc ( sizeof ( * ost - > forced_kf_pts ) * n ) ;
if ( ! ost - > forced_kf_pts ) {
av_log ( NULL , AV_LOG_FATAL , " Could not allocate forced key frames array. \n " ) ;
exit_program ( 1 ) ;
}
p = kf ;
for ( i = 0 ; i < n ; i + + ) {
char * next = strchr ( p , ' , ' ) ;
if ( next )
* next + + = 0 ;
t = parse_time_or_die ( " force_key_frames " , p , 1 ) ;
ost - > forced_kf_pts [ i ] = av_rescale_q ( t , AV_TIME_BASE_Q , avctx - > time_base ) ;
p = next ;
}
}
static int init_output_stream_encode ( OutputStream * ost )
{
InputStream * ist = get_input_stream ( ost ) ;
AVCodecContext * enc_ctx = ost - > enc_ctx ;
AVCodecContext * dec_ctx = NULL ;
set_encoder_id ( output_files [ ost - > file_index ] , ost ) ;
if ( ist ) {
ost - > st - > disposition = ist - > st - > disposition ;
dec_ctx = ist - > dec_ctx ;
enc_ctx - > bits_per_raw_sample = dec_ctx - > bits_per_raw_sample ;
enc_ctx - > chroma_sample_location = dec_ctx - > chroma_sample_location ;
}
if ( ( enc_ctx - > codec_type = = AVMEDIA_TYPE_VIDEO | |
enc_ctx - > codec_type = = AVMEDIA_TYPE_AUDIO ) & &
filtergraph_is_simple ( ost - > filter - > graph ) ) {
FilterGraph * fg = ost - > filter - > graph ;
if ( configure_filtergraph ( fg ) ) {
av_log ( NULL , AV_LOG_FATAL , " Error opening filters! \n " ) ;
exit_program ( 1 ) ;
}
}
switch ( enc_ctx - > codec_type ) {
case AVMEDIA_TYPE_AUDIO :
enc_ctx - > sample_fmt = ost - > filter - > filter - > inputs [ 0 ] - > format ;
enc_ctx - > sample_rate = ost - > filter - > filter - > inputs [ 0 ] - > sample_rate ;
enc_ctx - > channel_layout = ost - > filter - > filter - > inputs [ 0 ] - > channel_layout ;
enc_ctx - > channels = av_get_channel_layout_nb_channels ( enc_ctx - > channel_layout ) ;
enc_ctx - > time_base = ( AVRational ) { 1 , enc_ctx - > sample_rate } ;
break ;
case AVMEDIA_TYPE_VIDEO :
enc_ctx - > time_base = ost - > filter - > filter - > inputs [ 0 ] - > time_base ;
enc_ctx - > width = ost - > filter - > filter - > inputs [ 0 ] - > w ;
enc_ctx - > height = ost - > filter - > filter - > inputs [ 0 ] - > h ;
enc_ctx - > sample_aspect_ratio = ost - > st - > sample_aspect_ratio =
ost - > frame_aspect_ratio ? // overridden by the -aspect cli option
av_d2q ( ost - > frame_aspect_ratio * enc_ctx - > height / enc_ctx - > width , 255 ) :
ost - > filter - > filter - > inputs [ 0 ] - > sample_aspect_ratio ;
enc_ctx - > pix_fmt = ost - > filter - > filter - > inputs [ 0 ] - > format ;
ost - > st - > avg_frame_rate = ost - > frame_rate ;
if ( dec_ctx & &
( enc_ctx - > width ! = dec_ctx - > width | |
enc_ctx - > height ! = dec_ctx - > height | |
enc_ctx - > pix_fmt ! = dec_ctx - > pix_fmt ) ) {
enc_ctx - > bits_per_raw_sample = 0 ;
}
if ( ost - > forced_keyframes )
parse_forced_key_frames ( ost - > forced_keyframes , ost ,
ost - > enc_ctx ) ;
break ;
case AVMEDIA_TYPE_SUBTITLE :
enc_ctx - > time_base = ( AVRational ) { 1 , 1000 } ;
break ;
default :
abort ( ) ;
break ;
}
return 0 ;
}
static int init_output_stream ( OutputStream * ost , char * error , int error_len )
{
int ret = 0 ;
@ -1881,6 +2020,10 @@ static int init_output_stream(OutputStream *ost, char *error, int error_len)
AVCodecContext * dec = NULL ;
InputStream * ist ;
ret = init_output_stream_encode ( ost ) ;
if ( ret < 0 )
return ret ;
if ( ( ist = get_input_stream ( ost ) ) )
dec = ist - > dec_ctx ;
if ( dec & & dec - > subtitle_header ) {
@ -1973,69 +2116,9 @@ static int init_output_stream(OutputStream *ost, char *error, int error_len)
return ret ;
}
static void parse_forced_key_frames ( char * kf , OutputStream * ost ,
AVCodecContext * avctx )
{
char * p ;
int n = 1 , i ;
int64_t t ;
for ( p = kf ; * p ; p + + )
if ( * p = = ' , ' )
n + + ;
ost - > forced_kf_count = n ;
ost - > forced_kf_pts = av_malloc ( sizeof ( * ost - > forced_kf_pts ) * n ) ;
if ( ! ost - > forced_kf_pts ) {
av_log ( NULL , AV_LOG_FATAL , " Could not allocate forced key frames array. \n " ) ;
exit_program ( 1 ) ;
}
p = kf ;
for ( i = 0 ; i < n ; i + + ) {
char * next = strchr ( p , ' , ' ) ;
if ( next )
* next + + = 0 ;
t = parse_time_or_die ( " force_key_frames " , p , 1 ) ;
ost - > forced_kf_pts [ i ] = av_rescale_q ( t , AV_TIME_BASE_Q , avctx - > time_base ) ;
p = next ;
}
}
static void set_encoder_id ( OutputFile * of , OutputStream * ost )
{
AVDictionaryEntry * e ;
uint8_t * encoder_string ;
int encoder_string_len ;
int format_flags = 0 ;
e = av_dict_get ( of - > opts , " fflags " , NULL , 0 ) ;
if ( e ) {
const AVOption * o = av_opt_find ( of - > ctx , " fflags " , NULL , 0 , 0 ) ;
if ( ! o )
return ;
av_opt_eval_flags ( of - > ctx , o , e - > value , & format_flags ) ;
}
encoder_string_len = sizeof ( LIBAVCODEC_IDENT ) + strlen ( ost - > enc - > name ) + 2 ;
encoder_string = av_mallocz ( encoder_string_len ) ;
if ( ! encoder_string )
exit_program ( 1 ) ;
if ( ! ( format_flags & AVFMT_FLAG_BITEXACT ) )
av_strlcpy ( encoder_string , LIBAVCODEC_IDENT " " , encoder_string_len ) ;
av_strlcat ( encoder_string , ost - > enc - > name , encoder_string_len ) ;
av_dict_set ( & ost - > st - > metadata , " encoder " , encoder_string ,
AV_DICT_DONT_STRDUP_VAL | AV_DICT_DONT_OVERWRITE ) ;
}
static int transcode_init ( void )
{
int ret = 0 , i , j , k ;
AVFormatContext * oc ;
OutputStream * ost ;
InputStream * ist ;
char error [ 1024 ] ;
@ -2048,97 +2131,6 @@ static int transcode_init(void)
input_streams [ j + ifile - > ist_index ] - > start = av_gettime_relative ( ) ;
}
/* for each output stream, we compute the right encoding parameters */
for ( i = 0 ; i < nb_output_streams ; i + + ) {
ost = output_streams [ i ] ;
oc = output_files [ ost - > file_index ] - > ctx ;
ist = get_input_stream ( ost ) ;
if ( ost - > attachment_filename )
continue ;
if ( ist ) {
ost - > st - > disposition = ist - > st - > disposition ;
}
if ( ! ost - > stream_copy ) {
AVCodecContext * enc_ctx = ost - > enc_ctx ;
AVCodecContext * dec_ctx = NULL ;
set_encoder_id ( output_files [ ost - > file_index ] , ost ) ;
if ( ist ) {
dec_ctx = ist - > dec_ctx ;
enc_ctx - > bits_per_raw_sample = dec_ctx - > bits_per_raw_sample ;
enc_ctx - > chroma_sample_location = dec_ctx - > chroma_sample_location ;
}
# if CONFIG_LIBMFX
if ( qsv_transcode_init ( ost ) )
exit_program ( 1 ) ;
# endif
if ( ( enc_ctx - > codec_type = = AVMEDIA_TYPE_VIDEO | |
enc_ctx - > codec_type = = AVMEDIA_TYPE_AUDIO ) & &
filtergraph_is_simple ( ost - > filter - > graph ) ) {
FilterGraph * fg = ost - > filter - > graph ;
ret = ifilter_parameters_from_decoder ( fg - > inputs [ 0 ] ,
dec_ctx ) ;
if ( ret < 0 ) {
av_log ( NULL , AV_LOG_FATAL , " Error initializing filter input \n " ) ;
exit_program ( 1 ) ;
}
if ( configure_filtergraph ( fg ) ) {
av_log ( NULL , AV_LOG_FATAL , " Error opening filters! \n " ) ;
exit_program ( 1 ) ;
}
}
switch ( enc_ctx - > codec_type ) {
case AVMEDIA_TYPE_AUDIO :
enc_ctx - > sample_fmt = ost - > filter - > filter - > inputs [ 0 ] - > format ;
enc_ctx - > sample_rate = ost - > filter - > filter - > inputs [ 0 ] - > sample_rate ;
enc_ctx - > channel_layout = ost - > filter - > filter - > inputs [ 0 ] - > channel_layout ;
enc_ctx - > channels = av_get_channel_layout_nb_channels ( enc_ctx - > channel_layout ) ;
enc_ctx - > time_base = ( AVRational ) { 1 , enc_ctx - > sample_rate } ;
break ;
case AVMEDIA_TYPE_VIDEO :
enc_ctx - > time_base = ost - > filter - > filter - > inputs [ 0 ] - > time_base ;
enc_ctx - > width = ost - > filter - > filter - > inputs [ 0 ] - > w ;
enc_ctx - > height = ost - > filter - > filter - > inputs [ 0 ] - > h ;
enc_ctx - > sample_aspect_ratio = ost - > st - > sample_aspect_ratio =
ost - > frame_aspect_ratio ? // overridden by the -aspect cli option
av_d2q ( ost - > frame_aspect_ratio * enc_ctx - > height / enc_ctx - > width , 255 ) :
ost - > filter - > filter - > inputs [ 0 ] - > sample_aspect_ratio ;
enc_ctx - > pix_fmt = ost - > filter - > filter - > inputs [ 0 ] - > format ;
ost - > st - > avg_frame_rate = ost - > frame_rate ;
if ( dec_ctx & &
( enc_ctx - > width ! = dec_ctx - > width | |
enc_ctx - > height ! = dec_ctx - > height | |
enc_ctx - > pix_fmt ! = dec_ctx - > pix_fmt ) ) {
enc_ctx - > bits_per_raw_sample = 0 ;
}
if ( ost - > forced_keyframes )
parse_forced_key_frames ( ost - > forced_keyframes , ost ,
ost - > enc_ctx ) ;
break ;
case AVMEDIA_TYPE_SUBTITLE :
enc_ctx - > time_base = ( AVRational ) { 1 , 1000 } ;
break ;
default :
abort ( ) ;
break ;
}
}
}
/* init input streams */
for ( i = 0 ; i < nb_input_streams ; i + + )
if ( ( ret = init_input_stream ( i , error , sizeof ( error ) ) ) < 0 )