[Scummvm-cvs-logs] SF.net SVN: scummvm:[52204] scummvm/trunk/common/unzip.cpp
sev at users.sourceforge.net
sev at users.sourceforge.net
Thu Aug 19 12:15:12 CEST 2010
Revision: 52204
http://scummvm.svn.sourceforge.net/scummvm/?rev=52204&view=rev
Author: sev
Date: 2010-08-19 10:15:12 +0000 (Thu, 19 Aug 2010)
Log Message:
-----------
COMMON: Add caching to ZipArchive. Patch #3048388
Based on patch #3048388: "Hash map for ZipArchive class", though
I made the hashing by default and removed the old code.
It is a really good thing and will speed up any archive operations.
Modified Paths:
--------------
scummvm/trunk/common/unzip.cpp
Modified: scummvm/trunk/common/unzip.cpp
===================================================================
--- scummvm/trunk/common/unzip.cpp 2010-08-19 10:11:52 UTC (rev 52203)
+++ scummvm/trunk/common/unzip.cpp 2010-08-19 10:15:12 UTC (rev 52204)
@@ -107,6 +107,9 @@
#include "common/unzip.h"
#include "common/file.h"
+#include "common/hashmap.h"
+#include "common/hash-str.h"
+
#if defined(STRICTUNZIP) || defined(STRICTZIPUNZIP)
/* like the STRICT of WIN32, we define a pointer that cannot be converted
from (void*) without cast */
@@ -362,7 +365,17 @@
uLong byte_before_the_zipfile;/* byte before the zipfile, (>0 for sfx)*/
} file_in_zip_read_info_s;
+typedef struct {
+ uLong num_file; /* number of the current file in the zipfile*/
+ uLong pos_in_central_dir; /* pos of the current file in the central dir*/
+ uLong current_file_ok; /* flag about the usability of the current file*/
+ unz_file_info cur_file_info; /* public info about the current file in zip*/
+ unz_file_info_internal cur_file_info_internal; /* private info about it*/
+} cached_file_in_zip;
+typedef Common::HashMap<Common::String, cached_file_in_zip, Common::IgnoreCase_Hash,
+ Common::IgnoreCase_EqualTo> ZipHash;
+
/* unz_s contain internal information about the zipfile
*/
typedef struct {
@@ -382,6 +395,7 @@
unz_file_info_internal cur_file_info_internal; /* private info about it*/
file_in_zip_read_info_s* pfile_in_zip_read; /* structure about the current
file if we are decompressing it */
+ ZipHash _hash;
} unz_s;
/* ===========================================================================
@@ -589,7 +603,27 @@
us->central_pos = central_pos;
us->pfile_in_zip_read = NULL;
- unzGoToFirstFile((unzFile)us);
+ err = unzGoToFirstFile((unzFile)us);
+
+ while (err == UNZ_OK) {
+ // Get the file details
+ char szCurrentFileName[UNZ_MAXFILENAMEINZIP+1];
+ unzGetCurrentFileInfo(us, NULL, szCurrentFileName, sizeof(szCurrentFileName) - 1,
+ NULL, 0, NULL, 0);
+
+ // Save details into the hash
+ cached_file_in_zip fe;
+ fe.num_file = us->num_file;
+ fe.pos_in_central_dir = us->pos_in_central_dir;
+ fe.current_file_ok = us->current_file_ok;
+ fe.cur_file_info = us->cur_file_info;
+ fe.cur_file_info_internal = us->cur_file_info_internal;
+
+ us->_hash[Common::String(szCurrentFileName)] = fe;
+
+ // Move to the next file
+ err = unzGoToNextFile((unzFile)us);
+ }
return (unzFile)us;
}
@@ -870,7 +904,6 @@
return err;
}
-
/*
Try locate the file szFileName in the zipfile.
For the iCaseSensitivity signification, see unzipStringFileNameCompare
@@ -881,13 +914,7 @@
*/
int unzLocateFile(unzFile file, const char *szFileName, int iCaseSensitivity) {
unz_s* s;
- int err;
-
- uLong num_fileSaved;
- uLong pos_in_central_dirSaved;
-
-
if (file==NULL)
return UNZ_PARAMERROR;
@@ -898,25 +925,20 @@
if (!s->current_file_ok)
return UNZ_END_OF_LIST_OF_FILE;
- num_fileSaved = s->num_file;
- pos_in_central_dirSaved = s->pos_in_central_dir;
+ // Check to see if the entry exists
+ ZipHash::iterator i = s->_hash.find(Common::String(szFileName));
+ if (i == s->_hash.end())
+ return UNZ_END_OF_LIST_OF_FILE;
- err = unzGoToFirstFile(file);
+ // Found it, so reset the details in the main structure
+ cached_file_in_zip &fe = i->_value;
+ s->num_file = fe.num_file;
+ s->pos_in_central_dir = fe.pos_in_central_dir;
+ s->current_file_ok = fe.current_file_ok;
+ s->cur_file_info = fe.cur_file_info;
+ s->cur_file_info_internal = fe.cur_file_info_internal;
- while (err == UNZ_OK) {
- char szCurrentFileName[UNZ_MAXFILENAMEINZIP+1];
- unzGetCurrentFileInfo(file,NULL,
- szCurrentFileName,sizeof(szCurrentFileName)-1,
- NULL,0,NULL,0);
- if (unzStringFileNameCompare(szCurrentFileName,
- szFileName,iCaseSensitivity)==0)
- return UNZ_OK;
- err = unzGoToNextFile(file);
- }
-
- s->num_file = num_fileSaved ;
- s->pos_in_central_dir = pos_in_central_dirSaved ;
- return err;
+ return UNZ_OK;
}
This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
More information about the Scummvm-git-logs
mailing list