File cups-2.2.7-CVE-2025-61915.patch of Package cups.41695

--- conf/cups-files.conf.in.orig	2018-03-23 04:48:36.000000000 +0100
+++ conf/cups-files.conf.in	2025-11-20 11:58:16.175792403 +0100
@@ -19,6 +19,9 @@
 SystemGroup @CUPS_SYSTEM_GROUPS@
 @CUPS_SYSTEM_AUTHKEY@
 
+# Are Unix domain socket peer credentials used for authorization?
+PeerCred @CUPS_PEER_CRED@
+
 # User that is substituted for unauthenticated (remote) root accesses...
 #RemoteRoot remroot
 
--- config-scripts/cups-defaults.m4.orig	2018-03-23 04:48:36.000000000 +0100
+++ config-scripts/cups-defaults.m4	2025-11-20 12:02:22.626167522 +0100
@@ -94,6 +94,15 @@ AC_ARG_WITH(log_level, [  --with-log-lev
 	CUPS_LOG_LEVEL="warn")
 AC_SUBST(CUPS_LOG_LEVEL)
 AC_DEFINE_UNQUOTED(CUPS_DEFAULT_LOG_LEVEL, "$CUPS_LOG_LEVEL")
+dnl Default PeerCred
+
+AC_ARG_WITH([peer_cred], AS_HELP_STRING([--with-peer-cred], [set default PeerCred value (on/off/root-only), default=on]), [
+    CUPS_PEER_CRED="$withval"
+], [
+    CUPS_PEER_CRED="on"
+])
+AC_SUBST([CUPS_PEER_CRED])
+AC_DEFINE_UNQUOTED([CUPS_DEFAULT_PEER_CRED], ["$CUPS_PEER_CRED"], [Default PeerCred value.])
 
 dnl Default AccessLogLevel
 AC_ARG_WITH(access_log_level, [  --with-access-log-level set default AccessLogLevel value, default=none],
--- config.h.in.orig	2018-03-23 04:48:36.000000000 +0100
+++ config.h.in	2025-11-20 12:03:55.083071269 +0100
@@ -88,6 +88,13 @@
 
 
 /*
+ * Default PeerCred value...
+ */
+
+#define CUPS_DEFAULT_PEER_CRED "on"
+
+
+/*
  * Default MaxCopies value...
  */
 
--- configure.orig	2018-03-23 04:48:36.000000000 +0100
+++ configure	2025-11-20 12:24:55.819219701 +0100
@@ -649,6 +649,7 @@ CUPS_BROWSE_LOCAL_PROTOCOLS
 CUPS_BROWSING
 CUPS_PAGE_LOG_FORMAT
 CUPS_ACCESS_LOG_LEVEL
+CUPS_PEER_CRED
 CUPS_LOG_LEVEL
 CUPS_FATAL_ERRORS
 CUPS_LOG_FILE_PERM
@@ -908,6 +909,7 @@ with_cupsd_file_perm
 with_log_file_perm
 with_fatal_errors
 with_log_level
+with_peer_cred
 with_access_log_level
 enable_page_logging
 enable_browsing
@@ -1632,6 +1634,7 @@ Optional Packages:
   --with-log-file-perm    set default LogFilePerm value, default=0644
   --with-fatal-errors     set default FatalErrors value, default=config
   --with-log-level        set default LogLevel value, default=warn
+  --with-peer-cred        set default PeerCred value (on/off/root-only), default=on
   --with-access-log-level set default AccessLogLevel value, default=none
   --with-local-protocols  set default BrowseLocalProtocols, default=""
   --with-cups-user        set default user for CUPS
@@ -9608,6 +9611,17 @@ cat >>confdefs.h <<_ACEOF
 _ACEOF
 
 
+# Check whether --with-peer_cred was given.
+if test "${with_peer_cred+set}" = set; then :
+  withval=$with_peer_cred; CUPS_PEER_CRED="$withval"
+else
+  CUPS_PEER_CRED="on"
+fi
+
+cat >>confdefs.h <<_ACEOF
+#define CUPS_DEFAULT_PEER_CRED "$CUPS_PEER_CRED"
+_ACEOF
+
 
 # Check whether --with-access_log_level was given.
 if test "${with_access_log_level+set}" = set; then :
--- scheduler/auth.c.orig	2025-09-03 09:46:21.127995909 +0200
+++ scheduler/auth.c	2025-11-20 12:39:00.819105309 +0100
@@ -403,7 +403,7 @@ cupsdAuthorize(cupsd_client_t *con)	/* I
   }
 #endif /* HAVE_AUTHORIZATION_H */
 #if defined(SO_PEERCRED) && defined(AF_LOCAL)
-  else if (!strncmp(authorization, "PeerCred ", 9) &&
+  else if (PeerCred != CUPSD_PEERCRED_OFF && !strncmp(authorization, "PeerCred ", 9) &&
            con->http->hostaddr->addr.sa_family == AF_LOCAL && con->best)
   {
    /*
@@ -446,6 +446,12 @@ cupsdAuthorize(cupsd_client_t *con)	/* I
     }
 #endif /* HAVE_AUTHORIZATION_H */
 
+    if ((PeerCred == CUPSD_PEERCRED_ROOTONLY || httpGetState(con->http) == HTTP_STATE_PUT_RECV) && strcmp(authorization + 9, "root"))
+    {
+      cupsdLogClient(con, CUPSD_LOG_INFO, "User \"%s\" is not allowed to use peer credentials.", authorization + 9);
+      return;
+    }
+
     if ((pwd = getpwnam(authorization + 9)) == NULL)
     {
       cupsdLogClient(con, CUPSD_LOG_ERROR, "User \"%s\" does not exist.", authorization + 9);
--- scheduler/auth.h.orig	2018-03-23 04:48:36.000000000 +0100
+++ scheduler/auth.h	2025-11-20 12:43:18.049684461 +0100
@@ -52,6 +52,10 @@
 #define CUPSD_AUTH_LIMIT_ALL	127	/* Limit all requests */
 #define CUPSD_AUTH_LIMIT_IPP	128	/* Limit IPP requests */
 
+#define CUPSD_PEERCRED_OFF	0	/* Don't allow PeerCred authorization */
+#define CUPSD_PEERCRED_ON	1	/* Allow PeerCred authorization for all users */
+#define CUPSD_PEERCRED_ROOTONLY	2	/* Allow PeerCred authorization for root user */
+
 #define IPP_ANY_OPERATION	(ipp_op_t)0
 					/* Any IPP operation */
 #define IPP_BAD_OPERATION	(ipp_op_t)-1
@@ -109,6 +113,9 @@ typedef struct cupsd_client_s cupsd_clie
 
 VAR cups_array_t	*Locations	VALUE(NULL);
 					/* Authorization locations */
+VAR int			PeerCred	VALUE(CUPSD_PEERCRED_ON);
+					/* Allow PeerCred authorization? */
+
 #ifdef HAVE_SSL
 VAR http_encryption_t	DefaultEncryption VALUE(HTTP_ENCRYPT_REQUIRED);
 					/* Default encryption for authentication */
--- scheduler/client.c.orig	2025-11-20 14:19:09.633650915 +0100
+++ scheduler/client.c	2025-11-20 14:19:18.777732647 +0100
@@ -2371,7 +2371,7 @@ cupsdSendHeader(
       auth_size = sizeof(auth_str) - (size_t)(auth_key - auth_str);
 
 #if defined(SO_PEERCRED) && defined(AF_LOCAL)
-      if (httpAddrFamily(httpGetAddress(con->http)) == AF_LOCAL)
+      if (PeerCred != CUPSD_PEERCRED_OFF && httpAddrFamily(httpGetAddress(con->http)) == AF_LOCAL)
       {
         strlcpy(auth_key, ", PeerCred", auth_size);
         auth_key += 10;
--- test/run-stp-tests.sh.orig	2025-11-20 14:19:02.525587381 +0100
+++ test/run-stp-tests.sh	2025-11-20 14:39:37.153909936 +0100
@@ -513,7 +513,7 @@ fi
 
 cat >$BASE/cups-files.conf <<EOF
 FileDevice yes
-Printcap
+Printcap $BASE/printcap
 User $user
 ServerRoot $BASE
 StateDir $BASE
--- vcnet/config.h.orig	2018-03-23 04:48:36.000000000 +0100
+++ vcnet/config.h	2025-11-20 14:42:19.895554432 +0100
@@ -164,6 +164,13 @@ typedef unsigned long useconds_t;
 
 
 /*
+ * Default PeerCred value...
+ */
+
+#define CUPS_DEFAULT_PEER_CRED "on"
+
+
+/*
  * Default MaxCopies value...
  */
 
--- xcode/CUPS.xcodeproj/project.pbxproj.orig	2025-11-20 14:42:52.259882033 +0100
+++ xcode/CUPS.xcodeproj/project.pbxproj	2025-11-20 14:44:01.176579525 +0100
@@ -3400,7 +3400,6 @@
 		72220FB313330BCE00FCA411 /* mime.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; name = mime.c; path = ../scheduler/mime.c; sourceTree = "<group>"; };
 		72220FB413330BCE00FCA411 /* mime.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = mime.h; path = ../scheduler/mime.h; sourceTree = "<group>"; };
 		72220FB513330BCE00FCA411 /* type.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; name = type.c; path = ../scheduler/type.c; sourceTree = "<group>"; };
-		7226369B18AE6D19004ED309 /* org.cups.cups-lpd.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; name = "org.cups.cups-lpd.plist"; path = "../scheduler/org.cups.cups-lpd.plist"; sourceTree = SOURCE_ROOT; };
 		7226369C18AE6D19004ED309 /* org.cups.cupsd.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; name = org.cups.cupsd.plist; path = ../scheduler/org.cups.cupsd.plist; sourceTree = SOURCE_ROOT; };
 		7226369D18AE73BB004ED309 /* config.h.in */ = {isa = PBXFileReference; lastKnownFileType = text; name = config.h.in; path = ../config.h.in; sourceTree = "<group>"; };
 		7234F41F1378A16F00D3E9C9 /* array-private.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = "array-private.h"; path = "../cups/array-private.h"; sourceTree = "<group>"; };
@@ -4982,7 +4981,6 @@
 			isa = PBXGroup;
 			children = (
 				72E65BDC18DC852700097E89 /* Makefile */,
-				7226369B18AE6D19004ED309 /* org.cups.cups-lpd.plist */,
 				72E65BD518DC818400097E89 /* org.cups.cups-lpd.plist.in */,
 				72496E171A13A03B0051899C /* org.cups.cups-lpdAT.service.in */,
 				72496E161A13A03B0051899C /* org.cups.cups-lpd.socket */,
--- xcode/config.h.orig	2018-03-23 04:48:36.000000000 +0100
+++ xcode/config.h	2025-11-20 14:47:40.598804446 +0100
@@ -92,6 +92,13 @@
 
 
 /*
+ * Default PeerCred value...
+ */
+
+#define CUPS_DEFAULT_PEER_CRED "on"
+
+
+/*
  * Default MaxCopies value...
  */
 
--- doc/help/man-cups-files.conf.html.orig	2025-11-20 14:18:54.401514766 +0100
+++ doc/help/man-cups-files.conf.html	2025-11-20 15:01:51.675513345 +0100
@@ -118,6 +118,13 @@ The default is "/var/log/cups/page_log".
 <dt><a name="PassEnv"></a><b>PassEnv </b><i>variable </i>[ ... <i>variable </i>]
 <dd style="margin-left: 5.0em">Passes the specified environment variable(s) to child processes.
 Note: the standard CUPS filter and backend environment variables cannot be overridden using this directive.
+<dt><a name="PeerCred"></a><b>PeerCred off</b>
+<dd style="margin-left: 5.0em"><dt><b>PeerCred on</b>
+<dd style="margin-left: 5.0em"><dt><b>PeerCred root-only</b>
+<dd style="margin-left: 5.0em">Specifies whether peer credentials are used for authorization when communicating over the UNIX domain socket.
+When <b>on</b>, the peer credentials of any user are accepted for authorization.
+The value <b>off</b> disables the use of peer credentials entirely, while the value <b>root-only</b> allows peer credentials only for the root user.
+Note: for security reasons, the <b>on</b> setting is reduced to <b>root-only</b> for authorization of PUT requests.
 <dt><a name="RemoteRoot"></a><b>RemoteRoot </b><i>username</i>
 <dd style="margin-left: 5.0em">Specifies the username that is associated with unauthenticated accesses by clients claiming to be the root user.
 The default is "remroot".
--- man/cups-files.conf.man.in.orig	2025-11-20 14:18:54.401514766 +0100
+++ man/cups-files.conf.man.in	2025-11-20 15:03:45.344682408 +0100
@@ -162,6 +162,17 @@ The default is "/var/log/cups/page_log".
 \fBPassEnv \fIvariable \fR[ ... \fIvariable \fR]
 Passes the specified environment variable(s) to child processes.
 Note: the standard CUPS filter and backend environment variables cannot be overridden using this directive.
+.\"#PeerCred
+.TP 5
+\fBPeerCred off\fR
+.TP 5
+\fBPeerCred on\fR
+.TP 5
+\fBPeerCred root-only\fR
+Specifies whether peer credentials are used for authorization when communicating over the UNIX domain socket.
+When \fBon\fR, the peer credentials of any user are accepted for authorization.
+The value \fBoff\fR disables the use of peer credentials entirely, while the value \fBroot-only\fR allows peer credentials only for the root user.
+Note: for security reasons, the \fBon\fR setting is reduced to \fBroot-only\fR for authorization of PUT requests.
 .\"#RemoteRoot
 .TP 5
 \fBRemoteRoot \fIusername\fR
--- scheduler/conf.c.orig	2025-11-20 14:19:13.697687239 +0100
+++ scheduler/conf.c	2025-11-21 12:27:05.019150174 +0100
@@ -49,6 +49,7 @@ typedef enum
 {
   CUPSD_VARTYPE_INTEGER,		/* Integer option */
   CUPSD_VARTYPE_TIME,			/* Time interval option */
+  CUPSD_VARTYPE_NULLSTRING,		/* String option or NULL/empty string */
   CUPSD_VARTYPE_STRING,			/* String option */
   CUPSD_VARTYPE_BOOLEAN,		/* Boolean option */
   CUPSD_VARTYPE_PATHNAME,		/* File/directory name option */
@@ -71,7 +72,7 @@ static const cupsd_var_t	cupsd_vars[] =
 {
   { "AutoPurgeJobs", 		&JobAutoPurge,		CUPSD_VARTYPE_BOOLEAN },
 #if defined(HAVE_DNSSD) || defined(HAVE_AVAHI)
-  { "BrowseDNSSDSubTypes",	&DNSSDSubTypes,		CUPSD_VARTYPE_STRING },
+  { "BrowseDNSSDSubTypes",	&DNSSDSubTypes,		CUPSD_VARTYPE_NULLSTRING },
 #endif /* HAVE_DNSSD || HAVE_AVAHI */
   { "BrowseWebIF",		&BrowseWebIF,		CUPSD_VARTYPE_BOOLEAN },
   { "Browsing",			&Browsing,		CUPSD_VARTYPE_BOOLEAN },
@@ -121,7 +122,7 @@ static const cupsd_var_t	cupsd_vars[] =
   { "MaxSubscriptionsPerPrinter",&MaxSubscriptionsPerPrinter,	CUPSD_VARTYPE_INTEGER },
   { "MaxSubscriptionsPerUser",	&MaxSubscriptionsPerUser,	CUPSD_VARTYPE_INTEGER },
   { "MultipleOperationTimeout",	&MultipleOperationTimeout,	CUPSD_VARTYPE_TIME },
-  { "PageLogFormat",		&PageLogFormat,		CUPSD_VARTYPE_STRING },
+  { "PageLogFormat",		&PageLogFormat,		CUPSD_VARTYPE_NULLSTRING },
   { "PreserveJobFiles",		&JobFiles,		CUPSD_VARTYPE_TIME },
   { "PreserveJobHistory",	&JobHistory,		CUPSD_VARTYPE_TIME },
   { "ReloadTimeout",		&ReloadTimeout,		CUPSD_VARTYPE_TIME },
@@ -782,6 +783,13 @@ cupsdReadConfiguration(void)
   IdleExitTimeout = 60;
 #endif /* HAVE_ONDEMAND */
 
+  if (!strcmp(CUPS_DEFAULT_PEER_CRED, "off"))
+    PeerCred = CUPSD_PEERCRED_OFF;
+  else if (!strcmp(CUPS_DEFAULT_PEER_CRED, "root-only"))
+    PeerCred = CUPSD_PEERCRED_ROOTONLY;
+  else
+    PeerCred = CUPSD_PEERCRED_ON;
+
  /*
   * Setup environment variables...
   */
@@ -1802,7 +1810,7 @@ get_addr_and_mask(const char *value,	/*
 
     family  = AF_INET6;
 
-    for (i = 0, ptr = value + 1; *ptr && i < 8; i ++)
+    for (i = 0, ptr = value + 1; *ptr && i >= 0 && i < 8; i ++)
     {
       if (*ptr == ']')
         break;
@@ -1951,7 +1959,7 @@ get_addr_and_mask(const char *value,	/*
 #ifdef AF_INET6
       if (family == AF_INET6)
       {
-        if (i > 128)
+        if (i < 0 || i > 128)
 	  return (0);
 
         i = 128 - i;
@@ -1985,7 +1993,7 @@ get_addr_and_mask(const char *value,	/*
       else
 #endif /* AF_INET6 */
       {
-        if (i > 32)
+        if (i < 0 || i > 32)
 	  return (0);
 
         mask[0] = 0xffffffff;
@@ -2895,7 +2903,17 @@ parse_variable(
 	cupsdSetString((char **)var->ptr, temp);
 	break;
 
+    case CUPSD_VARTYPE_NULLSTRING :
+	cupsdSetString((char **)var->ptr, value);
+	break;
+
     case CUPSD_VARTYPE_STRING :
+        if (!value)
+        {
+	  cupsdLogMessage(CUPSD_LOG_ERROR, "Missing value for %s on line %d of %s.", line, linenum, filename);
+	  return (0);
+        }
+
 	cupsdSetString((char **)var->ptr, value);
 	break;
   }
@@ -3404,9 +3422,10 @@ read_cupsd_conf(cups_file_t *fp)	/* I -
 		      line, value ? " " : "", value ? value : "", linenum,
 		      ConfigurationFile, CupsFilesFile);
     }
-    else
-      parse_variable(ConfigurationFile, linenum, line, value,
-                     sizeof(cupsd_vars) / sizeof(cupsd_vars[0]), cupsd_vars);
+    else if (!parse_variable(ConfigurationFile, linenum, line, value,
+			     sizeof(cupsd_vars) / sizeof(cupsd_vars[0]), cupsd_vars) &&
+	     (FatalErrors & CUPSD_FATAL_CONFIG))
+      return (0);
   }
 
   return (1);
@@ -3541,6 +3560,31 @@ read_cups_files_conf(cups_file_t *fp)	/*
 	    break;
       }
     }
+    else if (!_cups_strcasecmp(line, "PeerCred") && value)
+    {
+     /*
+      * PeerCred {off,on,root-only}
+      */
+
+      if (!_cups_strcasecmp(value, "off"))
+      {
+        PeerCred = CUPSD_PEERCRED_OFF;
+      }
+      else if (!_cups_strcasecmp(value, "on"))
+      {
+        PeerCred = CUPSD_PEERCRED_ON;
+      }
+      else if (!_cups_strcasecmp(value, "root-only"))
+      {
+        PeerCred = CUPSD_PEERCRED_ROOTONLY;
+      }
+      else
+      {
+	cupsdLogMessage(CUPSD_LOG_ERROR, "Unknown PeerCred \"%s\" on line %d of %s.", value, linenum, CupsFilesFile);
+        if (FatalErrors & CUPSD_FATAL_CONFIG)
+          return (0);
+      }
+    }
     else if (!_cups_strcasecmp(line, "PrintcapFormat") && value)
     {
      /*
openSUSE Build Service is sponsored by