diff --git a/.github/workflows/test-pr.yml b/.github/workflows/test-pr.yml index eb2f2267..25000758 100644 --- a/.github/workflows/test-pr.yml +++ b/.github/workflows/test-pr.yml @@ -7,16 +7,19 @@ on: jobs: build: name: Checkout and Build - runs-on: ubuntu-20.04 + runs-on: ubuntu-latest + + continue-on-error: true strategy: + fail-fast: false matrix: - java-version: [8, 11, 16, 17] + java-version: [8, 11, 16, 17, 21] steps: - - uses: actions/checkout@v2 + - uses: actions/checkout@v4 - name: JDK setup - uses: actions/setup-java@v2 + uses: actions/setup-java@v4 with: java-version: ${{ matrix.java-version }} distribution: 'temurin' @@ -31,7 +34,7 @@ jobs: path: target/site/jacoco/ coverage: name: Quality Assurance - runs-on: ubuntu-20.04 + runs-on: ubuntu-latest needs: [ build ] steps: diff --git a/.travis.yml b/.travis.yml deleted file mode 100644 index aca495ac..00000000 --- a/.travis.yml +++ /dev/null @@ -1,17 +0,0 @@ -language: java -sudo: required -dist: trusty - -jdk: - - openjdk8 - - oraclejdk8 - - openjdk11 - -branches: - except: - - /^v|d\d+\.\d+\.\d+$/ - - /^jenkins-veraPDF-parser-v|d\\d+\\.\\d+\\.\\d+$/ - -notifications: - slack: - secure: WgsTp3dk8wNWNJkESk1Hg317W1gNtksHPf8XFv2dzLN6ncv718CNwBg/wcFglLVSQk0AViOtpwdWtf1RO67TlvQV2WZHW2E7NLnJjozTCbXpeheywApou24QbW+i+CJaGVwsP1kFRw0hom3EjhF6o0g+tWJE0W4wVy5yX5u7+GYTfMKkRTRVf42AI/vvD6130AmGRQ8eMWGTyw2NU35q6Q6UGRSqpwx+w5dNWW+SXuL9eI5ZedHRu/mEteh7/jMylxM7W14BkZysXO0TmnfklpshjbOsicdIhdhIQ4SffBPSXdkGoE0XCLtLsEi4b+zTKlRTH/4qzJEiXdO7SwFzFt7uGXPx6gLIpnCGoSciikVMpr06ujz2vukR+tFmwLK6W6+R5PpgNVlfeP4WNHfZHGNbr6alp3loYZEA33BjbTOXKFtv68pPuIQ8LCinPL/J8EGyeIVh8xrxgdiswvO51CxpsuY/G6gm9BxcKbZE14GaZjrOhyPMBylZaBdzbOFkzbrgE7O8tYVt/asItUFQGysfBEQZLvb3eBeMK0p6SVmn0YZ5mqh6o5REr68cy4pK2jwcGQegj5vU61TjCIism+tRGxIanTRkUUfOpobpVa3k2saMTglY7/tnuqQsxYKl6eEg2cPeftr/b+M4o2nOtTBJYik93mTKJo9PmhCGZJ4= diff --git a/README.md b/README.md index 900ef8e7..7214fce9 100644 --- a/README.md +++ b/README.md @@ -29,7 +29,7 @@ Quick Start In order to build the parser you'll need: - * Java 8 - 17, which can be downloaded [from Oracle](https://www.oracle.com/technetwork/java/javase/downloads/index.html), or for Linux users [OpenJDK](http://openjdk.java.net/install/index.html). + * Java 8 - 21, which can be downloaded [from Oracle](https://www.oracle.com/technetwork/java/javase/downloads/index.html), or for Linux users [OpenJDK](http://openjdk.java.net/install/index.html). * [Maven v3+](https://maven.apache.org/) ### Building the veraPDF Parser diff --git a/src/main/java/org/verapdf/parser/COSParser.java b/src/main/java/org/verapdf/parser/COSParser.java index a7eca638..685218f1 100644 --- a/src/main/java/org/verapdf/parser/COSParser.java +++ b/src/main/java/org/verapdf/parser/COSParser.java @@ -3,10 +3,8 @@ import org.verapdf.as.exceptions.StringExceptions; import org.verapdf.cos.*; import org.verapdf.parser.postscript.PSObject; -import org.verapdf.pd.encryption.StandardSecurityHandler; import java.io.IOException; -import java.security.GeneralSecurityException; import java.util.LinkedList; import java.util.Queue; import java.util.logging.Level; diff --git a/src/main/java/org/verapdf/pd/PDNameTreeNode.java b/src/main/java/org/verapdf/pd/PDNameTreeNode.java index e50ac69a..36f7dcb3 100644 --- a/src/main/java/org/verapdf/pd/PDNameTreeNode.java +++ b/src/main/java/org/verapdf/pd/PDNameTreeNode.java @@ -26,7 +26,6 @@ import org.verapdf.cos.COSObjType; import org.verapdf.cos.COSObject; import org.verapdf.exceptions.LoopedException; -import org.verapdf.pd.structure.NameTreeIterator; import java.util.*; @@ -165,14 +164,22 @@ private COSObject getObject(String key, Set visitedKeys) { return null; } + private List getObjects() { + List result = new LinkedList<>(getNames().values()); + for (PDNameTreeNode kid : getKids()) { + result.addAll(kid.getObjects()); + } + return result; + } + @Override - public NameTreeIterator iterator() { - return new NameTreeIterator(this); + public Iterator iterator() { + return getObjects().iterator(); } public Long size() { long i = 0; - NameTreeIterator iterator = iterator(); + Iterator iterator = iterator(); for (; iterator.hasNext(); i++) { iterator.next(); } diff --git a/src/main/java/org/verapdf/pd/font/PDCIDFont.java b/src/main/java/org/verapdf/pd/font/PDCIDFont.java index a7610616..1c234226 100644 --- a/src/main/java/org/verapdf/pd/font/PDCIDFont.java +++ b/src/main/java/org/verapdf/pd/font/PDCIDFont.java @@ -162,7 +162,7 @@ public FontProgram getFontProgram() { this.isFontParsed = true; if (fontDescriptor.canParseFontFile(ASAtom.FONT_FILE2) && - this.getSubtype() == ASAtom.CID_FONT_TYPE2) { + this.getSubtypeEntryValue() == ASAtom.CID_FONT_TYPE2) { COSStream trueTypeFontFile = fontDescriptor.getFontFile2(); COSKey key = trueTypeFontFile.getObjectKey(); COSObject cidToGIDMap = this.getCIDToGIDMap(); @@ -170,8 +170,7 @@ public FontProgram getFontProgram() { this.fontProgram = StaticResources.getCachedFont(fontProgramID); if (fontProgram == null) { try (ASInputStream fontData = trueTypeFontFile.getData(COSStream.FilterFlags.DECODE)) { - this.fontProgram = new CIDFontType2Program( - fontData, this.cMap, cidToGIDMap); + this.fontProgram = new CIDFontType2Program(fontData, this.cMap, cidToGIDMap); StaticResources.cacheFontProgram(fontProgramID, this.fontProgram); } catch (IOException e) { LOGGER.log(Level.FINE, "Can't read TrueType font program.", e); @@ -193,17 +192,18 @@ public FontProgram getFontProgram() { } } } else if (ASAtom.OPEN_TYPE == subtype.getName()) { - ASAtom fontName = ASAtom.getASAtom(this.getName()); - boolean isCFF = fontName != ASAtom.TRUE_TYPE && fontName != ASAtom.CID_FONT_TYPE2; + boolean isCFF = this.getSubtypeEntryValue() != ASAtom.TRUE_TYPE && this.getSubtypeEntryValue() != ASAtom.CID_FONT_TYPE2; + boolean isCIDFontType2 = this.getSubtypeEntryValue() == ASAtom.CID_FONT_TYPE2; boolean isSymbolic = this.isSymbolic(); COSObject encoding = this.getEncoding(); String fontProgramID = FontProgramIDGenerator.getOpenTypeFontProgramID(key, isCFF, isSymbolic, encoding, this.cMap, isSubset); this.fontProgram = StaticResources.getCachedFont(fontProgramID); if (fontProgram == null) { + COSObject cidToGIDMap = this.getCIDToGIDMap(); try (ASInputStream fontData = fontFile.getData(COSStream.FilterFlags.DECODE)) { this.fontProgram = new OpenTypeFontProgram( - fontData, isCFF, isSymbolic, encoding, - this.cMap, isSubset); + fontData, isCFF, isCIDFontType2, isSymbolic, encoding, + this.cMap, isSubset, cidToGIDMap); StaticResources.cacheFontProgram(fontProgramID, this.fontProgram); } } diff --git a/src/main/java/org/verapdf/pd/font/PDFont.java b/src/main/java/org/verapdf/pd/font/PDFont.java index 9917bea6..80c7aefa 100644 --- a/src/main/java/org/verapdf/pd/font/PDFont.java +++ b/src/main/java/org/verapdf/pd/font/PDFont.java @@ -116,6 +116,10 @@ public String getType() { public ASAtom getSubtype() { return this.subtype; } + + public ASAtom getSubtypeEntryValue() { + return this.subtype; + } /** * @return true if the font flags in the font descriptor dictionary mark diff --git a/src/main/java/org/verapdf/pd/font/cff/CFFCIDFontProgram.java b/src/main/java/org/verapdf/pd/font/cff/CFFCIDFontProgram.java index 6c31096a..08ef08eb 100644 --- a/src/main/java/org/verapdf/pd/font/cff/CFFCIDFontProgram.java +++ b/src/main/java/org/verapdf/pd/font/cff/CFFCIDFontProgram.java @@ -57,13 +57,8 @@ public class CFFCIDFontProgram extends CFFFontBaseParser implements FontProgram CFFCIDFontProgram(SeekableInputStream stream, CFFIndex definedNames, CFFIndex globalSubrs, long topDictBeginOffset, long topDictEndOffset, CMap externalCMap, boolean isSubset) { - super(stream); - this.definedNames = definedNames; - this.globalSubrs = globalSubrs; - this.topDictBeginOffset = topDictBeginOffset; - this.topDictEndOffset = topDictEndOffset; + super(stream, definedNames, globalSubrs, topDictBeginOffset, topDictEndOffset, isSubset); this.externalCMap = externalCMap; - this.isSubset = isSubset; } /** diff --git a/src/main/java/org/verapdf/pd/font/cff/CFFFontBaseParser.java b/src/main/java/org/verapdf/pd/font/cff/CFFFontBaseParser.java index 771bfd54..3b71b6b5 100644 --- a/src/main/java/org/verapdf/pd/font/cff/CFFFontBaseParser.java +++ b/src/main/java/org/verapdf/pd/font/cff/CFFFontBaseParser.java @@ -36,7 +36,7 @@ * * @author Sergey Shemyakov */ -abstract class CFFFontBaseParser extends CFFFileBaseParser { +class CFFFontBaseParser extends CFFFileBaseParser { private static final Logger LOGGER = Logger.getLogger(CFFFontBaseParser.class.getCanonicalName()); @@ -72,6 +72,8 @@ abstract class CFFFontBaseParser extends CFFFileBaseParser { //Subrs protected long subrsOffset = -1; + private boolean containsROS = false; + public CFFFontBaseParser(SeekableInputStream source) { super(source); stack = new ArrayList<>(48); @@ -79,6 +81,30 @@ public CFFFontBaseParser(SeekableInputStream source) { this.charSetOffset = 0; // default } + public CFFFontBaseParser(SeekableInputStream stream, CFFIndex definedNames, CFFIndex globalSubrs, + long topDictBeginOffset, long topDictEndOffset, boolean isSubset) { + this(stream); + this.definedNames = definedNames; + this.globalSubrs = globalSubrs; + this.topDictBeginOffset = topDictBeginOffset; + this.topDictEndOffset = topDictEndOffset; + this.isSubset = isSubset; + } + + protected boolean containsROS() { + try { + this.source.seek(topDictBeginOffset); + while (this.source.getOffset() < topDictEndOffset) { + readTopDictUnit(); + } + if (containsROS) { + return true; + } + } catch (IOException ignored) { + } + return false; + } + protected void readTopDictUnit() throws IOException { try { int next = this.source.peek(); @@ -125,6 +151,9 @@ protected void readTopDictUnit() throws IOException { this.stack.get(this.stack.size() - 1).getInteger(); this.stack.clear(); break; + case 30: + this.containsROS = true; + break; default: readTopDictTwoByteOps(next); } diff --git a/src/main/java/org/verapdf/pd/font/cff/CFFFontProgram.java b/src/main/java/org/verapdf/pd/font/cff/CFFFontProgram.java index 6ba84d80..99f52024 100644 --- a/src/main/java/org/verapdf/pd/font/cff/CFFFontProgram.java +++ b/src/main/java/org/verapdf/pd/font/cff/CFFFontProgram.java @@ -76,7 +76,7 @@ public void parseFont() throws IOException { } this.definedNames = this.readIndex(); CFFIndex globalSubrs = this.readIndex(); - if (isCIDFont(top.get(0))) { + if (isCIDFont(top, globalSubrs, topOffset)) { font = new CFFCIDFontProgram(this.source, this.definedNames, globalSubrs, topOffset + top.getOffset(0) - 1 + top.getOffsetShift(), topOffset + top.getOffset(1) - 1 + top.getOffsetShift(), @@ -91,9 +91,10 @@ public void parseFont() throws IOException { } } - private boolean isCIDFont(byte[] topDict) { + private boolean isCIDFont(CFFIndex top, CFFIndex globalSubrs, long topOffset) { try { byte rosOffset; + byte[] topDict = top.get(0); int supplementFirstByte = topDict[4] & 0xFF; // checking if first operator is really ROS if (supplementFirstByte < 247 && supplementFirstByte > 31) { rosOffset = 5; @@ -104,25 +105,25 @@ private boolean isCIDFont(byte[] topDict) { } else if (supplementFirstByte == 29) { rosOffset = 9; } else { - return isContainsROS(topDict); + return containsROS(top, globalSubrs, topOffset); } if (topDict[rosOffset] == 12 && topDict[rosOffset + 1] == 30) { isCIDFont = true; return true; } - return isContainsROS(topDict); + return containsROS(top, globalSubrs, topOffset); } catch (ArrayIndexOutOfBoundsException ex) { - return isContainsROS(topDict); + return containsROS(top, globalSubrs, topOffset); } } - private boolean isContainsROS(byte[] topDict) { - for (int rosOffset = 0; rosOffset < topDict.length - 2; rosOffset++) { - if (topDict[rosOffset] == 12 && topDict[rosOffset + 1] == 30) { - LOGGER.log(Level.WARNING, "The Top DICT does not begin with ROS operator"); - isCIDFont = true; - return true; - } + private boolean containsROS(CFFIndex top, CFFIndex globalSubrs, long topOffset) { + if (new CFFFontBaseParser(this.source, this.definedNames, globalSubrs, + topOffset + top.getOffset(0) - 1 + top.getOffsetShift(), + topOffset + top.getOffset(1) - 1 + top.getOffsetShift(), + this.isSubset).containsROS()) { + LOGGER.log(Level.WARNING, "The Top DICT does not begin with ROS operator"); + return true; } return false; } diff --git a/src/main/java/org/verapdf/pd/font/cff/CFFType1FontProgram.java b/src/main/java/org/verapdf/pd/font/cff/CFFType1FontProgram.java index 80666cf0..22a8169a 100644 --- a/src/main/java/org/verapdf/pd/font/cff/CFFType1FontProgram.java +++ b/src/main/java/org/verapdf/pd/font/cff/CFFType1FontProgram.java @@ -58,15 +58,10 @@ public class CFFType1FontProgram extends CFFFontBaseParser implements FontProgra CFFType1FontProgram(SeekableInputStream stream, CFFIndex definedNames, CFFIndex globalSubrs, long topDictBeginOffset, long topDictEndOffset, CMap externalCMap, boolean isSubset) { - super(stream); + super(stream, definedNames, globalSubrs, topDictBeginOffset, topDictEndOffset, isSubset); encodingOffset = 0; encoding = new int[256]; - this.definedNames = definedNames; - this.globalSubrs = globalSubrs; - this.topDictBeginOffset = topDictBeginOffset; - this.topDictEndOffset = topDictEndOffset; this.externalCMap = externalCMap; - this.isSubset = isSubset; fontMatrix = new float[6]; System.arraycopy(DEFAULT_FONT_MATRIX, 0, this.fontMatrix, 0, DEFAULT_FONT_MATRIX.length); diff --git a/src/main/java/org/verapdf/pd/font/cmap/CMapParser.java b/src/main/java/org/verapdf/pd/font/cmap/CMapParser.java index 467cf252..7060de11 100644 --- a/src/main/java/org/verapdf/pd/font/cmap/CMapParser.java +++ b/src/main/java/org/verapdf/pd/font/cmap/CMapParser.java @@ -75,9 +75,10 @@ public void parse() throws IOException, PostScriptException { getBaseParser().initializeToken(); //Skipping starting comments getBaseParser().skipSpaces(true); + COSObject nextObject = nextObject(); while (getBaseParser().getToken().type != Token.Type.TT_EOF) { - COSObject nextObject = nextObject(); processObject(nextObject); + nextObject = nextObject(); } } finally { this.getSource().close(); // We close stream after first reading attempt diff --git a/src/main/java/org/verapdf/pd/font/opentype/OpenTypeFontProgram.java b/src/main/java/org/verapdf/pd/font/opentype/OpenTypeFontProgram.java index 7db80924..9c604b93 100644 --- a/src/main/java/org/verapdf/pd/font/opentype/OpenTypeFontProgram.java +++ b/src/main/java/org/verapdf/pd/font/opentype/OpenTypeFontProgram.java @@ -27,6 +27,7 @@ import org.verapdf.pd.font.FontProgram; import org.verapdf.pd.font.cff.CFFFontProgram; import org.verapdf.pd.font.cmap.CMap; +import org.verapdf.pd.font.truetype.CIDFontType2Program; import org.verapdf.pd.font.truetype.TrueTypeFontProgram; import org.verapdf.tools.StaticResources; import org.verapdf.tools.resource.ASFileStreamCloser; @@ -45,6 +46,7 @@ public class OpenTypeFontProgram implements FontProgram { // See TrueTypeFontParser table logic private final boolean isCFF; + private final boolean isCIDFontType2; private final boolean isSymbolic; private final boolean isSubset; private final COSObject encoding; @@ -54,6 +56,7 @@ public class OpenTypeFontProgram implements FontProgram { private boolean attemptedParsing = false; private boolean successfullyParsed = false; private final CMap externalCMap; + private final COSObject cidToGIDMap; /** * Constructor from stream, containing font data, and encoding details. @@ -62,14 +65,16 @@ public class OpenTypeFontProgram implements FontProgram { * @param isSymbolic is true if font is marked as symbolic. * @param encoding is value of /Encoding in font dictionary. */ - public OpenTypeFontProgram(ASInputStream source, boolean isCFF, boolean isSymbolic, - COSObject encoding, CMap externalCMap, boolean isSubset) { + public OpenTypeFontProgram(ASInputStream source, boolean isCFF, boolean isCIDFontType2, boolean isSymbolic, + COSObject encoding, CMap externalCMap, boolean isSubset, COSObject cidToGIDMap) { this.source = source; this.isCFF = isCFF; + this.isCIDFontType2 = isCIDFontType2; this.isSymbolic = isSymbolic; this.encoding = encoding; this.externalCMap = externalCMap; this.isSubset = isSubset; + this.cidToGIDMap = cidToGIDMap; } /** @@ -134,14 +139,17 @@ public boolean isSuccessfulParsing() { public void parseFont() throws IOException { if (!attemptedParsing) { attemptedParsing = true; - if (!isCFF) { - this.font = new TrueTypeFontProgram(source, isSymbolic, encoding); + if (isCIDFontType2) { + this.font = new CIDFontType2Program(source, externalCMap, cidToGIDMap); this.font.parseFont(); - } else { + } else if (isCFF) { try (ASInputStream cffTable = getCFFTable()) { this.font = new CFFFontProgram(cffTable, externalCMap, isSubset); this.font.parseFont(); } + } else { + this.font = new TrueTypeFontProgram(source, isSymbolic, encoding); + this.font.parseFont(); } StaticResources.cacheFontProgram(null, this.font); this.successfullyParsed = true; diff --git a/src/main/java/org/verapdf/pd/font/truetype/BaseTrueTypeProgram.java b/src/main/java/org/verapdf/pd/font/truetype/BaseTrueTypeProgram.java index 579f4865..2be9f235 100644 --- a/src/main/java/org/verapdf/pd/font/truetype/BaseTrueTypeProgram.java +++ b/src/main/java/org/verapdf/pd/font/truetype/BaseTrueTypeProgram.java @@ -84,7 +84,7 @@ public void parseFont() throws IOException { * this True Type font. */ public int getNrOfCMaps() { - if(this.parser.getCmapParser() != null) { + if (this.parser.getCmapParser() != null) { return this.parser.getCmapParser().getCmapInfos().length; } else { return 0; diff --git a/src/main/java/org/verapdf/pd/font/truetype/PDTrueTypeFont.java b/src/main/java/org/verapdf/pd/font/truetype/PDTrueTypeFont.java index f1af998f..60ceae49 100644 --- a/src/main/java/org/verapdf/pd/font/truetype/PDTrueTypeFont.java +++ b/src/main/java/org/verapdf/pd/font/truetype/PDTrueTypeFont.java @@ -103,8 +103,8 @@ private void parseTrueTypeFontProgram(ASAtom fontFileType) { this.fontProgram = StaticResources.getCachedFont(fontProgramID); if (fontProgram == null) { try (ASInputStream fontData = trueTypeFontFile.getData(COSStream.FilterFlags.DECODE)) { - this.fontProgram = new OpenTypeFontProgram(fontData, false, - isSymbolic, encoding, null, isSubset); + this.fontProgram = new OpenTypeFontProgram(fontData, false, false, + isSymbolic, encoding, null, isSubset, null); StaticResources.cacheFontProgram(fontProgramID, this.fontProgram); } } diff --git a/src/main/java/org/verapdf/pd/font/type1/PDType1Font.java b/src/main/java/org/verapdf/pd/font/type1/PDType1Font.java index 0848b211..289a7500 100644 --- a/src/main/java/org/verapdf/pd/font/type1/PDType1Font.java +++ b/src/main/java/org/verapdf/pd/font/type1/PDType1Font.java @@ -171,8 +171,8 @@ private void parseType1FontProgram(ASAtom fontFileType) { this.fontProgram = StaticResources.getCachedFont(fontProgramID); if (fontProgram == null) { try (ASInputStream fontData = type1FontFile.getData(COSStream.FilterFlags.DECODE)) { - this.fontProgram = new OpenTypeFontProgram(fontData, true, isSymbolic, - encoding, null, isSubset); + this.fontProgram = new OpenTypeFontProgram(fontData, true, false, isSymbolic, + encoding, null, isSubset, null); StaticResources.cacheFontProgram(fontProgramID, this.fontProgram); } } diff --git a/src/main/java/org/verapdf/pd/structure/NameTreeIterator.java b/src/main/java/org/verapdf/pd/structure/NameTreeIterator.java deleted file mode 100644 index b9d81c3c..00000000 --- a/src/main/java/org/verapdf/pd/structure/NameTreeIterator.java +++ /dev/null @@ -1,39 +0,0 @@ -package org.verapdf.pd.structure; - -import org.verapdf.cos.COSObject; -import org.verapdf.pd.PDNameTreeNode; - -import java.util.Iterator; - -public class NameTreeIterator implements Iterator { - - private NameTreeIterator innerCurrentIterator; - private final Iterator namesIterator; - private final Iterator kidsIterator; - - public NameTreeIterator(PDNameTreeNode root) { - namesIterator = root.getNames().values().iterator(); - kidsIterator = root.getKids().iterator(); - nextInnerIterator(); - } - - @Override - public boolean hasNext() { - return (innerCurrentIterator != null && innerCurrentIterator.hasNext()) || kidsIterator.hasNext() || namesIterator.hasNext(); - } - - @Override - public COSObject next() { - if (namesIterator.hasNext()) { - return namesIterator.next(); - } - if (!innerCurrentIterator.hasNext()) { - nextInnerIterator(); - } - return innerCurrentIterator.next(); - } - - private void nextInnerIterator() { - innerCurrentIterator = kidsIterator.hasNext() ? new NameTreeIterator(kidsIterator.next()) : null; - } -} diff --git a/src/main/java/org/verapdf/pd/structure/NumberTreeIterator.java b/src/main/java/org/verapdf/pd/structure/NumberTreeIterator.java deleted file mode 100644 index 2cdcbaaa..00000000 --- a/src/main/java/org/verapdf/pd/structure/NumberTreeIterator.java +++ /dev/null @@ -1,38 +0,0 @@ -package org.verapdf.pd.structure; - -import org.verapdf.cos.COSObject; - -import java.util.Iterator; - -public class NumberTreeIterator implements Iterator { - - private NumberTreeIterator innerCurrentIterator; - private final Iterator numbersIterator; - private final Iterator kidsIterator; - - public NumberTreeIterator(PDNumberTreeNode root) { - numbersIterator = root.getNums().values().iterator(); - kidsIterator = root.getKids().iterator(); - nextInnerIterator(); - } - - @Override - public boolean hasNext() { - return (innerCurrentIterator != null && innerCurrentIterator.hasNext()) || kidsIterator.hasNext() || numbersIterator.hasNext(); - } - - @Override - public COSObject next() { - if (numbersIterator.hasNext()) { - return numbersIterator.next(); - } - if (!innerCurrentIterator.hasNext()) { - nextInnerIterator(); - } - return innerCurrentIterator.next(); - } - - private void nextInnerIterator() { - innerCurrentIterator = kidsIterator.hasNext() ? new NumberTreeIterator(kidsIterator.next()) : null; - } -} diff --git a/src/main/java/org/verapdf/pd/structure/PDNumberTreeNode.java b/src/main/java/org/verapdf/pd/structure/PDNumberTreeNode.java index 91334ae8..b9f03b9f 100644 --- a/src/main/java/org/verapdf/pd/structure/PDNumberTreeNode.java +++ b/src/main/java/org/verapdf/pd/structure/PDNumberTreeNode.java @@ -100,6 +100,14 @@ public Map getNums() { return Collections.emptyMap(); } + private List getObjects() { + List result = new LinkedList<>(getNums().values()); + for (PDNumberTreeNode kid : getKids()) { + result.addAll(kid.getObjects()); + } + return result; + } + /** * Gets object with given key from this node and it's kids recursively. * @@ -157,13 +165,13 @@ private COSObject getObject(Long key, Set visitedKeys) { } @Override - public NumberTreeIterator iterator() { - return new NumberTreeIterator(this); + public Iterator iterator() { + return getObjects().iterator(); } public Long size() { long i = 0; - NumberTreeIterator iterator = iterator(); + Iterator iterator = iterator(); for (; iterator.hasNext(); i++) { iterator.next(); } diff --git a/src/main/java/org/verapdf/pd/structure/PDStructureNameSpace.java b/src/main/java/org/verapdf/pd/structure/PDStructureNameSpace.java index 72829462..0f1b76f6 100644 --- a/src/main/java/org/verapdf/pd/structure/PDStructureNameSpace.java +++ b/src/main/java/org/verapdf/pd/structure/PDStructureNameSpace.java @@ -40,7 +40,7 @@ public class PDStructureNameSpace extends PDObject { private PDStructureNameSpace(COSObject obj) { super(obj); COSObject roleMap = this.getKey(ASAtom.ROLE_MAP_NS); - if (obj != null && obj.getType() == COSObjType.COS_DICT) { + if (roleMap != null && roleMap.getType() == COSObjType.COS_DICT) { this.nsRoleMap = new PDNameSpaceRoleMapping(roleMap); } else { this.nsRoleMap = null; diff --git a/src/main/java/org/verapdf/tools/TaggedPDFHelper.java b/src/main/java/org/verapdf/tools/TaggedPDFHelper.java index a64e7936..64a15937 100644 --- a/src/main/java/org/verapdf/tools/TaggedPDFHelper.java +++ b/src/main/java/org/verapdf/tools/TaggedPDFHelper.java @@ -188,7 +188,7 @@ public static String getRoleMapToSameNamespaceTag(StructureType type) { if (curr.getNameSpaceURI() != null && curr.getNameSpaceURI().equals(prev.getNameSpaceURI())) { return prev.getNameSpaceURI() + ":" + (prev.getType() != null ? prev.getType().getValue() : null); } - if (isVisited(curr) || isStandardType(curr)) { + if (isVisited(curr)) { return null; } addVisited(curr); diff --git a/src/test/java/org/verapdf/pd/font/opentype/OpenTypeCFFTest.java b/src/test/java/org/verapdf/pd/font/opentype/OpenTypeCFFTest.java index 09cc7740..cd6981a3 100644 --- a/src/test/java/org/verapdf/pd/font/opentype/OpenTypeCFFTest.java +++ b/src/test/java/org/verapdf/pd/font/opentype/OpenTypeCFFTest.java @@ -44,8 +44,8 @@ public class OpenTypeCFFTest { public void test() throws IOException { COSObject encoding = COSName.construct(ASAtom.WIN_ANSI_ENCODING); ASInputStream stream = new InternalInputStream(fontFilePath, 2); - OpenTypeFontProgram font = new OpenTypeFontProgram(stream, true, false, - encoding, null, true); + OpenTypeFontProgram font = new OpenTypeFontProgram(stream, true, false, false, + encoding, null, true, null); font.parseFont(); assertTrue(font.getFont() instanceof CFFFontProgram); assertFalse(((CFFFontProgram) font.getFont()).isCIDFont());