Ensure that the /Form XObject /Resources-entry is actually a dictionary (issue 19848)

This commit is contained in:
Jonas Jenwald 2025-04-23 09:55:04 +02:00
parent 63e6566597
commit 64007e777e
4 changed files with 30 additions and 7 deletions

View File

@ -465,7 +465,7 @@ class PartialEvaluator {
localColorSpaceCache,
seenRefs
) {
const dict = xobj.dict;
const { dict } = xobj;
const matrix = lookupMatrix(dict.getArray("Matrix"), null);
const bbox = lookupNormalRect(dict.getArray("BBox"), null);
@ -521,10 +521,12 @@ class PartialEvaluator {
const args = [f32matrix, f32bbox];
operatorList.addOp(OPS.paintFormXObjectBegin, args);
const localResources = dict.get("Resources");
await this.getOperatorList({
stream: xobj,
task,
resources: dict.get("Resources") || resources,
resources: localResources instanceof Dict ? localResources : resources,
operatorList,
initialState,
prevRefs: seenRefs,
@ -3298,14 +3300,15 @@ class PartialEvaluator {
if (!(xobj instanceof BaseStream)) {
throw new FormatError("XObject should be a stream");
}
const { dict } = xobj;
const type = xobj.dict.get("Subtype");
const type = dict.get("Subtype");
if (!(type instanceof Name)) {
throw new FormatError("XObject should have a Name subtype");
}
if (type.name !== "Form") {
emptyXObjectCache.set(name, xobj.dict.objId, true);
emptyXObjectCache.set(name, dict.objId, true);
resolveXObject();
return;
@ -3319,11 +3322,13 @@ class PartialEvaluator {
const currentState = stateManager.state.clone();
const xObjStateManager = new StateManager(currentState);
const matrix = lookupMatrix(xobj.dict.getArray("Matrix"), null);
const matrix = lookupMatrix(dict.getArray("Matrix"), null);
if (matrix) {
xObjStateManager.transform(matrix);
}
const localResources = dict.get("Resources");
// Enqueue the `textContent` chunk before parsing the /Form
// XObject.
enqueueChunk();
@ -3348,7 +3353,10 @@ class PartialEvaluator {
.getTextContent({
stream: xobj,
task,
resources: xobj.dict.get("Resources") || resources,
resources:
localResources instanceof Dict
? localResources
: resources,
stateManager: xObjStateManager,
includeMarkedContent,
sink: sinkWrapper,
@ -3362,7 +3370,7 @@ class PartialEvaluator {
})
.then(function () {
if (!sinkWrapper.enqueueInvoked) {
emptyXObjectCache.set(name, xobj.dict.objId, true);
emptyXObjectCache.set(name, dict.objId, true);
}
resolveXObject();
}, rejectXObject);

View File

@ -473,6 +473,7 @@
!issue6069.pdf
!issue6106.pdf
!issue6296.pdf
!issue19848.pdf
!bug852992_reduced.pdf
!issue13271.pdf
!issue6298.pdf

BIN
test/pdfs/issue19848.pdf Normal file

Binary file not shown.

View File

@ -3886,6 +3886,20 @@
"rounds": 1,
"type": "eq"
},
{
"id": "issue19848-eq",
"file": "pdfs/issue19848.pdf",
"md5": "a6b05b61c883542e647b9a5a628e6422",
"rounds": 1,
"type": "eq"
},
{
"id": "issue19848-text",
"file": "pdfs/issue19848.pdf",
"md5": "a6b05b61c883542e647b9a5a628e6422",
"rounds": 1,
"type": "text"
},
{
"id": "issue14824",
"file": "pdfs/issue14824.pdf",