Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[wsi] Refactor platform system to support multiple WSI implementations #3738

Merged
merged 6 commits into from
May 13, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions include/native/wsi/native_sdl2.h
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
#include <windows.h>

#include <SDL2/SDL.h>
#include <SDL.h>

namespace dxvk::wsi {

Expand All @@ -22,4 +22,4 @@ namespace dxvk::wsi {
return reinterpret_cast<HMONITOR>(static_cast<intptr_t>(displayId + 1));
}

}
}
15 changes: 8 additions & 7 deletions meson.build
Original file line number Diff line number Diff line change
Expand Up @@ -115,7 +115,6 @@ if platform == 'windows'
)
endif

dxvk_wsi = 'win32'
dxvk_name_prefix = ''
compiler_args += ['-DDXVK_WSI_WIN32']
else
Expand All @@ -128,15 +127,17 @@ else
'./include/native/directx'
]

dxvk_wsi = get_option('dxvk_native_wsi')

if dxvk_wsi == 'sdl2'
lib_sdl2 = cpp.find_library('SDL2')
lib_sdl2 = dependency('SDL2', required: false)
lib_glfw = dependency('glfw', required: false)
if lib_sdl2.found()
compiler_args += ['-DDXVK_WSI_SDL2']
elif dxvk_wsi == 'glfw'
lib_glfw = cpp.find_library('glfw')
endif
if lib_glfw.found()
compiler_args += ['-DDXVK_WSI_GLFW']
endif
if (not lib_sdl2.found() and not lib_glfw.found())
error('SDL2 or GLFW are required to build dxvk-native')
endif

dxvk_name_prefix = 'libdxvk_'

Expand Down
5 changes: 5 additions & 0 deletions src/dxvk/dxvk_instance.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
#include "dxvk_openvr.h"
#include "dxvk_openxr.h"
#include "dxvk_platform_exts.h"
#include "../wsi/wsi_platform.h"

#include <algorithm>
#include <sstream>
Expand All @@ -20,6 +21,8 @@ namespace dxvk {
Logger::info(str::format("Game: ", env::getExeName()));
Logger::info(str::format("DXVK: ", DXVK_VERSION));

wsi::init();

m_config = Config::getUserConfig();
m_config.merge(Config::getAppConfig(env::getExePath()));
m_config.logOptions();
Expand Down Expand Up @@ -64,6 +67,8 @@ namespace dxvk {
DxvkInstance::~DxvkInstance() {
if (m_messenger)
m_vki->vkDestroyDebugUtilsMessengerEXT(m_vki->instance(), m_messenger, nullptr);

wsi::quit();
}


Expand Down
Original file line number Diff line number Diff line change
@@ -1,17 +1,21 @@
#include "../dxvk_platform_exts.h"
#include "dxvk_platform_exts.h"
#include "../wsi/wsi_platform.h"

namespace dxvk {

DxvkPlatformExts DxvkPlatformExts::s_instance;

std::string_view DxvkPlatformExts::getName() {
return "Win32 WSI";
return "Platform WSI";
}


DxvkNameSet DxvkPlatformExts::getInstanceExtensions() {
std::vector<const char *> extensionNames = wsi::getInstanceExtensions();

DxvkNameSet names;
names.add(VK_KHR_WIN32_SURFACE_EXTENSION_NAME);
for (const char* name : extensionNames)
names.add(name);

return names;
}
Expand All @@ -33,4 +37,4 @@ namespace dxvk {

}

}
}
15 changes: 1 addition & 14 deletions src/dxvk/meson.build
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,7 @@ dxvk_src = [
'dxvk_options.cpp',
'dxvk_pipelayout.cpp',
'dxvk_pipemanager.cpp',
'dxvk_platform_exts.cpp',
'dxvk_presenter.cpp',
'dxvk_queue.cpp',
'dxvk_resource.cpp',
Expand Down Expand Up @@ -117,20 +118,6 @@ if platform == 'windows'
]
endif

if dxvk_wsi == 'win32'
dxvk_src += [
'platform/dxvk_win32_exts.cpp'
]
elif dxvk_wsi == 'sdl2'
dxvk_src += [
'platform/dxvk_sdl2_exts.cpp'
]
elif dxvk_wsi == 'glfw'
dxvk_src += [
'platform/dxvk_glfw_exts.cpp'
]
endif

dxvk_extra_deps = [ dependency('threads') ]
if platform == 'linux'
dxvk_extra_deps += [ cpp.find_library('dl', required: false) ]
Expand Down
49 changes: 0 additions & 49 deletions src/dxvk/platform/dxvk_glfw_exts.cpp

This file was deleted.

50 changes: 0 additions & 50 deletions src/dxvk/platform/dxvk_sdl2_exts.cpp

This file was deleted.

22 changes: 13 additions & 9 deletions src/wsi/glfw/wsi_monitor_glfw.cpp
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
#if defined(DXVK_WSI_GLFW)

#include "../wsi_monitor.h"

#include "wsi/native_wsi.h"
Expand All @@ -11,22 +13,22 @@

namespace dxvk::wsi {

HMONITOR getDefaultMonitor() {
HMONITOR GlfwWsiDriver::getDefaultMonitor() {
return enumMonitors(0);
}


HMONITOR enumMonitors(uint32_t index) {
HMONITOR GlfwWsiDriver::enumMonitors(uint32_t index) {
return isDisplayValid(int32_t(index))
? toHmonitor(index)
: nullptr;
}

HMONITOR enumMonitors(const LUID *adapterLUID[], uint32_t numLUIDs, uint32_t index) {
HMONITOR GlfwWsiDriver::enumMonitors(const LUID *adapterLUID[], uint32_t numLUIDs, uint32_t index) {
return enumMonitors(index);
}

bool getDisplayName(
bool GlfwWsiDriver::getDisplayName(
HMONITOR hMonitor,
WCHAR (&Name)[32]) {
const int32_t displayId = fromHmonitor(hMonitor);
Expand All @@ -46,7 +48,7 @@ namespace dxvk::wsi {
}


bool getDesktopCoordinates(
bool GlfwWsiDriver::getDesktopCoordinates(
HMONITOR hMonitor,
RECT* pRect) {
const int32_t displayId = fromHmonitor(hMonitor);
Expand Down Expand Up @@ -97,7 +99,7 @@ namespace dxvk::wsi {
}


bool getDisplayMode(
bool GlfwWsiDriver::getDisplayMode(
HMONITOR hMonitor,
uint32_t ModeNumber,
WsiMode* pMode) {
Expand All @@ -121,7 +123,7 @@ namespace dxvk::wsi {
}


bool getCurrentDisplayMode(
bool GlfwWsiDriver::getCurrentDisplayMode(
HMONITOR hMonitor,
WsiMode* pMode) {
const int32_t displayId = fromHmonitor(hMonitor);
Expand All @@ -141,7 +143,7 @@ namespace dxvk::wsi {
}


bool getDesktopDisplayMode(
bool GlfwWsiDriver::getDesktopDisplayMode(
HMONITOR hMonitor,
WsiMode* pMode) {
const int32_t displayId = fromHmonitor(hMonitor);
Expand All @@ -159,9 +161,11 @@ namespace dxvk::wsi {
return true;
}

std::vector<uint8_t> getMonitorEdid(HMONITOR hMonitor) {
std::vector<uint8_t> GlfwWsiDriver::getMonitorEdid(HMONITOR hMonitor) {
Logger::err("getMonitorEdid not implemented on this platform.");
return {};
}

}

#endif
71 changes: 71 additions & 0 deletions src/wsi/glfw/wsi_platform_glfw.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
#if defined(DXVK_WSI_GLFW)

#include "wsi_platform_glfw.h"
#include "../../util/util_error.h"
#include "../../util/util_string.h"
#include "../../util/util_win32_compat.h"

namespace dxvk::wsi {

GlfwWsiDriver::GlfwWsiDriver() {
libglfw = LoadLibraryA( // FIXME: Get soname as string from meson
#if defined(_WIN32)
"glfw.dll"
#elif defined(__APPLE__)
"libglfw.3.dylib"
#else
"libglfw.so.3"
#endif
);
if (libglfw == nullptr)
throw DxvkError("GLFW WSI: Failed to load GLFW DLL.");

#define GLFW_PROC(ret, name, params) \
name = reinterpret_cast<pfn_##name>(GetProcAddress(libglfw, #name)); \
if (name == nullptr) { \
FreeLibrary(libglfw); \
libglfw = nullptr; \
throw DxvkError("GLFW WSI: Failed to load " #name "."); \
}
#include "wsi_platform_glfw_funcs.h"
}

GlfwWsiDriver::~GlfwWsiDriver() {
FreeLibrary(libglfw);
}

std::vector<const char *> GlfwWsiDriver::getInstanceExtensions() {
if (!glfwVulkanSupported())
throw DxvkError(str::format("GLFW WSI: Vulkan is not supported in any capacity!"));

uint32_t extensionCount = 0;
const char** extensionArray = glfwGetRequiredInstanceExtensions(&extensionCount);

if (extensionCount == 0)
throw DxvkError(str::format("GLFW WSI: Failed to get required instance extensions"));

std::vector<const char *> names(extensionCount);
for (uint32_t i = 0; i < extensionCount; ++i) {
names.push_back(extensionArray[i]);
}

return names;
}

static bool createGlfwWsiDriver(WsiDriver **driver) {
try {
*driver = new GlfwWsiDriver();
} catch (const DxvkError& e) {
return false;
}
return true;
}

WsiBootstrap GlfwWSI = {
"GLFW",
createGlfwWsiDriver
};

}

#endif
Loading
Loading