CVS: winex/server atom.c, 1.5, 1.6 change.c, 1.5, 1.6 console.c, 1.17, 1.18 dbus.c, 1.7, 1.8 debugger.c, 1.14, 1.15 device.c, 1.8, 1.9 distributed.c, 1.5, 1.6 event.c, 1.5, 1.6 fd_server.c, 1.16, 1.17 file.c, 1.22, 1.23 gdbremote.c, 1.9, 1.10 handle.c, 1.10, 1.11 handle.h, 1.4, 1.5 iocomp.c, 1.1, 1.2 mapping.c, 1.6, 1.7 mutex.c, 1.5, 1.6 named_pipe.c, 1.17, 1.18 object.c, 1.10, 1.11 object.h, 1.16, 1.17 process.c, 1.42, 1.43 protocol.def, 1.42, 1.43 queue.c, 1.9, 1.10 registry.c, 1.13, 1.14 request.c, 1.26, 1.27 semaphore.c, 1.5, 1.6 serial.c, 1.13, 1.14 snapshot.c, 1.8, 1.9 sock.c, 1.21, 1.22 thread.c, 1.55, 1.56 thread.h, 1.28, 1.29 timer.c, 1.6, 1.7 token.c, 1.3, 1.4 trace.c, 1.43, 1.44

[email protected] 31 Jul 2007 19:39:38 -0000
Newsgroups gmane.comp.emulators.winex.cvs
Message-ID <[email protected]>
Subject: winex/server atom.c,1.5,1.6 change.c,1.5,1.6 console.c,1.17,1.18 dbus.c,1.7,1.8 debugger.c,1.14,1.15 device.c,1.8,1.9 distributed.c,1.5,1.6 event.c,1.5,1.6 fd_server.c,1.16,1.17 file.c,1.22,1.23 gdbremote.c,1.9,1.10 handle.c,1.10,1.11 handle.h,1.4,1.5 iocomp.c,1.1,1.2 mapping.c,1.6,1.7 mutex.c,1.5,1.6 named_pipe.c,1.17,1.18 object.c,1.10,1.11 object.h,1.16,1.17 process.c,1.42,1.43 protocol.def,1.42,1.43 queue.c,1.9,1.10 registry.c,1.13,1.14 request.c,1.26,1.27 semaphore.c,1.5,1.6 serial.c,1.13,1.14 snapshot.c,1.8,1.9 sock.c,1.21,1.22 thread.c,1.55,1.56 thread.h,1.28,1.29 timer.c,1.6,1.7 token.c,1.3,1.4 trace.c,1.43,1.44Update of /var/lib/cvsd/cvsroot/winex/server
In directory agravaine:/tmp/cvs-serv30964/server

Modified Files:
	atom.c change.c console.c dbus.c debugger.c device.c 
	distributed.c event.c fd_server.c file.c gdbremote.c handle.c 
	handle.h iocomp.c mapping.c mutex.c named_pipe.c object.c 
	object.h process.c protocol.def queue.c registry.c request.c 
	semaphore.c serial.c snapshot.c sock.c thread.c thread.h 
	timer.c token.c trace.c 
Log Message:

- implement SignalObjectAndWait



Index: atom.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/atom.c,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -d -r1.5 -r1.6
--- atom.c	27 Mar 2007 20:25:26 -0000	1.5
+++ atom.c	31 Jul 2007 19:39:35 -0000	1.6
@@ -54,6 +54,7 @@
     no_add_queue,                 /* add_queue */
     NULL,                         /* remove_queue */
     NULL,                         /* signaled */
+    no_signal,                    /* signal */
     NULL,                         /* satified */
     NULL,                         /* get_poll_events */
     NULL,                         /* poll_event */

Index: change.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/change.c,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -d -r1.5 -r1.6
--- change.c	27 Mar 2007 20:25:26 -0000	1.5
+++ change.c	31 Jul 2007 19:39:35 -0000	1.6
@@ -31,6 +31,7 @@
     add_queue,                /* add_queue */
     remove_queue,             /* remove_queue */
     change_signaled,          /* signaled */
+    no_signal,                /* signal */
     no_satisfied,             /* satisfied */
     NULL,                     /* get_poll_events */
     NULL,                     /* poll_event */

Index: console.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/console.c,v
retrieving revision 1.17
retrieving revision 1.18
diff -u -d -r1.17 -r1.18
--- console.c	30 Mar 2007 15:55:02 -0000	1.17
+++ console.c	31 Jul 2007 19:39:35 -0000	1.18
@@ -37,6 +37,7 @@
     add_queue,                        /* add_queue */
     remove_queue,                     /* remove_queue */
     console_input_signaled,           /* signaled */
+    no_signal,                        /* signal */
     no_satisfied,                     /* satisfied */
     NULL,                             /* get_poll_events */
     NULL,                             /* poll_event */
@@ -68,6 +69,7 @@
     add_queue,                        /* add_queue */
     remove_queue,                     /* remove_queue */
     console_input_events_signaled,    /* signaled */
+    no_signal,                        /* signal */
     no_satisfied,                     /* satisfied */
     NULL,                             /* get_poll_events */
     NULL,                             /* poll_event */
@@ -111,6 +113,7 @@
     no_add_queue,                     /* add_queue */
     NULL,                             /* remove_queue */
     NULL,                             /* signaled */
+    no_signal,                        /* signal */
     NULL,                             /* satisfied */
     NULL,                             /* get_poll_events */
     NULL,                             /* poll_event */

Index: dbus.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/dbus.c,v
retrieving revision 1.7
retrieving revision 1.8
diff -u -d -r1.7 -r1.8
--- dbus.c	27 Apr 2007 13:14:16 -0000	1.7
+++ dbus.c	31 Jul 2007 19:39:35 -0000	1.8
@@ -232,6 +232,7 @@
   no_add_queue,                    /* add_queue */
   NULL,                            /* remove_queue */
   NULL,                            /* signaled */
+  no_signal,                       /* signal */
   NULL,                            /* satisfied */
   NULL,                            /* get_poll_events */
   dbus_poll_event,                 /* poll_event */

Index: debugger.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/debugger.c,v
retrieving revision 1.14
retrieving revision 1.15
diff -u -d -r1.14 -r1.15
--- debugger.c	30 Mar 2007 15:55:03 -0000	1.14
+++ debugger.c	31 Jul 2007 19:39:35 -0000	1.15
@@ -58,6 +58,7 @@
     add_queue,                     /* add_queue */
     remove_queue,                  /* remove_queue */
     debug_event_signaled,          /* signaled */
+    no_signal,                     /* signal */
     no_satisfied,                  /* satisfied */
     NULL,                          /* get_poll_events */
     NULL,                          /* poll_event */
@@ -81,6 +82,7 @@
     add_queue,                     /* add_queue */
     remove_queue,                  /* remove_queue */
     debug_ctx_signaled,            /* signaled */
+    no_signal,                     /* signal */
     no_satisfied,                  /* satisfied */
     NULL,                          /* get_poll_events */
     NULL,                          /* poll_event */

Index: device.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/device.c,v
retrieving revision 1.8
retrieving revision 1.9
diff -u -d -r1.8 -r1.9
--- device.c	27 Mar 2007 20:25:26 -0000	1.8
+++ device.c	31 Jul 2007 19:39:35 -0000	1.9
@@ -38,6 +38,7 @@
     no_add_queue,             /* add_queue */
     NULL,                     /* remove_queue */
     NULL,                     /* signaled */
+    no_signal,                /* signal */
     NULL,                     /* satisfied */
     NULL,                     /* get_poll_events */
     NULL,                     /* poll_event */

Index: distributed.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/distributed.c,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -d -r1.5 -r1.6
--- distributed.c	27 Mar 2007 20:25:26 -0000	1.5
+++ distributed.c	31 Jul 2007 19:39:35 -0000	1.6
@@ -37,6 +37,7 @@
     no_add_queue,                         /* add_queue */
     NULL,                                 /* remove_queue */
     NULL,                                 /* signaled */
+    no_signal,                            /* signal */
     NULL,                                 /* satisfied */
     NULL,                                 /* get_poll_events */
     distributed_commands_poll_event,      /* poll_event */

Index: event.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/event.c,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -d -r1.5 -r1.6
--- event.c	27 Mar 2007 20:25:26 -0000	1.5
+++ event.c	31 Jul 2007 19:39:35 -0000	1.6
@@ -24,6 +24,7 @@
 static void event_dump( struct object *obj, int verbose );
 static int event_signaled( struct object *obj, struct wait_queue_entry *entry );
 static int event_satisfied( struct object *obj, struct thread *thread );
+static int event_signal( struct object *obj, unsigned int access);
 
 static const struct object_ops event_ops =
 {
@@ -32,6 +33,7 @@
     add_queue,                 /* add_queue */
     remove_queue,              /* remove_queue */
     event_signaled,            /* signaled */
+    event_signal,              /* signal event */
     event_satisfied,           /* satisfied */
     NULL,                      /* get_poll_events */
     NULL,                      /* poll_event */
@@ -104,6 +106,22 @@
     return event->signaled;
 }
 
+static int event_signal( struct object *obj, unsigned int access)
+{
+    struct event *event = (struct event *)obj;
+
+    assert (obj->ops == event_ops_tag);
+
+    if (!(access & EVENT_MODIFY_STATE))
+    {
+       set_error (STATUS_ACCESS_DENIED);
+       return 0;
+    }
+
+    set_event (event);
+    return 1;
+}
+
 static int event_satisfied( struct object *obj, struct thread *thread )
 {
     struct event *event = (struct event *)obj;

Index: fd_server.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/fd_server.c,v
retrieving revision 1.16
retrieving revision 1.17
diff -u -d -r1.16 -r1.17
--- fd_server.c	30 Mar 2007 15:55:03 -0000	1.16
+++ fd_server.c	31 Jul 2007 19:39:35 -0000	1.17
@@ -54,6 +54,7 @@
     no_add_queue,                  /* add_queue */
     NULL,                          /* remove_queue */
     NULL,                          /* signaled */
+    no_signal,                     /* signal */
     NULL,                          /* satisfied */
     NULL,                          /* get_poll_events */
     fd_server_poll_event,          /* poll_event */

Index: file.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/file.c,v
retrieving revision 1.22
retrieving revision 1.23
diff -u -d -r1.22 -r1.23
--- file.c	27 Mar 2007 20:25:26 -0000	1.22
+++ file.c	31 Jul 2007 19:39:35 -0000	1.23
@@ -59,6 +59,7 @@
     default_poll_add_queue,       /* add_queue */
     default_poll_remove_queue,    /* remove_queue */
     default_poll_signaled,        /* signaled */
+    no_signal,                    /* signal */
     no_satisfied,                 /* satisfied */
     file_get_poll_events,         /* get_poll_events */
     file_poll_event,              /* poll_event */

Index: gdbremote.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/gdbremote.c,v
retrieving revision 1.9
retrieving revision 1.10
diff -u -d -r1.9 -r1.10
--- gdbremote.c	21 Jan 2005 20:05:06 -0000	1.9
+++ gdbremote.c	31 Jul 2007 19:39:35 -0000	1.10
@@ -84,6 +84,7 @@
     no_add_queue,                  /* add_queue */
     NULL,                          /* remove_queue */
     NULL,                          /* signaled */
+    no_signal,                     /* signal */
     NULL,                          /* satisfied */
     NULL,                          /* get_poll_events */
     remote_gdb_poll_event,         /* poll_event */
@@ -949,6 +950,7 @@
     no_add_queue,                  /* add_queue */
     NULL,                          /* remove_queue */
     NULL,                          /* signaled */
+    no_signal,                     /* signal */
     NULL,                          /* satisfied */
     NULL,                          /* get_poll_events */
     gdb_socket_poll_event,         /* poll_event */

Index: handle.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/handle.c,v
retrieving revision 1.10
retrieving revision 1.11
diff -u -d -r1.10 -r1.11
--- handle.c	27 Mar 2007 20:25:26 -0000	1.10
+++ handle.c	31 Jul 2007 19:39:35 -0000	1.11
@@ -90,6 +90,7 @@
     no_add_queue,                    /* add_queue */
     NULL,                            /* remove_queue */
     NULL,                            /* signaled */
+    no_signal,                       /* signal */
     NULL,                            /* satisfied */
     NULL,                            /* get_poll_events */
     NULL,                            /* poll_event */
@@ -437,6 +438,21 @@
     }
 }
 
+/* Retrieve the access permissions set for a handle */
+unsigned int get_handle_access (struct process *process, handle_t handle)
+{
+    struct handle_entry *entry;
+
+    if (get_magic_handle (handle))
+       return ~RESERVED_ALL;
+
+    if (!(entry = get_handle (process, handle)))
+       return 0;
+
+    /* Ensure we don't return reserved access permissions */
+    return entry->access & ~RESERVED_ALL;
+}
+
 /* get/set the handle reserved flags */
 /* return the old flags (or -1 on error) */
 int set_handle_info( struct process *process, handle_t handle,

Index: handle.h
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/handle.h,v
retrieving revision 1.4
retrieving revision 1.5
diff -u -d -r1.4 -r1.5
--- handle.h	27 Mar 2007 20:25:27 -0000	1.4
+++ handle.h	31 Jul 2007 19:39:35 -0000	1.5
@@ -24,6 +24,8 @@
 extern struct object *get_handle_obj( struct process *process, handle_t handle,
                                       unsigned int access, const struct object_ops *ops );
 extern int get_handle_fd( struct process *process, handle_t handle, unsigned int access );
+extern unsigned int get_handle_access (struct process *process,
+                                       handle_t handle);
 extern int set_handle_info( struct process *process, handle_t handle, int mask, int flags, int *fd );
 extern handle_t duplicate_handle( struct process *src, handle_t src_handle, struct process *dst,
                                   unsigned int access, int inherit, int options );

Index: iocomp.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/iocomp.c,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -d -r1.1 -r1.2
--- iocomp.c	31 Jul 2007 18:00:22 -0000	1.1
+++ iocomp.c	31 Jul 2007 19:39:35 -0000	1.2
@@ -78,6 +78,7 @@
    add_queue,                  /* add_queue */
    remove_queue,               /* remove_queue */
    iocomp_signaled,            /* signaled */
+   no_signal,                  /* signal */
    iocomp_satisfied,           /* satisfied */
    NULL,                       /* get_poll_events */
    NULL,                       /* poll_event */
@@ -374,7 +375,7 @@
             interrupted while we're adding a new one */
          iocomp->abandon_waits = 0;
          select_on (1, req->cookie, &req->handle, req->select_flags,
-                    tv.tv_sec, tv.tv_usec, NULL);
+                    tv.tv_sec, tv.tv_usec, 0, NULL);
          iocomp->abandon_waits = 1;
 
          reply->completion_key = NULL;
@@ -426,7 +427,7 @@
       if (!task)
       {
          fprintf (stderr,
-                  "server: couldn't find assigned IO completion task??!!\n");
+                  "server: couldn't find assigned IO completion task?!\n");
          set_error (STATUS_INVALID_PARAMETER);
          reply->completion_key = NULL;
          reply->overlapped = NULL;

Index: mapping.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/mapping.c,v
retrieving revision 1.6
retrieving revision 1.7
diff -u -d -r1.6 -r1.7
--- mapping.c	27 Mar 2007 20:25:27 -0000	1.6
+++ mapping.c	31 Jul 2007 19:39:35 -0000	1.7
@@ -33,6 +33,7 @@
     no_add_queue,                /* add_queue */
     NULL,                        /* remove_queue */
     NULL,                        /* signaled */
+    no_signal,                   /* signal */
     NULL,                        /* satisfied */
     NULL,                        /* get_poll_events */
     NULL,                        /* poll_event */

Index: mutex.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/mutex.c,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -d -r1.5 -r1.6
--- mutex.c	27 Mar 2007 20:25:27 -0000	1.5
+++ mutex.c	31 Jul 2007 19:39:35 -0000	1.6
@@ -26,6 +26,7 @@
 
 static void mutex_dump( struct object *obj, int verbose );
 static int mutex_signaled( struct object *obj, struct wait_queue_entry *entry );
+static int mutex_signal( struct object *obj, unsigned int access );
 static int mutex_satisfied( struct object *obj, struct thread *thread );
 static void mutex_destroy( struct object *obj );
 
@@ -36,6 +37,7 @@
     add_queue,                 /* add_queue */
     remove_queue,              /* remove_queue */
     mutex_signaled,            /* signaled */
+    mutex_signal,              /* signal */
     mutex_satisfied,           /* satisfied */
     NULL,                      /* get_poll_events */
     NULL,                      /* poll_event */
@@ -108,6 +110,32 @@
     return (!mutex->count || (mutex->owner == entry->thread));
 }
 
+static int mutex_signal (struct object *obj, unsigned int access)
+{
+   struct mutex *mutex = (struct mutex *)obj;
+
+   assert (obj->ops == mutex_ops_tag);
+
+   /* One would think this should be MUTEX_MODIFY_STATE, but the msdn
+      entry for SignalObjectAndWait() specifies SYNCHRONIZE instead */
+   if (!(access & SYNCHRONIZE))
+   {
+      set_error (STATUS_ACCESS_DENIED);
+      return 0;
+   }
+
+   if (!mutex->count || (mutex->owner != current))
+   {
+      set_error (STATUS_MUTANT_NOT_OWNED);
+      return 0;
+   }
+
+   if (!--mutex->count)
+      do_release (mutex);
+
+   return 1;
+}
+
 static int mutex_satisfied( struct object *obj, struct thread *thread )
 {
     struct mutex *mutex = (struct mutex *)obj;

Index: named_pipe.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/named_pipe.c,v
retrieving revision 1.17
retrieving revision 1.18
diff -u -d -r1.17 -r1.18
--- named_pipe.c	29 Mar 2007 14:00:49 -0000	1.17
+++ named_pipe.c	31 Jul 2007 19:39:35 -0000	1.18
@@ -84,6 +84,7 @@
     no_add_queue,                 /* add_queue */
     NULL,                         /* remove_queue */
     NULL,                         /* signaled */
+    no_signal,                    /* signal */
     NULL,                         /* satisfied */
     NULL,                         /* get_poll_events */
     NULL,                         /* poll_event */
@@ -112,6 +113,7 @@
     default_poll_add_queue,       /* add_queue */
     default_poll_remove_queue,    /* remove_queue */
     default_poll_signaled,        /* signaled */
+    no_signal,                    /* signal */
     no_satisfied,                 /* satisfied */
     pipe_user_get_poll_events,    /* get_poll_events */
     pipe_user_poll_event,         /* poll_event */

Index: object.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/object.c,v
retrieving revision 1.10
retrieving revision 1.11
diff -u -d -r1.10 -r1.11
--- object.c	27 Mar 2007 20:25:27 -0000	1.10
+++ object.c	31 Jul 2007 19:39:35 -0000	1.11
@@ -677,6 +677,12 @@
     return 0;  /* not abandoned */
 }
 
+int no_signal (struct object *obj, unsigned int access)
+{
+   set_error (STATUS_OBJECT_TYPE_MISMATCH);
+   return 0;
+}
+
 int no_get_fd( struct object *obj )
 {
     set_error( STATUS_OBJECT_TYPE_MISMATCH );

Index: object.h
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/object.h,v
retrieving revision 1.16
retrieving revision 1.17
diff -u -d -r1.16 -r1.17
--- object.h	31 Jul 2007 18:00:22 -0000	1.16
+++ object.h	31 Jul 2007 19:39:35 -0000	1.17
@@ -52,6 +52,8 @@
     void (*remove_queue)(struct object *,struct wait_queue_entry *);
     /* is object signaled? */
     int  (*signaled)(struct object *,struct wait_queue_entry *entry);
+    /* signal the object */
+    int (*signal)(struct object *,unsigned int access);
     /* wait satisfied; return 1 if abandoned */
     int  (*satisfied)(struct object *,struct thread *);
     /* get the events we want to poll() for on this object */
@@ -116,6 +118,7 @@
 extern struct object *find_object( const WCHAR *name, size_t len );
 extern int no_add_queue( struct object *obj, struct wait_queue_entry *entry );
 extern int no_satisfied( struct object *obj, struct thread *thread );
+extern int no_signal( struct object *obj, unsigned int access );
 extern int no_get_fd( struct object *obj );
 extern context_fd no_get_ctx_fd( struct object *obj );
 extern int no_flush( struct object *obj );

Index: process.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/process.c,v
retrieving revision 1.42
retrieving revision 1.43
diff -u -d -r1.42 -r1.43
--- process.c	31 Jul 2007 17:38:40 -0000	1.42
+++ process.c	31 Jul 2007 19:39:35 -0000	1.43
@@ -53,6 +53,7 @@
     add_queue,                   /* add_queue */
     remove_queue,                /* remove_queue */
     process_signaled,            /* signaled */
+    no_signal,                   /* signal */
     no_satisfied,                /* satisfied */
     NULL,                        /* get_poll_events */
     process_poll_event,          /* poll_event */
@@ -96,6 +97,7 @@
     add_queue,                     /* add_queue */
     remove_queue,                  /* remove_queue */
     startup_info_signaled,         /* signaled */
+    no_signal,                     /* signal */
     no_satisfied,                  /* satisfied */
     NULL,                          /* get_poll_events */
     NULL,                          /* poll_event */

Index: protocol.def
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/protocol.def,v
retrieving revision 1.42
retrieving revision 1.43
diff -u -d -r1.42 -r1.43
--- protocol.def	31 Jul 2007 18:00:22 -0000	1.42
+++ protocol.def	31 Jul 2007 19:39:35 -0000	1.43
@@ -478,6 +478,7 @@
     void*        cookie;       /* magic cookie to return to client */
     int          sec;          /* absolute timeout */
     int          usec;         /* absolute timeout */
+    handle_t     hSignalObject; /* Object to signal at same time */
     VARARG(handles,handles);   /* handles to select on */
 @END
 #define SELECT_ALL           1
@@ -491,6 +492,7 @@
     void*        cookie;       /* magic cookie to return to client */
     int          sec;          /* absolute timeout */
     int          usec;         /* absolute timeout */
+    handle_t     hSignalObject; /* Object to signal at same time */
     void*        pollfd;       /* pollfd and object table to fill in */
     VARARG(handles,handles);   /* handles to select on */
 @REPLY

Index: queue.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/queue.c,v
retrieving revision 1.9
retrieving revision 1.10
diff -u -d -r1.9 -r1.10
--- queue.c	27 Mar 2007 20:25:27 -0000	1.9
+++ queue.c	31 Jul 2007 19:39:35 -0000	1.10
@@ -107,6 +107,7 @@
     msg_queue_add_queue,       /* add_queue */
     msg_queue_remove_queue,    /* remove_queue */
     msg_queue_signaled,        /* signaled */
+    no_signal,                 /* signal */
     msg_queue_satisfied,       /* satisfied */
     NULL,                      /* get_poll_events */
     NULL,                      /* poll_event */

Index: registry.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/registry.c,v
retrieving revision 1.13
retrieving revision 1.14
diff -u -d -r1.13 -r1.14
--- registry.c	30 Mar 2007 18:58:50 -0000	1.13
+++ registry.c	31 Jul 2007 19:39:35 -0000	1.14
@@ -123,6 +123,7 @@
     no_add_queue,            /* add_queue */
     NULL,                    /* remove_queue */
     NULL,                    /* signaled */
+    no_signal,               /* signal */
     NULL,                    /* satisfied */
     NULL,                    /* get_poll_events */
     NULL,                    /* poll_event */

Index: request.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/request.c,v
retrieving revision 1.26
retrieving revision 1.27
diff -u -d -r1.26 -r1.27
--- request.c	30 Mar 2007 15:55:03 -0000	1.26
+++ request.c	31 Jul 2007 19:39:35 -0000	1.27
@@ -75,6 +75,7 @@
     no_add_queue,                  /* add_queue */
     NULL,                          /* remove_queue */
     NULL,                          /* signaled */
+    no_signal,                     /* signal */
     NULL,                          /* satisfied */
     NULL,                          /* get_poll_events */
     master_socket_poll_event,      /* poll_event */

Index: semaphore.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/semaphore.c,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -d -r1.5 -r1.6
--- semaphore.c	27 Mar 2007 20:25:27 -0000	1.5
+++ semaphore.c	31 Jul 2007 19:39:35 -0000	1.6
@@ -23,6 +23,7 @@
 
 static void semaphore_dump( struct object *obj, int verbose );
 static int semaphore_signaled( struct object *obj, struct wait_queue_entry *entry );
+static int semaphore_do_signal (struct object *obj, unsigned int access);
 static int semaphore_satisfied( struct object *obj, struct thread *thread );
 
 static const struct object_ops semaphore_ops =
@@ -32,6 +33,7 @@
     add_queue,                     /* add_queue */
     remove_queue,                  /* remove_queue */
     semaphore_signaled,            /* signaled */
+    semaphore_do_signal,           /* signal */
     semaphore_satisfied,           /* satisfied */
     NULL,                          /* get_poll_events */
     NULL,                          /* poll_event */
@@ -66,35 +68,34 @@
     return sem;
 }
 
-static unsigned int release_semaphore( handle_t handle, unsigned int count )
+static int release_semaphore (struct semaphore *sem, unsigned int count,
+                              unsigned int *pPrev)
 {
-    struct semaphore *sem;
-    unsigned int prev = 0;
+   if (pPrev)
+      *pPrev = sem->count;
 
-    if ((sem = (struct semaphore *)get_handle_obj( current->process, handle,
-                                                   SEMAPHORE_MODIFY_STATE, semaphore_ops_tag )))
-    {
-        prev = sem->count;
-        if (sem->count + count < sem->count || sem->count + count > sem->max)
-        {
-            set_error( STATUS_SEMAPHORE_LIMIT_EXCEEDED );
-        }
-        else if (sem->count)
-        {
-            /* there cannot be any thread waiting if the count is != 0 */
-            assert( !sem->obj.head );
-            sem->count += count;
-        }
-        else
-        {
-            sem->count = count;
-            wake_up( &sem->obj, count );
-        }
-        release_object( sem );
-    }
-    return prev;
+   if ((sem->count + count < sem->count) || (sem->count + count > sem->max))
+   {
+      set_error (STATUS_SEMAPHORE_LIMIT_EXCEEDED);
+      return 0;
+   }
+
+   if (sem->count)
+   {
+      /* there cannot be any thread waiting if the count is != 0 */
+      assert (!sem->obj.head);
+      sem->count += count;
+   }
+   else
+   {
+      sem->count = count;
+      wake_up (&sem->obj, count);
+   }
+
+   return 1;
 }
 
+
 static void semaphore_dump( struct object *obj, int verbose )
 {
     struct semaphore *sem = (struct semaphore *)obj;
@@ -111,6 +112,23 @@
     return (sem->count > 0);
 }
 
+/* Not named semaphore_signal() as that conflicts with a function
+   on Apple */
+static int semaphore_do_signal (struct object *obj, unsigned int access)
+{
+   struct semaphore *sem = (struct semaphore *)obj;
+
+   assert (obj->ops == semaphore_ops_tag);
+
+   if (!(access & SEMAPHORE_MODIFY_STATE))
+   {
+      set_error (STATUS_ACCESS_DENIED);
+      return 0;
+   }
+
+   return release_semaphore (sem, 1, NULL);
+}
+
 static int semaphore_satisfied( struct object *obj, struct thread *thread )
 {
     struct semaphore *sem = (struct semaphore *)obj;
@@ -144,5 +162,14 @@
 /* release a semaphore */
 DECL_HANDLER(release_semaphore)
 {
-    reply->prev_count = release_semaphore( req->handle, req->count );
+   struct semaphore *sem;
+
+   if ((sem = (struct semaphore *)get_handle_obj (current->process,
+                                                  req->handle,
+                                                  SEMAPHORE_MODIFY_STATE,
+                                                  semaphore_ops_tag)))
+   {
+      release_semaphore (sem, req->count, &reply->prev_count);
+      release_object (sem);
+   }
 }

Index: serial.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/serial.c,v
retrieving revision 1.13
retrieving revision 1.14
diff -u -d -r1.13 -r1.14
--- serial.c	27 Mar 2007 20:25:27 -0000	1.13
+++ serial.c	31 Jul 2007 19:39:35 -0000	1.14
@@ -81,6 +81,7 @@
     default_poll_add_queue,       /* add_queue */
     default_poll_remove_queue,    /* remove_queue */
     default_poll_signaled,        /* signaled */
+    no_signal,                    /* signal */
     no_satisfied,                 /* satisfied */
     serial_get_poll_events,       /* get_poll_events */
     serial_poll_event,            /* poll_event */

Index: snapshot.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/snapshot.c,v
retrieving revision 1.8
retrieving revision 1.9
diff -u -d -r1.8 -r1.9
--- snapshot.c	27 Mar 2007 20:25:27 -0000	1.8
+++ snapshot.c	31 Jul 2007 19:39:35 -0000	1.9
@@ -44,6 +44,7 @@
     no_add_queue,                 /* add_queue */
     NULL,                         /* remove_queue */
     NULL,                         /* signaled */
+    no_signal,                    /* signal */
     NULL,                         /* satisfied */
     NULL,                         /* get_poll_events */
     NULL,                         /* poll_event */

Index: sock.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/sock.c,v
retrieving revision 1.21
retrieving revision 1.22
diff -u -d -r1.21 -r1.22
--- sock.c	27 Mar 2007 20:25:27 -0000	1.21
+++ sock.c	31 Jul 2007 19:39:35 -0000	1.22
@@ -90,6 +90,7 @@
     add_queue,                    /* add_queue */
     remove_queue,                 /* remove_queue */
     sock_signaled,                /* signaled */
+    no_signal,                    /* signal */
     no_satisfied,                 /* satisfied */
     sock_get_poll_events,         /* get_poll_events */
     sock_poll_event,              /* poll_event */

Index: thread.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/thread.c,v
retrieving revision 1.55
retrieving revision 1.56
diff -u -d -r1.55 -r1.56
--- thread.c	31 Jul 2007 18:00:22 -0000	1.55
+++ thread.c	31 Jul 2007 19:39:35 -0000	1.56
@@ -76,6 +76,7 @@
     add_queue,                  /* add_queue */
     remove_queue,               /* remove_queue */
     thread_signaled,            /* signaled */
+    no_signal,                  /* signal */
     no_satisfied,               /* satisfied */
     NULL,                       /* get_poll_events */
     thread_poll_event,          /* poll_event */
@@ -669,9 +670,32 @@
 
 extern int set_handle_in_place( struct process* process, handle_t handle, context_fd ctx_fd );
 
+
+/* Signal the passed object if it supports being signalled by
+   SignalObjectAndWait (events, mutexes and semaphores) and return 1. On
+   error, set error accordingly and return 0 */
+static int object_signal (handle_t hSignalObject)
+{
+   int ret = 0;
+   struct object *obj;
+
+   /* This sets error codes as required */
+   obj = get_handle_obj (current->process, hSignalObject, 0, NULL);
+   if (!obj)
+      return 0;
+
+   ret = get_ops (obj->ops)->signal (obj, get_handle_access (current->process,
+                                                             hSignalObject));
+   release_object (obj);
+
+   return ret;
+}
+
+
 /* select on a list of handles */
 void select_on( int count, void *cookie, const handle_t *handles,
-                int flags, int sec, int usec, struct object* objs[] )
+                int flags, int sec, int usec, handle_t hSignalObject,
+                struct object* objs[] )
 {
     int ret, i;
     struct object *objects[MAXIMUM_WAIT_OBJECTS];
@@ -708,6 +732,20 @@
 
     if (!wait_on( count, objects, flags, sec, usec )) goto done;
 
+    /* See SignalObjectAndWait() */
+    if (hSignalObject)
+    {
+       if (!object_signal (hSignalObject))
+       {
+          end_wait (current);
+          goto done;
+       }
+
+       /* Check for the case that we just signaled ourselves */
+       if (!current->wait)
+          goto done;
+    }
+
     if ((ret = check_wait( current )) != -1)
     {
         /* condition is already satisfied */
@@ -1348,7 +1386,8 @@
 DECL_HANDLER(select)
 {
     int count = get_req_data_size() / sizeof(int);
-    select_on( count, req->cookie, get_req_data(), req->flags, req->sec, req->usec, NULL );
+    select_on( count, req->cookie, get_req_data(), req->flags, req->sec,
+               req->usec, req->hSignalObject, NULL );
 }
 
 /* select on a handle list */
@@ -1361,7 +1400,8 @@
 
     is_select = 1;
 
-    select_on( count, req->cookie, get_req_data(), req->flags, req->sec, req->usec, (struct object**)pfd->objects );
+    select_on( count, req->cookie, get_req_data(), req->flags, req->sec,
+               req->usec, req->hSignalObject, (struct object**)pfd->objects );
 
     if( get_error() == STATUS_PENDING ) update_pollfd_for_thread( pfd, &reply->pollfds, count );
     else reply->pollfds = 0;

Index: thread.h
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/thread.h,v
retrieving revision 1.28
retrieving revision 1.29
diff -u -d -r1.28 -r1.29
--- thread.h	31 Jul 2007 18:00:22 -0000	1.28
+++ thread.h	31 Jul 2007 19:39:35 -0000	1.29
@@ -176,7 +176,8 @@
 extern int is_cookie_satisfied( const struct thread* thread, const  void* cookie );
 extern void send_unix_signal( struct thread *thread, int resume, int code, size_t size, void *data );
 extern void select_on( int count, void *cookie, const handle_t *handles,
-                       int flags, int sec, int usec, struct object* objs[] );
+                       int flags, int sec, int usec, handle_t hSignalObject,
+                       struct object* objs[] );
 extern void iocomp_notify_thread_inactive (struct iocomp *iocomp);
 extern void iocomp_notify_thread_active (struct iocomp *iocomp);
 

Index: timer.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/timer.c,v
retrieving revision 1.6
retrieving revision 1.7
diff -u -d -r1.6 -r1.7
--- timer.c	27 Mar 2007 20:25:27 -0000	1.6
+++ timer.c	31 Jul 2007 19:39:35 -0000	1.7
@@ -44,6 +44,7 @@
     add_queue,                 /* add_queue */
     remove_queue,              /* remove_queue */
     timer_signaled,            /* signaled */
+    no_signal,                 /* signal */
     timer_satisfied,           /* satisfied */
     NULL,                      /* get_poll_events */
     NULL,                      /* poll_event */

Index: token.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/token.c,v
retrieving revision 1.3
retrieving revision 1.4
diff -u -d -r1.3 -r1.4
--- token.c	27 Mar 2007 20:25:27 -0000	1.3
+++ token.c	31 Jul 2007 19:39:35 -0000	1.4
@@ -30,6 +30,7 @@
     no_add_queue,                 /* add_queue */
     NULL,                         /* remove_queue */
     NULL,                         /* signaled */
+    no_signal,                    /* signal */
     NULL,                         /* satisfied */
     NULL,                         /* get_poll_events */
     NULL,                         /* poll_event */

Index: trace.c
===================================================================
RCS file: /var/lib/cvsd/cvsroot/winex/server/trace.c,v
retrieving revision 1.43
retrieving revision 1.44
diff -u -d -r1.43 -r1.44
--- trace.c	31 Jul 2007 18:00:22 -0000	1.43
+++ trace.c	31 Jul 2007 19:39:35 -0000	1.44
@@ -639,6 +639,7 @@
     fprintf( stderr, " cookie=%p,", req->cookie );
     fprintf( stderr, " sec=%d,", req->sec );
     fprintf( stderr, " usec=%d,", req->usec );
+    fprintf( stderr, " hSignalObject=%d,", req->hSignalObject );
     fprintf( stderr, " handles=" );
     dump_varargs_handles( cur_size );
 }
@@ -649,6 +650,7 @@
     fprintf( stderr, " cookie=%p,", req->cookie );
     fprintf( stderr, " sec=%d,", req->sec );
     fprintf( stderr, " usec=%d,", req->usec );
+    fprintf( stderr, " hSignalObject=%d,", req->hSignalObject );
     fprintf( stderr, " pollfd=%p,", req->pollfd );
     fprintf( stderr, " handles=" );
     dump_varargs_handles( cur_size );