* autoload.cc (WSAEventSelect): Define new autoload function.
(WSAEnumNetworkEvents): Ditto. * fhandler_socket.cc (fhandler_socket::accept): If socket is in blocking mode wait for incoming connection and signal.
This commit is contained in:
parent
65604bc18f
commit
3c6bd99175
|
@ -1,3 +1,10 @@
|
|||
2002-07-03 Thomas Pfaff <tpfaff@gmx.net>
|
||||
|
||||
* autoload.cc (WSAEventSelect): Define new autoload function.
|
||||
(WSAEnumNetworkEvents): Ditto.
|
||||
* fhandler_socket.cc (fhandler_socket::accept): If socket is
|
||||
in blocking mode wait for incoming connection and signal.
|
||||
|
||||
2002-07-02 Christopher Faylor <cgf@redhat.com>
|
||||
|
||||
* cygheap.cc (init_cheap): Rearrange error message.
|
||||
|
|
|
@ -480,6 +480,8 @@ LoadDLLfuncEx (WSASendTo, 36, ws2_32, 1)
|
|||
LoadDLLfuncEx (WSASetEvent, 4, ws2_32, 1)
|
||||
LoadDLLfuncEx (WSASocketA, 24, ws2_32, 1)
|
||||
LoadDLLfuncEx (WSAWaitForMultipleEvents, 20, ws2_32, 1)
|
||||
LoadDLLfuncEx (WSAEventSelect, 12, ws2_32, 1)
|
||||
LoadDLLfuncEx (WSAEnumNetworkEvents, 12, ws2_32, 1)
|
||||
|
||||
LoadDLLfuncEx (GetIfTable, 12, iphlpapi, 1)
|
||||
LoadDLLfuncEx (GetIpAddrTable, 12, iphlpapi, 1)
|
||||
|
|
|
@ -469,6 +469,7 @@ int
|
|||
fhandler_socket::accept (struct sockaddr *peer, int *len)
|
||||
{
|
||||
int res = -1;
|
||||
WSAEVENT ev[2] = { WSA_INVALID_EVENT, signal_arrived };
|
||||
BOOL secret_check_failed = FALSE;
|
||||
BOOL in_progress = FALSE;
|
||||
|
||||
|
@ -492,7 +493,58 @@ fhandler_socket::accept (struct sockaddr *peer, int *len)
|
|||
if (len && ((unsigned) *len < sizeof (struct sockaddr_in)))
|
||||
*len = sizeof (struct sockaddr_in);
|
||||
|
||||
res = ::accept (get_socket (), peer, len); // can't use a blocking call inside a lock
|
||||
if (!is_nonblocking())
|
||||
{
|
||||
ev[0] = WSACreateEvent ();
|
||||
|
||||
if (ev[0] != WSA_INVALID_EVENT &&
|
||||
!WSAEventSelect (get_socket (), ev[0], FD_ACCEPT))
|
||||
{
|
||||
WSANETWORKEVENTS sock_event;
|
||||
int wait_result;
|
||||
|
||||
wait_result = WSAWaitForMultipleEvents (2, ev, FALSE, WSA_INFINITE,
|
||||
FALSE);
|
||||
if (wait_result == WSA_WAIT_EVENT_0)
|
||||
WSAEnumNetworkEvents (get_socket (), ev[0], &sock_event);
|
||||
|
||||
/* Unset events for listening socket and
|
||||
switch back to blocking mode */
|
||||
WSAEventSelect (get_socket (), ev[0], 0 );
|
||||
ioctlsocket (get_socket (), FIONBIO, 0);
|
||||
|
||||
switch (wait_result)
|
||||
{
|
||||
case WSA_WAIT_EVENT_0:
|
||||
if (sock_event.lNetworkEvents & FD_ACCEPT)
|
||||
{
|
||||
if (sock_event.iErrorCode[FD_ACCEPT_BIT])
|
||||
{
|
||||
WSASetLastError (sock_event.iErrorCode[FD_ACCEPT_BIT]);
|
||||
set_winsock_errno ();
|
||||
res = -1;
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
/* else; : Should never happen since FD_ACCEPT is the only event
|
||||
that has been selected */
|
||||
break;
|
||||
case WSA_WAIT_EVENT_0 + 1:
|
||||
debug_printf ("signal received during accept");
|
||||
set_errno (EINTR);
|
||||
res = -1;
|
||||
goto done;
|
||||
case WSA_WAIT_FAILED:
|
||||
default: /* Should never happen */
|
||||
WSASetLastError (WSAEFAULT);
|
||||
set_winsock_errno ();
|
||||
res = -1;
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
res = ::accept (get_socket (), peer, len);
|
||||
|
||||
if ((SOCKET) res == (SOCKET) INVALID_SOCKET &&
|
||||
WSAGetLastError () == WSAEWOULDBLOCK)
|
||||
|
@ -525,24 +577,30 @@ fhandler_socket::accept (struct sockaddr *peer, int *len)
|
|||
closesocket (res);
|
||||
set_errno (ECONNABORTED);
|
||||
res = -1;
|
||||
return res;
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
|
||||
cygheap_fdnew res_fd;
|
||||
if (res_fd < 0)
|
||||
/* FIXME: what is correct errno? */;
|
||||
else if ((SOCKET) res == (SOCKET) INVALID_SOCKET)
|
||||
set_winsock_errno ();
|
||||
else
|
||||
{
|
||||
fhandler_socket* res_fh = fdsock (res_fd, get_name (), res);
|
||||
if (get_addr_family () == AF_LOCAL)
|
||||
res_fh->set_sun_path (get_sun_path ());
|
||||
res_fh->set_addr_family (get_addr_family ());
|
||||
res_fh->set_socket_type (get_socket_type ());
|
||||
res = res_fd;
|
||||
}
|
||||
{
|
||||
cygheap_fdnew res_fd;
|
||||
if (res_fd < 0)
|
||||
/* FIXME: what is correct errno? */;
|
||||
else if ((SOCKET) res == (SOCKET) INVALID_SOCKET)
|
||||
set_winsock_errno ();
|
||||
else
|
||||
{
|
||||
fhandler_socket* res_fh = fdsock (res_fd, get_name (), res);
|
||||
if (get_addr_family () == AF_LOCAL)
|
||||
res_fh->set_sun_path (get_sun_path ());
|
||||
res_fh->set_addr_family (get_addr_family ());
|
||||
res_fh->set_socket_type (get_socket_type ());
|
||||
res = res_fd;
|
||||
}
|
||||
}
|
||||
|
||||
done:
|
||||
if (ev[0] != WSA_INVALID_EVENT)
|
||||
WSACloseEvent (ev[0]);
|
||||
|
||||
return res;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue