]> git.ipfire.org Git - thirdparty/curl.git/commitdiff
snpego_sspi: preserve distinction btw policy-only and uncond delegation
authorDaniel Stenberg <daniel@haxx.se>
Wed, 13 May 2026 07:55:36 +0000 (09:55 +0200)
committerDaniel Stenberg <daniel@haxx.se>
Wed, 13 May 2026 12:34:08 +0000 (14:34 +0200)
CURLOPT_GSSAPI_DELEGATION exposes distinct modes:
CURLGSSAPI_DELEGATION_POLICY_FLAG is documented as delegating only when
OK-AS-DELEGATE policy permits it, while CURLGSSAPI_DELEGATION_FLAG is
unconditional. The new SSPI implementation checks for either bit and
sets ISC_REQ_DELEGATE, so a caller requesting policy-limited delegation
is put on the same SSPI path as unconditional delegation.

In addition, curl's existing protection that avoids reusing a connection
when the GSS delegation setting differs was guarded only by HAVE_GSSAPI;
SSPI-only builds now have an effective delegation option, but the
connection's delegation setting was neither copied nor compared. This
would cause Windows SSPI Negotiate/Kerberos authentication to delegate
credentials contrary to the caller's selected policy or reuse an
already-delegated authenticated connection for a transfer that requested
no delegation.

Follow-up to cc6777d939976b2f322dcbe5a

Reported by Codex Security
Closes #21583

lib/url.c
lib/vauth/spnego_sspi.c

index 5159b25e50cadb37906aae942cac6d3c48ee8258..bcd8f54aa8aa131a17e7e1fab69f3fb9bef730d1 100644 (file)
--- a/lib/url.c
+++ b/lib/url.c
@@ -943,9 +943,9 @@ static bool url_match_auth(struct connectdata *conn,
     if(!Curl_creds_same(m->data->state.creds, conn->creds))
       return FALSE;
   }
-#ifdef HAVE_GSSAPI
-  /* GSS delegation differences do not actually affect every connection
-     and auth method, but this check takes precaution before efficiency */
+#if defined(HAVE_GSSAPI) || defined(USE_WINDOWS_SSPI)
+  /* GSS delegation differences do not actually affect every connection and
+     auth method, but this check takes precaution before efficiency */
   if(m->needle->gssapi_delegation != conn->gssapi_delegation)
     return FALSE;
 #endif
@@ -1340,7 +1340,7 @@ static struct connectdata *allocate_conn(struct Curl_easy *data)
   conn->fclosesocket = data->set.fclosesocket;
   conn->closesocket_client = data->set.closesocket_client;
   conn->lastused = conn->created;
-#ifdef HAVE_GSSAPI
+#if defined(HAVE_GSSAPI) || defined(USE_WINDOWS_SSPI)
   conn->gssapi_delegation = data->set.gssapi_delegation;
 #endif
   DEBUGF(infof(data, "alloc connection, bits.close=%d", conn->bits.close));
index d636dfbed49cbcbe7af5dfa045059f3707311dce..8808631e49a46febf100a12ae47a960871a57767 100644 (file)
@@ -227,8 +227,7 @@ CURLcode Curl_auth_decode_spnego_message(struct Curl_easy *data,
   /* Generate our challenge-response message */
   {
     DWORD sspi_flags = ISC_REQ_CONFIDENTIALITY;
-    if(data->set.gssapi_delegation & (CURLGSSAPI_DELEGATION_FLAG |
-                                      CURLGSSAPI_DELEGATION_POLICY_FLAG))
+    if(data->set.gssapi_delegation & CURLGSSAPI_DELEGATION_FLAG)
       sspi_flags |= ISC_REQ_DELEGATE | ISC_REQ_MUTUAL_AUTH;
     nego->status =
       Curl_pSecFn->InitializeSecurityContext(nego->credentials,