* [FFmpeg-devel] [PATCH 02/31] fftools/ffmpeg_dec: export subtitle_header in Decoder
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 03/31] fftools/ffmpeg_filter: consolidate decoder/filter type checks Anton Khirnov
` (28 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
This way the encoder does not need to access the decoder AVCodecContext,
which will allow to make it private in future commits.
---
fftools/ffmpeg.h | 3 ++-
fftools/ffmpeg_dec.c | 3 +++
fftools/ffmpeg_enc.c | 19 ++++++++++---------
3 files changed, 15 insertions(+), 10 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index 429c1aba85..4c9424d02f 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -281,7 +281,8 @@ typedef struct FilterGraph {
} FilterGraph;
typedef struct Decoder {
- char dummy;
+ const uint8_t *subtitle_header;
+ int subtitle_header_size;
} Decoder;
typedef struct InputStream {
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index fd697c5f1e..cb967d5930 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -969,5 +969,8 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
if (ret < 0)
return ret;
+ dp->dec.subtitle_header = ist->dec_ctx->subtitle_header;
+ dp->dec.subtitle_header_size = ist->dec_ctx->subtitle_header_size;
+
return 0;
}
diff --git a/fftools/ffmpeg_enc.c b/fftools/ffmpeg_enc.c
index 2a7fba0c51..bbd86a6fe1 100644
--- a/fftools/ffmpeg_enc.c
+++ b/fftools/ffmpeg_enc.c
@@ -171,7 +171,7 @@ int enc_open(void *opaque, const AVFrame *frame)
InputStream *ist = ost->ist;
Encoder *e = ost->enc;
AVCodecContext *enc_ctx = ost->enc_ctx;
- AVCodecContext *dec_ctx = NULL;
+ Decoder *dec;
const AVCodec *enc = enc_ctx->codec;
OutputFile *of = ost->file;
FrameData *fd;
@@ -193,9 +193,8 @@ int enc_open(void *opaque, const AVFrame *frame)
if (ret < 0)
return ret;
- if (ist) {
- dec_ctx = ist->dec_ctx;
- }
+ if (ist)
+ dec = ist->decoder;
// the timebase is chosen by filtering code
if (ost->type == AVMEDIA_TYPE_AUDIO || ost->type == AVMEDIA_TYPE_VIDEO) {
@@ -279,14 +278,16 @@ int enc_open(void *opaque, const AVFrame *frame)
enc_ctx->width = ost->ist->par->width;
enc_ctx->height = ost->ist->par->height;
}
- if (dec_ctx && dec_ctx->subtitle_header) {
+
+ av_assert0(dec);
+ if (dec->subtitle_header) {
/* ASS code assumes this buffer is null terminated so add extra byte. */
- enc_ctx->subtitle_header = av_mallocz(dec_ctx->subtitle_header_size + 1);
+ enc_ctx->subtitle_header = av_mallocz(dec->subtitle_header_size + 1);
if (!enc_ctx->subtitle_header)
return AVERROR(ENOMEM);
- memcpy(enc_ctx->subtitle_header, dec_ctx->subtitle_header,
- dec_ctx->subtitle_header_size);
- enc_ctx->subtitle_header_size = dec_ctx->subtitle_header_size;
+ memcpy(enc_ctx->subtitle_header, dec->subtitle_header,
+ dec->subtitle_header_size);
+ enc_ctx->subtitle_header_size = dec->subtitle_header_size;
}
break;
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 03/31] fftools/ffmpeg_filter: consolidate decoder/filter type checks
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 02/31] fftools/ffmpeg_dec: export subtitle_header in Decoder Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 04/31] fftools/ffmpeg: make decoding AVCodecContext private to the decoder Anton Khirnov
` (27 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Also perform them earlier.
---
fftools/ffmpeg_filter.c | 18 +++++++-----------
1 file changed, 7 insertions(+), 11 deletions(-)
diff --git a/fftools/ffmpeg_filter.c b/fftools/ffmpeg_filter.c
index 82ee4fae7d..4b660002ed 100644
--- a/fftools/ffmpeg_filter.c
+++ b/fftools/ffmpeg_filter.c
@@ -663,6 +663,13 @@ static int ifilter_bind_ist(InputFilter *ifilter, InputStream *ist)
av_assert0(!ifp->ist);
+ if (ifp->type != ist->par->codec_type &&
+ !(ifp->type == AVMEDIA_TYPE_VIDEO && ist->par->codec_type == AVMEDIA_TYPE_SUBTITLE)) {
+ av_log(fgp, AV_LOG_ERROR, "Tried to connect %s stream to %s filtergraph input\n",
+ av_get_media_type_string(ist->par->codec_type), av_get_media_type_string(ifp->type));
+ return AVERROR(EINVAL);
+ }
+
ifp->ist = ist;
ifp->type_src = ist->st->codecpar->codec_type;
@@ -1476,12 +1483,6 @@ static int configure_input_video_filter(FilterGraph *fg, AVFilterGraph *graph,
if (!par)
return AVERROR(ENOMEM);
- if (ist->dec_ctx->codec_type == AVMEDIA_TYPE_AUDIO) {
- av_log(fg, AV_LOG_ERROR, "Cannot connect video filter to audio input\n");
- ret = AVERROR(EINVAL);
- goto fail;
- }
-
if (!fr.num)
fr = ist->framerate_guessed;
@@ -1598,11 +1599,6 @@ static int configure_input_audio_filter(FilterGraph *fg, AVFilterGraph *graph,
int ret, pad_idx = 0;
int64_t tsoffset = 0;
- if (ist->dec_ctx->codec_type != AVMEDIA_TYPE_AUDIO) {
- av_log(fg, AV_LOG_ERROR, "Cannot connect audio filter to non audio input\n");
- return AVERROR(EINVAL);
- }
-
ifp->time_base = (AVRational){ 1, ifp->sample_rate };
av_bprint_init(&args, 0, AV_BPRINT_SIZE_AUTOMATIC);
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 04/31] fftools/ffmpeg: make decoding AVCodecContext private to the decoder
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 02/31] fftools/ffmpeg_dec: export subtitle_header in Decoder Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 03/31] fftools/ffmpeg_filter: consolidate decoder/filter type checks Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 05/31] fftools/ffmpeg_dec: add an AVClass to Decoder Anton Khirnov
` (26 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
---
fftools/ffmpeg.h | 3 +-
fftools/ffmpeg_dec.c | 90 ++++++++++++++++++++++++++----------------
fftools/ffmpeg_demux.c | 16 +-------
3 files changed, 60 insertions(+), 49 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index 4c9424d02f..f0f57d48bc 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -306,7 +306,6 @@ typedef struct InputStream {
*/
AVCodecParameters *par;
Decoder *decoder;
- AVCodecContext *dec_ctx;
const AVCodec *dec;
AVRational framerate_guessed;
@@ -733,6 +732,8 @@ int hwaccel_retrieve_data(AVCodecContext *avctx, AVFrame *input);
int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx);
void dec_free(Decoder **pdec);
+int dec_add_filter(Decoder *dec, InputFilter *ifilter);
+
int enc_alloc(Encoder **penc, const AVCodec *codec,
Scheduler *sch, unsigned sch_idx);
void enc_free(Encoder **penc);
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index cb967d5930..230da4fa7f 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -37,6 +37,8 @@
typedef struct DecoderPriv {
Decoder dec;
+ AVCodecContext *dec_ctx;
+
AVFrame *frame;
AVPacket *pkt;
@@ -79,6 +81,8 @@ void dec_free(Decoder **pdec)
return;
dp = dp_from_dec(dec);
+ avcodec_free_context(&dp->dec_ctx);
+
av_frame_free(&dp->frame);
av_packet_free(&dp->pkt);
@@ -216,9 +220,9 @@ static int64_t video_duration_estimate(const InputStream *ist, const AVFrame *fr
if (frame->duration > 0 && (!ifile->format_nots || ist->framerate.num))
return frame->duration;
- if (ist->dec_ctx->framerate.den && ist->dec_ctx->framerate.num) {
+ if (dp->dec_ctx->framerate.den && dp->dec_ctx->framerate.num) {
int fields = frame->repeat_pict + 2;
- AVRational field_rate = av_mul_q(ist->dec_ctx->framerate,
+ AVRational field_rate = av_mul_q(dp->dec_ctx->framerate,
(AVRational){ 2, 1 });
codec_duration = av_rescale_q(fields, av_inv_q(field_rate),
frame->time_base);
@@ -258,29 +262,29 @@ static int video_frame_process(InputStream *ist, AVFrame *frame)
// The following line may be required in some cases where there is no parser
// or the parser does not has_b_frames correctly
- if (ist->par->video_delay < ist->dec_ctx->has_b_frames) {
- if (ist->dec_ctx->codec_id == AV_CODEC_ID_H264) {
- ist->par->video_delay = ist->dec_ctx->has_b_frames;
+ if (ist->par->video_delay < dp->dec_ctx->has_b_frames) {
+ if (dp->dec_ctx->codec_id == AV_CODEC_ID_H264) {
+ ist->par->video_delay = dp->dec_ctx->has_b_frames;
} else
- av_log(ist->dec_ctx, AV_LOG_WARNING,
+ av_log(dp->dec_ctx, AV_LOG_WARNING,
"video_delay is larger in decoder than demuxer %d > %d.\n"
"If you want to help, upload a sample "
"of this file to https://streams.videolan.org/upload/ "
"and contact the ffmpeg-devel mailing list. (ffmpeg-devel@ffmpeg.org)\n",
- ist->dec_ctx->has_b_frames,
+ dp->dec_ctx->has_b_frames,
ist->par->video_delay);
}
- if (ist->dec_ctx->width != frame->width ||
- ist->dec_ctx->height != frame->height ||
- ist->dec_ctx->pix_fmt != frame->format) {
+ if (dp->dec_ctx->width != frame->width ||
+ dp->dec_ctx->height != frame->height ||
+ dp->dec_ctx->pix_fmt != frame->format) {
av_log(NULL, AV_LOG_DEBUG, "Frame parameters mismatch context %d,%d,%d != %d,%d,%d\n",
frame->width,
frame->height,
frame->format,
- ist->dec_ctx->width,
- ist->dec_ctx->height,
- ist->dec_ctx->pix_fmt);
+ dp->dec_ctx->width,
+ dp->dec_ctx->height,
+ dp->dec_ctx->pix_fmt);
}
#if FFMPEG_OPT_TOP
@@ -291,7 +295,7 @@ static int video_frame_process(InputStream *ist, AVFrame *frame)
#endif
if (frame->format == dp->hwaccel_pix_fmt) {
- int err = hwaccel_retrieve_data(ist->dec_ctx, frame);
+ int err = hwaccel_retrieve_data(dp->dec_ctx, frame);
if (err < 0)
return err;
}
@@ -431,7 +435,7 @@ static int transcode_subtitles(InputStream *ist, const AVPacket *pkt,
return AVERROR(ENOMEM);
}
- ret = avcodec_decode_subtitle2(ist->dec_ctx, &subtitle, &got_output,
+ ret = avcodec_decode_subtitle2(dp->dec_ctx, &subtitle, &got_output,
pkt ? pkt : flush_pkt);
av_packet_free(&flush_pkt);
@@ -457,8 +461,8 @@ static int transcode_subtitles(InputStream *ist, const AVPacket *pkt,
return ret;
}
- frame->width = ist->dec_ctx->width;
- frame->height = ist->dec_ctx->height;
+ frame->width = dp->dec_ctx->width;
+ frame->height = dp->dec_ctx->height;
return process_subtitle(ist, frame);
}
@@ -467,7 +471,7 @@ static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
{
const InputFile *ifile = ist->file;
DecoderPriv *dp = dp_from_dec(ist->decoder);
- AVCodecContext *dec = ist->dec_ctx;
+ AVCodecContext *dec = dp->dec_ctx;
const char *type_desc = av_get_media_type_string(dec->codec_type);
int ret;
@@ -582,11 +586,11 @@ static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
}
}
-static void dec_thread_set_name(const InputStream *ist)
+static void dec_thread_set_name(const InputStream *ist, const DecoderPriv *dp)
{
char name[16];
snprintf(name, sizeof(name), "dec%d:%d:%s", ist->file->index, ist->index,
- ist->dec_ctx->codec->name);
+ dp->dec_ctx->codec->name);
ff_thread_setname(name);
}
@@ -628,7 +632,7 @@ void *decoder_thread(void *arg)
if (ret < 0)
goto finish;
- dec_thread_set_name(ist);
+ dec_thread_set_name(ist, dp);
while (!input_status) {
int flush_buffers, have_data;
@@ -669,7 +673,7 @@ void *decoder_thread(void *arg)
dt.pkt->time_base = dp->last_frame_tb;
}
- avcodec_flush_buffers(ist->dec_ctx);
+ avcodec_flush_buffers(dp->dec_ctx);
} else if (ret < 0) {
av_log(ist, AV_LOG_ERROR, "Error processing packet in decoder: %s\n",
av_err2str(ret));
@@ -769,7 +773,7 @@ static HWDevice *hw_device_match_by_codec(const AVCodec *codec)
}
}
-static int hw_device_setup_for_decode(InputStream *ist)
+static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp)
{
const AVCodecHWConfig *config;
enum AVHWDeviceType type;
@@ -890,8 +894,8 @@ static int hw_device_setup_for_decode(InputStream *ist)
return err;
}
- ist->dec_ctx->hw_device_ctx = av_buffer_ref(dev->device_ref);
- if (!ist->dec_ctx->hw_device_ctx)
+ dp->dec_ctx->hw_device_ctx = av_buffer_ref(dev->device_ref);
+ if (!dp->dec_ctx->hw_device_ctx)
return AVERROR(ENOMEM);
return 0;
@@ -906,7 +910,7 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
if (!codec) {
av_log(ist, AV_LOG_ERROR,
"Decoding requested, but no decoder found for: %s\n",
- avcodec_get_name(ist->dec_ctx->codec_id));
+ avcodec_get_name(ist->par->codec_id));
return AVERROR(EINVAL);
}
@@ -929,10 +933,20 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
return AVERROR(ENOMEM);
}
- ist->dec_ctx->opaque = ist;
- ist->dec_ctx->get_format = get_format;
+ dp->dec_ctx = avcodec_alloc_context3(codec);
+ if (!dp->dec_ctx)
+ return AVERROR(ENOMEM);
- if (ist->dec_ctx->codec_id == AV_CODEC_ID_DVB_SUBTITLE &&
+ ret = avcodec_parameters_to_context(dp->dec_ctx, ist->par);
+ if (ret < 0) {
+ av_log(ist, AV_LOG_ERROR, "Error initializing the decoder context.\n");
+ return ret;
+ }
+
+ dp->dec_ctx->opaque = ist;
+ dp->dec_ctx->get_format = get_format;
+
+ if (dp->dec_ctx->codec_id == AV_CODEC_ID_DVB_SUBTITLE &&
(ist->decoding_needed & DECODING_FOR_OST)) {
av_dict_set(&ist->decoder_opts, "compute_edt", "1", AV_DICT_DONT_OVERWRITE);
if (ist->decoding_needed & DECODING_FOR_FILTER)
@@ -941,7 +955,7 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
/* Useful for subtitles retiming by lavf (FIXME), skipping samples in
* audio, and video decoders such as cuvid or mediacodec */
- ist->dec_ctx->pkt_timebase = ist->st->time_base;
+ dp->dec_ctx->pkt_timebase = ist->st->time_base;
if (!av_dict_get(ist->decoder_opts, "threads", NULL, 0))
av_dict_set(&ist->decoder_opts, "threads", "auto", 0);
@@ -951,7 +965,7 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
av_dict_set(&ist->decoder_opts, "flags", "+copy_opaque", AV_DICT_MULTIKEY);
- ret = hw_device_setup_for_decode(ist);
+ ret = hw_device_setup_for_decode(ist, dp);
if (ret < 0) {
av_log(ist, AV_LOG_ERROR,
"Hardware device setup failed for decoder: %s\n",
@@ -959,7 +973,7 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
return ret;
}
- if ((ret = avcodec_open2(ist->dec_ctx, codec, &ist->decoder_opts)) < 0) {
+ if ((ret = avcodec_open2(dp->dec_ctx, codec, &ist->decoder_opts)) < 0) {
av_log(ist, AV_LOG_ERROR, "Error while opening decoder: %s\n",
av_err2str(ret));
return ret;
@@ -969,8 +983,16 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
if (ret < 0)
return ret;
- dp->dec.subtitle_header = ist->dec_ctx->subtitle_header;
- dp->dec.subtitle_header_size = ist->dec_ctx->subtitle_header_size;
+ dp->dec.subtitle_header = dp->dec_ctx->subtitle_header;
+ dp->dec.subtitle_header_size = dp->dec_ctx->subtitle_header_size;
return 0;
}
+
+int dec_add_filter(Decoder *dec, InputFilter *ifilter)
+{
+ DecoderPriv *dp = dp_from_dec(dec);
+
+ // initialize fallback parameters for filtering
+ return ifilter_parameters_from_dec(ifilter, dp->dec_ctx);
+}
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 16d4f67e59..8e904d2150 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -825,7 +825,6 @@ static void ist_free(InputStream **pist)
av_freep(&ist->outputs);
av_freep(&ist->hwaccel_device);
- avcodec_free_context(&ist->dec_ctx);
avcodec_parameters_free(&ist->par);
av_bsf_free(&ds->bsf);
@@ -886,16 +885,6 @@ static int ist_use(InputStream *ist, int decoding_needed)
if (decoding_needed && ds->sch_idx_dec < 0) {
int is_audio = ist->st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO;
- ist->dec_ctx = avcodec_alloc_context3(ist->dec);
- if (!ist->dec_ctx)
- return AVERROR(ENOMEM);
-
- ret = avcodec_parameters_to_context(ist->dec_ctx, ist->par);
- if (ret < 0) {
- av_log(ist, AV_LOG_ERROR, "Error initializing the decoder context.\n");
- return ret;
- }
-
ret = sch_add_dec(d->sch, decoder_thread, ist, d->loop && is_audio);
if (ret < 0)
return ret;
@@ -950,12 +939,11 @@ int ist_filter_add(InputStream *ist, InputFilter *ifilter, int is_simple)
ist->filters[ist->nb_filters - 1] = ifilter;
- // initialize fallback parameters for filtering
- ret = ifilter_parameters_from_dec(ifilter, ist->dec_ctx);
+ ret = dec_add_filter(ist->decoder, ifilter);
if (ret < 0)
return ret;
- if (ist->dec_ctx->codec_type == AVMEDIA_TYPE_SUBTITLE) {
+ if (ist->par->codec_type == AVMEDIA_TYPE_SUBTITLE) {
if (!d->pkt_heartbeat) {
d->pkt_heartbeat = av_packet_alloc();
if (!d->pkt_heartbeat)
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 05/31] fftools/ffmpeg_dec: add an AVClass to Decoder
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (2 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 04/31] fftools/ffmpeg: make decoding AVCodecContext private to the decoder Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 06/31] fftools/ffmpeg_dec: pass decoder options as an argument to dec_open() Anton Khirnov
` (25 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Log decoder messages to the decoder rather than InputStream.
This is a step towards decoupling Decoder and InputStream.
---
fftools/ffmpeg.h | 2 +
fftools/ffmpeg_dec.c | 92 ++++++++++++++++++++++++++++----------------
2 files changed, 60 insertions(+), 34 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index f0f57d48bc..9e29ae1785 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -281,6 +281,8 @@ typedef struct FilterGraph {
} FilterGraph;
typedef struct Decoder {
+ const AVClass *class;
+
const uint8_t *subtitle_header;
int subtitle_header_size;
} Decoder;
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index 230da4fa7f..6dca730e51 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -59,6 +59,9 @@ typedef struct DecoderPriv {
Scheduler *sch;
unsigned sch_idx;
+
+ void *log_parent;
+ char log_name[32];
} DecoderPriv;
static DecoderPriv *dp_from_dec(Decoder *d)
@@ -124,7 +127,7 @@ fail:
return AVERROR(ENOMEM);
}
-static AVRational audio_samplerate_update(void *logctx, DecoderPriv *dp,
+static AVRational audio_samplerate_update(DecoderPriv *dp,
const AVFrame *frame)
{
const int prev = dp->last_frame_tb.den;
@@ -139,7 +142,7 @@ static AVRational audio_samplerate_update(void *logctx, DecoderPriv *dp,
gcd = av_gcd(prev, sr);
if (prev / gcd >= INT_MAX / sr) {
- av_log(logctx, AV_LOG_WARNING,
+ av_log(dp, AV_LOG_WARNING,
"Audio timestamps cannot be represented exactly after "
"sample rate change: %d -> %d\n", prev, sr);
@@ -167,7 +170,7 @@ finish:
return dp->last_frame_tb;
}
-static void audio_ts_process(void *logctx, DecoderPriv *dp, AVFrame *frame)
+static void audio_ts_process(DecoderPriv *dp, AVFrame *frame)
{
AVRational tb_filter = (AVRational){1, frame->sample_rate};
AVRational tb;
@@ -176,7 +179,7 @@ static void audio_ts_process(void *logctx, DecoderPriv *dp, AVFrame *frame)
// on samplerate change, choose a new internal timebase for timestamp
// generation that can represent timestamps from all the samplerates
// seen so far
- tb = audio_samplerate_update(logctx, dp, frame);
+ tb = audio_samplerate_update(dp, frame);
pts_pred = dp->last_frame_pts == AV_NOPTS_VALUE ? 0 :
dp->last_frame_pts + dp->last_frame_duration_est;
@@ -278,7 +281,7 @@ static int video_frame_process(InputStream *ist, AVFrame *frame)
if (dp->dec_ctx->width != frame->width ||
dp->dec_ctx->height != frame->height ||
dp->dec_ctx->pix_fmt != frame->format) {
- av_log(NULL, AV_LOG_DEBUG, "Frame parameters mismatch context %d,%d,%d != %d,%d,%d\n",
+ av_log(dp, AV_LOG_DEBUG, "Frame parameters mismatch context %d,%d,%d != %d,%d,%d\n",
frame->width,
frame->height,
frame->format,
@@ -289,7 +292,7 @@ static int video_frame_process(InputStream *ist, AVFrame *frame)
#if FFMPEG_OPT_TOP
if(ist->top_field_first>=0) {
- av_log(ist, AV_LOG_WARNING, "-top is deprecated, use the setfield filter instead\n");
+ av_log(dp, AV_LOG_WARNING, "-top is deprecated, use the setfield filter instead\n");
frame->flags |= AV_FRAME_FLAG_TOP_FIELD_FIRST;
}
#endif
@@ -320,7 +323,7 @@ static int video_frame_process(InputStream *ist, AVFrame *frame)
dp->last_frame_tb = frame->time_base;
if (debug_ts) {
- av_log(ist, AV_LOG_INFO,
+ av_log(dp, AV_LOG_INFO,
"decoder -> pts:%s pts_time:%s "
"pkt_dts:%s pkt_dts_time:%s "
"duration:%s duration_time:%s "
@@ -355,7 +358,7 @@ static int process_subtitle(InputStream *ist, AVFrame *frame)
end = av_rescale(subtitle->pts - sub_prev->pts,
1000, AV_TIME_BASE);
if (end < sub_prev->end_display_time) {
- av_log(NULL, AV_LOG_DEBUG,
+ av_log(dp, AV_LOG_DEBUG,
"Subtitle duration reduced from %"PRId32" to %d%s\n",
sub_prev->end_display_time, end,
end <= 0 ? ", dropping it" : "");
@@ -440,8 +443,8 @@ static int transcode_subtitles(InputStream *ist, const AVPacket *pkt,
av_packet_free(&flush_pkt);
if (ret < 0) {
- av_log(ist, AV_LOG_ERROR, "Error decoding subtitles: %s\n",
- av_err2str(ret));
+ av_log(dp, AV_LOG_ERROR, "Error decoding subtitles: %s\n",
+ av_err2str(ret));
ist->decode_errors++;
return exit_on_error ? ret : 0;
}
@@ -501,11 +504,11 @@ static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
// In particular, we don't expect AVERROR(EAGAIN), because we read all
// decoded frames with avcodec_receive_frame() until done.
if (ret == AVERROR(EAGAIN)) {
- av_log(ist, AV_LOG_FATAL, "A decoder returned an unexpected error code. "
- "This is a bug, please report it.\n");
+ av_log(dp, AV_LOG_FATAL, "A decoder returned an unexpected error code. "
+ "This is a bug, please report it.\n");
return AVERROR_BUG;
}
- av_log(ist, AV_LOG_ERROR, "Error submitting %s to decoder: %s\n",
+ av_log(dp, AV_LOG_ERROR, "Error submitting %s to decoder: %s\n",
pkt ? "packet" : "EOF", av_err2str(ret));
if (ret != AVERROR_EOF) {
@@ -533,7 +536,7 @@ static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
} else if (ret == AVERROR_EOF) {
return ret;
} else if (ret < 0) {
- av_log(ist, AV_LOG_ERROR, "Decoding error: %s\n", av_err2str(ret));
+ av_log(dp, AV_LOG_ERROR, "Decoding error: %s\n", av_err2str(ret));
ist->decode_errors++;
if (exit_on_error)
@@ -543,7 +546,7 @@ static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
}
if (frame->decode_error_flags || (frame->flags & AV_FRAME_FLAG_CORRUPT)) {
- av_log(ist, exit_on_error ? AV_LOG_FATAL : AV_LOG_WARNING,
+ av_log(dp, exit_on_error ? AV_LOG_FATAL : AV_LOG_WARNING,
"corrupt decoded frame\n");
if (exit_on_error)
return AVERROR_INVALIDDATA;
@@ -566,12 +569,12 @@ static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
if (dec->codec_type == AVMEDIA_TYPE_AUDIO) {
ist->samples_decoded += frame->nb_samples;
- audio_ts_process(ist, dp, frame);
+ audio_ts_process(dp, frame);
} else {
ret = video_frame_process(ist, frame);
if (ret < 0) {
- av_log(NULL, AV_LOG_FATAL, "Error while processing the decoded "
- "data for stream #%d:%d\n", ifile->index, ist->index);
+ av_log(dp, AV_LOG_FATAL,
+ "Error while processing the decoded data\n");
return ret;
}
}
@@ -644,7 +647,7 @@ void *decoder_thread(void *arg)
(intptr_t)dt.pkt->opaque == PKT_OPAQUE_FIX_SUB_DURATION);
flush_buffers = input_status >= 0 && !have_data;
if (!have_data)
- av_log(ist, AV_LOG_VERBOSE, "Decoder thread received %s packet\n",
+ av_log(dp, AV_LOG_VERBOSE, "Decoder thread received %s packet\n",
flush_buffers ? "flush" : "EOF");
ret = packet_decode(ist, have_data ? dt.pkt : NULL, dt.frame);
@@ -661,7 +664,7 @@ void *decoder_thread(void *arg)
}
if (ret == AVERROR_EOF) {
- av_log(ist, AV_LOG_VERBOSE, "Decoder returned EOF, %s\n",
+ av_log(dp, AV_LOG_VERBOSE, "Decoder returned EOF, %s\n",
flush_buffers ? "resetting" : "finishing");
if (!flush_buffers)
@@ -675,7 +678,7 @@ void *decoder_thread(void *arg)
avcodec_flush_buffers(dp->dec_ctx);
} else if (ret < 0) {
- av_log(ist, AV_LOG_ERROR, "Error processing packet in decoder: %s\n",
+ av_log(dp, AV_LOG_ERROR, "Error processing packet in decoder: %s\n",
av_err2str(ret));
break;
}
@@ -698,7 +701,7 @@ void *decoder_thread(void *arg)
ret = sch_dec_send(dp->sch, dp->sch_idx, dt.frame);
if (ret < 0 && ret != AVERROR_EOF) {
- av_log(NULL, AV_LOG_FATAL,
+ av_log(dp, AV_LOG_FATAL,
"Error signalling EOF timestamp: %s\n", av_err2str(ret));
goto finish;
}
@@ -707,11 +710,11 @@ void *decoder_thread(void *arg)
err_rate = (ist->frames_decoded || ist->decode_errors) ?
ist->decode_errors / (ist->frames_decoded + ist->decode_errors) : 0.f;
if (err_rate > max_error_rate) {
- av_log(ist, AV_LOG_FATAL, "Decode error rate %g exceeds maximum %g\n",
+ av_log(dp, AV_LOG_FATAL, "Decode error rate %g exceeds maximum %g\n",
err_rate, max_error_rate);
ret = FFMPEG_ERROR_RATE_EXCEEDED;
} else if (err_rate)
- av_log(ist, AV_LOG_VERBOSE, "Decode error rate %g\n", err_rate);
+ av_log(dp, AV_LOG_VERBOSE, "Decode error rate %g\n", err_rate);
}
finish:
@@ -798,7 +801,7 @@ static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp)
if (ist->hwaccel_id == HWACCEL_AUTO) {
ist->hwaccel_device_type = dev->type;
} else if (ist->hwaccel_device_type != dev->type) {
- av_log(NULL, AV_LOG_ERROR, "Invalid hwaccel device "
+ av_log(dp, AV_LOG_ERROR, "Invalid hwaccel device "
"specified for decoder: device %s of type %s is not "
"usable with hwaccel %s.\n", dev->name,
av_hwdevice_get_type_name(dev->type),
@@ -849,7 +852,7 @@ static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp)
type = config->device_type;
dev = hw_device_get_by_type(type);
if (dev) {
- av_log(NULL, AV_LOG_INFO, "Using auto "
+ av_log(dp, AV_LOG_INFO, "Using auto "
"hwaccel type %s with existing device %s.\n",
av_hwdevice_get_type_name(type), dev->name);
}
@@ -867,12 +870,12 @@ static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp)
continue;
}
if (ist->hwaccel_device) {
- av_log(NULL, AV_LOG_INFO, "Using auto "
+ av_log(dp, AV_LOG_INFO, "Using auto "
"hwaccel type %s with new device created "
"from %s.\n", av_hwdevice_get_type_name(type),
ist->hwaccel_device);
} else {
- av_log(NULL, AV_LOG_INFO, "Using auto "
+ av_log(dp, AV_LOG_INFO, "Using auto "
"hwaccel type %s with new default device.\n",
av_hwdevice_get_type_name(type));
}
@@ -880,7 +883,7 @@ static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp)
if (dev) {
ist->hwaccel_device_type = type;
} else {
- av_log(NULL, AV_LOG_INFO, "Auto hwaccel "
+ av_log(dp, AV_LOG_INFO, "Auto hwaccel "
"disabled: no device found.\n");
ist->hwaccel_id = HWACCEL_NONE;
return 0;
@@ -888,7 +891,7 @@ static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp)
}
if (!dev) {
- av_log(NULL, AV_LOG_ERROR, "No device available "
+ av_log(dp, AV_LOG_ERROR, "No device available "
"for decoder: device type %s needed for codec %s.\n",
av_hwdevice_get_type_name(type), ist->dec->name);
return err;
@@ -901,6 +904,20 @@ static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp)
return 0;
}
+static const char *dec_item_name(void *obj)
+{
+ const DecoderPriv *dp = obj;
+
+ return dp->log_name;
+}
+
+static const AVClass dec_class = {
+ .class_name = "Decoder",
+ .version = LIBAVUTIL_VERSION_INT,
+ .parent_log_context_offset = offsetof(DecoderPriv, log_parent),
+ .item_name = dec_item_name,
+};
+
int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
{
DecoderPriv *dp;
@@ -922,6 +939,11 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
dp->sch = sch;
dp->sch_idx = sch_idx;
+ dp->dec.class = &dec_class;
+ dp->log_parent = ist;
+
+ snprintf(dp->log_name, sizeof(dp->log_name), "dec:%s", codec->name);
+
if (codec->type == AVMEDIA_TYPE_SUBTITLE && ist->fix_sub_duration) {
for (int i = 0; i < FF_ARRAY_ELEMS(dp->sub_prev); i++) {
dp->sub_prev[i] = av_frame_alloc();
@@ -939,7 +961,7 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
ret = avcodec_parameters_to_context(dp->dec_ctx, ist->par);
if (ret < 0) {
- av_log(ist, AV_LOG_ERROR, "Error initializing the decoder context.\n");
+ av_log(dp, AV_LOG_ERROR, "Error initializing the decoder context.\n");
return ret;
}
@@ -950,7 +972,9 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
(ist->decoding_needed & DECODING_FOR_OST)) {
av_dict_set(&ist->decoder_opts, "compute_edt", "1", AV_DICT_DONT_OVERWRITE);
if (ist->decoding_needed & DECODING_FOR_FILTER)
- av_log(NULL, AV_LOG_WARNING, "Warning using DVB subtitles for filtering and output at the same time is not fully supported, also see -compute_edt [0|1]\n");
+ av_log(dp, AV_LOG_WARNING,
+ "Warning using DVB subtitles for filtering and output at the "
+ "same time is not fully supported, also see -compute_edt [0|1]\n");
}
/* Useful for subtitles retiming by lavf (FIXME), skipping samples in
@@ -967,14 +991,14 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
ret = hw_device_setup_for_decode(ist, dp);
if (ret < 0) {
- av_log(ist, AV_LOG_ERROR,
+ av_log(dp, AV_LOG_ERROR,
"Hardware device setup failed for decoder: %s\n",
av_err2str(ret));
return ret;
}
if ((ret = avcodec_open2(dp->dec_ctx, codec, &ist->decoder_opts)) < 0) {
- av_log(ist, AV_LOG_ERROR, "Error while opening decoder: %s\n",
+ av_log(dp, AV_LOG_ERROR, "Error while opening decoder: %s\n",
av_err2str(ret));
return ret;
}
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 06/31] fftools/ffmpeg_dec: pass decoder options as an argument to dec_open()
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (3 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 05/31] fftools/ffmpeg_dec: add an AVClass to Decoder Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 07/31] fftools/ffmpeg_dec: move decoding counters from InputStream to Decoder Anton Khirnov
` (24 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Rather than access the dictionary in InputStream.
This is a step towards decoupling Decoder and InputStream.
---
fftools/ffmpeg.h | 7 ++++++-
fftools/ffmpeg_dec.c | 17 +++++++++--------
fftools/ffmpeg_demux.c | 3 ++-
3 files changed, 17 insertions(+), 10 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index 9e29ae1785..227929b022 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -731,7 +731,12 @@ AVBufferRef *hw_device_for_filter(void);
int hwaccel_retrieve_data(AVCodecContext *avctx, AVFrame *input);
-int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx);
+/**
+ * @param dec_opts Dictionary filled with decoder options. Its ownership
+ * is transferred to the decoder.
+ */
+int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
+ AVDictionary **dec_opts);
void dec_free(Decoder **pdec);
int dec_add_filter(Decoder *dec, InputFilter *ifilter);
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index 6dca730e51..15d49d0d69 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -918,7 +918,8 @@ static const AVClass dec_class = {
.item_name = dec_item_name,
};
-int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
+int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
+ AVDictionary **dec_opts)
{
DecoderPriv *dp;
const AVCodec *codec = ist->dec;
@@ -970,7 +971,7 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
if (dp->dec_ctx->codec_id == AV_CODEC_ID_DVB_SUBTITLE &&
(ist->decoding_needed & DECODING_FOR_OST)) {
- av_dict_set(&ist->decoder_opts, "compute_edt", "1", AV_DICT_DONT_OVERWRITE);
+ av_dict_set(dec_opts, "compute_edt", "1", AV_DICT_DONT_OVERWRITE);
if (ist->decoding_needed & DECODING_FOR_FILTER)
av_log(dp, AV_LOG_WARNING,
"Warning using DVB subtitles for filtering and output at the "
@@ -981,13 +982,13 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
* audio, and video decoders such as cuvid or mediacodec */
dp->dec_ctx->pkt_timebase = ist->st->time_base;
- if (!av_dict_get(ist->decoder_opts, "threads", NULL, 0))
- av_dict_set(&ist->decoder_opts, "threads", "auto", 0);
+ if (!av_dict_get(*dec_opts, "threads", NULL, 0))
+ av_dict_set(dec_opts, "threads", "auto", 0);
/* Attached pics are sparse, therefore we would not want to delay their decoding till EOF. */
if (ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC)
- av_dict_set(&ist->decoder_opts, "threads", "1", 0);
+ av_dict_set(dec_opts, "threads", "1", 0);
- av_dict_set(&ist->decoder_opts, "flags", "+copy_opaque", AV_DICT_MULTIKEY);
+ av_dict_set(dec_opts, "flags", "+copy_opaque", AV_DICT_MULTIKEY);
ret = hw_device_setup_for_decode(ist, dp);
if (ret < 0) {
@@ -997,13 +998,13 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx)
return ret;
}
- if ((ret = avcodec_open2(dp->dec_ctx, codec, &ist->decoder_opts)) < 0) {
+ if ((ret = avcodec_open2(dp->dec_ctx, codec, dec_opts)) < 0) {
av_log(dp, AV_LOG_ERROR, "Error while opening decoder: %s\n",
av_err2str(ret));
return ret;
}
- ret = check_avoptions(ist->decoder_opts);
+ ret = check_avoptions(*dec_opts);
if (ret < 0)
return ret;
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 8e904d2150..b2cbde2aa5 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -895,7 +895,8 @@ static int ist_use(InputStream *ist, int decoding_needed)
if (ret < 0)
return ret;
- ret = dec_open(ist, d->sch, ds->sch_idx_dec);
+ ret = dec_open(ist, d->sch, ds->sch_idx_dec,
+ &ist->decoder_opts);
if (ret < 0)
return ret;
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 07/31] fftools/ffmpeg_dec: move decoding counters from InputStream to Decoder
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (4 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 06/31] fftools/ffmpeg_dec: pass decoder options as an argument to dec_open() Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 08/31] fftools/ffmpeg_dec: drop useless and racy code Anton Khirnov
` (23 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
This is a step towards decoupling Decoder and InputStream.
---
fftools/ffmpeg.h | 11 +++++------
fftools/ffmpeg_dec.c | 16 ++++++++--------
fftools/ffmpeg_demux.c | 4 ++--
3 files changed, 15 insertions(+), 16 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index 227929b022..db9bd8cc7a 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -285,6 +285,11 @@ typedef struct Decoder {
const uint8_t *subtitle_header;
int subtitle_header_size;
+
+ // number of frames/samples retrieved from the decoder
+ uint64_t frames_decoded;
+ uint64_t samples_decoded;
+ uint64_t decode_errors;
} Decoder;
typedef struct InputStream {
@@ -346,12 +351,6 @@ typedef struct InputStream {
enum AVHWDeviceType hwaccel_device_type;
char *hwaccel_device;
enum AVPixelFormat hwaccel_output_format;
-
- /* stats */
- // number of frames/samples retrieved from the decoder
- uint64_t frames_decoded;
- uint64_t samples_decoded;
- uint64_t decode_errors;
} InputStream;
typedef struct InputFile {
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index 15d49d0d69..4a59a4b392 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -445,14 +445,14 @@ static int transcode_subtitles(InputStream *ist, const AVPacket *pkt,
if (ret < 0) {
av_log(dp, AV_LOG_ERROR, "Error decoding subtitles: %s\n",
av_err2str(ret));
- ist->decode_errors++;
+ dp->dec.decode_errors++;
return exit_on_error ? ret : 0;
}
if (!got_output)
return pkt ? 0 : AVERROR_EOF;
- ist->frames_decoded++;
+ dp->dec.frames_decoded++;
// XXX the queue for transferring data to consumers runs
// on AVFrames, so we wrap AVSubtitle in an AVBufferRef and put that
@@ -512,7 +512,7 @@ static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
pkt ? "packet" : "EOF", av_err2str(ret));
if (ret != AVERROR_EOF) {
- ist->decode_errors++;
+ dp->dec.decode_errors++;
if (!exit_on_error)
ret = 0;
}
@@ -537,7 +537,7 @@ static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
return ret;
} else if (ret < 0) {
av_log(dp, AV_LOG_ERROR, "Decoding error: %s\n", av_err2str(ret));
- ist->decode_errors++;
+ dp->dec.decode_errors++;
if (exit_on_error)
return ret;
@@ -567,7 +567,7 @@ static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
frame->time_base = dec->pkt_timebase;
if (dec->codec_type == AVMEDIA_TYPE_AUDIO) {
- ist->samples_decoded += frame->nb_samples;
+ dp->dec.samples_decoded += frame->nb_samples;
audio_ts_process(dp, frame);
} else {
@@ -579,7 +579,7 @@ static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
}
}
- ist->frames_decoded++;
+ dp->dec.frames_decoded++;
ret = sch_dec_send(dp->sch, dp->sch_idx, frame);
if (ret < 0) {
@@ -707,8 +707,8 @@ void *decoder_thread(void *arg)
}
ret = 0;
- err_rate = (ist->frames_decoded || ist->decode_errors) ?
- ist->decode_errors / (ist->frames_decoded + ist->decode_errors) : 0.f;
+ err_rate = (dp->dec.frames_decoded || dp->dec.decode_errors) ?
+ dp->dec.decode_errors / (dp->dec.frames_decoded + dp->dec.decode_errors) : 0.f;
if (err_rate > max_error_rate) {
av_log(dp, AV_LOG_FATAL, "Decode error rate %g exceeds maximum %g\n",
err_rate, max_error_rate);
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index b2cbde2aa5..5a58bb735a 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -796,9 +796,9 @@ static void demux_final_stats(Demuxer *d)
if (ist->decoding_needed) {
av_log(f, AV_LOG_VERBOSE,
"%"PRIu64" frames decoded; %"PRIu64" decode errors",
- ist->frames_decoded, ist->decode_errors);
+ ist->decoder->frames_decoded, ist->decoder->decode_errors);
if (type == AVMEDIA_TYPE_AUDIO)
- av_log(f, AV_LOG_VERBOSE, " (%"PRIu64" samples)", ist->samples_decoded);
+ av_log(f, AV_LOG_VERBOSE, " (%"PRIu64" samples)", ist->decoder->samples_decoded);
av_log(f, AV_LOG_VERBOSE, "; ");
}
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 08/31] fftools/ffmpeg_dec: drop useless and racy code
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (5 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 07/31] fftools/ffmpeg_dec: move decoding counters from InputStream to Decoder Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 09/31] fftools/ffmpeg_dec: drop a useless log message Anton Khirnov
` (22 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Setting demuxer's video_delay from the decoder cannot accomplish
anything meaningful and is racy, as they run in different threads.
---
fftools/ffmpeg_dec.c | 15 ---------------
1 file changed, 15 deletions(-)
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index 4a59a4b392..baaba966c6 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -263,21 +263,6 @@ static int video_frame_process(InputStream *ist, AVFrame *frame)
{
DecoderPriv *dp = dp_from_dec(ist->decoder);
- // The following line may be required in some cases where there is no parser
- // or the parser does not has_b_frames correctly
- if (ist->par->video_delay < dp->dec_ctx->has_b_frames) {
- if (dp->dec_ctx->codec_id == AV_CODEC_ID_H264) {
- ist->par->video_delay = dp->dec_ctx->has_b_frames;
- } else
- av_log(dp->dec_ctx, AV_LOG_WARNING,
- "video_delay is larger in decoder than demuxer %d > %d.\n"
- "If you want to help, upload a sample "
- "of this file to https://streams.videolan.org/upload/ "
- "and contact the ffmpeg-devel mailing list. (ffmpeg-devel@ffmpeg.org)\n",
- dp->dec_ctx->has_b_frames,
- ist->par->video_delay);
- }
-
if (dp->dec_ctx->width != frame->width ||
dp->dec_ctx->height != frame->height ||
dp->dec_ctx->pix_fmt != frame->format) {
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 09/31] fftools/ffmpeg_dec: drop a useless log message
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (6 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 08/31] fftools/ffmpeg_dec: drop useless and racy code Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 10/31] fftools/ffmpeg: move decoder existence check to a more appropriate place Anton Khirnov
` (21 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
---
fftools/ffmpeg_dec.c | 12 ------------
1 file changed, 12 deletions(-)
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index baaba966c6..00428dff48 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -263,18 +263,6 @@ static int video_frame_process(InputStream *ist, AVFrame *frame)
{
DecoderPriv *dp = dp_from_dec(ist->decoder);
- if (dp->dec_ctx->width != frame->width ||
- dp->dec_ctx->height != frame->height ||
- dp->dec_ctx->pix_fmt != frame->format) {
- av_log(dp, AV_LOG_DEBUG, "Frame parameters mismatch context %d,%d,%d != %d,%d,%d\n",
- frame->width,
- frame->height,
- frame->format,
- dp->dec_ctx->width,
- dp->dec_ctx->height,
- dp->dec_ctx->pix_fmt);
- }
-
#if FFMPEG_OPT_TOP
if(ist->top_field_first>=0) {
av_log(dp, AV_LOG_WARNING, "-top is deprecated, use the setfield filter instead\n");
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 10/31] fftools/ffmpeg: move decoder existence check to a more appropriate place
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (7 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 09/31] fftools/ffmpeg_dec: drop a useless log message Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 11/31] fftools/ffmpeg_dec: override video SAR with AVCodecParameters value Anton Khirnov
` (20 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
---
fftools/ffmpeg_dec.c | 7 -------
fftools/ffmpeg_demux.c | 7 +++++++
2 files changed, 7 insertions(+), 7 deletions(-)
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index 00428dff48..d16049ab4c 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -898,13 +898,6 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
const AVCodec *codec = ist->dec;
int ret;
- if (!codec) {
- av_log(ist, AV_LOG_ERROR,
- "Decoding requested, but no decoder found for: %s\n",
- avcodec_get_name(ist->par->codec_id));
- return AVERROR(EINVAL);
- }
-
ret = dec_alloc(&ist->decoder);
if (ret < 0)
return ret;
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 5a58bb735a..11db118b72 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -866,6 +866,13 @@ static int ist_use(InputStream *ist, int decoding_needed)
return AVERROR(EINVAL);
}
+ if (decoding_needed && !ist->dec) {
+ av_log(ist, AV_LOG_ERROR,
+ "Decoding requested, but no decoder found for: %s\n",
+ avcodec_get_name(ist->par->codec_id));
+ return AVERROR(EINVAL);
+ }
+
if (ds->sch_idx_stream < 0) {
ret = sch_add_demux_stream(d->sch, d->f.index);
if (ret < 0)
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 11/31] fftools/ffmpeg_dec: override video SAR with AVCodecParameters value
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (8 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 10/31] fftools/ffmpeg: move decoder existence check to a more appropriate place Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-03-24 22:09 ` Michael Niedermayer
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 12/31] fftools/ffmpeg_dec: stop accesing InputStream.fix_sub_duration Anton Khirnov
` (19 subsequent siblings)
29 siblings, 1 reply; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Rather than access the AVStream one.
This is a step towards decoupling Decoder and InputStream.
---
fftools/ffmpeg_dec.c | 9 +++++++--
fftools/ffmpeg_demux.c | 3 +++
2 files changed, 10 insertions(+), 2 deletions(-)
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index d16049ab4c..b5a0ce9080 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -42,6 +42,9 @@ typedef struct DecoderPriv {
AVFrame *frame;
AVPacket *pkt;
+ // override output video sample aspect ratio with this value
+ AVRational sar_override;
+
enum AVPixelFormat hwaccel_pix_fmt;
// pts/estimated duration of the last decoded frame
@@ -311,8 +314,8 @@ static int video_frame_process(InputStream *ist, AVFrame *frame)
frame->time_base.num, frame->time_base.den);
}
- if (ist->st->sample_aspect_ratio.num)
- frame->sample_aspect_ratio = ist->st->sample_aspect_ratio;
+ if (dp->sar_override.num)
+ frame->sample_aspect_ratio = dp->sar_override;
return 0;
}
@@ -922,6 +925,8 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
return AVERROR(ENOMEM);
}
+ dp->sar_override = ist->par->sample_aspect_ratio;
+
dp->dec_ctx = avcodec_alloc_context3(codec);
if (!dp->dec_ctx)
return AVERROR(ENOMEM);
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 11db118b72..a58217223b 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -1336,6 +1336,9 @@ static int ist_add(const OptionsContext *o, Demuxer *d, AVStream *st)
return ret;
}
+ if (ist->st->sample_aspect_ratio.num)
+ ist->par->sample_aspect_ratio = ist->st->sample_aspect_ratio;
+
MATCH_PER_STREAM_OPT(bitstream_filters, str, bsfs, ic, st);
if (bsfs) {
ret = av_bsf_list_parse_str(bsfs, &ds->bsf);
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: [FFmpeg-devel] [PATCH 11/31] fftools/ffmpeg_dec: override video SAR with AVCodecParameters value
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 11/31] fftools/ffmpeg_dec: override video SAR with AVCodecParameters value Anton Khirnov
@ 2024-03-24 22:09 ` Michael Niedermayer
0 siblings, 0 replies; 34+ messages in thread
From: Michael Niedermayer @ 2024-03-24 22:09 UTC (permalink / raw)
To: FFmpeg development discussions and patches
[-- Attachment #1.1: Type: text/plain, Size: 855 bytes --]
On Wed, Jan 24, 2024 at 09:16:41AM +0100, Anton Khirnov wrote:
> Rather than access the AVStream one.
>
> This is a step towards decoupling Decoder and InputStream.
> ---
> fftools/ffmpeg_dec.c | 9 +++++++--
> fftools/ffmpeg_demux.c | 3 +++
> 2 files changed, 10 insertions(+), 2 deletions(-)
This breaks
./ffmpeg -i ~/tickets/4161/VR_MOVIE_GuyMartinsSpitfireBcast169\ qsf\ lappyAspectNoChnge_extract.mpg -vcodec libx264 -an -vsync cfr /tmp/file-16:9.ts
the aspect ratio of the resulting file is completely wrong
https://trac.ffmpeg.org/ticket/4161
thx
[...]
--
Michael GnuPG fingerprint: 9FF2128B147EF6730BADF133611EC787040B0FAB
Many things microsoft did are stupid, but not doing something just because
microsoft did it is even more stupid. If everything ms did were stupid they
would be bankrupt already.
[-- Attachment #1.2: signature.asc --]
[-- Type: application/pgp-signature, Size: 195 bytes --]
[-- Attachment #2: Type: text/plain, Size: 251 bytes --]
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 12/31] fftools/ffmpeg_dec: stop accesing InputStream.fix_sub_duration
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (9 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 11/31] fftools/ffmpeg_dec: override video SAR with AVCodecParameters value Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 13/31] fftools/ffmpeg: refactor disabling decoder threading for attached pictures Anton Khirnov
` (18 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Pass this information to dec_open() instead.
This is a step towards decoupling Decoder and InputStream.
---
fftools/ffmpeg.h | 6 +++++-
fftools/ffmpeg_dec.c | 13 +++++++++----
fftools/ffmpeg_demux.c | 3 ++-
3 files changed, 16 insertions(+), 6 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index db9bd8cc7a..8b7560b359 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -280,6 +280,10 @@ typedef struct FilterGraph {
int nb_outputs;
} FilterGraph;
+enum DecoderFlags {
+ DECODER_FLAG_FIX_SUB_DURATION = (1 << 0),
+};
+
typedef struct Decoder {
const AVClass *class;
@@ -735,7 +739,7 @@ int hwaccel_retrieve_data(AVCodecContext *avctx, AVFrame *input);
* is transferred to the decoder.
*/
int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
- AVDictionary **dec_opts);
+ AVDictionary **dec_opts, int flags);
void dec_free(Decoder **pdec);
int dec_add_filter(Decoder *dec, InputFilter *ifilter);
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index b5a0ce9080..7037175a48 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -45,6 +45,9 @@ typedef struct DecoderPriv {
// override output video sample aspect ratio with this value
AVRational sar_override;
+ // a combination of DECODER_FLAG_*, provided to dec_open()
+ int flags;
+
enum AVPixelFormat hwaccel_pix_fmt;
// pts/estimated duration of the last decoded frame
@@ -326,7 +329,7 @@ static int process_subtitle(InputStream *ist, AVFrame *frame)
const AVSubtitle *subtitle = (AVSubtitle*)frame->buf[0]->data;
int ret = 0;
- if (ist->fix_sub_duration) {
+ if (dp->flags & DECODER_FLAG_FIX_SUB_DURATION) {
AVSubtitle *sub_prev = dp->sub_prev[0]->buf[0] ?
(AVSubtitle*)dp->sub_prev[0]->buf[0]->data : NULL;
int end = 1;
@@ -372,7 +375,7 @@ static int fix_sub_duration_heartbeat(InputStream *ist, int64_t signal_pts)
(AVSubtitle*)dp->sub_prev[0]->buf[0]->data : NULL;
AVSubtitle *subtitle;
- if (!ist->fix_sub_duration || !prev_subtitle ||
+ if (!(dp->flags & DECODER_FLAG_FIX_SUB_DURATION) || !prev_subtitle ||
!prev_subtitle->num_rects || signal_pts <= prev_subtitle->pts)
return 0;
@@ -895,7 +898,7 @@ static const AVClass dec_class = {
};
int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
- AVDictionary **dec_opts)
+ AVDictionary **dec_opts, int flags)
{
DecoderPriv *dp;
const AVCodec *codec = ist->dec;
@@ -909,12 +912,14 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
dp->sch = sch;
dp->sch_idx = sch_idx;
+ dp->flags = flags;
dp->dec.class = &dec_class;
dp->log_parent = ist;
snprintf(dp->log_name, sizeof(dp->log_name), "dec:%s", codec->name);
- if (codec->type == AVMEDIA_TYPE_SUBTITLE && ist->fix_sub_duration) {
+ if (codec->type == AVMEDIA_TYPE_SUBTITLE &&
+ (dp->flags & DECODER_FLAG_FIX_SUB_DURATION)) {
for (int i = 0; i < FF_ARRAY_ELEMS(dp->sub_prev); i++) {
dp->sub_prev[i] = av_frame_alloc();
if (!dp->sub_prev[i])
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index a58217223b..02add669a0 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -891,6 +891,7 @@ static int ist_use(InputStream *ist, int decoding_needed)
if (decoding_needed && ds->sch_idx_dec < 0) {
int is_audio = ist->st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO;
+ int dec_flags = !!ist->fix_sub_duration * DECODER_FLAG_FIX_SUB_DURATION;
ret = sch_add_dec(d->sch, decoder_thread, ist, d->loop && is_audio);
if (ret < 0)
@@ -903,7 +904,7 @@ static int ist_use(InputStream *ist, int decoding_needed)
return ret;
ret = dec_open(ist, d->sch, ds->sch_idx_dec,
- &ist->decoder_opts);
+ &ist->decoder_opts, dec_flags);
if (ret < 0)
return ret;
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 13/31] fftools/ffmpeg: refactor disabling decoder threading for attached pictures
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (10 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 12/31] fftools/ffmpeg_dec: stop accesing InputStream.fix_sub_duration Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 14/31] fftools/ffmpeg_dec: replace InputFile.format_nots with a decoder flag Anton Khirnov
` (17 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
* as this decision is based on demuxing information, move it from the
decoder to the demuxer
* as the issue being addressed is latency added by frame threading, we
only need to disable frame threading, not all threading
---
fftools/ffmpeg_dec.c | 3 ---
fftools/ffmpeg_demux.c | 5 +++++
2 files changed, 5 insertions(+), 3 deletions(-)
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index 7037175a48..e0d8e27098 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -960,9 +960,6 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
if (!av_dict_get(*dec_opts, "threads", NULL, 0))
av_dict_set(dec_opts, "threads", "auto", 0);
- /* Attached pics are sparse, therefore we would not want to delay their decoding till EOF. */
- if (ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC)
- av_dict_set(dec_opts, "threads", "1", 0);
av_dict_set(dec_opts, "flags", "+copy_opaque", AV_DICT_MULTIKEY);
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 02add669a0..d804358d55 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -1259,6 +1259,11 @@ static int ist_add(const OptionsContext *o, Demuxer *d, AVStream *st)
if (o->bitexact)
av_dict_set(&ist->decoder_opts, "flags", "+bitexact", AV_DICT_MULTIKEY);
+ /* Attached pics are sparse, therefore we would not want to delay their decoding
+ * till EOF. */
+ if (ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC)
+ av_dict_set(&ist->decoder_opts, "thread_type", "-frame", 0);
+
switch (par->codec_type) {
case AVMEDIA_TYPE_VIDEO:
MATCH_PER_STREAM_OPT(frame_rates, str, framerate, ic, st);
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 14/31] fftools/ffmpeg_dec: replace InputFile.format_nots with a decoder flag
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (11 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 13/31] fftools/ffmpeg: refactor disabling decoder threading for attached pictures Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 15/31] fftools/ffmpeg: move hwaccel_retrieve_data() from ffmpeg_hw to ffmpeg_dec Anton Khirnov
` (16 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Reduces the need to access InputFile from decoding.
This is a step towards decoupling Decoder and InputStream.
---
fftools/ffmpeg.h | 5 ++---
fftools/ffmpeg_dec.c | 8 ++++----
fftools/ffmpeg_demux.c | 5 ++---
3 files changed, 8 insertions(+), 10 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index 8b7560b359..e87af70698 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -282,6 +282,8 @@ typedef struct FilterGraph {
enum DecoderFlags {
DECODER_FLAG_FIX_SUB_DURATION = (1 << 0),
+ // input timestamps are unreliable (guessed by demuxer)
+ DECODER_FLAG_TS_UNRELIABLE = (1 << 1),
};
typedef struct Decoder {
@@ -362,9 +364,6 @@ typedef struct InputFile {
int index;
- // input format has no timestamps
- int format_nots;
-
AVFormatContext *ctx;
int64_t input_ts_offset;
int input_sync_ref;
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index e0d8e27098..f647db3611 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -216,7 +216,7 @@ static void audio_ts_process(DecoderPriv *dp, AVFrame *frame)
static int64_t video_duration_estimate(const InputStream *ist, const AVFrame *frame)
{
const DecoderPriv *dp = dp_from_dec(ist->decoder);
- const InputFile *ifile = ist->file;
+ const int ts_unreliable = dp->flags & DECODER_FLAG_TS_UNRELIABLE;
int64_t codec_duration = 0;
// XXX lavf currently makes up frame durations when they are not provided by
@@ -226,7 +226,7 @@ static int64_t video_duration_estimate(const InputStream *ist, const AVFrame *fr
// durations, then this should be simplified.
// prefer frame duration for containers with timestamps
- if (frame->duration > 0 && (!ifile->format_nots || ist->framerate.num))
+ if (frame->duration > 0 && (!ts_unreliable || ist->framerate.num))
return frame->duration;
if (dp->dec_ctx->framerate.den && dp->dec_ctx->framerate.num) {
@@ -238,7 +238,7 @@ static int64_t video_duration_estimate(const InputStream *ist, const AVFrame *fr
}
// prefer codec-layer duration for containers without timestamps
- if (codec_duration > 0 && ifile->format_nots)
+ if (codec_duration > 0 && ts_unreliable)
return codec_duration;
// when timestamps are available, repeat last frame's actual duration
@@ -466,7 +466,7 @@ static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
if (pkt && pkt->size == 0)
return 0;
- if (pkt && ifile->format_nots) {
+ if (pkt && (dp->flags & DECODER_FLAG_TS_UNRELIABLE)) {
pkt->pts = AV_NOPTS_VALUE;
pkt->dts = AV_NOPTS_VALUE;
}
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index d804358d55..729d7e476b 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -891,7 +891,8 @@ static int ist_use(InputStream *ist, int decoding_needed)
if (decoding_needed && ds->sch_idx_dec < 0) {
int is_audio = ist->st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO;
- int dec_flags = !!ist->fix_sub_duration * DECODER_FLAG_FIX_SUB_DURATION;
+ int dec_flags = (!!ist->fix_sub_duration * DECODER_FLAG_FIX_SUB_DURATION) |
+ (!!(d->f.ctx->iformat->flags & AVFMT_NOTIMESTAMPS) * DECODER_FLAG_TS_UNRELIABLE);
ret = sch_add_dec(d->sch, decoder_thread, ist, d->loop && is_audio);
if (ret < 0)
@@ -1698,8 +1699,6 @@ int ifile_open(const OptionsContext *o, const char *filename, Scheduler *sch)
d->min_pts = (Timestamp){ .ts = AV_NOPTS_VALUE, .tb = (AVRational){ 1, 1 } };
d->max_pts = (Timestamp){ .ts = AV_NOPTS_VALUE, .tb = (AVRational){ 1, 1 } };
- f->format_nots = !!(ic->iformat->flags & AVFMT_NOTIMESTAMPS);
-
d->readrate = o->readrate ? o->readrate : 0.0;
if (d->readrate < 0.0f) {
av_log(d, AV_LOG_ERROR, "Option -readrate is %0.3f; it must be non-negative.\n", d->readrate);
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 15/31] fftools/ffmpeg: move hwaccel_retrieve_data() from ffmpeg_hw to ffmpeg_dec
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (12 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 14/31] fftools/ffmpeg_dec: replace InputFile.format_nots with a decoder flag Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 16/31] fftools/ffmpeg_dec: pass hwaccel options to the decoder in a separate struct Anton Khirnov
` (15 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
This function is decoding-only and has no interaction with the rest of
ffmpeg_hw. It thus belongs more properly in ffmpeg_dec.
---
fftools/ffmpeg.h | 2 --
fftools/ffmpeg_dec.c | 42 ++++++++++++++++++++++++++++++++++++++++++
fftools/ffmpeg_hw.c | 42 ------------------------------------------
3 files changed, 42 insertions(+), 44 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index e87af70698..80c09d1662 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -731,8 +731,6 @@ void hw_device_free_all(void);
*/
AVBufferRef *hw_device_for_filter(void);
-int hwaccel_retrieve_data(AVCodecContext *avctx, AVFrame *input);
-
/**
* @param dec_opts Dictionary filled with decoder options. Its ownership
* is transferred to the decoder.
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index f647db3611..f65857bea3 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -265,6 +265,48 @@ static int64_t video_duration_estimate(const InputStream *ist, const AVFrame *fr
return FFMAX(dp->last_frame_duration_est, 1);
}
+static int hwaccel_retrieve_data(AVCodecContext *avctx, AVFrame *input)
+{
+ InputStream *ist = avctx->opaque;
+ AVFrame *output = NULL;
+ enum AVPixelFormat output_format = ist->hwaccel_output_format;
+ int err;
+
+ if (input->format == output_format) {
+ // Nothing to do.
+ return 0;
+ }
+
+ output = av_frame_alloc();
+ if (!output)
+ return AVERROR(ENOMEM);
+
+ output->format = output_format;
+
+ err = av_hwframe_transfer_data(output, input, 0);
+ if (err < 0) {
+ av_log(avctx, AV_LOG_ERROR, "Failed to transfer data to "
+ "output frame: %d.\n", err);
+ goto fail;
+ }
+
+ err = av_frame_copy_props(output, input);
+ if (err < 0) {
+ av_frame_unref(output);
+ goto fail;
+ }
+
+ av_frame_unref(input);
+ av_frame_move_ref(input, output);
+ av_frame_free(&output);
+
+ return 0;
+
+fail:
+ av_frame_free(&output);
+ return err;
+}
+
static int video_frame_process(InputStream *ist, AVFrame *frame)
{
DecoderPriv *dp = dp_from_dec(ist->decoder);
diff --git a/fftools/ffmpeg_hw.c b/fftools/ffmpeg_hw.c
index 46bc7e39c2..8608d24517 100644
--- a/fftools/ffmpeg_hw.c
+++ b/fftools/ffmpeg_hw.c
@@ -297,48 +297,6 @@ void hw_device_free_all(void)
nb_hw_devices = 0;
}
-int hwaccel_retrieve_data(AVCodecContext *avctx, AVFrame *input)
-{
- InputStream *ist = avctx->opaque;
- AVFrame *output = NULL;
- enum AVPixelFormat output_format = ist->hwaccel_output_format;
- int err;
-
- if (input->format == output_format) {
- // Nothing to do.
- return 0;
- }
-
- output = av_frame_alloc();
- if (!output)
- return AVERROR(ENOMEM);
-
- output->format = output_format;
-
- err = av_hwframe_transfer_data(output, input, 0);
- if (err < 0) {
- av_log(avctx, AV_LOG_ERROR, "Failed to transfer data to "
- "output frame: %d.\n", err);
- goto fail;
- }
-
- err = av_frame_copy_props(output, input);
- if (err < 0) {
- av_frame_unref(output);
- goto fail;
- }
-
- av_frame_unref(input);
- av_frame_move_ref(input, output);
- av_frame_free(&output);
-
- return 0;
-
-fail:
- av_frame_free(&output);
- return err;
-}
-
AVBufferRef *hw_device_for_filter(void)
{
// Pick the last hardware device if the user doesn't pick the device for
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 16/31] fftools/ffmpeg_dec: pass hwaccel options to the decoder in a separate struct
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (13 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 15/31] fftools/ffmpeg: move hwaccel_retrieve_data() from ffmpeg_hw to ffmpeg_dec Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 17/31] fftools/ffmpeg_dec: move flags to DecoderOpts Anton Khirnov
` (14 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Stop reading them from InputStream.
This is a step towards decoupling Decoder and InputStream.
---
fftools/ffmpeg.h | 16 +++++-----
fftools/ffmpeg_dec.c | 67 +++++++++++++++++++++++-------------------
fftools/ffmpeg_demux.c | 36 ++++++++++++-----------
3 files changed, 65 insertions(+), 54 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index 80c09d1662..abf95f106b 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -286,6 +286,14 @@ enum DecoderFlags {
DECODER_FLAG_TS_UNRELIABLE = (1 << 1),
};
+typedef struct DecoderOpts {
+ /* hwaccel options */
+ enum HWAccelID hwaccel_id;
+ enum AVHWDeviceType hwaccel_device_type;
+ char *hwaccel_device;
+ enum AVPixelFormat hwaccel_output_format;
+} DecoderOpts;
+
typedef struct Decoder {
const AVClass *class;
@@ -351,12 +359,6 @@ typedef struct InputStream {
int nb_outputs;
int reinit_filters;
-
- /* hwaccel options */
- enum HWAccelID hwaccel_id;
- enum AVHWDeviceType hwaccel_device_type;
- char *hwaccel_device;
- enum AVPixelFormat hwaccel_output_format;
} InputStream;
typedef struct InputFile {
@@ -736,7 +738,7 @@ AVBufferRef *hw_device_for_filter(void);
* is transferred to the decoder.
*/
int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
- AVDictionary **dec_opts, int flags);
+ AVDictionary **dec_opts, int flags, const DecoderOpts *o);
void dec_free(Decoder **pdec);
int dec_add_filter(Decoder *dec, InputFilter *ifilter);
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index f65857bea3..0cbe16ea5f 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -48,7 +48,10 @@ typedef struct DecoderPriv {
// a combination of DECODER_FLAG_*, provided to dec_open()
int flags;
- enum AVPixelFormat hwaccel_pix_fmt;
+ enum AVPixelFormat hwaccel_pix_fmt;
+ enum HWAccelID hwaccel_id;
+ enum AVHWDeviceType hwaccel_device_type;
+ enum AVPixelFormat hwaccel_output_format;
// pts/estimated duration of the last decoded frame
// * in decoder timebase for video,
@@ -267,9 +270,9 @@ static int64_t video_duration_estimate(const InputStream *ist, const AVFrame *fr
static int hwaccel_retrieve_data(AVCodecContext *avctx, AVFrame *input)
{
- InputStream *ist = avctx->opaque;
+ DecoderPriv *dp = avctx->opaque;
AVFrame *output = NULL;
- enum AVPixelFormat output_format = ist->hwaccel_output_format;
+ enum AVPixelFormat output_format = dp->hwaccel_output_format;
int err;
if (input->format == output_format) {
@@ -746,8 +749,7 @@ finish:
static enum AVPixelFormat get_format(AVCodecContext *s, const enum AVPixelFormat *pix_fmts)
{
- InputStream *ist = s->opaque;
- DecoderPriv *dp = dp_from_dec(ist->decoder);
+ DecoderPriv *dp = s->opaque;
const enum AVPixelFormat *p;
for (p = pix_fmts; *p != AV_PIX_FMT_NONE; p++) {
@@ -758,8 +760,8 @@ static enum AVPixelFormat get_format(AVCodecContext *s, const enum AVPixelFormat
if (!(desc->flags & AV_PIX_FMT_FLAG_HWACCEL))
break;
- if (ist->hwaccel_id == HWACCEL_GENERIC ||
- ist->hwaccel_id == HWACCEL_AUTO) {
+ if (dp->hwaccel_id == HWACCEL_GENERIC ||
+ dp->hwaccel_id == HWACCEL_AUTO) {
for (i = 0;; i++) {
config = avcodec_get_hw_config(s->codec, i);
if (!config)
@@ -771,7 +773,7 @@ static enum AVPixelFormat get_format(AVCodecContext *s, const enum AVPixelFormat
break;
}
}
- if (config && config->device_type == ist->hwaccel_device_type) {
+ if (config && config->device_type == dp->hwaccel_device_type) {
dp->hwaccel_pix_fmt = *p;
break;
}
@@ -797,21 +799,22 @@ static HWDevice *hw_device_match_by_codec(const AVCodec *codec)
}
}
-static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp)
+static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp,
+ const char *hwaccel_device)
{
const AVCodecHWConfig *config;
enum AVHWDeviceType type;
HWDevice *dev = NULL;
int err, auto_device = 0;
- if (ist->hwaccel_device) {
- dev = hw_device_get_by_name(ist->hwaccel_device);
+ if (hwaccel_device) {
+ dev = hw_device_get_by_name(hwaccel_device);
if (!dev) {
- if (ist->hwaccel_id == HWACCEL_AUTO) {
+ if (dp->hwaccel_id == HWACCEL_AUTO) {
auto_device = 1;
- } else if (ist->hwaccel_id == HWACCEL_GENERIC) {
- type = ist->hwaccel_device_type;
- err = hw_device_init_from_type(type, ist->hwaccel_device,
+ } else if (dp->hwaccel_id == HWACCEL_GENERIC) {
+ type = dp->hwaccel_device_type;
+ err = hw_device_init_from_type(type, hwaccel_device,
&dev);
} else {
// This will be dealt with by API-specific initialisation
@@ -819,22 +822,22 @@ static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp)
return 0;
}
} else {
- if (ist->hwaccel_id == HWACCEL_AUTO) {
- ist->hwaccel_device_type = dev->type;
- } else if (ist->hwaccel_device_type != dev->type) {
+ if (dp->hwaccel_id == HWACCEL_AUTO) {
+ dp->hwaccel_device_type = dev->type;
+ } else if (dp->hwaccel_device_type != dev->type) {
av_log(dp, AV_LOG_ERROR, "Invalid hwaccel device "
"specified for decoder: device %s of type %s is not "
"usable with hwaccel %s.\n", dev->name,
av_hwdevice_get_type_name(dev->type),
- av_hwdevice_get_type_name(ist->hwaccel_device_type));
+ av_hwdevice_get_type_name(dp->hwaccel_device_type));
return AVERROR(EINVAL);
}
}
} else {
- if (ist->hwaccel_id == HWACCEL_AUTO) {
+ if (dp->hwaccel_id == HWACCEL_AUTO) {
auto_device = 1;
- } else if (ist->hwaccel_id == HWACCEL_GENERIC) {
- type = ist->hwaccel_device_type;
+ } else if (dp->hwaccel_id == HWACCEL_GENERIC) {
+ type = dp->hwaccel_device_type;
dev = hw_device_get_by_type(type);
// When "-qsv_device device" is used, an internal QSV device named
@@ -884,17 +887,17 @@ static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp)
break;
type = config->device_type;
// Try to make a new device of this type.
- err = hw_device_init_from_type(type, ist->hwaccel_device,
+ err = hw_device_init_from_type(type, hwaccel_device,
&dev);
if (err < 0) {
// Can't make a device of this type.
continue;
}
- if (ist->hwaccel_device) {
+ if (hwaccel_device) {
av_log(dp, AV_LOG_INFO, "Using auto "
"hwaccel type %s with new device created "
"from %s.\n", av_hwdevice_get_type_name(type),
- ist->hwaccel_device);
+ hwaccel_device);
} else {
av_log(dp, AV_LOG_INFO, "Using auto "
"hwaccel type %s with new default device.\n",
@@ -902,11 +905,11 @@ static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp)
}
}
if (dev) {
- ist->hwaccel_device_type = type;
+ dp->hwaccel_device_type = type;
} else {
av_log(dp, AV_LOG_INFO, "Auto hwaccel "
"disabled: no device found.\n");
- ist->hwaccel_id = HWACCEL_NONE;
+ dp->hwaccel_id = HWACCEL_NONE;
return 0;
}
}
@@ -940,7 +943,7 @@ static const AVClass dec_class = {
};
int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
- AVDictionary **dec_opts, int flags)
+ AVDictionary **dec_opts, int flags, const DecoderOpts *o)
{
DecoderPriv *dp;
const AVCodec *codec = ist->dec;
@@ -958,6 +961,10 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
dp->dec.class = &dec_class;
dp->log_parent = ist;
+ dp->hwaccel_id = o->hwaccel_id;
+ dp->hwaccel_device_type = o->hwaccel_device_type;
+ dp->hwaccel_output_format = o->hwaccel_output_format;
+
snprintf(dp->log_name, sizeof(dp->log_name), "dec:%s", codec->name);
if (codec->type == AVMEDIA_TYPE_SUBTITLE &&
@@ -984,7 +991,7 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
return ret;
}
- dp->dec_ctx->opaque = ist;
+ dp->dec_ctx->opaque = dp;
dp->dec_ctx->get_format = get_format;
if (dp->dec_ctx->codec_id == AV_CODEC_ID_DVB_SUBTITLE &&
@@ -1005,7 +1012,7 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
av_dict_set(dec_opts, "flags", "+copy_opaque", AV_DICT_MULTIKEY);
- ret = hw_device_setup_for_decode(ist, dp);
+ ret = hw_device_setup_for_decode(ist, dp, o->hwaccel_device);
if (ret < 0) {
av_log(dp, AV_LOG_ERROR,
"Hardware device setup failed for decoder: %s\n",
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 729d7e476b..0f426e3c2e 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -72,6 +72,8 @@ typedef struct DemuxStream {
const AVCodecDescriptor *codec_desc;
+ DecoderOpts dec_opts;
+
AVBSFContext *bsf;
/* number of packets successfully read for this stream */
@@ -823,7 +825,7 @@ static void ist_free(InputStream **pist)
av_dict_free(&ist->decoder_opts);
av_freep(&ist->filters);
av_freep(&ist->outputs);
- av_freep(&ist->hwaccel_device);
+ av_freep(&ds->dec_opts.hwaccel_device);
avcodec_parameters_free(&ist->par);
@@ -905,7 +907,7 @@ static int ist_use(InputStream *ist, int decoding_needed)
return ret;
ret = dec_open(ist, d->sch, ds->sch_idx_dec,
- &ist->decoder_opts, dec_flags);
+ &ist->decoder_opts, dec_flags, &ds->dec_opts);
if (ret < 0)
return ret;
@@ -1166,25 +1168,25 @@ static int ist_add(const OptionsContext *o, Demuxer *d, AVStream *st)
"WARNING: defaulting hwaccel_output_format to cuda for compatibility "
"with old commandlines. This behaviour is DEPRECATED and will be removed "
"in the future. Please explicitly set \"-hwaccel_output_format cuda\".\n");
- ist->hwaccel_output_format = AV_PIX_FMT_CUDA;
+ ds->dec_opts.hwaccel_output_format = AV_PIX_FMT_CUDA;
} else if (!hwaccel_output_format && hwaccel && !strcmp(hwaccel, "qsv")) {
av_log(ist, 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;
+ ds->dec_opts.hwaccel_output_format = AV_PIX_FMT_QSV;
} else if (!hwaccel_output_format && hwaccel && !strcmp(hwaccel, "mediacodec")) {
// There is no real AVHWFrameContext implementation. Set
// hwaccel_output_format to avoid av_hwframe_transfer_data error.
- ist->hwaccel_output_format = AV_PIX_FMT_MEDIACODEC;
+ ds->dec_opts.hwaccel_output_format = AV_PIX_FMT_MEDIACODEC;
} else if (hwaccel_output_format) {
- ist->hwaccel_output_format = av_get_pix_fmt(hwaccel_output_format);
- if (ist->hwaccel_output_format == AV_PIX_FMT_NONE) {
+ ds->dec_opts.hwaccel_output_format = av_get_pix_fmt(hwaccel_output_format);
+ if (ds->dec_opts.hwaccel_output_format == AV_PIX_FMT_NONE) {
av_log(ist, AV_LOG_FATAL, "Unrecognised hwaccel output "
"format: %s", hwaccel_output_format);
}
} else {
- ist->hwaccel_output_format = AV_PIX_FMT_NONE;
+ ds->dec_opts.hwaccel_output_format = AV_PIX_FMT_NONE;
}
if (hwaccel) {
@@ -1193,17 +1195,17 @@ static int ist_add(const OptionsContext *o, Demuxer *d, AVStream *st)
hwaccel = "cuda";
if (!strcmp(hwaccel, "none"))
- ist->hwaccel_id = HWACCEL_NONE;
+ ds->dec_opts.hwaccel_id = HWACCEL_NONE;
else if (!strcmp(hwaccel, "auto"))
- ist->hwaccel_id = HWACCEL_AUTO;
+ ds->dec_opts.hwaccel_id = HWACCEL_AUTO;
else {
enum AVHWDeviceType type = av_hwdevice_find_type_by_name(hwaccel);
if (type != AV_HWDEVICE_TYPE_NONE) {
- ist->hwaccel_id = HWACCEL_GENERIC;
- ist->hwaccel_device_type = type;
+ ds->dec_opts.hwaccel_id = HWACCEL_GENERIC;
+ ds->dec_opts.hwaccel_device_type = type;
}
- if (!ist->hwaccel_id) {
+ if (!ds->dec_opts.hwaccel_id) {
av_log(ist, AV_LOG_FATAL, "Unrecognized hwaccel: %s.\n",
hwaccel);
av_log(ist, AV_LOG_FATAL, "Supported hwaccels: ");
@@ -1220,14 +1222,14 @@ static int ist_add(const OptionsContext *o, Demuxer *d, AVStream *st)
MATCH_PER_STREAM_OPT(hwaccel_devices, str, hwaccel_device, ic, st);
if (hwaccel_device) {
- ist->hwaccel_device = av_strdup(hwaccel_device);
- if (!ist->hwaccel_device)
+ ds->dec_opts.hwaccel_device = av_strdup(hwaccel_device);
+ if (!ds->dec_opts.hwaccel_device)
return AVERROR(ENOMEM);
}
}
- ret = choose_decoder(o, ic, st, ist->hwaccel_id, ist->hwaccel_device_type,
- &ist->dec);
+ ret = choose_decoder(o, ic, st, ds->dec_opts.hwaccel_id,
+ ds->dec_opts.hwaccel_device_type, &ist->dec);
if (ret < 0)
return ret;
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 17/31] fftools/ffmpeg_dec: move flags to DecoderOpts
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (14 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 16/31] fftools/ffmpeg_dec: pass hwaccel options to the decoder in a separate struct Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 18/31] fftools/ffmpeg_dec: pass forced/estimated framerate though DecoderOpts Anton Khirnov
` (13 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Will be useful in the following commit.
---
fftools/ffmpeg.h | 4 +++-
fftools/ffmpeg_dec.c | 4 ++--
fftools/ffmpeg_demux.c | 7 ++++---
3 files changed, 9 insertions(+), 6 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index abf95f106b..b4288e7352 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -287,6 +287,8 @@ enum DecoderFlags {
};
typedef struct DecoderOpts {
+ int flags;
+
/* hwaccel options */
enum HWAccelID hwaccel_id;
enum AVHWDeviceType hwaccel_device_type;
@@ -738,7 +740,7 @@ AVBufferRef *hw_device_for_filter(void);
* is transferred to the decoder.
*/
int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
- AVDictionary **dec_opts, int flags, const DecoderOpts *o);
+ AVDictionary **dec_opts, const DecoderOpts *o);
void dec_free(Decoder **pdec);
int dec_add_filter(Decoder *dec, InputFilter *ifilter);
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index 0cbe16ea5f..babfeb1b96 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -943,7 +943,7 @@ static const AVClass dec_class = {
};
int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
- AVDictionary **dec_opts, int flags, const DecoderOpts *o)
+ AVDictionary **dec_opts, const DecoderOpts *o)
{
DecoderPriv *dp;
const AVCodec *codec = ist->dec;
@@ -957,7 +957,7 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
dp->sch = sch;
dp->sch_idx = sch_idx;
- dp->flags = flags;
+ dp->flags = o->flags;
dp->dec.class = &dec_class;
dp->log_parent = ist;
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 0f426e3c2e..5ee07f706b 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -893,8 +893,6 @@ static int ist_use(InputStream *ist, int decoding_needed)
if (decoding_needed && ds->sch_idx_dec < 0) {
int is_audio = ist->st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO;
- int dec_flags = (!!ist->fix_sub_duration * DECODER_FLAG_FIX_SUB_DURATION) |
- (!!(d->f.ctx->iformat->flags & AVFMT_NOTIMESTAMPS) * DECODER_FLAG_TS_UNRELIABLE);
ret = sch_add_dec(d->sch, decoder_thread, ist, d->loop && is_audio);
if (ret < 0)
@@ -906,8 +904,11 @@ static int ist_use(InputStream *ist, int decoding_needed)
if (ret < 0)
return ret;
+ ds->dec_opts.flags = (!!ist->fix_sub_duration * DECODER_FLAG_FIX_SUB_DURATION) |
+ (!!(d->f.ctx->iformat->flags & AVFMT_NOTIMESTAMPS) * DECODER_FLAG_TS_UNRELIABLE);
+
ret = dec_open(ist, d->sch, ds->sch_idx_dec,
- &ist->decoder_opts, dec_flags, &ds->dec_opts);
+ &ist->decoder_opts, &ds->dec_opts);
if (ret < 0)
return ret;
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 18/31] fftools/ffmpeg_dec: pass forced/estimated framerate though DecoderOpts
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (15 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 17/31] fftools/ffmpeg_dec: move flags to DecoderOpts Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 19/31] fftools/ffmpeg_dec: move setting compute_edt to demuxer Anton Khirnov
` (12 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Stop reading them from InputStream.
This is a step towards decoupling Decoder and InputStream.
---
fftools/ffmpeg.h | 7 +++++++
fftools/ffmpeg_dec.c | 15 ++++++++++-----
fftools/ffmpeg_demux.c | 6 ++++++
3 files changed, 23 insertions(+), 5 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index b4288e7352..106f943a2b 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -284,6 +284,9 @@ enum DecoderFlags {
DECODER_FLAG_FIX_SUB_DURATION = (1 << 0),
// input timestamps are unreliable (guessed by demuxer)
DECODER_FLAG_TS_UNRELIABLE = (1 << 1),
+ // decoder should override timestamps by fixed framerate
+ // from DecoderOpts.framerate
+ DECODER_FLAG_FRAMERATE_FORCED = (1 << 2),
};
typedef struct DecoderOpts {
@@ -294,6 +297,10 @@ typedef struct DecoderOpts {
enum AVHWDeviceType hwaccel_device_type;
char *hwaccel_device;
enum AVPixelFormat hwaccel_output_format;
+
+ // Either forced (when DECODER_FLAG_FRAMERATE_FORCED is set) or
+ // estimated (otherwise) video framerate.
+ AVRational framerate;
} DecoderOpts;
typedef struct Decoder {
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index babfeb1b96..937e969988 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -45,6 +45,8 @@ typedef struct DecoderPriv {
// override output video sample aspect ratio with this value
AVRational sar_override;
+ AVRational framerate_in;
+
// a combination of DECODER_FLAG_*, provided to dec_open()
int flags;
@@ -220,6 +222,7 @@ static int64_t video_duration_estimate(const InputStream *ist, const AVFrame *fr
{
const DecoderPriv *dp = dp_from_dec(ist->decoder);
const int ts_unreliable = dp->flags & DECODER_FLAG_TS_UNRELIABLE;
+ const int fr_forced = dp->flags & DECODER_FLAG_FRAMERATE_FORCED;
int64_t codec_duration = 0;
// XXX lavf currently makes up frame durations when they are not provided by
@@ -229,7 +232,7 @@ static int64_t video_duration_estimate(const InputStream *ist, const AVFrame *fr
// durations, then this should be simplified.
// prefer frame duration for containers with timestamps
- if (frame->duration > 0 && (!ts_unreliable || ist->framerate.num))
+ if (frame->duration > 0 && (!ts_unreliable || fr_forced))
return frame->duration;
if (dp->dec_ctx->framerate.den && dp->dec_ctx->framerate.num) {
@@ -257,8 +260,8 @@ static int64_t video_duration_estimate(const InputStream *ist, const AVFrame *fr
return codec_duration;
// try average framerate
- if (ist->st->avg_frame_rate.num && ist->st->avg_frame_rate.den) {
- int64_t d = av_rescale_q(1, av_inv_q(ist->st->avg_frame_rate),
+ if (dp->framerate_in.num && dp->framerate_in.den) {
+ int64_t d = av_rescale_q(1, av_inv_q(dp->framerate_in),
frame->time_base);
if (d > 0)
return d;
@@ -330,10 +333,10 @@ static int video_frame_process(InputStream *ist, AVFrame *frame)
frame->pts = frame->best_effort_timestamp;
// forced fixed framerate
- if (ist->framerate.num) {
+ if (dp->flags & DECODER_FLAG_FRAMERATE_FORCED) {
frame->pts = AV_NOPTS_VALUE;
frame->duration = 1;
- frame->time_base = av_inv_q(ist->framerate);
+ frame->time_base = av_inv_q(dp->framerate_in);
}
// no timestamp available - extrapolate from previous frame duration
@@ -961,6 +964,8 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
dp->dec.class = &dec_class;
dp->log_parent = ist;
+ dp->framerate_in = o->framerate;
+
dp->hwaccel_id = o->hwaccel_id;
dp->hwaccel_device_type = o->hwaccel_device_type;
dp->hwaccel_output_format = o->hwaccel_output_format;
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 5ee07f706b..2a34f97545 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -907,6 +907,12 @@ static int ist_use(InputStream *ist, int decoding_needed)
ds->dec_opts.flags = (!!ist->fix_sub_duration * DECODER_FLAG_FIX_SUB_DURATION) |
(!!(d->f.ctx->iformat->flags & AVFMT_NOTIMESTAMPS) * DECODER_FLAG_TS_UNRELIABLE);
+ if (ist->framerate.num) {
+ ds->dec_opts.flags |= DECODER_FLAG_FRAMERATE_FORCED;
+ ds->dec_opts.framerate = ist->framerate;
+ } else
+ ds->dec_opts.framerate = ist->st->avg_frame_rate;
+
ret = dec_open(ist, d->sch, ds->sch_idx_dec,
&ist->decoder_opts, &ds->dec_opts);
if (ret < 0)
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 19/31] fftools/ffmpeg_dec: move setting compute_edt to demuxer
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (16 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 18/31] fftools/ffmpeg_dec: pass forced/estimated framerate though DecoderOpts Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 20/31] fftools/ffmpeg_dec: pass input timebase through DecoderOpts Anton Khirnov
` (11 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
It is done based on demuxer information, so that is the more appropriate
place for this code.
This is a step towards decoupling Decoder and InputStream.
---
fftools/ffmpeg_dec.c | 9 ---------
fftools/ffmpeg_demux.c | 9 +++++++++
2 files changed, 9 insertions(+), 9 deletions(-)
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index 937e969988..46eac025a3 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -999,15 +999,6 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
dp->dec_ctx->opaque = dp;
dp->dec_ctx->get_format = get_format;
- if (dp->dec_ctx->codec_id == AV_CODEC_ID_DVB_SUBTITLE &&
- (ist->decoding_needed & DECODING_FOR_OST)) {
- av_dict_set(dec_opts, "compute_edt", "1", AV_DICT_DONT_OVERWRITE);
- if (ist->decoding_needed & DECODING_FOR_FILTER)
- av_log(dp, AV_LOG_WARNING,
- "Warning using DVB subtitles for filtering and output at the "
- "same time is not fully supported, also see -compute_edt [0|1]\n");
- }
-
/* Useful for subtitles retiming by lavf (FIXME), skipping samples in
* audio, and video decoders such as cuvid or mediacodec */
dp->dec_ctx->pkt_timebase = ist->st->time_base;
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 2a34f97545..7cb85c127a 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -913,6 +913,15 @@ static int ist_use(InputStream *ist, int decoding_needed)
} else
ds->dec_opts.framerate = ist->st->avg_frame_rate;
+ if (ist->dec->id == AV_CODEC_ID_DVB_SUBTITLE &&
+ (ist->decoding_needed & DECODING_FOR_OST)) {
+ av_dict_set(&ist->decoder_opts, "compute_edt", "1", AV_DICT_DONT_OVERWRITE);
+ if (ist->decoding_needed & DECODING_FOR_FILTER)
+ av_log(ist, AV_LOG_WARNING,
+ "Warning using DVB subtitles for filtering and output at the "
+ "same time is not fully supported, also see -compute_edt [0|1]\n");
+ }
+
ret = dec_open(ist, d->sch, ds->sch_idx_dec,
&ist->decoder_opts, &ds->dec_opts);
if (ret < 0)
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 20/31] fftools/ffmpeg_dec: pass input timebase through DecoderOpts
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (17 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 19/31] fftools/ffmpeg_dec: move setting compute_edt to demuxer Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 21/31] fftools/ffmpeg_dec: pass top_field_first " Anton Khirnov
` (10 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Do not read it from AVStream directly.
This is a step towards decoupling Decoder and InputStream.
---
fftools/ffmpeg.h | 2 ++
fftools/ffmpeg_dec.c | 5 +----
fftools/ffmpeg_demux.c | 2 ++
3 files changed, 5 insertions(+), 4 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index 106f943a2b..5d6a538aa0 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -298,6 +298,8 @@ typedef struct DecoderOpts {
char *hwaccel_device;
enum AVPixelFormat hwaccel_output_format;
+ AVRational time_base;
+
// Either forced (when DECODER_FLAG_FRAMERATE_FORCED is set) or
// estimated (otherwise) video framerate.
AVRational framerate;
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index 46eac025a3..4a2ea83f97 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -998,10 +998,7 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
dp->dec_ctx->opaque = dp;
dp->dec_ctx->get_format = get_format;
-
- /* Useful for subtitles retiming by lavf (FIXME), skipping samples in
- * audio, and video decoders such as cuvid or mediacodec */
- dp->dec_ctx->pkt_timebase = ist->st->time_base;
+ dp->dec_ctx->pkt_timebase = o->time_base;
if (!av_dict_get(*dec_opts, "threads", NULL, 0))
av_dict_set(dec_opts, "threads", "auto", 0);
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 7cb85c127a..4cced4a7f8 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -1152,6 +1152,8 @@ static int ist_add(const OptionsContext *o, Demuxer *d, AVStream *st)
ds->first_dts = AV_NOPTS_VALUE;
ds->next_dts = AV_NOPTS_VALUE;
+ ds->dec_opts.time_base = st->time_base;
+
ds->ts_scale = 1.0;
MATCH_PER_STREAM_OPT(ts_scale, dbl, ds->ts_scale, ic, st);
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 21/31] fftools/ffmpeg_dec: pass top_field_first through DecoderOpts
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (18 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 20/31] fftools/ffmpeg_dec: pass input timebase through DecoderOpts Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 22/31] fftools/ffmpeg_dec: pass decoder name " Anton Khirnov
` (9 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Do not read it from InputStream directly.
This is a step towards decoupling Decoder and InputStream.
---
fftools/ffmpeg.h | 3 +++
fftools/ffmpeg_dec.c | 2 +-
fftools/ffmpeg_demux.c | 6 +++++-
3 files changed, 9 insertions(+), 2 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index 5d6a538aa0..9add5cac85 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -287,6 +287,9 @@ enum DecoderFlags {
// decoder should override timestamps by fixed framerate
// from DecoderOpts.framerate
DECODER_FLAG_FRAMERATE_FORCED = (1 << 2),
+#if FFMPEG_OPT_TOP
+ DECODER_FLAG_TOP_FIELD_FIRST = (1 << 3),
+#endif
};
typedef struct DecoderOpts {
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index 4a2ea83f97..e34b23b40c 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -318,7 +318,7 @@ static int video_frame_process(InputStream *ist, AVFrame *frame)
DecoderPriv *dp = dp_from_dec(ist->decoder);
#if FFMPEG_OPT_TOP
- if(ist->top_field_first>=0) {
+ if (dp->flags & DECODER_FLAG_TOP_FIELD_FIRST) {
av_log(dp, AV_LOG_WARNING, "-top is deprecated, use the setfield filter instead\n");
frame->flags |= AV_FRAME_FLAG_TOP_FIELD_FIRST;
}
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 4cced4a7f8..3c3be214c5 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -905,7 +905,11 @@ static int ist_use(InputStream *ist, int decoding_needed)
return ret;
ds->dec_opts.flags = (!!ist->fix_sub_duration * DECODER_FLAG_FIX_SUB_DURATION) |
- (!!(d->f.ctx->iformat->flags & AVFMT_NOTIMESTAMPS) * DECODER_FLAG_TS_UNRELIABLE);
+ (!!(d->f.ctx->iformat->flags & AVFMT_NOTIMESTAMPS) * DECODER_FLAG_TS_UNRELIABLE)
+#if FFMPEG_OPT_TOP
+ | ((ist->top_field_first >= 0) * DECODER_FLAG_TOP_FIELD_FIRST)
+#endif
+ ;
if (ist->framerate.num) {
ds->dec_opts.flags |= DECODER_FLAG_FRAMERATE_FORCED;
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 22/31] fftools/ffmpeg_dec: pass decoder name through DecoderOpts
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (19 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 21/31] fftools/ffmpeg_dec: pass top_field_first " Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 23/31] fftools/ffmpeg_dec: eliminate InputStream use in hw_device_setup_for_decode() Anton Khirnov
` (8 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Do not build it from InputStream values.
This is a step towards decoupling Decoder and InputStream.
---
fftools/ffmpeg.h | 2 ++
fftools/ffmpeg_dec.c | 17 +++++++++++------
fftools/ffmpeg_demux.c | 4 ++++
3 files changed, 17 insertions(+), 6 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index 9add5cac85..bdfacf16b7 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -295,6 +295,8 @@ enum DecoderFlags {
typedef struct DecoderOpts {
int flags;
+ char *name;
+
/* hwaccel options */
enum HWAccelID hwaccel_id;
enum AVHWDeviceType hwaccel_device_type;
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index e34b23b40c..6c8f08d33e 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -73,6 +73,7 @@ typedef struct DecoderPriv {
void *log_parent;
char log_name[32];
+ char *parent_name;
} DecoderPriv;
static DecoderPriv *dp_from_dec(Decoder *d)
@@ -104,6 +105,8 @@ void dec_free(Decoder **pdec)
av_frame_free(&dp->sub_prev[i]);
av_frame_free(&dp->sub_heartbeat);
+ av_freep(&dp->parent_name);
+
av_freep(pdec);
}
@@ -499,7 +502,6 @@ static int transcode_subtitles(InputStream *ist, const AVPacket *pkt,
static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
{
- const InputFile *ifile = ist->file;
DecoderPriv *dp = dp_from_dec(ist->decoder);
AVCodecContext *dec = dp->dec_ctx;
const char *type_desc = av_get_media_type_string(dec->codec_type);
@@ -554,8 +556,7 @@ static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
update_benchmark(NULL);
ret = avcodec_receive_frame(dec, frame);
- update_benchmark("decode_%s %d.%d", type_desc,
- ifile->index, ist->index);
+ update_benchmark("decode_%s %s", type_desc, dp->parent_name);
if (ret == AVERROR(EAGAIN)) {
av_assert0(pkt); // should never happen during flushing
@@ -616,10 +617,10 @@ static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
}
}
-static void dec_thread_set_name(const InputStream *ist, const DecoderPriv *dp)
+static void dec_thread_set_name(const DecoderPriv *dp)
{
char name[16];
- snprintf(name, sizeof(name), "dec%d:%d:%s", ist->file->index, ist->index,
+ snprintf(name, sizeof(name), "dec%s:%s", dp->parent_name,
dp->dec_ctx->codec->name);
ff_thread_setname(name);
}
@@ -662,7 +663,7 @@ void *decoder_thread(void *arg)
if (ret < 0)
goto finish;
- dec_thread_set_name(ist, dp);
+ dec_thread_set_name(dp);
while (!input_status) {
int flush_buffers, have_data;
@@ -972,6 +973,10 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
snprintf(dp->log_name, sizeof(dp->log_name), "dec:%s", codec->name);
+ dp->parent_name = av_strdup(o->name ? o->name : "");
+ if (!dp->parent_name)
+ return AVERROR(ENOMEM);
+
if (codec->type == AVMEDIA_TYPE_SUBTITLE &&
(dp->flags & DECODER_FLAG_FIX_SUB_DURATION)) {
for (int i = 0; i < FF_ARRAY_ELEMS(dp->sub_prev); i++) {
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 3c3be214c5..8bc73e2bf3 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -73,6 +73,7 @@ typedef struct DemuxStream {
const AVCodecDescriptor *codec_desc;
DecoderOpts dec_opts;
+ char dec_name[16];
AVBSFContext *bsf;
@@ -926,6 +927,9 @@ static int ist_use(InputStream *ist, int decoding_needed)
"same time is not fully supported, also see -compute_edt [0|1]\n");
}
+ snprintf(ds->dec_name, sizeof(ds->dec_name), "%d:%d", ist->file->index, ist->index);
+ ds->dec_opts.name = ds->dec_name;
+
ret = dec_open(ist, d->sch, ds->sch_idx_dec,
&ist->decoder_opts, &ds->dec_opts);
if (ret < 0)
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 23/31] fftools/ffmpeg_dec: eliminate InputStream use in hw_device_setup_for_decode()
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (20 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 22/31] fftools/ffmpeg_dec: pass decoder name " Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 24/31] fftools/ffmpeg_dec: pass AVCodec through DecoderOpts Anton Khirnov
` (7 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
The same information can also be obtained from the decoder itself.
This is a step towards decoupling Decoder and InputStream.
---
fftools/ffmpeg_dec.c | 15 ++++++++-------
1 file changed, 8 insertions(+), 7 deletions(-)
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index 6c8f08d33e..ba261f4912 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -803,7 +803,8 @@ static HWDevice *hw_device_match_by_codec(const AVCodec *codec)
}
}
-static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp,
+static int hw_device_setup_for_decode(DecoderPriv *dp,
+ const AVCodec *codec,
const char *hwaccel_device)
{
const AVCodecHWConfig *config;
@@ -858,7 +859,7 @@ static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp,
if (!dev)
err = hw_device_init_from_type(type, NULL, &dev);
} else {
- dev = hw_device_match_by_codec(ist->dec);
+ dev = hw_device_match_by_codec(codec);
if (!dev) {
// No device for this codec, but not using generic hwaccel
// and therefore may well not need one - ignore.
@@ -869,12 +870,12 @@ static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp,
if (auto_device) {
int i;
- if (!avcodec_get_hw_config(ist->dec, 0)) {
+ if (!avcodec_get_hw_config(codec, 0)) {
// Decoder does not support any hardware devices.
return 0;
}
for (i = 0; !dev; i++) {
- config = avcodec_get_hw_config(ist->dec, i);
+ config = avcodec_get_hw_config(codec, i);
if (!config)
break;
type = config->device_type;
@@ -886,7 +887,7 @@ static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp,
}
}
for (i = 0; !dev; i++) {
- config = avcodec_get_hw_config(ist->dec, i);
+ config = avcodec_get_hw_config(codec, i);
if (!config)
break;
type = config->device_type;
@@ -921,7 +922,7 @@ static int hw_device_setup_for_decode(InputStream *ist, DecoderPriv *dp,
if (!dev) {
av_log(dp, AV_LOG_ERROR, "No device available "
"for decoder: device type %s needed for codec %s.\n",
- av_hwdevice_get_type_name(type), ist->dec->name);
+ av_hwdevice_get_type_name(type), codec->name);
return err;
}
@@ -1010,7 +1011,7 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
av_dict_set(dec_opts, "flags", "+copy_opaque", AV_DICT_MULTIKEY);
- ret = hw_device_setup_for_decode(ist, dp, o->hwaccel_device);
+ ret = hw_device_setup_for_decode(dp, codec, o->hwaccel_device);
if (ret < 0) {
av_log(dp, AV_LOG_ERROR,
"Hardware device setup failed for decoder: %s\n",
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 24/31] fftools/ffmpeg_dec: pass AVCodec through DecoderOpts
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (21 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 23/31] fftools/ffmpeg_dec: eliminate InputStream use in hw_device_setup_for_decode() Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 25/31] fftools/ffmpeg_dec: pass AVCodecParameters " Anton Khirnov
` (6 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Do not retrieve it from InputStream directly.
This is a step towards decoupling Decoder and InputStream.
---
fftools/ffmpeg.h | 2 ++
fftools/ffmpeg_dec.c | 2 +-
fftools/ffmpeg_demux.c | 2 ++
3 files changed, 5 insertions(+), 1 deletion(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index bdfacf16b7..b169b1a323 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -297,6 +297,8 @@ typedef struct DecoderOpts {
char *name;
+ const AVCodec *codec;
+
/* hwaccel options */
enum HWAccelID hwaccel_id;
enum AVHWDeviceType hwaccel_device_type;
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index ba261f4912..c64b9f5b70 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -951,7 +951,7 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
AVDictionary **dec_opts, const DecoderOpts *o)
{
DecoderPriv *dp;
- const AVCodec *codec = ist->dec;
+ const AVCodec *codec = o->codec;
int ret;
ret = dec_alloc(&ist->decoder);
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 8bc73e2bf3..f66319aafe 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -930,6 +930,8 @@ static int ist_use(InputStream *ist, int decoding_needed)
snprintf(ds->dec_name, sizeof(ds->dec_name), "%d:%d", ist->file->index, ist->index);
ds->dec_opts.name = ds->dec_name;
+ ds->dec_opts.codec = ist->dec;
+
ret = dec_open(ist, d->sch, ds->sch_idx_dec,
&ist->decoder_opts, &ds->dec_opts);
if (ret < 0)
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 25/31] fftools/ffmpeg_dec: pass AVCodecParameters through DecoderOpts
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (22 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 24/31] fftools/ffmpeg_dec: pass AVCodec through DecoderOpts Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 26/31] fftools/ffmpeg_dec: remove unnecessary InputStream arguments Anton Khirnov
` (5 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Do not retrieve it from InputStream directly.
This is a step towards decoupling Decoder and InputStream.
---
fftools/ffmpeg.h | 1 +
fftools/ffmpeg_dec.c | 4 ++--
fftools/ffmpeg_demux.c | 1 +
3 files changed, 4 insertions(+), 2 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index b169b1a323..02c614d0ff 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -298,6 +298,7 @@ typedef struct DecoderOpts {
char *name;
const AVCodec *codec;
+ const AVCodecParameters *par;
/* hwaccel options */
enum HWAccelID hwaccel_id;
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index c64b9f5b70..fd1c9ca609 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -990,13 +990,13 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
return AVERROR(ENOMEM);
}
- dp->sar_override = ist->par->sample_aspect_ratio;
+ dp->sar_override = o->par->sample_aspect_ratio;
dp->dec_ctx = avcodec_alloc_context3(codec);
if (!dp->dec_ctx)
return AVERROR(ENOMEM);
- ret = avcodec_parameters_to_context(dp->dec_ctx, ist->par);
+ ret = avcodec_parameters_to_context(dp->dec_ctx, o->par);
if (ret < 0) {
av_log(dp, AV_LOG_ERROR, "Error initializing the decoder context.\n");
return ret;
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index f66319aafe..6216b7c684 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -931,6 +931,7 @@ static int ist_use(InputStream *ist, int decoding_needed)
ds->dec_opts.name = ds->dec_name;
ds->dec_opts.codec = ist->dec;
+ ds->dec_opts.par = ist->par;
ret = dec_open(ist, d->sch, ds->sch_idx_dec,
&ist->decoder_opts, &ds->dec_opts);
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 26/31] fftools/ffmpeg_dec: remove unnecessary InputStream arguments
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (23 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 25/31] fftools/ffmpeg_dec: pass AVCodecParameters " Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 27/31] fftools/ffmpeg_dec: stop passing InputStream to dec_open() Anton Khirnov
` (4 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
---
fftools/ffmpeg_dec.c | 35 ++++++++++++++---------------------
1 file changed, 14 insertions(+), 21 deletions(-)
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index fd1c9ca609..98cde0a040 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -221,9 +221,8 @@ static void audio_ts_process(DecoderPriv *dp, AVFrame *frame)
frame->time_base = tb_filter;
}
-static int64_t video_duration_estimate(const InputStream *ist, const AVFrame *frame)
+static int64_t video_duration_estimate(const DecoderPriv *dp, const AVFrame *frame)
{
- const DecoderPriv *dp = dp_from_dec(ist->decoder);
const int ts_unreliable = dp->flags & DECODER_FLAG_TS_UNRELIABLE;
const int fr_forced = dp->flags & DECODER_FLAG_FRAMERATE_FORCED;
int64_t codec_duration = 0;
@@ -316,10 +315,8 @@ fail:
return err;
}
-static int video_frame_process(InputStream *ist, AVFrame *frame)
+static int video_frame_process(DecoderPriv *dp, AVFrame *frame)
{
- DecoderPriv *dp = dp_from_dec(ist->decoder);
-
#if FFMPEG_OPT_TOP
if (dp->flags & DECODER_FLAG_TOP_FIELD_FIRST) {
av_log(dp, AV_LOG_WARNING, "-top is deprecated, use the setfield filter instead\n");
@@ -348,7 +345,7 @@ static int video_frame_process(InputStream *ist, AVFrame *frame)
dp->last_frame_pts + dp->last_frame_duration_est;
// update timestamp history
- dp->last_frame_duration_est = video_duration_estimate(ist, frame);
+ dp->last_frame_duration_est = video_duration_estimate(dp, frame);
dp->last_frame_pts = frame->pts;
dp->last_frame_tb = frame->time_base;
@@ -374,9 +371,8 @@ static int video_frame_process(InputStream *ist, AVFrame *frame)
return 0;
}
-static int process_subtitle(InputStream *ist, AVFrame *frame)
+static int process_subtitle(DecoderPriv *dp, AVFrame *frame)
{
- DecoderPriv *dp = dp_from_dec(ist->decoder);
const AVSubtitle *subtitle = (AVSubtitle*)frame->buf[0]->data;
int ret = 0;
@@ -418,9 +414,8 @@ static int process_subtitle(InputStream *ist, AVFrame *frame)
return ret == AVERROR_EOF ? AVERROR_EXIT : ret;
}
-static int fix_sub_duration_heartbeat(InputStream *ist, int64_t signal_pts)
+static int fix_sub_duration_heartbeat(DecoderPriv *dp, int64_t signal_pts)
{
- DecoderPriv *dp = dp_from_dec(ist->decoder);
int ret = AVERROR_BUG;
AVSubtitle *prev_subtitle = dp->sub_prev[0]->buf[0] ?
(AVSubtitle*)dp->sub_prev[0]->buf[0]->data : NULL;
@@ -438,13 +433,12 @@ static int fix_sub_duration_heartbeat(InputStream *ist, int64_t signal_pts)
subtitle = (AVSubtitle*)dp->sub_heartbeat->buf[0]->data;
subtitle->pts = signal_pts;
- return process_subtitle(ist, dp->sub_heartbeat);
+ return process_subtitle(dp, dp->sub_heartbeat);
}
-static int transcode_subtitles(InputStream *ist, const AVPacket *pkt,
+static int transcode_subtitles(DecoderPriv *dp, const AVPacket *pkt,
AVFrame *frame)
{
- DecoderPriv *dp = dp_from_dec(ist->decoder);
AVPacket *flush_pkt = NULL;
AVSubtitle subtitle;
int got_output;
@@ -458,8 +452,8 @@ static int transcode_subtitles(InputStream *ist, const AVPacket *pkt,
ret = sch_dec_send(dp->sch, dp->sch_idx, frame);
return ret == AVERROR_EOF ? AVERROR_EXIT : ret;
} else if (pkt && (intptr_t)pkt->opaque == PKT_OPAQUE_FIX_SUB_DURATION) {
- return fix_sub_duration_heartbeat(ist, av_rescale_q(pkt->pts, pkt->time_base,
- AV_TIME_BASE_Q));
+ return fix_sub_duration_heartbeat(dp, av_rescale_q(pkt->pts, pkt->time_base,
+ AV_TIME_BASE_Q));
}
if (!pkt) {
@@ -497,18 +491,17 @@ static int transcode_subtitles(InputStream *ist, const AVPacket *pkt,
frame->width = dp->dec_ctx->width;
frame->height = dp->dec_ctx->height;
- return process_subtitle(ist, frame);
+ return process_subtitle(dp, frame);
}
-static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
+static int packet_decode(DecoderPriv *dp, AVPacket *pkt, AVFrame *frame)
{
- DecoderPriv *dp = dp_from_dec(ist->decoder);
AVCodecContext *dec = dp->dec_ctx;
const char *type_desc = av_get_media_type_string(dec->codec_type);
int ret;
if (dec->codec_type == AVMEDIA_TYPE_SUBTITLE)
- return transcode_subtitles(ist, pkt, frame);
+ return transcode_subtitles(dp, pkt, frame);
// With fate-indeo3-2, we're getting 0-sized packets before EOF for some
// reason. This seems like a semi-critical bug. Don't trigger EOF, and
@@ -599,7 +592,7 @@ static int packet_decode(InputStream *ist, AVPacket *pkt, AVFrame *frame)
audio_ts_process(dp, frame);
} else {
- ret = video_frame_process(ist, frame);
+ ret = video_frame_process(dp, frame);
if (ret < 0) {
av_log(dp, AV_LOG_FATAL,
"Error while processing the decoded data\n");
@@ -678,7 +671,7 @@ void *decoder_thread(void *arg)
av_log(dp, AV_LOG_VERBOSE, "Decoder thread received %s packet\n",
flush_buffers ? "flush" : "EOF");
- ret = packet_decode(ist, have_data ? dt.pkt : NULL, dt.frame);
+ ret = packet_decode(dp, have_data ? dt.pkt : NULL, dt.frame);
av_packet_unref(dt.pkt);
av_frame_unref(dt.frame);
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 27/31] fftools/ffmpeg_dec: stop passing InputStream to dec_open()
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (24 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 26/31] fftools/ffmpeg_dec: remove unnecessary InputStream arguments Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-25 1:19 ` Michael Niedermayer
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 28/31] fftools/ffmpeg_dec: eliminate all remaining InputStream uses Anton Khirnov
` (3 subsequent siblings)
29 siblings, 1 reply; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
---
fftools/ffmpeg.h | 3 ++-
fftools/ffmpeg_dec.c | 50 +++++++++++++++++++++++++++---------------
fftools/ffmpeg_demux.c | 4 +++-
3 files changed, 37 insertions(+), 20 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index 02c614d0ff..c8cba72006 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -296,6 +296,7 @@ typedef struct DecoderOpts {
int flags;
char *name;
+ void *log_parent;
const AVCodec *codec;
const AVCodecParameters *par;
@@ -756,7 +757,7 @@ AVBufferRef *hw_device_for_filter(void);
* @param dec_opts Dictionary filled with decoder options. Its ownership
* is transferred to the decoder.
*/
-int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
+int dec_open(Decoder **pdec, Scheduler *sch, unsigned sch_idx,
AVDictionary **dec_opts, const DecoderOpts *o);
void dec_free(Decoder **pdec);
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index 98cde0a040..3610256f31 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -110,7 +110,7 @@ void dec_free(Decoder **pdec)
av_freep(pdec);
}
-static int dec_alloc(Decoder **pdec)
+static int dec_alloc(DecoderPriv **pdec)
{
DecoderPriv *dp;
@@ -133,7 +133,7 @@ static int dec_alloc(Decoder **pdec)
dp->last_frame_tb = (AVRational){ 1, 1 };
dp->hwaccel_pix_fmt = AV_PIX_FMT_NONE;
- *pdec = &dp->dec;
+ *pdec = dp;
return 0;
fail:
@@ -940,24 +940,25 @@ static const AVClass dec_class = {
.item_name = dec_item_name,
};
-int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
+int dec_open(Decoder **pdec, Scheduler *sch, unsigned sch_idx,
AVDictionary **dec_opts, const DecoderOpts *o)
{
DecoderPriv *dp;
const AVCodec *codec = o->codec;
int ret;
- ret = dec_alloc(&ist->decoder);
+ *pdec = NULL;
+
+ ret = dec_alloc(&dp);
if (ret < 0)
return ret;
- dp = dp_from_dec(ist->decoder);
dp->sch = sch;
dp->sch_idx = sch_idx;
dp->flags = o->flags;
dp->dec.class = &dec_class;
- dp->log_parent = ist;
+ dp->log_parent = o->log_parent;
dp->framerate_in = o->framerate;
@@ -968,31 +969,39 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
snprintf(dp->log_name, sizeof(dp->log_name), "dec:%s", codec->name);
dp->parent_name = av_strdup(o->name ? o->name : "");
- if (!dp->parent_name)
- return AVERROR(ENOMEM);
+ if (!dp->parent_name) {
+ ret = AVERROR(ENOMEM);
+ goto fail;
+ }
if (codec->type == AVMEDIA_TYPE_SUBTITLE &&
(dp->flags & DECODER_FLAG_FIX_SUB_DURATION)) {
for (int i = 0; i < FF_ARRAY_ELEMS(dp->sub_prev); i++) {
dp->sub_prev[i] = av_frame_alloc();
- if (!dp->sub_prev[i])
- return AVERROR(ENOMEM);
+ if (!dp->sub_prev[i]) {
+ ret = AVERROR(ENOMEM);
+ goto fail;
+ }
}
dp->sub_heartbeat = av_frame_alloc();
- if (!dp->sub_heartbeat)
- return AVERROR(ENOMEM);
+ if (!dp->sub_heartbeat) {
+ ret = AVERROR(ENOMEM);
+ goto fail;
+ }
}
dp->sar_override = o->par->sample_aspect_ratio;
dp->dec_ctx = avcodec_alloc_context3(codec);
- if (!dp->dec_ctx)
- return AVERROR(ENOMEM);
+ if (!dp->dec_ctx) {
+ ret = AVERROR(ENOMEM);
+ goto fail;
+ }
ret = avcodec_parameters_to_context(dp->dec_ctx, o->par);
if (ret < 0) {
av_log(dp, AV_LOG_ERROR, "Error initializing the decoder context.\n");
- return ret;
+ goto fail;
}
dp->dec_ctx->opaque = dp;
@@ -1009,23 +1018,28 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
av_log(dp, AV_LOG_ERROR,
"Hardware device setup failed for decoder: %s\n",
av_err2str(ret));
- return ret;
+ goto fail;
}
if ((ret = avcodec_open2(dp->dec_ctx, codec, dec_opts)) < 0) {
av_log(dp, AV_LOG_ERROR, "Error while opening decoder: %s\n",
av_err2str(ret));
- return ret;
+ goto fail;
}
ret = check_avoptions(*dec_opts);
if (ret < 0)
- return ret;
+ goto fail;
dp->dec.subtitle_header = dp->dec_ctx->subtitle_header;
dp->dec.subtitle_header_size = dp->dec_ctx->subtitle_header_size;
+ *pdec = &dp->dec;
+
return 0;
+fail:
+ dec_free((Decoder**)dp);
+ return ret;
}
int dec_add_filter(Decoder *dec, InputFilter *ifilter)
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 6216b7c684..5178bcbce4 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -933,7 +933,9 @@ static int ist_use(InputStream *ist, int decoding_needed)
ds->dec_opts.codec = ist->dec;
ds->dec_opts.par = ist->par;
- ret = dec_open(ist, d->sch, ds->sch_idx_dec,
+ ds->dec_opts.log_parent = ist;
+
+ ret = dec_open(&ist->decoder, d->sch, ds->sch_idx_dec,
&ist->decoder_opts, &ds->dec_opts);
if (ret < 0)
return ret;
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* Re: [FFmpeg-devel] [PATCH 27/31] fftools/ffmpeg_dec: stop passing InputStream to dec_open()
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 27/31] fftools/ffmpeg_dec: stop passing InputStream to dec_open() Anton Khirnov
@ 2024-01-25 1:19 ` Michael Niedermayer
2024-01-28 9:40 ` [FFmpeg-devel] [PATCH v2 " Anton Khirnov
0 siblings, 1 reply; 34+ messages in thread
From: Michael Niedermayer @ 2024-01-25 1:19 UTC (permalink / raw)
To: FFmpeg development discussions and patches
[-- Attachment #1.1: Type: text/plain, Size: 4287 bytes --]
On Wed, Jan 24, 2024 at 09:16:57AM +0100, Anton Khirnov wrote:
> ---
> fftools/ffmpeg.h | 3 ++-
> fftools/ffmpeg_dec.c | 50 +++++++++++++++++++++++++++---------------
> fftools/ffmpeg_demux.c | 4 +++-
> 3 files changed, 37 insertions(+), 20 deletions(-)
This causes segfaults:
(ill mail you the sample)
Metadata:
creation_time : 1999-10-07T10:13:38.000000Z
Duration: 00:00:17.54, start: 0.000000, bitrate: 1980 kb/s
Stream #0:0[0x1](eng): Video: qtrle (rle / 0x20656C72), none, 310x280, 438202 kb/s, 25 fps, 25 tbr, 600 tbn (default)
Metadata:
creation_time : 1999-10-07T10:13:38.000000Z
handler_name : Apple Video Media Handler
vendor_id : appl
encoder : Animation
[qtrle @ 0x16a2bf40] Unsupported colorspace: 108 bits/sample?
==24457== at 0x13E0719: VALGRIND_PRINTF_BACKTRACE (valgrind.h:6303)
==24457== by 0x13E1318: av_log_default_callback (log.c:404)
==24457== by 0x13E15BF: av_vlog (log.c:439)
==24457== by 0x13E141E: av_log (log.c:418)
==24457== by 0xC7C031: qtrle_decode_init (qtrle.c:434)
==24457== by 0x88AF88: avcodec_open2 (avcodec.c:337)
==24457== by 0x2448EE: dec_open (ffmpeg_dec.c:1024)
==24457== by 0x2486D7: ist_use (ffmpeg_demux.c:938)
==24457== by 0x248835: ist_filter_add (ffmpeg_demux.c:973)
==24457== by 0x253BC5: ifilter_bind_ist (ffmpeg_filter.c:676)
==24457== by 0x254C21: init_simple_filtergraph (ffmpeg_filter.c:1072)
==24457== by 0x26ADAB: ost_add (ffmpeg_mux_init.c:1444)
==24457== by 0x26B491: map_auto_video (ffmpeg_mux_init.c:1550)
==24457== by 0x26C3A1: create_streams (ffmpeg_mux_init.c:1858)
==24457== by 0x270A6C: of_open (ffmpeg_mux_init.c:3091)
==24457== by 0x274D48: open_files (ffmpeg_opt.c:1333)
==24457== by 0x274F74: ffmpeg_parse_options (ffmpeg_opt.c:1387)
==24457== by 0x289391: main (ffmpeg.c:1032)
[vist#0:0/qtrle @ 0x16a25e80] [dec:qtrle @ 0x16a2b9c0] Error while opening decoder: Invalid data found when processing input
==24457== at 0x13E0719: VALGRIND_PRINTF_BACKTRACE (valgrind.h:6303)
==24457== by 0x13E1318: av_log_default_callback (log.c:404)
==24457== by 0x13E15BF: av_vlog (log.c:439)
==24457== by 0x13E141E: av_log (log.c:418)
==24457== by 0x24494E: dec_open (ffmpeg_dec.c:1025)
==24457== by 0x2486D7: ist_use (ffmpeg_demux.c:938)
==24457== by 0x248835: ist_filter_add (ffmpeg_demux.c:973)
==24457== by 0x253BC5: ifilter_bind_ist (ffmpeg_filter.c:676)
==24457== by 0x254C21: init_simple_filtergraph (ffmpeg_filter.c:1072)
==24457== by 0x26ADAB: ost_add (ffmpeg_mux_init.c:1444)
==24457== by 0x26B491: map_auto_video (ffmpeg_mux_init.c:1550)
==24457== by 0x26C3A1: create_streams (ffmpeg_mux_init.c:1858)
==24457== by 0x270A6C: of_open (ffmpeg_mux_init.c:3091)
==24457== by 0x274D48: open_files (ffmpeg_opt.c:1333)
==24457== by 0x274F74: ffmpeg_parse_options (ffmpeg_opt.c:1387)
==24457== by 0x289391: main (ffmpeg.c:1032)
==24457==
==24457== Process terminating with default action of signal 11 (SIGSEGV)
==24457== Bad permissions for mapped region at address 0x1B68D28
==24457== at 0x13E45C9: av_freep (mem.c:250)
==24457== by 0x241E09: dec_free (ffmpeg_dec.c:108)
==24457== by 0x2449D4: dec_open (ffmpeg_dec.c:1041)
==24457== by 0x2486D7: ist_use (ffmpeg_demux.c:938)
==24457== by 0x248835: ist_filter_add (ffmpeg_demux.c:973)
==24457== by 0x253BC5: ifilter_bind_ist (ffmpeg_filter.c:676)
==24457== by 0x254C21: init_simple_filtergraph (ffmpeg_filter.c:1072)
==24457== by 0x26ADAB: ost_add (ffmpeg_mux_init.c:1444)
==24457== by 0x26B491: map_auto_video (ffmpeg_mux_init.c:1550)
==24457== by 0x26C3A1: create_streams (ffmpeg_mux_init.c:1858)
==24457== by 0x270A6C: of_open (ffmpeg_mux_init.c:3091)
==24457== by 0x274D48: open_files (ffmpeg_opt.c:1333)
==24457== by 0x274F74: ffmpeg_parse_options (ffmpeg_opt.c:1387)
==24457== by 0x289391: main (ffmpeg.c:1032)
[...]
--
Michael GnuPG fingerprint: 9FF2128B147EF6730BADF133611EC787040B0FAB
Into a blind darkness they enter who follow after the Ignorance,
they as if into a greater darkness enter who devote themselves
to the Knowledge alone. -- Isha Upanishad
[-- Attachment #1.2: signature.asc --]
[-- Type: application/pgp-signature, Size: 195 bytes --]
[-- Attachment #2: Type: text/plain, Size: 251 bytes --]
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH v2 27/31] fftools/ffmpeg_dec: stop passing InputStream to dec_open()
2024-01-25 1:19 ` Michael Niedermayer
@ 2024-01-28 9:40 ` Anton Khirnov
0 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-28 9:40 UTC (permalink / raw)
To: ffmpeg-devel
---
fftools/ffmpeg.h | 3 ++-
fftools/ffmpeg_dec.c | 50 +++++++++++++++++++++++++++---------------
fftools/ffmpeg_demux.c | 4 +++-
3 files changed, 37 insertions(+), 20 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index 02c614d0ff..c8cba72006 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -296,6 +296,7 @@ typedef struct DecoderOpts {
int flags;
char *name;
+ void *log_parent;
const AVCodec *codec;
const AVCodecParameters *par;
@@ -756,7 +757,7 @@ AVBufferRef *hw_device_for_filter(void);
* @param dec_opts Dictionary filled with decoder options. Its ownership
* is transferred to the decoder.
*/
-int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
+int dec_open(Decoder **pdec, Scheduler *sch, unsigned sch_idx,
AVDictionary **dec_opts, const DecoderOpts *o);
void dec_free(Decoder **pdec);
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index 98cde0a040..0fde686eec 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -110,7 +110,7 @@ void dec_free(Decoder **pdec)
av_freep(pdec);
}
-static int dec_alloc(Decoder **pdec)
+static int dec_alloc(DecoderPriv **pdec)
{
DecoderPriv *dp;
@@ -133,7 +133,7 @@ static int dec_alloc(Decoder **pdec)
dp->last_frame_tb = (AVRational){ 1, 1 };
dp->hwaccel_pix_fmt = AV_PIX_FMT_NONE;
- *pdec = &dp->dec;
+ *pdec = dp;
return 0;
fail:
@@ -940,24 +940,25 @@ static const AVClass dec_class = {
.item_name = dec_item_name,
};
-int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
+int dec_open(Decoder **pdec, Scheduler *sch, unsigned sch_idx,
AVDictionary **dec_opts, const DecoderOpts *o)
{
DecoderPriv *dp;
const AVCodec *codec = o->codec;
int ret;
- ret = dec_alloc(&ist->decoder);
+ *pdec = NULL;
+
+ ret = dec_alloc(&dp);
if (ret < 0)
return ret;
- dp = dp_from_dec(ist->decoder);
dp->sch = sch;
dp->sch_idx = sch_idx;
dp->flags = o->flags;
dp->dec.class = &dec_class;
- dp->log_parent = ist;
+ dp->log_parent = o->log_parent;
dp->framerate_in = o->framerate;
@@ -968,31 +969,39 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
snprintf(dp->log_name, sizeof(dp->log_name), "dec:%s", codec->name);
dp->parent_name = av_strdup(o->name ? o->name : "");
- if (!dp->parent_name)
- return AVERROR(ENOMEM);
+ if (!dp->parent_name) {
+ ret = AVERROR(ENOMEM);
+ goto fail;
+ }
if (codec->type == AVMEDIA_TYPE_SUBTITLE &&
(dp->flags & DECODER_FLAG_FIX_SUB_DURATION)) {
for (int i = 0; i < FF_ARRAY_ELEMS(dp->sub_prev); i++) {
dp->sub_prev[i] = av_frame_alloc();
- if (!dp->sub_prev[i])
- return AVERROR(ENOMEM);
+ if (!dp->sub_prev[i]) {
+ ret = AVERROR(ENOMEM);
+ goto fail;
+ }
}
dp->sub_heartbeat = av_frame_alloc();
- if (!dp->sub_heartbeat)
- return AVERROR(ENOMEM);
+ if (!dp->sub_heartbeat) {
+ ret = AVERROR(ENOMEM);
+ goto fail;
+ }
}
dp->sar_override = o->par->sample_aspect_ratio;
dp->dec_ctx = avcodec_alloc_context3(codec);
- if (!dp->dec_ctx)
- return AVERROR(ENOMEM);
+ if (!dp->dec_ctx) {
+ ret = AVERROR(ENOMEM);
+ goto fail;
+ }
ret = avcodec_parameters_to_context(dp->dec_ctx, o->par);
if (ret < 0) {
av_log(dp, AV_LOG_ERROR, "Error initializing the decoder context.\n");
- return ret;
+ goto fail;
}
dp->dec_ctx->opaque = dp;
@@ -1009,23 +1018,28 @@ int dec_open(InputStream *ist, Scheduler *sch, unsigned sch_idx,
av_log(dp, AV_LOG_ERROR,
"Hardware device setup failed for decoder: %s\n",
av_err2str(ret));
- return ret;
+ goto fail;
}
if ((ret = avcodec_open2(dp->dec_ctx, codec, dec_opts)) < 0) {
av_log(dp, AV_LOG_ERROR, "Error while opening decoder: %s\n",
av_err2str(ret));
- return ret;
+ goto fail;
}
ret = check_avoptions(*dec_opts);
if (ret < 0)
- return ret;
+ goto fail;
dp->dec.subtitle_header = dp->dec_ctx->subtitle_header;
dp->dec.subtitle_header_size = dp->dec_ctx->subtitle_header_size;
+ *pdec = &dp->dec;
+
return 0;
+fail:
+ dec_free((Decoder**)&dp);
+ return ret;
}
int dec_add_filter(Decoder *dec, InputFilter *ifilter)
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 6216b7c684..5178bcbce4 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -933,7 +933,9 @@ static int ist_use(InputStream *ist, int decoding_needed)
ds->dec_opts.codec = ist->dec;
ds->dec_opts.par = ist->par;
- ret = dec_open(ist, d->sch, ds->sch_idx_dec,
+ ds->dec_opts.log_parent = ist;
+
+ ret = dec_open(&ist->decoder, d->sch, ds->sch_idx_dec,
&ist->decoder_opts, &ds->dec_opts);
if (ret < 0)
return ret;
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 28/31] fftools/ffmpeg_dec: eliminate all remaining InputStream uses
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (25 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 27/31] fftools/ffmpeg_dec: stop passing InputStream to dec_open() Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 29/31] fftools/ffmpeg: make InputStream.decoding_needed private to demuxer Anton Khirnov
` (2 subsequent siblings)
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
Previously, the demuxer would register decoder with the scheduler, using
InputStream as opaque, and pass the scheduling index to the decoder.
Now the registration is done by the decoder itself, using DecoderPriv as
opaque, and the scheduling index is returned to demuxer from dec_open().
decoder_thread() then no longer needs to be accessed from outside of
ffmpeg_dec and can be made static.
---
fftools/ffmpeg.h | 7 +++++--
fftools/ffmpeg_dec.c | 16 +++++++++-------
fftools/ffmpeg_demux.c | 21 +++++++++------------
3 files changed, 23 insertions(+), 21 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index c8cba72006..4881174632 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -290,6 +290,7 @@ enum DecoderFlags {
#if FFMPEG_OPT_TOP
DECODER_FLAG_TOP_FIELD_FIRST = (1 << 3),
#endif
+ DECODER_FLAG_SEND_END_TS = (1 << 4),
};
typedef struct DecoderOpts {
@@ -756,8 +757,11 @@ AVBufferRef *hw_device_for_filter(void);
/**
* @param dec_opts Dictionary filled with decoder options. Its ownership
* is transferred to the decoder.
+ *
+ * @retval ">=0" non-negative scheduler index on success
+ * @retval "<0" an error code on failure
*/
-int dec_open(Decoder **pdec, Scheduler *sch, unsigned sch_idx,
+int dec_open(Decoder **pdec, Scheduler *sch,
AVDictionary **dec_opts, const DecoderOpts *o);
void dec_free(Decoder **pdec);
@@ -847,7 +851,6 @@ const char *opt_match_per_type_str(const SpecifierOptList *sol,
char mediatype);
void *muxer_thread(void *arg);
-void *decoder_thread(void *arg);
void *encoder_thread(void *arg);
#endif /* FFTOOLS_FFMPEG_H */
diff --git a/fftools/ffmpeg_dec.c b/fftools/ffmpeg_dec.c
index 3610256f31..57017faa59 100644
--- a/fftools/ffmpeg_dec.c
+++ b/fftools/ffmpeg_dec.c
@@ -645,10 +645,9 @@ fail:
return AVERROR(ENOMEM);
}
-void *decoder_thread(void *arg)
+static void *decoder_thread(void *arg)
{
- InputStream *ist = arg;
- DecoderPriv *dp = dp_from_dec(ist->decoder);
+ DecoderPriv *dp = arg;
DecThreadContext dt;
int ret = 0, input_status = 0;
@@ -692,7 +691,7 @@ void *decoder_thread(void *arg)
break;
/* report last frame duration to the scheduler */
- if (ist->dec->type == AVMEDIA_TYPE_AUDIO) {
+ if (dp->dec_ctx->codec_type == AVMEDIA_TYPE_AUDIO) {
dt.pkt->pts = dp->last_frame_pts + dp->last_frame_duration_est;
dt.pkt->time_base = dp->last_frame_tb;
}
@@ -940,7 +939,7 @@ static const AVClass dec_class = {
.item_name = dec_item_name,
};
-int dec_open(Decoder **pdec, Scheduler *sch, unsigned sch_idx,
+int dec_open(Decoder **pdec, Scheduler *sch,
AVDictionary **dec_opts, const DecoderOpts *o)
{
DecoderPriv *dp;
@@ -953,8 +952,11 @@ int dec_open(Decoder **pdec, Scheduler *sch, unsigned sch_idx,
if (ret < 0)
return ret;
+ ret = sch_add_dec(sch, decoder_thread, dp, o->flags & DECODER_FLAG_SEND_END_TS);
+ if (ret < 0)
+ return ret;
dp->sch = sch;
- dp->sch_idx = sch_idx;
+ dp->sch_idx = ret;
dp->flags = o->flags;
dp->dec.class = &dec_class;
@@ -1036,7 +1038,7 @@ int dec_open(Decoder **pdec, Scheduler *sch, unsigned sch_idx,
*pdec = &dp->dec;
- return 0;
+ return dp->sch_idx;
fail:
dec_free((Decoder**)dp);
return ret;
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 5178bcbce4..0ccb05b1d0 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -895,18 +895,9 @@ static int ist_use(InputStream *ist, int decoding_needed)
if (decoding_needed && ds->sch_idx_dec < 0) {
int is_audio = ist->st->codecpar->codec_type == AVMEDIA_TYPE_AUDIO;
- ret = sch_add_dec(d->sch, decoder_thread, ist, d->loop && is_audio);
- if (ret < 0)
- return ret;
- ds->sch_idx_dec = ret;
-
- ret = sch_connect(d->sch, SCH_DSTREAM(d->f.index, ds->sch_idx_stream),
- SCH_DEC(ds->sch_idx_dec));
- if (ret < 0)
- return ret;
-
ds->dec_opts.flags = (!!ist->fix_sub_duration * DECODER_FLAG_FIX_SUB_DURATION) |
- (!!(d->f.ctx->iformat->flags & AVFMT_NOTIMESTAMPS) * DECODER_FLAG_TS_UNRELIABLE)
+ (!!(d->f.ctx->iformat->flags & AVFMT_NOTIMESTAMPS) * DECODER_FLAG_TS_UNRELIABLE) |
+ (!!(d->loop && is_audio) * DECODER_FLAG_SEND_END_TS)
#if FFMPEG_OPT_TOP
| ((ist->top_field_first >= 0) * DECODER_FLAG_TOP_FIELD_FIRST)
#endif
@@ -935,10 +926,16 @@ static int ist_use(InputStream *ist, int decoding_needed)
ds->dec_opts.log_parent = ist;
- ret = dec_open(&ist->decoder, d->sch, ds->sch_idx_dec,
+ ret = dec_open(&ist->decoder, d->sch,
&ist->decoder_opts, &ds->dec_opts);
if (ret < 0)
return ret;
+ ds->sch_idx_dec = ret;
+
+ ret = sch_connect(d->sch, SCH_DSTREAM(d->f.index, ds->sch_idx_stream),
+ SCH_DEC(ds->sch_idx_dec));
+ if (ret < 0)
+ return ret;
d->have_audio_dec |= is_audio;
}
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 29/31] fftools/ffmpeg: make InputStream.decoding_needed private to demuxer
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (26 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 28/31] fftools/ffmpeg_dec: eliminate all remaining InputStream uses Anton Khirnov
@ 2024-01-24 8:16 ` Anton Khirnov
2024-01-24 8:17 ` [FFmpeg-devel] [PATCH 30/31] fftools/ffmpeg: make InputStream.decoder_opts " Anton Khirnov
2024-01-24 8:17 ` [FFmpeg-devel] [PATCH 31/31] fftools/ffmpeg: cosmetics, vertically align Input{File, Stream} Anton Khirnov
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:16 UTC (permalink / raw)
To: ffmpeg-devel
It is no longer used outside of ffmpeg_demux.
---
fftools/ffmpeg.h | 3 ---
fftools/ffmpeg_demux.c | 13 +++++++++----
2 files changed, 9 insertions(+), 7 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index 4881174632..29d8ea4355 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -337,9 +337,6 @@ typedef struct InputStream {
AVStream *st;
int user_set_discard;
- int decoding_needed; /* non zero if the packets must be decoded in 'raw_fifo', see DECODING_FOR_* */
-#define DECODING_FOR_OST 1
-#define DECODING_FOR_FILTER 2
/**
* Codec parameters - to be used by the decoding/streamcopy code.
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 0ccb05b1d0..61a4a745b4 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -50,6 +50,11 @@ typedef struct DemuxStream {
double ts_scale;
+ /* non zero if the packets must be decoded in 'raw_fifo', see DECODING_FOR_* */
+ int decoding_needed;
+#define DECODING_FOR_OST 1
+#define DECODING_FOR_FILTER 2
+
/* true if stream data should be discarded */
int discard;
@@ -796,7 +801,7 @@ static void demux_final_stats(Demuxer *d)
av_log(f, AV_LOG_VERBOSE, "%"PRIu64" packets read (%"PRIu64" bytes); ",
ds->nb_packets, ds->data_size);
- if (ist->decoding_needed) {
+ if (ds->decoding_needed) {
av_log(f, AV_LOG_VERBOSE,
"%"PRIu64" frames decoded; %"PRIu64" decode errors",
ist->decoder->frames_decoded, ist->decoder->decode_errors);
@@ -889,7 +894,7 @@ static int ist_use(InputStream *ist, int decoding_needed)
}
ist->st->discard = ist->user_set_discard;
- ist->decoding_needed |= decoding_needed;
+ ds->decoding_needed |= decoding_needed;
ds->streamcopy_needed |= !decoding_needed;
if (decoding_needed && ds->sch_idx_dec < 0) {
@@ -910,9 +915,9 @@ static int ist_use(InputStream *ist, int decoding_needed)
ds->dec_opts.framerate = ist->st->avg_frame_rate;
if (ist->dec->id == AV_CODEC_ID_DVB_SUBTITLE &&
- (ist->decoding_needed & DECODING_FOR_OST)) {
+ (ds->decoding_needed & DECODING_FOR_OST)) {
av_dict_set(&ist->decoder_opts, "compute_edt", "1", AV_DICT_DONT_OVERWRITE);
- if (ist->decoding_needed & DECODING_FOR_FILTER)
+ if (ds->decoding_needed & DECODING_FOR_FILTER)
av_log(ist, AV_LOG_WARNING,
"Warning using DVB subtitles for filtering and output at the "
"same time is not fully supported, also see -compute_edt [0|1]\n");
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 30/31] fftools/ffmpeg: make InputStream.decoder_opts private to demuxer
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (27 preceding siblings ...)
2024-01-24 8:16 ` [FFmpeg-devel] [PATCH 29/31] fftools/ffmpeg: make InputStream.decoding_needed private to demuxer Anton Khirnov
@ 2024-01-24 8:17 ` Anton Khirnov
2024-01-24 8:17 ` [FFmpeg-devel] [PATCH 31/31] fftools/ffmpeg: cosmetics, vertically align Input{File, Stream} Anton Khirnov
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:17 UTC (permalink / raw)
To: ffmpeg-devel
It is no longer used outside of ffmpeg_demux.
---
fftools/ffmpeg.h | 1 -
fftools/ffmpeg_demux.c | 16 +++++++++-------
2 files changed, 9 insertions(+), 8 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index 29d8ea4355..8395fd260c 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -349,7 +349,6 @@ typedef struct InputStream {
AVRational framerate_guessed;
- AVDictionary *decoder_opts;
AVRational framerate; /* framerate forced with -r */
#if FFMPEG_OPT_TOP
int top_field_first;
diff --git a/fftools/ffmpeg_demux.c b/fftools/ffmpeg_demux.c
index 61a4a745b4..60dc9620c2 100644
--- a/fftools/ffmpeg_demux.c
+++ b/fftools/ffmpeg_demux.c
@@ -77,6 +77,7 @@ typedef struct DemuxStream {
const AVCodecDescriptor *codec_desc;
+ AVDictionary *decoder_opts;
DecoderOpts dec_opts;
char dec_name[16];
@@ -828,7 +829,7 @@ static void ist_free(InputStream **pist)
dec_free(&ist->decoder);
- av_dict_free(&ist->decoder_opts);
+ av_dict_free(&ds->decoder_opts);
av_freep(&ist->filters);
av_freep(&ist->outputs);
av_freep(&ds->dec_opts.hwaccel_device);
@@ -916,7 +917,7 @@ static int ist_use(InputStream *ist, int decoding_needed)
if (ist->dec->id == AV_CODEC_ID_DVB_SUBTITLE &&
(ds->decoding_needed & DECODING_FOR_OST)) {
- av_dict_set(&ist->decoder_opts, "compute_edt", "1", AV_DICT_DONT_OVERWRITE);
+ av_dict_set(&ds->decoder_opts, "compute_edt", "1", AV_DICT_DONT_OVERWRITE);
if (ds->decoding_needed & DECODING_FOR_FILTER)
av_log(ist, AV_LOG_WARNING,
"Warning using DVB subtitles for filtering and output at the "
@@ -932,7 +933,7 @@ static int ist_use(InputStream *ist, int decoding_needed)
ds->dec_opts.log_parent = ist;
ret = dec_open(&ist->decoder, d->sch,
- &ist->decoder_opts, &ds->dec_opts);
+ &ds->decoder_opts, &ds->dec_opts);
if (ret < 0)
return ret;
ds->sch_idx_dec = ret;
@@ -1267,7 +1268,7 @@ static int ist_add(const OptionsContext *o, Demuxer *d, AVStream *st)
return ret;
ret = filter_codec_opts(o->g->codec_opts, ist->st->codecpar->codec_id,
- ic, st, ist->dec, &ist->decoder_opts);
+ ic, st, ist->dec, &ds->decoder_opts);
if (ret < 0)
return ret;
@@ -1293,12 +1294,12 @@ static int ist_add(const OptionsContext *o, Demuxer *d, AVStream *st)
}
if (o->bitexact)
- av_dict_set(&ist->decoder_opts, "flags", "+bitexact", AV_DICT_MULTIKEY);
+ av_dict_set(&ds->decoder_opts, "flags", "+bitexact", AV_DICT_MULTIKEY);
/* Attached pics are sparse, therefore we would not want to delay their decoding
* till EOF. */
if (ist->st->disposition & AV_DISPOSITION_ATTACHED_PIC)
- av_dict_set(&ist->decoder_opts, "thread_type", "-frame", 0);
+ av_dict_set(&ds->decoder_opts, "thread_type", "-frame", 0);
switch (par->codec_type) {
case AVMEDIA_TYPE_VIDEO:
@@ -1772,8 +1773,9 @@ int ifile_open(const OptionsContext *o, const char *filename, Scheduler *sch)
/* check if all codec options have been used */
unused_opts = strip_specifiers(o->g->codec_opts);
for (i = 0; i < f->nb_streams; i++) {
+ DemuxStream *ds = ds_from_ist(f->streams[i]);
e = NULL;
- while ((e = av_dict_iterate(f->streams[i]->decoder_opts, e)))
+ while ((e = av_dict_iterate(ds->decoder_opts, e)))
av_dict_set(&unused_opts, e->key, NULL, 0);
}
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread
* [FFmpeg-devel] [PATCH 31/31] fftools/ffmpeg: cosmetics, vertically align Input{File, Stream}
2024-01-24 8:16 [FFmpeg-devel] [PATCH 01/31] fftools/ffmpeg_dec: split Decoder into a private and public part Anton Khirnov
` (28 preceding siblings ...)
2024-01-24 8:17 ` [FFmpeg-devel] [PATCH 30/31] fftools/ffmpeg: make InputStream.decoder_opts " Anton Khirnov
@ 2024-01-24 8:17 ` Anton Khirnov
29 siblings, 0 replies; 34+ messages in thread
From: Anton Khirnov @ 2024-01-24 8:17 UTC (permalink / raw)
To: ffmpeg-devel
---
fftools/ffmpeg.h | 54 +++++++++++++++++++++++++-----------------------
1 file changed, 28 insertions(+), 26 deletions(-)
diff --git a/fftools/ffmpeg.h b/fftools/ffmpeg.h
index 8395fd260c..33750e0bb3 100644
--- a/fftools/ffmpeg.h
+++ b/fftools/ffmpeg.h
@@ -328,35 +328,36 @@ typedef struct Decoder {
} Decoder;
typedef struct InputStream {
- const AVClass *class;
+ const AVClass *class;
/* parent source */
- struct InputFile *file;
+ struct InputFile *file;
- int index;
+ int index;
- AVStream *st;
- int user_set_discard;
+ AVStream *st;
+ int user_set_discard;
/**
* Codec parameters - to be used by the decoding/streamcopy code.
* st->codecpar should not be accessed, because it may be modified
* concurrently by the demuxing thread.
*/
- AVCodecParameters *par;
- Decoder *decoder;
- const AVCodec *dec;
+ AVCodecParameters *par;
+ Decoder *decoder;
+ const AVCodec *dec;
- AVRational framerate_guessed;
+ AVRational framerate_guessed;
- AVRational framerate; /* framerate forced with -r */
+ /* framerate forced with -r */
+ AVRational framerate;
#if FFMPEG_OPT_TOP
- int top_field_first;
+ int top_field_first;
#endif
- int autorotate;
+ int autorotate;
- int fix_sub_duration;
+ int fix_sub_duration;
struct sub2video {
int w, h;
@@ -364,8 +365,8 @@ typedef struct InputStream {
/* decoded data from this stream goes into all those filters
* currently video and audio only */
- InputFilter **filters;
- int nb_filters;
+ InputFilter **filters;
+ int nb_filters;
/*
* Output targets that do not go through lavfi, i.e. subtitles or
@@ -379,28 +380,29 @@ typedef struct InputStream {
} InputStream;
typedef struct InputFile {
- const AVClass *class;
+ const AVClass *class;
- int index;
+ int index;
AVFormatContext *ctx;
- int64_t input_ts_offset;
- int input_sync_ref;
+ int64_t input_ts_offset;
+ int input_sync_ref;
/**
* Effective format start time based on enabled streams.
*/
- int64_t start_time_effective;
- int64_t ts_offset;
- int64_t start_time; /* user-specified start time in AV_TIME_BASE or AV_NOPTS_VALUE */
- int64_t recording_time;
+ int64_t start_time_effective;
+ int64_t ts_offset;
+ /* user-specified start time in AV_TIME_BASE or AV_NOPTS_VALUE */
+ int64_t start_time;
+ int64_t recording_time;
/* streams that ffmpeg is aware of;
* there may be extra streams in ctx that are not mapped to an InputStream
* if new streams appear dynamically during demuxing */
- InputStream **streams;
- int nb_streams;
+ InputStream **streams;
+ int nb_streams;
- int accurate_seek;
+ int accurate_seek;
} InputFile;
enum forced_keyframes_const {
--
2.42.0
_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".
^ permalink raw reply [flat|nested] 34+ messages in thread