Skip to content

Commit

Permalink
ZipFile - speedup initialization for zip archive by 30-50%
Browse files Browse the repository at this point in the history
unzip.h/.cpp - unzGoToFirstFile/unzGoToNextFile retrieves information
about the current file, so it is possible to remove redundant calls
to unzGetCurrentFileInfo and speed up general execution.

unzip.h/.cpp are modified accordingly by creation unzGoToFirstFile64
and unzGoToNextFile64 with file info (unz_file_info64) and name as
possible output parameters.

ZipFile::setFilter (it is used to create a file list at ZipFile
constructor) - redundant calls to unzGetCurrentFileInfo64 are removed,
so briefly the time required to generate a zip file list is something
like 1 average old unzLocateFile call.
  • Loading branch information
mingulov committed Nov 11, 2012
1 parent efb61a8 commit f73568d
Show file tree
Hide file tree
Showing 3 changed files with 77 additions and 25 deletions.
36 changes: 17 additions & 19 deletions cocos2dx/support/zip_support/ZipUtils.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -300,7 +300,7 @@ class ZipFilePrivate
unzFile zipFile;

// std::unordered_map is faster if available on the platform
typedef std::map<std::string, ZipEntryInfo> FileListContainer;
typedef std::map<std::string, struct ZipEntryInfo> FileListContainer;
FileListContainer fileList;
};

Expand Down Expand Up @@ -334,35 +334,33 @@ bool ZipFile::setFilter(const std::string &filter)
// clear existing file list
m_data->fileList.clear();

// UNZ_MAXFILENAMEINZIP + 1 - it is done so in unzLocateFile
char szCurrentFileName[UNZ_MAXFILENAMEINZIP + 1];
unz_file_info64 fileInfo;

// go through all files and store position information about the required files
int err = unzGoToFirstFile(m_data->zipFile);
int err = unzGoToFirstFile64(m_data->zipFile, &fileInfo,
szCurrentFileName, sizeof(szCurrentFileName) - 1);
while (err == UNZ_OK)
{
unz_file_pos posInfo;
int posErr = unzGetFilePos(m_data->zipFile, &posInfo);
if (posErr == UNZ_OK)
{
// UNZ_MAXFILENAMEINZIP + 1 - it is done so in unzLocateFile
char szCurrentFileName[UNZ_MAXFILENAMEINZIP + 1];
unz_file_info64 fileInfo;
int nameErr = unzGetCurrentFileInfo64(m_data->zipFile, &fileInfo,
szCurrentFileName, sizeof(szCurrentFileName) - 1,
NULL, 0, NULL, 0);
std::string currentFileName = szCurrentFileName;
if (nameErr == UNZ_OK)
// cache info about filtered files only (like 'assets/')
if (filter.empty()
|| currentFileName.substr(0, filter.length()) == filter)
{
// cache info about filtered files only (like 'assets/')
if (filter.empty()
|| currentFileName.substr(0, filter.length()) == filter)
{
ZipEntryInfo entry;
entry.pos = posInfo;
entry.uncompressed_size = (uLong)fileInfo.uncompressed_size;
m_data->fileList[currentFileName] = entry;
}
ZipEntryInfo entry;
entry.pos = posInfo;
entry.uncompressed_size = (uLong)fileInfo.uncompressed_size;
m_data->fileList[currentFileName] = entry;
}
}
err = unzGoToNextFile(m_data->zipFile);
// next file - also get the information about it
err = unzGoToNextFile64(m_data->zipFile, &fileInfo,
szCurrentFileName, sizeof(szCurrentFileName) - 1);
}
ret = true;

Expand Down
44 changes: 38 additions & 6 deletions cocos2dx/support/zip_support/unzip.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1172,11 +1172,16 @@ int ZEXPORT unzGetCurrentFileInfo (unzFile file,
}
return err;
}

/*
Set the current file of the zipfile to the first file.
Set the current file of the zipfile to the first file
with retrieving an information about the file.
return UNZ_OK if there is no problem
*/
int ZEXPORT unzGoToFirstFile (unzFile file)
int ZEXPORT unzGoToFirstFile64 (unzFile file,
unz_file_info64 *pfile_info,
char *szFileName,
uLong fileNameBufferSize)
{
int err=UNZ_OK;
unz64_s* s;
Expand All @@ -1187,17 +1192,32 @@ int ZEXPORT unzGoToFirstFile (unzFile file)
s->num_file=0;
err=unz64local_GetCurrentFileInfoInternal(file,&s->cur_file_info,
&s->cur_file_info_internal,
NULL,0,NULL,0,NULL,0);
szFileName,fileNameBufferSize,NULL,0,NULL,0);
s->current_file_ok = (err == UNZ_OK);
if (pfile_info)
*pfile_info = s->cur_file_info;
return err;
}

/*
Set the current file of the zipfile to the next file.
Set the current file of the zipfile to the first file.
return UNZ_OK if there is no problem
*/
int ZEXPORT unzGoToFirstFile (unzFile file)
{
return unzGoToFirstFile64(file, NULL, NULL, 0);
}

/*
Set the current file of the zipfile to the next file
with retrieving an information about the file.
return UNZ_OK if there is no problem
return UNZ_END_OF_LIST_OF_FILE if the actual file was the latest.
*/
int ZEXPORT unzGoToNextFile (unzFile file)
int ZEXPORT unzGoToNextFile64 (unzFile file,
unz_file_info64 *pfile_info,
char *szFileName,
uLong fileNameBufferSize)
{
unz64_s* s;
int err;
Expand All @@ -1216,11 +1236,23 @@ int ZEXPORT unzGoToNextFile (unzFile file)
s->num_file++;
err = unz64local_GetCurrentFileInfoInternal(file,&s->cur_file_info,
&s->cur_file_info_internal,
NULL,0,NULL,0,NULL,0);
szFileName,fileNameBufferSize,NULL,0,NULL,0);
s->current_file_ok = (err == UNZ_OK);
if (pfile_info)
*pfile_info = s->cur_file_info;
return err;
}

/*
Set the current file of the zipfile to the next file.
return UNZ_OK if there is no problem
return UNZ_END_OF_LIST_OF_FILE if the actual file was the latest.
*/
int ZEXPORT unzGoToNextFile (unzFile file)
{
return unzGoToNextFile64(file, NULL, NULL, 0);
}


/*
Try locate the file szFileName in the zipfile.
Expand Down
22 changes: 22 additions & 0 deletions cocos2dx/support/zip_support/unzip.h
Original file line number Diff line number Diff line change
Expand Up @@ -225,18 +225,40 @@ int ZEXPORT unzGetGlobalComment OF((unzFile file,
/* Unzip package allow you browse the directory of the zipfile */

int ZEXPORT unzGoToFirstFile OF((unzFile file));

/*
Set the current file of the zipfile to the first file.
return UNZ_OK if there is no problem
*/

int ZEXPORT unzGoToFirstFile64 OF((unzFile file,
unz_file_info64 *pfile_info,
char *szFileName,
uLong fileNameBufferSize));
/*
Set the current file of the zipfile to the first file
with retrieving an information about the file.
return UNZ_OK if there is no problem
*/

int ZEXPORT unzGoToNextFile OF((unzFile file));
/*
Set the current file of the zipfile to the next file.
return UNZ_OK if there is no problem
return UNZ_END_OF_LIST_OF_FILE if the actual file was the latest.
*/

int ZEXPORT unzGoToNextFile64 OF((unzFile file,
unz_file_info64 *pfile_info,
char *szFileName,
uLong fileNameBufferSize));
/*
Set the current file of the zipfile to the next file
with retrieving an information about the file.
return UNZ_OK if there is no problem
return UNZ_END_OF_LIST_OF_FILE if the actual file was the latest.
*/

int ZEXPORT unzLocateFile OF((unzFile file,
const char *szFileName,
int iCaseSensitivity));
Expand Down

0 comments on commit f73568d

Please sign in to comment.