pvr: Fix seg fault in vkAllocateDescriptorSets().

In cases when no immutable samplers were present but sampler
descriptor set layout bindings were, a seg fault was being caused
by an attempt to get the immutable sampler from within the
immutable sampler array while the array was not allocated.

This commit also remove the binding type check since only those
specific types can have immutable samplers. The check is covered
by the descriptor set layout creation and assignment of
has_immutable_samplers.

This commit also makes the immutable samplers const, since they're
meant to be immutable.

This commit also adds has_immutable_samplers field to descriptor
set layout. Previously to check whether immutable
samplers were present or not you'd check for the layout binding's
descriptor count to be 0 and the immutable sampler offset to be 0.
This doesn't tell you everything. If you have a descriptor of the
appropriate type (VK_DESCRIPTOR_TYPE_{COMBINED_,}IMAGE_SAMPLER).
So descriptor count of >1. The offset can be 0 if you don't have
immutable sampler, or have them at the beginning of the immutable
samplers array. So you can't determine if you really have immutable
samplers or not. One could attempt to perform a NULL check on the
array but this would not work in cases where you have following set
layout bindings with immutable samplers as the array stores the
whole layout's immutable samplers.

Signed-off-by: Karmjit Mahil <Karmjit.Mahil@imgtec.com>
Reviewed-by: Rajnesh Kanwal <rajnesh.kanwal@imgtec.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/15688>
This commit is contained in:
Karmjit Mahil 2022-02-25 09:29:57 +00:00 committed by Marge Bot
parent 93ee0c7911
commit 0d25db406b
2 changed files with 6 additions and 7 deletions

View File

@ -201,7 +201,7 @@ pvr_descriptor_set_layout_allocate(struct pvr_device *device,
struct pvr_descriptor_set_layout_binding *bindings;
struct pvr_descriptor_set_layout *layout;
__typeof__(layout->per_stage_descriptor_count) counts;
struct pvr_sampler **immutable_samplers;
const struct pvr_sampler **immutable_samplers;
VK_MULTIALLOC(ma);
vk_multialloc_add(&ma, &layout, __typeof__(*layout), 1);
@ -531,6 +531,7 @@ VkResult pvr_CreateDescriptorSetLayout(
case VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER:
case VK_DESCRIPTOR_TYPE_SAMPLER:
if (binding->pImmutableSamplers && binding->descriptorCount > 0) {
internal_binding->has_immutable_samplers = true;
internal_binding->immutable_samplers_index =
layout->immutable_sampler_count;
@ -1186,9 +1187,7 @@ pvr_descriptor_set_create(struct pvr_device *device,
const struct pvr_descriptor_set_layout_binding *binding =
&layout->bindings[i];
if (binding->descriptor_count == 0 ||
(binding->type != VK_DESCRIPTOR_TYPE_SAMPLER &&
binding->type != VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER))
if (binding->descriptor_count == 0 || !binding->has_immutable_samplers)
continue;
for (uint32_t stage = 0;
@ -1199,7 +1198,7 @@ pvr_descriptor_set_create(struct pvr_device *device,
for (uint32_t j = 0; j < binding->descriptor_count; j++) {
uint32_t idx = binding->immutable_samplers_index + j;
struct pvr_sampler *sampler = layout->immutable_samplers[idx];
const struct pvr_sampler *sampler = layout->immutable_samplers[idx];
unsigned int offset_in_dwords =
pvr_get_descriptor_primary_offset(device,
layout,

View File

@ -396,9 +396,9 @@ struct pvr_descriptor_set_layout_binding {
uint32_t secondary;
} per_stage_offset_in_dwords[PVR_STAGE_ALLOCATION_COUNT];
bool has_immutable_samplers;
/* Index at which the samplers can be found in the descriptor_set_layout.
* 0 when the samplers are at index 0 or no samplers are present.
* Check descriptor_count to differentiate. It will be 0 for 0 samplers.
*/
uint32_t immutable_samplers_index;
};
@ -428,7 +428,7 @@ struct pvr_descriptor_set_layout {
struct pvr_descriptor_set_layout_binding *bindings;
uint32_t immutable_sampler_count;
struct pvr_sampler **immutable_samplers;
const struct pvr_sampler **immutable_samplers;
/* Shader stages requiring access to descriptors in this set. */
VkShaderStageFlags shader_stages;