SDL: Fix compatibility with Windows XP (e70db)

From e70db38d6039b356d2f175214214b6c67f7d3e37 Mon Sep 17 00:00:00 2001
From: Cameron Cawley <[EMAIL REDACTED]>
Date: Tue, 6 Sep 2022 11:21:57 +0100
Subject: [PATCH] Fix compatibility with Windows XP (cherry picked from commit
 10e1ef00e29479f3ac0ba4d0bf3e0083fca8b2a0)

---
 src/render/direct3d12/SDL_render_d3d12.c | 24 +++++++++++++++++++++++-
 1 file changed, 23 insertions(+), 1 deletion(-)

diff --git a/src/render/direct3d12/SDL_render_d3d12.c b/src/render/direct3d12/SDL_render_d3d12.c
index 397101974eb..6e76ed3b8e2 100644
--- a/src/render/direct3d12/SDL_render_d3d12.c
+++ b/src/render/direct3d12/SDL_render_d3d12.c
@@ -719,6 +719,13 @@ D3D12_CreateDeviceResources(SDL_Renderer* renderer)
     typedef HRESULT(WINAPI* PFN_CREATE_DXGI_FACTORY)(UINT flags, REFIID riid, void** ppFactory);
     PFN_CREATE_DXGI_FACTORY CreateDXGIFactoryFunc;
     PFN_D3D12_CREATE_DEVICE D3D12CreateDeviceFunc;
+#endif
+#ifndef __GDK__
+    HMODULE kernel32;
+    typedef HANDLE(WINAPI* PFN_CREATE_EVENT_EX)(LPSECURITY_ATTRIBUTES lpEventAttributes, LPCWSTR lpName, DWORD dwFlags, DWORD dwDesiredAccess);
+    PFN_CREATE_EVENT_EX CreateEventExFunc;
+#else
+#define CreateEventExFunc CreateEventEx
 #endif
     D3D12_RenderData* data = (D3D12_RenderData*)renderer->driverdata;
     ID3D12Device* d3dDevice = NULL;
@@ -748,6 +755,21 @@ D3D12_CreateDeviceResources(SDL_Renderer* renderer)
     /* See if we need debug interfaces */
     createDebug = SDL_GetHintBoolean(SDL_HINT_RENDER_DIRECT3D11_DEBUG, SDL_FALSE);
 
+#ifndef __GDK__
+    /* CreateEventEx() arrived in Vista, so we need to load it with GetProcAddress for XP. */
+    kernel32 = GetModuleHandle(TEXT("kernel32.dll"));
+    if (!kernel32) {
+        result = E_FAIL;
+        goto done;
+    }
+
+    CreateEventExFunc = (PFN_CREATE_EVENT_EX) GetProcAddress(kernel32, "CreateEventExW");
+    if (!CreateEventExFunc) {
+        result = E_FAIL;
+        goto done;
+    }
+#endif
+
 #if !defined(__XBOXONE__) && !defined(__XBOXSERIES__)
     data->hDXGIMod = SDL_LoadObject("dxgi.dll");
     if (!data->hDXGIMod) {
@@ -999,7 +1021,7 @@ D3D12_CreateDeviceResources(SDL_Renderer* renderer)
 
     data->fenceValue++;
 
-    data->fenceEvent = CreateEventEx(NULL, NULL, 0, EVENT_MODIFY_STATE | SYNCHRONIZE);
+    data->fenceEvent = CreateEventExFunc(NULL, NULL, 0, EVENT_MODIFY_STATE | SYNCHRONIZE);
     if (!data->fenceEvent) {
         WIN_SetErrorFromHRESULT(SDL_COMPOSE_ERROR("CreateEventEx"), result);
         goto done;