diff options
author | Hans-Kristian Arntzen <post@arntzen-software.no> | 2021-04-16 14:32:37 +0300 |
---|---|---|
committer | Hans-Kristian Arntzen <post@arntzen-software.no> | 2021-04-19 13:10:49 +0300 |
commit | b4a380a04c47a5cbed8655b8cdb729563e952c5b (patch) | |
tree | fe15ebc56dc3e7c258e931ccadbc4362da690b56 /spirv_cross.cpp | |
parent | 852f2da63cb3b501fe52504f67a550329b0bfa7e (diff) |
Support reflecting builtins.
They were ignored in input/output variables.
Diffstat (limited to 'spirv_cross.cpp')
-rw-r--r-- | spirv_cross.cpp | 54 |
1 files changed, 50 insertions, 4 deletions
diff --git a/spirv_cross.cpp b/spirv_cross.cpp index 3c37cb21..afd8c508 100644 --- a/spirv_cross.cpp +++ b/spirv_cross.cpp @@ -853,7 +853,7 @@ ShaderResources Compiler::get_shader_resources(const unordered_set<VariableID> * // It is possible for uniform storage classes to be passed as function parameters, so detect // that. To detect function parameters, check of StorageClass of variable is function scope. - if (var.storage == StorageClassFunction || !type.pointer || is_builtin_variable(var)) + if (var.storage == StorageClassFunction || !type.pointer) return; if (active_variables && active_variables->find(var.self) == end(*active_variables)) @@ -873,13 +873,59 @@ ShaderResources Compiler::get_shader_resources(const unordered_set<VariableID> * if (!active_in_entry_point) return; + bool is_builtin = is_builtin_variable(var); + + if (is_builtin) + { + if (var.storage != StorageClassInput && var.storage != StorageClassOutput) + return; + + auto &list = var.storage == StorageClassInput ? res.builtin_inputs : res.builtin_outputs; + BuiltInResource resource; + + if (has_decoration(type.self, DecorationBlock)) + { + resource.resource = { var.self, var.basetype, type.self, + get_remapped_declared_block_name(var.self, false) }; + + for (uint32_t i = 0; i < uint32_t(type.member_types.size()); i++) + { + resource.value_type_id = type.member_types[i]; + resource.builtin = BuiltIn(get_member_decoration(type.self, i, DecorationBuiltIn)); + list.push_back(resource); + } + } + else + { + bool strip_array = + !has_decoration(var.self, DecorationPatch) && ( + get_execution_model() == ExecutionModelTessellationControl || + (get_execution_model() == ExecutionModelTessellationEvaluation && + var.storage == StorageClassInput)); + + resource.resource = { var.self, var.basetype, type.self, get_name(var.self) }; + + if (strip_array && !type.array.empty()) + resource.value_type_id = get_variable_data_type(var).parent_type; + else + resource.value_type_id = get_variable_data_type_id(var); + + assert(resource.value_type_id); + + resource.builtin = BuiltIn(get_decoration(var.self, DecorationBuiltIn)); + list.push_back(std::move(resource)); + } + return; + } + // Input if (var.storage == StorageClassInput) { if (has_decoration(type.self, DecorationBlock)) { res.stage_inputs.push_back( - { var.self, var.basetype, type.self, get_remapped_declared_block_name(var.self, false) }); + { var.self, var.basetype, type.self, + get_remapped_declared_block_name(var.self, false) }); } else res.stage_inputs.push_back({ var.self, var.basetype, type.self, get_name(var.self) }); @@ -895,7 +941,7 @@ ShaderResources Compiler::get_shader_resources(const unordered_set<VariableID> * if (has_decoration(type.self, DecorationBlock)) { res.stage_outputs.push_back( - { var.self, var.basetype, type.self, get_remapped_declared_block_name(var.self, false) }); + { var.self, var.basetype, type.self, get_remapped_declared_block_name(var.self, false) }); } else res.stage_outputs.push_back({ var.self, var.basetype, type.self, get_name(var.self) }); @@ -4085,7 +4131,7 @@ void Compiler::update_active_builtins() } // Returns whether this shader uses a builtin of the storage class -bool Compiler::has_active_builtin(BuiltIn builtin, StorageClass storage) +bool Compiler::has_active_builtin(BuiltIn builtin, StorageClass storage) const { const Bitset *flags; switch (storage) |