| 193 | |
| 194 | |
| 195 | class _WaitHandleFuture(_BaseWaitHandleFuture): |
| 196 | def __init__(self, ov, handle, wait_handle, proactor, *, loop=None): |
| 197 | super().__init__(ov, handle, wait_handle, loop=loop) |
| 198 | self._proactor = proactor |
| 199 | self._unregister_proactor = True |
| 200 | self._event = _overlapped.CreateEvent(None, True, False, None) |
| 201 | self._event_fut = None |
| 202 | |
| 203 | def _unregister_wait_cb(self, fut): |
| 204 | if self._event is not None: |
| 205 | _winapi.CloseHandle(self._event) |
| 206 | self._event = None |
| 207 | self._event_fut = None |
| 208 | |
| 209 | # If the wait was cancelled, the wait may never be signalled, so |
| 210 | # it's required to unregister it. Otherwise, IocpProactor.close() will |
| 211 | # wait forever for an event which will never come. |
| 212 | # |
| 213 | # If the IocpProactor already received the event, it's safe to call |
| 214 | # _unregister() because we kept a reference to the Overlapped object |
| 215 | # which is used as a unique key. |
| 216 | self._proactor._unregister(self._ov) |
| 217 | self._proactor = None |
| 218 | |
| 219 | super()._unregister_wait_cb(fut) |
| 220 | |
| 221 | def _unregister_wait(self): |
| 222 | if not self._registered: |
| 223 | return |
| 224 | self._registered = False |
| 225 | |
| 226 | wait_handle = self._wait_handle |
| 227 | self._wait_handle = None |
| 228 | try: |
| 229 | _overlapped.UnregisterWaitEx(wait_handle, self._event) |
| 230 | except OSError as exc: |
| 231 | if exc.winerror != _overlapped.ERROR_IO_PENDING: |
| 232 | context = { |
| 233 | 'message': 'Failed to unregister the wait handle', |
| 234 | 'exception': exc, |
| 235 | 'future': self, |
| 236 | } |
| 237 | if self._source_traceback: |
| 238 | context['source_traceback'] = self._source_traceback |
| 239 | self._loop.call_exception_handler(context) |
| 240 | return |
| 241 | # ERROR_IO_PENDING is not an error, the wait was unregistered |
| 242 | |
| 243 | self._event_fut = self._proactor._wait_cancel(self._event, |
| 244 | self._unregister_wait_cb) |
| 245 | |
| 246 | |
| 247 | class PipeServer(object): |
no outgoing calls
no test coverage detected
searching dependent graphs…