static int ktimer_delete(struct filter *filt, struct knote *kn) { if (kn->data.handle == NULL || kn->kn_event_whandle == NULL) return (0); if(!UnregisterWaitEx(kn->kn_event_whandle, INVALID_HANDLE_VALUE)) { dbg_lasterror("UnregisterWait()"); return (-1); } if (!CancelWaitableTimer(kn->data.handle)) { dbg_lasterror("CancelWaitableTimer()"); return (-1); } if (!CloseHandle(kn->data.handle)) { dbg_lasterror("CloseHandle()"); return (-1); } if( !(kn->kev.flags & EV_ONESHOT) ) knote_release(kn); kn->data.handle = NULL; return (0); }
DirectoryWinAPI::~DirectoryWinAPI() { for(auto it = callbacks.begin(); it != callbacks.end(); ++it) { UnregisterWaitEx(it->second.waitHandle, INVALID_HANDLE_VALUE); FindCloseChangeNotification(it->first); delete it->second.cb; } }
void CEXIETHERNET::RecvStop() { if (!IsActivated()) return; UnregisterWaitEx(mHReadWait, INVALID_HANDLE_VALUE); CloseHandle(mHRecvEvent); mHRecvEvent = INVALID_HANDLE_VALUE; }
/* * Disconnect, but do not close, a pipe handle; and deregister * any pending waiter threads from its event handles. * * XXX: This must be called from primary thread, or lock held if not! */ void pipe_disconnect(pipe_instance_t *pp) { TRACE0(ENTER, "Entering pipe_disconnect"); if (pp == NULL) return; /* * Cancel pending I/O before deregistering the callback, * and disconnect the pipe, to avoid race conditions. * We also reset the event(s) to avoid being signalled for * things which haven't actually happened yet. * * XXX: To avoid races during shutdown, we may have to * NULL out the second argument to UnregisterWaitEx(). * We can't, however, do that from a service thread. */ if (pp->cwait != NULL) { UnregisterWaitEx(pp->cwait, pp->cevent); ResetEvent(pp->cevent); pp->cwait = NULL; } if (pp->rwait != NULL) { UnregisterWaitEx(pp->rwait, pp->revent); ResetEvent(pp->revent); pp->rwait = NULL; } if (pp->pipe != NULL) { CancelIo(pp->pipe); if (pp->state == PIPE_STATE_CONNECTED || pp->state == PIPE_STATE_LISTEN) { DisconnectNamedPipe(pp->pipe); } } pp->state = PIPE_STATE_INIT; TRACE0(ENTER, "Leaving pipe_disconnect"); }
void uv_process_close(uv_loop_t* loop, uv_process_t* handle) { if (handle->wait_handle != INVALID_HANDLE_VALUE) { handle->close_handle = CreateEvent(NULL, FALSE, FALSE, NULL); UnregisterWaitEx(handle->wait_handle, handle->close_handle); handle->wait_handle = NULL; RegisterWaitForSingleObject(&handle->wait_handle, handle->close_handle, close_wait_callback, (void*)handle, INFINITE, WT_EXECUTEINWAITTHREAD | WT_EXECUTEONLYONCE); } else { uv_want_endgame(loop, (uv_handle_t*)handle); } }
static PyObject * overlapped_UnregisterWaitEx(PyObject *self, PyObject *args) { HANDLE WaitHandle, Event; BOOL ret; if (!PyArg_ParseTuple(args, F_HANDLE F_HANDLE, &WaitHandle, &Event)) return NULL; Py_BEGIN_ALLOW_THREADS ret = UnregisterWaitEx(WaitHandle, Event); Py_END_ALLOW_THREADS if (!ret) return SetFromWindowsErr(0); Py_RETURN_NONE; }
void uv_process_close(uv_loop_t* loop, uv_process_t* handle) { uv__handle_start(handle); if (handle->wait_handle != INVALID_HANDLE_VALUE) { /* This blocks until either the wait was cancelled, or the callback has */ /* completed. */ BOOL r = UnregisterWaitEx(handle->wait_handle, INVALID_HANDLE_VALUE); if (!r) { /* This should never happen, and if it happens, we can't recover... */ uv_fatal_error(GetLastError(), "UnregisterWaitEx"); } handle->wait_handle = INVALID_HANDLE_VALUE; } if (!handle->exit_cb_pending) { uv_want_endgame(loop, (uv_handle_t*)handle); } }
/* This code gets executed when a child process is terminated. */ void WINAPI deadChildProcCallBack( PVOID lpParameter, BOOLEAN timeoutHappened) { DeadChildInfo childInfo = (DeadChildInfo)lpParameter; DWORD exitcode; if (timeoutHappened) /* Timeout happened. */ return; /* Unregister the wait handler. */ UnregisterWaitEx(childInfo->waitHandle, NULL); /* Retrieves the termination status of the specified process. */ if (!GetExitCodeProcess(childInfo->procHandle, &exitcode)) { fprintf(stderr, "could not read exit code for process\n"); exitcode = 255; } }
bool ObjectWatcher::StopWatching() { if (!wait_object_) return false; // Make sure ObjectWatcher is used in a single-threaded fashion. assert(origin_loop_ == MessageLoop::current()); // Blocking call to cancel the wait. Any callbacks already in progress will // finish before we return from this call. if (!UnregisterWaitEx(wait_object_, INVALID_HANDLE_VALUE)) { return false; } signal_weakflag_.Cancel(); object_ = NULL; wait_object_ = NULL; MessageLoop::current()->RemoveDestructionObserver(this); return true; }
bool ObjectWatcher::StopWatching() { if (!wait_object_) return false; // Make sure ObjectWatcher is used in a single-threaded fashion. DCHECK_EQ(origin_loop_, MessageLoop::current()); // Blocking call to cancel the wait. Any callbacks already in progress will // finish before we return from this call. if (!UnregisterWaitEx(wait_object_, INVALID_HANDLE_VALUE)) { DPLOG(FATAL) << "UnregisterWaitEx failed"; return false; } weak_factory_.InvalidateWeakPtrs(); object_ = NULL; wait_object_ = NULL; MessageLoop::current()->RemoveDestructionObserver(this); return true; }
//----------------------------------------------------------------------------- // Function: PeoplePickerModelDestroy // // Purpose: Frees up all the resources needed by the model // // Returns: VOID // VOID PeoplePickerModelDestroy() { UnregisterWaitEx(g_hModelWaitObject,INVALID_HANDLE_VALUE); PeerCollabUnregisterEvent(g_hModelPeerEvent); CloseHandle(g_hModelEvent); }
/* callback from ares when socket operation is started */ static void uv_ares_sockstate_cb(void *data, ares_socket_t sock, int read, int write) { /* look to see if we have a handle for this socket in our list */ uv_loop_t* loop = (uv_loop_t*) data; uv_ares_task_t* uv_handle_ares = uv_find_ares_handle(loop, sock); if (read == 0 && write == 0) { /* if read and write are 0, cleanup existing data */ /* The code assumes that c-ares does a callback with read = 0 and */ /* write = 0 when the socket is closed. After we receive this we stop */ /* monitoring the socket. */ if (uv_handle_ares != NULL) { uv_req_t* uv_ares_req; uv_handle_ares->h_close_event = CreateEvent(NULL, FALSE, FALSE, NULL); /* remove Wait */ if (uv_handle_ares->h_wait) { UnregisterWaitEx(uv_handle_ares->h_wait, uv_handle_ares->h_close_event); uv_handle_ares->h_wait = NULL; } /* detach socket from the event */ WSAEventSelect(sock, NULL, 0); if (uv_handle_ares->h_event != WSA_INVALID_EVENT) { WSACloseEvent(uv_handle_ares->h_event); uv_handle_ares->h_event = WSA_INVALID_EVENT; } /* remove handle from list */ uv_remove_ares_handle(uv_handle_ares); /* Post request to cleanup the Task */ uv_ares_req = &uv_handle_ares->ares_req; uv_req_init(loop, uv_ares_req); uv_ares_req->type = UV_ARES_CLEANUP_REQ; uv_ares_req->data = uv_handle_ares; /* post ares done with socket - finish cleanup when all threads done. */ POST_COMPLETION_FOR_REQ(loop, uv_ares_req); } else { assert(0); uv_fatal_error(ERROR_INVALID_DATA, "ares_SockStateCB"); } } else { if (uv_handle_ares == NULL) { /* setup new handle */ /* The code assumes that c-ares will call us when it has an open socket. We need to call into c-ares when there is something to read, or when it becomes writable. */ uv_handle_ares = (uv_ares_task_t*)malloc(sizeof(uv_ares_task_t)); if (uv_handle_ares == NULL) { uv_fatal_error(ERROR_OUTOFMEMORY, "malloc"); } uv_handle_ares->type = UV_ARES_TASK; uv_handle_ares->close_cb = NULL; uv_handle_ares->loop = loop; uv_handle_ares->data = loop; uv_handle_ares->sock = sock; uv_handle_ares->h_wait = NULL; uv_handle_ares->flags = 0; /* create an event to wait on socket signal */ uv_handle_ares->h_event = WSACreateEvent(); if (uv_handle_ares->h_event == WSA_INVALID_EVENT) { uv_fatal_error(WSAGetLastError(), "WSACreateEvent"); } /* tie event to socket */ if (SOCKET_ERROR == WSAEventSelect(sock, uv_handle_ares->h_event, FD_READ | FD_WRITE | FD_CONNECT)) { uv_fatal_error(WSAGetLastError(), "WSAEventSelect"); } /* add handle to list */ uv_add_ares_handle(loop, uv_handle_ares); uv_ref(loop); /* * we have a single polling timer for all ares sockets. * This is preferred to using ares_timeout. See ares_timeout.c warning. * if timer is not running start it, and keep socket count */ if (loop->ares_active_sockets == 0) { uv_timer_init(loop, &loop->ares_polling_timer); uv_timer_start(&loop->ares_polling_timer, uv_ares_poll, 1000L, 1000L); } loop->ares_active_sockets++; /* specify thread pool function to call when event is signaled */ if (RegisterWaitForSingleObject(&uv_handle_ares->h_wait, uv_handle_ares->h_event, uv_ares_socksignal_tp, (void*)uv_handle_ares, INFINITE, WT_EXECUTEINWAITTHREAD) == 0) { uv_fatal_error(GetLastError(), "RegisterWaitForSingleObject"); } } else { /* found existing handle. */ assert(uv_handle_ares->type == UV_ARES_TASK); assert(uv_handle_ares->data != NULL); assert(uv_handle_ares->h_event != WSA_INVALID_EVENT); } } }
void WINAPI pipe_reread_cb(void *ctx) { pipe_instance_t *pp; DWORD result; int failed; pp = (pipe_instance_t *)ctx; EnterCriticalSection(&pp->rcs); TRACE1(ENTER, "Entering pipe_reread_cb %p", ctx); failed = 0; if (pp->state != PIPE_STATE_CONNECTED) { TRACE0(NETWORK, "WARNING: not PIPE_STATE_CONNECTED"); } /* * Tear down and wire up read thread callback again. * This is probably inefficient. */ UnregisterWaitEx(pp->rwait, pp->revent); ResetEvent(pp->revent); /* XXX ReadFile() should do this for us? */ pp->rwait = NULL; /* * Post a new read request. Deal with fatal errors. */ result = ReadFile(pp->pipe, pp->rbuf, pp->rsize, NULL, &pp->rov); if (result == 0) { result = GetLastError(); if (result != ERROR_IO_PENDING) { TRACE1(ANY, "WARNING: pipe_reread_cb read returned %d", result); } if (result == ERROR_BROKEN_PIPE) { failed = 1; goto fail; } } /* * Now, and only now, do we kick off the read thread, in order * to avoid being preempted if the client disconnects. */ result = RegisterWaitForSingleObject(&(pp->rwait), pp->revent, pipe_read_cb, pp, INFINITE, WT_EXECUTEINIOTHREAD | WT_EXECUTEONLYONCE); if (result == 0) { result = GetLastError(); TRACE1(CONFIGURATION, "Error %u RegisterWaitForSingleObject()", result); failed = 1; } fail: /* * If a fatal error occurred, disconnect the pipe client, and * listen for a new connection on this instance. */ if (failed) { ResetEvent(pp->revent); QueueUserWorkItem( (LPTHREAD_START_ROUTINE)pipe_relisten_cb, (PVOID)pp, WT_EXECUTEINIOTHREAD); } out: TRACE0(ENTER, "Leaving pipe_reread_cb"); LeaveCriticalSection(&pp->rcs); }
/* * XXX: This must be called from primary thread, or lock held if not! */ int pipe_listen(pipe_instance_t *pp) { int retval; DWORD result; retval = -1; TRACE1(ENTER, "Entering pipe_listen %p", pp); if (pp == NULL || pp->state != PIPE_STATE_INIT) return (retval); /* * Register a pool thread to wait for pipe connection. * Clear event state to avoid spurious signals. */ ResetEvent(pp->cevent); result = RegisterWaitForSingleObject(&(pp->cwait), pp->cevent, pipe_connect_cb, pp, INFINITE, WT_EXECUTEINIOTHREAD | WT_EXECUTEONLYONCE); if (result == 0) { result = GetLastError(); TRACE1(CONFIGURATION, "Error %u RegisterWaitForSingleObject()", result); goto fail; } /* * Register a pool thread to wait for data to be received on the pipe. * We don't cause this to be activated until we post a read request * from within the connection callback. * XXX: We want the read callback to be called whenever the * object is signalled, not just once. */ ResetEvent(pp->revent); result = RegisterWaitForSingleObject(&(pp->rwait), pp->revent, pipe_read_cb, pp, INFINITE, WT_EXECUTEINIOTHREAD | WT_EXECUTEONLYONCE); if (result == 0) { result = GetLastError(); TRACE1(CONFIGURATION, "Error %u RegisterWaitForSingleObject()", result); goto fail; } /* * Post the connection request. If it returns non-zero, then the * connection attempt is pending and the thread will be signalled * when complete. If it returns zero, then there's a problem. * ERROR_NO_DATA means the client disconnected, but we didn't * call DisconnectNamedPipe(). * ConnectNamedPipe() does not reset the event object associated * with the OVERLAPPED parameter. */ result = ConnectNamedPipe(pp->pipe, &pp->cov); if (result == 0) { result = GetLastError(); if (result == ERROR_PIPE_LISTENING) { TRACE0(NETWORK, "Error: listening; Reconnecting named pipe"); result = ConnectNamedPipe(pp->pipe, &pp->cov); } if (result == ERROR_PIPE_CONNECTED) { TRACE0(NETWORK, "Error: named pipe already connected"); goto fail; } if (result == ERROR_NO_DATA) { TRACE0(NETWORK, "Error: previous session not cleaned up"); goto fail; } } pp->state = PIPE_STATE_LISTEN; retval = 0; fail: if (retval == -1) { if (pp->cwait != NULL) { UnregisterWaitEx(pp->cwait, pp->cevent); ResetEvent(pp->cevent); pp->cwait = NULL; } if (pp->rwait != NULL) { UnregisterWaitEx(pp->rwait, pp->revent); ResetEvent(pp->revent); pp->rwait = NULL; } } TRACE1(ENTER, "Leaving pipe_listen", pp); return (retval); }