80 lines
3.0 KiB
Diff
80 lines
3.0 KiB
Diff
From 1e2b77cd1661f2fb2565e21a558295e631763baa Mon Sep 17 00:00:00 2001
|
|
From: Jiri Popelka <jpopelka@redhat.com>
|
|
Date: Wed, 2 Apr 2014 09:57:32 +0200
|
|
Subject: [PATCH] cups-browsed: SECURITY FIX to prevent arbitrary code
|
|
injection (RHBZ#1083327)
|
|
|
|
into the System V interface scripts generated for
|
|
queues for discovered native IPP printers by a malicious IPP
|
|
print service with forged make/model and/or PDL string.
|
|
---
|
|
utils/cups-browsed.c | 31 +++++++++++++++++++++++++++----
|
|
1 file changed, 27 insertions(+), 4 deletions(-)
|
|
|
|
diff --git a/utils/cups-browsed.c b/utils/cups-browsed.c
|
|
index c312804..ec64a4d 100644
|
|
--- a/utils/cups-browsed.c
|
|
+++ b/utils/cups-browsed.c
|
|
@@ -563,7 +563,28 @@ create_local_queue (const char *name,
|
|
return NULL;
|
|
}
|
|
|
|
-char *generate_queue_name(const char *str_orig)
|
|
+/*
|
|
+ * Remove all illegal characters and replace each group of such characters
|
|
+ * by a single dash
|
|
+ *
|
|
+ * mode = 0: Only allow letters, numbers, and dashes, for turning make/model
|
|
+ * info into a valid print queue name or inro a string which can
|
|
+ * be supplied as option value in a filter command line without
|
|
+ * need of quoting
|
|
+ * mode = 1: Allow also '/', '.', ',', '_', for cleaning up MIME type
|
|
+ * strings (here available Page Description Languages, PDLs) to
|
|
+ * supply them on a filter command line without quoting
|
|
+ *
|
|
+ * Especially this prevents from arbitrary code execution by interface scripts
|
|
+ * generated for print queues to native IPP printers when a malicious IPP
|
|
+ * print service with forged PDL and/or make/model info gets broadcasted into
|
|
+ * the local network.
|
|
+ */
|
|
+
|
|
+char * /* O - Cleaned string */
|
|
+remove_bad_chars(const char *str_orig, /* I - Original string */
|
|
+ int mode) /* I - 0: Make/Model, queue name */
|
|
+ /* 1: MIME types/PDLs */
|
|
{
|
|
int i, j;
|
|
int havedash = 0;
|
|
@@ -576,7 +597,9 @@ char *generate_queue_name(const char *str_orig)
|
|
for (i = 0, j = 0; i < strlen(str); i++, j++) {
|
|
if (((str[i] >= 'A') && (str[i] <= 'Z')) ||
|
|
((str[i] >= 'a') && (str[i] <= 'z')) ||
|
|
- ((str[i] >= '0') && (str[i] <= '9'))) {
|
|
+ ((str[i] >= '0') && (str[i] <= '9')) ||
|
|
+ (mode == 1 && (str[i] == '/' || str[i] == '_' ||
|
|
+ str[i] == '.' || str[i] == ','))) {
|
|
/* Letter or number, keep it */
|
|
havedash = 0;
|
|
} else {
|
|
@@ -950,7 +973,7 @@ void generate_local_queue(const char *host,
|
|
if (entry) {
|
|
avahi_string_list_get_pair(entry, &key, &value, NULL);
|
|
if (key && value && !strcmp(key, *f) && strlen(value) >= 3) {
|
|
- remote_queue = generate_queue_name(value);
|
|
+ remote_queue = remove_bad_chars(value, 0);
|
|
break;
|
|
}
|
|
}
|
|
@@ -959,7 +982,7 @@ void generate_local_queue(const char *host,
|
|
if (entry) {
|
|
avahi_string_list_get_pair(entry, &key, &value, NULL);
|
|
if (key && value && !strcmp(key, "pdl") && strlen(value) >= 3) {
|
|
- pdl = strdup(value);
|
|
+ pdl = remove_bad_chars(value, 1);
|
|
}
|
|
}
|
|
}
|
|
--
|
|
1.9.0
|
|
|