diff --git a/src/panfrost/vulkan/csf/panvk_vX_cmd_draw.c b/src/panfrost/vulkan/csf/panvk_vX_cmd_draw.c index 8df4f0b2f2c..216c90abfe0 100644 --- a/src/panfrost/vulkan/csf/panvk_vX_cmd_draw.c +++ b/src/panfrost/vulkan/csf/panvk_vX_cmd_draw.c @@ -239,7 +239,9 @@ prepare_fs_driver_set(struct panvk_cmd_buffer *cmdbuf) const struct panvk_shader *fs = cmdbuf->state.gfx.fs.shader; const struct panvk_descriptor_state *desc_state = &cmdbuf->state.gfx.desc_state; - uint32_t desc_count = fs->desc_info.dyn_bufs.count + MAX_VARYING + 1; + uint32_t num_varying_attr_descs = fs->desc_info.max_varying_loads; + uint32_t desc_count = + fs->desc_info.dyn_bufs.count + num_varying_attr_descs + 1; struct panfrost_ptr driver_set = panvk_cmd_alloc_dev_mem( cmdbuf, desc, desc_count * PANVK_DESCRIPTOR_SIZE, PANVK_DESCRIPTOR_SIZE); struct panvk_opaque_desc *descs = driver_set.cpu; @@ -250,12 +252,13 @@ prepare_fs_driver_set(struct panvk_cmd_buffer *cmdbuf) emit_varying_descs(cmdbuf, (struct mali_attribute_packed *)(&descs[0])); /* Dummy sampler always comes right after the varyings. */ - pan_cast_and_pack(&descs[MAX_VARYING], SAMPLER, cfg) { + pan_cast_and_pack(&descs[num_varying_attr_descs], SAMPLER, cfg) { cfg.clamp_integer_array_indices = false; } panvk_per_arch(cmd_fill_dyn_bufs)( - desc_state, fs, (struct mali_buffer_packed *)(&descs[1 + MAX_VARYING])); + desc_state, fs, + (struct mali_buffer_packed *)(&descs[num_varying_attr_descs + 1])); fs_desc_state->driver_set.dev_addr = driver_set.gpu; fs_desc_state->driver_set.size = desc_count * PANVK_DESCRIPTOR_SIZE; diff --git a/src/panfrost/vulkan/panvk_shader.h b/src/panfrost/vulkan/panvk_shader.h index 6df60626234..93b1f34d3ce 100644 --- a/src/panfrost/vulkan/panvk_shader.h +++ b/src/panfrost/vulkan/panvk_shader.h @@ -277,6 +277,7 @@ struct panvk_shader { uint32_t map[MAX_DYNAMIC_BUFFERS]; uint32_t count; } dyn_bufs; + uint32_t max_varying_loads; #endif } desc_info; diff --git a/src/panfrost/vulkan/panvk_vX_nir_lower_descriptors.c b/src/panfrost/vulkan/panvk_vX_nir_lower_descriptors.c index aa733635f0f..06f907fd451 100644 --- a/src/panfrost/vulkan/panvk_vX_nir_lower_descriptors.c +++ b/src/panfrost/vulkan/panvk_vX_nir_lower_descriptors.c @@ -61,6 +61,7 @@ struct panvk_shader_desc_info { uint32_t dummy_sampler_handle; uint32_t dyn_bufs_start; struct panvk_shader_desc_map dyn_bufs; + uint32_t num_varying_attr_descs; #endif }; @@ -1033,7 +1034,7 @@ create_copy_table(nir_shader *nir, struct lower_desc_ctx *ctx) break; case MESA_SHADER_FRAGMENT: /* Dummy sampler comes after the varyings. */ - dummy_sampler_idx = MAX_VARYING; + dummy_sampler_idx = desc_info->num_varying_attr_descs; break; case MESA_SHADER_COMPUTE: dummy_sampler_idx = 0; @@ -1256,6 +1257,9 @@ panvk_per_arch(nir_lower_descriptors)( if (!progress) goto out; +#if PAN_ARCH >= 9 + ctx.desc_info.num_varying_attr_descs = shader->desc_info.max_varying_loads; +#endif create_copy_table(nir, &ctx); upload_shader_desc_info(dev, shader, &ctx.desc_info); diff --git a/src/panfrost/vulkan/panvk_vX_shader.c b/src/panfrost/vulkan/panvk_vX_shader.c index ee5b96c918b..ca58d0a4fbe 100644 --- a/src/panfrost/vulkan/panvk_vX_shader.c +++ b/src/panfrost/vulkan/panvk_vX_shader.c @@ -650,6 +650,17 @@ panvk_lower_nir(struct panvk_device *dev, nir_shader *nir, } #endif + /* Lower input intrinsics for fragment shaders early to get the max + * number of varying loads, as this number is required during descriptor + * lowering for v9+. */ + if (stage == MESA_SHADER_FRAGMENT) { + nir_assign_io_var_locations(nir, nir_var_shader_in, &nir->num_inputs, + stage); +#if PAN_ARCH >= 9 + shader->desc_info.max_varying_loads = nir->num_inputs; +#endif + } + panvk_per_arch(nir_lower_descriptors)(nir, dev, rs, set_layout_count, set_layouts, shader); @@ -706,7 +717,8 @@ panvk_lower_nir(struct panvk_device *dev, nir_shader *nir, var->data.location <= VERT_ATTRIB_GENERIC15); var->data.driver_location = var->data.location - VERT_ATTRIB_GENERIC0; } - } else { + } else if (stage != MESA_SHADER_FRAGMENT) { + /* Input varyings in fragment shader have been lowered early. */ nir_assign_io_var_locations(nir, nir_var_shader_in, &nir->num_inputs, stage); }