2
0
Эх сурвалжийг харах

SPIR-V: Emit RayTmaxKHR builtin for RayTCurrent IOP (#3320)

* SPIR-V: Emit RayTmaxKHR builtin for RayTCurrent IOP

HitTKHR was [removed] from the spec as it merely shadows RayTmaxKHR.
Emitting it results in invalid SPIR-V:

    generated SPIR-V is invalid: Operand 3 of Decorate requires one of these capabilities: RayTracingNV
      OpDecorate %6 BuiltIn HitTNV

Replace the builtin by RayTmaxKHR if NV_ray_tracing enabled to resolve
this.

[removed]: https://github.com/KhronosGroup/SPIRV-Headers/commit/bdd2aa34c450edb77441c82fdc2f20f1dc9d833d

* test/CodeGenSPIRV: Test RayTCurrent for RayTmax or HitT builtin
Marijn Suijten 4 жил өмнө
parent
commit
f3ba78bf6b

+ 1 - 0
tools/clang/lib/SPIRV/DeclResultIdMapper.cpp

@@ -2895,6 +2895,7 @@ SpirvVariable *DeclResultIdMapper::getBuiltinVar(spv::BuiltIn builtIn,
   case spv::BuiltIn::SubgroupSize:
   case spv::BuiltIn::SubgroupLocalInvocationId:
   case spv::BuiltIn::HitTNV:
+  case spv::BuiltIn::RayTmaxNV:
   case spv::BuiltIn::RayTminNV:
   case spv::BuiltIn::HitKindNV:
   case spv::BuiltIn::IncomingRayFlagsNV:

+ 6 - 1
tools/clang/lib/SPIRV/SpirvEmitter.cpp

@@ -9814,6 +9814,8 @@ SpirvEmitter::processIntrinsicLog10(const CallExpr *callExpr) {
 
 SpirvInstruction *SpirvEmitter::processRayBuiltins(const CallExpr *callExpr,
                                                    hlsl::IntrinsicOp op) {
+  bool nvRayTracing =
+      featureManager.isExtensionEnabled(Extension::NV_ray_tracing);
   spv::BuiltIn builtin = spv::BuiltIn::Max;
   bool transposeMatrix = false;
   const auto loc = callExpr->getExprLoc();
@@ -9825,7 +9827,10 @@ SpirvInstruction *SpirvEmitter::processRayBuiltins(const CallExpr *callExpr,
     builtin = spv::BuiltIn::LaunchIdNV;
     break;
   case hlsl::IntrinsicOp::IOP_RayTCurrent:
-    builtin = spv::BuiltIn::HitTNV;
+    if (nvRayTracing)
+      builtin = spv::BuiltIn::HitTNV;
+    else
+      builtin = spv::BuiltIn::RayTmaxKHR;
     break;
   case hlsl::IntrinsicOp::IOP_RayTMin:
     builtin = spv::BuiltIn::RayTminNV;

+ 3 - 0
tools/clang/test/CodeGenSPIRV/raytracing.khr.closesthit.hlsl

@@ -16,6 +16,7 @@
 // CHECK:  OpDecorate [[k:%\d+]] BuiltIn WorldToObjectNV
 // CHECK:  OpDecorate [[l:%\d+]] BuiltIn HitKindNV
 // CHECK:  OpDecorate [[m:%\d+]] BuiltIn RayGeometryIndexKHR
+// CHECK:  OpDecorate [[n:%\d+]] BuiltIn RayTmaxNV
 
 // CHECK:  OpTypePointer IncomingRayPayloadNV %Payload
 struct Payload
@@ -75,6 +76,8 @@ void main(inout Payload MyPayload, in Attribute MyAttr) {
   uint _16 = HitKind();
 // CHECK:  OpLoad %uint [[m]]
   uint _17 = GeometryIndex();
+// CHECK:  OpLoad %float [[n]]
+  uint _18 = RayTCurrent();
 
   Payload myPayload = { float4(0.0f,0.0f,0.0f,0.0f) };
   CallData myCallData = { float4(0.0f,0.0f,0.0f,0.0f) };

+ 3 - 0
tools/clang/test/CodeGenSPIRV/raytracing.nv.anyhit.hlsl

@@ -15,6 +15,7 @@
 // CHECK:  OpDecorate [[j:%\d+]] BuiltIn ObjectToWorldNV
 // CHECK:  OpDecorate [[k:%\d+]] BuiltIn WorldToObjectNV
 // CHECK:  OpDecorate [[l:%\d+]] BuiltIn HitKindNV
+// CHECK:  OpDecorate [[m:%\d+]] BuiltIn HitTNV
 
 // CHECK:  OpTypePointer IncomingRayPayloadNV %Payload
 struct Payload
@@ -67,6 +68,8 @@ void main(inout Payload MyPayload, in Attribute MyAttr) {
   float4x3 _15 = WorldToObject4x3();
 // CHECK:  OpLoad %uint [[l]]
   uint _16 = HitKind();
+// CHECK:  OpLoad %float [[m]]
+  uint _17 = RayTCurrent();
 
   if (_16 == 1U) {
 // CHECK:  [[payloadread0:%\d+]] = OpLoad %Payload %MyPayload_0

+ 3 - 0
tools/clang/test/CodeGenSPIRV/raytracing.nv.closesthit.hlsl

@@ -15,6 +15,7 @@
 // CHECK:  OpDecorate [[j:%\d+]] BuiltIn ObjectToWorldNV
 // CHECK:  OpDecorate [[k:%\d+]] BuiltIn WorldToObjectNV
 // CHECK:  OpDecorate [[l:%\d+]] BuiltIn HitKindNV
+// CHECK:  OpDecorate [[m:%\d+]] BuiltIn HitTNV
 
 // CHECK:  OpTypePointer IncomingRayPayloadNV %Payload
 struct Payload
@@ -67,6 +68,8 @@ void main(inout Payload MyPayload, in Attribute MyAttr) {
   float4x3 _15 = WorldToObject4x3();
 // CHECK:  OpLoad %uint [[l]]
   uint _16 = HitKind();
+// CHECK:  OpLoad %float [[m]]
+  uint _17 = RayTCurrent();
 
   Payload myPayload = { float4(0.0f,0.0f,0.0f,0.0f) };
   RayDesc rayDesc;