diff --git a/src/amd/vulkan/meta/radv_meta_bufimage.c b/src/amd/vulkan/meta/radv_meta_bufimage.c index 9ffbb477a00..0ed95c64714 100644 --- a/src/amd/vulkan/meta/radv_meta_bufimage.c +++ b/src/amd/vulkan/meta/radv_meta_bufimage.c @@ -56,110 +56,77 @@ build_nir_itob_compute_shader(struct radv_device *dev, bool is_3d) } static VkResult -create_itob_layout(struct radv_device *device) -{ - VkResult result = VK_SUCCESS; - - if (!device->meta_state.itob.img_ds_layout) { - const VkDescriptorSetLayoutBinding bindings[] = { - { - .binding = 0, - .descriptorType = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, - .descriptorCount = 1, - .stageFlags = VK_SHADER_STAGE_COMPUTE_BIT, - }, - { - .binding = 1, - .descriptorType = VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER, - .descriptorCount = 1, - .stageFlags = VK_SHADER_STAGE_COMPUTE_BIT, - }, - }; - - result = radv_meta_create_descriptor_set_layout(device, 2, bindings, &device->meta_state.itob.img_ds_layout); - if (result != VK_SUCCESS) - return result; - } - - if (!device->meta_state.itob.img_p_layout) { - const VkPushConstantRange pc_range = { - .stageFlags = VK_SHADER_STAGE_COMPUTE_BIT, - .size = 16, - }; - - result = radv_meta_create_pipeline_layout(device, &device->meta_state.itob.img_ds_layout, 1, &pc_range, - &device->meta_state.itob.img_p_layout); - } - - return result; -} - -static VkResult -create_itob_pipeline(struct radv_device *device, bool is_3d, VkPipeline *pipeline) +get_itob_pipeline(struct radv_device *device, const struct radv_image *image, VkPipeline *pipeline_out, + VkPipelineLayout *layout_out) { + const bool is_3d = image->vk.image_type == VK_IMAGE_TYPE_3D; + char key_data[64]; VkResult result; - result = create_itob_layout(device); + snprintf(key_data, sizeof(key_data), "radv-itob-%d", is_3d); + + const VkDescriptorSetLayoutBinding bindings[] = { + { + .binding = 0, + .descriptorType = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, + .descriptorCount = 1, + .stageFlags = VK_SHADER_STAGE_COMPUTE_BIT, + }, + { + .binding = 1, + .descriptorType = VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER, + .descriptorCount = 1, + .stageFlags = VK_SHADER_STAGE_COMPUTE_BIT, + }, + }; + + const VkDescriptorSetLayoutCreateInfo desc_info = { + .sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO, + .flags = VK_DESCRIPTOR_SET_LAYOUT_CREATE_PUSH_DESCRIPTOR_BIT, + .bindingCount = 2, + .pBindings = bindings, + }; + + const VkPushConstantRange pc_range = { + .stageFlags = VK_SHADER_STAGE_COMPUTE_BIT, + .size = 16, + }; + + result = vk_meta_get_pipeline_layout(&device->vk, &device->meta_state.device, &desc_info, &pc_range, key_data, + strlen(key_data), layout_out); if (result != VK_SUCCESS) return result; + VkPipeline pipeline_from_cache = vk_meta_lookup_pipeline(&device->meta_state.device, key_data, strlen(key_data)); + if (pipeline_from_cache != VK_NULL_HANDLE) { + *pipeline_out = pipeline_from_cache; + return VK_SUCCESS; + } + nir_shader *cs = build_nir_itob_compute_shader(device, is_3d); - result = radv_meta_create_compute_pipeline(device, cs, device->meta_state.itob.img_p_layout, pipeline); + const VkPipelineShaderStageCreateInfo stage_info = { + .sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO, + .stage = VK_SHADER_STAGE_COMPUTE_BIT, + .module = vk_shader_module_handle_from_nir(cs), + .pName = "main", + .pSpecializationInfo = NULL, + }; + + const VkComputePipelineCreateInfo pipeline_info = { + .sType = VK_STRUCTURE_TYPE_COMPUTE_PIPELINE_CREATE_INFO, + .stage = stage_info, + .flags = 0, + .layout = *layout_out, + }; + + result = vk_meta_create_compute_pipeline(&device->vk, &device->meta_state.device, &pipeline_info, key_data, + strlen(key_data), pipeline_out); ralloc_free(cs); return result; } -static VkResult -get_itob_pipeline(struct radv_device *device, const struct radv_image *image, VkPipeline *pipeline_out) -{ - struct radv_meta_state *state = &device->meta_state; - const bool is_3d = image->vk.image_type == VK_IMAGE_TYPE_3D; - VkResult result = VK_SUCCESS; - VkPipeline *pipeline; - - mtx_lock(&state->mtx); - - pipeline = is_3d ? &state->itob.pipeline_3d : &state->itob.pipeline; - if (!*pipeline) { - result = create_itob_pipeline(device, is_3d, pipeline); - if (result != VK_SUCCESS) - goto fail; - } - - *pipeline_out = *pipeline; - -fail: - mtx_unlock(&state->mtx); - return result; -} - -/* Image to buffer - don't write use image accessors */ -static VkResult -radv_device_init_meta_itob_state(struct radv_device *device) -{ - VkResult result; - - result = create_itob_pipeline(device, false, &device->meta_state.itob.pipeline); - if (result != VK_SUCCESS) - return result; - - return create_itob_pipeline(device, true, &device->meta_state.itob.pipeline_3d); -} - -static void -radv_device_finish_meta_itob_state(struct radv_device *device) -{ - struct radv_meta_state *state = &device->meta_state; - - radv_DestroyPipelineLayout(radv_device_to_handle(device), state->itob.img_p_layout, &state->alloc); - device->vk.dispatch_table.DestroyDescriptorSetLayout(radv_device_to_handle(device), state->itob.img_ds_layout, - &state->alloc); - radv_DestroyPipeline(radv_device_to_handle(device), state->itob.pipeline, &state->alloc); - radv_DestroyPipeline(radv_device_to_handle(device), state->itob.pipeline_3d, &state->alloc); -} - static nir_shader * build_nir_btoi_compute_shader(struct radv_device *dev, bool is_3d) { @@ -1061,7 +1028,6 @@ radv_device_finish_meta_cleari_r32g32b32_state(struct radv_device *device) void radv_device_finish_meta_bufimage_state(struct radv_device *device) { - radv_device_finish_meta_itob_state(device); radv_device_finish_meta_btoi_state(device); radv_device_finish_meta_btoi_r32g32b32_state(device); radv_device_finish_meta_itoi_state(device); @@ -1078,10 +1044,6 @@ radv_device_init_meta_bufimage_state(struct radv_device *device, bool on_demand) if (on_demand) return VK_SUCCESS; - result = radv_device_init_meta_itob_state(device); - if (result != VK_SUCCESS) - return result; - result = radv_device_init_meta_btoi_state(device); if (result != VK_SUCCESS) return result; @@ -1313,13 +1275,28 @@ get_image_stride_for_r32g32b32(struct radv_cmd_buffer *cmd_buffer, struct radv_m return stride; } -static void -itob_bind_descriptors(struct radv_cmd_buffer *cmd_buffer, struct radv_image_view *src, struct radv_buffer_view *dst) +void +radv_meta_image_to_buffer(struct radv_cmd_buffer *cmd_buffer, struct radv_meta_blit2d_surf *src, + struct radv_meta_blit2d_buffer *dst, struct radv_meta_blit2d_rect *rect) { struct radv_device *device = radv_cmd_buffer_device(cmd_buffer); + struct radv_image_view src_view; + struct radv_buffer_view dst_view; + VkPipelineLayout layout; + VkPipeline pipeline; + VkResult result; + + result = get_itob_pipeline(device, src->image, &pipeline, &layout); + if (result != VK_SUCCESS) { + vk_command_buffer_set_error(&cmd_buffer->vk, result); + return; + } + + create_iview(cmd_buffer, src, &src_view, VK_FORMAT_UNDEFINED, src->aspect_mask); + create_bview(cmd_buffer, dst->buffer, dst->offset, dst->format, &dst_view); radv_meta_push_descriptor_set( - cmd_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, device->meta_state.itob.img_p_layout, 0, 2, + cmd_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, layout, 0, 2, (VkWriteDescriptorSet[]){{.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET, .dstBinding = 0, .dstArrayElement = 0, @@ -1329,7 +1306,7 @@ itob_bind_descriptors(struct radv_cmd_buffer *cmd_buffer, struct radv_image_view (VkDescriptorImageInfo[]){ { .sampler = VK_NULL_HANDLE, - .imageView = radv_image_view_to_handle(src), + .imageView = radv_image_view_to_handle(&src_view), .imageLayout = VK_IMAGE_LAYOUT_GENERAL, }, }}, @@ -1339,35 +1316,14 @@ itob_bind_descriptors(struct radv_cmd_buffer *cmd_buffer, struct radv_image_view .dstArrayElement = 0, .descriptorCount = 1, .descriptorType = VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER, - .pTexelBufferView = (VkBufferView[]){radv_buffer_view_to_handle(dst)}, + .pTexelBufferView = (VkBufferView[]){radv_buffer_view_to_handle(&dst_view)}, }}); -} - -void -radv_meta_image_to_buffer(struct radv_cmd_buffer *cmd_buffer, struct radv_meta_blit2d_surf *src, - struct radv_meta_blit2d_buffer *dst, struct radv_meta_blit2d_rect *rect) -{ - struct radv_device *device = radv_cmd_buffer_device(cmd_buffer); - struct radv_image_view src_view; - struct radv_buffer_view dst_view; - VkPipeline pipeline; - VkResult result; - - result = get_itob_pipeline(device, src->image, &pipeline); - if (result != VK_SUCCESS) { - vk_command_buffer_set_error(&cmd_buffer->vk, result); - return; - } - - create_iview(cmd_buffer, src, &src_view, VK_FORMAT_UNDEFINED, src->aspect_mask); - create_bview(cmd_buffer, dst->buffer, dst->offset, dst->format, &dst_view); - itob_bind_descriptors(cmd_buffer, &src_view, &dst_view); radv_CmdBindPipeline(radv_cmd_buffer_to_handle(cmd_buffer), VK_PIPELINE_BIND_POINT_COMPUTE, pipeline); unsigned push_constants[4] = {rect->src_x, rect->src_y, src->layer, dst->pitch}; - vk_common_CmdPushConstants(radv_cmd_buffer_to_handle(cmd_buffer), device->meta_state.itob.img_p_layout, - VK_SHADER_STAGE_COMPUTE_BIT, 0, 16, push_constants); + vk_common_CmdPushConstants(radv_cmd_buffer_to_handle(cmd_buffer), layout, VK_SHADER_STAGE_COMPUTE_BIT, 0, 16, + push_constants); radv_unaligned_dispatch(cmd_buffer, rect->width, rect->height, 1); fixup_gfx9_cs_copy(cmd_buffer, dst, src, rect, false); diff --git a/src/amd/vulkan/radv_device.h b/src/amd/vulkan/radv_device.h index 3a6e56f87c5..21ec7ae55cc 100644 --- a/src/amd/vulkan/radv_device.h +++ b/src/amd/vulkan/radv_device.h @@ -141,12 +141,6 @@ struct radv_meta_state { VkPipeline stencil_only_pipeline[5]; } blit2d[MAX_SAMPLES_LOG2]; - struct { - VkPipelineLayout img_p_layout; - VkDescriptorSetLayout img_ds_layout; - VkPipeline pipeline; - VkPipeline pipeline_3d; - } itob; struct { VkPipelineLayout img_p_layout; VkDescriptorSetLayout img_ds_layout;