git.s-ol.nu ~forks/DiligentCore / 0606e96
Unified pipeline resource compatibility validation in D3D12 and Vk; added more PRS creation failure tests assiduous 6 months ago
5 changed file(s) with 324 addition(s) and 133 deletion(s). Raw diff Collapse all Expand all
5050 void ValidateComputePipelineCreateInfo(const ComputePipelineStateCreateInfo& CreateInfo) noexcept(false);
5151 void ValidateRayTracingPipelineCreateInfo(IRenderDevice* pDevice, Uint32 MaxRecursion, const RayTracingPipelineStateCreateInfo& CreateInfo) noexcept(false);
5252
53 /// Validates that pipeline resource description 'ResDesc' is compatible with the actual resource
54 /// attributes and throws an exception in case of an error.
55 void ValidatePipelineResourceCompatibility(const PipelineResourceDesc& ResDesc,
56 SHADER_RESOURCE_TYPE Type,
57 PIPELINE_RESOURCE_FLAGS ResourceFlags,
58 Uint32 ArraySize,
59 const char* ShaderName,
60 const char* SignatureName) noexcept(false);
61
62
5363 /// Copies ray tracing shader group names and also initializes the mapping from the group name to its index.
5464 void CopyRTShaderGroupNames(std::unordered_map<HashMapStringKey, Uint32, HashMapStringKey::Hasher>& NameToGroupIndex,
5565 const RayTracingPipelineStateCreateInfo& CreateInfo,
513513 #undef VALIDATE_SHADER_TYPE
514514 #undef LOG_PSO_ERROR_AND_THROW
515515
516 void ValidatePipelineResourceCompatibility(const PipelineResourceDesc& ResDesc,
517 SHADER_RESOURCE_TYPE Type,
518 PIPELINE_RESOURCE_FLAGS ResourceFlags,
519 Uint32 ArraySize,
520 const char* ShaderName,
521 const char* SignatureName) noexcept(false)
522 {
523 if (Type != ResDesc.ResourceType)
524 {
525 LOG_ERROR_AND_THROW("Shader '", ShaderName, "' contains resource with name '", ResDesc.Name,
526 "' and type '", GetShaderResourceTypeLiteralName(Type), "' that is not compatible with type '",
527 GetShaderResourceTypeLiteralName(ResDesc.ResourceType), "' specified in pipeline resource signature '", SignatureName, "'.");
528 }
529
530 if ((ResourceFlags & PIPELINE_RESOURCE_FLAG_FORMATTED_BUFFER) != (ResDesc.Flags & PIPELINE_RESOURCE_FLAG_FORMATTED_BUFFER))
531 {
532 LOG_ERROR_AND_THROW("Shader '", ShaderName, "' contains resource '", ResDesc.Name,
533 "' that is", ((ResourceFlags & PIPELINE_RESOURCE_FLAG_FORMATTED_BUFFER) ? "" : " not"),
534 " labeled as formatted buffer, while the same resource specified by the pipeline resource signature '",
535 SignatureName, "' is", ((ResDesc.Flags & PIPELINE_RESOURCE_FLAG_FORMATTED_BUFFER) ? "" : " not"),
536 " labeled as such.");
537 }
538
539 VERIFY(ResDesc.ArraySize > 0, "ResDesc.ArraySize can't be zero. This error should've be caught by ValidatePipelineResourceSignatureDesc().");
540
541 if (ArraySize == 0)
542 {
543 // ArraySize == 0 means that the resource is a runtime-sized array and ResDesc.ArraySize from the
544 // resource signature may have any non-zero value.
545 if ((ResDesc.Flags & PIPELINE_RESOURCE_FLAG_RUNTIME_ARRAY) == 0)
546 {
547 LOG_ERROR_AND_THROW("Shader '", ShaderName, "' contains resource '", ResDesc.Name,
548 "' that is a runtime-sized array, but in the resource signature '", SignatureName,
549 "' the resource is defined without the PIPELINE_RESOURCE_FLAG_RUNTIME_ARRAY flag.");
550 }
551 }
552 else
553 {
554 if (ResDesc.ArraySize < ArraySize)
555 {
556 LOG_ERROR_AND_THROW("Shader '", ShaderName, "' contains resource '", ResDesc.Name,
557 "' whose array size (", ArraySize, ") is greater than the array size (",
558 ResDesc.ArraySize, ") specified by the pipeline resource signature '", SignatureName, "'.");
559 }
560
561 //if (ResDesc.Flags & PIPELINE_RESOURCE_FLAG_RUNTIME_ARRAY)
562 //{
563 // LOG_WARNING_MESSAGE("Shader '", ShaderName, "' contains resource with name '", ResDesc.Name,
564 // "' that is defined in resource signature '", SignatureName,
565 // "' with flag PIPELINE_RESOURCE_FLAG_RUNTIME_ARRAY, but the resource is not a runtime-sized array.");
566 //}
567 }
568 }
569
516570 void CorrectGraphicsPipelineDesc(GraphicsPipelineDesc& GraphicsPipeline) noexcept
517571 {
518572 CorrectBlendStateDesc(GraphicsPipeline);
649649 if (IsDXILBytecode(pBytecode->GetBufferPointer(), pBytecode->GetBufferSize()))
650650 {
651651 if (!compiler)
652 LOG_ERROR_AND_THROW("DXC compiler is not exists, can not remap resource bindings");
652 LOG_ERROR_AND_THROW("DXC compiler does not exists, can not remap resource bindings");
653653
654654 if (!compiler->RemapResourceBindings(ResourceMap, reinterpret_cast<IDxcBlob*>(pBytecode.p), reinterpret_cast<IDxcBlob**>(&pBlob)))
655655 LOG_ERROR_AND_THROW("Failed to remap resource bindings in shader '", pShader->GetDesc().Name, "'.");
730730
731731 if (ResAttribution.ResourceIndex != ResourceAttribution::InvalidResourceIndex)
732732 {
733 const auto& ResDesc = pSignature->GetResourceDesc(ResAttribution.ResourceIndex);
734
735 auto ResourceType = ResDesc.ResourceType;
736 if (ResourceType == SHADER_RESOURCE_TYPE_INPUT_ATTACHMENT)
737 ResourceType = SHADER_RESOURCE_TYPE_TEXTURE_SRV;
738 if (Type != ResourceType)
739 {
740 LOG_ERROR_AND_THROW("Shader '", pShader->GetDesc().Name, "' contains resource with name '", Attribs.Name,
741 "' and type '", GetShaderResourceTypeLiteralName(Type), "' that is not compatible with type '",
742 GetShaderResourceTypeLiteralName(ResDesc.ResourceType), "' in pipeline resource signature '", pSignature->GetDesc().Name, "'.");
743 }
744
745 if ((Flags & PIPELINE_RESOURCE_FLAG_FORMATTED_BUFFER) != (ResDesc.Flags & PIPELINE_RESOURCE_FLAG_FORMATTED_BUFFER))
746 {
747 LOG_ERROR_AND_THROW("Shader '", pShader->GetDesc().Name, "' contains resource '", Attribs.Name,
748 "' that is", ((Flags & PIPELINE_RESOURCE_FLAG_FORMATTED_BUFFER) ? "" : " not"),
749 " labeled as formatted buffer, while the same resource specified by the pipeline resource signature '",
750 pSignature->GetDesc().Name, "' is", ((ResDesc.Flags & PIPELINE_RESOURCE_FLAG_FORMATTED_BUFFER) ? "" : " not"),
751 " labeled as such.");
752 }
753
754 if (Attribs.BindCount == 0)
755 {
756 if ((ResDesc.Flags & PIPELINE_RESOURCE_FLAG_RUNTIME_ARRAY) == 0)
757 {
758 LOG_ERROR_AND_THROW("Shader '", pShader->GetDesc().Name, "' contains resource with name '", Attribs.Name,
759 "' that is runtime-sized array, but in resource signature '", pSignature->GetDesc().Name,
760 "' resource defined without PIPELINE_RESOURCE_FLAG_RUNTIME_ARRAY flag.");
761 }
762 }
763 else
764 {
765 if (ResDesc.ArraySize < Attribs.BindCount)
766 {
767 LOG_ERROR_AND_THROW("Shader '", pShader->GetDesc().Name, "' contains resource '", Attribs.Name,
768 "' whose array size (", Attribs.BindCount, ") is greater than the array size (",
769 ResDesc.ArraySize, ") specified by the pipeline resource signature '", pSignature->GetDesc().Name, "'.");
770 }
771
772 if (ResDesc.Flags & PIPELINE_RESOURCE_FLAG_RUNTIME_ARRAY)
773 {
774 LOG_WARNING_MESSAGE("Shader '", pShader->GetDesc().Name, "' contains resource with name '", Attribs.Name,
775 "' that defined in resource signature '", pSignature->GetDesc().Name,
776 "' with flag PIPELINE_RESOURCE_FLAG_RUNTIME_ARRAY, but resource is not a runtime-sized array.");
777 }
778 }
733 auto ResDesc = pSignature->GetResourceDesc(ResAttribution.ResourceIndex);
734 if (ResDesc.ResourceType == SHADER_RESOURCE_TYPE_INPUT_ATTACHMENT)
735 ResDesc.ResourceType = SHADER_RESOURCE_TYPE_TEXTURE_SRV;
736 ValidatePipelineResourceCompatibility(ResDesc, Type, Flags, Attribs.BindCount,
737 pShader->GetDesc().Name, pSignature->GetDesc().Name);
779738 }
780739 else if (ResAttribution.ImmutableSamplerIndex != ResourceAttribution::InvalidResourceIndex)
781740 {
921921 }
922922 if (!Info)
923923 {
924 LOG_ERROR_AND_THROW("Shader '", pShader->GetDesc().Name, "' contains resource with name '", SPIRVAttribs.Name,
925 "' that is not present in any pipeline resource signature that is used to create pipeline state '",
924 LOG_ERROR_AND_THROW("Shader '", pShader->GetDesc().Name, "' contains resource '", SPIRVAttribs.Name,
925 "' that is not present in any pipeline resource signature used to create pipeline state '",
926926 m_Desc.Name, "'.");
927927 }
928928
933933 {
934934 LOG_ERROR_AND_THROW("Shader '", pShader->GetDesc().Name, "' contains resource with name '", SPIRVAttribs.Name,
935935 "' and type '", GetShaderResourceTypeLiteralName(Type), "' that is not compatible with type '",
936 GetShaderResourceTypeLiteralName(Info.Type), "' in pipeline resource signature '", Info.Signature->GetDesc().Name, "'.");
936 GetShaderResourceTypeLiteralName(Info.Type), "' specified in pipeline resource signature '", Info.Signature->GetDesc().Name, "'.");
937937 }
938938
939939 if (Info.ResIndex != ~0u)
940940 {
941941 const auto& ResDesc = Info.Signature->GetResourceDesc(Info.ResIndex);
942
943 if ((Flags & PIPELINE_RESOURCE_FLAG_FORMATTED_BUFFER) != (ResDesc.Flags & PIPELINE_RESOURCE_FLAG_FORMATTED_BUFFER))
944 {
945 LOG_ERROR_AND_THROW("Shader '", pShader->GetDesc().Name, "' contains resource '", SPIRVAttribs.Name,
946 "' that is", ((Flags & PIPELINE_RESOURCE_FLAG_FORMATTED_BUFFER) ? "" : " not"),
947 " labeled as formatted buffer, while the same resource specified by the pipeline resource signature '",
948 Info.Signature->GetDesc().Name, "' is", ((ResDesc.Flags & PIPELINE_RESOURCE_FLAG_FORMATTED_BUFFER) ? "" : " not"),
949 " labeled as such.");
950 }
951
952 // SPIRVAttribs.ArraySize == 0 means that the resource is a runtime-sized array and ResDesc.ArraySize from the
953 // resource signature may have any non-zero value.
954 VERIFY(ResDesc.ArraySize > 0, "ResDesc.ArraySize can't be zero. This error should've be caught by ValidatePipelineResourceSignatureDesc().");
955 if (ResDesc.ArraySize < SPIRVAttribs.ArraySize)
956 {
957 LOG_ERROR_AND_THROW("Shader '", pShader->GetDesc().Name, "' contains resource '", SPIRVAttribs.Name,
958 "' whose array size (", SPIRVAttribs.ArraySize, ") is greater than the array size (",
959 ResDesc.ArraySize, ") specified by the pipeline resource signature '", Info.Signature->GetDesc().Name, "'.");
960 }
942 ValidatePipelineResourceCompatibility(ResDesc, Type, Flags, SPIRVAttribs.ArraySize,
943 pShader->GetDesc().Name, Info.Signature->GetDesc().Name);
961944 }
962
963945 SPIRV[SPIRVAttribs.BindingDecorationOffset] = Info.BindingIndex;
964946 SPIRV[SPIRVAttribs.DescriptorSetDecorationOffset] = Info.DescrSetIndex;
965947
3838 namespace
3939 {
4040
41 static const char g_TrivialVSSource[] = R"(
41 static constexpr char g_TrivialVSSource[] = R"(
4242 void main(out float4 pos : SV_Position)
4343 {
4444 pos = float4(0.0, 0.0, 0.0, 0.0);
4545 }
4646 )";
4747
48 static const char g_TrivialPSSource[] = R"(
48 static constexpr char g_TrivialPSSource[] = R"(
4949 float4 main() : SV_Target
5050 {
5151 return float4(0.0, 0.0, 0.0, 0.0);
5252 }
5353 )";
5454
55 static const char g_TrivialMSSource[] = R"(
55 static constexpr char g_TexturePSSource[] = R"(
56 Texture2D g_Texture;
57 float4 main() : SV_Target
58 {
59 return g_Texture.Load(int3(0,0,0));
60 }
61 )";
62
63 static constexpr char g_TrivialMSSource[] = R"(
5664 struct VertexOut
5765 {
5866 float4 Pos : SV_Position;
7280 }
7381 )";
7482
75 static const char g_TrivialCSSource[] = R"(
83 static constexpr char g_TrivialCSSource[] = R"(
7684 [numthreads(8,8,1)]
7785 void main()
7886 {
7987 }
8088 )";
8189
82 static const char g_TrivialRGenSource[] = R"(
90 static constexpr char g_TrivialRGenSource[] = R"(
8391 [shader("raygeneration")]
8492 void main()
8593 {}
8694 )";
8795
88 static const char g_TrivialRMissSource[] = R"(
96 static constexpr char g_TrivialRMissSource[] = R"(
8997 struct RTPayload { float4 Color; };
9098 [shader("miss")]
9199 void main(inout RTPayload payload)
92100 {}
93101 )";
94102
95 static const char g_TrivialRCHitSource[] = R"(
103 static constexpr char g_TrivialRCHitSource[] = R"(
96104 struct RTPayload { float4 Color; };
97105 [shader("closesthit")]
98106 void main(inout RTPayload payload, in BuiltInTriangleIntersectionAttributes attr)
99107 {}
100108 )";
101109
102 static const char g_TrivialRAHitSource[] = R"(
110 static constexpr char g_TrivialRAHitSource[] = R"(
103111 struct RTPayload { float4 Color; };
104112 [shader("anyhit")]
105113 void main(inout RTPayload payload, in BuiltInTriangleIntersectionAttributes attr)
106114 {}
107115 )";
108116
109 static const char g_TrivialRIntSource[] = R"(
117 static constexpr char g_TrivialRIntSource[] = R"(
110118 [shader("intersection")]
111119 void main()
112120 {}
113121 )";
114122
115 static const char g_TrivialRCallSource[] = R"(
123 static constexpr char g_TrivialRCallSource[] = R"(
116124 struct Params { float4 Col; };
117125 [shader("callable")]
118126 void main(inout Params params)
131139 sm_HasMeshShader = pDevice->GetDeviceCaps().Features.MeshShaders;
132140 sm_HasRayTracing = pDevice->GetDeviceCaps().Features.RayTracing;
133141
134 ShaderCreateInfo Attrs;
135 Attrs.Source = g_TrivialVSSource;
136 Attrs.EntryPoint = "main";
137 Attrs.Desc.ShaderType = SHADER_TYPE_VERTEX;
138 Attrs.Desc.Name = "TrivialVS (PSOCreationFailureTest)";
139 Attrs.SourceLanguage = SHADER_SOURCE_LANGUAGE_HLSL;
140 Attrs.ShaderCompiler = pEnv->GetDefaultCompiler(Attrs.SourceLanguage);
141 Attrs.UseCombinedTextureSamplers = true;
142 pDevice->CreateShader(Attrs, &sm_pTrivialVS);
142 ShaderCreateInfo ShaderCI;
143 ShaderCI.Source = g_TrivialVSSource;
144 ShaderCI.EntryPoint = "main";
145 ShaderCI.Desc.ShaderType = SHADER_TYPE_VERTEX;
146 ShaderCI.Desc.Name = "TrivialVS (PSOCreationFailureTest)";
147 ShaderCI.SourceLanguage = SHADER_SOURCE_LANGUAGE_HLSL;
148 ShaderCI.ShaderCompiler = pEnv->GetDefaultCompiler(ShaderCI.SourceLanguage);
149 ShaderCI.UseCombinedTextureSamplers = true;
150 pDevice->CreateShader(ShaderCI, &sm_pTrivialVS);
143151 ASSERT_TRUE(sm_pTrivialVS);
144152
145 Attrs.Source = g_TrivialPSSource;
146 Attrs.Desc.ShaderType = SHADER_TYPE_PIXEL;
147 Attrs.Desc.Name = "TrivialPS (PSOCreationFailureTest)";
148 pDevice->CreateShader(Attrs, &sm_pTrivialPS);
153 ShaderCI.Source = g_TrivialPSSource;
154 ShaderCI.Desc.ShaderType = SHADER_TYPE_PIXEL;
155 ShaderCI.Desc.Name = "TrivialPS (PSOCreationFailureTest)";
156 pDevice->CreateShader(ShaderCI, &sm_pTrivialPS);
149157 ASSERT_TRUE(sm_pTrivialPS);
150158
151 Attrs.Source = g_TrivialCSSource;
152 Attrs.Desc.ShaderType = SHADER_TYPE_COMPUTE;
153 Attrs.Desc.Name = "TrivialCS (PSOCreationFailureTest)";
154 pDevice->CreateShader(Attrs, &sm_pTrivialCS);
159 ShaderCI.Source = g_TexturePSSource;
160 ShaderCI.Desc.ShaderType = SHADER_TYPE_PIXEL;
161 ShaderCI.Desc.Name = "TexturePS (PSOCreationFailureTest)";
162 pDevice->CreateShader(ShaderCI, &sm_pTexturePS);
163 ASSERT_TRUE(sm_pTexturePS);
164
165
166
167 ShaderCI.Source = g_TrivialCSSource;
168 ShaderCI.Desc.ShaderType = SHADER_TYPE_COMPUTE;
169 ShaderCI.Desc.Name = "TrivialCS (PSOCreationFailureTest)";
170 pDevice->CreateShader(ShaderCI, &sm_pTrivialCS);
155171 ASSERT_TRUE(sm_pTrivialCS);
156172
157173 sm_DefaultGraphicsPsoCI.PSODesc.Name = "PSOCreationFailureTest - default graphics PSO desc";
179195
180196 if (sm_HasMeshShader)
181197 {
182 Attrs.ShaderCompiler = SHADER_COMPILER_DXC;
183
184 Attrs.Source = g_TrivialMSSource;
185 Attrs.Desc.ShaderType = SHADER_TYPE_MESH;
186 Attrs.Desc.Name = "TrivialMS DXC (PSOCreationFailureTest)";
187 pDevice->CreateShader(Attrs, &sm_pTrivialMS);
198 ShaderCI.ShaderCompiler = SHADER_COMPILER_DXC;
199
200 ShaderCI.Source = g_TrivialMSSource;
201 ShaderCI.Desc.ShaderType = SHADER_TYPE_MESH;
202 ShaderCI.Desc.Name = "TrivialMS DXC (PSOCreationFailureTest)";
203 pDevice->CreateShader(ShaderCI, &sm_pTrivialMS);
188204 ASSERT_TRUE(sm_pTrivialMS);
189205
190 Attrs.Source = g_TrivialPSSource;
191 Attrs.Desc.ShaderType = SHADER_TYPE_PIXEL;
192 Attrs.Desc.Name = "TrivialPS DXC (PSOCreationFailureTest)";
193 pDevice->CreateShader(Attrs, &sm_pTrivialPS_DXC);
206 ShaderCI.Source = g_TrivialPSSource;
207 ShaderCI.Desc.ShaderType = SHADER_TYPE_PIXEL;
208 ShaderCI.Desc.Name = "TrivialPS DXC (PSOCreationFailureTest)";
209 pDevice->CreateShader(ShaderCI, &sm_pTrivialPS_DXC);
194210 ASSERT_TRUE(sm_pTrivialPS_DXC);
195211
196212 sm_DefaultMeshPsoCI.PSODesc.Name = "PSOCreationFailureTest - default mesh PSO desc";
209225
210226 if (sm_HasRayTracing)
211227 {
212 Attrs.ShaderCompiler = SHADER_COMPILER_DXC;
213
214 Attrs.Source = g_TrivialRGenSource;
215 Attrs.Desc.ShaderType = SHADER_TYPE_RAY_GEN;
216 Attrs.Desc.Name = "TrivialRGen (PSOCreationFailureTest)";
217 pDevice->CreateShader(Attrs, &sm_pTrivialRG);
228 ShaderCI.ShaderCompiler = SHADER_COMPILER_DXC;
229
230 ShaderCI.Source = g_TrivialRGenSource;
231 ShaderCI.Desc.ShaderType = SHADER_TYPE_RAY_GEN;
232 ShaderCI.Desc.Name = "TrivialRGen (PSOCreationFailureTest)";
233 pDevice->CreateShader(ShaderCI, &sm_pTrivialRG);
218234 ASSERT_TRUE(sm_pTrivialRG);
219235
220 Attrs.Source = g_TrivialRMissSource;
221 Attrs.Desc.ShaderType = SHADER_TYPE_RAY_MISS;
222 Attrs.Desc.Name = "TrivialRMiss (PSOCreationFailureTest)";
223 pDevice->CreateShader(Attrs, &sm_pTrivialRMiss);
236 ShaderCI.Source = g_TrivialRMissSource;
237 ShaderCI.Desc.ShaderType = SHADER_TYPE_RAY_MISS;
238 ShaderCI.Desc.Name = "TrivialRMiss (PSOCreationFailureTest)";
239 pDevice->CreateShader(ShaderCI, &sm_pTrivialRMiss);
224240 ASSERT_TRUE(sm_pTrivialRMiss);
225241
226 Attrs.Source = g_TrivialRCallSource;
227 Attrs.Desc.ShaderType = SHADER_TYPE_CALLABLE;
228 Attrs.Desc.Name = "TrivialRCall (PSOCreationFailureTest)";
229 pDevice->CreateShader(Attrs, &sm_pTrivialRCall);
242 ShaderCI.Source = g_TrivialRCallSource;
243 ShaderCI.Desc.ShaderType = SHADER_TYPE_CALLABLE;
244 ShaderCI.Desc.Name = "TrivialRCall (PSOCreationFailureTest)";
245 pDevice->CreateShader(ShaderCI, &sm_pTrivialRCall);
230246 ASSERT_TRUE(sm_pTrivialRCall);
231247
232 Attrs.Source = g_TrivialRCHitSource;
233 Attrs.Desc.ShaderType = SHADER_TYPE_RAY_CLOSEST_HIT;
234 Attrs.Desc.Name = "TrivialRCHit (PSOCreationFailureTest)";
235 pDevice->CreateShader(Attrs, &sm_pTrivialRCHit);
248 ShaderCI.Source = g_TrivialRCHitSource;
249 ShaderCI.Desc.ShaderType = SHADER_TYPE_RAY_CLOSEST_HIT;
250 ShaderCI.Desc.Name = "TrivialRCHit (PSOCreationFailureTest)";
251 pDevice->CreateShader(ShaderCI, &sm_pTrivialRCHit);
236252 ASSERT_TRUE(sm_pTrivialRCHit);
237253
238 Attrs.Source = g_TrivialRAHitSource;
239 Attrs.Desc.ShaderType = SHADER_TYPE_RAY_ANY_HIT;
240 Attrs.Desc.Name = "TrivialRAHit (PSOCreationFailureTest)";
241 pDevice->CreateShader(Attrs, &sm_pTrivialRAHit);
254 ShaderCI.Source = g_TrivialRAHitSource;
255 ShaderCI.Desc.ShaderType = SHADER_TYPE_RAY_ANY_HIT;
256 ShaderCI.Desc.Name = "TrivialRAHit (PSOCreationFailureTest)";
257 pDevice->CreateShader(ShaderCI, &sm_pTrivialRAHit);
242258 ASSERT_TRUE(sm_pTrivialRAHit);
243259
244 Attrs.Source = g_TrivialRIntSource;
245 Attrs.Desc.ShaderType = SHADER_TYPE_RAY_INTERSECTION;
246 Attrs.Desc.Name = "TrivialRInt (PSOCreationFailureTest)";
247 pDevice->CreateShader(Attrs, &sm_pTrivialRInt);
260 ShaderCI.Source = g_TrivialRIntSource;
261 ShaderCI.Desc.ShaderType = SHADER_TYPE_RAY_INTERSECTION;
262 ShaderCI.Desc.Name = "TrivialRInt (PSOCreationFailureTest)";
263 pDevice->CreateShader(ShaderCI, &sm_pTrivialRInt);
248264 ASSERT_TRUE(sm_pTrivialRInt);
249265
250266 sm_DefaultRayTracingPsoCI.PSODesc.Name = "PSOCreationFailureTest - default ray tracing PSO desc";
366382 sm_pTrivialVS.Release();
367383 sm_pTrivialPS.Release();
368384 sm_pTrivialPS_DXC.Release();
385 sm_pTexturePS.Release();
369386 sm_pTrivialMS.Release();
370387 sm_pTrivialCS.Release();
371388 sm_pTrivialRG.Release();
431448 static IShader* GetPS() { return sm_pTrivialPS; }
432449 static IShader* GetMS() { return sm_pTrivialMS; }
433450
451 static IShader* GetTexturePS() { return sm_pTexturePS; }
452
434453 static IShader* GetRayGen() { return sm_pTrivialRG; }
435454 static IShader* GetRayMiss() { return sm_pTrivialRMiss; }
436455 static IShader* GetCallable() { return sm_pTrivialRCall; }
513532 static RefCntAutoPtr<IShader> sm_pTrivialVS;
514533 static RefCntAutoPtr<IShader> sm_pTrivialPS;
515534 static RefCntAutoPtr<IShader> sm_pTrivialPS_DXC;
535 static RefCntAutoPtr<IShader> sm_pTexturePS;
516536 static RefCntAutoPtr<IShader> sm_pTrivialMS;
517537 static RefCntAutoPtr<IShader> sm_pTrivialRG;
518538 static RefCntAutoPtr<IShader> sm_pTrivialRMiss;
536556
537557 RefCntAutoPtr<IShader> PSOCreationFailureTest::sm_pTrivialVS;
538558 RefCntAutoPtr<IShader> PSOCreationFailureTest::sm_pTrivialPS;
559 RefCntAutoPtr<IShader> PSOCreationFailureTest::sm_pTexturePS;
539560 RefCntAutoPtr<IShader> PSOCreationFailureTest::sm_pTrivialPS_DXC;
540561 RefCntAutoPtr<IShader> PSOCreationFailureTest::sm_pTrivialMS;
541562 RefCntAutoPtr<IShader> PSOCreationFailureTest::sm_pTrivialCS;
11491170 TestCreatePSOFailure(PsoCI, "SHADER_TYPE_RAY_CLOSEST_HIT is not a valid type for ray tracing procedural any hit");
11501171 }
11511172
1173 TEST_F(PSOCreationFailureTest, MissingResource)
1174 {
1175 PipelineResourceSignatureDesc PRSDesc;
1176 PRSDesc.Name = "PSO Create Failure - missing resource";
1177 PipelineResourceDesc Resources[]{
1178 {SHADER_TYPE_PIXEL, "g_AnotherTexture", 1, SHADER_RESOURCE_TYPE_TEXTURE_SRV, SHADER_RESOURCE_VARIABLE_TYPE_MUTABLE}};
1179 PRSDesc.UseCombinedTextureSamplers = true;
1180 PRSDesc.Resources = Resources;
1181 PRSDesc.NumResources = _countof(Resources);
1182
1183 auto* pDevice = TestingEnvironment::GetInstance()->GetDevice();
1184
1185 RefCntAutoPtr<IPipelineResourceSignature> pPRS;
1186 pDevice->CreatePipelineResourceSignature(PRSDesc, &pPRS);
1187 ASSERT_NE(pPRS, nullptr);
1188
1189 IPipelineResourceSignature* ppSignatures[] = {pPRS};
1190
1191 auto PsoCI{GetGraphicsPSOCreateInfo("PSO Create Failure - missing resource")};
1192 PsoCI.ppResourceSignatures = ppSignatures;
1193 PsoCI.ResourceSignaturesCount = _countof(ppSignatures);
1194
1195 PsoCI.pPS = GetTexturePS();
1196
1197 TestCreatePSOFailure(PsoCI, "Shader 'TexturePS (PSOCreationFailureTest)' contains resource 'g_Texture' that is not present in any pipeline resource signature");
1198 }
1199
1200 TEST_F(PSOCreationFailureTest, InvalidResourceType)
1201 {
1202 PipelineResourceSignatureDesc PRSDesc;
1203 PRSDesc.Name = "PSO Create Failure - Invalid Resource Type";
1204 PipelineResourceDesc Resources[]{
1205 {SHADER_TYPE_PIXEL, "g_Texture", 1, SHADER_RESOURCE_TYPE_BUFFER_SRV, SHADER_RESOURCE_VARIABLE_TYPE_MUTABLE}};
1206 PRSDesc.UseCombinedTextureSamplers = true;
1207 PRSDesc.Resources = Resources;
1208 PRSDesc.NumResources = _countof(Resources);
1209
1210 auto* pDevice = TestingEnvironment::GetInstance()->GetDevice();
1211
1212 RefCntAutoPtr<IPipelineResourceSignature> pPRS;
1213 pDevice->CreatePipelineResourceSignature(PRSDesc, &pPRS);
1214 ASSERT_NE(pPRS, nullptr);
1215
1216 IPipelineResourceSignature* ppSignatures[] = {pPRS};
1217
1218 auto PsoCI{GetGraphicsPSOCreateInfo("PSO Create Failure - Invalid Resource Type")};
1219 PsoCI.ppResourceSignatures = ppSignatures;
1220 PsoCI.ResourceSignaturesCount = _countof(ppSignatures);
1221
1222 PsoCI.pPS = GetTexturePS();
1223
1224 TestCreatePSOFailure(PsoCI, "Shader 'TexturePS (PSOCreationFailureTest)' contains resource with name 'g_Texture' and type 'texture SRV' that is not compatible with type 'buffer SRV'");
1225 }
1226
1227 TEST_F(PSOCreationFailureTest, InvalidArraySize)
1228 {
1229 static constexpr char PSSource[] = R"(
1230 Texture2D g_Texture[3];
1231 float4 main() : SV_Target
1232 {
1233 return g_Texture[0].Load(int3(0,0,0)) + g_Texture[1].Load(int3(0,0,0)) + g_Texture[2].Load(int3(0,0,0));
1234 }
1235 )";
1236
1237 auto* const pEnv = TestingEnvironment::GetInstance();
1238 auto* const pDevice = pEnv->GetDevice();
1239
1240 ShaderCreateInfo ShaderCI;
1241 ShaderCI.Source = PSSource;
1242 ShaderCI.Desc.ShaderType = SHADER_TYPE_PIXEL;
1243 ShaderCI.Desc.Name = "Invalid Array Size (PSOCreationFailureTest)";
1244 ShaderCI.SourceLanguage = SHADER_SOURCE_LANGUAGE_HLSL;
1245 ShaderCI.ShaderCompiler = pEnv->GetDefaultCompiler(ShaderCI.SourceLanguage);
1246 ShaderCI.UseCombinedTextureSamplers = true;
1247 RefCntAutoPtr<IShader> pPS;
1248 pDevice->CreateShader(ShaderCI, &pPS);
1249
1250 PipelineResourceSignatureDesc PRSDesc;
1251 PRSDesc.Name = "PSO Create Failure - Invalid Array Size";
1252 PipelineResourceDesc Resources[]{
1253 {SHADER_TYPE_PIXEL, "g_Texture", 2, SHADER_RESOURCE_TYPE_TEXTURE_SRV, SHADER_RESOURCE_VARIABLE_TYPE_MUTABLE}};
1254
1255 PRSDesc.UseCombinedTextureSamplers = true;
1256 PRSDesc.Resources = Resources;
1257 PRSDesc.NumResources = _countof(Resources);
1258
1259 RefCntAutoPtr<IPipelineResourceSignature> pPRS;
1260 pDevice->CreatePipelineResourceSignature(PRSDesc, &pPRS);
1261 ASSERT_NE(pPRS, nullptr);
1262
1263 IPipelineResourceSignature* ppSignatures[] = {pPRS};
1264
1265 auto PsoCI{GetGraphicsPSOCreateInfo("PSO Create Failure - Invalid Array Size")};
1266 PsoCI.ppResourceSignatures = ppSignatures;
1267 PsoCI.ResourceSignaturesCount = _countof(ppSignatures);
1268
1269 PsoCI.pPS = pPS;
1270
1271 TestCreatePSOFailure(PsoCI, "Shader 'Invalid Array Size (PSOCreationFailureTest)' contains resource 'g_Texture' whose array size (3) is greater than the array size (2)");
1272 }
1273
1274
1275 TEST_F(PSOCreationFailureTest, InvalidRunTimeArray)
1276 {
1277 auto* const pEnv = TestingEnvironment::GetInstance();
1278 auto* const pDevice = pEnv->GetDevice();
1279 const auto& deviceCaps = pDevice->GetDeviceCaps();
1280
1281 if (!pDevice->GetDeviceCaps().Features.ShaderResourceRuntimeArray)
1282 {
1283 GTEST_SKIP();
1284 }
1285
1286 static constexpr char PSSource[] = R"(
1287 Texture2D g_Texture[];
1288 cbuffer ConstBuffer
1289 {
1290 uint Index;
1291 }
1292 float4 main() : SV_Target
1293 {
1294 return g_Texture[Index].Load(int3(0,0,0));
1295 }
1296 )";
1297
1298 ShaderCreateInfo ShaderCI;
1299 ShaderCI.Source = PSSource;
1300 ShaderCI.Desc.ShaderType = SHADER_TYPE_PIXEL;
1301 ShaderCI.Desc.Name = "Invalid Run-Time Array (PSOCreationFailureTest)";
1302 ShaderCI.SourceLanguage = SHADER_SOURCE_LANGUAGE_HLSL;
1303 if (deviceCaps.IsVulkanDevice())
1304 ShaderCI.ShaderCompiler = SHADER_COMPILER_DXC; // GLSLang does not handle HLSL run-time arrays properly
1305 else
1306 ShaderCI.ShaderCompiler = pEnv->GetDefaultCompiler(ShaderCI.SourceLanguage);
1307 ShaderCI.UseCombinedTextureSamplers = true;
1308 ShaderCI.CompileFlags = SHADER_COMPILE_FLAG_ENABLE_UNBOUNDED_ARRAYS;
1309 RefCntAutoPtr<IShader> pPS;
1310 pDevice->CreateShader(ShaderCI, &pPS);
1311
1312 PipelineResourceSignatureDesc PRSDesc;
1313 PRSDesc.Name = "PSO Create Failure - Invalid Run-Time Array";
1314 PipelineResourceDesc Resources[]{
1315 {SHADER_TYPE_PIXEL, "ConstBuffer", 1, SHADER_RESOURCE_TYPE_CONSTANT_BUFFER, SHADER_RESOURCE_VARIABLE_TYPE_MUTABLE},
1316 {SHADER_TYPE_PIXEL, "g_Texture", 2, SHADER_RESOURCE_TYPE_TEXTURE_SRV, SHADER_RESOURCE_VARIABLE_TYPE_MUTABLE}};
1317
1318 PRSDesc.UseCombinedTextureSamplers = true;
1319 PRSDesc.Resources = Resources;
1320 PRSDesc.NumResources = _countof(Resources);
1321
1322 RefCntAutoPtr<IPipelineResourceSignature> pPRS;
1323 pDevice->CreatePipelineResourceSignature(PRSDesc, &pPRS);
1324 ASSERT_NE(pPRS, nullptr);
1325
1326 IPipelineResourceSignature* ppSignatures[] = {pPRS};
1327
1328 auto PsoCI{GetGraphicsPSOCreateInfo("PSO Create Failure - Invalid Run-Time Array")};
1329 PsoCI.ppResourceSignatures = ppSignatures;
1330 PsoCI.ResourceSignaturesCount = _countof(ppSignatures);
1331
1332 PsoCI.pPS = pPS;
1333
1334 TestCreatePSOFailure(PsoCI, "Shader 'Invalid Run-Time Array (PSOCreationFailureTest)' contains resource 'g_Texture' that is a runtime-sized array, "
1335 "but in the resource signature 'PSO Create Failure - Invalid Run-Time Array' the resource is defined without the PIPELINE_RESOURCE_FLAG_RUNTIME_ARRAY flag.");
1336 }
1337
11521338 } // namespace