From 2bf8be99b0f3dedd8fb23eeba998f6e1c540edf7 Mon Sep 17 00:00:00 2001 From: Jason Ekstrand Date: Fri, 29 Jun 2018 14:14:52 -0700 Subject: [PATCH] nir/types: Add a natural size and alignment helper The size and alignment are "natural" in the sense that everything is aligned to a scalar. This is a bit tighter than std430 where vec3s are required to be aligned to a vec4. Reviewed-by: Timothy Arceri Reviewed-by: Iago Toral Quiroga Reviewed-by: Kenneth Graunke --- src/compiler/nir_types.cpp | 56 ++++++++++++++++++++++++++++++++++++++ src/compiler/nir_types.h | 6 ++++ 2 files changed, 62 insertions(+) diff --git a/src/compiler/nir_types.cpp b/src/compiler/nir_types.cpp index d2b2a93b207..2b932b1967e 100644 --- a/src/compiler/nir_types.cpp +++ b/src/compiler/nir_types.cpp @@ -477,3 +477,59 @@ glsl_channel_type(const glsl_type *t) unreachable("Unhandled base type glsl_channel_type()"); } } + +void +glsl_get_natural_size_align_bytes(const struct glsl_type *type, + unsigned *size, unsigned *align) +{ + switch (type->base_type) { + case GLSL_TYPE_UINT8: + case GLSL_TYPE_INT8: + case GLSL_TYPE_UINT16: + case GLSL_TYPE_INT16: + case GLSL_TYPE_FLOAT16: + case GLSL_TYPE_UINT: + case GLSL_TYPE_INT: + case GLSL_TYPE_FLOAT: + case GLSL_TYPE_BOOL: + case GLSL_TYPE_DOUBLE: + case GLSL_TYPE_UINT64: + case GLSL_TYPE_INT64: { + unsigned N = glsl_get_bit_size(type) / 8; + *size = N * type->components(); + *align = N; + break; + } + + case GLSL_TYPE_ARRAY: { + unsigned elem_size, elem_align; + glsl_get_natural_size_align_bytes(type->fields.array, + &elem_size, &elem_align); + *align = elem_align; + *size = type->length * ALIGN_POT(elem_size, elem_align); + break; + } + + case GLSL_TYPE_STRUCT: + *size = 0; + *align = 0; + for (unsigned i = 0; i < type->length; i++) { + unsigned elem_size, elem_align; + glsl_get_natural_size_align_bytes(type->fields.structure[i].type, + &elem_size, &elem_align); + *align = MAX2(*align, elem_align); + *size = ALIGN_POT(*size, elem_align) + elem_size; + } + break; + + case GLSL_TYPE_SAMPLER: + case GLSL_TYPE_ATOMIC_UINT: + case GLSL_TYPE_SUBROUTINE: + case GLSL_TYPE_IMAGE: + case GLSL_TYPE_VOID: + case GLSL_TYPE_ERROR: + case GLSL_TYPE_INTERFACE: + case GLSL_TYPE_FUNCTION: + unreachable("type does not have a natural size"); + } +} diff --git a/src/compiler/nir_types.h b/src/compiler/nir_types.h index 1107cfd73f2..67c4d7b5097 100644 --- a/src/compiler/nir_types.h +++ b/src/compiler/nir_types.h @@ -184,6 +184,12 @@ const struct glsl_type *glsl_transposed_type(const struct glsl_type *type); const struct glsl_type *glsl_channel_type(const struct glsl_type *type); +typedef void (*glsl_type_size_align_func)(const struct glsl_type *type, + unsigned *size, unsigned *align); + +void glsl_get_natural_size_align_bytes(const struct glsl_type *type, + unsigned *size, unsigned *align); + #ifdef __cplusplus } #endif -- 2.30.2