From 614630df69c111402291beb955671a2fd6892288 Mon Sep 17 00:00:00 2001 From: Sam Lantinga Date: Tue, 27 Feb 2024 18:51:08 -0800 Subject: [PATCH] Allow using an external Vulkan device with the vulkan renderer --- include/SDL3/SDL_render.h | 71 +++++++--- src/render/vulkan/SDL_render_vulkan.c | 185 ++++++++++++++++---------- 2 files changed, 173 insertions(+), 83 deletions(-) diff --git a/include/SDL3/SDL_render.h b/include/SDL3/SDL_render.h index b02361cf7..52b773a6e 100644 --- a/include/SDL3/SDL_render.h +++ b/include/SDL3/SDL_render.h @@ -250,6 +250,15 @@ extern DECLSPEC SDL_Renderer * SDLCALL SDL_CreateRenderer(SDL_Window *window, co * - `SDL_PROP_RENDERER_CREATE_PRESENT_VSYNC_BOOLEAN`: true if you want * present synchronized with the refresh rate * + * With the vulkan renderer: + * + * - `SDL_PROP_RENDERER_CREATE_VULKAN_INSTANCE_POINTER`: the VkInstance to use with the renderer, optional. + * - `SDL_PROP_RENDERER_CREATE_VULKAN_SURFACE_NUMBER`: the VkSurfaceKHR to use with the renderer, optional. + * - `SDL_PROP_RENDERER_CREATE_VULKAN_PHYSICAL_DEVICE_POINTER`: the VkPhysicalDevice to use with the renderer, optional. + * - `SDL_PROP_RENDERER_CREATE_VULKAN_DEVICE_POINTER`: the VkDevice to use with the renderer, optional. + * - `SDL_PROP_RENDERER_CREATE_VULKAN_GRAPHICS_QUEUE_FAMILY_INDEX_NUMBER`: the queue family index used for rendering. + * - `SDL_PROP_RENDERER_CREATE_VULKAN_PRESENT_QUEUE_FAMILY_INDEX_NUMBER`: the queue family index used for presentation. + * * \param props the properties to use * \returns a valid rendering context or NULL if there was an error; call * SDL_GetError() for more information. @@ -263,11 +272,17 @@ extern DECLSPEC SDL_Renderer * SDLCALL SDL_CreateRenderer(SDL_Window *window, co */ extern DECLSPEC SDL_Renderer * SDLCALL SDL_CreateRendererWithProperties(SDL_PropertiesID props); -#define SDL_PROP_RENDERER_CREATE_NAME_STRING "name" -#define SDL_PROP_RENDERER_CREATE_WINDOW_POINTER "window" -#define SDL_PROP_RENDERER_CREATE_SURFACE_POINTER "surface" -#define SDL_PROP_RENDERER_CREATE_OUTPUT_COLORSPACE_NUMBER "output_colorspace" -#define SDL_PROP_RENDERER_CREATE_PRESENT_VSYNC_BOOLEAN "present_vsync" +#define SDL_PROP_RENDERER_CREATE_NAME_STRING "name" +#define SDL_PROP_RENDERER_CREATE_WINDOW_POINTER "window" +#define SDL_PROP_RENDERER_CREATE_SURFACE_POINTER "surface" +#define SDL_PROP_RENDERER_CREATE_OUTPUT_COLORSPACE_NUMBER "output_colorspace" +#define SDL_PROP_RENDERER_CREATE_PRESENT_VSYNC_BOOLEAN "present_vsync" +#define SDL_PROP_RENDERER_CREATE_VULKAN_INSTANCE_POINTER "vulkan.instance" +#define SDL_PROP_RENDERER_CREATE_VULKAN_SURFACE_NUMBER "vulkan.surface" +#define SDL_PROP_RENDERER_CREATE_VULKAN_PHYSICAL_DEVICE_POINTER "vulkan.physical_device" +#define SDL_PROP_RENDERER_CREATE_VULKAN_DEVICE_POINTER "vulkan.device" +#define SDL_PROP_RENDERER_CREATE_VULKAN_GRAPHICS_QUEUE_FAMILY_INDEX_NUMBER "vulkan.graphics_queue_family_index" +#define SDL_PROP_RENDERER_CREATE_VULKAN_PRESENT_QUEUE_FAMILY_INDEX_NUMBER "vulkan.present_queue_family_index" /** * Create a 2D software rendering context for a surface. @@ -354,15 +369,33 @@ extern DECLSPEC int SDLCALL SDL_GetRendererInfo(SDL_Renderer *renderer, SDL_Rend * that can be displayed, in terms of the SDR white point. When HDR is not * enabled, this will be 1.0. This property can change dynamically when * SDL_EVENT_DISPLAY_HDR_STATE_CHANGED is sent. + * + * With the direct3d renderer: + * * - `SDL_PROP_RENDERER_D3D9_DEVICE_POINTER`: the IDirect3DDevice9 associated * with the renderer + * + * With the direct3d11 renderer: + * * - `SDL_PROP_RENDERER_D3D11_DEVICE_POINTER`: the ID3D11Device associated * with the renderer + * + * With the direct3d12 renderer: + * * - `SDL_PROP_RENDERER_D3D12_DEVICE_POINTER`: the ID3D12Device associated * with the renderer * - `SDL_PROP_RENDERER_D3D12_COMMAND_QUEUE_POINTER`: the ID3D12CommandQueue * associated with the renderer * + * With the vulkan renderer: + * + * - `SDL_PROP_RENDERER_VULKAN_INSTANCE_POINTER`: the VkInstance associated with the renderer + * - `SDL_PROP_RENDERER_VULKAN_SURFACE_NUMBER`: the VkSurfaceKHR associated with the renderer + * - `SDL_PROP_RENDERER_VULKAN_PHYSICAL_DEVICE_POINTER`: the VkPhysicalDevice associated with the renderer + * - `SDL_PROP_RENDERER_VULKAN_DEVICE_POINTER`: the VkDevice associated with the renderer + * - `SDL_PROP_RENDERER_VULKAN_GRAPHICS_QUEUE_FAMILY_INDEX_NUMBER`: the queue family index used for rendering + * - `SDL_PROP_RENDERER_VULKAN_PRESENT_QUEUE_FAMILY_INDEX_NUMBER`: the queue family index used for presentation + * * \param renderer the rendering context * \returns a valid property ID on success or 0 on failure; call * SDL_GetError() for more information. @@ -374,17 +407,23 @@ extern DECLSPEC int SDLCALL SDL_GetRendererInfo(SDL_Renderer *renderer, SDL_Rend */ extern DECLSPEC SDL_PropertiesID SDLCALL SDL_GetRendererProperties(SDL_Renderer *renderer); -#define SDL_PROP_RENDERER_NAME_STRING "SDL.renderer.name" -#define SDL_PROP_RENDERER_WINDOW_POINTER "SDL.renderer.window" -#define SDL_PROP_RENDERER_SURFACE_POINTER "SDL.renderer.surface" -#define SDL_PROP_RENDERER_OUTPUT_COLORSPACE_NUMBER "SDL.renderer.output_colorspace" -#define SDL_PROP_RENDERER_HDR_ENABLED_BOOLEAN "SDL.renderer.HDR_enabled" -#define SDL_PROP_RENDERER_SDR_WHITE_POINT_FLOAT "SDL.renderer.SDR_white_point" -#define SDL_PROP_RENDERER_HDR_HEADROOM_FLOAT "SDL.renderer.HDR_headroom" -#define SDL_PROP_RENDERER_D3D9_DEVICE_POINTER "SDL.renderer.d3d9.device" -#define SDL_PROP_RENDERER_D3D11_DEVICE_POINTER "SDL.renderer.d3d11.device" -#define SDL_PROP_RENDERER_D3D12_DEVICE_POINTER "SDL.renderer.d3d12.device" -#define SDL_PROP_RENDERER_D3D12_COMMAND_QUEUE_POINTER "SDL.renderer.d3d12.command_queue" +#define SDL_PROP_RENDERER_NAME_STRING "SDL.renderer.name" +#define SDL_PROP_RENDERER_WINDOW_POINTER "SDL.renderer.window" +#define SDL_PROP_RENDERER_SURFACE_POINTER "SDL.renderer.surface" +#define SDL_PROP_RENDERER_OUTPUT_COLORSPACE_NUMBER "SDL.renderer.output_colorspace" +#define SDL_PROP_RENDERER_HDR_ENABLED_BOOLEAN "SDL.renderer.HDR_enabled" +#define SDL_PROP_RENDERER_SDR_WHITE_POINT_FLOAT "SDL.renderer.SDR_white_point" +#define SDL_PROP_RENDERER_HDR_HEADROOM_FLOAT "SDL.renderer.HDR_headroom" +#define SDL_PROP_RENDERER_D3D9_DEVICE_POINTER "SDL.renderer.d3d9.device" +#define SDL_PROP_RENDERER_D3D11_DEVICE_POINTER "SDL.renderer.d3d11.device" +#define SDL_PROP_RENDERER_D3D12_DEVICE_POINTER "SDL.renderer.d3d12.device" +#define SDL_PROP_RENDERER_D3D12_COMMAND_QUEUE_POINTER "SDL.renderer.d3d12.command_queue" +#define SDL_PROP_RENDERER_VULKAN_INSTANCE_POINTER "SDL.renderer.vulkan.instance" +#define SDL_PROP_RENDERER_VULKAN_SURFACE_NUMBER "SDL.renderer.vulkan.surface" +#define SDL_PROP_RENDERER_VULKAN_PHYSICAL_DEVICE_POINTER "SDL.renderer.vulkan.physical_device" +#define SDL_PROP_RENDERER_VULKAN_DEVICE_POINTER "SDL.renderer.vulkan.device" +#define SDL_PROP_RENDERER_VULKAN_GRAPHICS_QUEUE_FAMILY_INDEX_NUMBER "SDL.renderer.vulkan.graphics_queue_family_index" +#define SDL_PROP_RENDERER_VULKAN_PRESENT_QUEUE_FAMILY_INDEX_NUMBER "SDL.renderer.vulkan.present_queue_family_index" /** * Get the output size in pixels of a rendering context. diff --git a/src/render/vulkan/SDL_render_vulkan.c b/src/render/vulkan/SDL_render_vulkan.c index d5564cfd3..18f398241 100644 --- a/src/render/vulkan/SDL_render_vulkan.c +++ b/src/render/vulkan/SDL_render_vulkan.c @@ -270,7 +270,9 @@ typedef struct { PFN_vkGetInstanceProcAddr vkGetInstanceProcAddr; VkInstance instance; + SDL_bool instance_external; VkSurfaceKHR surface; + SDL_bool surface_external; VkPhysicalDevice physicalDevice; VkPhysicalDeviceProperties physicalDeviceProperties; VkPhysicalDeviceMemoryProperties physicalDeviceMemoryProperties; @@ -278,6 +280,7 @@ typedef struct VkQueue graphicsQueue; VkQueue presentQueue; VkDevice device; + SDL_bool device_external; uint32_t graphicsQueueFamilyIndex; uint32_t presentQueueFamilyIndex; VkSwapchainKHR swapchain; @@ -567,15 +570,15 @@ static void VULKAN_DestroyAll(SDL_Renderer *renderer) rendererData->constantBuffers = NULL; } - if (rendererData->device != VK_NULL_HANDLE) { + if (rendererData->device != VK_NULL_HANDLE && !rendererData->device_external) { vkDestroyDevice(rendererData->device, NULL); rendererData->device = VK_NULL_HANDLE; } - if (rendererData->surface != VK_NULL_HANDLE) { + if (rendererData->surface != VK_NULL_HANDLE && !rendererData->surface_external) { vkDestroySurfaceKHR(rendererData->instance, rendererData->surface, NULL); rendererData->surface = VK_NULL_HANDLE; } - if (rendererData->instance != VK_NULL_HANDLE) { + if (rendererData->instance != VK_NULL_HANDLE && !rendererData->instance_external) { vkDestroyInstance(rendererData->instance, NULL); rendererData->instance = VK_NULL_HANDLE; } @@ -1524,7 +1527,7 @@ static SDL_bool VULKAN_ValidationLayersFound() } /* Create resources that depend on the device. */ -static VkResult VULKAN_CreateDeviceResources(SDL_Renderer *renderer) +static VkResult VULKAN_CreateDeviceResources(SDL_Renderer *renderer, SDL_PropertiesID create_props) { VULKAN_RenderData *rendererData = (VULKAN_RenderData *)renderer->driverdata; SDL_VideoDevice *device = SDL_GetVideoDevice(); @@ -1549,46 +1552,53 @@ static VkResult VULKAN_CreateDeviceResources(SDL_Renderer *renderer) return VK_ERROR_UNKNOWN; } - /* Create VkInstance */ - VkInstanceCreateInfo instanceCreateInfo = { 0 }; - VkApplicationInfo appInfo = { 0 }; - appInfo.sType = VK_STRUCTURE_TYPE_APPLICATION_INFO; - appInfo.apiVersion = VK_API_VERSION_1_0; - instanceCreateInfo.sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO; - instanceCreateInfo.pApplicationInfo = &appInfo; - char const* const* instanceExtensions = SDL_Vulkan_GetInstanceExtensions(&instanceCreateInfo.enabledExtensionCount); - rendererData->supportsEXTSwapchainColorspace = VK_FALSE; - + /* Check for colorspace extension */ if (renderer->output_colorspace == SDL_COLORSPACE_SRGB_LINEAR || renderer->output_colorspace == SDL_COLORSPACE_HDR10) { rendererData->supportsEXTSwapchainColorspace = VULKAN_InstanceExtensionFound(rendererData, VK_EXT_SWAPCHAIN_COLOR_SPACE_EXTENSION_NAME); - if (rendererData->supportsEXTSwapchainColorspace == SDL_FALSE) { + if (!rendererData->supportsEXTSwapchainColorspace) { return SDL_SetError("[Vulkan] Using HDR output but %s not supported.", VK_EXT_SWAPCHAIN_COLOR_SPACE_EXTENSION_NAME); } } - char **instanceExtensionsCopy = SDL_calloc(sizeof(const char *), instanceCreateInfo.enabledExtensionCount + 1); - for (uint32_t i = 0; i < instanceCreateInfo.enabledExtensionCount; i++) { - instanceExtensionsCopy[i] = SDL_strdup(instanceExtensions[i]); - } - if (rendererData->supportsEXTSwapchainColorspace) { - instanceExtensionsCopy[instanceCreateInfo.enabledExtensionCount] = SDL_strdup(VK_EXT_SWAPCHAIN_COLOR_SPACE_EXTENSION_NAME); - instanceCreateInfo.enabledExtensionCount++; - } - instanceCreateInfo.ppEnabledExtensionNames = (const char* const*) instanceExtensionsCopy; - if (createDebug && VULKAN_ValidationLayersFound()) { - instanceCreateInfo.ppEnabledLayerNames = validationLayerName; - instanceCreateInfo.enabledLayerCount = 1; - } - result = vkCreateInstance(&instanceCreateInfo, NULL, &rendererData->instance); - if (result != VK_SUCCESS) { - SDL_LogError(SDL_LOG_CATEGORY_RENDER, "vkCreateInstance(): %s\n", SDL_Vulkan_GetResultString(result)); - return result; + + /* Create VkInstance */ + rendererData->instance = (VkInstance)SDL_GetProperty(create_props, SDL_PROP_RENDERER_CREATE_VULKAN_INSTANCE_POINTER, NULL); + if (rendererData->instance) { + rendererData->instance_external = SDL_TRUE; + } else { + VkInstanceCreateInfo instanceCreateInfo = { 0 }; + VkApplicationInfo appInfo = { 0 }; + appInfo.sType = VK_STRUCTURE_TYPE_APPLICATION_INFO; + appInfo.apiVersion = VK_API_VERSION_1_0; + instanceCreateInfo.sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO; + instanceCreateInfo.pApplicationInfo = &appInfo; + char const *const *instanceExtensions = SDL_Vulkan_GetInstanceExtensions(&instanceCreateInfo.enabledExtensionCount); + + char **instanceExtensionsCopy = SDL_calloc(sizeof(const char *), instanceCreateInfo.enabledExtensionCount + 1); + for (uint32_t i = 0; i < instanceCreateInfo.enabledExtensionCount; i++) { + instanceExtensionsCopy[i] = SDL_strdup(instanceExtensions[i]); + } + if (rendererData->supportsEXTSwapchainColorspace) { + instanceExtensionsCopy[instanceCreateInfo.enabledExtensionCount] = SDL_strdup(VK_EXT_SWAPCHAIN_COLOR_SPACE_EXTENSION_NAME); + instanceCreateInfo.enabledExtensionCount++; + } + instanceCreateInfo.ppEnabledExtensionNames = (const char *const *)instanceExtensionsCopy; + if (createDebug && VULKAN_ValidationLayersFound()) { + instanceCreateInfo.ppEnabledLayerNames = validationLayerName; + instanceCreateInfo.enabledLayerCount = 1; + } + result = vkCreateInstance(&instanceCreateInfo, NULL, &rendererData->instance); + if (result != VK_SUCCESS) { + SDL_LogError(SDL_LOG_CATEGORY_RENDER, "vkCreateInstance(): %s\n", SDL_Vulkan_GetResultString(result)); + return result; + } + + for (uint32_t i = 0; i < instanceCreateInfo.enabledExtensionCount; i++) { + SDL_free(instanceExtensionsCopy[i]); + } + SDL_free(instanceExtensionsCopy); } - for (uint32_t i = 0; i < instanceCreateInfo.enabledExtensionCount; i++) { - SDL_free(instanceExtensionsCopy[i]); - } - SDL_free(instanceExtensionsCopy); /* Load instance Vulkan functions */ if (VULKAN_LoadInstanceFunctions(rendererData) != 0) { VULKAN_DestroyAll(renderer); @@ -1596,45 +1606,78 @@ static VkResult VULKAN_CreateDeviceResources(SDL_Renderer *renderer) } /* Create Vulkan surface */ - if (!device->Vulkan_CreateSurface || !device->Vulkan_CreateSurface(device, renderer->window, rendererData->instance, NULL, &rendererData->surface)) { - VULKAN_DestroyAll(renderer); - SDL_LogError(SDL_LOG_CATEGORY_RENDER, "Vulkan_CreateSurface() failed.\n"); - return VK_ERROR_UNKNOWN; + rendererData->surface = (VkSurfaceKHR)SDL_GetNumberProperty(create_props, SDL_PROP_RENDERER_CREATE_VULKAN_SURFACE_NUMBER, 0); + if (rendererData->surface) { + rendererData->surface_external = SDL_TRUE; + } else { + if (!device->Vulkan_CreateSurface || !device->Vulkan_CreateSurface(device, renderer->window, rendererData->instance, NULL, &rendererData->surface)) { + VULKAN_DestroyAll(renderer); + SDL_LogError(SDL_LOG_CATEGORY_RENDER, "Vulkan_CreateSurface() failed.\n"); + return VK_ERROR_UNKNOWN; + } } /* Choose Vulkan physical device */ - if (VULKAN_FindPhysicalDevice(rendererData) != VK_SUCCESS) { - VULKAN_DestroyAll(renderer); - return VK_ERROR_UNKNOWN; + rendererData->physicalDevice = (VkPhysicalDevice)SDL_GetProperty(create_props, SDL_PROP_RENDERER_CREATE_VULKAN_PHYSICAL_DEVICE_POINTER, NULL); + if (rendererData->physicalDevice) { + vkGetPhysicalDeviceMemoryProperties(rendererData->physicalDevice, &rendererData->physicalDeviceMemoryProperties); + vkGetPhysicalDeviceFeatures(rendererData->physicalDevice, &rendererData->physicalDeviceFeatures); + } else { + if (VULKAN_FindPhysicalDevice(rendererData) != VK_SUCCESS) { + VULKAN_DestroyAll(renderer); + return VK_ERROR_UNKNOWN; + } + } + + if (SDL_HasProperty(create_props, SDL_PROP_RENDERER_CREATE_VULKAN_GRAPHICS_QUEUE_FAMILY_INDEX_NUMBER)) { + rendererData->graphicsQueueFamilyIndex = (uint32_t)SDL_GetNumberProperty(create_props, SDL_PROP_RENDERER_CREATE_VULKAN_GRAPHICS_QUEUE_FAMILY_INDEX_NUMBER, 0); + } + if (SDL_HasProperty(create_props, SDL_PROP_RENDERER_CREATE_VULKAN_PRESENT_QUEUE_FAMILY_INDEX_NUMBER)) { + rendererData->presentQueueFamilyIndex = (uint32_t)SDL_GetNumberProperty(create_props, SDL_PROP_RENDERER_CREATE_VULKAN_PRESENT_QUEUE_FAMILY_INDEX_NUMBER, 0); } /* Create Vulkan device */ - VkDeviceQueueCreateInfo deviceQueueCreateInfo[1] = { { 0 } }; - static const float queuePriority[] = { 1.0f }; - VkDeviceCreateInfo deviceCreateInfo = { 0 }; - static const char *const deviceExtensionNames[] = { - VK_KHR_SWAPCHAIN_EXTENSION_NAME, - }; + rendererData->device = (VkDevice)SDL_GetProperty(create_props, SDL_PROP_RENDERER_CREATE_VULKAN_DEVICE_POINTER, NULL); + if (rendererData->device) { + rendererData->device_external = SDL_TRUE; + } else { + VkDeviceQueueCreateInfo deviceQueueCreateInfo[2] = { { 0 }, { 0 } }; + static const float queuePriority[] = { 1.0f }; + VkDeviceCreateInfo deviceCreateInfo = { 0 }; + static const char *const deviceExtensionNames[] = { + VK_KHR_SWAPCHAIN_EXTENSION_NAME, + }; - deviceQueueCreateInfo->sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO; - deviceQueueCreateInfo->queueFamilyIndex = rendererData->graphicsQueueFamilyIndex; - deviceQueueCreateInfo->queueCount = 1; - deviceQueueCreateInfo->pQueuePriorities = &queuePriority[0]; + deviceCreateInfo.sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO; + deviceCreateInfo.queueCreateInfoCount = 0; + deviceCreateInfo.pQueueCreateInfos = deviceQueueCreateInfo; + deviceCreateInfo.pEnabledFeatures = NULL; + deviceCreateInfo.enabledExtensionCount = SDL_arraysize(deviceExtensionNames); + deviceCreateInfo.ppEnabledExtensionNames = deviceExtensionNames; - deviceCreateInfo.sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO; - deviceCreateInfo.queueCreateInfoCount = 1; - deviceCreateInfo.pQueueCreateInfos = deviceQueueCreateInfo; - deviceCreateInfo.pEnabledFeatures = NULL; - deviceCreateInfo.enabledExtensionCount = SDL_arraysize(deviceExtensionNames); - deviceCreateInfo.ppEnabledExtensionNames = deviceExtensionNames; - result = vkCreateDevice(rendererData->physicalDevice, &deviceCreateInfo, NULL, &rendererData->device); - if (result != VK_SUCCESS) { - SDL_LogError(SDL_LOG_CATEGORY_RENDER, "vkCreateDevice(): %s\n", SDL_Vulkan_GetResultString(result)); - VULKAN_DestroyAll(renderer); - return result; + deviceQueueCreateInfo[0].sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO; + deviceQueueCreateInfo[0].queueFamilyIndex = rendererData->graphicsQueueFamilyIndex; + deviceQueueCreateInfo[0].queueCount = 1; + deviceQueueCreateInfo[0].pQueuePriorities = queuePriority; + ++deviceCreateInfo.queueCreateInfoCount; + + if (rendererData->presentQueueFamilyIndex != rendererData->graphicsQueueFamilyIndex) { + deviceQueueCreateInfo[1].sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO; + deviceQueueCreateInfo[1].queueFamilyIndex = rendererData->presentQueueFamilyIndex; + deviceQueueCreateInfo[1].queueCount = 1; + deviceQueueCreateInfo[1].pQueuePriorities = queuePriority; + ++deviceCreateInfo.queueCreateInfoCount; + } + + result = vkCreateDevice(rendererData->physicalDevice, &deviceCreateInfo, NULL, &rendererData->device); + if (result != VK_SUCCESS) { + SDL_LogError(SDL_LOG_CATEGORY_RENDER, "vkCreateDevice(): %s\n", SDL_Vulkan_GetResultString(result)); + VULKAN_DestroyAll(renderer); + return result; + } } - if(VULKAN_LoadDeviceFunctions(rendererData) != 0) { + if (VULKAN_LoadDeviceFunctions(rendererData) != 0) { VULKAN_DestroyAll(renderer); return VK_ERROR_UNKNOWN; } @@ -1789,6 +1832,14 @@ static VkResult VULKAN_CreateDeviceResources(SDL_Renderer *renderer) } } + SDL_PropertiesID props = SDL_GetRendererProperties(renderer); + SDL_SetProperty(props, SDL_PROP_RENDERER_VULKAN_INSTANCE_POINTER, rendererData->instance); + SDL_SetNumberProperty(props, SDL_PROP_RENDERER_VULKAN_SURFACE_NUMBER, (Sint64)rendererData->surface); + SDL_SetProperty(props, SDL_PROP_RENDERER_VULKAN_PHYSICAL_DEVICE_POINTER, rendererData->physicalDevice); + SDL_SetProperty(props, SDL_PROP_RENDERER_VULKAN_DEVICE_POINTER, rendererData->device); + SDL_SetNumberProperty(props, SDL_PROP_RENDERER_VULKAN_GRAPHICS_QUEUE_FAMILY_INDEX_NUMBER, rendererData->graphicsQueueFamilyIndex); + SDL_SetNumberProperty(props, SDL_PROP_RENDERER_VULKAN_PRESENT_QUEUE_FAMILY_INDEX_NUMBER, rendererData->presentQueueFamilyIndex); + return VK_SUCCESS; } @@ -3880,8 +3931,8 @@ SDL_Renderer *VULKAN_CreateRenderer(SDL_Window *window, SDL_PropertiesID create_ */ renderer->window = window; - /* Initialize Direct3D resources */ - if (VULKAN_CreateDeviceResources(renderer) != VK_SUCCESS) { + /* Initialize Vulkan resources */ + if (VULKAN_CreateDeviceResources(renderer, create_props) != VK_SUCCESS) { VULKAN_DestroyRenderer(renderer); return NULL; }