diff --git a/CHANGES b/CHANGES index acd7ed763..c626016e0 100644 --- a/CHANGES +++ b/CHANGES @@ -6,6 +6,19 @@ Changelog +Daniel (21 December 2006) +- Robson Braga Araujo reported bug #1618359 + (http://curl.haxx.se/bug/view.cgi?id=1618359) and subsequently provided a + patch for it: when downloading 2 zero byte files in a row, curl 7.16.0 + enters an infinite loop, while curl 7.16.1-20061218 does one additional + unnecessary request. + + Fix: During the "Major overhaul introducing http pipelining support and + shared connection cache within the multi handle." change, headerbytecount + was moved to live in the Curl_transfer_keeper structure. But that structure + is reset in the Transfer method, losing the information that we had about + the header size. This patch moves it back to the connectdata struct. + Daniel (16 December 2006) - Brendan Jurd provided a fix that now prevents libcurl from getting a SIGPIPE during certain conditions when GnuTLS is used. diff --git a/RELEASE-NOTES b/RELEASE-NOTES index d1823d4b8..251ccf7c1 100644 --- a/RELEASE-NOTES +++ b/RELEASE-NOTES @@ -36,6 +36,7 @@ This release includes the following bugfixes: o getting FTP response code errors when using the multi-interface caused libcurl to leak memory o no more SIGPIPE when GnuTLS is used + o FTP downloading 2 zero byte files in a row Other curl-related news: @@ -54,6 +55,7 @@ advice from friends like these: James Housley, Olaf Stueben, Yang Tse, Gisle Vanem, Bradford Bruce, Ciprian Badescu, Dmitriy Sergeyev, Nir Soffer, Venkat Akella, Toon Verwaest, Matt Witherspoon, Alexey Simak, Martin Skinner, Sh Diao, Jared Lundell, - Stefan Krause, Sebastien Willemijns, Alexey Simak, Brendan Jurd + Stefan Krause, Sebastien Willemijns, Alexey Simak, Brendan Jurd, + Robson Braga Araujo Thanks! (and sorry if I forgot to mention someone) diff --git a/lib/ftp.c b/lib/ftp.c index 7175c99a7..0f19bca58 100644 --- a/lib/ftp.c +++ b/lib/ftp.c @@ -329,7 +329,7 @@ static CURLcode ftp_readresp(curl_socket_t sockfd, * line */ int i; - k->headerbytecount += gotbytes; + conn->headerbytecount += gotbytes; ftpc->nread_resp += gotbytes; for(i = 0; i < gotbytes; ptr++, i++) { @@ -562,7 +562,7 @@ CURLcode Curl_GetFTPResponse(ssize_t *nreadp, /* return number of bytes read */ * line */ int i; - k->headerbytecount += gotbytes; + conn->headerbytecount += gotbytes; *nreadp += gotbytes; for(i = 0; i < gotbytes; ptr++, i++) { diff --git a/lib/http.c b/lib/http.c index 0b537e45e..2f8b98e2e 100644 --- a/lib/http.c +++ b/lib/http.c @@ -1527,8 +1527,8 @@ CURLcode Curl_http_done(struct connectdata *conn, if(!conn->bits.retry && ((http->readbytecount + - k->headerbytecount - - k->deductheadercount)) <= 0) { + conn->headerbytecount - + conn->deductheadercount)) <= 0) { /* If this connection isn't simply closed to be retried, AND nothing was read from the HTTP server (that counts), this can't be right so we return an error here */ diff --git a/lib/transfer.c b/lib/transfer.c index 4a37244f1..5aa1540c8 100644 --- a/lib/transfer.c +++ b/lib/transfer.c @@ -581,10 +581,10 @@ CURLcode Curl_readwrite(struct connectdata *conn, return result; data->info.header_size += (long)headerlen; - k->headerbytecount += (long)headerlen; + conn->headerbytecount += (long)headerlen; - k->deductheadercount = - (100 == k->httpcode)?k->headerbytecount:0; + conn->deductheadercount = + (100 == k->httpcode)?conn->headerbytecount:0; if (data->reqdata.resume_from && (data->set.httpreq==HTTPREQ_GET) && @@ -1040,7 +1040,7 @@ CURLcode Curl_readwrite(struct connectdata *conn, return result; data->info.header_size += (long)k->hbuflen; - k->headerbytecount += (long)k->hbuflen; + conn->headerbytecount += (long)k->hbuflen; /* reset hbufp pointer && hbuflen */ k->hbufp = data->state.headerbuff; @@ -1564,7 +1564,6 @@ CURLcode Curl_readwrite_init(struct connectdata *conn) k->writebytecountp = data->reqdata.writebytecountp; k->bytecount = 0; - k->headerbytecount = 0; k->buf = data->state.buffer; k->uploadbuf = data->state.uploadbuffer; @@ -2247,7 +2246,7 @@ bool Curl_retry_request(struct connectdata *conn, struct SessionHandle *data = conn->data; struct Curl_transfer_keeper *k = &data->reqdata.keep; - if((data->reqdata.keep.bytecount+k->headerbytecount == 0) && + if((data->reqdata.keep.bytecount+conn->headerbytecount == 0) && conn->bits.reuse && !conn->bits.no_body) { /* We got no data, we attempted to re-use a connection and yet we want a diff --git a/lib/url.c b/lib/url.c index 9a3c68d0b..7b87a92c4 100644 --- a/lib/url.c +++ b/lib/url.c @@ -3964,6 +3964,8 @@ static CURLcode SetupConnection(struct connectdata *conn, } } + conn->headerbytecount = 0; + #ifdef CURL_DO_LINEEND_CONV data->state.crlf_conversions = 0; /* reset CRLF conversion counter */ #endif /* CURL_DO_LINEEND_CONV */ diff --git a/lib/urldata.h b/lib/urldata.h index 7f2279e96..5953779ce 100644 --- a/lib/urldata.h +++ b/lib/urldata.h @@ -534,13 +534,6 @@ struct Curl_transfer_keeper { curl_off_t bytecount; /* total number of bytes read */ curl_off_t writebytecount; /* number of bytes written */ - long headerbytecount; /* only count received headers */ - long deductheadercount; /* this amount of bytes doesn't count when we check - if anything has been transfered at the end of - a connection. We use this counter to make only - a 100 reply (without a following second response - code) result in a CURLE_GOT_NOTHING error code */ - struct timeval start; /* transfer started at this time */ struct timeval now; /* current time */ bool header; /* incoming data has HTTP header */ @@ -742,6 +735,13 @@ struct connectdata { unsigned short remote_port; /* what remote port to connect to, not the proxy port! */ + long headerbytecount; /* only count received headers */ + long deductheadercount; /* this amount of bytes doesn't count when we check + if anything has been transfered at the end of + a connection. We use this counter to make only + a 100 reply (without a following second response + code) result in a CURLE_GOT_NOTHING error code */ + char *user; /* user name string, allocated */ char *passwd; /* password string, allocated */