poppler/XRef.cc | 62 +++++++++++++++++++++++++++++++++++++++++++++++--------- poppler/XRef.h | 4 +-- 2 files changed, 55 insertions(+), 11 deletions(-)
New commits: commit 3ca304f3837af27ae49541a5f441d8729264a945 Author: Albert Astals Cid <[email protected]> Date: Mon Jun 14 19:16:41 2010 +0100 Add more caching to ObjectStreams Makes opening of file from bug 26759 ten times faster diff --git a/poppler/XRef.cc b/poppler/XRef.cc index 9d0cd3b..a9cf571 100644 --- a/poppler/XRef.cc +++ b/poppler/XRef.cc @@ -45,6 +45,7 @@ #include "Error.h" #include "ErrorCodes.h" #include "XRef.h" +#include "PopplerCache.h" //------------------------------------------------------------------------ @@ -97,6 +98,37 @@ private: GBool ok; }; +class ObjectStreamKey : public PopplerCacheKey +{ + public: + ObjectStreamKey(int num) : objStrNum(num) + { + } + + bool operator==(const PopplerCacheKey &key) const + { + const ObjectStreamKey *k = static_cast<const ObjectStreamKey*>(&key); + return objStrNum == k->objStrNum; + } + + const int objStrNum; +}; + +class ObjectStreamItem : public PopplerCacheItem +{ + public: + ObjectStreamItem(ObjectStream *objStr) : objStream(objStr) + { + } + + ~ObjectStreamItem() + { + delete objStream; + } + + ObjectStream *objStream; +}; + ObjectStream::ObjectStream(XRef *xref, int objStrNumA) { Stream *str; Parser *parser; @@ -233,7 +265,7 @@ XRef::XRef() { size = 0; streamEnds = NULL; streamEndsLen = 0; - objStr = NULL; + objStrs = new PopplerCache(5); } XRef::XRef(BaseStream *strA) { @@ -246,7 +278,7 @@ XRef::XRef(BaseStream *strA) { entries = NULL; streamEnds = NULL; streamEndsLen = 0; - objStr = NULL; + objStrs = new PopplerCache(5); encrypted = gFalse; permFlags = defPermFlags; @@ -309,8 +341,8 @@ XRef::~XRef() { if (streamEnds) { gfree(streamEnds); } - if (objStr) { - delete objStr; + if (objStrs) { + delete objStrs; } } @@ -1010,22 +1042,34 @@ Object *XRef::fetch(int num, int gen, Object *obj) { break; case xrefEntryCompressed: + { if (gen != 0) { goto err; } - if (!objStr || objStr->getObjStrNum() != (int)e->offset) { - if (objStr) { - delete objStr; - } + + ObjectStream *objStr = NULL; + ObjectStreamKey key(e->offset); + PopplerCacheItem *item = objStrs->lookup(key); + if (item) { + ObjectStreamItem *it = static_cast<ObjectStreamItem *>(item); + objStr = it->objStream; + } + + if (!objStr) { objStr = new ObjectStream(this, e->offset); if (!objStr->isOk()) { delete objStr; objStr = NULL; goto err; + } else { + ObjectStreamKey *newkey = new ObjectStreamKey(e->offset); + ObjectStreamItem *newitem = new ObjectStreamItem(objStr); + objStrs->put(newkey, newitem); } } objStr->getObject(e->gen, num, obj); - break; + } + break; default: goto err; diff --git a/poppler/XRef.h b/poppler/XRef.h index 36546fc..be19e23 100644 --- a/poppler/XRef.h +++ b/poppler/XRef.h @@ -37,7 +37,7 @@ class Dict; class Stream; class Parser; -class ObjectStream; +class PopplerCache; //------------------------------------------------------------------------ // XRef @@ -146,7 +146,7 @@ private: Guint *streamEnds; // 'endstream' positions - only used in // damaged files int streamEndsLen; // number of valid entries in streamEnds - ObjectStream *objStr; // cached object stream + PopplerCache *objStrs; // cached object streams GBool encrypted; // true if file is encrypted int encRevision; int encVersion; // encryption algorithm _______________________________________________ poppler mailing list [email protected] http://lists.freedesktop.org/mailman/listinfo/poppler
