diff --git a/ThunkLibs/include/common/X11Manager.h b/ThunkLibs/include/common/X11Manager.h index 01ad7093a..a0b1f9e8e 100644 --- a/ThunkLibs/include/common/X11Manager.h +++ b/ThunkLibs/include/common/X11Manager.h @@ -2,6 +2,7 @@ #include <cstdio> #include <cstdlib> +#include <cstdint> #include <dlfcn.h> #include <mutex> #include <unordered_map> @@ -9,6 +10,14 @@ #include <X11/Xlib.h> #include <xcb/xcb.h> +#ifdef IS_32BIT_THUNK +using guest_long = int32_t; +using guest_size_t = int32_t; +#else +using guest_long = long; +using guest_size_t = size_t; +#endif + /** * Guest X11 displays and xcb connections can't be used by the host, so * instead an intermediary object is created and mapped to the original @@ -47,7 +56,7 @@ struct X11Manager { std::unique_lock lock(mutex); auto [it, inserted] = displays.emplace(GuestDisplay, nullptr); if (inserted) { - auto host_display = HostXOpenDisplay(DisplayString(GuestDisplay)); + auto host_display = HostXOpenDisplay(GuestXDisplayString(GuestDisplay)); fprintf(stderr, "Opening host-side X11 display: %p -> %p\n", GuestDisplay, host_display); if (!host_display) { fprintf(stderr, "ERROR: Could not open X display\n"); @@ -104,7 +113,7 @@ struct X11Manager { // NOTE: Struct pointers are replaced by void* to avoid involving data layout conversion here. int (*GuestXSync)(void*, int) = nullptr; - void* (*GuestXGetVisualInfo)(void*, long, void*, int*) = nullptr; + void* (*GuestXGetVisualInfo)(void*, guest_long, void*, int*) = nullptr; // XDisplayString internally just reads data from _XDisplay's internal struct definition. // This breaks when data layout is different, so allow reading from a guest context instead. diff --git a/ThunkLibs/libGL/libGL_Guest.cpp b/ThunkLibs/libGL/libGL_Guest.cpp index 1e264a6fa..120e28607 100644 --- a/ThunkLibs/libGL/libGL_Guest.cpp +++ b/ThunkLibs/libGL/libGL_Guest.cpp @@ -16,9 +16,10 @@ $end_info$ #undef GL_ARB_viewport_array #include "glcorearb.h" -#include <stdio.h> -#include <cstdlib> #include <dlfcn.h> +#include <cstdio> +#include <cstdlib> +#include <cstring> #include <functional> #include <string_view> #include <unordered_map> diff --git a/ThunkLibs/libGL/libGL_Host.cpp b/ThunkLibs/libGL/libGL_Host.cpp index cfab36e95..3c76205e5 100644 --- a/ThunkLibs/libGL/libGL_Host.cpp +++ b/ThunkLibs/libGL/libGL_Host.cpp @@ -35,7 +35,7 @@ struct host_layout<_XDisplay*> { static X11Manager x11_manager; -static void* (*GuestMalloc)(size_t) = nullptr; +static void* (*GuestMalloc)(guest_size_t) = nullptr; host_layout<_XDisplay*>::host_layout(guest_layout<_XDisplay*>& guest) : guest_display(guest.force_get_host_pointer()) { @@ -136,10 +136,19 @@ auto fexfn_impl_libGL_glXGetProcAddress(const GLubyte* name) -> void (*)() { return (VoidFn)fexfn_impl_libGL_glXGetConfig; } else if (name_sv == "glXGetVisualFromFBConfig") { return (VoidFn)fexfn_impl_libGL_glXGetVisualFromFBConfig; +#ifdef IS_32BIT_THUNK + } else if (name_sv == "glXGetSelectedEvent") { + return (VoidFn)fexfn_impl_libGL_glXGetSelectedEvent; + } else if (name_sv == "glXGetSelectedEventSGIX") { + return (VoidFn)fexfn_impl_libGL_glXGetSelectedEventSGIX; +#endif } return (VoidFn)glXGetProcAddress((const GLubyte*)name); } +// TODO: unsigned int *glXEnumerateVideoDevicesNV (Display *dpy, int screen, int *nelements); + + void fexfn_impl_libGL_glCompileShaderIncludeARB(GLuint a_0, GLsizei Count, guest_layout<const GLchar* const*> a_2, const GLint* a_3) { // TODO: Only on 32-bit auto sources = (const char**)alloca(Count * sizeof(const char*)); @@ -282,7 +291,8 @@ static XVisualInfo* LookupHostVisualInfo(Display* HostDisplay, guest_layout<XVis } int num_matches; - auto ret = x11_manager.HostXGetVisualInfo(HostDisplay, VisualScreenMask | VisualIDMask, GuestInfo.force_get_host_pointer(), &num_matches); + auto HostInfo = host_layout<XVisualInfo> {*GuestInfo.get_pointer()}.data; + auto ret = x11_manager.HostXGetVisualInfo(HostDisplay, uint64_t {VisualScreenMask | VisualIDMask}, &HostInfo, &num_matches); if (num_matches != 1) { fprintf(stderr, "ERROR: Did not find unique host XVisualInfo\n"); std::abort(); @@ -296,9 +306,17 @@ static guest_layout<XVisualInfo*> MapToGuestVisualInfo(Display* HostDisplay, XVi return guest_layout<XVisualInfo*> {.data = 0}; } - int num_matches; auto guest_display = x11_manager.HostToGuestDisplay(HostDisplay); - auto ret = x11_manager.GuestXGetVisualInfo(guest_display.get_pointer(), VisualScreenMask | VisualIDMask, HostInfo, &num_matches); +#ifndef IS_32BIT_THUNK + int num_matches; + auto GuestInfo = to_guest(to_host_layout(*HostInfo)); +#else + GuestStackBumpAllocator GuestStack; + auto& num_matches = *GuestStack.New<int>(); + auto& GuestInfo = *GuestStack.New<guest_layout<XVisualInfo>>(to_guest(to_host_layout(*HostInfo))); +#endif + auto ret = x11_manager.GuestXGetVisualInfo(guest_display.get_pointer(), VisualScreenMask | VisualIDMask, &GuestInfo, &num_matches); + if (num_matches != 1) { fprintf(stderr, "ERROR: Did not find unique guest XVisualInfo\n"); std::abort(); @@ -409,6 +427,17 @@ void fexfn_impl_libGL_glVertexArrayVertexBuffers(GLuint a_0, GLuint a_1, GLsizei } fexldr_ptr_libGL_glVertexArrayVertexBuffers(a_0, a_1, count, a_3, HostOffsets, a_5); } + +void fexfn_impl_libGL_glXGetSelectedEvent(Display* Display, GLXDrawable Drawable, guest_layout<uint32_t*> Mask) { + unsigned long HostMask; + fexldr_ptr_libGL_glXGetSelectedEvent(Display, Drawable, &HostMask); + *Mask.get_pointer() = HostMask; +} +void fexfn_impl_libGL_glXGetSelectedEventSGIX(Display* Display, GLXDrawable Drawable, guest_layout<uint32_t*> Mask) { + unsigned long HostMask; + fexldr_ptr_libGL_glXGetSelectedEventSGIX(Display, Drawable, &HostMask); + *Mask.get_pointer() = HostMask; +} #endif EXPORTS(libGL) diff --git a/ThunkLibs/libGL/libGL_interface.cpp b/ThunkLibs/libGL/libGL_interface.cpp index 17dc3604a..8765c93d2 100644 --- a/ThunkLibs/libGL/libGL_interface.cpp +++ b/ThunkLibs/libGL/libGL_interface.cpp @@ -74,7 +74,6 @@ struct fex_gen_config : fexgen::generate_guest_symtable, fexgen::indirect_guest_ template<auto, int, typename = void> struct fex_gen_param {}; -#ifndef IS_32BIT_THUNK template<> struct fex_gen_config<glXQueryCurrentRendererStringMESA> {}; template<> @@ -135,8 +134,16 @@ template<> struct fex_gen_config<glXDestroyGLXPbufferSGIX> {}; template<> struct fex_gen_config<glXFreeContextEXT> {}; +#ifndef IS_32BIT_THUNK template<> struct fex_gen_config<glXGetSelectedEventSGIX> {}; +#else +template<> +struct fex_gen_config<glXGetSelectedEventSGIX> : fexgen::custom_host_impl {}; +template<> +struct fex_gen_param<glXGetSelectedEventSGIX, 2, unsigned long*> : fexgen::ptr_passthrough {}; +#endif + template<> struct fex_gen_config<glXQueryGLXPbufferSGIX> {}; template<> @@ -215,8 +222,15 @@ template<> struct fex_gen_config<glXDestroyWindow> {}; template<> struct fex_gen_config<glXFreeMemoryNV> {}; +#ifndef IS_32BIT_THUNK template<> struct fex_gen_config<glXGetSelectedEvent> {}; +#else +template<> +struct fex_gen_config<glXGetSelectedEvent> : fexgen::custom_host_impl {}; +template<> +struct fex_gen_param<glXGetSelectedEvent, 2, unsigned long*> : fexgen::ptr_passthrough {}; +#endif template<> struct fex_gen_config<glXQueryDrawable> {}; template<> @@ -241,7 +255,6 @@ template<> struct fex_gen_config<glXCreateContextAttribsARB> {}; template<> struct fex_gen_config<glXSwapIntervalEXT> {}; -#endif template<> struct fex_gen_config<glColorP3ui> {}; @@ -6352,7 +6365,6 @@ struct fex_gen_config<glGetPathTexGenfvNV> {}; template<> struct fex_gen_config<glBlendEquationSeparateATI> {}; -#ifndef IS_32BIT_THUNK // glx.h template<> struct fex_gen_config<glXWaitX> {}; @@ -6428,8 +6440,11 @@ template<> struct fex_gen_config<glXResetFrameCountNV> {}; template<> struct fex_gen_config<glXBindVideoCaptureDeviceNV> {}; +#ifndef IS_32BIT_THUNK +// TODO: 32-bit support template<> struct fex_gen_config<glXEnumerateVideoCaptureDevicesNV> {}; +#endif template<> struct fex_gen_config<glXLockVideoCaptureDeviceNV> {}; template<> @@ -6444,10 +6459,13 @@ template<> struct fex_gen_config<glXBindVideoImageNV> {}; template<> struct fex_gen_config<glXReleaseVideoImageNV> {}; +#ifndef IS_32BIT_THUNK +// TODO: 32-bit support template<> struct fex_gen_config<glXSendPbufferToVideoNV> {}; template<> struct fex_gen_config<glXGetVideoInfoNV> {}; +#endif template<> struct fex_gen_config<glXQueryHyperpipeNetworkSGIX> {}; template<> @@ -6482,6 +6500,8 @@ template<> struct fex_gen_config<glXChannelRectSyncSGIX> {}; template<> struct fex_gen_config<glXCushionSGI> {}; +#ifndef IS_32BIT_THUNK +// TODO: 32-bit support template<> struct fex_gen_config<glXGetTransparentIndexSUN> {}; #endif