From ff4bc8bab922b6664d19943234e49b23c25117bd Mon Sep 17 00:00:00 2001 From: "alexey.lysiuk" Date: Sat, 3 Aug 2019 13:15:06 +0300 Subject: [PATCH] - use EXT_metal_surface extension for Vulkan surface creation Prefer EXT_metal_surface over deprecated MVK_macos_surface extension, and use it only when modern one is not available --- src/posix/cocoa/i_video.mm | 50 ++++++++++++++++++--- src/rendering/vulkan/thirdparty/volk/volk.c | 1 + 2 files changed, 46 insertions(+), 5 deletions(-) diff --git a/src/posix/cocoa/i_video.mm b/src/posix/cocoa/i_video.mm index d157c4b33..5ad566b7f 100644 --- a/src/posix/cocoa/i_video.mm +++ b/src/posix/cocoa/i_video.mm @@ -35,6 +35,7 @@ #ifdef HAVE_VULKAN #define VK_USE_PLATFORM_MACOS_MVK +#define VK_USE_PLATFORM_METAL_EXT #include "volk/volk.h" #endif @@ -867,12 +868,37 @@ void I_GetVulkanDrawableSize(int *width, int *height) bool I_GetVulkanPlatformExtensions(unsigned int *count, const char **names) { - static const char* extensions[] = + static std::vector extensions; + + if (extensions.empty()) { - VK_KHR_SURFACE_EXTENSION_NAME, - VK_MVK_MACOS_SURFACE_EXTENSION_NAME - }; - static const unsigned int extensionCount = static_cast(sizeof extensions / sizeof extensions[0]); + uint32_t extensionPropertyCount = 0; + vkEnumerateInstanceExtensionProperties(nullptr, &extensionPropertyCount, nullptr); + + std::vector extensionProperties(extensionPropertyCount); + vkEnumerateInstanceExtensionProperties(nullptr, &extensionPropertyCount, extensionProperties.data()); + + static const char* const EXTENSION_NAMES[] = + { + VK_KHR_SURFACE_EXTENSION_NAME, // KHR_surface, required + VK_EXT_METAL_SURFACE_EXTENSION_NAME, // EXT_metal_surface, optional, preferred + VK_MVK_MACOS_SURFACE_EXTENSION_NAME, // MVK_macos_surface, optional, deprecated + }; + + for (const VkExtensionProperties ¤tProperties : extensionProperties) + { + for (const char *const extensionName : EXTENSION_NAMES) + { + if (strcmp(currentProperties.extensionName, extensionName) == 0) + { + extensions.push_back(extensionName); + } + } + } + } + + static const unsigned int extensionCount = static_cast(extensions.size()); + assert(extensionCount >= 2); // KHR_surface + at least one of the platform surface extentions if (count == nullptr && names == nullptr) { @@ -899,6 +925,20 @@ bool I_GetVulkanPlatformExtensions(unsigned int *count, const char **names) bool I_CreateVulkanSurface(VkInstance instance, VkSurfaceKHR *surface) { + if (vkCreateMetalSurfaceEXT) + { + // Preferred surface creation path + VkMetalSurfaceCreateInfoEXT surfaceCreateInfo; + surfaceCreateInfo.sType = VK_STRUCTURE_TYPE_METAL_SURFACE_CREATE_INFO_EXT; + surfaceCreateInfo.pNext = nullptr; + surfaceCreateInfo.flags = 0; + surfaceCreateInfo.pLayer = static_cast(CocoaVideo::GetWindow().contentView.layer); + + const VkResult result = vkCreateMetalSurfaceEXT(instance, &surfaceCreateInfo, nullptr, surface); + return result == VK_SUCCESS; + } + + // Deprecated surface creation path VkMacOSSurfaceCreateInfoMVK windowCreateInfo; windowCreateInfo.sType = VK_STRUCTURE_TYPE_MACOS_SURFACE_CREATE_INFO_MVK; windowCreateInfo.pNext = nullptr; diff --git a/src/rendering/vulkan/thirdparty/volk/volk.c b/src/rendering/vulkan/thirdparty/volk/volk.c index 66344cae5..bcaf541c3 100644 --- a/src/rendering/vulkan/thirdparty/volk/volk.c +++ b/src/rendering/vulkan/thirdparty/volk/volk.c @@ -4,6 +4,7 @@ #ifdef __APPLE__ #define VK_USE_PLATFORM_MACOS_MVK +#define VK_USE_PLATFORM_METAL_EXT #endif