From b51af1a2ca01090cbcbd4855dc29adf40d3bd612 Mon Sep 17 00:00:00 2001 From: Frodo Baggins Date: Wed, 18 Sep 2024 23:04:20 -0700 Subject: [PATCH 1/5] Add NonSemantic DebugPrintf --- include/sirit/sirit.h | 173 +++++++++++++++++---------------- src/instructions/extension.cpp | 9 ++ src/sirit.cpp | 13 ++- 3 files changed, 111 insertions(+), 84 deletions(-) diff --git a/include/sirit/sirit.h b/include/sirit/sirit.h index c7f3e2b..e656603 100644 --- a/include/sirit/sirit.h +++ b/include/sirit/sirit.h @@ -73,9 +73,9 @@ public: // TODO: Change std::is_convertible_v to std::convertible_to when compilers // support it; same elsewhere. template - requires(...&& std::is_convertible_v) void AddEntryPoint( - spv::ExecutionModel execution_model, Id entry_point, std::string_view name, - Ts&&... interfaces) { + requires(... && std::is_convertible_v) + void AddEntryPoint(spv::ExecutionModel execution_model, Id entry_point, std::string_view name, + Ts&&... interfaces) { AddEntryPoint(execution_model, std::move(entry_point), name, std::span({interfaces...})); } @@ -86,8 +86,8 @@ public: /// Declare an execution mode for an entry point. template - requires(...&& std::is_convertible_v) void AddExecutionMode( - Id entry_point, spv::ExecutionMode mode, Ts&&... literals) { + requires(... && std::is_convertible_v) + void AddExecutionMode(Id entry_point, spv::ExecutionMode mode, Ts&&... literals) { AddExecutionMode(entry_point, mode, std::span({literals...})); } @@ -162,7 +162,8 @@ public: /// Returns type struct. template - requires(...&& std::is_convertible_v) Id TypeStruct(Ts&&... members) { + requires(... && std::is_convertible_v) + Id TypeStruct(Ts&&... members) { return TypeStruct(std::span({members...})); } @@ -177,8 +178,8 @@ public: /// Returns type function. template - requires(...&& std::is_convertible_v) Id - TypeFunction(Id return_type, Ts&&... arguments) { + requires(... && std::is_convertible_v) + Id TypeFunction(Id return_type, Ts&&... arguments) { return TypeFunction(return_type, std::span({arguments...})); } @@ -213,8 +214,8 @@ public: /// Returns a numeric scalar constant. template - requires(...&& std::is_convertible_v) Id - ConstantComposite(Id result_type, Ts&&... constituents) { + requires(... && std::is_convertible_v) + Id ConstantComposite(Id result_type, Ts&&... constituents) { return ConstantComposite(result_type, std::span({constituents...})); } @@ -238,8 +239,8 @@ public: /// Call a function. template - requires(...&& std::is_convertible_v) Id - OpFunctionCall(Id result_type, Id function, Ts&&... arguments) { + requires(... && std::is_convertible_v) + Id OpFunctionCall(Id result_type, Id function, Ts&&... arguments) { return OpFunctionCall(result_type, function, std::span({arguments...})); } @@ -257,11 +258,11 @@ public: Id OpPhi(Id result_type, std::span operands); template - requires(...&& std::is_convertible_v) Id - OpPhi(Id result_type, Ts&&... operands) { + requires(... && std::is_convertible_v) + Id OpPhi(Id result_type, Ts&&... operands) { return OpPhi(result_type, std::span({operands...})); } - + /** * The SSA phi function. This instruction will be revisited when patching phi nodes. * @@ -276,9 +277,9 @@ public: /// Declare a structured loop. template - requires(...&& std::is_convertible_v) Id - OpLoopMerge(Id merge_block, Id continue_target, spv::LoopControlMask loop_control, - Ts&&... literals) { + requires(... && std::is_convertible_v) + Id OpLoopMerge(Id merge_block, Id continue_target, spv::LoopControlMask loop_control, + Ts&&... literals) { return OpLoopMerge(merge_block, continue_target, loop_control, std::span({literals...})); } @@ -356,8 +357,8 @@ public: /// Create a pointer into a composite object that can be used with OpLoad and OpStore. template - requires(...&& std::is_convertible_v) Id - OpAccessChain(Id result_type, Id base, Ts&&... indexes) { + requires(... && std::is_convertible_v) + Id OpAccessChain(Id result_type, Id base, Ts&&... indexes) { return OpAccessChain(result_type, base, std::span({indexes...})); } @@ -368,14 +369,16 @@ public: Id OpVectorInsertDynamic(Id result_type, Id vector, Id component, Id index); /// Select arbitrary components from two vectors to make a new vector. - Id OpVectorShuffle(Id result_type, Id vector_1, Id vector_2, std::span components); + Id OpVectorShuffle(Id result_type, Id vector_1, Id vector_2, + std::span components); /// Select arbitrary components from two vectors to make a new vector. template - requires(...&& std::is_convertible_v) Id - OpVectorShuffle(Id result_type, Id vector_1, Id vector_2, Ts&&... components) { + requires(... && std::is_convertible_v) + Id OpVectorShuffle(Id result_type, Id vector_1, Id vector_2, Ts&&... components) { const Literal stack_literals[] = {std::forward(components)...}; - return OpVectorShuffle(result_type, vector_1, vector_2, std::span{stack_literals}); + return OpVectorShuffle(result_type, vector_1, vector_2, + std::span{stack_literals}); } /// Make a copy of a composite object, while modifying one part of it. @@ -384,8 +387,8 @@ public: /// Make a copy of a composite object, while modifying one part of it. template - requires(...&& std::is_convertible_v) Id - OpCompositeInsert(Id result_type, Id object, Id composite, Ts&&... indexes) { + requires(... && std::is_convertible_v) + Id OpCompositeInsert(Id result_type, Id object, Id composite, Ts&&... indexes) { const Literal stack_indexes[] = {std::forward(indexes)...}; return OpCompositeInsert(result_type, object, composite, std::span{stack_indexes}); @@ -396,8 +399,8 @@ public: /// Extract a part of a composite object. template - requires(...&& std::is_convertible_v) Id - OpCompositeExtract(Id result_type, Id composite, Ts&&... indexes) { + requires(... && std::is_convertible_v) + Id OpCompositeExtract(Id result_type, Id composite, Ts&&... indexes) { const Literal stack_indexes[] = {std::forward(indexes)...}; return OpCompositeExtract(result_type, composite, std::span{stack_indexes}); } @@ -407,8 +410,8 @@ public: /// Construct a new composite object from a set of constituent objects that will fully form it. template - requires(...&& std::is_convertible_v) Id - OpCompositeConstruct(Id result_type, Ts&&... ids) { + requires(... && std::is_convertible_v) + Id OpCompositeConstruct(Id result_type, Ts&&... ids) { return OpCompositeConstruct(result_type, std::span({ids...})); } @@ -419,15 +422,16 @@ public: /// Add a decoration to target. template - requires(...&& std::is_convertible_v) Id - Decorate(Id target, spv::Decoration decoration, Ts&&... literals) { + requires(... && std::is_convertible_v) + Id Decorate(Id target, spv::Decoration decoration, Ts&&... literals) { const Literal stack_literals[] = {std::forward(literals)...}; return Decorate(target, decoration, std::span{stack_literals}); } /// Add a decoration to target. template - requires std::is_enum_v Id Decorate(Id target, spv::Decoration decoration, T literal) { + requires std::is_enum_v + Id Decorate(Id target, spv::Decoration decoration, T literal) { return Decorate(target, decoration, static_cast(literal)); } @@ -435,9 +439,9 @@ public: std::span literals = {}); template - requires(...&& std::is_convertible_v) Id - MemberDecorate(Id structure_type, Literal member, spv::Decoration decoration, - Ts&&... literals) { + requires(... && std::is_convertible_v) + Id MemberDecorate(Id structure_type, Literal member, spv::Decoration decoration, + Ts&&... literals) { const Literal stack_literals[] = {std::forward(literals)...}; return MemberDecorate(structure_type, member, decoration, std::span{stack_literals}); @@ -718,8 +722,8 @@ public: /// Execute an instruction in an imported set of extended instructions. template - requires(...&& std::is_convertible_v) Id - OpExtInst(Id result_type, Id set, std::uint32_t instruction, Ts&&... operands) { + requires(... && std::is_convertible_v) + Id OpExtInst(Id result_type, Id set, std::uint32_t instruction, Ts&&... operands) { return OpExtInst(result_type, set, instruction, std::span({operands...})); } @@ -793,7 +797,8 @@ public: /// Result is the reciprocal of sqrt x. Result is undefined if x <= 0. Id OpInverseSqrt(Id result_type, Id x); - /// Result is a floating-point number from x and the corresponding integral exponent of two in exp. + /// Result is a floating-point number from x and the corresponding integral exponent of two in + /// exp. Id OpLdexp(Id result_type, Id x, Id exp); /// Result is y if y < x; otherwise result is x. Which operand is the result is undefined if one @@ -808,8 +813,8 @@ public: /// integers. Id OpSMin(Id result_type, Id x, Id y); - /// Result is y if y < x, either x or y if both x and y are zeros, otherwise x. If one operand is a NaN, the other - /// operand is the result. If both operands are NaN, the result is a NaN. + /// Result is y if y < x, either x or y if both x and y are zeros, otherwise x. If one operand + /// is a NaN, the other operand is the result. If both operands are NaN, the result is a NaN. Id OpNMin(Id result_type, Id x, Id y); /// Result is y if x < y; otherwise result is x. Which operand is the result is undefined if one @@ -824,8 +829,8 @@ public: /// integers. Id OpSMax(Id result_type, Id x, Id y); - /// Result is y if x < y, either x or y if both x and y are zeros, otherwise x. If one operand is a NaN, the other - /// operand is the result. If both operands are NaN, the result is a NaN. + /// Result is y if x < y, either x or y if both x and y are zeros, otherwise x. If one operand + /// is a NaN, the other operand is the result. If both operands are NaN, the result is a NaN. Id OpNMax(Id result_type, Id x, Id y); /// Result is min(max(x, minVal), maxVal). Result is undefined if minVal > maxVal.The semantics @@ -943,9 +948,9 @@ public: /// Sample an image with an implicit level of detail. template - requires(...&& std::is_convertible_v) Id - OpImageSampleImplicitLod(Id result_type, Id sampled_image, Id coordinate, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(... && std::is_convertible_v) + Id OpImageSampleImplicitLod(Id result_type, Id sampled_image, Id coordinate, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleImplicitLod(result_type, sampled_image, coordinate, image_operands, std::span({operands...})); } @@ -957,9 +962,9 @@ public: /// Sample an image using an explicit level of detail. template - requires(...&& std::is_convertible_v) Id - OpImageSampleExplicitLod(Id result_type, Id sampled_image, Id coordinate, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(... && std::is_convertible_v) + Id OpImageSampleExplicitLod(Id result_type, Id sampled_image, Id coordinate, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleExplicitLod(result_type, sampled_image, coordinate, image_operands, std::span({operands...})); } @@ -972,9 +977,9 @@ public: /// Sample an image doing depth-comparison with an implicit level of detail. template - requires(...&& std::is_convertible_v) Id - OpImageSampleDrefImplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(... && std::is_convertible_v) + Id OpImageSampleDrefImplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleDrefImplicitLod(result_type, sampled_image, coordinate, dref, image_operands, std::span({operands...})); } @@ -986,9 +991,9 @@ public: /// Sample an image doing depth-comparison using an explicit level of detail. template - requires(...&& std::is_convertible_v) Id - OpImageSampleDrefExplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(... && std::is_convertible_v) + Id OpImageSampleDrefExplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleDrefExplicitLod(result_type, sampled_image, coordinate, dref, image_operands, std::span({operands...})); } @@ -1001,9 +1006,9 @@ public: /// Sample an image with with a project coordinate and an implicit level of detail. template - requires(...&& std::is_convertible_v) Id - OpImageSampleProjImplicitLod(Id result_type, Id sampled_image, Id coordinate, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(... && std::is_convertible_v) + Id OpImageSampleProjImplicitLod(Id result_type, Id sampled_image, Id coordinate, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleProjImplicitLod(result_type, sampled_image, coordinate, image_operands, std::span({operands...})); } @@ -1015,9 +1020,9 @@ public: /// Sample an image with a project coordinate using an explicit level of detail. template - requires(...&& std::is_convertible_v) Id - OpImageSampleProjExplicitLod(Id result_type, Id sampled_image, Id coordinate, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(... && std::is_convertible_v) + Id OpImageSampleProjExplicitLod(Id result_type, Id sampled_image, Id coordinate, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleProjExplicitLod(result_type, sampled_image, coordinate, image_operands, std::span({operands...})); } @@ -1032,9 +1037,9 @@ public: /// Sample an image with a project coordinate, doing depth-comparison, with an implicit level of /// detail. template - requires(...&& std::is_convertible_v) Id - OpImageSampleProjDrefImplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(... && std::is_convertible_v) + Id OpImageSampleProjDrefImplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleProjDrefImplicitLod(result_type, sampled_image, coordinate, dref, image_operands, std::span({operands...})); } @@ -1048,9 +1053,9 @@ public: /// Sample an image with a project coordinate, doing depth-comparison, using an explicit level /// of detail. template - requires(...&& std::is_convertible_v) Id - OpImageSampleProjDrefExplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(... && std::is_convertible_v) + Id OpImageSampleProjDrefExplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleProjDrefExplicitLod(result_type, sampled_image, coordinate, dref, image_operands, std::span({operands...})); } @@ -1062,9 +1067,9 @@ public: /// Fetch a single texel from an image whose Sampled operand is 1. template - requires(...&& std::is_convertible_v) Id - OpImageFetch(Id result_type, Id sampled_image, Id coordinate, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(... && std::is_convertible_v) + Id OpImageFetch(Id result_type, Id sampled_image, Id coordinate, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageFetch(result_type, sampled_image, coordinate, image_operands, std::span({operands...})); } @@ -1076,9 +1081,9 @@ public: /// Gathers the requested component from four texels. template - requires(...&& std::is_convertible_v) Id - OpImageGather(Id result_type, Id sampled_image, Id coordinate, Id component, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(... && std::is_convertible_v) + Id OpImageGather(Id result_type, Id sampled_image, Id coordinate, Id component, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageGather(result_type, sampled_image, coordinate, component, image_operands, std::span({operands...})); } @@ -1090,9 +1095,9 @@ public: /// Gathers the requested depth-comparison from four texels. template - requires(...&& std::is_convertible_v) Id - OpImageDrefGather(Id result_type, Id sampled_image, Id coordinate, Id dref, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(... && std::is_convertible_v) + Id OpImageDrefGather(Id result_type, Id sampled_image, Id coordinate, Id dref, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageDrefGather(result_type, sampled_image, coordinate, dref, image_operands, std::span({operands...})); } @@ -1104,9 +1109,9 @@ public: /// Read a texel from an image without a sampler. template - requires(...&& std::is_convertible_v) Id - OpImageRead(Id result_type, Id sampled_image, Id coordinate, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(... && std::is_convertible_v) + Id OpImageRead(Id result_type, Id sampled_image, Id coordinate, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageRead(result_type, sampled_image, coordinate, image_operands, std::span({operands...})); } @@ -1118,9 +1123,9 @@ public: /// Write a texel to an image without a sampler. template - requires(...&& std::is_convertible_v) Id - OpImageWrite(Id image, Id coordinate, Id texel, spv::ImageOperandsMask image_operands, - Ts&&... operands) { + requires(... && std::is_convertible_v) + Id OpImageWrite(Id image, Id coordinate, Id texel, spv::ImageOperandsMask image_operands, + Ts&&... operands) { return OpImageWrite(image, coordinate, texel, image_operands, std::span({operands...})); } @@ -1347,8 +1352,11 @@ public: /// 3) store the New Value back through Pointer. Id OpAtomicXor(Id result_type, Id pointer, Id memory, Id semantics, Id value); + Id OpDebugPrintf(Id fmt, std::span fmt_args); + private: Id GetGLSLstd450(); + Id GetNonSemanticDebugPrintf(); std::uint32_t version{}; std::uint32_t bound{}; @@ -1356,6 +1364,7 @@ private: std::unordered_set extensions; std::unordered_set capabilities; std::optional glsl_std_450; + std::optional non_semantic_debug_printf; spv::AddressingModel addressing_model{spv::AddressingModel::Logical}; spv::MemoryModel memory_model{spv::MemoryModel::GLSL450}; diff --git a/src/instructions/extension.cpp b/src/instructions/extension.cpp index 44dc691..4eff1a7 100644 --- a/src/instructions/extension.cpp +++ b/src/instructions/extension.cpp @@ -5,6 +5,7 @@ */ #include +#include #include "sirit/sirit.h" @@ -80,4 +81,12 @@ DEFINE_BINARY(OpCross, GLSLstd450Cross) DEFINE_UNARY(OpLength, GLSLstd450Length) DEFINE_TRINARY(OpFMix, GLSLstd450FMix) +Id Module::OpDebugPrintf(Id fmt, std::span fmt_args) { + std::vector operands; + operands.push_back(fmt); + std::copy(fmt_args.begin(), fmt_args.end(), operands.end()); + return OpExtInst(TypeVoid(), GetNonSemanticDebugPrintf(), NonSemanticDebugPrintfDebugPrintf, + operands); +} + } // namespace Sirit diff --git a/src/sirit.cpp b/src/sirit.cpp index 7075f23..b30379a 100644 --- a/src/sirit.cpp +++ b/src/sirit.cpp @@ -21,8 +21,8 @@ Module::Module(u32 version_) : version{version_}, ext_inst_imports{std::make_unique(&bound)}, entry_points{std::make_unique(&bound)}, execution_modes{std::make_unique(&bound)}, debug{std::make_unique(&bound)}, - annotations{std::make_unique(&bound)}, declarations{std::make_unique( - &bound)}, + annotations{std::make_unique(&bound)}, + declarations{std::make_unique(&bound)}, global_variables{std::make_unique(&bound)}, code{std::make_unique(&bound)} {} Module::~Module() = default; @@ -139,4 +139,13 @@ Id Module::GetGLSLstd450() { return *glsl_std_450; } +Id Module::GetNonSemanticDebugPrintf() { + if (!non_semantic_debug_printf) { + ext_inst_imports->Reserve(3 + 4); + non_semantic_debug_printf = *ext_inst_imports << OpId{spv::Op::OpExtInstImport} + << "NonSemantic.DebugPrintf" << EndOp{}; + } + return *non_semantic_debug_printf; +} + } // namespace Sirit From b0f30ba7715ea5bb50d600cc700e790144c41c78 Mon Sep 17 00:00:00 2001 From: Frodo Baggins Date: Thu, 19 Sep 2024 16:40:51 -0700 Subject: [PATCH 2/5] fix wordcount of printf OpExtInstImport. Also refactor so OpString and other debug insts come before OpName and OpMemberName to fix spirv-val errors --- include/sirit/sirit.h | 1 + src/instructions/debug.cpp | 8 ++++---- src/sirit.cpp | 18 +++++++++++------- 3 files changed, 16 insertions(+), 11 deletions(-) diff --git a/include/sirit/sirit.h b/include/sirit/sirit.h index e656603..fbcb26f 100644 --- a/include/sirit/sirit.h +++ b/include/sirit/sirit.h @@ -1373,6 +1373,7 @@ private: std::unique_ptr entry_points; std::unique_ptr execution_modes; std::unique_ptr debug; + std::unique_ptr debug_name; std::unique_ptr annotations; std::unique_ptr declarations; std::unique_ptr global_variables; diff --git a/src/instructions/debug.cpp b/src/instructions/debug.cpp index 1ca3462..2907e66 100644 --- a/src/instructions/debug.cpp +++ b/src/instructions/debug.cpp @@ -12,14 +12,14 @@ namespace Sirit { Id Module::Name(Id target, std::string_view name) { - debug->Reserve(3 + WordsInString(name)); - *debug << spv::Op::OpName << target << name << EndOp{}; + debug_name->Reserve(3 + WordsInString(name)); + *debug_name << spv::Op::OpName << target << name << EndOp{}; return target; } Id Module::MemberName(Id type, u32 member, std::string_view name) { - debug->Reserve(4 + WordsInString(name)); - *debug << spv::Op::OpMemberName << type << member << name << EndOp{}; + debug_name->Reserve(4 + WordsInString(name)); + *debug_name << spv::Op::OpMemberName << type << member << name << EndOp{}; return type; } diff --git a/src/sirit.cpp b/src/sirit.cpp index b30379a..48a5f61 100644 --- a/src/sirit.cpp +++ b/src/sirit.cpp @@ -21,7 +21,7 @@ Module::Module(u32 version_) : version{version_}, ext_inst_imports{std::make_unique(&bound)}, entry_points{std::make_unique(&bound)}, execution_modes{std::make_unique(&bound)}, debug{std::make_unique(&bound)}, - annotations{std::make_unique(&bound)}, + debug_name{std::make_unique(&bound)}, annotations{std::make_unique(&bound)}, declarations{std::make_unique(&bound)}, global_variables{std::make_unique(&bound)}, code{std::make_unique(&bound)} {} @@ -60,6 +60,7 @@ std::vector Module::Assemble() const { insert(entry_points->Words()); insert(execution_modes->Words()); insert(debug->Words()); + insert(debug_name->Words()); insert(annotations->Words()); insert(declarations->Words()); insert(global_variables->Words()); @@ -131,19 +132,22 @@ Id Module::AddGlobalVariable(Id result_type, spv::StorageClass storage_class, } Id Module::GetGLSLstd450() { + const char* extname = "GLSL.std.450"; + size_t len = WordsInString(extname); if (!glsl_std_450) { - ext_inst_imports->Reserve(3 + 4); - glsl_std_450 = *ext_inst_imports << OpId{spv::Op::OpExtInstImport} << "GLSL.std.450" - << EndOp{}; + ext_inst_imports->Reserve(3 + len); + glsl_std_450 = *ext_inst_imports << OpId{spv::Op::OpExtInstImport} << extname << EndOp{}; } return *glsl_std_450; } Id Module::GetNonSemanticDebugPrintf() { + const char* extname = "NonSemantic.DebugPrintf"; + size_t len = WordsInString(extname); if (!non_semantic_debug_printf) { - ext_inst_imports->Reserve(3 + 4); - non_semantic_debug_printf = *ext_inst_imports << OpId{spv::Op::OpExtInstImport} - << "NonSemantic.DebugPrintf" << EndOp{}; + ext_inst_imports->Reserve(3 + len); + non_semantic_debug_printf = *ext_inst_imports << OpId{spv::Op::OpExtInstImport} << extname + << EndOp{}; } return *non_semantic_debug_printf; } From c3619a5f42775287e8bec6f45c9e236fa80bdc2e Mon Sep 17 00:00:00 2001 From: Frodo Baggins Date: Thu, 19 Sep 2024 17:09:30 -0700 Subject: [PATCH 3/5] fix operand copy --- src/instructions/extension.cpp | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/instructions/extension.cpp b/src/instructions/extension.cpp index 4eff1a7..501b515 100644 --- a/src/instructions/extension.cpp +++ b/src/instructions/extension.cpp @@ -4,6 +4,7 @@ * 3-Clause BSD License */ +#include #include #include @@ -84,7 +85,7 @@ DEFINE_TRINARY(OpFMix, GLSLstd450FMix) Id Module::OpDebugPrintf(Id fmt, std::span fmt_args) { std::vector operands; operands.push_back(fmt); - std::copy(fmt_args.begin(), fmt_args.end(), operands.end()); + std::copy(fmt_args.begin(), fmt_args.end(), std::back_inserter(operands)); return OpExtInst(TypeVoid(), GetNonSemanticDebugPrintf(), NonSemanticDebugPrintfDebugPrintf, operands); } From d8fa51152fecf64ca57cdcb330ad4adc546add61 Mon Sep 17 00:00:00 2001 From: Frodo Baggins Date: Thu, 19 Sep 2024 17:56:30 -0700 Subject: [PATCH 4/5] revert some clang format stuff --- include/sirit/sirit.h | 169 ++++++++++++++++++++---------------------- 1 file changed, 82 insertions(+), 87 deletions(-) diff --git a/include/sirit/sirit.h b/include/sirit/sirit.h index fbcb26f..7470eed 100644 --- a/include/sirit/sirit.h +++ b/include/sirit/sirit.h @@ -73,9 +73,9 @@ public: // TODO: Change std::is_convertible_v to std::convertible_to when compilers // support it; same elsewhere. template - requires(... && std::is_convertible_v) - void AddEntryPoint(spv::ExecutionModel execution_model, Id entry_point, std::string_view name, - Ts&&... interfaces) { + requires(...&& std::is_convertible_v) void AddEntryPoint( + spv::ExecutionModel execution_model, Id entry_point, std::string_view name, + Ts&&... interfaces) { AddEntryPoint(execution_model, std::move(entry_point), name, std::span({interfaces...})); } @@ -86,8 +86,8 @@ public: /// Declare an execution mode for an entry point. template - requires(... && std::is_convertible_v) - void AddExecutionMode(Id entry_point, spv::ExecutionMode mode, Ts&&... literals) { + requires(...&& std::is_convertible_v) void AddExecutionMode( + Id entry_point, spv::ExecutionMode mode, Ts&&... literals) { AddExecutionMode(entry_point, mode, std::span({literals...})); } @@ -162,8 +162,7 @@ public: /// Returns type struct. template - requires(... && std::is_convertible_v) - Id TypeStruct(Ts&&... members) { + requires(...&& std::is_convertible_v) Id TypeStruct(Ts&&... members) { return TypeStruct(std::span({members...})); } @@ -178,8 +177,8 @@ public: /// Returns type function. template - requires(... && std::is_convertible_v) - Id TypeFunction(Id return_type, Ts&&... arguments) { + requires(...&& std::is_convertible_v) Id + TypeFunction(Id return_type, Ts&&... arguments) { return TypeFunction(return_type, std::span({arguments...})); } @@ -214,8 +213,8 @@ public: /// Returns a numeric scalar constant. template - requires(... && std::is_convertible_v) - Id ConstantComposite(Id result_type, Ts&&... constituents) { + requires(...&& std::is_convertible_v) Id + ConstantComposite(Id result_type, Ts&&... constituents) { return ConstantComposite(result_type, std::span({constituents...})); } @@ -239,8 +238,8 @@ public: /// Call a function. template - requires(... && std::is_convertible_v) - Id OpFunctionCall(Id result_type, Id function, Ts&&... arguments) { + requires(...&& std::is_convertible_v) Id + OpFunctionCall(Id result_type, Id function, Ts&&... arguments) { return OpFunctionCall(result_type, function, std::span({arguments...})); } @@ -258,11 +257,11 @@ public: Id OpPhi(Id result_type, std::span operands); template - requires(... && std::is_convertible_v) - Id OpPhi(Id result_type, Ts&&... operands) { + requires(...&& std::is_convertible_v) Id + OpPhi(Id result_type, Ts&&... operands) { return OpPhi(result_type, std::span({operands...})); } - + /** * The SSA phi function. This instruction will be revisited when patching phi nodes. * @@ -277,9 +276,9 @@ public: /// Declare a structured loop. template - requires(... && std::is_convertible_v) - Id OpLoopMerge(Id merge_block, Id continue_target, spv::LoopControlMask loop_control, - Ts&&... literals) { + requires(...&& std::is_convertible_v) Id + OpLoopMerge(Id merge_block, Id continue_target, spv::LoopControlMask loop_control, + Ts&&... literals) { return OpLoopMerge(merge_block, continue_target, loop_control, std::span({literals...})); } @@ -357,8 +356,8 @@ public: /// Create a pointer into a composite object that can be used with OpLoad and OpStore. template - requires(... && std::is_convertible_v) - Id OpAccessChain(Id result_type, Id base, Ts&&... indexes) { + requires(...&& std::is_convertible_v) Id + OpAccessChain(Id result_type, Id base, Ts&&... indexes) { return OpAccessChain(result_type, base, std::span({indexes...})); } @@ -369,16 +368,14 @@ public: Id OpVectorInsertDynamic(Id result_type, Id vector, Id component, Id index); /// Select arbitrary components from two vectors to make a new vector. - Id OpVectorShuffle(Id result_type, Id vector_1, Id vector_2, - std::span components); + Id OpVectorShuffle(Id result_type, Id vector_1, Id vector_2, std::span components); /// Select arbitrary components from two vectors to make a new vector. template - requires(... && std::is_convertible_v) - Id OpVectorShuffle(Id result_type, Id vector_1, Id vector_2, Ts&&... components) { + requires(...&& std::is_convertible_v) Id + OpVectorShuffle(Id result_type, Id vector_1, Id vector_2, Ts&&... components) { const Literal stack_literals[] = {std::forward(components)...}; - return OpVectorShuffle(result_type, vector_1, vector_2, - std::span{stack_literals}); + return OpVectorShuffle(result_type, vector_1, vector_2, std::span{stack_literals}); } /// Make a copy of a composite object, while modifying one part of it. @@ -387,8 +384,8 @@ public: /// Make a copy of a composite object, while modifying one part of it. template - requires(... && std::is_convertible_v) - Id OpCompositeInsert(Id result_type, Id object, Id composite, Ts&&... indexes) { + requires(...&& std::is_convertible_v) Id + OpCompositeInsert(Id result_type, Id object, Id composite, Ts&&... indexes) { const Literal stack_indexes[] = {std::forward(indexes)...}; return OpCompositeInsert(result_type, object, composite, std::span{stack_indexes}); @@ -399,8 +396,8 @@ public: /// Extract a part of a composite object. template - requires(... && std::is_convertible_v) - Id OpCompositeExtract(Id result_type, Id composite, Ts&&... indexes) { + requires(...&& std::is_convertible_v) Id + OpCompositeExtract(Id result_type, Id composite, Ts&&... indexes) { const Literal stack_indexes[] = {std::forward(indexes)...}; return OpCompositeExtract(result_type, composite, std::span{stack_indexes}); } @@ -410,8 +407,8 @@ public: /// Construct a new composite object from a set of constituent objects that will fully form it. template - requires(... && std::is_convertible_v) - Id OpCompositeConstruct(Id result_type, Ts&&... ids) { + requires(...&& std::is_convertible_v) Id + OpCompositeConstruct(Id result_type, Ts&&... ids) { return OpCompositeConstruct(result_type, std::span({ids...})); } @@ -422,16 +419,15 @@ public: /// Add a decoration to target. template - requires(... && std::is_convertible_v) - Id Decorate(Id target, spv::Decoration decoration, Ts&&... literals) { + requires(...&& std::is_convertible_v) Id + Decorate(Id target, spv::Decoration decoration, Ts&&... literals) { const Literal stack_literals[] = {std::forward(literals)...}; return Decorate(target, decoration, std::span{stack_literals}); } /// Add a decoration to target. template - requires std::is_enum_v - Id Decorate(Id target, spv::Decoration decoration, T literal) { + requires std::is_enum_v Id Decorate(Id target, spv::Decoration decoration, T literal) { return Decorate(target, decoration, static_cast(literal)); } @@ -439,9 +435,9 @@ public: std::span literals = {}); template - requires(... && std::is_convertible_v) - Id MemberDecorate(Id structure_type, Literal member, spv::Decoration decoration, - Ts&&... literals) { + requires(...&& std::is_convertible_v) Id + MemberDecorate(Id structure_type, Literal member, spv::Decoration decoration, + Ts&&... literals) { const Literal stack_literals[] = {std::forward(literals)...}; return MemberDecorate(structure_type, member, decoration, std::span{stack_literals}); @@ -722,8 +718,8 @@ public: /// Execute an instruction in an imported set of extended instructions. template - requires(... && std::is_convertible_v) - Id OpExtInst(Id result_type, Id set, std::uint32_t instruction, Ts&&... operands) { + requires(...&& std::is_convertible_v) Id + OpExtInst(Id result_type, Id set, std::uint32_t instruction, Ts&&... operands) { return OpExtInst(result_type, set, instruction, std::span({operands...})); } @@ -797,8 +793,7 @@ public: /// Result is the reciprocal of sqrt x. Result is undefined if x <= 0. Id OpInverseSqrt(Id result_type, Id x); - /// Result is a floating-point number from x and the corresponding integral exponent of two in - /// exp. + /// Result is a floating-point number from x and the corresponding integral exponent of two in exp. Id OpLdexp(Id result_type, Id x, Id exp); /// Result is y if y < x; otherwise result is x. Which operand is the result is undefined if one @@ -813,8 +808,8 @@ public: /// integers. Id OpSMin(Id result_type, Id x, Id y); - /// Result is y if y < x, either x or y if both x and y are zeros, otherwise x. If one operand - /// is a NaN, the other operand is the result. If both operands are NaN, the result is a NaN. + /// Result is y if y < x, either x or y if both x and y are zeros, otherwise x. If one operand is a NaN, the other + /// operand is the result. If both operands are NaN, the result is a NaN. Id OpNMin(Id result_type, Id x, Id y); /// Result is y if x < y; otherwise result is x. Which operand is the result is undefined if one @@ -829,8 +824,8 @@ public: /// integers. Id OpSMax(Id result_type, Id x, Id y); - /// Result is y if x < y, either x or y if both x and y are zeros, otherwise x. If one operand - /// is a NaN, the other operand is the result. If both operands are NaN, the result is a NaN. + /// Result is y if x < y, either x or y if both x and y are zeros, otherwise x. If one operand is a NaN, the other + /// operand is the result. If both operands are NaN, the result is a NaN. Id OpNMax(Id result_type, Id x, Id y); /// Result is min(max(x, minVal), maxVal). Result is undefined if minVal > maxVal.The semantics @@ -948,9 +943,9 @@ public: /// Sample an image with an implicit level of detail. template - requires(... && std::is_convertible_v) - Id OpImageSampleImplicitLod(Id result_type, Id sampled_image, Id coordinate, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(...&& std::is_convertible_v) Id + OpImageSampleImplicitLod(Id result_type, Id sampled_image, Id coordinate, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleImplicitLod(result_type, sampled_image, coordinate, image_operands, std::span({operands...})); } @@ -962,9 +957,9 @@ public: /// Sample an image using an explicit level of detail. template - requires(... && std::is_convertible_v) - Id OpImageSampleExplicitLod(Id result_type, Id sampled_image, Id coordinate, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(...&& std::is_convertible_v) Id + OpImageSampleExplicitLod(Id result_type, Id sampled_image, Id coordinate, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleExplicitLod(result_type, sampled_image, coordinate, image_operands, std::span({operands...})); } @@ -977,9 +972,9 @@ public: /// Sample an image doing depth-comparison with an implicit level of detail. template - requires(... && std::is_convertible_v) - Id OpImageSampleDrefImplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(...&& std::is_convertible_v) Id + OpImageSampleDrefImplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleDrefImplicitLod(result_type, sampled_image, coordinate, dref, image_operands, std::span({operands...})); } @@ -991,9 +986,9 @@ public: /// Sample an image doing depth-comparison using an explicit level of detail. template - requires(... && std::is_convertible_v) - Id OpImageSampleDrefExplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(...&& std::is_convertible_v) Id + OpImageSampleDrefExplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleDrefExplicitLod(result_type, sampled_image, coordinate, dref, image_operands, std::span({operands...})); } @@ -1006,9 +1001,9 @@ public: /// Sample an image with with a project coordinate and an implicit level of detail. template - requires(... && std::is_convertible_v) - Id OpImageSampleProjImplicitLod(Id result_type, Id sampled_image, Id coordinate, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(...&& std::is_convertible_v) Id + OpImageSampleProjImplicitLod(Id result_type, Id sampled_image, Id coordinate, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleProjImplicitLod(result_type, sampled_image, coordinate, image_operands, std::span({operands...})); } @@ -1020,9 +1015,9 @@ public: /// Sample an image with a project coordinate using an explicit level of detail. template - requires(... && std::is_convertible_v) - Id OpImageSampleProjExplicitLod(Id result_type, Id sampled_image, Id coordinate, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(...&& std::is_convertible_v) Id + OpImageSampleProjExplicitLod(Id result_type, Id sampled_image, Id coordinate, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleProjExplicitLod(result_type, sampled_image, coordinate, image_operands, std::span({operands...})); } @@ -1037,9 +1032,9 @@ public: /// Sample an image with a project coordinate, doing depth-comparison, with an implicit level of /// detail. template - requires(... && std::is_convertible_v) - Id OpImageSampleProjDrefImplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(...&& std::is_convertible_v) Id + OpImageSampleProjDrefImplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleProjDrefImplicitLod(result_type, sampled_image, coordinate, dref, image_operands, std::span({operands...})); } @@ -1053,9 +1048,9 @@ public: /// Sample an image with a project coordinate, doing depth-comparison, using an explicit level /// of detail. template - requires(... && std::is_convertible_v) - Id OpImageSampleProjDrefExplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(...&& std::is_convertible_v) Id + OpImageSampleProjDrefExplicitLod(Id result_type, Id sampled_image, Id coordinate, Id dref, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageSampleProjDrefExplicitLod(result_type, sampled_image, coordinate, dref, image_operands, std::span({operands...})); } @@ -1067,9 +1062,9 @@ public: /// Fetch a single texel from an image whose Sampled operand is 1. template - requires(... && std::is_convertible_v) - Id OpImageFetch(Id result_type, Id sampled_image, Id coordinate, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(...&& std::is_convertible_v) Id + OpImageFetch(Id result_type, Id sampled_image, Id coordinate, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageFetch(result_type, sampled_image, coordinate, image_operands, std::span({operands...})); } @@ -1081,9 +1076,9 @@ public: /// Gathers the requested component from four texels. template - requires(... && std::is_convertible_v) - Id OpImageGather(Id result_type, Id sampled_image, Id coordinate, Id component, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(...&& std::is_convertible_v) Id + OpImageGather(Id result_type, Id sampled_image, Id coordinate, Id component, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageGather(result_type, sampled_image, coordinate, component, image_operands, std::span({operands...})); } @@ -1095,9 +1090,9 @@ public: /// Gathers the requested depth-comparison from four texels. template - requires(... && std::is_convertible_v) - Id OpImageDrefGather(Id result_type, Id sampled_image, Id coordinate, Id dref, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(...&& std::is_convertible_v) Id + OpImageDrefGather(Id result_type, Id sampled_image, Id coordinate, Id dref, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageDrefGather(result_type, sampled_image, coordinate, dref, image_operands, std::span({operands...})); } @@ -1109,9 +1104,9 @@ public: /// Read a texel from an image without a sampler. template - requires(... && std::is_convertible_v) - Id OpImageRead(Id result_type, Id sampled_image, Id coordinate, - spv::ImageOperandsMask image_operands, Ts&&... operands) { + requires(...&& std::is_convertible_v) Id + OpImageRead(Id result_type, Id sampled_image, Id coordinate, + spv::ImageOperandsMask image_operands, Ts&&... operands) { return OpImageRead(result_type, sampled_image, coordinate, image_operands, std::span({operands...})); } @@ -1123,9 +1118,9 @@ public: /// Write a texel to an image without a sampler. template - requires(... && std::is_convertible_v) - Id OpImageWrite(Id image, Id coordinate, Id texel, spv::ImageOperandsMask image_operands, - Ts&&... operands) { + requires(...&& std::is_convertible_v) Id + OpImageWrite(Id image, Id coordinate, Id texel, spv::ImageOperandsMask image_operands, + Ts&&... operands) { return OpImageWrite(image, coordinate, texel, image_operands, std::span({operands...})); } From 339ed29ccbdabe90749127c242203b9772292efa Mon Sep 17 00:00:00 2001 From: Frodo Baggins Date: Fri, 20 Sep 2024 18:42:27 -0700 Subject: [PATCH 5/5] add description for instruction --- include/sirit/sirit.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/include/sirit/sirit.h b/include/sirit/sirit.h index 7470eed..065496f 100644 --- a/include/sirit/sirit.h +++ b/include/sirit/sirit.h @@ -1347,6 +1347,8 @@ public: /// 3) store the New Value back through Pointer. Id OpAtomicXor(Id result_type, Id pointer, Id memory, Id semantics, Id value); + // Print a message for vulkan layers to use, e.g. renderdoc + // Usage is like C printf Id OpDebugPrintf(Id fmt, std::span fmt_args); private: