diff options
author | Eric Anholt <[email protected]> | 2018-03-30 16:04:34 -0700 |
---|---|---|
committer | Eric Anholt <[email protected]> | 2018-06-06 13:46:55 -0700 |
commit | 833c4046007f22ce1da0e1c2b89e8f1892f8d38e (patch) | |
tree | 41fc2aed75e84437d8cc83f0d6ecb84942832104 /src/compiler/nir | |
parent | f69473a712147c27fefbe83b9beacb251969fd92 (diff) |
nir: Look into uniform structs for samplers when counting num_textures.
mesa/st decides whether to update samplers after a program change based on
whether num_textures is nonzero. By not counting samplers in a uniform
struct, we would segfault in
KHR-GLES3.shaders.struct.uniform.sampler_vertex if it was run in the same
context after a non-vertex-shader-uniform testcase (as is the case during
a full conformance run).
v2: Implement using two separate pure functions instead of updating
pointers.
Reviewed-by: Jason Ekstrand <[email protected]>
Diffstat (limited to 'src/compiler/nir')
-rw-r--r-- | src/compiler/nir/nir_gather_info.c | 56 |
1 files changed, 44 insertions, 12 deletions
diff --git a/src/compiler/nir/nir_gather_info.c b/src/compiler/nir/nir_gather_info.c index dba9f199ec6..3534b6949eb 100644 --- a/src/compiler/nir/nir_gather_info.c +++ b/src/compiler/nir/nir_gather_info.c @@ -352,24 +352,56 @@ gather_info_block(nir_block *block, nir_shader *shader) } } +static unsigned +glsl_type_get_sampler_count(const struct glsl_type *type) +{ + if (glsl_type_is_array(type)) { + return (glsl_get_aoa_size(type) * + glsl_type_get_sampler_count(glsl_without_array(type))); + } + + if (glsl_type_is_struct(type)) { + unsigned count = 0; + for (int i = 0; i < glsl_get_length(type); i++) + count += glsl_type_get_sampler_count(glsl_get_struct_field(type, i)); + return count; + } + + if (glsl_type_is_sampler(type)) + return 1; + + return 0; +} + +static unsigned +glsl_type_get_image_count(const struct glsl_type *type) +{ + if (glsl_type_is_array(type)) { + return (glsl_get_aoa_size(type) * + glsl_type_get_image_count(glsl_without_array(type))); + } + + if (glsl_type_is_struct(type)) { + unsigned count = 0; + for (int i = 0; i < glsl_get_length(type); i++) + count += glsl_type_get_image_count(glsl_get_struct_field(type, i)); + return count; + } + + if (glsl_type_is_image(type)) + return 1; + + return 0; +} + void nir_shader_gather_info(nir_shader *shader, nir_function_impl *entrypoint) { shader->info.num_textures = 0; shader->info.num_images = 0; nir_foreach_variable(var, &shader->uniforms) { - const struct glsl_type *type = var->type; - unsigned count = 1; - if (glsl_type_is_array(type)) { - count = glsl_get_aoa_size(type); - type = glsl_without_array(type); - } - - if (glsl_type_is_image(type)) { - shader->info.num_images += count; - } else if (glsl_type_is_sampler(type)) { - shader->info.num_textures += count; - } + shader->info.num_textures += glsl_type_get_sampler_count(var->type); + shader->info.num_images += glsl_type_get_image_count(var->type); } shader->info.inputs_read = 0; |