On Wednesday 05 April 2017, Bas Nieuwenhuizen wrote: > Could you move the declarations you add in radv_descriptor_set.h to > radv_private.h? I'd like to keep it limited to whatever is necessary > for the compiler, which is only the set & pipeline layouts. You could > just put it next to the radv_descriptor_set declaration.
Will do. > Otherwise, nice work! The series is > > Reviewed-by: Bas Nieuwenhuizen <b...@basnieuwenhuizen.nl> > > Did you have push access? Yes; I'll push the series in a couple of hours with a v2 of patch 4. Thanks for the review! > On Tue, Apr 4, 2017 at 11:29 PM, Fredrik Höglund <fred...@kde.org> wrote: > > All offsets and strides are precomputed by > > radv_CreateDescriptorUpdateTemplateKHR and stored in the template. > > > > Signed-off-by: Fredrik Höglund <fred...@kde.org> > > --- > > src/amd/vulkan/radv_cmd_buffer.c | 24 +++++ > > src/amd/vulkan/radv_descriptor_set.c | 163 > > +++++++++++++++++++++++++++++++++ > > src/amd/vulkan/radv_descriptor_set.h | 31 +++++++ > > src/amd/vulkan/radv_device.c | 4 + > > src/amd/vulkan/radv_entrypoints_gen.py | 1 + > > src/amd/vulkan/radv_private.h | 8 ++ > > 6 files changed, 231 insertions(+) > > > > diff --git a/src/amd/vulkan/radv_cmd_buffer.c > > b/src/amd/vulkan/radv_cmd_buffer.c > > index 46c139a8fc..992dc123a2 100644 > > --- a/src/amd/vulkan/radv_cmd_buffer.c > > +++ b/src/amd/vulkan/radv_cmd_buffer.c > > @@ -1988,6 +1988,30 @@ void radv_CmdPushDescriptorSetKHR( > > cmd_buffer->state.push_descriptors_dirty = true; > > } > > > > +void radv_CmdPushDescriptorSetWithTemplateKHR( > > + VkCommandBuffer commandBuffer, > > + VkDescriptorUpdateTemplateKHR > > descriptorUpdateTemplate, > > + VkPipelineLayout _layout, > > + uint32_t set, > > + const void* pData) > > +{ > > + RADV_FROM_HANDLE(radv_cmd_buffer, cmd_buffer, commandBuffer); > > + RADV_FROM_HANDLE(radv_pipeline_layout, layout, _layout); > > + struct radv_descriptor_set *push_set = > > &cmd_buffer->push_descriptors.set; > > + > > + assert(layout->set[set].layout->flags & > > VK_DESCRIPTOR_SET_LAYOUT_CREATE_PUSH_DESCRIPTOR_BIT_KHR); > > + > > + if (!radv_init_push_descriptor_set(cmd_buffer, push_set, > > layout->set[set].layout)) > > + return; > > + > > + radv_update_descriptor_set_with_template(cmd_buffer->device, > > cmd_buffer, push_set, > > + descriptorUpdateTemplate, > > pData); > > + > > + cmd_buffer->state.descriptors[set] = push_set; > > + cmd_buffer->state.descriptors_dirty |= (1 << set); > > + cmd_buffer->state.push_descriptors_dirty = true; > > +} > > + > > void radv_CmdPushConstants(VkCommandBuffer commandBuffer, > > VkPipelineLayout layout, > > VkShaderStageFlags stageFlags, > > diff --git a/src/amd/vulkan/radv_descriptor_set.c > > b/src/amd/vulkan/radv_descriptor_set.c > > index 0ff9aa206d..c2bf006f34 100644 > > --- a/src/amd/vulkan/radv_descriptor_set.c > > +++ b/src/amd/vulkan/radv_descriptor_set.c > > @@ -742,3 +742,166 @@ void radv_UpdateDescriptorSets( > > radv_update_descriptor_sets(device, NULL, VK_NULL_HANDLE, > > descriptorWriteCount, pDescriptorWrites, > > descriptorCopyCount, pDescriptorCopies); > > } > > + > > +VkResult radv_CreateDescriptorUpdateTemplateKHR(VkDevice _device, > > + const > > VkDescriptorUpdateTemplateCreateInfoKHR *pCreateInfo, > > + const > > VkAllocationCallbacks *pAllocator, > > + > > VkDescriptorUpdateTemplateKHR *pDescriptorUpdateTemplate) > > +{ > > + RADV_FROM_HANDLE(radv_device, device, _device); > > + RADV_FROM_HANDLE(radv_descriptor_set_layout, set_layout, > > pCreateInfo->descriptorSetLayout); > > + const uint32_t entry_count = > > pCreateInfo->descriptorUpdateEntryCount; > > + const size_t size = sizeof(struct radv_descriptor_update_template) + > > + sizeof(struct radv_descriptor_update_template_entry) * > > entry_count; > > + struct radv_descriptor_update_template *templ; > > + uint32_t i; > > + > > + templ = vk_alloc2(&device->alloc, pAllocator, size, 8, > > VK_SYSTEM_ALLOCATION_SCOPE_OBJECT); > > + if (!templ) > > + return vk_error(VK_ERROR_OUT_OF_HOST_MEMORY); > > + > > + templ->entry_count = entry_count; > > + > > + for (i = 0; i < entry_count; i++) { > > + const VkDescriptorUpdateTemplateEntryKHR *entry = > > &pCreateInfo->pDescriptorUpdateEntries[i]; > > + const struct radv_descriptor_set_binding_layout > > *binding_layout = > > + set_layout->binding + entry->dstBinding; > > + const uint32_t buffer_offset = > > binding_layout->buffer_offset + > > + binding_layout->buffer_count * > > entry->dstArrayElement; > > + uint32_t *immutable_samplers = NULL; > > + uint16_t dst_offset; > > + uint16_t dst_stride; > > + > > + /* dst_offset is an offset into dynamic_descriptors when > > the descriptor > > + is dynamic, and an offset into mapped_ptr otherwise */ > > + switch (entry->descriptorType) { > > + case VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC: > > + case VK_DESCRIPTOR_TYPE_STORAGE_BUFFER_DYNAMIC: > > + assert(pCreateInfo->templateType == > > VK_DESCRIPTOR_UPDATE_TEMPLATE_TYPE_DESCRIPTOR_SET_KHR); > > + dst_offset = binding_layout->dynamic_offset_offset > > + entry->dstArrayElement; > > + dst_stride = 0; /* Not used */ > > + break; > > + default: > > + switch (entry->descriptorType) { > > + case VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER: > > + case VK_DESCRIPTOR_TYPE_SAMPLER: > > + /* Immutable samplers are copied into push > > descriptors when they are pushed */ > > + if (pCreateInfo->templateType == > > VK_DESCRIPTOR_UPDATE_TEMPLATE_TYPE_PUSH_DESCRIPTORS_KHR && > > + binding_layout->immutable_samplers && > > !binding_layout->immutable_samplers_equal) > > + immutable_samplers = > > binding_layout->immutable_samplers + entry->dstArrayElement * 4; > > + break; > > + default: > > + break; > > + } > > + dst_offset = binding_layout->offset / 4 + > > binding_layout->size * entry->dstArrayElement / 4; > > + dst_stride = binding_layout->size / 4; > > + break; > > + } > > + > > + templ->entry[i] = (struct > > radv_descriptor_update_template_entry) { > > + .descriptor_type = entry->descriptorType, > > + .descriptor_count = entry->descriptorCount, > > + .src_offset = entry->offset, > > + .src_stride = entry->stride, > > + .dst_offset = dst_offset, > > + .dst_stride = dst_stride, > > + .buffer_offset = buffer_offset, > > + .buffer_count = binding_layout->buffer_count, > > + .has_sampler = !binding_layout->immutable_samplers, > > + .immutable_samplers = immutable_samplers > > + }; > > + } > > + > > + *pDescriptorUpdateTemplate = > > radv_descriptor_update_template_to_handle(templ); > > + return VK_SUCCESS; > > +} > > + > > +void radv_DestroyDescriptorUpdateTemplateKHR(VkDevice _device, > > + VkDescriptorUpdateTemplateKHR > > descriptorUpdateTemplate, > > + const VkAllocationCallbacks > > *pAllocator) > > +{ > > + RADV_FROM_HANDLE(radv_device, device, _device); > > + RADV_FROM_HANDLE(radv_descriptor_update_template, templ, > > descriptorUpdateTemplate); > > + > > + if (!templ) > > + return; > > + > > + vk_free2(&device->alloc, pAllocator, templ); > > +} > > + > > +void radv_update_descriptor_set_with_template(struct radv_device *device, > > + struct radv_cmd_buffer > > *cmd_buffer, > > + struct radv_descriptor_set > > *set, > > + > > VkDescriptorUpdateTemplateKHR descriptorUpdateTemplate, > > + const void *pData) > > +{ > > + RADV_FROM_HANDLE(radv_descriptor_update_template, templ, > > descriptorUpdateTemplate); > > + uint32_t i; > > + > > + for (i = 0; i < templ->entry_count; ++i) { > > + struct radeon_winsys_bo **buffer_list = set->descriptors + > > templ->entry[i].buffer_offset; > > + uint32_t *pDst = set->mapped_ptr + > > templ->entry[i].dst_offset; > > + const uint8_t *pSrc = ((const uint8_t *) pData) + > > templ->entry[i].src_offset; > > + uint32_t j; > > + > > + for (j = 0; j < templ->entry[i].descriptor_count; ++j) { > > + switch (templ->entry[i].descriptor_type) { > > + case VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC: > > + case VK_DESCRIPTOR_TYPE_STORAGE_BUFFER_DYNAMIC: { > > + const unsigned idx = > > templ->entry[i].dst_offset + j; > > + assert(!(set->layout->flags & > > VK_DESCRIPTOR_SET_LAYOUT_CREATE_PUSH_DESCRIPTOR_BIT_KHR)); > > + write_dynamic_buffer_descriptor(device, > > set->dynamic_descriptors + idx, > > + > > buffer_list, (struct VkDescriptorBufferInfo *) pSrc); > > + break; > > + } > > + case VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER: > > + case VK_DESCRIPTOR_TYPE_STORAGE_BUFFER: > > + write_buffer_descriptor(device, cmd_buffer, > > pDst, buffer_list, > > + (struct > > VkDescriptorBufferInfo *) pSrc); > > + break; > > + case VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER: > > + case VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER: > > + write_texel_buffer_descriptor(device, > > cmd_buffer, pDst, buffer_list, > > + > > *(VkBufferView *) pSrc); > > + break; > > + case VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE: > > + case VK_DESCRIPTOR_TYPE_STORAGE_IMAGE: > > + case VK_DESCRIPTOR_TYPE_INPUT_ATTACHMENT: > > + write_image_descriptor(device, cmd_buffer, > > pDst, buffer_list, > > + (struct > > VkDescriptorImageInfo *) pSrc); > > + break; > > + case VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER: > > + > > write_combined_image_sampler_descriptor(device, cmd_buffer, pDst, > > buffer_list, > > + > > (struct VkDescriptorImageInfo *) pSrc, > > + > > templ->entry[i].has_sampler); > > + if (templ->entry[i].immutable_samplers) > > + memcpy(pDst + 16, > > templ->entry[i].immutable_samplers + 4 * j, 16); > > + break; > > + case VK_DESCRIPTOR_TYPE_SAMPLER: > > + if (templ->entry[i].has_sampler) > > + write_sampler_descriptor(device, > > pDst, > > + (struct > > VkDescriptorImageInfo *) pSrc); > > + else if (templ->entry[i].immutable_samplers) > > + memcpy(pDst, > > templ->entry[i].immutable_samplers + 4 * j, 16); > > + break; > > + default: > > + unreachable("unimplemented descriptor > > type"); > > + break; > > + } > > + pSrc += templ->entry[i].src_stride; > > + pDst += templ->entry[i].dst_stride; > > + buffer_list += templ->entry[i].buffer_count; > > + } > > + } > > +} > > + > > +void radv_UpdateDescriptorSetWithTemplateKHR(VkDevice _device, > > + VkDescriptorSet descriptorSet, > > + VkDescriptorUpdateTemplateKHR > > descriptorUpdateTemplate, > > + const void *pData) > > +{ > > + RADV_FROM_HANDLE(radv_device, device, _device); > > + RADV_FROM_HANDLE(radv_descriptor_set, set, descriptorSet); > > + > > + radv_update_descriptor_set_with_template(device, NULL, set, > > descriptorUpdateTemplate, pData); > > +} > > diff --git a/src/amd/vulkan/radv_descriptor_set.h > > b/src/amd/vulkan/radv_descriptor_set.h > > index b3bbb193e8..49d997fd8a 100644 > > --- a/src/amd/vulkan/radv_descriptor_set.h > > +++ b/src/amd/vulkan/radv_descriptor_set.h > > @@ -86,4 +86,35 @@ struct radv_pipeline_layout { > > unsigned char sha1[20]; > > }; > > > > +struct radv_descriptor_update_template_entry { > > + VkDescriptorType descriptor_type; > > + > > + /* The number of descriptors to update */ > > + uint16_t descriptor_count; > > + > > + /* Into mapped_ptr or dynamic_descriptors, in units of the respective > > array */ > > + uint16_t dst_offset; > > + > > + /* In dwords. Not valid/used for dynamic descriptors */ > > + uint16_t dst_stride; > > + > > + uint16_t buffer_offset; > > + uint16_t buffer_count; > > + > > + /* Only valid for combined image samplers and samplers */ > > + uint16_t has_sampler; > > + > > + /* In bytes */ > > + size_t src_offset; > > + size_t src_stride; > > + > > + /* For push descriptors */ > > + uint32_t *immutable_samplers; > > +}; > > + > > +struct radv_descriptor_update_template { > > + uint32_t entry_count; > > + struct radv_descriptor_update_template_entry entry[0]; > > +}; > > + > > #endif /* RADV_DESCRIPTOR_SET_H */ > > diff --git a/src/amd/vulkan/radv_device.c b/src/amd/vulkan/radv_device.c > > index 059c013f35..9e8faa3da9 100644 > > --- a/src/amd/vulkan/radv_device.c > > +++ b/src/amd/vulkan/radv_device.c > > @@ -92,6 +92,10 @@ static const VkExtensionProperties instance_extensions[] > > = { > > > > static const VkExtensionProperties common_device_extensions[] = { > > { > > + .extensionName = > > VK_KHR_DESCRIPTOR_UPDATE_TEMPLATE_EXTENSION_NAME, > > + .specVersion = 1, > > + }, > > + { > > .extensionName = VK_KHR_INCREMENTAL_PRESENT_EXTENSION_NAME, > > .specVersion = 1, > > }, > > diff --git a/src/amd/vulkan/radv_entrypoints_gen.py > > b/src/amd/vulkan/radv_entrypoints_gen.py > > index 4651c63dcf..3474c789ea 100644 > > --- a/src/amd/vulkan/radv_entrypoints_gen.py > > +++ b/src/amd/vulkan/radv_entrypoints_gen.py > > @@ -30,6 +30,7 @@ max_api_version = 1.0 > > supported_extensions = [ > > 'VK_AMD_draw_indirect_count', > > 'VK_NV_dedicated_allocation', > > + 'VK_KHR_descriptor_update_template', > > 'VK_KHR_get_physical_device_properties2', > > 'VK_KHR_incremental_present', > > 'VK_KHR_maintenance1', > > diff --git a/src/amd/vulkan/radv_private.h b/src/amd/vulkan/radv_private.h > > index e39819fff3..abbb9d69be 100644 > > --- a/src/amd/vulkan/radv_private.h > > +++ b/src/amd/vulkan/radv_private.h > > @@ -1363,6 +1363,13 @@ radv_update_descriptor_sets(struct radv_device > > *device, > > uint32_t descriptorCopyCount, > > const VkCopyDescriptorSet *pDescriptorCopies); > > > > +void > > +radv_update_descriptor_set_with_template(struct radv_device *device, > > + struct radv_cmd_buffer > > *cmd_buffer, > > + struct radv_descriptor_set *set, > > + VkDescriptorUpdateTemplateKHR > > descriptorUpdateTemplate, > > + const void *pData); > > + > > void radv_initialise_cmask(struct radv_cmd_buffer *cmd_buffer, > > struct radv_image *image, uint32_t value); > > void radv_initialize_dcc(struct radv_cmd_buffer *cmd_buffer, > > @@ -1419,6 +1426,7 @@ RADV_DEFINE_NONDISP_HANDLE_CASTS(radv_buffer_view, > > VkBufferView) > > RADV_DEFINE_NONDISP_HANDLE_CASTS(radv_descriptor_pool, VkDescriptorPool) > > RADV_DEFINE_NONDISP_HANDLE_CASTS(radv_descriptor_set, VkDescriptorSet) > > RADV_DEFINE_NONDISP_HANDLE_CASTS(radv_descriptor_set_layout, > > VkDescriptorSetLayout) > > +RADV_DEFINE_NONDISP_HANDLE_CASTS(radv_descriptor_update_template, > > VkDescriptorUpdateTemplateKHR) > > RADV_DEFINE_NONDISP_HANDLE_CASTS(radv_device_memory, VkDeviceMemory) > > RADV_DEFINE_NONDISP_HANDLE_CASTS(radv_fence, VkFence) > > RADV_DEFINE_NONDISP_HANDLE_CASTS(radv_event, VkEvent) > > -- > > 2.11.0 > > > > _______________________________________________ > > mesa-dev mailing list > > mesa-dev@lists.freedesktop.org > > https://lists.freedesktop.org/mailman/listinfo/mesa-dev > _______________________________________________ mesa-dev mailing list mesa-dev@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/mesa-dev