extension_manual.c 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315
  1. /*
  2. * Copyright (c) 2015-2017 The Khronos Group Inc.
  3. * Copyright (c) 2015-2017 Valve Corporation
  4. * Copyright (c) 2015-2017 LunarG, Inc.
  5. *
  6. * Licensed under the Apache License, Version 2.0 (the "License");
  7. * you may not use this file except in compliance with the License.
  8. * You may obtain a copy of the License at
  9. *
  10. * http://www.apache.org/licenses/LICENSE-2.0
  11. *
  12. * Unless required by applicable law or agreed to in writing, software
  13. * distributed under the License is distributed on an "AS IS" BASIS,
  14. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  15. * See the License for the specific language governing permissions and
  16. * limitations under the License.
  17. *
  18. * Author: Mark Young <[email protected]>
  19. * Author: Lenny Komow <[email protected]>
  20. */
  21. #ifndef _GNU_SOURCE
  22. #define _GNU_SOURCE
  23. #endif
  24. #include <stdio.h>
  25. #include <stdlib.h>
  26. #include <string.h>
  27. #include "vk_loader_platform.h"
  28. #include "loader.h"
  29. #include "vk_loader_extensions.h"
  30. #include <vulkan/vk_icd.h>
  31. #include "wsi.h"
  32. #include "debug_utils.h"
  33. // ---- Manually added trampoline/terminator functions
  34. // These functions, for whatever reason, require more complex changes than
  35. // can easily be automatically generated.
  36. // ---- VK_NV_external_memory_capabilities extension trampoline/terminators
  37. VKAPI_ATTR VkResult VKAPI_CALL
  38. GetPhysicalDeviceExternalImageFormatPropertiesNV(
  39. VkPhysicalDevice physicalDevice, VkFormat format, VkImageType type,
  40. VkImageTiling tiling, VkImageUsageFlags usage, VkImageCreateFlags flags,
  41. VkExternalMemoryHandleTypeFlagsNV externalHandleType,
  42. VkExternalImageFormatPropertiesNV *pExternalImageFormatProperties) {
  43. const VkLayerInstanceDispatchTable *disp;
  44. VkPhysicalDevice unwrapped_phys_dev = loader_unwrap_physical_device(physicalDevice);
  45. disp = loader_get_instance_layer_dispatch(physicalDevice);
  46. return disp->GetPhysicalDeviceExternalImageFormatPropertiesNV(
  47. unwrapped_phys_dev, format, type, tiling, usage, flags,
  48. externalHandleType, pExternalImageFormatProperties);
  49. }
  50. VKAPI_ATTR VkResult VKAPI_CALL
  51. terminator_GetPhysicalDeviceExternalImageFormatPropertiesNV(
  52. VkPhysicalDevice physicalDevice, VkFormat format, VkImageType type,
  53. VkImageTiling tiling, VkImageUsageFlags usage, VkImageCreateFlags flags,
  54. VkExternalMemoryHandleTypeFlagsNV externalHandleType,
  55. VkExternalImageFormatPropertiesNV *pExternalImageFormatProperties) {
  56. struct loader_physical_device_term *phys_dev_term =
  57. (struct loader_physical_device_term *)physicalDevice;
  58. struct loader_icd_term *icd_term = phys_dev_term->this_icd_term;
  59. if (!icd_term->dispatch.GetPhysicalDeviceExternalImageFormatPropertiesNV) {
  60. if (externalHandleType) {
  61. return VK_ERROR_FORMAT_NOT_SUPPORTED;
  62. }
  63. if (!icd_term->dispatch.GetPhysicalDeviceImageFormatProperties) {
  64. return VK_ERROR_INITIALIZATION_FAILED;
  65. }
  66. pExternalImageFormatProperties->externalMemoryFeatures = 0;
  67. pExternalImageFormatProperties->exportFromImportedHandleTypes = 0;
  68. pExternalImageFormatProperties->compatibleHandleTypes = 0;
  69. return icd_term->dispatch.GetPhysicalDeviceImageFormatProperties(
  70. phys_dev_term->phys_dev, format, type, tiling, usage, flags,
  71. &pExternalImageFormatProperties->imageFormatProperties);
  72. }
  73. return icd_term->dispatch.GetPhysicalDeviceExternalImageFormatPropertiesNV(
  74. phys_dev_term->phys_dev, format, type, tiling, usage, flags,
  75. externalHandleType, pExternalImageFormatProperties);
  76. }
  77. // ---- VK_EXT_display_surface_counter extension trampoline/terminators
  78. VKAPI_ATTR VkResult VKAPI_CALL GetPhysicalDeviceSurfaceCapabilities2EXT(VkPhysicalDevice physicalDevice, VkSurfaceKHR surface,
  79. VkSurfaceCapabilities2EXT *pSurfaceCapabilities) {
  80. const VkLayerInstanceDispatchTable *disp;
  81. VkPhysicalDevice unwrapped_phys_dev = loader_unwrap_physical_device(physicalDevice);
  82. disp = loader_get_instance_layer_dispatch(physicalDevice);
  83. return disp->GetPhysicalDeviceSurfaceCapabilities2EXT(unwrapped_phys_dev, surface, pSurfaceCapabilities);
  84. }
  85. VKAPI_ATTR VkResult VKAPI_CALL terminator_GetPhysicalDeviceSurfaceCapabilities2EXT(
  86. VkPhysicalDevice physicalDevice, VkSurfaceKHR surface, VkSurfaceCapabilities2EXT *pSurfaceCapabilities) {
  87. struct loader_physical_device_term *phys_dev_term = (struct loader_physical_device_term *)physicalDevice;
  88. struct loader_icd_term *icd_term = phys_dev_term->this_icd_term;
  89. VkIcdSurface *icd_surface = (VkIcdSurface *)(surface);
  90. uint8_t icd_index = phys_dev_term->icd_index;
  91. // Unwrap the surface if needed
  92. VkSurfaceKHR unwrapped_surface = surface;
  93. if (icd_surface->real_icd_surfaces != NULL && (void *)icd_surface->real_icd_surfaces[icd_index] != NULL) {
  94. unwrapped_surface = icd_surface->real_icd_surfaces[icd_index];
  95. }
  96. if (icd_term->dispatch.GetPhysicalDeviceSurfaceCapabilities2EXT != NULL) {
  97. // Pass the call to the driver
  98. return icd_term->dispatch.GetPhysicalDeviceSurfaceCapabilities2EXT(phys_dev_term->phys_dev, unwrapped_surface,
  99. pSurfaceCapabilities);
  100. } else {
  101. // Emulate the call
  102. loader_log(icd_term->this_instance, VK_DEBUG_REPORT_INFORMATION_BIT_EXT, 0,
  103. "vkGetPhysicalDeviceSurfaceCapabilities2EXT: Emulating call in ICD \"%s\" using "
  104. "vkGetPhysicalDeviceSurfaceCapabilitiesKHR",
  105. icd_term->scanned_icd->lib_name);
  106. VkSurfaceCapabilitiesKHR surface_caps;
  107. VkResult res =
  108. icd_term->dispatch.GetPhysicalDeviceSurfaceCapabilitiesKHR(phys_dev_term->phys_dev, unwrapped_surface, &surface_caps);
  109. pSurfaceCapabilities->minImageCount = surface_caps.minImageCount;
  110. pSurfaceCapabilities->maxImageCount = surface_caps.maxImageCount;
  111. pSurfaceCapabilities->currentExtent = surface_caps.currentExtent;
  112. pSurfaceCapabilities->minImageExtent = surface_caps.minImageExtent;
  113. pSurfaceCapabilities->maxImageExtent = surface_caps.maxImageExtent;
  114. pSurfaceCapabilities->maxImageArrayLayers = surface_caps.maxImageArrayLayers;
  115. pSurfaceCapabilities->supportedTransforms = surface_caps.supportedTransforms;
  116. pSurfaceCapabilities->currentTransform = surface_caps.currentTransform;
  117. pSurfaceCapabilities->supportedCompositeAlpha = surface_caps.supportedCompositeAlpha;
  118. pSurfaceCapabilities->supportedUsageFlags = surface_caps.supportedUsageFlags;
  119. pSurfaceCapabilities->supportedSurfaceCounters = 0;
  120. if (pSurfaceCapabilities->pNext != NULL) {
  121. loader_log(icd_term->this_instance, VK_DEBUG_REPORT_WARNING_BIT_EXT, 0,
  122. "vkGetPhysicalDeviceSurfaceCapabilities2EXT: Emulation found unrecognized structure type in "
  123. "pSurfaceCapabilities->pNext - this struct will be ignored");
  124. }
  125. return res;
  126. }
  127. }
  128. // ---- VK_EXT_direct_mode_display extension trampoline/terminators
  129. VKAPI_ATTR VkResult VKAPI_CALL ReleaseDisplayEXT(VkPhysicalDevice physicalDevice, VkDisplayKHR display) {
  130. const VkLayerInstanceDispatchTable *disp;
  131. VkPhysicalDevice unwrapped_phys_dev = loader_unwrap_physical_device(physicalDevice);
  132. disp = loader_get_instance_layer_dispatch(physicalDevice);
  133. return disp->ReleaseDisplayEXT(unwrapped_phys_dev, display);
  134. }
  135. VKAPI_ATTR VkResult VKAPI_CALL terminator_ReleaseDisplayEXT(VkPhysicalDevice physicalDevice, VkDisplayKHR display) {
  136. struct loader_physical_device_term *phys_dev_term = (struct loader_physical_device_term *)physicalDevice;
  137. struct loader_icd_term *icd_term = phys_dev_term->this_icd_term;
  138. if (icd_term->dispatch.ReleaseDisplayEXT == NULL) {
  139. loader_log(icd_term->this_instance, VK_DEBUG_REPORT_ERROR_BIT_EXT, 0,
  140. "ICD \"%s\" associated with VkPhysicalDevice does not support vkReleaseDisplayEXT - Consequently, the call is "
  141. "invalid because it should not be possible to acquire a display on this device",
  142. icd_term->scanned_icd->lib_name);
  143. }
  144. return icd_term->dispatch.ReleaseDisplayEXT(phys_dev_term->phys_dev, display);
  145. }
  146. // ---- VK_EXT_acquire_xlib_display extension trampoline/terminators
  147. #ifdef VK_USE_PLATFORM_XLIB_XRANDR_EXT
  148. VKAPI_ATTR VkResult VKAPI_CALL AcquireXlibDisplayEXT(VkPhysicalDevice physicalDevice, Display *dpy, VkDisplayKHR display) {
  149. const VkLayerInstanceDispatchTable *disp;
  150. VkPhysicalDevice unwrapped_phys_dev = loader_unwrap_physical_device(physicalDevice);
  151. disp = loader_get_instance_layer_dispatch(physicalDevice);
  152. return disp->AcquireXlibDisplayEXT(unwrapped_phys_dev, dpy, display);
  153. }
  154. VKAPI_ATTR VkResult VKAPI_CALL terminator_AcquireXlibDisplayEXT(VkPhysicalDevice physicalDevice, Display *dpy,
  155. VkDisplayKHR display) {
  156. struct loader_physical_device_term *phys_dev_term = (struct loader_physical_device_term *)physicalDevice;
  157. struct loader_icd_term *icd_term = phys_dev_term->this_icd_term;
  158. if (icd_term->dispatch.AcquireXlibDisplayEXT != NULL) {
  159. // Pass the call to the driver
  160. return icd_term->dispatch.AcquireXlibDisplayEXT(phys_dev_term->phys_dev, dpy, display);
  161. } else {
  162. // Emulate the call
  163. loader_log(icd_term->this_instance, VK_DEBUG_REPORT_INFORMATION_BIT_EXT, 0,
  164. "vkAcquireXLibDisplayEXT: Emulating call in ICD \"%s\" by returning error", icd_term->scanned_icd->lib_name);
  165. // Fail for the unsupported command
  166. return VK_ERROR_INITIALIZATION_FAILED;
  167. }
  168. }
  169. VKAPI_ATTR VkResult VKAPI_CALL GetRandROutputDisplayEXT(VkPhysicalDevice physicalDevice, Display *dpy, RROutput rrOutput,
  170. VkDisplayKHR *pDisplay) {
  171. const VkLayerInstanceDispatchTable *disp;
  172. VkPhysicalDevice unwrapped_phys_dev = loader_unwrap_physical_device(physicalDevice);
  173. disp = loader_get_instance_layer_dispatch(physicalDevice);
  174. return disp->GetRandROutputDisplayEXT(unwrapped_phys_dev, dpy, rrOutput, pDisplay);
  175. }
  176. VKAPI_ATTR VkResult VKAPI_CALL terminator_GetRandROutputDisplayEXT(VkPhysicalDevice physicalDevice, Display *dpy, RROutput rrOutput,
  177. VkDisplayKHR *pDisplay) {
  178. struct loader_physical_device_term *phys_dev_term = (struct loader_physical_device_term *)physicalDevice;
  179. struct loader_icd_term *icd_term = phys_dev_term->this_icd_term;
  180. if (icd_term->dispatch.GetRandROutputDisplayEXT != NULL) {
  181. // Pass the call to the driver
  182. return icd_term->dispatch.GetRandROutputDisplayEXT(phys_dev_term->phys_dev, dpy, rrOutput, pDisplay);
  183. } else {
  184. // Emulate the call
  185. loader_log(icd_term->this_instance, VK_DEBUG_REPORT_INFORMATION_BIT_EXT, 0,
  186. "vkGetRandROutputDisplayEXT: Emulating call in ICD \"%s\" by returning null display",
  187. icd_term->scanned_icd->lib_name);
  188. // Return a null handle to indicate this can't be done
  189. *pDisplay = VK_NULL_HANDLE;
  190. return VK_SUCCESS;
  191. }
  192. }
  193. #endif // VK_USE_PLATFORM_XLIB_XRANDR_EXT
  194. #ifdef VK_USE_PLATFORM_WIN32_KHR
  195. VKAPI_ATTR VkResult VKAPI_CALL GetPhysicalDeviceSurfacePresentModes2EXT(
  196. VkPhysicalDevice physicalDevice,
  197. const VkPhysicalDeviceSurfaceInfo2KHR* pSurfaceInfo,
  198. uint32_t* pPresentModeCount,
  199. VkPresentModeKHR* pPresentModes) {
  200. const VkLayerInstanceDispatchTable *disp;
  201. VkPhysicalDevice unwrapped_phys_dev = loader_unwrap_physical_device(physicalDevice);
  202. disp = loader_get_instance_layer_dispatch(physicalDevice);
  203. return disp->GetPhysicalDeviceSurfacePresentModes2EXT(unwrapped_phys_dev, pSurfaceInfo, pPresentModeCount, pPresentModes);
  204. }
  205. VKAPI_ATTR VkResult VKAPI_CALL terminator_GetPhysicalDeviceSurfacePresentModes2EXT(
  206. VkPhysicalDevice physicalDevice,
  207. const VkPhysicalDeviceSurfaceInfo2KHR* pSurfaceInfo,
  208. uint32_t* pPresentModeCount,
  209. VkPresentModeKHR* pPresentModes) {
  210. struct loader_physical_device_term *phys_dev_term = (struct loader_physical_device_term *)physicalDevice;
  211. struct loader_icd_term *icd_term = phys_dev_term->this_icd_term;
  212. if (NULL == icd_term->dispatch.GetPhysicalDeviceSurfacePresentModes2EXT) {
  213. loader_log(icd_term->this_instance, VK_DEBUG_REPORT_ERROR_BIT_EXT, 0,
  214. "ICD associated with VkPhysicalDevice does not support GetPhysicalDeviceSurfacePresentModes2EXT");
  215. }
  216. VkIcdSurface *icd_surface = (VkIcdSurface *)(pSurfaceInfo->surface);
  217. uint8_t icd_index = phys_dev_term->icd_index;
  218. if (NULL != icd_surface->real_icd_surfaces && NULL != (void *)icd_surface->real_icd_surfaces[icd_index]) {
  219. const VkPhysicalDeviceSurfaceInfo2KHR surface_info_copy = {
  220. .sType = pSurfaceInfo->sType,
  221. .pNext = pSurfaceInfo->pNext,
  222. .surface = icd_surface->real_icd_surfaces[icd_index],
  223. };
  224. return icd_term->dispatch.GetPhysicalDeviceSurfacePresentModes2EXT(phys_dev_term->phys_dev, &surface_info_copy, pPresentModeCount, pPresentModes);
  225. }
  226. return icd_term->dispatch.GetPhysicalDeviceSurfacePresentModes2EXT(phys_dev_term->phys_dev, pSurfaceInfo, pPresentModeCount, pPresentModes);
  227. }
  228. VKAPI_ATTR VkResult VKAPI_CALL GetDeviceGroupSurfacePresentModes2EXT(
  229. VkDevice device,
  230. const VkPhysicalDeviceSurfaceInfo2KHR* pSurfaceInfo,
  231. VkDeviceGroupPresentModeFlagsKHR* pModes) {
  232. const VkLayerDispatchTable *disp = loader_get_dispatch(device);
  233. return disp->GetDeviceGroupSurfacePresentModes2EXT(device, pSurfaceInfo, pModes);
  234. }
  235. VKAPI_ATTR VkResult VKAPI_CALL terminator_GetDeviceGroupSurfacePresentModes2EXT(
  236. VkDevice device,
  237. const VkPhysicalDeviceSurfaceInfo2KHR* pSurfaceInfo,
  238. VkDeviceGroupPresentModeFlagsKHR* pModes) {
  239. uint32_t icd_index = 0;
  240. struct loader_device *dev;
  241. struct loader_icd_term *icd_term = loader_get_icd_and_device(device, &dev, &icd_index);
  242. if (NULL != icd_term && NULL != icd_term->dispatch.GetDeviceGroupSurfacePresentModes2EXT) {
  243. VkIcdSurface *icd_surface = (VkIcdSurface *)(uintptr_t)pSurfaceInfo->surface;
  244. if (NULL != icd_surface->real_icd_surfaces && (VkSurfaceKHR)NULL != icd_surface->real_icd_surfaces[icd_index]) {
  245. const VkPhysicalDeviceSurfaceInfo2KHR surface_info_copy = {
  246. .sType = pSurfaceInfo->sType,
  247. .pNext = pSurfaceInfo->pNext,
  248. .surface = icd_surface->real_icd_surfaces[icd_index],
  249. };
  250. return icd_term->dispatch.GetDeviceGroupSurfacePresentModes2EXT(device, &surface_info_copy, pModes);
  251. }
  252. return icd_term->dispatch.GetDeviceGroupSurfacePresentModes2EXT(device, pSurfaceInfo, pModes);
  253. }
  254. return VK_SUCCESS;
  255. }
  256. #endif // VK_USE_PLATFORM_WIN32_KHR
  257. // ---- VK_EXT_tooling_info extension trampoline/terminators
  258. VKAPI_ATTR VkResult VKAPI_CALL GetPhysicalDeviceToolPropertiesEXT(
  259. VkPhysicalDevice physicalDevice,
  260. uint32_t* pToolCount,
  261. VkPhysicalDeviceToolPropertiesEXT* pToolProperties) {
  262. const VkLayerInstanceDispatchTable *disp;
  263. VkPhysicalDevice unwrapped_phys_dev = loader_unwrap_physical_device(physicalDevice);
  264. disp = loader_get_instance_layer_dispatch(physicalDevice);
  265. return disp->GetPhysicalDeviceToolPropertiesEXT(unwrapped_phys_dev, pToolCount, pToolProperties);
  266. }
  267. VKAPI_ATTR VkResult VKAPI_CALL terminator_GetPhysicalDeviceToolPropertiesEXT(
  268. VkPhysicalDevice physicalDevice,
  269. uint32_t* pToolCount,
  270. VkPhysicalDeviceToolPropertiesEXT* pToolProperties) {
  271. return VK_SUCCESS;
  272. }