Using handle close callback now.
authorArmin Novak <armin.novak@thincast.com>
Wed, 11 Mar 2015 14:11:11 +0000 (15:11 +0100)
committerArmin Novak <armin.novak@thincast.com>
Wed, 11 Mar 2015 14:11:11 +0000 (15:11 +0100)
winpr/libwinpr/synch/event.c

index a7ec4e9..9d102c0 100644 (file)
 
 CRITICAL_SECTION cs = { NULL, 0, 0, NULL, NULL, 0 };
 
+static pthread_once_t event_initialized = PTHREAD_ONCE_INIT;
+
+static HANDLE_CLOSE_CB _EventHandleCloseCb;
+
+static BOOL EventCloseHandle(HANDLE handle);
+
+static BOOL EventIsHandled(HANDLE handle)
+{
+       WINPR_TIMER* pEvent = (WINPR_TIMER*) handle;
+
+       if (!pEvent || pEvent->Type != HANDLE_TYPE_EVENT)
+       {
+               SetLastError(ERROR_INVALID_HANDLE);
+               return FALSE;
+       }
+
+       return TRUE;
+}
+
+static void EventInitialize(void)
+{
+       _EventHandleCloseCb.IsHandled = EventIsHandled;
+       _EventHandleCloseCb.CloseHandle = EventCloseHandle;
+       RegisterHandleCloseCb(&_EventHandleCloseCb);
+}
+
+BOOL EventCloseHandle(HANDLE handle) {
+       WINPR_EVENT* event = (WINPR_EVENT*) handle;
+
+       if (!EventIsHandled(handle))
+               return FALSE;
+
+    if (!event->bAttached)
+    {
+        if (event->pipe_fd[0] != -1)
+        {
+               close(event->pipe_fd[0]);
+               event->pipe_fd[0] = -1;
+        }
+
+        if (event->pipe_fd[1] != -1)
+        {
+               close(event->pipe_fd[1]);
+               event->pipe_fd[1] = -1;
+        }
+    }
+
+    free(event);
+    return TRUE;
+}
+
 HANDLE CreateEventW(LPSECURITY_ATTRIBUTES lpEventAttributes, BOOL bManualReset, BOOL bInitialState, LPCWSTR lpName)
 {
        WINPR_EVENT* event;
-       event = (WINPR_EVENT*) calloc(1, sizeof(WINPR_EVENT));
 
+       if (pthread_once(&event_initialized, EventInitialize))
+               return NULL;
+
+       event = (WINPR_EVENT*) calloc(1, sizeof(WINPR_EVENT));
        if (event)
        {
                event->bAttached = FALSE;