cURL / Mailing Lists / curl-library / Single Mail

curl-library

Re: CURLE_GOT_NOTHING on slow connections

From: Joe Halpin <j.p.h_at_comcast.net>
Date: Fri, 27 Feb 2004 13:18:14 -0600

Joe Halpin wrote:
> Richard Bramante wrote:

>> Curl then calls waitconnect() and select() returns 1, *but* it does
>> not set this socket in the errfd set, so curl assumes that it is
>> connected and waitconnect returns 0.
>
> I don't recall ever using a system in which the errfd set was used for
> this. POSIX, in fact, specifies that for a socket, this set will report
> pending exceptional conditions, not errors. The only exceptional
> condition I know of for TCP sockets is out-of-band data.
>
> Perhaps Windows does this differently, I wouldn't be surprised, but I
> don't think this is a reliable way to detect an error in general.

I'm not as familiar with the socket code in curl as I probably should
be, so take this for what it's worth. Here's a suggestion for a
different way to check whether the socket was connected or not.

Joe

Index: lib/connect.c
===================================================================
RCS file: /repository/curl/lib/connect.c,v
retrieving revision 1.77
diff -u -r1.77 connect.c
--- lib/connect.c 15 Feb 2004 13:55:24 -0000 1.77
+++ lib/connect.c 27 Feb 2004 19:13:31 -0000
@@ -173,9 +173,10 @@
                  int timeout_msec)
  {
    fd_set fd;
- fd_set errfd;
    struct timeval interval;
    int rc;
+ struct sockaddr_in name;
+ socklen_t namelen = sizeof name;
  #ifdef mpeix
    /* Call this function once now, and ignore the results. We do this to
       "clear" the error state on the socket so that we can later read it
@@ -187,15 +188,12 @@
    FD_ZERO(&fd);
    FD_SET(sockfd, &fd);

- FD_ZERO(&errfd);
- FD_SET(sockfd, &errfd);
-
    interval.tv_sec = timeout_msec/1000;
    timeout_msec -= interval.tv_sec*1000;

    interval.tv_usec = timeout_msec*1000;

- rc = select(sockfd+1, NULL, &fd, &errfd, &interval);
+ rc = select(sockfd+1, NULL, &fd, (fd_set*)0, &interval);
    if(-1 == rc)
      /* error, no connect here, try next */
      return -1;
@@ -204,8 +202,10 @@
      /* timeout, no connect today */
      return 1;

- if(FD_ISSET(sockfd, &errfd))
- /* error condition caught */
+ if(-1 == getpeername(sockfd, (struct sockaddr*)&name, &namelen))
+ /* not connected */
+ /* might want to add some kind of debug output to
+ display strerror(errno) here */
      return 2;

    /* we have a connect! */
Received on 2004-02-27