From 39ed21c12fb663fad2878309431d06d3462f91d6 Mon Sep 17 00:00:00 2001 From: baldurk Date: Wed, 15 Apr 2020 13:13:07 +0100 Subject: [PATCH] Process lifetime of Id params to GLSL ExtInsts --- renderdoc/driver/shaders/spirv/spirv_common.h | 83 +++++++++++++++++++ .../shaders/spirv/spirv_debug_setup.cpp | 15 ++++ renderdoc/driver/shaders/spirv/spirv_editor.h | 51 ------------ 3 files changed, 98 insertions(+), 51 deletions(-) diff --git a/renderdoc/driver/shaders/spirv/spirv_common.h b/renderdoc/driver/shaders/spirv/spirv_common.h index 9ec0dfa49..130672ec9 100644 --- a/renderdoc/driver/shaders/spirv/spirv_common.h +++ b/renderdoc/driver/shaders/spirv/spirv_common.h @@ -218,6 +218,89 @@ public: const T &operator[](Id id) const { return (*this)[id.value()]; } }; +struct IdOrWord +{ + constexpr inline IdOrWord() : value(0) {} + constexpr inline IdOrWord(uint32_t val) : value(val) {} + inline IdOrWord(Id id) : value(id.value()) {} + inline operator uint32_t() const { return value; } + constexpr inline bool operator==(const IdOrWord o) const { return value == o.value; } + constexpr inline bool operator!=(const IdOrWord o) const { return value != o.value; } + constexpr inline bool operator<(const IdOrWord o) const { return value < o.value; } +private: + uint32_t value; +}; + +// helper in the style of the auto-generated one for ext insts +template +struct OpExtInstGeneric +{ + OpExtInstGeneric(IdResultType resultType, IdResult result, Id set, InstType inst, + const rdcarray ¶ms) + : op(OpCode), wordCount(MinWordSize + (uint16_t)params.size()) + { + this->resultType = resultType; + this->result = result; + this->set = set; + this->inst = inst; + this->params.resize(params.size()); + for(size_t i = 0; i < params.size(); i++) + this->params[i] = params[i]; + } + OpExtInstGeneric(const ConstIter &it) + { + this->op = OpCode; + this->wordCount = (uint16_t)it.size(); + this->resultType = Id::fromWord(it.word(1)); + this->result = Id::fromWord(it.word(2)); + this->set = Id::fromWord(it.word(3)); + this->inst = InstType(it.word(4)); + this->params.reserve(it.size() - 5); + for(size_t word = 5; word < it.size(); word++) + this->params.push_back(it.word(word)); + } + + operator Operation() const + { + rdcarray words; + words.push_back(resultType.value()); + words.push_back(result.value()); + words.push_back(set.value()); + words.push_back((uint32_t)inst); + words.append(params); + return Operation(OpCode, words); + } + + static constexpr Op OpCode = Op::ExtInst; + static constexpr uint16_t MinWordSize = 4U; + Op op; + uint16_t wordCount; + IdResultType resultType; + IdResult result; + Id set; + InstType inst; + rdcarray params; +}; + +struct OpExtInst : public OpExtInstGeneric +{ + OpExtInst(IdResultType resultType, IdResult result, Id set, uint32_t inst, + const rdcarray ¶ms) + : OpExtInstGeneric(resultType, result, set, inst, params) + { + } + OpExtInst(const ConstIter &it) : OpExtInstGeneric(it) {} +}; +struct OpGLSL450 : public OpExtInstGeneric +{ + OpGLSL450(IdResultType resultType, IdResult result, Id set, rdcspv::GLSLstd450 inst, + const rdcarray ¶ms) + : OpExtInstGeneric(resultType, result, set, inst, params) + { + } + OpGLSL450(const ConstIter &it) : OpExtInstGeneric(it) {} +}; + }; // namespace rdcspv static const uint32_t SpecializationConstantBindSet = 1234567; diff --git a/renderdoc/driver/shaders/spirv/spirv_debug_setup.cpp b/renderdoc/driver/shaders/spirv/spirv_debug_setup.cpp index 475f50260..eb780fb18 100644 --- a/renderdoc/driver/shaders/spirv/spirv_debug_setup.cpp +++ b/renderdoc/driver/shaders/spirv/spirv_debug_setup.cpp @@ -1646,6 +1646,21 @@ void Debugger::RegisterOp(Iter it) idDeathOffset[id] = RDCMAX(it.offs() + 1, idDeathOffset[id]); }); + if(opdata.op == Op::ExtInst) + { + OpExtInst extinst(it); + + if(extSets[extinst.set] == "GLSL.std.450") + { + // all parameters to GLSL.std.450 are Ids, extend idDeathOffset appropriately + for(const uint32_t param : extinst.params) + { + Id id = Id::fromWord(param); + idDeathOffset[id] = RDCMAX(it.offs() + 1, idDeathOffset[id]); + } + } + } + if(opdata.op == Op::Line || opdata.op == Op::NoLine) { // ignore OpLine/OpNoLine diff --git a/renderdoc/driver/shaders/spirv/spirv_editor.h b/renderdoc/driver/shaders/spirv/spirv_editor.h index da83b5315..376c930f3 100644 --- a/renderdoc/driver/shaders/spirv/spirv_editor.h +++ b/renderdoc/driver/shaders/spirv/spirv_editor.h @@ -34,57 +34,6 @@ namespace rdcspv { class Editor; -struct IdOrWord -{ - constexpr inline IdOrWord() : value(0) {} - constexpr inline IdOrWord(uint32_t val) : value(val) {} - inline IdOrWord(Id id) : value(id.value()) {} - inline operator uint32_t() const { return value; } - constexpr inline bool operator==(const IdOrWord o) const { return value == o.value; } - constexpr inline bool operator!=(const IdOrWord o) const { return value != o.value; } - constexpr inline bool operator<(const IdOrWord o) const { return value < o.value; } -private: - uint32_t value; -}; - -// helper in the style of the auto-generated one for GLSL ext insts -struct OpGLSL450 -{ - OpGLSL450(IdResultType resultType, IdResult result, Id glsl450, rdcspv::GLSLstd450 inst, - const rdcarray ¶ms) - : op(OpCode), wordCount(MinWordSize + (uint16_t)params.size()) - { - this->resultType = resultType; - this->result = result; - this->glsl450 = glsl450; - this->inst = inst; - this->params.resize(params.size()); - for(size_t i = 0; i < params.size(); i++) - this->params[i] = params[i]; - } - - operator Operation() const - { - rdcarray words; - words.push_back(resultType.value()); - words.push_back(result.value()); - words.push_back(glsl450.value()); - words.push_back((uint32_t)inst); - words.append(params); - return Operation(OpCode, words); - } - - static constexpr Op OpCode = Op::ExtInst; - static constexpr uint16_t MinWordSize = 4U; - Op op; - uint16_t wordCount; - IdResultType resultType; - IdResult result; - Id glsl450; - rdcspv::GLSLstd450 inst; - rdcarray params; -}; - struct OperationList : public rdcarray { // add an operation and return its result id