rediffed some patches; removed 'struct-serialize' patch which was applied upstream in 1.25.12
276 lines
10 KiB
Diff
276 lines
10 KiB
Diff
From 867cf74ae3a95da7483e94052fd9b3743beb86ec Mon Sep 17 00:00:00 2001
|
|
From: giraffedata <giraffedata@adbb7d4b-a73a-0410-a071-c5f57c452bd4>
|
|
Date: Sun, 7 Aug 2011 02:50:57 +0000
|
|
Subject: [PATCH 9/9] backported GSSAPI_DELEGATION patch
|
|
|
|
---
|
|
include/xmlrpc-c/client.h | 1 +
|
|
include/xmlrpc-c/client_transport.hpp | 1 +
|
|
lib/curl_transport/curltransaction.c | 108 +++++++++++++++++++++++++++-
|
|
lib/curl_transport/curltransaction.h | 3 +
|
|
lib/curl_transport/curlversion.h | 6 ++
|
|
lib/curl_transport/xmlrpc_curl_transport.c | 5 ++
|
|
src/cpp/curl.cpp | 8 ++-
|
|
7 files changed, 129 insertions(+), 3 deletions(-)
|
|
|
|
diff --git a/include/xmlrpc-c/client.h b/include/xmlrpc-c/client.h
|
|
index 99eefd7..8dd3842 100644
|
|
--- a/include/xmlrpc-c/client.h
|
|
+++ b/include/xmlrpc-c/client.h
|
|
@@ -108,6 +108,7 @@ struct xmlrpc_curl_xportparms {
|
|
enum xmlrpc_httpproxyauth values
|
|
*/
|
|
const char * proxy_userpwd;
|
|
+ xmlrpc_bool gssapi_delegation;
|
|
};
|
|
|
|
|
|
diff --git a/include/xmlrpc-c/client_transport.hpp b/include/xmlrpc-c/client_transport.hpp
|
|
index ada5b5d..58a8c52 100644
|
|
--- a/include/xmlrpc-c/client_transport.hpp
|
|
+++ b/include/xmlrpc-c/client_transport.hpp
|
|
@@ -292,6 +292,7 @@ public:
|
|
constrOpt & proxy_auth (unsigned int const& arg);
|
|
constrOpt & proxy_userpwd (std::string const& arg);
|
|
constrOpt & proxy_type (xmlrpc_httpproxytype const& arg);
|
|
+ constrOpt & gssapi_delegation (bool const& arg);
|
|
|
|
private:
|
|
struct constrOpt_impl * implP;
|
|
diff --git a/lib/curl_transport/curltransaction.c b/lib/curl_transport/curltransaction.c
|
|
index 1ae6765..9cd6204 100644
|
|
--- a/lib/curl_transport/curltransaction.c
|
|
+++ b/lib/curl_transport/curltransaction.c
|
|
@@ -448,6 +448,99 @@ assertConstantsMatch(void) {
|
|
|
|
|
|
|
|
+/* About Curl and GSSAPI credential delegation:
|
|
+
|
|
+ Up through Curl 7.21.6, libcurl always delegates GSSAPI credentials, which
|
|
+ means it gives the client's secrets to the server so the server can operate
|
|
+ on the client's behalf. In mid-2011, this was noticed to be a major
|
|
+ security exposure, because the server is not necessarily trustworthy.
|
|
+ One is supposed to delegate one's credentials only to a server one trusts.
|
|
+ So in 7.21.7, Curl never delegates GSSAPI credentials.
|
|
+
|
|
+ But that causes problems for clients that _do_ trust their server, which
|
|
+ had always relied upon Curl's delegation.
|
|
+
|
|
+ So starting in 7.21.8, Curl gives the user the choice. The default is no
|
|
+ delegation, but the Curl user can set the CURLOPT_GSSAPI_DELEGATION flag to
|
|
+ order delegation.
|
|
+
|
|
+ Complicating matters is that some people made local variations of Curl
|
|
+ during the transition phase, so the version number alone isn't
|
|
+ determinative, so we rely on it only where we have to.
|
|
+
|
|
+ So Xmlrpc-c gives the same choice to its own user, via its
|
|
+ 'gssapi_delegation' Curl transport option.
|
|
+
|
|
+ Current Xmlrpc-c can be linked with, and compiled with, any version of
|
|
+ Curl, so it has to carefully consider all the possibilities.
|
|
+*/
|
|
+
|
|
+
|
|
+
|
|
+static bool
|
|
+curlAlwaysDelegatesGssapi(void) {
|
|
+/*----------------------------------------------------------------------------
|
|
+ The Curl library we're using always delegates GSSAPI credentials
|
|
+ (we don't have a choice).
|
|
+
|
|
+ This works with Curl as distributed by the Curl project, but there are
|
|
+ other versions of Curl for which it doesn't -- those versions report
|
|
+ older version numbers but in fact don't always delegate. Some never
|
|
+ delegate, and some give the user the option.
|
|
+-----------------------------------------------------------------------------*/
|
|
+ curl_version_info_data * const curlInfoP =
|
|
+ curl_version_info(CURLVERSION_NOW);
|
|
+
|
|
+ return (curlInfoP->version_num <= 0x071506); /* 7.21.6 */
|
|
+}
|
|
+
|
|
+
|
|
+
|
|
+static void
|
|
+requestGssapiDelegation(CURL * const curlSessionP ATTR_UNUSED,
|
|
+ bool * const gotItP) {
|
|
+/*----------------------------------------------------------------------------
|
|
+ Set up the Curl session *curlSessionP to delegate its GSSAPI credentials to
|
|
+ the server.
|
|
+
|
|
+ Return *gotitP is true iff we succeed. We fail when the version of libcurl
|
|
+ for which we are compiled or to which we are linked is not capable of such
|
|
+ delegation.
|
|
+-----------------------------------------------------------------------------*/
|
|
+#if HAVE_CURL_GSSAPI_DELEGATION
|
|
+ int rc;
|
|
+
|
|
+ rc = curl_easy_setopt(curlSessionP, CURLOPT_GSSAPI_DELEGATION,
|
|
+ CURLGSSAPI_DELEGATION_FLAG);
|
|
+
|
|
+ if (rc == CURLE_OK)
|
|
+ *gotItP = true;
|
|
+ else {
|
|
+ /* The only way curl_easy_setopt() could have failed is that we
|
|
+ are running with an old libcurl from before
|
|
+ CURLOPT_GSSAPI_DELEGATION was invented.
|
|
+ */
|
|
+ if (curlAlwaysDelegatesGssapi()) {
|
|
+ /* No need to request delegation; we got it anyway */
|
|
+ *gotItP = true;
|
|
+ } else
|
|
+ *gotItP = false;
|
|
+ }
|
|
+#else
|
|
+ if (curlAlwaysDelegatesGssapi())
|
|
+ *gotItP = true;
|
|
+ else {
|
|
+ /* The library may be able to do credential delegation on request, but
|
|
+ we have no way to request it; the Curl for which we are compiled is
|
|
+ too old.
|
|
+ */
|
|
+ *gotItP = false;
|
|
+ }
|
|
+#endif
|
|
+}
|
|
+
|
|
+
|
|
+
|
|
static void
|
|
setupCurlSession(xmlrpc_env * const envP,
|
|
curlTransaction * const curlTransactionP,
|
|
@@ -482,7 +575,7 @@ setupCurlSession(xmlrpc_env * const envP,
|
|
a particular transaction finished.
|
|
*/
|
|
|
|
- /* It is out policy to do a libcurl call only where necessary, I.e. not
|
|
+ /* It is our policy to do a libcurl call only where necessary, I.e. not
|
|
to set what is the default anyhow. The reduction in calls may save
|
|
some time, but mostly, it will save us encountering rare bugs or
|
|
suffering from backward incompatibilities in future libcurl. I.e. we
|
|
@@ -593,7 +686,18 @@ setupCurlSession(xmlrpc_env * const envP,
|
|
if (curlSetupP->timeout)
|
|
setCurlTimeout(curlSessionP, curlSetupP->timeout);
|
|
|
|
- {
|
|
+ if (curlSetupP->gssapiDelegation) {
|
|
+ bool gotIt;
|
|
+ requestGssapiDelegation(curlSessionP, &gotIt);
|
|
+
|
|
+ if (!gotIt)
|
|
+ xmlrpc_faultf(envP, "Cannot honor 'gssapi_delegation' "
|
|
+ "Curl transport option. "
|
|
+ "This version of libcurl is not "
|
|
+ "capable of delegating GSSAPI credentials");
|
|
+ }
|
|
+
|
|
+ if (!envP->fault_occurred) {
|
|
const char * authHdrValue;
|
|
/* NULL means we don't have to construct an explicit
|
|
Authorization: header. non-null means we have to
|
|
diff --git a/lib/curl_transport/curltransaction.h b/lib/curl_transport/curltransaction.h
|
|
index 4edc365..585dcca 100644
|
|
--- a/lib/curl_transport/curltransaction.h
|
|
+++ b/lib/curl_transport/curltransaction.h
|
|
@@ -81,6 +81,9 @@ struct curlSetup {
|
|
unsigned int proxyType;
|
|
/* see enum curl_proxytype: CURLPROXY_HTTP, CURLPROXY_SOCKS4, ... */
|
|
|
|
+ bool gssapiDelegation;
|
|
+ /* allow GSSAPI credential delegation */
|
|
+
|
|
unsigned int timeout;
|
|
/* 0 = no Curl timeout. This is in milliseconds. */
|
|
|
|
diff --git a/lib/curl_transport/curlversion.h b/lib/curl_transport/curlversion.h
|
|
index 71c5a68..4ad445a 100644
|
|
--- a/lib/curl_transport/curlversion.h
|
|
+++ b/lib/curl_transport/curlversion.h
|
|
@@ -14,6 +14,12 @@
|
|
#define HAVE_CURL_STRERROR 0
|
|
#endif
|
|
|
|
+#ifdef CURLGSSAPI_DELEGATION_FLAG
|
|
+#define HAVE_CURL_GSSAPI_DELEGATION 1
|
|
+#else
|
|
+#define HAVE_CURL_GSSAPI_DELEGATION 0
|
|
+#endif
|
|
+
|
|
#undef CMAJOR
|
|
#undef CMINOR
|
|
|
|
diff --git a/lib/curl_transport/xmlrpc_curl_transport.c b/lib/curl_transport/xmlrpc_curl_transport.c
|
|
index c48b927..9fedcda 100644
|
|
--- a/lib/curl_transport/xmlrpc_curl_transport.c
|
|
+++ b/lib/curl_transport/xmlrpc_curl_transport.c
|
|
@@ -836,6 +836,11 @@ getXportParms(xmlrpc_env * const envP,
|
|
else
|
|
curlSetupP->proxyType = curlXportParmsP->proxy_type;
|
|
|
|
+ if (!curlXportParmsP || parmSize < XMLRPC_CXPSIZE(gssapi_delegation))
|
|
+ curlSetupP->gssapiDelegation = false;
|
|
+ else
|
|
+ curlSetupP->gssapiDelegation = !!curlXportParmsP->gssapi_delegation;
|
|
+
|
|
getTimeoutParm(envP, curlXportParmsP, parmSize, &curlSetupP->timeout);
|
|
}
|
|
|
|
diff --git a/src/cpp/curl.cpp b/src/cpp/curl.cpp
|
|
index 9f38ffb..24a84ff 100644
|
|
--- a/src/cpp/curl.cpp
|
|
+++ b/src/cpp/curl.cpp
|
|
@@ -157,6 +157,7 @@ struct clientXmlTransport_curl::constrOpt_impl {
|
|
unsigned int proxy_port;
|
|
std::string proxy_userpwd;
|
|
xmlrpc_httpproxytype proxy_type;
|
|
+ bool gssapi_delegation;
|
|
} value;
|
|
struct {
|
|
bool network_interface;
|
|
@@ -184,6 +185,7 @@ struct clientXmlTransport_curl::constrOpt_impl {
|
|
bool proxy_port;
|
|
bool proxy_userpwd;
|
|
bool proxy_type;
|
|
+ bool gssapi_delegation;
|
|
} present;
|
|
};
|
|
|
|
@@ -214,6 +216,7 @@ clientXmlTransport_curl::constrOpt_impl::constrOpt_impl() {
|
|
present.proxy_auth = false;
|
|
present.proxy_userpwd = false;
|
|
present.proxy_type = false;
|
|
+ present.gssapi_delegation = false;
|
|
}
|
|
|
|
|
|
@@ -251,6 +254,7 @@ DEFINE_OPTION_SETTER(proxy_port, unsigned int);
|
|
DEFINE_OPTION_SETTER(proxy_auth, unsigned int);
|
|
DEFINE_OPTION_SETTER(proxy_userpwd, string);
|
|
DEFINE_OPTION_SETTER(proxy_type, xmlrpc_httpproxytype);
|
|
+DEFINE_OPTION_SETTER(gssapi_delegation, bool);
|
|
|
|
#undef DEFINE_OPTION_SETTER
|
|
|
|
@@ -333,6 +337,8 @@ clientXmlTransport_curl::initialize(constrOpt const& optExt) {
|
|
opt.value.proxy_userpwd.c_str() : NULL;
|
|
transportParms.proxy_type = opt.present.proxy_type ?
|
|
opt.value.proxy_type : XMLRPC_HTTPPROXY_HTTP;
|
|
+ transportParms.gssapi_delegation = opt.present.gssapi_delegation ?
|
|
+ opt.value.gssapi_delegation : false;
|
|
|
|
this->c_transportOpsP = &xmlrpc_curl_transport_ops;
|
|
|
|
@@ -340,7 +346,7 @@ clientXmlTransport_curl::initialize(constrOpt const& optExt) {
|
|
|
|
xmlrpc_curl_transport_ops.create(
|
|
&env.env_c, 0, "", "",
|
|
- &transportParms, XMLRPC_CXPSIZE(proxy_userpwd),
|
|
+ &transportParms, XMLRPC_CXPSIZE(gssapi_delegation),
|
|
&this->c_transportP);
|
|
|
|
if (env.env_c.fault_occurred)
|
|
--
|
|
1.7.7.5
|
|
|