Rearranged code and changed Curl_readwrite_init() and Curl_pre_readwrite() into
do_init() and do_complete() which now are called first and last in the DO function. It simplified the flow in multi.c and the functions got more sensible names!
This commit is contained in:
		| @@ -378,7 +378,6 @@ static CURLcode Curl_file(struct connectdata *conn, bool *done) | |||||||
|  |  | ||||||
|   *done = TRUE; /* unconditionally */ |   *done = TRUE; /* unconditionally */ | ||||||
|  |  | ||||||
|   Curl_readwrite_init(conn); |  | ||||||
|   Curl_initinfo(data); |   Curl_initinfo(data); | ||||||
|   Curl_pgrsStartNow(data); |   Curl_pgrsStartNow(data); | ||||||
|  |  | ||||||
|   | |||||||
| @@ -178,7 +178,7 @@ CHUNKcode Curl_httpchunk_read(struct connectdata *conn, | |||||||
|       if(*datap == 0x0a) { |       if(*datap == 0x0a) { | ||||||
|         /* we're now expecting data to come, unless size was zero! */ |         /* we're now expecting data to come, unless size was zero! */ | ||||||
|         if(0 == ch->datasize) { |         if(0 == ch->datasize) { | ||||||
|           if(conn->bits.trailerHdrPresent!=TRUE) { |           if(conn->bits.trailerhdrpresent!=TRUE) { | ||||||
|             /* No Trailer: header found - revert to original Curl processing */ |             /* No Trailer: header found - revert to original Curl processing */ | ||||||
|             ch->state = CHUNK_STOPCR; |             ch->state = CHUNK_STOPCR; | ||||||
|  |  | ||||||
|   | |||||||
							
								
								
									
										12
									
								
								lib/multi.c
									
									
									
									
									
								
							
							
						
						
									
										12
									
								
								lib/multi.c
									
									
									
									
									
								
							| @@ -1121,13 +1121,10 @@ static CURLMcode multi_runsingle(struct Curl_multi *multi, | |||||||
|           } |           } | ||||||
|           else { |           else { | ||||||
|             /* we're done with the DO, now DO_DONE */ |             /* we're done with the DO, now DO_DONE */ | ||||||
|             easy->result = Curl_readwrite_init(easy->easy_conn); |  | ||||||
|             if(CURLE_OK == easy->result) { |  | ||||||
|             multistate(easy, CURLM_STATE_DO_DONE); |             multistate(easy, CURLM_STATE_DO_DONE); | ||||||
|             result = CURLM_CALL_MULTI_PERFORM; |             result = CURLM_CALL_MULTI_PERFORM; | ||||||
|           } |           } | ||||||
|         } |         } | ||||||
|         } |  | ||||||
|         else { |         else { | ||||||
|           /* failure detected */ |           /* failure detected */ | ||||||
|           Curl_posttransfer(easy->easy_handle); |           Curl_posttransfer(easy->easy_handle); | ||||||
| @@ -1152,12 +1149,9 @@ static CURLMcode multi_runsingle(struct Curl_multi *multi, | |||||||
|           } |           } | ||||||
|           else { |           else { | ||||||
|             /* we're done with the DO, now DO_DONE */ |             /* we're done with the DO, now DO_DONE */ | ||||||
|             easy->result = Curl_readwrite_init(easy->easy_conn); |  | ||||||
|             if(CURLE_OK == easy->result) { |  | ||||||
|             multistate(easy, CURLM_STATE_DO_DONE); |             multistate(easy, CURLM_STATE_DO_DONE); | ||||||
|             result = CURLM_CALL_MULTI_PERFORM; |             result = CURLM_CALL_MULTI_PERFORM; | ||||||
|           } |           } | ||||||
|           } |  | ||||||
|         } /* dophase_done */ |         } /* dophase_done */ | ||||||
|       } |       } | ||||||
|       else { |       else { | ||||||
| @@ -1179,9 +1173,6 @@ static CURLMcode multi_runsingle(struct Curl_multi *multi, | |||||||
|          */ |          */ | ||||||
|         easy->result = Curl_do_more(easy->easy_conn); |         easy->result = Curl_do_more(easy->easy_conn); | ||||||
|  |  | ||||||
|         if(CURLE_OK == easy->result) |  | ||||||
|           easy->result = Curl_readwrite_init(easy->easy_conn); |  | ||||||
|  |  | ||||||
|         /* No need to remove ourselves from the send pipeline here since that |         /* No need to remove ourselves from the send pipeline here since that | ||||||
|            is done for us in Curl_done() */ |            is done for us in Curl_done() */ | ||||||
|  |  | ||||||
| @@ -1207,9 +1198,6 @@ static CURLMcode multi_runsingle(struct Curl_multi *multi, | |||||||
|                                               easy->easy_conn->recv_pipe); |                                               easy->easy_conn->recv_pipe); | ||||||
|       multistate(easy, CURLM_STATE_WAITPERFORM); |       multistate(easy, CURLM_STATE_WAITPERFORM); | ||||||
|       result = CURLM_CALL_MULTI_PERFORM; |       result = CURLM_CALL_MULTI_PERFORM; | ||||||
|  |  | ||||||
|       Curl_pre_readwrite(easy->easy_conn); |  | ||||||
|  |  | ||||||
|       break; |       break; | ||||||
|  |  | ||||||
|     case CURLM_STATE_WAITPERFORM: |     case CURLM_STATE_WAITPERFORM: | ||||||
|   | |||||||
| @@ -725,10 +725,6 @@ static CURLcode Curl_tftp(struct connectdata *conn, bool *done) | |||||||
|   } |   } | ||||||
|   state = (tftp_state_data_t *)data->reqdata.proto.tftp; |   state = (tftp_state_data_t *)data->reqdata.proto.tftp; | ||||||
|  |  | ||||||
|   code = Curl_readwrite_init(conn); |  | ||||||
|   if(code) |  | ||||||
|     return code; |  | ||||||
|  |  | ||||||
|   /* Run the TFTP State Machine */ |   /* Run the TFTP State Machine */ | ||||||
|   for(code=tftp_state_machine(state, TFTP_EVENT_INIT); |   for(code=tftp_state_machine(state, TFTP_EVENT_INIT); | ||||||
|       (state->state != TFTP_STATE_FIN) && (code == CURLE_OK); |       (state->state != TFTP_STATE_FIN) && (code == CURLE_OK); | ||||||
|   | |||||||
							
								
								
									
										171
									
								
								lib/transfer.c
									
									
									
									
									
								
							
							
						
						
									
										171
									
								
								lib/transfer.c
									
									
									
									
									
								
							| @@ -992,7 +992,7 @@ CURLcode Curl_readwrite(struct connectdata *conn, | |||||||
|                * |                * | ||||||
|                * It seems both Trailer: and Trailers: occur in the wild. |                * It seems both Trailer: and Trailers: occur in the wild. | ||||||
|                */ |                */ | ||||||
|               conn->bits.trailerHdrPresent = TRUE; |               conn->bits.trailerhdrpresent = TRUE; | ||||||
|             } |             } | ||||||
|  |  | ||||||
|             else if(checkprefix("Content-Encoding:", k->p) && |             else if(checkprefix("Content-Encoding:", k->p) && | ||||||
| @@ -1640,102 +1640,6 @@ CURLcode Curl_readwrite(struct connectdata *conn, | |||||||
|   return CURLE_OK; |   return CURLE_OK; | ||||||
| } | } | ||||||
|  |  | ||||||
|  |  | ||||||
| /* |  | ||||||
|  * Curl_readwrite_init() inits the readwrite session. This is inited each time |  | ||||||
|  * for a transfer, sometimes multiple times on the same SessionHandle |  | ||||||
|  */ |  | ||||||
|  |  | ||||||
| CURLcode Curl_readwrite_init(struct connectdata *conn) |  | ||||||
| { |  | ||||||
|   struct SessionHandle *data = conn->data; |  | ||||||
|   struct Curl_transfer_keeper *k = &data->reqdata.keep; |  | ||||||
|  |  | ||||||
|   /* NB: the content encoding software depends on this initialization of |  | ||||||
|      Curl_transfer_keeper.*/ |  | ||||||
|   memset(k, 0, sizeof(struct Curl_transfer_keeper)); |  | ||||||
|  |  | ||||||
|   k->start = Curl_tvnow(); /* start time */ |  | ||||||
|   k->now = k->start;   /* current time is now */ |  | ||||||
|   k->header = TRUE; /* assume header */ |  | ||||||
|   k->httpversion = -1; /* unknown at this point */ |  | ||||||
|  |  | ||||||
|   k->size = data->reqdata.size; |  | ||||||
|   k->maxdownload = data->reqdata.maxdownload; |  | ||||||
|   k->bytecountp = data->reqdata.bytecountp; |  | ||||||
|   k->writebytecountp = data->reqdata.writebytecountp; |  | ||||||
|  |  | ||||||
|   k->bytecount = 0; |  | ||||||
|  |  | ||||||
|   k->buf = data->state.buffer; |  | ||||||
|   k->uploadbuf = data->state.uploadbuffer; |  | ||||||
|   k->maxfd = (conn->sockfd>conn->writesockfd? |  | ||||||
|               conn->sockfd:conn->writesockfd)+1; |  | ||||||
|   k->hbufp = data->state.headerbuff; |  | ||||||
|   k->ignorebody=FALSE; |  | ||||||
|  |  | ||||||
|   Curl_pgrsTime(data, TIMER_PRETRANSFER); |  | ||||||
|   Curl_speedinit(data); |  | ||||||
|  |  | ||||||
|   Curl_pgrsSetUploadCounter(data, 0); |  | ||||||
|   Curl_pgrsSetDownloadCounter(data, 0); |  | ||||||
|  |  | ||||||
|   if(!conn->bits.getheader) { |  | ||||||
|     k->header = FALSE; |  | ||||||
|     if(k->size > 0) |  | ||||||
|       Curl_pgrsSetDownloadSize(data, k->size); |  | ||||||
|   } |  | ||||||
|   /* we want header and/or body, if neither then don't do this! */ |  | ||||||
|   if(conn->bits.getheader || !conn->bits.no_body) { |  | ||||||
|  |  | ||||||
|     if(conn->sockfd != CURL_SOCKET_BAD) { |  | ||||||
|       k->keepon |= KEEP_READ; |  | ||||||
|     } |  | ||||||
|  |  | ||||||
|     if(conn->writesockfd != CURL_SOCKET_BAD) { |  | ||||||
|       /* HTTP 1.1 magic: |  | ||||||
|  |  | ||||||
|          Even if we require a 100-return code before uploading data, we might |  | ||||||
|          need to write data before that since the REQUEST may not have been |  | ||||||
|          finished sent off just yet. |  | ||||||
|  |  | ||||||
|          Thus, we must check if the request has been sent before we set the |  | ||||||
|          state info where we wait for the 100-return code |  | ||||||
|       */ |  | ||||||
|       if(data->state.expect100header && |  | ||||||
|           (data->reqdata.proto.http->sending == HTTPSEND_BODY)) { |  | ||||||
|         /* wait with write until we either got 100-continue or a timeout */ |  | ||||||
|         k->write_after_100_header = TRUE; |  | ||||||
|         k->start100 = k->start; |  | ||||||
|       } |  | ||||||
|       else { |  | ||||||
|         if(data->state.expect100header) |  | ||||||
|           /* when we've sent off the rest of the headers, we must await a |  | ||||||
|              100-continue */ |  | ||||||
|           k->wait100_after_headers = TRUE; |  | ||||||
|         k->keepon |= KEEP_WRITE; |  | ||||||
|       } |  | ||||||
|     } |  | ||||||
|   } |  | ||||||
|  |  | ||||||
|   return CURLE_OK; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| /* |  | ||||||
|  * Curl_readwrite may get called multiple times.  This function is called |  | ||||||
|  * immediately before the first Curl_readwrite.  Note that this can't be moved |  | ||||||
|  * to Curl_readwrite_init since that function can get called while another |  | ||||||
|  * pipeline request is in the middle of receiving data. |  | ||||||
|  * |  | ||||||
|  * We init chunking and trailer bits to their default values here immediately |  | ||||||
|  * before receiving any header data for the current request in the pipeline. |  | ||||||
|  */ |  | ||||||
| void Curl_pre_readwrite(struct connectdata *conn) |  | ||||||
| { |  | ||||||
|   conn->bits.chunk=FALSE; |  | ||||||
|   conn->bits.trailerHdrPresent=FALSE; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| /* | /* | ||||||
|  * Curl_single_getsock() gets called by the multi interface code when the app |  * Curl_single_getsock() gets called by the multi interface code when the app | ||||||
|  * has requested to get the sockets for the current connection. This function |  * has requested to get the sockets for the current connection. This function | ||||||
| @@ -1757,6 +1661,9 @@ int Curl_single_getsock(const struct connectdata *conn, | |||||||
|     return GETSOCK_BLANK; |     return GETSOCK_BLANK; | ||||||
|  |  | ||||||
|   if(data->reqdata.keep.keepon & KEEP_READ) { |   if(data->reqdata.keep.keepon & KEEP_READ) { | ||||||
|  |  | ||||||
|  |     DEBUGASSERT(conn->sockfd != CURL_SOCKET_BAD); | ||||||
|  |  | ||||||
|     bitmap |= GETSOCK_READSOCK(sockindex); |     bitmap |= GETSOCK_READSOCK(sockindex); | ||||||
|     sock[sockindex] = conn->sockfd; |     sock[sockindex] = conn->sockfd; | ||||||
|   } |   } | ||||||
| @@ -1769,6 +1676,9 @@ int Curl_single_getsock(const struct connectdata *conn, | |||||||
|          one, we increase index */ |          one, we increase index */ | ||||||
|       if(data->reqdata.keep.keepon & KEEP_READ) |       if(data->reqdata.keep.keepon & KEEP_READ) | ||||||
|         sockindex++; /* increase index if we need two entries */ |         sockindex++; /* increase index if we need two entries */ | ||||||
|  |  | ||||||
|  |       DEBUGASSERT(conn->writesockfd != CURL_SOCKET_BAD); | ||||||
|  |  | ||||||
|       sock[sockindex] = conn->writesockfd; |       sock[sockindex] = conn->writesockfd; | ||||||
|     } |     } | ||||||
|  |  | ||||||
| @@ -1810,15 +1720,6 @@ Transfer(struct connectdata *conn) | |||||||
|   if(!conn->bits.getheader && conn->bits.no_body) |   if(!conn->bits.getheader && conn->bits.no_body) | ||||||
|     return CURLE_OK; |     return CURLE_OK; | ||||||
|  |  | ||||||
|   if(!(conn->protocol & (PROT_FILE|PROT_TFTP))) { |  | ||||||
|     /* Only do this if we are not transferring FILE or TFTP, since those |  | ||||||
|        transfers are treated differently. They do their entire transfers in |  | ||||||
|        the DO function and just returns from this. That is ugly indeed. |  | ||||||
|     */ |  | ||||||
|     Curl_readwrite_init(conn); |  | ||||||
|     Curl_pre_readwrite(conn); |  | ||||||
|   } |  | ||||||
|  |  | ||||||
|   while(!done) { |   while(!done) { | ||||||
|     curl_socket_t fd_read; |     curl_socket_t fd_read; | ||||||
|     curl_socket_t fd_write; |     curl_socket_t fd_write; | ||||||
| @@ -2523,25 +2424,23 @@ CURLcode Curl_perform(struct SessionHandle *data) | |||||||
|  */ |  */ | ||||||
| CURLcode | CURLcode | ||||||
| Curl_setup_transfer( | Curl_setup_transfer( | ||||||
|     struct connectdata *c_conn, /* connection data */ |   struct connectdata *conn, /* connection data */ | ||||||
|   int sockindex,            /* socket index to read from or -1 */ |   int sockindex,            /* socket index to read from or -1 */ | ||||||
|   curl_off_t size,          /* -1 if unknown at this point */ |   curl_off_t size,          /* -1 if unknown at this point */ | ||||||
|   bool getheader,           /* TRUE if header parsing is wanted */ |   bool getheader,           /* TRUE if header parsing is wanted */ | ||||||
|   curl_off_t *bytecountp,   /* return number of bytes read or NULL */ |   curl_off_t *bytecountp,   /* return number of bytes read or NULL */ | ||||||
|     int writesockindex,  /* socket index to write to, it may very |   int writesockindex,       /* socket index to write to, it may very well be | ||||||
|                             well be the same we read from. -1 |                                the same we read from. -1 disables */ | ||||||
|                             disables */ |   curl_off_t *writecountp   /* return number of bytes written or NULL */ | ||||||
|     curl_off_t *writecountp /* return number of bytes written or |  | ||||||
|                                NULL */ |  | ||||||
|   ) |   ) | ||||||
| { | { | ||||||
|   struct connectdata *conn = (struct connectdata *)c_conn; |  | ||||||
|   struct SessionHandle *data; |   struct SessionHandle *data; | ||||||
|  |   struct Curl_transfer_keeper *k; | ||||||
|  |  | ||||||
|   if(!conn) |   DEBUGASSERT(conn != NULL); | ||||||
|     return CURLE_BAD_FUNCTION_ARGUMENT; |  | ||||||
|  |  | ||||||
|   data = conn->data; |   data = conn->data; | ||||||
|  |   k = &data->reqdata.keep; | ||||||
|  |  | ||||||
|   DEBUGASSERT((sockindex <= 1) && (sockindex >= -1)); |   DEBUGASSERT((sockindex <= 1) && (sockindex >= -1)); | ||||||
|  |  | ||||||
| @@ -2556,5 +2455,47 @@ Curl_setup_transfer( | |||||||
|   data->reqdata.bytecountp = bytecountp; |   data->reqdata.bytecountp = bytecountp; | ||||||
|   data->reqdata.writebytecountp = writecountp; |   data->reqdata.writebytecountp = writecountp; | ||||||
|  |  | ||||||
|  |   /* The code sequence below is placed in this function just because all | ||||||
|  |      necessary input is not always known in do_complete() as this function may | ||||||
|  |      be called after that */ | ||||||
|  |  | ||||||
|  |   if(!conn->bits.getheader) { | ||||||
|  |     k->header = FALSE; | ||||||
|  |     if(k->size > 0) | ||||||
|  |       Curl_pgrsSetDownloadSize(data, k->size); | ||||||
|  |   } | ||||||
|  |   /* we want header and/or body, if neither then don't do this! */ | ||||||
|  |   if(conn->bits.getheader || !conn->bits.no_body) { | ||||||
|  |  | ||||||
|  |     if(conn->sockfd != CURL_SOCKET_BAD) { | ||||||
|  |       k->keepon |= KEEP_READ; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     if(conn->writesockfd != CURL_SOCKET_BAD) { | ||||||
|  |       /* HTTP 1.1 magic: | ||||||
|  |  | ||||||
|  |          Even if we require a 100-return code before uploading data, we might | ||||||
|  |          need to write data before that since the REQUEST may not have been | ||||||
|  |          finished sent off just yet. | ||||||
|  |  | ||||||
|  |          Thus, we must check if the request has been sent before we set the | ||||||
|  |          state info where we wait for the 100-return code | ||||||
|  |       */ | ||||||
|  |       if(data->state.expect100header && | ||||||
|  |           (data->reqdata.proto.http->sending == HTTPSEND_BODY)) { | ||||||
|  |         /* wait with write until we either got 100-continue or a timeout */ | ||||||
|  |         k->write_after_100_header = TRUE; | ||||||
|  |         k->start100 = k->start; | ||||||
|  |       } | ||||||
|  |       else { | ||||||
|  |         if(data->state.expect100header) | ||||||
|  |           /* when we've sent off the rest of the headers, we must await a | ||||||
|  |              100-continue */ | ||||||
|  |           k->wait100_after_headers = TRUE; | ||||||
|  |         k->keepon |= KEEP_WRITE; | ||||||
|  |       } | ||||||
|  |     } | ||||||
|  |   } | ||||||
|  |  | ||||||
|   return CURLE_OK; |   return CURLE_OK; | ||||||
| } | } | ||||||
|   | |||||||
| @@ -31,8 +31,6 @@ CURLcode Curl_readwrite(struct connectdata *conn, bool *done); | |||||||
| int Curl_single_getsock(const struct connectdata *conn, | int Curl_single_getsock(const struct connectdata *conn, | ||||||
|                         curl_socket_t *socks, |                         curl_socket_t *socks, | ||||||
|                         int numsocks); |                         int numsocks); | ||||||
| CURLcode Curl_readwrite_init(struct connectdata *conn); |  | ||||||
| void Curl_pre_readwrite(struct connectdata *conn); |  | ||||||
| CURLcode Curl_readrewind(struct connectdata *conn); | CURLcode Curl_readrewind(struct connectdata *conn); | ||||||
| CURLcode Curl_fillreadbuffer(struct connectdata *conn, int bytes, int *nreadp); | CURLcode Curl_fillreadbuffer(struct connectdata *conn, int bytes, int *nreadp); | ||||||
| bool Curl_retry_request(struct connectdata *conn, char **url); | bool Curl_retry_request(struct connectdata *conn, char **url); | ||||||
|   | |||||||
							
								
								
									
										75
									
								
								lib/url.c
									
									
									
									
									
								
							
							
						
						
									
										75
									
								
								lib/url.c
									
									
									
									
									
								
							| @@ -121,6 +121,7 @@ void idn_free (void *ptr); /* prototype from idn-free.h, not provided by | |||||||
| #include "select.h" | #include "select.h" | ||||||
| #include "multiif.h" | #include "multiif.h" | ||||||
| #include "easyif.h" | #include "easyif.h" | ||||||
|  | #include "speedcheck.h" | ||||||
|  |  | ||||||
| /* And now for the protocols */ | /* And now for the protocols */ | ||||||
| #include "ftp.h" | #include "ftp.h" | ||||||
| @@ -164,6 +165,8 @@ static void conn_free(struct connectdata *conn); | |||||||
| static void signalPipeClose(struct curl_llist *pipeline); | static void signalPipeClose(struct curl_llist *pipeline); | ||||||
|  |  | ||||||
| static struct SessionHandle* gethandleathead(struct curl_llist *pipeline); | static struct SessionHandle* gethandleathead(struct curl_llist *pipeline); | ||||||
|  | static CURLcode do_init(struct connectdata *conn); | ||||||
|  | static void do_complete(struct connectdata *conn); | ||||||
|  |  | ||||||
| #if !defined(CURL_DISABLE_HTTP) && !defined(CURL_DISABLE_COOKIES) | #if !defined(CURL_DISABLE_HTTP) && !defined(CURL_DISABLE_COOKIES) | ||||||
| static void flush_cookies(struct SessionHandle *data, int cleanup); | static void flush_cookies(struct SessionHandle *data, int cleanup); | ||||||
| @@ -4449,21 +4452,83 @@ CURLcode Curl_done(struct connectdata **connp, | |||||||
|   return result; |   return result; | ||||||
| } | } | ||||||
|  |  | ||||||
|  | /* | ||||||
|  |  * do_init() inits the readwrite session. This is inited each time (in the DO | ||||||
|  |  * function before the protocol-specific DO functions are invoked) for a | ||||||
|  |  * transfer, sometimes multiple times on the same SessionHandle. Make sure | ||||||
|  |  * nothing in here depends on stuff that are setup dynamicly for the transfer. | ||||||
|  |  */ | ||||||
|  |  | ||||||
|  | static CURLcode do_init(struct connectdata *conn) | ||||||
|  | { | ||||||
|  |   struct SessionHandle *data = conn->data; | ||||||
|  |   struct Curl_transfer_keeper *k = &data->reqdata.keep; | ||||||
|  |  | ||||||
|  |   conn->bits.done = FALSE; /* Curl_done() is not called yet */ | ||||||
|  |   conn->bits.do_more = FALSE; /* by default there's no curl_do_more() to use */ | ||||||
|  |  | ||||||
|  |   /* NB: the content encoding software depends on this initialization of | ||||||
|  |      Curl_transfer_keeper.*/ | ||||||
|  |   memset(k, 0, sizeof(struct Curl_transfer_keeper)); | ||||||
|  |  | ||||||
|  |   k->start = Curl_tvnow(); /* start time */ | ||||||
|  |   k->now = k->start;   /* current time is now */ | ||||||
|  |   k->header = TRUE; /* assume header */ | ||||||
|  |   k->httpversion = -1; /* unknown at this point */ | ||||||
|  |  | ||||||
|  |   k->bytecount = 0; | ||||||
|  |  | ||||||
|  |   k->buf = data->state.buffer; | ||||||
|  |   k->uploadbuf = data->state.uploadbuffer; | ||||||
|  |   k->hbufp = data->state.headerbuff; | ||||||
|  |   k->ignorebody=FALSE; | ||||||
|  |  | ||||||
|  |   Curl_pgrsTime(data, TIMER_PRETRANSFER); | ||||||
|  |   Curl_speedinit(data); | ||||||
|  |  | ||||||
|  |   Curl_pgrsSetUploadCounter(data, 0); | ||||||
|  |   Curl_pgrsSetDownloadCounter(data, 0); | ||||||
|  |  | ||||||
|  |   return CURLE_OK; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | /* | ||||||
|  |  * do_complete is called when the DO actions are complete. | ||||||
|  |  * | ||||||
|  |  * We init chunking and trailer bits to their default values here immediately | ||||||
|  |  * before receiving any header data for the current request in the pipeline. | ||||||
|  |  */ | ||||||
|  | static void do_complete(struct connectdata *conn) | ||||||
|  | { | ||||||
|  |   struct SessionHandle *data = conn->data; | ||||||
|  |   struct Curl_transfer_keeper *k = &data->reqdata.keep; | ||||||
|  |   conn->bits.chunk=FALSE; | ||||||
|  |   conn->bits.trailerhdrpresent=FALSE; | ||||||
|  |  | ||||||
|  |   k->maxfd = (conn->sockfd>conn->writesockfd? | ||||||
|  |               conn->sockfd:conn->writesockfd)+1; | ||||||
|  |  | ||||||
|  |   k->size = data->reqdata.size; | ||||||
|  |   k->maxdownload = data->reqdata.maxdownload; | ||||||
|  |   k->bytecountp = data->reqdata.bytecountp; | ||||||
|  |   k->writebytecountp = data->reqdata.writebytecountp; | ||||||
|  |  | ||||||
|  | } | ||||||
|  |  | ||||||
| CURLcode Curl_do(struct connectdata **connp, bool *done) | CURLcode Curl_do(struct connectdata **connp, bool *done) | ||||||
| { | { | ||||||
|   CURLcode result=CURLE_OK; |   CURLcode result=CURLE_OK; | ||||||
|   struct connectdata *conn = *connp; |   struct connectdata *conn = *connp; | ||||||
|   struct SessionHandle *data = conn->data; |   struct SessionHandle *data = conn->data; | ||||||
|  |  | ||||||
|   conn->bits.done = FALSE; /* Curl_done() is not called yet */ |   /* setup and init stuff before DO starts, in preparing for the transfer */ | ||||||
|   conn->bits.do_more = FALSE; /* by default there's no curl_do_more() to use */ |   do_init(conn); | ||||||
|  |  | ||||||
|   if(conn->handler->do_it) { |   if(conn->handler->do_it) { | ||||||
|     /* generic protocol-specific function pointer set in curl_connect() */ |     /* generic protocol-specific function pointer set in curl_connect() */ | ||||||
|     result = conn->handler->do_it(conn, done); |     result = conn->handler->do_it(conn, done); | ||||||
|  |  | ||||||
|     /* This was formerly done in transfer.c, but we better do it here */ |     /* This was formerly done in transfer.c, but we better do it here */ | ||||||
|  |  | ||||||
|     if((CURLE_SEND_ERROR == result) && conn->bits.reuse) { |     if((CURLE_SEND_ERROR == result) && conn->bits.reuse) { | ||||||
|       /* This was a re-use of a connection and we got a write error in the |       /* This was a re-use of a connection and we got a write error in the | ||||||
|        * DO-phase. Then we DISCONNECT this connection and have another attempt |        * DO-phase. Then we DISCONNECT this connection and have another attempt | ||||||
| @@ -4513,6 +4578,10 @@ CURLcode Curl_do(struct connectdata **connp, bool *done) | |||||||
|         } |         } | ||||||
|       } |       } | ||||||
|     } |     } | ||||||
|  |  | ||||||
|  |     if(result == CURLE_OK) | ||||||
|  |       /* pre readwrite must be called after the protocol-specific DO function */ | ||||||
|  |       do_complete(conn); | ||||||
|   } |   } | ||||||
|   return result; |   return result; | ||||||
| } | } | ||||||
|   | |||||||
| @@ -600,7 +600,7 @@ struct ConnectBits { | |||||||
|                          requests */ |                          requests */ | ||||||
|   bool netrc;         /* name+password provided by netrc */ |   bool netrc;         /* name+password provided by netrc */ | ||||||
|  |  | ||||||
|   bool trailerHdrPresent; /* Set when Trailer: header found in HTTP response. |   bool trailerhdrpresent; /* Set when Trailer: header found in HTTP response. | ||||||
|                              Required to determine whether to look for trailers |                              Required to determine whether to look for trailers | ||||||
|                              in case of Transfer-Encoding: chunking */ |                              in case of Transfer-Encoding: chunking */ | ||||||
|   bool done;          /* set to FALSE when Curl_do() is called and set to TRUE |   bool done;          /* set to FALSE when Curl_do() is called and set to TRUE | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user
	 Daniel Stenberg
					Daniel Stenberg