diff --git a/drivers/vulkan/rendering_context_driver_vulkan.cpp b/drivers/vulkan/rendering_context_driver_vulkan.cpp index 17a086ed874..5340b2e7e56 100644 --- a/drivers/vulkan/rendering_context_driver_vulkan.cpp +++ b/drivers/vulkan/rendering_context_driver_vulkan.cpp @@ -37,6 +37,7 @@ #include "vk_enum_string_helper.h" #include "core/config/project_settings.h" +#include "core/error/error_list.h" #include "core/version.h" #include "rendering_device_driver_vulkan.h" @@ -914,15 +915,72 @@ Error RenderingContextDriverVulkan::_create_vulkan_instance(const VkInstanceCrea return OK; } -Error RenderingContextDriverVulkan::initialize() { - Error err; +bool RenderingContextDriverVulkan::_vulkan_is_supported() { + if (VulkanHooks::get_singleton() != nullptr) { + VkPhysicalDevice hooked_device = VK_NULL_HANDLE; + return VulkanHooks::get_singleton()->get_physical_device(&hooked_device); + } #ifdef USE_VOLK if (volkInitialize() != VK_SUCCESS) { - return FAILED; + return false; + } + + if (!vkCreateInstance) { + return false; + } +#endif + + VkApplicationInfo app_info{}; + app_info.sType = VK_STRUCTURE_TYPE_APPLICATION_INFO; + app_info.apiVersion = VK_API_VERSION_1_0; + + VkInstanceCreateInfo create_info{}; + create_info.sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO; + create_info.pApplicationInfo = &app_info; + +#if defined(USE_VOLK) && (defined(MACOS_ENABLED) || defined(IOS_ENABLED)) + const char *probe_extensions[] = { VK_KHR_PORTABILITY_ENUMERATION_EXTENSION_NAME }; + create_info.enabledExtensionCount = 1; + create_info.ppEnabledExtensionNames = probe_extensions; + create_info.flags |= VK_INSTANCE_CREATE_ENUMERATE_PORTABILITY_BIT_KHR; +#endif + + VkInstance _instance; + if (vkCreateInstance(&create_info, nullptr, &_instance) != VK_SUCCESS) { + return false; + } + +#ifdef USE_VOLK + volkLoadInstance(_instance); +#endif + +#ifdef USE_VOLK + if (!vkEnumeratePhysicalDevices) { + vkDestroyInstance(_instance, nullptr); + return false; } #endif + uint32_t device_count = 0; + VkResult result = vkEnumeratePhysicalDevices(_instance, &device_count, nullptr); + + vkDestroyInstance(_instance, nullptr); + + if (result != VK_SUCCESS || device_count == 0) { + return false; + } + + return true; +} + +Error RenderingContextDriverVulkan::initialize() { + Error err; + + if (!_vulkan_is_supported()) { + return ERR_UNAVAILABLE; + } + err = _initialize_vulkan_version(); ERR_FAIL_COND_V(err != OK, err); diff --git a/drivers/vulkan/rendering_context_driver_vulkan.h b/drivers/vulkan/rendering_context_driver_vulkan.h index 8d8805d8558..ccf8ea5e956 100644 --- a/drivers/vulkan/rendering_context_driver_vulkan.h +++ b/drivers/vulkan/rendering_context_driver_vulkan.h @@ -108,6 +108,7 @@ class RenderingContextDriverVulkan : public RenderingContextDriver { VkDebugReportCallbackEXT debug_report = VK_NULL_HANDLE; Functions functions; + bool _vulkan_is_supported(); Error _initialize_vulkan_version(); void _register_requested_instance_extension(const CharString &p_extension_name, bool p_required); Error _initialize_instance_extensions();