[packages/ffmpeg] Up to 8.1.1 (rel 0.1 to prevent accidential sending due to incompatible changes)

arekm arekm at pld-linux.org
Fri Jun 12 20:46:42 CEST 2026


commit e78a9e755db3278a0d448613ac8854cde51ba4d5
Author: Arkadiusz Miśkiewicz <arekm at maven.pl>
Date:   Fri Jun 12 20:46:12 2026 +0200

    Up to 8.1.1 (rel 0.1 to prevent accidential sending due to incompatible changes)

 ffmpeg-atadenoise.patch    |   21 +-
 ffmpeg-vulkan1.3.280.patch | 1526 --------
 ffmpeg.spec                |  170 +-
 gcc14.patch                |  162 -
 libv4l2-1.30.patch         |   67 -
 opencv4.patch              |   14 -
 texinfo-7.2.patch          |  297 --
 v4l2-request-hwdec.patch   | 8262 +++++++++++++++++++++++++-------------------
 8 files changed, 4826 insertions(+), 5693 deletions(-)
---
diff --git a/ffmpeg.spec b/ffmpeg.spec
index 0491e2d..1b359a9 100644
--- a/ffmpeg.spec
+++ b/ffmpeg.spec
@@ -1,7 +1,9 @@
 # TODO:
+# - libtorch (https://github.com/pytorch/pytorch) [--enable-libtorch, Torch as one DNN backend]
 # - libopenvino
 # - libtensorflow [-ltensorflow tensorflow/c/c_api.h]
-# - AMF >= 1.4.29.0 (available at https://github.com/GPUOpen-LibrariesAndSDKs/AMF, where is original source?)
+# - AMF >= 1.4.36.0 (available at https://github.com/GPUOpen-LibrariesAndSDKs/AMF, where is original source?)
+# - ohcodec (--enable-ohcodec, enable OpenHarmony Codec support; specific to OpenHarmony OS?)
 #
 # How to deal with ffmpeg/opencv/chromaprint checken-egg problem:
 #	1. make-request -r --with bootstrap ffmpeg.spec
@@ -12,7 +14,7 @@
 #
 # Conditional build:
 %bcond_with	bootstrap	# disable features to able to build without installed ffmpeg
-%bcond_with	nonfree		# unblock non free options of package (currently: cuda_nvcc, decklib, fdk_aac, npp, openssl, libressl/libtls)
+%bcond_with	nonfree		# unblock non free options of package (currently: cuda_nvcc, decklib, fdk_aac, mpeghdec, npp, openssl, libressl/libtls)
 %bcond_without	amr		# AMR-NB/WB de/encoding via libopencore-amrnb/wb
 %bcond_without	aom		# AV1 viden de/encoding via libaom
 %bcond_without	aribb24		# ARIB text and caption decoding via libaribb24
@@ -21,13 +23,16 @@
 %bcond_without	avs2		# AVS2 de/encoding via libdavs2/libxavs2
 %bcond_without	bs2b		# BS2B audio filter support
 %bcond_without	caca		# textual display using libcaca
+%bcond_without	cairo		# drawvg filter via libcairo
 %bcond_without	codec2		# codec2 support using libcodec2
 %bcond_without	chromaprint	# audio fingerprinting with chromaprint
 %bcond_with	cudasdk		# NVIDIA CUDA code using nvcc from CUDA SDK [BR: cuda.h, non-free]
 %bcond_with	dav1d		# AV1 decoding via libdav1d
 %bcond_without	dc1394		# IIDC-1394 grabbing using libdc1394
 %bcond_with	decklink	# Blackmagic DeckLink I/O support (requires nonfree)
+%bcond_without	dvd		# DVD demuxing via libdvdnav+libdvdread
 %bcond_with	fdk_aac		# AAC de/encoding via libfdk_aac (requires nonfree)
+%bcond_with	mpeghdec	# MPEG-H 3D Audio decoding via libmpeghdec (requires nonfree)
 %bcond_without	ffnvcodec	# NVIDIA codecs support using ffnvcodec headers (covered: cuda cuvid nvdec nvenc)
 %bcond_without	flite		# flite voice synthesis support
 %bcond_without	frei0r		# frei0r video filtering
@@ -39,14 +44,17 @@
 %bcond_without	ilbc		# iLBC de/encoding via WebRTC libilbc
 %bcond_without	kvazaar		# Kvazaar HEVC encoder support
 %bcond_without	ladspa		# LADSPA audio filtering
+%bcond_without	lc3		# LC3 audio de/encoding via liblc3
+%bcond_without	lcevcdec	# LCEVC audio decoding via liblcevc_dec
 %bcond_without	lcms		# ICC profile support via lcms2
 %bcond_with	lensfun		# lensfun lens correction
 %bcond_with	libaribcaption	# ARIB text and caption decoding via libaribcaption
-%bcond_with	libdrm		# Linux Direct Rendering Manager code
+%bcond_without	libdrm		# Linux Direct Rendering Manager code
 %bcond_without	libjxl		# JPEG XL de/encoding via libjxl
 %bcond_with	libklvanc	# Kernel Labs VANC processing (in decklink driver)
 %bcond_without	libmysofa	# sofalizer filter
 %bcond_with	libplacebo	# libplacebo filters
+%bcond_without	libquirc	# QR decoding via libquirc
 %bcond_without	librist		# RIST support via librist
 %bcond_with	librsvg		# SVG rasterization via librsvg
 %bcond_with	libxml2		# XML parsing using libxml2
@@ -56,6 +64,7 @@
 %bcond_with	npp		# NVIDIA Performance Primitives-based code (requires nonfree) [BR: libnppc+libnppi, npp.h]
 %bcond_without	omx		# OpenMAX IL support
 %bcond_without	openal		# OpenAL 1.1 capture support
+%bcond_without	openapv		# APV codec encoding support via OpenAPV
 %bcond_without	opencl		# OpenCL 1.2 code
 %bcond_with	opencv		# OpenCV video filtering
 %bcond_without	opengl		# OpenGL rendering support
@@ -63,6 +72,7 @@
 %bcond_without	openmpt		# OpenMPT module decoder
 %bcond_with	pocketsphinx	# asr filter using PocketSphinx
 %bcond_without	pulseaudio	# PulseAudio input support
+%bcond_without	qrencode	# QR encoding via qrencode
 %bcond_without	rabbitmq	# RabbitMQ support
 %bcond_with	rav1e		# AV1 encoding using rav1e
 %bcond_with	rkmpp		# Rockchip Media Process Platform code [implies libdrm]
@@ -75,6 +85,7 @@
 %bcond_without	srt		# Haivision SRT protocol support
 %bcond_without	ssh		# SFTP protocol support via libssh
 %bcond_with	svtav1		# AV1 encoding via SVT-AV1
+%bcond_with	svtjpegxs	# JPEG-XS de/encoding via SVT-JPEG-XS
 %bcond_with	tesseract	# OCR filter based on Tesseract
 %bcond_without	theora		# Theora encoding via libtheora
 %bcond_with	uavs3d		# AVS3 decoding via libuavs3d (TODO: enable when 1.1.41 released)
@@ -87,9 +98,12 @@
 %bcond_with	vpl		# libvpl instead of MFX
 %bcond_without	vpx		# VP8, a high-quality video codec
 %bcond_without	vulkan		# Vulkan code
+%bcond_without	vvenc		# H.266/VVC video encoding via vvenc
 %bcond_without	webp		# WebP encoding support
+%bcond_with	whisper		# Whisper ASR support
 %bcond_without	x264		# H.264 x264 encoder
 %bcond_without	x265		# H.265/HEVC x265 encoder
+%bcond_without	xevc		# MPEG-5 EVC decoding/encoding via xecd/xeve
 %bcond_without	xvid		# vid encoding via xvidcore
 %bcond_without	zimg		# zscale filter based on z.lib
 %bcond_without	zmq		# 0MQ message passing
@@ -102,8 +116,9 @@
 %undefine	with_opencv
 %undefine	with_chromaprint
 %endif
-%if %{with rkmpp} || %{with v4l2_request}
-%define		with_libdrm	1
+%if %{without libdrm}
+%undefine	with_rkmpp
+%undefine	v4l2_request
 %endif
 %if %{with glslang}
 %undefine	with_shaderc
@@ -124,15 +139,11 @@
 %ifarch i386 i486
 %undefine	with_x265
 %endif
-%ifarch i686 pentium4 athlon %{x8664} x32
-%define		with_crystalhd	1
-%endif
 Summary:	FFmpeg - a very fast video and audio converter
 Summary(pl.UTF-8):	FFmpeg - szybki konwerter audio/wideo
 Name:		ffmpeg
-# NOTE: 7.x/8.x prepared on DEVEL-{7.0,7.1,8.0} branches, but other software is not ready (e.g. xine-lib 1.2.13, gstreamer-libav 1.24.2)
-Version:	6.1.5
-Release:	1
+Version:	8.1.1
+Release:	0.1
 # LGPL or GPL, chosen at configure time (GPL version is more featured)
 # GPL: frei0r libcdio libdavs2 rubberband vidstab x264 x265 xavs xavs2 xvid
 # v3 (allows *GPLv3 or Apache-licensed libs): gmp lensfun opencore-amr vmaf vo-*enc rkmpp
@@ -140,18 +151,14 @@ Release:	1
 License:	GPL v3+ with LGPL v3+ parts
 Group:		Applications/Multimedia
 Source0:	https://ffmpeg.org/releases/%{name}-%{version}.tar.xz
-# Source0-md5:	77a89d36871a3fcb41883cb5fac3efd3
+# Source0-md5:	f423232dd414c77008dfd85ea5523b8c
 Patch0:		%{name}-omx-libnames.patch
 Patch1:		%{name}-atadenoise.patch
-Patch2:		opencv4.patch
-Patch3:		v4l2-request-hwdec.patch
-Patch4:		ffmpeg-vulkan1.3.280.patch
-Patch5:		gcc14.patch
-Patch6:		texinfo-7.2.patch
-Patch7:		libv4l2-1.30.patch
+Patch2:		v4l2-request-hwdec.patch
 URL:		https://ffmpeg.org/
 %{?with_avisynth:BuildRequires:	AviSynthPlus-devel >= 3.7.3}
 %{?with_decklink:BuildRequires:	Blackmagic_DeckLink_SDK >= 10.11}
+%{?with_lcevcdec:BuildRequires:	LCEVCdec-devel >= 2.0.0}
 %{?with_openal:BuildRequires:	OpenAL-devel >= 1.1}
 %{?with_opencl:BuildRequires:	OpenCL-devel >= 1.2}
 %{?with_opengl:BuildRequires:	OpenGL-GLX-devel}
@@ -159,11 +166,12 @@ URL:		https://ffmpeg.org/
 %{?with_omx:BuildRequires:	OpenMAX-IL-devel}
 BuildRequires:	SDL2-devel >= 2.0.1
 BuildRequires:	SDL2-devel < 3.0.0
-%{?with_vulkan:BuildRequires:	Vulkan-Loader-devel >= 1.3.277}
+%{?with_vulkan:BuildRequires:	Vulkan-Loader-devel >= 1.4.317}
 BuildRequires:	alsa-lib-devel
-%{?with_aom:BuildRequires:	aom-devel >= 1.0.0}
+%{?with_aom:BuildRequires:	aom-devel >= 2.0.0}
 %{?with_aribb24:BuildRequires:	aribb24-devel}
 BuildRequires:	bzip2-devel
+%{?with_cairo:BuildRequires:	cairo-devel}
 BuildRequires:	celt-devel >= 0.11.0
 %{?with_codec2:BuildRequires:	codec2-devel}
 %{?with_dav1d:BuildRequires:	dav1d-devel >= 0.5.0}
@@ -175,11 +183,8 @@ BuildRequires:	freetype-devel
 %{?with_frei0r:BuildRequires:	frei0r-devel}
 %{?with_fribidi:BuildRequires:	fribidi-devel}
 %{?with_gme:BuildRequires:	game-music-emu-devel}
+BuildRequires:	gcc >= 6:4.7
 BuildRequires:	harfbuzz-devel
-%ifarch ppc
-# require version with altivec support fixed
-BuildRequires:	gcc >= 5:3.3.2-3
-%endif
 %{?with_glslang:BuildRequires:	glslang-devel >= 11}
 BuildRequires:	gmp-devel
 BuildRequires:	gnutls-devel
@@ -200,17 +205,20 @@ BuildRequires:	libbluray-devel
 %{?with_caca:BuildRequires:	libcaca-devel}
 BuildRequires:	libcdio-paranoia-devel >= 0.90-2
 %{?with_chromaprint:BuildRequires:	libchromaprint-devel}
-%{?with_crystalhd:BuildRequires:	libcrystalhd-devel}
 %{?with_dc1394:BuildRequires:	libdc1394-devel >= 2}
 %{?with_libdrm:BuildRequires:	libdrm-devel}
+%{?with_dvd:BuildRequires:	libdvdnav-devel >= 6.1.1}
+%{?with_dvd:BuildRequires:	libdvdread-devel >= 6.1.2}
 %{?with_gsm:BuildRequires:	libgsm-devel}
 %{?with_iec61883:BuildRequires:	libiec61883-devel}
 %{?with_libjxl:BuildRequires:	libjxl-devel >= 0.7.0}
 %{?with_libklvanc:BuildRequires:	libklvanc-devel}
+%{?with_lc3:BuildRequires:	liblc3-devel >= 1.1.0}
 %{?with_modplug:BuildRequires:	libmodplug-devel}
 %{?with_libmysofa:BuildRequires:	libmysofa-devel >= 0.7}
 %{?with_openmpt:BuildRequires: libopenmpt-devel >= 0.4.5}
-%{?with_libplacebo:BuildRequires:	libplacebo-devel >= 4.192.0}
+%{?with_libplacebo:BuildRequires:	libplacebo-devel >= 5.229.0}
+%{?with_libquirc:BuildRequires:	libquirc-devel}
 %if %{with dc1394} || %{with iec61883}
 BuildRequires:	libraw1394-devel >= 2
 %endif
@@ -232,7 +240,7 @@ BuildRequires:	libvorbis-devel
 %{?with_vpl:BuildRequires:	libvpl-devel >= 2.6}
 %{?with_vpx:BuildRequires:	libvpx-devel >= 1.4.0}
 %{?with_webp:BuildRequires:	libwebp-devel >= 0.4.0}
-# X264_BUILD >= 122
+# X264_BUILD >= 163
 %{?with_x264:BuildRequires:	libx264-devel >= 0.1.3-1.20130827_2245}
 # X265_BUILD >= 89
 %{?with_x265:BuildRequires:	libx265-devel >= 2.0}
@@ -243,12 +251,14 @@ BuildRequires:	libxcb-devel >= 1.4
 %{?with_v4l2_request:BuildRequires:	linux-libc-headers >= 7:5.11.0}
 %{?with_lv2:BuildRequires:	lv2-devel}
 %{?with_mfx:BuildRequires:	mfx_dispatch-devel >= 1.28}
+%{?with_mpeghdec:BuildRequires:	mpeghdec-devel >= 3.0.0}
 %ifarch %{ix86}
 %ifnarch i386 i486
 BuildRequires:	nasm
 %endif
 %endif
 %{?with_ffnvcodec:BuildRequires:	nv-codec-headers >= 12.1.14.0}
+%{?with_openapv:BuildRequires:	openapv-devel >= 0.2.0.0}
 # amrnb,amrwb
 %{?with_amr:BuildRequires:	opencore-amr-devel}
 %{?with_opencv:BuildRequires:	opencv-devel >= 2}
@@ -260,6 +270,7 @@ BuildRequires:	perl-tools-pod
 %{?with_pocketsphinx:BuildRequires:	pocketsphinx-devel > 0.8}
 BuildRequires:	pkgconfig
 %{?with_pulseaudio:BuildRequires:	pulseaudio-devel}
+%{?with_qrencode:BuildRequires:	qrencode-devel}
 %{?with_rabbitmq:BuildRequires:	rabbitmq-c-devel >= 0.7.1}
 %{?with_rav1e:BuildRequires:	rav1e-devel >= 0.5.0}
 %{?with_rkmpp:BuildRequires:	rockchip-mpp-devel >= 1.3.7}
@@ -273,6 +284,7 @@ BuildRequires:	speex-devel >= 1:1.2-rc1
 %{?with_glslang:BuildRequires:	spirv-tools-devel}
 %{?with_srt:BuildRequires:	srt-devel >= 1.3}
 %{?with_svtav1:BuildRequires:	svt-av1-devel >= 0.9.0}
+%{?with_svtjpegxs:BuildRequires:	svt-jpegxs-devel >= 0.10.0}
 BuildRequires:	tar >= 1:1.22
 %{?with_tesseract:BuildRequires:	tesseract-devel}
 %{?with_doc:BuildRequires:	tetex}
@@ -285,9 +297,13 @@ BuildRequires:	twolame-devel >= 0.3.10
 %{?with_vidstab:BuildRequires:	vid.stab-devel >= 0.98}
 %{?with_vmaf:BuildRequires:	vmaf-devel >= 2.0.0}
 %{?with_voamrwbenc:BuildRequires:	vo-amrwbenc-devel}
+%{?with_vvenc:BuildRequires:	vvenc-devel >= 1.6.1}
 %{?with_ilbc:BuildRequires:	webrtc-libilbc-devel}
+%{?with_whisper:BuildRequires:	whisper.cpp-devel >= 1.7.5}
 %{?with_avs:BuildRequires:	xavs-devel}
 %{?with_avs2:BuildRequires:	xavs2-devel >= 1.3}
+%{?with_xevc:BuildRequires:	xevd-devel >= 0.4.1}
+%{?with_xevc:BuildRequires:	xeve-devel >= 0.5.1}
 BuildRequires:	xorg-lib-libX11-devel
 BuildRequires:	xorg-lib-libXext-devel
 BuildRequires:	xorg-lib-libXv-devel
@@ -331,9 +347,11 @@ telewizyjnej.
 Summary:	ffmpeg libraries
 Summary(pl.UTF-8):	Biblioteki ffmpeg
 Group:		Libraries
+%{?with_lcevcdec:Requires:	LCEVCdec%{?_isa} >= 2.0.0}
 Requires:	SDL2%{?_isa} >= 2.0.1
-%{?with_vulkan:Requires:	Vulkan-Loader%{?_isa} >= 1.3.277}
-%{?with_aom:Requires:	aom%{?_isa} >= 1.0.0}
+%{?with_vulkan:Requires:	Vulkan-Loader%{?_isa} >= 1.4.317}
+%{?with_aom:Requires:	aom%{?_isa} >= 2.0.0}
+%{?with_cairo:Requires:	cairo%{?_isa}}
 Requires:	celt%{?_isa} >= 0.11.0
 %{?with_dav1d:Requires:	dav1d%{?_isa} >= 0.5.0}
 %{?with_avs2:Requires:	davs2%{?_isa} >= 1.6}
@@ -344,7 +362,10 @@ Requires:	gnutls-libs%{?_isa} >= 3.0.20
 %endif
 %{?with_kvazaar:Requires:	kvazaar-libs%{?_isa} >= 2.0.0}
 Requires:	libass%{?_isa} >= 0.11.0
+%{?with_dvd:Requires:	libdvdnav%{?_isa} >= 6.1.1}
+%{?with_dvd:Requires:	libdvdread%{?_isa} >= 6.1.2}
 %{?with_libjxl:Requires:	libjxl%{?_isa} >= 0.7.0}
+%{?with_lc3:Requires:	liblc3%{?_isa} >= 1.1.0}
 %{?with_libmysofa:Requires:	libmysofa%{?_isa} >= 0.7}
 %{?with_openmpt:Requires: libopenmpt%{?_isa} >= 0.4.5}
 %{?with_libplacebo:Requires:	libplacebo%{?_isa} >= 4.192.0}
@@ -366,6 +387,7 @@ Requires:	libxcb%{?_isa} >= 1.4
 Requires:	lame-libs%{?_isa} >= 3.98.3
 %{?with_lcms:Requires:	lcms2%{?_isa} >= 2.13}
 %{?with_mfx:Requires:	mfx_dispatch%{?_isa} >= 1.28}
+%{?with_openapv:Requires:	openapv%{?_isa} >= 0.2.0.0}
 %{?with_openh264:Requires:	openh264%{?_isa} >= 1.3}
 Requires:	openjpeg2%{?_isa} >= 2.1
 %{?with_rabbitmq:Requires:	rabbitmq-c%{?_isa} >= 0.7.1}
@@ -376,12 +398,17 @@ Requires:	openjpeg2%{?_isa} >= 2.1
 Requires:	speex%{?_isa} >= 1:1.2-rc1
 %{?with_srt:Requires:	srt%{?_isa} >= 1.3}
 %{?with_svtav1:Requires:	svt-av1%{?_isa} >= 0.9.0}
+%{?with_svtjpegxs:Requires:	svt-jpegxs%{?_isa} >= 0.10.0}
 Requires:	twolame-libs%{?_isa} >= 0.3.10
 %{?with_uavs3d:Requires:	uavs3d%{?_isa} >= 1.1.41}
 %{?with_vapoursynth:Requires:	vapoursynth%{?_isa} >= 42}
 %{?with_vidstab:Requires:	vid.stab%{?_isa} >= 0.98}
 %{?with_vmaf:Requires:	vmaf-libs%{?_isa} >= 2.0.0}
+%{?with_vvenc:Requires:	vvenc%{?_isa} >= 1.6.1}
+%{?with_whisper:Requires:	whisper.cpp%{?_isa} >= 1.7.5}
 %{?with_avs2:Requires:	xavs2%{?_isa} >= 1.3}
+%{?with_xevc:Requires:	xevd%{?_isa} >= 0.4.1}
+%{?with_xevc:Requires:	xeve%{?_isa} >= 0.4.3}
 %{?with_xvid:Requires:	xvid%{?_isa} >= 1:1.1.0}
 %{?with_zmq:Requires:	zeromq%{?_isa} >= 4.2.1}
 %{?with_zimg:Requires:	zimg%{?_isa} >= 2.7.0}
@@ -394,16 +421,14 @@ This package contains the ffmpeg shared libraries:
 - the codec library (libavcodec). It supports most existing encoding
   formats (MPEG, DivX, MPEG4, AC3, DV...),
 - demuxer library (libavformat). It supports most existing file
-  formats (AVI, MPEG, OGG, Matroska, ASF...),
-- video postprocessing library (libpostproc).
+  formats (AVI, MPEG, OGG, Matroska, ASF...).
 
 %description libs -l pl.UTF-8
 Ten pakiet zawiera biblioteki współdzielone ffmpeg:
 - bibliotekę kodeków (libavcodec); obsługuje większość istniejących
   formatów kodowania (MPEG, DivX, MPEG4, AC3, DV...),
 - bibliotekę demuksera (libavformat); obsługuje większość istniejących
-  formatów plików (AVI, MPEG, OGG, Matroska, ASF...),
-- bibliotekę postprocessingu (libpostproc).
+  formatów plików (AVI, MPEG, OGG, Matroska, ASF...).
 
 %package devel
 Summary:	ffmpeg header files
@@ -411,15 +436,17 @@ Summary(pl.UTF-8):	Pliki nagłówkowe ffmpeg
 Group:		Development/Libraries
 Requires:	%{name}-libs%{?_isa} = %{version}-%{release}
 # Libs.private from *.pc
+%{?with_lcevcdec:Requires:	LCEVCdec-devel%{?_isa} >= 2.0.0}
 %{?with_openal:Requires:	OpenAL-devel%{?_isa} >= 1.1}
 %{?with_opencl:Requires:	OpenCL-devel >= 1.2}
 %{?with_opengl:Requires:	OpenGL-devel}
 Requires:	SDL2-devel%{?_isa} >= 2.0.1
-%{?with_vulkan:Requires:	Vulkan-Loader-devel%{?_isa} >= 1.3.277}
+%{?with_vulkan:Requires:	Vulkan-Loader-devel%{?_isa} >= 1.4.317}
 Requires:	alsa-lib-devel%{?_isa}
-%{?with_aom:Requires:	aom-devel%{?_isa} >= 1.0.0}
+%{?with_aom:Requires:	aom-devel%{?_isa} >= 2.0.0}
 %{?with_aribb24:Requires:	aribb24-devel%{?_isa}}
 Requires:	bzip2-devel%{?_isa}
+%{?with_cairo:Requires:	cairo-devel%{?_isa}}
 Requires:	celt-devel%{?_isa} >= 0.11.0
 %{?with_codec2:Requires:	codec2-devel%{?_isa}}
 %{?with_dav1d:Requires:	dav1d-devel%{?_isa} >= 0.5.0}
@@ -446,16 +473,19 @@ Requires:	libbluray-devel%{?_isa}
 %{?with_caca:Requires:	libcaca-devel%{?_isa}}
 Requires:	libcdio-paranoia-devel%{?_isa} >= 0.90-2
 %{?with_chromaprint:Requires:	libchromaprint-devel%{?_isa}}
-%{?with_crystalhd:Requires:	libcrystalhd-devel%{?_isa}}
 %{?with_dc1394:Requires:	libdc1394-devel%{?_isa} >= 2}
 %{?with_libdrm:Requires:	libdrm-devel%{?_isa}}
+%{?with_dvd:Requires:	libdvdnav-devel%{?_isa} >= 6.1.1}
+%{?with_dvd:Requires:	libdvdread-devel%{?_isa} >= 6.1.2}
 %{?with_gsm:Requires:	libgsm-devel%{?_isa}}
 %{?with_iec61883:Requires:	libiec61883-devel%{?_isa}}
 %{?with_libjxl:Requires:	libjxl-devel%{?_isa} >= 0.7.0}
 %{?with_libklvanc:Requires:	libklvanc-devel%{?_isa}}
+%{?with_lc3:Requires:	liblc3-devel%{?_isa} >= 1.1.0}
 %{?with_modplug:Requires:	libmodplug-devel%{?_isa}}
 %{?with_libmysofa:Requires:	libmysofa-devel%{?_isa} >= 0.7}
 %{?with_openmpt:Requires: libopenmpt-devel%{?_isa} >= 0.4.5}
+%{?with_libquirc:Requires:	libquirc-devel%{?_isa}}
 %if %{with dc1394} || %{with iec61883}
 Requires:	libraw1394-devel%{?_isa} >= 2
 %endif
@@ -482,12 +512,15 @@ Requires:	libxcb-devel%{?_isa} >= 1.4
 %{?with_libxml2:Requires:	libxml2-devel%{?_isa} >= 2}
 %{?with_lv2:Requires:	lilv-devel%{?_isa}}
 %{?with_mfx:Requires:	mfx_dispatch-devel%{?_isa} >= 1.28}
+%{?with_mpeghdec:Requires:	mpeghdec-devel%{?_isa} >= 3.0.0}
+%{?with_openapv:Requires:	openapv-devel%{?_isa} >= 0.2.0.0}
 %{?with_amr:Requires:	opencore-amr-devel%{?_isa}}
 %{?with_opencv:Requires:	opencv-devel%{?_isa} >= 2}
 %{?with_openh264:Requires:	openh264-devel%{?_isa} >= 1.3}
 Requires:	openjpeg2-devel%{?_isa} >= 2.1
 Requires:	opus-devel%{?_isa}
 %{?with_pulseaudio:Requires:	pulseaudio-devel%{?_isa}}
+%{?with_qrencode:Requires:	qrencode-devel%{?_isa}}
 %{?with_rabbitmq:Requires:	rabbitmq-c-devel%{?_isa} >= 0.7.1}
 %{?with_rav1e:Requires:	rav1e-devel%{?_isa} >= 0.5.0}
 %{?with_rkmpp:Requires:	rockchip-mpp-devel%{?_isa} >= 1.3.7}
@@ -500,6 +533,7 @@ Requires:	speex-devel%{?_isa} >= 1:1.2-rc1
 %{?with_glslang:Requires:	spirv-tools-devel%{?_isa}}
 %{?with_srt:Requires:	srt-devel%{?_isa} >= 1.3}
 %{?with_svtav1:Requires:	svt-av1-devel%{?_isa} >= 0.9.0}
+%{?with_svtjpegxs:Requires:	svt-jpegxs-devel%{?_isa} >= 0.10.0}
 %{?with_tesseract:Requires:	tesseract-devel%{?_isa}}
 Requires:	twolame-devel%{?_isa} >= 0.3.10
 %{?with_uavs3d:Requires:	uavs3d-devel%{?_isa} >= 1.1.41}
@@ -507,9 +541,13 @@ Requires:	twolame-devel%{?_isa} >= 0.3.10
 %{?with_vidstab:Requires:	vid.stab-devel%{?_isa} >= 0.98}
 %{?with_voamrwbenc:Requires:	vo-amrwbenc-devel%{?_isa}}
 %{?with_vmaf:Requires:	vmaf-devel%{?_isa} >= 2.0.0}
+%{?with_vvenc:Requires:	vvenc-devel%{?_isa} >= 1.6.1}
 %{?with_ilbc:Requires:	webrtc-libilbc-devel%{?_isa}}
+%{?with_whisper:Requires:	whisper.cpp-devel%{?_isa} >= 1.7.5}
 %{?with_avs:Requires:	xavs-devel%{?_isa}}
 %{?with_avs2:Requires:	xavs2-devel%{?_isa} >= 1.3}
+%{?with_xevc:Requires:	xevd-devel%{?_isa} >= 0.4.1}
+%{?with_xevc:Requires:	xeve-devel%{?_isa} >= 0.4.3}
 Requires:	xorg-lib-libX11-devel%{?_isa}
 Requires:	xorg-lib-libXext-devel%{?_isa}
 Requires:	xorg-lib-libXv-devel%{?_isa}
@@ -571,14 +609,9 @@ Dokumentacja pakietu FFmpeg w formacie HTML.
 %setup -q
 %patch -P0 -p1
 %patch -P1 -p1
-%patch -P2 -p1
 %if %{with v4l2_request}
-%patch -P3 -p1
+%patch -P2 -p1
 %endif
-%patch -P4 -p1
-%patch -P5 -p1
-%patch -P6 -p1
-%patch -P7 -p1
 
 # package the grep result for mplayer, the result formatted as ./mplayer/configure
 cat <<EOF > ffmpeg-avconfig
@@ -663,6 +696,7 @@ EOF
 	%{!?with_doc:--disable-doc} \
 	--enable-avfilter \
 	%{?with_avisynth:--enable-avisynth} \
+	%{?with_cairo:--enable-cairo} \
 	%{?with_chromaprint:--enable-chromaprint} \
 	%{?with_cudasdk:--enable-cuda-nvcc} \
 	%{?with_decklink:--enable-decklink} \
@@ -686,7 +720,9 @@ EOF
 	%{?with_dav1d:--enable-libdav1d} \
 	%{?with_avs2:--enable-libdavs2} \
 	%{?with_dc1394:--enable-libdc1394} \
-	%{?with_libdrm:--enable-libdrm} \
+	%{!?with_libdrm:--disable-libdrm} \
+	%{?with_dvd:--enable-libdvdnav} \
+	%{?with_dvd:--enable-libdvdread} \
 	%{?with_flite:--enable-libflite} \
 	--enable-libfontconfig \
 	--enable-libfreetype \
@@ -701,11 +737,14 @@ EOF
 	%{?with_libjxl:--enable-libjxl} \
 	%{?with_kvazaar:--enable-libkvazaar} \
 	%{?with_libklvanc:--enable-libklvanc} \
+	%{?with_lc3:--enable-liblc3} \
+	%{?with_lcevcdec:--enable-liblcevc_dec} \
 	%{?with_lensfun:--enable-liblensfun} \
 	%{?with_mfx:--enable-libmfx} \
 	%{?with_modplug:--enable-libmodplug} \
 	--enable-libmp3lame \
 	%{?with_libmysofa:--enable-libmysofa} \
+	%{?with_openapv:--enable-liboapv} \
 	%{?with_amr:--enable-libopencore-amrnb} \
 	%{?with_amr:--enable-libopencore-amrwb} \
 	%{?with_opencv:--enable-libopencv} \
@@ -715,6 +754,8 @@ EOF
 	--enable-libopus \
 	%{?with_libplacebo:--enable-libplacebo} \
 	%{?with_pulseaudio:--enable-libpulse} \
+	%{?with_qrencode:--enable-libqrencode} \
+	%{?with_libquirc:--enable-libquirc} \
 	%{?with_rabbitmq:--enable-librabbitmq} \
 	%{?with_rav1e:--enable-librav1e} \
 	%{?with_librist:--enable-librist} \
@@ -730,6 +771,7 @@ EOF
 	%{?with_srt:--enable-libsrt} \
 	%{?with_ssh:--enable-libssh} \
 	%{?with_svtav1:--enable-libsvtav1} \
+	%{?with_svtjpegxs:--enable-libsvtjpegxs} \
 	%{?with_tesseract:--enable-libtesseract} \
 	%{?with_theora:--enable-libtheora} \
 	--enable-libtwolame \
@@ -740,12 +782,15 @@ EOF
 	%{?with_voamrwbenc:--enable-libvo-amrwbenc} \
 	--enable-libvorbis \
 	%{?with_vpx:--enable-libvpx} \
+	%{?with_vvenc:--enable-libvvenc} \
 	%{?with_webp:--enable-libwebp} \
 	%{?with_x264:--enable-libx264} \
 	%{?with_x265:--enable-libx265} \
 	%{?with_avs:--enable-libxavs} \
 	%{?with_avs2:--enable-libxavs2} \
 	--enable-libxcb \
+	%{?with_xevc:--enable-libxevd} \
+	%{?with_xevc:--enable-libxeve} \
 	%{?with_libxml2:--enable-libxml2} \
 	%{?with_xvid:--enable-libxvid} \
 	%{?with_zimg:--enable-libzimg} \
@@ -757,7 +802,6 @@ EOF
 	%{?with_opencl:--enable-opencl} \
 	%{?with_opengl:--enable-opengl} \
 	%{?with_pocketsphinx:--enable-pocketsphinx} \
-	--enable-postproc \
 	--enable-pthreads \
 	%{?with_rkmpp:--enable-rkmpp} \
 	--enable-shared \
@@ -766,6 +810,7 @@ EOF
 	%{!?with_va:--disable-vaapi} \
 	%{?with_vapoursynth:--enable-vapoursynth} \
 	%{!?with_vulkan:--disable-vulkan} \
+	%{?with_whisper:--enable-whisper} \
 %if %{with v4l2_request}
 	--enable-libudev \
 	--enable-v4l2-request \
@@ -782,6 +827,7 @@ EOF
 %if %{with nonfree}
 	--enable-nonfree \
 	%{?with_fdk_aac:--enable-libfdk-aac} \
+	%{?with_mpeghdec:--enable-libmpeghdec} \
 	%{?with_npp:--enable-libnpp} \
 %endif
 	--enable-runtime-cpudetect
@@ -859,41 +905,37 @@ rm -rf $RPM_BUILD_ROOT
 %files libs
 %defattr(644,root,root,755)
 %attr(755,root,root) %{_libdir}/libavcodec.so.*.*.*
-%attr(755,root,root) %ghost %{_libdir}/libavcodec.so.60
+%ghost %{_libdir}/libavcodec.so.62
 %attr(755,root,root) %{_libdir}/libavdevice.so.*.*.*
-%attr(755,root,root) %ghost %{_libdir}/libavdevice.so.60
+%ghost %{_libdir}/libavdevice.so.62
 %attr(755,root,root) %{_libdir}/libavfilter.so.*.*.*
-%attr(755,root,root) %ghost %{_libdir}/libavfilter.so.9
+%ghost %{_libdir}/libavfilter.so.11
 %attr(755,root,root) %{_libdir}/libavformat.so.*.*.*
-%attr(755,root,root) %ghost %{_libdir}/libavformat.so.60
+%ghost %{_libdir}/libavformat.so.62
 %attr(755,root,root) %{_libdir}/libavutil.so.*.*.*
-%attr(755,root,root) %ghost %{_libdir}/libavutil.so.58
-%attr(755,root,root) %{_libdir}/libpostproc.so.*.*.*
-%attr(755,root,root) %ghost %{_libdir}/libpostproc.so.57
+%ghost %{_libdir}/libavutil.so.60
 %attr(755,root,root) %{_libdir}/libswresample.so.*.*.*
-%attr(755,root,root) %ghost %{_libdir}/libswresample.so.4
+%ghost %{_libdir}/libswresample.so.6
 %attr(755,root,root) %{_libdir}/libswscale.so.*.*.*
-%attr(755,root,root) %ghost %{_libdir}/libswscale.so.7
+%ghost %{_libdir}/libswscale.so.9
 
 %files devel
 %defattr(644,root,root,755)
 %doc doc/optimization.txt
-%attr(755,root,root) %{_bindir}/ffmpeg-avconfig
-%attr(755,root,root) %{_libdir}/libavcodec.so
-%attr(755,root,root) %{_libdir}/libavdevice.so
-%attr(755,root,root) %{_libdir}/libavfilter.so
-%attr(755,root,root) %{_libdir}/libavformat.so
-%attr(755,root,root) %{_libdir}/libavutil.so
-%attr(755,root,root) %{_libdir}/libpostproc.so
-%attr(755,root,root) %{_libdir}/libswresample.so
-%attr(755,root,root) %{_libdir}/libswscale.so
+%{_bindir}/ffmpeg-avconfig
+%{_libdir}/libavcodec.so
+%{_libdir}/libavdevice.so
+%{_libdir}/libavfilter.so
+%{_libdir}/libavformat.so
+%{_libdir}/libavutil.so
+%{_libdir}/libswresample.so
+%{_libdir}/libswscale.so
 %{_includedir}/ffmpeg
 %{_includedir}/libavcodec
 %{_includedir}/libavdevice
 %{_includedir}/libavfilter
 %{_includedir}/libavformat
 %{_includedir}/libavutil
-%{_includedir}/libpostproc
 %{_includedir}/libswresample
 %{_includedir}/libswscale
 %{_pkgconfigdir}/libavcodec.pc
@@ -901,7 +943,6 @@ rm -rf $RPM_BUILD_ROOT
 %{_pkgconfigdir}/libavfilter.pc
 %{_pkgconfigdir}/libavformat.pc
 %{_pkgconfigdir}/libavutil.pc
-%{_pkgconfigdir}/libpostproc.pc
 %{_pkgconfigdir}/libswresample.pc
 %{_pkgconfigdir}/libswscale.pc
 %if %{with doc}
@@ -923,7 +964,6 @@ rm -rf $RPM_BUILD_ROOT
 %{_libdir}/libavfilter.a
 %{_libdir}/libavformat.a
 %{_libdir}/libavutil.a
-%{_libdir}/libpostproc.a
 %{_libdir}/libswresample.a
 %{_libdir}/libswscale.a
 %endif
diff --git a/ffmpeg-atadenoise.patch b/ffmpeg-atadenoise.patch
index 6d7877c..be545f6 100644
--- a/ffmpeg-atadenoise.patch
+++ b/ffmpeg-atadenoise.patch
@@ -1,12 +1,13 @@
---- ffmpeg-4.3/libavfilter/x86/Makefile.orig	2020-06-15 20:54:24.000000000 +0200
-+++ ffmpeg-4.3/libavfilter/x86/Makefile	2020-06-30 11:50:18.575161000 +0200
-@@ -42,7 +42,9 @@
- 
- X86ASM-OBJS-$(CONFIG_AFIR_FILTER)            += x86/af_afir.o
- X86ASM-OBJS-$(CONFIG_ANLMDN_FILTER)          += x86/af_anlmdn.o
+--- ffmpeg-8.1.1/libavfilter/x86/Makefile.orig	2026-06-12 18:41:48.182355011 +0200
++++ ffmpeg-8.1.1/libavfilter/x86/Makefile	2026-06-12 18:41:48.187637726 +0200
+@@ -5,8 +5,10 @@
+
+ X86ASM-OBJS-$(CONFIG_AFIR_FILTER)            += x86/af_afir.o x86/af_afir_init.o
+ X86ASM-OBJS-$(CONFIG_ANLMDN_FILTER)          += x86/af_anlmdn.o x86/af_anlmdn_init.o
 +ifdef ARCH_X86_64
- X86ASM-OBJS-$(CONFIG_ATADENOISE_FILTER)      += x86/vf_atadenoise.o
+ X86ASM-OBJS-$(CONFIG_ATADENOISE_FILTER)      += x86/vf_atadenoise.o           \
+                                                 x86/vf_atadenoise_init.o
 +endif
- X86ASM-OBJS-$(CONFIG_BLEND_FILTER)           += x86/vf_blend.o
- X86ASM-OBJS-$(CONFIG_BWDIF_FILTER)           += x86/vf_bwdif.o
- X86ASM-OBJS-$(CONFIG_COLORSPACE_FILTER)      += x86/colorspacedsp.o
+ X86ASM-OBJS-$(CONFIG_BLACKDETECT_FILTER)     += x86/vf_blackdetect.o          \
+                                                 x86/vf_blackdetect_init.o
+ X86ASM-OBJS-$(CONFIG_BLEND_FILTER)           += x86/vf_blend.o x86/vf_blend_init.o
diff --git a/ffmpeg-vulkan1.3.280.patch b/ffmpeg-vulkan1.3.280.patch
deleted file mode 100644
index b72174d..0000000
--- a/ffmpeg-vulkan1.3.280.patch
+++ /dev/null
@@ -1,1526 +0,0 @@
-From 998aa66a10546be207d5dfc1a4a76bc2ce9ea07c Mon Sep 17 00:00:00 2001
-From: Lynne <dev at lynne.ee>
-Date: Sun, 17 Mar 2024 19:31:17 +0100
-Subject: [PATCH] av1dec: add AV1_REF_FRAME_NONE
-
----
- libavcodec/av1.h                     |  1 +
- libavcodec/cbs_av1_syntax_template.c | 12 ++++++------
- 2 files changed, 7 insertions(+), 6 deletions(-)
-
-diff --git a/libavcodec/av1.h b/libavcodec/av1.h
-index 8704bc41c1..94e88f8484 100644
---- a/libavcodec/av1.h
-+++ b/libavcodec/av1.h
-@@ -58,6 +58,7 @@ enum {
- 
- // Reference frames (section 6.10.24).
- enum {
-+    AV1_REF_FRAME_NONE    = -1,
-     AV1_REF_FRAME_INTRA   = 0,
-     AV1_REF_FRAME_LAST    = 1,
-     AV1_REF_FRAME_LAST2   = 2,
-diff --git a/libavcodec/cbs_av1_syntax_template.c b/libavcodec/cbs_av1_syntax_template.c
-index 2979c5d98f..3f4b13a177 100644
---- a/libavcodec/cbs_av1_syntax_template.c
-+++ b/libavcodec/cbs_av1_syntax_template.c
-@@ -360,7 +360,7 @@ static int FUNC(set_frame_refs)(CodedBitstreamContext *ctx, RWContext *rw,
-     int i, j;
- 
-     for (i = 0; i < AV1_REFS_PER_FRAME; i++)
--        ref_frame_idx[i] = -1;
-+        ref_frame_idx[i] = AV1_REF_FRAME_NONE;
-     ref_frame_idx[AV1_REF_FRAME_LAST - AV1_REF_FRAME_LAST] = current->last_frame_idx;
-     ref_frame_idx[AV1_REF_FRAME_GOLDEN - AV1_REF_FRAME_LAST] = current->golden_frame_idx;
- 
-@@ -378,7 +378,7 @@ static int FUNC(set_frame_refs)(CodedBitstreamContext *ctx, RWContext *rw,
-     latest_order_hint = shifted_order_hints[current->last_frame_idx];
-     earliest_order_hint = shifted_order_hints[current->golden_frame_idx];
- 
--    ref = -1;
-+    ref = AV1_REF_FRAME_NONE;
-     for (i = 0; i < AV1_NUM_REF_FRAMES; i++) {
-         int hint = shifted_order_hints[i];
-         if (!used_frame[i] && hint >= cur_frame_hint &&
-@@ -392,7 +392,7 @@ static int FUNC(set_frame_refs)(CodedBitstreamContext *ctx, RWContext *rw,
-         used_frame[ref] = 1;
-     }
- 
--    ref = -1;
-+    ref = AV1_REF_FRAME_NONE;
-     for (i = 0; i < AV1_NUM_REF_FRAMES; i++) {
-         int hint = shifted_order_hints[i];
-         if (!used_frame[i] && hint >= cur_frame_hint &&
-@@ -406,7 +406,7 @@ static int FUNC(set_frame_refs)(CodedBitstreamContext *ctx, RWContext *rw,
-         used_frame[ref] = 1;
-     }
- 
--    ref = -1;
-+    ref = AV1_REF_FRAME_NONE;
-     for (i = 0; i < AV1_NUM_REF_FRAMES; i++) {
-         int hint = shifted_order_hints[i];
-         if (!used_frame[i] && hint >= cur_frame_hint &&
-@@ -423,7 +423,7 @@ static int FUNC(set_frame_refs)(CodedBitstreamContext *ctx, RWContext *rw,
-     for (i = 0; i < AV1_REFS_PER_FRAME - 2; i++) {
-         int ref_frame = ref_frame_list[i];
-         if (ref_frame_idx[ref_frame - AV1_REF_FRAME_LAST] < 0 ) {
--            ref = -1;
-+            ref = AV1_REF_FRAME_NONE;
-             for (j = 0; j < AV1_NUM_REF_FRAMES; j++) {
-                 int hint = shifted_order_hints[j];
-                 if (!used_frame[j] && hint < cur_frame_hint &&
-@@ -439,7 +439,7 @@ static int FUNC(set_frame_refs)(CodedBitstreamContext *ctx, RWContext *rw,
-         }
-     }
- 
--    ref = -1;
-+    ref = AV1_REF_FRAME_NONE;
-     for (i = 0; i < AV1_NUM_REF_FRAMES; i++) {
-         int hint = shifted_order_hints[i];
-         if (ref < 0 || hint < earliest_order_hint) {
--- 
-2.25.1
-
-From cafb4c554845332eeb33284cf6498049997dc67e Mon Sep 17 00:00:00 2001
-From: Mark Thompson <sw at jkqxz.net>
-Date: Wed, 20 Mar 2024 20:35:28 +0000
-Subject: [PATCH] lavc/cbs_av1: Save more frame ordering information
-
-This is wanted by the Vulkan decoder.
----
- libavcodec/cbs_av1.h                 |  5 +++++
- libavcodec/cbs_av1_syntax_template.c | 25 +++++++++++++++++++++----
- 2 files changed, 26 insertions(+), 4 deletions(-)
-
-diff --git a/libavcodec/cbs_av1.h b/libavcodec/cbs_av1.h
-index a5402f069d..a027013bc7 100644
---- a/libavcodec/cbs_av1.h
-+++ b/libavcodec/cbs_av1.h
-@@ -427,6 +427,8 @@ typedef struct AV1ReferenceFrameState {
-     int bit_depth;      // RefBitDepth
-     int order_hint;     // RefOrderHint
- 
-+    int saved_order_hints[AV1_TOTAL_REFS_PER_FRAME]; // SavedOrderHints[ref]
-+
-     int8_t  loop_filter_ref_deltas[AV1_TOTAL_REFS_PER_FRAME];
-     int8_t  loop_filter_mode_deltas[2];
-     uint8_t feature_enabled[AV1_MAX_SEGMENTS][AV1_SEG_LVL_MAX];
-@@ -464,6 +466,9 @@ typedef struct CodedBitstreamAV1Context {
-     int tile_rows;
-     int tile_num;
- 
-+    int order_hints[AV1_TOTAL_REFS_PER_FRAME];         // OrderHints
-+    int ref_frame_sign_bias[AV1_TOTAL_REFS_PER_FRAME]; // RefFrameSignBias
-+
-     AV1ReferenceFrameState ref[AV1_NUM_REF_FRAMES];
- 
-     // AVOptions
-diff --git a/libavcodec/cbs_av1_syntax_template.c b/libavcodec/cbs_av1_syntax_template.c
-index 3be1f2d30f..2979c5d98f 100644
---- a/libavcodec/cbs_av1_syntax_template.c
-+++ b/libavcodec/cbs_av1_syntax_template.c
-@@ -1414,6 +1414,8 @@ static int FUNC(uncompressed_header)(CodedBitstreamContext *ctx, RWContext *rw,
-             priv->ref[i].valid = 0;
-             priv->ref[i].order_hint = 0;
-         }
-+        for (i = 0; i < AV1_REFS_PER_FRAME; i++)
-+            priv->order_hints[i + AV1_REF_FRAME_LAST] = 0;
-     }
- 
-     flag(disable_cdf_update);
-@@ -1568,11 +1570,20 @@ static int FUNC(uncompressed_header)(CodedBitstreamContext *ctx, RWContext *rw,
-         else
-             flag(use_ref_frame_mvs);
- 
--        infer(allow_intrabc, 0);
--    }
-+        for (i = 0; i < AV1_REFS_PER_FRAME; i++) {
-+            int ref_frame = AV1_REF_FRAME_LAST + i;
-+            int hint = priv->ref[current->ref_frame_idx[i]].order_hint;
-+            priv->order_hints[ref_frame] = hint;
-+            if (!seq->enable_order_hint) {
-+                priv->ref_frame_sign_bias[ref_frame] = 0;
-+            } else {
-+                priv->ref_frame_sign_bias[ref_frame] =
-+                    cbs_av1_get_relative_dist(seq, hint,
-+                                              current->order_hint) > 0;
-+            }
-+        }
- 
--    if (!frame_is_intra) {
--        // Derive reference frame sign biases.
-+        infer(allow_intrabc, 0);
-     }
- 
-     if (seq->reduced_still_picture_header || current->disable_cdf_update)
-@@ -1674,6 +1685,12 @@ update_refs:
-                 .bit_depth      = priv->bit_depth,
-                 .order_hint     = priv->order_hint,
-             };
-+
-+            for (int j = 0; j < AV1_REFS_PER_FRAME; j++) {
-+                priv->ref[i].saved_order_hints[j + AV1_REF_FRAME_LAST] =
-+                    priv->order_hints[j + AV1_REF_FRAME_LAST];
-+            }
-+
-             memcpy(priv->ref[i].loop_filter_ref_deltas, current->loop_filter_ref_deltas,
-                    sizeof(current->loop_filter_ref_deltas));
-             memcpy(priv->ref[i].loop_filter_mode_deltas, current->loop_filter_mode_deltas,
--- 
-2.25.1
-
-From: Lynne <dev at lynne.ee>
-Date: Fri, 19 Jan 2024 00:49:02 +0000 (+1000)
-Subject: vulkan_av1: port to the new stable API
-X-Git-Tag: n7.0~143
-X-Git-Url: http://git.ffmpeg.org/gitweb/ffmpeg.git/commitdiff_plain/ecdc94b97f809d5f2b88640842fd0541951ad295
-
-vulkan_av1: port to the new stable API
-
-Co-Authored-by: Dave Airlie <airlied at redhat.com>
----
-
---- ffmpeg-6.1.1/configure.orig	2024-04-15 21:35:22.596075876 +0200
-+++ ffmpeg-6.1.1/configure	2024-04-15 21:41:06.030881997 +0200
-@@ -7150,8 +7150,8 @@ enabled crystalhd && check_lib crystalhd
-          "in maintaining it."
- 
- if enabled vulkan; then
--    check_pkg_config_header_only vulkan "vulkan >= 1.3.255" "vulkan/vulkan.h" "defined VK_VERSION_1_3" ||
--        check_cpp_condition vulkan "vulkan/vulkan.h" "defined(VK_VERSION_1_4) || (defined(VK_VERSION_1_3) && VK_HEADER_VERSION >= 255)"
-+    check_pkg_config_header_only vulkan "vulkan >= 1.3.277" "vulkan/vulkan.h" "defined VK_VERSION_1_3" ||
-+        check_cpp_condition vulkan "vulkan/vulkan.h" "defined(VK_VERSION_1_4) || (defined(VK_VERSION_1_3) && VK_HEADER_VERSION >= 277)"
- fi
- 
- if disabled vulkan; then
---- ffmpeg-6.1.1/libavcodec/Makefile.orig	2024-04-15 21:35:22.596075876 +0200
-+++ ffmpeg-6.1.1/libavcodec/Makefile	2024-04-15 21:43:51.719984382 +0200
-@@ -1284,7 +1284,6 @@ SKIPHEADERS                            +
-                                           aacenc_quantization.h         \
-                                           aacenc_quantization_misc.h    \
-                                           bitstream_template.h          \
--                                          vulkan_video_codec_av1std_mesa.h \
-                                           $(ARCH)/vpx_arith.h          \
- 
- SKIPHEADERS-$(CONFIG_AMF)              += amfenc.h
-@@ -1306,7 +1305,7 @@ SKIPHEADERS-$(CONFIG_XVMC)             +
- SKIPHEADERS-$(CONFIG_VAAPI)            += vaapi_decode.h vaapi_hevc.h vaapi_encode.h
- SKIPHEADERS-$(CONFIG_VDPAU)            += vdpau.h vdpau_internal.h
- SKIPHEADERS-$(CONFIG_VIDEOTOOLBOX)     += videotoolbox.h vt_internal.h
--SKIPHEADERS-$(CONFIG_VULKAN)           += vulkan.h vulkan_video.h vulkan_decode.h vulkan_video_codec_av1std_decode_mesa.h
-+SKIPHEADERS-$(CONFIG_VULKAN)           += vulkan.h vulkan_video.h vulkan_decode.h
- SKIPHEADERS-$(CONFIG_V4L2_M2M)         += v4l2_buffers.h v4l2_context.h v4l2_m2m.h
- SKIPHEADERS-$(CONFIG_ZLIB)             += zlib_wrapper.h
- 
-diff --git a/libavcodec/vulkan_av1.c b/libavcodec/vulkan_av1.c
-index 5afd5353cc..c9e398eaec 100644
---- a/libavcodec/vulkan_av1.c
-+++ b/libavcodec/vulkan_av1.c
-@@ -36,33 +36,47 @@ const FFVulkanDecodeDescriptor ff_vk_dec_av1_desc = {
- typedef struct AV1VulkanDecodePicture {
-     FFVulkanDecodePicture           vp;
- 
--    /* Workaround for a spec issue.
--     *Can be removed once no longer needed, and threading can be enabled. */
-+    /* TODO: investigate if this can be removed to make decoding completely
-+     * independent. */
-     FFVulkanDecodeContext          *dec;
- 
--    StdVideoAV1MESATile            tiles[MAX_TILES];
--    StdVideoAV1MESATileList        tile_list;
--    const uint32_t                *tile_offsets;
-+    uint32_t tile_sizes[MAX_TILES];
- 
-     /* Current picture */
--    VkVideoDecodeAV1DpbSlotInfoMESA    vkav1_ref;
--    StdVideoAV1MESAFrameHeader         av1_frame_header;
--    VkVideoDecodeAV1PictureInfoMESA    av1_pic_info;
-+    StdVideoDecodeAV1ReferenceInfo     std_ref;
-+    VkVideoDecodeAV1DpbSlotInfoKHR     vkav1_ref;
-+    uint16_t width_in_sbs_minus1[64];
-+    uint16_t height_in_sbs_minus1[64];
-+    uint16_t mi_col_starts[64];
-+    uint16_t mi_row_starts[64];
-+    StdVideoAV1TileInfo tile_info;
-+    StdVideoAV1Quantization quantization;
-+    StdVideoAV1Segmentation segmentation;
-+    StdVideoAV1LoopFilter loop_filter;
-+    StdVideoAV1CDEF cdef;
-+    StdVideoAV1LoopRestoration loop_restoration;
-+    StdVideoAV1GlobalMotion global_motion;
-+    StdVideoAV1FilmGrain film_grain;
-+    StdVideoDecodeAV1PictureInfo    std_pic_info;
-+    VkVideoDecodeAV1PictureInfoKHR     av1_pic_info;
- 
-     /* Picture refs */
-     const AV1Frame                     *ref_src   [AV1_NUM_REF_FRAMES];
--    VkVideoDecodeAV1DpbSlotInfoMESA     vkav1_refs[AV1_NUM_REF_FRAMES];
-+    StdVideoDecodeAV1ReferenceInfo      std_refs  [AV1_NUM_REF_FRAMES];
-+    VkVideoDecodeAV1DpbSlotInfoKHR      vkav1_refs[AV1_NUM_REF_FRAMES];
- 
-     uint8_t frame_id_set;
-     uint8_t frame_id;
-+    uint8_t ref_frame_sign_bias_mask;
- } AV1VulkanDecodePicture;
- 
- static int vk_av1_fill_pict(AVCodecContext *avctx, const AV1Frame **ref_src,
-                             VkVideoReferenceSlotInfoKHR *ref_slot,      /* Main structure */
-                             VkVideoPictureResourceInfoKHR *ref,         /* Goes in ^ */
--                            VkVideoDecodeAV1DpbSlotInfoMESA *vkav1_ref, /* Goes in ^ */
-+                            StdVideoDecodeAV1ReferenceInfo *vkav1_std_ref,
-+                            VkVideoDecodeAV1DpbSlotInfoKHR *vkav1_ref, /* Goes in ^ */
-                             const AV1Frame *pic, int is_current, int has_grain,
--                            int dpb_slot_index)
-+                            int *saved_order_hints)
- {
-     FFVulkanDecodeContext *dec = avctx->internal->hwaccel_priv_data;
-     AV1VulkanDecodePicture *hp = pic->hwaccel_picture_private;
-@@ -73,31 +87,42 @@ static int vk_av1_fill_pict(AVCodecContext *avctx, const AV1Frame **ref_src,
-     if (err < 0)
-         return err;
- 
--    *vkav1_ref = (VkVideoDecodeAV1DpbSlotInfoMESA) {
--        .sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_DPB_SLOT_INFO_MESA,
--        .frameIdx = hp->frame_id,
-+    *vkav1_std_ref = (StdVideoDecodeAV1ReferenceInfo) {
-+        .flags = (StdVideoDecodeAV1ReferenceInfoFlags) {
-+            .disable_frame_end_update_cdf = pic->raw_frame_header->disable_frame_end_update_cdf,
-+            .segmentation_enabled = pic->raw_frame_header->segmentation_enabled,
-+        },
-+        .frame_type = pic->raw_frame_header->frame_type,
-+        .OrderHint = pic->raw_frame_header->order_hint,
-+        .RefFrameSignBias = hp->ref_frame_sign_bias_mask,
-     };
- 
--    for (unsigned i = 0; i < 7; i++) {
--        const int idx = pic->raw_frame_header->ref_frame_idx[i];
--        vkav1_ref->ref_order_hint[i] = pic->raw_frame_header->ref_order_hint[idx];
--    }
-+    if (saved_order_hints)
-+        for (int i = 0; i < AV1_TOTAL_REFS_PER_FRAME; i++)
-+            vkav1_std_ref->SavedOrderHints[i] = saved_order_hints[i];
-+
-+    *vkav1_ref = (VkVideoDecodeAV1DpbSlotInfoKHR) {
-+        .sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_DPB_SLOT_INFO_KHR,
-+        .pStdReferenceInfo = vkav1_std_ref,
-+    };
- 
--    vkav1_ref->disable_frame_end_update_cdf = pic->raw_frame_header->disable_frame_end_update_cdf;
-+    vkav1_std_ref->flags.disable_frame_end_update_cdf = pic->raw_frame_header->disable_frame_end_update_cdf;
-+    vkav1_std_ref->flags.segmentation_enabled = pic->raw_frame_header->segmentation_enabled;
-+    vkav1_std_ref->frame_type = pic->raw_frame_header->frame_type;
- 
-     *ref = (VkVideoPictureResourceInfoKHR) {
-         .sType = VK_STRUCTURE_TYPE_VIDEO_PICTURE_RESOURCE_INFO_KHR,
-         .codedOffset = (VkOffset2D){ 0, 0 },
-         .codedExtent = (VkExtent2D){ pic->f->width, pic->f->height },
-         .baseArrayLayer = ((has_grain || dec->dedicated_dpb) && dec->layered_dpb) ?
--                          dpb_slot_index : 0,
-+                          hp->frame_id : 0,
-         .imageViewBinding = vkpic->img_view_ref,
-     };
- 
-     *ref_slot = (VkVideoReferenceSlotInfoKHR) {
-         .sType = VK_STRUCTURE_TYPE_VIDEO_REFERENCE_SLOT_INFO_KHR,
-         .pNext = vkav1_ref,
--        .slotIndex = dpb_slot_index,
-+        .slotIndex = hp->frame_id,
-         .pPictureResource = ref,
-     };
- 
-@@ -115,15 +140,40 @@ static int vk_av1_create_params(AVCodecContext *avctx, AVBufferRef **buf)
- 
-     const AV1RawSequenceHeader *seq = s->raw_seq;
- 
--    StdVideoAV1MESASequenceHeader av1_sequence_header;
--    VkVideoDecodeAV1SessionParametersAddInfoMESA av1_params_info;
--    VkVideoDecodeAV1SessionParametersCreateInfoMESA av1_params;
-+    StdVideoAV1SequenceHeader av1_sequence_header;
-+    StdVideoAV1TimingInfo av1_timing_info;
-+    StdVideoAV1ColorConfig av1_color_config;
-+    VkVideoDecodeAV1SessionParametersCreateInfoKHR av1_params;
-     VkVideoSessionParametersCreateInfoKHR session_params_create;
- 
-     int err;
- 
--    av1_sequence_header = (StdVideoAV1MESASequenceHeader) {
--        .flags = (StdVideoAV1MESASequenceHeaderFlags) {
-+    av1_timing_info = (StdVideoAV1TimingInfo) {
-+        .flags = (StdVideoAV1TimingInfoFlags) {
-+            .equal_picture_interval = seq->timing_info.equal_picture_interval,
-+        },
-+        .num_units_in_display_tick = seq->timing_info.num_units_in_display_tick,
-+        .time_scale = seq->timing_info.time_scale,
-+        .num_ticks_per_picture_minus_1 = seq->timing_info.num_ticks_per_picture_minus_1,
-+    };
-+
-+    av1_color_config = (StdVideoAV1ColorConfig) {
-+        .flags = (StdVideoAV1ColorConfigFlags) {
-+            .mono_chrome = seq->color_config.mono_chrome,
-+            .color_range = seq->color_config.color_range,
-+            .separate_uv_delta_q = seq->color_config.separate_uv_delta_q,
-+        },
-+        .BitDepth = seq->color_config.twelve_bit    ? 12 :
-+                    seq->color_config.high_bitdepth ? 10 : 8,
-+        .subsampling_x = seq->color_config.subsampling_x,
-+        .subsampling_y = seq->color_config.subsampling_y,
-+        .color_primaries = seq->color_config.color_primaries,
-+        .transfer_characteristics = seq->color_config.transfer_characteristics,
-+        .matrix_coefficients = seq->color_config.matrix_coefficients,
-+    };
-+
-+    av1_sequence_header = (StdVideoAV1SequenceHeader) {
-+        .flags = (StdVideoAV1SequenceHeaderFlags) {
-             .still_picture = seq->still_picture,
-             .reduced_still_picture_header = seq->reduced_still_picture_header,
-             .use_128x128_superblock = seq->use_128x128_superblock,
-@@ -152,34 +202,15 @@ static int vk_av1_create_params(AVCodecContext *avctx, AVBufferRef **buf)
-         .delta_frame_id_length_minus_2 = seq->delta_frame_id_length_minus_2,
-         .additional_frame_id_length_minus_1 = seq->additional_frame_id_length_minus_1,
-         .order_hint_bits_minus_1 = seq->order_hint_bits_minus_1,
--        .timing_info = (StdVideoAV1MESATimingInfo) {
--            .flags = (StdVideoAV1MESATimingInfoFlags) {
--                .equal_picture_interval = seq->timing_info.equal_picture_interval,
--            },
--            .num_units_in_display_tick = seq->timing_info.num_units_in_display_tick,
--            .time_scale = seq->timing_info.time_scale,
--            .num_ticks_per_picture_minus_1 = seq->timing_info.num_ticks_per_picture_minus_1,
--        },
--        .color_config = (StdVideoAV1MESAColorConfig) {
--            .flags = (StdVideoAV1MESAColorConfigFlags) {
--                .mono_chrome = seq->color_config.mono_chrome,
--                .color_range = seq->color_config.color_range,
--                .separate_uv_delta_q = seq->color_config.separate_uv_delta_q,
--            },
--            .bit_depth = seq->color_config.twelve_bit ? 12 :
--                         seq->color_config.high_bitdepth ? 10 : 8,
--            .subsampling_x = seq->color_config.subsampling_x,
--            .subsampling_y = seq->color_config.subsampling_y,
--        },
-+        .seq_force_integer_mv = seq->seq_force_integer_mv,
-+        .seq_force_screen_content_tools = seq->seq_force_screen_content_tools,
-+        .pTimingInfo = &av1_timing_info,
-+        .pColorConfig = &av1_color_config,
-     };
- 
--    av1_params_info = (VkVideoDecodeAV1SessionParametersAddInfoMESA) {
--        .sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_SESSION_PARAMETERS_ADD_INFO_MESA,
--        .sequence_header = &av1_sequence_header,
--    };
--    av1_params = (VkVideoDecodeAV1SessionParametersCreateInfoMESA) {
--        .sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_SESSION_PARAMETERS_CREATE_INFO_MESA,
--        .pParametersAddInfo = &av1_params_info,
-+    av1_params = (VkVideoDecodeAV1SessionParametersCreateInfoKHR) {
-+        .sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_SESSION_PARAMETERS_CREATE_INFO_KHR,
-+        .pStdSequenceHeader = &av1_sequence_header,
-     };
-     session_params_create = (VkVideoSessionParametersCreateInfoKHR) {
-         .sType = VK_STRUCTURE_TYPE_VIDEO_SESSION_PARAMETERS_CREATE_INFO_KHR,
-@@ -211,8 +242,14 @@ static int vk_av1_start_frame(AVCodecContext          *avctx,
- 
-     const AV1RawFrameHeader *frame_header = s->raw_frame_header;
-     const AV1RawFilmGrainParams *film_grain = &s->cur_frame.film_grain;
-+    CodedBitstreamAV1Context *cbs_ctx = (CodedBitstreamAV1Context *)(s->cbc->priv_data);
-+
-     const int apply_grain = !(avctx->export_side_data & AV_CODEC_EXPORT_DATA_FILM_GRAIN) &&
-                             film_grain->apply_grain;
-+    StdVideoAV1FrameRestorationType remap_lr_type[4] = { STD_VIDEO_AV1_FRAME_RESTORATION_TYPE_NONE,
-+                                                         STD_VIDEO_AV1_FRAME_RESTORATION_TYPE_SWITCHABLE,
-+                                                         STD_VIDEO_AV1_FRAME_RESTORATION_TYPE_WIENER,
-+                                                         STD_VIDEO_AV1_FRAME_RESTORATION_TYPE_SGRPROJ };
- 
-     if (!dec->session_params) {
-         err = vk_av1_create_params(avctx, &dec->session_params);
-@@ -233,15 +270,31 @@ static int vk_av1_start_frame(AVCodecContext          *avctx,
-         dec->frame_id_alloc_mask |= (1 << slot_idx);
-     }
- 
--    /* Fill in references */
--    for (int i = 0; i < AV1_NUM_REF_FRAMES; i++) {
--        const AV1Frame *ref_frame = &s->ref[i];
--        if (s->ref[i].f->pict_type == AV_PICTURE_TYPE_NONE)
-+    ap->ref_frame_sign_bias_mask = 0x0;
-+    for (int i = 0; i < STD_VIDEO_AV1_TOTAL_REFS_PER_FRAME; i++)
-+        ap->ref_frame_sign_bias_mask |= cbs_ctx->ref_frame_sign_bias[i] << i;
-+
-+    for (int i = 0; i < STD_VIDEO_AV1_REFS_PER_FRAME; i++) {
-+        const int idx = pic->raw_frame_header->ref_frame_idx[i];
-+        const AV1Frame *ref_frame = &s->ref[idx];
-+        AV1VulkanDecodePicture *hp = ref_frame->hwaccel_picture_private;
-+        int found = 0;
-+
-+        if (ref_frame->f->pict_type == AV_PICTURE_TYPE_NONE)
-+            continue;
-+
-+        for (int j = 0; j < ref_count; j++) {
-+            if (vp->ref_slots[j].slotIndex == hp->frame_id) {
-+                found = 1;
-+                break;
-+            }
-+        }
-+        if (found)
-             continue;
- 
--        err = vk_av1_fill_pict(avctx, &ap->ref_src[i], &vp->ref_slots[i],
--                               &vp->refs[i], &ap->vkav1_refs[i],
--                               ref_frame, 0, 0, i);
-+        err = vk_av1_fill_pict(avctx, &ap->ref_src[ref_count], &vp->ref_slots[ref_count],
-+                               &vp->refs[ref_count], &ap->std_refs[ref_count], &ap->vkav1_refs[ref_count],
-+                               ref_frame, 0, 0, cbs_ctx->ref[idx].saved_order_hints);
-         if (err < 0)
-             return err;
- 
-@@ -249,20 +302,32 @@ static int vk_av1_start_frame(AVCodecContext          *avctx,
-     }
- 
-     err = vk_av1_fill_pict(avctx, NULL, &vp->ref_slot, &vp->ref,
-+                           &ap->std_ref,
-                            &ap->vkav1_ref,
--                           pic, 1, apply_grain, 8);
-+                           pic, 1, apply_grain, NULL);
-     if (err < 0)
-         return err;
- 
--    ap->tile_list.nb_tiles = 0;
--    ap->tile_list.tile_list = ap->tiles;
--
--    ap->av1_pic_info = (VkVideoDecodeAV1PictureInfoMESA) {
--        .sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_PICTURE_INFO_MESA,
--        .frame_header = &ap->av1_frame_header,
--        .tile_list = &ap->tile_list,
-+    ap->av1_pic_info = (VkVideoDecodeAV1PictureInfoKHR) {
-+        .sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_PICTURE_INFO_KHR,
-+        .pStdPictureInfo = &ap->std_pic_info,
-+        .frameHeaderOffset = 0,
-+        .tileCount = 0,
-+        .pTileOffsets = NULL,
-+        .pTileSizes = ap->tile_sizes,
-     };
- 
-+    for (int i = 0; i < STD_VIDEO_AV1_REFS_PER_FRAME; i++) {
-+        const int idx = pic->raw_frame_header->ref_frame_idx[i];
-+        const AV1Frame *ref_frame = &s->ref[idx];
-+        AV1VulkanDecodePicture *hp = ref_frame->hwaccel_picture_private;
-+
-+        if (ref_frame->f->pict_type == AV_PICTURE_TYPE_NONE)
-+            ap->av1_pic_info.referenceNameSlotIndices[i] = AV1_REF_FRAME_NONE;
-+        else
-+            ap->av1_pic_info.referenceNameSlotIndices[i] = hp->frame_id;
-+    }
-+
-     vp->decode_info = (VkVideoDecodeInfoKHR) {
-         .sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_INFO_KHR,
-         .pNext = &ap->av1_pic_info,
-@@ -279,9 +344,87 @@ static int vk_av1_start_frame(AVCodecContext          *avctx,
-         },
-     };
- 
-+    ap->tile_info = (StdVideoAV1TileInfo) {
-+        .flags = (StdVideoAV1TileInfoFlags) {
-+            .uniform_tile_spacing_flag = frame_header->uniform_tile_spacing_flag,
-+        },
-+        .TileCols = frame_header->tile_cols,
-+        .TileRows = frame_header->tile_rows,
-+        .context_update_tile_id = frame_header->context_update_tile_id,
-+        .tile_size_bytes_minus_1 = frame_header->tile_size_bytes_minus1,
-+        .pWidthInSbsMinus1 = ap->width_in_sbs_minus1,
-+        .pHeightInSbsMinus1 = ap->height_in_sbs_minus1,
-+        .pMiColStarts = ap->mi_col_starts,
-+        .pMiRowStarts = ap->mi_row_starts,
-+    };
-+
-+    ap->quantization = (StdVideoAV1Quantization) {
-+        .flags.using_qmatrix = frame_header->using_qmatrix,
-+        .flags.diff_uv_delta = frame_header->diff_uv_delta,
-+        .base_q_idx = frame_header->base_q_idx,
-+        .DeltaQYDc = frame_header->delta_q_y_dc,
-+        .DeltaQUDc = frame_header->delta_q_u_dc,
-+        .DeltaQUAc = frame_header->delta_q_u_ac,
-+        .DeltaQVDc = frame_header->delta_q_v_dc,
-+        .DeltaQVAc = frame_header->delta_q_v_ac,
-+        .qm_y = frame_header->qm_y,
-+        .qm_u = frame_header->qm_u,
-+        .qm_v = frame_header->qm_v,
-+    };
-+
-+    ap->loop_filter = (StdVideoAV1LoopFilter) {
-+        .flags = (StdVideoAV1LoopFilterFlags) {
-+            .loop_filter_delta_enabled = frame_header->loop_filter_delta_enabled,
-+            .loop_filter_delta_update = frame_header->loop_filter_delta_update,
-+        },
-+        .loop_filter_sharpness = frame_header->loop_filter_sharpness,
-+    };
-+
-+    for (int i = 0; i < STD_VIDEO_AV1_MAX_LOOP_FILTER_STRENGTHS; i++)
-+        ap->loop_filter.loop_filter_level[i] = frame_header->loop_filter_level[i];
-+    for (int i = 0; i < STD_VIDEO_AV1_LOOP_FILTER_ADJUSTMENTS; i++)
-+        ap->loop_filter.loop_filter_mode_deltas[i] = frame_header->loop_filter_mode_deltas[i];
-+
-+    ap->cdef = (StdVideoAV1CDEF) {
-+        .cdef_damping_minus_3 = frame_header->cdef_damping_minus_3,
-+        .cdef_bits = frame_header->cdef_bits,
-+    };
-+
-+    ap->loop_restoration = (StdVideoAV1LoopRestoration) {
-+        .FrameRestorationType[0] = remap_lr_type[frame_header->lr_type[0]],
-+        .FrameRestorationType[1] = remap_lr_type[frame_header->lr_type[1]],
-+        .FrameRestorationType[2] = remap_lr_type[frame_header->lr_type[2]],
-+        .LoopRestorationSize[0] = 1 + frame_header->lr_unit_shift,
-+        .LoopRestorationSize[1] = 1 + frame_header->lr_unit_shift - frame_header->lr_uv_shift,
-+        .LoopRestorationSize[2] = 1 + frame_header->lr_unit_shift - frame_header->lr_uv_shift,
-+    };
-+
-+    ap->film_grain = (StdVideoAV1FilmGrain) {
-+        .flags = (StdVideoAV1FilmGrainFlags) {
-+            .chroma_scaling_from_luma = film_grain->chroma_scaling_from_luma,
-+            .overlap_flag = film_grain->overlap_flag,
-+            .clip_to_restricted_range = film_grain->clip_to_restricted_range,
-+        },
-+        .grain_scaling_minus_8 = film_grain->grain_scaling_minus_8,
-+        .ar_coeff_lag = film_grain->ar_coeff_lag,
-+        .ar_coeff_shift_minus_6 = film_grain->ar_coeff_shift_minus_6,
-+        .grain_scale_shift = film_grain->grain_scale_shift,
-+        .grain_seed = film_grain->grain_seed,
-+        .film_grain_params_ref_idx = film_grain->film_grain_params_ref_idx,
-+        .num_y_points = film_grain->num_y_points,
-+        .num_cb_points = film_grain->num_cb_points,
-+        .num_cr_points = film_grain->num_cr_points,
-+        .cb_mult = film_grain->cb_mult,
-+        .cb_luma_mult = film_grain->cb_luma_mult,
-+        .cb_offset = film_grain->cb_offset,
-+        .cr_mult = film_grain->cr_mult,
-+        .cr_luma_mult = film_grain->cr_luma_mult,
-+        .cr_offset = film_grain->cr_offset,
-+    };
-+
-     /* Setup frame header */
--    ap->av1_frame_header = (StdVideoAV1MESAFrameHeader) {
--        .flags = (StdVideoAV1MESAFrameHeaderFlags) {
-+    ap->std_pic_info = (StdVideoDecodeAV1PictureInfo) {
-+        .flags = (StdVideoDecodeAV1PictureInfoFlags) {
-             .error_resilient_mode = frame_header->error_resilient_mode,
-             .disable_cdf_update = frame_header->disable_cdf_update,
-             .use_superres = frame_header->use_superres,
-@@ -302,174 +445,92 @@ static int vk_av1_start_frame(AVCodecContext          *avctx,
-             .reference_select = frame_header->reference_select,
-             .skip_mode_present = frame_header->skip_mode_present,
-             .delta_q_present = frame_header->delta_q_present,
-+            .delta_lf_present = frame_header->delta_lf_present,
-+            .delta_lf_multi = frame_header->delta_lf_multi,
-+            .segmentation_enabled = frame_header->segmentation_enabled,
-+            .segmentation_update_map = frame_header->segmentation_update_map,
-+            .segmentation_temporal_update = frame_header->segmentation_temporal_update,
-+            .segmentation_update_data = frame_header->segmentation_update_data,
-+            .UsesLr = frame_header->lr_type[0] || frame_header->lr_type[1] || frame_header->lr_type[2],
-+            .apply_grain = apply_grain,
-         },
--        .frame_to_show_map_idx = frame_header->frame_to_show_map_idx,
--        .frame_presentation_time = frame_header->frame_presentation_time,
--        .display_frame_id = frame_header->display_frame_id,
-         .frame_type = frame_header->frame_type,
-         .current_frame_id = frame_header->current_frame_id,
--        .order_hint = frame_header->order_hint,
-+        .OrderHint = frame_header->order_hint,
-         .primary_ref_frame = frame_header->primary_ref_frame,
--        .frame_width_minus_1 = frame_header->frame_width_minus_1,
--        .frame_height_minus_1 = frame_header->frame_height_minus_1,
--        .coded_denom = frame_header->coded_denom,
--        .render_width_minus_1 = frame_header->render_width_minus_1,
--        .render_height_minus_1 = frame_header->render_height_minus_1,
-         .refresh_frame_flags = frame_header->refresh_frame_flags,
-         .interpolation_filter = frame_header->interpolation_filter,
--        .tx_mode = frame_header->tx_mode,
--        .tiling = (StdVideoAV1MESATileInfo) {
--            .flags = (StdVideoAV1MESATileInfoFlags) {
--                .uniform_tile_spacing_flag = frame_header->uniform_tile_spacing_flag,
--            },
--            .tile_cols = frame_header->tile_cols,
--            .tile_rows = frame_header->tile_rows,
--            .context_update_tile_id = frame_header->context_update_tile_id,
--            .tile_size_bytes_minus1 = frame_header->tile_size_bytes_minus1,
--        },
--        .quantization = (StdVideoAV1MESAQuantization) {
--            .flags.using_qmatrix = frame_header->using_qmatrix,
--            .base_q_idx = frame_header->base_q_idx,
--            .delta_q_y_dc = frame_header->delta_q_y_dc,
--            .diff_uv_delta = frame_header->diff_uv_delta,
--            .delta_q_u_dc = frame_header->delta_q_u_dc,
--            .delta_q_u_ac = frame_header->delta_q_u_ac,
--            .delta_q_v_dc = frame_header->delta_q_v_dc,
--            .delta_q_v_ac = frame_header->delta_q_v_ac,
--            .qm_y = frame_header->qm_y,
--            .qm_u = frame_header->qm_u,
--            .qm_v = frame_header->qm_v,
--        },
--        .delta_q = (StdVideoAV1MESADeltaQ) {
--            .flags = (StdVideoAV1MESADeltaQFlags) {
--                .delta_lf_present = frame_header->delta_lf_present,
--                .delta_lf_multi = frame_header->delta_lf_multi,
--            },
--            .delta_q_res = frame_header->delta_q_res,
--            .delta_lf_res = frame_header->delta_lf_res,
--        },
--        .loop_filter = (StdVideoAV1MESALoopFilter) {
--            .flags = (StdVideoAV1MESALoopFilterFlags) {
--                .delta_enabled = frame_header->loop_filter_delta_enabled,
--                .delta_update = frame_header->loop_filter_delta_update,
--            },
--            .level = {
--                frame_header->loop_filter_level[0], frame_header->loop_filter_level[1],
--                frame_header->loop_filter_level[2], frame_header->loop_filter_level[3],
--            },
--            .sharpness = frame_header->loop_filter_sharpness,
--            .mode_deltas = {
--                frame_header->loop_filter_mode_deltas[0], frame_header->loop_filter_mode_deltas[1],
--            },
--        },
--        .cdef = (StdVideoAV1MESACDEF) {
--            .damping_minus_3 = frame_header->cdef_damping_minus_3,
--            .bits = frame_header->cdef_bits,
--        },
--        .lr = (StdVideoAV1MESALoopRestoration) {
--            .lr_unit_shift = frame_header->lr_unit_shift,
--            .lr_uv_shift = frame_header->lr_uv_shift,
--            .lr_type = { frame_header->lr_type[0], frame_header->lr_type[1], frame_header->lr_type[2] },
--        },
--        .segmentation = (StdVideoAV1MESASegmentation) {
--            .flags = (StdVideoAV1MESASegmentationFlags) {
--                .enabled = frame_header->segmentation_enabled,
--                .update_map = frame_header->segmentation_update_map,
--                .temporal_update = frame_header->segmentation_temporal_update,
--                .update_data = frame_header->segmentation_update_data,
--            },
--        },
--        .film_grain = (StdVideoAV1MESAFilmGrainParameters) {
--            .flags = (StdVideoAV1MESAFilmGrainFlags) {
--                .apply_grain = apply_grain,
--                .chroma_scaling_from_luma = film_grain->chroma_scaling_from_luma,
--                .overlap_flag = film_grain->overlap_flag,
--                .clip_to_restricted_range = film_grain->clip_to_restricted_range,
--            },
--            .grain_scaling_minus_8 = film_grain->grain_scaling_minus_8,
--            .ar_coeff_lag = film_grain->ar_coeff_lag,
--            .ar_coeff_shift_minus_6 = film_grain->ar_coeff_shift_minus_6,
--            .grain_scale_shift = film_grain->grain_scale_shift,
--            .grain_seed = film_grain->grain_seed,
--            .num_y_points = film_grain->num_y_points,
--            .num_cb_points = film_grain->num_cb_points,
--            .num_cr_points = film_grain->num_cr_points,
--            .cb_mult = film_grain->cb_mult,
--            .cb_luma_mult = film_grain->cb_luma_mult,
--            .cb_offset = film_grain->cb_offset,
--            .cr_mult = film_grain->cr_mult,
--            .cr_luma_mult = film_grain->cr_luma_mult,
--            .cr_offset = film_grain->cr_offset,
--        },
-+        .TxMode = frame_header->tx_mode,
-+        .delta_q_res = frame_header->delta_q_res,
-+        .delta_lf_res = frame_header->delta_lf_res,
-+        .SkipModeFrame[0] = s->cur_frame.skip_mode_frame_idx[0],
-+        .SkipModeFrame[1] = s->cur_frame.skip_mode_frame_idx[1],
-+        .coded_denom = frame_header->coded_denom,
-+        .pTileInfo = &ap->tile_info,
-+        .pQuantization = &ap->quantization,
-+        .pSegmentation = &ap->segmentation,
-+        .pLoopFilter = &ap->loop_filter,
-+        .pCDEF = &ap->cdef,
-+        .pLoopRestoration = &ap->loop_restoration,
-+        .pGlobalMotion = &ap->global_motion,
-+        .pFilmGrain = apply_grain ? &ap->film_grain : NULL,
-     };
- 
-     for (int i = 0; i < 64; i++) {
--        ap->av1_frame_header.tiling.width_in_sbs_minus_1[i] = frame_header->width_in_sbs_minus_1[i];
--        ap->av1_frame_header.tiling.height_in_sbs_minus_1[i] = frame_header->height_in_sbs_minus_1[i];
--        ap->av1_frame_header.tiling.tile_start_col_sb[i] = frame_header->tile_start_col_sb[i];
--        ap->av1_frame_header.tiling.tile_start_row_sb[i] = frame_header->tile_start_row_sb[i];
-+        ap->width_in_sbs_minus1[i] = frame_header->width_in_sbs_minus_1[i];
-+        ap->height_in_sbs_minus1[i] = frame_header->height_in_sbs_minus_1[i];
-+        ap->mi_col_starts[i] = frame_header->tile_start_col_sb[i];
-+        ap->mi_row_starts[i] = frame_header->tile_start_row_sb[i];
-     }
- 
--    for (int i = 0; i < 8; i++) {
--        ap->av1_frame_header.segmentation.feature_enabled_bits[i] = 0;
--        for (int j = 0; j < 8; j++) {
--            ap->av1_frame_header.segmentation.feature_enabled_bits[i] |= (frame_header->feature_enabled[i][j] << j);
--            ap->av1_frame_header.segmentation.feature_data[i][j] = frame_header->feature_value[i][j];
-+    for (int i = 0; i < STD_VIDEO_AV1_MAX_SEGMENTS; i++) {
-+        ap->segmentation.FeatureEnabled[i] = 0x0;
-+        for (int j = 0; j < STD_VIDEO_AV1_SEG_LVL_MAX; j++) {
-+            ap->segmentation.FeatureEnabled[i] |= (frame_header->feature_enabled[i][j] << j);
-+            ap->segmentation.FeatureData[i][j] = frame_header->feature_value[i][j];
-         }
--
--        ap->av1_frame_header.loop_filter.ref_deltas[i] = frame_header->loop_filter_ref_deltas[i];
--
--        ap->av1_frame_header.cdef.y_pri_strength[i] = frame_header->cdef_y_pri_strength[i];
--        ap->av1_frame_header.cdef.y_sec_strength[i] = frame_header->cdef_y_sec_strength[i];
--        ap->av1_frame_header.cdef.uv_pri_strength[i] = frame_header->cdef_uv_pri_strength[i];
--        ap->av1_frame_header.cdef.uv_sec_strength[i] = frame_header->cdef_uv_sec_strength[i];
--
--        ap->av1_frame_header.ref_order_hint[i] = frame_header->ref_order_hint[i];
--        ap->av1_frame_header.global_motion[i] = (StdVideoAV1MESAGlobalMotion) {
--            .flags = (StdVideoAV1MESAGlobalMotionFlags) {
--                .gm_invalid = s->cur_frame.gm_invalid[i],
--            },
--            .gm_type = s->cur_frame.gm_type[i],
--            .gm_params = {
--                s->cur_frame.gm_params[i][0], s->cur_frame.gm_params[i][1],
--                s->cur_frame.gm_params[i][2], s->cur_frame.gm_params[i][3],
--                s->cur_frame.gm_params[i][4], s->cur_frame.gm_params[i][5],
--            },
--        };
-     }
- 
--    for (int i = 0; i < 7; i++) {
--        ap->av1_frame_header.ref_frame_idx[i] = frame_header->ref_frame_idx[i];
--        ap->av1_frame_header.delta_frame_id_minus1[i] = frame_header->delta_frame_id_minus1[i];
-+    for (int i = 0; i < STD_VIDEO_AV1_TOTAL_REFS_PER_FRAME; i++)
-+        ap->loop_filter.loop_filter_ref_deltas[i] = frame_header->loop_filter_ref_deltas[i];
-+
-+    for (int i = 0; i < STD_VIDEO_AV1_MAX_CDEF_FILTER_STRENGTHS; i++) {
-+        ap->cdef.cdef_y_pri_strength[i] = frame_header->cdef_y_pri_strength[i];
-+        ap->cdef.cdef_y_sec_strength[i] = frame_header->cdef_y_sec_strength[i];
-+        ap->cdef.cdef_uv_pri_strength[i] = frame_header->cdef_uv_pri_strength[i];
-+        ap->cdef.cdef_uv_sec_strength[i] = frame_header->cdef_uv_sec_strength[i];
-     }
- 
--    ap->av1_pic_info.skip_mode_frame_idx[0] = s->cur_frame.skip_mode_frame_idx[0];
--    ap->av1_pic_info.skip_mode_frame_idx[1] = s->cur_frame.skip_mode_frame_idx[1];
-+    for (int i = 0; i < STD_VIDEO_AV1_NUM_REF_FRAMES; i++) {
-+        ap->std_pic_info.OrderHints[i] = frame_header->ref_order_hint[i];
-+        ap->global_motion.GmType[i] = s->cur_frame.gm_type[i];
-+        for (int j = 0; j < STD_VIDEO_AV1_GLOBAL_MOTION_PARAMS; j++) {
-+            ap->global_motion.gm_params[i][j] = s->cur_frame.gm_params[i][j];
-+        }
-+    }
- 
-     if (apply_grain) {
--        for (int i = 0; i < 14; i++) {
--            ap->av1_frame_header.film_grain.point_y_value[i] = film_grain->point_y_value[i];
--            ap->av1_frame_header.film_grain.point_y_scaling[i] = film_grain->point_y_scaling[i];
-+        for (int i = 0; i < STD_VIDEO_AV1_MAX_NUM_Y_POINTS; i++) {
-+            ap->film_grain.point_y_value[i] = film_grain->point_y_value[i];
-+            ap->film_grain.point_y_scaling[i] = film_grain->point_y_scaling[i];
-         }
- 
--        for (int i = 0; i < 10; i++) {
--            ap->av1_frame_header.film_grain.point_cb_value[i] = film_grain->point_cb_value[i];
--            ap->av1_frame_header.film_grain.point_cb_scaling[i] = film_grain->point_cb_scaling[i];
--            ap->av1_frame_header.film_grain.point_cr_value[i] = film_grain->point_cr_value[i];
--            ap->av1_frame_header.film_grain.point_cr_scaling[i] = film_grain->point_cr_scaling[i];
-+        for (int i = 0; i < STD_VIDEO_AV1_MAX_NUM_CB_POINTS; i++) {
-+            ap->film_grain.point_cb_value[i] = film_grain->point_cb_value[i];
-+            ap->film_grain.point_cb_scaling[i] = film_grain->point_cb_scaling[i];
-+            ap->film_grain.point_cr_value[i] = film_grain->point_cr_value[i];
-+            ap->film_grain.point_cr_scaling[i] = film_grain->point_cr_scaling[i];
-         }
- 
--        for (int i = 0; i < 24; i++) {
--            ap->av1_frame_header.film_grain.ar_coeffs_y_plus_128[i] = film_grain->ar_coeffs_y_plus_128[i];
--            ap->av1_frame_header.film_grain.ar_coeffs_cb_plus_128[i] = film_grain->ar_coeffs_cb_plus_128[i];
--            ap->av1_frame_header.film_grain.ar_coeffs_cr_plus_128[i] = film_grain->ar_coeffs_cr_plus_128[i];
--        }
-+        for (int i = 0; i < STD_VIDEO_AV1_MAX_NUM_POS_LUMA; i++)
-+            ap->film_grain.ar_coeffs_y_plus_128[i] = film_grain->ar_coeffs_y_plus_128[i];
- 
--        ap->av1_frame_header.film_grain.ar_coeffs_cb_plus_128[24] = film_grain->ar_coeffs_cb_plus_128[24];
--        ap->av1_frame_header.film_grain.ar_coeffs_cr_plus_128[24] = film_grain->ar_coeffs_cr_plus_128[24];
-+        for (int i = 0; i < STD_VIDEO_AV1_MAX_NUM_POS_CHROMA; i++) {
-+            ap->film_grain.ar_coeffs_cb_plus_128[i] = film_grain->ar_coeffs_cb_plus_128[i];
-+            ap->film_grain.ar_coeffs_cr_plus_128[i] = film_grain->ar_coeffs_cr_plus_128[i];
-+        }
-     }
- 
--    /* Workaround for a spec issue. */
-     ap->dec = dec;
- 
-     return 0;
-@@ -484,25 +545,20 @@ static int vk_av1_decode_slice(AVCodecContext *avctx,
-     AV1VulkanDecodePicture *ap = s->cur_frame.hwaccel_picture_private;
-     FFVulkanDecodePicture *vp = &ap->vp;
- 
-+    /* Too many tiles, exceeding all defined levels in the AV1 spec */
-+    if (ap->av1_pic_info.tileCount > MAX_TILES)
-+        return AVERROR(ENOSYS);
-+
-     for (int i = s->tg_start; i <= s->tg_end; i++) {
--        ap->tiles[ap->tile_list.nb_tiles] = (StdVideoAV1MESATile) {
--            .size     = s->tile_group_info[i].tile_size,
--            .offset   = s->tile_group_info[i].tile_offset,
--            .row      = s->tile_group_info[i].tile_row,
--            .column   = s->tile_group_info[i].tile_column,
--            .tg_start = s->tg_start,
--            .tg_end   = s->tg_end,
--        };
-+        ap->tile_sizes[ap->av1_pic_info.tileCount] = s->tile_group_info[i].tile_size;
- 
-         err = ff_vk_decode_add_slice(avctx, vp,
-                                      data + s->tile_group_info[i].tile_offset,
-                                      s->tile_group_info[i].tile_size, 0,
--                                     &ap->tile_list.nb_tiles,
--                                     &ap->tile_offsets);
-+                                     &ap->av1_pic_info.tileCount,
-+                                     &ap->av1_pic_info.pTileOffsets);
-         if (err < 0)
-             return err;
--
--        ap->tiles[ap->tile_list.nb_tiles - 1].offset = ap->tile_offsets[ap->tile_list.nb_tiles - 1];
-     }
- 
-     return 0;
-@@ -518,7 +574,7 @@ static int vk_av1_end_frame(AVCodecContext *avctx)
-     FFVulkanDecodePicture *rvp[AV1_NUM_REF_FRAMES] = { 0 };
-     AVFrame *rav[AV1_NUM_REF_FRAMES] = { 0 };
- 
--    if (!ap->tile_list.nb_tiles)
-+    if (!ap->av1_pic_info.tileCount)
-         return 0;
- 
-     if (!dec->session_params) {
-@@ -536,7 +592,7 @@ static int vk_av1_end_frame(AVCodecContext *avctx)
-     }
- 
-     av_log(avctx, AV_LOG_VERBOSE, "Decoding frame, %"SIZE_SPECIFIER" bytes, %i tiles\n",
--           vp->slices_size, ap->tile_list.nb_tiles);
-+           vp->slices_size, ap->av1_pic_info.tileCount);
- 
-     return ff_vk_decode_frame(avctx, pic->f, vp, rav, rvp);
- }
-@@ -580,8 +636,6 @@ const FFHWAccel ff_av1_vulkan_hwaccel = {
-      * flexibility, this index cannot be present anywhere.
-      * The current implementation tracks the index for the driver and submits it
-      * as necessary information. Due to needing to modify the decoding context,
--     * which is not thread-safe, on frame free, threading is disabled.
--     * In the future, once this is fixed in the spec, the workarounds may be removed
--     * and threading enabled. */
-+     * which is not thread-safe, on frame free, threading is disabled. */
-     .caps_internal         = HWACCEL_CAP_ASYNC_SAFE,
- };
---- ffmpeg-6.1.1/libavcodec/vulkan_decode.c.orig	2023-11-11 01:25:17.000000000 +0100
-+++ ffmpeg-6.1.1/libavcodec/vulkan_decode.c	2024-04-15 21:49:59.451325544 +0200
-@@ -50,7 +50,7 @@ static const VkVideoProfileInfoKHR *get_
-     VkStructureType profile_struct_type =
-         codec_id == AV_CODEC_ID_H264 ? VK_STRUCTURE_TYPE_VIDEO_DECODE_H264_PROFILE_INFO_KHR :
-         codec_id == AV_CODEC_ID_HEVC ? VK_STRUCTURE_TYPE_VIDEO_DECODE_H265_PROFILE_INFO_KHR :
--        codec_id == AV_CODEC_ID_AV1  ? VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_PROFILE_INFO_MESA :
-+        codec_id == AV_CODEC_ID_AV1  ? VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_PROFILE_INFO_KHR :
-         0;
- 
-     profile_list = ff_vk_find_struct(ctx->s.hwfc->create_pnext,
-@@ -663,7 +663,7 @@ static VkResult vulkan_setup_profile(AVC
-                                      const struct FFVkCodecMap *vk_codec,
-                                      VkVideoDecodeH264CapabilitiesKHR *h264_caps,
-                                      VkVideoDecodeH265CapabilitiesKHR *h265_caps,
--                                     VkVideoDecodeAV1CapabilitiesMESA *av1_caps,
-+                                     VkVideoDecodeAV1CapabilitiesKHR *av1_caps,
-                                      VkVideoCapabilitiesKHR *caps,
-                                      VkVideoDecodeCapabilitiesKHR *dec_caps,
-                                      int cur_profile)
-@@ -674,7 +674,7 @@ static VkResult vulkan_setup_profile(AVC
- 
-     VkVideoDecodeH264ProfileInfoKHR *h264_profile = &prof->h264_profile;
-     VkVideoDecodeH265ProfileInfoKHR *h265_profile = &prof->h265_profile;
--    VkVideoDecodeAV1ProfileInfoMESA *av1_profile  = &prof->av1_profile;
-+    VkVideoDecodeAV1ProfileInfoKHR *av1_profile  = &prof->av1_profile;
- 
-     const AVPixFmtDescriptor *desc = av_pix_fmt_desc_get(avctx->sw_pix_fmt);
-     if (!desc)
-@@ -702,8 +702,9 @@ static VkResult vulkan_setup_profile(AVC
-     } else if (avctx->codec_id == AV_CODEC_ID_AV1) {
-         dec_caps->pNext = av1_caps;
-         usage->pNext = av1_profile;
--        av1_profile->sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_PROFILE_INFO_MESA;
--        av1_profile->stdProfileIdc = cur_profile;
-+        av1_profile->sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_PROFILE_INFO_KHR;
-+        av1_profile->stdProfile = cur_profile;
-+        av1_profile->filmGrainSupport = !(avctx->export_side_data & AV_CODEC_EXPORT_DATA_FILM_GRAIN);
-     }
- 
-     usage->sType           = VK_STRUCTURE_TYPE_VIDEO_DECODE_USAGE_INFO_KHR;
-@@ -758,8 +759,8 @@ static int vulkan_decode_get_profile(AVC
-     VkVideoDecodeH265CapabilitiesKHR h265_caps = {
-         .sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_H265_CAPABILITIES_KHR,
-     };
--    VkVideoDecodeAV1CapabilitiesMESA av1_caps = {
--        .sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_CAPABILITIES_MESA,
-+    VkVideoDecodeAV1CapabilitiesKHR av1_caps = {
-+        .sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_CAPABILITIES_KHR,
-     };
- 
-     VkPhysicalDeviceVideoFormatInfoKHR fmt_info = {
-@@ -782,7 +783,7 @@ static int vulkan_decode_get_profile(AVC
-     cur_profile = avctx->profile;
-     base_profile = avctx->codec_id == AV_CODEC_ID_H264 ? AV_PROFILE_H264_CONSTRAINED_BASELINE :
-                    avctx->codec_id == AV_CODEC_ID_H265 ? AV_PROFILE_HEVC_MAIN :
--                   avctx->codec_id == AV_CODEC_ID_AV1  ? STD_VIDEO_AV1_MESA_PROFILE_MAIN :
-+                   avctx->codec_id == AV_CODEC_ID_AV1  ? STD_VIDEO_AV1_PROFILE_MAIN :
-                    0;
- 
-     ret = vulkan_setup_profile(avctx, prof, hwctx, vk, vk_codec,
-@@ -830,7 +831,7 @@ static int vulkan_decode_get_profile(AVC
- 
-     max_level = avctx->codec_id == AV_CODEC_ID_H264 ? ff_vk_h264_level_to_av(h264_caps.maxLevelIdc) :
-                 avctx->codec_id == AV_CODEC_ID_H265 ? ff_vk_h265_level_to_av(h265_caps.maxLevelIdc) :
--                avctx->codec_id == AV_CODEC_ID_AV1  ? av1_caps.maxLevelIdc  :
-+                avctx->codec_id == AV_CODEC_ID_AV1  ? av1_caps.maxLevel :
-                 0;
- 
-     av_log(avctx, AV_LOG_VERBOSE, "Decoder capabilities for %s profile \"%s\":\n",
-@@ -901,17 +902,11 @@ static int vulkan_decode_get_profile(AVC
-                "VK_VIDEO_DECODE_CAPABILITY_DPB_AND_OUTPUT_COINCIDE_BIT_KHR set "
-                "but VK_VIDEO_CAPABILITY_SEPARATE_REFERENCE_IMAGES_BIT_KHR is unset!\n");
-         return AVERROR_EXTERNAL;
--    } else if (!(dec_caps->flags & VK_VIDEO_DECODE_CAPABILITY_DPB_AND_OUTPUT_DISTINCT_BIT_KHR) &&
--               avctx->codec_id == AV_CODEC_ID_AV1) {
--        av_log(avctx, AV_LOG_ERROR, "Cannot initialize Vulkan decoding session, buggy driver: "
--               "codec is AV1, but VK_VIDEO_DECODE_CAPABILITY_DPB_AND_OUTPUT_DISTINCT_BIT_KHR isn't set!\n");
--        return AVERROR_EXTERNAL;
-     }
- 
-     /* TODO: make dedicated_dpb tunable */
-     dec->dedicated_dpb = !(dec_caps->flags & VK_VIDEO_DECODE_CAPABILITY_DPB_AND_OUTPUT_COINCIDE_BIT_KHR);
-     dec->layered_dpb = !(caps->flags & VK_VIDEO_CAPABILITY_SEPARATE_REFERENCE_IMAGES_BIT_KHR);
--    dec->external_fg = av1_caps.flags & VK_VIDEO_DECODE_AV1_CAPABILITY_EXTERNAL_FILM_GRAIN_MESA;
- 
-     if (dec->dedicated_dpb) {
-         fmt_info.imageUsage = VK_IMAGE_USAGE_VIDEO_DECODE_DPB_BIT_KHR;
-@@ -1118,8 +1113,10 @@ int ff_vk_decode_init(AVCodecContext *av
-     VkVideoDecodeH265SessionParametersCreateInfoKHR h265_params = {
-         .sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_H265_SESSION_PARAMETERS_CREATE_INFO_KHR,
-     };
--    VkVideoDecodeAV1SessionParametersCreateInfoMESA av1_params = {
--        .sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_SESSION_PARAMETERS_CREATE_INFO_MESA,
-+    StdVideoAV1SequenceHeader av1_empty_seq = { 0 };
-+    VkVideoDecodeAV1SessionParametersCreateInfoKHR av1_params = {
-+        .sType = VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_SESSION_PARAMETERS_CREATE_INFO_KHR,
-+        .pStdSequenceHeader = &av1_empty_seq,
-     };
-     VkVideoSessionParametersCreateInfoKHR session_params_create = {
-         .sType = VK_STRUCTURE_TYPE_VIDEO_SESSION_PARAMETERS_CREATE_INFO_KHR,
-diff --git a/libavcodec/vulkan_decode.h b/libavcodec/vulkan_decode.h
-index a43e328d73..7ba8b239cb 100644
---- a/libavcodec/vulkan_decode.h
-+++ b/libavcodec/vulkan_decode.h
-@@ -37,7 +37,7 @@ typedef struct FFVulkanDecodeDescriptor {
- typedef struct FFVulkanDecodeProfileData {
-     VkVideoDecodeH264ProfileInfoKHR h264_profile;
-     VkVideoDecodeH265ProfileInfoKHR h265_profile;
--    VkVideoDecodeAV1ProfileInfoMESA av1_profile;
-+    VkVideoDecodeAV1ProfileInfoKHR av1_profile;
-     VkVideoDecodeUsageInfoKHR usage;
-     VkVideoProfileInfoKHR profile;
-     VkVideoProfileListInfoKHR profile_list;
---- ffmpeg-6.1.1/libavcodec/vulkan_video.h.orig	2024-04-15 21:35:22.599409192 +0200
-+++ ffmpeg-6.1.1/libavcodec/vulkan_video.h	2024-04-15 21:50:11.117929007 +0200
-@@ -23,8 +23,6 @@
- #include "vulkan.h"
- 
- #include <vk_video/vulkan_video_codecs_common.h>
--#include "vulkan_video_codec_av1std_mesa.h"
--#include "vulkan_video_codec_av1std_decode_mesa.h"
- 
- #define CODEC_VER_MAJ(ver) (ver >> 22)
- #define CODEC_VER_MIN(ver) ((ver >> 12) & ((1 << 10) - 1))
-diff --git a/libavcodec/vulkan_video_codec_av1std_decode.h b/libavcodec/vulkan_video_codec_av1std_decode.h
-deleted file mode 100644
-index e2f37b4e6e..0000000000
---- a/libavcodec/vulkan_video_codec_av1std_decode_mesa.h
-+++ /dev/null
-@@ -1,36 +0,0 @@
--/* Copyright 2023 Lynne
-- * Copyright 2023 Dave Airlie
-- *
-- * Licensed under the Apache License, Version 2.0 (the "License");
-- * you may not use this file except in compliance with the License.
-- * You may obtain a copy of the License at
-- *
-- * http://www.apache.org/licenses/LICENSE-2.0
-- *
-- * Unless required by applicable law or agreed to in writing, software
-- * distributed under the License is distributed on an "AS IS" BASIS,
-- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-- * See the License for the specific language governing permissions and
-- * limitations under the License.
-- */
--
--#ifndef VULKAN_VIDEO_CODEC_AV1STD_DECODE_MESA_H_
--#define VULKAN_VIDEO_CODEC_AV1STD_DECODE_MESA_H_ 1
--
--/*
--** This header is NOT YET generated from the Khronos Vulkan XML API Registry.
--**
--*/
--
--#ifdef __cplusplus
--extern "C" {
--#endif
--#define vulkan_video_codec_av1std_decode 1
--
--
--
--#ifdef __cplusplus
--}
--#endif
--
--#endif
-diff --git a/libavcodec/vulkan_video_codec_av1std.h b/libavcodec/vulkan_video_codec_av1std.h
-deleted file mode 100644
-index c91589eee2..0000000000
---- a/libavcodec/vulkan_video_codec_av1std_mesa.h
-+++ /dev/null
-@@ -1,403 +0,0 @@
--/* Copyright 2023 Lynne
-- * Copyright 2023 Dave Airlie
-- *
-- * Licensed under the Apache License, Version 2.0 (the "License");
-- * you may not use this file except in compliance with the License.
-- * You may obtain a copy of the License at
-- *
-- * http://www.apache.org/licenses/LICENSE-2.0
-- *
-- * Unless required by applicable law or agreed to in writing, software
-- * distributed under the License is distributed on an "AS IS" BASIS,
-- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-- * See the License for the specific language governing permissions and
-- * limitations under the License.
-- */
--
--#ifndef VULKAN_VIDEO_CODEC_AV1STD_MESA_H_
--#define VULKAN_VIDEO_CODEC_AV1STD_MESA_H_ 1
--
--/*
--** This header is NOT YET generated from the Khronos Vulkan XML API Registry.
--**
--*/
--
--#ifdef __cplusplus
--extern "C" {
--#endif
--#define vulkan_video_codec_av1std 1
--
--#define VK_MAKE_VIDEO_STD_VERSION(major, minor, patch) \
--   ((((uint32_t)(major)) << 22) | (((uint32_t)(minor)) << 12) | ((uint32_t)(patch)))
--#define VK_STD_VULKAN_VIDEO_CODEC_AV1_DECODE_API_VERSION_0_1_0 VK_MAKE_VIDEO_STD_VERSION(0, 1, 0)
--#define VK_STD_VULKAN_VIDEO_CODEC_AV1_DECODE_SPEC_VERSION VK_STD_VULKAN_VIDEO_CODEC_AV1_DECODE_API_VERSION_0_1_0
--#define VK_STD_VULKAN_VIDEO_CODEC_AV1_DECODE_EXTENSION_NAME "VK_STD_vulkan_video_codec_av1_decode"
--
--typedef enum StdVideoAV1MESAProfile {
--   STD_VIDEO_AV1_MESA_PROFILE_MAIN = 0,
--   STD_VIDEO_AV1_MESA_PROFILE_HIGH = 1,
--   STD_VIDEO_AV1_MESA_PROFILE_PROFESSIONAL = 2,
--} StdVideoAV1MESAProfile;
--
--typedef enum StdVideoAV1MESALevel {
--    STD_VIDEO_AV1_MESA_LEVEL_2_0 = 0,
--    STD_VIDEO_AV1_MESA_LEVEL_2_1 = 1,
--    STD_VIDEO_AV1_MESA_LEVEL_2_2 = 2,
--    STD_VIDEO_AV1_MESA_LEVEL_2_3 = 3,
--    STD_VIDEO_AV1_MESA_LEVEL_3_0 = 4,
--    STD_VIDEO_AV1_MESA_LEVEL_3_1 = 5,
--    STD_VIDEO_AV1_MESA_LEVEL_3_2 = 6,
--    STD_VIDEO_AV1_MESA_LEVEL_3_3 = 7,
--    STD_VIDEO_AV1_MESA_LEVEL_4_0 = 8,
--    STD_VIDEO_AV1_MESA_LEVEL_4_1 = 9,
--    STD_VIDEO_AV1_MESA_LEVEL_4_2 = 10,
--    STD_VIDEO_AV1_MESA_LEVEL_4_3 = 11,
--    STD_VIDEO_AV1_MESA_LEVEL_5_0 = 12,
--    STD_VIDEO_AV1_MESA_LEVEL_5_1 = 13,
--    STD_VIDEO_AV1_MESA_LEVEL_5_2 = 14,
--    STD_VIDEO_AV1_MESA_LEVEL_5_3 = 15,
--    STD_VIDEO_AV1_MESA_LEVEL_6_0 = 16,
--    STD_VIDEO_AV1_MESA_LEVEL_6_1 = 17,
--    STD_VIDEO_AV1_MESA_LEVEL_6_2 = 18,
--    STD_VIDEO_AV1_MESA_LEVEL_6_3 = 19,
--    STD_VIDEO_AV1_MESA_LEVEL_7_0 = 20,
--    STD_VIDEO_AV1_MESA_LEVEL_7_1 = 21,
--    STD_VIDEO_AV1_MESA_LEVEL_7_2 = 22,
--    STD_VIDEO_AV1_MESA_LEVEL_7_3 = 23,
--    STD_VIDEO_AV1_MESA_LEVEL_MAX = 31,
--} StdVideoAV1MESALevel;
--
--typedef struct StdVideoAV1MESAFilmGrainFlags {
--   uint8_t apply_grain;
--   uint8_t chroma_scaling_from_luma;
--   uint8_t overlap_flag;
--   uint8_t clip_to_restricted_range;
--} StdVideoAV1MESAFilmGrainFlags;
--
--typedef struct StdVideoAV1MESAFilmGrainParameters {
--   StdVideoAV1MESAFilmGrainFlags flags;
--   uint32_t grain_scaling_minus_8;
--   uint32_t ar_coeff_lag;
--   uint32_t ar_coeff_shift_minus_6;
--   uint32_t grain_scale_shift;
--
--   uint16_t grain_seed;
--   uint8_t num_y_points;
--   uint8_t point_y_value[14];
--   uint8_t point_y_scaling[14];
--
--   uint8_t num_cb_points;
--   uint8_t point_cb_value[10];
--   uint8_t point_cb_scaling[10];
--
--   uint8_t num_cr_points;
--   uint8_t point_cr_value[10];
--   uint8_t point_cr_scaling[10];
--
--   int8_t ar_coeffs_y_plus_128[24];
--   int8_t ar_coeffs_cb_plus_128[25];
--   int8_t ar_coeffs_cr_plus_128[25];
--   uint8_t cb_mult;
--   uint8_t cb_luma_mult;
--   uint16_t cb_offset;
--   uint8_t cr_mult;
--   uint8_t cr_luma_mult;
--   uint16_t cr_offset;
--} StdVideoAV1MESAFilmGrainParameters;
--
--typedef struct StdVideoAV1MESAGlobalMotionFlags {
--    uint8_t gm_invalid;
--} StdVideoAV1MESAGlobalMotionFlags;
--
--typedef struct StdVideoAV1MESAGlobalMotion {
--    StdVideoAV1MESAGlobalMotionFlags flags;
--    uint8_t gm_type;
--    uint32_t gm_params[6];
--} StdVideoAV1MESAGlobalMotion;
--
--typedef struct StdVideoAV1MESALoopRestoration {
--    uint8_t lr_type[3];
--    uint8_t lr_unit_shift;
--    uint8_t lr_uv_shift;
--} StdVideoAV1MESALoopRestoration;
--
--typedef struct StdVideoAV1MESATileInfoFlags {
--    uint8_t uniform_tile_spacing_flag;
--} StdVideoAV1MESATileInfoFlags;
--
--typedef struct StdVideoAV1MESATileInfo {
--    StdVideoAV1MESATileInfoFlags flags;
--    uint8_t tile_cols;
--    uint8_t tile_rows;
--    uint8_t tile_start_col_sb[64];
--    uint8_t tile_start_row_sb[64];
--    uint8_t width_in_sbs_minus_1[64];
--    uint8_t height_in_sbs_minus_1[64];
--    uint16_t context_update_tile_id;
--    uint8_t tile_size_bytes_minus1;
--} StdVideoAV1MESATileInfo;
--
--typedef struct StdVideoAV1MESAQuantizationFlags {
--    uint8_t using_qmatrix;
--} StdVideoAV1MESAQuantizationFlags;
--
--typedef struct StdVideoAV1MESAQuantization {
--    StdVideoAV1MESAQuantizationFlags flags;
--    uint8_t base_q_idx;
--    int8_t  delta_q_y_dc;
--    uint8_t diff_uv_delta;
--    int8_t  delta_q_u_dc;
--    int8_t  delta_q_u_ac;
--    int8_t  delta_q_v_dc;
--    int8_t  delta_q_v_ac;
--    uint8_t qm_y;
--    uint8_t qm_u;
--    uint8_t qm_v;
--} StdVideoAV1MESAQuantization;
--
--typedef struct StdVideoAV1MESACDEF {
--    uint8_t damping_minus_3;
--    uint8_t bits;
--    uint8_t y_pri_strength[8];
--    uint8_t y_sec_strength[8];
--    uint8_t uv_pri_strength[8];
--    uint8_t uv_sec_strength[8];
--} StdVideoAV1MESACDEF;
--
--typedef struct StdVideoAV1MESADeltaQFlags {
--    uint8_t delta_lf_present;
--    uint8_t delta_lf_multi;
--} StdVideoAV1MESADeltaQFlags;
--
--typedef struct StdVideoAV1MESADeltaQ {
--    StdVideoAV1MESADeltaQFlags flags;
--    uint8_t delta_q_res;
--    uint8_t delta_lf_res;
--} StdVideoAV1MESADeltaQ;
--
--typedef struct StdVideoAV1MESASegmentationFlags {
--    uint8_t enabled;
--    uint8_t update_map;
--    uint8_t temporal_update;
--    uint8_t update_data;
--} StdVideoAV1MESASegmentationFlags;
--
--typedef struct StdVideoAV1MESASegmentation {
--    StdVideoAV1MESASegmentationFlags flags;
--    uint8_t                      feature_enabled_bits[8];
--    int16_t                      feature_data[8][8];
--} StdVideoAV1MESASegmentation;
--
--typedef struct StdVideoAV1MESALoopFilterFlags {
--    uint8_t delta_enabled;
--    uint8_t delta_update;
--} StdVideoAV1MESALoopFilterFlags;
--
--typedef struct StdVideoAV1MESALoopFilter {
--    StdVideoAV1MESALoopFilterFlags flags;
--    uint8_t level[4];
--    uint8_t sharpness;
--    int8_t  ref_deltas[8];
--    int8_t  mode_deltas[2];
--} StdVideoAV1MESALoopFilter;
--
--typedef struct StdVideoAV1MESAFrameHeaderFlags {
--    uint8_t error_resilient_mode;
--    uint8_t disable_cdf_update;
--    uint8_t use_superres;
--    uint8_t render_and_frame_size_different;
--    uint8_t allow_screen_content_tools;
--    uint8_t is_filter_switchable;
--    uint8_t force_integer_mv;
--    uint8_t frame_size_override_flag;
--    uint8_t buffer_removal_time_present_flag;
--    uint8_t allow_intrabc;
--    uint8_t frame_refs_short_signaling;
--    uint8_t allow_high_precision_mv;
--    uint8_t is_motion_mode_switchable;
--    uint8_t use_ref_frame_mvs;
--    uint8_t disable_frame_end_update_cdf;
--    uint8_t allow_warped_motion;
--    uint8_t reduced_tx_set;
--    uint8_t reference_select;
--    uint8_t skip_mode_present;
--    uint8_t delta_q_present;
--    uint8_t UsesLr;
--} StdVideoAV1MESAFrameHeaderFlags;
--
--typedef struct StdVideoAV1MESAFrameHeader {
--    StdVideoAV1MESAFrameHeaderFlags flags;
--
--    uint32_t frame_presentation_time;
--    uint32_t display_frame_id;
--    uint32_t current_frame_id;
--    uint8_t  frame_to_show_map_idx;
--    uint8_t  frame_type;
--    uint8_t  order_hint;
--    uint8_t  primary_ref_frame;
--    uint16_t frame_width_minus_1;
--    uint16_t frame_height_minus_1;
--    uint16_t render_width_minus_1;
--    uint16_t render_height_minus_1;
--    uint8_t  coded_denom;
--
--    uint8_t refresh_frame_flags;
--    uint8_t ref_order_hint[8];
--    int8_t  ref_frame_idx[7];
--    uint32_t delta_frame_id_minus1[7];
--
--    uint8_t interpolation_filter;
--    uint8_t tx_mode;
--
--    StdVideoAV1MESATileInfo                   tiling;
--    StdVideoAV1MESAQuantization               quantization;
--    StdVideoAV1MESASegmentation               segmentation;
--    StdVideoAV1MESADeltaQ                     delta_q;
--    StdVideoAV1MESALoopFilter                 loop_filter;
--    StdVideoAV1MESACDEF                       cdef;
--    StdVideoAV1MESALoopRestoration            lr;
--    StdVideoAV1MESAGlobalMotion               global_motion[8]; // One per ref frame
--    StdVideoAV1MESAFilmGrainParameters        film_grain;
--} StdVideoAV1MESAFrameHeader;
--
--typedef struct StdVideoAV1MESAScreenCoding {
--    uint8_t seq_force_screen_content_tools;
--} StdVideoAV1MESAScreenCoding;
--
--typedef struct StdVideoAV1MESATimingInfoFlags {
--    uint8_t equal_picture_interval;
--} StdVideoAV1MESATimingInfoFlags;
--
--typedef struct StdVideoAV1MESATimingInfo {
--    StdVideoAV1MESATimingInfoFlags flags;
--    uint32_t num_units_in_display_tick;
--    uint32_t time_scale;
--    uint32_t num_ticks_per_picture_minus_1;
--} StdVideoAV1MESATimingInfo;
--
--typedef struct StdVideoAV1MESAColorConfigFlags {
--    uint8_t mono_chrome;
--    uint8_t color_range;
--    uint8_t separate_uv_delta_q;
--} StdVideoAV1MESAColorConfigFlags;
--
--typedef struct StdVideoAV1MESAColorConfig {
--    StdVideoAV1MESAColorConfigFlags flags;
--    uint8_t bit_depth;
--    uint8_t subsampling_x;
--    uint8_t subsampling_y;
--} StdVideoAV1MESAColorConfig;
--
--typedef struct StdVideoAV1MESASequenceHeaderFlags {
--    uint8_t still_picture;
--    uint8_t reduced_still_picture_header;
--    uint8_t use_128x128_superblock;
--    uint8_t enable_filter_intra;
--    uint8_t enable_intra_edge_filter;
--    uint8_t enable_interintra_compound;
--    uint8_t enable_masked_compound;
--    uint8_t enable_warped_motion;
--    uint8_t enable_dual_filter;
--    uint8_t enable_order_hint;
--    uint8_t enable_jnt_comp;
--    uint8_t enable_ref_frame_mvs;
--    uint8_t frame_id_numbers_present_flag;
--    uint8_t enable_superres;
--    uint8_t enable_cdef;
--    uint8_t enable_restoration;
--    uint8_t film_grain_params_present;
--    uint8_t timing_info_present_flag;
--    uint8_t initial_display_delay_present_flag;
--} StdVideoAV1MESASequenceHeaderFlags;
--
--typedef struct StdVideoAV1MESASequenceHeader {
--    StdVideoAV1MESASequenceHeaderFlags flags;
--
--    StdVideoAV1MESAProfile seq_profile;
--    uint8_t  frame_width_bits_minus_1;
--    uint8_t  frame_height_bits_minus_1;
--    uint16_t max_frame_width_minus_1;
--    uint16_t max_frame_height_minus_1;
--    uint8_t  delta_frame_id_length_minus_2;
--    uint8_t  additional_frame_id_length_minus_1;
--    uint8_t  order_hint_bits_minus_1;
--    uint8_t  seq_choose_integer_mv;
--    uint8_t  seq_force_integer_mv;
--
--    StdVideoAV1MESATimingInfo       timing_info;
--    StdVideoAV1MESAColorConfig      color_config;
--} StdVideoAV1MESASequenceHeader;
--
--typedef struct StdVideoAV1MESATile {
--    uint16_t tg_start;
--    uint16_t tg_end;
--    uint16_t row;
--    uint16_t column;
--    uint32_t size;
--    uint32_t offset;
--} StdVideoAV1MESATile;
--
--typedef struct StdVideoAV1MESATileList {
--    StdVideoAV1MESATile *tile_list;
--    uint32_t nb_tiles;
--} StdVideoAV1MESATileList;
--
--typedef struct VkVideoDecodeAV1PictureInfoMESA {
--    VkStructureType sType;
--    const void *pNext;
--    StdVideoAV1MESAFrameHeader *frame_header;
--    StdVideoAV1MESATileList *tile_list;
--    uint8_t skip_mode_frame_idx[2];
--} VkVideoDecodeAV1PictureInfoMESA;
--
--typedef struct VkVideoDecodeAV1DpbSlotInfoMESA {
--    VkStructureType sType;
--    const void *pNext;
--    uint8_t frameIdx;
--    uint8_t ref_order_hint[7];
--    uint8_t disable_frame_end_update_cdf;
--} VkVideoDecodeAV1DpbSlotInfoMESA;
--
--typedef struct VkVideoDecodeAV1SessionParametersAddInfoMESA {
--    VkStructureType sType;
--    const void *pNext;
--    StdVideoAV1MESASequenceHeader *sequence_header;
--} VkVideoDecodeAV1SessionParametersAddInfoMESA;
--
--typedef struct VkVideoDecodeAV1SessionParametersCreateInfoMESA {
--    VkStructureType sType;
--    const void *pNext;
--    const VkVideoDecodeAV1SessionParametersAddInfoMESA *pParametersAddInfo;
--} VkVideoDecodeAV1SessionParametersCreateInfoMESA;
--
--typedef struct VkVideoDecodeAV1ProfileInfoMESA {
--    VkStructureType sType;
--    const void *pNext;
--    StdVideoAV1MESAProfile stdProfileIdc;
--} VkVideoDecodeAV1ProfileInfoMESA;
--
--typedef enum VkVideoDecodeAV1CapabilityFlagBitsMESA {
--    VK_VIDEO_DECODE_AV1_CAPABILITY_EXTERNAL_FILM_GRAIN_MESA = 0x00000001,
--    VK_VIDEO_DECODE_AV1_CAPABILITY_FLAG_BITS_MAX_ENUM_MESA = 0x7FFFFFFF
--} VkVideoDecodeAV1CapabilityFlagBitsMESA;
--typedef VkFlags VkVideoDecodeAV1CapabilityFlagsMESA;
--
--typedef struct VkVideoDecodeAV1CapabilitiesMESA {
--    VkStructureType sType;
--    const void *pNext;
--    VkVideoDecodeAV1CapabilityFlagsMESA flags;
--    StdVideoAV1MESALevel maxLevelIdc;
--} VkVideoDecodeAV1CapabilitiesMESA;
--
--#define VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_PICTURE_INFO_MESA 1000509000
--#define VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_SESSION_PARAMETERS_CREATE_INFO_MESA 1000509001
--#define VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_SESSION_PARAMETERS_ADD_INFO_MESA 1000509002
--#define VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_DPB_SLOT_INFO_MESA 1000509003
--#define VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_CAPABILITIES_MESA 1000509004
--#define VK_STRUCTURE_TYPE_VIDEO_DECODE_AV1_PROFILE_INFO_MESA 1000509005
--
--#ifdef __cplusplus
--}
--#endif
--
--#endif
-diff --git a/libavutil/hwcontext_vulkan.c b/libavutil/hwcontext_vulkan.c
-index 91b9f96ccf..6e3b96b73a 100644
---- a/libavutil/hwcontext_vulkan.c
-+++ b/libavutil/hwcontext_vulkan.c
-@@ -446,7 +446,7 @@ static const VulkanOptExtension optional_device_exts[] = {
-     { VK_KHR_VIDEO_DECODE_QUEUE_EXTENSION_NAME,               FF_VK_EXT_VIDEO_DECODE_QUEUE     },
-     { VK_KHR_VIDEO_DECODE_H264_EXTENSION_NAME,                FF_VK_EXT_VIDEO_DECODE_H264      },
-     { VK_KHR_VIDEO_DECODE_H265_EXTENSION_NAME,                FF_VK_EXT_VIDEO_DECODE_H265      },
--    { "VK_MESA_video_decode_av1",                             FF_VK_EXT_VIDEO_DECODE_AV1       },
-+    { VK_KHR_VIDEO_DECODE_AV1_EXTENSION_NAME,                 FF_VK_EXT_VIDEO_DECODE_AV1       },
- };
- 
- static VkBool32 VKAPI_CALL vk_dbg_callback(VkDebugUtilsMessageSeverityFlagBitsEXT severity,
-diff --git a/libavutil/vulkan_functions.h b/libavutil/vulkan_functions.h
-index 65021b04b1..6b379acf93 100644
---- a/libavutil/vulkan_functions.h
-+++ b/libavutil/vulkan_functions.h
-@@ -43,7 +43,7 @@ typedef enum FFVulkanExtensions {
-     FF_VK_EXT_VIDEO_DECODE_QUEUE     = 1ULL << 11, /* VK_KHR_video_decode_queue */
-     FF_VK_EXT_VIDEO_DECODE_H264      = 1ULL << 12, /* VK_EXT_video_decode_h264 */
-     FF_VK_EXT_VIDEO_DECODE_H265      = 1ULL << 13, /* VK_EXT_video_decode_h265 */
--    FF_VK_EXT_VIDEO_DECODE_AV1       = 1ULL << 14, /* VK_MESA_video_decode_av1 */
-+    FF_VK_EXT_VIDEO_DECODE_AV1       = 1ULL << 14, /* VK_KHR_video_decode_av1 */
-     FF_VK_EXT_ATOMIC_FLOAT           = 1ULL << 15, /* VK_EXT_shader_atomic_float */
-     FF_VK_EXT_COOP_MATRIX            = 1ULL << 16, /* VK_KHR_cooperative_matrix */
- 
-diff --git a/libavutil/vulkan_loader.h b/libavutil/vulkan_loader.h
-index f9e739e1e3..73cf03935d 100644
---- a/libavutil/vulkan_loader.h
-+++ b/libavutil/vulkan_loader.h
-@@ -58,7 +58,7 @@ static inline uint64_t ff_vk_extensions_to_mask(const char * const *extensions,
-         { VK_KHR_VIDEO_DECODE_QUEUE_EXTENSION_NAME,        FF_VK_EXT_VIDEO_DECODE_QUEUE     },
-         { VK_KHR_VIDEO_DECODE_H264_EXTENSION_NAME,         FF_VK_EXT_VIDEO_DECODE_H264      },
-         { VK_KHR_VIDEO_DECODE_H265_EXTENSION_NAME,         FF_VK_EXT_VIDEO_DECODE_H265      },
--        { "VK_MESA_video_decode_av1",                      FF_VK_EXT_VIDEO_DECODE_AV1       },
-+        { VK_KHR_VIDEO_DECODE_AV1_EXTENSION_NAME,          FF_VK_EXT_VIDEO_DECODE_AV1       },
-     };
- 
-     FFVulkanExtensions mask = 0x0;
---- ffmpeg-6.1.1/libavcodec/vulkan_video.c.orig	2023-11-11 01:25:17.000000000 +0100
-+++ ffmpeg-6.1.1/libavcodec/vulkan_video.c	2024-04-15 21:49:23.744852316 +0200
-@@ -37,7 +37,7 @@ const FFVkCodecMap ff_vk_codec_map[AV_CO
-                            0,
-                            0,
-                            FF_VK_EXT_VIDEO_DECODE_AV1,
--                           0x01000000 /* TODO fix this */
-+                           VK_VIDEO_CODEC_OPERATION_DECODE_AV1_BIT_KHR,
-     },
- };
- 
diff --git a/gcc14.patch b/gcc14.patch
deleted file mode 100644
index 9feedf9..0000000
--- a/gcc14.patch
+++ /dev/null
@@ -1,162 +0,0 @@
---- ffmpeg-6.1.1/libavutil/hwcontext_vaapi.c.orig	2023-11-11 01:25:17.000000000 +0100
-+++ ffmpeg-6.1.1/libavutil/hwcontext_vaapi.c	2024-05-30 13:40:31.574621109 +0200
-@@ -1086,7 +1086,7 @@
-     int err, i, j;
- 
- #if !VA_CHECK_VERSION(1, 1, 0)
--    unsigned long buffer_handle;
-+    uintptr_t buffer_handle;
-     VASurfaceAttribExternalBuffers buffer_desc;
-     VASurfaceAttrib attrs[2] = {
-         {
-@@ -1203,7 +1203,7 @@
- 
-     if (!use_prime2 || vas != VA_STATUS_SUCCESS) {
-         int k;
--        unsigned long buffer_handle;
-+        uintptr_t buffer_handle;
-         VASurfaceAttribExternalBuffers buffer_desc;
-         VASurfaceAttrib buffer_attrs[2] = {
-             {
-From 5860a966d2fffbbda1af0014f0a4d37a21c4f2ca Mon Sep 17 00:00:00 2001
-From: Lynne <dev at lynne.ee>
-Date: Wed, 31 Jan 2024 14:15:04 +0100
-Subject: [PATCH 1/1] lavfi/vsrc_testsrc_vulkan: fix -Wint-conversion
-
-While VK_NULL_HANDLE is equivalent to NULL on 64-bit platforms, the same is not
-true across all platforms.
-
-Fixes building with gcc-14.
----
- libavfilter/vsrc_testsrc_vulkan.c | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
-diff --git a/libavfilter/vsrc_testsrc_vulkan.c b/libavfilter/vsrc_testsrc_vulkan.c
-index 8761c21dfd..1720bfac5e 100644
---- a/libavfilter/vsrc_testsrc_vulkan.c
-+++ b/libavfilter/vsrc_testsrc_vulkan.c
-@@ -231,7 +231,7 @@ static int testsrc_vulkan_activate(AVFilterContext *ctx)
-                 return AVERROR(ENOMEM);
- 
-             err = ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->pl, s->picref, NULL,
--                                              NULL, &s->opts, sizeof(s->opts));
-+                                              VK_NULL_HANDLE, &s->opts, sizeof(s->opts));
-             if (err < 0)
-                 return err;
-         }
-@@ -250,7 +250,7 @@ static int testsrc_vulkan_activate(AVFilterContext *ctx)
-     frame->sample_aspect_ratio = s->sar;
-     if (!s->draw_once) {
-         err = ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->pl, frame, NULL,
--                                          NULL, &s->opts, sizeof(s->opts));
-+                                          VK_NULL_HANDLE, &s->opts, sizeof(s->opts));
-         if (err < 0) {
-             av_frame_free(&frame);
-             return err;
--- 
-2.25.1
-
-From 2f24f10d9cf34ddce274496c4daa73f732d370c1 Mon Sep 17 00:00:00 2001
-From: Sam James <sam at gentoo.org>
-Date: Wed, 20 Dec 2023 12:32:43 +0000
-Subject: [PATCH] libavcodec: fix -Wint-conversion in vulkan
-MIME-Version: 1.0
-Content-Type: text/plain; charset=utf8
-Content-Transfer-Encoding: 8bit
-
-FIx warnings (soon to be errors in GCC 14, already so in Clang 15):
-```
-src/libavcodec/vulkan_av1.c: In function ‘vk_av1_create_params’:
-src/libavcodec/vulkan_av1.c:183:43: error: initialization of ‘long long unsigned int’ from ‘void *’ makes integer from pointer without a cast [-Wint-conversion]
-  183 |         .videoSessionParametersTemplate = NULL,
-      |                                           ^~~~
-src/libavcodec/vulkan_av1.c:183:43: note: (near initialization for ‘(anonymous).videoSessionParametersTemplate’)
-```
-
-Use Vulkan's VK_NULL_HANDLE instead of bare NULL.
-
-Fix Trac ticket #10724.
-
-Was reported downstream in Gentoo at https://bugs.gentoo.org/919067.
-
-Signed-off-by: Sam James <sam at gentoo.org>
----
- libavcodec/vulkan_av1.c    | 2 +-
- libavcodec/vulkan_decode.c | 6 +++---
- libavcodec/vulkan_h264.c   | 2 +-
- libavcodec/vulkan_hevc.c   | 2 +-
- libavcodec/vulkan_video.c  | 2 +-
- 5 files changed, 7 insertions(+), 7 deletions(-)
-
-diff --git a/libavcodec/vulkan_av1.c b/libavcodec/vulkan_av1.c
-index 4998bf7ebc..9730e4b08d 100644
---- a/libavcodec/vulkan_av1.c
-+++ b/libavcodec/vulkan_av1.c
-@@ -180,7 +180,7 @@ static int vk_av1_create_params(AVCodecContext *avctx, AVBufferRef **buf)
-         .sType = VK_STRUCTURE_TYPE_VIDEO_SESSION_PARAMETERS_CREATE_INFO_KHR,
-         .pNext = &av1_params,
-         .videoSession = ctx->common.session,
--        .videoSessionParametersTemplate = NULL,
-+        .videoSessionParametersTemplate = VK_NULL_HANDLE,
-     };
- 
-     err = ff_vk_decode_create_params(buf, avctx, ctx, &session_params_create);
-diff --git a/libavcodec/vulkan_decode.c b/libavcodec/vulkan_decode.c
-index a89d84fcaa..fdbcbb450a 100644
---- a/libavcodec/vulkan_decode.c
-+++ b/libavcodec/vulkan_decode.c
-@@ -188,9 +188,9 @@ int ff_vk_decode_prepare_frame(FFVulkanDecodeContext *dec, AVFrame *pic,
-         return 0;
- 
-     vkpic->dpb_frame     = NULL;
--    vkpic->img_view_ref  = NULL;
--    vkpic->img_view_out  = NULL;
--    vkpic->img_view_dest = NULL;
-+    vkpic->img_view_ref  = VK_NULL_HANDLE;
-+    vkpic->img_view_out  = VK_NULL_HANDLE;
-+    vkpic->img_view_dest = VK_NULL_HANDLE;
- 
-     vkpic->destroy_image_view = vk->DestroyImageView;
-     vkpic->wait_semaphores = vk->WaitSemaphores;
-diff --git a/libavcodec/vulkan_h264.c b/libavcodec/vulkan_h264.c
-index e727aafb16..39c123ddca 100644
---- a/libavcodec/vulkan_h264.c
-+++ b/libavcodec/vulkan_h264.c
-@@ -315,7 +315,7 @@ static int vk_h264_create_params(AVCodecContext *avctx, AVBufferRef **buf)
-         .sType = VK_STRUCTURE_TYPE_VIDEO_SESSION_PARAMETERS_CREATE_INFO_KHR,
-         .pNext = &h264_params,
-         .videoSession = ctx->common.session,
--        .videoSessionParametersTemplate = NULL,
-+        .videoSessionParametersTemplate = VK_NULL_HANDLE,
-     };
- 
-     /* SPS list */
-diff --git a/libavcodec/vulkan_hevc.c b/libavcodec/vulkan_hevc.c
-index 99fdcf3b45..033172cbd6 100644
---- a/libavcodec/vulkan_hevc.c
-+++ b/libavcodec/vulkan_hevc.c
-@@ -653,7 +653,7 @@ static int vk_hevc_create_params(AVCodecContext *avctx, AVBufferRef **buf)
-         .sType = VK_STRUCTURE_TYPE_VIDEO_SESSION_PARAMETERS_CREATE_INFO_KHR,
-         .pNext = &h265_params,
-         .videoSession = ctx->common.session,
--        .videoSessionParametersTemplate = NULL,
-+        .videoSessionParametersTemplate = VK_NULL_HANDLE,
-     };
- 
-     HEVCHeaderSet *hdr;
-diff --git a/libavcodec/vulkan_video.c b/libavcodec/vulkan_video.c
-index 5fa8292b28..fb20315db4 100644
---- a/libavcodec/vulkan_video.c
-+++ b/libavcodec/vulkan_video.c
-@@ -287,7 +287,7 @@ av_cold void ff_vk_video_common_uninit(FFVulkanContext *s,
-     if (common->session) {
-         vk->DestroyVideoSessionKHR(s->hwctx->act_dev, common->session,
-                                    s->hwctx->alloc);
--        common->session = NULL;
-+        common->session = VK_NULL_HANDLE;
-     }
- 
-     if (common->nb_mem && common->mem)
--- 
-2.25.1
-
diff --git a/libv4l2-1.30.patch b/libv4l2-1.30.patch
deleted file mode 100644
index 16b3e65..0000000
--- a/libv4l2-1.30.patch
+++ /dev/null
@@ -1,67 +0,0 @@
-From 5fea5e3e11d6ff425db48f44489916399822aece Mon Sep 17 00:00:00 2001
-From: Leo Izen <leo.izen at gmail.com>
-Date: Fri, 6 Jun 2025 16:09:34 -0400
-Subject: [PATCH] configure: rename POSIX ioctl check
-
-Commit 00b64fca55a3a009c9d0e391c85f4fd3291e5d12 introduced configure
-detection for HAVE_POSIX_IOCTL but unfortunately this conflicts with
-v4l-utils version 1.30, which itself checks for #ifdef HAVE_POSIX_IOCTL
-in a public header and erroneously determines it to be true because we
-define this to be 0.
-
-Since this is only used for avdevice/v4l2, we rename this to something
-else, namely ioctl_posix, simply to prevent the name conflict with the
-file /usr/include/libv4l2.h at least until they can upstream a fix on
-their end.
-
-Signed-off-by: Leo Izen <leo.izen at gmail.com>
----
- configure          | 4 ++--
- libavdevice/v4l2.c | 2 +-
- 2 files changed, 3 insertions(+), 3 deletions(-)
-
-diff --git a/configure b/configure
-index de1b88150f..534b443f7d 100755
---- a/configure
-+++ b/configure
-@@ -2533,6 +2533,7 @@ HAVE_LIST="
-     $TOOLCHAIN_FEATURES
-     $TYPES_LIST
-     gzip
-+    ioctl_posix
-     libdrm_getfb2
-     makeinfo
-     makeinfo_html
-@@ -2545,7 +2546,6 @@ HAVE_LIST="
-     opencl_vaapi_intel_media
-     perl
-     pod2man
--    posix_ioctl
-     texi2html
-     xmllint
-     zlib_gzip
-@@ -7275,7 +7275,7 @@ xmllint --version  > /dev/null 2>&1 && enable xmllint   || disable xmllint
- check_headers linux/fb.h
- check_headers linux/videodev2.h
- test_code cc linux/videodev2.h "struct v4l2_frmsizeenum vfse; vfse.discrete.width = 0;" && enable_sanitized struct_v4l2_frmivalenum_discrete
--test_code cc sys/ioctl.h "int ioctl(int, int, ...)" && enable posix_ioctl
-+test_code cc sys/ioctl.h "int ioctl(int, int, ...)" && enable ioctl_posix
- 
- # check V4L2 codecs available in the API
- if enabled v4l2_m2m; then
-diff --git a/libavdevice/v4l2.c b/libavdevice/v4l2.c
-index 0ae6872338..c38ecbb378 100644
---- a/libavdevice/v4l2.c
-+++ b/libavdevice/v4l2.c
-@@ -111,7 +111,7 @@ struct video_data {
-     int (*open_f)(const char *file, int oflag, ...);
-     int (*close_f)(int fd);
-     int (*dup_f)(int fd);
--#if HAVE_POSIX_IOCTL
-+#if HAVE_IOCTL_POSIX
-     int (*ioctl_f)(int fd, int request, ...);
- #else
-     int (*ioctl_f)(int fd, unsigned long int request, ...);
--- 
-2.25.1
-
diff --git a/opencv4.patch b/opencv4.patch
deleted file mode 100644
index 2c6c4c1..0000000
--- a/opencv4.patch
+++ /dev/null
@@ -1,14 +0,0 @@
---- ffmpeg-4.3.2/configure~	2021-02-20 21:27:47.000000000 +0100
-+++ ffmpeg-4.3.2/configure	2021-03-06 22:46:31.336556852 +0100
-@@ -6340,9 +6340,9 @@
- enabled libopencore_amrnb && require libopencore_amrnb opencore-amrnb/interf_dec.h Decoder_Interface_init -lopencore-amrnb
- enabled libopencore_amrwb && require libopencore_amrwb opencore-amrwb/dec_if.h D_IF_init -lopencore-amrwb
- enabled libopencv         && { check_headers opencv2/core/core_c.h &&
--                               { check_pkg_config libopencv opencv opencv2/core/core_c.h cvCreateImageHeader ||
-+                               { check_pkg_config libopencv opencv4 opencv2/core/core_c.h cvCreateImageHeader ||
-                                  require libopencv opencv2/core/core_c.h cvCreateImageHeader -lopencv_core -lopencv_imgproc; } ||
--                               require_pkg_config libopencv opencv opencv/cxcore.h cvCreateImageHeader; }
-+                               require_pkg_config libopencv opencv4 opencv/cxcore.h cvCreateImageHeader; }
- enabled libopenh264       && require_pkg_config libopenh264 openh264 wels/codec_api.h WelsGetCodecVersion
- enabled libopenjpeg       && { check_pkg_config libopenjpeg "libopenjp2 >= 2.1.0" openjpeg.h opj_version ||
-                                { require_pkg_config libopenjpeg "libopenjp2 >= 2.1.0" openjpeg.h opj_version -DOPJ_STATIC && add_cppflags -DOPJ_STATIC; } }
diff --git a/texinfo-7.2.patch b/texinfo-7.2.patch
deleted file mode 100644
index 52d4aa2..0000000
--- a/texinfo-7.2.patch
+++ /dev/null
@@ -1,297 +0,0 @@
-Date: Fri, 1 Nov 2024 15:57:07 +0100
-From: Patrice Dumas <pertususatfree.fr>
-Subject: [FFmpeg-devel] [PATCH] doc/t2h: Support texinfo 7.1 and 7.2 pretest
-
-Here is a proposed patch for portability of doc/t2h.pm for GNU Texinfo
-7.1 and 7.1.90 (7.2 pretest).  I tested against 7.1 and 7.1.90 (7.2
-pretest).  There is a difference in the headings compared to the website
-version, maybe related to FA_ICONS not being set the same, but the
-result seems correct.
-
-I also renamed $element to $output_unit in ffmpeg_heading_command as in
-new equivalent makeinfo/texi2any code the $element variable is the
-$command variable in ffmpeg_heading_command, which is very confusing.  I
-left as is the $command variable to have a patch easier to read, but it
-could make sense to rename $command as $element later on.
-
-The patch could also have effects with Texinfo 7.0, since some of the
-changes are for that version, but that probably never show up because it
-is for situations that may not exist in ffmpeg manuals (for example
- at node without sectioning command), or because the code is robust to some
-missing information (case of $heading_level in ffmpeg_heading_command
-that was not set, as far as I can tell).
-
----
- doc/t2h.pm | 169 ++++++++++++++++++++++++++++++++++++++++-------------
- 1 file changed, 129 insertions(+), 40 deletions(-)
-
-diff --git a/doc/t2h.pm b/doc/t2h.pm
-index b7485e1f1e..1359960f27 100644
---- a/doc/t2h.pm
-+++ b/doc/t2h.pm
-@@ -54,12 +54,24 @@ sub get_formatting_function($$) {
- }
- 
- # determine texinfo version
--my $program_version_num = version->declare(ff_get_conf('PACKAGE_VERSION'))->numify;
-+my $package_version = ff_get_conf('PACKAGE_VERSION');
-+$package_version =~ s/\+dev$//;
-+my $program_version_num = version->declare($package_version)->numify;
- my $program_version_6_8 = $program_version_num >= 6.008000;
- 
- # no navigation elements
- ff_set_from_init_file('HEADERS', 0);
- 
-+my %sectioning_commands = %Texinfo::Common::sectioning_commands;
-+if (scalar(keys(%sectioning_commands)) == 0) {
-+  %sectioning_commands = %Texinfo::Commands::sectioning_heading_commands;
-+}
-+
-+my %root_commands = %Texinfo::Common::root_commands;
-+if (scalar(keys(%root_commands)) == 0) {
-+  %root_commands = %Texinfo::Commands::root_commands;
-+}
-+
- sub ffmpeg_heading_command($$$$$)
- {
-     my $self = shift;
-@@ -77,6 +89,9 @@ sub ffmpeg_heading_command($$$$$)
-         return $result;
-     }
- 
-+    # no need to set it as the $element_id is output unconditionally
-+    my $heading_id;
-+
-     my $element_id = $self->command_id($command);
-     $result .= "<a name=\"$element_id\"></a>\n"
-         if (defined($element_id) and $element_id ne '');
-@@ -84,24 +99,40 @@ sub ffmpeg_heading_command($$$$$)
-     print STDERR "Process $command "
-         .Texinfo::Structuring::_print_root_command_texi($command)."\n"
-             if ($self->get_conf('DEBUG'));
--    my $element;
--    if ($Texinfo::Common::root_commands{$command->{'cmdname'}}
--        and $command->{'parent'}
--        and $command->{'parent'}->{'type'}
--        and $command->{'parent'}->{'type'} eq 'element') {
--        $element = $command->{'parent'};
-+    my $output_unit;
-+    if ($root_commands{$command->{'cmdname'}}) {
-+        if ($command->{'associated_unit'}) {
-+          $output_unit = $command->{'associated_unit'};
-+        } elsif ($command->{'structure'}
-+                 and $command->{'structure'}->{'associated_unit'}) {
-+          $output_unit = $command->{'structure'}->{'associated_unit'};
-+        } elsif ($command->{'parent'}
-+                 and $command->{'parent'}->{'type'}
-+                 and $command->{'parent'}->{'type'} eq 'element') {
-+          $output_unit = $command->{'parent'};
-+        }
-     }
--    if ($element) {
-+
-+    if ($output_unit) {
-         $result .= &{get_formatting_function($self, 'format_element_header')}($self, $cmdname,
--                                                       $command, $element);
-+                                                       $command, $output_unit);
-     }
- 
-     my $heading_level;
-     # node is used as heading if there is nothing else.
-     if ($cmdname eq 'node') {
--        if (!$element or (!$element->{'extra'}->{'section'}
--            and $element->{'extra'}->{'node'}
--            and $element->{'extra'}->{'node'} eq $command
-+        if (!$output_unit or
-+            (((!$output_unit->{'extra'}->{'section'}
-+              and $output_unit->{'extra'}->{'node'}
-+              and $output_unit->{'extra'}->{'node'} eq $command)
-+             or
-+             ((($output_unit->{'extra'}->{'unit_command'}
-+                and $output_unit->{'extra'}->{'unit_command'} eq $command)
-+               or
-+               ($output_unit->{'unit_command'}
-+                and $output_unit->{'unit_command'} eq $command))
-+              and $command->{'extra'}
-+              and not $command->{'extra'}->{'associated_section'}))
-              # bogus node may not have been normalized
-             and defined($command->{'extra'}->{'normalized'}))) {
-             if ($command->{'extra'}->{'normalized'} eq 'Top') {
-@@ -111,7 +142,15 @@ sub ffmpeg_heading_command($$$$$)
-             }
-         }
-     } else {
--        $heading_level = $command->{'level'};
-+        if (defined($command->{'extra'})
-+            and defined($command->{'extra'}->{'section_level'})) {
-+          $heading_level = $command->{'extra'}->{'section_level'};
-+        } elsif ($command->{'structure'}
-+                 and defined($command->{'structure'}->{'section_level'})) {
-+          $heading_level = $command->{'structure'}->{'section_level'};
-+        } else {
-+          $heading_level = $command->{'level'};
-+        }
-     }
- 
-     my $heading = $self->command_text($command);
-@@ -119,8 +158,8 @@ sub ffmpeg_heading_command($$$$$)
-     # if there is an error in the node.
-     if (defined($heading) and $heading ne '' and defined($heading_level)) {
- 
--        if ($Texinfo::Common::root_commands{$cmdname}
--            and $Texinfo::Common::sectioning_commands{$cmdname}) {
-+        if ($root_commands{$cmdname}
-+            and $sectioning_commands{$cmdname}) {
-             my $content_href = $self->command_contents_href($command, 'contents',
-                                                             $self->{'current_filename'});
-             if ($content_href) {
-@@ -140,7 +179,13 @@ sub ffmpeg_heading_command($$$$$)
-             }
-         }
- 
--        if ($self->in_preformatted()) {
-+        my $in_preformatted;
-+        if ($program_version_num >= 7.001090) {
-+          $in_preformatted = $self->in_preformatted_context();
-+        } else {
-+          $in_preformatted = $self->in_preformatted();
-+        }
-+        if ($in_preformatted) {
-             $result .= $heading."\n";
-         } else {
-             # if the level was changed, set the command name right
-@@ -149,21 +194,25 @@ sub ffmpeg_heading_command($$$$$)
-                 $cmdname
-                     = $Texinfo::Common::level_to_structuring_command{$cmdname}->[$heading_level];
-             }
--            # format_heading_text expects an array of headings for texinfo >= 7.0
-             if ($program_version_num >= 7.000000) {
--                $heading = [$heading];
--            }
--            $result .= &{get_formatting_function($self,'format_heading_text')}(
-+                $result .= &{get_formatting_function($self,'format_heading_text')}($self,
-+                     $cmdname, [$cmdname], $heading,
-+                     $heading_level +$self->get_conf('CHAPTER_HEADER_LEVEL') -1,
-+                     $heading_id, $command);
-+
-+            } else {
-+              $result .= &{get_formatting_function($self,'format_heading_text')}(
-                         $self, $cmdname, $heading,
-                         $heading_level +
-                         $self->get_conf('CHAPTER_HEADER_LEVEL') - 1, $command);
-+            }
-         }
-     }
-     $result .= $content if (defined($content));
-     return $result;
- }
- 
--foreach my $command (keys(%Texinfo::Common::sectioning_commands), 'node') {
-+foreach my $command (keys(%sectioning_commands), 'node') {
-     texinfo_register_command_formatting($command, \&ffmpeg_heading_command);
- }
- 
-@@ -188,28 +237,56 @@ sub ffmpeg_begin_file($$$)
-     my $filename = shift;
-     my $element = shift;
- 
--    my $command;
--    if ($element and $self->get_conf('SPLIT')) {
--        $command = $self->element_command($element);
-+    my ($element_command, $node_command, $command_for_title);
-+    if ($element) {
-+        if ($element->{'unit_command'}) {
-+          $element_command = $element->{'unit_command'};
-+        } elsif ($self->can('tree_unit_element_command')) {
-+          $element_command = $self->tree_unit_element_command($element);
-+        } elsif ($self->can('tree_unit_element_command')) {
-+          $element_command = $self->element_command($element);
-+        }
-+
-+       $node_command = $element_command;
-+       if ($element_command and $element_command->{'cmdname'}
-+           and $element_command->{'cmdname'} ne 'node'
-+           and $element_command->{'extra'}
-+           and $element_command->{'extra'}->{'associated_node'}) {
-+         $node_command = $element_command->{'extra'}->{'associated_node'};
-+       }
-+
-+       $command_for_title = $element_command if ($self->get_conf('SPLIT'));
-     }
- 
--    my ($title, $description, $encoding, $date, $css_lines,
--        $doctype, $bodytext, $copying_comment, $after_body_open,
--        $extra_head, $program_and_version, $program_homepage,
-+    my ($title, $description, $keywords, $encoding, $date, $css_lines, $doctype,
-+        $root_html_element_attributes, $body_attributes, $copying_comment,
-+        $after_body_open, $extra_head, $program_and_version, $program_homepage,
-         $program, $generator);
--    if ($program_version_num >= 7.000000) {
--        ($title, $description, $encoding, $date, $css_lines,
--         $doctype, $bodytext, $copying_comment, $after_body_open,
-+    if ($program_version_num >= 7.001090) {
-+        ($title, $description, $keywords, $encoding, $date, $css_lines, $doctype,
-+         $root_html_element_attributes, $body_attributes, $copying_comment,
-+         $after_body_open, $extra_head, $program_and_version, $program_homepage,
-+         $program, $generator) = $self->_file_header_information($command_for_title,
-+                                                                 $filename); 
-+    } elsif ($program_version_num >= 7.000000) {
-+        ($title, $description, $encoding, $date, $css_lines, $doctype,
-+         $root_html_element_attributes, $copying_comment, $after_body_open,
-          $extra_head, $program_and_version, $program_homepage,
--         $program, $generator) = $self->_file_header_information($command);
-+         $program, $generator) = $self->_file_header_information($command_for_title,
-+                                                                 $filename);
-     } else {
-         ($title, $description, $encoding, $date, $css_lines,
--         $doctype, $bodytext, $copying_comment, $after_body_open,
--         $extra_head, $program_and_version, $program_homepage,
--         $program, $generator) = $self->_file_header_informations($command);
-+         $doctype, $root_html_element_attributes, $copying_comment,
-+         $after_body_open, $extra_head, $program_and_version, $program_homepage,
-+         $program, $generator) = $self->_file_header_informations($command_for_title);
-     }
- 
--    my $links = $self->_get_links ($filename, $element);
-+    my $links;
-+    if ($program_version_num >= 7.000000) {
-+      $links = $self->_get_links($filename, $element, $node_command);
-+    } else {
-+      $links = $self->_get_links ($filename, $element);
-+    }
- 
-     my $head1 = $ENV{"FFMPEG_HEADER1"} || <<EOT;
- <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
-@@ -252,13 +329,25 @@ sub ffmpeg_program_string($)
-   if (defined($self->get_conf('PROGRAM'))
-       and $self->get_conf('PROGRAM') ne ''
-       and defined($self->get_conf('PACKAGE_URL'))) {
--    return $self->convert_tree(
-+    if ($program_version_num >= 7.001090) {
-+     return $self->convert_tree(
-+      $self->cdt('This document was generated using @uref{{program_homepage}, @emph{{program}}}.',
-+         { 'program_homepage' => {'text' => $self->get_conf('PACKAGE_URL')},
-+           'program' => {'text' => $self->get_conf('PROGRAM') }}));
-+    } else {
-+     return $self->convert_tree(
-       $self->gdt('This document was generated using @uref{{program_homepage}, @emph{{program}}}.',
--         { 'program_homepage' => $self->get_conf('PACKAGE_URL'),
--           'program' => $self->get_conf('PROGRAM') }));
-+         { 'program_homepage' => {'text' => $self->get_conf('PACKAGE_URL')},
-+           'program' => {'text' => $self->get_conf('PROGRAM') }}));
-+    }
-   } else {
--    return $self->convert_tree(
--      $self->gdt('This document was generated automatically.'));
-+    if ($program_version_num >= 7.001090) {
-+      return $self->convert_tree(
-+        $self->cdt('This document was generated automatically.'));
-+    } else {
-+      return $self->convert_tree(
-+        $self->gdt('This document was generated automatically.'));
-+    }
-   }
- }
- if ($program_version_6_8) {
--- 
-2.45.2
diff --git a/v4l2-request-hwdec.patch b/v4l2-request-hwdec.patch
index b9eb3ef..634e6c4 100644
--- a/v4l2-request-hwdec.patch
+++ b/v4l2-request-hwdec.patch
@@ -1,180 +1,486 @@
-From 8b34700cbd43b18950dc81cceb958d0b39126806 Mon Sep 17 00:00:00 2001
-From: Jonas Karlman <jonas at kwiboo.se>
-Date: Mon, 3 Dec 2018 23:48:04 +0100
-Subject: [PATCH 01/18] avutil: add av_buffer_pool_flush()
+V4L2 stateless Request API hwaccels (h264, hevc, vp8, vp9, mpeg2, av1) for FFmpeg.
+Out-of-tree series maintained by Jonas Karlman (Kwiboo); not merged upstream.
 
-Used by V4L2 request API hwaccel
-
-Signed-off-by: Jonas Karlman <jonas at kwiboo.se>
----
- libavutil/buffer.c | 13 +++++++++++++
- libavutil/buffer.h |  5 +++++
- 2 files changed, 18 insertions(+)
-
-diff --git a/libavutil/buffer.c b/libavutil/buffer.c
-index e4562a7..09da632 100644
---- a/libavutil/buffer.c
-+++ b/libavutil/buffer.c
-@@ -319,6 +319,19 @@ static void buffer_pool_free(AVBufferPool *pool)
-     av_freep(&pool);
- }
- 
-+void av_buffer_pool_flush(AVBufferPool *pool)
-+{
-+    ff_mutex_lock(&pool->mutex);
-+    while (pool->pool) {
-+        BufferPoolEntry *buf = pool->pool;
-+        pool->pool = buf->next;
-+
-+        buf->free(buf->opaque, buf->data);
-+        av_freep(&buf);
-+    }
-+    ff_mutex_unlock(&pool->mutex);
-+}
-+
- void av_buffer_pool_uninit(AVBufferPool **ppool)
- {
-     AVBufferPool *pool;
-diff --git a/libavutil/buffer.h b/libavutil/buffer.h
-index e1ef5b7..fde9bae 100644
---- a/libavutil/buffer.h
-+++ b/libavutil/buffer.h
-@@ -284,6 +284,11 @@ AVBufferPool *av_buffer_pool_init2(size_t size, void *opaque,
-                                    AVBufferRef* (*alloc)(void *opaque, size_t size),
-                                    void (*pool_free)(void *opaque));
- 
-+/**
-+ * Free all available buffers in a buffer pool.
-+ */
-+ void av_buffer_pool_flush(AVBufferPool *pool);
-+
- /**
-  * Mark the pool as being available for freeing. It will actually be freed only
-  * once all the allocated buffers associated with the pool are released. Thus it
--- 
-2.44.0
-
-
-From da33bb8f94c073c8fb6dc7a3f3efe72d78b64a14 Mon Sep 17 00:00:00 2001
-From: Jonas Karlman <jonas at kwiboo.se>
-Date: Sat, 15 Dec 2018 22:32:16 +0100
-Subject: [PATCH 02/18] Add common V4L2 request API code
-
-Signed-off-by: Jonas Karlman <jonas at kwiboo.se>
-Signed-off-by: Alex Bee <knaerzche at gmail.com>
----
- configure                 |   12 +
- libavcodec/Makefile       |    1 +
- libavcodec/hwconfig.h     |    2 +
- libavcodec/v4l2_request.c | 1048 +++++++++++++++++++++++++++++++++++++
- libavcodec/v4l2_request.h |   78 +++
- 5 files changed, 1141 insertions(+)
- create mode 100644 libavcodec/v4l2_request.c
- create mode 100644 libavcodec/v4l2_request.h
+Source: https://github.com/Kwiboo/FFmpeg branch v4l2-request-n8.1
+  combined diff: git diff n8.1..v4l2-request-n8.1
+Regenerate on ffmpeg bump from the matching v4l2-request-nX.Y branch.
 
 diff --git a/configure b/configure
-index a89cfa6..503eb06 100755
+index 17596942749ab..3d4009f3480de 100755
 --- a/configure
 +++ b/configure
-@@ -279,6 +279,7 @@ External library support:
-                            if openssl, gnutls or mbedtls is not used [no]
-   --enable-libtwolame      enable MP2 encoding via libtwolame [no]
-   --enable-libuavs3d       enable AVS3 decoding via libuavs3d [no]
-+  --enable-libudev         enable libudev [no]
-   --enable-libv4l2         enable libv4l2/v4l-utils [no]
-   --enable-libvidstab      enable video stabilization using vid.stab [no]
-   --enable-libvmaf         enable vmaf filter via libvmaf [no]
-@@ -347,6 +348,7 @@ External library support:
+@@ -368,6 +368,7 @@ External library support:
    --enable-omx-rpi         enable OpenMAX IL code for Raspberry Pi [no]
    --enable-rkmpp           enable Rockchip Media Process Platform code [no]
    --disable-v4l2-m2m       disable V4L2 mem2mem code [autodetect]
-+  --enable-v4l2-request    enable V4L2 request API code [no]
++  --disable-v4l2-request   disable V4L2 Request API code [autodetect]
    --disable-vaapi          disable Video Acceleration API (mainly Unix/Intel) code [autodetect]
    --disable-vdpau          disable Nvidia Video Decode and Presentation API for Unix code [autodetect]
    --disable-videotoolbox   disable VideoToolbox code [autodetect]
-@@ -1896,6 +1898,7 @@ EXTERNAL_LIBRARY_LIST="
-     libtheora
+@@ -2097,6 +2098,7 @@ EXTERNAL_LIBRARY_LIST="
+     libtorch
      libtwolame
      libuavs3d
 +    libudev
      libv4l2
      libvmaf
      libvorbis
-@@ -1952,6 +1955,7 @@ HWACCEL_LIBRARY_LIST="
-     mmal
-     omx
-     opencl
+@@ -2141,6 +2143,7 @@ HWACCEL_AUTODETECT_LIBRARY_LIST="
+     videotoolbox
+     vulkan
+     v4l2_m2m
 +    v4l2_request
  "
  
- DOCUMENT_LIST="
-@@ -3045,6 +3049,7 @@ dxva2_deps="dxva2api_h DXVA2_ConfigPictureDecode ole32 user32"
+ # catchall list of things that require external libs to link
+@@ -2642,6 +2645,7 @@ TYPES_LIST="
+     struct_sockaddr_sa_len
+     struct_sockaddr_storage
+     struct_stat_st_mtim_tv_nsec
++    struct_v4l2_ctrl_hevc_decode_params_num_delta_pocs_of_ref_rps_idx
+     struct_v4l2_frmivalenum_discrete
+     struct_mfxConfigInterface
+ "
+@@ -3341,6 +3345,8 @@ dxva2_deps="dxva2api_h DXVA2_ConfigPictureDecode ole32 user32"
  ffnvcodec_deps_any="libdl LoadLibrary"
- mediacodec_deps="android"
+ mediacodec_deps="android mediandk pthreads"
  nvdec_deps="ffnvcodec"
-+v4l2_request_deps="linux_videodev2_h linux_media_h v4l2_timeval_to_ns libdrm libudev"
++v4l2_request_deps="linux_media_h v4l2_timeval_to_ns v4l2_m2m_hold_capture_buf libdrm libudev"
++v4l2_request_suggest="libdrm libudev"
  vaapi_x11_deps="xlib_x11"
  videotoolbox_hwaccel_deps="videotoolbox pthreads"
  videotoolbox_hwaccel_extralibs="-framework QuartzCore"
-@@ -6807,6 +6812,7 @@ enabled libtwolame        && require libtwolame twolame.h twolame_init -ltwolame
-                              { check_lib libtwolame twolame.h twolame_encode_buffer_float32_interleaved -ltwolame ||
-                                die "ERROR: libtwolame must be installed and version must be >= 0.3.10"; }
- enabled libuavs3d         && require_pkg_config libuavs3d "uavs3d >= 1.1.41" uavs3d.h uavs3d_decode
-+enabled libudev           && require_pkg_config libudev libudev libudev.h udev_new
- enabled libv4l2           && require_pkg_config libv4l2 libv4l2 libv4l2.h v4l2_ioctl
- enabled libvidstab        && require_pkg_config libvidstab "vidstab >= 0.98" vid.stab/libvidstab.h vsMotionDetectInit
- enabled libvmaf           && require_pkg_config libvmaf "libvmaf >= 2.0.0" libvmaf.h vmaf_init
-@@ -6910,6 +6916,10 @@ enabled rkmpp             && { require_pkg_config rkmpp rockchip_mpp  rockchip/r
-                                { enabled libdrm ||
-                                  die "ERROR: rkmpp requires --enable-libdrm"; }
-                              }
-+enabled v4l2_request      && { enabled libdrm ||
-+                               die "ERROR: v4l2-request requires --enable-libdrm"; } &&
-+                             { enabled libudev ||
-+                               die "ERROR: v4l2-request requires --enable-libudev"; }
- enabled vapoursynth       && require_pkg_config vapoursynth "vapoursynth-script >= 42" VSScript.h vsscript_init
+@@ -3357,6 +3363,8 @@ av1_dxva2_hwaccel_deps="dxva2 DXVA_PicParams_AV1"
+ av1_dxva2_hwaccel_select="av1_decoder"
+ av1_nvdec_hwaccel_deps="nvdec CUVIDAV1PICPARAMS"
+ av1_nvdec_hwaccel_select="av1_decoder"
++av1_v4l2request_hwaccel_deps="v4l2_request av1_v4l2_request"
++av1_v4l2request_hwaccel_select="av1_decoder"
+ av1_vaapi_hwaccel_deps="vaapi VADecPictureParameterBufferAV1_bit_depth_idx"
+ av1_vaapi_hwaccel_select="av1_decoder"
+ av1_vdpau_hwaccel_deps="vdpau VdpPictureInfoAV1"
+@@ -3383,6 +3391,8 @@ h264_dxva2_hwaccel_deps="dxva2"
+ h264_dxva2_hwaccel_select="h264_decoder"
+ h264_nvdec_hwaccel_deps="nvdec"
+ h264_nvdec_hwaccel_select="h264_decoder"
++h264_v4l2request_hwaccel_deps="v4l2_request h264_v4l2_request"
++h264_v4l2request_hwaccel_select="h264_decoder"
+ h264_vaapi_hwaccel_deps="vaapi"
+ h264_vaapi_hwaccel_select="h264_decoder"
+ h264_vdpau_hwaccel_deps="vdpau"
+@@ -3401,6 +3411,8 @@ hevc_dxva2_hwaccel_deps="dxva2 DXVA_PicParams_HEVC"
+ hevc_dxva2_hwaccel_select="hevc_decoder"
+ hevc_nvdec_hwaccel_deps="nvdec"
+ hevc_nvdec_hwaccel_select="hevc_decoder"
++hevc_v4l2request_hwaccel_deps="v4l2_request hevc_v4l2_request"
++hevc_v4l2request_hwaccel_select="hevc_decoder"
+ hevc_vaapi_hwaccel_deps="vaapi VAPictureParameterBufferHEVC"
+ hevc_vaapi_hwaccel_select="hevc_decoder"
+ hevc_vdpau_hwaccel_deps="vdpau VdpPictureInfoHEVC"
+@@ -3429,6 +3441,8 @@ mpeg2_dxva2_hwaccel_deps="dxva2"
+ mpeg2_dxva2_hwaccel_select="mpeg2video_decoder"
+ mpeg2_nvdec_hwaccel_deps="nvdec"
+ mpeg2_nvdec_hwaccel_select="mpeg2video_decoder"
++mpeg2_v4l2request_hwaccel_deps="v4l2_request mpeg2_v4l2_request"
++mpeg2_v4l2request_hwaccel_select="mpeg2video_decoder"
+ mpeg2_vaapi_hwaccel_deps="vaapi"
+ mpeg2_vaapi_hwaccel_select="mpeg2video_decoder"
+ mpeg2_vdpau_hwaccel_deps="vdpau"
+@@ -3465,6 +3479,8 @@ vc1_vdpau_hwaccel_deps="vdpau"
+ vc1_vdpau_hwaccel_select="vc1_decoder"
+ vp8_nvdec_hwaccel_deps="nvdec"
+ vp8_nvdec_hwaccel_select="vp8_decoder"
++vp8_v4l2request_hwaccel_deps="v4l2_request vp8_v4l2_request"
++vp8_v4l2request_hwaccel_select="vp8_decoder"
+ vp8_vaapi_hwaccel_deps="vaapi"
+ vp8_vaapi_hwaccel_select="vp8_decoder"
+ vp9_d3d11va_hwaccel_deps="d3d11va DXVA_PicParams_VP9"
+@@ -3477,6 +3493,8 @@ vp9_dxva2_hwaccel_deps="dxva2 DXVA_PicParams_VP9"
+ vp9_dxva2_hwaccel_select="vp9_decoder"
+ vp9_nvdec_hwaccel_deps="nvdec"
+ vp9_nvdec_hwaccel_select="vp9_decoder"
++vp9_v4l2request_hwaccel_deps="v4l2_request vp9_v4l2_request"
++vp9_v4l2request_hwaccel_select="vp9_decoder"
+ vp9_vaapi_hwaccel_deps="vaapi VADecPictureParameterBufferVP9_bit_depth"
+ vp9_vaapi_hwaccel_select="vp9_decoder"
+ vp9_vdpau_hwaccel_deps="vdpau VdpPictureInfoVP9"
+@@ -4309,7 +4327,7 @@ shader_compression_suggest="zlib"
  
+ avcodec_extralibs="pthreads_extralibs iconv_extralibs dxva2_extralibs liblcevc_dec_extralibs lcms2_extralibs"
+ avfilter_extralibs="pthreads_extralibs"
+-avutil_extralibs="d3d11va_extralibs d3d12va_extralibs mediacodec_extralibs nanosleep_extralibs pthreads_extralibs vaapi_drm_extralibs vaapi_x11_extralibs vaapi_win32_extralibs vdpau_x11_extralibs"
++avutil_extralibs="d3d11va_extralibs d3d12va_extralibs mediacodec_extralibs nanosleep_extralibs pthreads_extralibs v4l2_request_extralibs vaapi_drm_extralibs vaapi_x11_extralibs vaapi_win32_extralibs vdpau_x11_extralibs"
  
-@@ -6992,6 +7002,8 @@ if enabled v4l2_m2m; then
+ # programs
+ ffmpeg_deps="avcodec avfilter avformat threads"
+@@ -7588,6 +7606,20 @@ if enabled v4l2_m2m; then
      check_cc vp9_v4l2_m2m linux/videodev2.h "int i = V4L2_PIX_FMT_VP9;"
  fi
  
-+check_func_headers "linux/media.h linux/videodev2.h" v4l2_timeval_to_ns
++if enabled v4l2_request; then
++    check_cc av1_v4l2_request linux/videodev2.h "int i = V4L2_CID_STATELESS_AV1_SEQUENCE"
++    check_cc h264_v4l2_request linux/videodev2.h "int i = V4L2_CID_STATELESS_H264_DECODE_MODE"
++    check_cc hevc_v4l2_request linux/videodev2.h "int i = V4L2_CID_STATELESS_HEVC_SPS"
++    check_cc mpeg2_v4l2_request linux/videodev2.h "int i = V4L2_CID_STATELESS_MPEG2_SEQUENCE"
++    check_cc v4l2_m2m_hold_capture_buf linux/videodev2.h "int i = V4L2_BUF_FLAG_M2M_HOLD_CAPTURE_BUF"
++    check_cc vp8_v4l2_request linux/videodev2.h "int i = V4L2_CID_STATELESS_VP8_FRAME"
++    check_cc vp9_v4l2_request linux/videodev2.h "int i = V4L2_CID_STATELESS_VP9_FRAME"
++    check_func_headers "linux/media.h linux/videodev2.h" v4l2_timeval_to_ns
++    check_pkg_config libudev libudev libudev.h udev_new
++    check_struct linux/videodev2.h "struct v4l2_ctrl_hevc_decode_params" num_delta_pocs_of_ref_rps_idx
++    v4l2_request_extralibs="$libudev_extralibs"
++fi
 +
  check_headers sys/videoio.h
  test_code cc sys/videoio.h "struct v4l2_frmsizeenum vfse; vfse.discrete.width = 0;" && enable_sanitized struct_v4l2_frmivalenum_discrete
  
 diff --git a/libavcodec/Makefile b/libavcodec/Makefile
-index ec57e53..5e626c9 100644
+index 12a8265025bc7..c6735d32a511a 100644
 --- a/libavcodec/Makefile
 +++ b/libavcodec/Makefile
-@@ -169,6 +169,7 @@ OBJS-$(CONFIG_VP3DSP)                  += vp3dsp.o
- OBJS-$(CONFIG_VP56DSP)                 += vp56dsp.o
+@@ -185,6 +185,7 @@ OBJS-$(CONFIG_VIDEODSP)                += videodsp.o
+ OBJS-$(CONFIG_VP3DSP)                  += vp3dsp.o
  OBJS-$(CONFIG_VP8DSP)                  += vp8dsp.o
  OBJS-$(CONFIG_V4L2_M2M)                += v4l2_m2m.o v4l2_context.o v4l2_buffers.o v4l2_fmt.o
 +OBJS-$(CONFIG_V4L2_REQUEST)            += v4l2_request.o
  OBJS-$(CONFIG_WMA_FREQS)               += wma_freqs.o
  OBJS-$(CONFIG_WMV2DSP)                 += wmv2dsp.o
  
+@@ -1050,6 +1051,7 @@ OBJS-$(CONFIG_AV1_D3D11VA_HWACCEL)        += dxva2_av1.o
+ OBJS-$(CONFIG_AV1_DXVA2_HWACCEL)          += dxva2_av1.o
+ OBJS-$(CONFIG_AV1_D3D12VA_HWACCEL)        += dxva2_av1.o d3d12va_av1.o
+ OBJS-$(CONFIG_AV1_NVDEC_HWACCEL)          += nvdec_av1.o
++OBJS-$(CONFIG_AV1_V4L2REQUEST_HWACCEL)    += v4l2_request_av1.o
+ OBJS-$(CONFIG_AV1_VAAPI_HWACCEL)          += vaapi_av1.o
+ OBJS-$(CONFIG_AV1_VDPAU_HWACCEL)          += vdpau_av1.o
+ OBJS-$(CONFIG_AV1_VIDEOTOOLBOX_HWACCEL)   += videotoolbox_av1.o
+@@ -1063,6 +1065,7 @@ OBJS-$(CONFIG_H264_DXVA2_HWACCEL)         += dxva2_h264.o
+ OBJS-$(CONFIG_H264_D3D12VA_HWACCEL)       += dxva2_h264.o d3d12va_h264.o
+ OBJS-$(CONFIG_H264_NVDEC_HWACCEL)         += nvdec_h264.o
+ OBJS-$(CONFIG_H264_QSV_HWACCEL)           += qsvdec.o
++OBJS-$(CONFIG_H264_V4L2REQUEST_HWACCEL)   += v4l2_request_h264.o
+ OBJS-$(CONFIG_H264_VAAPI_HWACCEL)         += vaapi_h264.o
+ OBJS-$(CONFIG_H264_VDPAU_HWACCEL)         += vdpau_h264.o
+ OBJS-$(CONFIG_H264_VIDEOTOOLBOX_HWACCEL)  += videotoolbox.o
+@@ -1072,6 +1075,7 @@ OBJS-$(CONFIG_HEVC_DXVA2_HWACCEL)         += dxva2_hevc.o
+ OBJS-$(CONFIG_HEVC_D3D12VA_HWACCEL)       += dxva2_hevc.o d3d12va_hevc.o
+ OBJS-$(CONFIG_HEVC_NVDEC_HWACCEL)         += nvdec_hevc.o
+ OBJS-$(CONFIG_HEVC_QSV_HWACCEL)           += qsvdec.o
++OBJS-$(CONFIG_HEVC_V4L2REQUEST_HWACCEL)   += v4l2_request_hevc.o
+ OBJS-$(CONFIG_HEVC_VAAPI_HWACCEL)         += vaapi_hevc.o h265_profile_level.o
+ OBJS-$(CONFIG_HEVC_VDPAU_HWACCEL)         += vdpau_hevc.o h265_profile_level.o
+ OBJS-$(CONFIG_HEVC_VULKAN_HWACCEL)        += vulkan_decode.o vulkan_hevc.o
+@@ -1085,6 +1089,7 @@ OBJS-$(CONFIG_MPEG2_DXVA2_HWACCEL)        += dxva2_mpeg2.o
+ OBJS-$(CONFIG_MPEG2_D3D12VA_HWACCEL)      += dxva2_mpeg2.o d3d12va_mpeg2.o
+ OBJS-$(CONFIG_MPEG2_NVDEC_HWACCEL)        += nvdec_mpeg12.o
+ OBJS-$(CONFIG_MPEG2_QSV_HWACCEL)          += qsvdec.o
++OBJS-$(CONFIG_MPEG2_V4L2REQUEST_HWACCEL)  += v4l2_request_mpeg2.o
+ OBJS-$(CONFIG_MPEG2_VAAPI_HWACCEL)        += vaapi_mpeg2.o
+ OBJS-$(CONFIG_MPEG2_VDPAU_HWACCEL)        += vdpau_mpeg12.o
+ OBJS-$(CONFIG_MPEG2_VIDEOTOOLBOX_HWACCEL) += videotoolbox.o
+@@ -1100,11 +1105,13 @@ OBJS-$(CONFIG_VC1_QSV_HWACCEL)            += qsvdec.o
+ OBJS-$(CONFIG_VC1_VAAPI_HWACCEL)          += vaapi_vc1.o
+ OBJS-$(CONFIG_VC1_VDPAU_HWACCEL)          += vdpau_vc1.o
+ OBJS-$(CONFIG_VP8_NVDEC_HWACCEL)          += nvdec_vp8.o
++OBJS-$(CONFIG_VP8_V4L2REQUEST_HWACCEL)    += v4l2_request_vp8.o
+ OBJS-$(CONFIG_VP8_VAAPI_HWACCEL)          += vaapi_vp8.o
+ OBJS-$(CONFIG_VP9_D3D11VA_HWACCEL)        += dxva2_vp9.o
+ OBJS-$(CONFIG_VP9_DXVA2_HWACCEL)          += dxva2_vp9.o
+ OBJS-$(CONFIG_VP9_D3D12VA_HWACCEL)        += dxva2_vp9.o d3d12va_vp9.o
+ OBJS-$(CONFIG_VP9_NVDEC_HWACCEL)          += nvdec_vp9.o
++OBJS-$(CONFIG_VP9_V4L2REQUEST_HWACCEL)    += v4l2_request_vp9.o
+ OBJS-$(CONFIG_VP9_VAAPI_HWACCEL)          += vaapi_vp9.o
+ OBJS-$(CONFIG_VP9_VDPAU_HWACCEL)          += vdpau_vp9.o
+ OBJS-$(CONFIG_VP9_VIDEOTOOLBOX_HWACCEL)   += videotoolbox_vp9.o
+@@ -1360,6 +1367,7 @@ SKIPHEADERS-$(CONFIG_VIDEOTOOLBOX)     += videotoolbox.h vt_internal.h
+ SKIPHEADERS-$(CONFIG_VULKAN)           += ffv1_vulkan.h prores_vulkan.h vulkan_video.h \
+                                           vulkan_encode.h vulkan_decode.h
+ SKIPHEADERS-$(CONFIG_V4L2_M2M)         += v4l2_buffers.h v4l2_context.h v4l2_m2m.h
++SKIPHEADERS-$(CONFIG_V4L2_REQUEST)     += v4l2_request.h
+ SKIPHEADERS-$(CONFIG_ZLIB)             += zlib_wrapper.h
+ 
+ TESTPROGS = avcodec                                                     \
+diff --git a/libavcodec/av1dec.c b/libavcodec/av1dec.c
+index ba8442077a9ec..dd89bf857bc57 100644
+--- a/libavcodec/av1dec.c
++++ b/libavcodec/av1dec.c
+@@ -542,6 +542,7 @@ static int get_pixel_format(AVCodecContext *avctx)
+                      CONFIG_AV1_D3D11VA_HWACCEL * 2 + \
+                      CONFIG_AV1_D3D12VA_HWACCEL + \
+                      CONFIG_AV1_NVDEC_HWACCEL + \
++                     CONFIG_AV1_V4L2REQUEST_HWACCEL + \
+                      CONFIG_AV1_VAAPI_HWACCEL + \
+                      CONFIG_AV1_VDPAU_HWACCEL + \
+                      CONFIG_AV1_VIDEOTOOLBOX_HWACCEL + \
+@@ -577,6 +578,9 @@ static int get_pixel_format(AVCodecContext *avctx)
+ #endif
+ #if CONFIG_AV1_VULKAN_HWACCEL
+         *fmtp++ = AV_PIX_FMT_VULKAN;
++#endif
++#if CONFIG_AV1_V4L2REQUEST_HWACCEL
++        *fmtp++ = AV_PIX_FMT_DRM_PRIME;
+ #endif
+         break;
+     case AV_PIX_FMT_YUV420P10:
+@@ -604,6 +608,9 @@ static int get_pixel_format(AVCodecContext *avctx)
+ #endif
+ #if CONFIG_AV1_VULKAN_HWACCEL
+         *fmtp++ = AV_PIX_FMT_VULKAN;
++#endif
++#if CONFIG_AV1_V4L2REQUEST_HWACCEL
++        *fmtp++ = AV_PIX_FMT_DRM_PRIME;
+ #endif
+         break;
+     case AV_PIX_FMT_YUV420P12:
+@@ -1630,6 +1637,9 @@ const FFCodec ff_av1_decoder = {
+ #if CONFIG_AV1_VULKAN_HWACCEL
+         HWACCEL_VULKAN(av1),
+ #endif
++#if CONFIG_AV1_V4L2REQUEST_HWACCEL
++        HWACCEL_V4L2REQUEST(av1),
++#endif
+ 
+         NULL
+     },
+diff --git a/libavcodec/h264_slice.c b/libavcodec/h264_slice.c
+index 0ce8e46c72b4a..97fab7085c726 100644
+--- a/libavcodec/h264_slice.c
++++ b/libavcodec/h264_slice.c
+@@ -789,6 +789,7 @@ static enum AVPixelFormat get_pixel_format(H264Context *h, int force_callback)
+                      (CONFIG_H264_D3D11VA_HWACCEL * 2) + \
+                      CONFIG_H264_D3D12VA_HWACCEL + \
+                      CONFIG_H264_NVDEC_HWACCEL + \
++                     CONFIG_H264_V4L2REQUEST_HWACCEL + \
+                      CONFIG_H264_VAAPI_HWACCEL + \
+                      CONFIG_H264_VIDEOTOOLBOX_HWACCEL + \
+                      CONFIG_H264_VDPAU_HWACCEL + \
+@@ -817,6 +818,9 @@ static enum AVPixelFormat get_pixel_format(H264Context *h, int force_callback)
+ #endif
+ #if CONFIG_H264_NVDEC_HWACCEL
+         *fmt++ = AV_PIX_FMT_CUDA;
++#endif
++#if CONFIG_H264_V4L2REQUEST_HWACCEL
++        *fmt++ = AV_PIX_FMT_DRM_PRIME;
+ #endif
+         if (CHROMA444(h)) {
+             if (h->avctx->colorspace == AVCOL_SPC_RGB) {
+@@ -873,6 +877,9 @@ static enum AVPixelFormat get_pixel_format(H264Context *h, int force_callback)
+ #if CONFIG_H264_VIDEOTOOLBOX_HWACCEL
+         if (h->avctx->colorspace != AVCOL_SPC_RGB)
+             *fmt++ = AV_PIX_FMT_VIDEOTOOLBOX;
++#endif
++#if CONFIG_H264_V4L2REQUEST_HWACCEL
++        *fmt++ = AV_PIX_FMT_DRM_PRIME;
+ #endif
+         if (CHROMA444(h)) {
+             if (h->avctx->colorspace == AVCOL_SPC_RGB)
+@@ -1701,7 +1708,7 @@ static int h264_slice_header_parse(const H264Context *h, H264SliceContext *sl,
+     unsigned int slice_type, tmp, i;
+     int field_pic_flag, bottom_field_flag;
+     int first_slice = sl == h->slice_ctx && !h->current_slice;
+-    int picture_structure;
++    int picture_structure, pos;
+ 
+     if (first_slice)
+         av_assert0(!h->setup_finished);
+@@ -1792,6 +1799,7 @@ static int h264_slice_header_parse(const H264Context *h, H264SliceContext *sl,
+ 
+     sl->poc_lsb = 0;
+     sl->delta_poc_bottom = 0;
++    pos = get_bits_left(&sl->gb);
+     if (sps->poc_type == 0) {
+         sl->poc_lsb = get_bits(&sl->gb, sps->log2_max_poc_lsb);
+ 
+@@ -1806,6 +1814,7 @@ static int h264_slice_header_parse(const H264Context *h, H264SliceContext *sl,
+         if (pps->pic_order_present == 1 && picture_structure == PICT_FRAME)
+             sl->delta_poc[1] = get_se_golomb(&sl->gb);
+     }
++    sl->pic_order_cnt_bit_size = pos - get_bits_left(&sl->gb);
+ 
+     sl->redundant_pic_count = 0;
+     if (pps->redundant_pic_cnt_present)
+@@ -1845,9 +1854,11 @@ static int h264_slice_header_parse(const H264Context *h, H264SliceContext *sl,
+ 
+     sl->explicit_ref_marking = 0;
+     if (nal->ref_idc) {
++        pos = get_bits_left(&sl->gb);
+         ret = ff_h264_decode_ref_pic_marking(sl, &sl->gb, nal, h->avctx);
+         if (ret < 0 && (h->avctx->err_recognition & AV_EF_EXPLODE))
+             return AVERROR_INVALIDDATA;
++        sl->ref_pic_marking_bit_size = pos - get_bits_left(&sl->gb);
+     }
+ 
+     if (sl->slice_type_nos != AV_PICTURE_TYPE_I && pps->cabac) {
+diff --git a/libavcodec/h264dec.c b/libavcodec/h264dec.c
+index 809a938386438..6c4ce97f63f99 100644
+--- a/libavcodec/h264dec.c
++++ b/libavcodec/h264dec.c
+@@ -1144,6 +1144,9 @@ const FFCodec ff_h264_decoder = {
+ #endif
+ #if CONFIG_H264_VULKAN_HWACCEL
+                                HWACCEL_VULKAN(h264),
++#endif
++#if CONFIG_H264_V4L2REQUEST_HWACCEL
++                               HWACCEL_V4L2REQUEST(h264),
+ #endif
+                                NULL
+                            },
+diff --git a/libavcodec/h264dec.h b/libavcodec/h264dec.h
+index 74fd09dfaacd0..33d788627f383 100644
+--- a/libavcodec/h264dec.h
++++ b/libavcodec/h264dec.h
+@@ -322,6 +322,7 @@ typedef struct H264SliceContext {
+     MMCO mmco[H264_MAX_MMCO_COUNT];
+     int  nb_mmco;
+     int explicit_ref_marking;
++    int ref_pic_marking_bit_size;
+ 
+     int frame_num;
+     int idr_pic_id;
+@@ -330,6 +331,7 @@ typedef struct H264SliceContext {
+     int delta_poc[2];
+     int curr_pic_num;
+     int max_pic_num;
++    int pic_order_cnt_bit_size;
+ } H264SliceContext;
+ 
+ /**
+diff --git a/libavcodec/hevc/hevcdec.c b/libavcodec/hevc/hevcdec.c
+index ae5f0fe69d895..647251e6f0248 100644
+--- a/libavcodec/hevc/hevcdec.c
++++ b/libavcodec/hevc/hevcdec.c
+@@ -580,6 +580,7 @@ static enum AVPixelFormat get_format(HEVCContext *s, const HEVCSPS *sps)
+                      CONFIG_HEVC_D3D11VA_HWACCEL * 2 + \
+                      CONFIG_HEVC_D3D12VA_HWACCEL + \
+                      CONFIG_HEVC_NVDEC_HWACCEL + \
++                     CONFIG_HEVC_V4L2REQUEST_HWACCEL + \
+                      CONFIG_HEVC_VAAPI_HWACCEL + \
+                      CONFIG_HEVC_VIDEOTOOLBOX_HWACCEL + \
+                      CONFIG_HEVC_VDPAU_HWACCEL + \
+@@ -618,6 +619,9 @@ static enum AVPixelFormat get_format(HEVCContext *s, const HEVCSPS *sps)
+ #endif
+ #if CONFIG_HEVC_VULKAN_HWACCEL
+         *fmt++ = AV_PIX_FMT_VULKAN;
++#endif
++#if CONFIG_HEVC_V4L2REQUEST_HWACCEL
++        *fmt++ = AV_PIX_FMT_DRM_PRIME;
+ #endif
+         break;
+     case AV_PIX_FMT_YUV420P10:
+@@ -645,6 +649,9 @@ static enum AVPixelFormat get_format(HEVCContext *s, const HEVCSPS *sps)
+ #endif
+ #if CONFIG_HEVC_NVDEC_HWACCEL
+         *fmt++ = AV_PIX_FMT_CUDA;
++#endif
++#if CONFIG_HEVC_V4L2REQUEST_HWACCEL
++        *fmt++ = AV_PIX_FMT_DRM_PRIME;
+ #endif
+         break;
+     case AV_PIX_FMT_YUV444P:
+@@ -4280,6 +4287,9 @@ const FFCodec ff_hevc_decoder = {
+ #endif
+ #if CONFIG_HEVC_VULKAN_HWACCEL
+                                HWACCEL_VULKAN(hevc),
++#endif
++#if CONFIG_HEVC_V4L2REQUEST_HWACCEL
++                               HWACCEL_V4L2REQUEST(hevc),
+ #endif
+                                NULL
+                            },
+diff --git a/libavcodec/hwaccels.h b/libavcodec/hwaccels.h
+index 3de191288a597..7b6f67330a3cd 100644
+--- a/libavcodec/hwaccels.h
++++ b/libavcodec/hwaccels.h
+@@ -24,6 +24,7 @@ extern const struct FFHWAccel ff_av1_d3d11va2_hwaccel;
+ extern const struct FFHWAccel ff_av1_d3d12va_hwaccel;
+ extern const struct FFHWAccel ff_av1_dxva2_hwaccel;
+ extern const struct FFHWAccel ff_av1_nvdec_hwaccel;
++extern const struct FFHWAccel ff_av1_v4l2request_hwaccel;
+ extern const struct FFHWAccel ff_av1_vaapi_hwaccel;
+ extern const struct FFHWAccel ff_av1_vdpau_hwaccel;
+ extern const struct FFHWAccel ff_av1_videotoolbox_hwaccel;
+@@ -37,6 +38,7 @@ extern const struct FFHWAccel ff_h264_d3d11va2_hwaccel;
+ extern const struct FFHWAccel ff_h264_d3d12va_hwaccel;
+ extern const struct FFHWAccel ff_h264_dxva2_hwaccel;
+ extern const struct FFHWAccel ff_h264_nvdec_hwaccel;
++extern const struct FFHWAccel ff_h264_v4l2request_hwaccel;
+ extern const struct FFHWAccel ff_h264_vaapi_hwaccel;
+ extern const struct FFHWAccel ff_h264_vdpau_hwaccel;
+ extern const struct FFHWAccel ff_h264_videotoolbox_hwaccel;
+@@ -46,6 +48,7 @@ extern const struct FFHWAccel ff_hevc_d3d11va2_hwaccel;
+ extern const struct FFHWAccel ff_hevc_d3d12va_hwaccel;
+ extern const struct FFHWAccel ff_hevc_dxva2_hwaccel;
+ extern const struct FFHWAccel ff_hevc_nvdec_hwaccel;
++extern const struct FFHWAccel ff_hevc_v4l2request_hwaccel;
+ extern const struct FFHWAccel ff_hevc_vaapi_hwaccel;
+ extern const struct FFHWAccel ff_hevc_vdpau_hwaccel;
+ extern const struct FFHWAccel ff_hevc_videotoolbox_hwaccel;
+@@ -60,6 +63,7 @@ extern const struct FFHWAccel ff_mpeg2_d3d11va2_hwaccel;
+ extern const struct FFHWAccel ff_mpeg2_d3d12va_hwaccel;
+ extern const struct FFHWAccel ff_mpeg2_dxva2_hwaccel;
+ extern const struct FFHWAccel ff_mpeg2_nvdec_hwaccel;
++extern const struct FFHWAccel ff_mpeg2_v4l2request_hwaccel;
+ extern const struct FFHWAccel ff_mpeg2_vaapi_hwaccel;
+ extern const struct FFHWAccel ff_mpeg2_vdpau_hwaccel;
+ extern const struct FFHWAccel ff_mpeg2_videotoolbox_hwaccel;
+@@ -78,12 +82,14 @@ extern const struct FFHWAccel ff_vc1_nvdec_hwaccel;
+ extern const struct FFHWAccel ff_vc1_vaapi_hwaccel;
+ extern const struct FFHWAccel ff_vc1_vdpau_hwaccel;
+ extern const struct FFHWAccel ff_vp8_nvdec_hwaccel;
++extern const struct FFHWAccel ff_vp8_v4l2request_hwaccel;
+ extern const struct FFHWAccel ff_vp8_vaapi_hwaccel;
+ extern const struct FFHWAccel ff_vp9_d3d11va_hwaccel;
+ extern const struct FFHWAccel ff_vp9_d3d11va2_hwaccel;
+ extern const struct FFHWAccel ff_vp9_d3d12va_hwaccel;
+ extern const struct FFHWAccel ff_vp9_dxva2_hwaccel;
+ extern const struct FFHWAccel ff_vp9_nvdec_hwaccel;
++extern const struct FFHWAccel ff_vp9_v4l2request_hwaccel;
+ extern const struct FFHWAccel ff_vp9_vaapi_hwaccel;
+ extern const struct FFHWAccel ff_vp9_vdpau_hwaccel;
+ extern const struct FFHWAccel ff_vp9_videotoolbox_hwaccel;
 diff --git a/libavcodec/hwconfig.h b/libavcodec/hwconfig.h
-index e164722..ebafb6f 100644
+index ee29ca631df03..159064a1f14cd 100644
 --- a/libavcodec/hwconfig.h
 +++ b/libavcodec/hwconfig.h
-@@ -77,6 +77,8 @@ void ff_hwaccel_uninit(AVCodecContext *avctx);
-     HW_CONFIG_HWACCEL(1, 1, 1, VULKAN,       VULKAN,       ff_ ## codec ## _vulkan_hwaccel)
- #define HWACCEL_D3D11VA(codec) \
+@@ -79,6 +79,8 @@ void ff_hwaccel_uninit(AVCodecContext *avctx);
      HW_CONFIG_HWACCEL(0, 0, 1, D3D11VA_VLD,  NONE,         ff_ ## codec ## _d3d11va_hwaccel)
+ #define HWACCEL_D3D12VA(codec) \
+     HW_CONFIG_HWACCEL(1, 1, 0, D3D12,        D3D12VA,      ff_ ## codec ## _d3d12va_hwaccel)
 +#define HWACCEL_V4L2REQUEST(codec) \
-+    HW_CONFIG_HWACCEL(1, 0, 0, DRM_PRIME,    DRM,          ff_ ## codec ## _v4l2request_hwaccel)
++    HW_CONFIG_HWACCEL(1, 0, 0, DRM_PRIME,    V4L2REQUEST,  ff_ ## codec ## _v4l2request_hwaccel)
  
  #define HW_CONFIG_ENCODER(device, frames, ad_hoc, format, device_type_) \
      &(const AVCodecHWConfigInternal) { \
-diff --git a/libavcodec/v4l2_request.c b/libavcodec/v4l2_request.c
+diff --git a/libavcodec/mpeg12dec.c b/libavcodec/mpeg12dec.c
+index 4c83bcfa90e3f..c65e9e3b86a88 100644
+--- a/libavcodec/mpeg12dec.c
++++ b/libavcodec/mpeg12dec.c
+@@ -821,6 +821,9 @@ static const enum AVPixelFormat mpeg2_hwaccel_pixfmt_list_420[] = {
+ #endif
+ #if CONFIG_MPEG2_VIDEOTOOLBOX_HWACCEL
+     AV_PIX_FMT_VIDEOTOOLBOX,
++#endif
++#if CONFIG_MPEG2_V4L2REQUEST_HWACCEL
++    AV_PIX_FMT_DRM_PRIME,
+ #endif
+     AV_PIX_FMT_YUV420P,
+     AV_PIX_FMT_NONE
+@@ -2736,6 +2739,9 @@ const FFCodec ff_mpeg2video_decoder = {
+ #endif
+ #if CONFIG_MPEG2_VIDEOTOOLBOX_HWACCEL
+                         HWACCEL_VIDEOTOOLBOX(mpeg2),
++#endif
++#if CONFIG_MPEG2_V4L2REQUEST_HWACCEL
++                        HWACCEL_V4L2REQUEST(mpeg2),
+ #endif
+                         NULL
+                     },
+diff --git a/libavcodec/v4l2_request.c b/libavcodec/v4l2_request.c
 new file mode 100644
-index 0000000..595a53e
+index 0000000000000..36eec8540295a
 --- /dev/null
 +++ b/libavcodec/v4l2_request.c
-@@ -0,0 +1,1048 @@
+@@ -0,0 +1,784 @@
 +/*
 + * This file is part of FFmpeg.
 + *
@@ -193,54 +499,86 @@ index 0000000..595a53e
 + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
 + */
 +
-+#include <drm_fourcc.h>
-+#include <fcntl.h>
-+#include <libudev.h>
++#include "config.h"
++
 +#include <linux/media.h>
++#include <poll.h>
 +#include <sys/ioctl.h>
 +#include <sys/mman.h>
-+#include <sys/stat.h>
-+#include <sys/sysmacros.h>
-+#include <sys/types.h>
 +#include <unistd.h>
 +
++#include "libavutil/hwcontext_v4l2request_internal.h"
++#include "libavutil/mem.h"
 +#include "decode.h"
 +#include "internal.h"
 +#include "v4l2_request.h"
 +
++#define V4L2_PLANES_MAX 2
++
 +static const AVClass v4l2_request_context_class = {
 +    .class_name = "V4L2RequestContext",
 +    .item_name  = av_default_item_name,
 +    .version    = LIBAVUTIL_VERSION_INT,
 +};
 +
-+uint64_t ff_v4l2_request_get_capture_timestamp(AVFrame *frame)
++static inline V4L2RequestContext *v4l2_request_context(AVCodecContext *avctx)
 +{
-+    V4L2RequestDescriptor *req = (V4L2RequestDescriptor*)frame->data[0];
-+    return req ? v4l2_timeval_to_ns(&req->capture.buffer.timestamp) : 0;
++    return (V4L2RequestContext *)avctx->internal->hwaccel_priv_data;
 +}
 +
-+int ff_v4l2_request_reset_frame(AVCodecContext *avctx, AVFrame *frame)
++static inline uint32_t v4l2_request_frameindex(AVFrame *frame)
 +{
-+    V4L2RequestDescriptor *req = (V4L2RequestDescriptor*)frame->data[0];
-+    memset(&req->drm, 0, sizeof(AVDRMFrameDescriptor));
-+    req->output.used = 0;
-+    return 0;
++    return (uint32_t)(uintptr_t)frame->data[1];
 +}
 +
-+int ff_v4l2_request_append_output_buffer(AVCodecContext *avctx, AVFrame *frame, const uint8_t *data, uint32_t size)
++uint64_t ff_v4l2_request_get_capture_timestamp(AVFrame *frame)
 +{
-+    V4L2RequestDescriptor *req = (V4L2RequestDescriptor*)frame->data[0];
-+    if (req->output.used + size + (AV_INPUT_BUFFER_PADDING_SIZE * 4) <= req->output.size) {
-+        memcpy(req->output.addr + req->output.used, data, size);
-+        req->output.used += size;
-+    } else {
-+        av_log(avctx, AV_LOG_ERROR, "%s: output.used=%u output.size=%u size=%u\n", __func__, req->output.used, req->output.size, size);
++    /*
++     * The CAPTURE buffer index is used as a base for V4L2 frame reference.
++     * This works because frames are decoded into a CAPTURE buffer that is
++     * closely tied to an AVFrame.
++     */
++    struct timeval timestamp = {
++        .tv_sec = 0,
++        .tv_usec = v4l2_request_frameindex(frame) + 1,
++    };
++    return v4l2_timeval_to_ns(&timestamp);
++}
++
++int ff_v4l2_request_query_control(AVCodecContext *avctx,
++                                  struct v4l2_query_ext_ctrl *control)
++{
++    V4L2RequestContext *ctx = v4l2_request_context(avctx);
++
++    if (ioctl(ctx->fctxi->video_fd, VIDIOC_QUERY_EXT_CTRL, control) < 0) {
++        int ret = AVERROR(errno);
++        // Skip error logging when driver does not support control id (EINVAL)
++        if (errno != EINVAL)
++            av_log(ctx, AV_LOG_ERROR, "Failed to query control %u: %s (%d)\n",
++                   control->id, strerror(errno), errno);
++        return ret;
 +    }
++
 +    return 0;
 +}
 +
-+static int v4l2_request_controls(V4L2RequestContext *ctx, int request_fd, unsigned long type, struct v4l2_ext_control *control, int count)
++int ff_v4l2_request_query_control_default_value(AVCodecContext *avctx,
++                                                uint32_t id)
++{
++    struct v4l2_query_ext_ctrl control = {
++        .id = id,
++    };
++    int ret;
++
++    ret = ff_v4l2_request_query_control(avctx, &control);
++    if (ret < 0)
++        return ret;
++
++    return control.default_value;
++}
++
++static int v4l2_request_set_controls(V4L2RequestContext *ctx, int request_fd,
++                                     struct v4l2_ext_control *control, int count)
 +{
 +    struct v4l2_ext_controls controls = {
 +        .controls = control,
@@ -252,983 +590,1440 @@ index 0000000..595a53e
 +    if (!control || !count)
 +        return 0;
 +
-+    return ioctl(ctx->video_fd, type, &controls);
-+}
++    if (ioctl(ctx->fctxi->video_fd, VIDIOC_S_EXT_CTRLS, &controls) < 0)
++        return AVERROR(errno);
 +
-+static int v4l2_request_set_controls(V4L2RequestContext *ctx, int request_fd, struct v4l2_ext_control *control, int count)
-+{
-+    return v4l2_request_controls(ctx, request_fd, VIDIOC_S_EXT_CTRLS, control, count);
++    return 0;
 +}
 +
-+int ff_v4l2_request_set_controls(AVCodecContext *avctx, struct v4l2_ext_control *control, int count)
++int ff_v4l2_request_set_controls(AVCodecContext *avctx,
++                                 struct v4l2_ext_control *control, int count)
 +{
-+    V4L2RequestContext *ctx = avctx->internal->hwaccel_priv_data;
++    V4L2RequestContext *ctx = v4l2_request_context(avctx);
 +    int ret;
 +
-+    ret = v4l2_request_controls(ctx, -1, VIDIOC_S_EXT_CTRLS, control, count);
-+    if (ret < 0) {
-+        av_log(avctx, AV_LOG_ERROR, "%s: set controls failed, %s (%d)\n", __func__, strerror(errno), errno);
-+        return AVERROR(EINVAL);
-+    }
++    ret = v4l2_request_set_controls(ctx, -1, control, count);
++    if (ret < 0)
++        av_log(ctx, AV_LOG_ERROR, "Failed to set %d control(s): %s (%d)\n",
++               count, strerror(errno), errno);
 +
 +    return ret;
 +}
 +
-+int ff_v4l2_request_get_controls(AVCodecContext *avctx, struct v4l2_ext_control *control, int count)
++static int v4l2_request_queue_buffer(V4L2RequestContext *ctx,
++                                     struct v4l2_buffer *buffer)
 +{
-+    V4L2RequestContext *ctx = avctx->internal->hwaccel_priv_data;
-+    int ret;
++    struct v4l2_plane planes[V4L2_PLANES_MAX] = {};
 +
-+    ret = v4l2_request_controls(ctx, -1, VIDIOC_G_EXT_CTRLS, control, count);
-+    if (ret < 0) {
-+        av_log(avctx, AV_LOG_ERROR, "%s: get controls failed, %s (%d)\n", __func__, strerror(errno), errno);
-+        return AVERROR(EINVAL);
++    if (V4L2_TYPE_IS_MULTIPLANAR(buffer->type)) {
++        planes[0].bytesused = buffer->bytesused;
++        buffer->bytesused = 0;
++        buffer->length = FF_ARRAY_ELEMS(planes);
++        buffer->m.planes = planes;
 +    }
 +
-+    return ret;
-+}
-+
-+int ff_v4l2_request_query_control(AVCodecContext *avctx, struct v4l2_query_ext_ctrl *control)
-+{
-+    int ret;
-+    V4L2RequestContext *ctx = avctx->internal->hwaccel_priv_data;
++    // Queue the buffer
++    if (ioctl(ctx->fctxi->video_fd, VIDIOC_QBUF, buffer) < 0)
++        return AVERROR(errno);
 +
-+    ret = ioctl(ctx->video_fd, VIDIOC_QUERY_EXT_CTRL, control);
-+    if (ret < 0) {
-+        av_log(avctx, AV_LOG_ERROR, "%s: query control failed, %s (%d)\n", __func__, strerror(errno), errno);
-+        return AVERROR(EINVAL);
-+    }
++    // Mark the buffer as queued
++    if (V4L2_TYPE_IS_OUTPUT(buffer->type))
++        ctx->queued_output |= 1 << buffer->index;
++    else
++        ctx->queued_capture |= 1 << buffer->index;
 +
 +    return 0;
 +}
 +
-+int ff_v4l2_request_query_control_default_value(AVCodecContext *avctx, uint32_t id)
++static int v4l2_request_queue_capture_buffer(V4L2RequestContext *ctx,
++                                             uint32_t index)
 +{
-+    int ret;
-+    V4L2RequestContext *ctx = avctx->internal->hwaccel_priv_data;
-+    struct v4l2_queryctrl control = {
-+        .id = id,
++    struct v4l2_buffer buffer = {
++        .index = index,
++        .type = ctx->fctxi->capture.format.type,
++        .memory = V4L2_MEMORY_MMAP,
 +    };
++    return v4l2_request_queue_buffer(ctx, &buffer);
++}
 +
-+    ret = ioctl(ctx->video_fd, VIDIOC_QUERYCTRL, &control);
-+    if (ret < 0) {
-+        av_log(avctx, AV_LOG_ERROR, "%s: query control failed, %s (%d)\n", __func__, strerror(errno), errno);
-+        return AVERROR(EINVAL);
-+    }
-+
-+    return control.default_value;
++static int v4l2_request_queue_output_buffer(V4L2RequestContext *ctx,
++                                            V4L2RequestOutputBuffer *output,
++                                            uint32_t flags)
++{
++    struct v4l2_buffer buffer = {
++        .index = output->index,
++        .type = ctx->fctxi->output.format.type,
++        .memory = V4L2_MEMORY_MMAP,
++        .timestamp = output->timestamp,
++        .bytesused = output->bytesused,
++        .request_fd = output->request_fd,
++        .flags = V4L2_BUF_FLAG_REQUEST_FD | flags,
++    };
++    return v4l2_request_queue_buffer(ctx, &buffer);
 +}
 +
-+static int v4l2_request_queue_buffer(V4L2RequestContext *ctx, int request_fd, V4L2RequestBuffer *buf, uint32_t flags)
++static int v4l2_request_dequeue_buffer(V4L2RequestContext *ctx,
++                                       enum v4l2_buf_type type)
 +{
-+    struct v4l2_plane planes[1] = {};
++    struct v4l2_plane planes[V4L2_PLANES_MAX] = {};
 +    struct v4l2_buffer buffer = {
-+        .type = buf->buffer.type,
-+        .memory = buf->buffer.memory,
-+        .index = buf->index,
-+        .timestamp.tv_usec = buf->index + 1,
-+        .bytesused = buf->used,
-+        .request_fd = request_fd,
-+        .flags = ((request_fd >= 0) ? V4L2_BUF_FLAG_REQUEST_FD : 0) | flags,
++        .type = type,
++        .memory = V4L2_MEMORY_MMAP,
 +    };
 +
-+    if (V4L2_TYPE_IS_MULTIPLANAR(buf->buffer.type)) {
-+        planes[0].bytesused = buf->used;
-+        buffer.bytesused = 0;
-+        buffer.length = 1;
++    if (V4L2_TYPE_IS_MULTIPLANAR(buffer.type)) {
++        buffer.length = FF_ARRAY_ELEMS(planes);
 +        buffer.m.planes = planes;
 +    }
 +
-+    return ioctl(ctx->video_fd, VIDIOC_QBUF, &buffer);
++    // Dequeue next completed buffer
++    if (ioctl(ctx->fctxi->video_fd, VIDIOC_DQBUF, &buffer) < 0)
++        return AVERROR(errno);
++
++    // Mark the buffer as dequeued
++    if (V4L2_TYPE_IS_OUTPUT(buffer.type))
++        ctx->queued_output &= ~(1 << buffer.index);
++    else
++        ctx->queued_capture &= ~(1 << buffer.index);
++
++    return 0;
 +}
 +
-+static int v4l2_request_dequeue_buffer(V4L2RequestContext *ctx, V4L2RequestBuffer *buf)
++static inline int v4l2_request_dequeue_completed_buffers(V4L2RequestContext *ctx,
++                                                         enum v4l2_buf_type type)
 +{
 +    int ret;
-+    struct v4l2_plane planes[1] = {};
-+    struct v4l2_buffer buffer = {
-+        .type = buf->buffer.type,
-+        .memory = buf->buffer.memory,
-+        .index = buf->index,
++
++    do {
++        ret = v4l2_request_dequeue_buffer(ctx, type);
++    } while (!ret);
++
++    return ret;
++}
++
++static int v4l2_request_wait_on_capture(V4L2RequestContext *ctx, uint32_t index)
++{
++    enum v4l2_buf_type type = ctx->fctxi->capture.format.type;
++    struct pollfd pollfd = {
++        .fd = ctx->fctxi->video_fd,
++        .events = POLLIN,
 +    };
 +
-+    if (V4L2_TYPE_IS_MULTIPLANAR(buf->buffer.type)) {
-+        buffer.length = 1;
-+        buffer.m.planes = planes;
-+    }
++    ff_mutex_lock(&ctx->mutex);
 +
-+    ret = ioctl(ctx->video_fd, VIDIOC_DQBUF, &buffer);
-+    if (ret < 0)
-+        return ret;
++    // Dequeue all completed CAPTURE buffers
++    if (ctx->queued_capture)
++        v4l2_request_dequeue_completed_buffers(ctx, type);
++
++    // Wait on the specific CAPTURE buffer
++    while (ctx->queued_capture & (1 << index)) {
++        int ret = poll(&pollfd, 1, 2000);
++        if (ret <= 0)
++            goto fail;
 +
-+    buf->buffer.timestamp = buffer.timestamp;
++        ret = v4l2_request_dequeue_buffer(ctx, type);
++        if (ret < 0 && ret != AVERROR(EAGAIN))
++            goto fail;
++    }
++
++    ff_mutex_unlock(&ctx->mutex);
 +    return 0;
-+}
 +
-+static const struct {
-+    uint32_t pixelformat;
-+    enum AVPixelFormat sw_format;
-+    uint32_t drm_format;
-+    uint64_t format_modifier;
-+} v4l2_request_capture_pixelformats[] = {
-+    { V4L2_PIX_FMT_NV12, AV_PIX_FMT_NV12, DRM_FORMAT_NV12, DRM_FORMAT_MOD_LINEAR },
-+    { V4L2_PIX_FMT_SUNXI_TILED_NV12, AV_PIX_FMT_NV12, DRM_FORMAT_NV12, DRM_FORMAT_MOD_ALLWINNER_TILED },
-+};
++fail:
++    ff_mutex_unlock(&ctx->mutex);
++    av_log(ctx, AV_LOG_ERROR, "Failed waiting on CAPTURE buffer %d\n", index);
++    return AVERROR(EINVAL);
++}
 +
-+static int v4l2_request_set_drm_descriptor(V4L2RequestDescriptor *req, struct v4l2_format *format)
++static V4L2RequestOutputBuffer *v4l2_request_next_output(V4L2RequestContext *ctx)
 +{
-+    AVDRMFrameDescriptor *desc = &req->drm;
-+    AVDRMLayerDescriptor *layer = &desc->layers[0];
-+    uint32_t pixelformat = V4L2_TYPE_IS_MULTIPLANAR(format->type) ? format->fmt.pix_mp.pixelformat : format->fmt.pix.pixelformat;
++    enum v4l2_buf_type type = ctx->fctxi->output.format.type;
++    V4L2RequestOutputBuffer *output;
++    struct pollfd pollfd = {
++        .fd = ctx->fctxi->video_fd,
++        .events = POLLOUT,
++    };
++    uint8_t index;
 +
-+    layer->format = 0;
-+    for (int i = 0; i < FF_ARRAY_ELEMS(v4l2_request_capture_pixelformats); i++) {
-+        if (pixelformat == v4l2_request_capture_pixelformats[i].pixelformat) {
-+            layer->format = v4l2_request_capture_pixelformats[i].drm_format;
-+            desc->objects[0].format_modifier = v4l2_request_capture_pixelformats[i].format_modifier;
-+            break;
-+        }
-+    }
++    ff_mutex_lock(&ctx->mutex);
 +
-+    if (!layer->format)
-+        return -1;
++    // Use next OUTPUT buffer in the circular queue
++    index = ctx->next_output;
++    output = &ctx->output[index];
++    ctx->next_output = (index + 1) % FF_ARRAY_ELEMS(ctx->output);
 +
-+    desc->nb_objects = 1;
-+    desc->objects[0].fd = req->capture.fd;
-+    desc->objects[0].size = req->capture.size;
++    // Dequeue all completed OUTPUT buffers
++    if (ctx->queued_output)
++        v4l2_request_dequeue_completed_buffers(ctx, type);
 +
-+    desc->nb_layers = 1;
-+    layer->nb_planes = 2;
++    // Wait on the specific OUTPUT buffer
++    while (ctx->queued_output & (1 << output->index)) {
++        int ret = poll(&pollfd, 1, 2000);
++        if (ret <= 0)
++            goto fail;
 +
-+    layer->planes[0].object_index = 0;
-+    layer->planes[0].offset = 0;
-+    layer->planes[0].pitch = V4L2_TYPE_IS_MULTIPLANAR(format->type) ? format->fmt.pix_mp.plane_fmt[0].bytesperline : format->fmt.pix.bytesperline;
++        ret = v4l2_request_dequeue_buffer(ctx, type);
++        if (ret < 0 && ret != AVERROR(EAGAIN))
++            goto fail;
++    }
 +
-+    layer->planes[1].object_index = 0;
-+    layer->planes[1].offset = layer->planes[0].pitch * (V4L2_TYPE_IS_MULTIPLANAR(format->type) ? format->fmt.pix_mp.height : format->fmt.pix.height);
-+    layer->planes[1].pitch = layer->planes[0].pitch;
++    ff_mutex_unlock(&ctx->mutex);
 +
-+    return 0;
++    // Reset bytesused state
++    output->bytesused = 0;
++
++    return output;
++
++fail:
++    ff_mutex_unlock(&ctx->mutex);
++    av_log(ctx, AV_LOG_ERROR, "Failed waiting on OUTPUT buffer %d\n",
++           output->index);
++    return NULL;
 +}
 +
-+static int v4l2_request_queue_decode(AVCodecContext *avctx, AVFrame *frame, struct v4l2_ext_control *control, int count, int first_slice, int last_slice)
++static int v4l2_request_wait_on_request(V4L2RequestContext *ctx,
++                                        V4L2RequestOutputBuffer *output)
 +{
-+    V4L2RequestContext *ctx = avctx->internal->hwaccel_priv_data;
-+    V4L2RequestDescriptor *req = (V4L2RequestDescriptor*)frame->data[0];
-+    struct timeval tv = { 2, 0 };
-+    fd_set except_fds;
-+    int ret;
++    struct pollfd pollfd = {
++        .fd = output->request_fd,
++        .events = POLLPRI,
++    };
 +
-+    av_log(avctx, AV_LOG_DEBUG, "%s: ctx=%p used=%u controls=%d index=%d fd=%d request_fd=%d first_slice=%d last_slice=%d\n", __func__,
-+           ctx, req->output.used, count, req->capture.index, req->capture.fd, req->request_fd, first_slice, last_slice);
++    // Wait on the specific request to complete
++    while (ctx->queued_request & (1 << output->index)) {
++        int ret = poll(&pollfd, 1, 2000);
++        if (ret <= 0)
++            break;
 +
-+    ret = v4l2_request_set_controls(ctx, req->request_fd, control, count);
-+    if (ret < 0) {
-+        av_log(avctx, AV_LOG_ERROR, "%s: set controls failed for request %d, %s (%d)\n", __func__, req->request_fd, strerror(errno), errno);
-+        return -1;
++        // Mark request as dequeued
++        if (pollfd.revents & (POLLPRI | POLLERR)) {
++            ctx->queued_request &= ~(1 << output->index);
++            break;
++        }
 +    }
 +
-+    memset(req->output.addr + req->output.used, 0, AV_INPUT_BUFFER_PADDING_SIZE * 4);
++    // Reinit the request object
++    if (ioctl(output->request_fd, MEDIA_REQUEST_IOC_REINIT) < 0) {
++        int ret = AVERROR(errno);
++        av_log(ctx, AV_LOG_ERROR, "Failed to reinit request object %d: %s (%d)\n",
++               output->request_fd, strerror(errno), errno);
++        return ret;
++    }
 +
-+    ret = v4l2_request_queue_buffer(ctx, req->request_fd, &req->output, last_slice ? 0 : V4L2_BUF_FLAG_M2M_HOLD_CAPTURE_BUF);
-+    if (ret < 0) {
-+        av_log(avctx, AV_LOG_ERROR, "%s: queue output buffer %d failed for request %d, %s (%d)\n", __func__, req->output.index, req->request_fd, strerror(errno), errno);
-+        return -1;
++    // Ensure request is marked as dequeued
++    ctx->queued_request &= ~(1 << output->index);
++
++    return 0;
++}
++
++int ff_v4l2_request_append_output(AVCodecContext *avctx,
++                                  V4L2RequestPictureContext *pic,
++                                  const uint8_t *data, uint32_t size)
++{
++    V4L2RequestContext *ctx = v4l2_request_context(avctx);
++
++    // Append data to OUTPUT buffer and ensure there is enough space for padding
++    if (pic->output->bytesused + size + AV_INPUT_BUFFER_PADDING_SIZE <= pic->output->size) {
++        memcpy(pic->output->addr + pic->output->bytesused, data, size);
++        pic->output->bytesused += size;
++        return 0;
++    } else {
++        av_log(ctx, AV_LOG_ERROR,
++               "Failed to append %u bytes data to OUTPUT buffer %d (%u of %u used)\n",
++               size, pic->output->index, pic->output->bytesused, pic->output->size);
++        return AVERROR(ENOMEM);
 +    }
++}
++
++static int v4l2_request_queue_decode(AVCodecContext *avctx,
++                                     V4L2RequestPictureContext *pic,
++                                     struct v4l2_ext_control *control, int count,
++                                     bool first_slice, bool last_slice)
++{
++    V4L2RequestContext *ctx = v4l2_request_context(avctx);
++    uint32_t flags;
++    int ret;
 +
 +    if (first_slice) {
-+        ret = v4l2_request_queue_buffer(ctx, -1, &req->capture, 0);
-+        if (ret < 0) {
-+            av_log(avctx, AV_LOG_ERROR, "%s: queue capture buffer %d failed for request %d, %s (%d)\n", __func__, req->capture.index, req->request_fd, strerror(errno), errno);
-+            return -1;
-+        }
++        /*
++         * Wait on dequeue of the target CAPTURE buffer. Otherwise V4L2 decoder
++         * may use a different CAPTURE buffer than hwaccel expects.
++         *
++         * Normally decoding has already completed when a CAPTURE buffer is
++         * reused so this is more or less a no-op, however in some situations
++         * FFmpeg may reuse an AVFrame early, i.e. when no output frame was
++         * produced prior time, and a synchronization is necessary.
++         */
++        ret = v4l2_request_wait_on_capture(ctx, pic->capture_index);
++        if (ret < 0)
++            return ret;
 +    }
 +
-+    // NOTE: do we need to dequeue when request fails/timeout?
++    ff_mutex_lock(&ctx->mutex);
 +
-+    // 4. queue request and wait
-+    ret = ioctl(req->request_fd, MEDIA_REQUEST_IOC_QUEUE, NULL);
-+    if (ret < 0) {
-+        av_log(avctx, AV_LOG_ERROR, "%s: queue request %d failed, %s (%d)\n", __func__, req->request_fd, strerror(errno), errno);
++    /*
++     * The OUTPUT buffer tied to prior use of current request object can
++     * independently be dequeued before the full decode request has been
++     * completed. This may happen when a decoder use multi stage decoding,
++     * e.g. rpi-hevc-dec. In such case we can start reusing the OUTPUT buffer,
++     * however we must wait on the prior request to fully complete before we
++     * can reuse the request object, and a synchronization is necessary.
++     */
++    ret = v4l2_request_wait_on_request(ctx, pic->output);
++    if (ret < 0)
 +        goto fail;
-+    }
 +
-+    FD_ZERO(&except_fds);
-+    FD_SET(req->request_fd, &except_fds);
++    /*
++     * Dequeue any completed OUTPUT buffers, this is strictly not necessary,
++     * however if a synchronization was necessary for the CAPTURE and/or request
++     * there is more than likely one or more OUTPUT buffers that can be dequeued.
++     */
++    if (ctx->queued_output)
++        v4l2_request_dequeue_completed_buffers(ctx, ctx->fctxi->output.format.type);
 +
-+    ret = select(req->request_fd + 1, NULL, NULL, &except_fds, &tv);
-+    if (ret == 0) {
-+        av_log(avctx, AV_LOG_ERROR, "%s: request %d timeout\n", __func__, req->request_fd);
-+        goto fail;
-+    } else if (ret < 0) {
-+        av_log(avctx, AV_LOG_ERROR, "%s: select request %d failed, %s (%d)\n", __func__, req->request_fd, strerror(errno), errno);
++    // Set codec controls for current request
++    ret = v4l2_request_set_controls(ctx, pic->output->request_fd, control, count);
++    if (ret < 0) {
++        av_log(ctx, AV_LOG_ERROR, "Failed to set %d control(s) for request %d: %s (%d)\n",
++               count, pic->output->request_fd, strerror(errno), errno);
 +        goto fail;
 +    }
 +
-+    ret = v4l2_request_dequeue_buffer(ctx, &req->output);
++    // Ensure there is zero padding at the end of bitstream data
++    memset(pic->output->addr + pic->output->bytesused, 0, AV_INPUT_BUFFER_PADDING_SIZE);
++
++    /*
++     * Use CAPTURE buffer index as base for V4L2 frame reference.
++     * This works because a CAPTURE buffer is closely tied to a AVFrame
++     * and FFmpeg handle all frame reference tracking for us.
++     */
++    pic->output->timestamp = (struct timeval) {
++        .tv_sec = 0,
++        .tv_usec = pic->capture_index + 1,
++    };
++
++    /*
++     * Queue the OUTPUT buffer of current request. The CAPTURE buffer may be
++     * hold by the V4L2 decoder unless this is the last slice of a frame.
++     */
++    flags = last_slice ? 0 : V4L2_BUF_FLAG_M2M_HOLD_CAPTURE_BUF;
++    ret = v4l2_request_queue_output_buffer(ctx, pic->output, flags);
 +    if (ret < 0) {
-+        av_log(avctx, AV_LOG_ERROR, "%s: dequeue output buffer %d failed for request %d, %s (%d)\n", __func__, req->output.index, req->request_fd, strerror(errno), errno);
-+        return -1;
++        av_log(ctx, AV_LOG_ERROR, "Failed to queue OUTPUT buffer %d for request %d: %s (%d)\n",
++               pic->output->index, pic->output->request_fd, strerror(errno), errno);
++        goto fail;
 +    }
 +
-+    if (last_slice) {
-+        ret = v4l2_request_dequeue_buffer(ctx, &req->capture);
++    if (first_slice) {
++        /*
++         * Queue the target CAPTURE buffer, hwaccel expect and depend on that
++         * this specific CAPTURE buffer will be used as decode target for
++         * current request, otherwise frames may be output in wrong order or
++         * wrong CAPTURE buffer could get used as a reference frame.
++         */
++        ret = v4l2_request_queue_capture_buffer(ctx, pic->capture_index);
 +        if (ret < 0) {
-+            av_log(avctx, AV_LOG_ERROR, "%s: dequeue capture buffer %d failed for request %d, %s (%d)\n", __func__, req->capture.index, req->request_fd, strerror(errno), errno);
-+            return -1;
++            av_log(ctx, AV_LOG_ERROR, "Failed to queue CAPTURE buffer %d for request %d: %s (%d)\n",
++                   pic->capture_index, pic->output->request_fd, strerror(errno), errno);
++            goto fail;
 +        }
 +    }
 +
-+    // TODO: check errors
-+    // buffer.flags & V4L2_BUF_FLAG_ERROR
-+
-+    ret = ioctl(req->request_fd, MEDIA_REQUEST_IOC_REINIT, NULL);
++    // Queue current request
++    ret = ioctl(pic->output->request_fd, MEDIA_REQUEST_IOC_QUEUE);
 +    if (ret < 0) {
-+        av_log(avctx, AV_LOG_ERROR, "%s: reinit request %d failed, %s (%d)\n", __func__, req->request_fd, strerror(errno), errno);
-+        return -1;
++        ret = AVERROR(errno);
++        av_log(ctx, AV_LOG_ERROR, "Failed to queue request object %d: %s (%d)\n",
++               pic->output->request_fd, strerror(errno), errno);
++        goto fail;
 +    }
 +
-+    if (last_slice)
-+        return v4l2_request_set_drm_descriptor(req, &ctx->format);
-+
-+    return 0;
++    // Mark current request as queued
++    ctx->queued_request |= 1 << pic->output->index;
 +
++    ret = 0;
 +fail:
-+    ret = v4l2_request_dequeue_buffer(ctx, &req->output);
-+    if (ret < 0)
-+        av_log(avctx, AV_LOG_ERROR, "%s: dequeue output buffer %d failed for request %d, %s (%d)\n", __func__, req->output.index, req->request_fd, strerror(errno), errno);
++    ff_mutex_unlock(&ctx->mutex);
++    return ret;
++}
 +
-+    ret = v4l2_request_dequeue_buffer(ctx, &req->capture);
-+    if (ret < 0)
-+        av_log(avctx, AV_LOG_ERROR, "%s: dequeue capture buffer %d failed for request %d, %s (%d)\n", __func__, req->capture.index, req->request_fd, strerror(errno), errno);
++int ff_v4l2_request_decode_slice(AVCodecContext *avctx,
++                                 V4L2RequestPictureContext *pic,
++                                 struct v4l2_ext_control *control, int count,
++                                 bool first_slice, bool last_slice)
++{
++    V4L2RequestContext *ctx = v4l2_request_context(avctx);
 +
-+    ret = ioctl(req->request_fd, MEDIA_REQUEST_IOC_REINIT, NULL);
-+    if (ret < 0)
-+        av_log(avctx, AV_LOG_ERROR, "%s: reinit request %d failed, %s (%d)\n", __func__, req->request_fd, strerror(errno), errno);
++    /*
<Skipped 7907 lines>
================================================================

---- gitweb:

http://git.pld-linux.org/gitweb.cgi/packages/ffmpeg.git/commitdiff/e78a9e755db3278a0d448613ac8854cde51ba4d5



More information about the pld-cvs-commit mailing list