<pre style='margin:0'>
Perry E. Metzger (pmetzger) pushed a commit to branch master
in repository macports-ports.
</pre>
<p><a href="https://github.com/macports/macports-ports/commit/facffaf1632ee83f99eaac61abe3793b9eb7adef">https://github.com/macports/macports-ports/commit/facffaf1632ee83f99eaac61abe3793b9eb7adef</a></p>
<pre style="white-space: pre; background: #F8F8F8">The following commit(s) were added to refs/heads/master by this push:
<span style='display:block; white-space:pre;color:#404040;'> new facffaf1632 wine-devel,wine-staging: update to 9.15
</span>facffaf1632 is described below
<span style='display:block; white-space:pre;color:#808000;'>commit facffaf1632ee83f99eaac61abe3793b9eb7adef
</span>Author: Dean M Greer <38226388+Gcenx@users.noreply.github.com>
AuthorDate: Mon Aug 12 15:18:05 2024 -0400
<span style='display:block; white-space:pre;color:#404040;'> wine-devel,wine-staging: update to 9.15
</span><span style='display:block; white-space:pre;color:#404040;'>
</span><span style='display:block; white-space:pre;color:#404040;'> Co-Authored-By: marzent <44967463+marzent@users.noreply.github.com>
</span>---
emulators/wine-devel/Portfile | 22 +-
.../{1001-msync.diff => 1001-devel-msync.diff} | 1260 +++++++++-----------
.../{1001-msync.diff => 1001-staging-msync.diff} | 190 +--
3 files changed, 711 insertions(+), 761 deletions(-)
<span style='display:block; white-space:pre;color:#808080;'>diff --git a/emulators/wine-devel/Portfile b/emulators/wine-devel/Portfile
</span><span style='display:block; white-space:pre;color:#808080;'>index d101bff2f75..9e5df0c1352 100644
</span><span style='display:block; white-space:pre;background:#e0e0ff;'>--- a/emulators/wine-devel/Portfile
</span><span style='display:block; white-space:pre;background:#e0e0ff;'>+++ b/emulators/wine-devel/Portfile
</span><span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -7,7 +7,7 @@ PortGroup muniversal 1.1
</span>
# Keep the wine-stable, wine-devel and wine-crossover portfiles as similar as possible.
<span style='display:block; white-space:pre;background:#ffe0e0;'>-github.setup wine-mirror wine 9.14 wine-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+github.setup wine-mirror wine 9.15 wine-
</span> github.tarball_from archive
name wine-devel
conflicts wine-stable wine-staging wine-crossover
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -37,9 +37,9 @@ long_description \
</span>
checksums \
${distname}${extract.suffix} \
<span style='display:block; white-space:pre;background:#ffe0e0;'>- rmd160 84db00576e723c3e0b929e4f07e29d2784205729 \
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- sha256 2a66b02b1ba8b59aa31dd3c7e0f5a369f36bf4c1494b1dd292976a0ae263b90c \
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- size 49637864
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ rmd160 34f72b65f5f98d07ec09b2f2e8b2a461c2abc51c \
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ sha256 735c34c446fe00439d22f42eca9dec91acc0aed3b5164260fc726e03ad8bc60e \
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ size 49668690
</span>
depends_build \
port:bison \
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -129,6 +129,10 @@ compiler.blacklist-append {*gcc*} {clang < 800} {macports-clang-3.*}
</span> # https://gitlab.winehq.org/wine/wine/-/merge_requests/5935#note_74758
macosx_deployment_target 10.15
<span style='display:block; white-space:pre;background:#e0ffe0;'>+if {${subport} eq "wine-devel"} {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ patchfiles-append 1001-devel-msync.diff
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+}
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+
</span> subport wine-staging {
conflicts wine-stable wine-devel wine-crossover
set staging_version ${version}
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -140,18 +144,18 @@ subport wine-staging {
</span>
checksums-append \
${wine_staging_distfile} \
<span style='display:block; white-space:pre;background:#ffe0e0;'>- rmd160 a4333fa62df0f57921410ef0e5281b54f7396e5c \
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- sha256 0a7c9ca9f8d137657417495d5445793f89e5681965a6381d7cfafd998d019557 \
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- size 9452219
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ rmd160 220db5f902d65b29a704d3f5f53b090b5cb7ad83 \
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ sha256 1534258ee6cd8cb853c650193644ea4a08357b5c9ca1345fe3efb798a3acf70e \
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ size 9516589
</span>
depends_patch-append port:autoconf
# Applying staging after other patchfiles to avoid problems
post-patch {
system -W ${worksrcpath} \
<span style='display:block; white-space:pre;background:#ffe0e0;'>- "${workpath}/wine-staging-${staging_version}/staging/patchinstall.py --all -W winemac.drv-no-flicker-patch -W ntdll-Syscall_Emulation"
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ "${workpath}/wine-staging-${staging_version}/staging/patchinstall.py --all -W ntdll-Syscall_Emulation -W winemac.drv-no-flicker-patch"
</span> system -W ${worksrcpath} \
<span style='display:block; white-space:pre;background:#ffe0e0;'>- "patch -p1 < ${filespath}/1001-msync.diff"
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ "patch -p1 < ${filespath}/1001-staging-msync.diff"
</span> }
}
<span style='display:block; white-space:pre;color:#808080;'>diff --git a/emulators/wine-devel/files/1001-msync.diff b/emulators/wine-devel/files/1001-devel-msync.diff
</span>similarity index 83%
copy from emulators/wine-devel/files/1001-msync.diff
copy to emulators/wine-devel/files/1001-devel-msync.diff
<span style='display:block; white-space:pre;color:#808080;'>index d9457b5f342..628c5220230 100644
</span><span style='display:block; white-space:pre;background:#e0e0ff;'>--- a/emulators/wine-devel/files/1001-msync.diff
</span><span style='display:block; white-space:pre;background:#e0e0ff;'>+++ b/emulators/wine-devel/files/1001-devel-msync.diff
</span><span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1,100 +1,41 @@
</span> diff --git a/dlls/ntdll/Makefile.in b/dlls/ntdll/Makefile.in
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 78b3fdf94aa..061c730bf63 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 37bd6c86e31..89ee0286daa 100644
</span> --- a/dlls/ntdll/Makefile.in
+++ b/dlls/ntdll/Makefile.in
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -50,6 +50,7 @@ SOURCES = \
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -49,6 +49,7 @@ SOURCES = \
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ unix/debug.c \
</span> unix/env.c \
<span style='display:block; white-space:pre;background:#ffe0e0;'>- unix/esync.c \
</span> unix/file.c \
+ unix/msync.c \
unix/loader.c \
unix/loadorder.c \
unix/process.c \
<span style='display:block; white-space:pre;background:#ffe0e0;'>-diff --git a/dlls/ntdll/unix/esync.c b/dlls/ntdll/unix/esync.c
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-index 85d3db0cb8c..b63a386ee96 100644
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>---- a/dlls/ntdll/unix/esync.c
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+++ b/dlls/ntdll/unix/esync.c
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -51,6 +51,7 @@
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- #include "unix_private.h"
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- #include "esync.h"
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+#include "msync.h"
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- WINE_DEFAULT_DEBUG_CHANNEL(esync);
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -60,13 +61,16 @@ int do_esync(void)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- static int do_esync_cached = -1;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync_cached == -1)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-- do_esync_cached = getenv("WINEESYNC") && atoi(getenv("WINEESYNC"));
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ do_esync_cached = getenv("WINEESYNC") && atoi(getenv("WINEESYNC")) && !do_msync();
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return do_esync_cached;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- #else
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- static int once;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (!once++)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-- FIXME("eventfd not supported on this platform.\n");
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ {
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (getenv("WINEESYNC") && atoi(getenv("WINEESYNC")) && !do_msync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ FIXME("eventfd not supported on this platform.\n");
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ }
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return 0;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- #endif
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- }
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -571,6 +575,9 @@ NTSTATUS esync_reset_event( HANDLE handle )
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if ((ret = get_object( handle, &obj ))) return ret;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- event = obj->shm;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (obj->type != ESYNC_MANUAL_EVENT && obj->type != ESYNC_AUTO_EVENT)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ return STATUS_OBJECT_TYPE_MISMATCH;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (obj->type == ESYNC_MANUAL_EVENT)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- {
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- /* Acquire the spinlock. */
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -861,7 +868,7 @@ static NTSTATUS __esync_wait_objects( DWORD count, const HANDLE *handles, BOOLEA
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return ret;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- }
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-- if (objs[count - 1] && objs[count - 1]->type == ESYNC_QUEUE)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (count && objs[count - 1] && objs[count - 1]->type == ESYNC_QUEUE)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- msgwait = TRUE;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (has_esync && has_server)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -890,7 +897,7 @@ static NTSTATUS __esync_wait_objects( DWORD count, const HANDLE *handles, BOOLEA
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- }
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- }
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-- if (wait_any || count == 1)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (wait_any || count <= 1)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- {
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- /* Try to check objects now, so we can obviate poll() at least. */
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- for (i = 0; i < count; i++)
</span> diff --git a/dlls/ntdll/unix/loader.c b/dlls/ntdll/unix/loader.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index ae7e2e8e6ec..a7175b35ae6 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 92f2e2eb3a3..bc9af9d34a8 100644
</span> --- a/dlls/ntdll/unix/loader.c
+++ b/dlls/ntdll/unix/loader.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -89,6 +89,7 @@ extern char **environ;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -90,6 +90,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ #include "winioctl.h"
</span> #include "winternl.h"
#include "unix_private.h"
<span style='display:block; white-space:pre;background:#ffe0e0;'>- #include "esync.h"
</span> +#include "msync.h"
#include "wine/list.h"
#include "ntsyscalls.h"
#include "wine/debug.h"
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1896,6 +1897,7 @@ static void start_main_thread(void)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1858,6 +1859,7 @@ static void start_main_thread(void)
</span> signal_alloc_thread( teb );
dbg_init();
startup_info_size = server_init_process();
+ msync_init();
<span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_init();
</span> virtual_map_user_shared_data();
init_cpu_info();
<span style='display:block; white-space:pre;background:#e0ffe0;'>+ init_files();
</span> diff --git a/dlls/ntdll/unix/msync.c b/dlls/ntdll/unix/msync.c
new file mode 100644
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 00000000000..90e785f6df2
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 00000000000..2eef30dd0f2
</span> --- /dev/null
+++ b/dlls/ntdll/unix/msync.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -0,0 +1,1661 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -0,0 +1,1689 @@
</span> +/*
+ * mach semaphore-based synchronization objects
+ *
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -412,7 +353,7 @@ index 00000000000..90e785f6df2
</span> +
+static const mach_msg_bits_t msgh_bits_send = MACH_MSGH_BITS_REMOTE(MACH_MSG_TYPE_COPY_SEND);
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+static inline void server_register_wait( semaphore_t sem, unsigned int msgh_id,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++static inline mach_msg_return_t server_register_wait( semaphore_t sem, unsigned int msgh_id,
</span> + struct msync **wait_objs, const int count )
+{
+ int i, is_mutex;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -444,10 +385,11 @@ index 00000000000..90e785f6df2
</span> +
+ if (mr != MACH_MSG_SUCCESS)
+ ERR("Failed to send server register wait: %#x\n", mr);
<span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ return mr;
</span> +}
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+static inline void server_remove_wait( semaphore_t sem, unsigned int msgh_id,
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ struct msync **wait_objs, const int count )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++static inline void server_remove_wait( unsigned int msgh_id, struct msync **wait_objs, const int count )
</span> +{
+ int i;
+ mach_msg_return_t mr;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -504,19 +446,19 @@ index 00000000000..90e785f6df2
</span> +}
+
+static inline NTSTATUS msync_wait_single( struct msync *wait_obj,
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ ULONGLONG *end )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ ULONGLONG *end, int tid )
</span> +{
+ int ret, val = 0;
+ void *addr = wait_obj->shm;
+ ULONGLONG ns_timeleft = 0;
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ do
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ do
</span> + {
+ if (wait_obj->type == MSYNC_MUTEX)
+ {
+ val = __atomic_load_n( (int *)addr, __ATOMIC_ACQUIRE );
+ if (!val || val == ~0)
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ val = GetCurrentThreadId();
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ val = tid;
</span> + }
+
+ if (__atomic_load_n( (int *)addr, __ATOMIC_ACQUIRE ) != val)
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -577,27 +519,51 @@ index 00000000000..90e785f6df2
</span> +}
+
+static NTSTATUS msync_wait_multiple( struct msync **wait_objs,
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ int count, ULONGLONG *end )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ int count, ULONGLONG *end, int tid )
</span> +{
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ int tid;
</span> + semaphore_t *sem;
+ kern_return_t kr;
<span style='display:block; white-space:pre;background:#e0ffe0;'>++ mach_msg_return_t mr;
</span> + unsigned int msgh_id;
+ __thread static struct msync *objs[MAXIMUM_WAIT_OBJECTS + 1];
+
+ count = resize_wait_objs( wait_objs, objs, count );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (count == 1 && __ulock_wait2) return msync_wait_single( objs[0], end );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (count == 1 && __ulock_wait2) return msync_wait_single( objs[0], end, tid );
</span> + if (!count) return destroyed_wait( end );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ tid = GetCurrentThreadId();
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span> + if (check_shm_contention( objs, count, tid ))
+ return STATUS_PENDING;
+
+ sem = semaphore_pool_alloc();
+ msgh_id = (tid << 8) | count;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ server_register_wait( *sem, msgh_id, objs, count );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ mr = server_register_wait( *sem, msgh_id, objs, count );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (mr != MACH_MSG_SUCCESS)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ /* The os failed to send the mach message, which is either because
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ * we lost the wineserver process or the semaphore from semaphore_pool_alloc
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ * is not valid...
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ * To avoid pooling in a dead port, recreate it here.
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ * Worst case, this will behave effectively like a spinlock. */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ semaphore_destroy( mach_task_self(), *sem) ;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ kr = semaphore_create( mach_task_self(), sem, SYNC_POLICY_FIFO, 0 );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (kr != KERN_SUCCESS)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ ERR("Cannot create semaphore: %#x %s\n", kr, mach_error_string(kr));
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ semaphore_pool_free( sem );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ return STATUS_PENDING;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ mr = server_register_wait( *sem, msgh_id, objs, count );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (mr != MACH_MSG_SUCCESS)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ semaphore_pool_free( sem );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ return STATUS_PENDING;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ }
</span> +
+ do
+ {
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -613,7 +579,7 @@ index 00000000000..90e785f6df2
</span> + if (is_destroyed( objs, count ))
+ return destroyed_wait( end );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ server_remove_wait( *sem, msgh_id, objs, count );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ server_remove_wait( msgh_id, objs, count );
</span> +
+ switch (kr) {
+ case KERN_SUCCESS:
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1220,7 +1186,7 @@ index 00000000000..90e785f6df2
</span> + return STATUS_SUCCESS;
+}
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+static NTSTATUS do_single_wait( struct msync *obj, ULONGLONG *end, BOOLEAN alertable )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++static NTSTATUS do_single_wait( struct msync *obj, ULONGLONG *end, BOOLEAN alertable, int tid )
</span> +{
+ NTSTATUS status;
+ struct msync *wait_objs[2];
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1241,14 +1207,14 @@ index 00000000000..90e785f6df2
</span> +
+ wait_objs[1] = &apc_obj;
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ status = msync_wait_multiple( wait_objs, 2, end );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ status = msync_wait_multiple( wait_objs, 2, end, tid );
</span> +
+ if (__atomic_load_n( apc_addr, __ATOMIC_SEQ_CST ))
+ return STATUS_USER_APC;
+ }
+ else
+ {
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ status = msync_wait_multiple( wait_objs, 1, end );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ status = msync_wait_multiple( wait_objs, 1, end, tid );
</span> + }
+ return status;
+}
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1258,6 +1224,7 @@ index 00000000000..90e785f6df2
</span> +{
+ static const LARGE_INTEGER zero = {0};
+
<span style='display:block; white-space:pre;background:#e0ffe0;'>++ __thread static int current_tid = 0;
</span> + __thread static struct msync *objs[MAXIMUM_WAIT_OBJECTS + 1];
+ struct msync apc_obj;
+ int has_msync = 0, has_server = 0;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1268,6 +1235,8 @@ index 00000000000..90e785f6df2
</span> + ULONGLONG end;
+ int i, ret;
+
<span style='display:block; white-space:pre;background:#e0ffe0;'>++ current_tid = current_tid ? current_tid : GetCurrentThreadId();
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + /* Grab the APC idx if we don't already have it. */
+ if (alertable && !ntdll_get_thread_data()->msync_apc_addr)
+ {
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1386,7 +1355,7 @@ index 00000000000..90e785f6df2
</span> + struct mutex *mutex = obj->shm;
+ int tid;
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (mutex->tid == GetCurrentThreadId())
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (mutex->tid == current_tid)
</span> + {
+ TRACE("Woken up by handle %p [%d].\n", handles[i], i);
+ mutex->count++;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1394,13 +1363,13 @@ index 00000000000..90e785f6df2
</span> + }
+
+ tid = 0;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (__atomic_compare_exchange_n(&mutex->tid, &tid, GetCurrentThreadId(), 0, __ATOMIC_ACQ_REL, __ATOMIC_RELAXED))
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (__atomic_compare_exchange_n(&mutex->tid, &tid, current_tid, 0, __ATOMIC_ACQ_REL, __ATOMIC_RELAXED))
</span> + {
+ TRACE("Woken up by handle %p [%d].\n", handles[i], i);
+ mutex->count = 1;
+ return i;
+ }
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ else if (tid == ~0 && __atomic_compare_exchange_n(&mutex->tid, &tid, GetCurrentThreadId(), 0, __ATOMIC_ACQ_REL, __ATOMIC_RELAXED))
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ else if (tid == ~0 && __atomic_compare_exchange_n(&mutex->tid, &tid, current_tid, 0, __ATOMIC_ACQ_REL, __ATOMIC_RELAXED))
</span> + {
+ TRACE("Woken up by abandoned mutex %p [%d].\n", handles[i], i);
+ mutex->count = 1;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1463,7 +1432,7 @@ index 00000000000..90e785f6df2
</span> + return STATUS_TIMEOUT;
+ }
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ ret = msync_wait_multiple( objs, waitcount, timeout ? &end : NULL );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ ret = msync_wait_multiple( objs, waitcount, timeout ? &end : NULL, current_tid );
</span> +
+ if (ret == STATUS_TIMEOUT)
+ {
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1514,12 +1483,12 @@ index 00000000000..90e785f6df2
</span> + {
+ struct mutex *mutex = obj->shm;
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (mutex->tid == GetCurrentThreadId())
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (mutex->tid == current_tid)
</span> + continue;
+
+ while (__atomic_load_n( &mutex->tid, __ATOMIC_SEQ_CST ))
+ {
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ status = do_single_wait( obj, timeout ? &end : NULL, alertable );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ status = do_single_wait( obj, timeout ? &end : NULL, alertable, current_tid );
</span> + if (status != STATUS_PENDING)
+ break;
+ }
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1531,7 +1500,7 @@ index 00000000000..90e785f6df2
</span> +
+ while (!__atomic_load_n( &event->signaled, __ATOMIC_SEQ_CST ))
+ {
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ status = do_single_wait( obj, timeout ? &end : NULL, alertable );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ status = do_single_wait( obj, timeout ? &end : NULL, alertable, current_tid );
</span> + if (status != STATUS_PENDING)
+ break;
+ }
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1557,7 +1526,7 @@ index 00000000000..90e785f6df2
</span> + struct mutex *mutex = obj->shm;
+ int tid = __atomic_load_n( &mutex->tid, __ATOMIC_SEQ_CST );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (tid && tid != ~0 && tid != GetCurrentThreadId())
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (tid && tid != ~0 && tid != current_tid)
</span> + goto tryagain;
+ }
+ else if (obj)
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1580,11 +1549,11 @@ index 00000000000..90e785f6df2
</span> + {
+ struct mutex *mutex = obj->shm;
+ int tid = __atomic_load_n( &mutex->tid, __ATOMIC_SEQ_CST );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (tid == GetCurrentThreadId())
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (tid == current_tid)
</span> + break;
+ if (tid && tid != ~0)
+ goto tooslow;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (__sync_val_compare_and_swap( &mutex->tid, tid, GetCurrentThreadId() ) != tid)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (__sync_val_compare_and_swap( &mutex->tid, tid, current_tid ) != tid)
</span> + goto tooslow;
+ if (tid == ~0)
+ abandoned = TRUE;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1813,189 +1782,184 @@ index 00000000000..3e6eb2c8b1e
</span> +extern NTSTATUS msync_signal_and_wait( HANDLE signal, HANDLE wait,
+ BOOLEAN alertable, const LARGE_INTEGER *timeout );
diff --git a/dlls/ntdll/unix/server.c b/dlls/ntdll/unix/server.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 77aa995326c..f45db2f3090 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index f3ffd99c3fc..aac6c8aedb7 100644
</span> --- a/dlls/ntdll/unix/server.c
+++ b/dlls/ntdll/unix/server.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -84,6 +84,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -79,6 +79,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ #include "wine/server.h"
</span> #include "wine/debug.h"
#include "unix_private.h"
<span style='display:block; white-space:pre;background:#ffe0e0;'>- #include "esync.h"
</span> +#include "msync.h"
#include "ddk/wdm.h"
WINE_DEFAULT_DEBUG_CHANNEL(server);
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1882,6 +1883,9 @@ NTSTATUS WINAPI NtClose( HANDLE handle )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1830,6 +1831,9 @@ NTSTATUS WINAPI NtClose( HANDLE handle )
</span> * retrieve it again */
fd = remove_fd_from_cache( handle );
+ if (do_msync())
+ msync_close( handle );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_close( handle );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SERVER_START_REQ( close_handle )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ req->handle = wine_server_obj_handle( handle );
</span> diff --git a/dlls/ntdll/unix/sync.c b/dlls/ntdll/unix/sync.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index a52327841d2..4d4644f9c8c 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 21e66f01875..7ebc8cdd77c 100644
</span> --- a/dlls/ntdll/unix/sync.c
+++ b/dlls/ntdll/unix/sync.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -67,6 +67,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -66,6 +66,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ #include "wine/server.h"
</span> #include "wine/debug.h"
#include "unix_private.h"
<span style='display:block; white-space:pre;background:#ffe0e0;'>- #include "esync.h"
</span> +#include "msync.h"
WINE_DEFAULT_DEBUG_CHANNEL(sync);
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -120,7 +121,7 @@ static inline int futex_wait( const LONG *addr, int val, struct timespec *timeou
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- long tv_nsec;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- } timeout32 = { timeout->tv_sec, timeout->tv_nsec };
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-- return syscall( __NR_futex, addr, FUTEX_WAIT_PRIVATE, val, &timeout32, 0, 0 );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ return syscall( __NR_futex, addr, FUTEX_WAIT_PRIVATE| futex_private, val, &timeout32, 0, 0 );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- }
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- #endif
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return syscall( __NR_futex, addr, FUTEX_WAIT_PRIVATE, val, timeout, 0, 0 );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -320,6 +321,9 @@ NTSTATUS WINAPI NtCreateSemaphore( HANDLE *handle, ACCESS_MASK access, const OBJ
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -319,6 +320,9 @@ NTSTATUS WINAPI NtCreateSemaphore( HANDLE *handle, ACCESS_MASK access, const OBJ
</span> if (max <= 0 || initial < 0 || initial > max) return STATUS_INVALID_PARAMETER;
if ((ret = alloc_object_attributes( attr, &objattr, &len ))) return ret;
+ if (do_msync())
+ return msync_create_semaphore( handle, access, attr, initial, max );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return esync_create_semaphore( handle, access, attr, initial, max );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -348,6 +352,9 @@ NTSTATUS WINAPI NtOpenSemaphore( HANDLE *handle, ACCESS_MASK access, const OBJEC
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SERVER_START_REQ( create_semaphore )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ req->access = access;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -343,6 +347,10 @@ NTSTATUS WINAPI NtOpenSemaphore( HANDLE *handle, ACCESS_MASK access, const OBJEC
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ unsigned int ret;
</span>
*handle = 0;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync())
+ return msync_open_semaphore( handle, access, attr );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return esync_open_semaphore( handle, access, attr );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if ((ret = validate_open_object_attributes( attr ))) return ret;
</span>
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -387,6 +394,9 @@ NTSTATUS WINAPI NtQuerySemaphore( HANDLE handle, SEMAPHORE_INFORMATION_CLASS cla
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SERVER_START_REQ( open_semaphore )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -379,6 +387,9 @@ NTSTATUS WINAPI NtQuerySemaphore( HANDLE handle, SEMAPHORE_INFORMATION_CLASS cla
</span>
if (len != sizeof(SEMAPHORE_BASIC_INFORMATION)) return STATUS_INFO_LENGTH_MISMATCH;
+ if (do_msync())
+ return msync_query_semaphore( handle, info, ret_len );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return esync_query_semaphore( handle, info, ret_len );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -412,6 +422,9 @@ NTSTATUS WINAPI NtReleaseSemaphore( HANDLE handle, ULONG count, ULONG *previous
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SERVER_START_REQ( query_semaphore )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ req->handle = wine_server_obj_handle( handle );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -401,6 +412,9 @@ NTSTATUS WINAPI NtReleaseSemaphore( HANDLE handle, ULONG count, ULONG *previous
</span> {
unsigned int ret;
+ if (do_msync())
+ return msync_release_semaphore( handle, count, previous );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return esync_release_semaphore( handle, count, previous );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SERVER_START_REQ( release_semaphore )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ req->handle = wine_server_obj_handle( handle );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -427,6 +441,10 @@ NTSTATUS WINAPI NtCreateEvent( HANDLE *handle, ACCESS_MASK access, const OBJECT_
</span>
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -442,6 +455,9 @@ NTSTATUS WINAPI NtCreateEvent( HANDLE *handle, ACCESS_MASK access, const OBJECT_
</span> *handle = 0;
if (type != NotificationEvent && type != SynchronizationEvent) return STATUS_INVALID_PARAMETER;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync())
+ return msync_create_event( handle, access, attr, type, state );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return esync_create_event( handle, access, attr, type, state );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if ((ret = alloc_object_attributes( attr, &objattr, &len ))) return ret;
</span>
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -473,6 +489,9 @@ NTSTATUS WINAPI NtOpenEvent( HANDLE *handle, ACCESS_MASK access, const OBJECT_AT
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SERVER_START_REQ( create_event )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -455,6 +473,9 @@ NTSTATUS WINAPI NtOpenEvent( HANDLE *handle, ACCESS_MASK access, const OBJECT_AT
</span> *handle = 0;
if ((ret = validate_open_object_attributes( attr ))) return ret;
+ if (do_msync())
+ return msync_open_event( handle, access, attr );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return esync_open_event( handle, access, attr );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -499,6 +518,9 @@ NTSTATUS WINAPI NtSetEvent( HANDLE handle, LONG *prev_state )
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- /* This comment is a dummy to make sure this patch applies in the right place. */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SERVER_START_REQ( open_event )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ req->access = access;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -477,6 +498,9 @@ NTSTATUS WINAPI NtSetEvent( HANDLE handle, LONG *prev_state )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span> unsigned int ret;
+ if (do_msync())
+ return msync_set_event( handle, prev_state );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return esync_set_event( handle );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -522,6 +544,9 @@ NTSTATUS WINAPI NtResetEvent( HANDLE handle, LONG *prev_state )
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- /* This comment is a dummy to make sure this patch applies in the right place. */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SERVER_START_REQ( event_op )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ req->handle = wine_server_obj_handle( handle );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -496,6 +520,10 @@ NTSTATUS WINAPI NtResetEvent( HANDLE handle, LONG *prev_state )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span> unsigned int ret;
+ if (do_msync())
+ return msync_reset_event( handle, prev_state );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return esync_reset_event( handle );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -555,6 +580,9 @@ NTSTATUS WINAPI NtPulseEvent( HANDLE handle, LONG *prev_state )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SERVER_START_REQ( event_op )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ req->handle = wine_server_obj_handle( handle );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -525,6 +553,9 @@ NTSTATUS WINAPI NtPulseEvent( HANDLE handle, LONG *prev_state )
</span> {
unsigned int ret;
+ if (do_msync())
+ return msync_pulse_event( handle, prev_state );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return esync_pulse_event( handle );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -589,6 +617,9 @@ NTSTATUS WINAPI NtQueryEvent( HANDLE handle, EVENT_INFORMATION_CLASS class,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SERVER_START_REQ( event_op )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ req->handle = wine_server_obj_handle( handle );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -556,6 +587,9 @@ NTSTATUS WINAPI NtQueryEvent( HANDLE handle, EVENT_INFORMATION_CLASS class,
</span>
if (len != sizeof(EVENT_BASIC_INFORMATION)) return STATUS_INFO_LENGTH_MISMATCH;
+ if (do_msync())
+ return msync_query_event( handle, info, ret_len );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return esync_query_event( handle, info, ret_len );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -619,6 +650,9 @@ NTSTATUS WINAPI NtCreateMutant( HANDLE *handle, ACCESS_MASK access, const OBJECT
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SERVER_START_REQ( query_event )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ req->handle = wine_server_obj_handle( handle );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -582,6 +616,10 @@ NTSTATUS WINAPI NtCreateMutant( HANDLE *handle, ACCESS_MASK access, const OBJECT
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ struct object_attributes *objattr;
</span>
*handle = 0;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync())
+ return msync_create_mutex( handle, access, attr, owned );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return esync_create_mutex( handle, access, attr, owned );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if ((ret = alloc_object_attributes( attr, &objattr, &len ))) return ret;
</span>
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -649,6 +683,9 @@ NTSTATUS WINAPI NtOpenMutant( HANDLE *handle, ACCESS_MASK access, const OBJECT_A
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SERVER_START_REQ( create_mutex )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -609,6 +647,9 @@ NTSTATUS WINAPI NtOpenMutant( HANDLE *handle, ACCESS_MASK access, const OBJECT_A
</span> *handle = 0;
if ((ret = validate_open_object_attributes( attr ))) return ret;
+ if (do_msync())
+ return msync_open_mutex( handle, access, attr );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return esync_open_mutex( handle, access, attr );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -674,6 +711,9 @@ NTSTATUS WINAPI NtReleaseMutant( HANDLE handle, LONG *prev_count )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SERVER_START_REQ( open_mutex )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ req->access = access;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -631,6 +672,9 @@ NTSTATUS WINAPI NtReleaseMutant( HANDLE handle, LONG *prev_count )
</span> {
unsigned int ret;
+ if (do_msync())
+ return msync_release_mutex( handle, prev_count );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return esync_release_mutex( handle, prev_count );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -707,6 +747,9 @@ NTSTATUS WINAPI NtQueryMutant( HANDLE handle, MUTANT_INFORMATION_CLASS class,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SERVER_START_REQ( release_mutex )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ req->handle = wine_server_obj_handle( handle );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -661,6 +705,9 @@ NTSTATUS WINAPI NtQueryMutant( HANDLE handle, MUTANT_INFORMATION_CLASS class,
</span>
if (len != sizeof(MUTANT_BASIC_INFORMATION)) return STATUS_INFO_LENGTH_MISMATCH;
+ if (do_msync())
+ return msync_query_mutex( handle, info, ret_len );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return esync_query_mutex( handle, info, ret_len );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1630,6 +1673,13 @@ NTSTATUS WINAPI NtWaitForMultipleObjects( DWORD count, const HANDLE *handles, BO
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SERVER_START_REQ( query_mutex )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ req->handle = wine_server_obj_handle( handle );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1581,6 +1628,13 @@ NTSTATUS WINAPI NtWaitForMultipleObjects( DWORD count, const HANDLE *handles, BO
</span>
if (!count || count > MAXIMUM_WAIT_OBJECTS) return STATUS_INVALID_PARAMETER_1;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2006,20 +1970,20 @@ index a52327841d2..4d4644f9c8c 100644
</span> + return ret;
+ }
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- {
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- NTSTATUS ret = esync_wait_objects( count, handles, wait_any, alertable, timeout );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1662,6 +1712,9 @@ NTSTATUS WINAPI NtSignalAndWaitForSingleObject( HANDLE signal, HANDLE wait,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if (alertable) flags |= SELECT_ALERTABLE;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ select_op.wait.op = wait_any ? SELECT_WAIT : SELECT_WAIT_ALL;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ for (i = 0; i < count; i++) select_op.wait.handles[i] = wine_server_obj_handle( handles[i] );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1606,6 +1660,9 @@ NTSTATUS WINAPI NtSignalAndWaitForSingleObject( HANDLE signal, HANDLE wait,
</span> select_op_t select_op;
UINT flags = SELECT_INTERRUPTIBLE;
+ if (do_msync())
+ return msync_signal_and_wait( signal, wait, alertable, timeout );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return esync_signal_and_wait( signal, wait, alertable, timeout );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if (!signal) return STATUS_INVALID_HANDLE;
</span>
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1705,7 +1758,24 @@ NTSTATUS WINAPI NtYieldExecution(void)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if (alertable) flags |= SELECT_ALERTABLE;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1646,7 +1703,17 @@ NTSTATUS WINAPI NtYieldExecution(void)
</span> NTSTATUS WINAPI NtDelayExecution( BOOLEAN alertable, const LARGE_INTEGER *timeout )
{
/* if alertable, we need to query the server */
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2033,50 +1997,43 @@ index a52327841d2..4d4644f9c8c 100644
</span> + return ret;
+ }
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ {
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ NTSTATUS ret = esync_wait_objects( 0, NULL, TRUE, TRUE, timeout );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (ret != STATUS_NOT_IMPLEMENTED)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ return ret;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ }
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span> + return server_wait( NULL, 0, SELECT_INTERRUPTIBLE | SELECT_ALERTABLE, timeout );
+ }
if (!timeout || timeout->QuadPart == TIMEOUT_INFINITE) /* sleep forever */
{
diff --git a/dlls/ntdll/unix/unix_private.h b/dlls/ntdll/unix/unix_private.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 791b7b88c62..dc194eb09ac 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index ee5630e76f1..84f0bef8bda 100644
</span> --- a/dlls/ntdll/unix/unix_private.h
+++ b/dlls/ntdll/unix/unix_private.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -104,6 +104,8 @@ struct ntdll_thread_data
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -103,6 +103,8 @@ struct ntdll_thread_data
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span> void *cpu_data[16]; /* reserved for CPU-specific data */
void *kernel_stack; /* stack for thread startup and kernel syscalls */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- int esync_apc_fd; /* fd to wait on for user APCs */
</span> + int *msync_apc_addr;
+ unsigned int msync_apc_idx;
int request_fd; /* fd for sending server requests */
int reply_fd; /* fd for receiving server replies */
int wait_fd[2]; /* fd for sleeping server requests */
diff --git a/dlls/ntdll/unix/virtual.c b/dlls/ntdll/unix/virtual.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index efccfac76d0..8247b82852d 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 0fedfe0fb1d..ff770ecbdb4 100644
</span> --- a/dlls/ntdll/unix/virtual.c
+++ b/dlls/ntdll/unix/virtual.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -3737,6 +3737,8 @@ static TEB *init_teb( void *ptr, BOOL is_wow )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -3653,6 +3653,8 @@ static TEB *init_teb( void *ptr, BOOL is_wow )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ teb->StaticUnicodeString.Buffer = teb->StaticUnicodeBuffer;
</span> teb->StaticUnicodeString.MaximumLength = sizeof(teb->StaticUnicodeBuffer);
thread_data = (struct ntdll_thread_data *)&teb->GdiTebBatch;
<span style='display:block; white-space:pre;background:#ffe0e0;'>- thread_data->esync_apc_fd = -1;
</span> + thread_data->msync_apc_addr = NULL;
+ thread_data->msync_apc_idx = 0;
thread_data->request_fd = -1;
thread_data->reply_fd = -1;
thread_data->wait_fd[0] = -1;
diff --git a/include/wine/server_protocol.h b/include/wine/server_protocol.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index d3399268d00..c38120548ab 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 74bf0f0c839..fd84ee0d1a9 100644
</span> --- a/include/wine/server_protocol.h
+++ b/include/wine/server_protocol.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -5828,6 +5828,92 @@ struct get_esync_apc_fd_reply
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- struct reply_header __header;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -5722,6 +5722,92 @@ struct set_keyboard_repeat_reply
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ char __pad_12[4];
</span> };
+enum msync_type
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2168,10 +2125,10 @@ index d3399268d00..c38120548ab 100644
</span>
enum request
{
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -6123,6 +6209,11 @@ enum request
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- REQ_esync_msgwait,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -6011,6 +6097,11 @@ enum request
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ REQ_resume_process,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ REQ_get_next_thread,
</span> REQ_set_keyboard_repeat,
<span style='display:block; white-space:pre;background:#ffe0e0;'>- REQ_get_esync_apc_fd,
</span> + REQ_create_msync,
+ REQ_open_msync,
+ REQ_get_msync_idx,
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2180,10 +2137,10 @@ index d3399268d00..c38120548ab 100644
</span> REQ_NB_REQUESTS
};
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -6422,6 +6513,11 @@ union generic_request
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- struct esync_msgwait_request esync_msgwait_request;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -6304,6 +6395,11 @@ union generic_request
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ struct resume_process_request resume_process_request;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ struct get_next_thread_request get_next_thread_request;
</span> struct set_keyboard_repeat_request set_keyboard_repeat_request;
<span style='display:block; white-space:pre;background:#ffe0e0;'>- struct get_esync_apc_fd_request get_esync_apc_fd_request;
</span> + struct create_msync_request create_msync_request;
+ struct open_msync_request open_msync_request;
+ struct get_msync_idx_request get_msync_idx_request;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2192,10 +2149,10 @@ index d3399268d00..c38120548ab 100644
</span> };
union generic_reply
{
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -6719,11 +6815,16 @@ union generic_reply
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- struct esync_msgwait_reply esync_msgwait_reply;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -6595,11 +6691,16 @@ union generic_reply
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ struct resume_process_reply resume_process_reply;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ struct get_next_thread_reply get_next_thread_reply;
</span> struct set_keyboard_repeat_reply set_keyboard_repeat_reply;
<span style='display:block; white-space:pre;background:#ffe0e0;'>- struct get_esync_apc_fd_reply get_esync_apc_fd_reply;
</span> + struct create_msync_reply create_msync_reply;
+ struct open_msync_reply open_msync_reply;
+ struct get_msync_idx_reply get_msync_idx_reply;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2206,15 +2163,15 @@ index d3399268d00..c38120548ab 100644
</span> /* ### protocol_version begin ### */
-#define SERVER_PROTOCOL_VERSION 837
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+#define SERVER_PROTOCOL_VERSION 838
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++#define SERVER_PROTOCOL_VERSION 841
</span>
/* ### protocol_version end ### */
diff --git a/server/Makefile.in b/server/Makefile.in
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 87103cb2002..85b7b8f6693 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 7e571ac2ba6..dabe3fe83a8 100644
</span> --- a/server/Makefile.in
+++ b/server/Makefile.in
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -15,6 +15,7 @@ SOURCES = \
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -14,6 +14,7 @@ SOURCES = \
</span> event.c \
fd.c \
file.c \
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2223,180 +2180,176 @@ index 87103cb2002..85b7b8f6693 100644
</span> hook.c \
mach.c \
diff --git a/server/async.c b/server/async.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index b0f9fe42ad1..b7270394579 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 3c9b9588c6e..b53e2e5d15e 100644
</span> --- a/server/async.c
+++ b/server/async.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -78,6 +78,7 @@ static const struct object_ops async_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -77,6 +77,7 @@ static const struct object_ops async_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
async_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
async_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -688,6 +689,7 @@ static const struct object_ops iosb_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -686,6 +687,7 @@ static const struct object_ops iosb_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/atom.c b/server/atom.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index d9824de8eac..d99f10d6f19 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index ff0799f5880..7d53bd5e3bb 100644
</span> --- a/server/atom.c
+++ b/server/atom.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -80,6 +80,7 @@ static const struct object_ops atom_table_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -79,6 +79,7 @@ static const struct object_ops atom_table_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/change.c b/server/change.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 17a29c02867..84d4b25252b 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index f773ccf8831..798a7e9c841 100644
</span> --- a/server/change.c
+++ b/server/change.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -113,6 +113,7 @@ static const struct object_ops dir_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -112,6 +112,7 @@ static const struct object_ops dir_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
default_fd_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- default_fd_get_esync_fd, /* get_esync_fd */
</span> + default_fd_get_msync_idx, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
dir_get_fd, /* get_fd */
diff --git a/server/clipboard.c b/server/clipboard.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 8b265f2dcea..e7149f20488 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 8118a467dd8..927edb99a03 100644
</span> --- a/server/clipboard.c
+++ b/server/clipboard.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -77,6 +77,7 @@ static const struct object_ops clipboard_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -76,6 +76,7 @@ static const struct object_ops clipboard_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/completion.c b/server/completion.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 3d4be86a212..d761d372314 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 6933195e72d..6be3bc7da85 100644
</span> --- a/server/completion.c
+++ b/server/completion.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -76,6 +76,7 @@ static const struct object_ops completion_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -75,6 +75,7 @@ static const struct object_ops completion_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
completion_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/console.c b/server/console.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index dbd4a97459c..2b023546907 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index b64283baf4a..3b552346871 100644
</span> --- a/server/console.c
+++ b/server/console.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -42,6 +42,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -41,6 +41,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ #include "wincon.h"
</span> #include "winternl.h"
#include "wine/condrv.h"
<span style='display:block; white-space:pre;background:#ffe0e0;'>- #include "esync.h"
</span> +#include "msync.h"
struct screen_buffer;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -83,6 +84,7 @@ static const struct object_ops console_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -81,6 +82,7 @@ static const struct object_ops console_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ console_add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
console_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
console_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -142,12 +144,14 @@ struct console_server
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- int term_fd; /* UNIX terminal fd */
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- struct termios termios; /* original termios */
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- int esync_fd;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -139,11 +141,13 @@ struct console_server
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ unsigned int once_input : 1; /* flag if input thread has already been requested */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ int term_fd; /* UNIX terminal fd */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ struct termios termios; /* original termios */
</span> + unsigned int msync_idx;
};
static void console_server_dump( struct object *obj, int verbose );
static void console_server_destroy( struct object *obj );
static int console_server_signaled( struct object *obj, struct wait_queue_entry *entry );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- static int console_server_get_esync_fd( struct object *obj, enum esync_type *type );
</span> +static unsigned int console_server_get_msync_idx( struct object *obj, enum msync_type *type );
static struct fd *console_server_get_fd( struct object *obj );
static struct object *console_server_lookup_name( struct object *obj, struct unicode_str *name,
unsigned int attr, struct object *root );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -163,6 +167,7 @@ static const struct object_ops console_server_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -158,6 +162,7 @@ static const struct object_ops console_server_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
console_server_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- console_server_get_esync_fd, /* get_esync_fd */
</span> + console_server_get_msync_idx, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
console_server_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -233,6 +238,7 @@ static const struct object_ops screen_buffer_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -227,6 +232,7 @@ static const struct object_ops screen_buffer_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ screen_buffer_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
screen_buffer_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -283,6 +289,7 @@ static const struct object_ops console_device_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -276,6 +282,7 @@ static const struct object_ops console_device_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -321,6 +328,7 @@ static const struct object_ops console_input_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -313,6 +320,7 @@ static const struct object_ops console_input_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ console_input_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
console_input_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -379,6 +387,7 @@ static const struct object_ops console_output_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -370,6 +378,7 @@ static const struct object_ops console_output_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ console_output_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
console_output_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -438,6 +447,7 @@ static const struct object_ops console_connection_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -428,6 +437,7 @@ static const struct object_ops console_connection_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
console_connection_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -600,8 +610,13 @@ static void disconnect_console_server( struct console_server *server )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -590,6 +600,10 @@ static void disconnect_console_server( struct console_server *server )
</span> list_remove( &call->entry );
console_host_ioctl_terminate( call, STATUS_CANCELLED );
}
+
+ if (do_msync())
+ msync_clear_shm( server->msync_idx );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_clear( server->esync_fd );
</span> +
while (!list_empty( &server->read_queue ))
{
struct console_host_ioctl *call = LIST_ENTRY( list_head( &server->read_queue ), struct console_host_ioctl, entry );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -885,6 +900,7 @@ static void console_server_destroy( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -872,6 +886,7 @@ static void console_server_destroy( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ assert( obj->ops == &console_server_ops );
</span> disconnect_console_server( server );
if (server->fd) release_object( server->fd );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync()) close( server->esync_fd );
</span> + if (do_msync()) msync_destroy_semaphore( server->msync_idx );
}
static struct object *console_server_lookup_name( struct object *obj, struct unicode_str *name,
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -933,6 +949,13 @@ static int console_server_get_esync_fd( struct object *obj, enum esync_type *typ
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return server->esync_fd;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -913,6 +928,13 @@ static int console_server_signaled( struct object *obj, struct wait_queue_entry
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return !server->console || !list_empty( &server->queue );
</span> }
+static unsigned int console_server_get_msync_idx( struct object *obj, enum msync_type *type )
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2409,17 +2362,17 @@ index dbd4a97459c..2b023546907 100644
</span> static struct fd *console_server_get_fd( struct object* obj )
{
struct console_server *server = (struct console_server*)obj;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -966,6 +989,9 @@ static struct object *create_console_server( void )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -945,6 +967,9 @@ static struct object *create_console_server( void )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span> allow_fd_caching(server->fd);
<span style='display:block; white-space:pre;background:#ffe0e0;'>- server->esync_fd = -1;
</span>
+ if (do_msync())
+ server->msync_idx = msync_alloc_shm( 0, 0 );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- server->esync_fd = esync_create_fd( 0, 0 );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return &server->obj;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span>
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1581,6 +1607,10 @@ DECL_HANDLER(get_next_console_request)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1557,6 +1582,10 @@ DECL_HANDLER(get_next_console_request)
</span> /* set result of previous ioctl */
ioctl = LIST_ENTRY( list_head( &server->queue ), struct console_host_ioctl, entry );
list_remove( &ioctl->entry );
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2427,110 +2380,108 @@ index dbd4a97459c..2b023546907 100644
</span> + if (do_msync() && list_empty( &server->queue ))
+ msync_clear_shm( server->msync_idx );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync() && list_empty( &server->queue ))
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_clear( server->esync_fd );
</span> }
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1668,6 +1698,10 @@ DECL_HANDLER(get_next_console_request)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if (ioctl)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1643,5 +1672,9 @@ DECL_HANDLER(get_next_console_request)
</span> set_error( STATUS_PENDING );
}
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+
</span> + if (do_msync() && list_empty( &server->queue ))
+ msync_clear_shm( server->msync_idx );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync() && list_empty( &server->queue ))
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_clear( server->esync_fd );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ release_object( server );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span> diff --git a/server/debugger.c b/server/debugger.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index ca04d4c71ce..946dc7b04b5 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index c59a0abea77..273a75840e5 100644
</span> --- a/server/debugger.c
+++ b/server/debugger.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -87,6 +87,7 @@ static const struct object_ops debug_event_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -86,6 +86,7 @@ static const struct object_ops debug_event_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
debug_event_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -116,6 +117,7 @@ static const struct object_ops debug_obj_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -114,6 +115,7 @@ static const struct object_ops debug_obj_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
debug_obj_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/device.c b/server/device.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index c45d0102a56..93e22bbd78a 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 436dac6bfe9..225f8b9890d 100644
</span> --- a/server/device.c
+++ b/server/device.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -39,6 +39,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -38,6 +38,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ #include "handle.h"
</span> #include "request.h"
#include "process.h"
<span style='display:block; white-space:pre;background:#ffe0e0;'>- #include "esync.h"
</span> +#include "msync.h"
/* IRP object */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -68,6 +69,7 @@ static const struct object_ops irp_call_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -66,6 +67,7 @@ static const struct object_ops irp_call_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -95,11 +97,13 @@ struct device_manager
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -92,10 +94,12 @@ struct device_manager
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ struct list requests; /* list of pending irps across all devices */
</span> struct irp_call *current_call; /* call currently executed on client side */
struct wine_rb_tree kernel_objects; /* map of objects that have client side pointer associated */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- int esync_fd; /* esync file descriptor */
</span> + unsigned int msync_idx;
};
static void device_manager_dump( struct object *obj, int verbose );
static int device_manager_signaled( struct object *obj, struct wait_queue_entry *entry );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- static int device_manager_get_esync_fd( struct object *obj, enum esync_type *type );
</span> +static unsigned int device_manager_get_msync_idx( struct object *obj, enum msync_type *type );
static void device_manager_destroy( struct object *obj );
static const struct object_ops device_manager_ops =
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -111,6 +115,7 @@ static const struct object_ops device_manager_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -106,6 +110,7 @@ static const struct object_ops device_manager_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
device_manager_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- device_manager_get_esync_fd, /* get_esync_fd */
</span> + device_manager_get_msync_idx, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -169,6 +174,7 @@ static const struct object_ops device_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -163,6 +168,7 @@ static const struct object_ops device_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -222,6 +228,7 @@ static const struct object_ops device_file_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -215,6 +221,7 @@ static const struct object_ops device_file_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
default_fd_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
device_file_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -754,6 +761,9 @@ static void delete_file( struct device_file *file )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -747,6 +754,9 @@ static void delete_file( struct device_file *file )
</span> /* terminate all pending requests */
LIST_FOR_EACH_ENTRY_SAFE( irp, next, &file->requests, struct irp_call, dev_entry )
{
+ if (do_msync() && file->device->manager && list_empty( &file->device->manager->requests ))
+ msync_clear( &file->device->manager->obj );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync() && file->device->manager && list_empty( &file->device->manager->requests ))
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_clear( file->device->manager->esync_fd );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -799,6 +809,13 @@ static int device_manager_get_esync_fd( struct object *obj, enum esync_type *typ
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return manager->esync_fd;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ list_remove( &irp->mgr_entry );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ set_irp_result( irp, STATUS_FILE_DELETED, NULL, 0, 0 );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -782,6 +792,13 @@ static int device_manager_signaled( struct object *obj, struct wait_queue_entry
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return !list_empty( &manager->requests );
</span> }
+static unsigned int device_manager_get_msync_idx( struct object *obj, enum msync_type *type )
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2543,142 +2494,120 @@ index c45d0102a56..93e22bbd78a 100644
</span> static void device_manager_destroy( struct object *obj )
{
struct device_manager *manager = (struct device_manager *)obj;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -834,6 +851,9 @@ static void device_manager_destroy( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -816,6 +833,9 @@ static void device_manager_destroy( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ assert( !irp->file && !irp->async );
</span> release_object( irp );
}
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync())
+ msync_destroy_semaphore( manager->msync_idx );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- close( manager->esync_fd );
</span> }
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -849,6 +869,9 @@ static struct device_manager *create_device_manager(void)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ static struct device_manager *create_device_manager(void)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -828,6 +848,9 @@ static struct device_manager *create_device_manager(void)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ list_init( &manager->devices );
</span> list_init( &manager->requests );
wine_rb_init( &manager->kernel_objects, compare_kernel_object );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync())
+ manager->msync_idx = msync_alloc_shm( 0, 0 );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- manager->esync_fd = esync_create_fd( 0, 0 );
</span> }
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1041,6 +1064,9 @@ DECL_HANDLER(get_next_device_request)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return manager;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1017,6 +1040,9 @@ DECL_HANDLER(get_next_device_request)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ /* we already own the object if it's only on manager queue */
</span> if (irp->file) grab_object( irp );
manager->current_call = irp;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync() && list_empty( &manager->requests ))
+ msync_clear( &manager->obj );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync() && list_empty( &manager->requests ))
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_clear( manager->esync_fd );
</span> }
<span style='display:block; white-space:pre;background:#e0ffe0;'>+ else close_handle( current->process, reply->next );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span> diff --git a/server/directory.c b/server/directory.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 1c44ded4606..962daee2045 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index b3f055dfd01..753d8904b6b 100644
</span> --- a/server/directory.c
+++ b/server/directory.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -70,6 +70,7 @@ static const struct object_ops object_type_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -69,6 +69,7 @@ static const struct object_ops object_type_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -121,6 +122,7 @@ static const struct object_ops directory_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -119,6 +120,7 @@ static const struct object_ops directory_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-diff --git a/server/esync.c b/server/esync.c
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-index e193f61b3a7..06e17c01874 100644
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>---- a/server/esync.c
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+++ b/server/esync.c
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -49,7 +49,7 @@ int do_esync(void)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- static int do_esync_cached = -1;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync_cached == -1)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-- do_esync_cached = getenv("WINEESYNC") && atoi(getenv("WINEESYNC"));
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ do_esync_cached = getenv("WINEESYNC") && atoi(getenv("WINEESYNC")) && !do_msync();
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return do_esync_cached;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- #else
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -128,6 +128,7 @@ const struct object_ops esync_ops =
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* remove_queue */
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* signaled */
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_get_esync_fd, /* get_esync_fd */
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ NULL, /* get_msync_idx */
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* satisfied */
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- no_signal, /* signal */
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- no_get_fd, /* get_fd */
</span> diff --git a/server/event.c b/server/event.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index f4ca3e48c6f..2770d83e6d6 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index f1b79b1b35e..0162b78a5be 100644
</span> --- a/server/event.c
+++ b/server/event.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -36,6 +36,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -35,6 +35,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ #include "thread.h"
</span> #include "request.h"
#include "security.h"
<span style='display:block; white-space:pre;background:#ffe0e0;'>- #include "esync.h"
</span> +#include "msync.h"
static const WCHAR event_name[] = {'E','v','e','n','t'};
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -58,12 +59,14 @@ struct event
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -56,11 +57,13 @@ struct event
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ struct list kernel_object; /* list of kernel object pointers */
</span> int manual_reset; /* is it a manual reset event? */
int signaled; /* event has been signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- int esync_fd; /* esync file descriptor */
</span> + unsigned int msync_idx;
};
static void event_dump( struct object *obj, int verbose );
static int event_signaled( struct object *obj, struct wait_queue_entry *entry );
static void event_satisfied( struct object *obj, struct wait_queue_entry *entry );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- static int event_get_esync_fd( struct object *obj, enum esync_type *type );
</span> +static unsigned int event_get_msync_idx( struct object *obj, enum msync_type *type );
static int event_signal( struct object *obj, unsigned int access);
static struct list *event_get_kernel_obj_list( struct object *obj );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- static void event_destroy( struct object *obj );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -77,6 +80,7 @@ static const struct object_ops event_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -72,6 +75,7 @@ static const struct object_ops event_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
event_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- event_get_esync_fd, /* get_esync_fd */
</span> + event_get_msync_idx, /* get_msync_idx */
event_satisfied, /* satisfied */
event_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -125,6 +129,7 @@ static const struct object_ops keyed_event_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -119,6 +123,7 @@ static const struct object_ops keyed_event_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
keyed_event_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -157,6 +162,9 @@ struct event *create_event( struct object *root, const struct unicode_str *name,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -150,6 +155,9 @@ struct event *create_event( struct object *root, const struct unicode_str *name,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ list_init( &event->kernel_object );
</span> event->manual_reset = manual_reset;
event->signaled = initial_state;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync())
+ event->msync_idx = msync_alloc_shm( initial_state, 0 );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- event->esync_fd = esync_create_fd( initial_state, 0 );
</span> }
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -167,6 +175,10 @@ struct event *create_event( struct object *root, const struct unicode_str *name,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return event;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -157,6 +165,10 @@ struct event *create_event( struct object *root, const struct unicode_str *name,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+
</span> struct event *get_event_obj( struct process *process, obj_handle_t handle, unsigned int access )
{
<span style='display:block; white-space:pre;background:#ffe0e0;'>- struct object *obj;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ struct object *obj;
</span> + if (do_msync() && (obj = get_handle_obj( process, handle, access, &msync_ops)))
+ return (struct event *)obj; /* even though it's not an event */
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync() && (obj = get_handle_obj( process, handle, access, &esync_ops)))
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return (struct event *)obj; /* even though it's not an event */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return (struct event *)get_handle_obj( process, handle, access, &event_ops );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span>
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -179,10 +191,19 @@ static void pulse_event( struct event *event )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -166,10 +178,19 @@ static void pulse_event( struct event *event )
</span> /* wake up all waiters if manual reset, a single one otherwise */
wake_up( &event->obj, !event->manual_reset );
event->signaled = 0;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2695,10 +2624,10 @@ index f4ca3e48c6f..2770d83e6d6 100644
</span> + return;
+ }
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync() && event->obj.ops == &esync_ops)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- {
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_set_event( (struct esync *)event );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -196,6 +217,12 @@ void set_event( struct event *event )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ event->signaled = 1;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ /* wake up all waiters if manual reset, a single one otherwise */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ wake_up( &event->obj, !event->manual_reset );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -177,7 +198,16 @@ void set_event( struct event *event )
</span>
void reset_event( struct event *event )
{
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2708,21 +2637,15 @@ index f4ca3e48c6f..2770d83e6d6 100644
</span> + return;
+ }
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync() && event->obj.ops == &esync_ops)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- {
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_reset_event( (struct esync *)event );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -203,6 +230,9 @@ void reset_event( struct event *event )
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- }
</span> event->signaled = 0;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync())
+ msync_clear( &event->obj );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_clear( event->esync_fd );
</span> }
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -229,6 +259,13 @@ static int event_get_esync_fd( struct object *obj, enum esync_type *type )
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return event->esync_fd;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ static void event_dump( struct object *obj, int verbose )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -195,6 +225,13 @@ static int event_signaled( struct object *obj, struct wait_queue_entry *entry )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return event->signaled;
</span> }
+static unsigned int event_get_msync_idx( struct object *obj, enum msync_type *type )
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2735,89 +2658,93 @@ index f4ca3e48c6f..2770d83e6d6 100644
</span> static void event_satisfied( struct object *obj, struct wait_queue_entry *entry )
{
struct event *event = (struct event *)obj;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -261,6 +298,9 @@ static void event_destroy( struct object *obj )
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- {
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- struct event *event = (struct event *)obj;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -223,6 +260,14 @@ static struct list *event_get_kernel_obj_list( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return &event->kernel_object;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span>
<span style='display:block; white-space:pre;background:#e0ffe0;'>++static void event_destroy( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++{
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ struct event *event = (struct event *)obj;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync())
+ msync_destroy_semaphore( event->msync_idx );
<span style='display:block; white-space:pre;background:#e0ffe0;'>++}
</span> +
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- close( event->esync_fd );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ struct keyed_event *create_keyed_event( struct object *root, const struct unicode_str *name,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ unsigned int attr, const struct security_descriptor *sd )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span> diff --git a/server/fd.c b/server/fd.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index b90999aae3c..17132109b8e 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index f28937466fc..17bde66453a 100644
</span> --- a/server/fd.c
+++ b/server/fd.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -98,6 +98,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -96,6 +96,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ #include "handle.h"
</span> #include "process.h"
#include "request.h"
<span style='display:block; white-space:pre;background:#ffe0e0;'>- #include "esync.h"
</span> +#include "msync.h"
#include "winternl.h"
#include "winioctl.h"
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -163,6 +164,7 @@ struct fd
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -156,6 +157,7 @@ struct fd
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ struct completion *completion; /* completion object attached to this fd */
</span> apc_param_t comp_key; /* completion key to set in completion events */
unsigned int comp_flags; /* completion flags */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- int esync_fd; /* esync file descriptor */
</span> + unsigned int msync_idx; /* msync shm index */
};
static void fd_dump( struct object *obj, int verbose );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -177,6 +179,7 @@ static const struct object_ops fd_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -169,6 +171,7 @@ static const struct object_ops fd_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -219,6 +222,7 @@ static const struct object_ops device_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -210,6 +213,7 @@ static const struct object_ops device_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -260,6 +264,7 @@ static const struct object_ops inode_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -250,6 +254,7 @@ static const struct object_ops inode_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -303,6 +308,7 @@ static const struct object_ops file_lock_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -292,6 +297,7 @@ static const struct object_ops file_lock_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
file_lock_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1652,6 +1658,9 @@ static void fd_destroy( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1565,6 +1571,9 @@ static void fd_destroy( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if (fd->unix_fd != -1) close( fd->unix_fd );
</span> free( fd->unix_name );
}
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync())
+ msync_destroy_semaphore( fd->msync_idx );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- close( fd->esync_fd );
</span> }
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1773,6 +1782,7 @@ static struct fd *alloc_fd_object(void)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ /* check if the desired access is possible without violating */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1683,12 +1692,16 @@ static struct fd *alloc_fd_object(void)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ fd->poll_index = -1;
</span> fd->completion = NULL;
fd->comp_flags = 0;
<span style='display:block; white-space:pre;background:#ffe0e0;'>- fd->esync_fd = -1;
</span> + fd->msync_idx = 0;
init_async_queue( &fd->read_q );
init_async_queue( &fd->write_q );
init_async_queue( &fd->wait_q );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1782,6 +1792,9 @@ static struct fd *alloc_fd_object(void)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- fd->esync_fd = esync_create_fd( 1, 0 );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ list_init( &fd->inode_entry );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ list_init( &fd->locks );
</span>
+ if (do_msync())
+ fd->msync_idx = msync_alloc_shm( 1, 0 );
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2825,37 +2752,33 @@ index b90999aae3c..17132109b8e 100644
</span> if ((fd->poll_index = add_poll_user( fd )) == -1)
{
release_object( fd );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1818,14 +1831,19 @@ struct fd *alloc_pseudo_fd( const struct fd_ops *fd_user_ops, struct object *use
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1724,11 +1737,15 @@ struct fd *alloc_pseudo_fd( const struct fd_ops *fd_user_ops, struct object *use
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ fd->completion = NULL;
</span> fd->comp_flags = 0;
fd->no_fd_status = STATUS_BAD_DEVICE_TYPE;
<span style='display:block; white-space:pre;background:#ffe0e0;'>- fd->esync_fd = -1;
</span> + fd->msync_idx = 0;
init_async_queue( &fd->read_q );
init_async_queue( &fd->write_q );
init_async_queue( &fd->wait_q );
list_init( &fd->inode_entry );
list_init( &fd->locks );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync())
+ fd->msync_idx = msync_alloc_shm( 0, 0 );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- fd->esync_fd = esync_create_fd( 0, 0 );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span> return fd;
}
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -2284,6 +2302,9 @@ void set_fd_signaled( struct fd *fd, int signaled )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -2140,6 +2157,9 @@ void set_fd_signaled( struct fd *fd, int signaled )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if (fd->comp_flags & FILE_SKIP_SET_EVENT_ON_HANDLE) return;
</span> fd->signaled = signaled;
if (signaled) wake_up( fd->user, 0 );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync() && !signaled)
+ msync_clear( fd->user );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync() && !signaled)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_clear( fd->esync_fd );
</span> }
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -2320,6 +2341,15 @@ int default_fd_get_esync_fd( struct object *obj, enum esync_type *type )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ /* check if events are pending and if yes return which one(s) */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -2165,6 +2185,15 @@ int default_fd_signaled( struct object *obj, struct wait_queue_entry *entry )
</span> return ret;
}
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2872,151 +2795,148 @@ index b90999aae3c..17132109b8e 100644
</span> {
int events = 0;
diff --git a/server/file.c b/server/file.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 828a21c08c6..017c89bf025 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 76c687833c9..8f51635c38a 100644
</span> --- a/server/file.c
+++ b/server/file.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -124,6 +124,7 @@ static const struct object_ops file_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -94,6 +94,7 @@ static const struct object_ops file_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
default_fd_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
file_get_fd, /* get_fd */
diff --git a/server/file.h b/server/file.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 0a81d7c4a3d..2654cb15ed7 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 006b5a8e324..12e71541ec0 100644
</span> --- a/server/file.h
+++ b/server/file.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -109,6 +109,7 @@ extern void get_nt_name( struct fd *fd, struct unicode_str *name );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -108,6 +108,7 @@ extern char *dup_fd_name( struct fd *root, const char *name ) __WINE_DEALLOC(fre
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ extern void get_nt_name( struct fd *fd, struct unicode_str *name );
</span>
extern int default_fd_signaled( struct object *obj, struct wait_queue_entry *entry );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- extern int default_fd_get_esync_fd( struct object *obj, enum esync_type *type );
</span> +extern unsigned int default_fd_get_msync_idx( struct object *obj, enum msync_type *type );
extern int default_fd_get_poll_events( struct fd *fd );
extern void default_poll_event( struct fd *fd, int event );
extern void fd_cancel_async( struct fd *fd, struct async *async );
diff --git a/server/handle.c b/server/handle.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 7fc24d12a34..0d3e1f74655 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index ef243e06e0b..48ab37b314b 100644
</span> --- a/server/handle.c
+++ b/server/handle.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -127,6 +127,7 @@ static const struct object_ops handle_table_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -126,6 +126,7 @@ static const struct object_ops handle_table_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/hook.c b/server/hook.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index ab4d0e9dd31..0bbdcc5aa88 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index c2d2823cd61..dfb210b9de6 100644
</span> --- a/server/hook.c
+++ b/server/hook.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -82,6 +82,7 @@ static const struct object_ops hook_table_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -81,6 +81,7 @@ static const struct object_ops hook_table_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/mailslot.c b/server/mailslot.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 4cf9b73f784..d04fc2f4edc 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 7defbccdb44..f7b8bca210d 100644
</span> --- a/server/mailslot.c
+++ b/server/mailslot.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -75,6 +75,7 @@ static const struct object_ops mailslot_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -81,6 +81,7 @@ static const struct object_ops mailslot_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
default_fd_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
mailslot_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -135,6 +136,7 @@ static const struct object_ops mail_writer_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -142,6 +143,7 @@ static const struct object_ops mail_writer_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
mail_writer_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -199,6 +201,7 @@ static const struct object_ops mailslot_device_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -207,6 +209,7 @@ static const struct object_ops mailslot_device_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -230,6 +233,7 @@ static const struct object_ops mailslot_device_file_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -237,6 +240,7 @@ static const struct object_ops mailslot_device_file_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
default_fd_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
mailslot_device_file_get_fd, /* get_fd */
diff --git a/server/main.c b/server/main.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 5062d0999fa..d5a8c05cb86 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 1248b92f24d..cedc5776a95 100644
</span> --- a/server/main.c
+++ b/server/main.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -35,6 +35,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -34,6 +34,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ #include "thread.h"
</span> #include "request.h"
#include "unicode.h"
<span style='display:block; white-space:pre;background:#ffe0e0;'>- #include "esync.h"
</span> +#include "msync.h"
/* command-line options */
int debug_level = 0;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -230,9 +231,15 @@ int main( int argc, char *argv[] )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -229,6 +230,12 @@ int main( int argc, char *argv[] )
</span> sock_init();
open_master_socket();
+ if (do_msync())
+ msync_init();
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_init();
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (!do_msync() && !do_esync())
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (!do_msync())
</span> + fprintf( stderr, "wineserver: using server-side synchronization.\n" );
+
if (debug_level) fprintf( stderr, "wineserver: starting (pid=%ld)\n", (long) getpid() );
set_current_time();
<span style='display:block; white-space:pre;background:#ffe0e0;'>- init_scheduler();
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ init_signals();
</span> diff --git a/server/mapping.c b/server/mapping.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index bdb9ee5d840..597416130f1 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 8a34760b10e..81b8e48caaf 100644
</span> --- a/server/mapping.c
+++ b/server/mapping.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -68,6 +68,7 @@ static const struct object_ops ranges_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -67,6 +67,7 @@ static const struct object_ops ranges_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -105,6 +106,7 @@ static const struct object_ops shared_map_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -103,6 +104,7 @@ static const struct object_ops shared_map_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -179,6 +181,7 @@ static const struct object_ops mapping_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -176,6 +178,7 @@ static const struct object_ops mapping_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
mapping_get_fd, /* get_fd */
diff --git a/server/msync.c b/server/msync.c
new file mode 100644
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 00000000000..b6e98cbffbe
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 00000000000..58c3542b7fc
</span> --- /dev/null
+++ b/server/msync.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -0,0 +1,992 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -0,0 +1,991 @@
</span> +/*
+ * mach semaphore-based synchronization objects
+ *
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -3626,7 +3546,6 @@ index 00000000000..b6e98cbffbe
</span> + no_add_queue, /* add_queue */
+ NULL, /* remove_queue */
+ NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ NULL, /* get_esync_fd */
</span> + msync_get_msync_idx, /* get_msync_idx */
+ NULL, /* satisfied */
+ no_signal, /* signal */
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4052,146 +3971,146 @@ index 00000000000..000aa48c53d
</span> +extern void msync_reset_event( struct msync *msync );
+extern void msync_abandon_mutexes( struct thread *thread );
diff --git a/server/mutex.c b/server/mutex.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 4785a830e92..6a60adee0bd 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index af0efe72132..0f6d013a119 100644
</span> --- a/server/mutex.c
+++ b/server/mutex.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -74,6 +74,7 @@ static const struct object_ops mutex_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -73,6 +73,7 @@ static const struct object_ops mutex_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
mutex_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
mutex_satisfied, /* satisfied */
mutex_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/named_pipe.c b/server/named_pipe.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index a90ec606226..d8d17fa95f7 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index dd8c14b30a9..bfe60839b6f 100644
</span> --- a/server/named_pipe.c
+++ b/server/named_pipe.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -120,6 +120,7 @@ static const struct object_ops named_pipe_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -119,6 +119,7 @@ static const struct object_ops named_pipe_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -169,6 +170,7 @@ static const struct object_ops pipe_server_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -167,6 +168,7 @@ static const struct object_ops pipe_server_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
default_fd_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- default_fd_get_esync_fd, /* get_esync_fd */
</span> + default_fd_get_msync_idx, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
pipe_end_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -214,6 +216,7 @@ static const struct object_ops pipe_client_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -211,6 +213,7 @@ static const struct object_ops pipe_client_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
default_fd_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- default_fd_get_esync_fd, /* get_esync_fd */
</span> + default_fd_get_msync_idx, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
pipe_end_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -262,6 +265,7 @@ static const struct object_ops named_pipe_device_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -258,6 +261,7 @@ static const struct object_ops named_pipe_device_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -294,6 +298,7 @@ static const struct object_ops named_pipe_device_file_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -289,6 +293,7 @@ static const struct object_ops named_pipe_device_file_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
default_fd_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
named_pipe_device_file_get_fd, /* get_fd */
diff --git a/server/object.h b/server/object.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index a6e9af93664..a59eb135501 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 2337ee88231..77084b1ee32 100644
</span> --- a/server/object.h
+++ b/server/object.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -80,6 +80,8 @@ struct object_ops
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -78,6 +78,8 @@ struct object_ops
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ void (*remove_queue)(struct object *,struct wait_queue_entry *);
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ /* is object signaled? */
</span> int (*signaled)(struct object *,struct wait_queue_entry *);
<span style='display:block; white-space:pre;background:#ffe0e0;'>- /* return the esync fd for this object */
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- int (*get_esync_fd)(struct object *, enum esync_type *type);
</span> + /* return the msync shm idx for this object */
+ unsigned int (*get_msync_idx)(struct object *, enum msync_type *type);
/* wait satisfied */
void (*satisfied)(struct object *,struct wait_queue_entry *);
/* signal an object */
diff --git a/server/process.c b/server/process.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index ce34f46166a..93bcd822b38 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 155dc050d95..f9b393e59e7 100644
</span> --- a/server/process.c
+++ b/server/process.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -64,6 +64,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -63,6 +63,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ #include "request.h"
</span> #include "user.h"
#include "security.h"
<span style='display:block; white-space:pre;background:#ffe0e0;'>- #include "esync.h"
</span> +#include "msync.h"
/* process object */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -97,6 +98,7 @@ static void process_poll_event( struct fd *fd, int event );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -95,6 +96,7 @@ static struct security_descriptor *process_get_sd( struct object *obj );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ static void process_poll_event( struct fd *fd, int event );
</span> static struct list *process_get_kernel_obj_list( struct object *obj );
static void process_destroy( struct object *obj );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- static int process_get_esync_fd( struct object *obj, enum esync_type *type );
</span> +static unsigned int process_get_msync_idx( struct object *obj, enum msync_type *type );
static void terminate_process( struct process *process, struct thread *skip, int exit_code );
static const struct object_ops process_ops =
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -108,6 +110,7 @@ static const struct object_ops process_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -105,6 +107,7 @@ static const struct object_ops process_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
process_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- process_get_esync_fd, /* get_esync_fd */
</span> + process_get_msync_idx, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -160,6 +163,7 @@ static const struct object_ops startup_info_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -156,6 +159,7 @@ static const struct object_ops startup_info_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
startup_info_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -222,6 +226,7 @@ static const struct object_ops job_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -217,6 +221,7 @@ static const struct object_ops job_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
job_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -691,6 +696,7 @@ struct process *create_process( int fd, struct process *parent, unsigned int fla
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -685,6 +690,7 @@ struct process *create_process( int fd, struct process *parent, unsigned int fla
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ process->rawinput_kbd = NULL;
</span> memset( &process->image_info, 0, sizeof(process->image_info) );
list_init( &process->rawinput_entry );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- process->esync_fd = -1;
</span> + process->msync_idx = 0;
list_init( &process->kernel_object );
list_init( &process->thread_list );
list_init( &process->locks );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -741,6 +747,9 @@ struct process *create_process( int fd, struct process *parent, unsigned int fla
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -735,6 +741,9 @@ struct process *create_process( int fd, struct process *parent, unsigned int fla
</span> if (!process->handles || !process->token) goto error;
process->session_id = token_get_session_id( process->token );
+ if (do_msync())
+ process->msync_idx = msync_alloc_shm( 0, 0 );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- process->esync_fd = esync_create_fd( 0, 0 );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ set_fd_events( process->msg_fd, POLLIN ); /* start listening to events */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return process;
</span>
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -793,6 +802,7 @@ static void process_destroy( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -783,6 +792,7 @@ static void process_destroy( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ free( process->rawinput_devices );
</span> free( process->dir_cache );
free( process->image );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync()) close( process->esync_fd );
</span> + if (do_msync()) msync_destroy_semaphore( process->msync_idx );
}
/* dump a process on stdout for debugging purposes */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -817,6 +827,13 @@ static int process_get_esync_fd( struct object *obj, enum esync_type *type )
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return process->esync_fd;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -800,6 +810,13 @@ static int process_signaled( struct object *obj, struct wait_queue_entry *entry
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return !process->running_threads;
</span> }
+static unsigned int process_get_msync_idx( struct object *obj, enum msync_type *type )
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4205,24 +4124,24 @@ index ce34f46166a..93bcd822b38 100644
</span> {
access = default_map_access( obj, access );
diff --git a/server/process.h b/server/process.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index bedd8bb4586..24276142a63 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 1e73e9d47dc..217d94aa63a 100644
</span> --- a/server/process.h
+++ b/server/process.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -87,6 +87,7 @@ struct process
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -86,6 +86,7 @@ struct process
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ struct list rawinput_entry; /* entry in the rawinput process list */
</span> struct list kernel_object; /* list of kernel object pointers */
pe_image_info_t image_info; /* main exe image info */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- int esync_fd; /* esync file descriptor (signaled on exit) */
</span> + unsigned int msync_idx;
};
/* process functions */
diff --git a/server/protocol.def b/server/protocol.def
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 1e4171c56ef..7ad9129f5d4 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 2c791cbdd46..9677e55f6ad 100644
</span> --- a/server/protocol.def
+++ b/server/protocol.def
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -4022,3 +4022,57 @@ enum esync_type
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- /* Retrieve the fd to wait on for user APCs. */
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- @REQ(get_esync_apc_fd)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -3953,3 +3953,57 @@ struct handle_info
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ @REPLY
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ int enable; /* previous state of auto-repeat enable */
</span> @END
+
+enum msync_type
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4279,62 +4198,62 @@ index 1e4171c56ef..7ad9129f5d4 100644
</span> + unsigned int shm_idx;
+@END
diff --git a/server/queue.c b/server/queue.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 109610b3d31..2c1f8053102 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 0156a4c66f2..ddf88a94581 100644
</span> --- a/server/queue.c
+++ b/server/queue.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -45,6 +45,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -44,6 +44,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ #include "process.h"
</span> #include "request.h"
#include "user.h"
<span style='display:block; white-space:pre;background:#ffe0e0;'>- #include "esync.h"
</span> +#include "msync.h"
#define WM_NCMOUSEFIRST WM_NCMOUSEMOVE
#define WM_NCMOUSELAST (WM_NCMOUSEFIRST+(WM_MOUSELAST-WM_MOUSEFIRST))
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -139,6 +140,8 @@ struct msg_queue
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- unsigned int ignore_post_msg; /* ignore post messages newer than this unique id */
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- int esync_fd; /* esync file descriptor (signalled on message) */
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- int esync_in_msgwait; /* our thread is currently waiting on us */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -133,6 +134,8 @@ struct msg_queue
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ timeout_t last_get_msg; /* time of last get message call */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ int keystate_lock; /* owns an input keystate lock */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ const queue_shm_t *shared; /* queue in session shared memory */
</span> + unsigned int msync_idx;
+ int msync_in_msgwait; /* our thread is currently waiting on us */
};
struct hotkey
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -156,6 +159,7 @@ static int msg_queue_add_queue( struct object *obj, struct wait_queue_entry *ent
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -149,6 +152,7 @@ static void msg_queue_dump( struct object *obj, int verbose );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ static int msg_queue_add_queue( struct object *obj, struct wait_queue_entry *entry );
</span> static void msg_queue_remove_queue( struct object *obj, struct wait_queue_entry *entry );
static int msg_queue_signaled( struct object *obj, struct wait_queue_entry *entry );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- static int msg_queue_get_esync_fd( struct object *obj, enum esync_type *type );
</span> +static unsigned int msg_queue_get_msync_idx( struct object *obj, enum msync_type *type );
static void msg_queue_satisfied( struct object *obj, struct wait_queue_entry *entry );
static void msg_queue_destroy( struct object *obj );
static void msg_queue_poll_event( struct fd *fd, int event );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -172,6 +176,7 @@ static const struct object_ops msg_queue_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -164,6 +168,7 @@ static const struct object_ops msg_queue_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ msg_queue_add_queue, /* add_queue */
</span> msg_queue_remove_queue, /* remove_queue */
msg_queue_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- msg_queue_get_esync_fd, /* get_esync_fd */
</span> + msg_queue_get_msync_idx, /* get_msync_idx */
msg_queue_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -210,6 +215,7 @@ static const struct object_ops thread_input_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -201,6 +206,7 @@ static const struct object_ops thread_input_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -324,6 +330,8 @@ static struct msg_queue *create_msg_queue( struct thread *thread, struct thread_
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- queue->ignore_post_msg = 0;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- queue->esync_fd = -1;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- queue->esync_in_msgwait = 0;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -312,6 +318,8 @@ static struct msg_queue *create_msg_queue( struct thread *thread, struct thread_
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ queue->hooks = NULL;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ queue->last_get_msg = current_time;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ queue->keystate_lock = 0;
</span> + queue->msync_idx = 0;
+ queue->msync_in_msgwait = 0;
list_init( &queue->send_result );
list_init( &queue->callback_result );
list_init( &queue->pending_timers );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -349,6 +357,9 @@ static struct msg_queue *create_msg_queue( struct thread *thread, struct thread_
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- queue->esync_fd = esync_create_fd( 0, 0 );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -334,6 +342,9 @@ static struct msg_queue *create_msg_queue( struct thread *thread, struct thread_
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SHARED_WRITE_END;
</span>
+ if (do_msync())
+ queue->msync_idx = msync_alloc_shm( 0, 0 );
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4342,28 +4261,29 @@ index 109610b3d31..2c1f8053102 100644
</span> thread->queue = queue;
if ((desktop = get_thread_desktop( thread, 0 )))
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -737,6 +748,9 @@ static inline void clear_queue_bits( struct msg_queue *queue, unsigned int bits
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -740,6 +751,9 @@ static inline void clear_queue_bits( struct msg_queue *queue, unsigned int bits
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if (queue->keystate_lock) unlock_input_keystate( queue->input );
</span> queue->keystate_lock = 0;
}
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync() && !is_signaled( queue ))
+ msync_clear( &queue->obj );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync() && !is_signaled( queue ))
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_clear( queue->esync_fd );
</span> }
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1228,6 +1242,9 @@ static int is_queue_hung( struct msg_queue *queue )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ /* check if message is matched by the filter */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1219,6 +1233,10 @@ static int is_queue_hung( struct msg_queue *queue )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if (get_wait_queue_thread(entry)->queue == queue)
</span> return 0; /* thread is waiting on queue -> not hung */
}
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync() && queue->msync_in_msgwait)
+ return 0; /* thread is waiting on queue in absentia -> not hung */
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync() && queue->esync_in_msgwait)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return 0; /* thread is waiting on queue in absentia -> not hung */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return 1;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span>
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1292,6 +1309,13 @@ static int msg_queue_get_esync_fd( struct object *obj, enum esync_type *type )
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return queue->esync_fd;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1273,6 +1291,13 @@ static int msg_queue_signaled( struct object *obj, struct wait_queue_entry *entr
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return ret || is_signaled( queue );
</span> }
+static unsigned int msg_queue_get_msync_idx( struct object *obj, enum msync_type *type )
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4376,46 +4296,49 @@ index 109610b3d31..2c1f8053102 100644
</span> static void msg_queue_satisfied( struct object *obj, struct wait_queue_entry *entry )
{
struct msg_queue *queue = (struct msg_queue *)obj;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1349,6 +1373,8 @@ static void msg_queue_destroy( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1329,6 +1354,8 @@ static void msg_queue_destroy( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if (queue->hooks) release_object( queue->hooks );
</span> if (queue->fd) release_object( queue->fd );
if (queue->shared) free_shared_object( queue->shared );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync()) close( queue->esync_fd );
</span> + if (do_msync())
+ msync_destroy_semaphore( queue->msync_idx );
}
static void msg_queue_poll_event( struct fd *fd, int event )
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -3121,6 +3147,8 @@ DECL_HANDLER(set_queue_mask)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -3106,6 +3133,9 @@ DECL_HANDLER(set_queue_mask)
</span> }
else wake_up( &queue->obj, 0 );
}
<span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync() && !is_signaled( queue ))
+ msync_clear( &queue->obj );
<span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span>
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync() && !is_signaled( queue ))
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_clear( queue->esync_fd );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -3145,6 +3173,9 @@ DECL_HANDLER(get_queue_status)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -3126,6 +3156,9 @@ DECL_HANDLER(get_queue_status)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ shared->changed_bits &= ~req->clear_bits;
</span> }
SHARED_WRITE_END;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync() && !is_signaled( queue ))
+ msync_clear( &queue->obj );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync() && !is_signaled( queue ))
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_clear( queue->esync_fd );
</span> }
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -3416,6 +3447,9 @@ DECL_HANDLER(get_message)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ else reply->wake_bits = reply->changed_bits = 0;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -3383,6 +3416,11 @@ DECL_HANDLER(get_message)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ SHARED_WRITE_END;
</span>
set_error( STATUS_PENDING ); /* FIXME */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync() && !is_signaled( queue ))
+ msync_clear( &queue->obj );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync() && !is_signaled( queue ))
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_clear( queue->esync_fd );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ return;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span>
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -4220,6 +4254,23 @@ DECL_HANDLER(esync_msgwait)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- set_fd_events( queue->fd, req->in_msgwait ? POLLIN : 0 );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -4155,6 +4193,23 @@ DECL_HANDLER(update_rawinput_devices)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span> }
+DECL_HANDLER(msync_msgwait)
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4439,37 +4362,37 @@ index 109610b3d31..2c1f8053102 100644
</span> {
struct desktop *desktop;
diff --git a/server/registry.c b/server/registry.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 1cca1acfe6b..eb54495208c 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 804cfcc638b..1b2da63cafb 100644
</span> --- a/server/registry.c
+++ b/server/registry.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -181,6 +181,7 @@ static const struct object_ops key_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -180,6 +180,7 @@ static const struct object_ops key_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/request.c b/server/request.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 8e7d88a0d4c..3287b16170d 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 2691e0c7cff..84f5032d59f 100644
</span> --- a/server/request.c
+++ b/server/request.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -91,6 +91,7 @@ static const struct object_ops master_socket_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -90,6 +90,7 @@ static const struct object_ops master_socket_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/request.h b/server/request.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index a68983ef6dc..32fd61d7903 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 6158aefdb78..6b876918510 100644
</span> --- a/server/request.h
+++ b/server/request.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -411,6 +411,11 @@ DECL_HANDLER(get_esync_fd);
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- DECL_HANDLER(esync_msgwait);
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -405,6 +405,11 @@ DECL_HANDLER(suspend_process);
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ DECL_HANDLER(resume_process);
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ DECL_HANDLER(get_next_thread);
</span> DECL_HANDLER(set_keyboard_repeat);
<span style='display:block; white-space:pre;background:#ffe0e0;'>- DECL_HANDLER(get_esync_apc_fd);
</span> +DECL_HANDLER(create_msync);
+DECL_HANDLER(open_msync);
+DECL_HANDLER(get_msync_idx);
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4478,10 +4401,10 @@ index a68983ef6dc..32fd61d7903 100644
</span>
#ifdef WANT_REQUEST_HANDLERS
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -709,6 +714,11 @@ static const req_handler req_handlers[REQ_NB_REQUESTS] =
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- (req_handler)req_esync_msgwait,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -697,6 +702,11 @@ static const req_handler req_handlers[REQ_NB_REQUESTS] =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ (req_handler)req_resume_process,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ (req_handler)req_get_next_thread,
</span> (req_handler)req_set_keyboard_repeat,
<span style='display:block; white-space:pre;background:#ffe0e0;'>- (req_handler)req_get_esync_apc_fd,
</span> + (req_handler)req_create_msync,
+ (req_handler)req_open_msync,
+ (req_handler)req_get_msync_idx,
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4490,10 +4413,10 @@ index a68983ef6dc..32fd61d7903 100644
</span> };
C_ASSERT( sizeof(abstime_t) == 8 );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -2386,6 +2396,34 @@ C_ASSERT( sizeof(struct set_keyboard_repeat_request) == 24 );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -2341,6 +2351,34 @@ C_ASSERT( FIELD_OFFSET(struct set_keyboard_repeat_request, period) == 20 );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ C_ASSERT( sizeof(struct set_keyboard_repeat_request) == 24 );
</span> C_ASSERT( FIELD_OFFSET(struct set_keyboard_repeat_reply, enable) == 8 );
C_ASSERT( sizeof(struct set_keyboard_repeat_reply) == 16 );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- C_ASSERT( sizeof(struct get_esync_apc_fd_request) == 16 );
</span> +C_ASSERT( FIELD_OFFSET(struct create_msync_request, access) == 12 );
+C_ASSERT( FIELD_OFFSET(struct create_msync_request, low) == 16 );
+C_ASSERT( FIELD_OFFSET(struct create_msync_request, high) == 20 );
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4526,135 +4449,135 @@ index a68983ef6dc..32fd61d7903 100644
</span> #endif /* WANT_REQUEST_HANDLERS */
diff --git a/server/semaphore.c b/server/semaphore.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index e3889f24601..8d3c325c0b3 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 53b42a886df..bbcbc831793 100644
</span> --- a/server/semaphore.c
+++ b/server/semaphore.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -71,6 +71,7 @@ static const struct object_ops semaphore_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -70,6 +70,7 @@ static const struct object_ops semaphore_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
semaphore_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
semaphore_satisfied, /* satisfied */
semaphore_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/serial.c b/server/serial.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 0d49a996c2a..9c28c78cf28 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 209f2e9174e..62eafa87408 100644
</span> --- a/server/serial.c
+++ b/server/serial.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -92,6 +92,7 @@ static const struct object_ops serial_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -91,6 +91,7 @@ static const struct object_ops serial_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
default_fd_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
serial_get_fd, /* get_fd */
diff --git a/server/signal.c b/server/signal.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 55cd6aa037e..e86ad49df8e 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 19b76d44c16..57415604d07 100644
</span> --- a/server/signal.c
+++ b/server/signal.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -63,6 +63,7 @@ static const struct object_ops handler_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -62,6 +62,7 @@ static const struct object_ops handler_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/sock.c b/server/sock.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 7be912b3b50..af92f134538 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 06ffd1b81f8..e7081476458 100644
</span> --- a/server/sock.c
+++ b/server/sock.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -454,6 +454,7 @@ static const struct object_ops sock_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -453,6 +453,7 @@ static const struct object_ops sock_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
default_fd_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
sock_get_fd, /* get_fd */
@@ -3562,6 +3563,7 @@ static const struct object_ops ifchange_ops =
<span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
ifchange_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -3784,6 +3786,7 @@ static const struct object_ops socket_device_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -3783,6 +3785,7 @@ static const struct object_ops socket_device_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/symlink.c b/server/symlink.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index c7f34412317..d40d060492b 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index dd28efd3a75..d6a51f0091d 100644
</span> --- a/server/symlink.c
+++ b/server/symlink.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -72,6 +72,7 @@ static const struct object_ops symlink_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -71,6 +71,7 @@ static const struct object_ops symlink_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/thread.c b/server/thread.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index dac5c43e3bd..5003898e822 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 6542e1584ab..7026c785a13 100644
</span> --- a/server/thread.c
+++ b/server/thread.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -51,6 +51,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -50,6 +50,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ #include "request.h"
</span> #include "user.h"
#include "security.h"
<span style='display:block; white-space:pre;background:#ffe0e0;'>- #include "esync.h"
</span> +#include "msync.h"
/* thread queues */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -98,6 +99,7 @@ static const struct object_ops thread_apc_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -96,6 +97,7 @@ static const struct object_ops thread_apc_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
thread_apc_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -141,6 +143,7 @@ static const struct object_ops context_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -138,6 +140,7 @@ static const struct object_ops context_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
context_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -178,6 +181,7 @@ struct type_descr thread_type =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -174,6 +177,7 @@ struct type_descr thread_type =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+
</span> static void dump_thread( struct object *obj, int verbose );
static int thread_signaled( struct object *obj, struct wait_queue_entry *entry );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- static int thread_get_esync_fd( struct object *obj, enum esync_type *type );
</span> +static unsigned int thread_get_msync_idx( struct object *obj, enum msync_type *type );
static unsigned int thread_map_access( struct object *obj, unsigned int access );
static void thread_poll_event( struct fd *fd, int event );
static struct list *thread_get_kernel_obj_list( struct object *obj );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -192,6 +196,7 @@ static const struct object_ops thread_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -187,6 +191,7 @@ static const struct object_ops thread_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
thread_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- thread_get_esync_fd, /* get_esync_fd */
</span> + thread_get_msync_idx, /* get_msync_idx */
no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -233,6 +238,8 @@ static inline void init_thread_structure( struct thread *thread )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -226,6 +231,8 @@ static inline void init_thread_structure( struct thread *thread )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ thread->context = NULL;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ thread->teb = 0;
</span> thread->entry_point = 0;
<span style='display:block; white-space:pre;background:#ffe0e0;'>- thread->esync_fd = -1;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- thread->esync_apc_fd = -1;
</span> + thread->msync_idx = 0;
+ thread->msync_apc_idx = 0;
thread->system_regs = 0;
thread->queue = NULL;
thread->wait = NULL;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -380,6 +387,12 @@ struct thread *create_thread( int fd, struct process *process, const struct secu
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -372,6 +379,12 @@ struct thread *create_thread( int fd, struct process *process, const struct secu
</span> }
}
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4664,13 +4587,13 @@ index dac5c43e3bd..5003898e822 100644
</span> + thread->msync_apc_idx = msync_alloc_shm( 0, 0 );
+ }
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- {
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- thread->esync_fd = esync_create_fd( 0, 0 );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -468,6 +481,12 @@ static void destroy_thread( struct object *obj )
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- close( thread->esync_fd );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ set_fd_events( thread->request_fd, POLLIN ); /* start listening to events */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_process_thread( thread->process, thread );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return thread;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -450,6 +463,12 @@ static void destroy_thread( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ release_object( thread->process );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if (thread->id) free_ptid( thread->id );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if (thread->token) release_object( thread->token );
</span> +
+ if (do_msync())
+ {
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4680,8 +4603,8 @@ index dac5c43e3bd..5003898e822 100644
</span> }
/* dump a thread on stdout for debugging purposes */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -493,6 +512,13 @@ static int thread_get_esync_fd( struct object *obj, enum esync_type *type )
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return thread->esync_fd;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -468,6 +487,13 @@ static int thread_signaled( struct object *obj, struct wait_queue_entry *entry )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return (mythread->state == TERMINATED);
</span> }
+static unsigned int thread_get_msync_idx( struct object *obj, enum msync_type *type )
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4694,7 +4617,7 @@ index dac5c43e3bd..5003898e822 100644
</span> static unsigned int thread_map_access( struct object *obj, unsigned int access )
{
access = default_map_access( obj, access );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -545,6 +571,7 @@ static struct thread_apc *create_apc( struct object *owner, const apc_call_t *ca
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -520,6 +546,7 @@ static struct thread_apc *create_apc( struct object *owner, const apc_call_t *ca
</span> apc->result.type = APC_NONE;
if (owner) grab_object( owner );
}
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4702,114 +4625,117 @@ index dac5c43e3bd..5003898e822 100644
</span> return apc;
}
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1091,6 +1118,9 @@ void wake_up( struct object *obj, int max )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1063,6 +1090,9 @@ void wake_up( struct object *obj, int max )
</span> struct list *ptr;
int ret;
+ if (do_msync())
+ msync_wake_up( obj );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_wake_up( obj );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1181,6 +1211,9 @@ static int queue_apc( struct process *process, struct thread *thread, struct thr
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ LIST_FOR_EACH( ptr, &obj->wait_queue )
</span> {
<span style='display:block; white-space:pre;background:#e0ffe0;'>+ struct wait_queue_entry *entry = LIST_ENTRY( ptr, struct wait_queue_entry, entry );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1147,8 +1177,12 @@ static int queue_apc( struct process *process, struct thread *thread, struct thr
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ grab_object( apc );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ list_add_tail( queue, &apc->entry );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if (!list_prev( queue, &apc->entry )) /* first one */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ {
</span> wake_thread( thread );
+ if (do_msync() && queue == &thread->user_apc)
+ msync_signal_all( thread->msync_apc_idx );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync() && queue == &thread->user_apc)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_wake_fd( thread->esync_apc_fd );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- }
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1231,6 +1264,9 @@ static struct thread_apc *thread_dequeue_apc( struct thread *thread, int system
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return 1;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1194,6 +1228,10 @@ static struct thread_apc *thread_dequeue_apc( struct thread *thread, int system
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ apc = LIST_ENTRY( ptr, struct thread_apc, entry );
</span> list_remove( ptr );
}
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync() && list_empty( &thread->system_apc ) && list_empty( &thread->user_apc ))
+ msync_clear_shm( thread->msync_apc_idx );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync() && list_empty( &thread->system_apc ) && list_empty( &thread->user_apc ))
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_clear( thread->esync_apc_fd );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return apc;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span>
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1349,6 +1385,8 @@ void kill_thread( struct thread *thread, int violent_death )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1289,6 +1327,8 @@ void kill_thread( struct thread *thread, int violent_death )
</span> }
kill_console_processes( thread, 0 );
abandon_mutexes( thread );
+ if (do_msync())
+ msync_abandon_mutexes( thread );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_abandon_mutexes( thread );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (violent_death)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ wake_up( &thread->obj, 0 );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ if (violent_death) send_thread_signal( thread, SIGQUIT );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ cleanup_thread( thread );
</span> diff --git a/server/thread.h b/server/thread.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 10e9e28b432..26b41745261 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 766ed78a72f..d9116df1cba 100644
</span> --- a/server/thread.h
+++ b/server/thread.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -57,6 +57,8 @@ struct thread
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -55,6 +55,8 @@ struct thread
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ struct process *process;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ thread_id_t id; /* thread id */
</span> struct list mutex_list; /* list of currently owned mutexes */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- int esync_fd; /* esync file descriptor (signalled on exit) */
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- int esync_apc_fd; /* esync apc fd (signalled when APCs are present) */
</span> + unsigned int msync_idx;
+ unsigned int msync_apc_idx;
unsigned int system_regs; /* which system regs have been set */
struct msg_queue *queue; /* message queue */
struct thread_wait *wait; /* current wait condition if sleeping */
diff --git a/server/timer.c b/server/timer.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 36645a2a8d2..d57a5536eb3 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 96dc9d00ca1..75756b27c66 100644
</span> --- a/server/timer.c
+++ b/server/timer.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -36,6 +36,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -35,6 +35,7 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ #include "file.h"
</span> #include "handle.h"
#include "request.h"
<span style='display:block; white-space:pre;background:#ffe0e0;'>- #include "esync.h"
</span> +#include "msync.h"
static const WCHAR timer_name[] = {'T','i','m','e','r'};
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -63,11 +64,13 @@ struct timer
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -61,10 +62,12 @@ struct timer
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ struct thread *thread; /* thread that set the APC function */
</span> client_ptr_t callback; /* callback APC function */
client_ptr_t arg; /* callback argument */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- int esync_fd; /* esync file descriptor */
</span> + unsigned int msync_idx; /* msync shm index */
};
static void timer_dump( struct object *obj, int verbose );
static int timer_signaled( struct object *obj, struct wait_queue_entry *entry );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- static int timer_get_esync_fd( struct object *obj, enum esync_type *type );
</span> +static unsigned int timer_get_msync_idx( struct object *obj, enum msync_type *type );
static void timer_satisfied( struct object *obj, struct wait_queue_entry *entry );
static void timer_destroy( struct object *obj );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -80,6 +83,7 @@ static const struct object_ops timer_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -76,6 +79,7 @@ static const struct object_ops timer_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ add_queue, /* add_queue */
</span> remove_queue, /* remove_queue */
timer_signaled, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- timer_get_esync_fd, /* get_esync_fd */
</span> + timer_get_msync_idx, /* get_msync_idx */
timer_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -116,6 +120,9 @@ static struct timer *create_timer( struct object *root, const struct unicode_str
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -110,6 +114,9 @@ static struct timer *create_timer( struct object *root, const struct unicode_str
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ timer->period = 0;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ timer->timeout = NULL;
</span> timer->thread = NULL;
<span style='display:block; white-space:pre;background:#ffe0e0;'>- timer->esync_fd = -1;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span> + if (do_msync())
+ timer->msync_idx = msync_alloc_shm( 0, 0 );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- timer->esync_fd = esync_create_fd( 0, 0 );
</span> }
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -190,6 +197,9 @@ static int set_timer( struct timer *timer, timeout_t expire, unsigned int period
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return timer;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -181,6 +188,9 @@ static int set_timer( struct timer *timer, timeout_t expire, unsigned int period
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ {
</span> period = 0; /* period doesn't make any sense for a manual timer */
timer->signaled = 0;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + if (do_msync())
+ msync_clear( &timer->obj );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync())
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- esync_clear( timer->esync_fd );
</span> }
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -226,6 +236,13 @@ static int timer_get_esync_fd( struct object *obj, enum esync_type *type )
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return timer->esync_fd;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ timer->when = (expire <= 0) ? expire - monotonic_time : max( expire, current_time );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ timer->period = period;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -208,6 +218,13 @@ static int timer_signaled( struct object *obj, struct wait_queue_entry *entry )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ return timer->signaled;
</span> }
+static unsigned int timer_get_msync_idx( struct object *obj, enum msync_type *type )
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4822,33 +4748,33 @@ index 36645a2a8d2..d57a5536eb3 100644
</span> static void timer_satisfied( struct object *obj, struct wait_queue_entry *entry )
{
struct timer *timer = (struct timer *)obj;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -241,6 +258,8 @@ static void timer_destroy( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -222,6 +239,8 @@ static void timer_destroy( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+
</span> if (timer->timeout) remove_timeout_user( timer->timeout );
if (timer->thread) release_object( timer->thread );
<span style='display:block; white-space:pre;background:#ffe0e0;'>- if (do_esync()) close( timer->esync_fd );
</span> + if (do_msync())
+ msync_destroy_semaphore( timer->msync_idx );
}
/* create a timer */
diff --git a/server/token.c b/server/token.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index e40ba10f9aa..1101c7224b9 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index da7f0bb7ff2..1394d06750a 100644
</span> --- a/server/token.c
+++ b/server/token.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -146,6 +146,7 @@ static const struct object_ops token_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -145,6 +145,7 @@ static const struct object_ops token_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/trace.c b/server/trace.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 89e9c0b3aa1..f692e86a878 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 96dc5781d4c..345b622d22b 100644
</span> --- a/server/trace.c
+++ b/server/trace.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -4712,6 +4712,63 @@ static void dump_get_esync_apc_fd_request( const struct get_esync_apc_fd_request
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -4641,6 +4641,63 @@ static void dump_set_keyboard_repeat_reply( const struct set_keyboard_repeat_rep
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ fprintf( stderr, " enable=%d", req->enable );
</span> }
+static void dump_create_msync_request( const struct create_msync_request *req )
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4911,10 +4837,10 @@ index 89e9c0b3aa1..f692e86a878 100644
</span> static const dump_func req_dumpers[REQ_NB_REQUESTS] = {
(dump_func)dump_new_process_request,
(dump_func)dump_get_new_process_info_request,
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -5005,6 +5062,11 @@ static const dump_func req_dumpers[REQ_NB_REQUESTS] = {
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- (dump_func)dump_esync_msgwait_request,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -4928,6 +4985,11 @@ static const dump_func req_dumpers[REQ_NB_REQUESTS] = {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ (dump_func)dump_resume_process_request,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ (dump_func)dump_get_next_thread_request,
</span> (dump_func)dump_set_keyboard_repeat_request,
<span style='display:block; white-space:pre;background:#ffe0e0;'>- (dump_func)dump_get_esync_apc_fd_request,
</span> + (dump_func)dump_create_msync_request,
+ (dump_func)dump_open_msync_request,
+ (dump_func)dump_get_msync_idx_request,
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4923,10 +4849,10 @@ index 89e9c0b3aa1..f692e86a878 100644
</span> };
static const dump_func reply_dumpers[REQ_NB_REQUESTS] = {
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -5300,6 +5362,11 @@ static const dump_func reply_dumpers[REQ_NB_REQUESTS] = {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -5217,6 +5279,11 @@ static const dump_func reply_dumpers[REQ_NB_REQUESTS] = {
</span> NULL,
<span style='display:block; white-space:pre;background:#e0ffe0;'>+ (dump_func)dump_get_next_thread_reply,
</span> (dump_func)dump_set_keyboard_repeat_reply,
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL,
</span> + (dump_func)dump_create_msync_reply,
+ (dump_func)dump_open_msync_reply,
+ (dump_func)dump_get_msync_idx_reply,
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4935,10 +4861,10 @@ index 89e9c0b3aa1..f692e86a878 100644
</span> };
static const char * const req_names[REQ_NB_REQUESTS] = {
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -5595,6 +5662,11 @@ static const char * const req_names[REQ_NB_REQUESTS] = {
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- "esync_msgwait",
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -5506,6 +5573,11 @@ static const char * const req_names[REQ_NB_REQUESTS] = {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ "resume_process",
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ "get_next_thread",
</span> "set_keyboard_repeat",
<span style='display:block; white-space:pre;background:#ffe0e0;'>- "get_esync_apc_fd",
</span> + "create_msync",
+ "open_msync",
+ "get_msync_idx",
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4948,33 +4874,33 @@ index 89e9c0b3aa1..f692e86a878 100644
</span>
static const struct
diff --git a/server/window.c b/server/window.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 13318b75fe2..85ee8d8f9b2 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 564c69bf18d..e605324a865 100644
</span> --- a/server/window.c
+++ b/server/window.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -107,6 +107,7 @@ static const struct object_ops window_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -106,6 +106,7 @@ static const struct object_ops window_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/winstation.c b/server/winstation.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 5cd235c528e..c1dfbc85272 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 76a23b197a4..da1fecf30da 100644
</span> --- a/server/winstation.c
+++ b/server/winstation.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -77,6 +77,7 @@ static const struct object_ops winstation_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -76,6 +76,7 @@ static const struct object_ops winstation_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -118,6 +119,7 @@ static const struct object_ops desktop_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -116,6 +117,7 @@ static const struct object_ops desktop_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ no_add_queue, /* add_queue */
</span> NULL, /* remove_queue */
NULL, /* signaled */
<span style='display:block; white-space:pre;background:#ffe0e0;'>- NULL, /* get_esync_fd */
</span> + NULL, /* get_msync_idx */
NULL, /* satisfied */
no_signal, /* signal */
<span style='display:block; white-space:pre;color:#808080;'>diff --git a/emulators/wine-devel/files/1001-msync.diff b/emulators/wine-devel/files/1001-staging-msync.diff
</span>similarity index 97%
rename from emulators/wine-devel/files/1001-msync.diff
rename to emulators/wine-devel/files/1001-staging-msync.diff
<span style='display:block; white-space:pre;color:#808080;'>index d9457b5f342..d3c89c80a5a 100644
</span><span style='display:block; white-space:pre;background:#e0e0ff;'>--- a/emulators/wine-devel/files/1001-msync.diff
</span><span style='display:block; white-space:pre;background:#e0e0ff;'>+++ b/emulators/wine-devel/files/1001-staging-msync.diff
</span><span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -11,7 +11,7 @@ index 78b3fdf94aa..061c730bf63 100644
</span> unix/loadorder.c \
unix/process.c \
diff --git a/dlls/ntdll/unix/esync.c b/dlls/ntdll/unix/esync.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 85d3db0cb8c..b63a386ee96 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index f4748e405ef..2e116a56f4b 100644
</span> --- a/dlls/ntdll/unix/esync.c
+++ b/dlls/ntdll/unix/esync.c
@@ -51,6 +51,7 @@
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -70,10 +70,10 @@ index 85d3db0cb8c..b63a386ee96 100644
</span> /* Try to check objects now, so we can obviate poll() at least. */
for (i = 0; i < count; i++)
diff --git a/dlls/ntdll/unix/loader.c b/dlls/ntdll/unix/loader.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index ae7e2e8e6ec..a7175b35ae6 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index d8f289054d4..67485a863f5 100644
</span> --- a/dlls/ntdll/unix/loader.c
+++ b/dlls/ntdll/unix/loader.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -89,6 +89,7 @@ extern char **environ;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -91,6 +91,7 @@
</span> #include "winternl.h"
#include "unix_private.h"
#include "esync.h"
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -81,7 +81,7 @@ index ae7e2e8e6ec..a7175b35ae6 100644
</span> #include "wine/list.h"
#include "ntsyscalls.h"
#include "wine/debug.h"
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1896,6 +1897,7 @@ static void start_main_thread(void)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1859,6 +1860,7 @@ static void start_main_thread(void)
</span> signal_alloc_thread( teb );
dbg_init();
startup_info_size = server_init_process();
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -91,10 +91,10 @@ index ae7e2e8e6ec..a7175b35ae6 100644
</span> init_cpu_info();
diff --git a/dlls/ntdll/unix/msync.c b/dlls/ntdll/unix/msync.c
new file mode 100644
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 00000000000..90e785f6df2
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 00000000000..2eef30dd0f2
</span> --- /dev/null
+++ b/dlls/ntdll/unix/msync.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -0,0 +1,1661 @@
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -0,0 +1,1689 @@
</span> +/*
+ * mach semaphore-based synchronization objects
+ *
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -412,7 +412,7 @@ index 00000000000..90e785f6df2
</span> +
+static const mach_msg_bits_t msgh_bits_send = MACH_MSGH_BITS_REMOTE(MACH_MSG_TYPE_COPY_SEND);
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+static inline void server_register_wait( semaphore_t sem, unsigned int msgh_id,
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++static inline mach_msg_return_t server_register_wait( semaphore_t sem, unsigned int msgh_id,
</span> + struct msync **wait_objs, const int count )
+{
+ int i, is_mutex;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -444,10 +444,11 @@ index 00000000000..90e785f6df2
</span> +
+ if (mr != MACH_MSG_SUCCESS)
+ ERR("Failed to send server register wait: %#x\n", mr);
<span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ return mr;
</span> +}
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+static inline void server_remove_wait( semaphore_t sem, unsigned int msgh_id,
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ struct msync **wait_objs, const int count )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++static inline void server_remove_wait( unsigned int msgh_id, struct msync **wait_objs, const int count )
</span> +{
+ int i;
+ mach_msg_return_t mr;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -504,19 +505,19 @@ index 00000000000..90e785f6df2
</span> +}
+
+static inline NTSTATUS msync_wait_single( struct msync *wait_obj,
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ ULONGLONG *end )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ ULONGLONG *end, int tid )
</span> +{
+ int ret, val = 0;
+ void *addr = wait_obj->shm;
+ ULONGLONG ns_timeleft = 0;
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ do
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ do
</span> + {
+ if (wait_obj->type == MSYNC_MUTEX)
+ {
+ val = __atomic_load_n( (int *)addr, __ATOMIC_ACQUIRE );
+ if (!val || val == ~0)
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ val = GetCurrentThreadId();
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ val = tid;
</span> + }
+
+ if (__atomic_load_n( (int *)addr, __ATOMIC_ACQUIRE ) != val)
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -577,27 +578,51 @@ index 00000000000..90e785f6df2
</span> +}
+
+static NTSTATUS msync_wait_multiple( struct msync **wait_objs,
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ int count, ULONGLONG *end )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ int count, ULONGLONG *end, int tid )
</span> +{
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ int tid;
</span> + semaphore_t *sem;
+ kern_return_t kr;
<span style='display:block; white-space:pre;background:#e0ffe0;'>++ mach_msg_return_t mr;
</span> + unsigned int msgh_id;
+ __thread static struct msync *objs[MAXIMUM_WAIT_OBJECTS + 1];
+
+ count = resize_wait_objs( wait_objs, objs, count );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (count == 1 && __ulock_wait2) return msync_wait_single( objs[0], end );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (count == 1 && __ulock_wait2) return msync_wait_single( objs[0], end, tid );
</span> + if (!count) return destroyed_wait( end );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ tid = GetCurrentThreadId();
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+
</span> + if (check_shm_contention( objs, count, tid ))
+ return STATUS_PENDING;
+
+ sem = semaphore_pool_alloc();
+ msgh_id = (tid << 8) | count;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ server_register_wait( *sem, msgh_id, objs, count );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ mr = server_register_wait( *sem, msgh_id, objs, count );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (mr != MACH_MSG_SUCCESS)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ /* The os failed to send the mach message, which is either because
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ * we lost the wineserver process or the semaphore from semaphore_pool_alloc
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ * is not valid...
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ * To avoid pooling in a dead port, recreate it here.
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ * Worst case, this will behave effectively like a spinlock. */
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ semaphore_destroy( mach_task_self(), *sem) ;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ kr = semaphore_create( mach_task_self(), sem, SYNC_POLICY_FIFO, 0 );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (kr != KERN_SUCCESS)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ ERR("Cannot create semaphore: %#x %s\n", kr, mach_error_string(kr));
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ semaphore_pool_free( sem );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ return STATUS_PENDING;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ mr = server_register_wait( *sem, msgh_id, objs, count );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (mr != MACH_MSG_SUCCESS)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ {
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ semaphore_pool_free( sem );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ return STATUS_PENDING;
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ }
</span> +
+ do
+ {
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -613,7 +638,7 @@ index 00000000000..90e785f6df2
</span> + if (is_destroyed( objs, count ))
+ return destroyed_wait( end );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ server_remove_wait( *sem, msgh_id, objs, count );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ server_remove_wait( msgh_id, objs, count );
</span> +
+ switch (kr) {
+ case KERN_SUCCESS:
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1220,7 +1245,7 @@ index 00000000000..90e785f6df2
</span> + return STATUS_SUCCESS;
+}
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+static NTSTATUS do_single_wait( struct msync *obj, ULONGLONG *end, BOOLEAN alertable )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++static NTSTATUS do_single_wait( struct msync *obj, ULONGLONG *end, BOOLEAN alertable, int tid )
</span> +{
+ NTSTATUS status;
+ struct msync *wait_objs[2];
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1241,14 +1266,14 @@ index 00000000000..90e785f6df2
</span> +
+ wait_objs[1] = &apc_obj;
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ status = msync_wait_multiple( wait_objs, 2, end );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ status = msync_wait_multiple( wait_objs, 2, end, tid );
</span> +
+ if (__atomic_load_n( apc_addr, __ATOMIC_SEQ_CST ))
+ return STATUS_USER_APC;
+ }
+ else
+ {
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ status = msync_wait_multiple( wait_objs, 1, end );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ status = msync_wait_multiple( wait_objs, 1, end, tid );
</span> + }
+ return status;
+}
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1258,6 +1283,7 @@ index 00000000000..90e785f6df2
</span> +{
+ static const LARGE_INTEGER zero = {0};
+
<span style='display:block; white-space:pre;background:#e0ffe0;'>++ __thread static int current_tid = 0;
</span> + __thread static struct msync *objs[MAXIMUM_WAIT_OBJECTS + 1];
+ struct msync apc_obj;
+ int has_msync = 0, has_server = 0;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1268,6 +1294,8 @@ index 00000000000..90e785f6df2
</span> + ULONGLONG end;
+ int i, ret;
+
<span style='display:block; white-space:pre;background:#e0ffe0;'>++ current_tid = current_tid ? current_tid : GetCurrentThreadId();
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> + /* Grab the APC idx if we don't already have it. */
+ if (alertable && !ntdll_get_thread_data()->msync_apc_addr)
+ {
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1386,7 +1414,7 @@ index 00000000000..90e785f6df2
</span> + struct mutex *mutex = obj->shm;
+ int tid;
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (mutex->tid == GetCurrentThreadId())
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (mutex->tid == current_tid)
</span> + {
+ TRACE("Woken up by handle %p [%d].\n", handles[i], i);
+ mutex->count++;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1394,13 +1422,13 @@ index 00000000000..90e785f6df2
</span> + }
+
+ tid = 0;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (__atomic_compare_exchange_n(&mutex->tid, &tid, GetCurrentThreadId(), 0, __ATOMIC_ACQ_REL, __ATOMIC_RELAXED))
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (__atomic_compare_exchange_n(&mutex->tid, &tid, current_tid, 0, __ATOMIC_ACQ_REL, __ATOMIC_RELAXED))
</span> + {
+ TRACE("Woken up by handle %p [%d].\n", handles[i], i);
+ mutex->count = 1;
+ return i;
+ }
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ else if (tid == ~0 && __atomic_compare_exchange_n(&mutex->tid, &tid, GetCurrentThreadId(), 0, __ATOMIC_ACQ_REL, __ATOMIC_RELAXED))
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ else if (tid == ~0 && __atomic_compare_exchange_n(&mutex->tid, &tid, current_tid, 0, __ATOMIC_ACQ_REL, __ATOMIC_RELAXED))
</span> + {
+ TRACE("Woken up by abandoned mutex %p [%d].\n", handles[i], i);
+ mutex->count = 1;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1463,7 +1491,7 @@ index 00000000000..90e785f6df2
</span> + return STATUS_TIMEOUT;
+ }
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ ret = msync_wait_multiple( objs, waitcount, timeout ? &end : NULL );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ ret = msync_wait_multiple( objs, waitcount, timeout ? &end : NULL, current_tid );
</span> +
+ if (ret == STATUS_TIMEOUT)
+ {
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1514,12 +1542,12 @@ index 00000000000..90e785f6df2
</span> + {
+ struct mutex *mutex = obj->shm;
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (mutex->tid == GetCurrentThreadId())
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (mutex->tid == current_tid)
</span> + continue;
+
+ while (__atomic_load_n( &mutex->tid, __ATOMIC_SEQ_CST ))
+ {
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ status = do_single_wait( obj, timeout ? &end : NULL, alertable );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ status = do_single_wait( obj, timeout ? &end : NULL, alertable, current_tid );
</span> + if (status != STATUS_PENDING)
+ break;
+ }
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1531,7 +1559,7 @@ index 00000000000..90e785f6df2
</span> +
+ while (!__atomic_load_n( &event->signaled, __ATOMIC_SEQ_CST ))
+ {
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ status = do_single_wait( obj, timeout ? &end : NULL, alertable );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ status = do_single_wait( obj, timeout ? &end : NULL, alertable, current_tid );
</span> + if (status != STATUS_PENDING)
+ break;
+ }
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1557,7 +1585,7 @@ index 00000000000..90e785f6df2
</span> + struct mutex *mutex = obj->shm;
+ int tid = __atomic_load_n( &mutex->tid, __ATOMIC_SEQ_CST );
+
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (tid && tid != ~0 && tid != GetCurrentThreadId())
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (tid && tid != ~0 && tid != current_tid)
</span> + goto tryagain;
+ }
+ else if (obj)
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1580,11 +1608,11 @@ index 00000000000..90e785f6df2
</span> + {
+ struct mutex *mutex = obj->shm;
+ int tid = __atomic_load_n( &mutex->tid, __ATOMIC_SEQ_CST );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (tid == GetCurrentThreadId())
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (tid == current_tid)
</span> + break;
+ if (tid && tid != ~0)
+ goto tooslow;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-+ if (__sync_val_compare_and_swap( &mutex->tid, tid, GetCurrentThreadId() ) != tid)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++ if (__sync_val_compare_and_swap( &mutex->tid, tid, current_tid ) != tid)
</span> + goto tooslow;
+ if (tid == ~0)
+ abandoned = TRUE;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1835,7 +1863,7 @@ index 77aa995326c..f45db2f3090 100644
</span> esync_close( handle );
diff --git a/dlls/ntdll/unix/sync.c b/dlls/ntdll/unix/sync.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index a52327841d2..4d4644f9c8c 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index a52327841d2..3e3d2ea1fb4 100644
</span> --- a/dlls/ntdll/unix/sync.c
+++ b/dlls/ntdll/unix/sync.c
@@ -67,6 +67,7 @@
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -1846,15 +1874,6 @@ index a52327841d2..4d4644f9c8c 100644
</span>
WINE_DEFAULT_DEBUG_CHANNEL(sync);
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -120,7 +121,7 @@ static inline int futex_wait( const LONG *addr, int val, struct timespec *timeou
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- long tv_nsec;
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- } timeout32 = { timeout->tv_sec, timeout->tv_nsec };
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-- return syscall( __NR_futex, addr, FUTEX_WAIT_PRIVATE, val, &timeout32, 0, 0 );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+ return syscall( __NR_futex, addr, FUTEX_WAIT_PRIVATE| futex_private, val, &timeout32, 0, 0 );
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- }
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- #endif
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- return syscall( __NR_futex, addr, FUTEX_WAIT_PRIVATE, val, timeout, 0, 0 );
</span> @@ -320,6 +321,9 @@ NTSTATUS WINAPI NtCreateSemaphore( HANDLE *handle, ACCESS_MASK access, const OBJ
if (max <= 0 || initial < 0 || initial > max) return STATUS_INVALID_PARAMETER;
if ((ret = alloc_object_attributes( attr, &objattr, &len ))) return ret;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2046,7 +2065,7 @@ index a52327841d2..4d4644f9c8c 100644
</span> if (!timeout || timeout->QuadPart == TIMEOUT_INFINITE) /* sleep forever */
{
diff --git a/dlls/ntdll/unix/unix_private.h b/dlls/ntdll/unix/unix_private.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 791b7b88c62..dc194eb09ac 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 0f92988d9d5..8f62d380cc4 100644
</span> --- a/dlls/ntdll/unix/unix_private.h
+++ b/dlls/ntdll/unix/unix_private.h
@@ -104,6 +104,8 @@ struct ntdll_thread_data
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2059,10 +2078,10 @@ index 791b7b88c62..dc194eb09ac 100644
</span> int reply_fd; /* fd for receiving server replies */
int wait_fd[2]; /* fd for sleeping server requests */
diff --git a/dlls/ntdll/unix/virtual.c b/dlls/ntdll/unix/virtual.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index efccfac76d0..8247b82852d 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 75088a2036d..8f55f14ca66 100644
</span> --- a/dlls/ntdll/unix/virtual.c
+++ b/dlls/ntdll/unix/virtual.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -3737,6 +3737,8 @@ static TEB *init_teb( void *ptr, BOOL is_wow )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -3700,6 +3700,8 @@ static TEB *init_teb( void *ptr, BOOL is_wow )
</span> teb->StaticUnicodeString.MaximumLength = sizeof(teb->StaticUnicodeBuffer);
thread_data = (struct ntdll_thread_data *)&teb->GdiTebBatch;
thread_data->esync_apc_fd = -1;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2072,10 +2091,10 @@ index efccfac76d0..8247b82852d 100644
</span> thread_data->reply_fd = -1;
thread_data->wait_fd[0] = -1;
diff --git a/include/wine/server_protocol.h b/include/wine/server_protocol.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index d3399268d00..c38120548ab 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 44f18710766..e6610d3cab5 100644
</span> --- a/include/wine/server_protocol.h
+++ b/include/wine/server_protocol.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -5828,6 +5828,92 @@ struct get_esync_apc_fd_reply
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -5830,6 +5830,92 @@ struct get_esync_apc_fd_reply
</span> struct reply_header __header;
};
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2168,7 +2187,7 @@ index d3399268d00..c38120548ab 100644
</span>
enum request
{
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -6123,6 +6209,11 @@ enum request
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -6125,6 +6211,11 @@ enum request
</span> REQ_esync_msgwait,
REQ_set_keyboard_repeat,
REQ_get_esync_apc_fd,
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2180,7 +2199,7 @@ index d3399268d00..c38120548ab 100644
</span> REQ_NB_REQUESTS
};
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -6422,6 +6513,11 @@ union generic_request
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -6424,6 +6515,11 @@ union generic_request
</span> struct esync_msgwait_request esync_msgwait_request;
struct set_keyboard_repeat_request set_keyboard_repeat_request;
struct get_esync_apc_fd_request get_esync_apc_fd_request;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2192,7 +2211,7 @@ index d3399268d00..c38120548ab 100644
</span> };
union generic_reply
{
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -6719,11 +6815,16 @@ union generic_reply
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -6721,11 +6817,16 @@ union generic_reply
</span> struct esync_msgwait_reply esync_msgwait_reply;
struct set_keyboard_repeat_reply set_keyboard_repeat_reply;
struct get_esync_apc_fd_reply get_esync_apc_fd_reply;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2205,8 +2224,8 @@ index d3399268d00..c38120548ab 100644
</span>
/* ### protocol_version begin ### */
<span style='display:block; white-space:pre;background:#ffe0e0;'>--#define SERVER_PROTOCOL_VERSION 837
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>-+#define SERVER_PROTOCOL_VERSION 838
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+-#define SERVER_PROTOCOL_VERSION 838
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++#define SERVER_PROTOCOL_VERSION 839
</span>
/* ### protocol_version end ### */
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2223,7 +2242,7 @@ index 87103cb2002..85b7b8f6693 100644
</span> hook.c \
mach.c \
diff --git a/server/async.c b/server/async.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index b0f9fe42ad1..b7270394579 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index bea720b1f19..2dff610f4bd 100644
</span> --- a/server/async.c
+++ b/server/async.c
@@ -78,6 +78,7 @@ static const struct object_ops async_ops =
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2920,10 +2939,10 @@ index ab4d0e9dd31..0bbdcc5aa88 100644
</span> no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/mailslot.c b/server/mailslot.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 4cf9b73f784..d04fc2f4edc 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index a8258328364..6301cdf06c1 100644
</span> --- a/server/mailslot.c
+++ b/server/mailslot.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -75,6 +75,7 @@ static const struct object_ops mailslot_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -82,6 +82,7 @@ static const struct object_ops mailslot_ops =
</span> remove_queue, /* remove_queue */
default_fd_signaled, /* signaled */
NULL, /* get_esync_fd */
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2931,7 +2950,7 @@ index 4cf9b73f784..d04fc2f4edc 100644
</span> no_satisfied, /* satisfied */
no_signal, /* signal */
mailslot_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -135,6 +136,7 @@ static const struct object_ops mail_writer_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -144,6 +145,7 @@ static const struct object_ops mail_writer_ops =
</span> NULL, /* remove_queue */
NULL, /* signaled */
NULL, /* get_esync_fd */
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2939,7 +2958,7 @@ index 4cf9b73f784..d04fc2f4edc 100644
</span> NULL, /* satisfied */
no_signal, /* signal */
mail_writer_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -199,6 +201,7 @@ static const struct object_ops mailslot_device_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -210,6 +212,7 @@ static const struct object_ops mailslot_device_ops =
</span> NULL, /* remove_queue */
NULL, /* signaled */
NULL, /* get_esync_fd */
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -2947,7 +2966,7 @@ index 4cf9b73f784..d04fc2f4edc 100644
</span> no_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -230,6 +233,7 @@ static const struct object_ops mailslot_device_file_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -241,6 +244,7 @@ static const struct object_ops mailslot_device_file_ops =
</span> remove_queue, /* remove_queue */
default_fd_signaled, /* signaled */
NULL, /* get_esync_fd */
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4064,7 +4083,7 @@ index 4785a830e92..6a60adee0bd 100644
</span> mutex_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/named_pipe.c b/server/named_pipe.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index a90ec606226..d8d17fa95f7 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 8ba8126563a..6396ea532b0 100644
</span> --- a/server/named_pipe.c
+++ b/server/named_pipe.c
@@ -120,6 +120,7 @@ static const struct object_ops named_pipe_ops =
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4217,10 +4236,10 @@ index bedd8bb4586..24276142a63 100644
</span>
/* process functions */
diff --git a/server/protocol.def b/server/protocol.def
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 1e4171c56ef..7ad9129f5d4 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 47c76c17c5b..5475a51639d 100644
</span> --- a/server/protocol.def
+++ b/server/protocol.def
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -4022,3 +4022,57 @@ enum esync_type
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -4023,3 +4023,57 @@ enum esync_type
</span> /* Retrieve the fd to wait on for user APCs. */
@REQ(get_esync_apc_fd)
@END
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4279,7 +4298,7 @@ index 1e4171c56ef..7ad9129f5d4 100644
</span> + unsigned int shm_idx;
+@END
diff --git a/server/queue.c b/server/queue.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 109610b3d31..2c1f8053102 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index ef4283e27df..c6dd91f8d4a 100644
</span> --- a/server/queue.c
+++ b/server/queue.c
@@ -45,6 +45,7 @@
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4290,7 +4309,7 @@ index 109610b3d31..2c1f8053102 100644
</span>
#define WM_NCMOUSEFIRST WM_NCMOUSEMOVE
#define WM_NCMOUSELAST (WM_NCMOUSEFIRST+(WM_MOUSELAST-WM_MOUSEFIRST))
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -139,6 +140,8 @@ struct msg_queue
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -137,6 +138,8 @@ struct msg_queue
</span> unsigned int ignore_post_msg; /* ignore post messages newer than this unique id */
int esync_fd; /* esync file descriptor (signalled on message) */
int esync_in_msgwait; /* our thread is currently waiting on us */
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4299,7 +4318,7 @@ index 109610b3d31..2c1f8053102 100644
</span> };
struct hotkey
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -156,6 +159,7 @@ static int msg_queue_add_queue( struct object *obj, struct wait_queue_entry *ent
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -154,6 +157,7 @@ static int msg_queue_add_queue( struct object *obj, struct wait_queue_entry *ent
</span> static void msg_queue_remove_queue( struct object *obj, struct wait_queue_entry *entry );
static int msg_queue_signaled( struct object *obj, struct wait_queue_entry *entry );
static int msg_queue_get_esync_fd( struct object *obj, enum esync_type *type );
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4307,7 +4326,7 @@ index 109610b3d31..2c1f8053102 100644
</span> static void msg_queue_satisfied( struct object *obj, struct wait_queue_entry *entry );
static void msg_queue_destroy( struct object *obj );
static void msg_queue_poll_event( struct fd *fd, int event );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -172,6 +176,7 @@ static const struct object_ops msg_queue_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -170,6 +174,7 @@ static const struct object_ops msg_queue_ops =
</span> msg_queue_remove_queue, /* remove_queue */
msg_queue_signaled, /* signaled */
msg_queue_get_esync_fd, /* get_esync_fd */
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4315,7 +4334,7 @@ index 109610b3d31..2c1f8053102 100644
</span> msg_queue_satisfied, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -210,6 +215,7 @@ static const struct object_ops thread_input_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -208,6 +213,7 @@ static const struct object_ops thread_input_ops =
</span> NULL, /* remove_queue */
NULL, /* signaled */
NULL, /* get_esync_fd */
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4323,7 +4342,7 @@ index 109610b3d31..2c1f8053102 100644
</span> NULL, /* satisfied */
no_signal, /* signal */
no_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -324,6 +330,8 @@ static struct msg_queue *create_msg_queue( struct thread *thread, struct thread_
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -322,6 +328,8 @@ static struct msg_queue *create_msg_queue( struct thread *thread, struct thread_
</span> queue->ignore_post_msg = 0;
queue->esync_fd = -1;
queue->esync_in_msgwait = 0;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4332,7 +4351,7 @@ index 109610b3d31..2c1f8053102 100644
</span> list_init( &queue->send_result );
list_init( &queue->callback_result );
list_init( &queue->pending_timers );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -349,6 +357,9 @@ static struct msg_queue *create_msg_queue( struct thread *thread, struct thread_
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -347,6 +355,9 @@ static struct msg_queue *create_msg_queue( struct thread *thread, struct thread_
</span> if (do_esync())
queue->esync_fd = esync_create_fd( 0, 0 );
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4342,7 +4361,7 @@ index 109610b3d31..2c1f8053102 100644
</span> thread->queue = queue;
if ((desktop = get_thread_desktop( thread, 0 )))
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -737,6 +748,9 @@ static inline void clear_queue_bits( struct msg_queue *queue, unsigned int bits
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -754,6 +765,9 @@ static inline void clear_queue_bits( struct msg_queue *queue, unsigned int bits
</span> queue->keystate_lock = 0;
}
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4352,7 +4371,7 @@ index 109610b3d31..2c1f8053102 100644
</span> if (do_esync() && !is_signaled( queue ))
esync_clear( queue->esync_fd );
}
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1228,6 +1242,9 @@ static int is_queue_hung( struct msg_queue *queue )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1245,6 +1259,9 @@ static int is_queue_hung( struct msg_queue *queue )
</span> return 0; /* thread is waiting on queue -> not hung */
}
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4362,7 +4381,7 @@ index 109610b3d31..2c1f8053102 100644
</span> if (do_esync() && queue->esync_in_msgwait)
return 0; /* thread is waiting on queue in absentia -> not hung */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1292,6 +1309,13 @@ static int msg_queue_get_esync_fd( struct object *obj, enum esync_type *type )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1309,6 +1326,13 @@ static int msg_queue_get_esync_fd( struct object *obj, enum esync_type *type )
</span> return queue->esync_fd;
}
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4376,7 +4395,7 @@ index 109610b3d31..2c1f8053102 100644
</span> static void msg_queue_satisfied( struct object *obj, struct wait_queue_entry *entry )
{
struct msg_queue *queue = (struct msg_queue *)obj;
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -1349,6 +1373,8 @@ static void msg_queue_destroy( struct object *obj )
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -1366,6 +1390,8 @@ static void msg_queue_destroy( struct object *obj )
</span> if (queue->fd) release_object( queue->fd );
if (queue->shared) free_shared_object( queue->shared );
if (do_esync()) close( queue->esync_fd );
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4385,16 +4404,17 @@ index 109610b3d31..2c1f8053102 100644
</span> }
static void msg_queue_poll_event( struct fd *fd, int event )
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -3121,6 +3147,8 @@ DECL_HANDLER(set_queue_mask)
</span><span style='display:block; white-space:pre;background:#ffe0e0;'>- }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -3152,6 +3178,9 @@ DECL_HANDLER(set_queue_mask)
</span> else wake_up( &queue->obj, 0 );
}
<span style='display:block; white-space:pre;background:#e0ffe0;'>+
</span> + if (do_msync() && !is_signaled( queue ))
+ msync_clear( &queue->obj );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>++
</span> if (do_esync() && !is_signaled( queue ))
esync_clear( queue->esync_fd );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -3145,6 +3173,9 @@ DECL_HANDLER(get_queue_status)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+ }
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -3175,6 +3204,9 @@ DECL_HANDLER(get_queue_status)
</span> }
SHARED_WRITE_END;
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4404,7 +4424,7 @@ index 109610b3d31..2c1f8053102 100644
</span> if (do_esync() && !is_signaled( queue ))
esync_clear( queue->esync_fd );
}
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -3416,6 +3447,9 @@ DECL_HANDLER(get_message)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -3446,6 +3478,9 @@ DECL_HANDLER(get_message)
</span>
set_error( STATUS_PENDING ); /* FIXME */
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4414,7 +4434,7 @@ index 109610b3d31..2c1f8053102 100644
</span> if (do_esync() && !is_signaled( queue ))
esync_clear( queue->esync_fd );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -4220,6 +4254,23 @@ DECL_HANDLER(esync_msgwait)
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -4248,6 +4283,23 @@ DECL_HANDLER(esync_msgwait)
</span> set_fd_events( queue->fd, req->in_msgwait ? POLLIN : 0 );
}
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4463,7 +4483,7 @@ index 8e7d88a0d4c..3287b16170d 100644
</span> no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/request.h b/server/request.h
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index a68983ef6dc..32fd61d7903 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index b8a3f24f521..a73b9bdd2f3 100644
</span> --- a/server/request.h
+++ b/server/request.h
@@ -411,6 +411,11 @@ DECL_HANDLER(get_esync_fd);
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4490,7 +4510,7 @@ index a68983ef6dc..32fd61d7903 100644
</span> };
C_ASSERT( sizeof(abstime_t) == 8 );
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -2386,6 +2396,34 @@ C_ASSERT( sizeof(struct set_keyboard_repeat_request) == 24 );
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -2387,6 +2397,34 @@ C_ASSERT( sizeof(struct set_keyboard_repeat_request) == 24 );
</span> C_ASSERT( FIELD_OFFSET(struct set_keyboard_repeat_reply, enable) == 8 );
C_ASSERT( sizeof(struct set_keyboard_repeat_reply) == 16 );
C_ASSERT( sizeof(struct get_esync_apc_fd_request) == 16 );
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4562,7 +4582,7 @@ index 55cd6aa037e..e86ad49df8e 100644
</span> no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/sock.c b/server/sock.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 7be912b3b50..af92f134538 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 3110a125add..3b6fb723548 100644
</span> --- a/server/sock.c
+++ b/server/sock.c
@@ -454,6 +454,7 @@ static const struct object_ops sock_ops =
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4573,7 +4593,7 @@ index 7be912b3b50..af92f134538 100644
</span> no_satisfied, /* satisfied */
no_signal, /* signal */
sock_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -3562,6 +3563,7 @@ static const struct object_ops ifchange_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -3564,6 +3565,7 @@ static const struct object_ops ifchange_ops =
</span> NULL, /* remove_queue */
NULL, /* signaled */
NULL, /* get_esync_fd */
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4581,7 +4601,7 @@ index 7be912b3b50..af92f134538 100644
</span> no_satisfied, /* satisfied */
no_signal, /* signal */
ifchange_get_fd, /* get_fd */
<span style='display:block; white-space:pre;background:#ffe0e0;'>-@@ -3784,6 +3786,7 @@ static const struct object_ops socket_device_ops =
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+@@ -3786,6 +3788,7 @@ static const struct object_ops socket_device_ops =
</span> NULL, /* remove_queue */
NULL, /* signaled */
NULL, /* get_esync_fd */
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4844,7 +4864,7 @@ index e40ba10f9aa..1101c7224b9 100644
</span> no_signal, /* signal */
no_get_fd, /* get_fd */
diff --git a/server/trace.c b/server/trace.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 89e9c0b3aa1..f692e86a878 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index fd224685bfb..0d7eac7dc60 100644
</span> --- a/server/trace.c
+++ b/server/trace.c
@@ -4712,6 +4712,63 @@ static void dump_get_esync_apc_fd_request( const struct get_esync_apc_fd_request
<span style='display:block; white-space:pre;background:#e0e0e0;'>@@ -4948,7 +4968,7 @@ index 89e9c0b3aa1..f692e86a878 100644
</span>
static const struct
diff --git a/server/window.c b/server/window.c
<span style='display:block; white-space:pre;background:#ffe0e0;'>-index 13318b75fe2..85ee8d8f9b2 100644
</span><span style='display:block; white-space:pre;background:#e0ffe0;'>+index 7e8055bac4a..f91794e278f 100644
</span> --- a/server/window.c
+++ b/server/window.c
@@ -107,6 +107,7 @@ static const struct object_ops window_ops =
</pre><pre style='margin:0'>
</pre>