summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRemi Collet <fedora@famillecollet.com>2012-06-24 18:59:40 +0200
committerRemi Collet <fedora@famillecollet.com>2012-06-24 18:59:40 +0200
commit46c63d5553c4f2d54b30679b6bfd22893fbb05f6 (patch)
treeae6557a386696721dbbf8991bd21958051083173
parent5f92f6832f1ee6d21ba25a5cb5c2d180f91a0ea5 (diff)
compat-libcurl3-7.15.5-2, sync with curl-7.15.5-15
-rw-r--r--compat-libcurl3.spec43
-rw-r--r--curl-7.15.5-bz652557.patch16
-rw-r--r--curl-7.15.5-bz657396.patch465
-rw-r--r--curl-7.15.5-bz688871.patch28
-rw-r--r--curl-7.15.5-bz723643.patch124
-rw-r--r--curl-7.15.5-bz746849.patch125
6 files changed, 798 insertions, 3 deletions
diff --git a/compat-libcurl3.spec b/compat-libcurl3.spec
index 6692433..1f593ed 100644
--- a/compat-libcurl3.spec
+++ b/compat-libcurl3.spec
@@ -1,7 +1,9 @@
+%global rhelrel 15-el5
+
Summary: A utility for getting files from remote servers (FTP, HTTP, and others).
Name: compat-libcurl3
Version: 7.15.5
-Release: 1%{?dist}
+Release: 2%{?dist}
License: MIT
Group: Applications/Internet
Source: http://curl.haxx.se/download/curl-%{version}.tar.bz2
@@ -18,6 +20,11 @@ Patch9: curl-7.15.5-bz532069.patch
Patch10: curl-7.15.5-bz563220.patch
Patch11: curl-7.15.5-bz655073.patch
Patch12: curl-7.15.5-CVE-2011-2192.patch
+Patch13: curl-7.15.5-bz723643.patch
+Patch14: curl-7.15.5-bz652557.patch
+Patch15: curl-7.15.5-bz657396.patch
+Patch16: curl-7.15.5-bz688871.patch
+Patch17: curl-7.15.5-bz746849.patch
URL: http://curl.haxx.se/
BuildRoot: %{_tmppath}/%{name}-%{version}-root
BuildRequires: openssl-devel, libtool, pkgconfig, libidn-devel
@@ -31,7 +38,8 @@ offers many useful capabilities, like proxy support, user
authentication, FTP upload, HTTP post, and file transfer resume.
%{name} is provided for compatibility for package build against old
-libcurl (libcurl.so.3 provided by version < 7.16)
+libcurl (libcurl.so.3 provided by version < 7.16).
+In sync with curl-%{version}-%{rhelrel}.
%package devel
@@ -63,6 +71,11 @@ rm -rf $RPM_BUILD_ROOT
%patch10 -p1 -b .bz563220
%patch11 -p1 -b .bz655073
%patch12 -p1 -b .CVE-2011-2192
+%patch13 -p1 -b .bz723643
+%patch14 -p1 -b .bz652557
+%patch15 -p1 -b .bz657396
+%patch16 -p1 -b .bz688871
+%patch17 -p1 -b .bz746849
%build
aclocal
@@ -119,15 +132,39 @@ rm -rf $RPM_BUILD_ROOT
%{_mandir}/man3/*
%changelog
-* Tue Aug 16 2011 Remi Collet <RPMS@FamilleCollet.com> - 7.21.7-3
+* Sun Jun 24 2012 Remi Collet <RPMS@FamilleCollet.com> - 7.15.5-2
+- sync with curl 7.15.5-15
+
+* Thu Oct 27 2011 Kamil Dudka <kdudka@redhat.com> 7.15.5-15
+- introduce the --delegation option of curl (#746849)
+
+* Fri Oct 21 2011 Kamil Dudka <kdudka@redhat.com> 7.15.5-14
+- fix stack smashing in the FTP implementation (#652557)
+- fix proxy kerberos authentication (#657396)
+- update running_handles counter properly in curl_multi_remove_handle (#688871)
+
+* Tue Aug 16 2011 Remi Collet <RPMS@FamilleCollet.com> - 7.15.5-1
- build as compat-libcurl3 for remi repository
+- sync with 7.15.5-9.el5_6.3
+
+* Wed Aug 03 2011 Kamil Dudka <kdudka@redhat.com> 7.15.5-13
+- add a new option CURLOPT_GSSAPI_DELEGATION (#723643)
+
+* Thu Jun 23 2011 Kamil Dudka <kdudka@redhat.com> 7.15.5-12
+- do not delegate GSSAPI credentials (CVE-2011-2192)
* Thu Jun 23 2011 Kamil Dudka <kdudka@redhat.com> 7.15.5-9.el5_6.3
- do not delegate GSSAPI credentials (CVE-2011-2192)
+* Mon Jan 24 2011 Kamil Dudka <kdudka@redhat.com> - 7.15.5-11
+- avoid use of uninitialized variable on failure of a LDAP request (#655073)
+
* Mon Jan 24 2011 Kamil Dudka <kdudka@redhat.com> - 7.15.5-9.el5_6.2
- avoid use of uninitialized variable on failure of a LDAP request (#670523)
+* Tue Jan 18 2011 Kamil Dudka <kdudka@redhat.com> - 7.15.5-10
+- proxy tunnel support for LDAP requests (#655073)
+
* Tue Jan 18 2011 Kamil Dudka <kdudka@redhat.com> - 7.15.5-9.el5_6.1
- proxy tunnel support for LDAP requests (#670523)
diff --git a/curl-7.15.5-bz652557.patch b/curl-7.15.5-bz652557.patch
new file mode 100644
index 0000000..9aba025
--- /dev/null
+++ b/curl-7.15.5-bz652557.patch
@@ -0,0 +1,16 @@
+diff --git a/lib/ftp.c b/lib/ftp.c
+index cd067e0..b1f61f9 100644
+--- a/lib/ftp.c
++++ b/lib/ftp.c
+@@ -214,8 +214,10 @@ static CURLcode AllowServerConnect(struct connectdata *conn)
+ socklen_t size = (socklen_t) sizeof(struct sockaddr_in);
+ struct sockaddr_in add;
+
+- if(0 == getsockname(sock, (struct sockaddr *) &add, &size))
++ if(0 == getsockname(sock, (struct sockaddr *) &add, &size)) {
++ size = sizeof(add);
+ s=accept(sock, (struct sockaddr *) &add, &size);
++ }
+
+ sclose(sock); /* close the first socket */
+
diff --git a/curl-7.15.5-bz657396.patch b/curl-7.15.5-bz657396.patch
new file mode 100644
index 0000000..8abba2c
--- /dev/null
+++ b/curl-7.15.5-bz657396.patch
@@ -0,0 +1,465 @@
+From 795a6b48946f22d4562e6ad859306ac62eb3f6a0 Mon Sep 17 00:00:00 2001
+From: Daniel Stenberg <daniel@haxx.se>
+Date: Fri, 3 Nov 2006 12:43:55 +0000
+Subject: [PATCH 1/4] Olaf Stueben provided a patch that I edited slightly. It
+ fixes the notorious KNOWN_BUGS #25, which happens when
+ a proxy closes the connection when libcurl has sent
+ CONNECT, as part of an authentication negotiation.
+ Starting now, libcurl will re-connect accordingly and
+ continue the authentication as it should.
+
+Signed-off-by: Kamil Dudka <kdudka@redhat.com>
+---
+ lib/http.c | 15 +++++++++++++++
+ lib/url.c | 54 +++++++++++++++++++++++++++++++++---------------------
+ lib/urldata.h | 3 +++
+ 3 files changed, 51 insertions(+), 21 deletions(-)
+
+diff --git a/lib/http.c b/lib/http.c
+index 0fd0cbe..4d39a98 100644
+--- a/lib/http.c
++++ b/lib/http.c
+@@ -1095,6 +1095,7 @@ CURLcode Curl_proxyCONNECT(struct connectdata *conn,
+ curl_socket_t tunnelsocket = conn->sock[sockindex];
+ send_buffer *req_buffer;
+ curl_off_t cl=0;
++ bool closeConnection = FALSE;
+
+ #define SELECT_OK 0
+ #define SELECT_ERROR 1
+@@ -1102,6 +1103,7 @@ CURLcode Curl_proxyCONNECT(struct connectdata *conn,
+ int error = SELECT_OK;
+
+ infof(data, "Establish HTTP proxy tunnel to %s:%d\n", hostname, remote_port);
++ conn->bits.proxy_connect_closed = FALSE;
+
+ do {
+ if(conn->newurl) {
+@@ -1295,6 +1297,9 @@ CURLcode Curl_proxyCONNECT(struct connectdata *conn,
+ cl = curlx_strtoofft(line_start + strlen("Content-Length:"),
+ NULL, 10);
+ }
++ else if(Curl_compareheader(line_start,
++ "Connection:", "close"))
++ closeConnection = TRUE;
+ else if(2 == sscanf(line_start, "HTTP/1.%d %d",
+ &subversion,
+ &k->httpcode)) {
+@@ -1321,11 +1326,21 @@ CURLcode Curl_proxyCONNECT(struct connectdata *conn,
+ headers. 'newurl' is set to a new URL if we must loop. */
+ Curl_http_auth_act(conn);
+
++ if (closeConnection && conn->newurl) {
++ /* Connection closed by server. Don't use it anymore */
++ sclose(conn->sock[sockindex]);
++ conn->sock[sockindex] = CURL_SOCKET_BAD;
++ break;
++ }
+ } while(conn->newurl);
+
+ if(200 != k->httpcode) {
+ failf(data, "Received HTTP code %d from proxy after CONNECT",
+ k->httpcode);
++
++ if (closeConnection && conn->newurl)
++ conn->bits.proxy_connect_closed = TRUE;
++
+ return CURLE_RECV_ERROR;
+ }
+
+diff --git a/lib/url.c b/lib/url.c
+index 1a0c206..bf4a3dd 100644
+--- a/lib/url.c
++++ b/lib/url.c
+@@ -2484,7 +2484,8 @@ CURLcode Curl_protocol_connect(struct connectdata *conn, bool *protocol_done)
+
+ /* it has started, possibly even completed but that knowledge isn't stored
+ in this bit! */
+- conn->bits.protoconnstart = TRUE;
++ if (!result)
++ conn->bits.protoconnstart = TRUE;
+ }
+
+ return result; /* pass back status */
+@@ -3981,30 +3982,41 @@ static CURLcode SetupConnection(struct connectdata *conn,
+ data->state.crlf_conversions = 0; /* reset CRLF conversion counter */
+ #endif /* CURL_DO_LINEEND_CONV */
+
+- if(CURL_SOCKET_BAD == conn->sock[FIRSTSOCKET]) {
+- bool connected = FALSE;
++ for(;;) {
++ /* loop for CURL_SERVER_CLOSED_CONNECTION */
+
+- /* Connect only if not already connected! */
+- result = ConnectPlease(conn, hostaddr, &connected);
++ if(CURL_SOCKET_BAD == conn->sock[FIRSTSOCKET]) {
++ bool connected = FALSE;
+
+- if(connected) {
+- result = Curl_protocol_connect(conn, protocol_done);
+- if(CURLE_OK == result)
+- conn->bits.tcpconnect = TRUE;
+- }
+- else
+- conn->bits.tcpconnect = FALSE;
++ /* Connect only if not already connected! */
++ result = ConnectPlease(conn, hostaddr, &connected);
+
++ if(connected) {
++ result = Curl_protocol_connect(conn, protocol_done);
++ if(CURLE_OK == result)
++ conn->bits.tcpconnect = TRUE;
++ }
++ else
++ conn->bits.tcpconnect = FALSE;
+
+- if(CURLE_OK != result)
+- return result;
+- }
+- else {
+- Curl_pgrsTime(data, TIMER_CONNECT); /* we're connected already */
+- conn->bits.tcpconnect = TRUE;
+- *protocol_done = TRUE;
+- if(data->set.verbose)
+- verboseconnect(conn);
++ /* if the connection was closed by the server while exchanging
++ authentication informations, retry with the new set
++ authentication information */
++ if(conn->bits.proxy_connect_closed)
++ continue;
++
++ if(CURLE_OK != result)
++ return result;
++ }
++ else {
++ Curl_pgrsTime(data, TIMER_CONNECT); /* we're connected already */
++ conn->bits.tcpconnect = TRUE;
++ *protocol_done = TRUE;
++ if(data->set.verbose)
++ verboseconnect(conn);
++ }
++ /* Stop the loop now */
++ break;
+ }
+
+ conn->now = Curl_tvnow(); /* time this *after* the connect is done, we
+diff --git a/lib/urldata.h b/lib/urldata.h
+index d092113..3ac8fbf 100644
+--- a/lib/urldata.h
++++ b/lib/urldata.h
+@@ -454,6 +454,9 @@ struct ConnectBits {
+ when Curl_done() is called, to prevent Curl_done() to
+ get invoked twice when the multi interface is
+ used. */
++ bool proxy_connect_closed; /* set true if a proxy disconnected the
++ connection in a CONNECT request with auth, so
++ that libcurl should reconnect and continue. */
+ };
+
+ struct hostname {
+--
+1.7.4.4
+
+
+From e3c76c19fd8d61f41b4025c4f085413dd9935e28 Mon Sep 17 00:00:00 2001
+From: Daniel Stenberg <daniel@haxx.se>
+Date: Tue, 10 Jul 2007 22:31:13 +0000
+Subject: [PATCH 2/4] Giancarlo Formicuccia reported and fixed a problem with
+ a closed connection to a proxy during CONNECT auth
+ negotiation.
+
+Signed-off-by: Kamil Dudka <kdudka@redhat.com>
+---
+ lib/http.c | 3 +++
+ 1 files changed, 3 insertions(+), 0 deletions(-)
+
+diff --git a/lib/http.c b/lib/http.c
+index 4d39a98..6481fa0 100644
+--- a/lib/http.c
++++ b/lib/http.c
+@@ -1300,6 +1300,9 @@ CURLcode Curl_proxyCONNECT(struct connectdata *conn,
+ else if(Curl_compareheader(line_start,
+ "Connection:", "close"))
+ closeConnection = TRUE;
++ else if(Curl_compareheader(line_start,
++ "Proxy-Connection:", "close"))
++ closeConnection = TRUE;
+ else if(2 == sscanf(line_start, "HTTP/1.%d %d",
+ &subversion,
+ &k->httpcode)) {
+--
+1.7.4.4
+
+
+From c1bfdb84733e58b11dce10eb2c99bf4c1f5c8806 Mon Sep 17 00:00:00 2001
+From: Daniel Stenberg <daniel@haxx.se>
+Date: Fri, 21 Sep 2007 11:05:31 +0000
+Subject: [PATCH 3/4] Mark Davies fixed Negotiate authentication over proxy,
+ and also introduced the --proxy-negotiate command line
+ option to allow a user to explicitly select it.
+
+Signed-off-by: Kamil Dudka <kdudka@redhat.com>
+---
+ docs/curl.1 | 11 +++++++++++
+ lib/http.c | 16 ++++++++++++++--
+ lib/http_negotiate.c | 14 +++++++-------
+ lib/http_negotiate.h | 4 ++--
+ src/main.c | 11 +++++++++++
+ 5 files changed, 45 insertions(+), 11 deletions(-)
+
+diff --git a/docs/curl.1 b/docs/curl.1
+index e62be55..2658954 100644
+--- a/docs/curl.1
++++ b/docs/curl.1
+@@ -688,6 +688,9 @@ meant as a support for Kerberos5 authentication but may be also used along
+ with another authentication methods. For more information see IETF draft
+ draft-brezak-spnego-http-04.txt.
+
++If you want to enable Negotiate for your proxy authentication, then use
++\fI--proxy-negotiate\fP.
++
+ This option requires that the library was built with GSSAPI support. This is
+ not very common. Use \fI-V/--version\fP to see if your version supports
+ GSS-Negotiate.
+@@ -768,6 +771,14 @@ Tells curl to use HTTP Digest authentication when communicating with the given
+ proxy. Use \fI--digest\fP for enabling HTTP Digest with a remote host.
+
+ If this option is used twice, the second will again disable proxy HTTP Digest.
++.IP "--proxy-negotiate"
++Tells curl to use HTTP Negotiate authentication when communicating
++with the given proxy. Use \fI--negotiate\fP for enabling HTTP Negotiate
++with a remote host.
++
++If this option is used twice, the second will again disable proxy HTTP
++Negotiate.
++
+ .IP "--proxy-ntlm"
+ Tells curl to use HTTP NTLM authentication when communicating with the given
+ proxy. Use \fI--ntlm\fP for enabling NTLM with a remote host.
+diff --git a/lib/http.c b/lib/http.c
+index 6481fa0..033ee9b 100644
+--- a/lib/http.c
++++ b/lib/http.c
+@@ -416,6 +416,18 @@ Curl_http_output_auth(struct connectdata *conn,
+ /* Send proxy authentication header if needed */
+ if (conn->bits.httpproxy &&
+ (conn->bits.tunnel_proxy == proxytunnel)) {
++#ifdef HAVE_GSSAPI
++ if((authproxy->picked == CURLAUTH_GSSNEGOTIATE) &&
++ data->state.negotiate.context &&
++ !GSS_ERROR(data->state.negotiate.status)) {
++ auth="GSS-Negotiate";
++ result = Curl_output_negotiate(conn, TRUE);
++ if (result)
++ return result;
++ authproxy->done = TRUE;
++ }
++ else
++#endif
+ #ifdef USE_NTLM
+ if(authproxy->picked == CURLAUTH_NTLM) {
+ auth=(char *)"NTLM";
+@@ -478,7 +490,7 @@ Curl_http_output_auth(struct connectdata *conn,
+ data->state.negotiate.context &&
+ !GSS_ERROR(data->state.negotiate.status)) {
+ auth=(char *)"GSS-Negotiate";
+- result = Curl_output_negotiate(conn);
++ result = Curl_output_negotiate(conn, FALSE);
+ if (result)
+ return result;
+ authhost->done = TRUE;
+@@ -585,7 +597,7 @@ CURLcode Curl_http_input_auth(struct connectdata *conn,
+ authp->avail |= CURLAUTH_GSSNEGOTIATE;
+ if(authp->picked == CURLAUTH_GSSNEGOTIATE) {
+ /* if exactly this is wanted, go */
+- int neg = Curl_input_negotiate(conn, start);
++ int neg = Curl_input_negotiate(conn, (bool)(httpcode == 407), start);
+ if (neg == 0) {
+ conn->newurl = strdup(data->change.url);
+ data->state.authproblem = (conn->newurl == NULL);
+diff --git a/lib/http_negotiate.c b/lib/http_negotiate.c
+index 3fc678f..73deda5 100644
+--- a/lib/http_negotiate.c
++++ b/lib/http_negotiate.c
+@@ -49,7 +49,7 @@
+ #include "memdebug.h"
+
+ static int
+-get_gss_name(struct connectdata *conn, gss_name_t *server)
++get_gss_name(struct connectdata *conn, bool proxy, gss_name_t *server)
+ {
+ struct negotiatedata *neg_ctx = &conn->data->state.negotiate;
+ OM_uint32 major_status, minor_status;
+@@ -69,11 +69,11 @@ get_gss_name(struct connectdata *conn, gss_name_t *server)
+ else
+ service = "HTTP";
+
+- token.length = strlen(service) + 1 + strlen(conn->host.name) + 1;
++ token.length = strlen(service) + 1 + strlen(proxy ? conn->proxy.name : conn->host.name) + 1;
+ if (token.length + 1 > sizeof(name))
+ return EMSGSIZE;
+
+- snprintf(name, sizeof(name), "%s@%s", service, conn->host.name);
++ snprintf(name, sizeof(name), "%s@%s", service, proxy ? conn->proxy.name : conn->host.name);
+
+ token.value = (void *) name;
+ major_status = gss_import_name(&minor_status,
+@@ -113,7 +113,7 @@ log_gss_error(struct connectdata *conn, OM_uint32 error_status, char *prefix)
+ infof(conn->data, "%s", buf);
+ }
+
+-int Curl_input_negotiate(struct connectdata *conn, char *header)
++int Curl_input_negotiate(struct connectdata *conn, bool proxy, char *header)
+ {
+ struct negotiatedata *neg_ctx = &conn->data->state.negotiate;
+ OM_uint32 major_status, minor_status, minor_status2;
+@@ -169,7 +169,7 @@ int Curl_input_negotiate(struct connectdata *conn, char *header)
+ }
+
+ if (neg_ctx->server_name == NULL &&
+- (ret = get_gss_name(conn, &neg_ctx->server_name)))
++ (ret = get_gss_name(conn, proxy, &neg_ctx->server_name)))
+ return ret;
+
+ header += strlen(neg_ctx->protocol);
+@@ -258,7 +258,7 @@ int Curl_input_negotiate(struct connectdata *conn, char *header)
+ }
+
+
+-CURLcode Curl_output_negotiate(struct connectdata *conn)
++CURLcode Curl_output_negotiate(struct connectdata *conn, bool proxy)
+ {
+ struct negotiatedata *neg_ctx = &conn->data->state.negotiate;
+ char *encoded = NULL;
+@@ -310,7 +310,7 @@ CURLcode Curl_output_negotiate(struct connectdata *conn)
+ return CURLE_OUT_OF_MEMORY;
+
+ conn->allocptr.userpwd =
+- aprintf("Authorization: %s %s\r\n", neg_ctx->protocol, encoded);
++ aprintf("%sAuthorization: %s %s\r\n", proxy ? "Proxy-" : "", neg_ctx->protocol, encoded);
+ free(encoded);
+ Curl_cleanup_negotiate (conn->data);
+ return (conn->allocptr.userpwd == NULL) ? CURLE_OUT_OF_MEMORY : CURLE_OK;
+diff --git a/lib/http_negotiate.h b/lib/http_negotiate.h
+index cf8b048..8604a0c 100644
+--- a/lib/http_negotiate.h
++++ b/lib/http_negotiate.h
+@@ -27,10 +27,10 @@
+ #ifdef HAVE_GSSAPI
+
+ /* this is for Negotiate header input */
+-int Curl_input_negotiate(struct connectdata *conn, char *header);
++int Curl_input_negotiate(struct connectdata *conn, bool proxy, char *header);
+
+ /* this is for creating Negotiate header output */
+-CURLcode Curl_output_negotiate(struct connectdata *conn);
++CURLcode Curl_output_negotiate(struct connectdata *conn, bool proxy);
+
+ void Curl_cleanup_negotiate(struct SessionHandle *data);
+
+diff --git a/src/main.c b/src/main.c
+index 9f378db..44dd2c4 100644
+--- a/src/main.c
++++ b/src/main.c
+@@ -309,6 +309,7 @@ struct Configurable {
+ bool create_dirs;
+ bool ftp_create_dirs;
+ bool ftp_skip_ip;
++ bool proxynegotiate;
+ bool proxyntlm;
+ bool proxydigest;
+ bool proxybasic;
+@@ -555,6 +556,7 @@ static void help(void)
+ " --proxy-anyauth Pick \"any\" proxy authentication method (H)",
+ " --proxy-basic Use Basic authentication on the proxy (H)",
+ " --proxy-digest Use Digest authentication on the proxy (H)",
++ " --proxy-negotiate Use Negotiate authentication on the proxy (H)",
+ " --proxy-ntlm Use NTLM authentication on the proxy (H)",
+ " -P/--ftp-port <address> Use PORT with address instead of PASV (F)",
+ " -q If used as the first parameter disables .curlrc",
+@@ -1347,6 +1349,7 @@ static ParameterError getparameter(char *flag, /* f or -long-flag */
+ {"$t", "socks4", TRUE},
+ {"$u", "ftp-alternative-to-user", TRUE},
+ {"$v", "ftp-ssl-reqd", FALSE},
++ {"$w", "proxy-negotiate", FALSE},
+
+ {"0", "http1.0", FALSE},
+ {"1", "tlsv1", FALSE},
+@@ -1789,6 +1792,12 @@ static ParameterError getparameter(char *flag, /* f or -long-flag */
+ case 'v': /* --ftp-ssl-reqd */
+ config->ftp_ssl_reqd ^= TRUE;
+ break;
++ case 'w': /* --proxy-negotiate */
++ if(curlinfo->features & CURL_VERSION_GSSNEGOTIATE)
++ config->proxynegotiate ^= TRUE;
++ else
++ return PARAM_LIBCURL_DOESNT_SUPPORT;
++ break;
+ }
+ break;
+ case '#': /* --progress-bar */
+@@ -3960,6 +3969,8 @@ operate(struct Configurable *config, int argc, char *argv[])
+ config->ftp_create_dirs);
+ if(config->proxyanyauth)
+ curl_easy_setopt(curl, CURLOPT_PROXYAUTH, CURLAUTH_ANY);
++ else if(config->proxynegotiate)
++ curl_easy_setopt(curl, CURLOPT_PROXYAUTH, CURLAUTH_GSSNEGOTIATE);
+ else if(config->proxyntlm)
+ curl_easy_setopt(curl, CURLOPT_PROXYAUTH, CURLAUTH_NTLM);
+ else if(config->proxydigest)
+--
+1.7.4.4
+
+
+From 88507544781155092ccee225bff92a0177e0f4df Mon Sep 17 00:00:00 2001
+From: Daniel Stenberg <daniel@haxx.se>
+Date: Mon, 16 Aug 2010 22:19:38 +0200
+Subject: [PATCH 4/4] negotiation: Wrong proxy authorization
+
+There's an error in http_negotiation.c where a mistake is using only
+userpwd even for proxy requests. Ludek provided a patch, but I decided
+to write the fix slightly different using his patch as inspiration.
+
+Reported by: Ludek Finstrle
+Bug: http://curl.haxx.se/bug/view.cgi?id=3046066
+
+Signed-off-by: Kamil Dudka <kdudka@redhat.com>
+---
+ lib/http_negotiate.c | 12 +++++++++---
+ 1 files changed, 9 insertions(+), 3 deletions(-)
+
+diff --git a/lib/http_negotiate.c b/lib/http_negotiate.c
+index 73deda5..1d6119d 100644
+--- a/lib/http_negotiate.c
++++ b/lib/http_negotiate.c
+@@ -263,6 +263,7 @@ CURLcode Curl_output_negotiate(struct connectdata *conn, bool proxy)
+ struct negotiatedata *neg_ctx = &conn->data->state.negotiate;
+ char *encoded = NULL;
+ int len;
++ char *userp;
+
+ #ifdef HAVE_SPNEGO /* Handle SPNEGO */
+ if (checkprefix("Negotiate",neg_ctx->protocol)) {
+@@ -309,11 +310,16 @@ CURLcode Curl_output_negotiate(struct connectdata *conn, bool proxy)
+ if (len < 0)
+ return CURLE_OUT_OF_MEMORY;
+
+- conn->allocptr.userpwd =
+- aprintf("%sAuthorization: %s %s\r\n", proxy ? "Proxy-" : "", neg_ctx->protocol, encoded);
++ userp = aprintf("%sAuthorization: %s %s\r\n", proxy ? "Proxy-" : "",
++ neg_ctx->protocol, encoded);
++
++ if(proxy)
++ conn->allocptr.proxyuserpwd = userp;
++ else
++ conn->allocptr.userpwd = userp;
+ free(encoded);
+ Curl_cleanup_negotiate (conn->data);
+- return (conn->allocptr.userpwd == NULL) ? CURLE_OUT_OF_MEMORY : CURLE_OK;
++ return (userp == NULL) ? CURLE_OUT_OF_MEMORY : CURLE_OK;
+ }
+
+ void Curl_cleanup_negotiate(struct SessionHandle *data)
+--
+1.7.4.4
+
diff --git a/curl-7.15.5-bz688871.patch b/curl-7.15.5-bz688871.patch
new file mode 100644
index 0000000..5904fc7
--- /dev/null
+++ b/curl-7.15.5-bz688871.patch
@@ -0,0 +1,28 @@
+From e1e8d68d8d731ab38aa55328ab5ed32bd26d8c94 Mon Sep 17 00:00:00 2001
+From: Daniel Stenberg <daniel@haxx.se>
+Date: Fri, 25 Aug 2006 13:53:20 +0000
+Subject: [PATCH] curl - rhbz #688871
+
+backport of upstream 2ff609d
+---
+ lib/multi.c | 4 ++++
+ 1 files changed, 4 insertions(+), 0 deletions(-)
+
+diff --git a/lib/multi.c b/lib/multi.c
+index 89a1f99..0bcc744 100644
+--- a/lib/multi.c
++++ b/lib/multi.c
+@@ -386,6 +386,10 @@ CURLMcode curl_multi_remove_handle(CURLM *multi_handle,
+ if(easy) {
+ /* If the 'state' is not INIT or COMPLETED, we might need to do something
+ nice to put the easy_handle in a good known state when this returns. */
++ if(easy->state != CURLM_STATE_COMPLETED)
++ /* this handle is "alive" so we need to count down the total number of
++ alive connections when this is removed */
++ multi->num_alive--;
+
+ /* The timer must be shut down before easy->multi is set to NULL,
+ else the timenode will remain in the splay tree after
+--
+1.7.4.4
+
diff --git a/curl-7.15.5-bz723643.patch b/curl-7.15.5-bz723643.patch
new file mode 100644
index 0000000..f354c5b
--- /dev/null
+++ b/curl-7.15.5-bz723643.patch
@@ -0,0 +1,124 @@
+From 5a40e781345ed1c6eb5ae8fd7103719ebacd66e8 Mon Sep 17 00:00:00 2001
+From: Kamil Dudka <kdudka@redhat.com>
+Date: Wed, 3 Aug 2011 14:30:45 +0200
+Subject: [PATCH] curl - rhbz #723643
+
+---
+ docs/libcurl/curl_easy_setopt.3 | 8 ++++++++
+ include/curl/curl.h | 7 +++++++
+ lib/http_negotiate.c | 15 ++++++++++++++-
+ lib/url.c | 6 ++++++
+ lib/urldata.h | 3 +++
+ 5 files changed, 38 insertions(+), 1 deletions(-)
+
+diff --git a/docs/libcurl/curl_easy_setopt.3 b/docs/libcurl/curl_easy_setopt.3
+index 00a819b..c259c5a 100644
+--- a/docs/libcurl/curl_easy_setopt.3
++++ b/docs/libcurl/curl_easy_setopt.3
+@@ -1330,6 +1330,14 @@ krb4 awareness. This is a string, 'clear', 'safe', 'confidential' or
+ \&'private'. If the string is set but doesn't match one of these, 'private'
+ will be used. Set the string to NULL to disable kerberos4. The kerberos
+ support only works for FTP.
++.IP CURLOPT_GSSAPI_DELEGATION
++Set the parameter to CURLGSSAPI_DELEGATION_FLAG to allow unconditional GSSAPI
++credential delegation. The delegation is disabled by default since 7.21.7.
++Set the parameter to CURLGSSAPI_DELEGATION_POLICY_FLAG to delegate only if
++the OK-AS-DELEGATE flag is set in the service ticket in case this feature is
++supported by the GSSAPI implementation and the definition of
++GSS_C_DELEG_POLICY_FLAG was available at compile-time.
++(Added in 7.21.8)
+ .SH OTHER OPTIONS
+ .IP CURLOPT_PRIVATE
+ Pass a char * as parameter, pointing to data that should be associated with
+diff --git a/include/curl/curl.h b/include/curl/curl.h
+index 8ff213b..c4a0cab 100644
+--- a/include/curl/curl.h
++++ b/include/curl/curl.h
+@@ -388,6 +388,10 @@ typedef enum {
+ #define CURLE_FTP_BAD_DOWNLOAD_RESUME CURLE_BAD_DOWNLOAD_RESUME
+ #endif
+
++#define CURLGSSAPI_DELEGATION_NONE 0 /* no delegation (default) */
++#define CURLGSSAPI_DELEGATION_POLICY_FLAG (1<<0) /* if permitted by policy */
++#define CURLGSSAPI_DELEGATION_FLAG (1<<1) /* delegate always */
++
+ #define CURL_ERROR_SIZE 256
+
+ /* parameter for the CURLOPT_FTP_SSL option */
+@@ -1012,6 +1016,9 @@ typedef enum {
+ to CURLPROTO_ALL & ~CURLPROTO_FILE. */
+ CINIT(REDIR_PROTOCOLS, LONG, 182),
+
++ /* allow GSSAPI credential delegation */
++ CINIT(GSSAPI_DELEGATION, LONG, 210),
++
+ CURLOPT_LASTENTRY /* the last unused */
+ } CURLoption;
+
+diff --git a/lib/http_negotiate.c b/lib/http_negotiate.c
+index 4015e2f..7758049 100644
+--- a/lib/http_negotiate.c
++++ b/lib/http_negotiate.c
+@@ -123,6 +123,19 @@ int Curl_input_negotiate(struct connectdata *conn, char *header)
+ size_t len;
+ bool gss;
+ const char* protocol;
++ OM_uint32 req_flags = 0;
++
++ if(conn->data->set.gssapi_delegation & CURLGSSAPI_DELEGATION_POLICY_FLAG) {
++#ifdef GSS_C_DELEG_POLICY_FLAG
++ req_flags |= GSS_C_DELEG_POLICY_FLAG;
++#else
++ infof(conn->data, "warning: support for CURLGSSAPI_DELEGATION_POLICY_FLAG "
++ "not compiled in\n");
++#endif
++ }
++
++ if(conn->data->set.gssapi_delegation & CURLGSSAPI_DELEGATION_FLAG)
++ req_flags |= GSS_C_DELEG_FLAG;
+
+ while(*header && isspace((int)*header))
+ header++;
+@@ -216,7 +229,7 @@ int Curl_input_negotiate(struct connectdata *conn, char *header)
+ &neg_ctx->context,
+ neg_ctx->server_name,
+ GSS_C_NO_OID,
+- 0,
++ req_flags,
+ 0,
+ GSS_C_NO_CHANNEL_BINDINGS,
+ &input_token,
+diff --git a/lib/url.c b/lib/url.c
+index 0528605..1a0c206 100644
+--- a/lib/url.c
++++ b/lib/url.c
+@@ -1322,6 +1322,12 @@ CURLcode Curl_setopt(struct SessionHandle *data, CURLoption option,
+ data->set.krb4_level = va_arg(param, char *);
+ data->set.krb4=data->set.krb4_level?TRUE:FALSE;
+ break;
++ case CURLOPT_GSSAPI_DELEGATION:
++ /*
++ * GSSAPI credential delegation
++ */
++ data->set.gssapi_delegation = va_arg(param, long);
++ break;
+ case CURLOPT_SSL_VERIFYPEER:
+ /*
+ * Enable peer SSL verifying.
+diff --git a/lib/urldata.h b/lib/urldata.h
+index 0ef49d5..d092113 100644
+--- a/lib/urldata.h
++++ b/lib/urldata.h
+@@ -1156,6 +1156,9 @@ struct UserDefined {
+ bool connect_only; /* make connection, let application use the socket */
+ long allowed_protocols;
+ long redir_protocols;
++
++ long gssapi_delegation; /* GSSAPI credential delegation, see the
++ documentation of CURLOPT_GSSAPI_DELEGATION */
+ };
+
+ struct Names {
+--
+1.7.4.4
+
diff --git a/curl-7.15.5-bz746849.patch b/curl-7.15.5-bz746849.patch
new file mode 100644
index 0000000..0994c83
--- /dev/null
+++ b/curl-7.15.5-bz746849.patch
@@ -0,0 +1,125 @@
+From 85d002123e5dea3de2499617d619253023335d8e Mon Sep 17 00:00:00 2001
+From: Daniel Stenberg <daniel@haxx.se>
+Date: Fri, 12 Aug 2011 14:48:32 +0200
+Subject: [PATCH 1/2] added --delegation
+
+Using this option with an argument being set to one of
+none/policy/always instructs libcurl how to deal with GSS
+credentials. Or rather how it tells the server that delegation is fine
+or not.
+
+Signed-off-by: Kamil Dudka <kdudka@redhat.com>
+---
+ src/main.c | 24 ++++++++++++++++++++++++
+ 1 files changed, 24 insertions(+), 0 deletions(-)
+
+diff --git a/src/main.c b/src/main.c
+index 44dd2c4..0753429 100644
+--- a/src/main.c
++++ b/src/main.c
+@@ -359,6 +359,7 @@ struct Configurable {
+ int ftp_filemethod;
+
+ bool ignorecl; /* --ignore-content-length */
++ long gssapi_delegation;
+ };
+
+ #define WARN_PREFIX "Warning: "
+@@ -489,6 +490,7 @@ static void help(void)
+ " --data-ascii <data> HTTP POST ASCII data (H)",
+ " --data-binary <data> HTTP POST binary data (H)",
+ " --negotiate Use HTTP Negotiate Authentication (H)",
++ " --delegation STRING GSS-API delegation permission",
+ " --digest Use HTTP Digest Authentication (H)",
+ " --disable-eprt Inhibit using EPRT or LPRT (F)",
+ " --disable-epsv Inhibit using EPSV (F)",
+@@ -1097,6 +1099,18 @@ static int formparse(struct Configurable *config,
+ return 0;
+ }
+
++static long delegation(struct Configurable *config,
++ char *str)
++{
++ if(!strcasecmp("none", str))
++ return CURLGSSAPI_DELEGATION_NONE;
++ if(!strcasecmp("policy", str))
++ return CURLGSSAPI_DELEGATION_POLICY_FLAG;
++ if(!strcasecmp("always", str))
++ return CURLGSSAPI_DELEGATION_FLAG;
++ warnf(config, "unrecognized delegation method '%s', using none\n", str);
++ return CURLGSSAPI_DELEGATION_NONE;
++}
+
+ typedef enum {
+ PARAM_OK,
+@@ -1351,6 +1365,8 @@ static ParameterError getparameter(char *flag, /* f or -long-flag */
+ {"$v", "ftp-ssl-reqd", FALSE},
+ {"$w", "proxy-negotiate", FALSE},
+
++ {"$G", "delegation", TRUE},
++
+ {"0", "http1.0", FALSE},
+ {"1", "tlsv1", FALSE},
+ {"2", "sslv2", FALSE},
+@@ -1798,6 +1814,9 @@ static ParameterError getparameter(char *flag, /* f or -long-flag */
+ else
+ return PARAM_LIBCURL_DOESNT_SUPPORT;
+ break;
++ case 'G': /* --delegation LEVEL */
++ config->gssapi_delegation = delegation(config, nextarg);
++ break;
+ }
+ break;
+ case '#': /* --progress-bar */
+@@ -4029,6 +4048,11 @@ operate(struct Configurable *config, int argc, char *argv[])
+ /* curl x.xx.x */
+ curl_easy_setopt(curl, CURLOPT_FTP_ALTERNATIVE_TO_USER, config->ftp_alternative_to_user);
+
++ /* new in 7.22.0 */
++ if(config->gssapi_delegation)
++ curl_easy_setopt(curl, CURLOPT_GSSAPI_DELEGATION,
++ config->gssapi_delegation);
++
+ retry_numretries = config->req_retry;
+
+ retrystart = curlx_tvnow();
+--
+1.7.1
+
+
+From 1a5566b1e84d0143899538f469596caf8f10d666 Mon Sep 17 00:00:00 2001
+From: Daniel Stenberg <daniel@haxx.se>
+Date: Fri, 12 Aug 2011 23:51:41 +0200
+Subject: [PATCH 2/2] docs: --delegation
+
+Signed-off-by: Kamil Dudka <kdudka@redhat.com>
+---
+ docs/curl.1 | 12 ++++++++++++
+ 1 files changed, 12 insertions(+), 0 deletions(-)
+
+diff --git a/docs/curl.1 b/docs/curl.1
+index 2658954..61bd4e9 100644
+--- a/docs/curl.1
++++ b/docs/curl.1
+@@ -256,6 +256,18 @@ the \fI--data-ascii\fP option, this is for you.
+
+ If this option is used several times, the ones following the first will
+ append data.
++.IP "--delegation LEVEL"
++Set \fILEVEL\fP to tell the server what it is allowed to delegate when it
++comes to user credentials. Used with GSS/kerberos.
++.RS
++.IP "none"
++Don't allow any delegation.
++.IP "policy"
++Delegates if and only if the OK-AS-DELEGATE flag is set in the Kerberos
++service ticket, which is a matter of realm policy.
++.IP "always"
++Unconditionally allow the server to delegate.
++.RE
+ .IP "--digest"
+ (HTTP) Enables HTTP Digest authentication. This is a authentication that
+ prevents the password from being sent over the wire in clear text. Use this in
+--
+1.7.1
+