70
71
} FILE_INFORMATION_CLASS, *PFILE_INFORMATION_CLASS;
72
73
typedef DWORD (WINAPI *PNtQueryInformationFile)
73
(HANDLE, IO_STATUS_BLOCK *, VOID *, ULONG, FILE_INFORMATION_CLASS);
74
(HANDLE, IO_STATUS_BLOCK *, VOID *, ULONG, FILE_INFORMATION_CLASS);
80
#define IsConsoleHandle(h) (((long) (h) & 3) == 3)
83
IsSocketHandle (HANDLE h)
87
if (IsConsoleHandle (h))
90
/* Under Wine, it seems that getsockopt returns 0 for pipes too.
91
WSAEnumNetworkEvents instead distinguishes the two correctly. */
92
ev.lNetworkEvents = 0xDEADBEEF;
93
WSAEnumNetworkEvents ((SOCKET) h, NULL, &ev);
94
return ev.lNetworkEvents != 0xDEADBEEF;
79
97
/* Compute output fd_sets for libc descriptor FD (whose Win32 handle is H). */
82
100
win32_poll_handle (HANDLE h, int fd, struct bitset *rbits, struct bitset *wbits,
101
struct bitset *xbits)
85
103
BOOL read, write, except;
103
121
case FILE_TYPE_PIPE:
106
NtQueryInformationFile = (PNtQueryInformationFile)
107
GetProcAddress (GetModuleHandle ("ntdll.dll"),
108
"NtQueryInformationFile");
124
NtQueryInformationFile = (PNtQueryInformationFile)
125
GetProcAddress (GetModuleHandle ("ntdll.dll"),
126
"NtQueryInformationFile");
112
130
if (PeekNamedPipe (h, NULL, 0, NULL, &avail, NULL) != 0)
120
/* It was the write-end of the pipe. Check if it is writable.
121
If NtQueryInformationFile fails, optimistically assume the pipe is
122
writable. This could happen on Win9x, where NtQueryInformationFile
123
is not available, or if we inherit a pipe that doesn't permit
124
FILE_READ_ATTRIBUTES access on the write end (I think this should
125
not happen since WinXP SP2; WINE seems fine too). Otherwise,
126
ensure that enough space is available for atomic writes. */
138
/* It was the write-end of the pipe. Check if it is writable.
139
If NtQueryInformationFile fails, optimistically assume the pipe is
140
writable. This could happen on Win9x, where NtQueryInformationFile
141
is not available, or if we inherit a pipe that doesn't permit
142
FILE_READ_ATTRIBUTES access on the write end (I think this should
143
not happen since WinXP SP2; WINE seems fine too). Otherwise,
144
ensure that enough space is available for atomic writes. */
127
145
memset (&iosb, 0, sizeof (iosb));
128
146
memset (&fpli, 0, sizeof (fpli));
130
148
if (!NtQueryInformationFile
131
149
|| NtQueryInformationFile (h, &iosb, &fpli, sizeof (fpli),
132
FilePipeLocalInformation)
133
|| fpli.WriteQuotaAvailable >= PIPE_BUF
134
|| (fpli.OutboundQuota < PIPE_BUF &&
135
fpli.WriteQuotaAvailable == fpli.OutboundQuota))
150
FilePipeLocalInformation)
151
|| fpli.WriteQuotaAvailable >= PIPE_BUF
152
|| (fpli.OutboundQuota < PIPE_BUF &&
153
fpli.WriteQuotaAvailable == fpli.OutboundQuota))
140
158
case FILE_TYPE_CHAR:
160
if (!(rbits->in[fd / CHAR_BIT] & (1 << (fd & (CHAR_BIT - 1)))))
141
163
ret = WaitForSingleObject (h, 0);
143
164
if (ret == WAIT_OBJECT_0)
146
bRet = GetNumberOfConsoleInputEvents (h, &nbuffer);
147
if (!bRet || nbuffer == 0)
150
irbuffer = (INPUT_RECORD *) alloca (nbuffer * sizeof (INPUT_RECORD));
151
bRet = PeekConsoleInput (h, irbuffer, nbuffer, &avail);
152
if (!bRet || avail == 0)
155
for (i = 0; i < avail; i++)
156
if (irbuffer[i].EventType == KEY_EVENT)
166
if (!IsConsoleHandle (h))
173
bRet = GetNumberOfConsoleInputEvents (h, &nbuffer);
175
/* Screen buffers handles are filtered earlier. */
183
irbuffer = (INPUT_RECORD *) alloca (nbuffer * sizeof (INPUT_RECORD));
184
bRet = PeekConsoleInput (h, irbuffer, nbuffer, &avail);
185
if (!bRet || avail == 0)
191
for (i = 0; i < avail; i++)
192
if (irbuffer[i].EventType == KEY_EVENT)
199
235
fd_set handle_rfds, handle_wfds, handle_xfds;
200
236
struct bitset rbits, wbits, xbits;
201
237
unsigned char anyfds_in[FD_SETSIZE / CHAR_BIT];
202
DWORD ret, wait_timeout, nhandles, nsock;
238
DWORD ret, wait_timeout, nhandles, nsock, nbuffer;
230
/* Copy descriptors to bitsets. */
266
/* Copy descriptors to bitsets. At the same time, eliminate
267
bits in the "wrong" direction for console input buffers
268
and screen buffers, because screen buffers are waitable
269
and they will block until a character is available. */
231
270
memset (&rbits, 0, sizeof (rbits));
232
271
memset (&wbits, 0, sizeof (wbits));
233
272
memset (&xbits, 0, sizeof (xbits));
273
322
/* Classify handles. Create fd sets for sockets, poll the others. */
274
323
for (i = 0; i < nfds; i++)
278
325
if ((anyfds_in[i / CHAR_BIT] & (1 << (i & (CHAR_BIT - 1)))) == 0)
281
328
h = (HANDLE) _get_osfhandle (i);
288
/* Under Wine, it seems that getsockopt returns 0 for pipes too.
289
WSAEnumNetworkEvents instead distinguishes the two correctly. */
290
ev.lNetworkEvents = 0xDEADBEEF;
291
WSAEnumNetworkEvents ((SOCKET) h, NULL, &ev);
292
if (ev.lNetworkEvents != 0xDEADBEEF)
335
if (IsSocketHandle (h))
294
337
int requested = FD_CLOSE;
296
339
/* See above; socket handles are mapped onto select, but we
297
need to map descriptors to handles. */
340
need to map descriptors to handles. */
298
341
if (rbits.in[i / CHAR_BIT] & (1 << (i & (CHAR_BIT - 1))))
300
343
requested |= FD_READ | FD_ACCEPT;
301
FD_SET ((SOCKET) h, rfds);
302
FD_SET ((SOCKET) h, &handle_rfds);
344
FD_SET ((SOCKET) h, rfds);
345
FD_SET ((SOCKET) h, &handle_rfds);
304
347
if (wbits.in[i / CHAR_BIT] & (1 << (i & (CHAR_BIT - 1))))
306
349
requested |= FD_WRITE | FD_CONNECT;
307
FD_SET ((SOCKET) h, wfds);
308
FD_SET ((SOCKET) h, &handle_wfds);
350
FD_SET ((SOCKET) h, wfds);
351
FD_SET ((SOCKET) h, &handle_wfds);
310
353
if (xbits.in[i / CHAR_BIT] & (1 << (i & (CHAR_BIT - 1))))
312
355
requested |= FD_OOB;
313
FD_SET ((SOCKET) h, xfds);
314
FD_SET ((SOCKET) h, &handle_xfds);
356
FD_SET ((SOCKET) h, xfds);
357
FD_SET ((SOCKET) h, &handle_xfds);
317
360
WSAEventSelect ((SOCKET) h, hEvent, requested);
322
365
handle_array[nhandles++] = h;
324
/* Poll now. If we get an event, do not wait below. */
367
/* Poll now. If we get an event, do not wait below. */
325
368
if (wait_timeout != 0
326
&& win32_poll_handle (h, i, &rbits, &wbits, &xbits))
369
&& win32_poll_handle (h, i, &rbits, &wbits, &xbits))
337
380
no need to call select again. */
338
381
rc = select (0, &handle_rfds, &handle_wfds, &handle_xfds, &tv0);
341
/* Restore the fd_sets for the other select we do below. */
384
/* Restore the fd_sets for the other select we do below. */
342
385
memcpy (&handle_rfds, rfds, sizeof (fd_set));
343
386
memcpy (&handle_wfds, wfds, sizeof (fd_set));
344
387
memcpy (&handle_xfds, xfds, sizeof (fd_set));
347
390
wait_timeout = 0;
352
395
ret = MsgWaitForMultipleObjects (nhandles, handle_array, FALSE,
353
wait_timeout, QS_ALLINPUT);
396
wait_timeout, QS_ALLINPUT);
355
398
if (ret == WAIT_OBJECT_0 + nhandles)
357
400
/* new input of some other kind */
359
402
while ((bRet = PeekMessage (&msg, NULL, 0, 0, PM_REMOVE)) != 0)
361
404
TranslateMessage (&msg);
362
405
DispatchMessage (&msg);
369
412
/* If we haven't done it yet, check the status of the sockets. */
381
424
for (i = 0; i < nfds; i++)
383
426
if ((anyfds_in[i / CHAR_BIT] & (1 << (i & (CHAR_BIT - 1)))) == 0)
386
429
h = (HANDLE) _get_osfhandle (i);
387
430
if (h != handle_array[nhandles])
389
/* Perform handle->descriptor mapping. Don't update rc, as these
390
results are counted in the return value of Winsock's select. */
432
/* Perform handle->descriptor mapping. Don't update rc, as these
433
results are counted in the return value of Winsock's select. */
391
434
WSAEventSelect ((SOCKET) h, NULL, 0);
392
435
if (FD_ISSET (h, &handle_rfds))
393
436
FD_SET (i, rfds);