use ffmpeg n4.5-dev-1598-gacd3c101ef

This commit is contained in:
Taner Sener 2021-08-14 22:19:51 +03:00
parent 9192df7694
commit 98bb5c7619
17 changed files with 372 additions and 114 deletions

View File

@ -70,6 +70,7 @@
#include "libavutil/avassert.h" #include "libavutil/avassert.h"
#include "libavutil/avstring.h" #include "libavutil/avstring.h"
#include "libavutil/bprint.h" #include "libavutil/bprint.h"
#include "libavutil/channel_layout.h"
#include "libavutil/display.h" #include "libavutil/display.h"
#include "libavutil/mathematics.h" #include "libavutil/mathematics.h"
#include "libavutil/imgutils.h" #include "libavutil/imgutils.h"
@ -82,6 +83,7 @@
#include "libavutil/cpu.h" #include "libavutil/cpu.h"
#include "libavutil/ffversion.h" #include "libavutil/ffversion.h"
#include "libavutil/version.h" #include "libavutil/version.h"
#include "libavcodec/bsf.h"
#include "fftools_cmdutils.h" #include "fftools_cmdutils.h"
#if HAVE_SYS_RESOURCE_H #if HAVE_SYS_RESOURCE_H
#include <sys/time.h> #include <sys/time.h>
@ -113,11 +115,6 @@ enum show_muxdemuxers {
SHOW_MUXERS, SHOW_MUXERS,
}; };
void init_opts(void)
{
av_dict_set(&sws_dict, "flags", "bicubic", 0);
}
void uninit_opts(void) void uninit_opts(void)
{ {
av_dict_free(&swr_opts); av_dict_free(&swr_opts);
@ -708,7 +705,6 @@ static void finish_group(OptionParseContext *octx, int group_idx,
resample_opts = NULL; resample_opts = NULL;
sws_dict = NULL; sws_dict = NULL;
swr_opts = NULL; swr_opts = NULL;
init_opts();
memset(&octx->cur_group, 0, sizeof(octx->cur_group)); memset(&octx->cur_group, 0, sizeof(octx->cur_group));
} }
@ -746,8 +742,6 @@ static void init_parse_context(OptionParseContext *octx,
octx->global_opts.group_def = &global_group; octx->global_opts.group_def = &global_group;
octx->global_opts.arg = ""; octx->global_opts.arg = "";
init_opts();
} }
void uninit_parse_context(OptionParseContext *octx) void uninit_parse_context(OptionParseContext *octx)
@ -899,6 +893,32 @@ int opt_cpuflags(void *optctx, const char *opt, const char *arg)
return 0; return 0;
} }
int opt_cpucount(void *optctx, const char *opt, const char *arg)
{
int ret;
int count;
static const AVOption opts[] = {
{"count", NULL, 0, AV_OPT_TYPE_INT, { .i64 = -1}, -1, INT_MAX, 0},
{NULL},
};
static const AVClass class = {
.class_name = "cpucount",
.item_name = av_default_item_name,
.option = opts,
.version = LIBAVUTIL_VERSION_INT,
};
const AVClass *pclass = &class;
ret = av_opt_eval_int(&pclass, opts, arg, &count);
if (!ret) {
av_cpu_force_count(count);
}
return ret;
}
int opt_loglevel(void *optctx, const char *opt, const char *arg) int opt_loglevel(void *optctx, const char *opt, const char *arg)
{ {
const struct { const char *name; int level; } log_levels[] = { const struct { const char *name; int level; } log_levels[] = {
@ -929,20 +949,18 @@ int opt_loglevel(void *optctx, const char *opt, const char *arg)
if (!i && !cmd) { if (!i && !cmd) {
flags = 0; /* missing relative prefix, build absolute value */ flags = 0; /* missing relative prefix, build absolute value */
} }
if (!strncmp(token, "repeat", 6)) { if (av_strstart(token, "repeat", &arg)) {
if (cmd == '-') { if (cmd == '-') {
flags |= AV_LOG_SKIP_REPEATED; flags |= AV_LOG_SKIP_REPEATED;
} else { } else {
flags &= ~AV_LOG_SKIP_REPEATED; flags &= ~AV_LOG_SKIP_REPEATED;
} }
arg = token + 6; } else if (av_strstart(token, "level", &arg)) {
} else if (!strncmp(token, "level", 5)) {
if (cmd == '-') { if (cmd == '-') {
flags &= ~AV_LOG_PRINT_LEVEL; flags &= ~AV_LOG_PRINT_LEVEL;
} else { } else {
flags |= AV_LOG_PRINT_LEVEL; flags |= AV_LOG_PRINT_LEVEL;
} }
arg = token + 5;
} else { } else {
break; break;
} }

View File

@ -115,6 +115,11 @@ void log_callback_help(void* ptr, int level, const char* fmt, va_list vl);
*/ */
int opt_cpuflags(void *optctx, const char *opt, const char *arg); int opt_cpuflags(void *optctx, const char *opt, const char *arg);
/**
* Override the cpucount.
*/
int opt_cpucount(void *optctx, const char *opt, const char *arg);
/** /**
* Fallback for options that are not explicitly handled, these will be * Fallback for options that are not explicitly handled, these will be
* parsed through AVOptions. * parsed through AVOptions.

View File

@ -1275,7 +1275,7 @@ static void do_video_out(OutputFile *of,
if (frame_rate.num > 0 && frame_rate.den > 0) if (frame_rate.num > 0 && frame_rate.den > 0)
duration = 1/(av_q2d(frame_rate) * av_q2d(enc->time_base)); duration = 1/(av_q2d(frame_rate) * av_q2d(enc->time_base));
if(ist && ist->st->start_time != AV_NOPTS_VALUE && ist->st->first_dts != AV_NOPTS_VALUE && ost->frame_rate.num) if(ist && ist->st->start_time != AV_NOPTS_VALUE && ist->first_dts != AV_NOPTS_VALUE && ost->frame_rate.num)
duration = FFMIN(duration, 1/(av_q2d(ost->frame_rate) * av_q2d(enc->time_base))); duration = FFMIN(duration, 1/(av_q2d(ost->frame_rate) * av_q2d(enc->time_base)));
if (!ost->filters_script && if (!ost->filters_script &&
@ -1394,6 +1394,7 @@ static void do_video_out(OutputFile *of,
} }
} }
ost->last_dropped = nb_frames == nb0_frames && next_picture; ost->last_dropped = nb_frames == nb0_frames && next_picture;
ost->dropped_keyframe = ost->last_dropped && next_picture && next_picture->key_frame;
/* duplicates frame if needed */ /* duplicates frame if needed */
for (i = 0; i < nb_frames; i++) { for (i = 0; i < nb_frames; i++) {
@ -1454,6 +1455,11 @@ static void do_video_out(OutputFile *of,
&& in_picture->key_frame==1 && in_picture->key_frame==1
&& !i) { && !i) {
forced_keyframe = 1; forced_keyframe = 1;
} else if ( ost->forced_keyframes
&& !strncmp(ost->forced_keyframes, "source_no_drop", 14)
&& !i) {
forced_keyframe = (in_picture->key_frame == 1) || ost->dropped_keyframe;
ost->dropped_keyframe = 0;
} }
if (forced_keyframe) { if (forced_keyframe) {
@ -2257,9 +2263,11 @@ static void do_streamcopy(InputStream *ist, OutputStream *ost, const AVPacket *p
} }
if (f->recording_time != INT64_MAX) { if (f->recording_time != INT64_MAX) {
start_time = f->ctx->start_time; start_time = 0;
if (f->start_time != AV_NOPTS_VALUE && copy_ts) if (copy_ts) {
start_time += f->start_time; start_time += f->start_time != AV_NOPTS_VALUE ? f->start_time : 0;
start_time += start_at_zero ? 0 : f->ctx->start_time;
}
if (ist->pts >= f->recording_time + start_time) { if (ist->pts >= f->recording_time + start_time) {
close_output_stream(ost); close_output_stream(ost);
return; return;
@ -2804,9 +2812,11 @@ static int process_input_packet(InputStream *ist, const AVPacket *pkt, int no_eo
avpkt = ist->pkt; avpkt = ist->pkt;
if (!ist->saw_first_ts) { if (!ist->saw_first_ts) {
ist->first_dts =
ist->dts = ist->st->avg_frame_rate.num ? - ist->dec_ctx->has_b_frames * AV_TIME_BASE / av_q2d(ist->st->avg_frame_rate) : 0; ist->dts = ist->st->avg_frame_rate.num ? - ist->dec_ctx->has_b_frames * AV_TIME_BASE / av_q2d(ist->st->avg_frame_rate) : 0;
ist->pts = 0; ist->pts = 0;
if (pkt && pkt->pts != AV_NOPTS_VALUE && !ist->decoding_needed) { if (pkt && pkt->pts != AV_NOPTS_VALUE && !ist->decoding_needed) {
ist->first_dts =
ist->dts += av_rescale_q(pkt->pts, ist->st->time_base, AV_TIME_BASE_Q); ist->dts += av_rescale_q(pkt->pts, ist->st->time_base, AV_TIME_BASE_Q);
ist->pts = ist->dts; //unused but better to set it to a value thats not totally wrong ist->pts = ist->dts; //unused but better to set it to a value thats not totally wrong
} }
@ -3139,7 +3149,9 @@ static int init_input_stream(int ist_index, char *error, int error_len)
ist->dec_ctx->get_format = get_format; ist->dec_ctx->get_format = get_format;
ist->dec_ctx->get_buffer2 = get_buffer; ist->dec_ctx->get_buffer2 = get_buffer;
#if LIBAVCODEC_VERSION_MAJOR < 60 #if LIBAVCODEC_VERSION_MAJOR < 60
FF_DISABLE_DEPRECATION_WARNINGS
ist->dec_ctx->thread_safe_callbacks = 1; ist->dec_ctx->thread_safe_callbacks = 1;
FF_ENABLE_DEPRECATION_WARNINGS
#endif #endif
if (ist->dec_ctx->codec_id == AV_CODEC_ID_DVB_SUBTITLE && if (ist->dec_ctx->codec_id == AV_CODEC_ID_DVB_SUBTITLE &&
@ -3651,12 +3663,7 @@ static int init_output_stream_encode(OutputStream *ost, AVFrame *frame)
enc_ctx->bits_per_raw_sample = frame_bits_per_raw_sample; enc_ctx->bits_per_raw_sample = frame_bits_per_raw_sample;
} }
if (ost->top_field_first == 0) { // Field order: autodetection
enc_ctx->field_order = AV_FIELD_BB;
} else if (ost->top_field_first == 1) {
enc_ctx->field_order = AV_FIELD_TT;
}
if (frame) { if (frame) {
if (enc_ctx->flags & (AV_CODEC_FLAG_INTERLACED_DCT | AV_CODEC_FLAG_INTERLACED_ME) && if (enc_ctx->flags & (AV_CODEC_FLAG_INTERLACED_DCT | AV_CODEC_FLAG_INTERLACED_ME) &&
ost->top_field_first >= 0) ost->top_field_first >= 0)
@ -3671,6 +3678,13 @@ static int init_output_stream_encode(OutputStream *ost, AVFrame *frame)
enc_ctx->field_order = AV_FIELD_PROGRESSIVE; enc_ctx->field_order = AV_FIELD_PROGRESSIVE;
} }
// Field order: override
if (ost->top_field_first == 0) {
enc_ctx->field_order = AV_FIELD_BB;
} else if (ost->top_field_first == 1) {
enc_ctx->field_order = AV_FIELD_TT;
}
if (ost->forced_keyframes) { if (ost->forced_keyframes) {
if (!strncmp(ost->forced_keyframes, "expr:", 5)) { if (!strncmp(ost->forced_keyframes, "expr:", 5)) {
ret = av_expr_parse(&ost->forced_keyframes_pexpr, ost->forced_keyframes+5, ret = av_expr_parse(&ost->forced_keyframes_pexpr, ost->forced_keyframes+5,
@ -3934,7 +3948,7 @@ static int transcode_init(void)
/* init framerate emulation */ /* init framerate emulation */
for (i = 0; i < nb_input_files; i++) { for (i = 0; i < nb_input_files; i++) {
InputFile *ifile = input_files[i]; InputFile *ifile = input_files[i];
if (ifile->rate_emu) if (ifile->readrate || ifile->rate_emu)
for (j = 0; j < ifile->nb_streams; j++) for (j = 0; j < ifile->nb_streams; j++)
input_streams[j + ifile->ist_index]->start = av_gettime_relative(); input_streams[j + ifile->ist_index]->start = av_gettime_relative();
} }
@ -4128,10 +4142,10 @@ static OutputStream *choose_output(void)
for (i = 0; i < nb_output_streams; i++) { for (i = 0; i < nb_output_streams; i++) {
OutputStream *ost = output_streams[i]; OutputStream *ost = output_streams[i];
int64_t opts = ost->st->cur_dts == AV_NOPTS_VALUE ? INT64_MIN : int64_t opts = ost->last_mux_dts == AV_NOPTS_VALUE ? INT64_MIN :
av_rescale_q(ost->st->cur_dts, ost->st->time_base, av_rescale_q(ost->last_mux_dts, ost->st->time_base,
AV_TIME_BASE_Q); AV_TIME_BASE_Q);
if (ost->st->cur_dts == AV_NOPTS_VALUE) if (ost->last_mux_dts == AV_NOPTS_VALUE)
av_log(NULL, AV_LOG_DEBUG, av_log(NULL, AV_LOG_DEBUG,
"cur_dts is invalid st:%d (%d) [init:%d i_done:%d finish:%d] (this is harmless if it occurs once at the start per stream)\n", "cur_dts is invalid st:%d (%d) [init:%d i_done:%d finish:%d] (this is harmless if it occurs once at the start per stream)\n",
ost->st->index, ost->st->id, ost->initialized, ost->inputs_done, ost->finished); ost->st->index, ost->st->id, ost->initialized, ost->inputs_done, ost->finished);
@ -4393,12 +4407,20 @@ static int get_input_packet_mt(InputFile *f, AVPacket **pkt)
static int get_input_packet(InputFile *f, AVPacket **pkt) static int get_input_packet(InputFile *f, AVPacket **pkt)
{ {
if (f->rate_emu) { if (f->readrate || f->rate_emu) {
int i; int i;
int64_t file_start = copy_ts * (
(f->ctx->start_time != AV_NOPTS_VALUE ? f->ctx->start_time * !start_at_zero : 0) +
(f->start_time != AV_NOPTS_VALUE ? f->start_time : 0)
);
float scale = f->rate_emu ? 1.0 : f->readrate;
for (i = 0; i < f->nb_streams; i++) { for (i = 0; i < f->nb_streams; i++) {
InputStream *ist = input_streams[f->ist_index + i]; InputStream *ist = input_streams[f->ist_index + i];
int64_t pts = av_rescale(ist->dts, 1000000, AV_TIME_BASE); int64_t stream_ts_offset, pts, now;
int64_t now = av_gettime_relative() - ist->start; if (!ist->nb_packets || (ist->decoding_needed && !ist->got_output)) continue;
stream_ts_offset = FFMAX(ist->first_dts != AV_NOPTS_VALUE ? ist->first_dts : 0, file_start);
pts = av_rescale(ist->dts, 1000000, AV_TIME_BASE);
now = (av_gettime_relative() - ist->start) * scale + stream_ts_offset;
if (pts > now) if (pts > now)
return AVERROR(EAGAIN); return AVERROR(EAGAIN);
} }
@ -5225,6 +5247,7 @@ int ffmpeg_execute(int argc, char **argv)
{ "report", 0, { .func_arg = opt_report }, "generate a report" }, { "report", 0, { .func_arg = opt_report }, "generate a report" },
{ "max_alloc", HAS_ARG, { .func_arg = opt_max_alloc }, "set maximum size of a single allocated block", "bytes" }, { "max_alloc", HAS_ARG, { .func_arg = opt_max_alloc }, "set maximum size of a single allocated block", "bytes" },
{ "cpuflags", HAS_ARG | OPT_EXPERT, { .func_arg = opt_cpuflags }, "force specific cpu flags", "flags" }, { "cpuflags", HAS_ARG | OPT_EXPERT, { .func_arg = opt_cpuflags }, "force specific cpu flags", "flags" },
{ "cpucount", HAS_ARG | OPT_EXPERT, { .func_arg = opt_cpucount }, "force specific cpu count", "count" },
{ "hide_banner", OPT_BOOL | OPT_EXPERT, {&hide_banner}, "do not show program banner", "hide_banner" }, { "hide_banner", OPT_BOOL | OPT_EXPERT, {&hide_banner}, "do not show program banner", "hide_banner" },
#if CONFIG_AVDEVICE #if CONFIG_AVDEVICE

View File

@ -54,6 +54,7 @@
#include "libavformat/avio.h" #include "libavformat/avio.h"
#include "libavcodec/avcodec.h" #include "libavcodec/avcodec.h"
#include "libavcodec/bsf.h"
#include "libavfilter/avfilter.h" #include "libavfilter/avfilter.h"
@ -83,7 +84,6 @@ enum HWAccelID {
HWACCEL_AUTO, HWACCEL_AUTO,
HWACCEL_GENERIC, HWACCEL_GENERIC,
HWACCEL_VIDEOTOOLBOX, HWACCEL_VIDEOTOOLBOX,
HWACCEL_QSV,
}; };
typedef struct HWAccel { typedef struct HWAccel {
@ -142,6 +142,7 @@ typedef struct OptionsContext {
int64_t input_ts_offset; int64_t input_ts_offset;
int loop; int loop;
int rate_emu; int rate_emu;
float readrate;
int accurate_seek; int accurate_seek;
int thread_queue_size; int thread_queue_size;
@ -339,6 +340,7 @@ typedef struct InputStream {
/* predicted dts of the next packet read for this stream or (when there are /* predicted dts of the next packet read for this stream or (when there are
* several frames in a packet) of the next frame in current packet (in AV_TIME_BASE units) */ * several frames in a packet) of the next frame in current packet (in AV_TIME_BASE units) */
int64_t next_dts; int64_t next_dts;
int64_t first_dts; ///< dts of the first packet read for this stream (in AV_TIME_BASE units)
int64_t dts; ///< dts of the last packet read for this stream (in AV_TIME_BASE units) int64_t dts; ///< dts of the last packet read for this stream (in AV_TIME_BASE units)
int64_t next_pts; ///< synthetic pts for the next decode frame (in AV_TIME_BASE units) int64_t next_pts; ///< synthetic pts for the next decode frame (in AV_TIME_BASE units)
@ -440,6 +442,7 @@ typedef struct InputFile {
from ctx.nb_streams if new streams appear during av_read_frame() */ from ctx.nb_streams if new streams appear during av_read_frame() */
int nb_streams_warn; /* number of streams that the user was warned of */ int nb_streams_warn; /* number of streams that the user was warned of */
int rate_emu; int rate_emu;
float readrate;
int accurate_seek; int accurate_seek;
AVPacket *pkt; AVPacket *pkt;
@ -526,6 +529,7 @@ typedef struct OutputStream {
char *forced_keyframes; char *forced_keyframes;
AVExpr *forced_keyframes_pexpr; AVExpr *forced_keyframes_pexpr;
double forced_keyframes_expr_const_values[FKF_NB]; double forced_keyframes_expr_const_values[FKF_NB];
int dropped_keyframe;
/* audio only */ /* audio only */
int *audio_channels_map; /* list of the channels id to pick from the source stream */ int *audio_channels_map; /* list of the channels id to pick from the source stream */

View File

@ -638,7 +638,7 @@ int configure_output_filter(FilterGraph *fg, OutputFilter *ofilter,
switch (avfilter_pad_get_type(out->filter_ctx->output_pads, out->pad_idx)) { switch (avfilter_pad_get_type(out->filter_ctx->output_pads, out->pad_idx)) {
case AVMEDIA_TYPE_VIDEO: return configure_output_video_filter(fg, ofilter, out); case AVMEDIA_TYPE_VIDEO: return configure_output_video_filter(fg, ofilter, out);
case AVMEDIA_TYPE_AUDIO: return configure_output_audio_filter(fg, ofilter, out); case AVMEDIA_TYPE_AUDIO: return configure_output_audio_filter(fg, ofilter, out);
default: av_assert0(0); default: av_assert0(0); return 0;
} }
} }
@ -948,7 +948,7 @@ static int configure_input_filter(FilterGraph *fg, InputFilter *ifilter,
switch (avfilter_pad_get_type(in->filter_ctx->input_pads, in->pad_idx)) { switch (avfilter_pad_get_type(in->filter_ctx->input_pads, in->pad_idx)) {
case AVMEDIA_TYPE_VIDEO: return configure_input_video_filter(fg, ifilter, in); case AVMEDIA_TYPE_VIDEO: return configure_input_video_filter(fg, ifilter, in);
case AVMEDIA_TYPE_AUDIO: return configure_input_audio_filter(fg, ifilter, in); case AVMEDIA_TYPE_AUDIO: return configure_input_audio_filter(fg, ifilter, in);
default: av_assert0(0); default: av_assert0(0); return 0;
} }
} }
@ -987,7 +987,11 @@ int configure_filtergraph(FilterGraph *fg)
} }
if (strlen(args)) if (strlen(args))
args[strlen(args)-1] = 0; args[strlen(args)-1] = 0;
fg->graph->scale_sws_opts = av_strdup(args);
if (!strncmp(args, "sws_flags=", 10)) {
// keep the 'flags=' part
fg->graph->scale_sws_opts = av_strdup(args+4);
}
args[0] = 0; args[0] = 0;
while ((e = av_dict_get(ost->swr_opts, "", e, while ((e = av_dict_get(ost->swr_opts, "", e,

View File

@ -348,6 +348,18 @@ int hw_device_setup_for_decode(InputStream *ist)
} else if (ist->hwaccel_id == HWACCEL_GENERIC) { } else if (ist->hwaccel_id == HWACCEL_GENERIC) {
type = ist->hwaccel_device_type; type = ist->hwaccel_device_type;
dev = hw_device_get_by_type(type); dev = hw_device_get_by_type(type);
// When "-qsv_device device" is used, an internal QSV device named
// as "__qsv_device" is created. Another QSV device is created too
// if "-init_hw_device qsv=name:device" is used. There are 2 QSV devices
// if both "-qsv_device device" and "-init_hw_device qsv=name:device"
// are used, hw_device_get_by_type(AV_HWDEVICE_TYPE_QSV) returns NULL.
// To keep back-compatibility with the removed ad-hoc libmfx setup code,
// call hw_device_get_by_name("__qsv_device") to select the internal QSV
// device.
if (!dev && type == AV_HWDEVICE_TYPE_QSV)
dev = hw_device_get_by_name("__qsv_device");
if (!dev) if (!dev)
err = hw_device_init_from_type(type, NULL, &dev); err = hw_device_init_from_type(type, NULL, &dev);
} else { } else {

View File

@ -45,6 +45,7 @@
#include "libavformat/avformat.h" #include "libavformat/avformat.h"
#include "libavcodec/avcodec.h" #include "libavcodec/avcodec.h"
#include "libavcodec/bsf.h"
#include "libavfilter/avfilter.h" #include "libavfilter/avfilter.h"
@ -154,9 +155,6 @@ static const char *const opt_name_enc_time_bases[] = {"enc_time_base"
const HWAccel hwaccels[] = { const HWAccel hwaccels[] = {
#if CONFIG_VIDEOTOOLBOX #if CONFIG_VIDEOTOOLBOX
{ "videotoolbox", videotoolbox_init, HWACCEL_VIDEOTOOLBOX, AV_PIX_FMT_VIDEOTOOLBOX }, { "videotoolbox", videotoolbox_init, HWACCEL_VIDEOTOOLBOX, AV_PIX_FMT_VIDEOTOOLBOX },
#endif
#if CONFIG_LIBMFX
{ "qsv", qsv_init, HWACCEL_QSV, AV_PIX_FMT_QSV },
#endif #endif
{ 0 }, { 0 },
}; };
@ -204,6 +202,7 @@ __thread int input_sync;
__thread int input_stream_potentially_available = 0; __thread int input_stream_potentially_available = 0;
__thread int ignore_unknown_streams = 0; __thread int ignore_unknown_streams = 0;
__thread int copy_unknown_streams = 0; __thread int copy_unknown_streams = 0;
__thread static int recast_media = 0;
__thread int find_stream_info = 1; __thread int find_stream_info = 1;
extern __thread OptionDef *ffmpeg_options; extern __thread OptionDef *ffmpeg_options;
@ -589,6 +588,23 @@ int opt_vaapi_device(void *optctx, const char *opt, const char *arg)
} }
#endif #endif
#if CONFIG_QSV
static int opt_qsv_device(void *optctx, const char *opt, const char *arg)
{
const char *prefix = "qsv=__qsv_device:hw_any,child_device=";
int err;
char *tmp = av_asprintf("%s%s", prefix, arg);
if (!tmp)
return AVERROR(ENOMEM);
err = hw_device_init_from_string(tmp, NULL);
av_free(tmp);
return err;
}
#endif
int opt_init_hw_device(void *optctx, const char *opt, const char *arg) int opt_init_hw_device(void *optctx, const char *opt, const char *arg)
{ {
if (!strcmp(arg, "list")) { if (!strcmp(arg, "list")) {
@ -779,7 +795,7 @@ const AVCodec *find_codec_or_die(const char *name, enum AVMediaType type, int en
av_log(NULL, AV_LOG_FATAL, "Unknown %s '%s'\n", codec_string, name); av_log(NULL, AV_LOG_FATAL, "Unknown %s '%s'\n", codec_string, name);
exit_program(1); exit_program(1);
} }
if (codec->type != type) { if (codec->type != type && !recast_media) {
av_log(NULL, AV_LOG_FATAL, "Invalid %s type '%s'\n", codec_string, name); av_log(NULL, AV_LOG_FATAL, "Invalid %s type '%s'\n", codec_string, name);
exit_program(1); exit_program(1);
} }
@ -794,6 +810,8 @@ const AVCodec *choose_decoder(OptionsContext *o, AVFormatContext *s, AVStream *s
if (codec_name) { if (codec_name) {
const AVCodec *codec = find_codec_or_die(codec_name, st->codecpar->codec_type, 0); const AVCodec *codec = find_codec_or_die(codec_name, st->codecpar->codec_type, 0);
st->codecpar->codec_id = codec->id; st->codecpar->codec_id = codec->id;
if (recast_media && st->codecpar->codec_type != codec->type)
st->codecpar->codec_type = codec->type;
return codec; return codec;
} else } else
return avcodec_find_decoder(st->codecpar->codec_id); return avcodec_find_decoder(st->codecpar->codec_id);
@ -829,6 +847,7 @@ void add_input_streams(OptionsContext *o, AVFormatContext *ic)
ist->discard = 1; ist->discard = 1;
st->discard = AVDISCARD_ALL; st->discard = AVDISCARD_ALL;
ist->nb_samples = 0; ist->nb_samples = 0;
ist->first_dts = AV_NOPTS_VALUE;
ist->min_pts = INT64_MAX; ist->min_pts = INT64_MAX;
ist->max_pts = INT64_MIN; ist->max_pts = INT64_MIN;
@ -913,6 +932,12 @@ void add_input_streams(OptionsContext *o, AVFormatContext *ic)
"with old commandlines. This behaviour is DEPRECATED and will be removed " "with old commandlines. This behaviour is DEPRECATED and will be removed "
"in the future. Please explicitly set \"-hwaccel_output_format cuda\".\n"); "in the future. Please explicitly set \"-hwaccel_output_format cuda\".\n");
ist->hwaccel_output_format = AV_PIX_FMT_CUDA; ist->hwaccel_output_format = AV_PIX_FMT_CUDA;
} else if (!hwaccel_output_format && hwaccel && !strcmp(hwaccel, "qsv")) {
av_log(NULL, AV_LOG_WARNING,
"WARNING: defaulting hwaccel_output_format to qsv for compatibility "
"with old commandlines. This behaviour is DEPRECATED and will be removed "
"in the future. Please explicitly set \"-hwaccel_output_format qsv\".\n");
ist->hwaccel_output_format = AV_PIX_FMT_QSV;
} else if (hwaccel_output_format) { } else if (hwaccel_output_format) {
ist->hwaccel_output_format = av_get_pix_fmt(hwaccel_output_format); ist->hwaccel_output_format = av_get_pix_fmt(hwaccel_output_format);
if (ist->hwaccel_output_format == AV_PIX_FMT_NONE) { if (ist->hwaccel_output_format == AV_PIX_FMT_NONE) {
@ -1302,6 +1327,17 @@ int open_input_file(OptionsContext *o, const char *filename)
f->loop = o->loop; f->loop = o->loop;
f->duration = 0; f->duration = 0;
f->time_base = (AVRational){ 1, 1 }; f->time_base = (AVRational){ 1, 1 };
f->readrate = o->readrate ? o->readrate : 0.0;
if (f->readrate < 0.0f) {
av_log(NULL, AV_LOG_ERROR, "Option -readrate for Input #%d is %0.3f; it must be non-negative.\n", nb_input_files, f->readrate);
exit_program(1);
}
if (f->readrate && f->rate_emu) {
av_log(NULL, AV_LOG_WARNING, "Both -readrate and -re set for Input #%d. Using -readrate %0.3f.\n", nb_input_files, f->readrate);
f->rate_emu = 0;
}
f->pkt = av_packet_alloc(); f->pkt = av_packet_alloc();
if (!f->pkt) if (!f->pkt)
exit_program(1); exit_program(1);
@ -2264,22 +2300,34 @@ int open_output_file(OptionsContext *o, const char *filename)
if (!o->video_disable && av_guess_codec(oc->oformat, NULL, filename, NULL, AVMEDIA_TYPE_VIDEO) != AV_CODEC_ID_NONE) { if (!o->video_disable && av_guess_codec(oc->oformat, NULL, filename, NULL, AVMEDIA_TYPE_VIDEO) != AV_CODEC_ID_NONE) {
int best_score = 0, idx = -1; int best_score = 0, idx = -1;
int qcr = avformat_query_codec(oc->oformat, oc->oformat->video_codec, 0); int qcr = avformat_query_codec(oc->oformat, oc->oformat->video_codec, 0);
for (i = 0; i < nb_input_streams; i++) { for (j = 0; j < nb_input_files; j++) {
int score; InputFile *ifile = input_files[j];
ist = input_streams[i]; int file_best_score = 0, file_best_idx = -1;
score = ist->st->codecpar->width * ist->st->codecpar->height for (i = 0; i < ifile->nb_streams; i++) {
int score;
ist = input_streams[ifile->ist_index + i];
score = ist->st->codecpar->width * ist->st->codecpar->height
+ 100000000 * !!(ist->st->event_flags & AVSTREAM_EVENT_FLAG_NEW_PACKETS) + 100000000 * !!(ist->st->event_flags & AVSTREAM_EVENT_FLAG_NEW_PACKETS)
+ 5000000*!!(ist->st->disposition & AV_DISPOSITION_DEFAULT); + 5000000*!!(ist->st->disposition & AV_DISPOSITION_DEFAULT);
if (ist->user_set_discard == AVDISCARD_ALL) if (ist->user_set_discard == AVDISCARD_ALL)
continue;
if((qcr!=MKTAG('A', 'P', 'I', 'C')) && (ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC))
score = 1;
if (ist->st->codecpar->codec_type == AVMEDIA_TYPE_VIDEO &&
score > best_score) {
if((qcr==MKTAG('A', 'P', 'I', 'C')) && !(ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC))
continue; continue;
best_score = score; if((qcr!=MKTAG('A', 'P', 'I', 'C')) && (ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC))
idx = i; score = 1;
if (ist->st->codecpar->codec_type == AVMEDIA_TYPE_VIDEO &&
score > file_best_score) {
if((qcr==MKTAG('A', 'P', 'I', 'C')) && !(ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC))
continue;
file_best_score = score;
file_best_idx = ifile->ist_index + i;
}
}
if (file_best_idx >= 0) {
if((qcr == MKTAG('A', 'P', 'I', 'C')) || !(ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC))
file_best_score -= 5000000*!!(input_streams[file_best_idx]->st->disposition & AV_DISPOSITION_DEFAULT);
if (file_best_score > best_score) {
best_score = file_best_score;
idx = file_best_idx;
}
} }
} }
if (idx >= 0) if (idx >= 0)
@ -2289,18 +2337,29 @@ int open_output_file(OptionsContext *o, const char *filename)
/* audio: most channels */ /* audio: most channels */
if (!o->audio_disable && av_guess_codec(oc->oformat, NULL, filename, NULL, AVMEDIA_TYPE_AUDIO) != AV_CODEC_ID_NONE) { if (!o->audio_disable && av_guess_codec(oc->oformat, NULL, filename, NULL, AVMEDIA_TYPE_AUDIO) != AV_CODEC_ID_NONE) {
int best_score = 0, idx = -1; int best_score = 0, idx = -1;
for (i = 0; i < nb_input_streams; i++) { for (j = 0; j < nb_input_files; j++) {
InputFile *ifile = input_files[j];
int file_best_score = 0, file_best_idx = -1;
for (i = 0; i < ifile->nb_streams; i++) {
int score; int score;
ist = input_streams[i]; ist = input_streams[ifile->ist_index + i];
score = ist->st->codecpar->channels score = ist->st->codecpar->channels
+ 100000000 * !!(ist->st->event_flags & AVSTREAM_EVENT_FLAG_NEW_PACKETS) + 100000000 * !!(ist->st->event_flags & AVSTREAM_EVENT_FLAG_NEW_PACKETS)
+ 5000000*!!(ist->st->disposition & AV_DISPOSITION_DEFAULT); + 5000000*!!(ist->st->disposition & AV_DISPOSITION_DEFAULT);
if (ist->user_set_discard == AVDISCARD_ALL) if (ist->user_set_discard == AVDISCARD_ALL)
continue; continue;
if (ist->st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO && if (ist->st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO &&
score > best_score) { score > file_best_score) {
best_score = score; file_best_score = score;
idx = i; file_best_idx = ifile->ist_index + i;
}
}
if (file_best_idx >= 0) {
file_best_score -= 5000000*!!(input_streams[file_best_idx]->st->disposition & AV_DISPOSITION_DEFAULT);
if (file_best_score > best_score) {
best_score = file_best_score;
idx = file_best_idx;
}
} }
} }
if (idx >= 0) if (idx >= 0)

View File

@ -40,6 +40,7 @@
#include "libavutil/avassert.h" #include "libavutil/avassert.h"
#include "libavutil/avstring.h" #include "libavutil/avstring.h"
#include "libavutil/bprint.h" #include "libavutil/bprint.h"
#include "libavutil/channel_layout.h"
#include "libavutil/display.h" #include "libavutil/display.h"
#include "libavutil/hash.h" #include "libavutil/hash.h"
#include "libavutil/hdr_dynamic_metadata.h" #include "libavutil/hdr_dynamic_metadata.h"
@ -1688,9 +1689,9 @@ static void xml_print_section_header(WriterContext *wctx)
wctx->section[wctx->level-1] : NULL; wctx->section[wctx->level-1] : NULL;
if (wctx->level == 0) { if (wctx->level == 0) {
const char *qual = " xmlns:xsi='http://www.w3.org/2001/XMLSchema-instance' " const char *qual = " xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" "
"xmlns:ffprobe='http://www.ffmpeg.org/schema/ffprobe' " "xmlns:ffprobe=\"http://www.ffmpeg.org/schema/ffprobe\" "
"xsi:schemaLocation='http://www.ffmpeg.org/schema/ffprobe ffprobe.xsd'"; "xsi:schemaLocation=\"http://www.ffmpeg.org/schema/ffprobe ffprobe.xsd\"";
av_log(NULL, AV_LOG_STDERR, "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n"); av_log(NULL, AV_LOG_STDERR, "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n");
av_log(NULL, AV_LOG_STDERR, "<%sffprobe%s>\n", av_log(NULL, AV_LOG_STDERR, "<%sffprobe%s>\n",
@ -2032,7 +2033,7 @@ static void print_pkt_side_data(WriterContext *w,
print_int("dv_bl_signal_compatibility_id", dovi->dv_bl_signal_compatibility_id); print_int("dv_bl_signal_compatibility_id", dovi->dv_bl_signal_compatibility_id);
} else if (sd->type == AV_PKT_DATA_AUDIO_SERVICE_TYPE) { } else if (sd->type == AV_PKT_DATA_AUDIO_SERVICE_TYPE) {
enum AVAudioServiceType *t = (enum AVAudioServiceType *)sd->data; enum AVAudioServiceType *t = (enum AVAudioServiceType *)sd->data;
print_int("type", *t); print_int("service_type", *t);
} else if (sd->type == AV_PKT_DATA_MPEGTS_STREAM_ID) { } else if (sd->type == AV_PKT_DATA_MPEGTS_STREAM_ID) {
print_int("id", *sd->data); print_int("id", *sd->data);
} else if (sd->type == AV_PKT_DATA_CPB_PROPERTIES) { } else if (sd->type == AV_PKT_DATA_CPB_PROPERTIES) {
@ -2248,8 +2249,8 @@ static void show_frame(WriterContext *w, AVFrame *frame, AVStream *stream,
else print_str_opt("media_type", "unknown"); else print_str_opt("media_type", "unknown");
print_int("stream_index", stream->index); print_int("stream_index", stream->index);
print_int("key_frame", frame->key_frame); print_int("key_frame", frame->key_frame);
print_ts ("pkt_pts", frame->pts); print_ts ("pts", frame->pts);
print_time("pkt_pts_time", frame->pts, &stream->time_base); print_time("pts_time", frame->pts, &stream->time_base);
print_ts ("pkt_dts", frame->pkt_dts); print_ts ("pkt_dts", frame->pkt_dts);
print_time("pkt_dts_time", frame->pkt_dts, &stream->time_base); print_time("pkt_dts_time", frame->pkt_dts, &stream->time_base);
print_ts ("best_effort_timestamp", frame->best_effort_timestamp); print_ts ("best_effort_timestamp", frame->best_effort_timestamp);
@ -3081,8 +3082,7 @@ static void close_input_file(InputFile *ifile)
/* close decoder for each stream */ /* close decoder for each stream */
for (i = 0; i < ifile->nb_streams; i++) for (i = 0; i < ifile->nb_streams; i++)
if (ifile->streams[i].st->codecpar->codec_id != AV_CODEC_ID_NONE) avcodec_free_context(&ifile->streams[i].dec_ctx);
avcodec_free_context(&ifile->streams[i].dec_ctx);
av_freep(&ifile->streams); av_freep(&ifile->streams);
ifile->nb_streams = 0; ifile->nb_streams = 0;
@ -3747,6 +3747,7 @@ int ffprobe_execute(int argc, char **argv)
{ "report", 0, { .func_arg = opt_report }, "generate a report" }, { "report", 0, { .func_arg = opt_report }, "generate a report" },
{ "max_alloc", HAS_ARG, { .func_arg = opt_max_alloc }, "set maximum size of a single allocated block", "bytes" }, { "max_alloc", HAS_ARG, { .func_arg = opt_max_alloc }, "set maximum size of a single allocated block", "bytes" },
{ "cpuflags", HAS_ARG | OPT_EXPERT, { .func_arg = opt_cpuflags }, "force specific cpu flags", "flags" }, { "cpuflags", HAS_ARG | OPT_EXPERT, { .func_arg = opt_cpuflags }, "force specific cpu flags", "flags" },
{ "cpucount", HAS_ARG | OPT_EXPERT, { .func_arg = opt_cpucount }, "force specific cpu count", "count" },
{ "hide_banner", OPT_BOOL | OPT_EXPERT, {&hide_banner}, "do not show program banner", "hide_banner" }, { "hide_banner", OPT_BOOL | OPT_EXPERT, {&hide_banner}, "do not show program banner", "hide_banner" },
#if CONFIG_AVDEVICE #if CONFIG_AVDEVICE
@ -3830,7 +3831,6 @@ int ffprobe_execute(int argc, char **argv)
ffprobe_options = options; ffprobe_options = options;
parse_loglevel(argc, argv, options); parse_loglevel(argc, argv, options);
avformat_network_init(); avformat_network_init();
init_opts();
#if CONFIG_AVDEVICE #if CONFIG_AVDEVICE
avdevice_register_all(); avdevice_register_all();
#endif #endif

View File

@ -67,6 +67,7 @@
#include "libavutil/avassert.h" #include "libavutil/avassert.h"
#include "libavutil/avstring.h" #include "libavutil/avstring.h"
#include "libavutil/bprint.h" #include "libavutil/bprint.h"
#include "libavutil/channel_layout.h"
#include "libavutil/display.h" #include "libavutil/display.h"
#include "libavutil/mathematics.h" #include "libavutil/mathematics.h"
#include "libavutil/imgutils.h" #include "libavutil/imgutils.h"
@ -79,6 +80,7 @@
#include "libavutil/cpu.h" #include "libavutil/cpu.h"
#include "libavutil/ffversion.h" #include "libavutil/ffversion.h"
#include "libavutil/version.h" #include "libavutil/version.h"
#include "libavcodec/bsf.h"
#include "fftools_cmdutils.h" #include "fftools_cmdutils.h"
#if HAVE_SYS_RESOURCE_H #if HAVE_SYS_RESOURCE_H
#include <sys/time.h> #include <sys/time.h>
@ -110,11 +112,6 @@ enum show_muxdemuxers {
SHOW_MUXERS, SHOW_MUXERS,
}; };
void init_opts(void)
{
av_dict_set(&sws_dict, "flags", "bicubic", 0);
}
void uninit_opts(void) void uninit_opts(void)
{ {
av_dict_free(&swr_opts); av_dict_free(&swr_opts);
@ -705,7 +702,6 @@ static void finish_group(OptionParseContext *octx, int group_idx,
resample_opts = NULL; resample_opts = NULL;
sws_dict = NULL; sws_dict = NULL;
swr_opts = NULL; swr_opts = NULL;
init_opts();
memset(&octx->cur_group, 0, sizeof(octx->cur_group)); memset(&octx->cur_group, 0, sizeof(octx->cur_group));
} }
@ -743,8 +739,6 @@ static void init_parse_context(OptionParseContext *octx,
octx->global_opts.group_def = &global_group; octx->global_opts.group_def = &global_group;
octx->global_opts.arg = ""; octx->global_opts.arg = "";
init_opts();
} }
void uninit_parse_context(OptionParseContext *octx) void uninit_parse_context(OptionParseContext *octx)
@ -896,6 +890,32 @@ int opt_cpuflags(void *optctx, const char *opt, const char *arg)
return 0; return 0;
} }
int opt_cpucount(void *optctx, const char *opt, const char *arg)
{
int ret;
int count;
static const AVOption opts[] = {
{"count", NULL, 0, AV_OPT_TYPE_INT, { .i64 = -1}, -1, INT_MAX, 0},
{NULL},
};
static const AVClass class = {
.class_name = "cpucount",
.item_name = av_default_item_name,
.option = opts,
.version = LIBAVUTIL_VERSION_INT,
};
const AVClass *pclass = &class;
ret = av_opt_eval_int(&pclass, opts, arg, &count);
if (!ret) {
av_cpu_force_count(count);
}
return ret;
}
int opt_loglevel(void *optctx, const char *opt, const char *arg) int opt_loglevel(void *optctx, const char *opt, const char *arg)
{ {
const struct { const char *name; int level; } log_levels[] = { const struct { const char *name; int level; } log_levels[] = {
@ -926,20 +946,18 @@ int opt_loglevel(void *optctx, const char *opt, const char *arg)
if (!i && !cmd) { if (!i && !cmd) {
flags = 0; /* missing relative prefix, build absolute value */ flags = 0; /* missing relative prefix, build absolute value */
} }
if (!strncmp(token, "repeat", 6)) { if (av_strstart(token, "repeat", &arg)) {
if (cmd == '-') { if (cmd == '-') {
flags |= AV_LOG_SKIP_REPEATED; flags |= AV_LOG_SKIP_REPEATED;
} else { } else {
flags &= ~AV_LOG_SKIP_REPEATED; flags &= ~AV_LOG_SKIP_REPEATED;
} }
arg = token + 6; } else if (av_strstart(token, "level", &arg)) {
} else if (!strncmp(token, "level", 5)) {
if (cmd == '-') { if (cmd == '-') {
flags &= ~AV_LOG_PRINT_LEVEL; flags &= ~AV_LOG_PRINT_LEVEL;
} else { } else {
flags |= AV_LOG_PRINT_LEVEL; flags |= AV_LOG_PRINT_LEVEL;
} }
arg = token + 5;
} else { } else {
break; break;
} }

View File

@ -115,6 +115,11 @@ void log_callback_help(void* ptr, int level, const char* fmt, va_list vl);
*/ */
int opt_cpuflags(void *optctx, const char *opt, const char *arg); int opt_cpuflags(void *optctx, const char *opt, const char *arg);
/**
* Override the cpucount.
*/
int opt_cpucount(void *optctx, const char *opt, const char *arg);
/** /**
* Fallback for options that are not explicitly handled, these will be * Fallback for options that are not explicitly handled, these will be
* parsed through AVOptions. * parsed through AVOptions.

View File

@ -1272,7 +1272,7 @@ static void do_video_out(OutputFile *of,
if (frame_rate.num > 0 && frame_rate.den > 0) if (frame_rate.num > 0 && frame_rate.den > 0)
duration = 1/(av_q2d(frame_rate) * av_q2d(enc->time_base)); duration = 1/(av_q2d(frame_rate) * av_q2d(enc->time_base));
if(ist && ist->st->start_time != AV_NOPTS_VALUE && ist->st->first_dts != AV_NOPTS_VALUE && ost->frame_rate.num) if(ist && ist->st->start_time != AV_NOPTS_VALUE && ist->first_dts != AV_NOPTS_VALUE && ost->frame_rate.num)
duration = FFMIN(duration, 1/(av_q2d(ost->frame_rate) * av_q2d(enc->time_base))); duration = FFMIN(duration, 1/(av_q2d(ost->frame_rate) * av_q2d(enc->time_base)));
if (!ost->filters_script && if (!ost->filters_script &&
@ -1391,6 +1391,7 @@ static void do_video_out(OutputFile *of,
} }
} }
ost->last_dropped = nb_frames == nb0_frames && next_picture; ost->last_dropped = nb_frames == nb0_frames && next_picture;
ost->dropped_keyframe = ost->last_dropped && next_picture && next_picture->key_frame;
/* duplicates frame if needed */ /* duplicates frame if needed */
for (i = 0; i < nb_frames; i++) { for (i = 0; i < nb_frames; i++) {
@ -1451,6 +1452,11 @@ static void do_video_out(OutputFile *of,
&& in_picture->key_frame==1 && in_picture->key_frame==1
&& !i) { && !i) {
forced_keyframe = 1; forced_keyframe = 1;
} else if ( ost->forced_keyframes
&& !strncmp(ost->forced_keyframes, "source_no_drop", 14)
&& !i) {
forced_keyframe = (in_picture->key_frame == 1) || ost->dropped_keyframe;
ost->dropped_keyframe = 0;
} }
if (forced_keyframe) { if (forced_keyframe) {
@ -2254,9 +2260,11 @@ static void do_streamcopy(InputStream *ist, OutputStream *ost, const AVPacket *p
} }
if (f->recording_time != INT64_MAX) { if (f->recording_time != INT64_MAX) {
start_time = f->ctx->start_time; start_time = 0;
if (f->start_time != AV_NOPTS_VALUE && copy_ts) if (copy_ts) {
start_time += f->start_time; start_time += f->start_time != AV_NOPTS_VALUE ? f->start_time : 0;
start_time += start_at_zero ? 0 : f->ctx->start_time;
}
if (ist->pts >= f->recording_time + start_time) { if (ist->pts >= f->recording_time + start_time) {
close_output_stream(ost); close_output_stream(ost);
return; return;
@ -2801,9 +2809,11 @@ static int process_input_packet(InputStream *ist, const AVPacket *pkt, int no_eo
avpkt = ist->pkt; avpkt = ist->pkt;
if (!ist->saw_first_ts) { if (!ist->saw_first_ts) {
ist->first_dts =
ist->dts = ist->st->avg_frame_rate.num ? - ist->dec_ctx->has_b_frames * AV_TIME_BASE / av_q2d(ist->st->avg_frame_rate) : 0; ist->dts = ist->st->avg_frame_rate.num ? - ist->dec_ctx->has_b_frames * AV_TIME_BASE / av_q2d(ist->st->avg_frame_rate) : 0;
ist->pts = 0; ist->pts = 0;
if (pkt && pkt->pts != AV_NOPTS_VALUE && !ist->decoding_needed) { if (pkt && pkt->pts != AV_NOPTS_VALUE && !ist->decoding_needed) {
ist->first_dts =
ist->dts += av_rescale_q(pkt->pts, ist->st->time_base, AV_TIME_BASE_Q); ist->dts += av_rescale_q(pkt->pts, ist->st->time_base, AV_TIME_BASE_Q);
ist->pts = ist->dts; //unused but better to set it to a value thats not totally wrong ist->pts = ist->dts; //unused but better to set it to a value thats not totally wrong
} }
@ -3136,7 +3146,9 @@ static int init_input_stream(int ist_index, char *error, int error_len)
ist->dec_ctx->get_format = get_format; ist->dec_ctx->get_format = get_format;
ist->dec_ctx->get_buffer2 = get_buffer; ist->dec_ctx->get_buffer2 = get_buffer;
#if LIBAVCODEC_VERSION_MAJOR < 60 #if LIBAVCODEC_VERSION_MAJOR < 60
FF_DISABLE_DEPRECATION_WARNINGS
ist->dec_ctx->thread_safe_callbacks = 1; ist->dec_ctx->thread_safe_callbacks = 1;
FF_ENABLE_DEPRECATION_WARNINGS
#endif #endif
if (ist->dec_ctx->codec_id == AV_CODEC_ID_DVB_SUBTITLE && if (ist->dec_ctx->codec_id == AV_CODEC_ID_DVB_SUBTITLE &&
@ -3648,12 +3660,7 @@ static int init_output_stream_encode(OutputStream *ost, AVFrame *frame)
enc_ctx->bits_per_raw_sample = frame_bits_per_raw_sample; enc_ctx->bits_per_raw_sample = frame_bits_per_raw_sample;
} }
if (ost->top_field_first == 0) { // Field order: autodetection
enc_ctx->field_order = AV_FIELD_BB;
} else if (ost->top_field_first == 1) {
enc_ctx->field_order = AV_FIELD_TT;
}
if (frame) { if (frame) {
if (enc_ctx->flags & (AV_CODEC_FLAG_INTERLACED_DCT | AV_CODEC_FLAG_INTERLACED_ME) && if (enc_ctx->flags & (AV_CODEC_FLAG_INTERLACED_DCT | AV_CODEC_FLAG_INTERLACED_ME) &&
ost->top_field_first >= 0) ost->top_field_first >= 0)
@ -3668,6 +3675,13 @@ static int init_output_stream_encode(OutputStream *ost, AVFrame *frame)
enc_ctx->field_order = AV_FIELD_PROGRESSIVE; enc_ctx->field_order = AV_FIELD_PROGRESSIVE;
} }
// Field order: override
if (ost->top_field_first == 0) {
enc_ctx->field_order = AV_FIELD_BB;
} else if (ost->top_field_first == 1) {
enc_ctx->field_order = AV_FIELD_TT;
}
if (ost->forced_keyframes) { if (ost->forced_keyframes) {
if (!strncmp(ost->forced_keyframes, "expr:", 5)) { if (!strncmp(ost->forced_keyframes, "expr:", 5)) {
ret = av_expr_parse(&ost->forced_keyframes_pexpr, ost->forced_keyframes+5, ret = av_expr_parse(&ost->forced_keyframes_pexpr, ost->forced_keyframes+5,
@ -3931,7 +3945,7 @@ static int transcode_init(void)
/* init framerate emulation */ /* init framerate emulation */
for (i = 0; i < nb_input_files; i++) { for (i = 0; i < nb_input_files; i++) {
InputFile *ifile = input_files[i]; InputFile *ifile = input_files[i];
if (ifile->rate_emu) if (ifile->readrate || ifile->rate_emu)
for (j = 0; j < ifile->nb_streams; j++) for (j = 0; j < ifile->nb_streams; j++)
input_streams[j + ifile->ist_index]->start = av_gettime_relative(); input_streams[j + ifile->ist_index]->start = av_gettime_relative();
} }
@ -4125,10 +4139,10 @@ static OutputStream *choose_output(void)
for (i = 0; i < nb_output_streams; i++) { for (i = 0; i < nb_output_streams; i++) {
OutputStream *ost = output_streams[i]; OutputStream *ost = output_streams[i];
int64_t opts = ost->st->cur_dts == AV_NOPTS_VALUE ? INT64_MIN : int64_t opts = ost->last_mux_dts == AV_NOPTS_VALUE ? INT64_MIN :
av_rescale_q(ost->st->cur_dts, ost->st->time_base, av_rescale_q(ost->last_mux_dts, ost->st->time_base,
AV_TIME_BASE_Q); AV_TIME_BASE_Q);
if (ost->st->cur_dts == AV_NOPTS_VALUE) if (ost->last_mux_dts == AV_NOPTS_VALUE)
av_log(NULL, AV_LOG_DEBUG, av_log(NULL, AV_LOG_DEBUG,
"cur_dts is invalid st:%d (%d) [init:%d i_done:%d finish:%d] (this is harmless if it occurs once at the start per stream)\n", "cur_dts is invalid st:%d (%d) [init:%d i_done:%d finish:%d] (this is harmless if it occurs once at the start per stream)\n",
ost->st->index, ost->st->id, ost->initialized, ost->inputs_done, ost->finished); ost->st->index, ost->st->id, ost->initialized, ost->inputs_done, ost->finished);
@ -4390,12 +4404,20 @@ static int get_input_packet_mt(InputFile *f, AVPacket **pkt)
static int get_input_packet(InputFile *f, AVPacket **pkt) static int get_input_packet(InputFile *f, AVPacket **pkt)
{ {
if (f->rate_emu) { if (f->readrate || f->rate_emu) {
int i; int i;
int64_t file_start = copy_ts * (
(f->ctx->start_time != AV_NOPTS_VALUE ? f->ctx->start_time * !start_at_zero : 0) +
(f->start_time != AV_NOPTS_VALUE ? f->start_time : 0)
);
float scale = f->rate_emu ? 1.0 : f->readrate;
for (i = 0; i < f->nb_streams; i++) { for (i = 0; i < f->nb_streams; i++) {
InputStream *ist = input_streams[f->ist_index + i]; InputStream *ist = input_streams[f->ist_index + i];
int64_t pts = av_rescale(ist->dts, 1000000, AV_TIME_BASE); int64_t stream_ts_offset, pts, now;
int64_t now = av_gettime_relative() - ist->start; if (!ist->nb_packets || (ist->decoding_needed && !ist->got_output)) continue;
stream_ts_offset = FFMAX(ist->first_dts != AV_NOPTS_VALUE ? ist->first_dts : 0, file_start);
pts = av_rescale(ist->dts, 1000000, AV_TIME_BASE);
now = (av_gettime_relative() - ist->start) * scale + stream_ts_offset;
if (pts > now) if (pts > now)
return AVERROR(EAGAIN); return AVERROR(EAGAIN);
} }
@ -5222,6 +5244,7 @@ int ffmpeg_execute(int argc, char **argv)
{ "report", 0, { .func_arg = opt_report }, "generate a report" }, { "report", 0, { .func_arg = opt_report }, "generate a report" },
{ "max_alloc", HAS_ARG, { .func_arg = opt_max_alloc }, "set maximum size of a single allocated block", "bytes" }, { "max_alloc", HAS_ARG, { .func_arg = opt_max_alloc }, "set maximum size of a single allocated block", "bytes" },
{ "cpuflags", HAS_ARG | OPT_EXPERT, { .func_arg = opt_cpuflags }, "force specific cpu flags", "flags" }, { "cpuflags", HAS_ARG | OPT_EXPERT, { .func_arg = opt_cpuflags }, "force specific cpu flags", "flags" },
{ "cpucount", HAS_ARG | OPT_EXPERT, { .func_arg = opt_cpucount }, "force specific cpu count", "count" },
{ "hide_banner", OPT_BOOL | OPT_EXPERT, {&hide_banner}, "do not show program banner", "hide_banner" }, { "hide_banner", OPT_BOOL | OPT_EXPERT, {&hide_banner}, "do not show program banner", "hide_banner" },
#if CONFIG_AVDEVICE #if CONFIG_AVDEVICE

View File

@ -54,6 +54,7 @@
#include "libavformat/avio.h" #include "libavformat/avio.h"
#include "libavcodec/avcodec.h" #include "libavcodec/avcodec.h"
#include "libavcodec/bsf.h"
#include "libavfilter/avfilter.h" #include "libavfilter/avfilter.h"
@ -83,7 +84,6 @@ enum HWAccelID {
HWACCEL_AUTO, HWACCEL_AUTO,
HWACCEL_GENERIC, HWACCEL_GENERIC,
HWACCEL_VIDEOTOOLBOX, HWACCEL_VIDEOTOOLBOX,
HWACCEL_QSV,
}; };
typedef struct HWAccel { typedef struct HWAccel {
@ -142,6 +142,7 @@ typedef struct OptionsContext {
int64_t input_ts_offset; int64_t input_ts_offset;
int loop; int loop;
int rate_emu; int rate_emu;
float readrate;
int accurate_seek; int accurate_seek;
int thread_queue_size; int thread_queue_size;
@ -339,6 +340,7 @@ typedef struct InputStream {
/* predicted dts of the next packet read for this stream or (when there are /* predicted dts of the next packet read for this stream or (when there are
* several frames in a packet) of the next frame in current packet (in AV_TIME_BASE units) */ * several frames in a packet) of the next frame in current packet (in AV_TIME_BASE units) */
int64_t next_dts; int64_t next_dts;
int64_t first_dts; ///< dts of the first packet read for this stream (in AV_TIME_BASE units)
int64_t dts; ///< dts of the last packet read for this stream (in AV_TIME_BASE units) int64_t dts; ///< dts of the last packet read for this stream (in AV_TIME_BASE units)
int64_t next_pts; ///< synthetic pts for the next decode frame (in AV_TIME_BASE units) int64_t next_pts; ///< synthetic pts for the next decode frame (in AV_TIME_BASE units)
@ -440,6 +442,7 @@ typedef struct InputFile {
from ctx.nb_streams if new streams appear during av_read_frame() */ from ctx.nb_streams if new streams appear during av_read_frame() */
int nb_streams_warn; /* number of streams that the user was warned of */ int nb_streams_warn; /* number of streams that the user was warned of */
int rate_emu; int rate_emu;
float readrate;
int accurate_seek; int accurate_seek;
AVPacket *pkt; AVPacket *pkt;
@ -526,6 +529,7 @@ typedef struct OutputStream {
char *forced_keyframes; char *forced_keyframes;
AVExpr *forced_keyframes_pexpr; AVExpr *forced_keyframes_pexpr;
double forced_keyframes_expr_const_values[FKF_NB]; double forced_keyframes_expr_const_values[FKF_NB];
int dropped_keyframe;
/* audio only */ /* audio only */
int *audio_channels_map; /* list of the channels id to pick from the source stream */ int *audio_channels_map; /* list of the channels id to pick from the source stream */

View File

@ -636,7 +636,7 @@ int configure_output_filter(FilterGraph *fg, OutputFilter *ofilter, AVFilterInOu
switch (avfilter_pad_get_type(out->filter_ctx->output_pads, out->pad_idx)) { switch (avfilter_pad_get_type(out->filter_ctx->output_pads, out->pad_idx)) {
case AVMEDIA_TYPE_VIDEO: return configure_output_video_filter(fg, ofilter, out); case AVMEDIA_TYPE_VIDEO: return configure_output_video_filter(fg, ofilter, out);
case AVMEDIA_TYPE_AUDIO: return configure_output_audio_filter(fg, ofilter, out); case AVMEDIA_TYPE_AUDIO: return configure_output_audio_filter(fg, ofilter, out);
default: av_assert0(0); default: av_assert0(0); return 0;
} }
} }
@ -946,7 +946,7 @@ static int configure_input_filter(FilterGraph *fg, InputFilter *ifilter,
switch (avfilter_pad_get_type(in->filter_ctx->input_pads, in->pad_idx)) { switch (avfilter_pad_get_type(in->filter_ctx->input_pads, in->pad_idx)) {
case AVMEDIA_TYPE_VIDEO: return configure_input_video_filter(fg, ifilter, in); case AVMEDIA_TYPE_VIDEO: return configure_input_video_filter(fg, ifilter, in);
case AVMEDIA_TYPE_AUDIO: return configure_input_audio_filter(fg, ifilter, in); case AVMEDIA_TYPE_AUDIO: return configure_input_audio_filter(fg, ifilter, in);
default: av_assert0(0); default: av_assert0(0); return 0;
} }
} }
@ -985,7 +985,11 @@ int configure_filtergraph(FilterGraph *fg)
} }
if (strlen(args)) if (strlen(args))
args[strlen(args)-1] = 0; args[strlen(args)-1] = 0;
fg->graph->scale_sws_opts = av_strdup(args);
if (!strncmp(args, "sws_flags=", 10)) {
// keep the 'flags=' part
fg->graph->scale_sws_opts = av_strdup(args+4);
}
args[0] = 0; args[0] = 0;
while ((e = av_dict_get(ost->swr_opts, "", e, while ((e = av_dict_get(ost->swr_opts, "", e,

View File

@ -348,6 +348,18 @@ int hw_device_setup_for_decode(InputStream *ist)
} else if (ist->hwaccel_id == HWACCEL_GENERIC) { } else if (ist->hwaccel_id == HWACCEL_GENERIC) {
type = ist->hwaccel_device_type; type = ist->hwaccel_device_type;
dev = hw_device_get_by_type(type); dev = hw_device_get_by_type(type);
// When "-qsv_device device" is used, an internal QSV device named
// as "__qsv_device" is created. Another QSV device is created too
// if "-init_hw_device qsv=name:device" is used. There are 2 QSV devices
// if both "-qsv_device device" and "-init_hw_device qsv=name:device"
// are used, hw_device_get_by_type(AV_HWDEVICE_TYPE_QSV) returns NULL.
// To keep back-compatibility with the removed ad-hoc libmfx setup code,
// call hw_device_get_by_name("__qsv_device") to select the internal QSV
// device.
if (!dev && type == AV_HWDEVICE_TYPE_QSV)
dev = hw_device_get_by_name("__qsv_device");
if (!dev) if (!dev)
err = hw_device_init_from_type(type, NULL, &dev); err = hw_device_init_from_type(type, NULL, &dev);
} else { } else {

View File

@ -42,6 +42,7 @@
#include "libavformat/avformat.h" #include "libavformat/avformat.h"
#include "libavcodec/avcodec.h" #include "libavcodec/avcodec.h"
#include "libavcodec/bsf.h"
#include "libavfilter/avfilter.h" #include "libavfilter/avfilter.h"
@ -151,9 +152,6 @@ static const char *const opt_name_enc_time_bases[] = {"enc_time_base"
const HWAccel hwaccels[] = { const HWAccel hwaccels[] = {
#if CONFIG_VIDEOTOOLBOX #if CONFIG_VIDEOTOOLBOX
{ "videotoolbox", videotoolbox_init, HWACCEL_VIDEOTOOLBOX, AV_PIX_FMT_VIDEOTOOLBOX }, { "videotoolbox", videotoolbox_init, HWACCEL_VIDEOTOOLBOX, AV_PIX_FMT_VIDEOTOOLBOX },
#endif
#if CONFIG_LIBMFX
{ "qsv", qsv_init, HWACCEL_QSV, AV_PIX_FMT_QSV },
#endif #endif
{ 0 }, { 0 },
}; };
@ -201,6 +199,7 @@ __thread int input_sync;
__thread int input_stream_potentially_available = 0; __thread int input_stream_potentially_available = 0;
__thread int ignore_unknown_streams = 0; __thread int ignore_unknown_streams = 0;
__thread int copy_unknown_streams = 0; __thread int copy_unknown_streams = 0;
__thread static int recast_media = 0;
__thread int find_stream_info = 1; __thread int find_stream_info = 1;
extern __thread OptionDef *ffmpeg_options; extern __thread OptionDef *ffmpeg_options;
@ -586,6 +585,23 @@ int opt_vaapi_device(void *optctx, const char *opt, const char *arg)
} }
#endif #endif
#if CONFIG_QSV
static int opt_qsv_device(void *optctx, const char *opt, const char *arg)
{
const char *prefix = "qsv=__qsv_device:hw_any,child_device=";
int err;
char *tmp = av_asprintf("%s%s", prefix, arg);
if (!tmp)
return AVERROR(ENOMEM);
err = hw_device_init_from_string(tmp, NULL);
av_free(tmp);
return err;
}
#endif
int opt_init_hw_device(void *optctx, const char *opt, const char *arg) int opt_init_hw_device(void *optctx, const char *opt, const char *arg)
{ {
if (!strcmp(arg, "list")) { if (!strcmp(arg, "list")) {
@ -776,7 +792,7 @@ const AVCodec *find_codec_or_die(const char *name, enum AVMediaType type, int en
av_log(NULL, AV_LOG_FATAL, "Unknown %s '%s'\n", codec_string, name); av_log(NULL, AV_LOG_FATAL, "Unknown %s '%s'\n", codec_string, name);
exit_program(1); exit_program(1);
} }
if (codec->type != type) { if (codec->type != type && !recast_media) {
av_log(NULL, AV_LOG_FATAL, "Invalid %s type '%s'\n", codec_string, name); av_log(NULL, AV_LOG_FATAL, "Invalid %s type '%s'\n", codec_string, name);
exit_program(1); exit_program(1);
} }
@ -791,6 +807,8 @@ const AVCodec *choose_decoder(OptionsContext *o, AVFormatContext *s, AVStream *s
if (codec_name) { if (codec_name) {
const AVCodec *codec = find_codec_or_die(codec_name, st->codecpar->codec_type, 0); const AVCodec *codec = find_codec_or_die(codec_name, st->codecpar->codec_type, 0);
st->codecpar->codec_id = codec->id; st->codecpar->codec_id = codec->id;
if (recast_media && st->codecpar->codec_type != codec->type)
st->codecpar->codec_type = codec->type;
return codec; return codec;
} else } else
return avcodec_find_decoder(st->codecpar->codec_id); return avcodec_find_decoder(st->codecpar->codec_id);
@ -826,6 +844,7 @@ void add_input_streams(OptionsContext *o, AVFormatContext *ic)
ist->discard = 1; ist->discard = 1;
st->discard = AVDISCARD_ALL; st->discard = AVDISCARD_ALL;
ist->nb_samples = 0; ist->nb_samples = 0;
ist->first_dts = AV_NOPTS_VALUE;
ist->min_pts = INT64_MAX; ist->min_pts = INT64_MAX;
ist->max_pts = INT64_MIN; ist->max_pts = INT64_MIN;
@ -910,6 +929,12 @@ void add_input_streams(OptionsContext *o, AVFormatContext *ic)
"with old commandlines. This behaviour is DEPRECATED and will be removed " "with old commandlines. This behaviour is DEPRECATED and will be removed "
"in the future. Please explicitly set \"-hwaccel_output_format cuda\".\n"); "in the future. Please explicitly set \"-hwaccel_output_format cuda\".\n");
ist->hwaccel_output_format = AV_PIX_FMT_CUDA; ist->hwaccel_output_format = AV_PIX_FMT_CUDA;
} else if (!hwaccel_output_format && hwaccel && !strcmp(hwaccel, "qsv")) {
av_log(NULL, AV_LOG_WARNING,
"WARNING: defaulting hwaccel_output_format to qsv for compatibility "
"with old commandlines. This behaviour is DEPRECATED and will be removed "
"in the future. Please explicitly set \"-hwaccel_output_format qsv\".\n");
ist->hwaccel_output_format = AV_PIX_FMT_QSV;
} else if (hwaccel_output_format) { } else if (hwaccel_output_format) {
ist->hwaccel_output_format = av_get_pix_fmt(hwaccel_output_format); ist->hwaccel_output_format = av_get_pix_fmt(hwaccel_output_format);
if (ist->hwaccel_output_format == AV_PIX_FMT_NONE) { if (ist->hwaccel_output_format == AV_PIX_FMT_NONE) {
@ -1299,6 +1324,17 @@ int open_input_file(OptionsContext *o, const char *filename)
f->loop = o->loop; f->loop = o->loop;
f->duration = 0; f->duration = 0;
f->time_base = (AVRational){ 1, 1 }; f->time_base = (AVRational){ 1, 1 };
f->readrate = o->readrate ? o->readrate : 0.0;
if (f->readrate < 0.0f) {
av_log(NULL, AV_LOG_ERROR, "Option -readrate for Input #%d is %0.3f; it must be non-negative.\n", nb_input_files, f->readrate);
exit_program(1);
}
if (f->readrate && f->rate_emu) {
av_log(NULL, AV_LOG_WARNING, "Both -readrate and -re set for Input #%d. Using -readrate %0.3f.\n", nb_input_files, f->readrate);
f->rate_emu = 0;
}
f->pkt = av_packet_alloc(); f->pkt = av_packet_alloc();
if (!f->pkt) if (!f->pkt)
exit_program(1); exit_program(1);
@ -2261,9 +2297,12 @@ int open_output_file(OptionsContext *o, const char *filename)
if (!o->video_disable && av_guess_codec(oc->oformat, NULL, filename, NULL, AVMEDIA_TYPE_VIDEO) != AV_CODEC_ID_NONE) { if (!o->video_disable && av_guess_codec(oc->oformat, NULL, filename, NULL, AVMEDIA_TYPE_VIDEO) != AV_CODEC_ID_NONE) {
int best_score = 0, idx = -1; int best_score = 0, idx = -1;
int qcr = avformat_query_codec(oc->oformat, oc->oformat->video_codec, 0); int qcr = avformat_query_codec(oc->oformat, oc->oformat->video_codec, 0);
for (i = 0; i < nb_input_streams; i++) { for (j = 0; j < nb_input_files; j++) {
InputFile *ifile = input_files[j];
int file_best_score = 0, file_best_idx = -1;
for (i = 0; i < ifile->nb_streams; i++) {
int score; int score;
ist = input_streams[i]; ist = input_streams[ifile->ist_index + i];
score = ist->st->codecpar->width * ist->st->codecpar->height score = ist->st->codecpar->width * ist->st->codecpar->height
+ 100000000 * !!(ist->st->event_flags & AVSTREAM_EVENT_FLAG_NEW_PACKETS) + 100000000 * !!(ist->st->event_flags & AVSTREAM_EVENT_FLAG_NEW_PACKETS)
+ 5000000*!!(ist->st->disposition & AV_DISPOSITION_DEFAULT); + 5000000*!!(ist->st->disposition & AV_DISPOSITION_DEFAULT);
@ -2272,11 +2311,20 @@ int open_output_file(OptionsContext *o, const char *filename)
if((qcr!=MKTAG('A', 'P', 'I', 'C')) && (ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC)) if((qcr!=MKTAG('A', 'P', 'I', 'C')) && (ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC))
score = 1; score = 1;
if (ist->st->codecpar->codec_type == AVMEDIA_TYPE_VIDEO && if (ist->st->codecpar->codec_type == AVMEDIA_TYPE_VIDEO &&
score > best_score) { score > file_best_score) {
if((qcr==MKTAG('A', 'P', 'I', 'C')) && !(ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC)) if((qcr==MKTAG('A', 'P', 'I', 'C')) && !(ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC))
continue; continue;
best_score = score; file_best_score = score;
idx = i; file_best_idx = ifile->ist_index + i;
}
}
if (file_best_idx >= 0) {
if((qcr == MKTAG('A', 'P', 'I', 'C')) || !(ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC))
file_best_score -= 5000000*!!(input_streams[file_best_idx]->st->disposition & AV_DISPOSITION_DEFAULT);
if (file_best_score > best_score) {
best_score = file_best_score;
idx = file_best_idx;
}
} }
} }
if (idx >= 0) if (idx >= 0)
@ -2286,18 +2334,29 @@ int open_output_file(OptionsContext *o, const char *filename)
/* audio: most channels */ /* audio: most channels */
if (!o->audio_disable && av_guess_codec(oc->oformat, NULL, filename, NULL, AVMEDIA_TYPE_AUDIO) != AV_CODEC_ID_NONE) { if (!o->audio_disable && av_guess_codec(oc->oformat, NULL, filename, NULL, AVMEDIA_TYPE_AUDIO) != AV_CODEC_ID_NONE) {
int best_score = 0, idx = -1; int best_score = 0, idx = -1;
for (i = 0; i < nb_input_streams; i++) { for (j = 0; j < nb_input_files; j++) {
InputFile *ifile = input_files[j];
int file_best_score = 0, file_best_idx = -1;
for (i = 0; i < ifile->nb_streams; i++) {
int score; int score;
ist = input_streams[i]; ist = input_streams[ifile->ist_index + i];
score = ist->st->codecpar->channels score = ist->st->codecpar->channels
+ 100000000 * !!(ist->st->event_flags & AVSTREAM_EVENT_FLAG_NEW_PACKETS) + 100000000 * !!(ist->st->event_flags & AVSTREAM_EVENT_FLAG_NEW_PACKETS)
+ 5000000*!!(ist->st->disposition & AV_DISPOSITION_DEFAULT); + 5000000*!!(ist->st->disposition & AV_DISPOSITION_DEFAULT);
if (ist->user_set_discard == AVDISCARD_ALL) if (ist->user_set_discard == AVDISCARD_ALL)
continue; continue;
if (ist->st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO && if (ist->st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO &&
score > best_score) { score > file_best_score) {
best_score = score; file_best_score = score;
idx = i; file_best_idx = ifile->ist_index + i;
}
}
if (file_best_idx >= 0) {
file_best_score -= 5000000*!!(input_streams[file_best_idx]->st->disposition & AV_DISPOSITION_DEFAULT);
if (file_best_score > best_score) {
best_score = file_best_score;
idx = file_best_idx;
}
} }
} }
if (idx >= 0) if (idx >= 0)

View File

@ -29,6 +29,7 @@
typedef struct VTContext { typedef struct VTContext {
AVFrame *tmp_frame; AVFrame *tmp_frame;
int log_once;
} VTContext; } VTContext;
__thread char *videotoolbox_pixfmt; __thread char *videotoolbox_pixfmt;
@ -44,6 +45,13 @@ static int videotoolbox_retrieve_data(AVCodecContext *s, AVFrame *frame)
int linesize[4] = { 0 }; int linesize[4] = { 0 };
int planes, ret, i; int planes, ret, i;
if (frame->format == ist->hwaccel_output_format) {
av_log_once(s, AV_LOG_INFO, AV_LOG_TRACE, &vt->log_once,
"There is no video filter for videotoolbox pix_fmt now, remove the "
"-hwaccel_output_format option if video filter doesn't work\n");
return 0;
}
av_frame_unref(vt->tmp_frame); av_frame_unref(vt->tmp_frame);
switch (pixel_format) { switch (pixel_format) {

View File

@ -8,7 +8,7 @@ get_library_source() {
case $1 in case $1 in
config) config)
SOURCE_REPO_URL="https://github.com/tanersener/gnu-config" SOURCE_REPO_URL="https://github.com/tanersener/gnu-config"
SOURCE_ID="v20201222" SOURCE_ID="v20210814"
SOURCE_TYPE="TAG" SOURCE_TYPE="TAG"
;; ;;
chromaprint) chromaprint)
@ -33,9 +33,9 @@ get_library_source() {
;; ;;
ffmpeg) ffmpeg)
SOURCE_REPO_URL="https://github.com/tanersener/FFmpeg" SOURCE_REPO_URL="https://github.com/tanersener/FFmpeg"
SOURCE_ID="c9a79532e5ec4ea265d3a82f185fca6e196088c2" SOURCE_ID="acd3c101ef4b84aac9c608bfe6ab22431529c48f"
SOURCE_TYPE="COMMIT" SOURCE_TYPE="COMMIT"
SOURCE_GIT_DESCRIBE="n4.5-dev-899-gc9a79532e5" # git describe --tags SOURCE_GIT_DESCRIBE="n4.5-dev-1598-gacd3c101ef" # git describe --tags
;; ;;
fontconfig) fontconfig)
SOURCE_REPO_URL="https://github.com/tanersener/fontconfig" SOURCE_REPO_URL="https://github.com/tanersener/fontconfig"