summaryrefslogtreecommitdiff
path: root/thirdparty/spirv-reflect/spirv_reflect.c
diff options
context:
space:
mode:
Diffstat (limited to 'thirdparty/spirv-reflect/spirv_reflect.c')
-rw-r--r--thirdparty/spirv-reflect/spirv_reflect.c51
1 files changed, 51 insertions, 0 deletions
diff --git a/thirdparty/spirv-reflect/spirv_reflect.c b/thirdparty/spirv-reflect/spirv_reflect.c
index 11ccbdee3a..f2be1f8cae 100644
--- a/thirdparty/spirv-reflect/spirv_reflect.c
+++ b/thirdparty/spirv-reflect/spirv_reflect.c
@@ -142,6 +142,7 @@ typedef struct SpvReflectPrvNode {
SpvOp op;
uint32_t result_type_id;
uint32_t type_id;
+ SpvCapability capability;
SpvStorageClass storage_class;
uint32_t word_offset;
uint32_t word_count;
@@ -208,6 +209,7 @@ typedef struct SpvReflectPrvParser {
size_t node_count;
SpvReflectPrvNode* nodes;
uint32_t entry_point_count;
+ uint32_t capability_count;
uint32_t function_count;
SpvReflectPrvFunction* functions;
uint32_t access_chain_count;
@@ -739,6 +741,12 @@ static SpvReflectResult ParseNodes(SpvReflectPrvParser* p_parser)
}
break;
+ case SpvOpCapability: {
+ CHECKED_READU32(p_parser, p_node->word_offset + 1, p_node->capability);
+ ++(p_parser->capability_count);
+ }
+ break;
+
case SpvOpName:
case SpvOpMemberName:
{
@@ -1886,6 +1894,44 @@ static SpvReflectResult ParseTypes(
return SPV_REFLECT_RESULT_SUCCESS;
}
+static SpvReflectResult ParseCapabilities(
+ SpvReflectPrvParser* p_parser,
+ SpvReflectShaderModule* p_module)
+{
+ if (p_parser->capability_count == 0) {
+ return SPV_REFLECT_RESULT_SUCCESS;
+ }
+
+ p_module->capability_count = p_parser->capability_count;
+ p_module->capabilities = (SpvReflectCapability*)calloc(p_module->capability_count,
+ sizeof(*(p_module->capabilities)));
+ if (IsNull(p_module->capabilities)) {
+ return SPV_REFLECT_RESULT_ERROR_ALLOC_FAILED;
+ }
+
+ // Mark all types with an invalid state
+ for (size_t i = 0; i < p_module->capability_count; ++i) {
+ SpvReflectCapability* p_cap = &(p_module->capabilities[i]);
+ p_cap->value = SpvCapabilityMax;
+ p_cap->word_offset = (uint32_t)INVALID_VALUE;
+ }
+
+ size_t capability_index = 0;
+ for (size_t i = 0; i < p_parser->node_count; ++i) {
+ SpvReflectPrvNode* p_node = &(p_parser->nodes[i]);
+ if (SpvOpCapability != p_node->op) {
+ continue;
+ }
+
+ SpvReflectCapability* p_cap = &(p_module->capabilities[capability_index]);
+ p_cap->value = p_node->capability;
+ p_cap->word_offset = p_node->word_offset + 1;
+ ++capability_index;
+ }
+
+ return SPV_REFLECT_RESULT_SUCCESS;
+}
+
static int SortCompareDescriptorBinding(const void* a, const void* b)
{
const SpvReflectDescriptorBinding* p_elem_a = (const SpvReflectDescriptorBinding*)a;
@@ -3825,6 +3871,10 @@ static SpvReflectResult CreateShaderModule(
result = ParseEntryPoints(&parser, p_module);
SPV_REFLECT_ASSERT(result == SPV_REFLECT_RESULT_SUCCESS);
}
+ if (result == SPV_REFLECT_RESULT_SUCCESS) {
+ result = ParseCapabilities(&parser, p_module);
+ SPV_REFLECT_ASSERT(result == SPV_REFLECT_RESULT_SUCCESS);
+ }
if (result == SPV_REFLECT_RESULT_SUCCESS && p_module->entry_point_count > 0) {
SpvReflectEntryPoint* p_entry = &(p_module->entry_points[0]);
p_module->entry_point_name = p_entry->name;
@@ -3978,6 +4028,7 @@ void spvReflectDestroyShaderModule(SpvReflectShaderModule* p_module)
SafeFree(p_entry->used_push_constants);
SafeFree(p_entry->execution_modes);
}
+ SafeFree(p_module->capabilities);
SafeFree(p_module->entry_points);
// -- GODOT begin --
SafeFree(p_module->specialization_constants);