1 /*-------------------------------------------------------------------------
2 * Vulkan CTS Framework
3 * --------------------
4 *
5 * Copyright (c) 2015 Google Inc.
6 *
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
10 *
11 * http://www.apache.org/licenses/LICENSE-2.0
12 *
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.
18 *
19 *//*!
20 * \file
21 * \brief Null (dummy) Vulkan implementation.
22 *//*--------------------------------------------------------------------*/
23
24 #include "vkNullDriver.hpp"
25 #include "vkPlatform.hpp"
26 #include "vkImageUtil.hpp"
27 #include "vkQueryUtil.hpp"
28 #include "tcuFunctionLibrary.hpp"
29 #include "deMemory.h"
30
31 #if (DE_OS == DE_OS_ANDROID) && defined(__ANDROID_API_O__) && (DE_ANDROID_API >= __ANDROID_API_O__ /* __ANDROID_API_O__ */)
32 # define USE_ANDROID_O_HARDWARE_BUFFER
33 #endif
34 #if defined(USE_ANDROID_O_HARDWARE_BUFFER)
35 # include <android/hardware_buffer.h>
36 #endif
37
38 #include <stdexcept>
39 #include <algorithm>
40
41 namespace vk
42 {
43
44 namespace
45 {
46
47 using std::vector;
48
49 // Memory management
50
51 template<typename T>
allocateSystemMem(const VkAllocationCallbacks * pAllocator,VkSystemAllocationScope scope)52 void* allocateSystemMem (const VkAllocationCallbacks* pAllocator, VkSystemAllocationScope scope)
53 {
54 void* ptr = pAllocator->pfnAllocation(pAllocator->pUserData, sizeof(T), sizeof(void*), scope);
55 if (!ptr)
56 throw std::bad_alloc();
57 return ptr;
58 }
59
freeSystemMem(const VkAllocationCallbacks * pAllocator,void * mem)60 void freeSystemMem (const VkAllocationCallbacks* pAllocator, void* mem)
61 {
62 pAllocator->pfnFree(pAllocator->pUserData, mem);
63 }
64
65 template<typename Object, typename Handle, typename Parent, typename CreateInfo>
allocateHandle(Parent parent,const CreateInfo * pCreateInfo,const VkAllocationCallbacks * pAllocator)66 Handle allocateHandle (Parent parent, const CreateInfo* pCreateInfo, const VkAllocationCallbacks* pAllocator)
67 {
68 Object* obj = DE_NULL;
69
70 if (pAllocator)
71 {
72 void* mem = allocateSystemMem<Object>(pAllocator, VK_SYSTEM_ALLOCATION_SCOPE_OBJECT);
73 try
74 {
75 obj = new (mem) Object(parent, pCreateInfo);
76 DE_ASSERT(obj == mem);
77 }
78 catch (...)
79 {
80 pAllocator->pfnFree(pAllocator->pUserData, mem);
81 throw;
82 }
83 }
84 else
85 obj = new Object(parent, pCreateInfo);
86
87 return reinterpret_cast<Handle>(obj);
88 }
89
90 template<typename Object, typename Handle, typename CreateInfo>
allocateHandle(const CreateInfo * pCreateInfo,const VkAllocationCallbacks * pAllocator)91 Handle allocateHandle (const CreateInfo* pCreateInfo, const VkAllocationCallbacks* pAllocator)
92 {
93 Object* obj = DE_NULL;
94
95 if (pAllocator)
96 {
97 void* mem = allocateSystemMem<Object>(pAllocator, VK_SYSTEM_ALLOCATION_SCOPE_OBJECT);
98 try
99 {
100 obj = new (mem) Object(pCreateInfo);
101 DE_ASSERT(obj == mem);
102 }
103 catch (...)
104 {
105 pAllocator->pfnFree(pAllocator->pUserData, mem);
106 throw;
107 }
108 }
109 else
110 obj = new Object(pCreateInfo);
111
112 return reinterpret_cast<Handle>(obj);
113 }
114
115 template<typename Object, typename Handle, typename Parent>
allocateHandle(Parent parent,const VkAllocationCallbacks * pAllocator)116 Handle allocateHandle (Parent parent, const VkAllocationCallbacks* pAllocator)
117 {
118 Object* obj = DE_NULL;
119
120 if (pAllocator)
121 {
122 void* mem = allocateSystemMem<Object>(pAllocator, VK_SYSTEM_ALLOCATION_SCOPE_OBJECT);
123 try
124 {
125 obj = new (mem) Object(parent);
126 DE_ASSERT(obj == mem);
127 }
128 catch (...)
129 {
130 pAllocator->pfnFree(pAllocator->pUserData, mem);
131 throw;
132 }
133 }
134 else
135 obj = new Object(parent);
136
137 return reinterpret_cast<Handle>(obj);
138 }
139
140 template<typename Object, typename Handle>
freeHandle(Handle handle,const VkAllocationCallbacks * pAllocator)141 void freeHandle (Handle handle, const VkAllocationCallbacks* pAllocator)
142 {
143 Object* obj = reinterpret_cast<Object*>(handle);
144
145 if (pAllocator)
146 {
147 obj->~Object();
148 freeSystemMem(pAllocator, reinterpret_cast<void*>(obj));
149 }
150 else
151 delete obj;
152 }
153
154 template<typename Object, typename BaseObject, typename Handle, typename Parent, typename CreateInfo>
allocateNonDispHandle(Parent parent,const CreateInfo * pCreateInfo,const VkAllocationCallbacks * pAllocator)155 Handle allocateNonDispHandle (Parent parent, const CreateInfo* pCreateInfo, const VkAllocationCallbacks* pAllocator)
156 {
157 Object* const obj = allocateHandle<Object, Object*>(parent, pCreateInfo, pAllocator);
158 return Handle((deUint64)(deUintptr)static_cast<BaseObject*>(obj));
159 }
160
161 template<typename Object, typename Handle, typename Parent, typename CreateInfo>
allocateNonDispHandle(Parent parent,const CreateInfo * pCreateInfo,const VkAllocationCallbacks * pAllocator)162 Handle allocateNonDispHandle (Parent parent, const CreateInfo* pCreateInfo, const VkAllocationCallbacks* pAllocator)
163 {
164 return allocateNonDispHandle<Object, Object, Handle, Parent, CreateInfo>(parent, pCreateInfo, pAllocator);
165 }
166
167 template<typename Object, typename Handle, typename Parent>
allocateNonDispHandle(Parent parent,const VkAllocationCallbacks * pAllocator)168 Handle allocateNonDispHandle (Parent parent, const VkAllocationCallbacks* pAllocator)
169 {
170 Object* const obj = allocateHandle<Object, Object*>(parent, pAllocator);
171 return Handle((deUint64)(deUintptr)obj);
172 }
173
174 template<typename Object, typename Handle>
freeNonDispHandle(Handle handle,const VkAllocationCallbacks * pAllocator)175 void freeNonDispHandle (Handle handle, const VkAllocationCallbacks* pAllocator)
176 {
177 freeHandle<Object>(reinterpret_cast<Object*>((deUintptr)handle.getInternal()), pAllocator);
178 }
179
180 // Object definitions
181
182 #define VK_NULL_RETURN(STMT) \
183 do { \
184 try { \
185 STMT; \
186 return VK_SUCCESS; \
187 } catch (const std::bad_alloc&) { \
188 return VK_ERROR_OUT_OF_HOST_MEMORY; \
189 } catch (VkResult res) { \
190 return res; \
191 } \
192 } while (deGetFalse())
193
194 // \todo [2015-07-14 pyry] Check FUNC type by checkedCastToPtr<T>() or similar
195 #define VK_NULL_FUNC_ENTRY(NAME, FUNC) { #NAME, (deFunctionPtr)FUNC } // NOLINT(FUNC)
196
197 #define VK_NULL_DEFINE_DEVICE_OBJ(NAME) \
198 struct NAME \
199 { \
200 NAME (VkDevice, const Vk##NAME##CreateInfo*) {} \
201 }
202
203 VK_NULL_DEFINE_DEVICE_OBJ(Fence);
204 VK_NULL_DEFINE_DEVICE_OBJ(Semaphore);
205 VK_NULL_DEFINE_DEVICE_OBJ(Event);
206 VK_NULL_DEFINE_DEVICE_OBJ(QueryPool);
207 VK_NULL_DEFINE_DEVICE_OBJ(BufferView);
208 VK_NULL_DEFINE_DEVICE_OBJ(ImageView);
209 VK_NULL_DEFINE_DEVICE_OBJ(ShaderModule);
210 VK_NULL_DEFINE_DEVICE_OBJ(PipelineCache);
211 VK_NULL_DEFINE_DEVICE_OBJ(PipelineLayout);
212 VK_NULL_DEFINE_DEVICE_OBJ(DescriptorSetLayout);
213 VK_NULL_DEFINE_DEVICE_OBJ(Sampler);
214 VK_NULL_DEFINE_DEVICE_OBJ(Framebuffer);
215
216 class Instance
217 {
218 public:
219 Instance (const VkInstanceCreateInfo* instanceInfo);
~Instance(void)220 ~Instance (void) {}
221
getProcAddr(const char * name) const222 PFN_vkVoidFunction getProcAddr (const char* name) const { return (PFN_vkVoidFunction)m_functions.getFunction(name); }
223
224 private:
225 const tcu::StaticFunctionLibrary m_functions;
226 };
227
228 class SurfaceKHR
229 {
230 public:
SurfaceKHR(VkInstance,const VkXlibSurfaceCreateInfoKHR *)231 SurfaceKHR (VkInstance, const VkXlibSurfaceCreateInfoKHR*) {}
SurfaceKHR(VkInstance,const VkXcbSurfaceCreateInfoKHR *)232 SurfaceKHR (VkInstance, const VkXcbSurfaceCreateInfoKHR*) {}
SurfaceKHR(VkInstance,const VkWaylandSurfaceCreateInfoKHR *)233 SurfaceKHR (VkInstance, const VkWaylandSurfaceCreateInfoKHR*) {}
SurfaceKHR(VkInstance,const VkAndroidSurfaceCreateInfoKHR *)234 SurfaceKHR (VkInstance, const VkAndroidSurfaceCreateInfoKHR*) {}
SurfaceKHR(VkInstance,const VkWin32SurfaceCreateInfoKHR *)235 SurfaceKHR (VkInstance, const VkWin32SurfaceCreateInfoKHR*) {}
SurfaceKHR(VkInstance,const VkDisplaySurfaceCreateInfoKHR *)236 SurfaceKHR (VkInstance, const VkDisplaySurfaceCreateInfoKHR*) {}
SurfaceKHR(VkInstance,const VkViSurfaceCreateInfoNN *)237 SurfaceKHR (VkInstance, const VkViSurfaceCreateInfoNN*) {}
SurfaceKHR(VkInstance,const VkIOSSurfaceCreateInfoMVK *)238 SurfaceKHR (VkInstance, const VkIOSSurfaceCreateInfoMVK*) {}
SurfaceKHR(VkInstance,const VkMacOSSurfaceCreateInfoMVK *)239 SurfaceKHR (VkInstance, const VkMacOSSurfaceCreateInfoMVK*) {}
SurfaceKHR(VkInstance,const VkImagePipeSurfaceCreateInfoFUCHSIA *)240 SurfaceKHR (VkInstance, const VkImagePipeSurfaceCreateInfoFUCHSIA*) {}
SurfaceKHR(VkInstance,const VkHeadlessSurfaceCreateInfoEXT *)241 SurfaceKHR (VkInstance, const VkHeadlessSurfaceCreateInfoEXT*) {}
SurfaceKHR(VkInstance,const VkStreamDescriptorSurfaceCreateInfoGGP *)242 SurfaceKHR (VkInstance, const VkStreamDescriptorSurfaceCreateInfoGGP*) {}
SurfaceKHR(VkInstance,const VkMetalSurfaceCreateInfoEXT *)243 SurfaceKHR (VkInstance, const VkMetalSurfaceCreateInfoEXT*) {}
~SurfaceKHR(void)244 ~SurfaceKHR (void) {}
245 };
246
247 class DisplayModeKHR
248 {
249 public:
DisplayModeKHR(VkDisplayKHR,const VkDisplayModeCreateInfoKHR *)250 DisplayModeKHR (VkDisplayKHR, const VkDisplayModeCreateInfoKHR*) {}
~DisplayModeKHR(void)251 ~DisplayModeKHR (void) {}
252 };
253
254 class DebugReportCallbackEXT
255 {
256 public:
DebugReportCallbackEXT(VkInstance,const VkDebugReportCallbackCreateInfoEXT *)257 DebugReportCallbackEXT (VkInstance, const VkDebugReportCallbackCreateInfoEXT*) {}
~DebugReportCallbackEXT(void)258 ~DebugReportCallbackEXT (void) {}
259 };
260
261 class Device
262 {
263 public:
264 Device (VkPhysicalDevice physicalDevice, const VkDeviceCreateInfo* deviceInfo);
~Device(void)265 ~Device (void) {}
266
getProcAddr(const char * name) const267 PFN_vkVoidFunction getProcAddr (const char* name) const { return (PFN_vkVoidFunction)m_functions.getFunction(name); }
268
269 private:
270 const tcu::StaticFunctionLibrary m_functions;
271 };
272
273 class Pipeline
274 {
275 public:
Pipeline(VkDevice,const VkGraphicsPipelineCreateInfo *)276 Pipeline (VkDevice, const VkGraphicsPipelineCreateInfo*) {}
Pipeline(VkDevice,const VkComputePipelineCreateInfo *)277 Pipeline (VkDevice, const VkComputePipelineCreateInfo*) {}
Pipeline(VkDevice,const VkRayTracingPipelineCreateInfoNV *)278 Pipeline (VkDevice, const VkRayTracingPipelineCreateInfoNV*) {}
Pipeline(VkDevice,const VkRayTracingPipelineCreateInfoKHR *)279 Pipeline (VkDevice, const VkRayTracingPipelineCreateInfoKHR*) {}
280 };
281
282 class RenderPass
283 {
284 public:
RenderPass(VkDevice,const VkRenderPassCreateInfo *)285 RenderPass (VkDevice, const VkRenderPassCreateInfo*) {}
RenderPass(VkDevice,const VkRenderPassCreateInfo2 *)286 RenderPass (VkDevice, const VkRenderPassCreateInfo2*) {}
287 };
288
289 class SwapchainKHR
290 {
291 public:
SwapchainKHR(VkDevice,const VkSwapchainCreateInfoKHR *)292 SwapchainKHR (VkDevice, const VkSwapchainCreateInfoKHR*) {}
~SwapchainKHR(void)293 ~SwapchainKHR (void) {}
294 };
295
296 class SamplerYcbcrConversion
297 {
298 public:
SamplerYcbcrConversion(VkDevice,const VkSamplerYcbcrConversionCreateInfo *)299 SamplerYcbcrConversion (VkDevice, const VkSamplerYcbcrConversionCreateInfo*) {}
300 };
301
302 class Buffer
303 {
304 public:
Buffer(VkDevice,const VkBufferCreateInfo * pCreateInfo)305 Buffer (VkDevice, const VkBufferCreateInfo* pCreateInfo)
306 : m_size (pCreateInfo->size)
307 {
308 }
309
getSize(void) const310 VkDeviceSize getSize (void) const { return m_size; }
311
312 private:
313 const VkDeviceSize m_size;
314 };
315
getExternalTypesHandle(const VkImageCreateInfo * pCreateInfo)316 VkExternalMemoryHandleTypeFlags getExternalTypesHandle (const VkImageCreateInfo* pCreateInfo)
317 {
318 const VkExternalMemoryImageCreateInfo* const externalInfo = findStructure<VkExternalMemoryImageCreateInfo> (pCreateInfo->pNext);
319
320 return externalInfo ? externalInfo->handleTypes : 0u;
321 }
322
323 class Image
324 {
325 public:
Image(VkDevice,const VkImageCreateInfo * pCreateInfo)326 Image (VkDevice, const VkImageCreateInfo* pCreateInfo)
327 : m_imageType (pCreateInfo->imageType)
328 , m_format (pCreateInfo->format)
329 , m_extent (pCreateInfo->extent)
330 , m_arrayLayers (pCreateInfo->arrayLayers)
331 , m_samples (pCreateInfo->samples)
332 , m_usage (pCreateInfo->usage)
333 , m_flags (pCreateInfo->flags)
334 , m_externalHandleTypes (getExternalTypesHandle(pCreateInfo))
335 {
336 }
337
getImageType(void) const338 VkImageType getImageType (void) const { return m_imageType; }
getFormat(void) const339 VkFormat getFormat (void) const { return m_format; }
getExtent(void) const340 VkExtent3D getExtent (void) const { return m_extent; }
getArrayLayers(void) const341 deUint32 getArrayLayers (void) const { return m_arrayLayers; }
getSamples(void) const342 VkSampleCountFlagBits getSamples (void) const { return m_samples; }
getUsage(void) const343 VkImageUsageFlags getUsage (void) const { return m_usage; }
getFlags(void) const344 VkImageCreateFlags getFlags (void) const { return m_flags; }
getExternalHandleTypes(void) const345 VkExternalMemoryHandleTypeFlags getExternalHandleTypes (void) const { return m_externalHandleTypes; }
346
347 private:
348 const VkImageType m_imageType;
349 const VkFormat m_format;
350 const VkExtent3D m_extent;
351 const deUint32 m_arrayLayers;
352 const VkSampleCountFlagBits m_samples;
353 const VkImageUsageFlags m_usage;
354 const VkImageCreateFlags m_flags;
355 const VkExternalMemoryHandleTypeFlags m_externalHandleTypes;
356 };
357
allocateHeap(const VkMemoryAllocateInfo * pAllocInfo)358 void* allocateHeap (const VkMemoryAllocateInfo* pAllocInfo)
359 {
360 // \todo [2015-12-03 pyry] Alignment requirements?
361 // \todo [2015-12-03 pyry] Empty allocations okay?
362 if (pAllocInfo->allocationSize > 0)
363 {
364 void* const heapPtr = deMalloc((size_t)pAllocInfo->allocationSize);
365 if (!heapPtr)
366 throw std::bad_alloc();
367 return heapPtr;
368 }
369 else
370 return DE_NULL;
371 }
372
freeHeap(void * ptr)373 void freeHeap (void* ptr)
374 {
375 deFree(ptr);
376 }
377
378 class DeviceMemory
379 {
380 public:
~DeviceMemory(void)381 virtual ~DeviceMemory (void) {}
382 virtual void* map (void) = 0;
383 virtual void unmap (void) = 0;
384 };
385
386 class PrivateDeviceMemory : public DeviceMemory
387 {
388 public:
PrivateDeviceMemory(VkDevice,const VkMemoryAllocateInfo * pAllocInfo)389 PrivateDeviceMemory (VkDevice, const VkMemoryAllocateInfo* pAllocInfo)
390 : m_memory(allocateHeap(pAllocInfo))
391 {
392 // \todo [2016-08-03 pyry] In some cases leaving data unintialized would help valgrind analysis,
393 // but currently it mostly hinders it.
394 if (m_memory)
395 deMemset(m_memory, 0xcd, (size_t)pAllocInfo->allocationSize);
396 }
~PrivateDeviceMemory(void)397 virtual ~PrivateDeviceMemory (void)
398 {
399 freeHeap(m_memory);
400 }
401
map(void)402 virtual void* map (void) /*override*/ { return m_memory; }
unmap(void)403 virtual void unmap (void) /*override*/ {}
404
405 private:
406 void* const m_memory;
407 };
408
409 #if defined(USE_ANDROID_O_HARDWARE_BUFFER)
findOrCreateHwBuffer(const VkMemoryAllocateInfo * pAllocInfo)410 AHardwareBuffer* findOrCreateHwBuffer (const VkMemoryAllocateInfo* pAllocInfo)
411 {
412 const VkExportMemoryAllocateInfo* const exportInfo = findStructure<VkExportMemoryAllocateInfo>(pAllocInfo->pNext);
413 const VkImportAndroidHardwareBufferInfoANDROID* const importInfo = findStructure<VkImportAndroidHardwareBufferInfoANDROID>(pAllocInfo->pNext);
414 const VkMemoryDedicatedAllocateInfo* const dedicatedInfo = findStructure<VkMemoryDedicatedAllocateInfo>(pAllocInfo->pNext);
415 const Image* const image = dedicatedInfo && !!dedicatedInfo->image ? reinterpret_cast<const Image*>(dedicatedInfo->image.getInternal()) : DE_NULL;
416 AHardwareBuffer* hwbuffer = DE_NULL;
417
418 // Import and export aren't mutually exclusive; we can have both simultaneously.
419 DE_ASSERT((importInfo && importInfo->buffer.internal) ||
420 (exportInfo && (exportInfo->handleTypes & VK_EXTERNAL_MEMORY_HANDLE_TYPE_ANDROID_HARDWARE_BUFFER_BIT_ANDROID) != 0));
421
422 if (importInfo && importInfo->buffer.internal)
423 {
424 hwbuffer = (AHardwareBuffer*)importInfo->buffer.internal;
425 AHardwareBuffer_acquire(hwbuffer);
426 }
427 else if (exportInfo && (exportInfo->handleTypes & VK_EXTERNAL_MEMORY_HANDLE_TYPE_ANDROID_HARDWARE_BUFFER_BIT_ANDROID) != 0)
428 {
429 AHardwareBuffer_Desc hwbufferDesc;
430 deMemset(&hwbufferDesc, 0, sizeof(hwbufferDesc));
431
432 if (image)
433 {
434 hwbufferDesc.width = image->getExtent().width;
435 hwbufferDesc.height = image->getExtent().height;
436 hwbufferDesc.layers = image->getArrayLayers();
437 switch (image->getFormat())
438 {
439 case VK_FORMAT_R8G8B8A8_UNORM:
440 hwbufferDesc.format = AHARDWAREBUFFER_FORMAT_R8G8B8A8_UNORM;
441 break;
442 case VK_FORMAT_R8G8B8_UNORM:
443 hwbufferDesc.format = AHARDWAREBUFFER_FORMAT_R8G8B8_UNORM;
444 break;
445 case VK_FORMAT_R5G6B5_UNORM_PACK16:
446 hwbufferDesc.format = AHARDWAREBUFFER_FORMAT_R5G6B5_UNORM;
447 break;
448 case VK_FORMAT_R16G16B16A16_SFLOAT:
449 hwbufferDesc.format = AHARDWAREBUFFER_FORMAT_R16G16B16A16_FLOAT;
450 break;
451 case VK_FORMAT_A2R10G10B10_UNORM_PACK32:
452 hwbufferDesc.format = AHARDWAREBUFFER_FORMAT_R10G10B10A2_UNORM;
453 break;
454 default:
455 DE_FATAL("Unsupported image format for Android hardware buffer export");
456 break;
457 }
458 if ((image->getUsage() & VK_IMAGE_USAGE_SAMPLED_BIT) != 0)
459 hwbufferDesc.usage |= AHARDWAREBUFFER_USAGE_GPU_SAMPLED_IMAGE;
460 if ((image->getUsage() & VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT) != 0)
461 hwbufferDesc.usage |= AHARDWAREBUFFER_USAGE_GPU_COLOR_OUTPUT;
462 // if ((image->getFlags() & VK_IMAGE_CREATE_PROTECTED_BIT) != 0)
463 // hwbufferDesc.usage |= AHARDWAREBUFFER_USAGE_PROTECTED_CONTENT;
464
465 // Make sure we have at least one AHB GPU usage, even if the image doesn't have any
466 // Vulkan usages with corresponding to AHB GPU usages.
467 if ((image->getUsage() & (VK_IMAGE_USAGE_SAMPLED_BIT | VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT)) == 0)
468 hwbufferDesc.usage |= AHARDWAREBUFFER_USAGE_GPU_SAMPLED_IMAGE;
469 }
470 else
471 {
472 hwbufferDesc.width = static_cast<deUint32>(pAllocInfo->allocationSize);
473 hwbufferDesc.height = 1,
474 hwbufferDesc.layers = 1,
475 hwbufferDesc.format = AHARDWAREBUFFER_FORMAT_BLOB,
476 hwbufferDesc.usage = AHARDWAREBUFFER_USAGE_GPU_DATA_BUFFER;
477 }
478
479 AHardwareBuffer_allocate(&hwbufferDesc, &hwbuffer);
480 }
481
482 return hwbuffer;
483 }
484
485 class ExternalDeviceMemoryAndroid : public DeviceMemory
486 {
487 public:
ExternalDeviceMemoryAndroid(VkDevice,const VkMemoryAllocateInfo * pAllocInfo)488 ExternalDeviceMemoryAndroid (VkDevice, const VkMemoryAllocateInfo* pAllocInfo)
489 : m_hwbuffer(findOrCreateHwBuffer(pAllocInfo))
490 {}
~ExternalDeviceMemoryAndroid(void)491 virtual ~ExternalDeviceMemoryAndroid (void)
492 {
493 if (m_hwbuffer)
494 AHardwareBuffer_release(m_hwbuffer);
495 }
496
map(void)497 virtual void* map (void) /*override*/
498 {
499 void* p;
500 AHardwareBuffer_lock(m_hwbuffer, AHARDWAREBUFFER_USAGE_CPU_READ_OFTEN | AHARDWAREBUFFER_USAGE_CPU_WRITE_OFTEN, -1, NULL, &p);
501 return p;
502 }
503
unmap(void)504 virtual void unmap (void) /*override*/ { AHardwareBuffer_unlock(m_hwbuffer, NULL); }
505
getHwBuffer(void)506 AHardwareBuffer* getHwBuffer (void) { return m_hwbuffer; }
507
508 private:
509 AHardwareBuffer* const m_hwbuffer;
510 };
511 #endif // defined(USE_ANDROID_O_HARDWARE_BUFFER)
512
513 class IndirectCommandsLayoutNV
514 {
515 public:
IndirectCommandsLayoutNV(VkDevice,const VkIndirectCommandsLayoutCreateInfoNV *)516 IndirectCommandsLayoutNV (VkDevice, const VkIndirectCommandsLayoutCreateInfoNV*)
517 {}
518 };
519
520 class DebugUtilsMessengerEXT
521 {
522 public:
DebugUtilsMessengerEXT(VkInstance,const VkDebugUtilsMessengerCreateInfoEXT *)523 DebugUtilsMessengerEXT (VkInstance, const VkDebugUtilsMessengerCreateInfoEXT*)
524 {}
525 };
526
527 class AccelerationStructureNV
528 {
529 public:
AccelerationStructureNV(VkDevice,const VkAccelerationStructureCreateInfoNV *)530 AccelerationStructureNV (VkDevice, const VkAccelerationStructureCreateInfoNV*)
531 {}
532 };
533
534 class AccelerationStructureKHR
535 {
536 public:
AccelerationStructureKHR(VkDevice,const VkAccelerationStructureCreateInfoKHR *)537 AccelerationStructureKHR (VkDevice, const VkAccelerationStructureCreateInfoKHR*)
538 {}
539 };
540
541 class DeferredOperationKHR
542 {
543 public:
DeferredOperationKHR(VkDevice)544 DeferredOperationKHR (VkDevice)
545 {}
546 };
547
548 class VideoSessionKHR
549 {
550 public:
VideoSessionKHR(VkDevice,const VkVideoSessionCreateInfoKHR *)551 VideoSessionKHR (VkDevice, const VkVideoSessionCreateInfoKHR*)
552 {}
553 };
554
555 class VideoSessionParametersKHR
556 {
557 public:
VideoSessionParametersKHR(VkDevice,const VkVideoSessionParametersCreateInfoKHR *)558 VideoSessionParametersKHR (VkDevice, const VkVideoSessionParametersCreateInfoKHR*)
559 {}
560 };
561
562 class ValidationCacheEXT
563 {
564 public:
ValidationCacheEXT(VkDevice,const VkValidationCacheCreateInfoEXT *)565 ValidationCacheEXT (VkDevice, const VkValidationCacheCreateInfoEXT*)
566 {}
567 };
568
569 class CommandBuffer
570 {
571 public:
CommandBuffer(VkDevice,VkCommandPool,VkCommandBufferLevel)572 CommandBuffer (VkDevice, VkCommandPool, VkCommandBufferLevel)
573 {}
574 };
575
576 class DescriptorUpdateTemplate
577 {
578 public:
DescriptorUpdateTemplate(VkDevice,const VkDescriptorUpdateTemplateCreateInfo *)579 DescriptorUpdateTemplate (VkDevice, const VkDescriptorUpdateTemplateCreateInfo*)
580 {}
581 };
582
583 class PrivateDataSlotEXT
584 {
585 public:
PrivateDataSlotEXT(VkDevice,const VkPrivateDataSlotCreateInfoEXT *)586 PrivateDataSlotEXT (VkDevice, const VkPrivateDataSlotCreateInfoEXT*)
587 {}
588 };
589
590 class CommandPool
591 {
592 public:
CommandPool(VkDevice device,const VkCommandPoolCreateInfo *)593 CommandPool (VkDevice device, const VkCommandPoolCreateInfo*)
594 : m_device(device)
595 {}
596 ~CommandPool (void);
597
598 VkCommandBuffer allocate (VkCommandBufferLevel level);
599 void free (VkCommandBuffer buffer);
600
601 private:
602 const VkDevice m_device;
603
604 vector<CommandBuffer*> m_buffers;
605 };
606
~CommandPool(void)607 CommandPool::~CommandPool (void)
608 {
609 for (size_t ndx = 0; ndx < m_buffers.size(); ++ndx)
610 delete m_buffers[ndx];
611 }
612
allocate(VkCommandBufferLevel level)613 VkCommandBuffer CommandPool::allocate (VkCommandBufferLevel level)
614 {
615 CommandBuffer* const impl = new CommandBuffer(m_device, VkCommandPool(reinterpret_cast<deUintptr>(this)), level);
616
617 try
618 {
619 m_buffers.push_back(impl);
620 }
621 catch (...)
622 {
623 delete impl;
624 throw;
625 }
626
627 return reinterpret_cast<VkCommandBuffer>(impl);
628 }
629
free(VkCommandBuffer buffer)630 void CommandPool::free (VkCommandBuffer buffer)
631 {
632 CommandBuffer* const impl = reinterpret_cast<CommandBuffer*>(buffer);
633
634 for (size_t ndx = 0; ndx < m_buffers.size(); ++ndx)
635 {
636 if (m_buffers[ndx] == impl)
637 {
638 std::swap(m_buffers[ndx], m_buffers.back());
639 m_buffers.pop_back();
640 delete impl;
641 return;
642 }
643 }
644
645 DE_FATAL("VkCommandBuffer not owned by VkCommandPool");
646 }
647
648 class DescriptorSet
649 {
650 public:
DescriptorSet(VkDevice,VkDescriptorPool,VkDescriptorSetLayout)651 DescriptorSet (VkDevice, VkDescriptorPool, VkDescriptorSetLayout) {}
652 };
653
654 class DescriptorPool
655 {
656 public:
DescriptorPool(VkDevice device,const VkDescriptorPoolCreateInfo * pCreateInfo)657 DescriptorPool (VkDevice device, const VkDescriptorPoolCreateInfo* pCreateInfo)
658 : m_device (device)
659 , m_flags (pCreateInfo->flags)
660 {}
~DescriptorPool(void)661 ~DescriptorPool (void)
662 {
663 reset();
664 }
665
666 VkDescriptorSet allocate (VkDescriptorSetLayout setLayout);
667 void free (VkDescriptorSet set);
668
669 void reset (void);
670
671 private:
672 const VkDevice m_device;
673 const VkDescriptorPoolCreateFlags m_flags;
674
675 vector<DescriptorSet*> m_managedSets;
676 };
677
allocate(VkDescriptorSetLayout setLayout)678 VkDescriptorSet DescriptorPool::allocate (VkDescriptorSetLayout setLayout)
679 {
680 DescriptorSet* const impl = new DescriptorSet(m_device, VkDescriptorPool(reinterpret_cast<deUintptr>(this)), setLayout);
681
682 try
683 {
684 m_managedSets.push_back(impl);
685 }
686 catch (...)
687 {
688 delete impl;
689 throw;
690 }
691
692 return VkDescriptorSet(reinterpret_cast<deUintptr>(impl));
693 }
694
free(VkDescriptorSet set)695 void DescriptorPool::free (VkDescriptorSet set)
696 {
697 DescriptorSet* const impl = reinterpret_cast<DescriptorSet*>((deUintptr)set.getInternal());
698
699 DE_ASSERT(m_flags & VK_DESCRIPTOR_POOL_CREATE_FREE_DESCRIPTOR_SET_BIT);
700 DE_UNREF(m_flags);
701
702 for (size_t ndx = 0; ndx < m_managedSets.size(); ++ndx)
703 {
704 if (m_managedSets[ndx] == impl)
705 {
706 std::swap(m_managedSets[ndx], m_managedSets.back());
707 m_managedSets.pop_back();
708 delete impl;
709 return;
710 }
711 }
712
713 DE_FATAL("VkDescriptorSet not owned by VkDescriptorPool");
714 }
715
reset(void)716 void DescriptorPool::reset (void)
717 {
718 for (size_t ndx = 0; ndx < m_managedSets.size(); ++ndx)
719 delete m_managedSets[ndx];
720 m_managedSets.clear();
721 }
722
723 // API implementation
724
725 extern "C"
726 {
727
getDeviceProcAddr(VkDevice device,const char * pName)728 VKAPI_ATTR PFN_vkVoidFunction VKAPI_CALL getDeviceProcAddr (VkDevice device, const char* pName)
729 {
730 return reinterpret_cast<Device*>(device)->getProcAddr(pName);
731 }
732
createGraphicsPipelines(VkDevice device,VkPipelineCache,deUint32 count,const VkGraphicsPipelineCreateInfo * pCreateInfos,const VkAllocationCallbacks * pAllocator,VkPipeline * pPipelines)733 VKAPI_ATTR VkResult VKAPI_CALL createGraphicsPipelines (VkDevice device, VkPipelineCache, deUint32 count, const VkGraphicsPipelineCreateInfo* pCreateInfos, const VkAllocationCallbacks* pAllocator, VkPipeline* pPipelines)
734 {
735 deUint32 allocNdx;
736 try
737 {
738 for (allocNdx = 0; allocNdx < count; allocNdx++)
739 pPipelines[allocNdx] = allocateNonDispHandle<Pipeline, VkPipeline>(device, pCreateInfos+allocNdx, pAllocator);
740
741 return VK_SUCCESS;
742 }
743 catch (const std::bad_alloc&)
744 {
745 for (deUint32 freeNdx = 0; freeNdx < allocNdx; freeNdx++)
746 freeNonDispHandle<Pipeline, VkPipeline>(pPipelines[freeNdx], pAllocator);
747
748 return VK_ERROR_OUT_OF_HOST_MEMORY;
749 }
750 catch (VkResult err)
751 {
752 for (deUint32 freeNdx = 0; freeNdx < allocNdx; freeNdx++)
753 freeNonDispHandle<Pipeline, VkPipeline>(pPipelines[freeNdx], pAllocator);
754
755 return err;
756 }
757 }
758
createComputePipelines(VkDevice device,VkPipelineCache,deUint32 count,const VkComputePipelineCreateInfo * pCreateInfos,const VkAllocationCallbacks * pAllocator,VkPipeline * pPipelines)759 VKAPI_ATTR VkResult VKAPI_CALL createComputePipelines (VkDevice device, VkPipelineCache, deUint32 count, const VkComputePipelineCreateInfo* pCreateInfos, const VkAllocationCallbacks* pAllocator, VkPipeline* pPipelines)
760 {
761 deUint32 allocNdx;
762 try
763 {
764 for (allocNdx = 0; allocNdx < count; allocNdx++)
765 pPipelines[allocNdx] = allocateNonDispHandle<Pipeline, VkPipeline>(device, pCreateInfos+allocNdx, pAllocator);
766
767 return VK_SUCCESS;
768 }
769 catch (const std::bad_alloc&)
770 {
771 for (deUint32 freeNdx = 0; freeNdx < allocNdx; freeNdx++)
772 freeNonDispHandle<Pipeline, VkPipeline>(pPipelines[freeNdx], pAllocator);
773
774 return VK_ERROR_OUT_OF_HOST_MEMORY;
775 }
776 catch (VkResult err)
777 {
778 for (deUint32 freeNdx = 0; freeNdx < allocNdx; freeNdx++)
779 freeNonDispHandle<Pipeline, VkPipeline>(pPipelines[freeNdx], pAllocator);
780
781 return err;
782 }
783 }
784
createRayTracingPipelinesNV(VkDevice device,VkPipelineCache,deUint32 count,const VkRayTracingPipelineCreateInfoKHR * pCreateInfos,const VkAllocationCallbacks * pAllocator,VkPipeline * pPipelines)785 VKAPI_ATTR VkResult VKAPI_CALL createRayTracingPipelinesNV (VkDevice device, VkPipelineCache, deUint32 count, const VkRayTracingPipelineCreateInfoKHR* pCreateInfos, const VkAllocationCallbacks* pAllocator, VkPipeline* pPipelines)
786 {
787 deUint32 allocNdx;
788 try
789 {
790 for (allocNdx = 0; allocNdx < count; allocNdx++)
791 pPipelines[allocNdx] = allocateNonDispHandle<Pipeline, VkPipeline>(device, pCreateInfos+allocNdx, pAllocator);
792
793 return VK_SUCCESS;
794 }
795 catch (const std::bad_alloc&)
796 {
797 for (deUint32 freeNdx = 0; freeNdx < allocNdx; freeNdx++)
798 freeNonDispHandle<Pipeline, VkPipeline>(pPipelines[freeNdx], pAllocator);
799
800 return VK_ERROR_OUT_OF_HOST_MEMORY;
801 }
802 catch (VkResult err)
803 {
804 for (deUint32 freeNdx = 0; freeNdx < allocNdx; freeNdx++)
805 freeNonDispHandle<Pipeline, VkPipeline>(pPipelines[freeNdx], pAllocator);
806
807 return err;
808 }
809 }
810
createRayTracingPipelinesKHR(VkDevice device,VkPipelineCache,deUint32 count,const VkRayTracingPipelineCreateInfoKHR * pCreateInfos,const VkAllocationCallbacks * pAllocator,VkPipeline * pPipelines)811 VKAPI_ATTR VkResult VKAPI_CALL createRayTracingPipelinesKHR (VkDevice device, VkPipelineCache, deUint32 count, const VkRayTracingPipelineCreateInfoKHR* pCreateInfos, const VkAllocationCallbacks* pAllocator, VkPipeline* pPipelines)
812 {
813 deUint32 allocNdx;
814 try
815 {
816 for (allocNdx = 0; allocNdx < count; allocNdx++)
817 pPipelines[allocNdx] = allocateNonDispHandle<Pipeline, VkPipeline>(device, pCreateInfos+allocNdx, pAllocator);
818
819 return VK_SUCCESS;
820 }
821 catch (const std::bad_alloc&)
822 {
823 for (deUint32 freeNdx = 0; freeNdx < allocNdx; freeNdx++)
824 freeNonDispHandle<Pipeline, VkPipeline>(pPipelines[freeNdx], pAllocator);
825
826 return VK_ERROR_OUT_OF_HOST_MEMORY;
827 }
828 catch (VkResult err)
829 {
830 for (deUint32 freeNdx = 0; freeNdx < allocNdx; freeNdx++)
831 freeNonDispHandle<Pipeline, VkPipeline>(pPipelines[freeNdx], pAllocator);
832
833 return err;
834 }
835 }
836
enumeratePhysicalDevices(VkInstance,deUint32 * pPhysicalDeviceCount,VkPhysicalDevice * pDevices)837 VKAPI_ATTR VkResult VKAPI_CALL enumeratePhysicalDevices (VkInstance, deUint32* pPhysicalDeviceCount, VkPhysicalDevice* pDevices)
838 {
839 if (pDevices && *pPhysicalDeviceCount >= 1u)
840 *pDevices = reinterpret_cast<VkPhysicalDevice>((void*)(deUintptr)1u);
841
842 *pPhysicalDeviceCount = 1;
843
844 return VK_SUCCESS;
845 }
846
enumerateExtensions(deUint32 numExtensions,const VkExtensionProperties * extensions,deUint32 * pPropertyCount,VkExtensionProperties * pProperties)847 VkResult enumerateExtensions (deUint32 numExtensions, const VkExtensionProperties* extensions, deUint32* pPropertyCount, VkExtensionProperties* pProperties)
848 {
849 const deUint32 dstSize = pPropertyCount ? *pPropertyCount : 0;
850
851 if (pPropertyCount)
852 *pPropertyCount = numExtensions;
853
854 if (pProperties)
855 {
856 for (deUint32 ndx = 0; ndx < de::min(numExtensions, dstSize); ++ndx)
857 pProperties[ndx] = extensions[ndx];
858
859 if (dstSize < numExtensions)
860 return VK_INCOMPLETE;
861 }
862
863 return VK_SUCCESS;
864 }
865
enumerateInstanceExtensionProperties(const char * pLayerName,deUint32 * pPropertyCount,VkExtensionProperties * pProperties)866 VKAPI_ATTR VkResult VKAPI_CALL enumerateInstanceExtensionProperties (const char* pLayerName, deUint32* pPropertyCount, VkExtensionProperties* pProperties)
867 {
868 static const VkExtensionProperties s_extensions[] =
869 {
870 { "VK_KHR_get_physical_device_properties2", 1u },
871 { "VK_KHR_external_memory_capabilities", 1u },
872 };
873
874 if (!pLayerName)
875 return enumerateExtensions((deUint32)DE_LENGTH_OF_ARRAY(s_extensions), s_extensions, pPropertyCount, pProperties);
876 else
877 return enumerateExtensions(0, DE_NULL, pPropertyCount, pProperties);
878 }
879
enumerateDeviceExtensionProperties(VkPhysicalDevice physicalDevice,const char * pLayerName,deUint32 * pPropertyCount,VkExtensionProperties * pProperties)880 VKAPI_ATTR VkResult VKAPI_CALL enumerateDeviceExtensionProperties (VkPhysicalDevice physicalDevice, const char* pLayerName, deUint32* pPropertyCount, VkExtensionProperties* pProperties)
881 {
882 DE_UNREF(physicalDevice);
883
884 static const VkExtensionProperties s_extensions[] =
885 {
886 { "VK_KHR_bind_memory2", 1u },
887 { "VK_KHR_external_memory", 1u },
888 { "VK_KHR_get_memory_requirements2", 1u },
889 { "VK_KHR_maintenance1", 1u },
890 { "VK_KHR_sampler_ycbcr_conversion", 1u },
891 #if defined(USE_ANDROID_O_HARDWARE_BUFFER)
892 { "VK_ANDROID_external_memory_android_hardware_buffer", 1u },
893 #endif
894 };
895
896 if (!pLayerName)
897 return enumerateExtensions((deUint32)DE_LENGTH_OF_ARRAY(s_extensions), s_extensions, pPropertyCount, pProperties);
898 else
899 return enumerateExtensions(0, DE_NULL, pPropertyCount, pProperties);
900 }
901
getPhysicalDeviceFeatures(VkPhysicalDevice physicalDevice,VkPhysicalDeviceFeatures * pFeatures)902 VKAPI_ATTR void VKAPI_CALL getPhysicalDeviceFeatures (VkPhysicalDevice physicalDevice, VkPhysicalDeviceFeatures* pFeatures)
903 {
904 DE_UNREF(physicalDevice);
905
906 // Enable all features allow as many tests to run as possible
907 pFeatures->robustBufferAccess = VK_TRUE;
908 pFeatures->fullDrawIndexUint32 = VK_TRUE;
909 pFeatures->imageCubeArray = VK_TRUE;
910 pFeatures->independentBlend = VK_TRUE;
911 pFeatures->geometryShader = VK_TRUE;
912 pFeatures->tessellationShader = VK_TRUE;
913 pFeatures->sampleRateShading = VK_TRUE;
914 pFeatures->dualSrcBlend = VK_TRUE;
915 pFeatures->logicOp = VK_TRUE;
916 pFeatures->multiDrawIndirect = VK_TRUE;
917 pFeatures->drawIndirectFirstInstance = VK_TRUE;
918 pFeatures->depthClamp = VK_TRUE;
919 pFeatures->depthBiasClamp = VK_TRUE;
920 pFeatures->fillModeNonSolid = VK_TRUE;
921 pFeatures->depthBounds = VK_TRUE;
922 pFeatures->wideLines = VK_TRUE;
923 pFeatures->largePoints = VK_TRUE;
924 pFeatures->alphaToOne = VK_TRUE;
925 pFeatures->multiViewport = VK_TRUE;
926 pFeatures->samplerAnisotropy = VK_TRUE;
927 pFeatures->textureCompressionETC2 = VK_TRUE;
928 pFeatures->textureCompressionASTC_LDR = VK_TRUE;
929 pFeatures->textureCompressionBC = VK_TRUE;
930 pFeatures->occlusionQueryPrecise = VK_TRUE;
931 pFeatures->pipelineStatisticsQuery = VK_TRUE;
932 pFeatures->vertexPipelineStoresAndAtomics = VK_TRUE;
933 pFeatures->fragmentStoresAndAtomics = VK_TRUE;
934 pFeatures->shaderTessellationAndGeometryPointSize = VK_TRUE;
935 pFeatures->shaderImageGatherExtended = VK_TRUE;
936 pFeatures->shaderStorageImageExtendedFormats = VK_TRUE;
937 pFeatures->shaderStorageImageMultisample = VK_TRUE;
938 pFeatures->shaderStorageImageReadWithoutFormat = VK_TRUE;
939 pFeatures->shaderStorageImageWriteWithoutFormat = VK_TRUE;
940 pFeatures->shaderUniformBufferArrayDynamicIndexing = VK_TRUE;
941 pFeatures->shaderSampledImageArrayDynamicIndexing = VK_TRUE;
942 pFeatures->shaderStorageBufferArrayDynamicIndexing = VK_TRUE;
943 pFeatures->shaderStorageImageArrayDynamicIndexing = VK_TRUE;
944 pFeatures->shaderClipDistance = VK_TRUE;
945 pFeatures->shaderCullDistance = VK_TRUE;
946 pFeatures->shaderFloat64 = VK_TRUE;
947 pFeatures->shaderInt64 = VK_TRUE;
948 pFeatures->shaderInt16 = VK_TRUE;
949 pFeatures->shaderResourceResidency = VK_TRUE;
950 pFeatures->shaderResourceMinLod = VK_TRUE;
951 pFeatures->sparseBinding = VK_TRUE;
952 pFeatures->sparseResidencyBuffer = VK_TRUE;
953 pFeatures->sparseResidencyImage2D = VK_TRUE;
954 pFeatures->sparseResidencyImage3D = VK_TRUE;
955 pFeatures->sparseResidency2Samples = VK_TRUE;
956 pFeatures->sparseResidency4Samples = VK_TRUE;
957 pFeatures->sparseResidency8Samples = VK_TRUE;
958 pFeatures->sparseResidency16Samples = VK_TRUE;
959 pFeatures->sparseResidencyAliased = VK_TRUE;
960 pFeatures->variableMultisampleRate = VK_TRUE;
961 pFeatures->inheritedQueries = VK_TRUE;
962 }
963
getPhysicalDeviceProperties(VkPhysicalDevice,VkPhysicalDeviceProperties * props)964 VKAPI_ATTR void VKAPI_CALL getPhysicalDeviceProperties (VkPhysicalDevice, VkPhysicalDeviceProperties* props)
965 {
966 deMemset(props, 0, sizeof(VkPhysicalDeviceProperties));
967
968 props->apiVersion = VK_API_VERSION_1_1;
969 props->driverVersion = 1u;
970 props->deviceType = VK_PHYSICAL_DEVICE_TYPE_OTHER;
971
972 deMemcpy(props->deviceName, "null", 5);
973
974 // Spec minmax
975 props->limits.maxImageDimension1D = 4096;
976 props->limits.maxImageDimension2D = 4096;
977 props->limits.maxImageDimension3D = 256;
978 props->limits.maxImageDimensionCube = 4096;
979 props->limits.maxImageArrayLayers = 256;
980 props->limits.maxTexelBufferElements = 65536;
981 props->limits.maxUniformBufferRange = 16384;
982 props->limits.maxStorageBufferRange = 1u<<27;
983 props->limits.maxPushConstantsSize = 128;
984 props->limits.maxMemoryAllocationCount = 4096;
985 props->limits.maxSamplerAllocationCount = 4000;
986 props->limits.bufferImageGranularity = 131072;
987 props->limits.sparseAddressSpaceSize = 1u<<31;
988 props->limits.maxBoundDescriptorSets = 4;
989 props->limits.maxPerStageDescriptorSamplers = 16;
990 props->limits.maxPerStageDescriptorUniformBuffers = 12;
991 props->limits.maxPerStageDescriptorStorageBuffers = 4;
992 props->limits.maxPerStageDescriptorSampledImages = 16;
993 props->limits.maxPerStageDescriptorStorageImages = 4;
994 props->limits.maxPerStageDescriptorInputAttachments = 4;
995 props->limits.maxPerStageResources = 128;
996 props->limits.maxDescriptorSetSamplers = 96;
997 props->limits.maxDescriptorSetUniformBuffers = 72;
998 props->limits.maxDescriptorSetUniformBuffersDynamic = 8;
999 props->limits.maxDescriptorSetStorageBuffers = 24;
1000 props->limits.maxDescriptorSetStorageBuffersDynamic = 4;
1001 props->limits.maxDescriptorSetSampledImages = 96;
1002 props->limits.maxDescriptorSetStorageImages = 24;
1003 props->limits.maxDescriptorSetInputAttachments = 4;
1004 props->limits.maxVertexInputAttributes = 16;
1005 props->limits.maxVertexInputBindings = 16;
1006 props->limits.maxVertexInputAttributeOffset = 2047;
1007 props->limits.maxVertexInputBindingStride = 2048;
1008 props->limits.maxVertexOutputComponents = 64;
1009 props->limits.maxTessellationGenerationLevel = 64;
1010 props->limits.maxTessellationPatchSize = 32;
1011 props->limits.maxTessellationControlPerVertexInputComponents = 64;
1012 props->limits.maxTessellationControlPerVertexOutputComponents = 64;
1013 props->limits.maxTessellationControlPerPatchOutputComponents = 120;
1014 props->limits.maxTessellationControlTotalOutputComponents = 2048;
1015 props->limits.maxTessellationEvaluationInputComponents = 64;
1016 props->limits.maxTessellationEvaluationOutputComponents = 64;
1017 props->limits.maxGeometryShaderInvocations = 32;
1018 props->limits.maxGeometryInputComponents = 64;
1019 props->limits.maxGeometryOutputComponents = 64;
1020 props->limits.maxGeometryOutputVertices = 256;
1021 props->limits.maxGeometryTotalOutputComponents = 1024;
1022 props->limits.maxFragmentInputComponents = 64;
1023 props->limits.maxFragmentOutputAttachments = 4;
1024 props->limits.maxFragmentDualSrcAttachments = 1;
1025 props->limits.maxFragmentCombinedOutputResources = 4;
1026 props->limits.maxComputeSharedMemorySize = 16384;
1027 props->limits.maxComputeWorkGroupCount[0] = 65535;
1028 props->limits.maxComputeWorkGroupCount[1] = 65535;
1029 props->limits.maxComputeWorkGroupCount[2] = 65535;
1030 props->limits.maxComputeWorkGroupInvocations = 128;
1031 props->limits.maxComputeWorkGroupSize[0] = 128;
1032 props->limits.maxComputeWorkGroupSize[1] = 128;
1033 props->limits.maxComputeWorkGroupSize[2] = 128;
1034 props->limits.subPixelPrecisionBits = 4;
1035 props->limits.subTexelPrecisionBits = 4;
1036 props->limits.mipmapPrecisionBits = 4;
1037 props->limits.maxDrawIndexedIndexValue = 0xffffffffu;
1038 props->limits.maxDrawIndirectCount = (1u<<16) - 1u;
1039 props->limits.maxSamplerLodBias = 2.0f;
1040 props->limits.maxSamplerAnisotropy = 16.0f;
1041 props->limits.maxViewports = 16;
1042 props->limits.maxViewportDimensions[0] = 4096;
1043 props->limits.maxViewportDimensions[1] = 4096;
1044 props->limits.viewportBoundsRange[0] = -8192.f;
1045 props->limits.viewportBoundsRange[1] = 8191.f;
1046 props->limits.viewportSubPixelBits = 0;
1047 props->limits.minMemoryMapAlignment = 64;
1048 props->limits.minTexelBufferOffsetAlignment = 256;
1049 props->limits.minUniformBufferOffsetAlignment = 256;
1050 props->limits.minStorageBufferOffsetAlignment = 256;
1051 props->limits.minTexelOffset = -8;
1052 props->limits.maxTexelOffset = 7;
1053 props->limits.minTexelGatherOffset = -8;
1054 props->limits.maxTexelGatherOffset = 7;
1055 props->limits.minInterpolationOffset = -0.5f;
1056 props->limits.maxInterpolationOffset = 0.5f; // -1ulp
1057 props->limits.subPixelInterpolationOffsetBits = 4;
1058 props->limits.maxFramebufferWidth = 4096;
1059 props->limits.maxFramebufferHeight = 4096;
1060 props->limits.maxFramebufferLayers = 256;
1061 props->limits.framebufferColorSampleCounts = VK_SAMPLE_COUNT_1_BIT|VK_SAMPLE_COUNT_4_BIT;
1062 props->limits.framebufferDepthSampleCounts = VK_SAMPLE_COUNT_1_BIT|VK_SAMPLE_COUNT_4_BIT;
1063 props->limits.framebufferStencilSampleCounts = VK_SAMPLE_COUNT_1_BIT|VK_SAMPLE_COUNT_4_BIT;
1064 props->limits.framebufferNoAttachmentsSampleCounts = VK_SAMPLE_COUNT_1_BIT|VK_SAMPLE_COUNT_4_BIT;
1065 props->limits.maxColorAttachments = 4;
1066 props->limits.sampledImageColorSampleCounts = VK_SAMPLE_COUNT_1_BIT|VK_SAMPLE_COUNT_4_BIT;
1067 props->limits.sampledImageIntegerSampleCounts = VK_SAMPLE_COUNT_1_BIT;
1068 props->limits.sampledImageDepthSampleCounts = VK_SAMPLE_COUNT_1_BIT|VK_SAMPLE_COUNT_4_BIT;
1069 props->limits.sampledImageStencilSampleCounts = VK_SAMPLE_COUNT_1_BIT|VK_SAMPLE_COUNT_4_BIT;
1070 props->limits.storageImageSampleCounts = VK_SAMPLE_COUNT_1_BIT|VK_SAMPLE_COUNT_4_BIT;
1071 props->limits.maxSampleMaskWords = 1;
1072 props->limits.timestampComputeAndGraphics = VK_TRUE;
1073 props->limits.timestampPeriod = 1.0f;
1074 props->limits.maxClipDistances = 8;
1075 props->limits.maxCullDistances = 8;
1076 props->limits.maxCombinedClipAndCullDistances = 8;
1077 props->limits.discreteQueuePriorities = 2;
1078 props->limits.pointSizeRange[0] = 1.0f;
1079 props->limits.pointSizeRange[1] = 64.0f; // -1ulp
1080 props->limits.lineWidthRange[0] = 1.0f;
1081 props->limits.lineWidthRange[1] = 8.0f; // -1ulp
1082 props->limits.pointSizeGranularity = 1.0f;
1083 props->limits.lineWidthGranularity = 1.0f;
1084 props->limits.strictLines = 0;
1085 props->limits.standardSampleLocations = VK_TRUE;
1086 props->limits.optimalBufferCopyOffsetAlignment = 256;
1087 props->limits.optimalBufferCopyRowPitchAlignment = 256;
1088 props->limits.nonCoherentAtomSize = 128;
1089 }
1090
getPhysicalDeviceQueueFamilyProperties(VkPhysicalDevice,deUint32 * count,VkQueueFamilyProperties * props)1091 VKAPI_ATTR void VKAPI_CALL getPhysicalDeviceQueueFamilyProperties (VkPhysicalDevice, deUint32* count, VkQueueFamilyProperties* props)
1092 {
1093 if (props && *count >= 1u)
1094 {
1095 deMemset(props, 0, sizeof(VkQueueFamilyProperties));
1096
1097 props->queueCount = 4u;
1098 props->queueFlags = VK_QUEUE_GRAPHICS_BIT|VK_QUEUE_COMPUTE_BIT;
1099 props->timestampValidBits = 64;
1100 }
1101
1102 *count = 1u;
1103 }
1104
getPhysicalDeviceMemoryProperties(VkPhysicalDevice,VkPhysicalDeviceMemoryProperties * props)1105 VKAPI_ATTR void VKAPI_CALL getPhysicalDeviceMemoryProperties (VkPhysicalDevice, VkPhysicalDeviceMemoryProperties* props)
1106 {
1107 deMemset(props, 0, sizeof(VkPhysicalDeviceMemoryProperties));
1108
1109 props->memoryTypeCount = 1u;
1110 props->memoryTypes[0].heapIndex = 0u;
1111 props->memoryTypes[0].propertyFlags = VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT
1112 | VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT
1113 | VK_MEMORY_PROPERTY_HOST_COHERENT_BIT;
1114
1115 props->memoryHeapCount = 1u;
1116 props->memoryHeaps[0].size = 1ull << 31;
1117 props->memoryHeaps[0].flags = 0u;
1118 }
1119
getPhysicalDeviceFormatProperties(VkPhysicalDevice,VkFormat format,VkFormatProperties * pFormatProperties)1120 VKAPI_ATTR void VKAPI_CALL getPhysicalDeviceFormatProperties (VkPhysicalDevice, VkFormat format, VkFormatProperties* pFormatProperties)
1121 {
1122 const VkFormatFeatureFlags allFeatures = VK_FORMAT_FEATURE_SAMPLED_IMAGE_BIT
1123 | VK_FORMAT_FEATURE_STORAGE_IMAGE_BIT
1124 | VK_FORMAT_FEATURE_STORAGE_IMAGE_ATOMIC_BIT
1125 | VK_FORMAT_FEATURE_UNIFORM_TEXEL_BUFFER_BIT
1126 | VK_FORMAT_FEATURE_STORAGE_TEXEL_BUFFER_BIT
1127 | VK_FORMAT_FEATURE_STORAGE_TEXEL_BUFFER_ATOMIC_BIT
1128 | VK_FORMAT_FEATURE_VERTEX_BUFFER_BIT
1129 | VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BIT
1130 | VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BLEND_BIT
1131 | VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT
1132 | VK_FORMAT_FEATURE_BLIT_SRC_BIT
1133 | VK_FORMAT_FEATURE_BLIT_DST_BIT
1134 | VK_FORMAT_FEATURE_SAMPLED_IMAGE_FILTER_LINEAR_BIT
1135 | VK_FORMAT_FEATURE_MIDPOINT_CHROMA_SAMPLES_BIT
1136 | VK_FORMAT_FEATURE_SAMPLED_IMAGE_YCBCR_CONVERSION_LINEAR_FILTER_BIT
1137 | VK_FORMAT_FEATURE_SAMPLED_IMAGE_YCBCR_CONVERSION_SEPARATE_RECONSTRUCTION_FILTER_BIT
1138 | VK_FORMAT_FEATURE_SAMPLED_IMAGE_YCBCR_CONVERSION_CHROMA_RECONSTRUCTION_EXPLICIT_BIT
1139 | VK_FORMAT_FEATURE_SAMPLED_IMAGE_YCBCR_CONVERSION_CHROMA_RECONSTRUCTION_EXPLICIT_FORCEABLE_BIT
1140 | VK_FORMAT_FEATURE_COSITED_CHROMA_SAMPLES_BIT;
1141
1142 pFormatProperties->linearTilingFeatures = allFeatures;
1143 pFormatProperties->optimalTilingFeatures = allFeatures;
1144 pFormatProperties->bufferFeatures = allFeatures;
1145
1146 if (isYCbCrFormat(format) && getPlaneCount(format) > 1)
1147 pFormatProperties->optimalTilingFeatures |= VK_FORMAT_FEATURE_DISJOINT_BIT;
1148 }
1149
getPhysicalDeviceImageFormatProperties(VkPhysicalDevice physicalDevice,VkFormat format,VkImageType type,VkImageTiling tiling,VkImageUsageFlags usage,VkImageCreateFlags flags,VkImageFormatProperties * pImageFormatProperties)1150 VKAPI_ATTR VkResult VKAPI_CALL getPhysicalDeviceImageFormatProperties (VkPhysicalDevice physicalDevice, VkFormat format, VkImageType type, VkImageTiling tiling, VkImageUsageFlags usage, VkImageCreateFlags flags, VkImageFormatProperties* pImageFormatProperties)
1151 {
1152 DE_UNREF(physicalDevice);
1153 DE_UNREF(format);
1154 DE_UNREF(type);
1155 DE_UNREF(tiling);
1156 DE_UNREF(usage);
1157 DE_UNREF(flags);
1158
1159 pImageFormatProperties->maxArrayLayers = 8;
1160 pImageFormatProperties->maxExtent.width = 4096;
1161 pImageFormatProperties->maxExtent.height = 4096;
1162 pImageFormatProperties->maxExtent.depth = 4096;
1163 pImageFormatProperties->maxMipLevels = deLog2Ceil32(4096) + 1;
1164 pImageFormatProperties->maxResourceSize = 64u * 1024u * 1024u;
1165 pImageFormatProperties->sampleCounts = VK_SAMPLE_COUNT_1_BIT|VK_SAMPLE_COUNT_4_BIT;
1166
1167 return VK_SUCCESS;
1168 }
1169
getDeviceQueue(VkDevice device,deUint32 queueFamilyIndex,deUint32 queueIndex,VkQueue * pQueue)1170 VKAPI_ATTR void VKAPI_CALL getDeviceQueue (VkDevice device, deUint32 queueFamilyIndex, deUint32 queueIndex, VkQueue* pQueue)
1171 {
1172 DE_UNREF(device);
1173 DE_UNREF(queueFamilyIndex);
1174
1175 if (pQueue)
1176 *pQueue = reinterpret_cast<VkQueue>((deUint64)queueIndex + 1);
1177 }
1178
getBufferMemoryRequirements(VkDevice,VkBuffer bufferHandle,VkMemoryRequirements * requirements)1179 VKAPI_ATTR void VKAPI_CALL getBufferMemoryRequirements (VkDevice, VkBuffer bufferHandle, VkMemoryRequirements* requirements)
1180 {
1181 const Buffer* buffer = reinterpret_cast<const Buffer*>(bufferHandle.getInternal());
1182
1183 requirements->memoryTypeBits = 1u;
1184 requirements->size = buffer->getSize();
1185 requirements->alignment = (VkDeviceSize)1u;
1186 }
1187
getPackedImageDataSize(VkFormat format,VkExtent3D extent,VkSampleCountFlagBits samples)1188 VkDeviceSize getPackedImageDataSize (VkFormat format, VkExtent3D extent, VkSampleCountFlagBits samples)
1189 {
1190 return (VkDeviceSize)getPixelSize(mapVkFormat(format))
1191 * (VkDeviceSize)extent.width
1192 * (VkDeviceSize)extent.height
1193 * (VkDeviceSize)extent.depth
1194 * (VkDeviceSize)samples;
1195 }
1196
getCompressedImageDataSize(VkFormat format,VkExtent3D extent)1197 VkDeviceSize getCompressedImageDataSize (VkFormat format, VkExtent3D extent)
1198 {
1199 try
1200 {
1201 const tcu::CompressedTexFormat tcuFormat = mapVkCompressedFormat(format);
1202 const size_t blockSize = tcu::getBlockSize(tcuFormat);
1203 const tcu::IVec3 blockPixelSize = tcu::getBlockPixelSize(tcuFormat);
1204 const int numBlocksX = deDivRoundUp32((int)extent.width, blockPixelSize.x());
1205 const int numBlocksY = deDivRoundUp32((int)extent.height, blockPixelSize.y());
1206 const int numBlocksZ = deDivRoundUp32((int)extent.depth, blockPixelSize.z());
1207
1208 return blockSize*numBlocksX*numBlocksY*numBlocksZ;
1209 }
1210 catch (...)
1211 {
1212 return 0; // Unsupported compressed format
1213 }
1214 }
1215
getYCbCrImageDataSize(VkFormat format,VkExtent3D extent)1216 VkDeviceSize getYCbCrImageDataSize (VkFormat format, VkExtent3D extent)
1217 {
1218 const PlanarFormatDescription desc = getPlanarFormatDescription(format);
1219 VkDeviceSize totalSize = 0;
1220
1221 DE_ASSERT(extent.depth == 1);
1222
1223 for (deUint32 planeNdx = 0; planeNdx < desc.numPlanes; ++planeNdx)
1224 {
1225 const deUint32 elementSize = desc.planes[planeNdx].elementSizeBytes;
1226
1227 totalSize = (VkDeviceSize)deAlign64((deInt64)totalSize, elementSize);
1228 totalSize += getPlaneSizeInBytes(desc, extent, planeNdx, 0, BUFFER_IMAGE_COPY_OFFSET_GRANULARITY);
1229 }
1230
1231 return totalSize;
1232 }
1233
getImageMemoryRequirements(VkDevice,VkImage imageHandle,VkMemoryRequirements * requirements)1234 VKAPI_ATTR void VKAPI_CALL getImageMemoryRequirements (VkDevice, VkImage imageHandle, VkMemoryRequirements* requirements)
1235 {
1236 const Image* image = reinterpret_cast<const Image*>(imageHandle.getInternal());
1237
1238 requirements->memoryTypeBits = 1u;
1239 requirements->alignment = 16u;
1240
1241 if (isCompressedFormat(image->getFormat()))
1242 requirements->size = getCompressedImageDataSize(image->getFormat(), image->getExtent());
1243 else if (isYCbCrFormat(image->getFormat()))
1244 requirements->size = getYCbCrImageDataSize(image->getFormat(), image->getExtent());
1245 else
1246 requirements->size = getPackedImageDataSize(image->getFormat(), image->getExtent(), image->getSamples());
1247 }
1248
allocateMemory(VkDevice device,const VkMemoryAllocateInfo * pAllocateInfo,const VkAllocationCallbacks * pAllocator,VkDeviceMemory * pMemory)1249 VKAPI_ATTR VkResult VKAPI_CALL allocateMemory (VkDevice device, const VkMemoryAllocateInfo* pAllocateInfo, const VkAllocationCallbacks* pAllocator, VkDeviceMemory* pMemory)
1250 {
1251 const VkExportMemoryAllocateInfo* const exportInfo = findStructure<VkExportMemoryAllocateInfo>(pAllocateInfo->pNext);
1252 const VkImportAndroidHardwareBufferInfoANDROID* const importInfo = findStructure<VkImportAndroidHardwareBufferInfoANDROID>(pAllocateInfo->pNext);
1253
1254 if ((exportInfo && (exportInfo->handleTypes & VK_EXTERNAL_MEMORY_HANDLE_TYPE_ANDROID_HARDWARE_BUFFER_BIT_ANDROID) != 0)
1255 || (importInfo && importInfo->buffer.internal))
1256 {
1257 #if defined(USE_ANDROID_O_HARDWARE_BUFFER)
1258 VK_NULL_RETURN((*pMemory = allocateNonDispHandle<ExternalDeviceMemoryAndroid, DeviceMemory, VkDeviceMemory>(device, pAllocateInfo, pAllocator)));
1259 #else
1260 return VK_ERROR_INVALID_EXTERNAL_HANDLE;
1261 #endif
1262 }
1263 else
1264 {
1265 VK_NULL_RETURN((*pMemory = allocateNonDispHandle<PrivateDeviceMemory, DeviceMemory, VkDeviceMemory>(device, pAllocateInfo, pAllocator)));
1266 }
1267 }
1268
mapMemory(VkDevice,VkDeviceMemory memHandle,VkDeviceSize offset,VkDeviceSize size,VkMemoryMapFlags flags,void ** ppData)1269 VKAPI_ATTR VkResult VKAPI_CALL mapMemory (VkDevice, VkDeviceMemory memHandle, VkDeviceSize offset, VkDeviceSize size, VkMemoryMapFlags flags, void** ppData)
1270 {
1271 DeviceMemory* const memory = reinterpret_cast<DeviceMemory*>(memHandle.getInternal());
1272
1273 DE_UNREF(size);
1274 DE_UNREF(flags);
1275
1276 *ppData = (deUint8*)memory->map() + offset;
1277
1278 return VK_SUCCESS;
1279 }
1280
unmapMemory(VkDevice device,VkDeviceMemory memHandle)1281 VKAPI_ATTR void VKAPI_CALL unmapMemory (VkDevice device, VkDeviceMemory memHandle)
1282 {
1283 DeviceMemory* const memory = reinterpret_cast<DeviceMemory*>(memHandle.getInternal());
1284
1285 DE_UNREF(device);
1286
1287 memory->unmap();
1288 }
1289
getMemoryAndroidHardwareBufferANDROID(VkDevice device,const VkMemoryGetAndroidHardwareBufferInfoANDROID * pInfo,pt::AndroidHardwareBufferPtr * pBuffer)1290 VKAPI_ATTR VkResult VKAPI_CALL getMemoryAndroidHardwareBufferANDROID (VkDevice device, const VkMemoryGetAndroidHardwareBufferInfoANDROID* pInfo, pt::AndroidHardwareBufferPtr* pBuffer)
1291 {
1292 DE_UNREF(device);
1293
1294 #if defined(USE_ANDROID_O_HARDWARE_BUFFER)
1295 DeviceMemory* const memory = reinterpret_cast<ExternalDeviceMemoryAndroid*>(pInfo->memory.getInternal());
1296 ExternalDeviceMemoryAndroid* const androidMemory = static_cast<ExternalDeviceMemoryAndroid*>(memory);
1297
1298 AHardwareBuffer* hwbuffer = androidMemory->getHwBuffer();
1299 AHardwareBuffer_acquire(hwbuffer);
1300 pBuffer->internal = hwbuffer;
1301 #else
1302 DE_UNREF(pInfo);
1303 DE_UNREF(pBuffer);
1304 #endif
1305
1306 return VK_SUCCESS;
1307 }
1308
allocateDescriptorSets(VkDevice,const VkDescriptorSetAllocateInfo * pAllocateInfo,VkDescriptorSet * pDescriptorSets)1309 VKAPI_ATTR VkResult VKAPI_CALL allocateDescriptorSets (VkDevice, const VkDescriptorSetAllocateInfo* pAllocateInfo, VkDescriptorSet* pDescriptorSets)
1310 {
1311 DescriptorPool* const poolImpl = reinterpret_cast<DescriptorPool*>((deUintptr)pAllocateInfo->descriptorPool.getInternal());
1312
1313 for (deUint32 ndx = 0; ndx < pAllocateInfo->descriptorSetCount; ++ndx)
1314 {
1315 try
1316 {
1317 pDescriptorSets[ndx] = poolImpl->allocate(pAllocateInfo->pSetLayouts[ndx]);
1318 }
1319 catch (const std::bad_alloc&)
1320 {
1321 for (deUint32 freeNdx = 0; freeNdx < ndx; freeNdx++)
1322 delete reinterpret_cast<DescriptorSet*>((deUintptr)pDescriptorSets[freeNdx].getInternal());
1323
1324 return VK_ERROR_OUT_OF_HOST_MEMORY;
1325 }
1326 catch (VkResult res)
1327 {
1328 for (deUint32 freeNdx = 0; freeNdx < ndx; freeNdx++)
1329 delete reinterpret_cast<DescriptorSet*>((deUintptr)pDescriptorSets[freeNdx].getInternal());
1330
1331 return res;
1332 }
1333 }
1334
1335 return VK_SUCCESS;
1336 }
1337
freeDescriptorSets(VkDevice,VkDescriptorPool descriptorPool,deUint32 count,const VkDescriptorSet * pDescriptorSets)1338 VKAPI_ATTR void VKAPI_CALL freeDescriptorSets (VkDevice, VkDescriptorPool descriptorPool, deUint32 count, const VkDescriptorSet* pDescriptorSets)
1339 {
1340 DescriptorPool* const poolImpl = reinterpret_cast<DescriptorPool*>((deUintptr)descriptorPool.getInternal());
1341
1342 for (deUint32 ndx = 0; ndx < count; ++ndx)
1343 poolImpl->free(pDescriptorSets[ndx]);
1344 }
1345
resetDescriptorPool(VkDevice,VkDescriptorPool descriptorPool,VkDescriptorPoolResetFlags)1346 VKAPI_ATTR VkResult VKAPI_CALL resetDescriptorPool (VkDevice, VkDescriptorPool descriptorPool, VkDescriptorPoolResetFlags)
1347 {
1348 DescriptorPool* const poolImpl = reinterpret_cast<DescriptorPool*>((deUintptr)descriptorPool.getInternal());
1349
1350 poolImpl->reset();
1351
1352 return VK_SUCCESS;
1353 }
1354
allocateCommandBuffers(VkDevice device,const VkCommandBufferAllocateInfo * pAllocateInfo,VkCommandBuffer * pCommandBuffers)1355 VKAPI_ATTR VkResult VKAPI_CALL allocateCommandBuffers (VkDevice device, const VkCommandBufferAllocateInfo* pAllocateInfo, VkCommandBuffer* pCommandBuffers)
1356 {
1357 DE_UNREF(device);
1358
1359 if (pAllocateInfo && pCommandBuffers)
1360 {
1361 CommandPool* const poolImpl = reinterpret_cast<CommandPool*>((deUintptr)pAllocateInfo->commandPool.getInternal());
1362
1363 for (deUint32 ndx = 0; ndx < pAllocateInfo->commandBufferCount; ++ndx)
1364 pCommandBuffers[ndx] = poolImpl->allocate(pAllocateInfo->level);
1365 }
1366
1367 return VK_SUCCESS;
1368 }
1369
freeCommandBuffers(VkDevice device,VkCommandPool commandPool,deUint32 commandBufferCount,const VkCommandBuffer * pCommandBuffers)1370 VKAPI_ATTR void VKAPI_CALL freeCommandBuffers (VkDevice device, VkCommandPool commandPool, deUint32 commandBufferCount, const VkCommandBuffer* pCommandBuffers)
1371 {
1372 CommandPool* const poolImpl = reinterpret_cast<CommandPool*>((deUintptr)commandPool.getInternal());
1373
1374 DE_UNREF(device);
1375
1376 for (deUint32 ndx = 0; ndx < commandBufferCount; ++ndx)
1377 poolImpl->free(pCommandBuffers[ndx]);
1378 }
1379
1380
createDisplayModeKHR(VkPhysicalDevice,VkDisplayKHR display,const VkDisplayModeCreateInfoKHR * pCreateInfo,const VkAllocationCallbacks * pAllocator,VkDisplayModeKHR * pMode)1381 VKAPI_ATTR VkResult VKAPI_CALL createDisplayModeKHR (VkPhysicalDevice, VkDisplayKHR display, const VkDisplayModeCreateInfoKHR* pCreateInfo, const VkAllocationCallbacks* pAllocator, VkDisplayModeKHR* pMode)
1382 {
1383 DE_UNREF(pAllocator);
1384 VK_NULL_RETURN((*pMode = allocateNonDispHandle<DisplayModeKHR, VkDisplayModeKHR>(display, pCreateInfo, pAllocator)));
1385 }
1386
createSharedSwapchainsKHR(VkDevice device,deUint32 swapchainCount,const VkSwapchainCreateInfoKHR * pCreateInfos,const VkAllocationCallbacks * pAllocator,VkSwapchainKHR * pSwapchains)1387 VKAPI_ATTR VkResult VKAPI_CALL createSharedSwapchainsKHR (VkDevice device, deUint32 swapchainCount, const VkSwapchainCreateInfoKHR* pCreateInfos, const VkAllocationCallbacks* pAllocator, VkSwapchainKHR* pSwapchains)
1388 {
1389 for (deUint32 ndx = 0; ndx < swapchainCount; ++ndx)
1390 {
1391 pSwapchains[ndx] = allocateNonDispHandle<SwapchainKHR, VkSwapchainKHR>(device, pCreateInfos+ndx, pAllocator);
1392 }
1393
1394 return VK_SUCCESS;
1395 }
1396
getPhysicalDeviceExternalBufferPropertiesKHR(VkPhysicalDevice physicalDevice,const VkPhysicalDeviceExternalBufferInfo * pExternalBufferInfo,VkExternalBufferProperties * pExternalBufferProperties)1397 VKAPI_ATTR void VKAPI_CALL getPhysicalDeviceExternalBufferPropertiesKHR (VkPhysicalDevice physicalDevice, const VkPhysicalDeviceExternalBufferInfo* pExternalBufferInfo, VkExternalBufferProperties* pExternalBufferProperties)
1398 {
1399 DE_UNREF(physicalDevice);
1400 DE_UNREF(pExternalBufferInfo);
1401
1402 pExternalBufferProperties->externalMemoryProperties.externalMemoryFeatures = 0;
1403 pExternalBufferProperties->externalMemoryProperties.exportFromImportedHandleTypes = 0;
1404 pExternalBufferProperties->externalMemoryProperties.compatibleHandleTypes = 0;
1405
1406 if (pExternalBufferInfo->handleType == VK_EXTERNAL_MEMORY_HANDLE_TYPE_ANDROID_HARDWARE_BUFFER_BIT_ANDROID)
1407 {
1408 pExternalBufferProperties->externalMemoryProperties.externalMemoryFeatures = VK_EXTERNAL_MEMORY_FEATURE_EXPORTABLE_BIT | VK_EXTERNAL_MEMORY_FEATURE_IMPORTABLE_BIT;
1409 pExternalBufferProperties->externalMemoryProperties.exportFromImportedHandleTypes = VK_EXTERNAL_MEMORY_HANDLE_TYPE_ANDROID_HARDWARE_BUFFER_BIT_ANDROID;
1410 pExternalBufferProperties->externalMemoryProperties.compatibleHandleTypes = VK_EXTERNAL_MEMORY_HANDLE_TYPE_ANDROID_HARDWARE_BUFFER_BIT_ANDROID;
1411 }
1412 }
1413
getPhysicalDeviceImageFormatProperties2KHR(VkPhysicalDevice physicalDevice,const VkPhysicalDeviceImageFormatInfo2 * pImageFormatInfo,VkImageFormatProperties2 * pImageFormatProperties)1414 VKAPI_ATTR VkResult VKAPI_CALL getPhysicalDeviceImageFormatProperties2KHR (VkPhysicalDevice physicalDevice, const VkPhysicalDeviceImageFormatInfo2* pImageFormatInfo, VkImageFormatProperties2* pImageFormatProperties)
1415 {
1416 const VkPhysicalDeviceExternalImageFormatInfo* const externalInfo = findStructure<VkPhysicalDeviceExternalImageFormatInfo>(pImageFormatInfo->pNext);
1417 VkExternalImageFormatProperties* const externalProperties = findStructure<VkExternalImageFormatProperties>(pImageFormatProperties->pNext);
1418 VkResult result;
1419
1420 result = getPhysicalDeviceImageFormatProperties(physicalDevice, pImageFormatInfo->format, pImageFormatInfo->type, pImageFormatInfo->tiling, pImageFormatInfo->usage, pImageFormatInfo->flags, &pImageFormatProperties->imageFormatProperties);
1421 if (result != VK_SUCCESS)
1422 return result;
1423
1424 if (externalInfo && externalInfo->handleType != 0)
1425 {
1426 if (externalInfo->handleType != VK_EXTERNAL_MEMORY_HANDLE_TYPE_ANDROID_HARDWARE_BUFFER_BIT_ANDROID)
1427 return VK_ERROR_FORMAT_NOT_SUPPORTED;
1428
1429 if (!(pImageFormatInfo->format == VK_FORMAT_R8G8B8A8_UNORM
1430 || pImageFormatInfo->format == VK_FORMAT_R8G8B8_UNORM
1431 || pImageFormatInfo->format == VK_FORMAT_R5G6B5_UNORM_PACK16
1432 || pImageFormatInfo->format == VK_FORMAT_R16G16B16A16_SFLOAT
1433 || pImageFormatInfo->format == VK_FORMAT_A2R10G10B10_UNORM_PACK32))
1434 {
1435 return VK_ERROR_FORMAT_NOT_SUPPORTED;
1436 }
1437
1438 if (pImageFormatInfo->type != VK_IMAGE_TYPE_2D)
1439 return VK_ERROR_FORMAT_NOT_SUPPORTED;
1440
1441 if ((pImageFormatInfo->usage & ~(VK_IMAGE_USAGE_TRANSFER_SRC_BIT
1442 | VK_IMAGE_USAGE_TRANSFER_DST_BIT
1443 | VK_IMAGE_USAGE_SAMPLED_BIT
1444 | VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT))
1445 != 0)
1446 {
1447 return VK_ERROR_FORMAT_NOT_SUPPORTED;
1448 }
1449
1450 if ((pImageFormatInfo->flags & ~(VK_IMAGE_CREATE_MUTABLE_FORMAT_BIT
1451 /*| VK_IMAGE_CREATE_PROTECTED_BIT*/
1452 /*| VK_IMAGE_CREATE_EXTENDED_USAGE_BIT*/))
1453 != 0)
1454 {
1455 return VK_ERROR_FORMAT_NOT_SUPPORTED;
1456 }
1457
1458 if (externalProperties)
1459 {
1460 externalProperties->externalMemoryProperties.externalMemoryFeatures = VK_EXTERNAL_MEMORY_FEATURE_DEDICATED_ONLY_BIT
1461 | VK_EXTERNAL_MEMORY_FEATURE_EXPORTABLE_BIT
1462 | VK_EXTERNAL_MEMORY_FEATURE_IMPORTABLE_BIT;
1463 externalProperties->externalMemoryProperties.exportFromImportedHandleTypes = VK_EXTERNAL_MEMORY_HANDLE_TYPE_ANDROID_HARDWARE_BUFFER_BIT_ANDROID;
1464 externalProperties->externalMemoryProperties.compatibleHandleTypes = VK_EXTERNAL_MEMORY_HANDLE_TYPE_ANDROID_HARDWARE_BUFFER_BIT_ANDROID;
1465 }
1466 }
1467
1468 return VK_SUCCESS;
1469 }
1470
1471 // \note getInstanceProcAddr is a little bit special:
1472 // vkNullDriverImpl.inl needs it to define s_platformFunctions but
1473 // getInstanceProcAddr() implementation needs other entry points from
1474 // vkNullDriverImpl.inl.
1475 VKAPI_ATTR PFN_vkVoidFunction VKAPI_CALL getInstanceProcAddr (VkInstance instance, const char* pName);
1476
1477 #include "vkNullDriverImpl.inl"
1478
getInstanceProcAddr(VkInstance instance,const char * pName)1479 VKAPI_ATTR PFN_vkVoidFunction VKAPI_CALL getInstanceProcAddr (VkInstance instance, const char* pName)
1480 {
1481 if (instance)
1482 {
1483 return reinterpret_cast<Instance*>(instance)->getProcAddr(pName);
1484 }
1485 else
1486 {
1487 const std::string name = pName;
1488
1489 if (name == "vkCreateInstance")
1490 return (PFN_vkVoidFunction)createInstance;
1491 else if (name == "vkEnumerateInstanceExtensionProperties")
1492 return (PFN_vkVoidFunction)enumerateInstanceExtensionProperties;
1493 else if (name == "vkEnumerateInstanceLayerProperties")
1494 return (PFN_vkVoidFunction)enumerateInstanceLayerProperties;
1495 else
1496 return (PFN_vkVoidFunction)DE_NULL;
1497 }
1498 }
1499
1500 } // extern "C"
1501
Instance(const VkInstanceCreateInfo *)1502 Instance::Instance (const VkInstanceCreateInfo*)
1503 : m_functions(s_instanceFunctions, DE_LENGTH_OF_ARRAY(s_instanceFunctions))
1504 {
1505 }
1506
Device(VkPhysicalDevice,const VkDeviceCreateInfo *)1507 Device::Device (VkPhysicalDevice, const VkDeviceCreateInfo*)
1508 : m_functions(s_deviceFunctions, DE_LENGTH_OF_ARRAY(s_deviceFunctions))
1509 {
1510 }
1511
1512 class NullDriverLibrary : public Library
1513 {
1514 public:
NullDriverLibrary(void)1515 NullDriverLibrary (void)
1516 : m_library (s_platformFunctions, DE_LENGTH_OF_ARRAY(s_platformFunctions))
1517 , m_driver (m_library)
1518 {}
1519
getPlatformInterface(void) const1520 const PlatformInterface& getPlatformInterface (void) const { return m_driver; }
getFunctionLibrary(void) const1521 const tcu::FunctionLibrary& getFunctionLibrary (void) const { return m_library; }
1522 private:
1523 const tcu::StaticFunctionLibrary m_library;
1524 const PlatformDriver m_driver;
1525 };
1526
1527 } // anonymous
1528
createNullDriver(void)1529 Library* createNullDriver (void)
1530 {
1531 return new NullDriverLibrary();
1532 }
1533
1534 } // vk
1535