From: Rémi Bernon rbernon@codeweavers.com
--- dlls/winex11.drv/desktop.c | 14 ---- dlls/winex11.drv/display.c | 154 ++++++++++++++++++++++++++++-------- dlls/winex11.drv/x11drv.h | 8 +- dlls/winex11.drv/xrandr.c | 136 +------------------------------ dlls/winex11.drv/xvidmode.c | 17 ---- 5 files changed, 122 insertions(+), 207 deletions(-)
diff --git a/dlls/winex11.drv/desktop.c b/dlls/winex11.drv/desktop.c index 7dc149b2e95..a0e24b837b9 100644 --- a/dlls/winex11.drv/desktop.c +++ b/dlls/winex11.drv/desktop.c @@ -122,19 +122,6 @@ BOOL is_virtual_desktop(void) return root_window != DefaultRootWindow( gdi_display ); }
-/* Virtual desktop display settings handler */ -static BOOL X11DRV_desktop_get_id( const WCHAR *device_name, ULONG_PTR *id, BOOL *is_primary ) -{ - WCHAR primary_adapter[CCHDEVICENAME]; - - if (!get_primary_adapter( primary_adapter ) || wcsicmp( primary_adapter, device_name )) - return FALSE; - - *is_primary = 1; - *id = 0; - return TRUE; -} - static void add_desktop_mode( DEVMODEW *mode, DWORD depth, DWORD width, DWORD height ) { mode->dmSize = sizeof(*mode); @@ -356,7 +343,6 @@ void X11DRV_init_desktop( Window win, unsigned int width, unsigned int height ) /* Initialize virtual desktop display settings handler */ settings_handler.name = "Virtual Desktop"; settings_handler.priority = 1000; - settings_handler.get_id = X11DRV_desktop_get_id; settings_handler.get_modes = X11DRV_desktop_get_modes; settings_handler.free_modes = X11DRV_desktop_free_modes; settings_handler.get_current_mode = X11DRV_desktop_get_current_mode; diff --git a/dlls/winex11.drv/display.c b/dlls/winex11.drv/display.c index 4465f3765b5..57cf8ca44ef 100644 --- a/dlls/winex11.drv/display.c +++ b/dlls/winex11.drv/display.c @@ -53,31 +53,135 @@ const unsigned int *depths;
static pthread_mutex_t settings_mutex = PTHREAD_MUTEX_INITIALIZER;
-void X11DRV_Settings_SetHandler(const struct x11drv_settings_handler *new_handler) +static struct current_mode { - if (new_handler->priority > settings_handler.priority) + ULONG_PTR id; + BOOL loaded; + BOOL primary; + DEVMODEW mode; +} *current_modes; +static int current_mode_count; + +void invalidate_current_mode_cache(void) +{ + pthread_mutex_lock( &settings_mutex ); + free( current_modes); + current_modes = NULL; + current_mode_count = 0; + pthread_mutex_unlock( &settings_mutex ); +} + +static BOOL get_current_mode( ULONG_PTR id, BOOL is_primary, DEVMODEW *mode ) +{ + struct current_mode *mode_ptr = NULL; + BOOL ret = FALSE; + INT mode_idx; + + pthread_mutex_lock( &settings_mutex ); + for (mode_idx = 0; mode_idx < current_mode_count; ++mode_idx) { - settings_handler = *new_handler; - TRACE("Display settings are now handled by: %s.\n", settings_handler.name); + if (current_modes[mode_idx].id != id) + continue; + + if (!current_modes[mode_idx].loaded) + { + mode_ptr = ¤t_modes[mode_idx]; + break; + } + + memcpy( mode, ¤t_modes[mode_idx].mode, sizeof(*mode) ); + pthread_mutex_unlock( &settings_mutex ); + return TRUE; + } + + if ((ret = settings_handler.get_current_mode( id, is_primary, mode )) && mode_ptr) + { + memcpy( &mode_ptr->mode, mode, sizeof(*mode) ); + mode_ptr->mode.dmSize = sizeof(*mode); + mode_ptr->mode.dmDriverExtra = 0; + mode_ptr->loaded = TRUE; } + pthread_mutex_unlock( &settings_mutex ); + return ret; }
-/*********************************************************************** - * Default handlers if resolution switching is not enabled - * - */ -static BOOL nores_get_id(const WCHAR *device_name, ULONG_PTR *id, BOOL *is_primary) +static BOOL get_adapter_id( const WCHAR *device_name, ULONG_PTR *id, BOOL *is_primary ) { - WCHAR primary_adapter[CCHDEVICENAME]; + struct current_mode *tmp_modes, *new_current_modes = NULL; + INT gpu_count, adapter_count, new_current_mode_count = 0; + INT gpu_idx, adapter_idx, display_idx; + struct gdi_adapter *adapters; + struct gdi_gpu *gpus; + WCHAR *end; + + /* Parse \.\DISPLAY%d */ + display_idx = wcstol( device_name + 11, &end, 10 ) - 1; + if (*end) + return FALSE; + + /* Update cache */ + pthread_mutex_lock( &settings_mutex ); + if (!current_modes) + { + if (!host_handler.get_gpus( &gpus, &gpu_count, FALSE )) + { + pthread_mutex_unlock( &settings_mutex ); + return FALSE; + } + + for (gpu_idx = 0; gpu_idx < gpu_count; ++gpu_idx) + { + if (!host_handler.get_adapters( gpus[gpu_idx].id, &adapters, &adapter_count )) + break; + + tmp_modes = realloc( new_current_modes, (new_current_mode_count + adapter_count) * sizeof(*tmp_modes) ); + if (!tmp_modes) + { + host_handler.free_adapters( adapters ); + break; + } + new_current_modes = tmp_modes;
- if (!get_primary_adapter( primary_adapter )) + for (adapter_idx = 0; adapter_idx < adapter_count; ++adapter_idx) + { + new_current_modes[new_current_mode_count + adapter_idx].id = adapters[adapter_idx].id; + new_current_modes[new_current_mode_count + adapter_idx].loaded = FALSE; + new_current_modes[new_current_mode_count + adapter_idx].primary = !!(adapters[adapter_idx].state_flags & DISPLAY_DEVICE_PRIMARY_DEVICE); + } + new_current_mode_count += adapter_count; + host_handler.free_adapters( adapters ); + } + host_handler.free_gpus( gpus ); + + if (new_current_modes) + { + free( current_modes ); + current_modes = new_current_modes; + current_mode_count = new_current_mode_count; + } + } + + if (display_idx >= current_mode_count) + { + pthread_mutex_unlock( &settings_mutex ); return FALSE; + }
- *is_primary = !wcsicmp( device_name, primary_adapter ); - *id = *is_primary ? 1 : 0; + *id = current_modes[display_idx].id; + *is_primary = current_modes[display_idx].primary; + pthread_mutex_unlock( &settings_mutex ); return TRUE; }
+void X11DRV_Settings_SetHandler(const struct x11drv_settings_handler *new_handler) +{ + if (new_handler->priority > settings_handler.priority) + { + settings_handler = *new_handler; + TRACE("Display settings are now handled by: %s.\n", settings_handler.name); + } +} + static BOOL nores_get_modes(ULONG_PTR id, DWORD flags, DEVMODEW **new_modes, UINT *mode_count) { RECT primary = get_host_primary_monitor_rect(); @@ -154,7 +258,6 @@ void X11DRV_Settings_Init(void)
nores_handler.name = "NoRes"; nores_handler.priority = 1; - nores_handler.get_id = nores_get_id; nores_handler.get_modes = nores_get_modes; nores_handler.free_modes = nores_free_modes; nores_handler.get_current_mode = nores_get_current_mode; @@ -197,24 +300,6 @@ void init_registry_display_settings(void) } }
-BOOL get_primary_adapter(WCHAR *name) -{ - DISPLAY_DEVICEW dd; - DWORD i; - - dd.cb = sizeof(dd); - for (i = 0; !NtUserEnumDisplayDevices( NULL, i, &dd, 0 ); ++i) - { - if (dd.StateFlags & DISPLAY_DEVICE_PRIMARY_DEVICE) - { - lstrcpyW(name, dd.DeviceName); - return TRUE; - } - } - - return FALSE; -} - static void set_display_depth(ULONG_PTR display_id, DWORD depth) { struct x11drv_display_depth *display_depth; @@ -273,7 +358,7 @@ BOOL X11DRV_GetCurrentDisplaySettings( LPCWSTR name, LPDEVMODEW devmode ) DEVMODEW mode; ULONG_PTR id;
- if (!settings_handler.get_id( name, &id, &is_primary ) || !settings_handler.get_current_mode( id, is_primary, &mode )) + if (!get_adapter_id( name, &id, &is_primary ) || !get_current_mode( id, is_primary, &mode )) { ERR("Failed to get %s current display settings.\n", wine_dbgstr_w(name)); return FALSE; @@ -391,6 +476,7 @@ static LONG apply_display_settings( DEVMODEW *displays, struct display_info *inf return ret; }
+ invalidate_current_mode_cache(); return DISP_CHANGE_SUCCESSFUL; }
@@ -417,7 +503,7 @@ LONG X11DRV_ChangeDisplaySettings( LPDEVMODEW displays, HWND hwnd, DWORD flags, if (!(infos = calloc( count, sizeof(*infos) ))) return DISP_CHANGE_FAILED; for (count = 0, mode = displays; mode->dmSize; mode = NEXT_DEVMODEW(mode), count++) { - if (!settings_handler.get_id( mode->dmDeviceName, &infos[count].id, &infos[count].is_primary )) goto done; + if (!get_adapter_id( mode->dmDeviceName, &infos[count].id, &infos[count].is_primary )) goto done; mode->dmPosition.x -= left_most; mode->dmPosition.y -= top_most; } diff --git a/dlls/winex11.drv/x11drv.h b/dlls/winex11.drv/x11drv.h index b5f948fa232..ec9a25d1acc 100644 --- a/dlls/winex11.drv/x11drv.h +++ b/dlls/winex11.drv/x11drv.h @@ -706,12 +706,6 @@ struct x11drv_settings_handler /* Higher priority can override handlers with a lower priority */ UINT priority;
- /* get_id() will be called to map a device name, e.g., \.\DISPLAY1 to a driver specific id. - * Following functions use this id to identify the device. - * - * Return FALSE if the device cannot be found and TRUE on success */ - BOOL (*get_id)(const WCHAR *device_name, ULONG_PTR *id, BOOL *is_primary); - /* get_modes() will be called to get a list of supported modes of the device of id in modes * with respect to flags, which could be 0, EDS_RAWMODE or EDS_ROTATEDMODE. If the implementation * uses dmDriverExtra then every DEVMODEW in the list must have the same dmDriverExtra value @@ -747,11 +741,11 @@ extern void X11DRV_Settings_SetHandler(const struct x11drv_settings_handler *han extern void X11DRV_init_desktop( Window win, unsigned int width, unsigned int height ) DECLSPEC_HIDDEN; extern void X11DRV_resize_desktop(void) DECLSPEC_HIDDEN; extern void init_registry_display_settings(void) DECLSPEC_HIDDEN; +extern void invalidate_current_mode_cache(void) DECLSPEC_HIDDEN; extern BOOL is_virtual_desktop(void) DECLSPEC_HIDDEN; extern BOOL is_desktop_fullscreen(void) DECLSPEC_HIDDEN; extern BOOL is_detached_mode(const DEVMODEW *) DECLSPEC_HIDDEN; extern BOOL create_desktop_win_data( Window win ) DECLSPEC_HIDDEN; -extern BOOL get_primary_adapter(WCHAR *) DECLSPEC_HIDDEN; void X11DRV_Settings_Init(void) DECLSPEC_HIDDEN;
void X11DRV_XF86VM_Init(void) DECLSPEC_HIDDEN; diff --git a/dlls/winex11.drv/xrandr.c b/dlls/winex11.drv/xrandr.c index 42cbe213333..94873f1bf55 100644 --- a/dlls/winex11.drv/xrandr.c +++ b/dlls/winex11.drv/xrandr.c @@ -143,22 +143,6 @@ static int XRandRErrorHandler(Display *dpy, XErrorEvent *event, void *arg) return 1; }
-/* XRandR 1.0 display settings handler */ -static BOOL xrandr10_get_id( const WCHAR *device_name, ULONG_PTR *id, BOOL *is_primary ) -{ - WCHAR primary_adapter[CCHDEVICENAME]; - - if (!get_primary_adapter( primary_adapter )) - return FALSE; - - /* RandR 1.0 only supports changing the primary adapter settings. - * For non-primary adapters, an id is still provided but getting - * and changing non-primary adapters' settings will be ignored. */ - *is_primary = !wcsicmp( device_name, primary_adapter ); - *id = *is_primary ? 1 : 0; - return TRUE; -} - static void add_xrandr10_mode( DEVMODEW *mode, DWORD depth, DWORD width, DWORD height, DWORD frequency, SizeID size_id ) { @@ -329,26 +313,6 @@ static LONG xrandr10_set_current_mode( ULONG_PTR id, BOOL is_primary, const DEVM
#ifdef HAVE_XRRGETPROVIDERRESOURCES
-static struct current_mode -{ - ULONG_PTR id; - BOOL loaded; - BOOL primary; - DEVMODEW mode; -} *current_modes; -static int current_mode_count; - -static pthread_mutex_t xrandr_mutex = PTHREAD_MUTEX_INITIALIZER; - -static void xrandr14_invalidate_current_mode_cache(void) -{ - pthread_mutex_lock( &xrandr_mutex ); - free( current_modes); - current_modes = NULL; - current_mode_count = 0; - pthread_mutex_unlock( &xrandr_mutex ); -} - static XRRScreenResources *xrandr_get_screen_resources(void) { XRRScreenResources *resources = pXRRGetScreenResourcesCurrent( gdi_display, root_window ); @@ -1192,7 +1156,7 @@ static void xrandr14_free_monitors( struct gdi_monitor *monitors, int count )
static BOOL xrandr14_device_change_handler( HWND hwnd, XEvent *event ) { - xrandr14_invalidate_current_mode_cache(); + invalidate_current_mode_cache(); if (hwnd == NtUserGetDesktopWindow() && NtUserGetWindowThread( hwnd, NULL ) == GetCurrentThreadId()) { X11DRV_DisplayDevices_Init( TRUE ); @@ -1220,75 +1184,6 @@ static void xrandr14_register_event_handlers(void) "XRandR ProviderChange" ); }
-/* XRandR 1.4 display settings handler */ -static BOOL xrandr14_get_id( const WCHAR *device_name, ULONG_PTR *id, BOOL *is_primary ) -{ - struct current_mode *tmp_modes, *new_current_modes = NULL; - INT gpu_count, adapter_count, new_current_mode_count = 0; - INT gpu_idx, adapter_idx, display_idx; - struct gdi_adapter *adapters; - struct gdi_gpu *gpus; - WCHAR *end; - - /* Parse \.\DISPLAY%d */ - display_idx = wcstol( device_name + 11, &end, 10 ) - 1; - if (*end) - return FALSE; - - /* Update cache */ - pthread_mutex_lock( &xrandr_mutex ); - if (!current_modes) - { - if (!xrandr14_get_gpus( &gpus, &gpu_count, FALSE )) - { - pthread_mutex_unlock( &xrandr_mutex ); - return FALSE; - } - - for (gpu_idx = 0; gpu_idx < gpu_count; ++gpu_idx) - { - if (!xrandr14_get_adapters( gpus[gpu_idx].id, &adapters, &adapter_count )) - break; - - tmp_modes = realloc( new_current_modes, (new_current_mode_count + adapter_count) * sizeof(*tmp_modes) ); - if (!tmp_modes) - { - xrandr14_free_adapters( adapters ); - break; - } - new_current_modes = tmp_modes; - - for (adapter_idx = 0; adapter_idx < adapter_count; ++adapter_idx) - { - new_current_modes[new_current_mode_count + adapter_idx].id = adapters[adapter_idx].id; - new_current_modes[new_current_mode_count + adapter_idx].loaded = FALSE; - new_current_modes[new_current_mode_count + adapter_idx].primary = !!(adapters[adapter_idx].state_flags & DISPLAY_DEVICE_PRIMARY_DEVICE); - } - new_current_mode_count += adapter_count; - xrandr14_free_adapters( adapters ); - } - xrandr14_free_gpus( gpus ); - - if (new_current_modes) - { - free( current_modes ); - current_modes = new_current_modes; - current_mode_count = new_current_mode_count; - } - } - - if (display_idx >= current_mode_count) - { - pthread_mutex_unlock( &xrandr_mutex ); - return FALSE; - } - - *id = current_modes[display_idx].id; - *is_primary = current_modes[display_idx].primary; - pthread_mutex_unlock( &xrandr_mutex ); - return TRUE; -} - static void add_xrandr14_mode( DEVMODEW *mode, XRRModeInfo *info, DWORD depth, DWORD frequency, DWORD orientation ) { @@ -1436,7 +1331,6 @@ static void xrandr14_free_modes( DEVMODEW *modes )
static BOOL xrandr14_get_current_mode( ULONG_PTR id, BOOL is_primary, DEVMODEW *mode ) { - struct current_mode *mode_ptr = NULL; XRRScreenResources *screen_resources; XRROutputInfo *output_info = NULL; RROutput output = (RROutput)id; @@ -1446,23 +1340,6 @@ static BOOL xrandr14_get_current_mode( ULONG_PTR id, BOOL is_primary, DEVMODEW * RECT primary; INT mode_idx;
- pthread_mutex_lock( &xrandr_mutex ); - for (mode_idx = 0; mode_idx < current_mode_count; ++mode_idx) - { - if (current_modes[mode_idx].id != id) - continue; - - if (!current_modes[mode_idx].loaded) - { - mode_ptr = ¤t_modes[mode_idx]; - break; - } - - memcpy( mode, ¤t_modes[mode_idx].mode, sizeof(*mode) ); - pthread_mutex_unlock( &xrandr_mutex ); - return TRUE; - } - screen_resources = xrandr_get_screen_resources(); if (!screen_resources) goto done; @@ -1523,14 +1400,6 @@ static BOOL xrandr14_get_current_mode( ULONG_PTR id, BOOL is_primary, DEVMODEW * ret = TRUE;
done: - if (ret && mode_ptr) - { - memcpy( &mode_ptr->mode, mode, sizeof(*mode) ); - mode_ptr->mode.dmSize = sizeof(*mode); - mode_ptr->mode.dmDriverExtra = 0; - mode_ptr->loaded = TRUE; - } - pthread_mutex_unlock( &xrandr_mutex ); if (crtc_info) pXRRFreeCrtcInfo( crtc_info ); if (output_info) @@ -1647,7 +1516,6 @@ done: if (output_info) pXRRFreeOutputInfo( output_info ); pXRRFreeScreenResources( screen_resources ); - xrandr14_invalidate_current_mode_cache(); return ret; }
@@ -1676,7 +1544,6 @@ void X11DRV_XRandR_Init(void)
settings_handler.name = "XRandR 1.0"; settings_handler.priority = 200; - settings_handler.get_id = xrandr10_get_id; settings_handler.get_modes = xrandr10_get_modes; settings_handler.free_modes = xrandr10_free_modes; settings_handler.get_current_mode = xrandr10_get_current_mode; @@ -1734,7 +1601,6 @@ void X11DRV_XRandR_Init(void)
settings_handler.name = "XRandR 1.4"; settings_handler.priority = 300; - settings_handler.get_id = xrandr14_get_id; settings_handler.get_modes = xrandr14_get_modes; settings_handler.free_modes = xrandr14_free_modes; settings_handler.get_current_mode = xrandr14_get_current_mode; diff --git a/dlls/winex11.drv/xvidmode.c b/dlls/winex11.drv/xvidmode.c index ca9444712d6..e0e59a8f801 100644 --- a/dlls/winex11.drv/xvidmode.c +++ b/dlls/winex11.drv/xvidmode.c @@ -84,22 +84,6 @@ static int XVidModeErrorHandler(Display *dpy, XErrorEvent *event, void *arg) return 1; }
-/* XF86VidMode display settings handler */ -static BOOL xf86vm_get_id(const WCHAR *device_name, ULONG_PTR *id, BOOL *is_primary) -{ - WCHAR primary_adapter[CCHDEVICENAME]; - - if (!get_primary_adapter( primary_adapter )) - return FALSE; - - /* XVidMode only supports changing the primary adapter settings. - * For non-primary adapters, an id is still provided but getting - * and changing non-primary adapters' settings will be ignored. */ - *is_primary = !wcsicmp( device_name, primary_adapter ); - *id = *is_primary ? 1 : 0; - return TRUE; -} - static void add_xf86vm_mode(DEVMODEW *mode, DWORD depth, const XF86VidModeModeInfo *mode_info) { mode->dmSize = sizeof(*mode); @@ -312,7 +296,6 @@ void X11DRV_XF86VM_Init(void)
xf86vm_handler.name = "XF86VidMode"; xf86vm_handler.priority = 100; - xf86vm_handler.get_id = xf86vm_get_id; xf86vm_handler.get_modes = xf86vm_get_modes; xf86vm_handler.free_modes = xf86vm_free_modes; xf86vm_handler.get_current_mode = xf86vm_get_current_mode;