1 /*-------------------------------------------------------------------------
2 * Vulkan Conformance Tests
3 * ------------------------
5 * Copyright (c) 2015 Google Inc.
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
11 * http://www.apache.org/licenses/LICENSE-2.0
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS,
15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
21 * \brief Object management tests
22 *//*--------------------------------------------------------------------*/
24 #include "vktApiObjectManagementTests.hpp"
25 #include "vktTestCaseUtil.hpp"
29 #include "vkRefUtil.hpp"
30 #include "vkQueryUtil.hpp"
31 #include "vkMemUtil.hpp"
32 #include "vkPrograms.hpp"
33 #include "vkTypeUtil.hpp"
34 #include "vkPlatform.hpp"
35 #include "vkStrUtil.hpp"
36 #include "vkAllocationCallbackUtil.hpp"
38 #include "tcuVector.hpp"
39 #include "tcuResultCollector.hpp"
40 #include "tcuCommandLine.hpp"
41 #include "tcuTestLog.hpp"
42 #include "tcuPlatform.hpp"
44 #include "deUniquePtr.hpp"
45 #include "deSharedPtr.hpp"
46 #include "deArrayUtil.hpp"
47 #include "deSpinBarrier.hpp"
48 #include "deThread.hpp"
69 using tcu::ResultCollector;
70 using tcu::TestStatus;
76 typedef SharedPtr<Move<VkPipeline> > VkPipelineSp; // Move so it's possible to disown the handle
77 typedef SharedPtr<Move<VkDescriptorSet> > VkDescriptorSetSp;
78 typedef SharedPtr<Move<VkCommandBuffer> > VkCommandBufferSp;
80 class ThreadGroupThread;
82 /*--------------------------------------------------------------------*//*!
85 * Thread group manages collection of threads that are expected to be
86 * launched simultaneously as a group.
88 * Shared barrier is provided for synchronizing execution. Terminating thread
89 * early either by returning from ThreadGroupThread::runThread() or throwing
90 * an exception is safe, and other threads will continue execution. The
91 * thread that has been terminated is simply removed from the synchronization
94 * TestException-based exceptions are collected and translated into a
95 * tcu::TestStatus by using tcu::ResultCollector.
97 * Use cases for ThreadGroup include for example testing thread-safety of
98 * certain API operations by poking API simultaneously from multiple
100 *//*--------------------------------------------------------------------*/
107 void add (de::MovePtr<ThreadGroupThread> thread);
108 TestStatus run (void);
111 typedef std::vector<de::SharedPtr<ThreadGroupThread> > ThreadVector;
113 ThreadVector m_threads;
114 de::SpinBarrier m_barrier;
115 } DE_WARN_UNUSED_TYPE;
117 class ThreadGroupThread : private de::Thread
120 ThreadGroupThread (void);
121 virtual ~ThreadGroupThread (void);
123 void start (de::SpinBarrier* groupBarrier);
125 ResultCollector& getResultCollector (void) { return m_resultCollector; }
127 using de::Thread::join;
130 virtual void runThread (void) = 0;
135 ThreadGroupThread (const ThreadGroupThread&);
136 ThreadGroupThread& operator= (const ThreadGroupThread&);
140 ResultCollector m_resultCollector;
141 de::SpinBarrier* m_barrier;
146 ThreadGroup::ThreadGroup (void)
151 ThreadGroup::~ThreadGroup (void)
155 void ThreadGroup::add (de::MovePtr<ThreadGroupThread> thread)
157 m_threads.push_back(de::SharedPtr<ThreadGroupThread>(thread.release()));
160 tcu::TestStatus ThreadGroup::run (void)
162 tcu::ResultCollector resultCollector;
164 m_barrier.reset((int)m_threads.size());
166 for (ThreadVector::iterator threadIter = m_threads.begin(); threadIter != m_threads.end(); ++threadIter)
167 (*threadIter)->start(&m_barrier);
169 for (ThreadVector::iterator threadIter = m_threads.begin(); threadIter != m_threads.end(); ++threadIter)
171 tcu::ResultCollector& threadResult = (*threadIter)->getResultCollector();
172 (*threadIter)->join();
173 resultCollector.addResult(threadResult.getResult(), threadResult.getMessage());
176 return tcu::TestStatus(resultCollector.getResult(), resultCollector.getMessage());
181 ThreadGroupThread::ThreadGroupThread (void)
186 ThreadGroupThread::~ThreadGroupThread (void)
190 void ThreadGroupThread::start (de::SpinBarrier* groupBarrier)
192 m_barrier = groupBarrier;
196 void ThreadGroupThread::run (void)
202 catch (const tcu::TestException& e)
204 getResultCollector().addResult(e.getTestResult(), e.getMessage());
206 catch (const std::exception& e)
208 getResultCollector().addResult(QP_TEST_RESULT_FAIL, e.what());
212 getResultCollector().addResult(QP_TEST_RESULT_FAIL, "Exception");
215 m_barrier->removeThread(de::SpinBarrier::WAIT_MODE_AUTO);
218 inline void ThreadGroupThread::barrier (void)
220 m_barrier->sync(de::SpinBarrier::WAIT_MODE_AUTO);
223 deUint32 getDefaultTestThreadCount (void)
225 return de::clamp(deGetNumAvailableLogicalCores(), 2u, 8u);
232 const PlatformInterface& vkp;
233 const DeviceInterface& vkd;
235 deUint32 queueFamilyIndex;
236 const BinaryCollection& programBinaries;
237 const VkAllocationCallbacks* allocationCallbacks;
238 deUint32 maxResourceConsumers; // Maximum number of objects using same Object::Resources concurrently
240 Environment (Context& context, deUint32 maxResourceConsumers_)
241 : vkp (context.getPlatformInterface())
242 , vkd (context.getDeviceInterface())
243 , device (context.getDevice())
244 , queueFamilyIndex (context.getUniversalQueueFamilyIndex())
245 , programBinaries (context.getBinaryCollection())
246 , allocationCallbacks (DE_NULL)
247 , maxResourceConsumers (maxResourceConsumers_)
251 Environment (const PlatformInterface& vkp_,
252 const DeviceInterface& vkd_,
254 deUint32 queueFamilyIndex_,
255 const BinaryCollection& programBinaries_,
256 const VkAllocationCallbacks* allocationCallbacks_,
257 deUint32 maxResourceConsumers_)
261 , queueFamilyIndex (queueFamilyIndex_)
262 , programBinaries (programBinaries_)
263 , allocationCallbacks (allocationCallbacks_)
264 , maxResourceConsumers (maxResourceConsumers_)
269 template<typename Case>
272 typename Case::Resources resources;
273 Unique<typename Case::Type> object;
275 Dependency (const Environment& env, const typename Case::Parameters& params)
276 : resources (env, params)
277 , object (Case::create(env, resources, params))
282 T roundUpToNextMultiple (T value, T multiple)
284 if (value % multiple == 0)
287 return value + multiple - (value % multiple);
290 #if defined(DE_DEBUG)
292 bool isPowerOfTwo (T value)
294 return ((value & (value - T(1))) == 0);
299 T alignToPowerOfTwo (T value, T align)
301 DE_ASSERT(isPowerOfTwo(align));
302 return (value + align - T(1)) & ~(align - T(1));
305 inline bool hasDeviceExtension (Context& context, const string& name)
307 return de::contains(context.getDeviceExtensions().begin(), context.getDeviceExtensions().end(), name);
310 VkDeviceSize getPageTableSize (const PlatformMemoryLimits& limits, VkDeviceSize allocationSize)
312 VkDeviceSize totalSize = 0;
314 for (size_t levelNdx = 0; levelNdx < limits.devicePageTableHierarchyLevels; ++levelNdx)
316 const VkDeviceSize coveredAddressSpaceSize = limits.devicePageSize<<levelNdx;
317 const VkDeviceSize numPagesNeeded = alignToPowerOfTwo(allocationSize, coveredAddressSpaceSize) / coveredAddressSpaceSize;
319 totalSize += numPagesNeeded*limits.devicePageTableEntrySize;
325 size_t getCurrentSystemMemoryUsage (const AllocationCallbackRecorder& allocRecoder)
327 const size_t systemAllocationOverhead = sizeof(void*)*2;
328 AllocationCallbackValidationResults validationResults;
330 validateAllocationCallbacks(allocRecoder, &validationResults);
331 TCU_CHECK(validationResults.violations.empty());
333 return getLiveSystemAllocationTotal(validationResults) + systemAllocationOverhead*validationResults.liveAllocations.size();
336 template<typename Object>
337 size_t computeSystemMemoryUsage (Context& context, const typename Object::Parameters& params)
339 AllocationCallbackRecorder allocRecorder (getSystemAllocator());
340 const Environment env (context.getPlatformInterface(),
341 context.getDeviceInterface(),
343 context.getUniversalQueueFamilyIndex(),
344 context.getBinaryCollection(),
345 allocRecorder.getCallbacks(),
347 const typename Object::Resources res (env, params);
348 const size_t resourceMemoryUsage = getCurrentSystemMemoryUsage(allocRecorder);
351 Unique<typename Object::Type> obj (Object::create(env, res, params));
352 const size_t totalMemoryUsage = getCurrentSystemMemoryUsage(allocRecorder);
354 return totalMemoryUsage - resourceMemoryUsage;
358 size_t getSafeObjectCount (const PlatformMemoryLimits& memoryLimits,
359 size_t objectSystemMemoryUsage,
360 VkDeviceSize objectDeviceMemoryUsage = 0)
362 const VkDeviceSize roundedUpDeviceMemory = roundUpToNextMultiple(objectDeviceMemoryUsage, memoryLimits.deviceMemoryAllocationGranularity);
364 if (memoryLimits.totalDeviceLocalMemory > 0 && roundedUpDeviceMemory > 0)
366 if (objectSystemMemoryUsage > 0)
367 return de::min(memoryLimits.totalSystemMemory / objectSystemMemoryUsage,
368 (size_t)(memoryLimits.totalDeviceLocalMemory / roundedUpDeviceMemory));
370 return (size_t)(memoryLimits.totalDeviceLocalMemory / roundedUpDeviceMemory);
372 else if (objectSystemMemoryUsage + roundedUpDeviceMemory > 0)
374 DE_ASSERT(roundedUpDeviceMemory <= std::numeric_limits<size_t>::max() - objectSystemMemoryUsage);
375 return memoryLimits.totalSystemMemory / (objectSystemMemoryUsage + (size_t)roundedUpDeviceMemory);
379 // Warning: at this point driver has probably not implemented allocation callbacks correctly
380 return std::numeric_limits<size_t>::max();
384 PlatformMemoryLimits getPlatformMemoryLimits (Context& context)
386 PlatformMemoryLimits memoryLimits;
388 context.getTestContext().getPlatform().getVulkanPlatform().getMemoryLimits(memoryLimits);
393 size_t getSafeObjectCount (Context& context, size_t objectSystemMemoryUsage, VkDeviceSize objectDeviceMemorySize = 0)
395 return getSafeObjectCount(getPlatformMemoryLimits(context), objectSystemMemoryUsage, objectDeviceMemorySize);
398 VkDeviceSize getPageTableSize (Context& context, VkDeviceSize allocationSize)
400 return getPageTableSize(getPlatformMemoryLimits(context), allocationSize);
403 template<typename Object>
404 deUint32 getSafeObjectCount (Context& context,
405 const typename Object::Parameters& params,
406 deUint32 hardCountLimit,
407 VkDeviceSize deviceMemoryUsage = 0)
409 return (deUint32)de::min((size_t)hardCountLimit,
410 getSafeObjectCount(context,
411 computeSystemMemoryUsage<Object>(context, params),
415 // Object definitions
419 MAX_CONCURRENT_INSTANCES = 32,
420 MAX_CONCURRENT_DEVICES = 32,
421 MAX_CONCURRENT_SYNC_PRIMITIVES = 100,
422 MAX_CONCURRENT_PIPELINE_CACHES = 128,
423 DEFAULT_MAX_CONCURRENT_OBJECTS = 16*1024,
428 typedef VkInstance Type;
437 Resources (const Environment&, const Parameters&) {}
440 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
442 return getSafeObjectCount<Instance>(context, params, MAX_CONCURRENT_INSTANCES);
445 static Move<VkInstance> create (const Environment& env, const Resources&, const Parameters&)
447 const VkApplicationInfo appInfo =
449 VK_STRUCTURE_TYPE_APPLICATION_INFO,
451 DE_NULL, // pApplicationName
452 0u, // applicationVersion
453 DE_NULL, // pEngineName
455 VK_MAKE_VERSION(1,0,0)
457 const VkInstanceCreateInfo instanceInfo =
459 VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO,
461 (VkInstanceCreateFlags)0,
463 0u, // enabledLayerNameCount
464 DE_NULL, // ppEnabledLayerNames
465 0u, // enabledExtensionNameCount
466 DE_NULL, // ppEnabledExtensionNames
469 return createInstance(env.vkp, &instanceInfo, env.allocationCallbacks);
475 typedef VkDevice Type;
479 deUint32 deviceIndex;
480 VkQueueFlags queueFlags;
482 Parameters (deUint32 deviceIndex_, VkQueueFlags queueFlags_)
483 : deviceIndex (deviceIndex_)
484 , queueFlags (queueFlags_)
490 Dependency<Instance> instance;
492 VkPhysicalDevice physicalDevice;
493 deUint32 queueFamilyIndex;
495 Resources (const Environment& env, const Parameters& params)
496 : instance (env, Instance::Parameters())
497 , vki (env.vkp, *instance.object)
499 , queueFamilyIndex (~0u)
502 const vector<VkPhysicalDevice> physicalDevices = enumeratePhysicalDevices(vki, *instance.object);
504 if (physicalDevices.size() <= (size_t)params.deviceIndex)
505 TCU_THROW(NotSupportedError, "Device not found");
507 physicalDevice = physicalDevices[params.deviceIndex];
511 const vector<VkQueueFamilyProperties> queueProps = getPhysicalDeviceQueueFamilyProperties(vki, physicalDevice);
512 bool foundMatching = false;
514 for (size_t curQueueNdx = 0; curQueueNdx < queueProps.size(); curQueueNdx++)
516 if ((queueProps[curQueueNdx].queueFlags & params.queueFlags) == params.queueFlags)
518 queueFamilyIndex = (deUint32)curQueueNdx;
519 foundMatching = true;
524 TCU_THROW(NotSupportedError, "Matching queue not found");
529 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
531 return getSafeObjectCount<Device>(context, params, MAX_CONCURRENT_DEVICES);
534 static Move<VkDevice> create (const Environment& env, const Resources& res, const Parameters&)
536 const float queuePriority = 1.0;
538 const VkDeviceQueueCreateInfo queues[] =
541 VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO,
543 (VkDeviceQueueCreateFlags)0,
544 res.queueFamilyIndex,
546 &queuePriority, // pQueuePriorities
549 const VkDeviceCreateInfo deviceInfo =
551 VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO,
553 (VkDeviceCreateFlags)0,
554 DE_LENGTH_OF_ARRAY(queues),
556 0u, // enabledLayerNameCount
557 DE_NULL, // ppEnabledLayerNames
558 0u, // enabledExtensionNameCount
559 DE_NULL, // ppEnabledExtensionNames
560 DE_NULL, // pEnabledFeatures
563 return createDevice(res.vki, res.physicalDevice, &deviceInfo, env.allocationCallbacks);
569 typedef VkDeviceMemory Type;
574 deUint32 memoryTypeIndex;
576 Parameters (VkDeviceSize size_, deUint32 memoryTypeIndex_)
578 , memoryTypeIndex (memoryTypeIndex_)
580 DE_ASSERT(memoryTypeIndex < VK_MAX_MEMORY_TYPES);
586 Resources (const Environment&, const Parameters&) {}
589 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
591 const VkDeviceSize deviceMemoryUsage = params.size + getPageTableSize(context, params.size);
593 return getSafeObjectCount<DeviceMemory>(context,
595 de::min(context.getDeviceProperties().limits.maxMemoryAllocationCount,
596 (deUint32)DEFAULT_MAX_CONCURRENT_OBJECTS),
600 static Move<VkDeviceMemory> create (const Environment& env, const Resources&, const Parameters& params)
602 const VkMemoryAllocateInfo allocInfo =
604 VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO,
607 params.memoryTypeIndex
610 return allocateMemory(env.vkd, env.device, &allocInfo, env.allocationCallbacks);
614 DeviceMemory::Parameters getDeviceMemoryParameters (const VkMemoryRequirements& memReqs)
616 return DeviceMemory::Parameters(memReqs.size, deCtz32(memReqs.memoryTypeBits));
619 DeviceMemory::Parameters getDeviceMemoryParameters (const Environment& env, VkImage image)
621 return getDeviceMemoryParameters(getImageMemoryRequirements(env.vkd, env.device, image));
624 DeviceMemory::Parameters getDeviceMemoryParameters (const Environment& env, VkBuffer image)
626 return getDeviceMemoryParameters(getBufferMemoryRequirements(env.vkd, env.device, image));
631 typedef VkBuffer Type;
636 VkBufferUsageFlags usage;
638 Parameters (VkDeviceSize size_,
639 VkBufferUsageFlags usage_)
647 Resources (const Environment&, const Parameters&) {}
650 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
652 const Environment env (context, 1u);
653 const Resources res (env, params);
654 const Unique<VkBuffer> buffer (create(env, res, params));
655 const VkMemoryRequirements memReqs = getBufferMemoryRequirements(env.vkd, env.device, *buffer);
657 return getSafeObjectCount<Buffer>(context,
659 DEFAULT_MAX_CONCURRENT_OBJECTS,
660 getPageTableSize(context, memReqs.size));
663 static Move<VkBuffer> create (const Environment& env, const Resources&, const Parameters& params)
665 const VkBufferCreateInfo bufferInfo =
667 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO,
669 (VkBufferCreateFlags)0,
672 VK_SHARING_MODE_EXCLUSIVE,
674 &env.queueFamilyIndex
677 return createBuffer(env.vkd, env.device, &bufferInfo, env.allocationCallbacks);
683 typedef VkBufferView Type;
687 Buffer::Parameters buffer;
692 Parameters (const Buffer::Parameters& buffer_,
694 VkDeviceSize offset_,
705 Dependency<Buffer> buffer;
706 Dependency<DeviceMemory> memory;
708 Resources (const Environment& env, const Parameters& params)
709 : buffer(env, params.buffer)
710 , memory(env, getDeviceMemoryParameters(env, *buffer.object))
712 VK_CHECK(env.vkd.bindBufferMemory(env.device, *buffer.object, *memory.object, 0));
716 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
718 return getSafeObjectCount<BufferView>(context, params, DEFAULT_MAX_CONCURRENT_OBJECTS);
721 static Move<VkBufferView> create (const Environment& env, const Resources& res, const Parameters& params)
723 const VkBufferViewCreateInfo bufferViewInfo =
725 VK_STRUCTURE_TYPE_BUFFER_VIEW_CREATE_INFO,
727 (VkBufferViewCreateFlags)0,
734 return createBufferView(env.vkd, env.device, &bufferViewInfo, env.allocationCallbacks);
740 typedef VkImage Type;
744 VkImageCreateFlags flags;
745 VkImageType imageType;
750 VkSampleCountFlagBits samples;
751 VkImageTiling tiling;
752 VkImageUsageFlags usage;
753 VkImageLayout initialLayout;
755 Parameters (VkImageCreateFlags flags_,
756 VkImageType imageType_,
761 VkSampleCountFlagBits samples_,
762 VkImageTiling tiling_,
763 VkImageUsageFlags usage_,
764 VkImageLayout initialLayout_)
766 , imageType (imageType_)
769 , mipLevels (mipLevels_)
770 , arraySize (arraySize_)
774 , initialLayout (initialLayout_)
780 Resources (const Environment&, const Parameters&) {}
783 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
785 const Environment env (context, 1u);
786 const Resources res (env, params);
787 const Unique<VkImage> image (create(env, res, params));
788 const VkMemoryRequirements memReqs = getImageMemoryRequirements(env.vkd, env.device, *image);
790 return getSafeObjectCount<Image>(context,
792 DEFAULT_MAX_CONCURRENT_OBJECTS,
793 getPageTableSize(context, memReqs.size));
796 static Move<VkImage> create (const Environment& env, const Resources&, const Parameters& params)
798 const VkImageCreateInfo imageInfo =
800 VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO,
811 VK_SHARING_MODE_EXCLUSIVE, // sharingMode
812 1u, // queueFamilyIndexCount
813 &env.queueFamilyIndex, // pQueueFamilyIndices
817 return createImage(env.vkd, env.device, &imageInfo, env.allocationCallbacks);
823 typedef VkImageView Type;
827 Image::Parameters image;
828 VkImageViewType viewType;
830 VkComponentMapping components;
831 VkImageSubresourceRange subresourceRange;
833 Parameters (const Image::Parameters& image_,
834 VkImageViewType viewType_,
836 VkComponentMapping components_,
837 VkImageSubresourceRange subresourceRange_)
839 , viewType (viewType_)
841 , components (components_)
842 , subresourceRange (subresourceRange_)
848 Dependency<Image> image;
849 Dependency<DeviceMemory> memory;
851 Resources (const Environment& env, const Parameters& params)
852 : image (env, params.image)
853 , memory(env, getDeviceMemoryParameters(env, *image.object))
855 VK_CHECK(env.vkd.bindImageMemory(env.device, *image.object, *memory.object, 0));
859 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
861 return getSafeObjectCount<ImageView>(context, params, DEFAULT_MAX_CONCURRENT_OBJECTS);
864 static Move<VkImageView> create (const Environment& env, const Resources& res, const Parameters& params)
866 const VkImageViewCreateInfo imageViewInfo =
868 VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
870 (VkImageViewCreateFlags)0,
875 params.subresourceRange,
878 return createImageView(env.vkd, env.device, &imageViewInfo, env.allocationCallbacks);
884 typedef VkSemaphore Type;
888 VkSemaphoreCreateFlags flags;
890 Parameters (VkSemaphoreCreateFlags flags_)
897 Resources (const Environment&, const Parameters&) {}
900 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
902 return getSafeObjectCount<Semaphore>(context, params, MAX_CONCURRENT_SYNC_PRIMITIVES);
905 static Move<VkSemaphore> create (const Environment& env, const Resources&, const Parameters& params)
907 const VkSemaphoreCreateInfo semaphoreInfo =
909 VK_STRUCTURE_TYPE_SEMAPHORE_CREATE_INFO,
914 return createSemaphore(env.vkd, env.device, &semaphoreInfo, env.allocationCallbacks);
920 typedef VkFence Type;
924 VkFenceCreateFlags flags;
926 Parameters (VkFenceCreateFlags flags_)
933 Resources (const Environment&, const Parameters&) {}
936 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
938 return getSafeObjectCount<Fence>(context, params, MAX_CONCURRENT_SYNC_PRIMITIVES);
941 static Move<VkFence> create (const Environment& env, const Resources&, const Parameters& params)
943 const VkFenceCreateInfo fenceInfo =
945 VK_STRUCTURE_TYPE_FENCE_CREATE_INFO,
950 return createFence(env.vkd, env.device, &fenceInfo, env.allocationCallbacks);
956 typedef VkEvent Type;
960 VkEventCreateFlags flags;
962 Parameters (VkEventCreateFlags flags_)
969 Resources (const Environment&, const Parameters&) {}
972 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
974 return getSafeObjectCount<Event>(context, params, MAX_CONCURRENT_SYNC_PRIMITIVES);
977 static Move<VkEvent> create (const Environment& env, const Resources&, const Parameters& params)
979 const VkEventCreateInfo eventInfo =
981 VK_STRUCTURE_TYPE_EVENT_CREATE_INFO,
986 return createEvent(env.vkd, env.device, &eventInfo, env.allocationCallbacks);
992 typedef VkQueryPool Type;
996 VkQueryType queryType;
998 VkQueryPipelineStatisticFlags pipelineStatistics;
1000 Parameters (VkQueryType queryType_,
1001 deUint32 entryCount_,
1002 VkQueryPipelineStatisticFlags pipelineStatistics_)
1003 : queryType (queryType_)
1004 , entryCount (entryCount_)
1005 , pipelineStatistics (pipelineStatistics_)
1011 Resources (const Environment&, const Parameters&) {}
1014 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
1016 return getSafeObjectCount<QueryPool>(context, params, DEFAULT_MAX_CONCURRENT_OBJECTS);
1019 static Move<VkQueryPool> create (const Environment& env, const Resources&, const Parameters& params)
1021 const VkQueryPoolCreateInfo queryPoolInfo =
1023 VK_STRUCTURE_TYPE_QUERY_POOL_CREATE_INFO,
1025 (VkQueryPoolCreateFlags)0,
1028 params.pipelineStatistics
1031 return createQueryPool(env.vkd, env.device, &queryPoolInfo, env.allocationCallbacks);
1037 typedef VkShaderModule Type;
1041 VkShaderStageFlagBits shaderStage;
1044 Parameters (VkShaderStageFlagBits shaderStage_,
1045 const std::string& binaryName_)
1046 : shaderStage (shaderStage_)
1047 , binaryName (binaryName_)
1053 const ProgramBinary& binary;
1055 Resources (const Environment& env, const Parameters& params)
1056 : binary(env.programBinaries.get(params.binaryName))
1060 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
1062 return getSafeObjectCount<ShaderModule>(context, params, DEFAULT_MAX_CONCURRENT_OBJECTS);
1065 static const char* getSource (VkShaderStageFlagBits stage)
1069 case VK_SHADER_STAGE_VERTEX_BIT:
1070 return "#version 310 es\n"
1071 "layout(location = 0) in highp vec4 a_position;\n"
1072 "void main () { gl_Position = a_position; }\n";
1074 case VK_SHADER_STAGE_FRAGMENT_BIT:
1075 return "#version 310 es\n"
1076 "layout(location = 0) out mediump vec4 o_color;\n"
1077 "void main () { o_color = vec4(1.0, 0.5, 0.25, 1.0); }";
1079 case VK_SHADER_STAGE_COMPUTE_BIT:
1080 return "#version 310 es\n"
1081 "layout(binding = 0) buffer Input { highp uint dataIn[]; };\n"
1082 "layout(binding = 1) buffer Output { highp uint dataOut[]; };\n"
1083 "void main (void)\n"
1085 " dataOut[gl_GlobalInvocationID.x] = ~dataIn[gl_GlobalInvocationID.x];\n"
1089 DE_FATAL("Not implemented");
1094 static void initPrograms (SourceCollections& dst, Parameters params)
1096 const char* const source = getSource(params.shaderStage);
1100 dst.glslSources.add(params.binaryName)
1101 << glu::ShaderSource(getGluShaderType(params.shaderStage), source);
1104 static Move<VkShaderModule> create (const Environment& env, const Resources& res, const Parameters&)
1106 const VkShaderModuleCreateInfo shaderModuleInfo =
1108 VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO,
1110 (VkShaderModuleCreateFlags)0,
1111 res.binary.getSize(),
1112 (const deUint32*)res.binary.getBinary(),
1115 return createShaderModule(env.vkd, env.device, &shaderModuleInfo, env.allocationCallbacks);
1119 struct PipelineCache
1121 typedef VkPipelineCache Type;
1125 Parameters (void) {}
1130 Resources (const Environment&, const Parameters&) {}
1133 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
1135 return getSafeObjectCount<PipelineCache>(context, params, MAX_CONCURRENT_PIPELINE_CACHES);
1138 static Move<VkPipelineCache> create (const Environment& env, const Resources&, const Parameters&)
1140 const VkPipelineCacheCreateInfo pipelineCacheInfo =
1142 VK_STRUCTURE_TYPE_PIPELINE_CACHE_CREATE_INFO,
1144 (VkPipelineCacheCreateFlags)0u,
1145 0u, // initialDataSize
1146 DE_NULL, // pInitialData
1149 return createPipelineCache(env.vkd, env.device, &pipelineCacheInfo, env.allocationCallbacks);
1155 typedef VkSampler Type;
1161 VkSamplerMipmapMode mipmapMode;
1162 VkSamplerAddressMode addressModeU;
1163 VkSamplerAddressMode addressModeV;
1164 VkSamplerAddressMode addressModeW;
1166 VkBool32 anisotropyEnable;
1167 float maxAnisotropy;
1168 VkBool32 compareEnable;
1169 VkCompareOp compareOp;
1172 VkBorderColor borderColor;
1173 VkBool32 unnormalizedCoordinates;
1175 // \todo [2015-09-17 pyry] Other configurations
1177 : magFilter (VK_FILTER_NEAREST)
1178 , minFilter (VK_FILTER_NEAREST)
1179 , mipmapMode (VK_SAMPLER_MIPMAP_MODE_NEAREST)
1180 , addressModeU (VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE)
1181 , addressModeV (VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE)
1182 , addressModeW (VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE)
1184 , anisotropyEnable (VK_FALSE)
1185 , maxAnisotropy (1.0f)
1186 , compareEnable (VK_FALSE)
1187 , compareOp (VK_COMPARE_OP_ALWAYS)
1190 , borderColor (VK_BORDER_COLOR_FLOAT_TRANSPARENT_BLACK)
1191 , unnormalizedCoordinates (VK_FALSE)
1197 Resources (const Environment&, const Parameters&) {}
1200 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
1202 return getSafeObjectCount<Sampler>(context,
1204 de::min(context.getDeviceProperties().limits.maxSamplerAllocationCount,
1205 (deUint32)DEFAULT_MAX_CONCURRENT_OBJECTS));
1208 static Move<VkSampler> create (const Environment& env, const Resources&, const Parameters& params)
1210 const VkSamplerCreateInfo samplerInfo =
1212 VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO,
1214 (VkSamplerCreateFlags)0,
1218 params.addressModeU,
1219 params.addressModeV,
1220 params.addressModeW,
1222 params.anisotropyEnable,
1223 params.maxAnisotropy,
1224 params.compareEnable,
1229 params.unnormalizedCoordinates
1232 return createSampler(env.vkd, env.device, &samplerInfo, env.allocationCallbacks);
1236 struct DescriptorSetLayout
1238 typedef VkDescriptorSetLayout Type;
1245 VkDescriptorType descriptorType;
1246 deUint32 descriptorCount;
1247 VkShaderStageFlags stageFlags;
1248 bool useImmutableSampler;
1250 Binding (deUint32 binding_,
1251 VkDescriptorType descriptorType_,
1252 deUint32 descriptorCount_,
1253 VkShaderStageFlags stageFlags_,
1254 bool useImmutableSampler_)
1255 : binding (binding_)
1256 , descriptorType (descriptorType_)
1257 , descriptorCount (descriptorCount_)
1258 , stageFlags (stageFlags_)
1259 , useImmutableSampler (useImmutableSampler_)
1265 vector<Binding> bindings;
1267 Parameters (const vector<Binding>& bindings_)
1268 : bindings(bindings_)
1271 static Parameters empty (void)
1273 return Parameters(vector<Binding>());
1276 static Parameters single (deUint32 binding,
1277 VkDescriptorType descriptorType,
1278 deUint32 descriptorCount,
1279 VkShaderStageFlags stageFlags,
1280 bool useImmutableSampler = false)
1282 vector<Binding> bindings;
1283 bindings.push_back(Binding(binding, descriptorType, descriptorCount, stageFlags, useImmutableSampler));
1284 return Parameters(bindings);
1290 vector<VkDescriptorSetLayoutBinding> bindings;
1291 MovePtr<Dependency<Sampler> > immutableSampler;
1292 vector<VkSampler> immutableSamplersPtr;
1294 Resources (const Environment& env, const Parameters& params)
1296 // Create immutable sampler if needed
1297 for (vector<Parameters::Binding>::const_iterator cur = params.bindings.begin(); cur != params.bindings.end(); cur++)
1299 if (cur->useImmutableSampler && !immutableSampler)
1301 immutableSampler = de::newMovePtr<Dependency<Sampler> >(env, Sampler::Parameters());
1303 if (cur->useImmutableSampler && immutableSamplersPtr.size() < (size_t)cur->descriptorCount)
1304 immutableSamplersPtr.resize(cur->descriptorCount, *immutableSampler->object);
1308 for (vector<Parameters::Binding>::const_iterator cur = params.bindings.begin(); cur != params.bindings.end(); cur++)
1310 const VkDescriptorSetLayoutBinding binding =
1313 cur->descriptorType,
1314 cur->descriptorCount,
1316 (cur->useImmutableSampler ? &immutableSamplersPtr[0] : DE_NULL)
1319 bindings.push_back(binding);
1324 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
1326 return getSafeObjectCount<DescriptorSetLayout>(context, params, DEFAULT_MAX_CONCURRENT_OBJECTS);
1329 static Move<VkDescriptorSetLayout> create (const Environment& env, const Resources& res, const Parameters&)
1331 const VkDescriptorSetLayoutCreateInfo descriptorSetLayoutInfo =
1333 VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO,
1335 (VkDescriptorSetLayoutCreateFlags)0,
1336 (deUint32)res.bindings.size(),
1337 (res.bindings.empty() ? DE_NULL : &res.bindings[0])
1340 return createDescriptorSetLayout(env.vkd, env.device, &descriptorSetLayoutInfo, env.allocationCallbacks);
1344 struct PipelineLayout
1346 typedef VkPipelineLayout Type;
1350 vector<DescriptorSetLayout::Parameters> descriptorSetLayouts;
1351 vector<VkPushConstantRange> pushConstantRanges;
1353 Parameters (void) {}
1355 static Parameters empty (void)
1357 return Parameters();
1360 static Parameters singleDescriptorSet (const DescriptorSetLayout::Parameters& descriptorSetLayout)
1363 params.descriptorSetLayouts.push_back(descriptorSetLayout);
1370 typedef SharedPtr<Dependency<DescriptorSetLayout> > DescriptorSetLayoutDepSp;
1371 typedef vector<DescriptorSetLayoutDepSp> DescriptorSetLayouts;
1373 DescriptorSetLayouts descriptorSetLayouts;
1374 vector<VkDescriptorSetLayout> pSetLayouts;
1376 Resources (const Environment& env, const Parameters& params)
1378 for (vector<DescriptorSetLayout::Parameters>::const_iterator dsParams = params.descriptorSetLayouts.begin();
1379 dsParams != params.descriptorSetLayouts.end();
1382 descriptorSetLayouts.push_back(DescriptorSetLayoutDepSp(new Dependency<DescriptorSetLayout>(env, *dsParams)));
1383 pSetLayouts.push_back(*descriptorSetLayouts.back()->object);
1388 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
1390 return getSafeObjectCount<PipelineLayout>(context, params, DEFAULT_MAX_CONCURRENT_OBJECTS);
1393 static Move<VkPipelineLayout> create (const Environment& env, const Resources& res, const Parameters& params)
1395 const VkPipelineLayoutCreateInfo pipelineLayoutInfo =
1397 VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO,
1399 (VkPipelineLayoutCreateFlags)0,
1400 (deUint32)res.pSetLayouts.size(),
1401 (res.pSetLayouts.empty() ? DE_NULL : &res.pSetLayouts[0]),
1402 (deUint32)params.pushConstantRanges.size(),
1403 (params.pushConstantRanges.empty() ? DE_NULL : ¶ms.pushConstantRanges[0]),
1406 return createPipelineLayout(env.vkd, env.device, &pipelineLayoutInfo, env.allocationCallbacks);
1412 typedef VkRenderPass Type;
1414 // \todo [2015-09-17 pyry] More interesting configurations
1417 Parameters (void) {}
1422 Resources (const Environment&, const Parameters&) {}
1425 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
1427 return getSafeObjectCount<RenderPass>(context, params, DEFAULT_MAX_CONCURRENT_OBJECTS);
1430 static Move<VkRenderPass> create (const Environment& env, const Resources&, const Parameters&)
1432 const VkAttachmentDescription attachments[] =
1435 (VkAttachmentDescriptionFlags)0,
1436 VK_FORMAT_R8G8B8A8_UNORM,
1437 VK_SAMPLE_COUNT_1_BIT,
1438 VK_ATTACHMENT_LOAD_OP_CLEAR,
1439 VK_ATTACHMENT_STORE_OP_STORE,
1440 VK_ATTACHMENT_LOAD_OP_DONT_CARE,
1441 VK_ATTACHMENT_STORE_OP_DONT_CARE,
1442 VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
1443 VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
1446 (VkAttachmentDescriptionFlags)0,
1447 VK_FORMAT_D16_UNORM,
1448 VK_SAMPLE_COUNT_1_BIT,
1449 VK_ATTACHMENT_LOAD_OP_CLEAR,
1450 VK_ATTACHMENT_STORE_OP_DONT_CARE,
1451 VK_ATTACHMENT_LOAD_OP_DONT_CARE,
1452 VK_ATTACHMENT_STORE_OP_DONT_CARE,
1453 VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
1454 VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
1457 const VkAttachmentReference colorAttachments[] =
1461 VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
1464 const VkAttachmentReference dsAttachment =
1467 VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL
1469 const VkSubpassDescription subpasses[] =
1472 (VkSubpassDescriptionFlags)0,
1473 VK_PIPELINE_BIND_POINT_GRAPHICS,
1474 0u, // inputAttachmentCount
1475 DE_NULL, // pInputAttachments
1476 DE_LENGTH_OF_ARRAY(colorAttachments),
1478 DE_NULL, // pResolveAttachments
1480 0u, // preserveAttachmentCount
1481 DE_NULL, // pPreserveAttachments
1484 const VkRenderPassCreateInfo renderPassInfo =
1486 VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO,
1488 (VkRenderPassCreateFlags)0,
1489 DE_LENGTH_OF_ARRAY(attachments),
1491 DE_LENGTH_OF_ARRAY(subpasses),
1493 0u, // dependencyCount
1494 DE_NULL // pDependencies
1497 return createRenderPass(env.vkd, env.device, &renderPassInfo, env.allocationCallbacks);
1501 struct GraphicsPipeline
1503 typedef VkPipeline Type;
1505 // \todo [2015-09-17 pyry] More interesting configurations
1508 Parameters (void) {}
1513 Dependency<ShaderModule> vertexShader;
1514 Dependency<ShaderModule> fragmentShader;
1515 Dependency<PipelineLayout> layout;
1516 Dependency<RenderPass> renderPass;
1517 Dependency<PipelineCache> pipelineCache;
1519 Resources (const Environment& env, const Parameters&)
1520 : vertexShader (env, ShaderModule::Parameters(VK_SHADER_STAGE_VERTEX_BIT, "vert"))
1521 , fragmentShader (env, ShaderModule::Parameters(VK_SHADER_STAGE_FRAGMENT_BIT, "frag"))
1522 , layout (env, PipelineLayout::Parameters::singleDescriptorSet(
1523 DescriptorSetLayout::Parameters::single(0u, VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, 1u, VK_SHADER_STAGE_FRAGMENT_BIT, true)))
1524 , renderPass (env, RenderPass::Parameters())
1525 , pipelineCache (env, PipelineCache::Parameters())
1529 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
1531 return getSafeObjectCount<GraphicsPipeline>(context, params, DEFAULT_MAX_CONCURRENT_OBJECTS);
1534 static void initPrograms (SourceCollections& dst, Parameters)
1536 ShaderModule::initPrograms(dst, ShaderModule::Parameters(VK_SHADER_STAGE_VERTEX_BIT, "vert"));
1537 ShaderModule::initPrograms(dst, ShaderModule::Parameters(VK_SHADER_STAGE_FRAGMENT_BIT, "frag"));
1540 static vector<VkPipelineSp> createMultiple (const Environment& env, const Resources& res, const Parameters&, vector<VkPipeline>* const pOutHandles, VkResult* const pOutResult)
1542 DE_ASSERT(pOutResult);
1543 DE_ASSERT(pOutHandles);
1544 DE_ASSERT(pOutHandles->size() != 0);
1546 const VkPipelineShaderStageCreateInfo stages[] =
1549 VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
1551 (VkPipelineShaderStageCreateFlags)0,
1552 VK_SHADER_STAGE_VERTEX_BIT,
1553 *res.vertexShader.object,
1555 DE_NULL, // pSpecializationInfo
1558 VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
1560 (VkPipelineShaderStageCreateFlags)0,
1561 VK_SHADER_STAGE_FRAGMENT_BIT,
1562 *res.fragmentShader.object,
1564 DE_NULL, // pSpecializationInfo
1567 const VkVertexInputBindingDescription vertexBindings[] =
1572 VK_VERTEX_INPUT_RATE_VERTEX
1575 const VkVertexInputAttributeDescription vertexAttribs[] =
1580 VK_FORMAT_R32G32B32A32_SFLOAT,
1584 const VkPipelineVertexInputStateCreateInfo vertexInputState =
1586 VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO,
1588 (VkPipelineVertexInputStateCreateFlags)0,
1589 DE_LENGTH_OF_ARRAY(vertexBindings),
1591 DE_LENGTH_OF_ARRAY(vertexAttribs),
1594 const VkPipelineInputAssemblyStateCreateInfo inputAssemblyState =
1596 VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO,
1598 (VkPipelineInputAssemblyStateCreateFlags)0,
1599 VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST,
1600 VK_FALSE // primitiveRestartEnable
1602 const VkViewport viewports[] =
1604 { 0.0f, 0.0f, 64.f, 64.f, 0.0f, 1.0f }
1606 const VkRect2D scissors[] =
1608 { { 0, 0 }, { 64, 64 } }
1610 const VkPipelineViewportStateCreateInfo viewportState =
1612 VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO,
1614 (VkPipelineViewportStateCreateFlags)0,
1615 DE_LENGTH_OF_ARRAY(viewports),
1617 DE_LENGTH_OF_ARRAY(scissors),
1620 const VkPipelineRasterizationStateCreateInfo rasterState =
1622 VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO,
1624 (VkPipelineRasterizationStateCreateFlags)0,
1625 VK_TRUE, // depthClampEnable
1626 VK_FALSE, // rasterizerDiscardEnable
1627 VK_POLYGON_MODE_FILL,
1628 VK_CULL_MODE_BACK_BIT,
1629 VK_FRONT_FACE_COUNTER_CLOCKWISE,
1630 VK_FALSE, // depthBiasEnable
1631 0.0f, // depthBiasConstantFactor
1632 0.0f, // depthBiasClamp
1633 0.0f, // depthBiasSlopeFactor
1636 const VkPipelineMultisampleStateCreateInfo multisampleState =
1638 VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO,
1640 (VkPipelineMultisampleStateCreateFlags)0,
1641 VK_SAMPLE_COUNT_1_BIT,
1642 VK_FALSE, // sampleShadingEnable
1643 1.0f, // minSampleShading
1644 DE_NULL, // pSampleMask
1645 VK_FALSE, // alphaToCoverageEnable
1646 VK_FALSE, // alphaToOneEnable
1648 const VkPipelineDepthStencilStateCreateInfo depthStencilState =
1650 VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO,
1652 (VkPipelineDepthStencilStateCreateFlags)0,
1653 VK_TRUE, // depthTestEnable
1654 VK_TRUE, // depthWriteEnable
1655 VK_COMPARE_OP_LESS, // depthCompareOp
1656 VK_FALSE, // depthBoundsTestEnable
1657 VK_FALSE, // stencilTestEnable
1658 { VK_STENCIL_OP_KEEP, VK_STENCIL_OP_KEEP, VK_STENCIL_OP_KEEP, VK_COMPARE_OP_ALWAYS, 0u, 0u, 0u },
1659 { VK_STENCIL_OP_KEEP, VK_STENCIL_OP_KEEP, VK_STENCIL_OP_KEEP, VK_COMPARE_OP_ALWAYS, 0u, 0u, 0u },
1660 0.0f, // minDepthBounds
1661 1.0f, // maxDepthBounds
1663 const VkPipelineColorBlendAttachmentState colorBlendAttState[]=
1666 VK_FALSE, // blendEnable
1667 VK_BLEND_FACTOR_ONE,
1668 VK_BLEND_FACTOR_ZERO,
1670 VK_BLEND_FACTOR_ONE,
1671 VK_BLEND_FACTOR_ZERO,
1673 VK_COLOR_COMPONENT_R_BIT|VK_COLOR_COMPONENT_G_BIT|VK_COLOR_COMPONENT_B_BIT|VK_COLOR_COMPONENT_A_BIT
1676 const VkPipelineColorBlendStateCreateInfo colorBlendState =
1678 VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO,
1680 (VkPipelineColorBlendStateCreateFlags)0,
1681 VK_FALSE, // logicOpEnable
1683 DE_LENGTH_OF_ARRAY(colorBlendAttState),
1685 { 0.0f, 0.0f, 0.0f, 0.0f } // blendConstants
1687 const VkGraphicsPipelineCreateInfo pipelineInfo =
1689 VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO,
1691 (VkPipelineCreateFlags)0,
1692 DE_LENGTH_OF_ARRAY(stages),
1695 &inputAssemblyState,
1696 DE_NULL, // pTessellationState
1702 (const VkPipelineDynamicStateCreateInfo*)DE_NULL,
1704 *res.renderPass.object,
1706 (VkPipeline)0, // basePipelineHandle
1707 0, // basePipelineIndex
1710 const deUint32 numPipelines = static_cast<deUint32>(pOutHandles->size());
1711 VkPipeline* const pHandles = &(*pOutHandles)[0];
1712 vector<VkGraphicsPipelineCreateInfo> pipelineInfos (numPipelines, pipelineInfo);
1714 *pOutResult = env.vkd.createGraphicsPipelines(env.device, *res.pipelineCache.object, numPipelines, &pipelineInfos[0], env.allocationCallbacks, pHandles);
1716 vector<VkPipelineSp> pipelines;
1718 // Even if an error is returned, some pipelines may have been created successfully
1719 for (deUint32 i = 0; i < numPipelines; ++i)
1721 if (pHandles[i] != DE_NULL)
1722 pipelines.push_back(VkPipelineSp(new Move<VkPipeline>(check<VkPipeline>(pHandles[i]), Deleter<VkPipeline>(env.vkd, env.device, env.allocationCallbacks))));
1728 static Move<VkPipeline> create (const Environment& env, const Resources& res, const Parameters&)
1730 vector<VkPipeline> handles (1, DE_NULL);
1731 VkResult result = VK_NOT_READY;
1732 vector<VkPipelineSp> scopedHandles = createMultiple(env, res, Parameters(), &handles, &result);
1735 return Move<VkPipeline>(check<VkPipeline>(scopedHandles.front()->disown()), Deleter<VkPipeline>(env.vkd, env.device, env.allocationCallbacks));
1739 struct ComputePipeline
1741 typedef VkPipeline Type;
1743 // \todo [2015-09-17 pyry] More interesting configurations
1746 Parameters (void) {}
1751 Dependency<ShaderModule> shaderModule;
1752 Dependency<PipelineLayout> layout;
1753 Dependency<PipelineCache> pipelineCache;
1755 static DescriptorSetLayout::Parameters getDescriptorSetLayout (void)
1757 typedef DescriptorSetLayout::Parameters::Binding Binding;
1759 vector<Binding> bindings;
1761 bindings.push_back(Binding(0, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, 1u, VK_SHADER_STAGE_COMPUTE_BIT, false));
1762 bindings.push_back(Binding(1, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, 1u, VK_SHADER_STAGE_COMPUTE_BIT, false));
1764 return DescriptorSetLayout::Parameters(bindings);
1767 Resources (const Environment& env, const Parameters&)
1768 : shaderModule (env, ShaderModule::Parameters(VK_SHADER_STAGE_COMPUTE_BIT, "comp"))
1769 , layout (env, PipelineLayout::Parameters::singleDescriptorSet(getDescriptorSetLayout()))
1770 , pipelineCache (env, PipelineCache::Parameters())
1774 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
1776 return getSafeObjectCount<ComputePipeline>(context, params, DEFAULT_MAX_CONCURRENT_OBJECTS);
1779 static void initPrograms (SourceCollections& dst, Parameters)
1781 ShaderModule::initPrograms(dst, ShaderModule::Parameters(VK_SHADER_STAGE_COMPUTE_BIT, "comp"));
1784 static Move<VkPipeline> create (const Environment& env, const Resources& res, const Parameters&)
1786 const VkComputePipelineCreateInfo pipelineInfo =
1788 VK_STRUCTURE_TYPE_COMPUTE_PIPELINE_CREATE_INFO,
1790 (VkPipelineCreateFlags)0,
1792 VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
1794 (VkPipelineShaderStageCreateFlags)0,
1795 VK_SHADER_STAGE_COMPUTE_BIT,
1796 *res.shaderModule.object,
1798 DE_NULL // pSpecializationInfo
1801 (VkPipeline)0, // basePipelineHandle
1802 0u, // basePipelineIndex
1805 return createComputePipeline(env.vkd, env.device, *res.pipelineCache.object, &pipelineInfo, env.allocationCallbacks);
1808 static vector<VkPipelineSp> createMultiple (const Environment& env, const Resources& res, const Parameters&, vector<VkPipeline>* const pOutHandles, VkResult* const pOutResult)
1810 DE_ASSERT(pOutResult);
1811 DE_ASSERT(pOutHandles);
1812 DE_ASSERT(pOutHandles->size() != 0);
1814 const VkComputePipelineCreateInfo commonPipelineInfo =
1816 VK_STRUCTURE_TYPE_COMPUTE_PIPELINE_CREATE_INFO,
1818 (VkPipelineCreateFlags)0,
1820 VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
1822 (VkPipelineShaderStageCreateFlags)0,
1823 VK_SHADER_STAGE_COMPUTE_BIT,
1824 *res.shaderModule.object,
1826 DE_NULL // pSpecializationInfo
1829 (VkPipeline)0, // basePipelineHandle
1830 0u, // basePipelineIndex
1833 const deUint32 numPipelines = static_cast<deUint32>(pOutHandles->size());
1834 VkPipeline* const pHandles = &(*pOutHandles)[0];
1835 vector<VkComputePipelineCreateInfo> pipelineInfos (numPipelines, commonPipelineInfo);
1837 *pOutResult = env.vkd.createComputePipelines(env.device, *res.pipelineCache.object, numPipelines, &pipelineInfos[0], env.allocationCallbacks, pHandles);
1839 vector<VkPipelineSp> pipelines;
1841 // Even if an error is returned, some pipelines may have been created successfully
1842 for (deUint32 i = 0; i < numPipelines; ++i)
1844 if (pHandles[i] != DE_NULL)
1845 pipelines.push_back(VkPipelineSp(new Move<VkPipeline>(check<VkPipeline>(pHandles[i]), Deleter<VkPipeline>(env.vkd, env.device, env.allocationCallbacks))));
1852 struct DescriptorPool
1854 typedef VkDescriptorPool Type;
1858 VkDescriptorPoolCreateFlags flags;
1860 vector<VkDescriptorPoolSize> poolSizes;
1862 Parameters (VkDescriptorPoolCreateFlags flags_,
1864 const vector<VkDescriptorPoolSize>& poolSizes_)
1866 , maxSets (maxSets_)
1867 , poolSizes (poolSizes_)
1870 static Parameters singleType (VkDescriptorPoolCreateFlags flags,
1872 VkDescriptorType type,
1875 vector<VkDescriptorPoolSize> poolSizes;
1876 poolSizes.push_back(makeDescriptorPoolSize(type, count));
1877 return Parameters(flags, maxSets, poolSizes);
1883 Resources (const Environment&, const Parameters&) {}
1886 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
1888 return getSafeObjectCount<DescriptorPool>(context, params, DEFAULT_MAX_CONCURRENT_OBJECTS);
1891 static Move<VkDescriptorPool> create (const Environment& env, const Resources&, const Parameters& params)
1893 const VkDescriptorPoolCreateInfo descriptorPoolInfo =
1895 VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO,
1899 (deUint32)params.poolSizes.size(),
1900 (params.poolSizes.empty() ? DE_NULL : ¶ms.poolSizes[0])
1903 return createDescriptorPool(env.vkd, env.device, &descriptorPoolInfo, env.allocationCallbacks);
1907 struct DescriptorSet
1909 typedef VkDescriptorSet Type;
1913 DescriptorSetLayout::Parameters descriptorSetLayout;
1915 Parameters (const DescriptorSetLayout::Parameters& descriptorSetLayout_)
1916 : descriptorSetLayout(descriptorSetLayout_)
1922 Dependency<DescriptorPool> descriptorPool;
1923 Dependency<DescriptorSetLayout> descriptorSetLayout;
1925 static vector<VkDescriptorPoolSize> computePoolSizes (const DescriptorSetLayout::Parameters& layout, int maxSets)
1927 deUint32 countByType[VK_DESCRIPTOR_TYPE_LAST];
1928 vector<VkDescriptorPoolSize> typeCounts;
1930 std::fill(DE_ARRAY_BEGIN(countByType), DE_ARRAY_END(countByType), 0u);
1932 for (vector<DescriptorSetLayout::Parameters::Binding>::const_iterator cur = layout.bindings.begin();
1933 cur != layout.bindings.end();
1936 DE_ASSERT((deUint32)cur->descriptorType < VK_DESCRIPTOR_TYPE_LAST);
1937 countByType[cur->descriptorType] += cur->descriptorCount * maxSets;
1940 for (deUint32 type = 0; type < VK_DESCRIPTOR_TYPE_LAST; ++type)
1942 if (countByType[type] > 0)
1943 typeCounts.push_back(makeDescriptorPoolSize((VkDescriptorType)type, countByType[type]));
1949 Resources (const Environment& env, const Parameters& params)
1950 : descriptorPool (env, DescriptorPool::Parameters(VK_DESCRIPTOR_POOL_CREATE_FREE_DESCRIPTOR_SET_BIT, env.maxResourceConsumers, computePoolSizes(params.descriptorSetLayout, env.maxResourceConsumers)))
1951 , descriptorSetLayout (env, params.descriptorSetLayout)
1956 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
1958 return getSafeObjectCount<DescriptorSet>(context, params, DEFAULT_MAX_CONCURRENT_OBJECTS);
1961 static Move<VkDescriptorSet> create (const Environment& env, const Resources& res, const Parameters&)
1963 const VkDescriptorSetAllocateInfo allocateInfo =
1965 VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO,
1967 *res.descriptorPool.object,
1969 &res.descriptorSetLayout.object.get(),
1972 return allocateDescriptorSet(env.vkd, env.device, &allocateInfo);
1975 static vector<VkDescriptorSetSp> createMultiple (const Environment& env, const Resources& res, const Parameters&, vector<VkDescriptorSet>* const pOutHandles, VkResult* const pOutResult)
1977 DE_ASSERT(pOutResult);
1978 DE_ASSERT(pOutHandles);
1979 DE_ASSERT(pOutHandles->size() != 0);
1981 const deUint32 numDescriptorSets = static_cast<deUint32>(pOutHandles->size());
1982 VkDescriptorSet* const pHandles = &(*pOutHandles)[0];
1983 const vector<VkDescriptorSetLayout> descriptorSetLayouts (numDescriptorSets, res.descriptorSetLayout.object.get());
1985 const VkDescriptorSetAllocateInfo allocateInfo =
1987 VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO,
1989 *res.descriptorPool.object,
1991 &descriptorSetLayouts[0],
1994 *pOutResult = env.vkd.allocateDescriptorSets(env.device, &allocateInfo, pHandles);
1996 vector<VkDescriptorSetSp> descriptorSets;
1998 if (*pOutResult == VK_SUCCESS)
2000 for (deUint32 i = 0; i < numDescriptorSets; ++i)
2001 descriptorSets.push_back(VkDescriptorSetSp(new Move<VkDescriptorSet>(check<VkDescriptorSet>(pHandles[i]), Deleter<VkDescriptorSet>(env.vkd, env.device, *res.descriptorPool.object))));
2004 return descriptorSets;
2010 typedef VkFramebuffer Type;
2020 Dependency<ImageView> colorAttachment;
2021 Dependency<ImageView> depthStencilAttachment;
2022 Dependency<RenderPass> renderPass;
2024 Resources (const Environment& env, const Parameters&)
2025 : colorAttachment (env, ImageView::Parameters(Image::Parameters(0u, VK_IMAGE_TYPE_2D, VK_FORMAT_R8G8B8A8_UNORM,
2026 makeExtent3D(256, 256, 1),
2028 VK_SAMPLE_COUNT_1_BIT,
2029 VK_IMAGE_TILING_OPTIMAL,
2030 VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT,
2031 VK_IMAGE_LAYOUT_UNDEFINED),
2032 VK_IMAGE_VIEW_TYPE_2D, VK_FORMAT_R8G8B8A8_UNORM,
2033 makeComponentMappingRGBA(),
2034 makeImageSubresourceRange(VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u)))
2035 , depthStencilAttachment (env, ImageView::Parameters(Image::Parameters(0u, VK_IMAGE_TYPE_2D, VK_FORMAT_D16_UNORM,
2036 makeExtent3D(256, 256, 1),
2038 VK_SAMPLE_COUNT_1_BIT,
2039 VK_IMAGE_TILING_OPTIMAL,
2040 VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT,
2041 VK_IMAGE_LAYOUT_UNDEFINED),
2042 VK_IMAGE_VIEW_TYPE_2D, VK_FORMAT_D16_UNORM,
2043 makeComponentMappingRGBA(),
2044 makeImageSubresourceRange(VK_IMAGE_ASPECT_DEPTH_BIT, 0u, 1u, 0u, 1u)))
2045 , renderPass (env, RenderPass::Parameters())
2049 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
2051 // \todo [2016-03-23 pyry] Take into account attachment sizes
2052 return getSafeObjectCount<Framebuffer>(context, params, DEFAULT_MAX_CONCURRENT_OBJECTS);
2055 static Move<VkFramebuffer> create (const Environment& env, const Resources& res, const Parameters&)
2057 const VkImageView attachments[] =
2059 *res.colorAttachment.object,
2060 *res.depthStencilAttachment.object,
2062 const VkFramebufferCreateInfo framebufferInfo =
2064 VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO,
2066 (VkFramebufferCreateFlags)0,
2067 *res.renderPass.object,
2068 (deUint32)DE_LENGTH_OF_ARRAY(attachments),
2075 return createFramebuffer(env.vkd, env.device, &framebufferInfo, env.allocationCallbacks);
2081 typedef VkCommandPool Type;
2085 VkCommandPoolCreateFlags flags;
2087 Parameters (VkCommandPoolCreateFlags flags_)
2094 Resources (const Environment&, const Parameters&) {}
2097 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
2099 return getSafeObjectCount<CommandPool>(context, params, DEFAULT_MAX_CONCURRENT_OBJECTS);
2102 static Move<VkCommandPool> create (const Environment& env, const Resources&, const Parameters& params)
2104 const VkCommandPoolCreateInfo cmdPoolInfo =
2106 VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO,
2109 env.queueFamilyIndex,
2112 return createCommandPool(env.vkd, env.device, &cmdPoolInfo, env.allocationCallbacks);
2116 struct CommandBuffer
2118 typedef VkCommandBuffer Type;
2122 CommandPool::Parameters commandPool;
2123 VkCommandBufferLevel level;
2125 Parameters (const CommandPool::Parameters& commandPool_,
2126 VkCommandBufferLevel level_)
2127 : commandPool (commandPool_)
2134 Dependency<CommandPool> commandPool;
2136 Resources (const Environment& env, const Parameters& params)
2137 : commandPool(env, params.commandPool)
2141 static deUint32 getMaxConcurrent (Context& context, const Parameters& params)
2143 return getSafeObjectCount<CommandBuffer>(context, params, DEFAULT_MAX_CONCURRENT_OBJECTS);
2146 static Move<VkCommandBuffer> create (const Environment& env, const Resources& res, const Parameters& params)
2148 const VkCommandBufferAllocateInfo cmdBufferInfo =
2150 VK_STRUCTURE_TYPE_COMMAND_BUFFER_ALLOCATE_INFO,
2152 *res.commandPool.object,
2157 return allocateCommandBuffer(env.vkd, env.device, &cmdBufferInfo);
2160 static vector<VkCommandBufferSp> createMultiple (const Environment& env, const Resources& res, const Parameters& params, vector<VkCommandBuffer>* const pOutHandles, VkResult* const pOutResult)
2162 DE_ASSERT(pOutResult);
2163 DE_ASSERT(pOutHandles);
2164 DE_ASSERT(pOutHandles->size() != 0);
2166 const deUint32 numCommandBuffers = static_cast<deUint32>(pOutHandles->size());
2167 VkCommandBuffer* const pHandles = &(*pOutHandles)[0];
2169 const VkCommandBufferAllocateInfo cmdBufferInfo =
2171 VK_STRUCTURE_TYPE_COMMAND_BUFFER_ALLOCATE_INFO,
2173 *res.commandPool.object,
2178 *pOutResult = env.vkd.allocateCommandBuffers(env.device, &cmdBufferInfo, pHandles);
2180 vector<VkCommandBufferSp> commandBuffers;
2182 if (*pOutResult == VK_SUCCESS)
2184 for (deUint32 i = 0; i < numCommandBuffers; ++i)
2185 commandBuffers.push_back(VkCommandBufferSp(new Move<VkCommandBuffer>(check<VkCommandBuffer>(pHandles[i]), Deleter<VkCommandBuffer>(env.vkd, env.device, *res.commandPool.object))));
2188 return commandBuffers;
2194 template<typename Object>
2195 tcu::TestStatus createSingleTest (Context& context, typename Object::Parameters params)
2197 const Environment env (context, 1u);
2198 const typename Object::Resources res (env, params);
2201 Unique<typename Object::Type> obj (Object::create(env, res, params));
2204 return tcu::TestStatus::pass("Ok");
2207 template<typename Object>
2208 tcu::TestStatus createMultipleUniqueResourcesTest (Context& context, typename Object::Parameters params)
2210 const Environment env (context, 1u);
2211 const typename Object::Resources res0 (env, params);
2212 const typename Object::Resources res1 (env, params);
2213 const typename Object::Resources res2 (env, params);
2214 const typename Object::Resources res3 (env, params);
2217 Unique<typename Object::Type> obj0 (Object::create(env, res0, params));
2218 Unique<typename Object::Type> obj1 (Object::create(env, res1, params));
2219 Unique<typename Object::Type> obj2 (Object::create(env, res2, params));
2220 Unique<typename Object::Type> obj3 (Object::create(env, res3, params));
2223 return tcu::TestStatus::pass("Ok");
2226 template<typename Object>
2227 tcu::TestStatus createMultipleSharedResourcesTest (Context& context, typename Object::Parameters params)
2229 const Environment env (context, 4u);
2230 const typename Object::Resources res (env, params);
2233 Unique<typename Object::Type> obj0 (Object::create(env, res, params));
2234 Unique<typename Object::Type> obj1 (Object::create(env, res, params));
2235 Unique<typename Object::Type> obj2 (Object::create(env, res, params));
2236 Unique<typename Object::Type> obj3 (Object::create(env, res, params));
2239 return tcu::TestStatus::pass("Ok");
2242 template<typename Object>
2243 tcu::TestStatus createMaxConcurrentTest (Context& context, typename Object::Parameters params)
2245 typedef Unique<typename Object::Type> UniqueObject;
2246 typedef SharedPtr<UniqueObject> ObjectPtr;
2248 const deUint32 numObjects = Object::getMaxConcurrent(context, params);
2249 const Environment env (context, numObjects);
2250 const typename Object::Resources res (env, params);
2251 vector<ObjectPtr> objects (numObjects);
2252 const deUint32 watchdogInterval = 1024;
2254 context.getTestContext().getLog()
2255 << TestLog::Message << "Creating " << numObjects << " " << getTypeName<typename Object::Type>() << " objects" << TestLog::EndMessage;
2257 for (deUint32 ndx = 0; ndx < numObjects; ndx++)
2259 objects[ndx] = ObjectPtr(new UniqueObject(Object::create(env, res, params)));
2261 if ((ndx > 0) && ((ndx % watchdogInterval) == 0))
2262 context.getTestContext().touchWatchdog();
2265 context.getTestContext().touchWatchdog();
2268 return tcu::TestStatus::pass("Ok");
2271 // How many objects to create per thread
2272 template<typename Object> int getCreateCount (void) { return 100; }
2274 // Creating VkDevice and VkInstance can take significantly longer than other object types
2275 template<> int getCreateCount<Instance> (void) { return 20; }
2276 template<> int getCreateCount<Device> (void) { return 20; }
2278 template<typename Object>
2279 class CreateThread : public ThreadGroupThread
2282 CreateThread (const Environment& env, const typename Object::Resources& resources, const typename Object::Parameters& params)
2284 , m_resources (resources)
2288 void runThread (void)
2290 const int numIters = getCreateCount<Object>();
2291 const int itersBetweenSyncs = numIters / 5;
2293 DE_ASSERT(itersBetweenSyncs > 0);
2295 for (int iterNdx = 0; iterNdx < numIters; iterNdx++)
2297 // Sync every Nth iteration to make entering driver at the same time more likely
2298 if ((iterNdx % itersBetweenSyncs) == 0)
2302 Unique<typename Object::Type> obj (Object::create(m_env, m_resources, m_params));
2308 const Environment& m_env;
2309 const typename Object::Resources& m_resources;
2310 const typename Object::Parameters& m_params;
2313 template<typename Object>
2314 tcu::TestStatus multithreadedCreateSharedResourcesTest (Context& context, typename Object::Parameters params)
2316 TestLog& log = context.getTestContext().getLog();
2317 const deUint32 numThreads = getDefaultTestThreadCount();
2318 const Environment env (context, numThreads);
2319 const typename Object::Resources res (env, params);
2320 ThreadGroup threads;
2322 log << TestLog::Message << "numThreads = " << numThreads << TestLog::EndMessage;
2324 for (deUint32 ndx = 0; ndx < numThreads; ndx++)
2325 threads.add(MovePtr<ThreadGroupThread>(new CreateThread<Object>(env, res, params)));
2327 return threads.run();
2330 template<typename Object>
2331 tcu::TestStatus multithreadedCreatePerThreadResourcesTest (Context& context, typename Object::Parameters params)
2333 typedef SharedPtr<typename Object::Resources> ResPtr;
2335 TestLog& log = context.getTestContext().getLog();
2336 const deUint32 numThreads = getDefaultTestThreadCount();
2337 const Environment env (context, 1u);
2338 vector<ResPtr> resources (numThreads);
2339 ThreadGroup threads;
2341 log << TestLog::Message << "numThreads = " << numThreads << TestLog::EndMessage;
2343 for (deUint32 ndx = 0; ndx < numThreads; ndx++)
2345 resources[ndx] = ResPtr(new typename Object::Resources(env, params));
2346 threads.add(MovePtr<ThreadGroupThread>(new CreateThread<Object>(env, *resources[ndx], params)));
2349 return threads.run();
2354 Device::Resources deviceRes;
2355 Unique<VkDevice> device;
2359 EnvClone (const Environment& parent, const Device::Parameters& deviceParams, deUint32 maxResourceConsumers)
2360 : deviceRes (parent, deviceParams)
2361 , device (Device::create(parent, deviceRes, deviceParams))
2362 , vkd (deviceRes.vki, *device)
2363 , env (parent.vkp, vkd, *device, deviceRes.queueFamilyIndex, parent.programBinaries, parent.allocationCallbacks, maxResourceConsumers)
2368 Device::Parameters getDefaulDeviceParameters (Context& context)
2370 return Device::Parameters(context.getTestContext().getCommandLine().getVKDeviceId()-1u,
2371 VK_QUEUE_GRAPHICS_BIT|VK_QUEUE_COMPUTE_BIT);
2374 template<typename Object>
2375 tcu::TestStatus multithreadedCreatePerThreadDeviceTest (Context& context, typename Object::Parameters params)
2377 typedef SharedPtr<EnvClone> EnvPtr;
2378 typedef SharedPtr<typename Object::Resources> ResPtr;
2380 TestLog& log = context.getTestContext().getLog();
2381 const deUint32 numThreads = getDefaultTestThreadCount();
2382 const Device::Parameters deviceParams = getDefaulDeviceParameters(context);
2383 const Environment sharedEnv (context, numThreads); // For creating Device's
2384 vector<EnvPtr> perThreadEnv (numThreads);
2385 vector<ResPtr> resources (numThreads);
2386 ThreadGroup threads;
2388 log << TestLog::Message << "numThreads = " << numThreads << TestLog::EndMessage;
2390 for (deUint32 ndx = 0; ndx < numThreads; ndx++)
2392 perThreadEnv[ndx] = EnvPtr(new EnvClone(sharedEnv, deviceParams, 1u));
2393 resources[ndx] = ResPtr(new typename Object::Resources(perThreadEnv[ndx]->env, params));
2395 threads.add(MovePtr<ThreadGroupThread>(new CreateThread<Object>(perThreadEnv[ndx]->env, *resources[ndx], params)));
2398 return threads.run();
2401 template<typename Object>
2402 tcu::TestStatus createSingleAllocCallbacksTest (Context& context, typename Object::Parameters params)
2404 const deUint32 noCmdScope = (1u << VK_SYSTEM_ALLOCATION_SCOPE_INSTANCE)
2405 | (1u << VK_SYSTEM_ALLOCATION_SCOPE_DEVICE)
2406 | (1u << VK_SYSTEM_ALLOCATION_SCOPE_CACHE)
2407 | (1u << VK_SYSTEM_ALLOCATION_SCOPE_OBJECT);
2409 // Callbacks used by resources
2410 AllocationCallbackRecorder resCallbacks (getSystemAllocator(), 128);
2412 // Root environment still uses default instance and device, created without callbacks
2413 const Environment rootEnv (context.getPlatformInterface(),
2414 context.getDeviceInterface(),
2415 context.getDevice(),
2416 context.getUniversalQueueFamilyIndex(),
2417 context.getBinaryCollection(),
2418 resCallbacks.getCallbacks(),
2422 // Test env has instance & device created with callbacks
2423 const EnvClone resEnv (rootEnv, getDefaulDeviceParameters(context), 1u);
2424 const typename Object::Resources res (resEnv.env, params);
2426 // Supply a separate callback recorder just for object construction
2427 AllocationCallbackRecorder objCallbacks(getSystemAllocator(), 128);
2428 const Environment objEnv (resEnv.env.vkp,
2431 resEnv.env.queueFamilyIndex,
2432 resEnv.env.programBinaries,
2433 objCallbacks.getCallbacks(),
2434 resEnv.env.maxResourceConsumers);
2437 Unique<typename Object::Type> obj (Object::create(objEnv, res, params));
2439 // Validate that no command-level allocations are live
2440 if (!validateAndLog(context.getTestContext().getLog(), objCallbacks, noCmdScope))
2441 return tcu::TestStatus::fail("Invalid allocation callback");
2444 // At this point all allocations made against object callbacks must have been freed
2445 if (!validateAndLog(context.getTestContext().getLog(), objCallbacks, 0u))
2446 return tcu::TestStatus::fail("Invalid allocation callback");
2449 if (!validateAndLog(context.getTestContext().getLog(), resCallbacks, 0u))
2450 return tcu::TestStatus::fail("Invalid allocation callback");
2452 return tcu::TestStatus::pass("Ok");
2455 template<typename Object> deUint32 getOomIterLimit (void) { return 1024; }
2456 template<> deUint32 getOomIterLimit<Device> (void) { return 20; }
2458 template<typename Object>
2459 tcu::TestStatus allocCallbackFailTest (Context& context, typename Object::Parameters params)
2461 AllocationCallbackRecorder resCallbacks (getSystemAllocator(), 128);
2462 const Environment rootEnv (context.getPlatformInterface(),
2463 context.getDeviceInterface(),
2464 context.getDevice(),
2465 context.getUniversalQueueFamilyIndex(),
2466 context.getBinaryCollection(),
2467 resCallbacks.getCallbacks(),
2469 deUint32 numPassingAllocs = 0;
2470 const deUint32 cmdLineIterCount = (deUint32)context.getTestContext().getCommandLine().getTestIterationCount();
2471 const deUint32 maxTries = cmdLineIterCount != 0 ? cmdLineIterCount : getOomIterLimit<Object>();
2474 const EnvClone resEnv (rootEnv, getDefaulDeviceParameters(context), 1u);
2475 const typename Object::Resources res (resEnv.env, params);
2477 // Iterate over test until object allocation succeeds
2478 for (; numPassingAllocs < maxTries; ++numPassingAllocs)
2480 DeterministicFailAllocator objAllocator(getSystemAllocator(),
2481 DeterministicFailAllocator::MODE_COUNT_AND_FAIL,
2483 AllocationCallbackRecorder recorder (objAllocator.getCallbacks(), 128);
2484 const Environment objEnv (resEnv.env.vkp,
2487 resEnv.env.queueFamilyIndex,
2488 resEnv.env.programBinaries,
2489 recorder.getCallbacks(),
2490 resEnv.env.maxResourceConsumers);
2491 bool createOk = false;
2493 context.getTestContext().getLog()
2495 << "Trying to create object with " << numPassingAllocs << " allocation" << (numPassingAllocs != 1 ? "s" : "") << " passing"
2496 << TestLog::EndMessage;
2500 Unique<typename Object::Type> obj (Object::create(objEnv, res, params));
2503 catch (const vk::OutOfMemoryError& e)
2505 if (e.getError() != VK_ERROR_OUT_OF_HOST_MEMORY)
2507 context.getTestContext().getLog() << e;
2508 return tcu::TestStatus::fail("Got invalid error code");
2512 if (!validateAndLog(context.getTestContext().getLog(), recorder, 0u))
2513 return tcu::TestStatus::fail("Invalid allocation callback");
2517 context.getTestContext().getLog()
2518 << TestLog::Message << "Object construction succeeded! " << TestLog::EndMessage;
2524 if (!validateAndLog(context.getTestContext().getLog(), resCallbacks, 0u))
2525 return tcu::TestStatus::fail("Invalid allocation callback");
2527 if (numPassingAllocs == 0)
2528 return tcu::TestStatus(QP_TEST_RESULT_QUALITY_WARNING, "Allocation callbacks not called");
2529 else if (numPassingAllocs == maxTries)
2531 context.getTestContext().getLog()
2532 << TestLog::Message << "WARNING: Maximum iteration count (" << maxTries << ") reached without object construction passing. "
2533 << "OOM testing incomplete, use --deqp-test-iteration-count= to test with higher limit." << TestLog::EndMessage;
2534 return tcu::TestStatus(QP_TEST_RESULT_PASS, "Max iter count reached");
2537 return tcu::TestStatus::pass("Ok");
2540 // Determine whether an API call sets the invalid handles to NULL (true) or leaves them undefined or not modified (false)
2541 template<typename T> inline bool isNullHandleOnAllocationFailure (Context&) { return false; }
2542 template<> inline bool isNullHandleOnAllocationFailure<VkCommandBuffer> (Context& context) { return hasDeviceExtension(context, "VK_KHR_maintenance1"); }
2543 template<> inline bool isNullHandleOnAllocationFailure<VkDescriptorSet> (Context& context) { return hasDeviceExtension(context, "VK_KHR_maintenance1"); }
2544 template<> inline bool isNullHandleOnAllocationFailure<VkPipeline> (Context&) { return true; }
2546 template<typename T> inline bool isPooledObject (void) { return false; };
2547 template<> inline bool isPooledObject<VkCommandBuffer> (void) { return true; };
2548 template<> inline bool isPooledObject<VkDescriptorSet> (void) { return true; };
2550 template<typename Object>
2551 tcu::TestStatus allocCallbackFailMultipleObjectsTest (Context& context, typename Object::Parameters params)
2553 typedef SharedPtr<Move<typename Object::Type> > ObjectTypeSp;
2555 static const deUint32 numObjects = 4;
2556 const bool expectNullHandles = isNullHandleOnAllocationFailure<typename Object::Type>(context);
2557 deUint32 numPassingAllocs = 0;
2560 vector<typename Object::Type> handles (numObjects);
2561 VkResult result = VK_NOT_READY;
2563 for (; numPassingAllocs <= numObjects; ++numPassingAllocs)
2565 ValidateQueryBits::fillBits(handles.begin(), handles.end()); // fill with garbage
2567 // \note We have to use the same allocator for both resource dependencies and the object under test,
2568 // because pooled objects take memory from the pool.
2569 DeterministicFailAllocator objAllocator(getSystemAllocator(), DeterministicFailAllocator::MODE_DO_NOT_COUNT, 0);
2570 AllocationCallbackRecorder recorder (objAllocator.getCallbacks(), 128);
2571 const Environment objEnv (context.getPlatformInterface(),
2572 context.getDeviceInterface(),
2573 context.getDevice(),
2574 context.getUniversalQueueFamilyIndex(),
2575 context.getBinaryCollection(),
2576 recorder.getCallbacks(),
2579 context.getTestContext().getLog()
2581 << "Trying to create " << numObjects << " objects with " << numPassingAllocs << " allocation" << (numPassingAllocs != 1 ? "s" : "") << " passing"
2582 << TestLog::EndMessage;
2585 const typename Object::Resources res (objEnv, params);
2587 objAllocator.reset(DeterministicFailAllocator::MODE_COUNT_AND_FAIL, numPassingAllocs);
2588 const vector<ObjectTypeSp> scopedHandles = Object::createMultiple(objEnv, res, params, &handles, &result);
2591 if (result == VK_SUCCESS)
2593 context.getTestContext().getLog() << TestLog::Message << "Construction of all objects succeeded! " << TestLog::EndMessage;
2598 if (expectNullHandles)
2600 for (deUint32 nullNdx = numPassingAllocs; nullNdx < numObjects; ++nullNdx)
2602 if (handles[nullNdx] != DE_NULL)
2603 return tcu::TestStatus::fail("Some object handles weren't set to NULL");
2607 if (result != VK_ERROR_OUT_OF_HOST_MEMORY)
2608 return tcu::TestStatus::fail("Got invalid error code: " + de::toString(getResultName(result)));
2610 if (!validateAndLog(context.getTestContext().getLog(), recorder, 0u))
2611 return tcu::TestStatus::fail("Invalid allocation callback");
2616 if (numPassingAllocs == 0)
2618 if (isPooledObject<typename Object::Type>())
2619 return tcu::TestStatus::pass("Not validated: pooled objects didn't seem to use host memory");
2621 return tcu::TestStatus(QP_TEST_RESULT_QUALITY_WARNING, "Allocation callbacks not called");
2624 return tcu::TestStatus::pass("Ok");
2627 // Utilities for creating groups
2629 template<typename Object>
2630 struct NamedParameters
2633 typename Object::Parameters parameters;
2636 template<typename Object>
2637 struct CaseDescription
2639 typename FunctionInstance1<typename Object::Parameters>::Function function;
2640 const NamedParameters<Object>* paramsBegin;
2641 const NamedParameters<Object>* paramsEnd;
2644 #define EMPTY_CASE_DESC(OBJECT) \
2645 { (FunctionInstance1<OBJECT::Parameters>::Function)DE_NULL, DE_NULL, DE_NULL }
2647 #define CASE_DESC(FUNCTION, CASES) \
2648 { FUNCTION, DE_ARRAY_BEGIN(CASES), DE_ARRAY_END(CASES) }
2650 struct CaseDescriptions
2652 CaseDescription<Instance> instance;
2653 CaseDescription<Device> device;
2654 CaseDescription<DeviceMemory> deviceMemory;
2655 CaseDescription<Buffer> buffer;
2656 CaseDescription<BufferView> bufferView;
2657 CaseDescription<Image> image;
2658 CaseDescription<ImageView> imageView;
2659 CaseDescription<Semaphore> semaphore;
2660 CaseDescription<Event> event;
2661 CaseDescription<Fence> fence;
2662 CaseDescription<QueryPool> queryPool;
2663 CaseDescription<ShaderModule> shaderModule;
2664 CaseDescription<PipelineCache> pipelineCache;
2665 CaseDescription<PipelineLayout> pipelineLayout;
2666 CaseDescription<RenderPass> renderPass;
2667 CaseDescription<GraphicsPipeline> graphicsPipeline;
2668 CaseDescription<ComputePipeline> computePipeline;
2669 CaseDescription<DescriptorSetLayout> descriptorSetLayout;
2670 CaseDescription<Sampler> sampler;
2671 CaseDescription<DescriptorPool> descriptorPool;
2672 CaseDescription<DescriptorSet> descriptorSet;
2673 CaseDescription<Framebuffer> framebuffer;
2674 CaseDescription<CommandPool> commandPool;
2675 CaseDescription<CommandBuffer> commandBuffer;
2678 template<typename Object>
2679 void addCases (const MovePtr<tcu::TestCaseGroup>& group, const CaseDescription<Object>& cases)
2681 for (const NamedParameters<Object>* cur = cases.paramsBegin; cur != cases.paramsEnd; ++cur)
2682 addFunctionCase(group.get(), cur->name, "", cases.function, cur->parameters);
2685 template<typename Object>
2686 void addCasesWithProgs (const MovePtr<tcu::TestCaseGroup>& group, const CaseDescription<Object>& cases)
2688 for (const NamedParameters<Object>* cur = cases.paramsBegin; cur != cases.paramsEnd; ++cur)
2689 addFunctionCaseWithPrograms(group.get(), cur->name, "", Object::initPrograms, cases.function, cur->parameters);
2692 tcu::TestCaseGroup* createGroup (tcu::TestContext& testCtx, const char* name, const char* desc, const CaseDescriptions& cases)
2694 MovePtr<tcu::TestCaseGroup> group (new tcu::TestCaseGroup(testCtx, name, desc));
2696 addCases (group, cases.instance);
2697 addCases (group, cases.device);
2698 addCases (group, cases.deviceMemory);
2699 addCases (group, cases.buffer);
2700 addCases (group, cases.bufferView);
2701 addCases (group, cases.image);
2702 addCases (group, cases.imageView);
2703 addCases (group, cases.semaphore);
2704 addCases (group, cases.event);
2705 addCases (group, cases.fence);
2706 addCases (group, cases.queryPool);
2707 addCases (group, cases.sampler);
2708 addCasesWithProgs (group, cases.shaderModule);
2709 addCases (group, cases.pipelineCache);
2710 addCases (group, cases.pipelineLayout);
2711 addCases (group, cases.renderPass);
2712 addCasesWithProgs (group, cases.graphicsPipeline);
2713 addCasesWithProgs (group, cases.computePipeline);
2714 addCases (group, cases.descriptorSetLayout);
2715 addCases (group, cases.descriptorPool);
2716 addCases (group, cases.descriptorSet);
2717 addCases (group, cases.framebuffer);
2718 addCases (group, cases.commandPool);
2719 addCases (group, cases.commandBuffer);
2721 return group.release();
2726 tcu::TestCaseGroup* createObjectManagementTests (tcu::TestContext& testCtx)
2728 MovePtr<tcu::TestCaseGroup> objectMgmtTests (new tcu::TestCaseGroup(testCtx, "object_management", "Object management tests"));
2730 const Image::Parameters img1D (0u, VK_IMAGE_TYPE_1D, VK_FORMAT_R8G8B8A8_UNORM, makeExtent3D(256, 1, 1), 1u, 4u, VK_SAMPLE_COUNT_1_BIT, VK_IMAGE_TILING_OPTIMAL, VK_IMAGE_USAGE_SAMPLED_BIT, VK_IMAGE_LAYOUT_UNDEFINED);
2731 const Image::Parameters img2D (0u, VK_IMAGE_TYPE_2D, VK_FORMAT_R8G8B8A8_UNORM, makeExtent3D( 64, 64, 1), 1u, 12u, VK_SAMPLE_COUNT_1_BIT, VK_IMAGE_TILING_OPTIMAL, VK_IMAGE_USAGE_SAMPLED_BIT|VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT, VK_IMAGE_LAYOUT_UNDEFINED);
2732 const Image::Parameters imgCube (VK_IMAGE_CREATE_CUBE_COMPATIBLE_BIT, VK_IMAGE_TYPE_2D, VK_FORMAT_R8G8B8A8_UNORM, makeExtent3D( 64, 64, 1), 1u, 12u, VK_SAMPLE_COUNT_1_BIT, VK_IMAGE_TILING_OPTIMAL, VK_IMAGE_USAGE_SAMPLED_BIT|VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT, VK_IMAGE_LAYOUT_UNDEFINED);
2733 const Image::Parameters img3D (0u, VK_IMAGE_TYPE_3D, VK_FORMAT_R8G8B8A8_UNORM, makeExtent3D( 64, 64, 4), 1u, 1u, VK_SAMPLE_COUNT_1_BIT, VK_IMAGE_TILING_OPTIMAL, VK_IMAGE_USAGE_SAMPLED_BIT, VK_IMAGE_LAYOUT_UNDEFINED);
2734 const ImageView::Parameters imgView1D (img1D, VK_IMAGE_VIEW_TYPE_1D, img1D.format, makeComponentMappingRGBA(), makeImageSubresourceRange(VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u));
2735 const ImageView::Parameters imgView1DArr (img1D, VK_IMAGE_VIEW_TYPE_1D_ARRAY, img1D.format, makeComponentMappingRGBA(), makeImageSubresourceRange(VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 4u));
2736 const ImageView::Parameters imgView2D (img2D, VK_IMAGE_VIEW_TYPE_2D, img2D.format, makeComponentMappingRGBA(), makeImageSubresourceRange(VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u));
2737 const ImageView::Parameters imgView2DArr (img2D, VK_IMAGE_VIEW_TYPE_2D_ARRAY, img2D.format, makeComponentMappingRGBA(), makeImageSubresourceRange(VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 8u));
2738 const ImageView::Parameters imgViewCube (imgCube, VK_IMAGE_VIEW_TYPE_CUBE, img2D.format, makeComponentMappingRGBA(), makeImageSubresourceRange(VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 6u));
2739 const ImageView::Parameters imgViewCubeArr (imgCube, VK_IMAGE_VIEW_TYPE_CUBE_ARRAY, img2D.format, makeComponentMappingRGBA(), makeImageSubresourceRange(VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 12u));
2740 const ImageView::Parameters imgView3D (img3D, VK_IMAGE_VIEW_TYPE_3D, img3D.format, makeComponentMappingRGBA(), makeImageSubresourceRange(VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u));
2742 const DescriptorSetLayout::Parameters singleUboDescLayout = DescriptorSetLayout::Parameters::single(0u, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 1u, VK_SHADER_STAGE_VERTEX_BIT);
2744 static NamedParameters<Instance> s_instanceCases[] =
2746 { "instance", Instance::Parameters() },
2748 // \note Device index may change - must not be static
2749 const NamedParameters<Device> s_deviceCases[] =
2751 { "device", Device::Parameters(testCtx.getCommandLine().getVKDeviceId()-1u, VK_QUEUE_GRAPHICS_BIT) },
2753 static const NamedParameters<DeviceMemory> s_deviceMemCases[] =
2755 { "device_memory_small", DeviceMemory::Parameters(1024, 0u) },
2757 static const NamedParameters<Buffer> s_bufferCases[] =
2759 { "buffer_uniform_small", Buffer::Parameters(1024u, VK_BUFFER_USAGE_UNIFORM_BUFFER_BIT), },
2760 { "buffer_uniform_large", Buffer::Parameters(1024u*1024u*16u, VK_BUFFER_USAGE_UNIFORM_BUFFER_BIT), },
2761 { "buffer_storage_small", Buffer::Parameters(1024u, VK_BUFFER_USAGE_STORAGE_BUFFER_BIT), },
2762 { "buffer_storage_large", Buffer::Parameters(1024u*1024u*16u, VK_BUFFER_USAGE_STORAGE_BUFFER_BIT), },
2764 static const NamedParameters<BufferView> s_bufferViewCases[] =
2766 { "buffer_view_uniform_r8g8b8a8_unorm", BufferView::Parameters(Buffer::Parameters(8192u, VK_BUFFER_USAGE_UNIFORM_TEXEL_BUFFER_BIT), VK_FORMAT_R8G8B8A8_UNORM, 0u, 4096u) },
2767 { "buffer_view_storage_r8g8b8a8_unorm", BufferView::Parameters(Buffer::Parameters(8192u, VK_BUFFER_USAGE_STORAGE_TEXEL_BUFFER_BIT), VK_FORMAT_R8G8B8A8_UNORM, 0u, 4096u) },
2769 static const NamedParameters<Image> s_imageCases[] =
2771 { "image_1d", img1D },
2772 { "image_2d", img2D },
2773 { "image_3d", img3D },
2775 static const NamedParameters<ImageView> s_imageViewCases[] =
2777 { "image_view_1d", imgView1D },
2778 { "image_view_1d_arr", imgView1DArr },
2779 { "image_view_2d", imgView2D },
2780 { "image_view_2d_arr", imgView2DArr },
2781 { "image_view_cube", imgViewCube },
2782 { "image_view_cube_arr", imgViewCubeArr },
2783 { "image_view_3d", imgView3D },
2785 static const NamedParameters<Semaphore> s_semaphoreCases[] =
2787 { "semaphore", Semaphore::Parameters(0u), }
2789 static const NamedParameters<Event> s_eventCases[] =
2791 { "event", Event::Parameters(0u) }
2793 static const NamedParameters<Fence> s_fenceCases[] =
2795 { "fence", Fence::Parameters(0u) },
2796 { "fence_signaled", Fence::Parameters(VK_FENCE_CREATE_SIGNALED_BIT) }
2798 static const NamedParameters<QueryPool> s_queryPoolCases[] =
2800 { "query_pool", QueryPool::Parameters(VK_QUERY_TYPE_OCCLUSION, 1u, 0u) }
2802 static const NamedParameters<ShaderModule> s_shaderModuleCases[] =
2804 { "shader_module", ShaderModule::Parameters(VK_SHADER_STAGE_COMPUTE_BIT, "test") }
2806 static const NamedParameters<PipelineCache> s_pipelineCacheCases[] =
2808 { "pipeline_cache", PipelineCache::Parameters() }
2810 static const NamedParameters<PipelineLayout> s_pipelineLayoutCases[] =
2812 { "pipeline_layout_empty", PipelineLayout::Parameters::empty() },
2813 { "pipeline_layout_single", PipelineLayout::Parameters::singleDescriptorSet(singleUboDescLayout) }
2815 static const NamedParameters<RenderPass> s_renderPassCases[] =
2817 { "render_pass", RenderPass::Parameters() }
2819 static const NamedParameters<GraphicsPipeline> s_graphicsPipelineCases[] =
2821 { "graphics_pipeline", GraphicsPipeline::Parameters() }
2823 static const NamedParameters<ComputePipeline> s_computePipelineCases[] =
2825 { "compute_pipeline", ComputePipeline::Parameters() }
2827 static const NamedParameters<DescriptorSetLayout> s_descriptorSetLayoutCases[] =
2829 { "descriptor_set_layout_empty", DescriptorSetLayout::Parameters::empty() },
2830 { "descriptor_set_layout_single", singleUboDescLayout }
2832 static const NamedParameters<Sampler> s_samplerCases[] =
2834 { "sampler", Sampler::Parameters() }
2836 static const NamedParameters<DescriptorPool> s_descriptorPoolCases[] =
2838 { "descriptor_pool", DescriptorPool::Parameters::singleType((VkDescriptorPoolCreateFlags)0, 4u, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 3u) },
2839 { "descriptor_pool_free_descriptor_set", DescriptorPool::Parameters::singleType(VK_DESCRIPTOR_POOL_CREATE_FREE_DESCRIPTOR_SET_BIT, 4u, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 3u) }
2841 static const NamedParameters<DescriptorSet> s_descriptorSetCases[] =
2843 { "descriptor_set", DescriptorSet::Parameters(singleUboDescLayout) }
2845 static const NamedParameters<Framebuffer> s_framebufferCases[] =
2847 { "framebuffer", Framebuffer::Parameters() }
2849 static const NamedParameters<CommandPool> s_commandPoolCases[] =
2851 { "command_pool", CommandPool::Parameters((VkCommandPoolCreateFlags)0) },
2852 { "command_pool_transient", CommandPool::Parameters(VK_COMMAND_POOL_CREATE_TRANSIENT_BIT) }
2854 static const NamedParameters<CommandBuffer> s_commandBufferCases[] =
2856 { "command_buffer_primary", CommandBuffer::Parameters(CommandPool::Parameters((VkCommandPoolCreateFlags)0u), VK_COMMAND_BUFFER_LEVEL_PRIMARY) },
2857 { "command_buffer_secondary", CommandBuffer::Parameters(CommandPool::Parameters((VkCommandPoolCreateFlags)0u), VK_COMMAND_BUFFER_LEVEL_SECONDARY) }
2860 static const CaseDescriptions s_createSingleGroup =
2862 CASE_DESC(createSingleTest <Instance>, s_instanceCases),
2863 CASE_DESC(createSingleTest <Device>, s_deviceCases),
2864 CASE_DESC(createSingleTest <DeviceMemory>, s_deviceMemCases),
2865 CASE_DESC(createSingleTest <Buffer>, s_bufferCases),
2866 CASE_DESC(createSingleTest <BufferView>, s_bufferViewCases),
2867 CASE_DESC(createSingleTest <Image>, s_imageCases),
2868 CASE_DESC(createSingleTest <ImageView>, s_imageViewCases),
2869 CASE_DESC(createSingleTest <Semaphore>, s_semaphoreCases),
2870 CASE_DESC(createSingleTest <Event>, s_eventCases),
2871 CASE_DESC(createSingleTest <Fence>, s_fenceCases),
2872 CASE_DESC(createSingleTest <QueryPool>, s_queryPoolCases),
2873 CASE_DESC(createSingleTest <ShaderModule>, s_shaderModuleCases),
2874 CASE_DESC(createSingleTest <PipelineCache>, s_pipelineCacheCases),
2875 CASE_DESC(createSingleTest <PipelineLayout>, s_pipelineLayoutCases),
2876 CASE_DESC(createSingleTest <RenderPass>, s_renderPassCases),
2877 CASE_DESC(createSingleTest <GraphicsPipeline>, s_graphicsPipelineCases),
2878 CASE_DESC(createSingleTest <ComputePipeline>, s_computePipelineCases),
2879 CASE_DESC(createSingleTest <DescriptorSetLayout>, s_descriptorSetLayoutCases),
2880 CASE_DESC(createSingleTest <Sampler>, s_samplerCases),
2881 CASE_DESC(createSingleTest <DescriptorPool>, s_descriptorPoolCases),
2882 CASE_DESC(createSingleTest <DescriptorSet>, s_descriptorSetCases),
2883 CASE_DESC(createSingleTest <Framebuffer>, s_framebufferCases),
2884 CASE_DESC(createSingleTest <CommandPool>, s_commandPoolCases),
2885 CASE_DESC(createSingleTest <CommandBuffer>, s_commandBufferCases),
2887 objectMgmtTests->addChild(createGroup(testCtx, "single", "Create single object", s_createSingleGroup));
2889 static const CaseDescriptions s_createMultipleUniqueResourcesGroup =
2891 CASE_DESC(createMultipleUniqueResourcesTest <Instance>, s_instanceCases),
2892 CASE_DESC(createMultipleUniqueResourcesTest <Device>, s_deviceCases),
2893 CASE_DESC(createMultipleUniqueResourcesTest <DeviceMemory>, s_deviceMemCases),
2894 CASE_DESC(createMultipleUniqueResourcesTest <Buffer>, s_bufferCases),
2895 CASE_DESC(createMultipleUniqueResourcesTest <BufferView>, s_bufferViewCases),
2896 CASE_DESC(createMultipleUniqueResourcesTest <Image>, s_imageCases),
2897 CASE_DESC(createMultipleUniqueResourcesTest <ImageView>, s_imageViewCases),
2898 CASE_DESC(createMultipleUniqueResourcesTest <Semaphore>, s_semaphoreCases),
2899 CASE_DESC(createMultipleUniqueResourcesTest <Event>, s_eventCases),
2900 CASE_DESC(createMultipleUniqueResourcesTest <Fence>, s_fenceCases),
2901 CASE_DESC(createMultipleUniqueResourcesTest <QueryPool>, s_queryPoolCases),
2902 CASE_DESC(createMultipleUniqueResourcesTest <ShaderModule>, s_shaderModuleCases),
2903 CASE_DESC(createMultipleUniqueResourcesTest <PipelineCache>, s_pipelineCacheCases),
2904 CASE_DESC(createMultipleUniqueResourcesTest <PipelineLayout>, s_pipelineLayoutCases),
2905 CASE_DESC(createMultipleUniqueResourcesTest <RenderPass>, s_renderPassCases),
2906 CASE_DESC(createMultipleUniqueResourcesTest <GraphicsPipeline>, s_graphicsPipelineCases),
2907 CASE_DESC(createMultipleUniqueResourcesTest <ComputePipeline>, s_computePipelineCases),
2908 CASE_DESC(createMultipleUniqueResourcesTest <DescriptorSetLayout>, s_descriptorSetLayoutCases),
2909 CASE_DESC(createMultipleUniqueResourcesTest <Sampler>, s_samplerCases),
2910 CASE_DESC(createMultipleUniqueResourcesTest <DescriptorPool>, s_descriptorPoolCases),
2911 CASE_DESC(createMultipleUniqueResourcesTest <DescriptorSet>, s_descriptorSetCases),
2912 CASE_DESC(createMultipleUniqueResourcesTest <Framebuffer>, s_framebufferCases),
2913 CASE_DESC(createMultipleUniqueResourcesTest <CommandPool>, s_commandPoolCases),
2914 CASE_DESC(createMultipleUniqueResourcesTest <CommandBuffer>, s_commandBufferCases),
2916 objectMgmtTests->addChild(createGroup(testCtx, "multiple_unique_resources", "Multiple objects with per-object unique resources", s_createMultipleUniqueResourcesGroup));
2918 static const CaseDescriptions s_createMultipleSharedResourcesGroup =
2920 EMPTY_CASE_DESC(Instance), // No resources used
2921 CASE_DESC(createMultipleSharedResourcesTest <Device>, s_deviceCases),
2922 CASE_DESC(createMultipleSharedResourcesTest <DeviceMemory>, s_deviceMemCases),
2923 CASE_DESC(createMultipleSharedResourcesTest <Buffer>, s_bufferCases),
2924 CASE_DESC(createMultipleSharedResourcesTest <BufferView>, s_bufferViewCases),
2925 CASE_DESC(createMultipleSharedResourcesTest <Image>, s_imageCases),
2926 CASE_DESC(createMultipleSharedResourcesTest <ImageView>, s_imageViewCases),
2927 CASE_DESC(createMultipleSharedResourcesTest <Semaphore>, s_semaphoreCases),
2928 CASE_DESC(createMultipleSharedResourcesTest <Event>, s_eventCases),
2929 CASE_DESC(createMultipleSharedResourcesTest <Fence>, s_fenceCases),
2930 CASE_DESC(createMultipleSharedResourcesTest <QueryPool>, s_queryPoolCases),
2931 CASE_DESC(createMultipleSharedResourcesTest <ShaderModule>, s_shaderModuleCases),
2932 CASE_DESC(createMultipleSharedResourcesTest <PipelineCache>, s_pipelineCacheCases),
2933 CASE_DESC(createMultipleSharedResourcesTest <PipelineLayout>, s_pipelineLayoutCases),
2934 CASE_DESC(createMultipleSharedResourcesTest <RenderPass>, s_renderPassCases),
2935 CASE_DESC(createMultipleSharedResourcesTest <GraphicsPipeline>, s_graphicsPipelineCases),
2936 CASE_DESC(createMultipleSharedResourcesTest <ComputePipeline>, s_computePipelineCases),
2937 CASE_DESC(createMultipleSharedResourcesTest <DescriptorSetLayout>, s_descriptorSetLayoutCases),
2938 CASE_DESC(createMultipleSharedResourcesTest <Sampler>, s_samplerCases),
2939 CASE_DESC(createMultipleSharedResourcesTest <DescriptorPool>, s_descriptorPoolCases),
2940 CASE_DESC(createMultipleSharedResourcesTest <DescriptorSet>, s_descriptorSetCases),
2941 CASE_DESC(createMultipleSharedResourcesTest <Framebuffer>, s_framebufferCases),
2942 CASE_DESC(createMultipleSharedResourcesTest <CommandPool>, s_commandPoolCases),
2943 CASE_DESC(createMultipleSharedResourcesTest <CommandBuffer>, s_commandBufferCases),
2945 objectMgmtTests->addChild(createGroup(testCtx, "multiple_shared_resources", "Multiple objects with shared resources", s_createMultipleSharedResourcesGroup));
2947 static const CaseDescriptions s_createMaxConcurrentGroup =
2949 CASE_DESC(createMaxConcurrentTest <Instance>, s_instanceCases),
2950 CASE_DESC(createMaxConcurrentTest <Device>, s_deviceCases),
2951 CASE_DESC(createMaxConcurrentTest <DeviceMemory>, s_deviceMemCases),
2952 CASE_DESC(createMaxConcurrentTest <Buffer>, s_bufferCases),
2953 CASE_DESC(createMaxConcurrentTest <BufferView>, s_bufferViewCases),
2954 CASE_DESC(createMaxConcurrentTest <Image>, s_imageCases),
2955 CASE_DESC(createMaxConcurrentTest <ImageView>, s_imageViewCases),
2956 CASE_DESC(createMaxConcurrentTest <Semaphore>, s_semaphoreCases),
2957 CASE_DESC(createMaxConcurrentTest <Event>, s_eventCases),
2958 CASE_DESC(createMaxConcurrentTest <Fence>, s_fenceCases),
2959 CASE_DESC(createMaxConcurrentTest <QueryPool>, s_queryPoolCases),
2960 CASE_DESC(createMaxConcurrentTest <ShaderModule>, s_shaderModuleCases),
2961 CASE_DESC(createMaxConcurrentTest <PipelineCache>, s_pipelineCacheCases),
2962 CASE_DESC(createMaxConcurrentTest <PipelineLayout>, s_pipelineLayoutCases),
2963 CASE_DESC(createMaxConcurrentTest <RenderPass>, s_renderPassCases),
2964 CASE_DESC(createMaxConcurrentTest <GraphicsPipeline>, s_graphicsPipelineCases),
2965 CASE_DESC(createMaxConcurrentTest <ComputePipeline>, s_computePipelineCases),
2966 CASE_DESC(createMaxConcurrentTest <DescriptorSetLayout>, s_descriptorSetLayoutCases),
2967 CASE_DESC(createMaxConcurrentTest <Sampler>, s_samplerCases),
2968 CASE_DESC(createMaxConcurrentTest <DescriptorPool>, s_descriptorPoolCases),
2969 CASE_DESC(createMaxConcurrentTest <DescriptorSet>, s_descriptorSetCases),
2970 CASE_DESC(createMaxConcurrentTest <Framebuffer>, s_framebufferCases),
2971 CASE_DESC(createMaxConcurrentTest <CommandPool>, s_commandPoolCases),
2972 CASE_DESC(createMaxConcurrentTest <CommandBuffer>, s_commandBufferCases),
2974 objectMgmtTests->addChild(createGroup(testCtx, "max_concurrent", "Maximum number of concurrently live objects", s_createMaxConcurrentGroup));
2976 static const CaseDescriptions s_multithreadedCreatePerThreadDeviceGroup =
2978 EMPTY_CASE_DESC(Instance), // Does not make sense
2979 EMPTY_CASE_DESC(Device), // Does not make sense
2980 CASE_DESC(multithreadedCreatePerThreadDeviceTest <DeviceMemory>, s_deviceMemCases),
2981 CASE_DESC(multithreadedCreatePerThreadDeviceTest <Buffer>, s_bufferCases),
2982 CASE_DESC(multithreadedCreatePerThreadDeviceTest <BufferView>, s_bufferViewCases),
2983 CASE_DESC(multithreadedCreatePerThreadDeviceTest <Image>, s_imageCases),
2984 CASE_DESC(multithreadedCreatePerThreadDeviceTest <ImageView>, s_imageViewCases),
2985 CASE_DESC(multithreadedCreatePerThreadDeviceTest <Semaphore>, s_semaphoreCases),
2986 CASE_DESC(multithreadedCreatePerThreadDeviceTest <Event>, s_eventCases),
2987 CASE_DESC(multithreadedCreatePerThreadDeviceTest <Fence>, s_fenceCases),
2988 CASE_DESC(multithreadedCreatePerThreadDeviceTest <QueryPool>, s_queryPoolCases),
2989 CASE_DESC(multithreadedCreatePerThreadDeviceTest <ShaderModule>, s_shaderModuleCases),
2990 CASE_DESC(multithreadedCreatePerThreadDeviceTest <PipelineCache>, s_pipelineCacheCases),
2991 CASE_DESC(multithreadedCreatePerThreadDeviceTest <PipelineLayout>, s_pipelineLayoutCases),
2992 CASE_DESC(multithreadedCreatePerThreadDeviceTest <RenderPass>, s_renderPassCases),
2993 CASE_DESC(multithreadedCreatePerThreadDeviceTest <GraphicsPipeline>, s_graphicsPipelineCases),
2994 CASE_DESC(multithreadedCreatePerThreadDeviceTest <ComputePipeline>, s_computePipelineCases),
2995 CASE_DESC(multithreadedCreatePerThreadDeviceTest <DescriptorSetLayout>, s_descriptorSetLayoutCases),
2996 CASE_DESC(multithreadedCreatePerThreadDeviceTest <Sampler>, s_samplerCases),
2997 CASE_DESC(multithreadedCreatePerThreadDeviceTest <DescriptorPool>, s_descriptorPoolCases),
2998 CASE_DESC(multithreadedCreatePerThreadDeviceTest <DescriptorSet>, s_descriptorSetCases),
2999 CASE_DESC(multithreadedCreatePerThreadDeviceTest <Framebuffer>, s_framebufferCases),
3000 CASE_DESC(multithreadedCreatePerThreadDeviceTest <CommandPool>, s_commandPoolCases),
3001 CASE_DESC(multithreadedCreatePerThreadDeviceTest <CommandBuffer>, s_commandBufferCases),
3003 objectMgmtTests->addChild(createGroup(testCtx, "multithreaded_per_thread_device", "Multithreaded object construction with per-thread device ", s_multithreadedCreatePerThreadDeviceGroup));
3005 static const CaseDescriptions s_multithreadedCreatePerThreadResourcesGroup =
3007 CASE_DESC(multithreadedCreatePerThreadResourcesTest <Instance>, s_instanceCases),
3008 CASE_DESC(multithreadedCreatePerThreadResourcesTest <Device>, s_deviceCases),
3009 CASE_DESC(multithreadedCreatePerThreadResourcesTest <DeviceMemory>, s_deviceMemCases),
3010 CASE_DESC(multithreadedCreatePerThreadResourcesTest <Buffer>, s_bufferCases),
3011 CASE_DESC(multithreadedCreatePerThreadResourcesTest <BufferView>, s_bufferViewCases),
3012 CASE_DESC(multithreadedCreatePerThreadResourcesTest <Image>, s_imageCases),
3013 CASE_DESC(multithreadedCreatePerThreadResourcesTest <ImageView>, s_imageViewCases),
3014 CASE_DESC(multithreadedCreatePerThreadResourcesTest <Semaphore>, s_semaphoreCases),
3015 CASE_DESC(multithreadedCreatePerThreadResourcesTest <Event>, s_eventCases),
3016 CASE_DESC(multithreadedCreatePerThreadResourcesTest <Fence>, s_fenceCases),
3017 CASE_DESC(multithreadedCreatePerThreadResourcesTest <QueryPool>, s_queryPoolCases),
3018 CASE_DESC(multithreadedCreatePerThreadResourcesTest <ShaderModule>, s_shaderModuleCases),
3019 CASE_DESC(multithreadedCreatePerThreadResourcesTest <PipelineCache>, s_pipelineCacheCases),
3020 CASE_DESC(multithreadedCreatePerThreadResourcesTest <PipelineLayout>, s_pipelineLayoutCases),
3021 CASE_DESC(multithreadedCreatePerThreadResourcesTest <RenderPass>, s_renderPassCases),
3022 CASE_DESC(multithreadedCreatePerThreadResourcesTest <GraphicsPipeline>, s_graphicsPipelineCases),
3023 CASE_DESC(multithreadedCreatePerThreadResourcesTest <ComputePipeline>, s_computePipelineCases),
3024 CASE_DESC(multithreadedCreatePerThreadResourcesTest <DescriptorSetLayout>, s_descriptorSetLayoutCases),
3025 CASE_DESC(multithreadedCreatePerThreadResourcesTest <Sampler>, s_samplerCases),
3026 CASE_DESC(multithreadedCreatePerThreadResourcesTest <DescriptorPool>, s_descriptorPoolCases),
3027 CASE_DESC(multithreadedCreatePerThreadResourcesTest <DescriptorSet>, s_descriptorSetCases),
3028 CASE_DESC(multithreadedCreatePerThreadResourcesTest <Framebuffer>, s_framebufferCases),
3029 CASE_DESC(multithreadedCreatePerThreadResourcesTest <CommandPool>, s_commandPoolCases),
3030 CASE_DESC(multithreadedCreatePerThreadResourcesTest <CommandBuffer>, s_commandBufferCases),
3032 objectMgmtTests->addChild(createGroup(testCtx, "multithreaded_per_thread_resources", "Multithreaded object construction with per-thread resources", s_multithreadedCreatePerThreadResourcesGroup));
3034 static const CaseDescriptions s_multithreadedCreateSharedResourcesGroup =
3036 EMPTY_CASE_DESC(Instance),
3037 CASE_DESC(multithreadedCreateSharedResourcesTest <Device>, s_deviceCases),
3038 CASE_DESC(multithreadedCreateSharedResourcesTest <DeviceMemory>, s_deviceMemCases),
3039 CASE_DESC(multithreadedCreateSharedResourcesTest <Buffer>, s_bufferCases),
3040 CASE_DESC(multithreadedCreateSharedResourcesTest <BufferView>, s_bufferViewCases),
3041 CASE_DESC(multithreadedCreateSharedResourcesTest <Image>, s_imageCases),
3042 CASE_DESC(multithreadedCreateSharedResourcesTest <ImageView>, s_imageViewCases),
3043 CASE_DESC(multithreadedCreateSharedResourcesTest <Semaphore>, s_semaphoreCases),
3044 CASE_DESC(multithreadedCreateSharedResourcesTest <Event>, s_eventCases),
3045 CASE_DESC(multithreadedCreateSharedResourcesTest <Fence>, s_fenceCases),
3046 CASE_DESC(multithreadedCreateSharedResourcesTest <QueryPool>, s_queryPoolCases),
3047 CASE_DESC(multithreadedCreateSharedResourcesTest <ShaderModule>, s_shaderModuleCases),
3048 CASE_DESC(multithreadedCreateSharedResourcesTest <PipelineCache>, s_pipelineCacheCases),
3049 CASE_DESC(multithreadedCreateSharedResourcesTest <PipelineLayout>, s_pipelineLayoutCases),
3050 CASE_DESC(multithreadedCreateSharedResourcesTest <RenderPass>, s_renderPassCases),
3051 CASE_DESC(multithreadedCreateSharedResourcesTest <GraphicsPipeline>, s_graphicsPipelineCases),
3052 CASE_DESC(multithreadedCreateSharedResourcesTest <ComputePipeline>, s_computePipelineCases),
3053 CASE_DESC(multithreadedCreateSharedResourcesTest <DescriptorSetLayout>, s_descriptorSetLayoutCases),
3054 CASE_DESC(multithreadedCreateSharedResourcesTest <Sampler>, s_samplerCases),
3055 CASE_DESC(multithreadedCreateSharedResourcesTest <DescriptorPool>, s_descriptorPoolCases),
3056 EMPTY_CASE_DESC(DescriptorSet), // \note Needs per-thread DescriptorPool
3057 CASE_DESC(multithreadedCreateSharedResourcesTest <Framebuffer>, s_framebufferCases),
3058 CASE_DESC(multithreadedCreateSharedResourcesTest <CommandPool>, s_commandPoolCases),
3059 EMPTY_CASE_DESC(CommandBuffer), // \note Needs per-thread CommandPool
3061 objectMgmtTests->addChild(createGroup(testCtx, "multithreaded_shared_resources", "Multithreaded object construction with shared resources", s_multithreadedCreateSharedResourcesGroup));
3063 static const CaseDescriptions s_createSingleAllocCallbacksGroup =
3065 CASE_DESC(createSingleAllocCallbacksTest <Instance>, s_instanceCases),
3066 CASE_DESC(createSingleAllocCallbacksTest <Device>, s_deviceCases),
3067 CASE_DESC(createSingleAllocCallbacksTest <DeviceMemory>, s_deviceMemCases),
3068 CASE_DESC(createSingleAllocCallbacksTest <Buffer>, s_bufferCases),
3069 CASE_DESC(createSingleAllocCallbacksTest <BufferView>, s_bufferViewCases),
3070 CASE_DESC(createSingleAllocCallbacksTest <Image>, s_imageCases),
3071 CASE_DESC(createSingleAllocCallbacksTest <ImageView>, s_imageViewCases),
3072 CASE_DESC(createSingleAllocCallbacksTest <Semaphore>, s_semaphoreCases),
3073 CASE_DESC(createSingleAllocCallbacksTest <Event>, s_eventCases),
3074 CASE_DESC(createSingleAllocCallbacksTest <Fence>, s_fenceCases),
3075 CASE_DESC(createSingleAllocCallbacksTest <QueryPool>, s_queryPoolCases),
3076 CASE_DESC(createSingleAllocCallbacksTest <ShaderModule>, s_shaderModuleCases),
3077 CASE_DESC(createSingleAllocCallbacksTest <PipelineCache>, s_pipelineCacheCases),
3078 CASE_DESC(createSingleAllocCallbacksTest <PipelineLayout>, s_pipelineLayoutCases),
3079 CASE_DESC(createSingleAllocCallbacksTest <RenderPass>, s_renderPassCases),
3080 CASE_DESC(createSingleAllocCallbacksTest <GraphicsPipeline>, s_graphicsPipelineCases),
3081 CASE_DESC(createSingleAllocCallbacksTest <ComputePipeline>, s_computePipelineCases),
3082 CASE_DESC(createSingleAllocCallbacksTest <DescriptorSetLayout>, s_descriptorSetLayoutCases),
3083 CASE_DESC(createSingleAllocCallbacksTest <Sampler>, s_samplerCases),
3084 CASE_DESC(createSingleAllocCallbacksTest <DescriptorPool>, s_descriptorPoolCases),
3085 CASE_DESC(createSingleAllocCallbacksTest <DescriptorSet>, s_descriptorSetCases),
3086 CASE_DESC(createSingleAllocCallbacksTest <Framebuffer>, s_framebufferCases),
3087 CASE_DESC(createSingleAllocCallbacksTest <CommandPool>, s_commandPoolCases),
3088 CASE_DESC(createSingleAllocCallbacksTest <CommandBuffer>, s_commandBufferCases),
3090 objectMgmtTests->addChild(createGroup(testCtx, "single_alloc_callbacks", "Create single object", s_createSingleAllocCallbacksGroup));
3092 // \note Skip pooled objects in this test group. They are properly handled by the "multiple" group farther down below.
3093 static const CaseDescriptions s_allocCallbackFailGroup =
3095 CASE_DESC(allocCallbackFailTest <Instance>, s_instanceCases),
3096 CASE_DESC(allocCallbackFailTest <Device>, s_deviceCases),
3097 CASE_DESC(allocCallbackFailTest <DeviceMemory>, s_deviceMemCases),
3098 CASE_DESC(allocCallbackFailTest <Buffer>, s_bufferCases),
3099 CASE_DESC(allocCallbackFailTest <BufferView>, s_bufferViewCases),
3100 CASE_DESC(allocCallbackFailTest <Image>, s_imageCases),
3101 CASE_DESC(allocCallbackFailTest <ImageView>, s_imageViewCases),
3102 CASE_DESC(allocCallbackFailTest <Semaphore>, s_semaphoreCases),
3103 CASE_DESC(allocCallbackFailTest <Event>, s_eventCases),
3104 CASE_DESC(allocCallbackFailTest <Fence>, s_fenceCases),
3105 CASE_DESC(allocCallbackFailTest <QueryPool>, s_queryPoolCases),
3106 CASE_DESC(allocCallbackFailTest <ShaderModule>, s_shaderModuleCases),
3107 CASE_DESC(allocCallbackFailTest <PipelineCache>, s_pipelineCacheCases),
3108 CASE_DESC(allocCallbackFailTest <PipelineLayout>, s_pipelineLayoutCases),
3109 CASE_DESC(allocCallbackFailTest <RenderPass>, s_renderPassCases),
3110 CASE_DESC(allocCallbackFailTest <GraphicsPipeline>, s_graphicsPipelineCases),
3111 CASE_DESC(allocCallbackFailTest <ComputePipeline>, s_computePipelineCases),
3112 CASE_DESC(allocCallbackFailTest <DescriptorSetLayout>, s_descriptorSetLayoutCases),
3113 CASE_DESC(allocCallbackFailTest <Sampler>, s_samplerCases),
3114 CASE_DESC(allocCallbackFailTest <DescriptorPool>, s_descriptorPoolCases),
3115 EMPTY_CASE_DESC(DescriptorSet),
3116 CASE_DESC(allocCallbackFailTest <Framebuffer>, s_framebufferCases),
3117 CASE_DESC(allocCallbackFailTest <CommandPool>, s_commandPoolCases),
3118 EMPTY_CASE_DESC(CommandBuffer),
3120 objectMgmtTests->addChild(createGroup(testCtx, "alloc_callback_fail", "Allocation callback failure", s_allocCallbackFailGroup));
3122 // \note Test objects that can be created in bulk
3123 static const CaseDescriptions s_allocCallbackFailMultipleObjectsGroup =
3125 EMPTY_CASE_DESC(Instance), // most objects can be created one at a time only
3126 EMPTY_CASE_DESC(Device),
3127 EMPTY_CASE_DESC(DeviceMemory),
3128 EMPTY_CASE_DESC(Buffer),
3129 EMPTY_CASE_DESC(BufferView),
3130 EMPTY_CASE_DESC(Image),
3131 EMPTY_CASE_DESC(ImageView),
3132 EMPTY_CASE_DESC(Semaphore),
3133 EMPTY_CASE_DESC(Event),
3134 EMPTY_CASE_DESC(Fence),
3135 EMPTY_CASE_DESC(QueryPool),
3136 EMPTY_CASE_DESC(ShaderModule),
3137 EMPTY_CASE_DESC(PipelineCache),
3138 EMPTY_CASE_DESC(PipelineLayout),
3139 EMPTY_CASE_DESC(RenderPass),
3140 CASE_DESC(allocCallbackFailMultipleObjectsTest <GraphicsPipeline>, s_graphicsPipelineCases),
3141 CASE_DESC(allocCallbackFailMultipleObjectsTest <ComputePipeline>, s_computePipelineCases),
3142 EMPTY_CASE_DESC(DescriptorSetLayout),
3143 EMPTY_CASE_DESC(Sampler),
3144 EMPTY_CASE_DESC(DescriptorPool),
3145 CASE_DESC(allocCallbackFailMultipleObjectsTest <DescriptorSet>, s_descriptorSetCases),
3146 EMPTY_CASE_DESC(Framebuffer),
3147 EMPTY_CASE_DESC(CommandPool),
3148 CASE_DESC(allocCallbackFailMultipleObjectsTest <CommandBuffer>, s_commandBufferCases),
3150 objectMgmtTests->addChild(createGroup(testCtx, "alloc_callback_fail_multiple", "Allocation callback failure creating multiple objects with one call", s_allocCallbackFailMultipleObjectsGroup));
3152 return objectMgmtTests.release();