Compare commits

..

7 commits

Author SHA1 Message Date
Zdenek Dohnal
30fbc6c913 cups-brf needs to be run as root 2019-02-01 14:42:56 +01:00
Zdenek Dohnal
864f0c58bb links in man page are wrong 2018-11-12 15:08:20 +01:00
Zdenek Dohnal
29ff2e9f76 1632267 - cups-filters needs to obsolete ghostscript-cups and foomatic-filters 2018-09-24 16:26:59 +02:00
Zdenek Dohnal
e778b74e1a fixed covscan issues 2018-09-21 16:00:58 +02:00
Zdenek Dohnal
f92ffeda2d add requires on cups, ghostscript and poppler-utils 2018-06-12 15:28:42 +02:00
Zdenek Dohnal
15c6c2c839 1572450 - cupsd: Filter "brftopagedbrf" not found. 2018-04-27 11:44:35 +02:00
Zdenek Dohnal
af099f65f7 dependency on poppler-utils is now only recommended 2018-04-05 13:11:04 +02:00
20 changed files with 2035 additions and 2734 deletions

View file

@ -1 +0,0 @@
1

85
.gitignore vendored
View file

@ -1 +1,84 @@
/cups-filters-*.tar.gz
/cups-filters-1.0.20.tar.xz
/cups-filters-1.0.22.tar.xz
/cups-filters-1.0.23.tar.xz
/cups-filters-1.0.24.tar.xz
/cups-filters-1.0.25.tar.xz
/cups-filters-1.0.28.tar.xz
/cups-filters-1.0.29.tar.xz
/cups-filters-1.0.30.tar.xz
/cups-filters-1.0.31.tar.xz
/cups-filters-1.0.32.tar.xz
/cups-filters-1.0.33.tar.xz
/cups-filters-1.0.34.tar.xz
/cups-filters-1.0.35.tar.xz
/cups-filters-1.0.36.tar.xz
/cups-filters-1.0.37.tar.xz
/cups-filters-1.0.38.tar.xz
/cups-filters-1.0.39.tar.xz
/cups-filters-1.0.40.tar.xz
/cups-filters-1.0.41.tar.xz
/cups-filters-1.0.42.tar.xz
/cups-filters-1.0.43.tar.xz
/cups-filters-1.0.44.tar.xz
/cups-filters-1.0.45.tar.xz
/cups-filters-1.0.46.tar.xz
/cups-filters-1.0.47.tar.xz
/cups-filters-1.0.48.tar.xz
/cups-filters-1.0.49.tar.xz
/cups-filters-1.0.50.tar.xz
/cups-filters-1.0.51.tar.xz
/cups-filters-1.0.52.tar.xz
/cups-filters-1.0.53.tar.xz
/cups-filters-1.0.54.tar.xz
/cups-filters-1.0.55.tar.xz
/cups-filters-1.0.58.tar.xz
/cups-filters-1.0.59.tar.xz
/cups-filters-1.0.60.tar.xz
/cups-filters-1.0.61.tar.xz
/cups-filters-1.0.65.tar.xz
/cups-filters-1.0.66.tar.xz
/cups-filters-1.0.67.tar.xz
/cups-filters-1.0.68.tar.xz
/cups-filters-1.0.69.tar.xz
/cups-filters-1.0.70.tar.xz
/cups-filters-1.0.71.tar.xz
/cups-filters-1.0.73.tar.xz
/cups-filters-1.0.74.tar.xz
/cups-filters-1.0.75.tar.xz
/cups-filters-1.0.76.tar.xz
/cups-filters-1.1.0.tar.xz
/cups-filters-1.2.0.tar.xz
/cups-filters-1.3.0.tar.xz
/cups-filters-1.4.0.tar.xz
/cups-filters-1.5.0.tar.xz
/cups-filters-1.6.0.tar.xz
/cups-filters-1.7.0.tar.xz
/cups-filters-1.8.0.tar.xz
/cups-filters-1.8.1.tar.xz
/cups-filters-1.8.2.tar.xz
/cups-filters-1.8.3.tar.xz
/cups-filters-1.9.0.tar.xz
/cups-filters-1.10.0.tar.xz
/cups-filters-1.11.2.tar.xz
/cups-filters-1.11.3.tar.xz
/cups-filters-1.11.4.tar.xz
/cups-filters-1.11.5.tar.xz
/cups-filters-1.11.6.tar.xz
/cups-filters-1.12.0.tar.xz
/cups-filters-1.13.0.tar.xz
/cups-filters-1.13.1.tar.xz
/cups-filters-1.13.2.tar.xz
/cups-filters-1.13.3.tar.xz
/cups-filters-1.13.4.tar.xz
/cups-filters-1.13.5.tar.xz
/cups-filters-1.14.0.tar.xz
/cups-filters-1.14.1.tar.xz
/cups-filters-1.16.0.tar.xz
/cups-filters-1.16.1.tar.xz
/cups-filters-1.16.3.tar.xz
/cups-filters-1.17.2.tar.xz
/cups-filters-1.17.7.tar.xz
/cups-filters-1.17.8.tar.xz
/cups-filters-1.17.9.tar.xz
/cups-filters-1.19.0.tar.xz
/cups-filters-1.20.0.tar.xz

View file

@ -1,27 +0,0 @@
From 44f59a1aa74c48515d8feba5a61b7ea3aaa592c4 Mon Sep 17 00:00:00 2001
From: Zdenek Dohnal <zdohnal@redhat.com>
Date: Fri, 24 Jan 2025 09:44:58 +0100
Subject: [PATCH] Fix build failure with GCC 15 and -std=c23
The newest standard has more strict data type checks, function pointers
in function prototypes have to declare data types of its arguments.
---
filter/foomatic-rip/process.h | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/filter/foomatic-rip/process.h b/filter/foomatic-rip/process.h
index f6e15f65c..54a42923a 100644
--- a/filter/foomatic-rip/process.h
+++ b/filter/foomatic-rip/process.h
@@ -18,7 +18,7 @@
#include <sys/wait.h>
-pid_t start_process(const char *name, int (*proc_func)(), void *user_arg,
+pid_t start_process(const char *name, int (*proc_func)(FILE*, FILE*, void*), void *user_arg,
FILE **fdin, FILE **fdout);
pid_t start_system_process(const char *name, const char *command, FILE **fdin,
FILE **fdout);
--
2.48.1

File diff suppressed because it is too large Load diff

View file

@ -1,79 +0,0 @@
From 0fe46c511e81062575b05936f804eb18c9f0a011 Mon Sep 17 00:00:00 2001
From: Zdenek Dohnal <zdohnal@redhat.com>
Date: Wed, 12 Nov 2025 15:47:24 +0100
Subject: [PATCH] rastertopclx.c: Fix infinite loop caused by crafted file
Infinite loop happened because of crafted input raster file, which led
into heap buffer overflow of `CompressBuf` array.
Based on comments there should be always some `count` when compressing
the data, and processing of crafted file ended with offset and count
being 0.
Fixes CVE-2025-64524
---
filter/rastertopclx.c | 25 +++++++++++++++++++++++--
1 file changed, 23 insertions(+), 2 deletions(-)
diff --git a/filter/rastertopclx.c b/filter/rastertopclx.c
index ded86f114..39cb378bf 100644
--- a/filter/rastertopclx.c
+++ b/filter/rastertopclx.c
@@ -825,10 +825,10 @@ StartPage(cf_filter_data_t *data, // I - filter data
}
if (header->cupsCompression)
- CompBuffer = malloc(DotBufferSize * 4);
+ CompBuffer = calloc(DotBufferSize * 4, sizeof(unsigned char));
if (header->cupsCompression >= 3)
- SeedBuffer = malloc(DotBufferSize);
+ SeedBuffer = calloc(DotBufferSize, sizeof(unsigned char));
SeedInvalid = 1;
@@ -1159,6 +1159,13 @@ CompressData(unsigned char *line, // I - Data to compress
seed ++;
count ++;
}
+
+ //
+ // Bail out if we don't have count to compress
+ //
+
+ if (count == 0)
+ break;
}
//
@@ -1252,6 +1259,13 @@ CompressData(unsigned char *line, // I - Data to compress
count = line_ptr - start;
+ //
+ // Bail out if we don't have count to compress
+ //
+
+ if (count == 0)
+ break;
+
#if 0
fprintf(stderr,
"DEBUG: offset=%d, count=%d, comp_ptr=%p(%d of %d)...\n",
@@ -1424,6 +1438,13 @@ CompressData(unsigned char *line, // I - Data to compress
count = (line_ptr - start) / 3;
+ //
+ // Bail out if we don't have count to compress
+ //
+
+ if (count == 0)
+ break;
+
//
// Place mode 10 compression data in the buffer; each sequence
// starts with a command byte that looks like:
--
2.51.1

1
ci.fmf
View file

@ -1 +0,0 @@
resultsdb-testcase: separate

14
cups-browsed.8.patch Normal file
View file

@ -0,0 +1,14 @@
diff -up cups-filters-1.20.0/utils/cups-browsed.8.manpage cups-filters-1.20.0/utils/cups-browsed.8
--- cups-filters-1.20.0/utils/cups-browsed.8.manpage 2018-11-12 14:14:48.436062013 +0100
+++ cups-filters-1.20.0/utils/cups-browsed.8 2018-11-12 14:19:10.188091043 +0100
@@ -100,8 +100,8 @@ and command line tools.
\fBcups-browsed.conf\fP(5)
.PP
-/usr/share/doc/\fBcups-browsed\fP/README.gz
+/usr/share/doc/cups-filters/README.gz
.SH AUTHOR
-The authors of \fBcups-browsed\fP are listed in /usr/share/doc/\fBcups-browsed\fP/AUTHORS.
+The authors of \fBcups-browsed\fP are listed in /usr/share/doc/cups-filters/AUTHORS.
.PP
This manual page was written for the Debian Project, but it may be used by others.

Binary file not shown.

View file

@ -0,0 +1,172 @@
diff -up cups-filters-1.20.0/configure.ac.brftopagedbrf-install cups-filters-1.20.0/configure.ac
--- cups-filters-1.20.0/configure.ac.brftopagedbrf-install 2018-01-29 19:14:59.000000000 +0100
+++ cups-filters-1.20.0/configure.ac 2018-04-27 11:19:33.987213243 +0200
@@ -856,6 +856,7 @@ AC_CONFIG_FILES([
filter/braille/filters/cups-braille.sh
filter/braille/filters/imagetobrf
filter/braille/filters/texttobrf
+ filter/braille/filters/brftopagedbrf
filter/braille/filters/vectortopdf
filter/braille/filters/vectortobrf
filter/braille/filters/musicxmltobrf
diff -up cups-filters-1.20.0/filter/braille/filters/brftopagedbrf.in.brftopagedbrf-install cups-filters-1.20.0/filter/braille/filters/brftopagedbrf.in
--- cups-filters-1.20.0/filter/braille/filters/brftopagedbrf.in.brftopagedbrf-install 2018-04-27 11:19:41.038152279 +0200
+++ cups-filters-1.20.0/filter/braille/filters/brftopagedbrf.in 2018-04-27 11:21:47.344068714 +0200
@@ -0,0 +1,146 @@
+#!/bin/bash
+
+#
+# Copyright (c) 2015-2017 Samuel Thibault <samuel.thibault@ens-lyon.org>
+#
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+#
+#
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+#
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+# THE SOFTWARE.
+#
+
+# Make sure we have enough options
+if [ $# != 5 -a $# != 6 ]; then
+ echo "ERROR: $0 jobid user name nb options [filename]" >&2
+ exit 1
+fi
+
+NB=$4
+OPTIONS=$5
+FILE=$6
+
+. @CUPS_DATADIR@/braille/cups-braille.sh
+
+shopt -s extglob
+
+# Construct list of pages from PAGERANGES
+
+PAGES=" " # Explicit list of pages
+AFTER= # All pages including and after this
+BEFORE= # All pages before and including this
+
+[ -n "$PAGERANGES" ] || PAGERANGES="1-"
+
+while [ -n "${PAGERANGES}" ]
+do
+ PAGERANGE=${PAGERANGES/,*}
+ PAGERANGE=${PAGERANGE%%*( )}
+ PAGERANGE=${PAGERANGE##*( )}
+ if [ -n "${PAGERANGES/*,*}" ]
+ then
+ # last range
+ PAGERANGES=""
+ else
+ # Remove leading range
+ PAGERANGES="${PAGERANGES#*,}"
+ fi
+
+ if [ -n "${PAGERANGE/*-*}" ]
+ then
+ # single-page
+ PAGES="$PAGES$PAGERANGE "
+
+ elif [ -z "${PAGERANGE%%*-}" ]
+ then
+ # To the end
+ FIRST=${PAGERANGE%%-*}
+ if [ -z "$AFTER" ] || [ "$FIRST" -lt "$AFTER" ]
+ then
+ AFTER="$FIRST"
+ fi
+
+ elif [ -z "${PAGERANGE##-*}" ]
+ then
+ # From the beginning
+ LAST=${PAGERANGE##*-}
+ if [ -z "$BEFORE" ] || [ "$LAST" -gt "$BEFORE" ]
+ then
+ BEFORE="$LAST"
+ fi
+
+ else
+ # page range
+ FIRST=${PAGERANGE/-*}
+ LAST=${PAGERANGE/*-}
+ PAGES="$PAGES$(seq "$FIRST" "$LAST" | tr $'\012' ' ')"
+
+ fi
+done
+
+# Determine whether to print this page
+doprint() {
+ PAGE="$1"
+ if [ -n "$BEFORE" ] && [ "$PAGE" -le "$BEFORE" ]
+ then
+ echo 1
+ return
+ elif [ -n "$AFTER" ] && [ "$PAGE" -ge "$AFTER" ]
+ then
+ echo 1
+ return
+ fi
+ case "$PAGES" in
+ *\ $PAGE\ *)
+ echo 1
+ return
+ ;;
+ esac
+ echo 0
+}
+
+if [ -z "$FILE" ]
+then
+ cat
+else
+ cat "$FILE"
+fi | (
+ P=1
+ DOPRINT=$(doprint $P)
+ while IFS=$'\n' read -r LINE
+ do
+ while [ -z "${LINE/*$'\014'*}" ]
+ do
+ # Possibly print before FF
+ HEAD=${LINE%%$'\014'*}
+ [ $DOPRINT == 0 ] || printf %s "$HEAD"$'\014'
+
+ # Next page
+ P=$(($P + 1))
+ DOPRINT=$(doprint $P)
+
+ # Drop head of line
+ LINE=${LINE#*$'\014'}
+ done
+
+ # Remainder of line
+ [ $DOPRINT == 0 ] || printf "%s\n" "$LINE"
+ done
+)
+
+echo "INFO: Ready" >&2
+exit 0
diff -up cups-filters-1.20.0/Makefile.am.brftopagedbrf-install cups-filters-1.20.0/Makefile.am
--- cups-filters-1.20.0/Makefile.am.brftopagedbrf-install 2017-12-15 02:15:32.000000000 +0100
+++ cups-filters-1.20.0/Makefile.am 2018-04-27 11:19:33.987213243 +0200
@@ -591,6 +591,7 @@ nodist_pkgfilter_SCRIPTS = \
filter/braille/filters/vectortopdf \
filter/braille/filters/vectortobrf \
filter/braille/filters/texttobrf \
+ filter/braille/filters/brftopagedbrf \
filter/braille/filters/musicxmltobrf
endif

678
cups-filters-covscan.patch Normal file
View file

@ -0,0 +1,678 @@
diff --git a/backend/beh.c b/backend/beh.c
index 9ba6613..7514e33 100644
--- a/backend/beh.c
+++ b/backend/beh.c
@@ -223,6 +223,8 @@ call_backend(char *uri, /* I - URI of final destination */
*/
strncpy(scheme, uri, sizeof(scheme));
+ if (strlen(uri) > 1023)
+ scheme[1023] = '\0';
if ((ptr = strchr(scheme, ':')) != NULL)
*ptr = '\0';
diff --git a/backend/implicitclass.c b/backend/implicitclass.c
index 3ce4d10..1593191 100644
--- a/backend/implicitclass.c
+++ b/backend/implicitclass.c
@@ -104,6 +104,8 @@ main(int argc, /* I - Number of command-line args */
}
ptr1 ++;
strncpy(queue_name, ptr1, sizeof(queue_name));
+ if (strlen(ptr1) > 1023)
+ queue_name[1023] = '\0';
httpAssembleURIf(HTTP_URI_CODING_ALL, uri, sizeof(uri), "ipp", NULL,
"localhost", ippPort(), "/printers/%s", queue_name);
job_id = argv[1];
@@ -162,6 +164,8 @@ main(int argc, /* I - Number of command-line args */
/* Read destination host name (or message) and check whether it is
complete (second double quote) */
strncpy(dest_host, ptr1, sizeof(dest_host));
+ if (strlen(ptr1) > 1023)
+ dest_host[1023] = '\0';
ptr1 = dest_host;
if ((ptr2 = strchr(ptr1, '"')) != NULL) {
*ptr2 = '\0';
diff --git a/cupsfilters/colormanager.c b/cupsfilters/colormanager.c
index 70074a3..a4a929d 100644
--- a/cupsfilters/colormanager.c
+++ b/cupsfilters/colormanager.c
@@ -272,6 +272,9 @@ _get_colord_profile(const char *printer_name, /* Dest name */
free(qualifier);
}
+ if (icc_profile != NULL)
+ free(icc_profile);
+
return is_profile_set;
}
@@ -325,8 +328,11 @@ _get_ppd_icc_fallback (ppd_file_t *ppd, char **qualifier)
if (attr->value[0] != '/')
snprintf(full_path, sizeof(full_path),
"%s/profiles/%s", CUPSDATA, attr->value);
- else
+ else {
strncpy(full_path, attr->value, sizeof(full_path));
+ if (strlen(attr->value) > 1023)
+ full_path[1023] = '\0';
+ }
/* check the file exists */
if (access(full_path, 0)) {
diff --git a/cupsfilters/image-sgilib.c b/cupsfilters/image-sgilib.c
index 0b70c13..bf2dd80 100644
--- a/cupsfilters/image-sgilib.c
+++ b/cupsfilters/image-sgilib.c
@@ -282,7 +282,7 @@ sgiOpenFile(FILE *file, /* I - File to open */
sgip->mode = SGI_WRITE;
putshort(SGI_MAGIC, sgip->file);
- putc((sgip->comp = comp) != 0, sgip->file);
+ putc(((sgip->comp = comp) != 0) ? '1': '0', sgip->file);
putc(sgip->bpp = bpp, sgip->file);
putshort(3, sgip->file); /* Dimensions */
putshort(sgip->xsize = xsize, sgip->file);
diff --git a/cupsfilters/image-sun.c b/cupsfilters/image-sun.c
index 609b194..989d039 100644
--- a/cupsfilters/image-sun.c
+++ b/cupsfilters/image-sun.c
@@ -114,6 +114,7 @@ _cupsImageReadSunRaster(
ras_depth == 0 || ras_depth > 32)
{
fputs("DEBUG: Raster image cannot be loaded!\n", stderr);
+ fclose(fp);
return (1);
}
diff --git a/cupsfilters/ppdgenerator.c b/cupsfilters/ppdgenerator.c
index 052e3c5..3bc4d8a 100644
--- a/cupsfilters/ppdgenerator.c
+++ b/cupsfilters/ppdgenerator.c
@@ -937,6 +937,10 @@ load_opt_strings_catalog(const char *location, cups_array_t *options)
}
}
cupsFileClose(fp);
+ if (choice_name != NULL)
+ free(choice_name);
+ if (opt_name != NULL)
+ free(opt_name);
if (filename == tmpfile)
unlink(filename);
}
diff --git a/cupsfilters/raster.c b/cupsfilters/raster.c
index 8203690..67d6b9b 100644
--- a/cupsfilters/raster.c
+++ b/cupsfilters/raster.c
@@ -151,11 +151,14 @@ cupsRasterParseIPPOptions(cups_page_header2_t *h, /* I - Raster header */
strcasestr(s, "right") ||
strcasestr(s, "side") ||
strcasestr(s, "main"))
- media_source = strdup(s);
+ {
+ if (media_source == NULL)
+ media_source = strdup(s);
+ }
else
media_type = strdup(s);
}
- if (size_found)
+ if (page_size == NULL && size_found)
page_size = strdup(size_found->pwg);
}
}
@@ -1079,6 +1082,13 @@ cupsRasterParseIPPOptions(cups_page_header2_t *h, /* I - Raster header */
h->cupsRenderingIntent[0] = '\0';
#endif /* HAVE_CUPS_1_7 */
+ if (media_source != NULL)
+ free(media_source);
+ if (media_type != NULL)
+ free(media_type);
+ if (page_size != NULL)
+ free(page_size);
+
return (0);
}
diff --git a/filter/bannertopdf.c b/filter/bannertopdf.c
index b78ea37..2b9bd76 100644
--- a/filter/bannertopdf.c
+++ b/filter/bannertopdf.c
@@ -513,6 +513,15 @@ static int generate_banner_pdf(banner_t *banner,
pdf_duplicate_page(doc, 1, copies);
pdf_write(doc, stdout);
+
+ opt_t * opt_current = known_opts;
+ opt_t * opt_next = NULL;
+ while (opt_current != NULL)
+ {
+ opt_next = opt_current->next;
+ free(opt_current);
+ opt_current = opt_next;
+ }
free(buf);
pdf_free(doc);
return 0;
diff --git a/filter/foomatic-rip/foomaticrip.c b/filter/foomatic-rip/foomaticrip.c
index 2a642ed..13d2035 100644
--- a/filter/foomatic-rip/foomaticrip.c
+++ b/filter/foomatic-rip/foomaticrip.c
@@ -666,6 +666,11 @@ int print_file(const char *filename, int convert)
ret = print_file("<STDIN>", 0);
wait_for_process(renderer_pid);
+ if (in != NULL)
+ fclose(in);
+ if (out != NULL)
+ fclose(out);
+
return ret;
}
@@ -683,6 +688,8 @@ int print_file(const char *filename, int convert)
case UNKNOWN_FILE:
_log("Cannot process \"%s\": Unknown filetype.\n", filename);
+ if (file != NULL)
+ fclose(file);
return 0;
}
@@ -811,10 +818,14 @@ int main(int argc, char** argv)
if (getenv("PPD")) {
strncpy(job->ppdfile, getenv("PPD"), 2048);
+ if (strlen(getenv("PPD")) > 2047)
+ job->ppdfile[2047] = '\0';
spooler = SPOOLER_CUPS;
- if (getenv("CUPS_SERVERBIN"))
- strncpy(cupsfilterpath, getenv("CUPS_SERVERBIN"),
- sizeof(cupsfilterpath));
+ if (getenv("CUPS_SERVERBIN")) {
+ strncpy(cupsfilterpath, getenv("CUPS_SERVERBIN"), sizeof(cupsfilterpath));
+ if (strlen(getenv("CUPS_SERVERBIN")) > PATH_MAX-1)
+ cupsfilterpath[PATH_MAX-1] = '\0';
+ }
}
/* Check status of printer color management from the color manager */
@@ -834,10 +845,14 @@ int main(int argc, char** argv)
allow duplicates, and use the last specified one */
while ((str = arglist_get_value(arglist, "-p"))) {
strncpy(job->ppdfile, str, 2048);
+ if (strlen(str) > 2047)
+ job->ppdfile[2047] = '\0';
arglist_remove(arglist, "-p");
}
while ((str = arglist_get_value(arglist, "--ppd"))) {
strncpy(job->ppdfile, str, 2048);
+ if (strlen(str) > 2047)
+ job->ppdfile[2047] = '\0';
arglist_remove(arglist, "--ppd");
}
@@ -1020,6 +1035,7 @@ int main(int argc, char** argv)
cmd[0] = '\0';
snprintf(gstoraster, sizeof(gstoraster), "gs -dQUIET -dDEBUG -dPARANOIDSAFER -dNOPAUSE -dBATCH -dNOINTERPOLATE -dNOMEDIAATTRS -sDEVICE=cups -dShowAcroForm %s -sOutputFile=- -", cmd);
+ free(icc_profile);
}
/* build Ghostscript/CUPS driver command line */
diff --git a/filter/foomatic-rip/options.c b/filter/foomatic-rip/options.c
index 325a0a6..798ddf9 100644
--- a/filter/foomatic-rip/options.c
+++ b/filter/foomatic-rip/options.c
@@ -1031,12 +1031,10 @@ int option_set_value(option_t *opt, int optionset, const char *value)
/* TODO only set the changed option, not all of them */
choice = option_find_choice(fromopt,
option_get_value(fromopt, optionset));
-
composite_set_values(fromopt, optionset, choice->command);
- }
- else {
+ free(newvalue);
+ } else
val->value = newvalue;
- }
if (option_is_composite(opt)) {
/* set dependent values */
@@ -1914,6 +1912,8 @@ int ppd_supports_pdf()
if (startswith(cmd, "gs"))
{
strncpy(cmd_pdf, cmd, 4096);
+ if (strlen(cmd) > 4095)
+ cmd_pdf[4095] = '\0';
return 1;
}
diff --git a/filter/foomatic-rip/spooler.c b/filter/foomatic-rip/spooler.c
index 236551f..4f27563 100644
--- a/filter/foomatic-rip/spooler.c
+++ b/filter/foomatic-rip/spooler.c
@@ -94,6 +94,8 @@ void init_cups(list_t *arglist, dstr_t *filelist, jobparams_t *job)
CUPS puts the print queue name into the PRINTER environment variable
when calling filters. */
strncpy(job->printer, getenv("PRINTER"), 256);
+ if (strlen(getenv("PRINTER")) > 255)
+ job->printer[255] = '\0';
free(cups_options);
}
diff --git a/filter/pdftops.c b/filter/pdftops.c
index 55d2ec1..a648444 100644
--- a/filter/pdftops.c
+++ b/filter/pdftops.c
@@ -427,6 +427,8 @@ main(int argc, /* I - Number of command-line args */
if ((val = cupsGetOption("make-and-model", num_options, options)) != NULL)
{
strncpy(make_model, val, sizeof(make_model));
+ if (strlen(val) > 127)
+ make_model[127] = '\0';
for (ptr = make_model; *ptr; ptr ++)
if (*ptr == '-') *ptr = ' ';
}
diff --git a/filter/pdftoraster.cxx b/filter/pdftoraster.cxx
index 4cd656a..0c63ab8 100644
--- a/filter/pdftoraster.cxx
+++ b/filter/pdftoraster.cxx
@@ -558,8 +558,10 @@ static void parseOpts(int argc, char **argv)
if (!cm_disabled)
cmGetPrinterIccProfile(getenv("PRINTER"), &profile, ppd);
- if (profile != NULL)
- colorProfile = cmsOpenProfileFromFile(profile,"r");
+ if (profile != NULL) {
+ colorProfile = cmsOpenProfileFromFile(profile,"r");
+ free(profile);
+ }
#ifdef HAVE_CUPS_1_7
if ((attr = ppdFindAttr(ppd,"PWGRaster",0)) != 0 &&
diff --git a/filter/rastertoescpx.c b/filter/rastertoescpx.c
index 5a3e5df..a0ec416 100644
--- a/filter/rastertoescpx.c
+++ b/filter/rastertoescpx.c
@@ -1141,7 +1141,10 @@ EndPage(ppd_file_t *ppd, /* I - PPD file */
}
}
else
+ {
free(DotBuffers[0]);
+ DotBuffers[0] = NULL;
+ }
/*
* Output a page eject sequence...
@@ -1440,7 +1443,7 @@ CompressData(ppd_file_t *ppd, /* I - PPD file information */
printf("\033i");
putchar(ctable[PrinterPlanes - 1][plane]);
- putchar(type != 0);
+ putchar((type != 0) ? '1': '0');
putchar(BitPlanes);
putchar(bytes & 255);
putchar(bytes >> 8);
@@ -1470,7 +1473,7 @@ CompressData(ppd_file_t *ppd, /* I - PPD file information */
bytes *= 8;
printf("\033.");
- putchar(type != 0);
+ putchar((type != 0) ? '1': '0');
putchar(ystep);
putchar(xstep);
putchar(rows);
@@ -1907,6 +1910,10 @@ main(int argc, /* I - Number of command-line arguments */
if (fd != 0)
close(fd);
+ for (int i = 0; i < 7; i++)
+ if (DotBuffers[i] != NULL)
+ free(DotBuffers[i]);
+
return (page == 0);
}
diff --git a/filter/rastertops.c b/filter/rastertops.c
index d5d955b..531eb70 100644
--- a/filter/rastertops.c
+++ b/filter/rastertops.c
@@ -282,6 +282,8 @@ write_flate(cups_raster_t *ras, /* I - Image data */
if (fwrite(out, 1, have, stdout) != have)
{
(void)deflateEnd(&strm);
+ if (convertedpix != NULL)
+ free(convertedpix);
return Z_ERRNO;
}
} while (strm.avail_out == 0);
diff --git a/filter/sys5ippprinter.c b/filter/sys5ippprinter.c
index ad75551..9a92c8e 100644
--- a/filter/sys5ippprinter.c
+++ b/filter/sys5ippprinter.c
@@ -570,6 +570,8 @@ exec_filter(const char *filter, /* I - Filter to execute */
dup2(fd, 2);
close(fd);
}
+ else
+ close(fd);
fcntl(2, F_SETFL, O_NDELAY);
}
@@ -578,6 +580,8 @@ exec_filter(const char *filter, /* I - Filter to execute */
dup2(fd, 3);
close(fd);
}
+ else
+ close(fd);
fcntl(3, F_SETFL, O_NDELAY);
if ((fd = open("/dev/null", O_RDWR)) > 4)
@@ -585,6 +589,8 @@ exec_filter(const char *filter, /* I - Filter to execute */
dup2(fd, 4);
close(fd);
}
+ else
+ close(fd);
fcntl(4, F_SETFL, O_NDELAY);
/*
@@ -654,8 +660,11 @@ exec_filters(cups_array_t *filters, /* I - Array of filters to run */
{
next = (char *)cupsArrayNext(filters);
- if (filter[0] == '/')
+ if (filter[0] == '/') {
strncpy(program, filter, sizeof(program));
+ if (strlen(filter) > 1023)
+ program[1023] = '\0';
+ }
else
{
if ((cups_serverbin = getenv("CUPS_SERVERBIN")) == NULL)
diff --git a/utils/cups-browsed.c b/utils/cups-browsed.c
index a2a4a08..19a2ac8 100644
--- a/utils/cups-browsed.c
+++ b/utils/cups-browsed.c
@@ -2245,7 +2245,10 @@ is_disabled(const char *printer, const char *reason) {
pstate = (ipp_pstate_t)ippGetInteger(attr, 0);
else if (!strcmp(ippGetName(attr), "printer-state-message") &&
ippGetValueTag(attr) == IPP_TAG_TEXT) {
- free(pstatemsg);
+ if (pstatemsg != NULL) {
+ free(pstatemsg);
+ pstatemsg = NULL;
+ }
p = ippGetString(attr, 0, NULL);
if (p != NULL) pstatemsg = strdup(p);
}
@@ -2262,16 +2265,22 @@ is_disabled(const char *printer, const char *reason) {
case IPP_PRINTER_IDLE:
case IPP_PRINTER_PROCESSING:
ippDelete(response);
- free(pstatemsg);
+ if (pstatemsg != NULL) {
+ free(pstatemsg);
+ pstatemsg = NULL;
+ }
return NULL;
case IPP_PRINTER_STOPPED:
ippDelete(response);
if (reason == NULL)
return pstatemsg;
- else if (strcasestr(pstatemsg, reason) != NULL)
+ else if (pstatemsg != NULL && (strcasestr(pstatemsg, reason) != NULL))
return pstatemsg;
else {
- free(pstatemsg);
+ if (pstatemsg != NULL) {
+ free(pstatemsg);
+ pstatemsg = NULL;
+ }
return NULL;
}
}
@@ -2280,12 +2289,18 @@ is_disabled(const char *printer, const char *reason) {
debug_printf("No information regarding enabled/disabled found about the requested printer '%s'\n",
printer);
ippDelete(response);
- free(pstatemsg);
+ if (pstatemsg != NULL) {
+ free(pstatemsg);
+ pstatemsg = NULL;
+ }
return NULL;
}
debug_printf("ERROR: Request for printer info failed: %s\n",
cupsLastErrorString());
- free(pstatemsg);
+ if (pstatemsg != NULL) {
+ free(pstatemsg);
+ pstatemsg = NULL;
+ }
return NULL;
}
@@ -3040,6 +3055,8 @@ on_printer_state_changed (CupsNotifier *object,
dest_host = p->ip ? p->ip : p->host;
dest_port = p->port;
strncpy(dest_name, remote_cups_queue, sizeof(dest_name));
+ if (strlen(remote_cups_queue) > 1023)
+ dest_name[1023] = '\0';
dest_index = i;
debug_printf("Printer %s on host %s, port %d is idle, take this as destination and stop searching.\n",
remote_cups_queue, p->host, p->port);
@@ -3056,8 +3073,9 @@ on_printer_state_changed (CupsNotifier *object,
min_jobs = num_jobs;
dest_host = p->ip ? p->ip : p->host;
dest_port = p->port;
- strncpy(dest_name, remote_cups_queue,
- sizeof(dest_name));
+ strncpy(dest_name, remote_cups_queue, sizeof(dest_name));
+ if (strlen(remote_cups_queue) > 1023)
+ dest_name[1023] = '\0';
dest_index = i;
}
debug_printf("Printer %s on host %s, port %d is printing and it has %d jobs.\n",
@@ -3566,8 +3584,9 @@ create_remote_printer_entry (const char *queue_name,
IPP_TAG_KEYWORD)) != NULL) {
debug_printf(" Attr: %s\n", ippGetName(attr));
for (i = 0; i < ippGetCount(attr); i ++) {
- strncpy(valuebuffer, ippGetString(attr, i, NULL),
- sizeof(valuebuffer));
+ strncpy(valuebuffer, ippGetString(attr, i, NULL), sizeof(valuebuffer));
+ if (strlen(ippGetString(attr, i, NULL)) > 65535)
+ valuebuffer[65535] = '\0';
debug_printf(" Keyword: %s\n", valuebuffer);
if (valuebuffer[0] > '1')
break;
@@ -3598,8 +3617,9 @@ create_remote_printer_entry (const char *queue_name,
debug_printf(" Value: %s\n", valuebuffer);
if (valuebuffer[0] == '\0') {
for (i = 0; i < ippGetCount(attr); i ++) {
- strncpy(valuebuffer, ippGetString(attr, i, NULL),
- sizeof(valuebuffer));
+ strncpy(valuebuffer, ippGetString(attr, i, NULL), sizeof(valuebuffer));
+ if (strlen(ippGetString(attr, i, NULL)) > 65535)
+ valuebuffer[65535] = '\0';
debug_printf(" Keyword: %s\n", valuebuffer);
if (valuebuffer[0] != '\0')
break;
@@ -3629,8 +3649,9 @@ create_remote_printer_entry (const char *queue_name,
debug_printf(" Value: %s\n", valuebuffer);
if (valuebuffer[0] == '\0') {
for (i = 0; i < ippGetCount(attr); i ++) {
- strncpy(valuebuffer, ippGetString(attr, i, NULL),
- sizeof(valuebuffer));
+ strncpy(valuebuffer, ippGetString(attr, i, NULL), sizeof(valuebuffer));
+ if (strlen(ippGetString(attr, i, NULL)) > 65535)
+ valuebuffer[65535] = '\0';
debug_printf(" Keyword: %s\n", valuebuffer);
if (valuebuffer[0] != '\0')
break;
@@ -3663,8 +3684,9 @@ create_remote_printer_entry (const char *queue_name,
debug_printf(" Value: %s\n", p->queue_name, valuebuffer);
if (valuebuffer[0] == '\0') {
for (i = 0; i < ippGetCount(attr); i ++) {
- strncpy(valuebuffer, ippGetString(attr, i, NULL),
- sizeof(valuebuffer));
+ strncpy(valuebuffer, ippGetString(attr, i, NULL), sizeof(valuebuffer));
+ if (strlen(ippGetString(attr, i, NULL)) > 65535)
+ valuebuffer[65535] = '\0';
debug_printf(" Keyword: %s\n", valuebuffer);
if (valuebuffer[0] != '\0')
break;
@@ -4498,6 +4520,8 @@ gboolean update_cups_queues(gpointer unused) {
} else {
/* Device URI: ipp(s)://<remote host>:631/printers/<remote queue> */
strncpy(device_uri, p->uri, sizeof(device_uri));
+ if (strlen(p->uri) > HTTP_MAX_URI-1)
+ device_uri[HTTP_MAX_URI-1] = '\0';
debug_printf("Print queue %s is for an IPP network printer, or we do not get notifications from CUPS, using direct device URI %s\n",
p->queue_name, device_uri);
}
@@ -4606,6 +4630,8 @@ gboolean update_cups_queues(gpointer unused) {
} else if (!strncmp(line, "*Default", 8)) {
cont_line_read = 0;
strncpy(keyword, line + 8, sizeof(keyword));
+ if ((strlen(line) + 8) > 1023)
+ keyword[1023] = '\0';
for (keyptr = keyword; *keyptr; keyptr ++)
if (*keyptr == ':' || isspace(*keyptr & 255))
break;
@@ -7144,7 +7170,7 @@ read_configuration (const char *filename)
in the configuration file is used. */
while ((i < cupsArrayCount(command_line_config) &&
(value = cupsArrayIndex(command_line_config, i++)) &&
- strncpy(line, value, sizeof(line))) ||
+ strncpy(line, value, sizeof(line)) && ((strlen(value) > HTTP_MAX_BUFFER-1)? line[HTTP_MAX_BUFFER-1] = '\0': 1)) ||
cupsFileGetConf(fp, line, sizeof(line), &value, &linenum)) {
if (linenum < 0) {
/* We are still reading options from the command line ("-o ..."),
@@ -7371,6 +7397,7 @@ read_configuration (const char *filename)
if (filter->cregexp)
regfree(filter->cregexp);
free(filter);
+ filter = NULL;
}
} else if ((!strcasecmp(line, "BrowseInterval") || !strcasecmp(line, "BrowseTimeout")) && value) {
int t = atoi(value);
@@ -7386,8 +7413,11 @@ read_configuration (const char *filename)
debug_printf("Invalid %s value: %d\n",
line, t);
} else if (!strcasecmp(line, "DomainSocket") && value) {
- if (value[0] != '\0')
+ if (value[0] != '\0') {
+ if (DomainSocket != NULL)
+ free(DomainSocket);
DomainSocket = strdup(value);
+ }
} else if ((!strcasecmp(line, "HttpLocalTimeout") || !strcasecmp(line, "HttpRemoteTimeout")) && value) {
int t = atoi(value);
if (t >= 0) {
@@ -7555,6 +7585,10 @@ read_configuration (const char *filename)
}
}
cupsArrayAdd (clusters, cluster);
+ if (start != NULL) {
+ free(start);
+ start = NULL;
+ }
continue;
cluster_fail:
if (cluster) {
@@ -7568,6 +7602,11 @@ read_configuration (const char *filename)
cupsArrayDelete (cluster->members);
}
free(cluster);
+ cluster = NULL;
+ }
+ if (start != NULL) {
+ free(start);
+ start = NULL;
}
} else if (!strcasecmp(line, "LoadBalancing") && value) {
if (!strncasecmp(value, "QueueOnClient", 13))
@@ -7575,7 +7614,7 @@ read_configuration (const char *filename)
else if (!strncasecmp(value, "QueueOnServers", 14))
LoadBalancingType = QUEUE_ON_SERVERS;
} else if (!strcasecmp(line, "DefaultOptions") && value) {
- if (strlen(value) > 0)
+ if (DefaultOptions == NULL && strlen(value) > 0)
DefaultOptions = strdup(value);
} else if (!strcasecmp(line, "AutoShutdown") && value) {
char *p, *saveptr;
@@ -7949,10 +7988,12 @@ int main(int argc, char*argv[]) {
daemon, not with remote ones. */
if (getenv("CUPS_SERVER") != NULL) {
strncpy(local_server_str, getenv("CUPS_SERVER"), sizeof(local_server_str));
+ if (strlen(getenv("CUPS_SERVER")) > 1023)
+ local_server_str[1023] = '\0';
} else {
#ifdef CUPS_DEFAULT_DOMAINSOCKET
if (DomainSocket == NULL)
- DomainSocket = CUPS_DEFAULT_DOMAINSOCKET;
+ DomainSocket = strdup(CUPS_DEFAULT_DOMAINSOCKET);
#endif
if (DomainSocket != NULL) {
struct stat sockinfo; /* Domain socket information */
@@ -8293,6 +8334,11 @@ fail:
if (debug_logfile == 1)
stop_debug_logging();
+ if (DefaultOptions != NULL)
+ free(DefaultOptions);
+ if (DomainSocket != NULL)
+ free(DomainSocket);
+
return ret;
help:
diff --git a/utils/driverless.c b/utils/driverless.c
index 7fc6dae..fe61e58 100644
--- a/utils/driverless.c
+++ b/utils/driverless.c
@@ -227,12 +227,16 @@ list_printers (int mode)
if (txt_usb_mfg[0] != '\0') {
strncpy(make, txt_usb_mfg, sizeof(make));
+ if (strlen(txt_usb_mfg) > 511)
+ make[511] = '\0';
ptr = device_id + strlen(device_id);
snprintf(ptr, sizeof(device_id) - (size_t)(ptr - device_id),
"MFG:%s;", txt_usb_mfg);
}
if (txt_usb_mdl[0] != '\0') {
strncpy(model, txt_usb_mdl, sizeof(model));
+ if (strlen(txt_usb_mdl) > 255)
+ model[255] = '\0';
ptr = device_id + strlen(device_id);
snprintf(ptr, sizeof(device_id) - (size_t)(ptr - device_id),
"MDL:%s;", txt_usb_mdl);
@@ -243,15 +247,22 @@ list_printers (int mode)
*ptr == ')')
*ptr = '\0';
strncpy(model, txt_product + 1, sizeof(model));
+ if ((strlen(txt_product) + 1) > 255)
+ model[255] = '\0';
} else
strncpy(model, txt_product, sizeof(model));
} else if (txt_ty[0] != '\0') {
strncpy(model, txt_ty, sizeof(model));
+ if (strlen(txt_ty) > 255)
+ model[255] = '\0';
if ((ptr = strchr(model, ',')) != NULL)
*ptr = '\0';
}
- if (txt_pdl[0] != '\0')
+ if (txt_pdl[0] != '\0') {
strncpy(pdl, txt_pdl, sizeof(pdl));
+ if (strlen(txt_pdl) > 255)
+ pdl[255] = '\0';
+ }
if (!device_id[0] && strcasecmp(model, "Unknown")) {
if (make[0])

View file

@ -0,0 +1,21 @@
diff -up cups-filters-1.16.1/utils/cups-browsed.conf.in.createall cups-filters-1.16.1/utils/cups-browsed.conf.in
--- cups-filters-1.16.1/utils/cups-browsed.conf.in.createall 2018-01-02 17:17:51.555941155 +0100
+++ cups-filters-1.16.1/utils/cups-browsed.conf.in 2018-01-02 17:19:49.651048564 +0100
@@ -359,7 +359,7 @@ BrowseRemoteProtocols @BROWSEREMOTEPROTO
# LocalQueueNamingRemoteCUPS DNS-SD
# LocalQueueNamingRemoteCUPS MakeModel
-# LocalQueueNamingRemoteCUPS RemoteName
+LocalQueueNamingRemoteCUPS RemoteName
# LocalQueueNamingIPPPrinter DNS-SD
# LocalQueueNamingIPPPrinter MakeModel
@@ -453,7 +453,7 @@ BrowseRemoteProtocols @BROWSEREMOTEPROTO
# CreateIPPPrinterQueues AppleRaster
# CreateIPPPrinterQueues Everywhere AppleRaster
# CreateIPPPrinterQueues Driverless
-# CreateIPPPrinterQueues All
+CreateIPPPrinterQueues All
# If cups-browsed is automatically creating print queues for native

File diff suppressed because it is too large Load diff

View file

@ -1,13 +0,0 @@
diff --git a/filter/foomatic-rip/util.c b/filter/foomatic-rip/util.c
index 508bc09..ad79fbf 100644
--- a/filter/foomatic-rip/util.c
+++ b/filter/foomatic-rip/util.c
@@ -76,7 +76,7 @@ rip_die(int status,
{
va_list ap;
- _log("Process is dying with \"");
+ _log("ERROR: Process is dying with \"");
va_start(ap, msg);
_logv(msg, ap);
va_end(ap);

View file

@ -1,188 +0,0 @@
From 41c5f2f6139e4d3693c2483ee4281202a80ae451 Mon Sep 17 00:00:00 2001
From: zdohnal <zdohnal@redhat.com>
Date: Tue, 22 Jul 2025 15:12:19 +0200
Subject: [PATCH] Introduce foomatic-hash and reject unauthorized values in
foomatic-rip (#648)
The change provides a way for users to have control over what values are
allowed for the foomatic-rip-related PPD keywords FoomaticRIPCommandLine,
FoomaticRIPCommandLinePDF, and FoomaticRIPOptionSetting. Since the
values can be later used when constructing a shell command, the filter
foomatic-rip was a target of several exploits (caused by issues at
different places in CUPS or in different projects of the printing stack) to
do arbitrary code execution when the filter is used.
By default the filter is run by user lp, so the issue is mitigated, but
this PR gives admin complete control over what can be run in
foomatic-rip and reject anything injected into system via different
ways.
First, the new tool - foomatic-hash - can be called on a PPD file or
directory with drivers/PPDs, with scan output and file with hexadecimal
representation of hashed values. Once the scan output is reviewed by
admin, admin can decide to put the resulting hashes into
/etc/foomatic/hashes.d and allow them for the filter.
---
Makefile.am | 44 ++-
README.md | 23 ++
configure.ac | 2 +-
filter/foomatic-rip/foomatic-hash.1 | 66 ++++
filter/foomatic-rip/foomatic-hash.c | 549 ++++++++++++++++++++++++++
filter/foomatic-rip/foomatic-rip.1.in | 16 +
filter/foomatic-rip/foomaticrip.c | 75 ----
filter/foomatic-rip/foomaticrip.h | 40 --
filter/foomatic-rip/options.c | 67 ++++
filter/foomatic-rip/process.c | 9 +
filter/foomatic-rip/process.h | 3 +
filter/foomatic-rip/util.c | 341 +++++++++++++++-
filter/foomatic-rip/util.h | 67 ++++
13 files changed, 1178 insertions(+), 124 deletions(-)
create mode 100644 filter/foomatic-rip/foomatic-hash.1
create mode 100644 filter/foomatic-rip/foomatic-hash.c
diff --git a/filter/foomatic-rip/foomatic-rip.1.in b/filter/foomatic-rip/foomatic-rip.1.in
index 9685a95f5..3dff5215f 100644
--- a/filter/foomatic-rip/foomatic-rip.1.in
+++ b/filter/foomatic-rip/foomatic-rip.1.in
@@ -193,6 +193,15 @@ friends. Several PPD files use shell constructs that require a more
modern shell like \fBbash\fR, \fBzsh\fR, or \fBksh\fR.
+.SH PPD OPTION VALUE RESTRICTIONS AND EXCEPTIONS
+
+The values of PPD options \fBFoomaticRIPCommandLine\fR, \fBFoomaticRIPCommandLinePDF\fR and \fBFoomaticRIPOptionSetting\fR
+are rejected in the default configuration because of security implications. Users can use the tool \fBfoomatic-hash(1)\fR, which provides
+values of affected PPD options from found drivers and hashes of those values in hexadecimal format. User is expected to review the found values,
+and if there is nothing suspicious in the output, copy the file with hashes into into the directory \fB@sysconfdir@/foomatic/hashes.d\fR
+to allow the exceptions for found values.
+
+
.SH FILES
.PD 0
.TP 0
@@ -209,6 +218,13 @@ The PPD files of the currently defined printers
Configuration file for foomatic-rip
+.TP 0
+@sysconfdir@/foomatic/hashes.d
+.TP 0
+@datadir@/foomatic/hashes.d
+
+Directories with hashes of allowed values
+
.PD 0
.\".SH SEE ALSO
diff --git a/filter/foomatic-rip/options.c b/filter/foomatic-rip/options.c
index bad833bc1..032fe9ec3 100644
--- a/filter/foomatic-rip/options.c
+++ b/filter/foomatic-rip/options.c
@@ -102,6 +102,42 @@ get_icc_profile_for_qualifier(const char **qualifier)
}
+//
+// 'is_allowed_value' - Check if the option value is allowed.
+//
+
+int // O - Boolean value - true 1 / false 0
+is_allowed_value(cups_array_t *ar, // I - Array of already known hashes from system
+ char *value, // I - Scanned value from PPD file
+ size_t value_len) // I - Value length
+{
+ char hash_string[65]; // Help array to store hexadecimal hashed string
+
+ //
+ // Empty string is allowed...
+ //
+
+ if (!value_len)
+ return (1);
+
+ //
+ // Hash the value and get hexadecimal string for it...
+ //
+
+ if (hash_data((unsigned char*)value, value_len, hash_string, sizeof(hash_string)))
+ return (0);
+
+ //
+ // Check if the found hexadecimal hashed string is in the array -> allowed on the system...
+ //
+
+ if (cupsArrayFind(ar, hash_string))
+ return (1);
+
+ return (0);
+}
+
+
// a selector is a general tri-dotted specification.
// The 2nd and 3rd elements of the qualifier are optionally modified by
// cupsICCQualifier2 and cupsICCQualifier3:
@@ -1866,12 +1902,19 @@ read_ppd_file(const char *filename)
option_t *opt, *current_opt = NULL;
param_t *param;
icc_mapping_entry_t *entry;
+ cups_array_t *known_hashes = NULL;
fh = fopen(filename, "r");
if (!fh)
rip_die(EXIT_PRNERR_NORETRY_BAD_SETTINGS, "Unable to open PPD file %s\n", filename);
_log("Parsing PPD file ...\n");
+ if (load_system_hashes(&known_hashes))
+ {
+ fclose(fh);
+ rip_die(EXIT_PRNERR_NORETRY, "Not enough memory for array allocation\n.");
+ }
+
dstrassure(value, 256);
qualifier_data = list_create();
@@ -1955,10 +1998,26 @@ read_ppd_file(const char *filename)
}
else if (strcmp(key, "FoomaticRIPCommandLine") == 0)
{
+ if (!is_allowed_value(known_hashes, value->data, strlen(value->data)))
+ {
+ cupsArrayDelete(known_hashes);
+ fclose(fh);
+
+ rip_die(EXIT_PRNERR_NOTALLOWED, "ERROR: The value of the key %s is not among the allowed values - see foomatic-rip man page for more instructions.\n", key);
+ }
+
unhtmlify(cmd, 4096, value->data);
}
else if (strcmp(key, "FoomaticRIPCommandLinePDF") == 0)
{
+ if (!is_allowed_value(known_hashes, value->data, strlen(value->data)))
+ {
+ cupsArrayDelete(known_hashes);
+ fclose(fh);
+
+ rip_die(EXIT_PRNERR_NOTALLOWED, "ERROR: The value of the key %s is not among the allowed values - see foomatic-rip man page for more instructions.\n", key);
+ }
+
unhtmlify(cmd_pdf, 4096, value->data);
}
else if (!strcmp(key, "cupsFilter"))
@@ -2097,6 +2156,14 @@ read_ppd_file(const char *filename)
}
else if (!strcmp(key, "FoomaticRIPOptionSetting"))
{
+ if (!is_allowed_value(known_hashes, value->data, strlen(value->data)))
+ {
+ cupsArrayDelete(known_hashes);
+ fclose(fh);
+
+ rip_die(EXIT_PRNERR_NOTALLOWED, "ERROR: The value of the key %s is not among the allowed values - see foomatic-rip man page for more instructions.\n", key);
+ }
+
// "*FoomaticRIPOptionSetting <option>[=<choice>]: <code>
// For boolean options <choice> is not given
option_set_choice(assure_option(name),
--
2.50.1

View file

@ -1,28 +0,0 @@
--- !Policy
product_versions:
- fedora-*
decision_context: bodhi_update_push_testing
subject_type: koji_build
rules:
- !PassingTestCaseRule {test_case_name: fedora-ci.koji-build./plans/tier1-public.functional}
- !PassingTestCaseRule {test_case_name: fedora-ci.koji-build./plans/cups-tier1-public.functional}
#Rawhide
--- !Policy
product_versions:
- fedora-*
decision_context: bodhi_update_push_stable
subject_type: koji_build
rules:
- !PassingTestCaseRule {test_case_name: fedora-ci.koji-build./plans/tier1-public.functional}
- !PassingTestCaseRule {test_case_name: fedora-ci.koji-build./plans/cups-tier1-public.functional}
#gating rhel
--- !Policy
product_versions:
- rhel-*
decision_context: osci_compose_gate
rules:
- !PassingTestCaseRule {test_case_name: osci.brew-build./plans/tier1-public.functional}
- !PassingTestCaseRule {test_case_name: osci.brew-build./plans/tier1-internal.functional}
- !PassingTestCaseRule {test_case_name: osci.brew-build./plans/cups-tier1-public.functional}
- !PassingTestCaseRule {test_case_name: osci.brew-build./plans/cups-tier1-internal.functional}

124
lftocrlf
View file

@ -1,124 +0,0 @@
#!/bin/bash
## Copyright (C) 2003-2006 Red Hat, Inc.
## Copyright (C) 2003-2006 Tim Waugh <twaugh@redhat.com>
## Changed on 2007/05/17, Opher Shachar, LADPC Ltd.
## Added support for page-ranges option.
## Added page accounting.
## This program is free software; you can redistribute it and/or
## modify it under the terms of the GNU General Public License
## as published by the Free Software Foundation; either version 2
## of the License, or (at your option) any later version.
## This program is distributed in the hope that it will be useful,
## but WITHOUT ANY WARRANTY; without even the implied warranty of
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
## GNU General Public License for more details.
## You should have received a copy of the GNU General Public License
## along with this program; if not, write to the Free Software
## Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
if [ $# == 0 ]; then
echo >&2 "ERROR: $0 job-id user title copies options [file]"
exit 1
fi
# Extract the papersize
SENDFF=`grep '^\*DefaultSendFF' "$PPD" | cut -d\ -f2`
COPIES=1
if [ $# -ge 4 ]; then
COPIES="$4"
fi
if [ $# -lt 6 ]; then
unset TMPFILE
trap -- 'rm -f "$TMPFILE"' EXIT
TMPFILE=$(mktemp ${TMPDIR:-/tmp}/lftocrlf.XXXXXX)
cat > "$TMPFILE"
else
TMPFILE="$6"
fi
PR=${5#*page-ranges=}
# Do options specify page-ranges?
if [[ "$PR" != "$5" ]]; then
PR=${PR%% *}
else
#unset PR
PR=1-999999
fi
if [[ "$PR" ]]; then
TMPFILE2=$(mktemp ${TMPDIR:-/tmp}/lftocrlf2.XXXXXX)
pagenum=0
EOF=
{
while [[ "$PR" ]]; do
pl=${PR%%,*} ;# take first subrange
PR=${PR#$pl};PR=${PR#,} ;# remove from range list
pu=${pl#*-} ;# extract upper and lower
pl=${pl%-*} ;# pages of subrange
# Allows interpreting 0-5,3-10 as 1-5,6-10 rejects 5-1 or 1-
(( pagenum >= pl )) && pl=$(( pagenum + 1 ))
(( pl > pu )) && continue
# Loop reading pages until at or over lower page of subrange.
while read -d `echo -ne '\f'` -r; do
(( pagenum++ ))
(( pagenum == pl )) && break
done
# Did we reach lower page of subrange or EOF?
if (( pagenum < pl )); then
[[ ! "$REPLY" ]] && break ;# empty last page - we're done.
(( pagenum++ ))
EOF=y
fi
# Output page and report to page log
if (( pagenum == pl )); then
echo -n "${REPLY}" >>"$TMPFILE2"
# If EOF then page has no final FF
[[ ! "$EOF" ]] && echo -ne '\f' >>"$TMPFILE2"
echo "PAGE: $pagenum $COPIES" >&2
fi
[[ "$EOF" ]] && break
# Is the current subrange a single page?
(( pagenum == pu )) && continue
while read -d `echo -ne '\f'` -r; do
(( pagenum++ ))
echo -ne "${REPLY}\f" >>"$TMPFILE2"
echo "PAGE: $pagenum $COPIES" >&2
(( pagenum == pu )) && break
done
# Could be that we reached EOF before page boundry
if (( pagenum < pu )); then
if [[ "$REPLY" ]]; then
(( pagenum++ ))
echo -n "${REPLY}" >>"$TMPFILE2"
echo "PAGE: $pagenum $COPIES" >&2
fi
break
fi
done
} <"$TMPFILE"
else
TMPFILE2="$TMPFILE"
pc=$(grep -co `echo -ne '\f'` "$TMPFILE2")
pc=$(( pc * $COPIES ))
echo "PAGE: $pc" >&2
fi
while [ "$COPIES" -gt 0 ]; do
# Just translate LF->CRLF at the moment, until the PPD has options added.
sed -e 's/$/'`echo -ne '\r'`'/g' "$TMPFILE2"
if [ "$SENDFF" == "True" ]
then
echo -ne \\014
fi
COPIES=$(($COPIES - 1))
done
# Cleanup
[[ "$TMPFILE" != "$TMPFILE2" ]] && rm -f "$TMPFILE2"
exit 0

View file

@ -1,47 +0,0 @@
*PPD-Adobe: "4.3"
*%
*% Text-only printer definition
*%
*FormatVersion: "4.3"
*FileVersion: "1.1"
*LanguageVersion: English
*LanguageEncoding: ISOLatin1
*PCFileName: "LFTOCRLF.PPD"
*Manufacturer: "Generic"
*Product: "(Generic)"
*cupsVersion: 1.0
*cupsManualCopies: True
*cupsModelNumber: 2
*cupsFilter: "text/plain 0 lftocrlf"
*ModelName: "Generic LF-to-CRLF printer"
*ShortNickName: "Generic LF-to-CRLF printer"
*NickName: "Generic LF-to-CRLF printer"
*PSVersion: "(2017.000) 0"
*LanguageLevel: "2"
*ColorDevice: False
*DefaultColorSpace: Gray
*FileSystem: False
*Throughput: "8"
*LandscapeOrientation: Plus90
*VariablePaperSize: False
*TTRasterizer: Type42
*DefaultImageableArea: Letter
*ImageableArea Letter/US Letter: "18 36 594 756"
*DefaultPaperDimension: Letter
*PaperDimension Letter/Letter: "612 792"
*OpenUI *PageSize/Media Size: PickOne
*OrderDependency: 10 AnySetup *PageSize
*DefaultPageSize: Letter
*PageSize Letter/Letter: "<</PageSize[612 792]/ImagingBBox null>>setpagedevice"
*CloseUI: *PageSize
*OpenUI *PageRegion: PickOne
*OrderDependency: 10 AnySetup *PageRegion
*DefaultPageRegion: Letter
*PageRegion Letter/Letter: "<</PageSize[612 792]/ImagingBBox null>>setpagedevice"
*CloseUI: *PageRegion
*OpenUI *SendFF: Boolean
*DefaultSendFF: False
*SendFF True/True: ""
*SendFF False/False: ""
*CloseUI: *SendFF

View file

@ -1,59 +0,0 @@
/tier1-internal:
plan:
import:
url: https://gitlab.com/redhat/centos-stream/tests/cups-filters.git
name: /plans/tier1/internal
/tier1-public:
plan:
import:
url: https://gitlab.com/redhat/centos-stream/tests/cups-filters.git
name: /plans/tier1/public
/tier2-tier3-internal:
plan:
import:
url: https://gitlab.com/redhat/centos-stream/tests/cups-filters.git
name: /plans/tier2-tier3/internal
/tier2-tier3-public:
plan:
import:
url: https://gitlab.com/redhat/centos-stream/tests/cups-filters.git
name: /plans/tier2-tier3/public
/others-internal:
plan:
import:
url: https://gitlab.com/redhat/centos-stream/tests/cups-filters.git
name: /plans/others/internal
/others-public:
plan:
import:
url: https://gitlab.com/redhat/centos-stream/tests/cups-filters.git
name: /plans/others/public
/multihost:
plan:
import:
url: https://gitlab.com/redhat/centos-stream/tests/cups-filters.git
name: /plans/multihost/multihost
/fips-internal:
plan:
import:
url: https://gitlab.com/redhat/centos-stream/tests/cups-filters.git
name: /plans/others/fips
/cups-tier1-internal:
plan:
import:
url: https://gitlab.com/redhat/centos-stream/tests/cups.git
name: /plans/tier1/internal
/cups-tier1-public:
plan:
import:
url: https://gitlab.com/redhat/centos-stream/tests/cups.git
name: /plans/tier1/public

825
poppler-0.58.patch Normal file
View file

@ -0,0 +1,825 @@
=== modified file 'filter/pdf.cxx'
--- filter/pdf.cxx 2017-08-15 18:32:47 +0000
+++ filter/pdf.cxx 2017-09-07 16:02:01 +0000
@@ -129,64 +129,125 @@
Object array;
Ref r;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ pageobj = xref->fetch(pageref->num, pageref->gen);
+#else
xref->fetch(pageref->num, pageref->gen, &pageobj);
- if (!pageobj.isDict() || !pageobj.dictLookupNF("Contents", &contents)) {
+#endif
+ if (!pageobj.isDict() ||
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ (contents = pageobj.dictLookupNF("Contents")).isNull()
+#else
+ !pageobj.dictLookupNF("Contents", &contents)
+#endif
+ ) {
fprintf(stderr, "Error: malformed pdf\n");
return;
}
- if (contents.isRef())
+ if (contents.isRef()) {
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ contents = xref->fetch(contents.getRefNum(), contents.getRefGen());
+#else
xref->fetch(contents.getRefNum(), contents.getRefGen(), &contents);
+#endif
+ }
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ (void) lenobj;
+ dict = Object(new Dict(xref));
+ dict.dictSet("Length", Object(static_cast<int>(len)));
+ stream = Object(static_cast<Stream *>(new MemStream(buf, 0, len, std::move(dict))));
+#else
lenobj.initInt(len);
dict.initDict(xref);
dict.dictSet("Length", &lenobj);
stream.initStream(new MemStream(buf, 0, len, &dict));
+#endif
r = xref->addIndirectObject(&stream);
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ streamrefobj = Object(r.num, r.gen);
+#else
streamrefobj.initRef(r.num, r.gen);
+#endif
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ array = Object(new Array(xref));
+ array.arrayAdd(std::move(streamrefobj));
+#else
array.initArray(xref);
array.arrayAdd(&streamrefobj);
+#endif
if (contents.isStream()) {
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ contents = pageobj.dictLookupNF("Contents"); // streams must be indirect, i.e. not fetch()-ed
+ array.arrayAdd(std::move(contents));
+#else
pageobj.dictLookupNF("Contents", &contents); // streams must be indirect, i.e. not fetch()-ed
array.arrayAdd(&contents);
+#endif
}
else if (contents.isArray()) {
int i, len = contents.arrayGetLength();
Object obj;
for (i = 0; i < len; i++) {
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ obj = contents.arrayGetNF(i);
+ array.arrayAdd(std::move(obj));
+#else
contents.arrayGetNF(i, &obj);
array.arrayAdd(&obj);
+#endif
}
}
else
fprintf(stderr, "Error: malformed pdf\n");
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ pageobj.dictSet("Contents", std::move(array));
+#else
pageobj.dictSet("Contents", &array);
+#endif
xref->setModifiedObject(&pageobj, *pageref);
+#if POPPLER_VERSION_MAJOR <= 0 && POPPLER_VERSION_MINOR < 58
pageobj.free();
-}
-
-
+#endif
+}
+
+
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+static Object name_object(const char *s)
+{
+ return Object(new GooString(s));
+}
+#else
static Object * name_object(const char *s)
{
Object *o = new Object();
o->initName((char *)s);
return o;
}
+#endif
/*
* Create new PDF integer type object.
*/
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+static Object int_object(int i)
+{
+ return Object(i);
+}
+#else
static Object * int_object(int i)
{
Object *o = new Object();
o->initInt(i);
return o;
}
+#endif
static Object * get_resource_dict(XRef *xref,
Dict *pagedict,
@@ -196,21 +257,36 @@
Object res;
/* TODO resource dict can also be inherited */
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ res = pagedict->lookupNF("Resources");
+ if (res.isNull())
+#else
if (!pagedict->lookupNF("Resources", &res))
+#endif
return NULL;
if (res.isRef()) {
*resref = res.getRef();
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ *resdict = xref->fetch(resref->num, resref->gen);
+#else
xref->fetch(resref->num, resref->gen, resdict);
+#endif
}
else if (res.isDict()) {
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ *resdict = res.copy();
+#else
res.copy(resdict);
+#endif
resref->num = 0;
}
else
resdict = NULL;
+#if POPPLER_VERSION_MAJOR <= 0 && POPPLER_VERSION_MINOR < 58
res.free();
+#endif
return resdict;
}
@@ -226,7 +302,11 @@
Object resdict;
Ref resref;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ pageobj = xref->fetch(pageref->num, pageref->gen);
+#else
xref->fetch(pageref->num, pageref->gen, &pageobj);
+#endif
if (!pageobj.isDict()) {
fprintf(stderr, "Error: malformed pdf\n");
return;
@@ -234,21 +314,35 @@
if (!get_resource_dict(xref, pageobj.getDict(), &resdict, &resref)) {
fprintf(stderr, "Error: malformed pdf\n");
+#if POPPLER_VERSION_MAJOR <= 0 && POPPLER_VERSION_MINOR < 58
pageobj.free();
+#endif
return;
}
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ font = Object(new Dict(xref));
+#else
font.initDict(xref);
+#endif
font.dictSet("Type", name_object("Font"));
font.dictSet("Subtype", name_object("Type1"));
font.dictSet("BaseFont", name_object(name));
xref->addIndirectObject(&font);
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ fonts = resdict.dictLookupNF("Font");
+#else
resdict.dictLookupNF("Font", &fonts);
+#endif
if (fonts.isNull()) {
/* Create new font dic obj in page's resources */
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ resdict.dictSet("Font", Object(new Dict(xref)));
+#else
fonts.initDict(xref);
resdict.dictSet("Font", &fonts);
+#endif
}
Object *fonts_dic;
@@ -259,7 +353,11 @@
fonts_dic = &fonts;
} else if ( fonts.isRef() ) {
/* "Font" resource is indirect reference object */
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ dereferenced_obj = xref->fetch(fonts.getRefNum(), fonts.getRefGen());
+#else
xref->fetch(fonts.getRefNum(), fonts.getRefGen(), &dereferenced_obj);
+#endif
fonts_dic = &dereferenced_obj;
}
@@ -269,7 +367,11 @@
}
/* Add new entry to "Font" resource */
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ fonts_dic->dictSet("bannertopdf-font", std::move(font));
+#else
fonts_dic->dictSet("bannertopdf-font", &font);
+#endif
/* Notify poppler about changes */
if ( fonts.isRef() ) {
@@ -281,7 +383,9 @@
else
xref->setModifiedObject(&resdict, resref);
+#if POPPLER_VERSION_MAJOR <= 0 && POPPLER_VERSION_MINOR < 58
pageobj.free();
+#endif
}
@@ -293,23 +397,38 @@
Array *array;
int i;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ o = dict->dictLookup(key);
+ if (o.isNull())
+#else
if (!dict->dictLookup(key, &o))
+#endif
return false;
if (!o.isArray()) {
+#if POPPLER_VERSION_MAJOR <= 0 && POPPLER_VERSION_MINOR < 58
o.free();
+#endif
return false;
}
array = o.getArray();
for (i = 0; i < 4; i++) {
Object el;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ el = array->get(i);
+ if (el.isNum())
+ rect[i] = el.getNum();
+#else
if (array->get(i, &el) && el.isNum())
rect[i] = el.getNum();
el.free();
+#endif
}
+#if POPPLER_VERSION_MAJOR <= 0 && POPPLER_VERSION_MINOR < 58
o.free();
+#endif
return i == 4;
}
@@ -322,6 +441,15 @@
Object array;
int i;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ array = Object(new Array(xref));
+
+ for (i = 0; i < 4; i++) {
+ array.arrayAdd(Object(static_cast<double>(rect[i])));
+ }
+
+ dict->dictSet(key, std::move(array));
+#else
array.initArray(xref);
for (i = 0; i < 4; i++) {
@@ -331,6 +459,7 @@
}
dict->dictSet(key, &array);
+#endif
}
@@ -361,7 +490,11 @@
float mediabox[4] = { 0.0, 0.0, width, length };
float old_mediabox[4];
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ pageobj = xref->fetch(pageref->num, pageref->gen);
+#else
xref->fetch(pageref->num, pageref->gen, &pageobj);
+#endif
if (!pageobj.isDict()) {
fprintf(stderr, "Error: malformed pdf\n");
return;
@@ -381,7 +514,9 @@
dict_set_rect (xref, &pageobj, "BleedBox", mediabox);
xref->setModifiedObject(&pageobj, *pageref);
+#if POPPLER_VERSION_MAJOR <= 0 && POPPLER_VERSION_MINOR < 58
pageobj.free();
+#endif
}
@@ -394,21 +529,34 @@
Object page, parentref, parent, kids, ref, countobj;
int i;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ page = xref->fetch(pageref->num, pageref->gen);
+#else
xref->fetch(pageref->num, pageref->gen, &page);
+#endif
if (!page.isDict("Page")) {
fprintf(stderr, "Error: malformed pdf (invalid Page object)\n");
return;
}
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ parentref = page.dictLookupNF("Parent");
+ parent = parentref.fetch(xref);
+#else
page.dictLookupNF("Parent", &parentref);
parentref.fetch(xref, &parent);
+#endif
if (!parent.isDict("Pages")) {
fprintf(stderr, "Error: malformed pdf (Page.Parent must point to a "
"Pages object)\n");
return;
}
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ kids = parent.dictLookup("Kids");
+#else
parent.dictLookup("Kids", &kids);
+#endif
if (!kids.isArray()) {
fprintf(stderr, "Error: malformed pdf (Pages.Kids must be an array)\n");
return;
@@ -420,14 +568,22 @@
// the pages tree (not supported by major pdf implementations).
for (i = 1; i < count; i++) {
Ref r = xref->addIndirectObject(&page);
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ kids.arrayAdd(Object(r.num, r.gen));
+#else
ref.initRef(r.num, r.gen);
kids.arrayAdd(&ref);
ref.free();
+#endif
}
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ parent.dictSet("Count", Object(count));
+#else
countobj.initInt(count);
parent.dictSet("Count", &countobj);
countobj.free();
+#endif
xref->setModifiedObject(&parent, parentref.getRef());
}
@@ -523,7 +679,11 @@
}
Object pageobj;
Ref pageref = page->getRef();
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ pageobj = xref->fetch(pageref.num, pageref.gen);
+#else
xref->fetch(pageref.num, pageref.gen, &pageobj);
+#endif
const char *font_size = lookup_opt(opt, "banner-font-size");
if ( ! font_size ) {
@@ -614,8 +774,12 @@
/* Modify field's appearance */
Object appearance_obj;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ field_obj->getDict()->set("DA", Object(appearance));
+#else
appearance_obj.initString(appearance);
field_obj->getDict()->set("DA", &appearance_obj);
+#endif
/*
* Create /AP - entry stuff.
@@ -653,7 +817,11 @@
appearance_stream->append("EMC\n");
Object appearance_stream_dic;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ appearance_stream_dic = Object(new Dict(xref));
+#else
appearance_stream_dic.initDict(xref);
+#endif
/*
* Appearance stream dic.
@@ -663,12 +831,46 @@
appearance_stream_dic.dictSet("Type", name_object("XObject"));
appearance_stream_dic.dictSet("Subtype", name_object("Form"));
appearance_stream_dic.dictSet("FormType", int_object(1));
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ appearance_stream_dic.dictSet("Resources", Object(resref.num, resref.gen));
+#else
Object obj_ref_x;
obj_ref_x.initRef(resref.num, resref.gen);
appearance_stream_dic.dictSet("Resources", &obj_ref_x);
+#endif
/* BBox array: TODO. currently out of the head. */
Object array;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ array = Object(new Array(xref));
+ array.arrayAdd(Object(0.0));
+ array.arrayAdd(Object(0.0));
+ array.arrayAdd(Object(237.0));
+ array.arrayAdd(Object(25.0));
+
+ appearance_stream_dic.dictSet("BBox", std::move(array));
+ appearance_stream_dic.dictSet("Length", Object(appearance_stream->getLength()));
+
+ MemStream *mem_stream = new MemStream(appearance_stream->getCString(),
+ 0, appearance_stream->getLength(), std::move(appearance_stream_dic));
+
+ /* Make obj stream */
+ Object stream = Object(static_cast<Stream *>(mem_stream));
+
+ Ref r = xref->addIndirectObject(&stream);
+
+ /* Update Xref table */
+ Object obj_ref = Object(r.num, r.gen);
+
+ /*
+ * Fill Annotation's appearance streams dic /AP
+ * See: 8.4.4 Appearance Streams
+ */
+ Object appearance_streams_dic = Object(new Dict(xref));
+ appearance_streams_dic.dictSet("N", std::move(obj_ref));
+
+ field_obj->getDict()->set("AP", std::move(appearance_streams_dic));
+#else
array.initArray(xref);
Object el;
el.initReal(0);
@@ -705,6 +907,7 @@
appearance_streams_dic.dictSet("N", &obj_ref);
field_obj->getDict()->set("AP", &appearance_streams_dic);
+#endif
/* Notify poppler about changes */
xref->setModifiedObject(field_obj, field_ref);
@@ -721,24 +924,38 @@
* OpenOffice - by default sets it to 'true'.
*/
Object *obj_form = catalog->getAcroForm();
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ obj_form->dictSet("NeedAppearances", Object(gFalse));
+#else
Object obj1;
obj1.initBool(gFalse);
obj_form->dictSet("NeedAppearances", &obj1);
+#endif
+
/* Add AccroForm as indirect obj */
Ref ref_form = xref->addIndirectObject(obj_form);
/*
* So update Catalog object.
*/
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ Object catObj = xref->getCatalog();
+#else
Object* catObj = new Object();
catObj = xref->getCatalog(catObj);
+#endif
Ref catRef;
catRef.gen = xref->getRootGen();
catRef.num = xref->getRootNum();
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ catObj.dictSet("AcroForm", Object(ref_form.num, ref_form.gen));
+ xref->setModifiedObject(&catObj, catRef);
+#else
Object obj2;
obj2.initRef(ref_form.num, ref_form.gen);
catObj->dictSet("AcroForm", &obj2);
xref->setModifiedObject(catObj, catRef);
+#endif
/* Success */
return 1;
@@ -780,7 +997,11 @@
/* Font dictionary object for embeded font */
Object f_dic;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ f_dic = Object(new Dict(xref));
+#else
f_dic.initDict(xref);
+#endif
f_dic.dictSet("Type", name_object("Font"));
/* Stream lenght */
@@ -798,12 +1019,18 @@
}
/* Create memory stream font. Add it to font dic. */
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ MemStream *mem_stream = new MemStream(font_stream->getCString(),
+ 0, outlen, std::move(f_dic));
+ Object stream = Object(static_cast<Stream *>(mem_stream));
+#else
MemStream *mem_stream = new MemStream(font_stream->getCString(),
0, outlen, &f_dic);
/* Make obj stream */
Object stream;
stream.initStream(mem_stream);
+#endif
Ref r;
@@ -813,7 +1040,11 @@
/* Get page object */
Object pageobj;
Ref pageref = page->getRef();
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ pageobj = xref->fetch(pageref.num, pageref.gen);
+#else
xref->fetch(pageref.num, pageref.gen, &pageobj);
+#endif
if (!pageobj.isDict()) {
fprintf(stderr, "Error: malformed pdf.\n");
return 0;
@@ -825,18 +1056,29 @@
Object *ret = get_resource_dict(xref, pageobj.getDict(), &resdict, &resref);
if ( !ret ) {
fprintf(stderr, "Error: malformed pdf\n");
+#if POPPLER_VERSION_MAJOR <= 0 && POPPLER_VERSION_MINOR < 58
pageobj.free();
+#endif
return 0;
}
/* Dictionary for all fonts in page's resources */
Object fonts;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ fonts = resdict.dictLookupNF("Font");
+#else
resdict.dictLookupNF("Font", &fonts);
+#endif
if (fonts.isNull()) {
/* Create new one, if doesn't exists */
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ resdict.dictSet("Font", Object(new Dict(xref)));
+ fonts = resdict.dictLookupNF("Font");
+#else
fonts.initDict(xref);
resdict.dictSet("Font", &fonts);
+#endif
fprintf(stderr, "Create new font dict in page's resources.\n");
}
@@ -866,7 +1108,11 @@
/* r - cid resource dic */
Object font_res_obj_ref;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ font_res_obj_ref = Object(r.num, r.gen);
+#else
font_res_obj_ref.initRef(r.num, r.gen);
+#endif
Object *fonts_dic;
Object dereferenced_obj;
@@ -876,7 +1122,11 @@
fonts_dic = &fonts;
} else if ( fonts.isRef() ) {
/* "Font" resource is indirect reference object */
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ dereferenced_obj = xref->fetch(fonts.getRefNum(), fonts.getRefGen());
+#else
xref->fetch(fonts.getRefNum(), fonts.getRefGen(), &dereferenced_obj);
+#endif
fonts_dic = &dereferenced_obj;
}
@@ -886,7 +1136,11 @@
}
/* Add to fonts dic new font */
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ fonts_dic->dictSet("stanv_font", std::move(font_res_obj_ref));
+#else
fonts_dic->dictSet("stanv_font", &font_res_obj_ref);
+#endif
/* Notify poppler about changes in fonts dic */
if ( fonts.isRef() ) {
@@ -897,7 +1151,9 @@
xref->setModifiedObject(&resdict, resref);
fprintf(stderr, "Resource dict was changed.\n");
+#if POPPLER_VERSION_MAJOR <= 0 && POPPLER_VERSION_MINOR < 58
pageobj.free();
+#endif
/* Success */
return 1;
@@ -1104,8 +1360,12 @@
XRef *xref = doc->getXRef();
/* Font dictionary for embeded font */
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ Object *dic = new Object(new Dict(xref));
+#else
Object *dic = new Object();
dic->initDict(xref);
+#endif
dic->dictSet("Type", name_object("FontDescriptor"));
dic->dictSet(
@@ -1119,6 +1379,15 @@
dic->dictSet("StemV", int_object(fdes->stemV));
/* FontBox array */
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ Object array = Object(new Array(xref));
+ array.arrayAdd(Object(static_cast<double>(fdes->bbxmin)));
+ array.arrayAdd(Object(static_cast<double>(fdes->bbymin)));
+ array.arrayAdd(Object(static_cast<double>(fdes->bbxmax)));
+ array.arrayAdd(Object(static_cast<double>(fdes->bbymax)));
+
+ dic->dictSet("FontBBox", std::move(array));
+#else
Object array;
array.initArray(xref);
@@ -1137,6 +1406,7 @@
array.arrayAdd(&el);
dic->dictSet("FontBBox", &array);
+#endif
if (fdes->xHeight) {
dic->dictSet("XHeight", int_object(fdes->xHeight));
@@ -1149,20 +1419,34 @@
if (fdes->panose) {
/* Font dictionary for embeded font */
Object style_dic;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ style_dic = Object(new Dict(xref));
+#else
style_dic.initDict(xref);
-
+#endif
+
+ GooString *panose_str = new GooString(fdes->panose, 12);
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ style_dic.dictSet("Panose", Object(panose_str));
+
+ dic->dictSet("Style", std::move(style_dic));
+#else
Object panose;
- GooString *panose_str = new GooString(fdes->panose, 12);
panose.initString(panose_str);
style_dic.dictSet("Panose", &panose);
dic->dictSet("Style", &style_dic);
+#endif
}
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ dic->dictSet(emb_pdf_get_fontfile_key(emb), Object(fontfile_obj_ref.num, fontfile_obj_ref.gen));
+#else
Object ref_obj;
ref_obj.initRef(fontfile_obj_ref.num, fontfile_obj_ref.gen);
dic->dictSet(emb_pdf_get_fontfile_key(emb), &ref_obj);
+#endif
return dic;
}
@@ -1181,8 +1465,12 @@
/* Get XREF table */
XRef *xref = doc->getXRef();
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ Object *dic = new Object(new Dict(xref));
+#else
Object *dic = new Object();
dic->initDict(xref);
+#endif
dic->dictSet("Type", name_object("Font"));
dic->dictSet(
@@ -1192,15 +1480,23 @@
"BaseFont",
name_object(copyString(emb_pdf_escape_name(fdes->fontname,-1))));
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ dic->dictSet("FontDescriptor", Object(fontdescriptor_obj_ref.num, fontdescriptor_obj_ref.gen));
+#else
Object ref_obj;
ref_obj.initRef(fontdescriptor_obj_ref.num, fontdescriptor_obj_ref.gen);
dic->dictSet("FontDescriptor", &ref_obj);
+#endif
if ( emb->plan & EMB_A_MULTIBYTE ) {
assert(fwid->warray);
Object CIDSystemInfo_dic;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ CIDSystemInfo_dic = Object(new Dict(xref));
+#else
CIDSystemInfo_dic.initDict(xref);
+#endif
Object registry;
Object ordering;
@@ -1208,16 +1504,28 @@
GooString *str;
str = new GooString(copyString(fdes->registry));
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ CIDSystemInfo_dic.dictSet("Registry", Object(str));
+#else
registry.initString(str);
CIDSystemInfo_dic.dictSet("Registry", &registry);
+#endif
str = new GooString(copyString(fdes->ordering));
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ CIDSystemInfo_dic.dictSet("Ordering", Object(str));
+#else
ordering.initString(str);
CIDSystemInfo_dic.dictSet("Ordering", &ordering);
+#endif
CIDSystemInfo_dic.dictSet("Supplement", int_object(fdes->supplement));
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ dic->dictSet("CIDSystemInfo", std::move(CIDSystemInfo_dic));
+#else
dic->dictSet("CIDSystemInfo", &CIDSystemInfo_dic);
+#endif
dic->dictSet("DW", int_object(fwid->default_width));
}
@@ -1249,8 +1557,12 @@
/* Get XREF table */
XRef *xref = doc->getXRef();
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ Object *dic = new Object(new Dict(xref));
+#else
Object *dic = new Object();
dic->initDict(xref);
+#endif
dic->dictSet("Type", name_object("Font"));
dic->dictSet("Subtype", name_object("Type0"));
@@ -1267,13 +1579,24 @@
dic->dictSet("Encoding", name_object(copyString(encoding)));
Object obj;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ obj = Object(fontdescriptor_obj_ref.num, fontdescriptor_obj_ref.gen);
+#else
obj.initRef(fontdescriptor_obj_ref.num, fontdescriptor_obj_ref.gen);
+#endif
Object array;
+#if POPPLER_VERSION_MAJOR > 0 || POPPLER_VERSION_MINOR >= 58
+ array = Object(new Array(xref));
+ array.arrayAdd(std::move(obj));
+
+ dic->dictSet("DescendantFonts", std::move(array));
+#else
array.initArray(xref);
array.arrayAdd(&obj);
dic->dictSet("DescendantFonts", &array);
+#endif
return dic;
}

View file

@ -1 +1 @@
SHA512 (cups-filters-2.0.1.tar.gz) = b5d7b8f5a89a6a6bba0e861dd3c3263195be75996d22129d123f325f6bff74fbabf22f2ee2d953908ffb8294d825af5568af6695896c76ef4082ae98cd19c42c
SHA512 (cups-filters-1.20.0.tar.xz) = b71722cc14f81cf8cbed5b8e980c9689adc2daf6cfa72e4174b6842bd89574090831f0e986b5e32a0e9fc4e29836f04e74e72c48918d7f3a8f65faa3a6c077af