Zip.h 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306
  1. /*
  2. ===========================================================================
  3. Doom 3 BFG Edition GPL Source Code
  4. Copyright (C) 1993-2012 id Software LLC, a ZeniMax Media company.
  5. This file is part of the Doom 3 BFG Edition GPL Source Code ("Doom 3 BFG Edition Source Code").
  6. Doom 3 BFG Edition Source Code is free software: you can redistribute it and/or modify
  7. it under the terms of the GNU General Public License as published by
  8. the Free Software Foundation, either version 3 of the License, or
  9. (at your option) any later version.
  10. Doom 3 BFG Edition Source Code is distributed in the hope that it will be useful,
  11. but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. GNU General Public License for more details.
  14. You should have received a copy of the GNU General Public License
  15. along with Doom 3 BFG Edition Source Code. If not, see <http://www.gnu.org/licenses/>.
  16. In addition, the Doom 3 BFG Edition Source Code is also subject to certain additional terms. You should have received a copy of these additional terms immediately following the terms and conditions of the GNU General Public License which accompanied the Doom 3 BFG Edition Source Code. If not, please request a copy in writing from id Software at the address below.
  17. If you have questions concerning this license or the applicable additional terms, you may contact in writing id Software LLC, c/o ZeniMax Media Inc., Suite 120, Rockville, Maryland 20850 USA.
  18. ===========================================================================
  19. */
  20. #ifndef __ZIP_H__
  21. #define __ZIP_H__
  22. #include "zlib/zlib.h"
  23. /*
  24. ================================================================================================
  25. Contains external code for building ZipFiles.
  26. The Unzip Package allows extraction of a file from .ZIP file, compatible with
  27. PKZip 2.04g, !WinZip, !InfoZip tools and compatibles. Encryption and multi-volume ZipFiles
  28. (span) are not supported. Old compressions used by old PKZip 1.x are not supported.
  29. ================================================================================================
  30. */
  31. #if defined(STRICTZIP) || defined(STRICTZIPUNZIP)
  32. /* like the STRICT of WIN32, we define a pointer that cannot be converted
  33. from (void*) without cast */
  34. typedef struct TagzipFile__ { int unused; } zipFile__;
  35. typedef zipFile__ *zipFile;
  36. #else
  37. typedef void* zipFile;
  38. #endif
  39. #define ZIP_OK (0)
  40. #define ZIP_EOF (0)
  41. #define ZIP_ERRNO (Z_ERRNO)
  42. #define ZIP_PARAMERROR (-102)
  43. #define ZIP_BADZIPFILE (-103)
  44. #define ZIP_INTERNALERROR (-104)
  45. #ifndef Z_BUFSIZE
  46. #define Z_BUFSIZE (16384)
  47. #endif
  48. /*
  49. ========================
  50. tm_zip
  51. contains date/time info
  52. ========================
  53. */
  54. typedef struct tm_zip_s {
  55. unsigned int tm_sec; /* seconds after the minute - [0,59] */
  56. unsigned int tm_min; /* minutes after the hour - [0,59] */
  57. unsigned int tm_hour; /* hours since midnight - [0,23] */
  58. unsigned int tm_mday; /* day of the month - [1,31] */
  59. unsigned int tm_mon; /* months since January - [0,11] */
  60. unsigned int tm_year; /* years - [1980..2044] */
  61. } tm_zip;
  62. /*
  63. ========================
  64. zip_fileinfo
  65. ========================
  66. */
  67. typedef struct {
  68. tm_zip tmz_date; /* date in understandable format */
  69. unsigned long dosDate; /* if dos_date == 0, tmu_date is used */
  70. // unsigned long flag; /* general purpose bit flag 2 bytes */
  71. unsigned long internal_fa; /* internal file attributes 2 bytes */
  72. unsigned long external_fa; /* external file attributes 4 bytes */
  73. } zip_fileinfo;
  74. #define NOCRYPT // ignore passwords
  75. #define SIZEDATA_INDATABLOCK (4096-(4*4))
  76. /*
  77. ========================
  78. linkedlist_datablock_internal
  79. ========================
  80. */
  81. typedef struct linkedlist_datablock_internal_s {
  82. struct linkedlist_datablock_internal_s* next_datablock;
  83. unsigned long avail_in_this_block;
  84. unsigned long filled_in_this_block;
  85. unsigned long unused; /* for future use and alignement */
  86. unsigned char data[SIZEDATA_INDATABLOCK];
  87. } linkedlist_datablock_internal;
  88. /*
  89. ========================
  90. linkedlist_data
  91. ========================
  92. */
  93. typedef struct linkedlist_data_s {
  94. linkedlist_datablock_internal* first_block;
  95. linkedlist_datablock_internal* last_block;
  96. } linkedlist_data;
  97. /*
  98. ========================
  99. curfile_info
  100. ========================
  101. */
  102. typedef struct {
  103. z_stream stream; /* zLib stream structure for inflate */
  104. int stream_initialised; /* 1 is stream is initialised */
  105. unsigned int pos_in_buffered_data; /* last written byte in buffered_data */
  106. unsigned long pos_local_header; /* offset of the local header of the file currenty writing */
  107. char* central_header; /* central header data for the current file */
  108. unsigned long size_centralheader; /* size of the central header for cur file */
  109. unsigned long flag; /* flag of the file currently writing */
  110. int method; /* compression method of file currenty wr.*/
  111. int raw; /* 1 for directly writing raw data */
  112. byte buffered_data[Z_BUFSIZE];/* buffer contain compressed data to be writ*/
  113. unsigned long dosDate;
  114. unsigned long crc32;
  115. int encrypt;
  116. #ifndef NOCRYPT
  117. unsigned long keys[3]; /* keys defining the pseudo-random sequence */
  118. const unsigned long* pcrc_32_tab;
  119. int crypt_header_size;
  120. #endif
  121. } curfile_info;
  122. //#define NO_ADDFILEINEXISTINGZIP
  123. /*
  124. ========================
  125. zip_internal
  126. ========================
  127. */
  128. typedef struct {
  129. idFile* filestream; /* io structore of the zipfile */
  130. linkedlist_data central_dir; /* datablock with central dir in construction*/
  131. int in_opened_file_inzip; /* 1 if a file in the zip is currently writ.*/
  132. curfile_info ci; /* info on the file curretly writing */
  133. unsigned long begin_pos; /* position of the beginning of the zipfile */
  134. unsigned long add_position_when_writting_offset;
  135. unsigned long number_entry;
  136. #ifndef NO_ADDFILEINEXISTINGZIP
  137. char* globalcomment;
  138. #endif
  139. } zip_internal;
  140. #define APPEND_STATUS_CREATE (0)
  141. #define APPEND_STATUS_CREATEAFTER (1)
  142. #define APPEND_STATUS_ADDINZIP (2)
  143. /*
  144. Create a zipfile.
  145. pathname contain on Windows XP a filename like "c:\\zlib\\zlib113.zip" or on
  146. an Unix computer "zlib/zlib113.zip".
  147. if the file pathname exist and append==APPEND_STATUS_CREATEAFTER, the zip
  148. will be created at the end of the file.
  149. (useful if the file contain a self extractor code)
  150. if the file pathname exist and append==APPEND_STATUS_ADDINZIP, we will
  151. add files in existing zip (be sure you don't add file that doesn't exist)
  152. If the zipfile cannot be opened, the return value is NULL.
  153. Else, the return value is a zipFile Handle, usable with other function
  154. of this zip package.
  155. */
  156. /* Note : there is no delete function into a zipfile.
  157. If you want delete file into a zipfile, you must open a zipfile, and create another
  158. Of couse, you can use RAW reading and writing to copy the file you did not want delte
  159. */
  160. extern zipFile zipOpen( const char *pathname, int append );
  161. /*
  162. Open a file in the ZIP for writing.
  163. filename : the filename in zip (if NULL, '-' without quote will be used
  164. *zipfi contain supplemental information
  165. if extrafield_local!=NULL and size_extrafield_local>0, extrafield_local
  166. contains the extrafield data the the local header
  167. if extrafield_global!=NULL and size_extrafield_global>0, extrafield_global
  168. contains the extrafield data the the local header
  169. if comment != NULL, comment contain the comment string
  170. method contain the compression method (0 for store, Z_DEFLATED for deflate)
  171. level contain the level of compression (can be Z_DEFAULT_COMPRESSION)
  172. */
  173. extern zipFile zipOpen2( const char* pathname, int append, char* globalcomment );
  174. extern int zipOpenNewFileInZip( zipFile file, const char* filename, const zip_fileinfo* zipfi, const void* extrafield_local,
  175. uInt size_extrafield_local, const void* extrafield_global, uInt size_extrafield_global, const char* comment,
  176. int method, int level );
  177. /*
  178. Same than zipOpenNewFileInZip, except if raw=1, we write raw file
  179. */
  180. extern int zipOpenNewFileInZip2( zipFile file, const char* filename, const zip_fileinfo* zipfi, const void* extrafield_local, uInt size_extrafield_local,
  181. const void* extrafield_global, uInt size_extrafield_global, const char* comment, int method, int level, int raw );
  182. /*
  183. Same than zipOpenNewFileInZip2, except
  184. windowBits,memLevel,,strategy : see parameter strategy in deflateInit2
  185. password : crypting password (NULL for no crypting)
  186. crcForCtypting : crc of file to compress (needed for crypting)
  187. */
  188. extern int zipOpenNewFileInZip3( zipFile file, const char* filename, const zip_fileinfo* zipfi, const void* extrafield_local, uInt size_extrafield_local,
  189. const void* extrafield_global, uInt size_extrafield_global, const char* comment, int method, int level, int raw, int windowBits,
  190. int memLevel, int strategy, const char* password, uLong crcForCtypting );
  191. /*
  192. Write data in the zipfile
  193. */
  194. extern int zipWriteInFileInZip( zipFile file, const void* buf, unsigned int len );
  195. /*
  196. Close the current file in the zipfile
  197. */
  198. extern int zipCloseFileInZip( zipFile file );
  199. /*
  200. Close the current file in the zipfile, for fiel opened with
  201. parameter raw=1 in zipOpenNewFileInZip2
  202. uncompressed_size and crc32 are value for the uncompressed size
  203. */
  204. extern int zipCloseFileInZipRaw( zipFile file, uLong uncompressed_size, uLong crc32 );
  205. /*
  206. Close the zipfile
  207. */
  208. extern int zipClose( zipFile file, const char* global_comment );
  209. /*
  210. ================================================
  211. idZipBuilder
  212. simple interface for zipping up a folder of files
  213. by default, the source folder files are added recursively
  214. ================================================
  215. */
  216. class idZipBuilder {
  217. public:
  218. idZipBuilder() {}
  219. ~idZipBuilder() {}
  220. public:
  221. // adds a list of file extensions ( e.g. "bcm|bmodel|" ) to be compressed in the zip file
  222. void AddFileFilters( const char *filters );
  223. // adds a list of file extensions ( e.g. "genmodel|" ) to be added to the zip file, in an uncompressed form
  224. void AddUncompressedFileFilters( const char *filters );
  225. // builds a zip file of all the files in the specified folder, overwriting if necessary
  226. bool Build( const char* zipPath, const char *folder, bool cleanFolder );
  227. // updates a zip file with the files in the specified folder
  228. bool Update( const char* zipPath, const char *folder, bool cleanFolder );
  229. // helper function to zip up all the files and put in a new zip file
  230. static bool BuildMapFolderZip( const char *mapFileName );
  231. // helper function to update a map folder zip for newer files
  232. static bool UpdateMapFolderZip( const char *mapFileName );
  233. // combines multiple in-memory files into a single memory file
  234. static idFile_Memory * CombineFiles( const idList< idFile_Memory * > & srcFiles );
  235. // extracts multiple in-memory files from a single memory file
  236. static bool ExtractFiles( idFile_Memory * & srcFile, idList< idFile_Memory * > & destFiles );
  237. void CleanSourceFolder();
  238. bool CreateZipFileFromFileList( const char *name, const idList< idFile_Memory * > & srcFiles );
  239. zipFile CreateZipFile( const char *name );
  240. bool AddFile( zipFile zf, idFile_Memory *fm, bool deleteFile );
  241. void CloseZipFile( zipFile zf );
  242. private:
  243. bool CreateZipFile( bool appendFiles );
  244. bool CreateZipFileFromFiles( const idList< idFile_Memory * > & srcFiles );
  245. bool GetFileTime( const idStr &filename, unsigned long *dostime ) const;
  246. bool IsFiltered( const idStr &filename ) const;
  247. bool IsUncompressed( const idStr &filename ) const;
  248. private:
  249. idStr zipFileName; // os path to the zip file
  250. idStr sourceFolderName; // source folder of files to zip or add
  251. idStrList filterExts; // file extensions we want to compressed
  252. idStrList uncompressedFilterExts; // file extensions we don't want to compress
  253. };
  254. #endif /* __ZIP_H__ */