[FFmpeg-devel] [PATCH 1/2] avformat/avformat: Introduced `AVInputFormat.read_timestamp2` to fix keyframe seeking for formats that rely on `read_timestamp` for seeking
James Almer
jamrial at gmail.com
Mon Sep 2 23:07:05 EEST 2019
On 8/31/2019 7:10 AM, fumoboy007 at me.com wrote:
> From: fumoboy007 <fumoboy007 at me.com>
>
> If the user omits `AVSEEK_FLAG_ANY`, then the result of the seek should be a keyframe. `ff_gen_search` did not respect that contract because it had no good way to determine whether a timestamp returned by `read_timestamp` was for a keyframe packet.
>
> Therefore, we introduce `read_timestamp2`, which adds a new parameter named `prefer_keyframe`. This new parameter tells the input format whether to skip non-keyframe packets. The parameter is named `prefer_keyframe` instead of something like `keyframe_only` because some formats do not distinguish between keyframe and non-keyframe packets.
>
> This commit adds the new function and deprecates the old function. Subsequent commits will migrate input formats to the new function.
>
> Signed-off-by: fumoboy007 <fumoboy007 at me.com>
> ---
> libavformat/avformat.h | 9 +++++++
> libavformat/internal.h | 6 +++--
> libavformat/nutdec.c | 6 ++---
> libavformat/utils.c | 56 +++++++++++++++++++++++++++++++++---------
> 4 files changed, 60 insertions(+), 17 deletions(-)
>
> diff --git a/libavformat/avformat.h b/libavformat/avformat.h
> index 6eb329f13f..1db548663c 100644
> --- a/libavformat/avformat.h
> +++ b/libavformat/avformat.h
> @@ -741,6 +741,7 @@ typedef struct AVInputFormat {
> * Get the next timestamp in stream[stream_index].time_base units.
> * @return the timestamp or AV_NOPTS_VALUE if an error occurred
> */
> + attribute_deprecated
> int64_t (*read_timestamp)(struct AVFormatContext *s, int stream_index,
> int64_t *pos, int64_t pos_limit);
>
> @@ -781,6 +782,14 @@ typedef struct AVInputFormat {
> * @see avdevice_capabilities_free() for more details.
> */
> int (*free_device_capabilities)(struct AVFormatContext *s, struct AVDeviceCapabilitiesQuery *caps);
> +
> + /**
> + * Get the next timestamp in stream[stream_index].time_base units.
> + * @param prefer_keyframe Whether to skip over non-keyframe packets (if possible).
> + * @return the timestamp or AV_NOPTS_VALUE if an error occurred
> + */
> + int64_t (*read_timestamp2)(struct AVFormatContext *s, int stream_index,
> + int64_t *pos, int64_t pos_limit, int prefer_keyframe);
> } AVInputFormat;
> /**
> * @}
AVInputFormat.read_timestamp() is not a public field. There's no need to
deprecate it and add a replacement. Just change it as you see fit,
making sure to update all demuxers that may use it.
More information about the ffmpeg-devel
mailing list