diff options
Diffstat (limited to 'winsup')
-rw-r--r-- | winsup/cygwin/ChangeLog | 12 | ||||
-rw-r--r-- | winsup/cygwin/fhandler.h | 6 | ||||
-rw-r--r-- | winsup/cygwin/fhandler_socket.cc | 44 |
3 files changed, 50 insertions, 12 deletions
diff --git a/winsup/cygwin/ChangeLog b/winsup/cygwin/ChangeLog index 02e0c05df..97a7c3899 100644 --- a/winsup/cygwin/ChangeLog +++ b/winsup/cygwin/ChangeLog @@ -1,3 +1,15 @@ +2004-05-10 Corinna Vinschen <corinna@vinschen.de> + + * fhandler.h (class fhandler_socket): Add "owner" status flag. + * fhandler_socket.cc (wait): Take flag parameter to take FD_OOB into + account. Don't wait infinitely. + (fhandler_socket::recvfrom): Also wait for FD_OOB if socket owner. + (fhandler_socket::recvmsg): Ditto. + (fhandler_socket::sendto): Ditto. + (fhandler_socket::sendmsg): Ditto. + (fhandler_socket::fcntl): Set owner status flag if F_SETOWN with own + pid is called. + 2004-05-09 Pierre Humblet <pierre.humblet@ieee.org> * environ.cc (build_env): Only try to construct required-but-missing diff --git a/winsup/cygwin/fhandler.h b/winsup/cygwin/fhandler.h index acdd09fa2..1e8129842 100644 --- a/winsup/cygwin/fhandler.h +++ b/winsup/cygwin/fhandler.h @@ -341,16 +341,17 @@ class fhandler_socket: public fhandler_base unsigned saw_shutdown_read : 1; /* Socket saw a SHUT_RD */ unsigned saw_shutdown_write : 1; /* Socket saw a SHUT_WR */ unsigned closed : 1; + unsigned owner : 1; unsigned connect_state : 2; public: status_flags () : async_io (0), saw_shutdown_read (0), saw_shutdown_write (0), - closed (0), connect_state (unconnected) + closed (0), owner (0), connect_state (unconnected) {} } status; bool prepare (HANDLE &event, long event_mask); - int wait (HANDLE event); + int wait (HANDLE event, int flags); void release (HANDLE event); public: @@ -363,6 +364,7 @@ class fhandler_socket: public fhandler_base IMPLEMENT_STATUS_FLAG (bool, saw_shutdown_read) IMPLEMENT_STATUS_FLAG (bool, saw_shutdown_write) IMPLEMENT_STATUS_FLAG (bool, closed) + IMPLEMENT_STATUS_FLAG (bool, owner) IMPLEMENT_STATUS_FLAG (conn_state, connect_state) int bind (const struct sockaddr *name, int namelen); diff --git a/winsup/cygwin/fhandler_socket.cc b/winsup/cygwin/fhandler_socket.cc index dedbd346b..aee32ac1b 100644 --- a/winsup/cygwin/fhandler_socket.cc +++ b/winsup/cygwin/fhandler_socket.cc @@ -713,15 +713,18 @@ fhandler_socket::prepare (HANDLE &event, long event_mask) } int -fhandler_socket::wait (HANDLE event) +fhandler_socket::wait (HANDLE event, int flags) { int ret = SOCKET_ERROR; int wsa_err = 0; WSAEVENT ev[2] = { event, signal_arrived }; WSANETWORKEVENTS evts; - switch (WSAWaitForMultipleEvents (2, ev, FALSE, WSA_INFINITE, FALSE)) + switch (WSAWaitForMultipleEvents (2, ev, FALSE, 10, FALSE)) { + case WSA_WAIT_TIMEOUT: + ret = 0; + break; case WSA_WAIT_EVENT_0: if (!WSAEnumNetworkEvents (get_socket (), event, &evts)) { @@ -730,6 +733,19 @@ fhandler_socket::wait (HANDLE event) ret = 0; break; } + if (evts.lNetworkEvents & FD_OOB) + { + if (evts.iErrorCode[FD_OOB_BIT]) + wsa_err = evts.iErrorCode[FD_OOB_BIT]; + else if (flags & MSG_OOB) + ret = 0; + else + { + raise (SIGURG); + WSASetLastError (WSAEINTR); + break; + } + } if (evts.lNetworkEvents & FD_READ) { if (evts.iErrorCode[FD_READ_BIT]) @@ -822,7 +838,7 @@ fhandler_socket::recvfrom (void *ptr, size_t len, int flags, else { HANDLE evt; - if (prepare (evt, FD_CLOSE | ((flags & MSG_OOB) ? FD_OOB : FD_READ))) + if (prepare (evt, FD_CLOSE | FD_READ | (owner () ? FD_OOB : 0))) { do { @@ -833,7 +849,7 @@ fhandler_socket::recvfrom (void *ptr, size_t len, int flags, while (res == SOCKET_ERROR && WSAGetLastError () == WSAEWOULDBLOCK && !closed () - && !(res = wait (evt))); + && !(res = wait (evt, flags))); release (evt); } } @@ -947,7 +963,7 @@ fhandler_socket::recvmsg (struct msghdr *msg, int flags, ssize_t tot) else { HANDLE evt; - if (prepare (evt, FD_CLOSE | ((flags & MSG_OOB) ? FD_OOB : FD_READ))) + if (prepare (evt, FD_CLOSE | FD_READ | (owner () ? FD_OOB : 0))) { do { @@ -958,7 +974,7 @@ fhandler_socket::recvmsg (struct msghdr *msg, int flags, ssize_t tot) while (res == SOCKET_ERROR && WSAGetLastError () == WSAEWOULDBLOCK && !closed () - && !(res = wait (evt))); + && !(res = wait (evt, flags))); release (evt); } } @@ -1024,7 +1040,7 @@ fhandler_socket::sendto (const void *ptr, size_t len, int flags, else { HANDLE evt; - if (prepare (evt, FD_CLOSE | FD_WRITE)) + if (prepare (evt, FD_CLOSE | FD_WRITE | (owner () ? FD_OOB : 0))) { do { @@ -1035,7 +1051,7 @@ fhandler_socket::sendto (const void *ptr, size_t len, int flags, } while (res == SOCKET_ERROR && WSAGetLastError () == WSAEWOULDBLOCK - && !(res = wait (evt)) + && !(res = wait (evt, 0)) && !closed ()); release (evt); } @@ -1154,7 +1170,7 @@ fhandler_socket::sendmsg (const struct msghdr *msg, int flags, ssize_t tot) else { HANDLE evt; - if (prepare (evt, FD_CLOSE | FD_WRITE)) + if (prepare (evt, FD_CLOSE | FD_WRITE | (owner () ? FD_OOB : 0))) { do { @@ -1165,7 +1181,7 @@ fhandler_socket::sendmsg (const struct msghdr *msg, int flags, ssize_t tot) } while (res == SOCKET_ERROR && WSAGetLastError () == WSAEWOULDBLOCK - && !(res = wait (evt)) + && !(res = wait (evt, 0)) && !closed ()); release (evt); } @@ -1402,6 +1418,14 @@ fhandler_socket::fcntl (int cmd, void *arg) switch (cmd) { + case F_SETOWN: + { + /* Urgh! Bad hack! */ + pid_t pid = (pid_t) arg; + owner (pid == getpid ()); + debug_printf ("owner set to %d", owner ()); + } + break; case F_SETFL: { /* Carefully test for the O_NONBLOCK or deprecated OLD_O_NDELAY flag. |