Loading lib/url.c +60 −35 Original line number Diff line number Diff line Loading @@ -158,6 +158,7 @@ static bool ConnectionExists(struct SessionHandle *data, static long ConnectionStore(struct SessionHandle *data, struct connectdata *conn); static bool IsPipeliningPossible(struct SessionHandle *handle); static bool IsPipeliningEnabled(struct SessionHandle *handle); static void conn_free(struct connectdata *conn); static void signalPipeClose(struct curl_llist *pipe); Loading Loading @@ -1790,8 +1791,10 @@ CURLcode Curl_disconnect(struct connectdata *conn) Curl_ssl_close(conn); /* Indicate to all handles on the pipe that we're dead */ if (IsPipeliningEnabled(data)) { signalPipeClose(conn->send_pipe); signalPipeClose(conn->recv_pipe); } conn_free(conn); Loading Loading @@ -1827,6 +1830,14 @@ static bool IsPipeliningPossible(struct SessionHandle *handle) return FALSE; } static bool IsPipeliningEnabled(struct SessionHandle *handle) { if (handle->multi && Curl_multi_canPipeline(handle->multi)) return TRUE; return FALSE; } void Curl_addHandleToPipeline(struct SessionHandle *data, struct curl_llist *pipe) { Loading Loading @@ -1937,21 +1948,44 @@ ConnectionExists(struct SessionHandle *data, /* NULL pointer means not filled-in entry */ continue; if (check->connectindex == -1) { check->connectindex = i; /* Set this appropriately since it might have been set to -1 when the easy was removed from the multi */ } infof(data, "Examining connection #%ld for reuse\n", check->connectindex); if(check->inuse && !canPipeline) { /* can only happen within multi handles, and means that another easy handle is using this connection */ continue; } #ifdef CURLRES_ASYNCH /* ip_addr_str is NULL only if the resolving of the name hasn't completed yet and until then we don't re-use this connection */ if (!check->ip_addr_str) if (!check->ip_addr_str) { infof(data, "Connection #%ld has not finished name resolve, can't reuse\n", check->connectindex); continue; } #endif if(check->inuse && !canPipeline) /* can only happen within multi handles, and means that another easy handle is using this connection */ if (check->send_pipe->size + check->recv_pipe->size >= MAX_PIPELINE_LENGTH) { infof(data, "Connection #%ld has its pipeline full, can't reuse\n", check->connectindex); continue; } if (check->send_pipe->size + check->recv_pipe->size >= MAX_PIPELINE_LENGTH) if (data->state.is_in_pipeline && check->bits.close) { /* Don't pick a connection that is going to be closed */ infof(data, "Connection #%ld has been marked for close, can't reuse\n", check->connectindex); continue; } if((needle->protocol&PROT_SSL) != (check->protocol&PROT_SSL)) /* don't do mixed SSL and non-SSL connections */ Loading Loading @@ -2002,33 +2036,22 @@ ConnectionExists(struct SessionHandle *data, } if(match) { #if 1 if (!IsPipeliningEnabled(data)) { /* The check for a dead socket makes sense only in the non-pipelining case */ bool dead = SocketIsDead(check->sock[FIRSTSOCKET]); if(dead) { if (!check->is_in_pipeline) { check->data = data; infof(data, "Connection %d seems to be dead!\n", i); infof(data, "Connection #%d seems to be dead!\n", i); Curl_disconnect(check); /* disconnect resources */ data->state.connc->connects[i]=NULL; /* nothing here */ } else { /* In the pipelining case, freeing the connection right away * doesn't work. Instead, we mark the connection for close * so that the handles will detect this automatically when * they try to do something and deal with it there. * Prematurely freeing this connection prevents handles that * have already finished with their transfers to shut down * cleanly. */ infof(data, "Connection %d seems dead - marking for close\n", i); check->bits.close = TRUE; } /* There's no need to continue searching, because we only store one connection for each unique set of identifiers */ return FALSE; } } #endif check->inuse = TRUE; /* mark this as being in use so that no other handle in a multi stack may nick it */ Loading @@ -2045,10 +2068,12 @@ ConnectionExists(struct SessionHandle *data, return TRUE; /* yes, we found one to use! */ } } return FALSE; /* no matching connecting exists */ } /* * This function frees/closes a connection in the connection cache. This * should take the previously set policy into account when deciding which Loading Loading @@ -2182,9 +2207,9 @@ static CURLcode ConnectPlease(struct SessionHandle *data, Curl_addrinfo *addr; char *hostname = data->change.proxy?conn->proxy.name:conn->host.name; infof(data, "About to connect() to %s%s port %d\n", infof(data, "About to connect() to %s%s port %d (#%d)\n", data->change.proxy?"proxy ":"", hostname, conn->port); hostname, conn->port, conn->connectindex); /************************************************************* * Connect to server/proxy Loading Loading @@ -2226,9 +2251,9 @@ static CURLcode ConnectPlease(struct SessionHandle *data, */ static void verboseconnect(struct connectdata *conn) { infof(conn->data, "Connected to %s (%s) port %d\n", infof(conn->data, "Connected to %s (%s) port %d (#%d)\n", conn->bits.httpproxy ? conn->proxy.dispname : conn->host.dispname, conn->ip_addr_str, conn->port); conn->ip_addr_str, conn->port, conn->connectindex); } int Curl_protocol_getsock(struct connectdata *conn, Loading Loading
lib/url.c +60 −35 Original line number Diff line number Diff line Loading @@ -158,6 +158,7 @@ static bool ConnectionExists(struct SessionHandle *data, static long ConnectionStore(struct SessionHandle *data, struct connectdata *conn); static bool IsPipeliningPossible(struct SessionHandle *handle); static bool IsPipeliningEnabled(struct SessionHandle *handle); static void conn_free(struct connectdata *conn); static void signalPipeClose(struct curl_llist *pipe); Loading Loading @@ -1790,8 +1791,10 @@ CURLcode Curl_disconnect(struct connectdata *conn) Curl_ssl_close(conn); /* Indicate to all handles on the pipe that we're dead */ if (IsPipeliningEnabled(data)) { signalPipeClose(conn->send_pipe); signalPipeClose(conn->recv_pipe); } conn_free(conn); Loading Loading @@ -1827,6 +1830,14 @@ static bool IsPipeliningPossible(struct SessionHandle *handle) return FALSE; } static bool IsPipeliningEnabled(struct SessionHandle *handle) { if (handle->multi && Curl_multi_canPipeline(handle->multi)) return TRUE; return FALSE; } void Curl_addHandleToPipeline(struct SessionHandle *data, struct curl_llist *pipe) { Loading Loading @@ -1937,21 +1948,44 @@ ConnectionExists(struct SessionHandle *data, /* NULL pointer means not filled-in entry */ continue; if (check->connectindex == -1) { check->connectindex = i; /* Set this appropriately since it might have been set to -1 when the easy was removed from the multi */ } infof(data, "Examining connection #%ld for reuse\n", check->connectindex); if(check->inuse && !canPipeline) { /* can only happen within multi handles, and means that another easy handle is using this connection */ continue; } #ifdef CURLRES_ASYNCH /* ip_addr_str is NULL only if the resolving of the name hasn't completed yet and until then we don't re-use this connection */ if (!check->ip_addr_str) if (!check->ip_addr_str) { infof(data, "Connection #%ld has not finished name resolve, can't reuse\n", check->connectindex); continue; } #endif if(check->inuse && !canPipeline) /* can only happen within multi handles, and means that another easy handle is using this connection */ if (check->send_pipe->size + check->recv_pipe->size >= MAX_PIPELINE_LENGTH) { infof(data, "Connection #%ld has its pipeline full, can't reuse\n", check->connectindex); continue; } if (check->send_pipe->size + check->recv_pipe->size >= MAX_PIPELINE_LENGTH) if (data->state.is_in_pipeline && check->bits.close) { /* Don't pick a connection that is going to be closed */ infof(data, "Connection #%ld has been marked for close, can't reuse\n", check->connectindex); continue; } if((needle->protocol&PROT_SSL) != (check->protocol&PROT_SSL)) /* don't do mixed SSL and non-SSL connections */ Loading Loading @@ -2002,33 +2036,22 @@ ConnectionExists(struct SessionHandle *data, } if(match) { #if 1 if (!IsPipeliningEnabled(data)) { /* The check for a dead socket makes sense only in the non-pipelining case */ bool dead = SocketIsDead(check->sock[FIRSTSOCKET]); if(dead) { if (!check->is_in_pipeline) { check->data = data; infof(data, "Connection %d seems to be dead!\n", i); infof(data, "Connection #%d seems to be dead!\n", i); Curl_disconnect(check); /* disconnect resources */ data->state.connc->connects[i]=NULL; /* nothing here */ } else { /* In the pipelining case, freeing the connection right away * doesn't work. Instead, we mark the connection for close * so that the handles will detect this automatically when * they try to do something and deal with it there. * Prematurely freeing this connection prevents handles that * have already finished with their transfers to shut down * cleanly. */ infof(data, "Connection %d seems dead - marking for close\n", i); check->bits.close = TRUE; } /* There's no need to continue searching, because we only store one connection for each unique set of identifiers */ return FALSE; } } #endif check->inuse = TRUE; /* mark this as being in use so that no other handle in a multi stack may nick it */ Loading @@ -2045,10 +2068,12 @@ ConnectionExists(struct SessionHandle *data, return TRUE; /* yes, we found one to use! */ } } return FALSE; /* no matching connecting exists */ } /* * This function frees/closes a connection in the connection cache. This * should take the previously set policy into account when deciding which Loading Loading @@ -2182,9 +2207,9 @@ static CURLcode ConnectPlease(struct SessionHandle *data, Curl_addrinfo *addr; char *hostname = data->change.proxy?conn->proxy.name:conn->host.name; infof(data, "About to connect() to %s%s port %d\n", infof(data, "About to connect() to %s%s port %d (#%d)\n", data->change.proxy?"proxy ":"", hostname, conn->port); hostname, conn->port, conn->connectindex); /************************************************************* * Connect to server/proxy Loading Loading @@ -2226,9 +2251,9 @@ static CURLcode ConnectPlease(struct SessionHandle *data, */ static void verboseconnect(struct connectdata *conn) { infof(conn->data, "Connected to %s (%s) port %d\n", infof(conn->data, "Connected to %s (%s) port %d (#%d)\n", conn->bits.httpproxy ? conn->proxy.dispname : conn->host.dispname, conn->ip_addr_str, conn->port); conn->ip_addr_str, conn->port, conn->connectindex); } int Curl_protocol_getsock(struct connectdata *conn, Loading