| /* | |
| * This file is part of FFmpeg. | |
| * | |
| * FFmpeg is free software; you can redistribute it and/or | |
| * modify it under the terms of the GNU Lesser General Public | |
| * License as published by the Free Software Foundation; either | |
| * version 2.1 of the License, or (at your option) any later version. | |
| * | |
| * FFmpeg is distributed in the hope that it will be useful, | |
| * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
| * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
| * Lesser General Public License for more details. | |
| * | |
| * You should have received a copy of the GNU Lesser General Public | |
| * License along with FFmpeg; if not, write to the Free Software | |
| * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | |
| */ | |
| #ifndef AVCODEC_VULKAN_DECODE_H | |
| #define AVCODEC_VULKAN_DECODE_H | |
| #include "codec_id.h" | |
| #include "decode.h" | |
| #include "hwaccel_internal.h" | |
| #include "internal.h" | |
| #include "vulkan_video.h" | |
| typedef struct FFVulkanDecodeDescriptor { | |
| enum AVCodecID codec_id; | |
| FFVulkanExtensions decode_extension; | |
| VkVideoCodecOperationFlagBitsKHR decode_op; | |
| VkExtensionProperties ext_props; | |
| } FFVulkanDecodeDescriptor; | |
| typedef struct FFVulkanDecodeProfileData { | |
| VkVideoDecodeH264ProfileInfoKHR h264_profile; | |
| VkVideoDecodeH265ProfileInfoKHR h265_profile; | |
| VkVideoDecodeAV1ProfileInfoKHR av1_profile; | |
| VkVideoDecodeUsageInfoKHR usage; | |
| VkVideoProfileInfoKHR profile; | |
| VkVideoProfileListInfoKHR profile_list; | |
| } FFVulkanDecodeProfileData; | |
| typedef struct FFVulkanDecodeShared { | |
| FFVulkanContext s; | |
| FFVkVideoCommon common; | |
| FFVkQueueFamilyCtx qf; | |
| VkVideoCapabilitiesKHR caps; | |
| VkVideoDecodeCapabilitiesKHR dec_caps; | |
| AVBufferRef *dpb_hwfc_ref; /* Only used for dedicated_dpb */ | |
| AVFrame *layered_frame; /* Only used for layered_dpb */ | |
| VkImageView layered_view; | |
| VkImageAspectFlags layered_aspect; | |
| VkVideoSessionParametersKHR empty_session_params; | |
| VkSamplerYcbcrConversion yuv_sampler; | |
| } FFVulkanDecodeShared; | |
| typedef struct FFVulkanDecodeContext { | |
| FFVulkanDecodeShared *shared_ctx; | |
| AVBufferRef *session_params; | |
| FFVkExecPool exec_pool; | |
| int dedicated_dpb; /* Oddity #1 - separate DPB images */ | |
| int layered_dpb; /* Madness #1 - layered DPB images */ | |
| int external_fg; /* Oddity #2 - hardware can't apply film grain */ | |
| uint32_t frame_id_alloc_mask; /* For AV1 only */ | |
| /* Workaround for NVIDIA drivers tested with CTS version 1.3.8 for AV1. | |
| * The tests were incorrect as the OrderHints were offset by 1. */ | |
| int quirk_av1_offset; | |
| /* Thread-local state below */ | |
| struct HEVCHeaderSet *hevc_headers; | |
| size_t hevc_headers_size; | |
| uint32_t *slice_off; | |
| unsigned int slice_off_max; | |
| } FFVulkanDecodeContext; | |
| typedef struct FFVulkanDecodePicture { | |
| AVFrame *dpb_frame; /* Only used for out-of-place decoding. */ | |
| VkImageView img_view_ref; /* Image representation view (reference) */ | |
| VkImageView img_view_out; /* Image representation view (output-only) */ | |
| VkImageView img_view_dest; /* Set to img_view_out if no layered refs are used */ | |
| VkImageAspectFlags img_aspect; /* Image plane mask bits */ | |
| VkImageAspectFlags img_aspect_ref; /* Only used for out-of-place decoding */ | |
| VkSemaphore sem; | |
| uint64_t sem_value; | |
| /* Current picture */ | |
| VkVideoPictureResourceInfoKHR ref; | |
| VkVideoReferenceSlotInfoKHR ref_slot; | |
| /* Picture refs. H264 has the maximum number of refs (36) of any supported codec. */ | |
| VkVideoPictureResourceInfoKHR refs [36]; | |
| VkVideoReferenceSlotInfoKHR ref_slots[36]; | |
| /* Main decoding struct */ | |
| VkVideoDecodeInfoKHR decode_info; | |
| /* Slice data */ | |
| AVBufferRef *slices_buf; | |
| size_t slices_size; | |
| /* Vulkan functions needed for destruction, as no other context is guaranteed to exist */ | |
| PFN_vkWaitSemaphores wait_semaphores; | |
| PFN_vkDestroyImageView destroy_image_view; | |
| } FFVulkanDecodePicture; | |
| /** | |
| * Initialize decoder. | |
| */ | |
| int ff_vk_decode_init(AVCodecContext *avctx); | |
| /** | |
| * Synchronize the contexts between 2 threads. | |
| */ | |
| int ff_vk_update_thread_context(AVCodecContext *dst, const AVCodecContext *src); | |
| /** | |
| * Initialize hw_frames_ctx with the parameters needed to decode the stream | |
| * using the parameters from avctx. | |
| * | |
| * NOTE: if avctx->internal->hwaccel_priv_data exists, will partially initialize | |
| * the context. | |
| */ | |
| int ff_vk_frame_params(AVCodecContext *avctx, AVBufferRef *hw_frames_ctx); | |
| /** | |
| * Removes current session parameters to recreate them | |
| */ | |
| int ff_vk_params_invalidate(AVCodecContext *avctx, int t, const uint8_t *b, uint32_t s); | |
| /** | |
| * Prepare a frame, creates the image view, and sets up the dpb fields. | |
| */ | |
| int ff_vk_decode_prepare_frame(FFVulkanDecodeContext *dec, AVFrame *pic, | |
| FFVulkanDecodePicture *vkpic, int is_current, | |
| int alloc_dpb); | |
| /** | |
| * Add slice data to frame. | |
| */ | |
| int ff_vk_decode_add_slice(AVCodecContext *avctx, FFVulkanDecodePicture *vp, | |
| const uint8_t *data, size_t size, int add_startcode, | |
| uint32_t *nb_slices, const uint32_t **offsets); | |
| /** | |
| * Decode a frame. | |
| */ | |
| int ff_vk_decode_frame(AVCodecContext *avctx, | |
| AVFrame *pic, FFVulkanDecodePicture *vp, | |
| AVFrame *rpic[], FFVulkanDecodePicture *rvkp[]); | |
| /** | |
| * Free a frame and its state. | |
| */ | |
| void ff_vk_decode_free_frame(AVHWDeviceContext *dev_ctx, FFVulkanDecodePicture *vp); | |
| /** | |
| * Get an FFVkBuffer suitable for decoding from. | |
| */ | |
| int ff_vk_get_decode_buffer(FFVulkanDecodeContext *ctx, AVBufferRef **buf, | |
| void *create_pNext, size_t size); | |
| /** | |
| * Create VkVideoSessionParametersKHR wrapped in an AVBufferRef. | |
| */ | |
| int ff_vk_decode_create_params(AVBufferRef **par_ref, void *logctx, FFVulkanDecodeShared *ctx, | |
| const VkVideoSessionParametersCreateInfoKHR *session_params_create); | |
| /** | |
| * Flush decoder. | |
| */ | |
| void ff_vk_decode_flush(AVCodecContext *avctx); | |
| /** | |
| * Free decoder. | |
| */ | |
| int ff_vk_decode_uninit(AVCodecContext *avctx); | |
| #endif /* AVCODEC_VULKAN_DECODE_H */ |