diff options
Diffstat (limited to 'Build/source/libs/xpdf/xpdf-src/xpdf/Gfx.cc')
-rw-r--r-- | Build/source/libs/xpdf/xpdf-src/xpdf/Gfx.cc | 184 |
1 files changed, 114 insertions, 70 deletions
diff --git a/Build/source/libs/xpdf/xpdf-src/xpdf/Gfx.cc b/Build/source/libs/xpdf/xpdf-src/xpdf/Gfx.cc index 5d34eb9f9ab..7a0c9c6a9a5 100644 --- a/Build/source/libs/xpdf/xpdf-src/xpdf/Gfx.cc +++ b/Build/source/libs/xpdf/xpdf-src/xpdf/Gfx.cc @@ -919,12 +919,24 @@ void Gfx::opSetFlat(Object args[], int numArgs) { } void Gfx::opSetLineJoin(Object args[], int numArgs) { - state->setLineJoin(args[0].getInt()); + int lineJoin; + + lineJoin = args[0].getInt(); + if (lineJoin < 0 || lineJoin > 2) { + lineJoin = 0; + } + state->setLineJoin(lineJoin); out->updateLineJoin(state); } void Gfx::opSetLineCap(Object args[], int numArgs) { - state->setLineCap(args[0].getInt()); + int lineCap; + + lineCap = args[0].getInt(); + if (lineCap < 0 || lineCap > 2) { + lineCap = 0; + } + state->setLineCap(lineCap); out->updateLineCap(state); } @@ -1041,17 +1053,17 @@ void Gfx::opSetExtGState(Object args[], int numArgs) { // fill/stroke overprint, overprint mode if ((haveFillOP = (obj1.dictLookup("op", &obj2)->isBool()))) { - if (!state->getInCachedT3Char()) { + if (!state->getIgnoreColorOps()) { state->setFillOverprint(obj2.getBool()); out->updateFillOverprint(state); } else { - error(errSyntaxWarning, getPos(), - "Ignoring overprint setting in cached Type 3 character"); + error(errSyntaxWarning, getPos(), "Ignoring overprint setting" + " in uncolored Type 3 char or tiling pattern"); } } obj2.free(); if (obj1.dictLookup("OP", &obj2)->isBool()) { - if (!state->getInCachedT3Char()) { + if (!state->getIgnoreColorOps()) { state->setStrokeOverprint(obj2.getBool()); out->updateStrokeOverprint(state); if (!haveFillOP) { @@ -1059,18 +1071,18 @@ void Gfx::opSetExtGState(Object args[], int numArgs) { out->updateFillOverprint(state); } } else { - error(errSyntaxWarning, getPos(), - "Ignoring overprint setting in cached Type 3 character"); + error(errSyntaxWarning, getPos(), "Ignoring overprint setting" + " in uncolored Type 3 char or tiling pattern"); } } obj2.free(); if (obj1.dictLookup("OPM", &obj2)->isInt()) { - if (!state->getInCachedT3Char()) { + if (!state->getIgnoreColorOps()) { state->setOverprintMode(obj2.getInt()); out->updateOverprintMode(state); } else { - error(errSyntaxWarning, getPos(), - "Ignoring overprint setting in cached Type 3 character"); + error(errSyntaxWarning, getPos(), "Ignoring overprint setting" + " in uncolored Type 3 char or tiling pattern"); } } obj2.free(); @@ -1088,7 +1100,7 @@ void Gfx::opSetExtGState(Object args[], int numArgs) { obj1.dictLookup("TR", &obj2); } if (!obj2.isNull()) { - if (!state->getInCachedT3Char()) { + if (!state->getIgnoreColorOps()) { if (obj2.isName("Default") || obj2.isName("Identity")) { funcs[0] = funcs[1] = funcs[2] = funcs[3] = NULL; @@ -1097,7 +1109,7 @@ void Gfx::opSetExtGState(Object args[], int numArgs) { } else if (obj2.isArray() && obj2.arrayGetLength() == 4) { for (i = 0; i < 4; ++i) { obj2.arrayGet(i, &obj3); - funcs[i] = Function::parse(&obj3); + funcs[i] = Function::parse(&obj3, 1, 1); obj3.free(); if (!funcs[i]) { break; @@ -1108,7 +1120,7 @@ void Gfx::opSetExtGState(Object args[], int numArgs) { out->updateTransfer(state); } } else if (obj2.isName() || obj2.isDict() || obj2.isStream()) { - if ((funcs[0] = Function::parse(&obj2))) { + if ((funcs[0] = Function::parse(&obj2, 1, 1))) { funcs[1] = funcs[2] = funcs[3] = NULL; state->setTransfer(funcs); out->updateTransfer(state); @@ -1118,8 +1130,8 @@ void Gfx::opSetExtGState(Object args[], int numArgs) { "Invalid transfer function in ExtGState"); } } else { - error(errSyntaxWarning, getPos(), - "Ignoring transfer function setting in cached Type 3 character"); + error(errSyntaxWarning, getPos(), "Ignoring transfer function setting" + " in uncolored Type 3 char or tiling pattern"); } } obj2.free(); @@ -1129,9 +1141,14 @@ void Gfx::opSetExtGState(Object args[], int numArgs) { if (obj2.isName("None")) { out->clearSoftMask(state); } else if (obj2.isDict()) { - if (obj2.dictLookup("S", &obj3)->isName("Alpha")) { + obj2.dictLookup("S", &obj3); + if (obj3.isName("Alpha")) { alpha = gTrue; - } else { // "Luminosity" + } else if (obj3.isName("Luminosity")) { + alpha = gFalse; + } else { + error(errSyntaxError, getPos(), + "Missing S (subtype) entry in soft mask"); alpha = gFalse; } obj3.free(); @@ -1141,9 +1158,7 @@ void Gfx::opSetExtGState(Object args[], int numArgs) { obj3.isName("Identity")) { funcs[0] = NULL; } else { - funcs[0] = Function::parse(&obj3); - if (funcs[0]->getInputSize() != 1 || - funcs[0]->getOutputSize() != 1) { + if (!(funcs[0] = Function::parse(&obj3, 1, 1))) { error(errSyntaxError, getPos(), "Invalid transfer function in soft mask in ExtGState"); delete funcs[0]; @@ -1290,9 +1305,9 @@ void Gfx::doSoftMask(Object *str, Object *strRef, GBool alpha, void Gfx::opSetRenderingIntent(Object args[], int numArgs) { GfxRenderingIntent ri; - if (state->getInCachedT3Char()) { - error(errSyntaxWarning, getPos(), - "Ignoring rendering intent setting in cached Type 3 character"); + if (state->getIgnoreColorOps()) { + error(errSyntaxWarning, getPos(), "Ignoring rendering intent setting" + " in uncolored Type 3 char or tiling pattern"); return; } ri = parseRenderingIntent(args[0].getName()); @@ -1320,9 +1335,9 @@ GfxRenderingIntent Gfx::parseRenderingIntent(const char *name) { void Gfx::opSetFillGray(Object args[], int numArgs) { GfxColor color; - if (state->getInCachedT3Char()) { - error(errSyntaxWarning, getPos(), - "Ignoring color setting in cached Type 3 character"); + if (state->getIgnoreColorOps()) { + error(errSyntaxWarning, getPos(), "Ignoring color setting" + " in uncolored Type 3 char or tiling pattern"); return; } state->setFillPattern(NULL); @@ -1336,9 +1351,9 @@ void Gfx::opSetFillGray(Object args[], int numArgs) { void Gfx::opSetStrokeGray(Object args[], int numArgs) { GfxColor color; - if (state->getInCachedT3Char()) { - error(errSyntaxWarning, getPos(), - "Ignoring color setting in cached Type 3 character"); + if (state->getIgnoreColorOps()) { + error(errSyntaxWarning, getPos(), "Ignoring color setting" + " in uncolored Type 3 char or tiling pattern"); return; } state->setStrokePattern(NULL); @@ -1353,9 +1368,9 @@ void Gfx::opSetFillCMYKColor(Object args[], int numArgs) { GfxColor color; int i; - if (state->getInCachedT3Char()) { - error(errSyntaxWarning, getPos(), - "Ignoring color setting in cached Type 3 character"); + if (state->getIgnoreColorOps()) { + error(errSyntaxWarning, getPos(), "Ignoring color setting" + " in uncolored Type 3 char or tiling pattern"); return; } state->setFillPattern(NULL); @@ -1372,9 +1387,9 @@ void Gfx::opSetStrokeCMYKColor(Object args[], int numArgs) { GfxColor color; int i; - if (state->getInCachedT3Char()) { - error(errSyntaxWarning, getPos(), - "Ignoring color setting in cached Type 3 character"); + if (state->getIgnoreColorOps()) { + error(errSyntaxWarning, getPos(), "Ignoring color setting" + " in uncolored Type 3 char or tiling pattern"); return; } state->setStrokePattern(NULL); @@ -1391,9 +1406,9 @@ void Gfx::opSetFillRGBColor(Object args[], int numArgs) { GfxColor color; int i; - if (state->getInCachedT3Char()) { - error(errSyntaxWarning, getPos(), - "Ignoring color setting in cached Type 3 character"); + if (state->getIgnoreColorOps()) { + error(errSyntaxWarning, getPos(), "Ignoring color setting" + " in uncolored Type 3 char or tiling pattern"); return; } state->setFillPattern(NULL); @@ -1410,9 +1425,9 @@ void Gfx::opSetStrokeRGBColor(Object args[], int numArgs) { GfxColor color; int i; - if (state->getInCachedT3Char()) { - error(errSyntaxWarning, getPos(), - "Ignoring color setting in cached Type 3 character"); + if (state->getIgnoreColorOps()) { + error(errSyntaxWarning, getPos(), "Ignoring color setting" + " in uncolored Type 3 char or tiling pattern"); return; } state->setStrokePattern(NULL); @@ -1430,9 +1445,9 @@ void Gfx::opSetFillColorSpace(Object args[], int numArgs) { GfxColorSpace *colorSpace; GfxColor color; - if (state->getInCachedT3Char()) { - error(errSyntaxWarning, getPos(), - "Ignoring color space setting in cached Type 3 character"); + if (state->getIgnoreColorOps()) { + error(errSyntaxWarning, getPos(), "Ignoring color space setting" + " in uncolored Type 3 char or tiling pattern"); return; } state->setFillPattern(NULL); @@ -1461,9 +1476,9 @@ void Gfx::opSetStrokeColorSpace(Object args[], int numArgs) { GfxColorSpace *colorSpace; GfxColor color; - if (state->getInCachedT3Char()) { - error(errSyntaxWarning, getPos(), - "Ignoring color space setting in cached Type 3 character"); + if (state->getIgnoreColorOps()) { + error(errSyntaxWarning, getPos(), "Ignoring color space setting" + " in uncolored Type 3 char or tiling pattern"); return; } state->setStrokePattern(NULL); @@ -1491,9 +1506,9 @@ void Gfx::opSetFillColor(Object args[], int numArgs) { GfxColor color; int i; - if (state->getInCachedT3Char()) { - error(errSyntaxWarning, getPos(), - "Ignoring color setting in cached Type 3 character"); + if (state->getIgnoreColorOps()) { + error(errSyntaxWarning, getPos(), "Ignoring color setting" + " in uncolored Type 3 char or tiling pattern"); return; } if (numArgs != state->getFillColorSpace()->getNComps()) { @@ -1531,9 +1546,9 @@ void Gfx::opSetFillColorN(Object args[], int numArgs) { GfxPattern *pattern; int i; - if (state->getInCachedT3Char()) { - error(errSyntaxWarning, getPos(), - "Ignoring color setting in cached Type 3 character"); + if (state->getIgnoreColorOps()) { + error(errSyntaxWarning, getPos(), "Ignoring color setting" + " in uncolored Type 3 char or tiling pattern"); return; } if (state->getFillColorSpace()->getMode() == csPattern) { @@ -1585,9 +1600,9 @@ void Gfx::opSetStrokeColorN(Object args[], int numArgs) { GfxPattern *pattern; int i; - if (state->getInCachedT3Char()) { - error(errSyntaxWarning, getPos(), - "Ignoring color setting in cached Type 3 character"); + if (state->getIgnoreColorOps()) { + error(errSyntaxWarning, getPos(), "Ignoring color setting" + " in uncolored Type 3 char or tiling pattern"); return; } if (state->getStrokeColorSpace()->getMode() == csPattern) { @@ -2068,6 +2083,7 @@ void Gfx::doTilingPatternFill(GfxTilingPattern *tPat, state->setStrokeColor(state->getFillColor()); out->updateFillColor(state); out->updateStrokeColor(state); + state->setIgnoreColorOps(gTrue); } else { state->setFillColorSpace(GfxColorSpace::create(csDeviceGray)); out->updateFillColorSpace(state); @@ -2223,6 +2239,7 @@ void Gfx::doShadingPatternFill(GfxShadingPattern *sPat, if (stroke) { state->clipToStrokePath(); out->clipToStrokePath(state); + state->setFillOverprint(state->getStrokeOverprint()); } else if (!text) { state->clip(); if (eoFill) { @@ -2241,6 +2258,7 @@ void Gfx::doShadingPatternFill(GfxShadingPattern *sPat, det = ctm[0] * ctm[3] - ctm[1] * ctm[2]; if (fabs(det) <= 1e-10) { error(errSyntaxError, getPos(), "Singular matrix in shading pattern fill"); + restoreStateStack(savedState); return; } det = 1 / det; @@ -2338,9 +2356,9 @@ void Gfx::opShFill(Object args[], int numArgs) { GfxState *savedState; double xMin, yMin, xMax, yMax; - if (state->getInCachedT3Char()) { - error(errSyntaxWarning, getPos(), - "Ignoring shaded fill in cached Type 3 character"); + if (state->getIgnoreColorOps()) { + error(errSyntaxWarning, getPos(), "Ignoring shaded fill" + " in uncolored Type 3 char or tiling pattern"); return; } @@ -4123,7 +4141,7 @@ void Gfx::opXObject(Object args[], int numArgs) { ocState = ocSaved; } -void Gfx::doImage(Object *ref, Stream *str, GBool inlineImg) { +GBool Gfx::doImage(Object *ref, Stream *str, GBool inlineImg) { Dict *dict, *maskDict; int width, height; int bits, maskBits; @@ -4145,7 +4163,7 @@ void Gfx::doImage(Object *ref, Stream *str, GBool inlineImg) { // check for optional content if (!ocState && !inlineImg) { - return; + return gTrue; } // get info from the stream @@ -4309,6 +4327,11 @@ void Gfx::doImage(Object *ref, Stream *str, GBool inlineImg) { if (!colorSpace) { goto err1; } + if (colorSpace->getMode() == csPattern) { + error(errSyntaxError, getPos(), "Image with a Pattern color space"); + delete colorSpace; + goto err1; + } dict->lookup("Decode", &obj1); if (obj1.isNull()) { obj1.free(); @@ -4365,6 +4388,12 @@ void Gfx::doImage(Object *ref, Stream *str, GBool inlineImg) { } maskHeight = obj1.getInt(); obj1.free(); + if (maskWidth <= 0 || maskHeight <= 0) { + delete colorMap; + maskObj.free(); + smaskObj.free(); + goto err1; + } maskDict->lookup("BitsPerComponent", &obj1); if (obj1.isNull()) { obj1.free(); @@ -4378,6 +4407,12 @@ void Gfx::doImage(Object *ref, Stream *str, GBool inlineImg) { } maskBits = obj1.getInt(); obj1.free(); + if (maskBits < 1 || maskBits > 16) { + delete colorMap; + maskObj.free(); + smaskObj.free(); + goto err1; + } maskDict->lookup("ColorSpace", &obj1); if (obj1.isNull()) { obj1.free(); @@ -4501,6 +4536,12 @@ void Gfx::doImage(Object *ref, Stream *str, GBool inlineImg) { } maskHeight = obj1.getInt(); obj1.free(); + if (maskWidth <= 0 || maskHeight <= 0) { + delete colorMap; + maskObj.free(); + smaskObj.free(); + goto err2; + } maskDict->lookup("ImageMask", &obj1); if (obj1.isNull()) { obj1.free(); @@ -4534,10 +4575,10 @@ void Gfx::doImage(Object *ref, Stream *str, GBool inlineImg) { } // if drawing is disabled, skip over inline image data - if (state->getInCachedT3Char() || !ocState) { - if (state->getInCachedT3Char()) { - error(errSyntaxWarning, getPos(), - "Ignoring image in cached Type 3 character"); + if (state->getIgnoreColorOps() || !ocState) { + if (state->getIgnoreColorOps()) { + error(errSyntaxWarning, getPos(), "Ignoring image" + " in uncolored Type 3 char or tiling pattern"); } if (inlineImg) { str->reset(); @@ -4582,7 +4623,7 @@ void Gfx::doImage(Object *ref, Stream *str, GBool inlineImg) { } opCounter += i; - return; + return gTrue; err2: obj1.free(); @@ -4594,6 +4635,8 @@ void Gfx::doImage(Object *ref, Stream *str, GBool inlineImg) { state->setRenderingIntent(riSaved); out->updateRenderingIntent(state); } + + return gFalse; } void Gfx::doForm(Object *strRef, Object *str) { @@ -4826,11 +4869,12 @@ void Gfx::opBeginImage(Object args[], int numArgs) { // display the image if (str) { - doImage(NULL, str, gTrue); + if (!doImage(NULL, str, gTrue)) { + delete str; // if we have the stream length, skip to end-of-stream and then // skip 'EI' in the original stream - if (haveLength) { + } else if (haveLength) { while ((c1 = str->getChar()) != EOF) ; delete str; str = parser->getStream(); @@ -4935,7 +4979,7 @@ void Gfx::opSetCharWidth(Object args[], int numArgs) { } void Gfx::opSetCacheDevice(Object args[], int numArgs) { - state->setInCachedT3Char(gTrue); + state->setIgnoreColorOps(gTrue); out->type3D1(state, args[0].getNum(), args[1].getNum(), args[2].getNum(), args[3].getNum(), args[4].getNum(), args[5].getNum()); |