poppler/CairoOutputDev.cc | 2 - poppler/Gfx.cc | 53 +++++++++++++++++++++++++-------------------- poppler/Gfx.h | 4 +-- poppler/PSOutputDev.cc | 2 - poppler/SplashOutputDev.cc | 2 - 5 files changed, 35 insertions(+), 28 deletions(-)
New commits: commit 1b65f9eb1beef0d1a41a4d59c89e4acd193a1a3f Author: Albert Astals Cid <[email protected]> Date: Fri Jun 22 17:29:26 2018 +0200 Gfx:Generalize protection against a pattern drawing itself fixes oss-fuzz/8929 diff --git a/poppler/CairoOutputDev.cc b/poppler/CairoOutputDev.cc index 18124b8f..8e8102e9 100644 --- a/poppler/CairoOutputDev.cc +++ b/poppler/CairoOutputDev.cc @@ -960,7 +960,7 @@ GBool CairoOutputDev::tilingPatternFill(GfxState *state, Gfx *gfxA, Catalog *cat adjusted_stroke_width_tmp = adjusted_stroke_width; maskTmp = mask; mask = nullptr; - gfx = new Gfx(doc, this, resDict, &box, nullptr, nullptr, nullptr, gfxA->getXRef()); + gfx = new Gfx(doc, this, resDict, &box, nullptr, nullptr, nullptr, gfxA); if (paintType == 2) inUncoloredPattern = gTrue; gfx->display(str); diff --git a/poppler/Gfx.cc b/poppler/Gfx.cc index 572f435c..0763e49f 100644 --- a/poppler/Gfx.cc +++ b/poppler/Gfx.cc @@ -589,12 +589,18 @@ Gfx::Gfx(PDFDoc *docA, OutputDev *outA, int pageNum, Dict *resDict, Gfx::Gfx(PDFDoc *docA, OutputDev *outA, Dict *resDict, PDFRectangle *box, PDFRectangle *cropBox, GBool (*abortCheckCbkA)(void *data), - void *abortCheckCbkDataA, XRef *xrefA) + void *abortCheckCbkDataA, Gfx *gfxA) { int i; doc = docA; - xref = (xrefA == nullptr) ? doc->getXRef() : xrefA; + if (gfxA) { + xref = gfxA->getXRef(); + formsDrawing = gfxA->formsDrawing; + charProcDrawing = gfxA->charProcDrawing; + } else { + xref = doc->getXRef(); + } catalog = doc->getCatalog(); subPage = gTrue; printCommands = globalParams->getPrintCommands(); @@ -2202,37 +2208,38 @@ void Gfx::doTilingPatternFill(GfxTilingPattern *tPat, } m1[4] = m[4]; m1[5] = m[5]; - if (out->useTilingPatternFill() && - out->tilingPatternFill(state, this, catalog, tPat->getContentStream(), - tPat->getMatrix(), tPat->getPaintType(), tPat->getTilingType(), - tPat->getResDict(), m1, tPat->getBBox(), - xi0, yi0, xi1, yi1, xstep, ystep)) { - goto restore; - } else { - bool shouldDrawForm = gTrue; + { + bool shouldDrawPattern = gTrue; std::set<int>::iterator patternRefIt; const int patternRefNum = tPat->getPatternRefNum(); if (patternRefNum != -1) { if (formsDrawing.find(patternRefNum) == formsDrawing.end()) { patternRefIt = formsDrawing.insert(patternRefNum).first; } else { - shouldDrawForm = gFalse; + shouldDrawPattern = gFalse; } } - - if (shouldDrawForm) { - out->updatePatternOpacity(state); - for (yi = yi0; yi < yi1; ++yi) { - for (xi = xi0; xi < xi1; ++xi) { - x = xi * xstep; - y = yi * ystep; - m1[4] = x * m[0] + y * m[2] + m[4]; - m1[5] = x * m[1] + y * m[3] + m[5]; - drawForm(tPat->getContentStream(), tPat->getResDict(), - m1, tPat->getBBox()); + if (shouldDrawPattern) { + if (out->useTilingPatternFill() && + out->tilingPatternFill(state, this, catalog, tPat->getContentStream(), + tPat->getMatrix(), tPat->getPaintType(), tPat->getTilingType(), + tPat->getResDict(), m1, tPat->getBBox(), + xi0, yi0, xi1, yi1, xstep, ystep)) { + // do nothing + } else { + out->updatePatternOpacity(state); + for (yi = yi0; yi < yi1; ++yi) { + for (xi = xi0; xi < xi1; ++xi) { + x = xi * xstep; + y = yi * ystep; + m1[4] = x * m[0] + y * m[2] + m[4]; + m1[5] = x * m[1] + y * m[3] + m[5]; + drawForm(tPat->getContentStream(), tPat->getResDict(), + m1, tPat->getBBox()); + } } + out->clearPatternOpacity(state); } - out->clearPatternOpacity(state); if (patternRefNum != -1) { formsDrawing.erase(patternRefIt); } diff --git a/poppler/Gfx.h b/poppler/Gfx.h index 2ea0d9fa..3ac4c929 100644 --- a/poppler/Gfx.h +++ b/poppler/Gfx.h @@ -161,7 +161,7 @@ public: Gfx(PDFDoc *docA, OutputDev *outA, Dict *resDict, PDFRectangle *box, PDFRectangle *cropBox, GBool (*abortCheckCbkA)(void *data) = NULL, - void *abortCheckCbkDataA = NULL, XRef *xrefA = NULL); + void *abortCheckCbkDataA = NULL, Gfx *gfxA = NULL); #ifdef USE_CMS void initDisplayProfile(); #endif @@ -236,7 +236,7 @@ private: Parser *parser; // parser for page content stream(s) - std::set<int> formsDrawing; // the forms that are being drawn + std::set<int> formsDrawing; // the forms/patterns that are being drawn std::set<int> charProcDrawing; // the charProc that are being drawn GBool // callback to check for an abort diff --git a/poppler/PSOutputDev.cc b/poppler/PSOutputDev.cc index b466bc69..d1ead586 100644 --- a/poppler/PSOutputDev.cc +++ b/poppler/PSOutputDev.cc @@ -4526,7 +4526,7 @@ GBool PSOutputDev::tilingPatternFill(GfxState *state, Gfx *gfxA, Catalog *cat, O box.y1 = bbox[1]; box.x2 = bbox[2]; box.y2 = bbox[3]; - gfx = new Gfx(doc, this, resDict, &box, nullptr, nullptr, nullptr, gfxA->getXRef()); + gfx = new Gfx(doc, this, resDict, &box, nullptr, nullptr, nullptr, gfxA); writePSFmt("[{0:.6g} {1:.6g} {2:.6g} {3:.6g} {4:.6g} {5:.6g}] cm\n", mat[0], mat[1], mat[2], mat[3], tx, ty); inType3Char = gTrue; gfx->display(str); diff --git a/poppler/SplashOutputDev.cc b/poppler/SplashOutputDev.cc index 74953839..3e883970 100644 --- a/poppler/SplashOutputDev.cc +++ b/poppler/SplashOutputDev.cc @@ -4697,7 +4697,7 @@ GBool SplashOutputDev::tilingPatternFill(GfxState *state, Gfx *gfxA, Catalog *ca box.x1 = bbox[0]; box.y1 = bbox[1]; box.x2 = bbox[2]; box.y2 = bbox[3]; - gfx = new Gfx(doc, this, resDict, &box, nullptr, nullptr, nullptr, gfxA->getXRef()); + gfx = new Gfx(doc, this, resDict, &box, nullptr, nullptr, nullptr, gfxA); // set pattern transformation matrix gfx->getState()->setCTM(m1.m[0], m1.m[1], m1.m[2], m1.m[3], m1.m[4], m1.m[5]); updateCTM(gfx->getState(), m1.m[0], m1.m[1], m1.m[2], m1.m[3], m1.m[4], m1.m[5]); _______________________________________________ poppler mailing list [email protected] https://lists.freedesktop.org/mailman/listinfo/poppler
