diff options
| -rw-r--r-- | CHANGES | 4 | ||||
| -rw-r--r-- | RELEASE-NOTES | 1 | ||||
| -rw-r--r-- | lib/http.c | 58 | ||||
| -rw-r--r-- | lib/url.c | 1 | ||||
| -rw-r--r-- | lib/urldata.h | 1 | ||||
| -rw-r--r-- | tests/data/test299 | 53 | 
6 files changed, 96 insertions, 22 deletions
@@ -6,6 +6,10 @@                                    Changelog +Michal Marek (16 Jun 2009) +- When doing non-anonymous ftp via http proxies and the password is not +  provided in the url, add it there (squid needs this). +  Daniel Stenberg (15 Jun 2009)  - Eric Wong's patch: diff --git a/RELEASE-NOTES b/RELEASE-NOTES index 6c0c53984..73dbcae61 100644 --- a/RELEASE-NOTES +++ b/RELEASE-NOTES @@ -28,6 +28,7 @@ This release includes the following bugfixes:   o libcurl-NSS client cert handling segfaults   o curl uploading from stdin/pipes now works in non-blocking way so that it     continues the downloading even when the read stalls + o ftp credentials are added to the url if needed for http proxies  This release includes the following known bugs: diff --git a/lib/http.c b/lib/http.c index 8457b51f4..f69c5aaaf 100644 --- a/lib/http.c +++ b/lib/http.c @@ -2060,6 +2060,7 @@ CURLcode Curl_http(struct connectdata *conn, bool *done)    CURLcode result=CURLE_OK;    struct HTTP *http;    const char *ppath = data->state.path; +  bool paste_ftp_userpwd = FALSE;    char ftp_typecode[sizeof(";type=?")] = "";    const char *host = conn->host.name;    const char *te = ""; /* transfer-encoding */ @@ -2288,24 +2289,26 @@ CURLcode Curl_http(struct connectdata *conn, bool *done)        }      }      ppath = data->change.url; -    if (data->set.proxy_transfer_mode) { -      /* when doing ftp, append ;type=<a|i> if not present */ -      if(checkprefix("ftp://", ppath) || checkprefix("ftps://", ppath)) { -        char *p = strstr(ppath, ";type="); -        if(p && p[6] && p[7] == 0) { -          switch (Curl_raw_toupper(p[6])) { -          case 'A': -          case 'D': -          case 'I': -            break; -          default: -            p = NULL; +    if(checkprefix("ftp://", ppath)) { +      if (data->set.proxy_transfer_mode) { +        /* when doing ftp, append ;type=<a|i> if not present */ +          char *p = strstr(ppath, ";type="); +          if(p && p[6] && p[7] == 0) { +            switch (Curl_raw_toupper(p[6])) { +            case 'A': +            case 'D': +            case 'I': +              break; +            default: +              p = NULL; +            }            } -        } -        if(!p) -          snprintf(ftp_typecode, sizeof(ftp_typecode), ";type=%c", -                   data->set.prefer_ascii ? 'a' : 'i'); +          if(!p) +            snprintf(ftp_typecode, sizeof(ftp_typecode), ";type=%c", +                     data->set.prefer_ascii ? 'a' : 'i');        } +      if (conn->bits.user_passwd && !conn->bits.userpwd_in_url) +        paste_ftp_userpwd = TRUE;      }    }  #endif /* CURL_DISABLE_PROXY */ @@ -2464,10 +2467,23 @@ CURLcode Curl_http(struct connectdata *conn, bool *done)      return CURLE_OUT_OF_MEMORY;    /* add the main request stuff */ -  result = -    add_bufferf(req_buffer, -                "%s " /* GET/HEAD/POST/PUT */ -                "%s%s HTTP/%s\r\n" /* path + HTTP version */ +  /* GET/HEAD/POST/PUT */ +  result = add_bufferf(req_buffer, "%s ", request); +  if (result) +    return result; + +  /* url */ +  if (paste_ftp_userpwd) +    result = add_bufferf(req_buffer, "ftp://%s:%s@%s", +        conn->user, conn->passwd, ppath + sizeof("ftp://") - 1); +  else +    result = add_buffer(req_buffer, ppath, strlen(ppath)); +  if (result) +    return result; + +  result = add_bufferf(req_buffer, +                "%s" /* ftp typecode (;type=x) */ +                " HTTP/%s\r\n" /* HTTP version */                  "%s" /* proxyuserpwd */                  "%s" /* userpwd */                  "%s" /* range */ @@ -2479,8 +2495,6 @@ CURLcode Curl_http(struct connectdata *conn, bool *done)                  "%s" /* Proxy-Connection */                  "%s",/* transfer-encoding */ -                request, -                ppath,                  ftp_typecode,                  httpstring,                  conn->allocptr.proxyuserpwd? @@ -3831,6 +3831,7 @@ static CURLcode parse_url_userpass(struct SessionHandle *data,         * set user/passwd, but doing that first adds more cases here :-(         */ +      conn->bits.userpwd_in_url = 1;        if(data->set.use_netrc != CURL_NETRC_REQUIRED) {          /* We could use the one in the URL */ diff --git a/lib/urldata.h b/lib/urldata.h index f41b6583e..a1d9be739 100644 --- a/lib/urldata.h +++ b/lib/urldata.h @@ -625,6 +625,7 @@ struct ConnectBits {                           EPRT doesn't work we disable it for the forthcoming                           requests */    bool netrc;         /* name+password provided by netrc */ +  bool userpwd_in_url; /* name+password found in url */    bool done;          /* set to FALSE when Curl_do() is called and set to TRUE                           when Curl_done() is called, to prevent Curl_done() to diff --git a/tests/data/test299 b/tests/data/test299 new file mode 100644 index 000000000..a557a14c7 --- /dev/null +++ b/tests/data/test299 @@ -0,0 +1,53 @@ +<testcase> +<info> +<keywords> +FTP +HTTP +CURLOPT_USERPWD +HTTP proxy +</keywords> +</info> + +# Server-side +<reply> +<data> +HTTP/1.0 200 OK swsclose +Date: Thu, 09 Nov 2010 14:49:00 GMT +Server: test-server/fake + +blablabla + +</data> +</reply> + +# Client-side +<client> +<server> +http +</server> +<features> +ftp +</features> + <name> +FTP over HTTP proxy with user:pass not in url + </name> + <command> +-x http://%HOSTIP:%HTTPPORT -u michal:aybabtu ftp://host.com/we/want/299 +</command> +</client> + +# Verify data after the test has been "shot" +<verify> +<strip> +^User-Agent:.* +</strip> +<protocol> +GET ftp://michal:aybabtu@host.com/we/want/299 HTTP/1.1
 +Authorization: Basic bWljaGFsOmF5YmFidHU=
 +Host: host.com:21
 +Accept: */*
 +Proxy-Connection: Keep-Alive
 +
 +</protocol> +</verify> +</testcase>  | 
