* fhandler.h (fhandler_socket::is_unconnected): Constify.

(fhandler_socket::is_connect_pending): Ditto.
	(fhandler_socket::is_connected): Ditto.
	(fhandler_socket::set_connect_state): New method.
	(struct select_record): Add member `except_on_write'.
	(select_record::select_record): Initialize all bool values to `false'.
	* fhandler_socket.cc: Use set_connect_state() method throughout.
	(fhandler_socket::connect): Set state always to connected if connection
	isn't pending.
	* net.cc (cygwin_getsockopt): Revert erroneous previous patch.
	* select.cc (set_bits): Check for `except_on_write'.  Set fd in
	write_fds if set.  Set connect state to connected if fd has been
	returned by WINSOCK_SELECT.
	(peek_socket): Check for `except_on_write'.
	(start_thread_socket): Ditto.
	(fhandler_socket::select_write): Don't set `write_ready' if connect
	is pending.  Set `except_on_write' if connect is pending.
This commit is contained in:
Corinna Vinschen 2002-07-06 11:16:07 +00:00
parent 6201dd26a6
commit 6bb769efa0
5 changed files with 55 additions and 20 deletions

View File

@ -1,3 +1,23 @@
2002-07-05 Corinna Vinschen <corinna@vinschen.de>
* fhandler.h (fhandler_socket::is_unconnected): Constify.
(fhandler_socket::is_connect_pending): Ditto.
(fhandler_socket::is_connected): Ditto.
(fhandler_socket::set_connect_state): New method.
(struct select_record): Add member `except_on_write'.
(select_record::select_record): Initialize all bool values to `false'.
* fhandler_socket.cc: Use set_connect_state() method throughout.
(fhandler_socket::connect): Set state always to connected if connection
isn't pending.
* net.cc (cygwin_getsockopt): Revert erroneous previous patch.
* select.cc (set_bits): Check for `except_on_write'. Set fd in
write_fds if set. Set connect state to connected if fd has been
returned by WINSOCK_SELECT.
(peek_socket): Check for `except_on_write'.
(start_thread_socket): Ditto.
(fhandler_socket::select_write): Don't set `write_ready' if connect
is pending. Set `except_on_write' if connect is pending.
2002-07-05 Christopher Faylor <cgf@redhat.com> 2002-07-05 Christopher Faylor <cgf@redhat.com>
* ntdll.h (_SYSTEM_PROCESSOR_TIMES): Force eight byte alignment. * ntdll.h (_SYSTEM_PROCESSOR_TIMES): Force eight byte alignment.

View File

@ -385,9 +385,10 @@ class fhandler_socket: public fhandler_base
void set_shutdown_read () {FHSETF (SHUTRD);} void set_shutdown_read () {FHSETF (SHUTRD);}
void set_shutdown_write () {FHSETF (SHUTWR);} void set_shutdown_write () {FHSETF (SHUTWR);}
bool is_unconnected () {return had_connect_or_listen == UNCONNECTED;} bool is_unconnected () const {return had_connect_or_listen == UNCONNECTED;}
bool is_connect_pending () {return had_connect_or_listen == CONNECT_PENDING;} bool is_connect_pending () const {return had_connect_or_listen == CONNECT_PENDING;}
bool is_connected () {return had_connect_or_listen == CONNECTED;} bool is_connected () const {return had_connect_or_listen == CONNECTED;}
void set_connect_state (int newstate) { had_connect_or_listen = newstate; }
int bind (const struct sockaddr *name, int namelen); int bind (const struct sockaddr *name, int namelen);
int connect (const struct sockaddr *name, int namelen); int connect (const struct sockaddr *name, int namelen);
@ -1185,6 +1186,7 @@ struct select_record
bool windows_handle; bool windows_handle;
bool read_ready, write_ready, except_ready; bool read_ready, write_ready, except_ready;
bool read_selected, write_selected, except_selected; bool read_selected, write_selected, except_selected;
bool except_on_write;
int (*startup) (select_record *me, class select_stuff *stuff); int (*startup) (select_record *me, class select_stuff *stuff);
int (*peek) (select_record *, bool); int (*peek) (select_record *, bool);
int (*verify) (select_record *me, fd_set *readfds, fd_set *writefds, int (*verify) (select_record *me, fd_set *readfds, fd_set *writefds,
@ -1193,9 +1195,10 @@ struct select_record
struct select_record *next; struct select_record *next;
select_record (fhandler_base *in_fh = NULL) : fd (0), h (NULL), select_record (fhandler_base *in_fh = NULL) : fd (0), h (NULL),
fh (in_fh), saw_error (0), windows_handle (0), fh (in_fh), saw_error (false), windows_handle (false),
read_ready (0), write_ready (0), except_ready (0), read_ready (false), write_ready (false), except_ready (false),
read_selected (0), write_selected (0), except_selected (0), read_selected (false), write_selected (false),
except_selected (false), except_on_write (false),
startup (NULL), peek (NULL), verify (NULL), cleanup (NULL), startup (NULL), peek (NULL), verify (NULL), cleanup (NULL),
next (NULL) {} next (NULL) {}
}; };

View File

@ -455,10 +455,10 @@ fhandler_socket::connect (const struct sockaddr *name, int namelen)
} }
} }
if (!res) if (WSAGetLastError () == WSAEINPROGRESS)
had_connect_or_listen = CONNECTED; set_connect_state (CONNECT_PENDING);
else if (WSAGetLastError () == WSAEINPROGRESS) else
had_connect_or_listen = CONNECT_PENDING; set_connect_state (CONNECTED);
return res; return res;
} }
@ -469,7 +469,7 @@ fhandler_socket::listen (int backlog)
if (res) if (res)
set_winsock_errno (); set_winsock_errno ();
else else
had_connect_or_listen = CONNECTED; set_connect_state (CONNECTED);
return res; return res;
} }

View File

@ -712,8 +712,6 @@ cygwin_getsockopt (int fd, int level, int optname, void *optval, int *optlen)
if (optname == SO_ERROR) if (optname == SO_ERROR)
{ {
int *e = (int *) optval; int *e = (int *) optval;
if (!*e && fh->is_connect_pending ())
*e = WSAEINPROGRESS;
*e = find_winsock_errno (*e); *e = find_winsock_errno (*e);
} }

View File

@ -336,11 +336,20 @@ set_bits (select_record *me, fd_set *readfds, fd_set *writefds,
if (me->write_selected && me->write_ready) if (me->write_selected && me->write_ready)
{ {
UNIX_FD_SET (me->fd, writefds); UNIX_FD_SET (me->fd, writefds);
if (me->except_on_write && me->fh->get_device () == FH_SOCKET)
((fhandler_socket *) me->fh)->set_connect_state (CONNECTED);
ready++; ready++;
} }
if (me->except_selected && me->except_ready) if ((me->except_selected || me->except_on_write) && me->except_ready)
{ {
UNIX_FD_SET (me->fd, exceptfds); if (me->except_on_write) /* Only on sockets */
{
UNIX_FD_SET (me->fd, writefds);
if (me->fh->get_device () == FH_SOCKET)
((fhandler_socket *) me->fh)->set_connect_state (CONNECTED);
}
if (me->except_selected)
UNIX_FD_SET (me->fd, exceptfds);
ready++; ready++;
} }
select_printf ("ready %d", ready); select_printf ("ready %d", ready);
@ -1192,7 +1201,7 @@ peek_socket (select_record *me, bool)
me->fd); me->fd);
WINSOCK_FD_SET (h, &ws_writefds); WINSOCK_FD_SET (h, &ws_writefds);
} }
if (me->except_selected && !me->except_ready) if ((me->except_selected || me->except_on_write) && !me->except_ready)
{ {
select_printf ("adding except fd_set %s, fd %d", me->fh->get_name (), select_printf ("adding except fd_set %s, fd %d", me->fh->get_name (),
me->fd); me->fd);
@ -1201,7 +1210,7 @@ peek_socket (select_record *me, bool)
int r; int r;
if ((me->read_selected && !me->read_ready) if ((me->read_selected && !me->read_ready)
|| (me->write_selected && !me->write_ready) || (me->write_selected && !me->write_ready)
|| (me->except_selected && !me->except_ready)) || ((me->except_selected || me->except_on_write) && !me->except_ready))
{ {
r = WINSOCK_SELECT (0, &ws_readfds, &ws_writefds, &ws_exceptfds, &tv); r = WINSOCK_SELECT (0, &ws_readfds, &ws_writefds, &ws_exceptfds, &tv);
select_printf ("WINSOCK_SELECT returned %d", r); select_printf ("WINSOCK_SELECT returned %d", r);
@ -1215,7 +1224,7 @@ peek_socket (select_record *me, bool)
me->read_ready = true; me->read_ready = true;
if (WINSOCK_FD_ISSET (h, &ws_writefds) || (me->write_selected && me->write_ready)) if (WINSOCK_FD_ISSET (h, &ws_writefds) || (me->write_selected && me->write_ready))
me->write_ready = true; me->write_ready = true;
if (WINSOCK_FD_ISSET (h, &ws_exceptfds) || (me->except_selected && me->except_ready)) if (WINSOCK_FD_ISSET (h, &ws_exceptfds) || ((me->except_selected || me->except_on_write) && me->except_ready))
me->except_ready = true; me->except_ready = true;
} }
return me->read_ready || me->write_ready || me->except_ready; return me->read_ready || me->write_ready || me->except_ready;
@ -1295,7 +1304,7 @@ start_thread_socket (select_record *me, select_stuff *stuff)
WINSOCK_FD_SET (h, &si->writefds); WINSOCK_FD_SET (h, &si->writefds);
select_printf ("Added to writefds"); select_printf ("Added to writefds");
} }
if (s->except_selected && !s->except_ready) if ((s->except_selected || s->except_on_write) && !s->except_ready)
{ {
WINSOCK_FD_SET (h, &si->exceptfds); WINSOCK_FD_SET (h, &si->exceptfds);
select_printf ("Added to exceptfds"); select_printf ("Added to exceptfds");
@ -1415,8 +1424,13 @@ fhandler_socket::select_write (select_record *s)
s->cleanup = socket_cleanup; s->cleanup = socket_cleanup;
} }
s->peek = peek_socket; s->peek = peek_socket;
s->write_ready = saw_shutdown_write () || !is_connected (); s->write_ready = saw_shutdown_write () || is_unconnected ();
s->write_selected = true; s->write_selected = true;
if (is_connect_pending ())
{
s->except_ready = saw_shutdown_write () || saw_shutdown_read ();
s->except_on_write = true;
}
return s; return s;
} }