From patchwork Sun Sep 29 09:42:48 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Lynne X-Patchwork-Id: 51924 Delivered-To: ffmpegpatchwork2@gmail.com Received: by 2002:a59:d8ca:0:b0:48e:c0f8:d0de with SMTP id dy10csp1341198vqb; Sun, 29 Sep 2024 02:43:52 -0700 (PDT) X-Forwarded-Encrypted: i=2; AJvYcCX3lQbVuEkzYJf1eug9BKBBnMGXZcS9VveCz2u1LZVtSgWwnXoNP3wl4voOM7TMu8h4zeqK/1HDUl/vyfEuQYdJ@gmail.com X-Google-Smtp-Source: AGHT+IG/E5/2NsfAS9eyM/ZtQgwAOFZQW/nlm0VGE4f348dQxscp44XJffIsFzLy5Jrj+37JT1Lx X-Received: by 2002:a17:907:31ce:b0:a72:7a71:7f4f with SMTP id a640c23a62f3a-a93c3094b53mr1008764366b.7.1727603032266; Sun, 29 Sep 2024 02:43:52 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1727603032; cv=none; d=google.com; s=arc-20240605; b=Bm4ftb04dnbxvWCkLyDx5jWiz+W3o/n7xjVzJw6m5Ng+JtAI/kvypKafAP1MLJwOpW fd6iFe6D7EDeGL3lLFeIyr24MzvGhRB2bThb0y7yvjWue4Yb2xyQZyoBUriDDlE1jNYD dvkAXPM0tgy32vbGpmCGnSxSZaX+q41evjezgLA83xM6DTXGvnBXj2Pc3kBilNwJP1oZ 568ksjCjVQLpdSpjFIIqIee4TU97Q+dwfElZRKv4rtH3sEaA3jQfsXiibfyQVt6MBWW2 sRrdoEKws8I6pC44NlORBlh9cURZMZdmRBXPQktOE5Z4acNa+3GdEkb7zjzooGZP9n9J MdKg== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20240605; h=sender:errors-to:content-transfer-encoding:cc:reply-to:from :list-subscribe:list-help:list-post:list-archive:list-unsubscribe :list-id:precedence:subject:mime-version:message-id:date:to :delivered-to; bh=ackCg3k68p7rW2218Ovi9+kA81prbLS8ex6GT//9Y1o=; fh=nenT92/WZoU6unXd3J6UhGUdod4piddKfVtctNBOh6k=; b=A5pCGRSuXjjCxi1S1AGAJQ6K+wTBwFxXkEQ7PV6odB+X4ABockboXLx1pgDmPw7hv1 OtpgzQKSdpykYP8Vmqgx1Lq8BJVCXWgHAIhXi9ZDgKd7d92U5i6N15eBH5BDF7cgvl5o MYmkJwdYrfk/BTfW/4nNtvABbA0NrLVgKabGy+iNYVHdKaZqmtoVs6NyV8G5vNh81hAp 5NB7flYOptAb9WC/eVAQrbvijLQndghpYpcJ1P/8gbFjmfLHPWy75hm4dGkY1vD1sdPO zmOJgI/qqYbLEahxfu0nRstrI9ySGYznZNSO8SFJZwoP7Dhr8fy71o8HesNRdG0RHtG7 RGUQ==; dara=google.com ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: domain of ffmpeg-devel-bounces@ffmpeg.org designates 79.124.17.100 as permitted sender) smtp.mailfrom=ffmpeg-devel-bounces@ffmpeg.org Return-Path: Received: from ffbox0-bg.mplayerhq.hu (ffbox0-bg.ffmpeg.org. [79.124.17.100]) by mx.google.com with ESMTP id a640c23a62f3a-a93c29e70d4si452326666b.576.2024.09.29.02.43.51; Sun, 29 Sep 2024 02:43:52 -0700 (PDT) Received-SPF: pass (google.com: domain of ffmpeg-devel-bounces@ffmpeg.org designates 79.124.17.100 as permitted sender) client-ip=79.124.17.100; Authentication-Results: mx.google.com; spf=pass (google.com: domain of ffmpeg-devel-bounces@ffmpeg.org designates 79.124.17.100 as permitted sender) smtp.mailfrom=ffmpeg-devel-bounces@ffmpeg.org Received: from [127.0.1.1] (localhost [127.0.0.1]) by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTP id 4E76768DA96; Sun, 29 Sep 2024 12:43:12 +0300 (EEST) X-Original-To: ffmpeg-devel@ffmpeg.org Delivered-To: ffmpeg-devel@ffmpeg.org Received: from vidala.lynne.ee (vidala.pars.ee [116.203.72.101]) by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTPS id 9528F68D9FF for ; Sun, 29 Sep 2024 12:43:00 +0300 (EEST) To: ffmpeg-devel@ffmpeg.org Date: Sun, 29 Sep 2024 11:42:48 +0200 Message-ID: <20240929094256.396352-1-dev@lynne.ee> X-Mailer: git-send-email 2.45.2.753.g447d99e1c3b MIME-Version: 1.0 Subject: [FFmpeg-devel] [PATCH 1/5] vulkan: merge FFVkSPIRVShader and FFVkPipeline into FFVkShader X-BeenThere: ffmpeg-devel@ffmpeg.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: FFmpeg development discussions and patches List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Lynne via ffmpeg-devel From: Lynne Reply-To: FFmpeg development discussions and patches Cc: Lynne Errors-To: ffmpeg-devel-bounces@ffmpeg.org Sender: "ffmpeg-devel" X-TUID: Nf4JJoty/OxZ Pipelines are just shaders. There's no reason to treat them differently. This also lets us implement shader objects and is an overall cleanup. --- libavfilter/vf_avgblur_vulkan.c | 28 +- libavfilter/vf_blend_vulkan.c | 24 +- libavfilter/vf_bwdif_vulkan.c | 29 +- libavfilter/vf_chromaber_vulkan.c | 28 +- libavfilter/vf_flip_vulkan.c | 24 +- libavfilter/vf_gblur_vulkan.c | 54 ++- libavfilter/vf_nlmeans_vulkan.c | 135 +++---- libavfilter/vf_overlay_vulkan.c | 28 +- libavfilter/vf_scale_vulkan.c | 28 +- libavfilter/vf_transpose_vulkan.c | 24 +- libavfilter/vf_xfade_vulkan.c | 28 +- libavfilter/vsrc_testsrc_vulkan.c | 30 +- libavfilter/vulkan_filter.c | 78 ++-- libavfilter/vulkan_filter.h | 6 +- libavfilter/vulkan_glslang.c | 4 +- libavfilter/vulkan_shaderc.c | 4 +- libavfilter/vulkan_spirv.h | 2 +- libavutil/vulkan.c | 633 ++++++++++++++++-------------- libavutil/vulkan.h | 146 ++++--- 19 files changed, 707 insertions(+), 626 deletions(-) diff --git a/libavfilter/vf_avgblur_vulkan.c b/libavfilter/vf_avgblur_vulkan.c index 439766968e..3972ea0cbb 100644 --- a/libavfilter/vf_avgblur_vulkan.c +++ b/libavfilter/vf_avgblur_vulkan.c @@ -33,8 +33,7 @@ typedef struct AvgBlurVulkanContext { FFVkExecPool e; FFVkQueueFamilyCtx qf; VkSampler sampler; - FFVulkanPipeline pl; - FFVkSPIRVShader shd; + FFVulkanShader shd; /* Push constants / options */ struct { @@ -68,7 +67,7 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) AvgBlurVulkanContext *s = ctx->priv; FFVulkanContext *vkctx = &s->vkctx; const int planes = av_pix_fmt_count_planes(s->vkctx.output_format); - FFVkSPIRVShader *shd; + FFVulkanShader *shd; FFVkSPIRVCompiler *spv; FFVulkanDescriptorSetBinding *desc; @@ -81,12 +80,13 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) ff_vk_qf_init(vkctx, &s->qf, VK_QUEUE_COMPUTE_BIT); RET(ff_vk_exec_pool_init(vkctx, &s->qf, &s->e, s->qf.nb_queues*4, 0, 0, 0, NULL)); RET(ff_vk_init_sampler(vkctx, &s->sampler, 1, VK_FILTER_LINEAR)); - RET(ff_vk_shader_init(&s->pl, &s->shd, "avgblur_compute", - VK_SHADER_STAGE_COMPUTE_BIT, 0)); + RET(ff_vk_shader_init(vkctx, &s->shd, "avgblur", + VK_SHADER_STAGE_COMPUTE_BIT, + NULL, 0, + 32, 1, 1, + 0)); shd = &s->shd; - ff_vk_shader_set_compute_sizes(shd, 32, 1, 1); - desc = (FFVulkanDescriptorSetBinding []) { { .name = "input_img", @@ -107,7 +107,7 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) }, }; - RET(ff_vk_pipeline_descriptor_set_add(vkctx, &s->pl, shd, desc, 2, 0, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, shd, desc, 2, 0, 0)); GLSLC(0, layout(push_constant, std430) uniform pushConstants { ); GLSLC(1, vec4 filter_norm; ); @@ -115,8 +115,8 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) GLSLC(0, }; ); GLSLC(0, ); - ff_vk_add_push_constant(&s->pl, 0, sizeof(s->opts), - VK_SHADER_STAGE_COMPUTE_BIT); + ff_vk_shader_add_push_const(&s->shd, 0, sizeof(s->opts), + VK_SHADER_STAGE_COMPUTE_BIT); GLSLD( blur_kernel ); GLSLC(0, void main() ); @@ -139,10 +139,9 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) RET(spv->compile_shader(spv, ctx, &s->shd, &spv_data, &spv_len, "main", &spv_opaque)); - RET(ff_vk_shader_create(vkctx, &s->shd, spv_data, spv_len, "main")); + RET(ff_vk_shader_link(vkctx, &s->shd, spv_data, spv_len, "main")); - RET(ff_vk_init_compute_pipeline(vkctx, &s->pl, &s->shd)); - RET(ff_vk_exec_pipeline_register(vkctx, &s->e, &s->pl)); + RET(ff_vk_shader_register_exec(vkctx, &s->e, &s->shd)); s->initialized = 1; s->opts.filter_len[0] = s->size_x - 1; @@ -180,7 +179,7 @@ static int avgblur_vulkan_filter_frame(AVFilterLink *link, AVFrame *in) if (!s->initialized) RET(init_filter(ctx, in)); - RET(ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->pl, + RET(ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->shd, out, in, s->sampler, &s->opts, sizeof(s->opts))); err = av_frame_copy_props(out, in); @@ -204,7 +203,6 @@ static void avgblur_vulkan_uninit(AVFilterContext *avctx) FFVulkanFunctions *vk = &vkctx->vkfn; ff_vk_exec_pool_free(vkctx, &s->e); - ff_vk_pipeline_free(vkctx, &s->pl); ff_vk_shader_free(vkctx, &s->shd); if (s->sampler) diff --git a/libavfilter/vf_blend_vulkan.c b/libavfilter/vf_blend_vulkan.c index f3eb5355f1..ccc025fe6b 100644 --- a/libavfilter/vf_blend_vulkan.c +++ b/libavfilter/vf_blend_vulkan.c @@ -46,10 +46,9 @@ typedef struct BlendVulkanContext { FFFrameSync fs; int initialized; - FFVulkanPipeline pl; FFVkExecPool e; FFVkQueueFamilyCtx qf; - FFVkSPIRVShader shd; + FFVulkanShader shd; VkSampler sampler; FilterParamsVulkan params[4]; @@ -132,7 +131,7 @@ static av_cold int init_filter(AVFilterContext *avctx) BlendVulkanContext *s = avctx->priv; FFVulkanContext *vkctx = &s->vkctx; const int planes = av_pix_fmt_count_planes(s->vkctx.output_format); - FFVkSPIRVShader *shd = &s->shd; + FFVulkanShader *shd = &s->shd; FFVkSPIRVCompiler *spv; FFVulkanDescriptorSetBinding *desc; @@ -145,10 +144,11 @@ static av_cold int init_filter(AVFilterContext *avctx) ff_vk_qf_init(vkctx, &s->qf, VK_QUEUE_COMPUTE_BIT); RET(ff_vk_exec_pool_init(vkctx, &s->qf, &s->e, s->qf.nb_queues*4, 0, 0, 0, NULL)); RET(ff_vk_init_sampler(vkctx, &s->sampler, 1, VK_FILTER_NEAREST)); - RET(ff_vk_shader_init(&s->pl, &s->shd, "blend_compute", - VK_SHADER_STAGE_COMPUTE_BIT, 0)); - - ff_vk_shader_set_compute_sizes(&s->shd, 32, 32, 1); + RET(ff_vk_shader_init(vkctx, &s->shd, "blend", + VK_SHADER_STAGE_COMPUTE_BIT, + NULL, 0, + 32, 32, 1, + 0)); desc = (FFVulkanDescriptorSetBinding []) { { @@ -178,7 +178,7 @@ static av_cold int init_filter(AVFilterContext *avctx) }, }; - RET(ff_vk_pipeline_descriptor_set_add(vkctx, &s->pl, shd, desc, 3, 0, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, &s->shd, desc, 3, 0, 0)); for (int i = 0, j = 0; i < planes; i++) { for (j = 0; j < i; j++) @@ -210,10 +210,9 @@ static av_cold int init_filter(AVFilterContext *avctx) RET(spv->compile_shader(spv, avctx, shd, &spv_data, &spv_len, "main", &spv_opaque)); - RET(ff_vk_shader_create(vkctx, shd, spv_data, spv_len, "main")); + RET(ff_vk_shader_link(vkctx, shd, spv_data, spv_len, "main")); - RET(ff_vk_init_compute_pipeline(vkctx, &s->pl, shd)); - RET(ff_vk_exec_pipeline_register(vkctx, &s->e, &s->pl)); + RET(ff_vk_shader_register_exec(vkctx, &s->e, &s->shd)); s->initialized = 1; @@ -257,7 +256,7 @@ static int blend_frame(FFFrameSync *fs) RET(init_filter(avctx)); } - RET(ff_vk_filter_process_Nin(&s->vkctx, &s->e, &s->pl, + RET(ff_vk_filter_process_Nin(&s->vkctx, &s->e, &s->shd, out, (AVFrame *[]){ top, bottom }, 2, s->sampler, NULL, 0)); @@ -284,7 +283,6 @@ static av_cold void uninit(AVFilterContext *avctx) FFVulkanFunctions *vk = &vkctx->vkfn; ff_vk_exec_pool_free(vkctx, &s->e); - ff_vk_pipeline_free(vkctx, &s->pl); ff_vk_shader_free(vkctx, &s->shd); if (s->sampler) diff --git a/libavfilter/vf_bwdif_vulkan.c b/libavfilter/vf_bwdif_vulkan.c index 4e43ade1c2..3164eb3395 100644 --- a/libavfilter/vf_bwdif_vulkan.c +++ b/libavfilter/vf_bwdif_vulkan.c @@ -35,8 +35,7 @@ typedef struct BWDIFVulkanContext { FFVkExecPool e; FFVkQueueFamilyCtx qf; VkSampler sampler; - FFVulkanPipeline pl; - FFVkSPIRVShader shd; + FFVulkanShader shd; } BWDIFVulkanContext; typedef struct BWDIFParameters { @@ -100,7 +99,7 @@ static av_cold int init_filter(AVFilterContext *ctx) BWDIFVulkanContext *s = ctx->priv; FFVulkanContext *vkctx = &s->vkctx; const int planes = av_pix_fmt_count_planes(s->vkctx.output_format); - FFVkSPIRVShader *shd; + FFVulkanShader *shd; FFVkSPIRVCompiler *spv; FFVulkanDescriptorSetBinding *desc; @@ -113,11 +112,13 @@ static av_cold int init_filter(AVFilterContext *ctx) ff_vk_qf_init(vkctx, &s->qf, VK_QUEUE_COMPUTE_BIT); RET(ff_vk_exec_pool_init(vkctx, &s->qf, &s->e, s->qf.nb_queues*4, 0, 0, 0, NULL)); RET(ff_vk_init_sampler(vkctx, &s->sampler, 1, VK_FILTER_NEAREST)); - RET(ff_vk_shader_init(&s->pl, &s->shd, "bwdif_compute", - VK_SHADER_STAGE_COMPUTE_BIT, 0)); - shd = &s->shd; - ff_vk_shader_set_compute_sizes(shd, 1, 64, 1); + RET(ff_vk_shader_init(vkctx, &s->shd, "bwdif", + VK_SHADER_STAGE_COMPUTE_BIT, + NULL, 0, + 1, 64, 1, + 0)); + shd = &s->shd; desc = (FFVulkanDescriptorSetBinding []) { { @@ -155,7 +156,7 @@ static av_cold int init_filter(AVFilterContext *ctx) }, }; - RET(ff_vk_pipeline_descriptor_set_add(vkctx, &s->pl, shd, desc, 4, 0, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, &s->shd, desc, 4, 0, 0)); GLSLC(0, layout(push_constant, std430) uniform pushConstants { ); GLSLC(1, int parity; ); @@ -163,8 +164,8 @@ static av_cold int init_filter(AVFilterContext *ctx) GLSLC(1, int current_field; ); GLSLC(0, }; ); - ff_vk_add_push_constant(&s->pl, 0, sizeof(BWDIFParameters), - VK_SHADER_STAGE_COMPUTE_BIT); + ff_vk_shader_add_push_const(&s->shd, 0, sizeof(BWDIFParameters), + VK_SHADER_STAGE_COMPUTE_BIT); GLSLD( filter_fn ); GLSLC(0, void main() ); @@ -245,10 +246,9 @@ static av_cold int init_filter(AVFilterContext *ctx) RET(spv->compile_shader(spv, ctx, &s->shd, &spv_data, &spv_len, "main", &spv_opaque)); - RET(ff_vk_shader_create(vkctx, &s->shd, spv_data, spv_len, "main")); + RET(ff_vk_shader_link(vkctx, &s->shd, spv_data, spv_len, "main")); - RET(ff_vk_init_compute_pipeline(vkctx, &s->pl, &s->shd)); - RET(ff_vk_exec_pipeline_register(vkctx, &s->e, &s->pl)); + RET(ff_vk_shader_register_exec(vkctx, &s->e, &s->shd)); s->initialized = 1; @@ -272,7 +272,7 @@ static void bwdif_vulkan_filter_frame(AVFilterContext *ctx, AVFrame *dst, .current_field = y->current_field, }; - ff_vk_filter_process_Nin(&s->vkctx, &s->e, &s->pl, dst, + ff_vk_filter_process_Nin(&s->vkctx, &s->e, &s->shd, dst, (AVFrame *[]){ y->prev, y->cur, y->next }, 3, s->sampler, ¶ms, sizeof(params)); @@ -287,7 +287,6 @@ static void bwdif_vulkan_uninit(AVFilterContext *avctx) FFVulkanFunctions *vk = &vkctx->vkfn; ff_vk_exec_pool_free(vkctx, &s->e); - ff_vk_pipeline_free(vkctx, &s->pl); ff_vk_shader_free(vkctx, &s->shd); if (s->sampler) diff --git a/libavfilter/vf_chromaber_vulkan.c b/libavfilter/vf_chromaber_vulkan.c index 60c8378b11..450715b36c 100644 --- a/libavfilter/vf_chromaber_vulkan.c +++ b/libavfilter/vf_chromaber_vulkan.c @@ -30,10 +30,9 @@ typedef struct ChromaticAberrationVulkanContext { FFVulkanContext vkctx; int initialized; - FFVulkanPipeline pl; FFVkExecPool e; FFVkQueueFamilyCtx qf; - FFVkSPIRVShader shd; + FFVulkanShader shd; VkSampler sampler; /* Push constants / options */ @@ -75,7 +74,7 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) ChromaticAberrationVulkanContext *s = ctx->priv; FFVulkanContext *vkctx = &s->vkctx; const int planes = av_pix_fmt_count_planes(s->vkctx.output_format); - FFVkSPIRVShader *shd = &s->shd; + FFVulkanShader *shd = &s->shd; FFVkSPIRVCompiler *spv; FFVulkanDescriptorSetBinding *desc; @@ -92,18 +91,19 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) ff_vk_qf_init(vkctx, &s->qf, VK_QUEUE_COMPUTE_BIT); RET(ff_vk_exec_pool_init(vkctx, &s->qf, &s->e, s->qf.nb_queues*4, 0, 0, 0, NULL)); RET(ff_vk_init_sampler(vkctx, &s->sampler, 0, VK_FILTER_LINEAR)); - RET(ff_vk_shader_init(&s->pl, &s->shd, "chromaber_compute", - VK_SHADER_STAGE_COMPUTE_BIT, 0)); - - ff_vk_shader_set_compute_sizes(&s->shd, 32, 32, 1); + RET(ff_vk_shader_init(vkctx, &s->shd, "chromatic_abberation", + VK_SHADER_STAGE_COMPUTE_BIT, + NULL, 0, + 32, 32, 1, + 0)); GLSLC(0, layout(push_constant, std430) uniform pushConstants { ); GLSLC(1, vec2 dist; ); GLSLC(0, }; ); GLSLC(0, ); - ff_vk_add_push_constant(&s->pl, 0, sizeof(s->opts), - VK_SHADER_STAGE_COMPUTE_BIT); + ff_vk_shader_add_push_const(&s->shd, 0, sizeof(s->opts), + VK_SHADER_STAGE_COMPUTE_BIT); desc = (FFVulkanDescriptorSetBinding []) { { @@ -125,7 +125,7 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) }, }; - RET(ff_vk_pipeline_descriptor_set_add(vkctx, &s->pl, shd, desc, 2, 0, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, &s->shd, desc, 2, 0, 0)); GLSLD( distort_chroma_kernel ); GLSLC(0, void main() ); @@ -150,10 +150,9 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) RET(spv->compile_shader(spv, ctx, shd, &spv_data, &spv_len, "main", &spv_opaque)); - RET(ff_vk_shader_create(vkctx, shd, spv_data, spv_len, "main")); + RET(ff_vk_shader_link(vkctx, shd, spv_data, spv_len, "main")); - RET(ff_vk_init_compute_pipeline(vkctx, &s->pl, shd)); - RET(ff_vk_exec_pipeline_register(vkctx, &s->e, &s->pl)); + RET(ff_vk_shader_register_exec(vkctx, &s->e, &s->shd)); s->initialized = 1; @@ -182,7 +181,7 @@ static int chromaber_vulkan_filter_frame(AVFilterLink *link, AVFrame *in) if (!s->initialized) RET(init_filter(ctx, in)); - RET(ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->pl, out, in, + RET(ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->shd, out, in, s->sampler, &s->opts, sizeof(s->opts))); err = av_frame_copy_props(out, in); @@ -206,7 +205,6 @@ static void chromaber_vulkan_uninit(AVFilterContext *avctx) FFVulkanFunctions *vk = &vkctx->vkfn; ff_vk_exec_pool_free(vkctx, &s->e); - ff_vk_pipeline_free(vkctx, &s->pl); ff_vk_shader_free(vkctx, &s->shd); if (s->sampler) diff --git a/libavfilter/vf_flip_vulkan.c b/libavfilter/vf_flip_vulkan.c index 1271396803..2b89a9a6a3 100644 --- a/libavfilter/vf_flip_vulkan.c +++ b/libavfilter/vf_flip_vulkan.c @@ -37,10 +37,9 @@ typedef struct FlipVulkanContext { FFVulkanContext vkctx; int initialized; - FFVulkanPipeline pl; FFVkExecPool e; FFVkQueueFamilyCtx qf; - FFVkSPIRVShader shd; + FFVulkanShader shd; VkSampler sampler; } FlipVulkanContext; @@ -53,7 +52,7 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in, enum FlipType FlipVulkanContext *s = ctx->priv; FFVulkanContext *vkctx = &s->vkctx; const int planes = av_pix_fmt_count_planes(s->vkctx.output_format); - FFVkSPIRVShader *shd = &s->shd; + FFVulkanShader *shd = &s->shd; FFVkSPIRVCompiler *spv; FFVulkanDescriptorSetBinding *desc; @@ -66,10 +65,11 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in, enum FlipType ff_vk_qf_init(vkctx, &s->qf, VK_QUEUE_COMPUTE_BIT); RET(ff_vk_exec_pool_init(vkctx, &s->qf, &s->e, s->qf.nb_queues*4, 0, 0, 0, NULL)); RET(ff_vk_init_sampler(vkctx, &s->sampler, 1, VK_FILTER_LINEAR)); - RET(ff_vk_shader_init(&s->pl, &s->shd, "flip_compute", - VK_SHADER_STAGE_COMPUTE_BIT, 0)); - - ff_vk_shader_set_compute_sizes(&s->shd, 32, 32, 1); + RET(ff_vk_shader_init(vkctx, &s->shd, "flip", + VK_SHADER_STAGE_COMPUTE_BIT, + NULL, 0, + 32, 32, 1, + 0)); desc = (FFVulkanDescriptorSetBinding []) { { @@ -91,7 +91,7 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in, enum FlipType }, }; - RET(ff_vk_pipeline_descriptor_set_add(vkctx, &s->pl, shd, desc, 2, 0, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, &s->shd, desc, 2, 0, 0)); GLSLC(0, void main() ); GLSLC(0, { ); @@ -123,10 +123,9 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in, enum FlipType RET(spv->compile_shader(spv, ctx, shd, &spv_data, &spv_len, "main", &spv_opaque)); - RET(ff_vk_shader_create(vkctx, shd, spv_data, spv_len, "main")); + RET(ff_vk_shader_link(vkctx, shd, spv_data, spv_len, "main")); - RET(ff_vk_init_compute_pipeline(vkctx, &s->pl, shd)); - RET(ff_vk_exec_pipeline_register(vkctx, &s->e, &s->pl)); + RET(ff_vk_shader_register_exec(vkctx, &s->e, &s->shd)); s->initialized = 1; @@ -147,7 +146,6 @@ static av_cold void flip_vulkan_uninit(AVFilterContext *avctx) FFVulkanFunctions *vk = &vkctx->vkfn; ff_vk_exec_pool_free(vkctx, &s->e); - ff_vk_pipeline_free(vkctx, &s->pl); ff_vk_shader_free(vkctx, &s->shd); if (s->sampler) @@ -176,7 +174,7 @@ static int filter_frame(AVFilterLink *link, AVFrame *in, enum FlipType type) if (!s->initialized) RET(init_filter(ctx, in, type)); - RET(ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->pl, out, in, + RET(ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->shd, out, in, s->sampler, NULL, 0)); RET(av_frame_copy_props(out, in)); diff --git a/libavfilter/vf_gblur_vulkan.c b/libavfilter/vf_gblur_vulkan.c index d0fb6c9940..a56a6ece00 100644 --- a/libavfilter/vf_gblur_vulkan.c +++ b/libavfilter/vf_gblur_vulkan.c @@ -38,11 +38,9 @@ typedef struct GBlurVulkanContext { FFVkExecPool e; FFVkQueueFamilyCtx qf; VkSampler sampler; - FFVulkanPipeline pl_hor; - FFVkSPIRVShader shd_hor; + FFVulkanShader shd_hor; FFVkBuffer params_hor; - FFVulkanPipeline pl_ver; - FFVkSPIRVShader shd_ver; + FFVulkanShader shd_ver; FFVkBuffer params_ver; int size; @@ -123,8 +121,8 @@ static av_cold void init_gaussian_params(GBlurVulkanContext *s) init_kernel_size(s, &s->sizeV); } -static int init_gblur_pipeline(GBlurVulkanContext *s, FFVulkanPipeline *pl, - FFVkSPIRVShader *shd, FFVkBuffer *params_buf, +static int init_gblur_pipeline(GBlurVulkanContext *s, + FFVulkanShader *shd, FFVkBuffer *params_buf, int ksize, float sigma, FFVkSPIRVCompiler *spv) { int err = 0; @@ -150,7 +148,7 @@ static int init_gblur_pipeline(GBlurVulkanContext *s, FFVulkanPipeline *pl, buf_desc.buf_content = kernel_def; - RET(ff_vk_pipeline_descriptor_set_add(&s->vkctx, pl, shd, &buf_desc, 1, 1, 0)); + RET(ff_vk_shader_add_descriptor_set(&s->vkctx, shd, &buf_desc, 1, 1, 0)); GLSLD( gblur_func ); GLSLC(0, void main() ); @@ -173,10 +171,9 @@ static int init_gblur_pipeline(GBlurVulkanContext *s, FFVulkanPipeline *pl, RET(spv->compile_shader(spv, s, shd, &spv_data, &spv_len, "main", &spv_opaque)); - RET(ff_vk_shader_create(&s->vkctx, shd, spv_data, spv_len, "main")); + RET(ff_vk_shader_link(&s->vkctx, shd, spv_data, spv_len, "main")); - RET(ff_vk_init_compute_pipeline(&s->vkctx, pl, shd)); - RET(ff_vk_exec_pipeline_register(&s->vkctx, &s->e, pl)); + RET(ff_vk_shader_register_exec(&s->vkctx, &s->e, shd)); RET(ff_vk_create_buf(&s->vkctx, params_buf, sizeof(float) * ksize, NULL, NULL, VK_BUFFER_USAGE_SHADER_DEVICE_ADDRESS_BIT | @@ -187,10 +184,9 @@ static int init_gblur_pipeline(GBlurVulkanContext *s, FFVulkanPipeline *pl, init_gaussian_kernel((float *)kernel_mapped, sigma, ksize); RET(ff_vk_unmap_buffer(&s->vkctx, params_buf, 1)); - - RET(ff_vk_set_descriptor_buffer(&s->vkctx, pl, NULL, 1, 0, 0, - params_buf, 0, params_buf->size, - VK_FORMAT_UNDEFINED)); + RET(ff_vk_shader_update_desc_buffer(&s->vkctx, &s->e.contexts[0], shd, 1, 0, 0, + params_buf, 0, params_buf->size, + VK_FORMAT_UNDEFINED)); fail: av_free(kernel_def); @@ -206,7 +202,7 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) FFVulkanContext *vkctx = &s->vkctx; const int planes = av_pix_fmt_count_planes(s->vkctx.output_format); - FFVkSPIRVShader *shd; + FFVulkanShader *shd; FFVkSPIRVCompiler *spv; FFVulkanDescriptorSetBinding *desc; @@ -219,10 +215,6 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) ff_vk_qf_init(vkctx, &s->qf, VK_QUEUE_COMPUTE_BIT); RET(ff_vk_exec_pool_init(vkctx, &s->qf, &s->e, s->qf.nb_queues*4, 0, 0, 0, NULL)); RET(ff_vk_init_sampler(vkctx, &s->sampler, 1, VK_FILTER_LINEAR)); - RET(ff_vk_shader_init(&s->pl_hor, &s->shd_hor, "gblur_hor_compute", - VK_SHADER_STAGE_COMPUTE_BIT, 0)); - RET(ff_vk_shader_init(&s->pl_ver, &s->shd_ver, "gblur_ver_compute", - VK_SHADER_STAGE_COMPUTE_BIT, 0)); desc = (FFVulkanDescriptorSetBinding []) { { @@ -248,22 +240,30 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) { shd = &s->shd_hor; - ff_vk_shader_set_compute_sizes(shd, 32, 1, 1); + RET(ff_vk_shader_init(vkctx, shd, "gblur_hor", + VK_SHADER_STAGE_COMPUTE_BIT, + NULL, 0, + 32, 1, 1, + 0)); - RET(ff_vk_pipeline_descriptor_set_add(vkctx, &s->pl_hor, shd, desc, 2, 0, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, shd, desc, 2, 0, 0)); GLSLC(0, #define OFFSET (vec2(i, 0.0))); - RET(init_gblur_pipeline(s, &s->pl_hor, shd, &s->params_hor, s->size, s->sigma, spv)); + RET(init_gblur_pipeline(s, shd, &s->params_hor, s->size, s->sigma, spv)); } { shd = &s->shd_ver; - ff_vk_shader_set_compute_sizes(shd, 1, 32, 1); + RET(ff_vk_shader_init(vkctx, shd, "gblur_hor", + VK_SHADER_STAGE_COMPUTE_BIT, + NULL, 0, + 1, 32, 1, + 0)); - RET(ff_vk_pipeline_descriptor_set_add(vkctx, &s->pl_ver, shd, desc, 2, 0, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, shd, desc, 2, 0, 0)); GLSLC(0, #define OFFSET (vec2(0.0, i))); - RET(init_gblur_pipeline(s, &s->pl_ver, shd, &s->params_ver, s->sizeV, s->sigmaV, spv)); + RET(init_gblur_pipeline(s, shd, &s->params_ver, s->sizeV, s->sigmaV, spv)); } s->initialized = 1; @@ -282,8 +282,6 @@ static av_cold void gblur_vulkan_uninit(AVFilterContext *avctx) FFVulkanFunctions *vk = &vkctx->vkfn; ff_vk_exec_pool_free(vkctx, &s->e); - ff_vk_pipeline_free(vkctx, &s->pl_hor); - ff_vk_pipeline_free(vkctx, &s->pl_ver); ff_vk_shader_free(vkctx, &s->shd_hor); ff_vk_shader_free(vkctx, &s->shd_ver); ff_vk_free_buf(vkctx, &s->params_hor); @@ -322,7 +320,7 @@ static int gblur_vulkan_filter_frame(AVFilterLink *link, AVFrame *in) RET(init_filter(ctx, in)); RET(ff_vk_filter_process_2pass(&s->vkctx, &s->e, - (FFVulkanPipeline *[2]){ &s->pl_hor, &s->pl_ver }, + (FFVulkanShader *[2]){ &s->shd_hor, &s->shd_ver }, out, tmp, in, s->sampler, NULL, 0)); err = av_frame_copy_props(out, in); diff --git a/libavfilter/vf_nlmeans_vulkan.c b/libavfilter/vf_nlmeans_vulkan.c index fc9b522c80..05c752925e 100644 --- a/libavfilter/vf_nlmeans_vulkan.c +++ b/libavfilter/vf_nlmeans_vulkan.c @@ -45,11 +45,8 @@ typedef struct NLMeansVulkanContext { FFVkBuffer xyoffsets_buf; int pl_weights_rows; - FFVulkanPipeline pl_weights; - FFVkSPIRVShader shd_weights; - - FFVulkanPipeline pl_denoise; - FFVkSPIRVShader shd_denoise; + FFVulkanShader shd_weights; + FFVulkanShader shd_denoise; int *xoffsets; int *yoffsets; @@ -69,7 +66,7 @@ typedef struct NLMeansVulkanContext { extern const char *ff_source_prefix_sum_comp; -static void insert_first(FFVkSPIRVShader *shd, int r, const char *off, int horiz, int plane, int comp) +static void insert_first(FFVulkanShader *shd, int r, const char *off, int horiz, int plane, int comp) { GLSLF(4, s1 = texture(input_img[%i], pos + ivec2(%i + %s, %i + %s))[%i]; ,plane, horiz ? r : 0, horiz ? off : "0", !horiz ? r : 0, !horiz ? off : "0", comp); @@ -86,7 +83,7 @@ static void insert_first(FFVkSPIRVShader *shd, int r, const char *off, int horiz GLSLC(4, s2 = (s1 - s2) * (s1 - s2); ); } -static void insert_horizontal_pass(FFVkSPIRVShader *shd, int nb_rows, int first, int plane, int comp) +static void insert_horizontal_pass(FFVulkanShader *shd, int nb_rows, int first, int plane, int comp) { GLSLF(1, pos.y = int(gl_GlobalInvocationID.x) * %i; ,nb_rows); if (!first) @@ -112,7 +109,7 @@ static void insert_horizontal_pass(FFVkSPIRVShader *shd, int nb_rows, int first, GLSLC(0, ); } -static void insert_vertical_pass(FFVkSPIRVShader *shd, int nb_rows, int first, int plane, int comp) +static void insert_vertical_pass(FFVulkanShader *shd, int nb_rows, int first, int plane, int comp) { GLSLF(1, pos.x = int(gl_GlobalInvocationID.x) * %i; ,nb_rows); GLSLC(1, #pragma unroll(1) ); @@ -141,7 +138,7 @@ static void insert_vertical_pass(FFVkSPIRVShader *shd, int nb_rows, int first, i GLSLC(0, ); } -static void insert_weights_pass(FFVkSPIRVShader *shd, int nb_rows, int vert, +static void insert_weights_pass(FFVulkanShader *shd, int nb_rows, int vert, int t, int dst_comp, int plane, int comp) { GLSLF(1, p = patch_size[%i]; ,dst_comp); @@ -214,7 +211,7 @@ typedef struct HorizontalPushData { } HorizontalPushData; static av_cold int init_weights_pipeline(FFVulkanContext *vkctx, FFVkExecPool *exec, - FFVulkanPipeline *pl, FFVkSPIRVShader *shd, + FFVulkanShader *shd, VkSampler sampler, FFVkSPIRVCompiler *spv, int width, int height, int t, const AVPixFmtDescriptor *desc, @@ -241,8 +238,12 @@ static av_cold int init_weights_pipeline(FFVulkanContext *vkctx, FFVkExecPool *e wg_rows++; } - RET(ff_vk_shader_init(pl, shd, "nlmeans_weights", VK_SHADER_STAGE_COMPUTE_BIT, 0)); - ff_vk_shader_set_compute_sizes(shd, wg_size, 1, 1); + RET(ff_vk_shader_init(vkctx, shd, "nlmeans_weights", + VK_SHADER_STAGE_COMPUTE_BIT, + NULL, 0, + wg_size, 1, 1, + 0)); + *nb_rows = wg_rows; if (t > 1) @@ -269,7 +270,8 @@ static av_cold int init_weights_pipeline(FFVulkanContext *vkctx, FFVkExecPool *e GLSLC(0, }; ); GLSLC(0, ); - ff_vk_add_push_constant(pl, 0, sizeof(HorizontalPushData), VK_SHADER_STAGE_COMPUTE_BIT); + ff_vk_shader_add_push_const(shd, 0, sizeof(HorizontalPushData), + VK_SHADER_STAGE_COMPUTE_BIT); desc_set = (FFVulkanDescriptorSetBinding []) { { @@ -329,7 +331,7 @@ static av_cold int init_weights_pipeline(FFVulkanContext *vkctx, FFVkExecPool *e .buf_content = "float sums_3[];", }, }; - RET(ff_vk_pipeline_descriptor_set_add(vkctx, pl, shd, desc_set, 1 + 2*desc->nb_components, 0, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, shd, desc_set, 1 + 2*desc->nb_components, 0, 0)); desc_set = (FFVulkanDescriptorSetBinding []) { { @@ -340,7 +342,7 @@ static av_cold int init_weights_pipeline(FFVulkanContext *vkctx, FFVkExecPool *e .buf_content = "ivec2 xyoffsets[];", }, }; - RET(ff_vk_pipeline_descriptor_set_add(vkctx, pl, shd, desc_set, 1, 1, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, shd, desc_set, 1, 1, 0)); GLSLC(0, ); GLSLC(0, void main() ); @@ -401,10 +403,9 @@ static av_cold int init_weights_pipeline(FFVulkanContext *vkctx, FFVkExecPool *e GLSLC(0, } ); RET(spv->compile_shader(spv, vkctx, shd, &spv_data, &spv_len, "main", &spv_opaque)); - RET(ff_vk_shader_create(vkctx, shd, spv_data, spv_len, "main")); + RET(ff_vk_shader_link(vkctx, shd, spv_data, spv_len, "main")); - RET(ff_vk_init_compute_pipeline(vkctx, pl, shd)); - RET(ff_vk_exec_pipeline_register(vkctx, exec, pl)); + RET(ff_vk_shader_register_exec(vkctx, exec, shd)); fail: if (spv_opaque) @@ -418,7 +419,7 @@ typedef struct DenoisePushData { } DenoisePushData; static av_cold int init_denoise_pipeline(FFVulkanContext *vkctx, FFVkExecPool *exec, - FFVulkanPipeline *pl, FFVkSPIRVShader *shd, + FFVulkanShader *shd, VkSampler sampler, FFVkSPIRVCompiler *spv, const AVPixFmtDescriptor *desc, int planes) { @@ -428,16 +429,18 @@ static av_cold int init_denoise_pipeline(FFVulkanContext *vkctx, FFVkExecPool *e void *spv_opaque = NULL; FFVulkanDescriptorSetBinding *desc_set; - RET(ff_vk_shader_init(pl, shd, "nlmeans_denoise", - VK_SHADER_STAGE_COMPUTE_BIT, 0)); - - ff_vk_shader_set_compute_sizes(shd, 32, 32, 1); + RET(ff_vk_shader_init(vkctx, shd, "nlmeans_denoise", + VK_SHADER_STAGE_COMPUTE_BIT, + NULL, 0, + 32, 32, 1, + 0)); GLSLC(0, layout(push_constant, std430) uniform pushConstants { ); GLSLC(1, uvec4 ws_stride; ); GLSLC(0, }; ); - ff_vk_add_push_constant(pl, 0, sizeof(DenoisePushData), VK_SHADER_STAGE_COMPUTE_BIT); + ff_vk_shader_add_push_const(shd, 0, sizeof(DenoisePushData), + VK_SHADER_STAGE_COMPUTE_BIT); desc_set = (FFVulkanDescriptorSetBinding []) { { @@ -458,7 +461,7 @@ static av_cold int init_denoise_pipeline(FFVulkanContext *vkctx, FFVkExecPool *e .stages = VK_SHADER_STAGE_COMPUTE_BIT, }, }; - RET(ff_vk_pipeline_descriptor_set_add(vkctx, pl, shd, desc_set, 2, 0, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, shd, desc_set, 2, 0, 0)); desc_set = (FFVulkanDescriptorSetBinding []) { { @@ -519,7 +522,7 @@ static av_cold int init_denoise_pipeline(FFVulkanContext *vkctx, FFVkExecPool *e }, }; - RET(ff_vk_pipeline_descriptor_set_add(vkctx, pl, shd, desc_set, 2*desc->nb_components, 0, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, shd, desc_set, 2*desc->nb_components, 0, 0)); GLSLC(0, void main() ); GLSLC(0, { ); @@ -551,10 +554,9 @@ static av_cold int init_denoise_pipeline(FFVulkanContext *vkctx, FFVkExecPool *e GLSLC(0, } ); RET(spv->compile_shader(spv, vkctx, shd, &spv_data, &spv_len, "main", &spv_opaque)); - RET(ff_vk_shader_create(vkctx, shd, spv_data, spv_len, "main")); + RET(ff_vk_shader_link(vkctx, shd, spv_data, spv_len, "main")); - RET(ff_vk_init_compute_pipeline(vkctx, pl, shd)); - RET(ff_vk_exec_pipeline_register(vkctx, exec, pl)); + RET(ff_vk_shader_register_exec(vkctx, exec, shd)); fail: if (spv_opaque) @@ -654,14 +656,15 @@ static av_cold int init_filter(AVFilterContext *ctx) RET(ff_vk_exec_pool_init(vkctx, &s->qf, &s->e, 1, 0, 0, 0, NULL)); RET(ff_vk_init_sampler(vkctx, &s->sampler, 1, VK_FILTER_NEAREST)); - RET(init_weights_pipeline(vkctx, &s->e, &s->pl_weights, &s->shd_weights, s->sampler, + RET(init_weights_pipeline(vkctx, &s->e, &s->shd_weights, s->sampler, spv, s->vkctx.output_width, s->vkctx.output_height, s->opts.t, desc, planes, &s->pl_weights_rows)); - RET(init_denoise_pipeline(vkctx, &s->e, &s->pl_denoise, &s->shd_denoise, s->sampler, + RET(init_denoise_pipeline(vkctx, &s->e, &s->shd_denoise, s->sampler, spv, desc, planes)); - RET(ff_vk_set_descriptor_buffer(&s->vkctx, &s->pl_weights, NULL, 1, 0, 0, + RET(ff_vk_shader_update_desc_buffer(vkctx, &s->e.contexts[0], &s->shd_weights, + 1, 0, 0, &s->xyoffsets_buf, 0, s->xyoffsets_buf.size, VK_FORMAT_UNDEFINED)); @@ -697,11 +700,12 @@ static int denoise_pass(NLMeansVulkanContext *s, FFVkExecContext *exec, }; /* Denoise pass pipeline */ - ff_vk_exec_bind_pipeline(vkctx, exec, &s->pl_denoise); + ff_vk_exec_bind_shader(vkctx, exec, &s->shd_denoise); /* Push data */ - ff_vk_update_push_exec(vkctx, exec, &s->pl_denoise, VK_SHADER_STAGE_COMPUTE_BIT, - 0, sizeof(pd), &pd); + ff_vk_shader_update_push_const(vkctx, exec, &s->shd_denoise, + VK_SHADER_STAGE_COMPUTE_BIT, + 0, sizeof(pd), &pd); buf_bar[nb_buf_bar++] = (VkBufferMemoryBarrier2) { .sType = VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER_2, @@ -726,8 +730,8 @@ static int denoise_pass(NLMeansVulkanContext *s, FFVkExecContext *exec, /* End of denoise pass */ vk->CmdDispatch(exec->buf, - FFALIGN(vkctx->output_width, s->pl_denoise.wg_size[0])/s->pl_denoise.wg_size[0], - FFALIGN(vkctx->output_height, s->pl_denoise.wg_size[1])/s->pl_denoise.wg_size[1], + FFALIGN(vkctx->output_width, s->shd_denoise.lg_size[0])/s->shd_denoise.lg_size[0], + FFALIGN(vkctx->output_height, s->shd_denoise.lg_size[1])/s->shd_denoise.lg_size[1], av_pix_fmt_count_planes(s->vkctx.output_format)); return 0; @@ -780,15 +784,15 @@ static int nlmeans_vulkan_filter_frame(AVFilterLink *link, AVFrame *in) return AVERROR(EINVAL); /* Integral image */ - int_stride = s->pl_weights.wg_size[0]*s->pl_weights_rows*TYPE_SIZE; - int_size = s->pl_weights.wg_size[0]*s->pl_weights_rows*int_stride; + int_stride = s->shd_weights.lg_size[0]*s->pl_weights_rows*TYPE_SIZE; + int_size = s->shd_weights.lg_size[0]*s->pl_weights_rows*int_stride; /* Plane dimensions */ for (int i = 0; i < desc->nb_components; i++) { plane_widths[i] = !i || (i == 3) ? vkctx->output_width : AV_CEIL_RSHIFT(vkctx->output_width, desc->log2_chroma_w); plane_heights[i] = !i || (i == 3) ? vkctx->output_height : AV_CEIL_RSHIFT(vkctx->output_height, desc->log2_chroma_w); - plane_widths[i] = FFALIGN(plane_widths[i], s->pl_denoise.wg_size[0]); - plane_heights[i] = FFALIGN(plane_heights[i], s->pl_denoise.wg_size[1]); + plane_widths[i] = FFALIGN(plane_widths[i], s->shd_denoise.lg_size[0]); + plane_heights[i] = FFALIGN(plane_heights[i], s->shd_denoise.lg_size[1]); ws_stride[i] = plane_widths[i]; ws_size[i] = ws_stride[i] * plane_heights[i] * sizeof(float); @@ -933,35 +937,35 @@ static int nlmeans_vulkan_filter_frame(AVFilterLink *link, AVFrame *in) ws_vk->access = buf_bar[0].dstAccessMask; /* Update weights descriptors */ - ff_vk_update_descriptor_img_array(vkctx, &s->pl_weights, exec, in, in_views, 0, 0, - VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL, - s->sampler); + ff_vk_shader_update_img_array(vkctx, exec, &s->shd_weights, in, in_views, 0, 0, + VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL, + s->sampler); for (int i = 0; i < desc->nb_components; i++) { - RET(ff_vk_set_descriptor_buffer(&s->vkctx, &s->pl_weights, exec, 0, 1 + i*2 + 0, 0, - ws_vk, weights_offs[i], ws_size[i], - VK_FORMAT_UNDEFINED)); - RET(ff_vk_set_descriptor_buffer(&s->vkctx, &s->pl_weights, exec, 0, 1 + i*2 + 1, 0, - ws_vk, sums_offs[i], ws_size[i], - VK_FORMAT_UNDEFINED)); + RET(ff_vk_shader_update_desc_buffer(&s->vkctx, exec, &s->shd_weights, 0, 1 + i*2 + 0, 0, + ws_vk, weights_offs[i], ws_size[i], + VK_FORMAT_UNDEFINED)); + RET(ff_vk_shader_update_desc_buffer(&s->vkctx, exec, &s->shd_weights, 0, 1 + i*2 + 1, 0, + ws_vk, sums_offs[i], ws_size[i], + VK_FORMAT_UNDEFINED)); } /* Update denoise descriptors */ - ff_vk_update_descriptor_img_array(vkctx, &s->pl_denoise, exec, in, in_views, 0, 0, - VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL, - s->sampler); - ff_vk_update_descriptor_img_array(vkctx, &s->pl_denoise, exec, out, out_views, 0, 1, - VK_IMAGE_LAYOUT_GENERAL, s->sampler); + ff_vk_shader_update_img_array(vkctx, exec, &s->shd_denoise, in, in_views, 0, 0, + VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL, + s->sampler); + ff_vk_shader_update_img_array(vkctx, exec, &s->shd_denoise, out, out_views, 0, 1, + VK_IMAGE_LAYOUT_GENERAL, s->sampler); for (int i = 0; i < desc->nb_components; i++) { - RET(ff_vk_set_descriptor_buffer(&s->vkctx, &s->pl_denoise, exec, 1, i*2 + 0, 0, - ws_vk, weights_offs[i], ws_size[i], - VK_FORMAT_UNDEFINED)); - RET(ff_vk_set_descriptor_buffer(&s->vkctx, &s->pl_denoise, exec, 1, i*2 + 1, 0, - ws_vk, sums_offs[i], ws_size[i], - VK_FORMAT_UNDEFINED)); + RET(ff_vk_shader_update_desc_buffer(&s->vkctx, exec, &s->shd_denoise, 1, i*2 + 0, 0, + ws_vk, weights_offs[i], ws_size[i], + VK_FORMAT_UNDEFINED)); + RET(ff_vk_shader_update_desc_buffer(&s->vkctx, exec, &s->shd_denoise, 1, i*2 + 1, 0, + ws_vk, sums_offs[i], ws_size[i], + VK_FORMAT_UNDEFINED)); } /* Weights pipeline */ - ff_vk_exec_bind_pipeline(vkctx, exec, &s->pl_weights); + ff_vk_exec_bind_shader(vkctx, exec, &s->shd_weights); do { int wg_invoc; @@ -978,8 +982,9 @@ static int nlmeans_vulkan_filter_frame(AVFilterLink *link, AVFrame *in) }; /* Push data */ - ff_vk_update_push_exec(vkctx, exec, &s->pl_weights, VK_SHADER_STAGE_COMPUTE_BIT, - 0, sizeof(pd), &pd); + ff_vk_shader_update_push_const(vkctx, exec, &s->shd_weights, + VK_SHADER_STAGE_COMPUTE_BIT, + 0, sizeof(pd), &pd); if (offsets_dispatched) { nb_buf_bar = 0; @@ -1044,9 +1049,7 @@ static void nlmeans_vulkan_uninit(AVFilterContext *avctx) FFVulkanFunctions *vk = &vkctx->vkfn; ff_vk_exec_pool_free(vkctx, &s->e); - ff_vk_pipeline_free(vkctx, &s->pl_weights); ff_vk_shader_free(vkctx, &s->shd_weights); - ff_vk_pipeline_free(vkctx, &s->pl_denoise); ff_vk_shader_free(vkctx, &s->shd_denoise); av_buffer_pool_uninit(&s->integral_buf_pool); diff --git a/libavfilter/vf_overlay_vulkan.c b/libavfilter/vf_overlay_vulkan.c index 09444067af..f1ad27167e 100644 --- a/libavfilter/vf_overlay_vulkan.c +++ b/libavfilter/vf_overlay_vulkan.c @@ -32,10 +32,9 @@ typedef struct OverlayVulkanContext { FFFrameSync fs; int initialized; - FFVulkanPipeline pl; FFVkExecPool e; FFVkQueueFamilyCtx qf; - FFVkSPIRVShader shd; + FFVulkanShader shd; VkSampler sampler; /* Push constants / options */ @@ -92,7 +91,7 @@ static av_cold int init_filter(AVFilterContext *ctx) const int planes = av_pix_fmt_count_planes(s->vkctx.output_format); const int ialpha = av_pix_fmt_desc_get(s->vkctx.input_format)->flags & AV_PIX_FMT_FLAG_ALPHA; const AVPixFmtDescriptor *pix_desc = av_pix_fmt_desc_get(s->vkctx.output_format); - FFVkSPIRVShader *shd = &s->shd; + FFVulkanShader *shd = &s->shd; FFVkSPIRVCompiler *spv; FFVulkanDescriptorSetBinding *desc; @@ -105,10 +104,11 @@ static av_cold int init_filter(AVFilterContext *ctx) ff_vk_qf_init(vkctx, &s->qf, VK_QUEUE_COMPUTE_BIT); RET(ff_vk_exec_pool_init(vkctx, &s->qf, &s->e, s->qf.nb_queues*4, 0, 0, 0, NULL)); RET(ff_vk_init_sampler(vkctx, &s->sampler, 1, VK_FILTER_NEAREST)); - RET(ff_vk_shader_init(&s->pl, &s->shd, "overlay_compute", - VK_SHADER_STAGE_COMPUTE_BIT, 0)); - - ff_vk_shader_set_compute_sizes(&s->shd, 32, 32, 1); + RET(ff_vk_shader_init(vkctx, &s->shd, "overlay", + VK_SHADER_STAGE_COMPUTE_BIT, + NULL, 0, + 32, 32, 1, + 0)); GLSLC(0, layout(push_constant, std430) uniform pushConstants { ); GLSLC(1, ivec2 o_offset[3]; ); @@ -116,8 +116,8 @@ static av_cold int init_filter(AVFilterContext *ctx) GLSLC(0, }; ); GLSLC(0, ); - ff_vk_add_push_constant(&s->pl, 0, sizeof(s->opts), - VK_SHADER_STAGE_COMPUTE_BIT); + ff_vk_shader_add_push_const(&s->shd, 0, sizeof(s->opts), + VK_SHADER_STAGE_COMPUTE_BIT); desc = (FFVulkanDescriptorSetBinding []) { { @@ -147,7 +147,7 @@ static av_cold int init_filter(AVFilterContext *ctx) }, }; - RET(ff_vk_pipeline_descriptor_set_add(vkctx, &s->pl, shd, desc, 3, 0, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, &s->shd, desc, 3, 0, 0)); GLSLD( overlay_noalpha ); GLSLD( overlay_alpha ); @@ -165,10 +165,9 @@ static av_cold int init_filter(AVFilterContext *ctx) RET(spv->compile_shader(spv, ctx, shd, &spv_data, &spv_len, "main", &spv_opaque)); - RET(ff_vk_shader_create(vkctx, shd, spv_data, spv_len, "main")); + RET(ff_vk_shader_link(vkctx, shd, spv_data, spv_len, "main")); - RET(ff_vk_init_compute_pipeline(vkctx, &s->pl, shd)); - RET(ff_vk_exec_pipeline_register(vkctx, &s->e, &s->pl)); + RET(ff_vk_shader_register_exec(vkctx, &s->e, &s->shd)); s->opts.o_offset[0] = s->overlay_x; s->opts.o_offset[1] = s->overlay_y; @@ -233,7 +232,7 @@ static int overlay_vulkan_blend(FFFrameSync *fs) goto fail; } - RET(ff_vk_filter_process_Nin(&s->vkctx, &s->e, &s->pl, + RET(ff_vk_filter_process_Nin(&s->vkctx, &s->e, &s->shd, out, (AVFrame *[]){ input_main, input_overlay }, 2, s->sampler, &s->opts, sizeof(s->opts))); @@ -288,7 +287,6 @@ static void overlay_vulkan_uninit(AVFilterContext *avctx) FFVulkanFunctions *vk = &vkctx->vkfn; ff_vk_exec_pool_free(vkctx, &s->e); - ff_vk_pipeline_free(vkctx, &s->pl); ff_vk_shader_free(vkctx, &s->shd); if (s->sampler) diff --git a/libavfilter/vf_scale_vulkan.c b/libavfilter/vf_scale_vulkan.c index 6a32ebbd5e..e39bc62aa8 100644 --- a/libavfilter/vf_scale_vulkan.c +++ b/libavfilter/vf_scale_vulkan.c @@ -38,10 +38,9 @@ typedef struct ScaleVulkanContext { FFVulkanContext vkctx; int initialized; - FFVulkanPipeline pl; FFVkExecPool e; FFVkQueueFamilyCtx qf; - FFVkSPIRVShader shd; + FFVulkanShader shd; VkSampler sampler; /* Push constants / options */ @@ -118,7 +117,7 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) VkFilter sampler_mode; ScaleVulkanContext *s = ctx->priv; FFVulkanContext *vkctx = &s->vkctx; - FFVkSPIRVShader *shd = &s->shd; + FFVulkanShader *shd = &s->shd; FFVkSPIRVCompiler *spv; FFVulkanDescriptorSetBinding *desc; @@ -146,18 +145,19 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) ff_vk_qf_init(vkctx, &s->qf, VK_QUEUE_COMPUTE_BIT); RET(ff_vk_exec_pool_init(vkctx, &s->qf, &s->e, s->qf.nb_queues*4, 0, 0, 0, NULL)); RET(ff_vk_init_sampler(vkctx, &s->sampler, 0, sampler_mode)); - RET(ff_vk_shader_init(&s->pl, &s->shd, "scale_compute", - VK_SHADER_STAGE_COMPUTE_BIT, 0)); - - ff_vk_shader_set_compute_sizes(&s->shd, 32, 32, 1); + RET(ff_vk_shader_init(vkctx, &s->shd, "scale", + VK_SHADER_STAGE_COMPUTE_BIT, + NULL, 0, + 32, 32, 1, + 0)); GLSLC(0, layout(push_constant, std430) uniform pushConstants { ); GLSLC(1, mat4 yuv_matrix; ); GLSLC(0, }; ); GLSLC(0, ); - ff_vk_add_push_constant(&s->pl, 0, sizeof(s->opts), - VK_SHADER_STAGE_COMPUTE_BIT); + ff_vk_shader_add_push_const(&s->shd, 0, sizeof(s->opts), + VK_SHADER_STAGE_COMPUTE_BIT); desc = (FFVulkanDescriptorSetBinding []) { { @@ -179,7 +179,7 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) }, }; - RET(ff_vk_pipeline_descriptor_set_add(vkctx, &s->pl, shd, desc, 2, 0, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, &s->shd, desc, 2, 0, 0)); GLSLD( scale_bilinear ); @@ -249,10 +249,9 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) RET(spv->compile_shader(spv, ctx, shd, &spv_data, &spv_len, "main", &spv_opaque)); - RET(ff_vk_shader_create(vkctx, shd, spv_data, spv_len, "main")); + RET(ff_vk_shader_link(vkctx, shd, spv_data, spv_len, "main")); - RET(ff_vk_init_compute_pipeline(vkctx, &s->pl, shd)); - RET(ff_vk_exec_pipeline_register(vkctx, &s->e, &s->pl)); + RET(ff_vk_shader_register_exec(vkctx, &s->e, &s->shd)); s->initialized = 1; @@ -281,7 +280,7 @@ static int scale_vulkan_filter_frame(AVFilterLink *link, AVFrame *in) if (!s->initialized) RET(init_filter(ctx, in)); - RET(ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->pl, out, in, + RET(ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->shd, out, in, s->sampler, &s->opts, sizeof(s->opts))); err = av_frame_copy_props(out, in); @@ -353,7 +352,6 @@ static void scale_vulkan_uninit(AVFilterContext *avctx) FFVulkanFunctions *vk = &vkctx->vkfn; ff_vk_exec_pool_free(vkctx, &s->e); - ff_vk_pipeline_free(vkctx, &s->pl); ff_vk_shader_free(vkctx, &s->shd); if (s->sampler) diff --git a/libavfilter/vf_transpose_vulkan.c b/libavfilter/vf_transpose_vulkan.c index 72ea142e52..c3282339af 100644 --- a/libavfilter/vf_transpose_vulkan.c +++ b/libavfilter/vf_transpose_vulkan.c @@ -32,10 +32,9 @@ typedef struct TransposeVulkanContext { FFVulkanContext vkctx; int initialized; - FFVulkanPipeline pl; FFVkExecPool e; FFVkQueueFamilyCtx qf; - FFVkSPIRVShader shd; + FFVulkanShader shd; VkSampler sampler; int dir; @@ -52,7 +51,7 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) FFVulkanContext *vkctx = &s->vkctx; const int planes = av_pix_fmt_count_planes(s->vkctx.output_format); - FFVkSPIRVShader *shd = &s->shd; + FFVulkanShader *shd = &s->shd; FFVkSPIRVCompiler *spv; FFVulkanDescriptorSetBinding *desc; @@ -65,10 +64,11 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) ff_vk_qf_init(vkctx, &s->qf, VK_QUEUE_COMPUTE_BIT); RET(ff_vk_exec_pool_init(vkctx, &s->qf, &s->e, s->qf.nb_queues*4, 0, 0, 0, NULL)); RET(ff_vk_init_sampler(vkctx, &s->sampler, 1, VK_FILTER_LINEAR)); - RET(ff_vk_shader_init(&s->pl, &s->shd, "transpose_compute", - VK_SHADER_STAGE_COMPUTE_BIT, 0)); - - ff_vk_shader_set_compute_sizes(&s->shd, 32, 1, 1); + RET(ff_vk_shader_init(vkctx, &s->shd, "transpose", + VK_SHADER_STAGE_COMPUTE_BIT, + NULL, 0, + 32, 1, 1, + 0)); desc = (FFVulkanDescriptorSetBinding []) { { @@ -90,7 +90,7 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) }, }; - RET(ff_vk_pipeline_descriptor_set_add(vkctx, &s->pl, shd, desc, 2, 0, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, &s->shd, desc, 2, 0, 0)); GLSLC(0, void main() ); GLSLC(0, { ); @@ -115,10 +115,9 @@ static av_cold int init_filter(AVFilterContext *ctx, AVFrame *in) RET(spv->compile_shader(spv, ctx, shd, &spv_data, &spv_len, "main", &spv_opaque)); - RET(ff_vk_shader_create(vkctx, shd, spv_data, spv_len, "main")); + RET(ff_vk_shader_link(vkctx, shd, spv_data, spv_len, "main")); - RET(ff_vk_init_compute_pipeline(vkctx, &s->pl, shd)); - RET(ff_vk_exec_pipeline_register(vkctx, &s->e, &s->pl)); + RET(ff_vk_shader_register_exec(vkctx, &s->e, &s->shd)); s->initialized = 1; @@ -151,7 +150,7 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *in) if (!s->initialized) RET(init_filter(ctx, in)); - RET(ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->pl, out, in, + RET(ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->shd, out, in, s->sampler, NULL, 0)); RET(av_frame_copy_props(out, in)); @@ -180,7 +179,6 @@ static av_cold void transpose_vulkan_uninit(AVFilterContext *avctx) FFVulkanFunctions *vk = &vkctx->vkfn; ff_vk_exec_pool_free(vkctx, &s->e); - ff_vk_pipeline_free(vkctx, &s->pl); ff_vk_shader_free(vkctx, &s->shd); if (s->sampler) diff --git a/libavfilter/vf_xfade_vulkan.c b/libavfilter/vf_xfade_vulkan.c index 94acc5258f..c230f5d833 100644 --- a/libavfilter/vf_xfade_vulkan.c +++ b/libavfilter/vf_xfade_vulkan.c @@ -40,10 +40,9 @@ typedef struct XFadeVulkanContext { int64_t offset; int initialized; - FFVulkanPipeline pl; FFVkExecPool e; FFVkQueueFamilyCtx qf; - FFVkSPIRVShader shd; + FFVulkanShader shd; VkSampler sampler; // PTS when the fade should start (in IN_A timebase) @@ -326,7 +325,7 @@ static av_cold int init_vulkan(AVFilterContext *avctx) XFadeVulkanContext *s = avctx->priv; FFVulkanContext *vkctx = &s->vkctx; const int planes = av_pix_fmt_count_planes(s->vkctx.output_format); - FFVkSPIRVShader *shd = &s->shd; + FFVulkanShader *shd = &s->shd; FFVkSPIRVCompiler *spv; FFVulkanDescriptorSetBinding *desc; @@ -339,10 +338,11 @@ static av_cold int init_vulkan(AVFilterContext *avctx) ff_vk_qf_init(vkctx, &s->qf, VK_QUEUE_COMPUTE_BIT); RET(ff_vk_exec_pool_init(vkctx, &s->qf, &s->e, s->qf.nb_queues*4, 0, 0, 0, NULL)); RET(ff_vk_init_sampler(vkctx, &s->sampler, 1, VK_FILTER_NEAREST)); - RET(ff_vk_shader_init(&s->pl, &s->shd, "xfade_compute", - VK_SHADER_STAGE_COMPUTE_BIT, 0)); - - ff_vk_shader_set_compute_sizes(&s->shd, 32, 32, 1); + RET(ff_vk_shader_init(vkctx, &s->shd, "xfade", + VK_SHADER_STAGE_COMPUTE_BIT, + NULL, 0, + 32, 32, 1, + 0)); desc = (FFVulkanDescriptorSetBinding []) { { @@ -372,14 +372,14 @@ static av_cold int init_vulkan(AVFilterContext *avctx) }, }; - RET(ff_vk_pipeline_descriptor_set_add(vkctx, &s->pl, shd, desc, 3, 0, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, &s->shd, desc, 3, 0, 0)); GLSLC(0, layout(push_constant, std430) uniform pushConstants { ); GLSLC(1, float progress; ); GLSLC(0, }; ); - ff_vk_add_push_constant(&s->pl, 0, sizeof(XFadeParameters), - VK_SHADER_STAGE_COMPUTE_BIT); + ff_vk_shader_add_push_const(&s->shd, 0, sizeof(XFadeParameters), + VK_SHADER_STAGE_COMPUTE_BIT); // Add the right transition type function to the shader GLSLD(transitions_map[s->transition]); @@ -395,10 +395,9 @@ static av_cold int init_vulkan(AVFilterContext *avctx) RET(spv->compile_shader(spv, avctx, shd, &spv_data, &spv_len, "main", &spv_opaque)); - RET(ff_vk_shader_create(vkctx, shd, spv_data, spv_len, "main")); + RET(ff_vk_shader_link(vkctx, shd, spv_data, spv_len, "main")); - RET(ff_vk_init_compute_pipeline(vkctx, &s->pl, shd)); - RET(ff_vk_exec_pipeline_register(vkctx, &s->e, &s->pl)); + RET(ff_vk_shader_register_exec(vkctx, &s->e, &s->shd)); s->initialized = 1; @@ -441,7 +440,7 @@ static int xfade_frame(AVFilterContext *avctx, AVFrame *frame_a, AVFrame *frame_ progress = av_clipf((float)(s->pts - s->start_pts) / s->duration_pts, 0.f, 1.f); - RET(ff_vk_filter_process_Nin(&s->vkctx, &s->e, &s->pl, output, + RET(ff_vk_filter_process_Nin(&s->vkctx, &s->e, &s->shd, output, (AVFrame *[]){ frame_a, frame_b }, 2, s->sampler, &(XFadeParameters){ progress }, sizeof(XFadeParameters))); @@ -632,7 +631,6 @@ static av_cold void uninit(AVFilterContext *avctx) FFVulkanFunctions *vk = &vkctx->vkfn; ff_vk_exec_pool_free(vkctx, &s->e); - ff_vk_pipeline_free(vkctx, &s->pl); ff_vk_shader_free(vkctx, &s->shd); if (s->sampler) diff --git a/libavfilter/vsrc_testsrc_vulkan.c b/libavfilter/vsrc_testsrc_vulkan.c index 77fa9a0ba1..bfef38ce51 100644 --- a/libavfilter/vsrc_testsrc_vulkan.c +++ b/libavfilter/vsrc_testsrc_vulkan.c @@ -39,10 +39,9 @@ typedef struct TestSrcVulkanContext { FFVulkanContext vkctx; int initialized; - FFVulkanPipeline pl; FFVkExecPool e; FFVkQueueFamilyCtx qf; - FFVkSPIRVShader shd; + FFVulkanShader shd; /* Only used by color_vulkan */ uint8_t color_rgba[4]; @@ -72,7 +71,7 @@ static av_cold int init_filter(AVFilterContext *ctx, enum TestSrcVulkanMode mode TestSrcVulkanContext *s = ctx->priv; FFVulkanContext *vkctx = &s->vkctx; const int planes = av_pix_fmt_count_planes(s->vkctx.output_format); - FFVkSPIRVShader *shd = &s->shd; + FFVulkanShader *shd = &s->shd; FFVkSPIRVCompiler *spv; FFVulkanDescriptorSetBinding *desc_set; const AVPixFmtDescriptor *desc = av_pix_fmt_desc_get(s->vkctx.output_format); @@ -85,18 +84,19 @@ static av_cold int init_filter(AVFilterContext *ctx, enum TestSrcVulkanMode mode ff_vk_qf_init(vkctx, &s->qf, VK_QUEUE_COMPUTE_BIT); RET(ff_vk_exec_pool_init(vkctx, &s->qf, &s->e, s->qf.nb_queues*4, 0, 0, 0, NULL)); - RET(ff_vk_shader_init(&s->pl, &s->shd, "testsrc_compute", - VK_SHADER_STAGE_COMPUTE_BIT, 0)); - - ff_vk_shader_set_compute_sizes(&s->shd, 32, 32, 1); + RET(ff_vk_shader_init(vkctx, &s->shd, "scale", + VK_SHADER_STAGE_COMPUTE_BIT, + NULL, 0, + 32, 32, 1, + 0)); GLSLC(0, layout(push_constant, std430) uniform pushConstants { ); GLSLC(1, vec4 color_comp; ); GLSLC(0, }; ); GLSLC(0, ); - ff_vk_add_push_constant(&s->pl, 0, sizeof(s->opts), - VK_SHADER_STAGE_COMPUTE_BIT); + ff_vk_shader_add_push_const(&s->shd, 0, sizeof(s->opts), + VK_SHADER_STAGE_COMPUTE_BIT); desc_set = (FFVulkanDescriptorSetBinding []) { { @@ -110,7 +110,7 @@ static av_cold int init_filter(AVFilterContext *ctx, enum TestSrcVulkanMode mode }, }; - RET(ff_vk_pipeline_descriptor_set_add(vkctx, &s->pl, shd, desc_set, 1, 0, 0)); + RET(ff_vk_shader_add_descriptor_set(vkctx, &s->shd, desc_set, 1, 0, 0)); GLSLC(0, void main() ); GLSLC(0, { ); @@ -181,10 +181,9 @@ static av_cold int init_filter(AVFilterContext *ctx, enum TestSrcVulkanMode mode RET(spv->compile_shader(spv, ctx, shd, &spv_data, &spv_len, "main", &spv_opaque)); - RET(ff_vk_shader_create(vkctx, shd, spv_data, spv_len, "main")); + RET(ff_vk_shader_link(vkctx, shd, spv_data, spv_len, "main")); - RET(ff_vk_init_compute_pipeline(vkctx, &s->pl, shd)); - RET(ff_vk_exec_pipeline_register(vkctx, &s->e, &s->pl)); + RET(ff_vk_shader_register_exec(vkctx, &s->e, &s->shd)); s->initialized = 1; @@ -229,7 +228,7 @@ static int testsrc_vulkan_activate(AVFilterContext *ctx) if (!s->picref) return AVERROR(ENOMEM); - err = ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->pl, s->picref, NULL, + err = ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->shd, s->picref, NULL, VK_NULL_HANDLE, &s->opts, sizeof(s->opts)); if (err < 0) return err; @@ -248,7 +247,7 @@ static int testsrc_vulkan_activate(AVFilterContext *ctx) frame->pict_type = AV_PICTURE_TYPE_I; frame->sample_aspect_ratio = s->sar; if (!s->draw_once) { - err = ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->pl, frame, NULL, + err = ff_vk_filter_process_simple(&s->vkctx, &s->e, &s->shd, frame, NULL, VK_NULL_HANDLE, &s->opts, sizeof(s->opts)); if (err < 0) { av_frame_free(&frame); @@ -311,7 +310,6 @@ static void testsrc_vulkan_uninit(AVFilterContext *avctx) av_frame_free(&s->picref); ff_vk_exec_pool_free(vkctx, &s->e); - ff_vk_pipeline_free(vkctx, &s->pl); ff_vk_shader_free(vkctx, &s->shd); ff_vk_uninit(&s->vkctx); diff --git a/libavfilter/vulkan_filter.c b/libavfilter/vulkan_filter.c index 2c6ab72849..5cee4572e6 100644 --- a/libavfilter/vulkan_filter.c +++ b/libavfilter/vulkan_filter.c @@ -238,7 +238,7 @@ int ff_vk_filter_init(AVFilterContext *avctx) } int ff_vk_filter_process_simple(FFVulkanContext *vkctx, FFVkExecPool *e, - FFVulkanPipeline *pl, AVFrame *out_f, AVFrame *in_f, + FFVulkanShader *shd, AVFrame *out_f, AVFrame *in_f, VkSampler sampler, void *push_src, size_t push_size) { int err = 0; @@ -256,24 +256,24 @@ int ff_vk_filter_process_simple(FFVulkanContext *vkctx, FFVkExecPool *e, VK_PIPELINE_STAGE_2_ALL_COMMANDS_BIT, VK_PIPELINE_STAGE_2_COMPUTE_SHADER_BIT)); RET(ff_vk_create_imageviews(vkctx, exec, out_views, out_f)); - ff_vk_update_descriptor_img_array(vkctx, pl, exec, out_f, out_views, 0, !!in_f, - VK_IMAGE_LAYOUT_GENERAL, - VK_NULL_HANDLE); + ff_vk_shader_update_img_array(vkctx, exec, shd, out_f, out_views, 0, !!in_f, + VK_IMAGE_LAYOUT_GENERAL, + VK_NULL_HANDLE); if (in_f) { RET(ff_vk_exec_add_dep_frame(vkctx, exec, in_f, VK_PIPELINE_STAGE_2_ALL_COMMANDS_BIT, VK_PIPELINE_STAGE_2_COMPUTE_SHADER_BIT)); RET(ff_vk_create_imageviews(vkctx, exec, in_views, in_f)); - ff_vk_update_descriptor_img_array(vkctx, pl, exec, in_f, in_views, 0, 0, + ff_vk_shader_update_img_array(vkctx, exec, shd, in_f, in_views, 0, 0, VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL, sampler); } /* Bind pipeline, update push data */ - ff_vk_exec_bind_pipeline(vkctx, exec, pl); + ff_vk_exec_bind_shader(vkctx, exec, shd); if (push_src) - ff_vk_update_push_exec(vkctx, exec, pl, VK_SHADER_STAGE_COMPUTE_BIT, - 0, push_size, push_src); + ff_vk_shader_update_push_const(vkctx, exec, shd, VK_SHADER_STAGE_COMPUTE_BIT, + 0, push_size, push_src); /* Add data sync barriers */ ff_vk_frame_barrier(vkctx, exec, out_f, img_bar, &nb_img_bar, @@ -297,9 +297,9 @@ int ff_vk_filter_process_simple(FFVulkanContext *vkctx, FFVkExecPool *e, }); vk->CmdDispatch(exec->buf, - FFALIGN(vkctx->output_width, pl->wg_size[0])/pl->wg_size[0], - FFALIGN(vkctx->output_height, pl->wg_size[1])/pl->wg_size[1], - pl->wg_size[2]); + FFALIGN(vkctx->output_width, shd->lg_size[0])/shd->lg_size[0], + FFALIGN(vkctx->output_height, shd->lg_size[1])/shd->lg_size[1], + shd->lg_size[2]); return ff_vk_exec_submit(vkctx, exec); fail: @@ -308,7 +308,7 @@ fail: } int ff_vk_filter_process_2pass(FFVulkanContext *vkctx, FFVkExecPool *e, - FFVulkanPipeline *pls[2], + FFVulkanShader *shd_list[2], AVFrame *out, AVFrame *tmp, AVFrame *in, VkSampler sampler, void *push_src, size_t push_size) { @@ -364,30 +364,30 @@ int ff_vk_filter_process_2pass(FFVulkanContext *vkctx, FFVkExecPool *e, }); for (int i = 0; i < 2; i++) { - FFVulkanPipeline *pl = pls[i]; + FFVulkanShader *shd = shd_list[i]; AVFrame *src_f = !i ? in : tmp; AVFrame *dst_f = !i ? tmp : out; VkImageView *src_views = !i ? in_views : tmp_views; VkImageView *dst_views = !i ? tmp_views : out_views; - ff_vk_update_descriptor_img_array(vkctx, pl, exec, src_f, src_views, 0, 0, - !i ? VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL : - VK_IMAGE_LAYOUT_GENERAL, - sampler); - ff_vk_update_descriptor_img_array(vkctx, pl, exec, dst_f, dst_views, 0, 1, - VK_IMAGE_LAYOUT_GENERAL, - VK_NULL_HANDLE); + ff_vk_shader_update_img_array(vkctx, exec, shd, src_f, src_views, 0, 0, + !i ? VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL : + VK_IMAGE_LAYOUT_GENERAL, + sampler); + ff_vk_shader_update_img_array(vkctx, exec, shd, dst_f, dst_views, 0, 1, + VK_IMAGE_LAYOUT_GENERAL, + VK_NULL_HANDLE); /* Bind pipeline, update push data */ - ff_vk_exec_bind_pipeline(vkctx, exec, pl); + ff_vk_exec_bind_shader(vkctx, exec, shd); if (push_src) - ff_vk_update_push_exec(vkctx, exec, pl, VK_SHADER_STAGE_COMPUTE_BIT, - 0, push_size, push_src); + ff_vk_shader_update_push_const(vkctx, exec, shd, VK_SHADER_STAGE_COMPUTE_BIT, + 0, push_size, push_src); vk->CmdDispatch(exec->buf, - FFALIGN(vkctx->output_width, pl->wg_size[0])/pl->wg_size[0], - FFALIGN(vkctx->output_height, pl->wg_size[1])/pl->wg_size[1], - pl->wg_size[2]); + FFALIGN(vkctx->output_width, shd->lg_size[0])/shd->lg_size[0], + FFALIGN(vkctx->output_height, shd->lg_size[1])/shd->lg_size[1], + shd->lg_size[2]); } return ff_vk_exec_submit(vkctx, exec); @@ -397,7 +397,7 @@ fail: } int ff_vk_filter_process_Nin(FFVulkanContext *vkctx, FFVkExecPool *e, - FFVulkanPipeline *pl, + FFVulkanShader *shd, AVFrame *out, AVFrame *in[], int nb_in, VkSampler sampler, void *push_src, size_t push_size) { @@ -425,19 +425,19 @@ int ff_vk_filter_process_Nin(FFVulkanContext *vkctx, FFVkExecPool *e, } /* Update descriptor sets */ - ff_vk_update_descriptor_img_array(vkctx, pl, exec, out, out_views, 0, nb_in, - VK_IMAGE_LAYOUT_GENERAL, - VK_NULL_HANDLE); + ff_vk_shader_update_img_array(vkctx, exec, shd, out, out_views, 0, nb_in, + VK_IMAGE_LAYOUT_GENERAL, + VK_NULL_HANDLE); for (int i = 0; i < nb_in; i++) - ff_vk_update_descriptor_img_array(vkctx, pl, exec, in[i], in_views[i], 0, i, - VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL, - sampler); + ff_vk_shader_update_img_array(vkctx, exec, shd, in[i], in_views[i], 0, i, + VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL, + sampler); /* Bind pipeline, update push data */ - ff_vk_exec_bind_pipeline(vkctx, exec, pl); + ff_vk_exec_bind_shader(vkctx, exec, shd); if (push_src) - ff_vk_update_push_exec(vkctx, exec, pl, VK_SHADER_STAGE_COMPUTE_BIT, - 0, push_size, push_src); + ff_vk_shader_update_push_const(vkctx, exec, shd, VK_SHADER_STAGE_COMPUTE_BIT, + 0, push_size, push_src); /* Add data sync barriers */ ff_vk_frame_barrier(vkctx, exec, out, img_bar, &nb_img_bar, @@ -461,9 +461,9 @@ int ff_vk_filter_process_Nin(FFVulkanContext *vkctx, FFVkExecPool *e, }); vk->CmdDispatch(exec->buf, - FFALIGN(vkctx->output_width, pl->wg_size[0])/pl->wg_size[0], - FFALIGN(vkctx->output_height, pl->wg_size[1])/pl->wg_size[1], - pl->wg_size[2]); + FFALIGN(vkctx->output_width, shd->lg_size[0])/shd->lg_size[0], + FFALIGN(vkctx->output_height, shd->lg_size[1])/shd->lg_size[1], + shd->lg_size[2]); return ff_vk_exec_submit(vkctx, exec); fail: diff --git a/libavfilter/vulkan_filter.h b/libavfilter/vulkan_filter.h index d2c14601d9..9f1297e0d2 100644 --- a/libavfilter/vulkan_filter.h +++ b/libavfilter/vulkan_filter.h @@ -43,14 +43,14 @@ int ff_vk_filter_init_context(AVFilterContext *avctx, FFVulkanContext *s, * Submit a compute shader with a zero/one input and single out for execution. */ int ff_vk_filter_process_simple(FFVulkanContext *vkctx, FFVkExecPool *e, - FFVulkanPipeline *pl, AVFrame *out_f, AVFrame *in_f, + FFVulkanShader *shd, AVFrame *out_f, AVFrame *in_f, VkSampler sampler, void *push_src, size_t push_size); /** * Submit a compute shader with a single in and single out with 2 stages. */ int ff_vk_filter_process_2pass(FFVulkanContext *vkctx, FFVkExecPool *e, - FFVulkanPipeline *pls[2], + FFVulkanShader *shd_list[2], AVFrame *out, AVFrame *tmp, AVFrame *in, VkSampler sampler, void *push_src, size_t push_size); @@ -58,7 +58,7 @@ int ff_vk_filter_process_2pass(FFVulkanContext *vkctx, FFVkExecPool *e, * Up to 16 inputs, one output */ int ff_vk_filter_process_Nin(FFVulkanContext *vkctx, FFVkExecPool *e, - FFVulkanPipeline *pl, + FFVulkanShader *shd, AVFrame *out, AVFrame *in[], int nb_in, VkSampler sampler, void *push_src, size_t push_size); diff --git a/libavfilter/vulkan_glslang.c b/libavfilter/vulkan_glslang.c index 845a530ee0..3c1b0a8fe6 100644 --- a/libavfilter/vulkan_glslang.c +++ b/libavfilter/vulkan_glslang.c @@ -137,7 +137,7 @@ static const glslang_resource_t glslc_resource_limits = { }; static int glslc_shader_compile(FFVkSPIRVCompiler *ctx, void *avctx, - FFVkSPIRVShader *shd, uint8_t **data, + FFVulkanShader *shd, uint8_t **data, size_t *size, const char *entrypoint, void **opaque) { @@ -153,7 +153,7 @@ static int glslc_shader_compile(FFVkSPIRVCompiler *ctx, void *avctx, const glslang_input_t glslc_input = { .language = GLSLANG_SOURCE_GLSL, - .stage = glslc_stage[shd->shader.stage], + .stage = glslc_stage[shd->stage], .client = GLSLANG_CLIENT_VULKAN, /* GLSLANG_TARGET_VULKAN_1_2 before 11.6 resulted in targeting 1.0 */ #if (((GLSLANG_VERSION_MAJOR) > 11) || ((GLSLANG_VERSION_MAJOR) == 11 && \ diff --git a/libavfilter/vulkan_shaderc.c b/libavfilter/vulkan_shaderc.c index 9e8a3d17ac..d2bd60e7ef 100644 --- a/libavfilter/vulkan_shaderc.c +++ b/libavfilter/vulkan_shaderc.c @@ -22,7 +22,7 @@ #include "vulkan_spirv.h" static int shdc_shader_compile(FFVkSPIRVCompiler *ctx, void *avctx, - FFVkSPIRVShader *shd, uint8_t **data, + FFVulkanShader *shd, uint8_t **data, size_t *size, const char *entrypoint, void **opaque) { @@ -57,7 +57,7 @@ static int shdc_shader_compile(FFVkSPIRVCompiler *ctx, void *avctx, res = shaderc_compile_into_spv((shaderc_compiler_t)ctx->priv, shd->src.str, strlen(shd->src.str), - shdc_kind[shd->shader.stage], + shdc_kind[shd->stage], shd->name, entrypoint, opts); shaderc_compile_options_release(opts); diff --git a/libavfilter/vulkan_spirv.h b/libavfilter/vulkan_spirv.h index 5638cd9696..c46c9e52da 100644 --- a/libavfilter/vulkan_spirv.h +++ b/libavfilter/vulkan_spirv.h @@ -27,7 +27,7 @@ typedef struct FFVkSPIRVCompiler { void *priv; int (*compile_shader)(struct FFVkSPIRVCompiler *ctx, void *avctx, - struct FFVkSPIRVShader *shd, uint8_t **data, + struct FFVulkanShader *shd, uint8_t **data, size_t *size, const char *entrypoint, void **opaque); void (*free_shader)(struct FFVkSPIRVCompiler *ctx, void **opaque); void (*uninit)(struct FFVkSPIRVCompiler **ctx); diff --git a/libavutil/vulkan.c b/libavutil/vulkan.c index 046ac5d67e..9ea9e478df 100644 --- a/libavutil/vulkan.c +++ b/libavutil/vulkan.c @@ -1191,17 +1191,18 @@ int ff_vk_get_pooled_buffer(FFVulkanContext *ctx, AVBufferPool **buf_pool, return 0; } -int ff_vk_add_push_constant(FFVulkanPipeline *pl, int offset, int size, - VkShaderStageFlagBits stage) +int ff_vk_shader_add_push_const(FFVulkanShader *shd, int offset, int size, + VkShaderStageFlagBits stage) { VkPushConstantRange *pc; - pl->push_consts = av_realloc_array(pl->push_consts, sizeof(*pl->push_consts), - pl->push_consts_num + 1); - if (!pl->push_consts) + shd->push_consts = av_realloc_array(shd->push_consts, + sizeof(*shd->push_consts), + shd->push_consts_num + 1); + if (!shd->push_consts) return AVERROR(ENOMEM); - pc = &pl->push_consts[pl->push_consts_num++]; + pc = &shd->push_consts[shd->push_consts_num++]; memset(pc, 0, sizeof(*pc)); pc->stageFlags = stage; @@ -1397,44 +1398,79 @@ void ff_vk_frame_barrier(FFVulkanContext *s, FFVkExecContext *e, ff_vk_exec_update_frame(s, e, pic, &bar[*nb_bar - nb_images], NULL); } -int ff_vk_shader_init(FFVulkanPipeline *pl, FFVkSPIRVShader *shd, const char *name, - VkShaderStageFlags stage, uint32_t required_subgroup_size) +int ff_vk_shader_init(FFVulkanContext *s, FFVulkanShader *shd, const char *name, + VkPipelineStageFlags stage, + const char *extensions[], int nb_extensions, + int lg_x, int lg_y, int lg_z, + uint32_t required_subgroup_size) { av_bprint_init(&shd->src, 0, AV_BPRINT_SIZE_UNLIMITED); - shd->shader.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO; - shd->shader.stage = stage; + shd->name = name; + shd->stage = stage; + shd->lg_size[0] = lg_x; + shd->lg_size[1] = lg_y; + shd->lg_size[2] = lg_z; + + switch (shd->stage) { + case VK_SHADER_STAGE_ANY_HIT_BIT_KHR: + case VK_SHADER_STAGE_CALLABLE_BIT_KHR: + case VK_SHADER_STAGE_CLOSEST_HIT_BIT_KHR: + case VK_SHADER_STAGE_INTERSECTION_BIT_KHR: + case VK_SHADER_STAGE_MISS_BIT_KHR: + case VK_SHADER_STAGE_RAYGEN_BIT_KHR: + shd->bind_point = VK_PIPELINE_BIND_POINT_RAY_TRACING_KHR; + break; + case VK_SHADER_STAGE_COMPUTE_BIT: + shd->bind_point = VK_PIPELINE_BIND_POINT_COMPUTE; + break; + default: + shd->bind_point = VK_PIPELINE_BIND_POINT_GRAPHICS; + break; + }; if (required_subgroup_size) { - shd->shader.flags |= VK_PIPELINE_SHADER_STAGE_CREATE_REQUIRE_FULL_SUBGROUPS_BIT; - shd->shader.pNext = &shd->subgroup_info; shd->subgroup_info.sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_REQUIRED_SUBGROUP_SIZE_CREATE_INFO; shd->subgroup_info.requiredSubgroupSize = required_subgroup_size; } - shd->name = name; - + av_bprintf(&shd->src, "/* %s shader: %s */\n", + (stage == VK_SHADER_STAGE_TASK_BIT_EXT || + stage == VK_SHADER_STAGE_MESH_BIT_EXT) ? + "Mesh" : + (shd->bind_point == VK_PIPELINE_BIND_POINT_RAY_TRACING_KHR) ? + "Raytrace" : + (shd->bind_point == VK_PIPELINE_BIND_POINT_COMPUTE) ? + "Compute" : "Graphics", + name); GLSLF(0, #version %i ,460); + GLSLC(0, ); + + /* Common utilities */ GLSLC(0, #define IS_WITHIN(v1, v2) ((v1.x < v2.x) && (v1.y < v2.y)) ); GLSLC(0, ); - GLSLC(0, #extension GL_EXT_buffer_reference : require ); - GLSLC(0, #extension GL_EXT_buffer_reference2 : require ); - return 0; -} + if (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) { + GLSLC(0, #extension GL_EXT_buffer_reference : require ); + GLSLC(0, #extension GL_EXT_buffer_reference2 : require ); + } -void ff_vk_shader_set_compute_sizes(FFVkSPIRVShader *shd, int x, int y, int z) -{ - shd->local_size[0] = x; - shd->local_size[1] = y; - shd->local_size[2] = z; + if (stage == VK_SHADER_STAGE_TASK_BIT_EXT || + stage == VK_SHADER_STAGE_MESH_BIT_EXT) + GLSLC(0, #extension GL_EXT_mesh_shader : require ); - av_bprintf(&shd->src, "layout (local_size_x = %i, " - "local_size_y = %i, local_size_z = %i) in;\n\n", - shd->local_size[0], shd->local_size[1], shd->local_size[2]); + for (int i = 0; i < nb_extensions; i++) + GLSLF(0, #extension %s : %s ,extensions[i], "require"); + GLSLC(0, ); + + GLSLF(0, layout (local_size_x = %i, local_size_y = %i, local_size_z = %i) in; + , shd->lg_size[0], shd->lg_size[1], shd->lg_size[2]); + GLSLC(0, ); + + return 0; } -void ff_vk_shader_print(void *ctx, FFVkSPIRVShader *shd, int prio) +void ff_vk_shader_print(void *ctx, FFVulkanShader *shd, int prio) { int line = 0; const char *p = shd->src.str; @@ -1456,37 +1492,86 @@ void ff_vk_shader_print(void *ctx, FFVkSPIRVShader *shd, int prio) av_bprint_finalize(&buf, NULL); } -void ff_vk_shader_free(FFVulkanContext *s, FFVkSPIRVShader *shd) +static int init_pipeline_layout(FFVulkanContext *s, FFVulkanShader *shd) { + VkResult ret; FFVulkanFunctions *vk = &s->vkfn; - av_bprint_finalize(&shd->src, NULL); + VkPipelineLayoutCreateInfo pipeline_layout_info; - if (shd->shader.module) - vk->DestroyShaderModule(s->hwctx->act_dev, shd->shader.module, s->hwctx->alloc); + /* Finally create the pipeline layout */ + pipeline_layout_info = (VkPipelineLayoutCreateInfo) { + .sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO, + .pSetLayouts = shd->desc_layout, + .setLayoutCount = shd->nb_descriptor_sets, + .pushConstantRangeCount = shd->push_consts_num, + .pPushConstantRanges = shd->push_consts, + }; + + ret = vk->CreatePipelineLayout(s->hwctx->act_dev, &pipeline_layout_info, + s->hwctx->alloc, &shd->pipeline_layout); + if (ret != VK_SUCCESS) { + av_log(s, AV_LOG_ERROR, "Unable to init pipeline layout: %s\n", + ff_vk_ret2str(ret)); + return AVERROR_EXTERNAL; + } + + return 0; } -int ff_vk_shader_create(FFVulkanContext *s, FFVkSPIRVShader *shd, - uint8_t *spirv, size_t spirv_size, const char *entrypoint) +static int create_shader_module(FFVulkanContext *s, FFVulkanShader *shd, + VkShaderModule *mod, + uint8_t *spirv, size_t spirv_len) { VkResult ret; FFVulkanFunctions *vk = &s->vkfn; - VkShaderModuleCreateInfo shader_create; - shd->shader.pName = entrypoint; + VkShaderModuleCreateInfo shader_module_info = { + .sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO, + .pNext = NULL, + .flags = 0x0, + .pCode = (void *)spirv, + .codeSize = spirv_len, + }; - av_log(s, AV_LOG_VERBOSE, "Shader %s compiled! Size: %zu bytes\n", - shd->name, spirv_size); + ret = vk->CreateShaderModule(s->hwctx->act_dev, &shader_module_info, + s->hwctx->alloc, mod); + if (ret != VK_SUCCESS) { + av_log(s, AV_LOG_VERBOSE, "Error creating shader module: %s\n", + ff_vk_ret2str(ret)); + return AVERROR_EXTERNAL; + } - shader_create.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO; - shader_create.pNext = NULL; - shader_create.codeSize = spirv_size; - shader_create.flags = 0; - shader_create.pCode = (void *)spirv; + return 0; +} - ret = vk->CreateShaderModule(s->hwctx->act_dev, &shader_create, NULL, - &shd->shader.module); +static int init_compute_pipeline(FFVulkanContext *s, FFVulkanShader *shd, + VkShaderModule mod, const char *entrypoint) +{ + VkResult ret; + FFVulkanFunctions *vk = &s->vkfn; + + VkComputePipelineCreateInfo pipeline_create_info = { + .sType = VK_STRUCTURE_TYPE_COMPUTE_PIPELINE_CREATE_INFO, + .flags = (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) ? + VK_PIPELINE_CREATE_DESCRIPTOR_BUFFER_BIT_EXT : 0x0, + .layout = shd->pipeline_layout, + .stage = (VkPipelineShaderStageCreateInfo) { + .sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO, + .pNext = shd->subgroup_info.requiredSubgroupSize ? + &shd->subgroup_info : NULL, + .pName = entrypoint, + .flags = shd->subgroup_info.requiredSubgroupSize ? + VK_PIPELINE_SHADER_STAGE_CREATE_REQUIRE_FULL_SUBGROUPS_BIT : 0x0, + .stage = shd->stage, + .module = mod, + }, + }; + + ret = vk->CreateComputePipelines(s->hwctx->act_dev, VK_NULL_HANDLE, 1, + &pipeline_create_info, + s->hwctx->alloc, &shd->pipeline); if (ret != VK_SUCCESS) { - av_log(s, AV_LOG_VERBOSE, "Error creating shader module: %s\n", + av_log(s, AV_LOG_ERROR, "Unable to init compute pipeline: %s\n", ff_vk_ret2str(ret)); return AVERROR_EXTERNAL; } @@ -1494,6 +1579,110 @@ int ff_vk_shader_create(FFVulkanContext *s, FFVkSPIRVShader *shd, return 0; } +static int init_descriptors(FFVulkanContext *s, FFVulkanShader *shd) +{ + VkResult ret; + FFVulkanFunctions *vk = &s->vkfn; + + shd->desc_layout = av_malloc_array(shd->nb_descriptor_sets, + sizeof(*shd->desc_layout)); + if (!shd->desc_layout) + return AVERROR(ENOMEM); + + if (!(s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER)) { + int has_singular = 0; + for (int i = 0; i < shd->nb_descriptor_sets; i++) { + if (shd->desc_set[i].singular) { + has_singular = 1; + break; + } + } + shd->use_push = (s->extensions & FF_VK_EXT_PUSH_DESCRIPTOR) && + (shd->nb_descriptor_sets == 1) && + !has_singular; + } + + for (int i = 0; i < shd->nb_descriptor_sets; i++) { + FFVulkanDescriptorSet *set = &shd->desc_set[i]; + VkDescriptorSetLayoutCreateInfo desc_layout_create = { + .sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO, + .bindingCount = set->nb_bindings, + .pBindings = set->binding, + .flags = (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) ? + VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT : + (shd->use_push) ? + VK_DESCRIPTOR_SET_LAYOUT_CREATE_PUSH_DESCRIPTOR_BIT_KHR : + 0x0, + }; + + ret = vk->CreateDescriptorSetLayout(s->hwctx->act_dev, + &desc_layout_create, + s->hwctx->alloc, + &shd->desc_layout[i]); + if (ret != VK_SUCCESS) { + av_log(s, AV_LOG_ERROR, "Unable to create descriptor set layout: %s", + ff_vk_ret2str(ret)); + return AVERROR_EXTERNAL; + } + + if (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) { + vk->GetDescriptorSetLayoutSizeEXT(s->hwctx->act_dev, shd->desc_layout[i], + &set->layout_size); + + set->aligned_size = FFALIGN(set->layout_size, + s->desc_buf_props.descriptorBufferOffsetAlignment); + + for (int j = 0; j < set->nb_bindings; j++) + vk->GetDescriptorSetLayoutBindingOffsetEXT(s->hwctx->act_dev, + shd->desc_layout[i], + j, + &set->binding_offset[j]); + } + } + + return 0; +} + +int ff_vk_shader_link(FFVulkanContext *s, FFVulkanShader *shd, + uint8_t *spirv, size_t spirv_len, + const char *entrypoint) +{ + int err; + FFVulkanFunctions *vk = &s->vkfn; + + err = init_descriptors(s, shd); + if (err < 0) + return err; + + err = init_pipeline_layout(s, shd); + if (err < 0) + return err; + + { + VkShaderModule mod; + err = create_shader_module(s, shd, &mod, spirv, spirv_len); + if (err < 0) + return err; + + switch (shd->bind_point) { + case VK_PIPELINE_BIND_POINT_COMPUTE: + err = init_compute_pipeline(s, shd, mod, entrypoint); + break; + default: + av_log(s, AV_LOG_ERROR, "Unsupported shader type: %i\n", + shd->bind_point); + err = AVERROR(EINVAL); + break; + }; + + vk->DestroyShaderModule(s->hwctx->act_dev, mod, s->hwctx->alloc); + if (err < 0) + return err; + } + + return 0; +} + static const struct descriptor_props { size_t struct_size; /* Size of the opaque which updates the descriptor */ const char *type; @@ -1515,10 +1704,9 @@ static const struct descriptor_props { [VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER] = { sizeof(VkBufferView), "imageBuffer", 1, 0, 0, 0, }, }; -int ff_vk_pipeline_descriptor_set_add(FFVulkanContext *s, FFVulkanPipeline *pl, - FFVkSPIRVShader *shd, - FFVulkanDescriptorSetBinding *desc, int nb, - int singular, int print_to_shader_only) +int ff_vk_shader_add_descriptor_set(FFVulkanContext *s, FFVulkanShader *shd, + FFVulkanDescriptorSetBinding *desc, int nb, + int singular, int print_to_shader_only) { int has_sampler = 0; FFVulkanDescriptorSet *set; @@ -1527,13 +1715,14 @@ int ff_vk_pipeline_descriptor_set_add(FFVulkanContext *s, FFVulkanPipeline *pl, goto print; /* Actual layout allocated for the pipeline */ - set = av_realloc_array(pl->desc_set, sizeof(*pl->desc_set), - pl->nb_descriptor_sets + 1); + set = av_realloc_array(shd->desc_set, + sizeof(*shd->desc_set), + shd->nb_descriptor_sets + 1); if (!set) return AVERROR(ENOMEM); - pl->desc_set = set; + shd->desc_set = set; - set = &set[pl->nb_descriptor_sets]; + set = &set[shd->nb_descriptor_sets]; memset(set, 0, sizeof(*set)); set->binding = av_calloc(nb, sizeof(*set->binding)); @@ -1567,34 +1756,34 @@ int ff_vk_pipeline_descriptor_set_add(FFVulkanContext *s, FFVulkanPipeline *pl, for (int i = 0; i < nb; i++) { int j; VkDescriptorPoolSize *desc_pool_size; - for (j = 0; j < pl->nb_desc_pool_size; j++) - if (pl->desc_pool_size[j].type == desc[i].type) + for (j = 0; j < shd->nb_desc_pool_size; j++) + if (shd->desc_pool_size[j].type == desc[i].type) break; - if (j >= pl->nb_desc_pool_size) { - desc_pool_size = av_realloc_array(pl->desc_pool_size, + if (j >= shd->nb_desc_pool_size) { + desc_pool_size = av_realloc_array(shd->desc_pool_size, sizeof(*desc_pool_size), - pl->nb_desc_pool_size + 1); + shd->nb_desc_pool_size + 1); if (!desc_pool_size) return AVERROR(ENOMEM); - pl->desc_pool_size = desc_pool_size; - pl->nb_desc_pool_size++; + shd->desc_pool_size = desc_pool_size; + shd->nb_desc_pool_size++; memset(&desc_pool_size[j], 0, sizeof(VkDescriptorPoolSize)); } - pl->desc_pool_size[j].type = desc[i].type; - pl->desc_pool_size[j].descriptorCount += FFMAX(desc[i].elems, 1); + shd->desc_pool_size[j].type = desc[i].type; + shd->desc_pool_size[j].descriptorCount += FFMAX(desc[i].elems, 1); } } set->singular = singular; set->nb_bindings = nb; - pl->nb_descriptor_sets++; + shd->nb_descriptor_sets++; print: /* Write shader info */ for (int i = 0; i < nb; i++) { const struct descriptor_props *prop = &descriptor_props[desc[i].type]; - GLSLA("layout (set = %i, binding = %i", pl->nb_descriptor_sets - 1, i); + GLSLA("layout (set = %i, binding = %i", shd->nb_descriptor_sets - 1, i); if (desc[i].mem_layout) GLSLA(", %s", desc[i].mem_layout); @@ -1627,26 +1816,26 @@ print: return 0; } -int ff_vk_exec_pipeline_register(FFVulkanContext *s, FFVkExecPool *pool, - FFVulkanPipeline *pl) +int ff_vk_shader_register_exec(FFVulkanContext *s, FFVkExecPool *pool, + FFVulkanShader *shd) { int err; - if (!pl->nb_descriptor_sets) + if (!shd->nb_descriptor_sets) return 0; if (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) { - pl->desc_bind = av_calloc(pl->nb_descriptor_sets, sizeof(*pl->desc_bind)); - if (!pl->desc_bind) + shd->desc_bind = av_calloc(shd->nb_descriptor_sets, sizeof(*shd->desc_bind)); + if (!shd->desc_bind) return AVERROR(ENOMEM); - pl->bound_buffer_indices = av_calloc(pl->nb_descriptor_sets, - sizeof(*pl->bound_buffer_indices)); - if (!pl->bound_buffer_indices) + shd->bound_buffer_indices = av_calloc(shd->nb_descriptor_sets, + sizeof(*shd->bound_buffer_indices)); + if (!shd->bound_buffer_indices) return AVERROR(ENOMEM); - for (int i = 0; i < pl->nb_descriptor_sets; i++) { - FFVulkanDescriptorSet *set = &pl->desc_set[i]; + for (int i = 0; i < shd->nb_descriptor_sets; i++) { + FFVulkanDescriptorSet *set = &shd->desc_set[i]; int nb = set->singular ? 1 : pool->pool_size; err = ff_vk_create_buf(s, &set->buf, set->aligned_size*nb, @@ -1661,34 +1850,34 @@ int ff_vk_exec_pipeline_register(FFVulkanContext *s, FFVkExecPool *pool, if (err < 0) return err; - pl->desc_bind[i] = (VkDescriptorBufferBindingInfoEXT) { + shd->desc_bind[i] = (VkDescriptorBufferBindingInfoEXT) { .sType = VK_STRUCTURE_TYPE_DESCRIPTOR_BUFFER_BINDING_INFO_EXT, .usage = set->usage, .address = set->buf.address, }; - pl->bound_buffer_indices[i] = i; + shd->bound_buffer_indices[i] = i; } - } else if (!pl->use_push) { + } else if (!shd->use_push) { VkResult ret; FFVulkanFunctions *vk = &s->vkfn; VkDescriptorSetLayout *tmp_layouts; VkDescriptorSetAllocateInfo set_alloc_info; VkDescriptorPoolCreateInfo pool_create_info; - for (int i = 0; i < pl->nb_desc_pool_size; i++) - pl->desc_pool_size[i].descriptorCount *= pool->pool_size; + for (int i = 0; i < shd->nb_desc_pool_size; i++) + shd->desc_pool_size[i].descriptorCount *= pool->pool_size; pool_create_info = (VkDescriptorPoolCreateInfo) { .sType = VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO, .flags = 0, - .pPoolSizes = pl->desc_pool_size, - .poolSizeCount = pl->nb_desc_pool_size, - .maxSets = pl->nb_descriptor_sets*pool->pool_size, + .pPoolSizes = shd->desc_pool_size, + .poolSizeCount = shd->nb_desc_pool_size, + .maxSets = shd->nb_descriptor_sets*pool->pool_size, }; ret = vk->CreateDescriptorPool(s->hwctx->act_dev, &pool_create_info, - s->hwctx->alloc, &pl->desc_pool); + s->hwctx->alloc, &shd->desc_pool); if (ret != VK_SUCCESS) { av_log(s, AV_LOG_ERROR, "Unable to create descriptor pool: %s\n", ff_vk_ret2str(ret)); @@ -1701,33 +1890,33 @@ int ff_vk_exec_pipeline_register(FFVulkanContext *s, FFVkExecPool *pool, /* Colate each execution context's descriptor set layouts */ for (int i = 0; i < pool->pool_size; i++) - for (int j = 0; j < pl->nb_descriptor_sets; j++) - tmp_layouts[i*pl->nb_descriptor_sets + j] = pl->desc_layout[j]; + for (int j = 0; j < shd->nb_descriptor_sets; j++) + tmp_layouts[i*shd->nb_descriptor_sets + j] = shd->desc_layout[j]; set_alloc_info = (VkDescriptorSetAllocateInfo) { .sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO, - .descriptorPool = pl->desc_pool, + .descriptorPool = shd->desc_pool, .pSetLayouts = tmp_layouts, .descriptorSetCount = pool_create_info.maxSets, }; - pl->desc_sets = av_malloc_array(pool_create_info.maxSets, + shd->desc_sets = av_malloc_array(pool_create_info.maxSets, sizeof(*tmp_layouts)); - if (!pl->desc_sets) { + if (!shd->desc_sets) { av_free(tmp_layouts); return AVERROR(ENOMEM); } ret = vk->AllocateDescriptorSets(s->hwctx->act_dev, &set_alloc_info, - pl->desc_sets); + shd->desc_sets); av_free(tmp_layouts); if (ret != VK_SUCCESS) { av_log(s, AV_LOG_ERROR, "Unable to allocate descriptor set: %s\n", ff_vk_ret2str(ret)); - av_freep(&pl->desc_sets); + av_freep(&shd->desc_sets); return AVERROR_EXTERNAL; } - pl->assoc_pool = pool; + shd->assoc_pool = pool; } return 0; @@ -1749,38 +1938,37 @@ static inline void update_set_descriptor(FFVulkanContext *s, FFVkExecContext *e, vk->GetDescriptorEXT(s->hwctx->act_dev, desc_get_info, desc_size, desc); } -static inline void update_set_pool_write(FFVulkanContext *s, - FFVulkanPipeline *pl, +static inline void update_set_pool_write(FFVulkanContext *s, FFVulkanShader *shd, FFVkExecContext *e, FFVulkanDescriptorSet *desc_set, int set, VkWriteDescriptorSet *write_info) { FFVulkanFunctions *vk = &s->vkfn; if (desc_set->singular) { - for (int i = 0; i < pl->assoc_pool->pool_size; i++) { - write_info->dstSet = pl->desc_sets[i*pl->nb_descriptor_sets + set]; + for (int i = 0; i < shd->assoc_pool->pool_size; i++) { + write_info->dstSet = shd->desc_sets[i*shd->nb_descriptor_sets + set]; vk->UpdateDescriptorSets(s->hwctx->act_dev, 1, write_info, 0, NULL); } } else { - if (pl->use_push) { + if (shd->use_push) { vk->CmdPushDescriptorSetKHR(e->buf, - pl->bind_point, - pl->pipeline_layout, + shd->bind_point, + shd->pipeline_layout, set, 1, write_info); } else { - write_info->dstSet = pl->desc_sets[e->idx*pl->nb_descriptor_sets + set]; + write_info->dstSet = shd->desc_sets[e->idx*shd->nb_descriptor_sets + set]; vk->UpdateDescriptorSets(s->hwctx->act_dev, 1, write_info, 0, NULL); } } } -static int vk_set_descriptor_image(FFVulkanContext *s, FFVulkanPipeline *pl, +static int vk_set_descriptor_image(FFVulkanContext *s, FFVulkanShader *shd, FFVkExecContext *e, int set, int bind, int offs, VkImageView view, VkImageLayout layout, VkSampler sampler) { - FFVulkanDescriptorSet *desc_set = &pl->desc_set[set]; + FFVulkanDescriptorSet *desc_set = &shd->desc_set[set]; if (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) { VkDescriptorGetInfoEXT desc_get_info = { @@ -1834,18 +2022,19 @@ static int vk_set_descriptor_image(FFVulkanContext *s, FFVulkanPipeline *pl, .descriptorType = desc_set->binding[bind].descriptorType, .pImageInfo = &desc_pool_write_info_img, }; - update_set_pool_write(s, pl, e, desc_set, set, &desc_pool_write_info); + update_set_pool_write(s, shd, e, desc_set, set, &desc_pool_write_info); } return 0; } -int ff_vk_set_descriptor_buffer(FFVulkanContext *s, FFVulkanPipeline *pl, - FFVkExecContext *e, int set, int bind, int elem, - FFVkBuffer *buf, VkDeviceSize offset, VkDeviceSize len, - VkFormat fmt) +int ff_vk_shader_update_desc_buffer(FFVulkanContext *s, FFVkExecContext *e, + FFVulkanShader *shd, + int set, int bind, int elem, + FFVkBuffer *buf, VkDeviceSize offset, VkDeviceSize len, + VkFormat fmt) { - FFVulkanDescriptorSet *desc_set = &pl->desc_set[set]; + FFVulkanDescriptorSet *desc_set = &shd->desc_set[set]; if (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) { VkDescriptorGetInfoEXT desc_get_info = { @@ -1899,208 +2088,84 @@ int ff_vk_set_descriptor_buffer(FFVulkanContext *s, FFVulkanPipeline *pl, .descriptorType = desc_set->binding[bind].descriptorType, .pBufferInfo = &desc_pool_write_info_buf, }; - update_set_pool_write(s, pl, e, desc_set, set, &desc_pool_write_info); + update_set_pool_write(s, shd, e, desc_set, set, &desc_pool_write_info); } return 0; } -void ff_vk_update_descriptor_img_array(FFVulkanContext *s, FFVulkanPipeline *pl, - FFVkExecContext *e, AVFrame *f, - VkImageView *views, int set, int binding, - VkImageLayout layout, VkSampler sampler) +void ff_vk_shader_update_img_array(FFVulkanContext *s, FFVkExecContext *e, + FFVulkanShader *shd, AVFrame *f, + VkImageView *views, int set, int binding, + VkImageLayout layout, VkSampler sampler) { AVHWFramesContext *hwfc = (AVHWFramesContext *)f->hw_frames_ctx->data; const int nb_planes = av_pix_fmt_count_planes(hwfc->sw_format); for (int i = 0; i < nb_planes; i++) - vk_set_descriptor_image(s, pl, e, set, binding, i, + vk_set_descriptor_image(s, shd, e, set, binding, i, views[i], layout, sampler); } -void ff_vk_update_push_exec(FFVulkanContext *s, FFVkExecContext *e, - FFVulkanPipeline *pl, - VkShaderStageFlagBits stage, - int offset, size_t size, void *src) +void ff_vk_shader_update_push_const(FFVulkanContext *s, FFVkExecContext *e, + FFVulkanShader *shd, + VkShaderStageFlagBits stage, + int offset, size_t size, void *src) { FFVulkanFunctions *vk = &s->vkfn; - vk->CmdPushConstants(e->buf, pl->pipeline_layout, + vk->CmdPushConstants(e->buf, shd->pipeline_layout, stage, offset, size, src); } -static int init_descriptors(FFVulkanContext *s, FFVulkanPipeline *pl) -{ - VkResult ret; - FFVulkanFunctions *vk = &s->vkfn; - - pl->desc_layout = av_malloc_array(pl->nb_descriptor_sets, - sizeof(*pl->desc_layout)); - if (!pl->desc_layout) - return AVERROR(ENOMEM); - - if (!(s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER)) { - int has_singular = 0; - for (int i = 0; i < pl->nb_descriptor_sets; i++) { - if (pl->desc_set[i].singular) { - has_singular = 1; - break; - } - } - pl->use_push = (s->extensions & FF_VK_EXT_PUSH_DESCRIPTOR) && - (pl->nb_descriptor_sets == 1) && - !has_singular; - } - - for (int i = 0; i < pl->nb_descriptor_sets; i++) { - FFVulkanDescriptorSet *set = &pl->desc_set[i]; - VkDescriptorSetLayoutCreateInfo desc_layout_create = { - .sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO, - .bindingCount = set->nb_bindings, - .pBindings = set->binding, - .flags = (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) ? - VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT : - (pl->use_push) ? - VK_DESCRIPTOR_SET_LAYOUT_CREATE_PUSH_DESCRIPTOR_BIT_KHR : - 0x0, - }; - - ret = vk->CreateDescriptorSetLayout(s->hwctx->act_dev, - &desc_layout_create, - s->hwctx->alloc, - &pl->desc_layout[i]); - if (ret != VK_SUCCESS) { - av_log(s, AV_LOG_ERROR, "Unable to create descriptor set layout: %s", - ff_vk_ret2str(ret)); - return AVERROR_EXTERNAL; - } - - if (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) { - vk->GetDescriptorSetLayoutSizeEXT(s->hwctx->act_dev, pl->desc_layout[i], - &set->layout_size); - - set->aligned_size = FFALIGN(set->layout_size, - s->desc_buf_props.descriptorBufferOffsetAlignment); - - for (int j = 0; j < set->nb_bindings; j++) - vk->GetDescriptorSetLayoutBindingOffsetEXT(s->hwctx->act_dev, - pl->desc_layout[i], - j, - &set->binding_offset[j]); - } - } - - return 0; -} - -static int init_pipeline_layout(FFVulkanContext *s, FFVulkanPipeline *pl) -{ - VkResult ret; - FFVulkanFunctions *vk = &s->vkfn; - VkPipelineLayoutCreateInfo pipeline_layout_info; - - /* Finally create the pipeline layout */ - pipeline_layout_info = (VkPipelineLayoutCreateInfo) { - .sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO, - .pSetLayouts = pl->desc_layout, - .setLayoutCount = pl->nb_descriptor_sets, - .pushConstantRangeCount = pl->push_consts_num, - .pPushConstantRanges = pl->push_consts, - }; - - ret = vk->CreatePipelineLayout(s->hwctx->act_dev, &pipeline_layout_info, - s->hwctx->alloc, &pl->pipeline_layout); - if (ret != VK_SUCCESS) { - av_log(s, AV_LOG_ERROR, "Unable to init pipeline layout: %s\n", - ff_vk_ret2str(ret)); - return AVERROR_EXTERNAL; - } - - return 0; -} - -int ff_vk_init_compute_pipeline(FFVulkanContext *s, FFVulkanPipeline *pl, - FFVkSPIRVShader *shd) -{ - int err; - VkResult ret; - FFVulkanFunctions *vk = &s->vkfn; - - VkComputePipelineCreateInfo pipeline_create_info; - - err = init_descriptors(s, pl); - if (err < 0) - return err; - - err = init_pipeline_layout(s, pl); - if (err < 0) - return err; - - pipeline_create_info = (VkComputePipelineCreateInfo) { - .sType = VK_STRUCTURE_TYPE_COMPUTE_PIPELINE_CREATE_INFO, - .flags = (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) ? - VK_PIPELINE_CREATE_DESCRIPTOR_BUFFER_BIT_EXT : 0x0, - .layout = pl->pipeline_layout, - .stage = shd->shader, - }; - - ret = vk->CreateComputePipelines(s->hwctx->act_dev, VK_NULL_HANDLE, 1, - &pipeline_create_info, - s->hwctx->alloc, &pl->pipeline); - if (ret != VK_SUCCESS) { - av_log(s, AV_LOG_ERROR, "Unable to init compute pipeline: %s\n", - ff_vk_ret2str(ret)); - return AVERROR_EXTERNAL; - } - - pl->bind_point = VK_PIPELINE_BIND_POINT_COMPUTE; - pl->wg_size[0] = shd->local_size[0]; - pl->wg_size[1] = shd->local_size[1]; - pl->wg_size[2] = shd->local_size[2]; - - return 0; -} - -void ff_vk_exec_bind_pipeline(FFVulkanContext *s, FFVkExecContext *e, - FFVulkanPipeline *pl) +void ff_vk_exec_bind_shader(FFVulkanContext *s, FFVkExecContext *e, + FFVulkanShader *shd) { FFVulkanFunctions *vk = &s->vkfn; VkDeviceSize offsets[1024]; /* Bind pipeline */ - vk->CmdBindPipeline(e->buf, pl->bind_point, pl->pipeline); + vk->CmdBindPipeline(e->buf, shd->bind_point, shd->pipeline); - if (pl->nb_descriptor_sets) { + if (shd->nb_descriptor_sets) { if (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) { - for (int i = 0; i < pl->nb_descriptor_sets; i++) - offsets[i] = pl->desc_set[i].singular ? 0 : pl->desc_set[i].aligned_size*e->idx; + for (int i = 0; i < shd->nb_descriptor_sets; i++) + offsets[i] = shd->desc_set[i].singular ? 0 : shd->desc_set[i].aligned_size*e->idx; /* Bind descriptor buffers */ - vk->CmdBindDescriptorBuffersEXT(e->buf, pl->nb_descriptor_sets, pl->desc_bind); + vk->CmdBindDescriptorBuffersEXT(e->buf, shd->nb_descriptor_sets, shd->desc_bind); /* Binding offsets */ - vk->CmdSetDescriptorBufferOffsetsEXT(e->buf, pl->bind_point, pl->pipeline_layout, - 0, pl->nb_descriptor_sets, - pl->bound_buffer_indices, offsets); - } else if (!pl->use_push) { - vk->CmdBindDescriptorSets(e->buf, pl->bind_point, pl->pipeline_layout, - 0, pl->nb_descriptor_sets, - &pl->desc_sets[e->idx*pl->nb_descriptor_sets], + vk->CmdSetDescriptorBufferOffsetsEXT(e->buf, shd->bind_point, shd->pipeline_layout, + 0, shd->nb_descriptor_sets, + shd->bound_buffer_indices, offsets); + } else if (!shd->use_push) { + vk->CmdBindDescriptorSets(e->buf, shd->bind_point, shd->pipeline_layout, + 0, shd->nb_descriptor_sets, + &shd->desc_sets[e->idx*shd->nb_descriptor_sets], 0, NULL); } } } -void ff_vk_pipeline_free(FFVulkanContext *s, FFVulkanPipeline *pl) +void ff_vk_shader_free(FFVulkanContext *s, FFVulkanShader *shd) { FFVulkanFunctions *vk = &s->vkfn; - if (pl->pipeline) - vk->DestroyPipeline(s->hwctx->act_dev, pl->pipeline, s->hwctx->alloc); - if (pl->pipeline_layout) - vk->DestroyPipelineLayout(s->hwctx->act_dev, pl->pipeline_layout, + av_bprint_finalize(&shd->src, NULL); + +#if 0 + if (shd->shader.module) + vk->DestroyShaderModule(s->hwctx->act_dev, shd->shader.module, + s->hwctx->alloc); +#endif + + if (shd->pipeline) + vk->DestroyPipeline(s->hwctx->act_dev, shd->pipeline, s->hwctx->alloc); + if (shd->pipeline_layout) + vk->DestroyPipelineLayout(s->hwctx->act_dev, shd->pipeline_layout, s->hwctx->alloc); - for (int i = 0; i < pl->nb_descriptor_sets; i++) { - FFVulkanDescriptorSet *set = &pl->desc_set[i]; + for (int i = 0; i < shd->nb_descriptor_sets; i++) { + FFVulkanDescriptorSet *set = &shd->desc_set[i]; if (set->buf.mem) ff_vk_unmap_buffer(s, &set->buf, 0); ff_vk_free_buf(s, &set->buf); @@ -2108,23 +2173,23 @@ void ff_vk_pipeline_free(FFVulkanContext *s, FFVulkanPipeline *pl) av_free(set->binding_offset); } - for (int i = 0; i < pl->nb_descriptor_sets; i++) - if (pl->desc_layout[i]) - vk->DestroyDescriptorSetLayout(s->hwctx->act_dev, pl->desc_layout[i], + for (int i = 0; i < shd->nb_descriptor_sets; i++) + if (shd->desc_layout[i]) + vk->DestroyDescriptorSetLayout(s->hwctx->act_dev, shd->desc_layout[i], s->hwctx->alloc); - if (pl->desc_pool) - vk->DestroyDescriptorPool(s->hwctx->act_dev, pl->desc_pool, + if (shd->desc_pool) + vk->DestroyDescriptorPool(s->hwctx->act_dev, shd->desc_pool, s->hwctx->alloc); - av_freep(&pl->desc_pool_size); - av_freep(&pl->desc_layout); - av_freep(&pl->desc_sets); - av_freep(&pl->desc_set); - av_freep(&pl->desc_bind); - av_freep(&pl->bound_buffer_indices); - av_freep(&pl->push_consts); - pl->push_consts_num = 0; + av_freep(&shd->desc_pool_size); + av_freep(&shd->desc_layout); + av_freep(&shd->desc_sets); + av_freep(&shd->desc_set); + av_freep(&shd->desc_bind); + av_freep(&shd->bound_buffer_indices); + av_freep(&shd->push_consts); + shd->push_consts_num = 0; } void ff_vk_uninit(FFVulkanContext *s) diff --git a/libavutil/vulkan.h b/libavutil/vulkan.h index e03fd702ca..9c87dd29cf 100644 --- a/libavutil/vulkan.h +++ b/libavutil/vulkan.h @@ -72,14 +72,6 @@ #define DUP_SAMPLER(x) { x, x, x, x } -typedef struct FFVkSPIRVShader { - const char *name; /* Name for id/debugging purposes */ - AVBPrint src; - int local_size[3]; /* Compute shader workgroup sizes */ - VkPipelineShaderStageCreateInfo shader; - VkPipelineShaderStageRequiredSubgroupSizeCreateInfo subgroup_info; -} FFVkSPIRVShader; - typedef struct FFVulkanDescriptorSetBinding { const char *name; VkDescriptorType type; @@ -204,20 +196,35 @@ typedef struct FFVulkanDescriptorSet { int singular; } FFVulkanDescriptorSet; -typedef struct FFVulkanPipeline { +typedef struct FFVulkanShader { + /* Name for id/debugging purposes */ + const char *name; + + /* Shader text */ + AVBPrint src; + + /* Compute shader local group sizes */ + int lg_size[3]; + + /* Shader bind point/type */ + VkPipelineStageFlags stage; VkPipelineBindPoint bind_point; - /* Contexts */ + /* Creation info */ + VkPipelineShaderStageRequiredSubgroupSizeCreateInfo subgroup_info; + + /* Base shader object */ + union { + VkPipeline pipeline; + }; + + /* Pipeline layout */ VkPipelineLayout pipeline_layout; - VkPipeline pipeline; /* Push consts */ VkPushConstantRange *push_consts; int push_consts_num; - /* Workgroup */ - int wg_size[3]; - /* Descriptor buffer */ VkDescriptorSetLayout *desc_layout; FFVulkanDescriptorSet *desc_set; @@ -233,7 +240,7 @@ typedef struct FFVulkanPipeline { int nb_desc_pool_size; int total_desc_sets; FFVkExecPool *assoc_pool; -} FFVulkanPipeline; +} FFVulkanShader; typedef struct FFVulkanContext { const AVClass *class; @@ -472,59 +479,86 @@ int ff_vk_init_sampler(FFVulkanContext *s, VkSampler *sampler, int unnorm_coords, VkFilter filt); /** - * Shader management. + * Initialize a shader object, with a specific set of extensions, type+bind, + * local group size, and subgroup requirements. */ -int ff_vk_shader_init(FFVulkanPipeline *pl, FFVkSPIRVShader *shd, const char *name, - VkShaderStageFlags stage, uint32_t required_subgroup_size); -void ff_vk_shader_set_compute_sizes(FFVkSPIRVShader *shd, int x, int y, int z); -void ff_vk_shader_print(void *ctx, FFVkSPIRVShader *shd, int prio); -int ff_vk_shader_create(FFVulkanContext *s, FFVkSPIRVShader *shd, - uint8_t *spirv, size_t spirv_size, const char *entrypoint); -void ff_vk_shader_free(FFVulkanContext *s, FFVkSPIRVShader *shd); +int ff_vk_shader_init(FFVulkanContext *s, FFVulkanShader *shd, const char *name, + VkPipelineStageFlags stage, + const char *extensions[], int nb_extensions, + int lg_x, int lg_y, int lg_z, + uint32_t required_subgroup_size); /** - * Add/update push constants for execution. + * Output the shader code as logging data, with a specific + * priority. */ -int ff_vk_add_push_constant(FFVulkanPipeline *pl, int offset, int size, - VkShaderStageFlagBits stage); -void ff_vk_update_push_exec(FFVulkanContext *s, FFVkExecContext *e, - FFVulkanPipeline *pl, - VkShaderStageFlagBits stage, - int offset, size_t size, void *src); +void ff_vk_shader_print(void *ctx, FFVulkanShader *shd, int prio); /** - * Add descriptor to a pipeline. Must be called before pipeline init. + * Link a shader into an executable. */ -int ff_vk_pipeline_descriptor_set_add(FFVulkanContext *s, FFVulkanPipeline *pl, - FFVkSPIRVShader *shd, - FFVulkanDescriptorSetBinding *desc, int nb, - int singular, int print_to_shader_only); +int ff_vk_shader_link(FFVulkanContext *s, FFVulkanShader *shd, + uint8_t *spirv, size_t spirv_len, + const char *entrypoint); -/* Initialize/free a pipeline. */ -int ff_vk_init_compute_pipeline(FFVulkanContext *s, FFVulkanPipeline *pl, - FFVkSPIRVShader *shd); -void ff_vk_pipeline_free(FFVulkanContext *s, FFVulkanPipeline *pl); +/** + * Add/update push constants for execution. + */ +int ff_vk_shader_add_push_const(FFVulkanShader *shd, int offset, int size, + VkShaderStageFlagBits stage); /** - * Register a pipeline with an exec pool. + * Add descriptor to a shader. Must be called before shader init. + */ +int ff_vk_shader_add_descriptor_set(FFVulkanContext *s, FFVulkanShader *shd, + FFVulkanDescriptorSetBinding *desc, int nb, + int singular, int print_to_shader_only); + +/** + * Register a shader with an exec pool. * Pool may be NULL if all descriptor sets are read-only. */ -int ff_vk_exec_pipeline_register(FFVulkanContext *s, FFVkExecPool *pool, - FFVulkanPipeline *pl); - -/* Bind pipeline */ -void ff_vk_exec_bind_pipeline(FFVulkanContext *s, FFVkExecContext *e, - FFVulkanPipeline *pl); - -int ff_vk_set_descriptor_buffer(FFVulkanContext *s, FFVulkanPipeline *pl, - FFVkExecContext *e, int set, int bind, int elem, - FFVkBuffer *buf, VkDeviceSize offset, VkDeviceSize len, - VkFormat fmt); - -void ff_vk_update_descriptor_img_array(FFVulkanContext *s, FFVulkanPipeline *pl, - FFVkExecContext *e, AVFrame *f, - VkImageView *views, int set, int binding, - VkImageLayout layout, VkSampler sampler); +int ff_vk_shader_register_exec(FFVulkanContext *s, FFVkExecPool *pool, + FFVulkanShader *shd); + +/** + * Bind a shader. + */ +void ff_vk_exec_bind_shader(FFVulkanContext *s, FFVkExecContext *e, + FFVulkanShader *shd); + +/** + * Update push constant in a shader. + * Must be called before binding the shader. + */ +void ff_vk_shader_update_push_const(FFVulkanContext *s, FFVkExecContext *e, + FFVulkanShader *shd, + VkShaderStageFlagBits stage, + int offset, size_t size, void *src); + +/** + * Update a descriptor in a buffer with a buffer. + * Must be called before binding the shader. + */ +int ff_vk_shader_update_desc_buffer(FFVulkanContext *s, FFVkExecContext *e, + FFVulkanShader *shd, + int set, int bind, int elem, + FFVkBuffer *buf, VkDeviceSize offset, VkDeviceSize len, + VkFormat fmt); + +/** + * Update a descriptor in a buffer with an image array.. + * Must be called before binding the shader. + */ +void ff_vk_shader_update_img_array(FFVulkanContext *s, FFVkExecContext *e, + FFVulkanShader *shd, AVFrame *f, + VkImageView *views, int set, int binding, + VkImageLayout layout, VkSampler sampler); + +/** + * Free a shader. + */ +void ff_vk_shader_free(FFVulkanContext *s, FFVulkanShader *shd); /** * Frees main context. From patchwork Sun Sep 29 09:42:49 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Lynne X-Patchwork-Id: 51925 Delivered-To: ffmpegpatchwork2@gmail.com Received: by 2002:a59:d8ca:0:b0:48e:c0f8:d0de with SMTP id dy10csp1342914vqb; Sun, 29 Sep 2024 02:51:15 -0700 (PDT) X-Forwarded-Encrypted: i=2; AJvYcCUCP2HOZpPRzF+9KTeqOr+DDI4SRX2j9h80CHNMvIP7pFQ5EFfk5h+BjDhG+otrX2px8+WIQTU8XwCRGOot2Dht@gmail.com X-Google-Smtp-Source: AGHT+IGWz2XmELmfsvEGaH19odJuNuYaU2rcT3Q0+gYU/7AQ71M9lYW9KGYkyyhTv/a4YCltqTve X-Received: by 2002:a05:6512:3b8c:b0:539:8c02:64d5 with SMTP id 2adb3069b0e04-5398c0265f5mr1579169e87.27.1727603475558; Sun, 29 Sep 2024 02:51:15 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1727603475; cv=none; d=google.com; s=arc-20240605; b=gI5Fp0c2uSgUtfbewiObiiqruwDDOZo5IMkivEMUS9dSSTgPuRlSV1px9qLETJEapj 1m/wNnlpaiesSam5oKWgyDkPsaszXpodPLX5teV0P0Oj1XcPOGqU3pbvlDRGeg+mb8Xm m30ZQ1F8lSptbkdlRnetIQscOzz7A93MUN2hXtDRza3fA02ga5g1uLh+/AXB6+jaLZMY 9BYW6Gy0Jl03gpVyFRp80YWfwlE7aqKPgY2lGdZoAezklf16DWHj7nhj6yCzpmaFkmZp SIHziTGEgIeVGrUaWzUpLWJRH+MZGrPN1iKoB7IMxmho11hcYPNbOol9v6NAc3xnX5XM p0eA== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20240605; h=sender:errors-to:content-transfer-encoding:cc:reply-to:from :list-subscribe:list-help:list-post:list-archive:list-unsubscribe :list-id:precedence:subject:mime-version:references:in-reply-to :message-id:date:to:delivered-to; bh=Ld9E6DaTLqYX958XlZAzJEY9XbaMigG+NFfeb/ufsXQ=; fh=nenT92/WZoU6unXd3J6UhGUdod4piddKfVtctNBOh6k=; b=Sual9zLt9uiUacMPy6svcU3zgzfwd4e0NAvK7oURC+lRE4Zblm3gMuHM0YZvD4Pg3K nc4JkW3dUD1HMeeZfWbDfPnMLM3ZlOaXYTQh4ErkYLO/A0MvAyPQhowW6XwgKnE2kvxn GjPF/sUO2Cr+PKpuN1/HkbMXPt26eyjdcoAxLIIaI81QKxiqsrPah7908NSarYTrAmUh yXdPF0KIzgU4oQo7MGUKOG6q78NIgsuc8lbI1wJmwhn/GR5Wb7Tnu5uRMuHPlRcY8/s5 s/CpQ3FesavEF4T/GayWAAdhAOvbUb7otEurZFNeGib+INJbV1ePsWVmMoMCutTOmeFQ SOew==; dara=google.com ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: domain of ffmpeg-devel-bounces@ffmpeg.org designates 79.124.17.100 as permitted sender) smtp.mailfrom=ffmpeg-devel-bounces@ffmpeg.org Return-Path: Received: from ffbox0-bg.mplayerhq.hu (ffbox0-bg.ffmpeg.org. [79.124.17.100]) by mx.google.com with ESMTP id 2adb3069b0e04-538a043c0basi1953437e87.424.2024.09.29.02.51.14; Sun, 29 Sep 2024 02:51:15 -0700 (PDT) Received-SPF: pass (google.com: domain of ffmpeg-devel-bounces@ffmpeg.org designates 79.124.17.100 as permitted sender) client-ip=79.124.17.100; Authentication-Results: mx.google.com; spf=pass (google.com: domain of ffmpeg-devel-bounces@ffmpeg.org designates 79.124.17.100 as permitted sender) smtp.mailfrom=ffmpeg-devel-bounces@ffmpeg.org Received: from [127.0.1.1] (localhost [127.0.0.1]) by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTP id 44B4268DA40; Sun, 29 Sep 2024 12:43:08 +0300 (EEST) X-Original-To: ffmpeg-devel@ffmpeg.org Delivered-To: ffmpeg-devel@ffmpeg.org Received: from vidala.lynne.ee (vidala.pars.ee [116.203.72.101]) by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTPS id 9066168D8F2 for ; Sun, 29 Sep 2024 12:43:00 +0300 (EEST) To: ffmpeg-devel@ffmpeg.org Date: Sun, 29 Sep 2024 11:42:49 +0200 Message-ID: <20240929094256.396352-2-dev@lynne.ee> X-Mailer: git-send-email 2.45.2.753.g447d99e1c3b In-Reply-To: <20240929094256.396352-1-dev@lynne.ee> References: <20240929094256.396352-1-dev@lynne.ee> MIME-Version: 1.0 Subject: [FFmpeg-devel] [PATCH 2/5] vulkan: move shader data execution state to execution pools X-BeenThere: ffmpeg-devel@ffmpeg.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: FFmpeg development discussions and patches List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Lynne via ffmpeg-devel From: Lynne Reply-To: FFmpeg development discussions and patches Cc: Lynne Errors-To: ffmpeg-devel-bounces@ffmpeg.org Sender: "ffmpeg-devel" X-TUID: s/1NSGeb8juR This finally permits using fully compiled shaders across multiple execution contexts. --- libavutil/vulkan.c | 157 +++++++++++++++++++++++++++++---------------- libavutil/vulkan.h | 81 ++++++++++++++--------- 2 files changed, 153 insertions(+), 85 deletions(-) diff --git a/libavutil/vulkan.c b/libavutil/vulkan.c index 9ea9e478df..71581b91a9 100644 --- a/libavutil/vulkan.c +++ b/libavutil/vulkan.c @@ -262,6 +262,28 @@ void ff_vk_exec_pool_free(FFVulkanContext *s, FFVkExecPool *pool) av_free(e->sem_wait); } + /* Free shader-specific data */ + for (int i = 0; i < pool->nb_reg_shd; i++) { + FFVulkanShaderData *sd = &pool->reg_shd[i]; + + if (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) { + for (int j = 0; j < sd->nb_descriptor_sets; j++) { + FFVulkanDescriptorSetData *set_data = &sd->desc_set_buf[j]; + if (set_data->buf.mem) + ff_vk_unmap_buffer(s, &set_data->buf, 0); + ff_vk_free_buf(s, &set_data->buf); + } + } + + if (sd->desc_pool) + vk->DestroyDescriptorPool(s->hwctx->act_dev, sd->desc_pool, + s->hwctx->alloc); + + av_freep(&sd->desc_set_buf); + av_freep(&sd->desc_bind); + av_freep(&sd->desc_sets); + } + if (pool->cmd_bufs) vk->FreeCommandBuffers(s->hwctx->act_dev, pool->cmd_buf_pool, pool->pool_size, pool->cmd_bufs); @@ -1658,6 +1680,16 @@ int ff_vk_shader_link(FFVulkanContext *s, FFVulkanShader *shd, if (err < 0) return err; + if (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) { + shd->bound_buffer_indices = av_calloc(shd->nb_descriptor_sets, + sizeof(*shd->bound_buffer_indices)); + if (!shd->bound_buffer_indices) + return AVERROR(ENOMEM); + + for (int i = 0; i < shd->nb_descriptor_sets; i++) + shd->bound_buffer_indices[i] = i; + } + { VkShaderModule mod; err = create_shader_module(s, shd, &mod, spirv, spirv_len); @@ -1820,25 +1852,40 @@ int ff_vk_shader_register_exec(FFVulkanContext *s, FFVkExecPool *pool, FFVulkanShader *shd) { int err; + FFVulkanShaderData *sd; if (!shd->nb_descriptor_sets) return 0; + sd = av_realloc_array(pool->reg_shd, + sizeof(*pool->reg_shd), + pool->nb_reg_shd + 1); + if (!sd) + return AVERROR(ENOMEM); + + pool->reg_shd = sd; + sd = &sd[pool->nb_reg_shd++]; + memset(sd, 0, sizeof(*sd)); + + sd->shd = shd; + sd->nb_descriptor_sets = shd->nb_descriptor_sets; + if (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) { - shd->desc_bind = av_calloc(shd->nb_descriptor_sets, sizeof(*shd->desc_bind)); - if (!shd->desc_bind) + sd->desc_bind = av_malloc_array(sd->nb_descriptor_sets, sizeof(*sd->desc_bind)); + if (!sd->desc_bind) return AVERROR(ENOMEM); - shd->bound_buffer_indices = av_calloc(shd->nb_descriptor_sets, - sizeof(*shd->bound_buffer_indices)); - if (!shd->bound_buffer_indices) + sd->desc_set_buf = av_calloc(sd->nb_descriptor_sets, sizeof(*sd->desc_set_buf)); + if (!sd->desc_set_buf) return AVERROR(ENOMEM); - for (int i = 0; i < shd->nb_descriptor_sets; i++) { + for (int i = 0; i < sd->nb_descriptor_sets; i++) { FFVulkanDescriptorSet *set = &shd->desc_set[i]; + FFVulkanDescriptorSetData *sdb = &sd->desc_set_buf[i]; int nb = set->singular ? 1 : pool->pool_size; - err = ff_vk_create_buf(s, &set->buf, set->aligned_size*nb, + err = ff_vk_create_buf(s, &sdb->buf, + set->aligned_size*nb, NULL, NULL, set->usage, VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT | VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT | @@ -1846,17 +1893,15 @@ int ff_vk_shader_register_exec(FFVulkanContext *s, FFVkExecPool *pool, if (err < 0) return err; - err = ff_vk_map_buffer(s, &set->buf, &set->desc_mem, 0); + err = ff_vk_map_buffer(s, &sdb->buf, &sdb->desc_mem, 0); if (err < 0) return err; - shd->desc_bind[i] = (VkDescriptorBufferBindingInfoEXT) { + sd->desc_bind[i] = (VkDescriptorBufferBindingInfoEXT) { .sType = VK_STRUCTURE_TYPE_DESCRIPTOR_BUFFER_BINDING_INFO_EXT, .usage = set->usage, - .address = set->buf.address, + .address = sdb->buf.address, }; - - shd->bound_buffer_indices[i] = i; } } else if (!shd->use_push) { VkResult ret; @@ -1873,11 +1918,11 @@ int ff_vk_shader_register_exec(FFVulkanContext *s, FFVkExecPool *pool, .flags = 0, .pPoolSizes = shd->desc_pool_size, .poolSizeCount = shd->nb_desc_pool_size, - .maxSets = shd->nb_descriptor_sets*pool->pool_size, + .maxSets = sd->nb_descriptor_sets*pool->pool_size, }; ret = vk->CreateDescriptorPool(s->hwctx->act_dev, &pool_create_info, - s->hwctx->alloc, &shd->desc_pool); + s->hwctx->alloc, &sd->desc_pool); if (ret != VK_SUCCESS) { av_log(s, AV_LOG_ERROR, "Unable to create descriptor pool: %s\n", ff_vk_ret2str(ret)); @@ -1890,63 +1935,75 @@ int ff_vk_shader_register_exec(FFVulkanContext *s, FFVkExecPool *pool, /* Colate each execution context's descriptor set layouts */ for (int i = 0; i < pool->pool_size; i++) - for (int j = 0; j < shd->nb_descriptor_sets; j++) - tmp_layouts[i*shd->nb_descriptor_sets + j] = shd->desc_layout[j]; + for (int j = 0; j < sd->nb_descriptor_sets; j++) + tmp_layouts[i*sd->nb_descriptor_sets + j] = shd->desc_layout[j]; set_alloc_info = (VkDescriptorSetAllocateInfo) { .sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO, - .descriptorPool = shd->desc_pool, + .descriptorPool = sd->desc_pool, .pSetLayouts = tmp_layouts, .descriptorSetCount = pool_create_info.maxSets, }; - shd->desc_sets = av_malloc_array(pool_create_info.maxSets, + sd->desc_sets = av_malloc_array(pool_create_info.maxSets, sizeof(*tmp_layouts)); - if (!shd->desc_sets) { + if (!sd->desc_sets) { av_free(tmp_layouts); return AVERROR(ENOMEM); } ret = vk->AllocateDescriptorSets(s->hwctx->act_dev, &set_alloc_info, - shd->desc_sets); + sd->desc_sets); av_free(tmp_layouts); if (ret != VK_SUCCESS) { av_log(s, AV_LOG_ERROR, "Unable to allocate descriptor set: %s\n", ff_vk_ret2str(ret)); - av_freep(&shd->desc_sets); + av_freep(&sd->desc_sets); return AVERROR_EXTERNAL; } - - shd->assoc_pool = pool; } return 0; } +static inline FFVulkanShaderData *get_shd_data(FFVkExecContext *e, + FFVulkanShader *shd) +{ + for (int i = 0; i < e->parent->nb_reg_shd; i++) + if (e->parent->reg_shd[i].shd == shd) + return &e->parent->reg_shd[i]; + av_assert0(0); +} + static inline void update_set_descriptor(FFVulkanContext *s, FFVkExecContext *e, - FFVulkanDescriptorSet *set, + FFVulkanShader *shd, int set, int bind_idx, int array_idx, VkDescriptorGetInfoEXT *desc_get_info, size_t desc_size) { FFVulkanFunctions *vk = &s->vkfn; - const size_t exec_offset = set->singular ? 0 : set->aligned_size*e->idx; - void *desc = set->desc_mem + /* Base */ - exec_offset + /* Execution context */ - set->binding_offset[bind_idx] + /* Descriptor binding */ - array_idx*desc_size; /* Array position */ + FFVulkanDescriptorSet *desc_set = &shd->desc_set[set]; + FFVulkanShaderData *sd = get_shd_data(e, shd); + const size_t exec_offset = desc_set->singular ? 0 : desc_set->aligned_size*e->idx; + + void *desc = sd->desc_set_buf[set].desc_mem + /* Base */ + exec_offset + /* Execution context */ + desc_set->binding_offset[bind_idx] + /* Descriptor binding */ + array_idx*desc_size; /* Array position */ vk->GetDescriptorEXT(s->hwctx->act_dev, desc_get_info, desc_size, desc); } -static inline void update_set_pool_write(FFVulkanContext *s, FFVulkanShader *shd, - FFVkExecContext *e, - FFVulkanDescriptorSet *desc_set, int set, +static inline void update_set_pool_write(FFVulkanContext *s, FFVkExecContext *e, + FFVulkanShader *shd, int set, VkWriteDescriptorSet *write_info) { FFVulkanFunctions *vk = &s->vkfn; + FFVulkanDescriptorSet *desc_set = &shd->desc_set[set]; + FFVulkanShaderData *sd = get_shd_data(e, shd); + if (desc_set->singular) { - for (int i = 0; i < shd->assoc_pool->pool_size; i++) { - write_info->dstSet = shd->desc_sets[i*shd->nb_descriptor_sets + set]; + for (int i = 0; i < e->parent->pool_size; i++) { + write_info->dstSet = sd->desc_sets[i*sd->nb_descriptor_sets + set]; vk->UpdateDescriptorSets(s->hwctx->act_dev, 1, write_info, 0, NULL); } } else { @@ -1957,7 +2014,7 @@ static inline void update_set_pool_write(FFVulkanContext *s, FFVulkanShader *shd set, 1, write_info); } else { - write_info->dstSet = shd->desc_sets[e->idx*shd->nb_descriptor_sets + set]; + write_info->dstSet = sd->desc_sets[e->idx*sd->nb_descriptor_sets + set]; vk->UpdateDescriptorSets(s->hwctx->act_dev, 1, write_info, 0, NULL); } } @@ -2006,7 +2063,7 @@ static int vk_set_descriptor_image(FFVulkanContext *s, FFVulkanShader *shd, break; }; - update_set_descriptor(s, e, desc_set, bind, offs, + update_set_descriptor(s, e, shd, set, bind, offs, &desc_get_info, desc_size); } else { VkDescriptorImageInfo desc_pool_write_info_img = { @@ -2022,7 +2079,7 @@ static int vk_set_descriptor_image(FFVulkanContext *s, FFVulkanShader *shd, .descriptorType = desc_set->binding[bind].descriptorType, .pImageInfo = &desc_pool_write_info_img, }; - update_set_pool_write(s, shd, e, desc_set, set, &desc_pool_write_info); + update_set_pool_write(s, e, shd, set, &desc_pool_write_info); } return 0; @@ -2073,7 +2130,7 @@ int ff_vk_shader_update_desc_buffer(FFVulkanContext *s, FFVkExecContext *e, break; }; - update_set_descriptor(s, e, desc_set, bind, elem, &desc_get_info, desc_size); + update_set_descriptor(s, e, shd, set, bind, elem, &desc_get_info, desc_size); } else { VkDescriptorBufferInfo desc_pool_write_info_buf = { .buffer = buf->buf, @@ -2088,7 +2145,7 @@ int ff_vk_shader_update_desc_buffer(FFVulkanContext *s, FFVkExecContext *e, .descriptorType = desc_set->binding[bind].descriptorType, .pBufferInfo = &desc_pool_write_info_buf, }; - update_set_pool_write(s, shd, e, desc_set, set, &desc_pool_write_info); + update_set_pool_write(s, e, shd, set, &desc_pool_write_info); } return 0; @@ -2122,25 +2179,26 @@ void ff_vk_exec_bind_shader(FFVulkanContext *s, FFVkExecContext *e, { FFVulkanFunctions *vk = &s->vkfn; VkDeviceSize offsets[1024]; + FFVulkanShaderData *sd = get_shd_data(e, shd); /* Bind pipeline */ vk->CmdBindPipeline(e->buf, shd->bind_point, shd->pipeline); - if (shd->nb_descriptor_sets) { + if (sd->nb_descriptor_sets) { if (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) { - for (int i = 0; i < shd->nb_descriptor_sets; i++) + for (int i = 0; i < sd->nb_descriptor_sets; i++) offsets[i] = shd->desc_set[i].singular ? 0 : shd->desc_set[i].aligned_size*e->idx; /* Bind descriptor buffers */ - vk->CmdBindDescriptorBuffersEXT(e->buf, shd->nb_descriptor_sets, shd->desc_bind); + vk->CmdBindDescriptorBuffersEXT(e->buf, sd->nb_descriptor_sets, sd->desc_bind); /* Binding offsets */ vk->CmdSetDescriptorBufferOffsetsEXT(e->buf, shd->bind_point, shd->pipeline_layout, - 0, shd->nb_descriptor_sets, + 0, sd->nb_descriptor_sets, shd->bound_buffer_indices, offsets); } else if (!shd->use_push) { vk->CmdBindDescriptorSets(e->buf, shd->bind_point, shd->pipeline_layout, - 0, shd->nb_descriptor_sets, - &shd->desc_sets[e->idx*shd->nb_descriptor_sets], + 0, sd->nb_descriptor_sets, + &sd->desc_sets[e->idx*sd->nb_descriptor_sets], 0, NULL); } } @@ -2166,9 +2224,6 @@ void ff_vk_shader_free(FFVulkanContext *s, FFVulkanShader *shd) for (int i = 0; i < shd->nb_descriptor_sets; i++) { FFVulkanDescriptorSet *set = &shd->desc_set[i]; - if (set->buf.mem) - ff_vk_unmap_buffer(s, &set->buf, 0); - ff_vk_free_buf(s, &set->buf); av_free(set->binding); av_free(set->binding_offset); } @@ -2178,15 +2233,9 @@ void ff_vk_shader_free(FFVulkanContext *s, FFVulkanShader *shd) vk->DestroyDescriptorSetLayout(s->hwctx->act_dev, shd->desc_layout[i], s->hwctx->alloc); - if (shd->desc_pool) - vk->DestroyDescriptorPool(s->hwctx->act_dev, shd->desc_pool, - s->hwctx->alloc); - av_freep(&shd->desc_pool_size); av_freep(&shd->desc_layout); - av_freep(&shd->desc_sets); av_freep(&shd->desc_set); - av_freep(&shd->desc_bind); av_freep(&shd->bound_buffer_indices); av_freep(&shd->push_consts); shd->push_consts_num = 0; diff --git a/libavutil/vulkan.h b/libavutil/vulkan.h index 9c87dd29cf..5391afa4e7 100644 --- a/libavutil/vulkan.h +++ b/libavutil/vulkan.h @@ -162,31 +162,11 @@ typedef struct FFVkExecContext { unsigned int frame_update_alloc_size; } FFVkExecContext; -typedef struct FFVkExecPool { - FFVkExecContext *contexts; - atomic_int_least64_t idx; - - VkCommandPool cmd_buf_pool; - VkCommandBuffer *cmd_bufs; - int pool_size; - - VkQueryPool query_pool; - void *query_data; - int query_results; - int query_statuses; - int query_64bit; - int query_status_stride; - int nb_queries; - size_t qd_size; -} FFVkExecPool; - typedef struct FFVulkanDescriptorSet { - FFVkBuffer buf; - uint8_t *desc_mem; - VkDeviceSize layout_size; - VkDeviceSize aligned_size; /* descriptorBufferOffsetAlignment */ - VkDeviceSize total_size; /* Once registered to an exec context */ - VkBufferUsageFlags usage; + /* Descriptor buffer */ + VkDeviceSize layout_size; + VkDeviceSize aligned_size; /* descriptorBufferOffsetAlignment */ + VkBufferUsageFlags usage; VkDescriptorSetLayoutBinding *binding; VkDeviceSize *binding_offset; @@ -225,23 +205,62 @@ typedef struct FFVulkanShader { VkPushConstantRange *push_consts; int push_consts_num; + /* Descriptor sets */ + FFVulkanDescriptorSet *desc_set; + int nb_descriptor_sets; + /* Descriptor buffer */ VkDescriptorSetLayout *desc_layout; - FFVulkanDescriptorSet *desc_set; - VkDescriptorBufferBindingInfoEXT *desc_bind; uint32_t *bound_buffer_indices; - int nb_descriptor_sets; /* Descriptor pool */ int use_push; - VkDescriptorSet *desc_sets; - VkDescriptorPool desc_pool; VkDescriptorPoolSize *desc_pool_size; int nb_desc_pool_size; - int total_desc_sets; - FFVkExecPool *assoc_pool; } FFVulkanShader; +typedef struct FFVulkanDescriptorSetData { + /* Descriptor buffer */ + FFVkBuffer buf; + uint8_t *desc_mem; +} FFVulkanDescriptorSetData; + +typedef struct FFVulkanShaderData { + /* Shader to which this data belongs to */ + FFVulkanShader *shd; + int nb_descriptor_sets; + + /* Descriptor buffer */ + FFVulkanDescriptorSetData *desc_set_buf; + VkDescriptorBufferBindingInfoEXT *desc_bind; + + /* Descriptor pools */ + VkDescriptorSet *desc_sets; + VkDescriptorPool desc_pool; +} FFVulkanShaderData; + +typedef struct FFVkExecPool { + FFVkExecContext *contexts; + atomic_int_least64_t idx; + + VkCommandPool cmd_buf_pool; + VkCommandBuffer *cmd_bufs; + int pool_size; + + VkQueryPool query_pool; + void *query_data; + int query_results; + int query_statuses; + int query_64bit; + int query_status_stride; + int nb_queries; + size_t qd_size; + + /* Registered shaders' data */ + FFVulkanShaderData *reg_shd; + int nb_reg_shd; +} FFVkExecPool; + typedef struct FFVulkanContext { const AVClass *class; void *log_parent; From patchwork Sun Sep 29 09:42:50 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Lynne X-Patchwork-Id: 51921 Delivered-To: ffmpegpatchwork2@gmail.com Received: by 2002:a59:d8ca:0:b0:48e:c0f8:d0de with SMTP id dy10csp1341048vqb; Sun, 29 Sep 2024 02:43:13 -0700 (PDT) X-Forwarded-Encrypted: i=2; AJvYcCXu6fxnnzWazqi5nfkGqyX6nc7BJbUzcmVxgODqx5a2o7m+oIFg52alEef32twSJJ5HPhtTOiQswkq4Sk/RQFnf@gmail.com X-Google-Smtp-Source: AGHT+IHfCCnrVqzrSytB9B6692oSbk3ZailyNw4gtEZki8p1zXCZCs4wVRkxchdUCGJX8M9S7FGg X-Received: by 2002:a17:907:1b13:b0:a90:df6f:f087 with SMTP id a640c23a62f3a-a93c4ae03bemr788615466b.47.1727602992979; Sun, 29 Sep 2024 02:43:12 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1727602992; cv=none; d=google.com; s=arc-20240605; b=PoFDKebWofx6C0t2Y41nTugqOu125LOJSNZ2/bPKwG5iGSetebuGyR4LBNgEW1Sxp/ e0lO2G8j/br0SnYCpZU95iV8RINWzZu9W5uiSFwfC0YFCZkWIp7gKq57mU4fDyF+PPXT avxdDFDLbNoMNfLQClOTjXS0oVtRywjvY1PIQxX7yEy469BDvrpB0B05b0RZ+raYhlVG pDZ4vgWtZY9GrSJYOy1rWydl4QTSYWsjboyhbE7rZTJa7T+ZYhxTuyrXAHwVGgGJ4EAQ yX0DPmctuBPbiZfK9DPdp2YDHjyLDwU6Je4Zt+EYeQ3RV4obuYeJhXN6fPdHckGyI7yv rY/Q== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20240605; h=sender:errors-to:content-transfer-encoding:cc:reply-to:from :list-subscribe:list-help:list-post:list-archive:list-unsubscribe :list-id:precedence:subject:mime-version:references:in-reply-to :message-id:date:to:delivered-to; bh=DCgrq55pGCYpzbKuOOrEID7XulLHQqteAHv7MqbOodY=; fh=nenT92/WZoU6unXd3J6UhGUdod4piddKfVtctNBOh6k=; b=f7t1Vl1ZnB5SxIPSd3be9Qeu81zg/e9j0jg5mdPbkFnjLAs47NST1lwJQy/UT/tZCV hVs7W3UCFayPw2lA8S46tQerOa52t0tb78xufY78ay55+i3ydiJVouHRMivEjBe6z/dz wLPcBc7KIH1oBRJxXsko3x2U3zZ1POYzOQHmQ+mF5s07ijiB1AbmhLO1FuDFvYkmZzid JRiRdXUwUZWEDk3qCGKOLTLMAGZV68wiSoaNiTaXeO0zB5GMWeiwhOFLiaeXxLX9Mo7X /vDwe7MceW7sHM1BOMMIEb5KL4qzrvQx+NrjCVBnJSvvUqVjP+wCjjrcU7RmZk7Oai91 UpfA==; dara=google.com ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: domain of ffmpeg-devel-bounces@ffmpeg.org designates 79.124.17.100 as permitted sender) smtp.mailfrom=ffmpeg-devel-bounces@ffmpeg.org Return-Path: Received: from ffbox0-bg.mplayerhq.hu (ffbox0-bg.ffmpeg.org. [79.124.17.100]) by mx.google.com with ESMTP id a640c23a62f3a-a93c29e637fsi442409466b.574.2024.09.29.02.43.11; Sun, 29 Sep 2024 02:43:12 -0700 (PDT) Received-SPF: pass (google.com: domain of ffmpeg-devel-bounces@ffmpeg.org designates 79.124.17.100 as permitted sender) client-ip=79.124.17.100; Authentication-Results: mx.google.com; spf=pass (google.com: domain of ffmpeg-devel-bounces@ffmpeg.org designates 79.124.17.100 as permitted sender) smtp.mailfrom=ffmpeg-devel-bounces@ffmpeg.org Received: from [127.0.1.1] (localhost [127.0.0.1]) by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTP id 2DF5268DA34; Sun, 29 Sep 2024 12:43:07 +0300 (EEST) X-Original-To: ffmpeg-devel@ffmpeg.org Delivered-To: ffmpeg-devel@ffmpeg.org Received: from vidala.lynne.ee (vidala.pars.ee [116.203.72.101]) by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTPS id 8D68068D5DE for ; Sun, 29 Sep 2024 12:43:00 +0300 (EEST) To: ffmpeg-devel@ffmpeg.org Date: Sun, 29 Sep 2024 11:42:50 +0200 Message-ID: <20240929094256.396352-3-dev@lynne.ee> X-Mailer: git-send-email 2.45.2.753.g447d99e1c3b In-Reply-To: <20240929094256.396352-1-dev@lynne.ee> References: <20240929094256.396352-1-dev@lynne.ee> MIME-Version: 1.0 Subject: [FFmpeg-devel] [PATCH 3/5] vulkan: use shader objects if supported X-BeenThere: ffmpeg-devel@ffmpeg.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: FFmpeg development discussions and patches List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Lynne via ffmpeg-devel From: Lynne Reply-To: FFmpeg development discussions and patches Cc: Lynne Errors-To: ffmpeg-devel-bounces@ffmpeg.org Sender: "ffmpeg-devel" X-TUID: xO9tQK7YIsiG Shader objects finally allow completely independent shaders. --- libavutil/vulkan.c | 51 +++++++++++++++++++++++++++++++++++++++++++--- libavutil/vulkan.h | 5 ++--- 2 files changed, 50 insertions(+), 6 deletions(-) diff --git a/libavutil/vulkan.c b/libavutil/vulkan.c index 71581b91a9..8b1c1eb796 100644 --- a/libavutil/vulkan.c +++ b/libavutil/vulkan.c @@ -1601,6 +1601,41 @@ static int init_compute_pipeline(FFVulkanContext *s, FFVulkanShader *shd, return 0; } +static int create_shader_object(FFVulkanContext *s, FFVulkanShader *shd, + uint8_t *spirv, size_t spirv_len, + const char *entrypoint) +{ + VkResult ret; + FFVulkanFunctions *vk = &s->vkfn; + + VkShaderCreateInfoEXT shader_obj_create = { + .sType = VK_STRUCTURE_TYPE_SHADER_CREATE_INFO_EXT, + .flags = shd->subgroup_info.requiredSubgroupSize ? + VK_SHADER_CREATE_REQUIRE_FULL_SUBGROUPS_BIT_EXT : 0x0, + .stage = shd->stage, + .nextStage = 0, + .codeType = VK_SHADER_CODE_TYPE_SPIRV_EXT, + .pCode = spirv, + .codeSize = spirv_len, + .pName = entrypoint, + .pSetLayouts = shd->desc_layout, + .setLayoutCount = shd->nb_descriptor_sets, + .pushConstantRangeCount = shd->push_consts_num, + .pPushConstantRanges = shd->push_consts, + .pSpecializationInfo = NULL, + }; + + ret = vk->CreateShadersEXT(s->hwctx->act_dev, 1, &shader_obj_create, + s->hwctx->alloc, &shd->object); + if (ret != VK_SUCCESS) { + av_log(s, AV_LOG_ERROR, "Unable to create shader object: %s\n", + ff_vk_ret2str(ret)); + return AVERROR_EXTERNAL; + } + + return 0; +} + static int init_descriptors(FFVulkanContext *s, FFVulkanShader *shd) { VkResult ret; @@ -1690,7 +1725,11 @@ int ff_vk_shader_link(FFVulkanContext *s, FFVulkanShader *shd, shd->bound_buffer_indices[i] = i; } - { + if (s->extensions & FF_VK_EXT_SHADER_OBJECT) { + err = create_shader_object(s, shd, spirv, spirv_len, entrypoint); + if (err < 0) + return err; + } else { VkShaderModule mod; err = create_shader_module(s, shd, &mod, spirv, spirv_len); if (err < 0) @@ -2181,8 +2220,12 @@ void ff_vk_exec_bind_shader(FFVulkanContext *s, FFVkExecContext *e, VkDeviceSize offsets[1024]; FFVulkanShaderData *sd = get_shd_data(e, shd); - /* Bind pipeline */ - vk->CmdBindPipeline(e->buf, shd->bind_point, shd->pipeline); + if (s->extensions & FF_VK_EXT_SHADER_OBJECT) { + VkShaderStageFlagBits stages = shd->stage; + vk->CmdBindShadersEXT(e->buf, 1, &stages, &shd->object); + } else { + vk->CmdBindPipeline(e->buf, shd->bind_point, shd->pipeline); + } if (sd->nb_descriptor_sets) { if (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) { @@ -2216,6 +2259,8 @@ void ff_vk_shader_free(FFVulkanContext *s, FFVulkanShader *shd) s->hwctx->alloc); #endif + if (shd->object) + vk->DestroyShaderEXT(s->hwctx->act_dev, shd->object, s->hwctx->alloc); if (shd->pipeline) vk->DestroyPipeline(s->hwctx->act_dev, shd->pipeline, s->hwctx->alloc); if (shd->pipeline_layout) diff --git a/libavutil/vulkan.h b/libavutil/vulkan.h index 5391afa4e7..47684e600d 100644 --- a/libavutil/vulkan.h +++ b/libavutil/vulkan.h @@ -194,9 +194,8 @@ typedef struct FFVulkanShader { VkPipelineShaderStageRequiredSubgroupSizeCreateInfo subgroup_info; /* Base shader object */ - union { - VkPipeline pipeline; - }; + VkShaderEXT object; + VkPipeline pipeline; /* Pipeline layout */ VkPipelineLayout pipeline_layout; From patchwork Sun Sep 29 09:42:51 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Lynne X-Patchwork-Id: 51922 Delivered-To: ffmpegpatchwork2@gmail.com Received: by 2002:a59:d8ca:0:b0:48e:c0f8:d0de with SMTP id dy10csp1341118vqb; Sun, 29 Sep 2024 02:43:32 -0700 (PDT) X-Forwarded-Encrypted: i=2; AJvYcCUNF6SvkxW1aJpHalvrK4C6YMfyKu0d02JBym6EU86bwUnB+8Ty8sINCiEpYLELaJzM48Qwwh47J45qvocPzQjo@gmail.com X-Google-Smtp-Source: AGHT+IEgkv3/MzewlHn8Fn3jchTqVVZ9P00FrApmt3/87Vf9y/1ifjQqN9ijM32TK9+dzjQnFOs+ X-Received: by 2002:a2e:4c0a:0:b0:2f9:ce91:dea9 with SMTP id 38308e7fff4ca-2f9d41b5f4amr31004061fa.32.1727603012435; Sun, 29 Sep 2024 02:43:32 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1727603012; cv=none; d=google.com; s=arc-20240605; b=YTtfh1GWywBI0GwryMzaXURugTbd1TB0Yf/jabrb/RweM9Xyi6mXTKWi4C8mjiL/UO sKyqcFvjwJyQ3FRm9v1ENtHg7rgx9igmgSPFyBLwd7VwJI9QAfFbkPqkLLrd3j3JNln5 eZcaznjpgfeRXj2MqpYFEYSVDUF4qUoAKc/kzBpKj9+UDMcvYNc92iQ4+AINo9dgzjOz xEFlMt6miLIOerePFib+NGErZ8gWr6BqYSp/Cgjhsv7D0knLsew5pO8FvxaNmJ+GSsUb FuvJLL2whquAs/4cXvJPYtj4PlBn5+94WxvK2cqFYSyB5cfzILNU264WL8oscwBH7hM0 Hx8g== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20240605; h=sender:errors-to:content-transfer-encoding:cc:reply-to:from :list-subscribe:list-help:list-post:list-archive:list-unsubscribe :list-id:precedence:subject:mime-version:references:in-reply-to :message-id:date:to:delivered-to; bh=oVxiR4d6fQVVzwhkLwmkv+IFwF3/JDgcpdst36YSYlA=; fh=nenT92/WZoU6unXd3J6UhGUdod4piddKfVtctNBOh6k=; b=dOq0l2Yf31R3wxZUcvv8pxNtwpXI0BBelkSOqS4iOhaDQsUExrQEbA7b14u5ZZssC+ DlHVINKzl5AbU30EUuO/4DA6VB+Sa2tH/tI+3dhSNEggWVpoApOPMc0D8tyyKQVFzcmT JUqr9x/h2rRt9CuUux0YRSMDwHtXzd9VYeT2Ea6CYywIQ9ACbUFcTo4cATYqvG6FBLAF aI7SGRgAcORgIik1op2vsp/QnJzJTkEPRpNTfwGckIrjt3nl4Xja/b4BThpzuUhKfK7Z BpWT1oT8wA4K2hFYGXGHb/GVLBsDbAcReV+sm+T9XcQt/biUEjD2QQ6Ppsiudw2HlEW/ 971g==; dara=google.com ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: domain of ffmpeg-devel-bounces@ffmpeg.org designates 79.124.17.100 as permitted sender) smtp.mailfrom=ffmpeg-devel-bounces@ffmpeg.org Return-Path: Received: from ffbox0-bg.mplayerhq.hu (ffbox0-bg.ffmpeg.org. [79.124.17.100]) by mx.google.com with ESMTP id 38308e7fff4ca-2f9d4643e23si19044861fa.550.2024.09.29.02.43.32; Sun, 29 Sep 2024 02:43:32 -0700 (PDT) Received-SPF: pass (google.com: domain of ffmpeg-devel-bounces@ffmpeg.org designates 79.124.17.100 as permitted sender) client-ip=79.124.17.100; Authentication-Results: mx.google.com; spf=pass (google.com: domain of ffmpeg-devel-bounces@ffmpeg.org designates 79.124.17.100 as permitted sender) smtp.mailfrom=ffmpeg-devel-bounces@ffmpeg.org Received: from [127.0.1.1] (localhost [127.0.0.1]) by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTP id 7B59F68DA4C; Sun, 29 Sep 2024 12:43:09 +0300 (EEST) X-Original-To: ffmpeg-devel@ffmpeg.org Delivered-To: ffmpeg-devel@ffmpeg.org Received: from vidala.lynne.ee (vidala.pars.ee [116.203.72.101]) by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTPS id 935C268D983 for ; Sun, 29 Sep 2024 12:43:00 +0300 (EEST) To: ffmpeg-devel@ffmpeg.org Date: Sun, 29 Sep 2024 11:42:51 +0200 Message-ID: <20240929094256.396352-4-dev@lynne.ee> X-Mailer: git-send-email 2.45.2.753.g447d99e1c3b In-Reply-To: <20240929094256.396352-1-dev@lynne.ee> References: <20240929094256.396352-1-dev@lynne.ee> MIME-Version: 1.0 Subject: [FFmpeg-devel] [PATCH 4/5] vulkan: always enable GL_EXT_scalar_block_layout X-BeenThere: ffmpeg-devel@ffmpeg.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: FFmpeg development discussions and patches List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Lynne via ffmpeg-devel From: Lynne Reply-To: FFmpeg development discussions and patches Cc: Lynne Errors-To: ffmpeg-devel-bounces@ffmpeg.org Sender: "ffmpeg-devel" X-TUID: 7zUV/RmBaHHv This makes std430 (which we use everywhere already) fully match C layout. Extension was made mandatory in 1.2. --- libavutil/hwcontext_vulkan.c | 1 + libavutil/vulkan.c | 1 + 2 files changed, 2 insertions(+) diff --git a/libavutil/hwcontext_vulkan.c b/libavutil/hwcontext_vulkan.c index 6317ab7d0e..3a3aff75c0 100644 --- a/libavutil/hwcontext_vulkan.c +++ b/libavutil/hwcontext_vulkan.c @@ -1501,6 +1501,7 @@ static int vulkan_device_create_internal(AVHWDeviceContext *ctx, p->device_features_1_1.uniformAndStorageBuffer16BitAccess = dev_features_1_1.uniformAndStorageBuffer16BitAccess; p->device_features_1_2.timelineSemaphore = 1; + p->device_features_1_2.scalarBlockLayout = dev_features_1_2.scalarBlockLayout; p->device_features_1_2.bufferDeviceAddress = dev_features_1_2.bufferDeviceAddress; p->device_features_1_2.hostQueryReset = dev_features_1_2.hostQueryReset; p->device_features_1_2.storagePushConstant8 = dev_features_1_2.storagePushConstant8; diff --git a/libavutil/vulkan.c b/libavutil/vulkan.c index 8b1c1eb796..ab2519bf35 100644 --- a/libavutil/vulkan.c +++ b/libavutil/vulkan.c @@ -1473,6 +1473,7 @@ int ff_vk_shader_init(FFVulkanContext *s, FFVulkanShader *shd, const char *name, GLSLC(0, ); if (s->extensions & FF_VK_EXT_DESCRIPTOR_BUFFER) { + GLSLC(0, #extension GL_EXT_scalar_block_layout : require ); GLSLC(0, #extension GL_EXT_buffer_reference : require ); GLSLC(0, #extension GL_EXT_buffer_reference2 : require ); } From patchwork Sun Sep 29 09:42:52 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Lynne X-Patchwork-Id: 51923 Delivered-To: ffmpegpatchwork2@gmail.com Received: by 2002:a59:d8ca:0:b0:48e:c0f8:d0de with SMTP id dy10csp1341148vqb; Sun, 29 Sep 2024 02:43:41 -0700 (PDT) X-Forwarded-Encrypted: i=2; AJvYcCUggZlVCK1Vn9mtoFjphohY28a4oVPH02GxkZppXrUIUZuEUlX7DdReKnCZlKFrrviFCUC2/O2BZLNlWJkZ85KD@gmail.com X-Google-Smtp-Source: AGHT+IFxV4lZt7tkxi54SO6/m+z54UadHOJLp2Gi2SqSAjjaAxNjMBCrNDGiAxbwbqHTWofx2bCZ X-Received: by 2002:a17:907:86a1:b0:a8a:5ff9:bcd1 with SMTP id a640c23a62f3a-a93c4915be0mr970429666b.21.1727603021119; Sun, 29 Sep 2024 02:43:41 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1727603021; cv=none; d=google.com; s=arc-20240605; b=U8fAISEsywiBvKAvtpXeymiO2Rhk/yjvXA3dd5nhVrEdNfHNZKU67ak1+BUz+KLivc bD+x5BDP81Hd9jlfifGLZvd4rho6t9FUgv7R1xRXZmRr7xZkIdq9C9eAM/2Ge37+XjJs O0ZT2UWUf2XHvUSkVMiMpL0c68+jhSHGMDY8HEA5QJbgtJpv6qELmDnBgkFYCsVygb0Z Wq68XNXMIf/MB1Ji1biqdkgYuDz98heztnYW3i17igV/kJFVPHKJRJnyp7rXiIjWGtC9 x0A7JYivL4pSglPWXCic1nXtGMnxdBK/Vz/W2KGIq1seMZJLVLCZiwUxRgHFwVpdpWdB U9CA== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20240605; h=sender:errors-to:content-transfer-encoding:cc:reply-to:from :list-subscribe:list-help:list-post:list-archive:list-unsubscribe :list-id:precedence:subject:mime-version:references:in-reply-to :message-id:date:to:delivered-to; bh=iZNUUCVLwJbt5dgrrGSR9p6TbAoAq+mzJX16cpfuExo=; fh=nenT92/WZoU6unXd3J6UhGUdod4piddKfVtctNBOh6k=; b=CimcdQj6rrK8L/h82ftRsQTSQb1K78egM88LFrzbW9Eyh0IUKQurmbtTWYHYl79cb2 fWRpOgBv+DPSeINAjJ+3/G9Mg94AW3jzTlBMWR71VXy0lZOlpErNAM4oENbNzpDWsFcM /E8kerDLnmOm2wkS8JdfO8uw/wJTNa3OI9n6Q9AckBqJjhuyWCJfrzK+yeLuSqFOvJhO M3b4AnlcbGPkXgUejyluH/cT0GpIj6bFlohWM8z1ztzAQM5KR4ryeKXFqCF8NG++wQ5C Rc7ErvASumqtCdyxiPUXrMTVxYMnfqlTn82UfAZaIhr9f3wdKPOrvSVlgtn81N1ZN+gE NdLw==; dara=google.com ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: domain of ffmpeg-devel-bounces@ffmpeg.org designates 79.124.17.100 as permitted sender) smtp.mailfrom=ffmpeg-devel-bounces@ffmpeg.org Return-Path: Received: from ffbox0-bg.mplayerhq.hu (ffbox0-bg.ffmpeg.org. [79.124.17.100]) by mx.google.com with ESMTP id a640c23a62f3a-a93c29ac3dfsi434548766b.278.2024.09.29.02.43.40; Sun, 29 Sep 2024 02:43:41 -0700 (PDT) Received-SPF: pass (google.com: domain of ffmpeg-devel-bounces@ffmpeg.org designates 79.124.17.100 as permitted sender) client-ip=79.124.17.100; Authentication-Results: mx.google.com; spf=pass (google.com: domain of ffmpeg-devel-bounces@ffmpeg.org designates 79.124.17.100 as permitted sender) smtp.mailfrom=ffmpeg-devel-bounces@ffmpeg.org Received: from [127.0.1.1] (localhost [127.0.0.1]) by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTP id E43C768DA6B; Sun, 29 Sep 2024 12:43:10 +0300 (EEST) X-Original-To: ffmpeg-devel@ffmpeg.org Delivered-To: ffmpeg-devel@ffmpeg.org Received: from vidala.lynne.ee (vidala.pars.ee [116.203.72.101]) by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTPS id 9816768DA01 for ; Sun, 29 Sep 2024 12:43:00 +0300 (EEST) To: ffmpeg-devel@ffmpeg.org Date: Sun, 29 Sep 2024 11:42:52 +0200 Message-ID: <20240929094256.396352-5-dev@lynne.ee> X-Mailer: git-send-email 2.45.2.753.g447d99e1c3b In-Reply-To: <20240929094256.396352-1-dev@lynne.ee> References: <20240929094256.396352-1-dev@lynne.ee> MIME-Version: 1.0 Subject: [FFmpeg-devel] [PATCH 5/5] vulkan: check if current buffer has finished execution before picking another X-BeenThere: ffmpeg-devel@ffmpeg.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: FFmpeg development discussions and patches List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Lynne via ffmpeg-devel From: Lynne Reply-To: FFmpeg development discussions and patches Cc: Lynne Errors-To: ffmpeg-devel-bounces@ffmpeg.org Sender: "ffmpeg-devel" X-TUID: ucJCO5/5pvtG This saves resources, as dependencies are freed/reclaimed with a lower latency, and provies a speedup. --- libavcodec/vulkan_decode.c | 4 ++-- libavcodec/vulkan_encode.c | 2 +- libavfilter/vf_nlmeans_vulkan.c | 2 +- libavfilter/vulkan_filter.c | 6 +++--- libavutil/hwcontext_vulkan.c | 6 +++--- libavutil/vulkan.c | 15 +++++++++++---- libavutil/vulkan.h | 2 +- libavutil/vulkan_functions.h | 1 + 8 files changed, 23 insertions(+), 15 deletions(-) diff --git a/libavcodec/vulkan_decode.c b/libavcodec/vulkan_decode.c index a8b906a9dd..7d7295e05e 100644 --- a/libavcodec/vulkan_decode.c +++ b/libavcodec/vulkan_decode.c @@ -293,7 +293,7 @@ void ff_vk_decode_flush(AVCodecContext *avctx) }; VkCommandBuffer cmd_buf; - FFVkExecContext *exec = ff_vk_exec_get(&dec->exec_pool); + FFVkExecContext *exec = ff_vk_exec_get(&ctx->s, &dec->exec_pool); int had_submission = exec->had_submission; ff_vk_exec_start(&ctx->s, exec); cmd_buf = exec->buf; @@ -345,7 +345,7 @@ int ff_vk_decode_frame(AVCodecContext *avctx, size_t data_size = FFALIGN(vp->slices_size, ctx->caps.minBitstreamBufferSizeAlignment); - FFVkExecContext *exec = ff_vk_exec_get(&dec->exec_pool); + FFVkExecContext *exec = ff_vk_exec_get(&ctx->s, &dec->exec_pool); /* The current decoding reference has to be bound as an inactive reference */ VkVideoReferenceSlotInfoKHR *cur_vk_ref; diff --git a/libavcodec/vulkan_encode.c b/libavcodec/vulkan_encode.c index d187b7cdd3..6d1743c7d7 100644 --- a/libavcodec/vulkan_encode.c +++ b/libavcodec/vulkan_encode.c @@ -339,7 +339,7 @@ static int vulkan_encode_issue(AVCodecContext *avctx, size_align); /* Start command buffer recording */ - exec = vp->exec = ff_vk_exec_get(&ctx->enc_pool); + exec = vp->exec = ff_vk_exec_get(&ctx->s, &ctx->enc_pool); ff_vk_exec_start(&ctx->s, exec); cmd_buf = exec->buf; diff --git a/libavfilter/vf_nlmeans_vulkan.c b/libavfilter/vf_nlmeans_vulkan.c index 05c752925e..b413194035 100644 --- a/libavfilter/vf_nlmeans_vulkan.c +++ b/libavfilter/vf_nlmeans_vulkan.c @@ -836,7 +836,7 @@ static int nlmeans_vulkan_filter_frame(AVFilterLink *link, AVFrame *in) } /* Execution context */ - exec = ff_vk_exec_get(&s->e); + exec = ff_vk_exec_get(&s->vkctx, &s->e); ff_vk_exec_start(vkctx, exec); /* Dependencies */ diff --git a/libavfilter/vulkan_filter.c b/libavfilter/vulkan_filter.c index 5cee4572e6..8d9b416d6a 100644 --- a/libavfilter/vulkan_filter.c +++ b/libavfilter/vulkan_filter.c @@ -249,7 +249,7 @@ int ff_vk_filter_process_simple(FFVulkanContext *vkctx, FFVkExecPool *e, int nb_img_bar = 0; /* Update descriptors and init the exec context */ - FFVkExecContext *exec = ff_vk_exec_get(e); + FFVkExecContext *exec = ff_vk_exec_get(vkctx, e); ff_vk_exec_start(vkctx, exec); RET(ff_vk_exec_add_dep_frame(vkctx, exec, out_f, @@ -321,7 +321,7 @@ int ff_vk_filter_process_2pass(FFVulkanContext *vkctx, FFVkExecPool *e, int nb_img_bar = 0; /* Update descriptors and init the exec context */ - FFVkExecContext *exec = ff_vk_exec_get(e); + FFVkExecContext *exec = ff_vk_exec_get(vkctx, e); ff_vk_exec_start(vkctx, exec); RET(ff_vk_exec_add_dep_frame(vkctx, exec, in, @@ -409,7 +409,7 @@ int ff_vk_filter_process_Nin(FFVulkanContext *vkctx, FFVkExecPool *e, int nb_img_bar = 0; /* Update descriptors and init the exec context */ - FFVkExecContext *exec = ff_vk_exec_get(e); + FFVkExecContext *exec = ff_vk_exec_get(vkctx, e); ff_vk_exec_start(vkctx, exec); /* Add deps and create temporary imageviews */ diff --git a/libavutil/hwcontext_vulkan.c b/libavutil/hwcontext_vulkan.c index 3a3aff75c0..d6500de677 100644 --- a/libavutil/hwcontext_vulkan.c +++ b/libavutil/hwcontext_vulkan.c @@ -2254,7 +2254,7 @@ static int prepare_frame(AVHWFramesContext *hwfc, FFVkExecPool *ectx, }; VkCommandBuffer cmd_buf; - FFVkExecContext *exec = ff_vk_exec_get(ectx); + FFVkExecContext *exec = ff_vk_exec_get(&p->vkctx, ectx); cmd_buf = exec->buf; ff_vk_exec_start(&p->vkctx, exec); @@ -3191,7 +3191,7 @@ static int vulkan_map_from_drm_frame_sync(AVHWFramesContext *hwfc, AVFrame *dst, } } - exec = ff_vk_exec_get(&fp->compute_exec); + exec = ff_vk_exec_get(&p->vkctx, &fp->compute_exec); cmd_buf = exec->buf; ff_vk_exec_start(&p->vkctx, exec); @@ -4099,7 +4099,7 @@ static int vulkan_transfer_frame(AVHWFramesContext *hwfc, } } - exec = ff_vk_exec_get(&fp->upload_exec); + exec = ff_vk_exec_get(&p->vkctx, &fp->upload_exec); cmd_buf = exec->buf; ff_vk_exec_start(&p->vkctx, exec); diff --git a/libavutil/vulkan.c b/libavutil/vulkan.c index ab2519bf35..849199ab4f 100644 --- a/libavutil/vulkan.c +++ b/libavutil/vulkan.c @@ -482,11 +482,18 @@ VkResult ff_vk_exec_get_query(FFVulkanContext *s, FFVkExecContext *e, pool->qd_size, qf); } -FFVkExecContext *ff_vk_exec_get(FFVkExecPool *pool) +FFVkExecContext *ff_vk_exec_get(FFVulkanContext *s, FFVkExecPool *pool) { - uint32_t idx = pool->idx++; - idx %= pool->pool_size; - return &pool->contexts[idx]; + FFVulkanFunctions *vk = &s->vkfn; + FFVkExecContext *e = &pool->contexts[pool->idx]; + + /* Check if last submission has already finished. + * If so, don't waste resources and reuse the same buffer. */ + if (vk->GetFenceStatus(s->hwctx->act_dev, e->fence) == VK_SUCCESS) + return e; + + pool->idx = (pool->idx + 1) % pool->pool_size; + return &pool->contexts[pool->idx]; } void ff_vk_exec_wait(FFVulkanContext *s, FFVkExecContext *e) diff --git a/libavutil/vulkan.h b/libavutil/vulkan.h index 47684e600d..8d60fae670 100644 --- a/libavutil/vulkan.h +++ b/libavutil/vulkan.h @@ -387,7 +387,7 @@ void ff_vk_exec_pool_free(FFVulkanContext *s, FFVkExecPool *pool); /** * Retrieve an execution pool. Threadsafe. */ -FFVkExecContext *ff_vk_exec_get(FFVkExecPool *pool); +FFVkExecContext *ff_vk_exec_get(FFVulkanContext *s, FFVkExecPool *pool); /** * Performs nb_queries queries and returns their results and statuses. diff --git a/libavutil/vulkan_functions.h b/libavutil/vulkan_functions.h index 91dd8b91e0..90e4d0004d 100644 --- a/libavutil/vulkan_functions.h +++ b/libavutil/vulkan_functions.h @@ -110,6 +110,7 @@ typedef enum FFVulkanExtensions { /* Fences */ \ MACRO(1, 1, FF_VK_EXT_NO_FLAG, CreateFence) \ MACRO(1, 1, FF_VK_EXT_NO_FLAG, WaitForFences) \ + MACRO(1, 1, FF_VK_EXT_NO_FLAG, GetFenceStatus) \ MACRO(1, 1, FF_VK_EXT_NO_FLAG, ResetFences) \ MACRO(1, 1, FF_VK_EXT_NO_FLAG, DestroyFence) \ \