Browse Source

[spirv] Add support for SV_ViewportIndex (#796)

Lei Zhang 8 years ago
parent
commit
0d462693b5

+ 4 - 0
docs/SPIR-V.rst

@@ -833,6 +833,10 @@ some system-value (SV) semantic strings will be translated into SPIR-V
 | SV_RenderTargetArrayIndex +-------------+--------------------------+-----------------------+
 | SV_RenderTargetArrayIndex +-------------+--------------------------+-----------------------+
 |                           | PSIn        | ``Layer``                | N/A                   |
 |                           | PSIn        | ``Layer``                | N/A                   |
 +---------------------------+-------------+--------------------------+-----------------------+
 +---------------------------+-------------+--------------------------+-----------------------+
+|                           | GSOut       | ``ViewportIndex``        | N/A                   |
+| SV_ViewportArrayIndex     +-------------+--------------------------+-----------------------+
+|                           | PSIn        | ``ViewportIndex``        | N/A                   |
++---------------------------+-------------+--------------------------+-----------------------+
 
 
 [TODO] add other SV semantic strings in the above
 [TODO] add other SV semantic strings in the above
 
 

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

@@ -1403,6 +1403,32 @@ uint32_t DeclResultIdMapper::createSpirvStageVar(StageVar *stageVar,
       llvm_unreachable("invalid usage of SV_RenderTargetArrayIndex sneaked in");
       llvm_unreachable("invalid usage of SV_RenderTargetArrayIndex sneaked in");
     }
     }
   }
   }
+  // According to DXIL spec, the ViewportArrayIndex SV can only be used by
+  // VSIn, VSOut, HSCPIn, HSCPOut, DSIn, DSOut, GSVIn, GSOut, PSIn.
+  // According to Vulkan spec, the ViewportIndex BuiltIn can only be used in
+  // GSOut and PSIn.
+  case hlsl::Semantic::Kind::ViewPortArrayIndex: {
+    switch (sigPointKind) {
+    case hlsl::SigPoint::Kind::VSIn:
+    case hlsl::SigPoint::Kind::VSOut:
+    case hlsl::SigPoint::Kind::HSCPIn:
+    case hlsl::SigPoint::Kind::HSCPOut:
+    case hlsl::SigPoint::Kind::PCOut:
+    case hlsl::SigPoint::Kind::DSIn:
+    case hlsl::SigPoint::Kind::DSCPIn:
+    case hlsl::SigPoint::Kind::DSOut:
+    case hlsl::SigPoint::Kind::GSVIn:
+      return theBuilder.addStageIOVar(type, sc, name.str());
+    case hlsl::SigPoint::Kind::GSOut:
+    case hlsl::SigPoint::Kind::PSIn:
+      theBuilder.requireCapability(spv::Capability::MultiViewport);
+
+      stageVar->setIsSpirvBuiltin();
+      return theBuilder.addStageBuiltinVar(type, sc, BuiltIn::ViewportIndex);
+    default:
+      llvm_unreachable("invalid usage of SV_ViewportArrayIndex sneaked in");
+    }
+  }
   default:
   default:
     emitError("semantic %0 unimplemented", srcLoc)
     emitError("semantic %0 unimplemented", srcLoc)
         << stageVar->getSemantic()->GetName();
         << stageVar->getSemantic()->GetName();

+ 2 - 0
tools/clang/test/CodeGenSPIRV/semantic.stencil-ref.ps.hlsl

@@ -4,6 +4,8 @@
 
 
 // CHECK: OpExtension "SPV_EXT_shader_stencil_export"
 // CHECK: OpExtension "SPV_EXT_shader_stencil_export"
 
 
+// TODO: we may need to check the StencilRefReplacingEXT execution mode here.
+
 // CHECK: OpEntryPoint Fragment %main "main" [[StencilRef:%\d+]]
 // CHECK: OpEntryPoint Fragment %main "main" [[StencilRef:%\d+]]
 
 
 // CEHCK: OpDecorate [[StencilRef]] BuiltIn FragStencilRefEXT
 // CEHCK: OpDecorate [[StencilRef]] BuiltIn FragStencilRefEXT

+ 39 - 0
tools/clang/test/CodeGenSPIRV/semantic.viewport-array-index.ds.hlsl

@@ -0,0 +1,39 @@
+// Run: %dxc -T ds_6_0 -E main
+
+// HS PCF output
+struct HsPcfOut {
+  float  outTessFactor[4]   : SV_TessFactor;
+  float  inTessFactor[2]    : SV_InsideTessFactor;
+  uint   index              : SV_ViewportArrayIndex;
+};
+
+// Per-vertex input structs
+struct DsCpIn {
+  uint   index              : SV_ViewportArrayIndex;
+};
+
+// Per-vertex output structs
+struct DsCpOut {
+  uint   index              : SV_ViewportArrayIndex;
+};
+
+// CHECK:      OpEntryPoint TessellationEvaluation %main "main"
+// CHECK-SAME: %in_var_SV_ViewportArrayIndex
+// CHECK-SAME: %in_var_SV_ViewportArrayIndex_0
+// CHECK-SAME: %out_var_SV_ViewportArrayIndex
+
+
+// CHECK:      OpDecorate %in_var_SV_ViewportArrayIndex Location 0
+// CHECK:      OpDecorate %in_var_SV_ViewportArrayIndex_0 Location 1
+// CHECK:      OpDecorate %out_var_SV_ViewportArrayIndex Location 0
+
+// CHECK:      %in_var_SV_ViewportArrayIndex = OpVariable %_ptr_Input__arr_uint_uint_3 Input
+// CHECK:      %in_var_SV_ViewportArrayIndex_0 = OpVariable %_ptr_Input_uint Input
+// CHECK:      %out_var_SV_ViewportArrayIndex = OpVariable %_ptr_Output_uint Output
+
+[domain("quad")]
+DsCpOut main(OutputPatch<DsCpIn, 3> patch, HsPcfOut pcfData) {
+  DsCpOut dsOut;
+  dsOut = (DsCpOut)0;
+  return dsOut;
+}

+ 34 - 0
tools/clang/test/CodeGenSPIRV/semantic.viewport-array-index.gs.hlsl

@@ -0,0 +1,34 @@
+// Run: %dxc -T gs_6_0 -E main
+
+// CHECK:      OpCapability MultiViewport
+
+// CHECK:      OpEntryPoint Geometry %main "main"
+// CHECK-SAME: %in_var_SV_ViewportArrayIndex
+// CHECK-SAME: %gl_ViewportIndex
+
+// CHECK:      OpDecorate %gl_ViewportIndex BuiltIn ViewportIndex
+// CHECK:      OpDecorate %in_var_SV_ViewportArrayIndex Location 0
+
+// CHECK:      %in_var_SV_ViewportArrayIndex = OpVariable %_ptr_Input__arr_uint_uint_2 Input
+// CHECK:      %gl_ViewportIndex = OpVariable %_ptr_Output_uint Output
+
+// GS per-vertex input
+struct GsVIn {
+  uint index : SV_ViewportArrayIndex;
+};
+
+// GS per-vertex output
+struct GsVOut {
+  uint index : SV_ViewportArrayIndex;
+};
+
+[maxvertexcount(2)]
+void main(in    line GsVIn              inData[2],
+          inout      LineStream<GsVOut> outData) {
+
+    GsVOut vertex;
+    vertex = (GsVOut)0;
+    outData.Append(vertex);
+
+    outData.RestartStrip();
+}

+ 49 - 0
tools/clang/test/CodeGenSPIRV/semantic.viewport-array-index.hs.hlsl

@@ -0,0 +1,49 @@
+// Run: %dxc -T hs_6_0 -E main
+
+#define NumOutPoints 2
+
+// CHECK:      OpEntryPoint TessellationControl %main "main"
+// CHECK-SAME: %in_var_SV_ViewportArrayIndex
+// CHECK-SAME: %out_var_SV_ViewportArrayIndex
+// CHECK-SAME: %out_var_SV_ViewportArrayIndex_0
+
+// CHECK:      OpDecorate %in_var_SV_ViewportArrayIndex Location 0
+// CHECK:      OpDecorate %out_var_SV_ViewportArrayIndex Location 0
+// CHECK:      OpDecorate %out_var_SV_ViewportArrayIndex_0 Location 1
+
+// CHECK:      %in_var_SV_ViewportArrayIndex = OpVariable %_ptr_Input__arr_uint_uint_2 Input
+// CHECK:      %out_var_SV_ViewportArrayIndex = OpVariable %_ptr_Output__arr_uint_uint_2 Output
+// CHECK:      %out_var_SV_ViewportArrayIndex_0 = OpVariable %_ptr_Output_uint Output
+
+struct HsCpIn {
+    uint index : SV_ViewportArrayIndex;
+};
+
+struct HsCpOut {
+    uint index : SV_ViewportArrayIndex;
+};
+
+struct HsPcfOut {
+  float tessOuter[4] : SV_TessFactor;
+  float tessInner[2] : SV_InsideTessFactor;
+  uint  index        : SV_ViewportArrayIndex;
+};
+
+// Patch Constant Function
+HsPcfOut pcf() {
+  HsPcfOut output;
+  output = (HsPcfOut)0;
+  return output;
+}
+
+[domain("quad")]
+[partitioning("fractional_odd")]
+[outputtopology("triangle_ccw")]
+[outputcontrolpoints(NumOutPoints)]
+[patchconstantfunc("pcf")]
+HsCpOut main(InputPatch<HsCpIn, NumOutPoints> patch,
+             uint id : SV_OutputControlPointID) {
+    HsCpOut output;
+    output = (HsCpOut)0;
+    return output;
+}

+ 14 - 0
tools/clang/test/CodeGenSPIRV/semantic.viewport-array-index.ps.hlsl

@@ -0,0 +1,14 @@
+// Run: %dxc -T ps_6_0 -E main
+
+// CHECK:      OpCapability MultiViewport
+
+// CHECK:      OpEntryPoint Fragment %main "main"
+// CHECK-SAME: %gl_ViewportIndex
+
+// CHECK:      OpDecorate %gl_ViewportIndex BuiltIn ViewportIndex
+
+// CHECK:      %gl_ViewportIndex = OpVariable %_ptr_Input_uint Input
+
+float4 main(uint input: SV_ViewportArrayIndex) : SV_Target {
+    return input;
+}

+ 15 - 0
tools/clang/test/CodeGenSPIRV/semantic.viewport-array-index.vs.hlsl

@@ -0,0 +1,15 @@
+// Run: %dxc -T vs_6_0 -E main
+
+// CHECK:      OpEntryPoint Vertex %main "main"
+// CHECK-SAME: %in_var_SV_ViewportArrayIndex
+// CHECK-SMAE: %out_var_SV_ViewportArrayIndex
+
+// CHECK:      OpDecorate %in_var_SV_ViewportArrayIndex Location 0
+// CHECK:      OpDecorate %out_var_SV_ViewportArrayIndex Location 0
+
+// CHECK:      %in_var_SV_ViewportArrayIndex = OpVariable %_ptr_Input_uint Input
+// CHECK:      %out_var_SV_ViewportArrayIndex = OpVariable %_ptr_Output_uint Output
+
+uint main(uint input: SV_ViewportArrayIndex) : SV_ViewportArrayIndex {
+    return input;
+}

+ 15 - 0
tools/clang/unittests/SPIRV/CodeGenSPIRVTest.cpp

@@ -477,6 +477,21 @@ TEST_F(FileTest, SemanticRenderTargetArrayIndexGS) {
 TEST_F(FileTest, SemanticRenderTargetArrayIndexPS) {
 TEST_F(FileTest, SemanticRenderTargetArrayIndexPS) {
   runFileTest("semantic.render-target-array-index.ps.hlsl");
   runFileTest("semantic.render-target-array-index.ps.hlsl");
 }
 }
+TEST_F(FileTest, SemanticViewportArrayIndexVS) {
+  runFileTest("semantic.viewport-array-index.vs.hlsl");
+}
+TEST_F(FileTest, SemanticViewportArrayIndexHS) {
+  runFileTest("semantic.viewport-array-index.hs.hlsl");
+}
+TEST_F(FileTest, SemanticViewportArrayIndexDS) {
+  runFileTest("semantic.viewport-array-index.ds.hlsl");
+}
+TEST_F(FileTest, SemanticViewportArrayIndexGS) {
+  runFileTest("semantic.viewport-array-index.gs.hlsl");
+}
+TEST_F(FileTest, SemanticViewportArrayIndexPS) {
+  runFileTest("semantic.viewport-array-index.ps.hlsl");
+}
 
 
 // For texture methods
 // For texture methods
 TEST_F(FileTest, TextureSample) { runFileTest("texture.sample.hlsl"); }
 TEST_F(FileTest, TextureSample) { runFileTest("texture.sample.hlsl"); }