* fhandler.h (UNCONNECTED): New define.
(CONNECT_PENDING): Ditto. (CONNECTED): Ditto. (class fhandler_socket): Add member `had_connect_or_listen'. Add member functions `is_unconnected', `is_connect_pending' and `is_connected'. * fhandler_socket.cc (fhandler_socket::connect): Set member `had_connect_or_listen' according to return code of WinSock call. (fhandler_socket::listen): Ditto. * net.cc (cygwin_getsockopt): Modify SO_ERROR return value in case of socket with pending connect(). * select.cc (peek_socket): Only add socket to matching fd_set if it's not "ready". Call WINSOCK_SELECT only if at least one socket is in one of the fd_sets. (start_thread_socket): Only add socket to matching fd_set if it's not "ready". (fhandler_socket::select_write): Set write_ready to true also if socket isn't connected or listening.
This commit is contained in:
parent
89ffbd66e7
commit
d5591d9df6
|
@ -1,3 +1,25 @@
|
||||||
|
2002-07-05 Corinna Vinschen <corinna@vinschen.de>
|
||||||
|
|
||||||
|
* fhandler.h (UNCONNECTED): New define.
|
||||||
|
(CONNECT_PENDING): Ditto.
|
||||||
|
(CONNECTED): Ditto.
|
||||||
|
(class fhandler_socket): Add member `had_connect_or_listen'.
|
||||||
|
Add member functions `is_unconnected', `is_connect_pending' and
|
||||||
|
`is_connected'.
|
||||||
|
* fhandler_socket.cc (fhandler_socket::connect): Set member
|
||||||
|
`had_connect_or_listen' according to return code of WinSock
|
||||||
|
call.
|
||||||
|
(fhandler_socket::listen): Ditto.
|
||||||
|
* net.cc (cygwin_getsockopt): Modify SO_ERROR return value in
|
||||||
|
case of socket with pending connect().
|
||||||
|
* select.cc (peek_socket): Only add socket to matching fd_set
|
||||||
|
if it's not "ready". Call WINSOCK_SELECT only if at least one
|
||||||
|
socket is in one of the fd_sets.
|
||||||
|
(start_thread_socket): Only add socket to matching fd_set
|
||||||
|
if it's not "ready".
|
||||||
|
(fhandler_socket::select_write): Set write_ready to true also
|
||||||
|
if socket isn't connected or listening.
|
||||||
|
|
||||||
2002-07-04 Corinna Vinschen <corinna@vinschen.de>
|
2002-07-04 Corinna Vinschen <corinna@vinschen.de>
|
||||||
|
|
||||||
* fhandler_socket.cc (fhandler_socket::set_sun_path): Don't free
|
* fhandler_socket.cc (fhandler_socket::set_sun_path): Don't free
|
||||||
|
|
|
@ -101,6 +101,10 @@ enum
|
||||||
both flags are set. */
|
both flags are set. */
|
||||||
#define O_NONBLOCK_MASK (O_NONBLOCK | OLD_O_NDELAY)
|
#define O_NONBLOCK_MASK (O_NONBLOCK | OLD_O_NDELAY)
|
||||||
|
|
||||||
|
#define UNCONNECTED 0
|
||||||
|
#define CONNECT_PENDING 1
|
||||||
|
#define CONNECTED 2
|
||||||
|
|
||||||
extern const char *windows_device_names[];
|
extern const char *windows_device_names[];
|
||||||
extern struct __cygwin_perfile *perfile_table;
|
extern struct __cygwin_perfile *perfile_table;
|
||||||
#define __fmode (*(user_data->fmode_ptr))
|
#define __fmode (*(user_data->fmode_ptr))
|
||||||
|
@ -367,6 +371,7 @@ class fhandler_socket: public fhandler_base
|
||||||
HANDLE secret_event;
|
HANDLE secret_event;
|
||||||
struct _WSAPROTOCOL_INFOA *prot_info_ptr;
|
struct _WSAPROTOCOL_INFOA *prot_info_ptr;
|
||||||
char *sun_path;
|
char *sun_path;
|
||||||
|
int had_connect_or_listen;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
fhandler_socket ();
|
fhandler_socket ();
|
||||||
|
@ -380,6 +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_connect_pending () {return had_connect_or_listen == CONNECT_PENDING;}
|
||||||
|
bool is_connected () {return had_connect_or_listen == CONNECTED;}
|
||||||
|
|
||||||
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);
|
||||||
int listen (int backlog);
|
int listen (int backlog);
|
||||||
|
|
|
@ -455,6 +455,10 @@ fhandler_socket::connect (const struct sockaddr *name, int namelen)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!res)
|
||||||
|
had_connect_or_listen = CONNECTED;
|
||||||
|
else if (WSAGetLastError () == WSAEINPROGRESS)
|
||||||
|
had_connect_or_listen = CONNECT_PENDING;
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -464,6 +468,8 @@ fhandler_socket::listen (int backlog)
|
||||||
int res = ::listen (get_socket (), backlog);
|
int res = ::listen (get_socket (), backlog);
|
||||||
if (res)
|
if (res)
|
||||||
set_winsock_errno ();
|
set_winsock_errno ();
|
||||||
|
else
|
||||||
|
had_connect_or_listen = CONNECTED;
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -712,6 +712,8 @@ 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);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1180,25 +1180,30 @@ peek_socket (select_record *me, bool)
|
||||||
set_handle_or_return_if_not_open (h, me);
|
set_handle_or_return_if_not_open (h, me);
|
||||||
select_printf ("considering handle %p", h);
|
select_printf ("considering handle %p", h);
|
||||||
|
|
||||||
if (me->read_selected)
|
if (me->read_selected && !me->read_ready)
|
||||||
{
|
{
|
||||||
select_printf ("adding read fd_set %s, fd %d", me->fh->get_name (),
|
select_printf ("adding read fd_set %s, fd %d", me->fh->get_name (),
|
||||||
me->fd);
|
me->fd);
|
||||||
WINSOCK_FD_SET (h, &ws_readfds);
|
WINSOCK_FD_SET (h, &ws_readfds);
|
||||||
}
|
}
|
||||||
if (me->write_selected)
|
if (me->write_selected && !me->write_ready)
|
||||||
{
|
{
|
||||||
select_printf ("adding write fd_set %s, fd %d", me->fh->get_name (),
|
select_printf ("adding write fd_set %s, fd %d", me->fh->get_name (),
|
||||||
me->fd);
|
me->fd);
|
||||||
WINSOCK_FD_SET (h, &ws_writefds);
|
WINSOCK_FD_SET (h, &ws_writefds);
|
||||||
}
|
}
|
||||||
if (me->except_selected)
|
if (me->except_selected && !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);
|
||||||
WINSOCK_FD_SET (h, &ws_exceptfds);
|
WINSOCK_FD_SET (h, &ws_exceptfds);
|
||||||
}
|
}
|
||||||
int r = WINSOCK_SELECT (0, &ws_readfds, &ws_writefds, &ws_exceptfds, &tv);
|
int r;
|
||||||
|
if ((me->read_selected && !me->read_ready)
|
||||||
|
|| (me->write_selected && !me->write_ready)
|
||||||
|
|| (me->except_selected && !me->except_ready))
|
||||||
|
{
|
||||||
|
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);
|
||||||
if (r == -1)
|
if (r == -1)
|
||||||
{
|
{
|
||||||
|
@ -1206,13 +1211,13 @@ peek_socket (select_record *me, bool)
|
||||||
set_winsock_errno ();
|
set_winsock_errno ();
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (WINSOCK_FD_ISSET (h, &ws_readfds) || (me->read_selected && me->read_ready))
|
if (WINSOCK_FD_ISSET (h, &ws_readfds) || (me->read_selected && me->read_ready))
|
||||||
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_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;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1280,17 +1285,17 @@ start_thread_socket (select_record *me, select_stuff *stuff)
|
||||||
{
|
{
|
||||||
HANDLE h = s->fh->get_handle ();
|
HANDLE h = s->fh->get_handle ();
|
||||||
select_printf ("Handle %p", h);
|
select_printf ("Handle %p", h);
|
||||||
if (s->read_selected)
|
if (s->read_selected && !s->read_ready)
|
||||||
{
|
{
|
||||||
WINSOCK_FD_SET (h, &si->readfds);
|
WINSOCK_FD_SET (h, &si->readfds);
|
||||||
select_printf ("Added to readfds");
|
select_printf ("Added to readfds");
|
||||||
}
|
}
|
||||||
if (s->write_selected)
|
if (s->write_selected && !s->write_ready)
|
||||||
{
|
{
|
||||||
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)
|
if (s->except_selected && !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");
|
||||||
|
@ -1410,7 +1415,7 @@ 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 ();
|
s->write_ready = saw_shutdown_write () || !is_connected ();
|
||||||
s->write_selected = true;
|
s->write_selected = true;
|
||||||
return s;
|
return s;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue