1 #ifndef _VKTSHADERRENDER_HPP 2 #define _VKTSHADERRENDER_HPP 3 /*------------------------------------------------------------------------ 4 * Vulkan Conformance Tests 5 * ------------------------ 6 * 7 * Copyright (c) 2015 The Khronos Group Inc. 8 * Copyright (c) 2015 Samsung Electronics Co., Ltd. 9 * 10 * Licensed under the Apache License, Version 2.0 (the "License"); 11 * you may not use this file except in compliance with the License. 12 * You may obtain a copy of the License at 13 * 14 * http://www.apache.org/licenses/LICENSE-2.0 15 * 16 * Unless required by applicable law or agreed to in writing, software 17 * distributed under the License is distributed on an "AS IS" BASIS, 18 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 19 * See the License for the specific language governing permissions and 20 * limitations under the License. 21 * 22 *//*! 23 * \file 24 * \brief Vulkan ShaderRenderCase 25 *//*--------------------------------------------------------------------*/ 26 27 #include "tcuTexture.hpp" 28 #include "tcuSurface.hpp" 29 30 #include "deMemory.h" 31 #include "deSharedPtr.hpp" 32 #include "deUniquePtr.hpp" 33 34 #include "vkDefs.hpp" 35 #include "vkRefUtil.hpp" 36 #include "vkPrograms.hpp" 37 #include "vkRef.hpp" 38 #include "vkMemUtil.hpp" 39 #include "vkBuilderUtil.hpp" 40 #include "vkTypeUtil.hpp" 41 #include "vkPlatform.hpp" 42 43 #include "vktTestCaseUtil.hpp" 44 45 namespace vkt 46 { 47 namespace sr 48 { 49 50 class LineStream 51 { 52 public: 53 LineStream (int indent = 0) { m_indent = indent; } 54 ~LineStream (void) {} 55 56 const char* str (void) const { m_string = m_stream.str(); return m_string.c_str(); } 57 LineStream& operator<< (const char* line) { for (int i = 0; i < m_indent; i++) { m_stream << "\t"; } m_stream << line << "\n"; return *this; } 58 59 private: 60 int m_indent; 61 std::ostringstream m_stream; 62 mutable std::string m_string; 63 }; 64 65 class QuadGrid; 66 class ShaderRenderCaseInstance; 67 68 class TextureBinding 69 { 70 public: 71 enum Type 72 { 73 TYPE_NONE = 0, 74 TYPE_1D, 75 TYPE_2D, 76 TYPE_3D, 77 TYPE_CUBE_MAP, 78 TYPE_1D_ARRAY, 79 TYPE_2D_ARRAY, 80 TYPE_CUBE_ARRAY, 81 82 TYPE_LAST 83 }; 84 85 enum Init 86 { 87 INIT_UPLOAD_DATA, 88 INIT_CLEAR, 89 90 INIT_LAST 91 }; 92 93 struct Parameters 94 { 95 deUint32 baseMipLevel; 96 vk::VkComponentMapping componentMapping; 97 vk::VkSampleCountFlagBits samples; 98 Init initialization; 99 100 Parameters (deUint32 baseMipLevel_ = 0, 101 vk::VkComponentMapping componentMapping_ = vk::makeComponentMappingRGBA(), 102 vk::VkSampleCountFlagBits samples_ = vk::VK_SAMPLE_COUNT_1_BIT, 103 Init initialization_ = INIT_UPLOAD_DATA) 104 : baseMipLevel (baseMipLevel_) 105 , componentMapping (componentMapping_) 106 , samples (samples_) 107 , initialization (initialization_) 108 { 109 } 110 }; 111 112 TextureBinding (const tcu::Archive& archive, 113 const char* filename, 114 const Type type, 115 const tcu::Sampler& sampler); 116 117 TextureBinding (const tcu::Texture1D* tex1D, const tcu::Sampler& sampler); 118 TextureBinding (const tcu::Texture2D* tex2D, const tcu::Sampler& sampler); 119 TextureBinding (const tcu::Texture3D* tex3D, const tcu::Sampler& sampler); 120 TextureBinding (const tcu::TextureCube* texCube, const tcu::Sampler& sampler); 121 TextureBinding (const tcu::Texture1DArray* tex1DArray, const tcu::Sampler& sampler); 122 TextureBinding (const tcu::Texture2DArray* tex2DArray, const tcu::Sampler& sampler); 123 TextureBinding (const tcu::TextureCubeArray* texCubeArray, const tcu::Sampler& sampler); 124 125 ~TextureBinding (void); 126 127 Type getType (void) const { return m_type; } 128 const tcu::Sampler& getSampler (void) const { return m_sampler; } 129 130 const tcu::Texture1D& get1D (void) const { DE_ASSERT(getType() == TYPE_1D && m_binding.tex1D != NULL); return *m_binding.tex1D; } 131 const tcu::Texture2D& get2D (void) const { DE_ASSERT(getType() == TYPE_2D && m_binding.tex2D != NULL); return *m_binding.tex2D; } 132 const tcu::Texture3D& get3D (void) const { DE_ASSERT(getType() == TYPE_3D && m_binding.tex3D != NULL); return *m_binding.tex3D; } 133 const tcu::TextureCube& getCube (void) const { DE_ASSERT(getType() == TYPE_CUBE_MAP && m_binding.texCube != NULL); return *m_binding.texCube; } 134 const tcu::Texture1DArray& get1DArray (void) const { DE_ASSERT(getType() == TYPE_1D_ARRAY && m_binding.tex1DArray != NULL); return *m_binding.tex1DArray; } 135 const tcu::Texture2DArray& get2DArray (void) const { DE_ASSERT(getType() == TYPE_2D_ARRAY && m_binding.tex2DArray != NULL); return *m_binding.tex2DArray; } 136 const tcu::TextureCubeArray& getCubeArray (void) const { DE_ASSERT(getType() == TYPE_CUBE_ARRAY && m_binding.texCubeArray != NULL); return *m_binding.texCubeArray; } 137 138 void setParameters (const Parameters& params) { m_params = params; } 139 const Parameters& getParameters (void) const { return m_params; } 140 141 private: 142 TextureBinding (const TextureBinding&); // not allowed! 143 TextureBinding& operator= (const TextureBinding&); // not allowed! 144 145 static de::MovePtr<tcu::Texture2D> loadTexture2D (const tcu::Archive& archive, const char* filename); 146 147 Type m_type; 148 tcu::Sampler m_sampler; 149 Parameters m_params; 150 151 union 152 { 153 const tcu::Texture1D* tex1D; 154 const tcu::Texture2D* tex2D; 155 const tcu::Texture3D* tex3D; 156 const tcu::TextureCube* texCube; 157 const tcu::Texture1DArray* tex1DArray; 158 const tcu::Texture2DArray* tex2DArray; 159 const tcu::TextureCubeArray* texCubeArray; 160 } m_binding; 161 }; 162 163 typedef de::SharedPtr<TextureBinding> TextureBindingSp; 164 165 // ShaderEvalContext. 166 167 class ShaderEvalContext 168 { 169 public: 170 // Limits. 171 enum 172 { 173 MAX_USER_ATTRIBS = 4, 174 MAX_TEXTURES = 4 175 }; 176 177 struct ShaderSampler 178 { 179 tcu::Sampler sampler; 180 const tcu::Texture1D* tex1D; 181 const tcu::Texture2D* tex2D; 182 const tcu::Texture3D* tex3D; 183 const tcu::TextureCube* texCube; 184 const tcu::Texture1DArray* tex1DArray; 185 const tcu::Texture2DArray* tex2DArray; 186 const tcu::TextureCubeArray* texCubeArray; 187 188 inline ShaderSampler (void) 189 : tex1D (DE_NULL) 190 , tex2D (DE_NULL) 191 , tex3D (DE_NULL) 192 , texCube (DE_NULL) 193 , tex1DArray (DE_NULL) 194 , tex2DArray (DE_NULL) 195 , texCubeArray (DE_NULL) 196 { 197 } 198 }; 199 200 ShaderEvalContext (const QuadGrid& quadGrid); 201 ~ShaderEvalContext (void); 202 203 void reset (float sx, float sy); 204 205 // Inputs. 206 tcu::Vec4 coords; 207 tcu::Vec4 unitCoords; 208 tcu::Vec4 constCoords; 209 210 tcu::Vec4 in[MAX_USER_ATTRIBS]; 211 ShaderSampler textures[MAX_TEXTURES]; 212 213 // Output. 214 tcu::Vec4 color; 215 bool isDiscarded; 216 217 // Functions. 218 inline void discard (void) { isDiscarded = true; } 219 tcu::Vec4 texture2D (int unitNdx, const tcu::Vec2& coords); 220 221 private: 222 const QuadGrid& m_quadGrid; 223 }; 224 225 typedef void (*ShaderEvalFunc) (ShaderEvalContext& c); 226 227 inline void evalCoordsPassthroughX (ShaderEvalContext& c) { c.color.x() = c.coords.x(); } 228 inline void evalCoordsPassthroughXY (ShaderEvalContext& c) { c.color.xy() = c.coords.swizzle(0,1); } 229 inline void evalCoordsPassthroughXYZ (ShaderEvalContext& c) { c.color.xyz() = c.coords.swizzle(0,1,2); } 230 inline void evalCoordsPassthrough (ShaderEvalContext& c) { c.color = c.coords; } 231 inline void evalCoordsSwizzleWZYX (ShaderEvalContext& c) { c.color = c.coords.swizzle(3,2,1,0); } 232 233 // ShaderEvaluator 234 // Either inherit a class with overridden evaluate() or just pass in an evalFunc. 235 236 class ShaderEvaluator 237 { 238 public: 239 ShaderEvaluator (void); 240 ShaderEvaluator (const ShaderEvalFunc evalFunc); 241 virtual ~ShaderEvaluator (void); 242 243 virtual void evaluate (ShaderEvalContext& ctx) const; 244 245 private: 246 ShaderEvaluator (const ShaderEvaluator&); // not allowed! 247 ShaderEvaluator& operator= (const ShaderEvaluator&); // not allowed! 248 249 const ShaderEvalFunc m_evalFunc; 250 }; 251 252 // UniformSetup 253 254 typedef void (*UniformSetupFunc) (ShaderRenderCaseInstance& instance, const tcu::Vec4& constCoords); 255 256 class UniformSetup 257 { 258 public: 259 UniformSetup (void); 260 UniformSetup (const UniformSetupFunc setup); 261 virtual ~UniformSetup (void); 262 virtual void setup (ShaderRenderCaseInstance& instance, const tcu::Vec4& constCoords) const; 263 264 private: 265 UniformSetup (const UniformSetup&); // not allowed! 266 UniformSetup& operator= (const UniformSetup&); // not allowed! 267 268 const UniformSetupFunc m_setupFunc; 269 }; 270 271 typedef void (*AttributeSetupFunc) (ShaderRenderCaseInstance& instance, deUint32 numVertices); 272 273 class ShaderRenderCase : public vkt::TestCase 274 { 275 public: 276 ShaderRenderCase (tcu::TestContext& testCtx, 277 const std::string& name, 278 const std::string& description, 279 const bool isVertexCase, 280 const ShaderEvalFunc evalFunc, 281 const UniformSetup* uniformSetup, 282 const AttributeSetupFunc attribFunc); 283 284 ShaderRenderCase (tcu::TestContext& testCtx, 285 const std::string& name, 286 const std::string& description, 287 const bool isVertexCase, 288 const ShaderEvaluator* evaluator, 289 const UniformSetup* uniformSetup, 290 const AttributeSetupFunc attribFunc); 291 292 virtual ~ShaderRenderCase (void); 293 virtual void initPrograms (vk::SourceCollections& programCollection) const; 294 virtual TestInstance* createInstance (Context& context) const; 295 296 protected: 297 std::string m_vertShaderSource; 298 std::string m_fragShaderSource; 299 300 const bool m_isVertexCase; 301 const de::UniquePtr<const ShaderEvaluator> m_evaluator; 302 const de::UniquePtr<const UniformSetup> m_uniformSetup; 303 const AttributeSetupFunc m_attribFunc; 304 }; 305 306 enum BaseUniformType 307 { 308 // Bool 309 UB_FALSE, 310 UB_TRUE, 311 312 // BVec4 313 UB4_FALSE, 314 UB4_TRUE, 315 316 // Integers 317 UI_ZERO, 318 UI_ONE, 319 UI_TWO, 320 UI_THREE, 321 UI_FOUR, 322 UI_FIVE, 323 UI_SIX, 324 UI_SEVEN, 325 UI_EIGHT, 326 UI_ONEHUNDREDONE, 327 328 // IVec2 329 UI2_MINUS_ONE, 330 UI2_ZERO, 331 UI2_ONE, 332 UI2_TWO, 333 UI2_THREE, 334 UI2_FOUR, 335 UI2_FIVE, 336 337 // IVec3 338 UI3_MINUS_ONE, 339 UI3_ZERO, 340 UI3_ONE, 341 UI3_TWO, 342 UI3_THREE, 343 UI3_FOUR, 344 UI3_FIVE, 345 346 // IVec4 347 UI4_MINUS_ONE, 348 UI4_ZERO, 349 UI4_ONE, 350 UI4_TWO, 351 UI4_THREE, 352 UI4_FOUR, 353 UI4_FIVE, 354 355 // Float 356 UF_ZERO, 357 UF_ONE, 358 UF_TWO, 359 UF_THREE, 360 UF_FOUR, 361 UF_FIVE, 362 UF_SIX, 363 UF_SEVEN, 364 UF_EIGHT, 365 366 UF_HALF, 367 UF_THIRD, 368 UF_FOURTH, 369 UF_FIFTH, 370 UF_SIXTH, 371 UF_SEVENTH, 372 UF_EIGHTH, 373 374 // Vec2 375 UV2_MINUS_ONE, 376 UV2_ZERO, 377 UV2_ONE, 378 UV2_TWO, 379 UV2_THREE, 380 381 UV2_HALF, 382 383 // Vec3 384 UV3_MINUS_ONE, 385 UV3_ZERO, 386 UV3_ONE, 387 UV3_TWO, 388 UV3_THREE, 389 390 UV3_HALF, 391 392 // Vec4 393 UV4_MINUS_ONE, 394 UV4_ZERO, 395 UV4_ONE, 396 UV4_TWO, 397 UV4_THREE, 398 399 UV4_HALF, 400 401 UV4_BLACK, 402 UV4_GRAY, 403 UV4_WHITE, 404 405 // Last 406 U_LAST 407 }; 408 409 enum BaseAttributeType 410 { 411 // User attributes 412 A_IN0, 413 A_IN1, 414 A_IN2, 415 A_IN3, 416 417 // Matrices 418 MAT2, 419 MAT2x3, 420 MAT2x4, 421 MAT3x2, 422 MAT3, 423 MAT3x4, 424 MAT4x2, 425 MAT4x3, 426 MAT4 427 }; 428 429 // ShaderRenderCaseInstance. 430 431 class ShaderRenderCaseInstance : public vkt::TestInstance 432 { 433 public: 434 enum ImageBackingMode 435 { 436 IMAGE_BACKING_MODE_REGULAR = 0, 437 IMAGE_BACKING_MODE_SPARSE, 438 }; 439 440 // Default wertex and fragment grid sizes are used by a large collection of tests 441 // to generate input sets. Some tests might change their behavior if the 442 // default grid size values are altered, so care should be taken to confirm that 443 // any changes to default values do not produce regressions. 444 // If a particular tests needs to use a different grid size value, rather than 445 // modifying the default grid size values for all tests, it is recommended that 446 // the test specifies the required grid size using the gridSize parameter in the 447 // ShaderRenderCaseInstance constuctor instead. 448 enum 449 { 450 GRID_SIZE_DEFAULTS = 0, 451 GRID_SIZE_DEFAULT_VERTEX = 90, 452 GRID_SIZE_DEFAULT_FRAGMENT = 4, 453 }; 454 455 ShaderRenderCaseInstance (Context& context); 456 ShaderRenderCaseInstance (Context& context, 457 const bool isVertexCase, 458 const ShaderEvaluator& evaluator, 459 const UniformSetup& uniformSetup, 460 const AttributeSetupFunc attribFunc, 461 const ImageBackingMode imageBackingMode = IMAGE_BACKING_MODE_REGULAR, 462 const deUint32 gridSize = static_cast<deUint32>(GRID_SIZE_DEFAULTS)); 463 464 virtual ~ShaderRenderCaseInstance (void); 465 virtual tcu::TestStatus iterate (void); 466 467 void addAttribute (deUint32 bindingLocation, 468 vk::VkFormat format, 469 deUint32 sizePerElement, 470 deUint32 count, 471 const void* data); 472 void useAttribute (deUint32 bindingLocation, 473 BaseAttributeType type); 474 475 template<typename T> 476 void addUniform (deUint32 bindingLocation, 477 vk::VkDescriptorType descriptorType, 478 const T& data); 479 void addUniform (deUint32 bindingLocation, 480 vk::VkDescriptorType descriptorType, 481 size_t dataSize, 482 const void* data); 483 void useUniform (deUint32 bindingLocation, 484 BaseUniformType type); 485 void useSampler (deUint32 bindingLocation, 486 deUint32 textureId); 487 488 static const tcu::Vec4 getDefaultConstCoords (void) { return tcu::Vec4(0.125f, 0.25f, 0.5f, 1.0f); } 489 void setPushConstantRanges (const deUint32 rangeCount, const vk::VkPushConstantRange* const pcRanges); 490 virtual void updatePushConstants (vk::VkCommandBuffer commandBuffer, vk::VkPipelineLayout pipelineLayout); 491 492 protected: 493 ShaderRenderCaseInstance (Context& context, 494 const bool isVertexCase, 495 const ShaderEvaluator* evaluator, 496 const UniformSetup* uniformSetup, 497 const AttributeSetupFunc attribFunc, 498 const ImageBackingMode imageBackingMode = IMAGE_BACKING_MODE_REGULAR, 499 const deUint32 gridSize = static_cast<deUint32>(GRID_SIZE_DEFAULTS)); 500 501 virtual void setup (void); 502 virtual void setupUniforms (const tcu::Vec4& constCoords); 503 virtual void setupDefaultInputs (void); 504 505 void render (deUint32 numVertices, 506 deUint32 numTriangles, 507 const deUint16* indices, 508 const tcu::Vec4& constCoords = getDefaultConstCoords()); 509 510 void render (deUint32 numVertices, 511 deUint32 numIndices, 512 const deUint16* indices, 513 vk::VkPrimitiveTopology topology, 514 const tcu::Vec4& constCoords = getDefaultConstCoords()); 515 516 const tcu::TextureLevel& getResultImage (void) const { return m_resultImage; } 517 518 const tcu::UVec2 getViewportSize (void) const; 519 520 void setSampleCount (vk::VkSampleCountFlagBits sampleCount); 521 522 bool isMultiSampling (void) const; 523 524 ImageBackingMode m_imageBackingMode; 525 526 deUint32 m_quadGridSize; 527 private: 528 529 struct SparseContext 530 { 531 SparseContext (vkt::Context& context); 532 533 vkt::Context& m_context; 534 const deUint32 m_queueFamilyIndex; 535 vk::Unique<vk::VkDevice> m_device; 536 vk::DeviceDriver m_deviceInterface; 537 const vk::VkQueue m_queue; 538 const de::UniquePtr<vk::Allocator> m_allocator; 539 private: 540 vk::Move<vk::VkDevice> createDevice (void) const; 541 vk::Allocator* createAllocator (void) const; 542 543 }; 544 545 de::UniquePtr<SparseContext> m_sparseContext; 546 protected: 547 vk::Allocator& m_memAlloc; 548 const tcu::Vec4 m_clearColor; 549 const bool m_isVertexCase; 550 551 std::vector<tcu::Mat4> m_userAttribTransforms; 552 std::vector<TextureBindingSp> m_textures; 553 554 std::string m_vertexShaderName; 555 std::string m_fragmentShaderName; 556 tcu::UVec2 m_renderSize; 557 vk::VkFormat m_colorFormat; 558 559 private: 560 typedef std::vector<tcu::ConstPixelBufferAccess> TextureLayerData; 561 typedef std::vector<TextureLayerData> TextureData; 562 563 void uploadImage (const tcu::TextureFormat& texFormat, 564 const TextureData& textureData, 565 const tcu::Sampler& refSampler, 566 deUint32 mipLevels, 567 deUint32 arrayLayers, 568 vk::VkImage destImage); 569 570 void clearImage (const tcu::Sampler& refSampler, 571 deUint32 mipLevels, 572 deUint32 arrayLayers, 573 vk::VkImage destImage); 574 575 void checkSparseSupport (const vk::VkImageCreateInfo& imageInfo) const; 576 577 void uploadSparseImage (const tcu::TextureFormat& texFormat, 578 const TextureData& textureData, 579 const tcu::Sampler& refSampler, 580 const deUint32 mipLevels, 581 const deUint32 arrayLayers, 582 const vk::VkImage sparseImage, 583 const vk::VkImageCreateInfo& imageCreateInfo, 584 const tcu::UVec3 texSize); 585 586 void createSamplerUniform (deUint32 bindingLocation, 587 TextureBinding::Type textureType, 588 TextureBinding::Init textureInit, 589 const tcu::TextureFormat& texFormat, 590 const tcu::UVec3 texSize, 591 const TextureData& textureData, 592 const tcu::Sampler& refSampler, 593 deUint32 mipLevels, 594 deUint32 arrayLayers, 595 TextureBinding::Parameters textureParams); 596 597 void setupUniformData (deUint32 bindingLocation, size_t size, const void* dataPtr); 598 599 void computeVertexReference (tcu::Surface& result, const QuadGrid& quadGrid); 600 void computeFragmentReference (tcu::Surface& result, const QuadGrid& quadGrid); 601 bool compareImages (const tcu::Surface& resImage, 602 const tcu::Surface& refImage, 603 float errorThreshold); 604 605 private: 606 const ShaderEvaluator* m_evaluator; 607 const UniformSetup* m_uniformSetup; 608 const AttributeSetupFunc m_attribFunc; 609 de::MovePtr<QuadGrid> m_quadGrid; 610 tcu::TextureLevel m_resultImage; 611 612 struct EnabledBaseAttribute 613 { 614 deUint32 location; 615 BaseAttributeType type; 616 }; 617 std::vector<EnabledBaseAttribute> m_enabledBaseAttributes; 618 619 de::MovePtr<vk::DescriptorSetLayoutBuilder> m_descriptorSetLayoutBuilder; 620 de::MovePtr<vk::DescriptorPoolBuilder> m_descriptorPoolBuilder; 621 de::MovePtr<vk::DescriptorSetUpdateBuilder> m_descriptorSetUpdateBuilder; 622 623 typedef de::SharedPtr<vk::Unique<vk::VkBuffer> > VkBufferSp; 624 typedef de::SharedPtr<vk::Unique<vk::VkImage> > VkImageSp; 625 typedef de::SharedPtr<vk::Unique<vk::VkImageView> > VkImageViewSp; 626 typedef de::SharedPtr<vk::Unique<vk::VkSampler> > VkSamplerSp; 627 typedef de::SharedPtr<vk::Allocation> AllocationSp; 628 629 class UniformInfo 630 { 631 public: 632 UniformInfo (void) {} 633 virtual ~UniformInfo (void) {} 634 635 vk::VkDescriptorType type; 636 deUint32 location; 637 }; 638 639 class BufferUniform : public UniformInfo 640 { 641 public: 642 BufferUniform (void) {} 643 virtual ~BufferUniform (void) {} 644 645 VkBufferSp buffer; 646 AllocationSp alloc; 647 vk::VkDescriptorBufferInfo descriptor; 648 }; 649 650 class SamplerUniform : public UniformInfo 651 { 652 public: 653 SamplerUniform (void) {} 654 virtual ~SamplerUniform (void) {} 655 656 VkImageSp image; 657 VkImageViewSp imageView; 658 VkSamplerSp sampler; 659 AllocationSp alloc; 660 vk::VkDescriptorImageInfo descriptor; 661 }; 662 663 typedef de::SharedPtr<de::UniquePtr<UniformInfo> > UniformInfoSp; 664 std::vector<UniformInfoSp> m_uniformInfos; 665 666 std::vector< de::SharedPtr<vk::Allocation> > m_allocations; 667 668 std::vector<vk::VkVertexInputBindingDescription> m_vertexBindingDescription; 669 std::vector<vk::VkVertexInputAttributeDescription> m_vertexAttributeDescription; 670 671 std::vector<VkBufferSp> m_vertexBuffers; 672 std::vector<AllocationSp> m_vertexBufferAllocs; 673 674 vk::VkSampleCountFlagBits m_sampleCount; 675 std::vector<vk::VkPushConstantRange> m_pushConstantRanges; 676 677 // Wrapper functions around m_context calls to support sparse cases. 678 vk::VkDevice getDevice (void) const; 679 deUint32 getUniversalQueueFamilyIndex (void) const; 680 const vk::DeviceInterface& getDeviceInterface (void) const; 681 vk::VkQueue getUniversalQueue (void) const; 682 vk::VkPhysicalDevice getPhysicalDevice (void) const; 683 const vk::InstanceInterface& getInstanceInterface (void) const; 684 SparseContext* createSparseContext (void) const; 685 vk::Allocator& getAllocator (void) const; 686 }; 687 688 template<typename T> 689 void ShaderRenderCaseInstance::addUniform (deUint32 bindingLocation, vk::VkDescriptorType descriptorType, const T& data) 690 { 691 addUniform(bindingLocation, descriptorType, sizeof(T), &data); 692 } 693 694 } // sr 695 } // vkt 696 697 #endif // _VKTSHADERRENDER_HPP 698