-
Notifications
You must be signed in to change notification settings - Fork 165
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #1038 from AlessandroBono/wip/abono/ffmpeg-upstrea…
…m-patch ffmpeg: switch to upstream MB_INFO patch
- Loading branch information
Showing
4 changed files
with
453 additions
and
294 deletions.
There are no files selected for viewing
262 changes: 262 additions & 0 deletions
262
gvsbuild/patches/ffmpeg/0001-lavu-add-video_hint-API.patch
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,262 @@ | ||
From 5012b4ab4ca65a1c71bbcc125ba39db074b94e70 Mon Sep 17 00:00:00 2001 | ||
From: Elias Carotti <eliascrt _at_ amazon _dot_ it> | ||
Date: Mon, 10 Jul 2023 14:34:53 +0200 | ||
Subject: [PATCH] lavu: add video_hint API | ||
|
||
Add side data type to provide hint to the video encoders about | ||
unchanged portions of each frame. | ||
|
||
Signed-off-by: Anton Khirnov <anton@khirnov.net> | ||
--- | ||
doc/APIchanges | 3 ++ | ||
libavutil/Makefile | 2 + | ||
libavutil/frame.h | 10 ++++ | ||
libavutil/version.h | 2 +- | ||
libavutil/video_hint.c | 81 +++++++++++++++++++++++++++++++ | ||
libavutil/video_hint.h | 107 +++++++++++++++++++++++++++++++++++++++++ | ||
6 files changed, 204 insertions(+), 1 deletion(-) | ||
create mode 100644 libavutil/video_hint.c | ||
create mode 100644 libavutil/video_hint.h | ||
|
||
diff --git a/libavutil/Makefile b/libavutil/Makefile | ||
index bd9c6f9e3277..7828c94dc562 100644 | ||
--- a/libavutil/Makefile | ||
+++ b/libavutil/Makefile | ||
@@ -91,6 +91,7 @@ HEADERS = adler32.h \ | ||
tea.h \ | ||
tx.h \ | ||
film_grain_params.h \ | ||
+ video_hint.h | ||
|
||
ARCH_HEADERS = bswap.h \ | ||
intmath.h \ | ||
@@ -181,6 +182,7 @@ OBJS = adler32.o \ | ||
uuid.o \ | ||
version.o \ | ||
video_enc_params.o \ | ||
+ video_hint.o \ | ||
film_grain_params.o \ | ||
|
||
|
||
diff --git a/libavutil/frame.h b/libavutil/frame.h | ||
index a491315f25cf..c0c1b23db7ce 100644 | ||
--- a/libavutil/frame.h | ||
+++ b/libavutil/frame.h | ||
@@ -214,6 +214,16 @@ enum AVFrameSideDataType { | ||
* Ambient viewing environment metadata, as defined by H.274. | ||
*/ | ||
AV_FRAME_DATA_AMBIENT_VIEWING_ENVIRONMENT, | ||
+ | ||
+ /** | ||
+ * Provide encoder-specific hinting information about changed/unchanged | ||
+ * portions of a frame. It can be used to pass information about which | ||
+ * macroblocks can be skipped because they didn't change from the | ||
+ * corresponding ones in the previous frame. This could be useful for | ||
+ * applications which know this information in advance to speed up | ||
+ * encoding. | ||
+ */ | ||
+ AV_FRAME_DATA_VIDEO_HINT, | ||
}; | ||
|
||
enum AVActiveFormatDescription { | ||
diff --git a/libavutil/video_hint.c b/libavutil/video_hint.c | ||
new file mode 100644 | ||
index 000000000000..431716ab675a | ||
--- /dev/null | ||
+++ b/libavutil/video_hint.c | ||
@@ -0,0 +1,81 @@ | ||
+/* | ||
+ * Copyright 2023 Elias Carotti <eliascrt at amazon dot it> | ||
+ * | ||
+ * This file is part of FFmpeg. | ||
+ * | ||
+ * FFmpeg is free software; you can redistribute it and/or | ||
+ * modify it under the terms of the GNU Lesser General Public | ||
+ * License as published by the Free Software Foundation; either | ||
+ * version 2.1 of the License, or (at your option) any later version. | ||
+ * | ||
+ * FFmpeg is distributed in the hope that it will be useful, | ||
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
+ * Lesser General Public License for more details. | ||
+ * | ||
+ * You should have received a copy of the GNU Lesser General Public | ||
+ * License along with FFmpeg; if not, write to the Free Software | ||
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
+ */ | ||
+ | ||
+#include <string.h> | ||
+ | ||
+#include "avstring.h" | ||
+#include "frame.h" | ||
+#include "macros.h" | ||
+#include "mem.h" | ||
+#include "video_hint.h" | ||
+ | ||
+AVVideoHint *av_video_hint_alloc(size_t nb_rects, | ||
+ size_t *out_size) | ||
+{ | ||
+ struct TestStruct { | ||
+ AVVideoHint hint; | ||
+ AVVideoRect rect; | ||
+ }; | ||
+ const size_t rect_offset = offsetof(struct TestStruct, rect); | ||
+ size_t size = rect_offset; | ||
+ AVVideoHint *hint; | ||
+ | ||
+ *out_size = 0; | ||
+ if (nb_rects > (SIZE_MAX - size) / sizeof(AVVideoRect)) | ||
+ return NULL; | ||
+ size += sizeof(AVVideoRect) * nb_rects; | ||
+ | ||
+ hint = av_mallocz(size); | ||
+ if (!hint) | ||
+ return NULL; | ||
+ | ||
+ hint->nb_rects = nb_rects; | ||
+ hint->rect_offset = rect_offset; | ||
+ hint->rect_size = sizeof(AVVideoRect); | ||
+ | ||
+ *out_size = size; | ||
+ | ||
+ return hint; | ||
+} | ||
+ | ||
+AVVideoHint *av_video_hint_create_side_data(AVFrame *frame, | ||
+ size_t nb_rects) | ||
+{ | ||
+ AVVideoHint *hint; | ||
+ AVBufferRef *buf; | ||
+ size_t size = 0; | ||
+ | ||
+ hint = av_video_hint_alloc(nb_rects, &size); | ||
+ if (!hint) | ||
+ return NULL; | ||
+ | ||
+ buf = av_buffer_create((uint8_t *)hint, size, NULL, NULL, 0); | ||
+ if (!buf) { | ||
+ av_freep(&hint); | ||
+ return NULL; | ||
+ } | ||
+ | ||
+ if (!av_frame_new_side_data_from_buf(frame, AV_FRAME_DATA_VIDEO_HINT, buf)) { | ||
+ av_buffer_unref(&buf); | ||
+ return NULL; | ||
+ } | ||
+ | ||
+ return hint; | ||
+} | ||
diff --git a/libavutil/video_hint.h b/libavutil/video_hint.h | ||
new file mode 100644 | ||
index 000000000000..1b2196093b6b | ||
--- /dev/null | ||
+++ b/libavutil/video_hint.h | ||
@@ -0,0 +1,107 @@ | ||
+/** | ||
+ * Copyright 2023 Elias Carotti <eliascrt at amazon dot it> | ||
+ * | ||
+ * This file is part of FFmpeg. | ||
+ * | ||
+ * FFmpeg is free software; you can redistribute it and/or | ||
+ * modify it under the terms of the GNU Lesser General Public | ||
+ * License as published by the Free Software Foundation; either | ||
+ * version 2.1 of the License, or (at your option) any later version. | ||
+ * | ||
+ * FFmpeg is distributed in the hope that it will be useful, | ||
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
+ * Lesser General Public License for more details. | ||
+ * | ||
+ * You should have received a copy of the GNU Lesser General Public | ||
+ * License along with FFmpeg; if not, write to the Free Software | ||
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
+ */ | ||
+ | ||
+#ifndef AVUTIL_VIDEO_HINT_H | ||
+#define AVUTIL_VIDEO_HINT_H | ||
+ | ||
+#include <stddef.h> | ||
+#include <stdint.h> | ||
+#include "libavutil/avassert.h" | ||
+#include "libavutil/frame.h" | ||
+ | ||
+typedef struct AVVideoRect { | ||
+ uint32_t x, y; | ||
+ uint32_t width, height; | ||
+} AVVideoRect; | ||
+ | ||
+typedef enum AVVideoHintType { | ||
+ /* rectangled delimit the constant areas (unchanged), default is changed */ | ||
+ AV_VIDEO_HINT_TYPE_CONSTANT, | ||
+ | ||
+ /* rectangled delimit the constant areas (changed), default is not changed */ | ||
+ AV_VIDEO_HINT_TYPE_CHANGED, | ||
+} AVVideoHintType; | ||
+ | ||
+typedef struct AVVideoHint { | ||
+ /** | ||
+ * Number of AVVideoRect present. | ||
+ * | ||
+ * May be 0, in which case no per-rectangle information is present. In this | ||
+ * case the values of rect_offset / rect_size are unspecified and should | ||
+ * not be accessed. | ||
+ */ | ||
+ size_t nb_rects; | ||
+ | ||
+ /** | ||
+ * Offset in bytes from the beginning of this structure at which the array | ||
+ * of AVVideoRect starts. | ||
+ */ | ||
+ size_t rect_offset; | ||
+ | ||
+ /** | ||
+ * Size in bytes of AVVideoRect. | ||
+ */ | ||
+ size_t rect_size; | ||
+ | ||
+ AVVideoHintType type; | ||
+} AVVideoHint; | ||
+ | ||
+static av_always_inline AVVideoRect * | ||
+av_video_hint_rects(const AVVideoHint *hints) { | ||
+ return (AVVideoRect *)((uint8_t *)hints + hints->rect_offset); | ||
+} | ||
+ | ||
+static av_always_inline AVVideoRect * | ||
+av_video_hint_get_rect(const AVVideoHint *hints, size_t idx) { | ||
+ return (AVVideoRect *)((uint8_t *)hints + hints->rect_offset + idx * hints->rect_size); | ||
+} | ||
+ | ||
+/** | ||
+ * Allocate memory for the AVVideoHint struct along with an nb_rects-sized | ||
+ * arrays of AVVideoRect. | ||
+ * | ||
+ * The side data contains a list of rectangles for the portions of the frame | ||
+ * which changed from the last encoded one (and the remainder are assumed to be | ||
+ * changed), or, alternately (depending on the type parameter) the unchanged | ||
+ * ones (and the remanining ones are those which changed). | ||
+ * Macroblocks will thus be hinted either to be P_SKIP-ped or go through the | ||
+ * regular encoding procedure. | ||
+ * | ||
+ * It's responsibility of the caller to fill the AVRects accordingly, and to set | ||
+ * the proper AVVideoHintType field. | ||
+ * | ||
+ * @param out_size if non-NULL, the size in bytes of the resulting data array is | ||
+ * written here | ||
+ * | ||
+ * @return newly allocated AVVideoHint struct (must be freed by the caller using | ||
+ * av_free()) on success, NULL on memory allocation failure | ||
+ */ | ||
+AVVideoHint *av_video_hint_alloc(size_t nb_rects, | ||
+ size_t *out_size); | ||
+ | ||
+/** | ||
+ * Same as av_video_hint_alloc(), except newly-allocated AVVideoHint is attached | ||
+ * as side data of type AV_FRAME_DATA_VIDEO_HINT_INFO to frame. | ||
+ */ | ||
+AVVideoHint *av_video_hint_create_side_data(AVFrame *frame, | ||
+ size_t nb_rects); | ||
+ | ||
+ | ||
+#endif /* AVUTIL_VIDEO_HINT_H */ | ||
|
Oops, something went wrong.