server-Shared_Memory: Cache the result of GetForegroundWindow.

This commit is contained in:
Sebastian Lackner 2015-03-21 22:47:01 +01:00
parent d1451cd34f
commit 8c880d262f
3 changed files with 130 additions and 0 deletions

View File

@ -1022,6 +1022,9 @@ if test "$enable_server_Shared_Memory" -eq 1; then
if test "$enable_ntdll_Threading" -gt 1; then
abort "Patchset ntdll-Threading disabled, but server-Shared_Memory depends on that."
fi
if test "$enable_server_ClipCursor" -gt 1; then
abort "Patchset server-ClipCursor disabled, but server-Shared_Memory depends on that."
fi
if test "$enable_server_Key_State" -gt 1; then
abort "Patchset server-Key_State disabled, but server-Shared_Memory depends on that."
fi
@ -1033,6 +1036,7 @@ if test "$enable_server_Shared_Memory" -eq 1; then
fi
enable_dinput_Events=1
enable_ntdll_Threading=1
enable_server_ClipCursor=1
enable_server_Key_State=1
enable_server_PeekMessage=1
enable_user32_Key_State=1
@ -3876,6 +3880,7 @@ if test "$enable_server_Shared_Memory" -eq 1; then
patch_apply server-Shared_Memory/0007-user32-Move-key_state-cache-into-separate-structure.patch
patch_apply server-Shared_Memory/0008-server-Store-a-list-of-associated-queues-for-each-th.patch
patch_apply server-Shared_Memory/0009-user32-Get-rid-of-wineserver-call-for-GetActiveWindo.patch
patch_apply server-Shared_Memory/0010-user32-Cache-the-result-of-GetForegroundWindow.patch
(
echo '+ { "Sebastian Lackner", "ntdll: Implement virtual_map_shared_memory.", 1 },';
echo '+ { "Michael Müller", "server: Implement support for global and local shared memory blocks based on memfd.", 1 },';
@ -3886,6 +3891,7 @@ if test "$enable_server_Shared_Memory" -eq 1; then
echo '+ { "Sebastian Lackner", "user32: Move key_state cache into separate structure.", 1 },';
echo '+ { "Sebastian Lackner", "server: Store a list of associated queues for each thread input.", 1 },';
echo '+ { "Sebastian Lackner", "user32: Get rid of wineserver call for GetActiveWindow, GetFocus, GetCapture.", 1 },';
echo '+ { "Sebastian Lackner", "user32: Cache the result of GetForegroundWindow.", 1 },';
) >> "$patchlist"
fi

View File

@ -0,0 +1,123 @@
From 8d67b53668f39c8684ddc8be8937f70eb50774df Mon Sep 17 00:00:00 2001
From: Sebastian Lackner <sebastian@fds-team.de>
Date: Sat, 21 Mar 2015 22:35:24 +0100
Subject: user32: Cache the result of GetForegroundWindow.
---
dlls/user32/focus.c | 21 ++++++++++++++++++++-
dlls/user32/user_private.h | 4 +++-
server/protocol.def | 5 ++++-
server/queue.c | 10 +++++++++-
4 files changed, 36 insertions(+), 4 deletions(-)
diff --git a/dlls/user32/focus.c b/dlls/user32/focus.c
index 35fe89b..8b17d1f 100644
--- a/dlls/user32/focus.c
+++ b/dlls/user32/focus.c
@@ -367,12 +367,31 @@ HWND WINAPI GetFocus(void)
*/
HWND WINAPI GetForegroundWindow(void)
{
+ struct user_thread_info *thread_info = get_user_thread_info();
+ shmglobal_t *shm = wine_get_shmglobal();
HWND ret = 0;
+ DWORD epoch;
+
+ if (shm)
+ {
+ epoch = shm->foreground_wnd_epoch;
+
+ if (epoch == thread_info->foreground_wnd_epoch)
+ return thread_info->foreground_wnd;
+ }
SERVER_START_REQ( get_thread_input )
{
req->tid = 0;
- if (!wine_server_call_err( req )) ret = wine_server_ptr_handle( reply->foreground );
+ if (!wine_server_call_err( req ))
+ {
+ ret = wine_server_ptr_handle( reply->foreground );
+ if (shm)
+ {
+ thread_info->foreground_wnd = ret;
+ thread_info->foreground_wnd_epoch = epoch;
+ }
+ }
}
SERVER_END_REQ;
return ret;
diff --git a/dlls/user32/user_private.h b/dlls/user32/user_private.h
index a35ebf3..7752416 100644
--- a/dlls/user32/user_private.h
+++ b/dlls/user32/user_private.h
@@ -190,8 +190,10 @@ struct user_thread_info
struct user_key_state_info *key_state; /* Cache of global key state */
UINT active_hooks; /* Bitmap of active hooks */
DWORD last_get_msg; /* Last message time */
+ HWND foreground_wnd; /* Cache of the foreground window */
+ DWORD foreground_wnd_epoch; /* Counter to invalidate foreground window */
- ULONG pad[5]; /* Available for more data */
+ ULONG pad[2]; /* Available for more data */
};
#include <poppack.h>
diff --git a/server/protocol.def b/server/protocol.def
index 7eaa6cd..c770644 100644
--- a/server/protocol.def
+++ b/server/protocol.def
@@ -69,11 +69,14 @@ struct request_max_size
#define FIRST_USER_HANDLE 0x0020 /* first possible value for low word of user handle */
#define LAST_USER_HANDLE 0xffef /* last possible value for low word of user handle */
+/* wineserver global shared memory block */
typedef struct
{
- unsigned int last_input_time; /* last input time */
+ unsigned int last_input_time; /* last input time */
+ unsigned int foreground_wnd_epoch; /* counter to invalidate foreground window */
} shmglobal_t;
+/* wineserver local shared memory block */
typedef struct
{
int queue_bits; /* queue wake bits */
diff --git a/server/queue.c b/server/queue.c
index 6fa076d..764ba11 100644
--- a/server/queue.c
+++ b/server/queue.c
@@ -436,6 +436,7 @@ static void set_foreground_input( struct desktop *desktop, struct thread_input *
if (desktop->foreground_input == input) return;
set_clip_rectangle( desktop, NULL, 1 );
desktop->foreground_input = input;
+ if (shmglobal) interlocked_xchg_add( (int *)&shmglobal->foreground_wnd_epoch, 1 );
}
/* get the hook table for a given thread */
@@ -1076,7 +1077,12 @@ static inline void thread_input_cleanup_window( struct msg_queue *queue, user_ha
if (window == input->focus) input->focus = 0;
if (window == input->capture) input->capture = 0;
- if (window == input->active) input->active = 0;
+ if (window == input->active)
+ {
+ input->active = 0;
+ if (shmglobal && input->desktop->foreground_input == input)
+ interlocked_xchg_add( (int *)&shmglobal->foreground_wnd_epoch, 1 );
+ }
if (window == input->menu_owner) input->menu_owner = 0;
if (window == input->move_size) input->move_size = 0;
if (window == input->caret) set_caret_window( input, 0 );
@@ -3018,6 +3024,8 @@ DECL_HANDLER(set_active_window)
reply->previous = queue->input->active;
queue->input->active = get_user_full_handle( req->handle );
update_shm_thread_input( queue->input );
+ if (shmglobal && queue->input->desktop->foreground_input == queue->input)
+ interlocked_xchg_add( (int *)&shmglobal->foreground_wnd_epoch, 1 );
}
else set_error( STATUS_INVALID_HANDLE );
}
--
2.3.2

View File

@ -3,3 +3,4 @@ Depends: user32-Key_State
Depends: dinput-Events
Depends: server-Key_State
Depends: server-PeekMessage
Depends: server-ClipCursor