blob: 0fea7539b63caddb14a179cdc7dcf2c08dce7dab [file] [log] [blame]
//========================================================================
//
// Linearization.cc
//
// This file is licensed under the GPLv2 or later
//
// Copyright 2010, 2012 Hib Eris <hib@hiberis.nl>
// Copyright 2015 Jason Crain <jason@aquaticape.us>
// Copyright 2017 Albert Astals Cid <aacid@kde.org>
// Copyright 2019 Adam Reichold <adam.reichold@t-online.de>
//
//========================================================================
#include "Linearization.h"
#include "Parser.h"
#include "Lexer.h"
//------------------------------------------------------------------------
// Linearization
//------------------------------------------------------------------------
Linearization::Linearization (BaseStream *str)
{
Parser *parser;
str->reset();
parser = new Parser(nullptr,
str->makeSubStream(str->getStart(), false, 0, Object(objNull)),
false);
Object obj1 = parser->getObj();
Object obj2 = parser->getObj();
Object obj3 = parser->getObj();
linDict = parser->getObj();
if (obj1.isInt() && obj2.isInt() && obj3.isCmd("obj") && linDict.isDict()) {
Object obj5 = linDict.dictLookup("Linearized");
if (!(obj5.isNum() && obj5.getNum() > 0)) {
linDict.setToNull();
}
}
delete parser;
}
Linearization:: ~Linearization()
{
}
unsigned int Linearization::getLength()
{
if (!linDict.isDict()) return 0;
int length;
if (linDict.getDict()->lookupInt("L", nullptr, &length) &&
length > 0) {
return length;
} else {
error(errSyntaxWarning, -1, "Length in linearization table is invalid");
return 0;
}
}
unsigned int Linearization::getHintsOffset()
{
int hintsOffset;
Object obj1, obj2;
if (linDict.isDict() &&
(obj1 = linDict.dictLookup("H"), obj1.isArray()) &&
obj1.arrayGetLength()>=2 &&
(obj2 = obj1.arrayGet(0), obj2.isInt()) &&
obj2.getInt() > 0) {
hintsOffset = obj2.getInt();
} else {
error(errSyntaxWarning, -1, "Hints table offset in linearization table is invalid");
hintsOffset = 0;
}
return hintsOffset;
}
unsigned int Linearization::getHintsLength()
{
int hintsLength;
Object obj1, obj2;
if (linDict.isDict() &&
(obj1 = linDict.dictLookup("H"), obj1.isArray()) &&
obj1.arrayGetLength()>=2 &&
(obj2 = obj1.arrayGet(1), obj2.isInt()) &&
obj2.getInt() > 0) {
hintsLength = obj2.getInt();
} else {
error(errSyntaxWarning, -1, "Hints table length in linearization table is invalid");
hintsLength = 0;
}
return hintsLength;
}
unsigned int Linearization::getHintsOffset2()
{
int hintsOffset2 = 0; // default to 0
Object obj1;
if (linDict.isDict() &&
(obj1 = linDict.dictLookup("H"), obj1.isArray()) &&
obj1.arrayGetLength()>=4) {
Object obj2 = obj1.arrayGet(2);
if (obj2.isInt() && obj2.getInt() > 0) {
hintsOffset2 = obj2.getInt();
} else {
error(errSyntaxWarning, -1, "Second hints table offset in linearization table is invalid");
hintsOffset2 = 0;
}
}
return hintsOffset2;
}
unsigned int Linearization::getHintsLength2()
{
int hintsLength2 = 0; // default to 0
Object obj1;
if (linDict.isDict() &&
(obj1 = linDict.dictLookup("H"), obj1.isArray()) &&
obj1.arrayGetLength()>=4) {
Object obj2 = obj1.arrayGet(3);
if (obj2.isInt() && obj2.getInt() > 0) {
hintsLength2 = obj2.getInt();
} else {
error(errSyntaxWarning, -1, "Second hints table length in linearization table is invalid");
hintsLength2 = 0;
}
}
return hintsLength2;
}
int Linearization::getObjectNumberFirst()
{
int objectNumberFirst = 0;
if (linDict.isDict() &&
linDict.getDict()->lookupInt("O", nullptr, &objectNumberFirst) &&
objectNumberFirst > 0) {
return objectNumberFirst;
} else {
error(errSyntaxWarning, -1, "Object number of first page in linearization table is invalid");
return 0;
}
}
unsigned int Linearization::getEndFirst()
{
int pageEndFirst = 0;
if (linDict.isDict() &&
linDict.getDict()->lookupInt("E", nullptr, &pageEndFirst) &&
pageEndFirst > 0) {
return pageEndFirst;
} else {
error(errSyntaxWarning, -1, "First page end offset in linearization table is invalid");
return 0;
}
}
int Linearization::getNumPages()
{
int numPages = 0;
if (linDict.isDict() &&
linDict.getDict()->lookupInt("N", nullptr, &numPages) &&
numPages > 0) {
return numPages;
} else {
error(errSyntaxWarning, -1, "Page count in linearization table is invalid");
return 0;
}
}
unsigned int Linearization::getMainXRefEntriesOffset()
{
int mainXRefEntriesOffset = 0;
if (linDict.isDict() &&
linDict.getDict()->lookupInt("T", nullptr, &mainXRefEntriesOffset) &&
mainXRefEntriesOffset > 0) {
return mainXRefEntriesOffset;
} else {
error(errSyntaxWarning, -1, "Main Xref offset in linearization table is invalid");
return 0;
}
}
int Linearization::getPageFirst()
{
int pageFirst = 0; // Optional, defaults to 0.
if (linDict.isDict()) {
linDict.getDict()->lookupInt("P", nullptr, &pageFirst);
}
if ((pageFirst < 0) || (pageFirst >= getNumPages())) {
error(errSyntaxWarning, -1, "First page in linearization table is invalid");
return 0;
}
return pageFirst;
}