beta-0.89.2
[luatex.git] / source / libs / poppler / poppler-src / poppler / XRef.h
blob70065d8963e9d97e448c91b9cbd6ea104ec480fa
1 //========================================================================
2 //
3 // XRef.h
4 //
5 // Copyright 1996-2003 Glyph & Cog, LLC
6 //
7 //========================================================================
9 //========================================================================
11 // Modified under the Poppler project - http://poppler.freedesktop.org
13 // All changes made under the Poppler project to this file are licensed
14 // under GPL version 2 or later
16 // Copyright (C) 2005 Brad Hards <bradh@frogmouth.net>
17 // Copyright (C) 2006, 2008, 2010-2013 Albert Astals Cid <aacid@kde.org>
18 // Copyright (C) 2007-2008 Julien Rebetez <julienr@svn.gnome.org>
19 // Copyright (C) 2007 Carlos Garcia Campos <carlosgc@gnome.org>
20 // Copyright (C) 2010 Ilya Gorenbein <igorenbein@finjan.com>
21 // Copyright (C) 2010 Hib Eris <hib@hiberis.nl>
22 // Copyright (C) 2012, 2013 Thomas Freitag <Thomas.Freitag@kabelmail.de>
23 // Copyright (C) 2012, 2013 Fabio D'Urso <fabiodurso@hotmail.it>
24 // Copyright (C) 2013 Adrian Johnson <ajohnson@redneon.com>
26 // To see a description of the changes please see the Changelog file that
27 // came with your tarball or type make ChangeLog if you are building from git
29 //========================================================================
31 #ifndef XREF_H
32 #define XREF_H
34 #ifdef USE_GCC_PRAGMAS
35 #pragma interface
36 #endif
38 #include "poppler-config.h"
39 #include "goo/gtypes.h"
40 #include "goo/GooMutex.h"
41 #include "Object.h"
42 #include "Stream.h"
44 #include <vector>
46 class Dict;
47 class Stream;
48 class Parser;
49 class PopplerCache;
51 //------------------------------------------------------------------------
52 // XRef
53 //------------------------------------------------------------------------
55 enum XRefEntryType {
56 xrefEntryFree,
57 xrefEntryUncompressed,
58 xrefEntryCompressed,
59 xrefEntryNone
62 struct XRefEntry {
63 Goffset offset;
64 int gen;
65 XRefEntryType type;
66 int flags;
67 Object obj; //if this entry was updated, obj will contains the updated object
69 enum Flag {
70 // Regular flags
71 Updated, // Entry was modified
73 // Special flags -- available only after xref->scanSpecialFlags() is run
74 Unencrypted, // Entry is stored in unencrypted form (meaningless in unencrypted documents)
75 DontRewrite // Entry must not be written back in case of full rewrite
78 inline GBool getFlag(Flag flag) {
79 const int mask = (1 << (int)flag);
80 return (flags & mask) != 0;
83 inline void setFlag(Flag flag, GBool value) {
84 const int mask = (1 << (int)flag);
85 if (value) {
86 flags |= mask;
87 } else {
88 flags &= ~mask;
93 class XRef {
94 public:
96 // Constructor, create an empty XRef, used for PDF writing
97 XRef();
98 // Constructor, create an empty XRef but with info dict, used for PDF writing
99 XRef(Object *trailerDictA);
100 // Constructor. Read xref table from stream.
101 XRef(BaseStream *strA, Goffset pos, Goffset mainXRefEntriesOffsetA = 0, GBool *wasReconstructed = NULL, GBool reconstruct = false);
103 // Destructor.
104 ~XRef();
106 // Copy xref but with new base stream!
107 XRef *copy();
109 // Is xref table valid?
110 GBool isOk() { return ok; }
112 // Is the last XRef section a stream or a table?
113 GBool isXRefStream() { return xRefStream; }
115 // Get the error code (if isOk() returns false).
116 int getErrorCode() { return errCode; }
118 // Set the encryption parameters.
119 void setEncryption(int permFlagsA, GBool ownerPasswordOkA,
120 Guchar *fileKeyA, int keyLengthA,
121 int encVersionA, int encRevisionA,
122 CryptAlgorithm encAlgorithmA);
123 // Mark Encrypt entry as Unencrypted
124 void markUnencrypted();
126 void getEncryptionParameters(Guchar **fileKeyA, CryptAlgorithm *encAlgorithmA, int *keyLengthA);
128 // Is the file encrypted?
129 GBool isEncrypted() { return encrypted; }
131 // Check various permissions.
132 GBool okToPrint(GBool ignoreOwnerPW = gFalse);
133 GBool okToPrintHighRes(GBool ignoreOwnerPW = gFalse);
134 GBool okToChange(GBool ignoreOwnerPW = gFalse);
135 GBool okToCopy(GBool ignoreOwnerPW = gFalse);
136 GBool okToAddNotes(GBool ignoreOwnerPW = gFalse);
137 GBool okToFillForm(GBool ignoreOwnerPW = gFalse);
138 GBool okToAccessibility(GBool ignoreOwnerPW = gFalse);
139 GBool okToAssemble(GBool ignoreOwnerPW = gFalse);
140 int getPermFlags() { return permFlags; }
142 // Get catalog object.
143 Object *getCatalog(Object *obj);
145 // Fetch an indirect reference.
146 Object *fetch(int num, int gen, Object *obj, int recursion = 0);
148 // Return the document's Info dictionary (if any).
149 Object *getDocInfo(Object *obj);
150 Object *getDocInfoNF(Object *obj);
152 // Return the number of objects in the xref table.
153 int getNumObjects() { return size; }
155 // Return the catalog object reference.
156 int getRootNum() { return rootNum; }
157 int getRootGen() { return rootGen; }
159 // Get end position for a stream in a damaged file.
160 // Returns false if unknown or file is not damaged.
161 GBool getStreamEnd(Goffset streamStart, Goffset *streamEnd);
163 // Retuns the entry that belongs to the offset
164 int getNumEntry(Goffset offset);
166 // Scans the document and sets special flags in all xref entries. One of those
167 // flags is Unencrypted, which affects how the object is fetched. Therefore,
168 // this function must be called before fetching unencrypted objects (e.g.
169 // Encrypt dictionary, XRef streams). Note that the code that initializes
170 // decryption doesn't need to call this function, because it runs before
171 // decryption is enabled, and therefore the Unencrypted flag is ignored.
172 void scanSpecialFlags();
174 // Direct access.
175 XRefEntry *getEntry(int i, GBool complainIfMissing = gTrue);
176 Object *getTrailerDict() { return &trailerDict; }
178 // Write access
179 void setModifiedObject(Object* o, Ref r);
180 Ref addIndirectObject (Object* o);
181 void removeIndirectObject(Ref r);
182 void add(int num, int gen, Goffset offs, GBool used);
184 // Output XRef table to stream
185 void writeTableToFile(OutStream* outStr, GBool writeAllEntries);
186 // Output XRef stream contents to GooString and fill trailerDict fields accordingly
187 void writeStreamToBuffer(GooString *stmBuf, Dict *xrefDict, XRef *xref);
189 // to be thread safe during write where changes are not allowed
190 void lock();
191 void unlock();
193 private:
195 BaseStream *str; // input stream
196 Goffset start; // offset in file (to allow for garbage
197 // at beginning of file)
198 XRefEntry *entries; // xref entries
199 int capacity; // size of <entries> array
200 int size; // number of entries
201 int rootNum, rootGen; // catalog dict
202 GBool ok; // true if xref table is valid
203 int errCode; // error code (if <ok> is false)
204 Object trailerDict; // trailer dictionary
205 Goffset *streamEnds; // 'endstream' positions - only used in
206 // damaged files
207 int streamEndsLen; // number of valid entries in streamEnds
208 PopplerCache *objStrs; // cached object streams
209 GBool encrypted; // true if file is encrypted
210 int encRevision;
211 int encVersion; // encryption algorithm
212 CryptAlgorithm encAlgorithm; // encryption algorithm
213 int keyLength; // length of key, in bytes
214 int permFlags; // permission bits
215 Guchar fileKey[32]; // file decryption key
216 GBool ownerPasswordOk; // true if owner password is correct
217 Goffset prevXRefOffset; // position of prev XRef section (= next to read)
218 Goffset mainXRefEntriesOffset; // offset of entries in main XRef table
219 GBool xRefStream; // true if last XRef section is a stream
220 Goffset mainXRefOffset; // position of the main XRef table/stream
221 GBool scannedSpecialFlags; // true if scanSpecialFlags has been called
222 GBool strOwner; // true if str is owned by the instance
223 #if MULTITHREADED
224 GooMutex mutex;
225 #endif
227 void init();
228 int reserve(int newSize);
229 int resize(int newSize);
230 GBool readXRef(Goffset *pos, std::vector<Goffset> *followedXRefStm, std::vector<int> *xrefStreamObjsNum);
231 GBool readXRefTable(Parser *parser, Goffset *pos, std::vector<Goffset> *followedXRefStm, std::vector<int> *xrefStreamObjsNum);
232 GBool readXRefStreamSection(Stream *xrefStr, int *w, int first, int n);
233 GBool readXRefStream(Stream *xrefStr, Goffset *pos);
234 GBool constructXRef(GBool *wasReconstructed, GBool needCatalogDict = gFalse);
235 GBool parseEntry(Goffset offset, XRefEntry *entry);
236 void readXRefUntil(int untilEntryNum, std::vector<int> *xrefStreamObjsNum = NULL);
237 void markUnencrypted(Object *obj);
239 class XRefWriter {
240 public:
241 virtual void startSection(int first, int count) = 0;
242 virtual void writeEntry(Goffset offset, int gen, XRefEntryType type) = 0;
243 virtual ~XRefWriter() {};
246 // XRefWriter subclass that writes a XRef table
247 class XRefTableWriter: public XRefWriter {
248 public:
249 XRefTableWriter(OutStream* outStrA);
250 void startSection(int first, int count);
251 void writeEntry(Goffset offset, int gen, XRefEntryType type);
252 private:
253 OutStream* outStr;
256 // XRefWriter subclass that writes a XRef stream
257 class XRefStreamWriter: public XRefWriter {
258 public:
259 XRefStreamWriter(Object *index, GooString *stmBuf, int offsetSize);
260 void startSection(int first, int count);
261 void writeEntry(Goffset offset, int gen, XRefEntryType type);
262 private:
263 Object *index;
264 GooString *stmBuf;
265 int offsetSize;
268 // Dummy XRefWriter subclass that only checks if all offsets fit in 4 bytes
269 class XRefPreScanWriter: public XRefWriter {
270 public:
271 XRefPreScanWriter();
272 void startSection(int first, int count);
273 void writeEntry(Goffset offset, int gen, XRefEntryType type);
275 GBool hasOffsetsBeyond4GB;
278 void writeXRef(XRefWriter *writer, GBool writeAllEntries);
281 #endif