From 3dc527987b102095a53cfebf677023f7eedcc05f Mon Sep 17 00:00:00 2001 From: CentOS Sources Date: Mar 31 2020 09:34:18 +0000 Subject: import poppler-0.26.5-42.el7 --- diff --git a/SOURCES/poppler-0.26.5-JPXStream-length.patch b/SOURCES/poppler-0.26.5-JPXStream-length.patch new file mode 100644 index 0000000..9d7e303 --- /dev/null +++ b/SOURCES/poppler-0.26.5-JPXStream-length.patch @@ -0,0 +1,26 @@ +From 68ef84e5968a4249c2162b839ca6d7975048a557 Mon Sep 17 00:00:00 2001 +From: Albert Astals Cid +Date: Mon, 15 Jul 2019 23:24:22 +0200 +Subject: [PATCH] JPXStream::init: ignore dict Length if clearly broken + +Fixes issue #805 +--- + poppler/JPEG2000Stream.cc | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/poppler/JPEG2000Stream.cc b/poppler/JPEG2000Stream.cc +index 0eea3a2d..8e6902f4 100644 +--- a/poppler/JPEG2000Stream.cc ++++ b/poppler/JPEG2000Stream.cc +@@ -219,7 +219,7 @@ void JPXStream::init() + if (getDict()) getDict()->lookup("Length", &oLen); + + int bufSize = BUFFER_INITIAL_SIZE; +- if (oLen.isInt()) bufSize = oLen.getInt(); ++ if (oLen.isInt() && oLen.getInt() > 0) bufSize = oLen.getInt(); + oLen.free(); + + +-- +2.21.0 + diff --git a/SOURCES/poppler-0.26.5-PSOutputDev-rgb.patch b/SOURCES/poppler-0.26.5-PSOutputDev-rgb.patch new file mode 100644 index 0000000..e488900 --- /dev/null +++ b/SOURCES/poppler-0.26.5-PSOutputDev-rgb.patch @@ -0,0 +1,372 @@ +From 64aa150a92ccb082db6a3383fa734a6ac91cf1bf Mon Sep 17 00:00:00 2001 +From: Marek Kasik +Date: Tue, 30 Apr 2019 18:47:44 +0200 +Subject: [PATCH] PSOutputDev: Don't read outside of image buffer + +Check whether input image is RGB or BGR to not treat +it as CMYK in those cases in PSOutputDev::checkPageSlice(). + +Fixes #751 +--- + poppler/PSOutputDev.cc | 248 ++++++++++++++++++++++++++++++++--------- + 1 file changed, 196 insertions(+), 52 deletions(-) + +diff --git a/poppler/PSOutputDev.cc b/poppler/PSOutputDev.cc +index 0d201835..155a8cbe 100644 +--- a/poppler/PSOutputDev.cc ++++ b/poppler/PSOutputDev.cc +@@ -3342,13 +3342,21 @@ GBool PSOutputDev::checkPageSlice(Page * + } + break; + case psLevel1Sep: ++ GfxColor inputColor; ++ GfxCMYK cmyk; ++ unsigned char cmykColor[4]; ++ GfxDeviceRGBColorSpace *rgbCS; ++ SplashColorMode colorMode; ++ ++ colorMode = bitmap->getMode(); ++ + useBinary = globalParams->getPSBinary(); + p = bitmap->getDataPtr(); + // Check for an all gray image + isGray = gTrue; + for (y = 0; y < h; ++y) { + for (x = 0; x < w; ++x) { +- if (p[4*x] != p[4*x + 1] || p[4*x] != p[4*x + 2]) { ++ if (p[numComps*x] != p[numComps*x + 1] || p[numComps*x] != p[numComps*x + 2]) { + isGray = gFalse; + y = h; + break; +@@ -3365,7 +3373,9 @@ GBool PSOutputDev::checkPageSlice(Page * + col[0] = col[1] = col[2] = col[3] = 0; + if (isGray) { + int g; +- if ((psProcessBlack & processColors) == 0) { ++ if ((psProcessBlack & processColors) == 0 && ++ colorMode != splashModeRGB8 && ++ colorMode != splashModeBGR8) { + // Check if the image uses black + for (y = 0; y < h; ++y) { + for (x = 0; x < w; ++x) { +@@ -3379,59 +3389,23 @@ GBool PSOutputDev::checkPageSlice(Page * + } + p = bitmap->getDataPtr() + (h - 1) * bitmap->getRowSize(); + } +- for (y = 0; y < h; ++y) { +- if (useBinary) { +- // Binary gray image +- for (x = 0; x < w; ++x) { +- g = p[4*x] + p[4*x + 3]; +- g = 255 - g; +- if (g < 0) g = 0; +- hexBuf[i++] = (Guchar) g; +- if (i >= 64) { +- writePSBuf(hexBuf, i); +- i = 0; +- } +- } +- } else { +- // Hex gray image +- for (x = 0; x < w; ++x) { +- g = p[4*x] + p[4*x + 3]; +- g = 255 - g; +- if (g < 0) g = 0; +- digit = g / 16; +- hexBuf[i++] = digit + ((digit >= 10)? 'a' - 10: '0'); +- digit = g % 16; +- hexBuf[i++] = digit + ((digit >= 10)? 'a' - 10: '0'); +- if (i >= 64) { +- hexBuf[i++] = '\n'; +- writePSBuf(hexBuf, i); +- i = 0; +- } +- } +- } +- p -= bitmap->getRowSize(); +- } +- } else if (((psProcessCyan | psProcessMagenta | psProcessYellow | psProcessBlack) & ~processColors) != 0) { +- // Color image, need to check color flags for each dot +- for (y = 0; y < h; ++y) { +- for (comp = 0; comp < 4; ++comp) { ++ if (colorMode == splashModeRGB8 || colorMode != splashModeBGR8) { ++ for (y = 0; y < h; ++y) { + if (useBinary) { +- // Binary color image ++ // Binary gray image + for (x = 0; x < w; ++x) { +- col[comp] |= p[4*x + comp]; +- hexBuf[i++] = p[4*x + comp]; ++ hexBuf[i++] = (Guchar) p[3*x]; + if (i >= 64) { + writePSBuf(hexBuf, i); + i = 0; + } + } + } else { +- // Gray color image ++ // Hex gray image + for (x = 0; x < w; ++x) { +- col[comp] |= p[4*x + comp]; +- digit = p[4*x + comp] / 16; ++ digit = p[3*x] / 16; + hexBuf[i++] = digit + ((digit >= 10)? 'a' - 10: '0'); +- digit = p[4*x + comp] % 16; ++ digit = p[3*x] % 16; + hexBuf[i++] = digit + ((digit >= 10)? 'a' - 10: '0'); + if (i >= 64) { + hexBuf[i++] = '\n'; +@@ -3439,29 +3413,31 @@ GBool PSOutputDev::checkPageSlice(Page * + i = 0; + } + } +- } ++ } + } +- p -= bitmap->getRowSize(); +- } +- } else { +- // Color image, do not need to check color flags +- for (y = 0; y < h; ++y) { +- for (comp = 0; comp < 4; ++comp) { ++ } else { ++ for (y = 0; y < h; ++y) { + if (useBinary) { +- // Binary color image ++ // Binary gray image + for (x = 0; x < w; ++x) { +- hexBuf[i++] = p[4*x + comp]; ++ g = p[4*x] + p[4*x + 3]; ++ g = 255 - g; ++ if (g < 0) g = 0; ++ hexBuf[i++] = (Guchar) g; + if (i >= 64) { + writePSBuf(hexBuf, i); + i = 0; + } + } + } else { +- // Hex color image ++ // Hex gray image + for (x = 0; x < w; ++x) { +- digit = p[4*x + comp] / 16; ++ g = p[4*x] + p[4*x + 3]; ++ g = 255 - g; ++ if (g < 0) g = 0; ++ digit = g / 16; + hexBuf[i++] = digit + ((digit >= 10)? 'a' - 10: '0'); +- digit = p[4*x + comp] % 16; ++ digit = g % 16; + hexBuf[i++] = digit + ((digit >= 10)? 'a' - 10: '0'); + if (i >= 64) { + hexBuf[i++] = '\n'; +@@ -3469,9 +3445,207 @@ GBool PSOutputDev::checkPageSlice(Page * + i = 0; + } + } +- } ++ } + } +- p -= bitmap->getRowSize(); ++ } ++ p -= bitmap->getRowSize(); ++ } else if (((psProcessCyan | psProcessMagenta | psProcessYellow | psProcessBlack) & ~processColors) != 0) { ++ // Color image, need to check color flags for each dot ++ switch (colorMode) { ++ case splashModeRGB8: ++ case splashModeBGR8: ++ rgbCS = new GfxDeviceRGBColorSpace(); ++ for (y = 0; y < h; ++y) { ++ for (comp = 0; comp < 4; ++comp) { ++ if (useBinary) { ++ // Binary color image ++ for (x = 0; x < w; ++x) { ++ if (likely(colorMode == splashModeRGB8)) { ++ inputColor.c[0] = byteToCol(p[3*x + 0]); ++ inputColor.c[1] = byteToCol(p[3*x + 1]); ++ inputColor.c[2] = byteToCol(p[3*x + 2]); ++ } else { ++ inputColor.c[0] = byteToCol(p[3*x + 2]); ++ inputColor.c[1] = byteToCol(p[3*x + 1]); ++ inputColor.c[2] = byteToCol(p[3*x + 0]); ++ } ++ rgbCS->getCMYK(&inputColor, &cmyk); ++ cmykColor[0] = colToByte(cmyk.c); ++ cmykColor[1] = colToByte(cmyk.m); ++ cmykColor[2] = colToByte(cmyk.y); ++ cmykColor[3] = colToByte(cmyk.k); ++ ++ col[comp] |= cmykColor[comp]; ++ hexBuf[i++] = cmykColor[comp]; ++ if (i >= 64) { ++ writePSBuf(hexBuf, i); ++ i = 0; ++ } ++ } ++ } else { ++ // Gray color image ++ for (x = 0; x < w; ++x) { ++ if (likely(colorMode == splashModeRGB8)) { ++ inputColor.c[0] = byteToCol(p[3*x + 0]); ++ inputColor.c[1] = byteToCol(p[3*x + 1]); ++ inputColor.c[2] = byteToCol(p[3*x + 2]); ++ } else { ++ inputColor.c[0] = byteToCol(p[3*x + 2]); ++ inputColor.c[1] = byteToCol(p[3*x + 1]); ++ inputColor.c[2] = byteToCol(p[3*x + 0]); ++ } ++ rgbCS->getCMYK(&inputColor, &cmyk); ++ cmykColor[0] = colToByte(cmyk.c); ++ cmykColor[1] = colToByte(cmyk.m); ++ cmykColor[2] = colToByte(cmyk.y); ++ cmykColor[3] = colToByte(cmyk.k); ++ ++ col[comp] |= cmykColor[comp]; ++ digit = cmykColor[comp] / 16; ++ hexBuf[i++] = digit + ((digit >= 10)? 'a' - 10: '0'); ++ digit = cmykColor[comp] % 16; ++ hexBuf[i++] = digit + ((digit >= 10)? 'a' - 10: '0'); ++ if (i >= 64) { ++ hexBuf[i++] = '\n'; ++ writePSBuf(hexBuf, i); ++ i = 0; ++ } ++ } ++ } ++ } ++ p -= bitmap->getRowSize(); ++ } ++ delete rgbCS; ++ break; ++ default: ++ for (y = 0; y < h; ++y) { ++ for (comp = 0; comp < 4; ++comp) { ++ if (useBinary) { ++ // Binary color image ++ for (x = 0; x < w; ++x) { ++ col[comp] |= p[4*x + comp]; ++ hexBuf[i++] = p[4*x + comp]; ++ if (i >= 64) { ++ writePSBuf(hexBuf, i); ++ i = 0; ++ } ++ } ++ } else { ++ // Gray color image ++ for (x = 0; x < w; ++x) { ++ col[comp] |= p[4*x + comp]; ++ digit = p[4*x + comp] / 16; ++ hexBuf[i++] = digit + ((digit >= 10)? 'a' - 10: '0'); ++ digit = p[4*x + comp] % 16; ++ hexBuf[i++] = digit + ((digit >= 10)? 'a' - 10: '0'); ++ if (i >= 64) { ++ hexBuf[i++] = '\n'; ++ writePSBuf(hexBuf, i); ++ i = 0; ++ } ++ } ++ } ++ } ++ p -= bitmap->getRowSize(); ++ } ++ break; ++ } ++ } else { ++ // Color image, do not need to check color flags ++ switch (colorMode) { ++ case splashModeRGB8: ++ case splashModeBGR8: ++ rgbCS = new GfxDeviceRGBColorSpace(); ++ for (y = 0; y < h; ++y) { ++ for (comp = 0; comp < 4; ++comp) { ++ if (useBinary) { ++ // Binary color image ++ for (x = 0; x < w; ++x) { ++ if (likely(colorMode == splashModeRGB8)) { ++ inputColor.c[0] = byteToCol(p[3*x + 0]); ++ inputColor.c[1] = byteToCol(p[3*x + 1]); ++ inputColor.c[2] = byteToCol(p[3*x + 2]); ++ } else { ++ inputColor.c[0] = byteToCol(p[3*x + 2]); ++ inputColor.c[1] = byteToCol(p[3*x + 1]); ++ inputColor.c[2] = byteToCol(p[3*x + 0]); ++ } ++ rgbCS->getCMYK(&inputColor, &cmyk); ++ cmykColor[0] = colToByte(cmyk.c); ++ cmykColor[1] = colToByte(cmyk.m); ++ cmykColor[2] = colToByte(cmyk.y); ++ cmykColor[3] = colToByte(cmyk.k); ++ ++ hexBuf[i++] = cmykColor[comp]; ++ if (i >= 64) { ++ writePSBuf(hexBuf, i); ++ i = 0; ++ } ++ } ++ } else { ++ // Hex color image ++ for (x = 0; x < w; ++x) { ++ if (likely(colorMode == splashModeRGB8)) { ++ inputColor.c[0] = byteToCol(p[3*x + 0]); ++ inputColor.c[1] = byteToCol(p[3*x + 1]); ++ inputColor.c[2] = byteToCol(p[3*x + 2]); ++ } else { ++ inputColor.c[0] = byteToCol(p[3*x + 2]); ++ inputColor.c[1] = byteToCol(p[3*x + 1]); ++ inputColor.c[2] = byteToCol(p[3*x + 0]); ++ } ++ rgbCS->getCMYK(&inputColor, &cmyk); ++ cmykColor[0] = colToByte(cmyk.c); ++ cmykColor[1] = colToByte(cmyk.m); ++ cmykColor[2] = colToByte(cmyk.y); ++ cmykColor[3] = colToByte(cmyk.k); ++ ++ digit = cmykColor[comp] / 16; ++ hexBuf[i++] = digit + ((digit >= 10)? 'a' - 10: '0'); ++ digit = cmykColor[comp] % 16; ++ hexBuf[i++] = digit + ((digit >= 10)? 'a' - 10: '0'); ++ if (i >= 64) { ++ hexBuf[i++] = '\n'; ++ writePSBuf(hexBuf, i); ++ i = 0; ++ } ++ } ++ } ++ } ++ p -= bitmap->getRowSize(); ++ } ++ delete rgbCS; ++ break; ++ default: ++ for (y = 0; y < h; ++y) { ++ for (comp = 0; comp < 4; ++comp) { ++ if (useBinary) { ++ // Binary color image ++ for (x = 0; x < w; ++x) { ++ hexBuf[i++] = p[4*x + comp]; ++ if (i >= 64) { ++ writePSBuf(hexBuf, i); ++ i = 0; ++ } ++ } ++ } else { ++ // Hex color image ++ for (x = 0; x < w; ++x) { ++ digit = p[4*x + comp] / 16; ++ hexBuf[i++] = digit + ((digit >= 10)? 'a' - 10: '0'); ++ digit = p[4*x + comp] % 16; ++ hexBuf[i++] = digit + ((digit >= 10)? 'a' - 10: '0'); ++ if (i >= 64) { ++ hexBuf[i++] = '\n'; ++ writePSBuf(hexBuf, i); ++ i = 0; ++ } ++ } ++ } ++ } ++ p -= bitmap->getRowSize(); ++ } ++ break; + } + } + if (i != 0) { diff --git a/SOURCES/poppler-0.26.5-jpeg2000-component-size.patch b/SOURCES/poppler-0.26.5-jpeg2000-component-size.patch new file mode 100644 index 0000000..20562da --- /dev/null +++ b/SOURCES/poppler-0.26.5-jpeg2000-component-size.patch @@ -0,0 +1,41 @@ +From 89a5367d49b2556a2635dbb6d48d6a6b182a2c6c Mon Sep 17 00:00:00 2001 +From: Albert Astals Cid +Date: Thu, 23 May 2019 00:54:29 +0200 +Subject: [PATCH] JPEG2000Stream: fail gracefully if not all components have + the same WxH + +I think this is just a mistake, or at least the only file we have with +this scenario is a fuzzed one +--- + poppler/JPEG2000Stream.cc | 8 +++++++- + 1 file changed, 7 insertions(+), 1 deletion(-) + +diff --git a/poppler/JPEG2000Stream.cc b/poppler/JPEG2000Stream.cc +index 15bbcae4..0eea3a2d 100644 +--- a/poppler/JPEG2000Stream.cc ++++ b/poppler/JPEG2000Stream.cc +@@ -4,7 +4,7 @@ + // + // A JPX stream decoder using OpenJPEG + // +-// Copyright 2008-2010, 2012 Albert Astals Cid ++// Copyright 2008-2010, 2012, 2019 Albert Astals Cid + // Copyright 2011 Daniel Glöckner + // Copyright 2013 Adrian Johnson + // +@@ -253,6 +253,12 @@ void JPXStream::init() + close(); + break; + } ++ const int componentPixels = image->comps[component].w * image->comps[component].h; ++ if (componentPixels != npixels) { ++ error(errSyntaxWarning, -1, "Component {0:d} has different WxH than component 0", component); ++ close(); ++ break; ++ } + unsigned char *cdata = (unsigned char *)image->comps[component].data; + int adjust = 0; + if (image->comps[component].prec > 8) +-- +2.21.0 + diff --git a/SOURCES/poppler-0.26.5-parser-integer-overflow.patch b/SOURCES/poppler-0.26.5-parser-integer-overflow.patch new file mode 100644 index 0000000..059a467 --- /dev/null +++ b/SOURCES/poppler-0.26.5-parser-integer-overflow.patch @@ -0,0 +1,23 @@ +--- poppler-0.26.5/poppler/Parser.cc ++++ poppler-0.26.5/poppler/Parser.cc +@@ -19,6 +19,7 @@ + // Copyright (C) 2012 Hib Eris + // Copyright (C) 2013 Adrian Johnson + // Copyright (C) 2013 Thomas Freitag ++// Copyright (C) 2018 Albert Astals Cid + // + // To see a description of the changes please see the Changelog file that + // came with your tarball or type make ChangeLog if you are building from git +@@ -257,6 +258,12 @@ Stream *Parser::makeStream(Object *dict, + pos = pos - 1; + lexer->lookCharLastValueCached = Lexer::LOOK_VALUE_NOT_CACHED; + } ++ if (unlikely(length < 0)) { ++ return NULL; ++ } ++ if (unlikely(pos > LONG_LONG_MAX - length)) { ++ return NULL; ++ } + lexer->setPos(pos + length); + + // refill token buffers and check for 'endstream' diff --git a/SPECS/poppler.spec b/SPECS/poppler.spec index 42ca775..9408e7b 100644 --- a/SPECS/poppler.spec +++ b/SPECS/poppler.spec @@ -1,7 +1,7 @@ Summary: PDF rendering library Name: poppler Version: 0.26.5 -Release: 38%{?dist} +Release: 42%{?dist} License: (GPLv2 or GPLv3) and GPLv2+ and LGPLv2+ and MIT Group: Development/Libraries URL: http://poppler.freedesktop.org/ @@ -117,6 +117,18 @@ Patch39: poppler-0.26.5-tiling-patterns.patch Patch40: poppler-0.26.5-coverage-values.patch Patch41: poppler-0.26.5-rescale-filter.patch +# https://bugzilla.redhat.com/show_bug.cgi?id=1696636 +Patch42: poppler-0.26.5-PSOutputDev-rgb.patch + +# https://bugzilla.redhat.com/show_bug.cgi?id=1713582 +Patch43: poppler-0.26.5-jpeg2000-component-size.patch + +# https://bugzilla.redhat.com/show_bug.cgi?id=1732340 +Patch44: poppler-0.26.5-JPXStream-length.patch + +# https://bugzilla.redhat.com/show_bug.cgi?id=1753850 +Patch45: poppler-0.26.5-parser-integer-overflow.patch + Requires: poppler-data >= 0.4.0 BuildRequires: automake libtool BuildRequires: gettext-devel @@ -274,6 +286,10 @@ Requires: %{name}%{?_isa} = %{version}-%{release} %patch39 -p1 -b .tiling-pattern %patch40 -p1 -b .coverage-values %patch41 -p1 -b .rescale-filter +%patch42 -p1 -b .psoutputdev-rgb +%patch43 -p1 -b .jpeg2000-component-size +%patch44 -p1 -b .jpxstream-length +%patch45 -p1 -b .parser-integer-overflow # hammer to nuke rpaths, recheck on new releases autoreconf -i -f @@ -395,6 +411,23 @@ test "$(pkg-config --modversion poppler-splash)" = "%{version}" %changelog +* Fri Nov 15 2019 Marek Kasik - 0.26.5-42 +- Fix potential integer overflow and check length for negative values +- Resolves: #1757283 + +* Tue Aug 13 2019 Marek Kasik - 0.26.5-41 +- Ignore dict Length if it is broken +- Resolves: #1733026 + +* Tue Aug 13 2019 Marek Kasik - 0.26.5-40 +- Fail gracefully if not all components of JPEG2000Stream +- have the same size +- Resolves: #1723504 + +* Tue Aug 13 2019 Marek Kasik - 0.26.5-39 +- Check whether input is RGB in PSOutputDev::checkPageSlice() +- Resolves: #1697575 + * Fri Mar 29 2019 Marek Kasik - 0.26.5-38 - Constrain number of cycles in rescale filter - Compute correct coverage values for box filter