Misc: Remove atexit() usage

pull/3794/head
Stenzek 2 weeks ago
parent 69fe550343
commit 0fbd997d4d
No known key found for this signature in database

@ -2,8 +2,8 @@
// SPDX-License-Identifier: CC-BY-NC-ND-4.0 // SPDX-License-Identifier: CC-BY-NC-ND-4.0
#include "opengl_context_wgl.h" #include "opengl_context_wgl.h"
#include "opengl_loader.h"
#include "gpu_texture.h" #include "gpu_texture.h"
#include "opengl_loader.h"
#include "common/assert.h" #include "common/assert.h"
#include "common/dynamic_library.h" #include "common/dynamic_library.h"
@ -17,8 +17,6 @@ LOG_CHANNEL(GPUDevice);
#pragma clang diagnostic ignored "-Wmicrosoft-cast" #pragma clang diagnostic ignored "-Wmicrosoft-cast"
#endif #endif
namespace dyn_libs {
#define OPENGL_FUNCTIONS(X) \ #define OPENGL_FUNCTIONS(X) \
X(wglCreateContext) \ X(wglCreateContext) \
X(wglDeleteContext) \ X(wglDeleteContext) \
@ -28,64 +26,61 @@ namespace dyn_libs {
X(wglMakeCurrent) \ X(wglMakeCurrent) \
X(wglShareLists) X(wglShareLists)
namespace {
struct Locals
{
DynamicLibrary opengl_library;
std::once_flag opengl_once_flag;
#define DECLARE_OPENGL_FUNCTION(F) decltype(&::F) F;
OPENGL_FUNCTIONS(DECLARE_OPENGL_FUNCTION)
#undef DECLARE_OPENGL_FUNCTION
};
} // namespace
static bool LoadOpenGLLibrary(Error* error); static bool LoadOpenGLLibrary(Error* error);
static void CloseOpenGLLibrary();
static void* GetProcAddressCallback(const char* name); static void* GetProcAddressCallback(const char* name);
static DynamicLibrary s_opengl_library; static Locals s_locals;
#define DECLARE_OPENGL_FUNCTION(F) static decltype(&::F) F;
OPENGL_FUNCTIONS(DECLARE_OPENGL_FUNCTION)
#undef DECLARE_OPENGL_FUNCTION
} // namespace dyn_libs
bool dyn_libs::LoadOpenGLLibrary(Error* error) bool LoadOpenGLLibrary(Error* error)
{ {
if (s_opengl_library.IsOpen()) if (s_locals.opengl_library.IsOpen())
return true; return true;
else if (!s_opengl_library.Open("opengl32.dll", error))
return false;
bool result = true;
#define RESOLVE_OPENGL_FUNCTION(F) result = result && s_opengl_library.GetSymbol(#F, &F);
OPENGL_FUNCTIONS(RESOLVE_OPENGL_FUNCTION);
#undef RESOLVE_OPENGL_FUNCTION
if (!result) std::call_once(s_locals.opengl_once_flag, [error]() {
{ if (!s_locals.opengl_library.Open("opengl32.dll", error))
CloseOpenGLLibrary(); {
Error::SetStringView(error, "One or more required functions from opengl32.dll is missing."); Error::AddPrefix(error, "Failed to load xcb: ");
return false; return;
} }
std::atexit(&CloseOpenGLLibrary); static const DynamicLibrary::SymbolTable symbols[] = {
return true; #define SYMBOL_ENTRY(F) {#F, reinterpret_cast<void**>(&s_locals.F)},
} OPENGL_FUNCTIONS(SYMBOL_ENTRY)
#undef SYMBOL_ENTRY
};
void dyn_libs::CloseOpenGLLibrary() if (!s_locals.opengl_library.ResolveSymbols(symbols, error))
{ DynamicLibrary::ClearSymbols(symbols);
#define CLOSE_OPENGL_FUNCTION(F) F = nullptr; });
OPENGL_FUNCTIONS(CLOSE_OPENGL_FUNCTION);
#undef CLOSE_OPENGL_FUNCTION
s_opengl_library.Close(); return s_locals.opengl_library.IsOpen();
} }
#undef OPENGL_FUNCTIONS void* GetProcAddressCallback(const char* name)
void* dyn_libs::GetProcAddressCallback(const char* name)
{ {
void* addr = dyn_libs::wglGetProcAddress(name); void* addr = s_locals.wglGetProcAddress(name);
if (addr) if (addr)
return addr; return addr;
// try opengl32.dll // try opengl32.dll
return s_opengl_library.GetSymbolAddress(name); return s_locals.opengl_library.GetSymbolAddress(name);
} }
static bool ReloadWGL(HDC dc, Error* error) static bool ReloadWGL(HDC dc, Error* error)
{ {
if (!gladLoadWGL(dc, [](const char* name) { return (GLADapiproc)dyn_libs::wglGetProcAddress(name); })) if (!gladLoadWGL(dc, [](const char* name) { return (GLADapiproc)s_locals.wglGetProcAddress(name); }))
{ {
Error::SetStringView(error, "Loading GLAD WGL functions failed"); Error::SetStringView(error, "Loading GLAD WGL functions failed");
return false; return false;
@ -100,10 +95,10 @@ OpenGLContextWGL::~OpenGLContextWGL()
{ {
if (m_rc) if (m_rc)
{ {
if (dyn_libs::wglGetCurrentContext() == m_rc) if (s_locals.wglGetCurrentContext() == m_rc)
dyn_libs::wglMakeCurrent(nullptr, nullptr); s_locals.wglMakeCurrent(nullptr, nullptr);
dyn_libs::wglDeleteContext(m_rc); s_locals.wglDeleteContext(m_rc);
} }
if (m_pbuffer) if (m_pbuffer)
@ -119,7 +114,7 @@ std::unique_ptr<OpenGLContext> OpenGLContextWGL::Create(WindowInfo& wi, SurfaceH
std::span<const Version> versions_to_try, Error* error) std::span<const Version> versions_to_try, Error* error)
{ {
std::unique_ptr<OpenGLContextWGL> context = std::make_unique<OpenGLContextWGL>(); std::unique_ptr<OpenGLContextWGL> context = std::make_unique<OpenGLContextWGL>();
if (!dyn_libs::LoadOpenGLLibrary(error) || !context->Initialize(wi, surface, versions_to_try, error)) if (!LoadOpenGLLibrary(error) || !context->Initialize(wi, surface, versions_to_try, error))
context.reset(); context.reset();
return context; return context;
@ -159,7 +154,7 @@ bool OpenGLContextWGL::Initialize(WindowInfo& wi, SurfaceHandle* surface, std::s
void* OpenGLContextWGL::GetProcAddress(const char* name) void* OpenGLContextWGL::GetProcAddress(const char* name)
{ {
return dyn_libs::GetProcAddressCallback(name); return GetProcAddressCallback(name);
} }
OpenGLContext::SurfaceHandle OpenGLContextWGL::CreateSurface(WindowInfo& wi, Error* error /*= nullptr*/) OpenGLContext::SurfaceHandle OpenGLContextWGL::CreateSurface(WindowInfo& wi, Error* error /*= nullptr*/)
@ -180,7 +175,7 @@ void OpenGLContextWGL::DestroySurface(SurfaceHandle handle)
return; return;
// current buffer? switch to pbuffer first // current buffer? switch to pbuffer first
if (dyn_libs::wglGetCurrentDC() == static_cast<HDC>(handle)) if (s_locals.wglGetCurrentDC() == static_cast<HDC>(handle))
MakeCurrent(nullptr); MakeCurrent(nullptr);
DeleteDC(static_cast<HDC>(handle)); DeleteDC(static_cast<HDC>(handle));
@ -201,7 +196,7 @@ bool OpenGLContextWGL::SwapBuffers()
bool OpenGLContextWGL::IsCurrent() const bool OpenGLContextWGL::IsCurrent() const
{ {
return (m_rc && dyn_libs::wglGetCurrentContext() == m_rc); return (m_rc && s_locals.wglGetCurrentContext() == m_rc);
} }
bool OpenGLContextWGL::MakeCurrent(SurfaceHandle surface, Error* error /* = nullptr */) bool OpenGLContextWGL::MakeCurrent(SurfaceHandle surface, Error* error /* = nullptr */)
@ -212,9 +207,11 @@ bool OpenGLContextWGL::MakeCurrent(SurfaceHandle surface, Error* error /* = null
else if (m_current_dc == new_dc) else if (m_current_dc == new_dc)
return true; return true;
if (!dyn_libs::wglMakeCurrent(new_dc, m_rc)) if (!s_locals.wglMakeCurrent(new_dc, m_rc))
{ {
ERROR_LOG("wglMakeCurrent() failed: {}", GetLastError()); const DWORD err = GetLastError();
ERROR_LOG("wglMakeCurrent() failed: {}", err);
Error::SetWin32(error, "wglMakeCurrent() failed: ", err);
return false; return false;
} }
@ -224,7 +221,7 @@ bool OpenGLContextWGL::MakeCurrent(SurfaceHandle surface, Error* error /* = null
bool OpenGLContextWGL::DoneCurrent() bool OpenGLContextWGL::DoneCurrent()
{ {
if (!dyn_libs::wglMakeCurrent(m_current_dc, nullptr)) if (!s_locals.wglMakeCurrent(m_current_dc, nullptr))
return false; return false;
m_current_dc = nullptr; m_current_dc = nullptr;
@ -388,16 +385,16 @@ HDC OpenGLContextWGL::GetPBufferDC(Error* error)
ScopedGuard temp_rc_guard([&temp_rc, hdc]() { ScopedGuard temp_rc_guard([&temp_rc, hdc]() {
if (temp_rc) if (temp_rc)
{ {
dyn_libs::wglMakeCurrent(hdc, nullptr); s_locals.wglMakeCurrent(hdc, nullptr);
dyn_libs::wglDeleteContext(temp_rc); s_locals.wglDeleteContext(temp_rc);
} }
}); });
if (!GLAD_WGL_ARB_pbuffer) if (!GLAD_WGL_ARB_pbuffer)
{ {
// we're probably running completely surfaceless... need a temporary context. // we're probably running completely surfaceless... need a temporary context.
temp_rc = dyn_libs::wglCreateContext(hdc); temp_rc = s_locals.wglCreateContext(hdc);
if (!temp_rc || !dyn_libs::wglMakeCurrent(hdc, temp_rc)) if (!temp_rc || !s_locals.wglMakeCurrent(hdc, temp_rc))
{ {
Error::SetStringView(error, "Failed to create temporary context to load WGL for pbuffer."); Error::SetStringView(error, "Failed to create temporary context to load WGL for pbuffer.");
return NULL; return NULL;
@ -444,7 +441,7 @@ HDC OpenGLContextWGL::GetPBufferDC(Error* error)
bool OpenGLContextWGL::CreateAnyContext(HDC hdc, HGLRC share_context, bool make_current, Error* error) bool OpenGLContextWGL::CreateAnyContext(HDC hdc, HGLRC share_context, bool make_current, Error* error)
{ {
m_rc = dyn_libs::wglCreateContext(hdc); m_rc = s_locals.wglCreateContext(hdc);
if (!m_rc) if (!m_rc)
{ {
Error::SetWin32(error, "wglCreateContext() failed: ", GetLastError()); Error::SetWin32(error, "wglCreateContext() failed: ", GetLastError());
@ -453,7 +450,7 @@ bool OpenGLContextWGL::CreateAnyContext(HDC hdc, HGLRC share_context, bool make_
if (make_current) if (make_current)
{ {
if (!dyn_libs::wglMakeCurrent(hdc, m_rc)) if (!s_locals.wglMakeCurrent(hdc, m_rc))
{ {
Error::SetWin32(error, "wglMakeCurrent() failed: ", GetLastError()); Error::SetWin32(error, "wglMakeCurrent() failed: ", GetLastError());
return false; return false;
@ -469,7 +466,7 @@ bool OpenGLContextWGL::CreateAnyContext(HDC hdc, HGLRC share_context, bool make_
} }
} }
if (share_context && !dyn_libs::wglShareLists(share_context, m_rc)) if (share_context && !s_locals.wglShareLists(share_context, m_rc))
{ {
Error::SetWin32(error, "wglShareLists() failed: ", GetLastError()); Error::SetWin32(error, "wglShareLists() failed: ", GetLastError());
return false; return false;
@ -542,10 +539,10 @@ bool OpenGLContextWGL::CreateVersionContext(const Version& version, HDC hdc, HGL
// destroy and swap contexts // destroy and swap contexts
if (m_rc) if (m_rc)
{ {
if (!dyn_libs::wglMakeCurrent(hdc, make_current ? new_rc : nullptr)) if (!s_locals.wglMakeCurrent(hdc, make_current ? new_rc : nullptr))
{ {
Error::SetWin32(error, "wglMakeCurrent() failed: ", GetLastError()); Error::SetWin32(error, "wglMakeCurrent() failed: ", GetLastError());
dyn_libs::wglDeleteContext(new_rc); s_locals.wglDeleteContext(new_rc);
return false; return false;
} }
@ -555,7 +552,7 @@ bool OpenGLContextWGL::CreateVersionContext(const Version& version, HDC hdc, HGL
if (make_current && !ReloadWGL(hdc, error)) if (make_current && !ReloadWGL(hdc, error))
return false; return false;
dyn_libs::wglDeleteContext(m_rc); s_locals.wglDeleteContext(m_rc);
} }
m_rc = new_rc; m_rc = new_rc;

@ -12,13 +12,10 @@
#include <xcb/xcb.h> #include <xcb/xcb.h>
#include <memory> #include <memory>
#include <mutex>
LOG_CHANNEL(WindowInfo); LOG_CHANNEL(WindowInfo);
namespace {
namespace dyn_libs {
#define XCB_FUNCTIONS(X) \ #define XCB_FUNCTIONS(X) \
X(xcb_get_geometry) \ X(xcb_get_geometry) \
X(xcb_get_geometry_reply) \ X(xcb_get_geometry_reply) \
@ -39,19 +36,7 @@ namespace dyn_libs {
X(xcb_free_colormap_checked) \ X(xcb_free_colormap_checked) \
X(xcb_configure_window_checked) X(xcb_configure_window_checked)
static bool OpenXcb(Error* error); namespace {
static void CloseXcb();
static void CloseAll();
static DynamicLibrary s_xcb_library;
static DynamicLibrary s_x11xcb_library;
static bool s_close_registered = false;
#define ADD_FUNC(F) static decltype(&::F) F;
XCB_FUNCTIONS(ADD_FUNC);
#undef ADD_FUNC
} // namespace dyn_libs
template<typename T> template<typename T>
struct XCBPointerDeleter struct XCBPointerDeleter
@ -62,52 +47,45 @@ struct XCBPointerDeleter
template<typename T> template<typename T>
using XCBPointer = std::unique_ptr<T, XCBPointerDeleter<T>>; using XCBPointer = std::unique_ptr<T, XCBPointerDeleter<T>>;
} // namespace struct Locals
bool dyn_libs::OpenXcb(Error* error)
{ {
if (s_xcb_library.IsOpen()) DynamicLibrary xcb_library;
return true; std::once_flag xcb_once_flag;
const std::string libname = DynamicLibrary::GetVersionedFilename("xcb", 1);
if (!s_xcb_library.Open(libname.c_str(), error))
{
Error::AddPrefix(error, "Failed to load xcb: ");
return false;
}
#define LOAD_FUNC(F) \ #define ADD_FUNC(F) decltype(&::F) F;
if (!s_xcb_library.GetSymbol(#F, &F)) \ XCB_FUNCTIONS(ADD_FUNC)
{ \ #undef ADD_FUNC
Error::SetStringFmt(error, "Failed to find function {}", #F); \ };
CloseXcb(); \
return false; \
}
XCB_FUNCTIONS(LOAD_FUNC) } // namespace
#undef LOAD_FUNC
if (!s_close_registered) static bool OpenXcb(Error* error);
{
s_close_registered = true;
std::atexit(&dyn_libs::CloseAll);
}
return true; static Locals s_locals;
}
void dyn_libs::CloseXcb() bool OpenXcb(Error* error)
{ {
#define UNLOAD_FUNC(F) F = nullptr; if (s_locals.xcb_library.IsOpen())
XCB_FUNCTIONS(UNLOAD_FUNC) return true;
#undef UNLOAD_FUNC
s_xcb_library.Close(); std::call_once(s_locals.xcb_once_flag, [error]() {
} if (!s_locals.xcb_library.Open(DynamicLibrary::GetVersionedFilename("xcb", 1).c_str(), error))
{
Error::AddPrefix(error, "Failed to load xcb: ");
return;
}
void dyn_libs::CloseAll() static const DynamicLibrary::SymbolTable symbols[] = {
{ #define SYMBOL_ENTRY(F) {#F, reinterpret_cast<void**>(&s_locals.F)},
CloseXcb(); XCB_FUNCTIONS(SYMBOL_ENTRY)
#undef SYMBOL_ENTRY
};
if (!s_locals.xcb_library.ResolveSymbols(symbols, error))
DynamicLibrary::ClearSymbols(symbols);
});
return s_locals.xcb_library.IsOpen();
} }
X11Window::X11Window() = default; X11Window::X11Window() = default;
@ -163,14 +141,14 @@ bool X11Window::Create(xcb_connection_t* connection, xcb_window_t parent_window,
{ {
xcb_generic_error_t* xerror; xcb_generic_error_t* xerror;
if (!dyn_libs::OpenXcb(error)) if (!OpenXcb(error))
return false; return false;
m_connection = connection; m_connection = connection;
m_parent_window = parent_window; m_parent_window = parent_window;
XCBPointer<xcb_get_geometry_reply_t> gwa( XCBPointer<xcb_get_geometry_reply_t> gwa(
dyn_libs::xcb_get_geometry_reply(connection, dyn_libs::xcb_get_geometry(connection, parent_window), &xerror)); s_locals.xcb_get_geometry_reply(connection, s_locals.xcb_get_geometry(connection, parent_window), &xerror));
if (!gwa) if (!gwa)
{ {
SetErrorObject(error, "xcb_get_geometry_reply() failed: ", xerror); SetErrorObject(error, "xcb_get_geometry_reply() failed: ", xerror);
@ -182,16 +160,16 @@ bool X11Window::Create(xcb_connection_t* connection, xcb_window_t parent_window,
// Need to find the root window to get an appropriate depth. Needed for NVIDIA+XWayland. // Need to find the root window to get an appropriate depth. Needed for NVIDIA+XWayland.
int visual_depth = XCB_COPY_FROM_PARENT; int visual_depth = XCB_COPY_FROM_PARENT;
for (xcb_screen_iterator_t it = dyn_libs::xcb_setup_roots_iterator(dyn_libs::xcb_get_setup(connection)); it.rem != 0; for (xcb_screen_iterator_t it = s_locals.xcb_setup_roots_iterator(s_locals.xcb_get_setup(connection)); it.rem != 0;
dyn_libs::xcb_screen_next(&it)) s_locals.xcb_screen_next(&it))
{ {
if (it.data->root == gwa->root) if (it.data->root == gwa->root)
{ {
for (xcb_depth_iterator_t dit = dyn_libs::xcb_screen_allowed_depths_iterator(it.data); dit.rem != 0; for (xcb_depth_iterator_t dit = s_locals.xcb_screen_allowed_depths_iterator(it.data); dit.rem != 0;
dyn_libs::xcb_depth_next(&dit)) s_locals.xcb_depth_next(&dit))
{ {
const int len = dyn_libs::xcb_depth_visuals_length(dit.data); const int len = s_locals.xcb_depth_visuals_length(dit.data);
const xcb_visualtype_t* visuals = dyn_libs::xcb_depth_visuals(dit.data); const xcb_visualtype_t* visuals = s_locals.xcb_depth_visuals(dit.data);
int idx = 0; int idx = 0;
for (; idx < len; idx++) for (; idx < len; idx++)
{ {
@ -210,24 +188,24 @@ bool X11Window::Create(xcb_connection_t* connection, xcb_window_t parent_window,
WARNING_LOG("Could not find visual's depth."); WARNING_LOG("Could not find visual's depth.");
// ID isn't "used" until the call succeeds. // ID isn't "used" until the call succeeds.
m_colormap = dyn_libs::xcb_generate_id(connection); m_colormap = s_locals.xcb_generate_id(connection);
if ((xerror = dyn_libs::xcb_request_check( if ((xerror = s_locals.xcb_request_check(
connection, connection,
dyn_libs::xcb_create_colormap_checked(connection, XCB_COLORMAP_ALLOC_NONE, m_colormap, parent_window, vi)))) s_locals.xcb_create_colormap_checked(connection, XCB_COLORMAP_ALLOC_NONE, m_colormap, parent_window, vi))))
{ {
SetErrorObject(error, "xcb_create_colormap_checked() failed: ", xerror); SetErrorObject(error, "xcb_create_colormap_checked() failed: ", xerror);
m_colormap = {}; m_colormap = {};
return false; return false;
} }
m_window = dyn_libs::xcb_generate_id(connection); m_window = s_locals.xcb_generate_id(connection);
const u32 window_values[] = {XCB_PIXMAP_NONE, 0u, m_colormap}; const u32 window_values[] = {XCB_PIXMAP_NONE, 0u, m_colormap};
xerror = dyn_libs::xcb_request_check( xerror = s_locals.xcb_request_check(
connection, connection,
dyn_libs::xcb_create_window_checked(connection, visual_depth, m_window, parent_window, 0, 0, m_width, m_height, 0, s_locals.xcb_create_window_checked(connection, visual_depth, m_window, parent_window, 0, 0, m_width, m_height, 0,
XCB_WINDOW_CLASS_INPUT_OUTPUT, vi, XCB_WINDOW_CLASS_INPUT_OUTPUT, vi,
XCB_CW_BACK_PIXMAP | XCB_CW_BORDER_PIXEL | XCB_CW_COLORMAP, window_values)); XCB_CW_BACK_PIXMAP | XCB_CW_BORDER_PIXEL | XCB_CW_COLORMAP, window_values));
if (xerror) if (xerror)
{ {
SetErrorObject(error, "xcb_create_window_checked() failed: ", xerror); SetErrorObject(error, "xcb_create_window_checked() failed: ", xerror);
@ -235,7 +213,7 @@ bool X11Window::Create(xcb_connection_t* connection, xcb_window_t parent_window,
return false; return false;
} }
xerror = dyn_libs::xcb_request_check(connection, dyn_libs::xcb_map_window_checked(connection, m_window)); xerror = s_locals.xcb_request_check(connection, s_locals.xcb_map_window_checked(connection, m_window));
if (xerror) if (xerror)
{ {
SetErrorObject(error, "xcb_map_window_checked() failed: ", xerror); SetErrorObject(error, "xcb_map_window_checked() failed: ", xerror);
@ -252,15 +230,14 @@ void X11Window::Destroy()
if (m_window) if (m_window)
{ {
if ((xerror = if ((xerror = s_locals.xcb_request_check(m_connection, s_locals.xcb_unmap_window_checked(m_connection, m_window))))
dyn_libs::xcb_request_check(m_connection, dyn_libs::xcb_unmap_window_checked(m_connection, m_window))))
{ {
SetErrorObject(&error, "xcb_unmap_window_checked() failed: ", xerror); SetErrorObject(&error, "xcb_unmap_window_checked() failed: ", xerror);
ERROR_LOG(error.GetDescription()); ERROR_LOG(error.GetDescription());
} }
if ((xerror = if ((xerror =
dyn_libs::xcb_request_check(m_connection, dyn_libs::xcb_destroy_window_checked(m_connection, m_window)))) s_locals.xcb_request_check(m_connection, s_locals.xcb_destroy_window_checked(m_connection, m_window))))
{ {
SetErrorObject(&error, "xcb_destroy_window_checked() failed: ", xerror); SetErrorObject(&error, "xcb_destroy_window_checked() failed: ", xerror);
ERROR_LOG(error.GetDescription()); ERROR_LOG(error.GetDescription());
@ -273,7 +250,7 @@ void X11Window::Destroy()
if (m_colormap) if (m_colormap)
{ {
if ((xerror = if ((xerror =
dyn_libs::xcb_request_check(m_connection, dyn_libs::xcb_free_colormap_checked(m_connection, m_colormap)))) s_locals.xcb_request_check(m_connection, s_locals.xcb_free_colormap_checked(m_connection, m_colormap))))
{ {
SetErrorObject(&error, "xcb_free_colormap_checked() failed: ", xerror); SetErrorObject(&error, "xcb_free_colormap_checked() failed: ", xerror);
ERROR_LOG(error.GetDescription()); ERROR_LOG(error.GetDescription());
@ -295,8 +272,8 @@ void X11Window::Resize(u16 width, u16 height)
} }
else else
{ {
XCBPointer<xcb_get_geometry_reply_t> gwa(dyn_libs::xcb_get_geometry_reply( XCBPointer<xcb_get_geometry_reply_t> gwa(
m_connection, dyn_libs::xcb_get_geometry(m_connection, m_parent_window), &xerror)); s_locals.xcb_get_geometry_reply(m_connection, s_locals.xcb_get_geometry(m_connection, m_parent_window), &xerror));
if (!gwa) if (!gwa)
{ {
SetErrorObject(&error, "xcb_get_geometry() failed: ", xerror); SetErrorObject(&error, "xcb_get_geometry() failed: ", xerror);
@ -309,8 +286,8 @@ void X11Window::Resize(u16 width, u16 height)
} }
u32 values[] = {width, height}; u32 values[] = {width, height};
if ((xerror = dyn_libs::xcb_request_check( if ((xerror = s_locals.xcb_request_check(
m_connection, dyn_libs::xcb_configure_window_checked( m_connection, s_locals.xcb_configure_window_checked(
m_connection, m_window, XCB_CONFIG_WINDOW_WIDTH | XCB_CONFIG_WINDOW_HEIGHT, values)))) m_connection, m_window, XCB_CONFIG_WINDOW_WIDTH | XCB_CONFIG_WINDOW_HEIGHT, values))))
{ {
SetErrorObject(&error, "xcb_configure_window_checked() failed: ", xerror); SetErrorObject(&error, "xcb_configure_window_checked() failed: ", xerror);

Loading…
Cancel
Save