[PATCH 0/3] MR5317: win32u: Fix a possible condition that makes EnumDisplayMonitors() not reporting any monitors.
When there are two monitors and they are mirrored, both of them are considered primary. When the first primary monitor happens to be a clone, EnumDisplayMonitors() ends up not reporting any monitors because should_enumerate_monitor() returns FALSE and we break out the loop to enumerate primary monitors after that. This is a regression from b59619d and my review comments. My indent was to break out of the loop after finding the *master* primary monitor, not cloned primary monitors, to avoid unnecessary iterations. However, the primary monitor count is small and it's cleaner this way so let's break when should_enumerate_monitor() returns TRUE. -- https://gitlab.winehq.org/wine/wine/-/merge_requests/5317
From: Zhiyi Zhang <zzhang(a)codeweavers.com> When there are two monitors and they are mirrored, both of them are considered primary. When the first primary monitor happens to be a clone, EnumDisplayMonitors() ends up not reporting any monitors because should_enumerate_monitor() returns FALSE and we break out the loop to enumerate primary monitors after that. This is a regression from b59619d and my review comments. My indent was to break out of the loop after finding the *master* primary monitor, not cloned primary monitors, to avoid unnecessary iterations. However, the primary monitor count is small and it's cleaner this way so let's break when should_enumerate_monitor() returns TRUE. --- dlls/win32u/sysparams.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/dlls/win32u/sysparams.c b/dlls/win32u/sysparams.c index 7cefb3822a3..d2f7396971b 100644 --- a/dlls/win32u/sysparams.c +++ b/dlls/win32u/sysparams.c @@ -3459,8 +3459,10 @@ BOOL WINAPI NtUserEnumDisplayMonitors( HDC hdc, RECT *rect, MONITORENUMPROC proc { if (!is_monitor_primary( monitor )) continue; if (should_enumerate_monitor( monitor, &origin, &limit, &enum_info[count].rect )) + { enum_info[count++].handle = monitor->handle; - break; + break; + } } /* then non-primary monitors */ -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/5317
From: Zhiyi Zhang <zzhang(a)codeweavers.com> Only one monitor in a mirrored monitor set contributes to the result of GetSystemMetrics(SM_CMONITORS). Tested manually on Win7 and Win10. --- dlls/win32u/sysparams.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/dlls/win32u/sysparams.c b/dlls/win32u/sysparams.c index d2f7396971b..6e638922629 100644 --- a/dlls/win32u/sysparams.c +++ b/dlls/win32u/sysparams.c @@ -3348,15 +3348,15 @@ struct monitor_enum_info RECT rect; }; -static unsigned int active_monitor_count(void) +static unsigned int active_unique_monitor_count(void) { struct monitor *monitor; unsigned int count = 0; LIST_FOR_EACH_ENTRY(monitor, &monitors, struct monitor, entry) { - if (!is_monitor_active( monitor )) continue; - count++; + if (is_monitor_active( monitor ) && !monitor->is_clone) + count++; } return count; } @@ -5941,7 +5941,7 @@ int get_system_metrics( int index ) return rect.bottom - rect.top; case SM_CMONITORS: if (!lock_display_devices()) return FALSE; - ret = active_monitor_count(); + ret = active_unique_monitor_count(); unlock_display_devices(); return ret; case SM_SAMEDISPLAYFORMAT: -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/5317
From: Zhiyi Zhang <zzhang(a)codeweavers.com> These functions don't need to enumerate mirrored monitor clones. --- dlls/win32u/sysparams.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/dlls/win32u/sysparams.c b/dlls/win32u/sysparams.c index 6e638922629..07b9d46d9eb 100644 --- a/dlls/win32u/sysparams.c +++ b/dlls/win32u/sysparams.c @@ -2248,7 +2248,7 @@ RECT get_virtual_screen_rect( UINT dpi ) LIST_FOR_EACH_ENTRY( monitor, &monitors, struct monitor, entry ) { - if (!is_monitor_active( monitor )) continue; + if (!is_monitor_active( monitor ) || monitor->is_clone) continue; union_rect( &rect, &rect, &monitor->rc_monitor ); } @@ -2269,7 +2269,7 @@ static BOOL is_window_rect_full_screen( const RECT *rect ) { RECT monrect; - if (!is_monitor_active( monitor )) continue; + if (!is_monitor_active( monitor ) || monitor->is_clone) continue; monrect = map_dpi_rect( monitor->rc_monitor, get_monitor_dpi( monitor->handle ), get_thread_dpi() ); @@ -3558,7 +3558,7 @@ HMONITOR monitor_from_rect( const RECT *rect, UINT flags, UINT dpi ) { RECT intersect, monitor_rect; - if (!is_monitor_active( monitor )) continue; + if (!is_monitor_active( monitor ) || monitor->is_clone) continue; monitor_rect = map_dpi_rect( monitor->rc_monitor, get_monitor_dpi( monitor->handle ), system_dpi ); if (intersect_rect( &intersect, &monitor_rect, &r )) -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/5317
This merge request was approved by Rémi Bernon. -- https://gitlab.winehq.org/wine/wine/-/merge_requests/5317
participants (3)
-
Rémi Bernon -
Zhiyi Zhang -
Zhiyi Zhang (@zhiyi)