]> git.ipfire.org Git - thirdparty/cups.git/commitdiff
Non-Kerberized IPP printing to Windows was broken (Issue #5515)
authorMichael R Sweet <michael.r.sweet@gmail.com>
Fri, 15 Feb 2019 22:06:35 +0000 (17:06 -0500)
committerMichael R Sweet <michael.r.sweet@gmail.com>
Fri, 15 Feb 2019 22:06:35 +0000 (17:06 -0500)
CHANGES.md
cups/auth.c

index cc4369c525ccf958944857738957bebd8a5a5622..c74c9d2577020362e71ace281b2a6de9dcdcdde5 100644 (file)
@@ -1,4 +1,4 @@
-CHANGES - 2.3b8 - 2019-02-14
+CHANGES - 2.3b8 - 2019-02-15
 ============================
 
 
@@ -21,6 +21,7 @@ Changes in CUPS v2.3b8
   Everywhere printer differently, resulting in different PPDs for the same
   printer (Issue #5484)
 - The web interface no longer provides access to the log files (Issue #5513)
+- Non-Kerberized printing to Windows via IPP was broken (Issue #5515)
 - Eliminated use of private headers and some deprecated macOS APIs (Issue #5516)
 - Localization updates (Issue #5461, Issues #5471, Issue #5481, Issue #5486,
   Issue #5489, Issue #5491, Issue #5492, Issue #5493, Issue #5494, Issue #5495,
index 0f7fd523a98c0790338b3f21b01beeec39975e93..634ed1fba2a2eb9bd8f33a2c4f50f7cd08874a52 100644 (file)
@@ -42,6 +42,9 @@ static const char     *cups_auth_param(const char *scheme, const char *name, char *v
 static const char      *cups_auth_scheme(const char *www_authenticate, char *scheme, size_t schemesize);
 
 #ifdef HAVE_GSSAPI
+#  define CUPS_GSS_OK  0               /* Successfully set credentials */
+#  define CUPS_GSS_NONE        -1              /* No credentials */
+#  define CUPS_GSS_FAIL        -2              /* Failed credentials/authentication */
 #  ifdef HAVE_GSS_ACQUIRE_CRED_EX_F
 #    ifdef HAVE_GSS_GSSAPI_SPI_H
 #      include <GSS/gssapi_spi.h>
@@ -168,6 +171,8 @@ cupsDoAuthentication(
     * Check the scheme name...
     */
 
+    DEBUG_printf(("2cupsDoAuthentication: Trying scheme \"%s\"...", scheme));
+
 #ifdef HAVE_GSSAPI
     if (!_cups_strcasecmp(scheme, "Negotiate"))
     {
@@ -175,18 +180,36 @@ cupsDoAuthentication(
       * Kerberos authentication...
       */
 
-      if (_cupsSetNegotiateAuthString(http, method, resource))
+      int gss_status;                  /* Auth status */
+
+      if ((gss_status = _cupsSetNegotiateAuthString(http, method, resource)) == CUPS_GSS_FAIL)
       {
+        DEBUG_puts("1cupsDoAuthentication: Negotiate failed.");
        http->status = HTTP_STATUS_CUPS_AUTHORIZATION_CANCELED;
        return (-1);
       }
-
-      break;
+      else if (gss_status == CUPS_GSS_NONE)
+      {
+        DEBUG_puts("2cupsDoAuthentication: No credentials for Negotiate.");
+        continue;
+      }
+      else
+      {
+        DEBUG_puts("2cupsDoAuthentication: Using Negotiate.");
+        break;
+      }
     }
     else
 #endif /* HAVE_GSSAPI */
     if (_cups_strcasecmp(scheme, "Basic") && _cups_strcasecmp(scheme, "Digest"))
-      continue;                                /* Not supported (yet) */
+    {
+     /*
+      * Other schemes not yet supported...
+      */
+
+      DEBUG_printf(("2cupsDoAuthentication: Scheme \"%s\" not yet supported.", scheme));
+      continue;
+    }
 
    /*
     * See if we should retry the current username:password...
@@ -216,6 +239,7 @@ cupsDoAuthentication(
 
       if ((password = cupsGetPassword2(prompt, http, method, resource)) == NULL)
       {
+        DEBUG_puts("1cupsDoAuthentication: User canceled password request.");
        http->status = HTTP_STATUS_CUPS_AUTHORIZATION_CANCELED;
        return (-1);
       }
@@ -245,6 +269,7 @@ cupsDoAuthentication(
 
       char     encode[256];            /* Base64 buffer */
 
+      DEBUG_puts("2cupsDoAuthentication: Using Basic.");
       httpEncode64_2(encode, sizeof(encode), http->userpass, (int)strlen(http->userpass));
       httpSetAuthString(http, "Basic", encode);
       break;
@@ -263,19 +288,22 @@ cupsDoAuthentication(
       cups_auth_param(schemedata, "realm", http->realm, sizeof(http->realm));
 
       if (_httpSetDigestAuthString(http, nonce, method, resource))
+      {
+       DEBUG_puts("2cupsDoAuthentication: Using Basic.");
         break;
+      }
     }
   }
 
   if (http->authstring)
   {
-    DEBUG_printf(("1cupsDoAuthentication: authstring=\"%s\"", http->authstring));
+    DEBUG_printf(("1cupsDoAuthentication: authstring=\"%s\".", http->authstring));
 
     return (0);
   }
   else
   {
-    DEBUG_printf(("1cupsDoAuthentication: Unknown auth type: \"%s\"", www_auth));
+    DEBUG_puts("1cupsDoAuthentication: No supported schemes.");
     http->status = HTTP_STATUS_CUPS_AUTHORIZATION_CANCELED;
 
     return (-1);
@@ -288,7 +316,7 @@ cupsDoAuthentication(
  * '_cupsSetNegotiateAuthString()' - Set the Kerberos authentication string.
  */
 
-int                                    /* O - 0 on success, -1 on error */
+int                                    /* O - 0 on success, negative on error */
 _cupsSetNegotiateAuthString(
     http_t     *http,                  /* I - Connection to server */
     const char *method,                        /* I - Request method ("GET", "POST", "PUT") */
@@ -313,10 +341,16 @@ _cupsSetNegotiateAuthString(
   {
     DEBUG_puts("1_cupsSetNegotiateAuthString: Weak-linked GSSAPI/Kerberos "
                "framework is not present");
-    return (-1);
+    return (CUPS_GSS_NONE);
   }
 #  endif /* __APPLE__ */
 
+  if (!strcmp(http->hostname, "localhost") || http->hostname[0] == '/' || isdigit(http->hostname[0] & 255) || !strchr(http->hostname, '.'))
+  {
+    DEBUG_printf(("1_cupsSetNegotiateAuthString: Kerberos not available for host \"%s\".", http->hostname));
+    return (CUPS_GSS_NONE);
+  }
+
   if (http->gssname == GSS_C_NO_NAME)
   {
     http->gssname = cups_gss_getname(http, _cupsGSSServiceName());
@@ -361,7 +395,7 @@ _cupsSetNegotiateAuthString(
             cupsUser(), http->gsshost);
 
     if ((password = cupsGetPassword2(prompt, http, method, resource)) == NULL)
-      return (-1);
+      return (CUPS_GSS_FAIL);
 
    /*
     * Try to acquire credentials...
@@ -415,18 +449,20 @@ _cupsSetNegotiateAuthString(
   }
 #  endif /* HAVE_GSS_ACQUIRED_CRED_EX_F */
 
-  if (GSS_ERROR(major_status))
+  if (major_status == GSS_S_NO_CRED)
   {
-    cups_gss_printf(major_status, minor_status,
-                   "_cupsSetNegotiateAuthString: Unable to initialize "
-                   "security context");
-    return (-1);
+    cups_gss_printf(major_status, minor_status, "_cupsSetNegotiateAuthString: No credentials");
+    return (CUPS_GSS_NONE);
+  }
+  else if (GSS_ERROR(major_status))
+  {
+    cups_gss_printf(major_status, minor_status, "_cupsSetNegotiateAuthString: Unable to initialize security context");
+    return (CUPS_GSS_FAIL);
   }
 
 #  ifdef DEBUG
   else if (major_status == GSS_S_CONTINUE_NEEDED)
-    cups_gss_printf(major_status, minor_status,
-                   "_cupsSetNegotiateAuthString: Continuation needed!");
+    cups_gss_printf(major_status, minor_status, "_cupsSetNegotiateAuthString: Continuation needed");
 #  endif /* DEBUG */
 
   if (output_token.length > 0 && output_token.length <= 65536)
@@ -460,10 +496,10 @@ _cupsSetNegotiateAuthString(
                   "large - %d bytes!", (int)output_token.length));
     gss_release_buffer(&minor_status, &output_token);
 
-    return (-1);
+    return (CUPS_GSS_FAIL);
   }
 
-  return (0);
+  return (CUPS_GSS_OK);
 }
 #endif /* HAVE_GSSAPI */