Mercurial > vba-linux
diff src/common/unzip.cpp @ 1:f9f4f1b99eed
importing src directory
author | Robert McIntyre <rlm@mit.edu> |
---|---|
date | Sat, 03 Mar 2012 10:31:27 -0600 |
parents | |
children |
line wrap: on
line diff
1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/src/common/unzip.cpp Sat Mar 03 10:31:27 2012 -0600 1.3 @@ -0,0 +1,1208 @@ 1.4 +/* unzip.c -- IO on .zip files using zlib 1.5 + Version 0.15 beta, Mar 19th, 1998, 1.6 + 1.7 + Read unzip.h for more info 1.8 + */ 1.9 + 1.10 +#include <cstdio> 1.11 +#include <cstdlib> 1.12 +#include <cstring> 1.13 +#include "zlib.h" 1.14 +#include "unzip.h" 1.15 + 1.16 +#ifdef NO_ERRNO_H 1.17 +extern int errno; 1.18 +#else 1.19 +# include <cerrno> 1.20 +#endif 1.21 + 1.22 +#ifndef local 1.23 +# define local static 1.24 +#endif 1.25 +/* compile with -Dlocal if your debugger can't find static symbols */ 1.26 + 1.27 +#if !defined(unix) && !defined(CASESENSITIVITYDEFAULT_YES) && \ 1.28 + !defined(CASESENSITIVITYDEFAULT_NO) 1.29 +#define CASESENSITIVITYDEFAULT_NO 1.30 +#endif 1.31 + 1.32 +#ifndef UNZ_BUFSIZE 1.33 +#define UNZ_BUFSIZE (16384) 1.34 +#endif 1.35 + 1.36 +#ifndef UNZ_MAXFILENAMEINZIP 1.37 +#define UNZ_MAXFILENAMEINZIP (256) 1.38 +#endif 1.39 + 1.40 +#ifndef ALLOC 1.41 +# define ALLOC(size) (malloc(size)) 1.42 +#endif 1.43 +#ifndef TRYFREE 1.44 +# define TRYFREE(p) {if (p) \ 1.45 + free(p);} 1.46 +#endif 1.47 + 1.48 +#define SIZECENTRALDIRITEM (0x2e) 1.49 +#define SIZEZIPLOCALHEADER (0x1e) 1.50 + 1.51 +/* I've found an old Unix (a SunOS 4.1.3_U1) without all SEEK_* defined.... */ 1.52 + 1.53 +#ifndef SEEK_CUR 1.54 +#define SEEK_CUR 1 1.55 +#endif 1.56 + 1.57 +#ifndef SEEK_END 1.58 +#define SEEK_END 2 1.59 +#endif 1.60 + 1.61 +#ifndef SEEK_SET 1.62 +#define SEEK_SET 0 1.63 +#endif 1.64 + 1.65 +const char unz_copyright[] = 1.66 + " unzip 0.15 Copyright 1998 Gilles Vollant "; 1.67 + 1.68 +/* unz_file_info_interntal contain internal info about a file in zipfile*/ 1.69 +typedef struct unz_file_info_internal_s 1.70 +{ 1.71 + uLong offset_curfile; /* relative offset of local header 4 bytes */ 1.72 +} unz_file_info_internal; 1.73 + 1.74 +/* file_in_zip_read_info_s contain internal information about a file in zipfile, 1.75 + when reading and decompress it */ 1.76 +typedef struct 1.77 +{ 1.78 + char * read_buffer; /* internal buffer for compressed data */ 1.79 + z_stream stream; /* zLib stream structure for inflate */ 1.80 + 1.81 + uLong pos_in_zipfile; /* position in byte on the zipfile, for fseek*/ 1.82 + uLong stream_initialised; /* flag set if stream structure is initialised*/ 1.83 + 1.84 + uLong offset_local_extrafield; /* offset of the local extra field */ 1.85 + uInt size_local_extrafield; /* size of the local extra field */ 1.86 + uLong pos_local_extrafield; /* position in the local extra field in read*/ 1.87 + 1.88 + uLong crc32; /* crc32 of all data uncompressed */ 1.89 + uLong crc32_wait; /* crc32 we must obtain after decompress all */ 1.90 + uLong rest_read_compressed; /* number of byte to be decompressed */ 1.91 + uLong rest_read_uncompressed; /*number of byte to be obtained after decomp*/ 1.92 + FILE* file; /* io structore of the zipfile */ 1.93 + uLong compression_method; /* compression method (0==store) */ 1.94 + uLong byte_before_the_zipfile; /* byte before the zipfile, (>0 for sfx)*/ 1.95 +} file_in_zip_read_info_s; 1.96 + 1.97 +/* unz_s contain internal information about the zipfile 1.98 + */ 1.99 +typedef struct 1.100 +{ 1.101 + FILE*file; /* io structore of the zipfile */ 1.102 + unz_global_info gi; /* public global information */ 1.103 + uLong byte_before_the_zipfile; /* byte before the zipfile, (>0 for sfx)*/ 1.104 + uLong num_file; /* number of the current file in the zipfile*/ 1.105 + uLong pos_in_central_dir; /* pos of the current file in the central dir*/ 1.106 + uLong current_file_ok; /* flag about the usability of the current file*/ 1.107 + uLong central_pos; /* position of the beginning of the central dir*/ 1.108 + 1.109 + uLong size_central_dir; /* size of the central directory */ 1.110 + uLong offset_central_dir; /* offset of start of central directory with 1.111 + respect to the starting disk number */ 1.112 + 1.113 + unz_file_info cur_file_info; /* public info about the current file in zip*/ 1.114 + unz_file_info_internal cur_file_info_internal; /* private info about it*/ 1.115 + file_in_zip_read_info_s*pfile_in_zip_read; /* structure about the current 1.116 + file if we are decompressing it */ 1.117 +} unz_s; 1.118 + 1.119 +/* =========================================================================== 1.120 + Read a byte from a gz_stream; update next_in and avail_in. Return EOF 1.121 + for end of file. 1.122 + IN assertion: the stream s has been sucessfully opened for reading. 1.123 + */ 1.124 + 1.125 +local int unzlocal_getByte(FILE *fin, int *pi) 1.126 +{ 1.127 + unsigned char c; 1.128 + int err = fread(&c, 1, 1, fin); 1.129 + if (err == 1) 1.130 + { 1.131 + *pi = (int)c; 1.132 + return UNZ_OK; 1.133 + } 1.134 + else 1.135 + { 1.136 + if (ferror(fin)) 1.137 + return UNZ_ERRNO; 1.138 + else 1.139 + return UNZ_EOF; 1.140 + } 1.141 +} 1.142 + 1.143 +/* =========================================================================== 1.144 + Reads a long in LSB order from the given gz_stream. Sets 1.145 + */ 1.146 +local int unzlocal_getShort(FILE *fin, uLong *pX) 1.147 +{ 1.148 + uLong x ; 1.149 + int i; 1.150 + int err; 1.151 + 1.152 + err = unzlocal_getByte(fin, &i); 1.153 + x = (uLong)i; 1.154 + 1.155 + if (err == UNZ_OK) 1.156 + err = unzlocal_getByte(fin, &i); 1.157 + x += ((uLong)i)<<8; 1.158 + 1.159 + if (err == UNZ_OK) 1.160 + *pX = x; 1.161 + else 1.162 + *pX = 0; 1.163 + return err; 1.164 +} 1.165 + 1.166 +local int unzlocal_getLong(FILE *fin, uLong *pX) 1.167 +{ 1.168 + uLong x ; 1.169 + int i; 1.170 + int err; 1.171 + 1.172 + err = unzlocal_getByte(fin, &i); 1.173 + x = (uLong)i; 1.174 + 1.175 + if (err == UNZ_OK) 1.176 + err = unzlocal_getByte(fin, &i); 1.177 + x += ((uLong)i)<<8; 1.178 + 1.179 + if (err == UNZ_OK) 1.180 + err = unzlocal_getByte(fin, &i); 1.181 + x += ((uLong)i)<<16; 1.182 + 1.183 + if (err == UNZ_OK) 1.184 + err = unzlocal_getByte(fin, &i); 1.185 + x += ((uLong)i)<<24; 1.186 + 1.187 + if (err == UNZ_OK) 1.188 + *pX = x; 1.189 + else 1.190 + *pX = 0; 1.191 + return err; 1.192 +} 1.193 + 1.194 +/* My own strcmpi / strcasecmp */ 1.195 +local int strcmpcasenosensitive_internal(const char *fileName1, 1.196 + const char *fileName2) 1.197 +{ 1.198 + for (;;) 1.199 + { 1.200 + char c1 = *(fileName1++); 1.201 + char c2 = *(fileName2++); 1.202 + if ((c1 >= 'a') && (c1 <= 'z')) 1.203 + c1 -= 0x20; 1.204 + if ((c2 >= 'a') && (c2 <= 'z')) 1.205 + c2 -= 0x20; 1.206 + if (c1 == '\0') 1.207 + return ((c2 == '\0') ? 0 : -1); 1.208 + if (c2 == '\0') 1.209 + return 1; 1.210 + if (c1 < c2) 1.211 + return -1; 1.212 + if (c1 > c2) 1.213 + return 1; 1.214 + } 1.215 +} 1.216 + 1.217 +#ifdef CASESENSITIVITYDEFAULT_NO 1.218 +#define CASESENSITIVITYDEFAULTVALUE 2 1.219 +#else 1.220 +#define CASESENSITIVITYDEFAULTVALUE 1 1.221 +#endif 1.222 + 1.223 +#ifndef STRCMPCASENOSENTIVEFUNCTION 1.224 +#define STRCMPCASENOSENTIVEFUNCTION strcmpcasenosensitive_internal 1.225 +#endif 1.226 + 1.227 +/* 1.228 + Compare two filename (fileName1,fileName2). 1.229 + If iCaseSenisivity = 1, comparision is case sensitivity (like strcmp) 1.230 + If iCaseSenisivity = 2, comparision is not case sensitivity (like strcmpi 1.231 + or strcasecmp) 1.232 + If iCaseSenisivity = 0, case sensitivity is defaut of your operating system 1.233 + (like 1 on Unix, 2 on Windows) 1.234 + 1.235 + */ 1.236 +extern int ZEXPORT unzStringFileNameCompare(const char *fileName1, 1.237 + const char *fileName2, 1.238 + int iCaseSensitivity) 1.239 +{ 1.240 + if (iCaseSensitivity == 0) 1.241 + iCaseSensitivity = CASESENSITIVITYDEFAULTVALUE; 1.242 + 1.243 + if (iCaseSensitivity == 1) 1.244 + return strcmp(fileName1, fileName2); 1.245 + 1.246 + return STRCMPCASENOSENTIVEFUNCTION(fileName1, fileName2); 1.247 +} 1.248 + 1.249 +#define BUFREADCOMMENT (0x400) 1.250 + 1.251 +/* 1.252 + Locate the Central directory of a zipfile (at the end, just before 1.253 + the global comment) 1.254 + */ 1.255 +local uLong unzlocal_SearchCentralDir(FILE *fin) 1.256 +{ 1.257 + unsigned char*buf; 1.258 + uLong uSizeFile; 1.259 + uLong uBackRead; 1.260 + uLong uMaxBack = 0xffff; /* maximum size of global comment */ 1.261 + uLong uPosFound = 0; 1.262 + 1.263 + if (fseek(fin, 0, SEEK_END) != 0) 1.264 + return 0; 1.265 + 1.266 + uSizeFile = ftell(fin); 1.267 + 1.268 + if (uMaxBack > uSizeFile) 1.269 + uMaxBack = uSizeFile; 1.270 + 1.271 + buf = (unsigned char *)ALLOC(BUFREADCOMMENT+4); 1.272 + if (buf == NULL) 1.273 + return 0; 1.274 + 1.275 + uBackRead = 4; 1.276 + while (uBackRead < uMaxBack) 1.277 + { 1.278 + uLong uReadSize, uReadPos ; 1.279 + int i; 1.280 + if (uBackRead+BUFREADCOMMENT > uMaxBack) 1.281 + uBackRead = uMaxBack; 1.282 + else 1.283 + uBackRead += BUFREADCOMMENT; 1.284 + uReadPos = uSizeFile-uBackRead ; 1.285 + 1.286 + uReadSize = ((BUFREADCOMMENT+4) < (uSizeFile-uReadPos)) ? 1.287 + (BUFREADCOMMENT+4) : (uSizeFile-uReadPos); 1.288 + if (fseek(fin, uReadPos, SEEK_SET) != 0) 1.289 + break; 1.290 + 1.291 + if (fread(buf, (uInt)uReadSize, 1, fin) != 1) 1.292 + break; 1.293 + 1.294 + for (i = (int)uReadSize-3; (i--) > 0;) 1.295 + if (((*(buf+i)) == 0x50) && ((*(buf+i+1)) == 0x4b) && 1.296 + ((*(buf+i+2)) == 0x05) && ((*(buf+i+3)) == 0x06)) 1.297 + { 1.298 + uPosFound = uReadPos+i; 1.299 + break; 1.300 + } 1.301 + 1.302 + if (uPosFound != 0) 1.303 + break; 1.304 + } 1.305 + TRYFREE(buf); 1.306 + return uPosFound; 1.307 +} 1.308 + 1.309 +/* 1.310 + Open a Zip file. path contain the full pathname (by example, 1.311 + on a Windows NT computer "c:\\test\\zlib109.zip" or on an Unix computer 1.312 + "zlib/zlib109.zip". 1.313 + If the zipfile cannot be opened (file don't exist or in not valid), the 1.314 + return value is NULL. 1.315 + Else, the return value is a unzFile Handle, usable with other function 1.316 + of this unzip package. 1.317 + */ 1.318 +extern unzFile ZEXPORT unzOpen(const char *path) 1.319 +{ 1.320 + unz_s us; 1.321 + unz_s *s; 1.322 + uLong central_pos, uL; 1.323 + FILE * fin ; 1.324 + 1.325 + uLong number_disk; /* number of the current dist, used for 1.326 + spaning ZIP, unsupported, always 0*/ 1.327 + uLong number_disk_with_CD; /* number the the disk with central dir, used 1.328 + for spaning ZIP, unsupported, always 0*/ 1.329 + uLong number_entry_CD; /* total number of entries in 1.330 + the central dir 1.331 + (same than number_entry on nospan) */ 1.332 + 1.333 + int err = UNZ_OK; 1.334 + 1.335 + if (unz_copyright[0] != ' ') 1.336 + return NULL; 1.337 + 1.338 + fin = fopen(path, "rb"); 1.339 + if (fin == NULL) 1.340 + return NULL; 1.341 + 1.342 + central_pos = unzlocal_SearchCentralDir(fin); 1.343 + if (central_pos == 0) 1.344 + err = UNZ_ERRNO; 1.345 + 1.346 + if (fseek(fin, central_pos, SEEK_SET) != 0) 1.347 + err = UNZ_ERRNO; 1.348 + 1.349 + /* the signature, already checked */ 1.350 + if (unzlocal_getLong(fin, &uL) != UNZ_OK) 1.351 + err = UNZ_ERRNO; 1.352 + 1.353 + /* number of this disk */ 1.354 + if (unzlocal_getShort(fin, &number_disk) != UNZ_OK) 1.355 + err = UNZ_ERRNO; 1.356 + 1.357 + /* number of the disk with the start of the central directory */ 1.358 + if (unzlocal_getShort(fin, &number_disk_with_CD) != UNZ_OK) 1.359 + err = UNZ_ERRNO; 1.360 + 1.361 + /* total number of entries in the central dir on this disk */ 1.362 + if (unzlocal_getShort(fin, &us.gi.number_entry) != UNZ_OK) 1.363 + err = UNZ_ERRNO; 1.364 + 1.365 + /* total number of entries in the central dir */ 1.366 + if (unzlocal_getShort(fin, &number_entry_CD) != UNZ_OK) 1.367 + err = UNZ_ERRNO; 1.368 + 1.369 + if ((number_entry_CD != us.gi.number_entry) || 1.370 + (number_disk_with_CD != 0) || 1.371 + (number_disk != 0)) 1.372 + err = UNZ_BADZIPFILE; 1.373 + 1.374 + /* size of the central directory */ 1.375 + if (unzlocal_getLong(fin, &us.size_central_dir) != UNZ_OK) 1.376 + err = UNZ_ERRNO; 1.377 + 1.378 + /* offset of start of central directory with respect to the 1.379 + starting disk number */ 1.380 + if (unzlocal_getLong(fin, &us.offset_central_dir) != UNZ_OK) 1.381 + err = UNZ_ERRNO; 1.382 + 1.383 + /* zipfile comment length */ 1.384 + if (unzlocal_getShort(fin, &us.gi.size_comment) != UNZ_OK) 1.385 + err = UNZ_ERRNO; 1.386 + 1.387 + if ((central_pos < us.offset_central_dir+us.size_central_dir) && 1.388 + (err == UNZ_OK)) 1.389 + err = UNZ_BADZIPFILE; 1.390 + 1.391 + if (err != UNZ_OK) 1.392 + { 1.393 + fclose(fin); 1.394 + return NULL; 1.395 + } 1.396 + 1.397 + us.file = fin; 1.398 + us.byte_before_the_zipfile = central_pos - 1.399 + (us.offset_central_dir+us.size_central_dir); 1.400 + us.central_pos = central_pos; 1.401 + us.pfile_in_zip_read = NULL; 1.402 + 1.403 + s = (unz_s *)ALLOC(sizeof(unz_s)); 1.404 + *s = us; 1.405 + unzGoToFirstFile((unzFile)s); 1.406 + return (unzFile)s; 1.407 +} 1.408 + 1.409 +/* 1.410 + Close a ZipFile opened with unzipOpen. 1.411 + If there is files inside the .Zip opened with unzipOpenCurrentFile (see later), 1.412 + these files MUST be closed with unzipCloseCurrentFile before call unzipClose. 1.413 + return UNZ_OK if there is no problem. */ 1.414 +extern int ZEXPORT unzClose(unzFile file) 1.415 +{ 1.416 + unz_s*s; 1.417 + if (file == NULL) 1.418 + return UNZ_PARAMERROR; 1.419 + s = (unz_s *)file; 1.420 + 1.421 + if (s->pfile_in_zip_read != NULL) 1.422 + unzCloseCurrentFile(file); 1.423 + 1.424 + fclose(s->file); 1.425 + TRYFREE(s); 1.426 + return UNZ_OK; 1.427 +} 1.428 + 1.429 +/* 1.430 + Write info about the ZipFile in the *pglobal_info structure. 1.431 + No preparation of the structure is needed 1.432 + return UNZ_OK if there is no problem. */ 1.433 +extern int ZEXPORT unzGetGlobalInfo(unzFile file, 1.434 + unz_global_info *pglobal_info) 1.435 +{ 1.436 + unz_s*s; 1.437 + if (file == NULL) 1.438 + return UNZ_PARAMERROR; 1.439 + s = (unz_s *)file; 1.440 + *pglobal_info = s->gi; 1.441 + return UNZ_OK; 1.442 +} 1.443 + 1.444 +/* 1.445 + Translate date/time from Dos format to tm_unz (readable more easilty) 1.446 + */ 1.447 +local void unzlocal_DosDateToTmuDate(uLong ulDosDate, tm_unz *ptm) 1.448 +{ 1.449 + uLong uDate; 1.450 + uDate = (uLong)(ulDosDate>>16); 1.451 + ptm->tm_mday = (uInt)(uDate&0x1f) ; 1.452 + ptm->tm_mon = (uInt)((((uDate)&0x1E0)/0x20)-1) ; 1.453 + ptm->tm_year = (uInt)(((uDate&0x0FE00)/0x0200)+1980) ; 1.454 + 1.455 + ptm->tm_hour = (uInt) ((ulDosDate &0xF800)/0x800); 1.456 + ptm->tm_min = (uInt) ((ulDosDate&0x7E0)/0x20) ; 1.457 + ptm->tm_sec = (uInt) (2*(ulDosDate&0x1f)) ; 1.458 +} 1.459 + 1.460 +/* 1.461 + Get Info about the current file in the zipfile, with internal only info 1.462 + */ 1.463 +local int unzlocal_GetCurrentFileInfoInternal OF((unzFile file, 1.464 + unz_file_info *pfile_info, 1.465 + unz_file_info_internal 1.466 + *pfile_info_internal, 1.467 + char *szFileName, 1.468 + uLong fileNameBufferSize, 1.469 + void *extraField, 1.470 + uLong extraFieldBufferSize, 1.471 + char *szComment, 1.472 + uLong commentBufferSize)); 1.473 + 1.474 +local int unzlocal_GetCurrentFileInfoInternal(unzFile file, 1.475 + unz_file_info *pfile_info, 1.476 + unz_file_info_internal *pfile_info_internal, 1.477 + char *szFileName, 1.478 + uLong fileNameBufferSize, 1.479 + void *extraField, 1.480 + uLong extraFieldBufferSize, 1.481 + char *szComment, 1.482 + uLong commentBufferSize) 1.483 +{ 1.484 + unz_s* s; 1.485 + unz_file_info file_info; 1.486 + unz_file_info_internal file_info_internal; 1.487 + int err = UNZ_OK; 1.488 + uLong uMagic; 1.489 + long lSeek = 0; 1.490 + 1.491 + if (file == NULL) 1.492 + return UNZ_PARAMERROR; 1.493 + s = (unz_s *)file; 1.494 + if (fseek(s->file, s->pos_in_central_dir+s->byte_before_the_zipfile, SEEK_SET) != 0) 1.495 + err = UNZ_ERRNO; 1.496 + 1.497 + /* we check the magic */ 1.498 + if (err == UNZ_OK) 1.499 + if (unzlocal_getLong(s->file, &uMagic) != UNZ_OK) 1.500 + err = UNZ_ERRNO; 1.501 + else if (uMagic != 0x02014b50) 1.502 + err = UNZ_BADZIPFILE; 1.503 + 1.504 + if (unzlocal_getShort(s->file, &file_info.version) != UNZ_OK) 1.505 + err = UNZ_ERRNO; 1.506 + 1.507 + if (unzlocal_getShort(s->file, &file_info.version_needed) != UNZ_OK) 1.508 + err = UNZ_ERRNO; 1.509 + 1.510 + if (unzlocal_getShort(s->file, &file_info.flag) != UNZ_OK) 1.511 + err = UNZ_ERRNO; 1.512 + 1.513 + if (unzlocal_getShort(s->file, &file_info.compression_method) != UNZ_OK) 1.514 + err = UNZ_ERRNO; 1.515 + 1.516 + if (unzlocal_getLong(s->file, &file_info.dosDate) != UNZ_OK) 1.517 + err = UNZ_ERRNO; 1.518 + 1.519 + unzlocal_DosDateToTmuDate(file_info.dosDate, &file_info.tmu_date); 1.520 + 1.521 + if (unzlocal_getLong(s->file, &file_info.crc) != UNZ_OK) 1.522 + err = UNZ_ERRNO; 1.523 + 1.524 + if (unzlocal_getLong(s->file, &file_info.compressed_size) != UNZ_OK) 1.525 + err = UNZ_ERRNO; 1.526 + 1.527 + if (unzlocal_getLong(s->file, &file_info.uncompressed_size) != UNZ_OK) 1.528 + err = UNZ_ERRNO; 1.529 + 1.530 + if (unzlocal_getShort(s->file, &file_info.size_filename) != UNZ_OK) 1.531 + err = UNZ_ERRNO; 1.532 + 1.533 + if (unzlocal_getShort(s->file, &file_info.size_file_extra) != UNZ_OK) 1.534 + err = UNZ_ERRNO; 1.535 + 1.536 + if (unzlocal_getShort(s->file, &file_info.size_file_comment) != UNZ_OK) 1.537 + err = UNZ_ERRNO; 1.538 + 1.539 + if (unzlocal_getShort(s->file, &file_info.disk_num_start) != UNZ_OK) 1.540 + err = UNZ_ERRNO; 1.541 + 1.542 + if (unzlocal_getShort(s->file, &file_info.internal_fa) != UNZ_OK) 1.543 + err = UNZ_ERRNO; 1.544 + 1.545 + if (unzlocal_getLong(s->file, &file_info.external_fa) != UNZ_OK) 1.546 + err = UNZ_ERRNO; 1.547 + 1.548 + if (unzlocal_getLong(s->file, &file_info_internal.offset_curfile) != UNZ_OK) 1.549 + err = UNZ_ERRNO; 1.550 + 1.551 + lSeek += file_info.size_filename; 1.552 + if ((err == UNZ_OK) && (szFileName != NULL)) 1.553 + { 1.554 + uLong uSizeRead ; 1.555 + if (file_info.size_filename < fileNameBufferSize) 1.556 + { 1.557 + *(szFileName+file_info.size_filename) = '\0'; 1.558 + uSizeRead = file_info.size_filename; 1.559 + } 1.560 + else 1.561 + uSizeRead = fileNameBufferSize; 1.562 + 1.563 + if ((file_info.size_filename > 0) && (fileNameBufferSize > 0)) 1.564 + if (fread(szFileName, (uInt)uSizeRead, 1, s->file) != 1) 1.565 + err = UNZ_ERRNO; 1.566 + lSeek -= uSizeRead; 1.567 + } 1.568 + 1.569 + if ((err == UNZ_OK) && (extraField != NULL)) 1.570 + { 1.571 + uLong uSizeRead ; 1.572 + if (file_info.size_file_extra < extraFieldBufferSize) 1.573 + uSizeRead = file_info.size_file_extra; 1.574 + else 1.575 + uSizeRead = extraFieldBufferSize; 1.576 + 1.577 + if (lSeek != 0) 1.578 + if (fseek(s->file, lSeek, SEEK_CUR) == 0) 1.579 + lSeek = 0; 1.580 + else 1.581 + err = UNZ_ERRNO; 1.582 + if ((file_info.size_file_extra > 0) && (extraFieldBufferSize > 0)) 1.583 + if (fread(extraField, (uInt)uSizeRead, 1, s->file) != 1) 1.584 + err = UNZ_ERRNO; 1.585 + lSeek += file_info.size_file_extra - uSizeRead; 1.586 + } 1.587 + else 1.588 + lSeek += file_info.size_file_extra; 1.589 + 1.590 + if ((err == UNZ_OK) && (szComment != NULL)) 1.591 + { 1.592 + uLong uSizeRead ; 1.593 + if (file_info.size_file_comment < commentBufferSize) 1.594 + { 1.595 + *(szComment+file_info.size_file_comment) = '\0'; 1.596 + uSizeRead = file_info.size_file_comment; 1.597 + } 1.598 + else 1.599 + uSizeRead = commentBufferSize; 1.600 + 1.601 + if (lSeek != 0) 1.602 + if (fseek(s->file, lSeek, SEEK_CUR) == 0) 1.603 + lSeek = 0; 1.604 + else 1.605 + err = UNZ_ERRNO; 1.606 + if ((file_info.size_file_comment > 0) && (commentBufferSize > 0)) 1.607 + if (fread(szComment, (uInt)uSizeRead, 1, s->file) != 1) 1.608 + err = UNZ_ERRNO; 1.609 + lSeek += file_info.size_file_comment - uSizeRead; 1.610 + } 1.611 + else 1.612 + lSeek += file_info.size_file_comment; 1.613 + 1.614 + if ((err == UNZ_OK) && (pfile_info != NULL)) 1.615 + *pfile_info = file_info; 1.616 + 1.617 + if ((err == UNZ_OK) && (pfile_info_internal != NULL)) 1.618 + *pfile_info_internal = file_info_internal; 1.619 + 1.620 + return err; 1.621 +} 1.622 + 1.623 +/* 1.624 + Write info about the ZipFile in the *pglobal_info structure. 1.625 + No preparation of the structure is needed 1.626 + return UNZ_OK if there is no problem. 1.627 + */ 1.628 +extern int ZEXPORT unzGetCurrentFileInfo(unzFile file, 1.629 + unz_file_info *pfile_info, 1.630 + char *szFileName, 1.631 + uLong fileNameBufferSize, 1.632 + void *extraField, 1.633 + uLong extraFieldBufferSize, 1.634 + char *szComment, 1.635 + uLong commentBufferSize) 1.636 +{ 1.637 + return unzlocal_GetCurrentFileInfoInternal(file, pfile_info, NULL, 1.638 + szFileName, fileNameBufferSize, 1.639 + extraField, extraFieldBufferSize, 1.640 + szComment, commentBufferSize); 1.641 +} 1.642 + 1.643 +/* 1.644 + Set the current file of the zipfile to the first file. 1.645 + return UNZ_OK if there is no problem 1.646 + */ 1.647 +extern int ZEXPORT unzGoToFirstFile(unzFile file) 1.648 +{ 1.649 + int err = UNZ_OK; 1.650 + unz_s*s; 1.651 + if (file == NULL) 1.652 + return UNZ_PARAMERROR; 1.653 + s = (unz_s *)file; 1.654 + s->pos_in_central_dir = s->offset_central_dir; 1.655 + s->num_file = 0; 1.656 + err = unzlocal_GetCurrentFileInfoInternal(file, &s->cur_file_info, 1.657 + &s->cur_file_info_internal, 1.658 + NULL, 0, NULL, 0, NULL, 0); 1.659 + s->current_file_ok = (err == UNZ_OK); 1.660 + return err; 1.661 +} 1.662 + 1.663 +/* 1.664 + Set the current file of the zipfile to the next file. 1.665 + return UNZ_OK if there is no problem 1.666 + return UNZ_END_OF_LIST_OF_FILE if the actual file was the latest. 1.667 + */ 1.668 +extern int ZEXPORT unzGoToNextFile(unzFile file) 1.669 +{ 1.670 + unz_s*s; 1.671 + int err; 1.672 + 1.673 + if (file == NULL) 1.674 + return UNZ_PARAMERROR; 1.675 + s = (unz_s *)file; 1.676 + if (!s->current_file_ok) 1.677 + return UNZ_END_OF_LIST_OF_FILE; 1.678 + if (s->num_file+1 == s->gi.number_entry) 1.679 + return UNZ_END_OF_LIST_OF_FILE; 1.680 + 1.681 + s->pos_in_central_dir += SIZECENTRALDIRITEM + s->cur_file_info.size_filename + 1.682 + s->cur_file_info.size_file_extra + s->cur_file_info.size_file_comment ; 1.683 + s->num_file++; 1.684 + err = unzlocal_GetCurrentFileInfoInternal(file, &s->cur_file_info, 1.685 + &s->cur_file_info_internal, 1.686 + NULL, 0, NULL, 0, NULL, 0); 1.687 + s->current_file_ok = (err == UNZ_OK); 1.688 + return err; 1.689 +} 1.690 + 1.691 +/* 1.692 + Try locate the file szFileName in the zipfile. 1.693 + For the iCaseSensitivity signification, see unzipStringFileNameCompare 1.694 + 1.695 + return value : 1.696 + UNZ_OK if the file is found. It becomes the current file. 1.697 + UNZ_END_OF_LIST_OF_FILE if the file is not found 1.698 + */ 1.699 +extern int ZEXPORT unzLocateFile(unzFile file, 1.700 + const char *szFileName, 1.701 + int iCaseSensitivity) 1.702 +{ 1.703 + unz_s*s; 1.704 + int err; 1.705 + 1.706 + uLong num_fileSaved; 1.707 + uLong pos_in_central_dirSaved; 1.708 + 1.709 + if (file == NULL) 1.710 + return UNZ_PARAMERROR; 1.711 + 1.712 + if (strlen(szFileName) >= UNZ_MAXFILENAMEINZIP) 1.713 + return UNZ_PARAMERROR; 1.714 + 1.715 + s = (unz_s *)file; 1.716 + if (!s->current_file_ok) 1.717 + return UNZ_END_OF_LIST_OF_FILE; 1.718 + 1.719 + num_fileSaved = s->num_file; 1.720 + pos_in_central_dirSaved = s->pos_in_central_dir; 1.721 + 1.722 + err = unzGoToFirstFile(file); 1.723 + 1.724 + while (err == UNZ_OK) 1.725 + { 1.726 + char szCurrentFileName[UNZ_MAXFILENAMEINZIP+1]; 1.727 + unzGetCurrentFileInfo(file, NULL, 1.728 + szCurrentFileName, sizeof(szCurrentFileName)-1, 1.729 + NULL, 0, NULL, 0); 1.730 + if (unzStringFileNameCompare(szCurrentFileName, 1.731 + szFileName, iCaseSensitivity) == 0) 1.732 + return UNZ_OK; 1.733 + err = unzGoToNextFile(file); 1.734 + } 1.735 + 1.736 + s->num_file = num_fileSaved ; 1.737 + s->pos_in_central_dir = pos_in_central_dirSaved ; 1.738 + return err; 1.739 +} 1.740 + 1.741 +/* 1.742 + Read the local header of the current zipfile 1.743 + Check the coherency of the local header and info in the end of central 1.744 + directory about this file 1.745 + store in *piSizeVar the size of extra info in local header 1.746 + (filename and size of extra field data) 1.747 + */ 1.748 +local int unzlocal_CheckCurrentFileCoherencyHeader(unz_s *s, 1.749 + uInt *piSizeVar, 1.750 + uLong *poffset_local_extrafield, 1.751 + uInt *psize_local_extrafield) 1.752 +{ 1.753 + uLong uMagic, uData, uFlags; 1.754 + uLong size_filename; 1.755 + uLong size_extra_field; 1.756 + int err = UNZ_OK; 1.757 + 1.758 + *piSizeVar = 0; 1.759 + *poffset_local_extrafield = 0; 1.760 + *psize_local_extrafield = 0; 1.761 + 1.762 + if (fseek(s->file, s->cur_file_info_internal.offset_curfile + 1.763 + s->byte_before_the_zipfile, SEEK_SET) != 0) 1.764 + return UNZ_ERRNO; 1.765 + 1.766 + if (err == UNZ_OK) 1.767 + if (unzlocal_getLong(s->file, &uMagic) != UNZ_OK) 1.768 + err = UNZ_ERRNO; 1.769 + else if (uMagic != 0x04034b50) 1.770 + err = UNZ_BADZIPFILE; 1.771 + 1.772 + if (unzlocal_getShort(s->file, &uData) != UNZ_OK) 1.773 + err = UNZ_ERRNO; 1.774 +/* 1.775 + else if ((err==UNZ_OK) && (uData!=s->cur_file_info.wVersion)) 1.776 + err=UNZ_BADZIPFILE; 1.777 + */ 1.778 + if (unzlocal_getShort(s->file, &uFlags) != UNZ_OK) 1.779 + err = UNZ_ERRNO; 1.780 + 1.781 + if (unzlocal_getShort(s->file, &uData) != UNZ_OK) 1.782 + err = UNZ_ERRNO; 1.783 + else if ((err == UNZ_OK) && (uData != s->cur_file_info.compression_method)) 1.784 + err = UNZ_BADZIPFILE; 1.785 + 1.786 + if ((err == UNZ_OK) && (s->cur_file_info.compression_method != 0) && 1.787 + (s->cur_file_info.compression_method != Z_DEFLATED)) 1.788 + err = UNZ_BADZIPFILE; 1.789 + 1.790 + if (unzlocal_getLong(s->file, &uData) != UNZ_OK) /* date/time */ 1.791 + err = UNZ_ERRNO; 1.792 + 1.793 + if (unzlocal_getLong(s->file, &uData) != UNZ_OK) /* crc */ 1.794 + err = UNZ_ERRNO; 1.795 + else if ((err == UNZ_OK) && (uData != s->cur_file_info.crc) && 1.796 + ((uFlags & 8) == 0)) 1.797 + err = UNZ_BADZIPFILE; 1.798 + 1.799 + if (unzlocal_getLong(s->file, &uData) != UNZ_OK) /* size compr */ 1.800 + err = UNZ_ERRNO; 1.801 + else if ((err == UNZ_OK) && (uData != s->cur_file_info.compressed_size) && 1.802 + ((uFlags & 8) == 0)) 1.803 + err = UNZ_BADZIPFILE; 1.804 + 1.805 + if (unzlocal_getLong(s->file, &uData) != UNZ_OK) /* size uncompr */ 1.806 + err = UNZ_ERRNO; 1.807 + else if ((err == UNZ_OK) && (uData != s->cur_file_info.uncompressed_size) && 1.808 + ((uFlags & 8) == 0)) 1.809 + err = UNZ_BADZIPFILE; 1.810 + 1.811 + if (unzlocal_getShort(s->file, &size_filename) != UNZ_OK) 1.812 + err = UNZ_ERRNO; 1.813 + else if ((err == UNZ_OK) && (size_filename != s->cur_file_info.size_filename)) 1.814 + err = UNZ_BADZIPFILE; 1.815 + 1.816 + *piSizeVar += (uInt)size_filename; 1.817 + 1.818 + if (unzlocal_getShort(s->file, &size_extra_field) != UNZ_OK) 1.819 + err = UNZ_ERRNO; 1.820 + *poffset_local_extrafield = s->cur_file_info_internal.offset_curfile + 1.821 + SIZEZIPLOCALHEADER + size_filename; 1.822 + *psize_local_extrafield = (uInt)size_extra_field; 1.823 + 1.824 + *piSizeVar += (uInt)size_extra_field; 1.825 + 1.826 + return err; 1.827 +} 1.828 + 1.829 +/* 1.830 + Open for reading data the current file in the zipfile. 1.831 + If there is no error and the file is opened, the return value is UNZ_OK. 1.832 + */ 1.833 +extern int ZEXPORT unzOpenCurrentFile(unzFile file) 1.834 +{ 1.835 + int err = UNZ_OK; 1.836 + int Store; 1.837 + uInt iSizeVar; 1.838 + unz_s*s; 1.839 + file_in_zip_read_info_s*pfile_in_zip_read_info; 1.840 + uLong offset_local_extrafield; /* offset of the local extra field */ 1.841 + uInt size_local_extrafield; /* size of the local extra field */ 1.842 + 1.843 + if (file == NULL) 1.844 + return UNZ_PARAMERROR; 1.845 + s = (unz_s *)file; 1.846 + if (!s->current_file_ok) 1.847 + return UNZ_PARAMERROR; 1.848 + 1.849 + if (s->pfile_in_zip_read != NULL) 1.850 + unzCloseCurrentFile(file); 1.851 + 1.852 + if (unzlocal_CheckCurrentFileCoherencyHeader(s, &iSizeVar, 1.853 + &offset_local_extrafield, &size_local_extrafield) != UNZ_OK) 1.854 + return UNZ_BADZIPFILE; 1.855 + 1.856 + pfile_in_zip_read_info = (file_in_zip_read_info_s *) 1.857 + ALLOC(sizeof(file_in_zip_read_info_s)); 1.858 + if (pfile_in_zip_read_info == NULL) 1.859 + return UNZ_INTERNALERROR; 1.860 + 1.861 + pfile_in_zip_read_info->read_buffer = (char *)ALLOC(UNZ_BUFSIZE); 1.862 + pfile_in_zip_read_info->offset_local_extrafield = offset_local_extrafield; 1.863 + pfile_in_zip_read_info->size_local_extrafield = size_local_extrafield; 1.864 + pfile_in_zip_read_info->pos_local_extrafield = 0; 1.865 + 1.866 + if (pfile_in_zip_read_info->read_buffer == NULL) 1.867 + { 1.868 + TRYFREE(pfile_in_zip_read_info); 1.869 + return UNZ_INTERNALERROR; 1.870 + } 1.871 + 1.872 + pfile_in_zip_read_info->stream_initialised = 0; 1.873 + 1.874 + if ((s->cur_file_info.compression_method != 0) && 1.875 + (s->cur_file_info.compression_method != Z_DEFLATED)) 1.876 + err = UNZ_BADZIPFILE; 1.877 + Store = s->cur_file_info.compression_method == 0; 1.878 + 1.879 + pfile_in_zip_read_info->crc32_wait = s->cur_file_info.crc; 1.880 + pfile_in_zip_read_info->crc32 = 0; 1.881 + pfile_in_zip_read_info->compression_method = 1.882 + s->cur_file_info.compression_method; 1.883 + pfile_in_zip_read_info->file = s->file; 1.884 + pfile_in_zip_read_info->byte_before_the_zipfile = s->byte_before_the_zipfile; 1.885 + 1.886 + pfile_in_zip_read_info->stream.total_out = 0; 1.887 + 1.888 + if (!Store) 1.889 + { 1.890 + pfile_in_zip_read_info->stream.zalloc = (alloc_func)0; 1.891 + pfile_in_zip_read_info->stream.zfree = (free_func)0; 1.892 + pfile_in_zip_read_info->stream.opaque = (voidpf)0; 1.893 + 1.894 + err = inflateInit2(&pfile_in_zip_read_info->stream, -MAX_WBITS); 1.895 + if (err == Z_OK) 1.896 + pfile_in_zip_read_info->stream_initialised = 1; 1.897 + /* windowBits is passed < 0 to tell that there is no zlib header. 1.898 + * Note that in this case inflate *requires* an extra "dummy" byte 1.899 + * after the compressed stream in order to complete decompression and 1.900 + * return Z_STREAM_END. 1.901 + * In unzip, i don't wait absolutely Z_STREAM_END because I known the 1.902 + * size of both compressed and uncompressed data 1.903 + */ 1.904 + } 1.905 + pfile_in_zip_read_info->rest_read_compressed = 1.906 + s->cur_file_info.compressed_size ; 1.907 + pfile_in_zip_read_info->rest_read_uncompressed = 1.908 + s->cur_file_info.uncompressed_size ; 1.909 + 1.910 + pfile_in_zip_read_info->pos_in_zipfile = 1.911 + s->cur_file_info_internal.offset_curfile + SIZEZIPLOCALHEADER + 1.912 + iSizeVar; 1.913 + 1.914 + pfile_in_zip_read_info->stream.avail_in = (uInt)0; 1.915 + 1.916 + s->pfile_in_zip_read = pfile_in_zip_read_info; 1.917 + return UNZ_OK; 1.918 +} 1.919 + 1.920 +/* 1.921 + Read bytes from the current file. 1.922 + buf contain buffer where data must be copied 1.923 + len the size of buf. 1.924 + 1.925 + return the number of byte copied if somes bytes are copied 1.926 + return 0 if the end of file was reached 1.927 + return <0 with error code if there is an error 1.928 + (UNZ_ERRNO for IO error, or zLib error for uncompress error) 1.929 + */ 1.930 +extern int ZEXPORT unzReadCurrentFile(unzFile file, voidp buf, unsigned len) 1.931 +{ 1.932 + int err = UNZ_OK; 1.933 + uInt iRead = 0; 1.934 + unz_s*s; 1.935 + file_in_zip_read_info_s*pfile_in_zip_read_info; 1.936 + if (file == NULL) 1.937 + return UNZ_PARAMERROR; 1.938 + s = (unz_s *)file; 1.939 + pfile_in_zip_read_info = s->pfile_in_zip_read; 1.940 + 1.941 + if (pfile_in_zip_read_info == NULL) 1.942 + return UNZ_PARAMERROR; 1.943 + 1.944 + if ((pfile_in_zip_read_info->read_buffer == NULL)) 1.945 + return UNZ_END_OF_LIST_OF_FILE; 1.946 + if (len == 0) 1.947 + return 0; 1.948 + 1.949 + pfile_in_zip_read_info->stream.next_out = (Bytef *)buf; 1.950 + 1.951 + pfile_in_zip_read_info->stream.avail_out = (uInt)len; 1.952 + 1.953 + if (len > pfile_in_zip_read_info->rest_read_uncompressed) 1.954 + pfile_in_zip_read_info->stream.avail_out = 1.955 + (uInt)pfile_in_zip_read_info->rest_read_uncompressed; 1.956 + 1.957 + while (pfile_in_zip_read_info->stream.avail_out > 0) 1.958 + { 1.959 + if ((pfile_in_zip_read_info->stream.avail_in == 0) && 1.960 + (pfile_in_zip_read_info->rest_read_compressed > 0)) 1.961 + { 1.962 + uInt uReadThis = UNZ_BUFSIZE; 1.963 + if (pfile_in_zip_read_info->rest_read_compressed < uReadThis) 1.964 + uReadThis = (uInt)pfile_in_zip_read_info->rest_read_compressed; 1.965 + if (uReadThis == 0) 1.966 + return UNZ_EOF; 1.967 + if (fseek(pfile_in_zip_read_info->file, 1.968 + pfile_in_zip_read_info->pos_in_zipfile + 1.969 + pfile_in_zip_read_info->byte_before_the_zipfile, SEEK_SET) != 0) 1.970 + return UNZ_ERRNO; 1.971 + if (fread(pfile_in_zip_read_info->read_buffer, uReadThis, 1, 1.972 + pfile_in_zip_read_info->file) != 1) 1.973 + return UNZ_ERRNO; 1.974 + pfile_in_zip_read_info->pos_in_zipfile += uReadThis; 1.975 + 1.976 + pfile_in_zip_read_info->rest_read_compressed -= uReadThis; 1.977 + 1.978 + pfile_in_zip_read_info->stream.next_in = 1.979 + (Bytef *)pfile_in_zip_read_info->read_buffer; 1.980 + pfile_in_zip_read_info->stream.avail_in = (uInt)uReadThis; 1.981 + } 1.982 + 1.983 + if (pfile_in_zip_read_info->compression_method == 0) 1.984 + { 1.985 + uInt uDoCopy, i ; 1.986 + if (pfile_in_zip_read_info->stream.avail_out < 1.987 + pfile_in_zip_read_info->stream.avail_in) 1.988 + uDoCopy = pfile_in_zip_read_info->stream.avail_out ; 1.989 + else 1.990 + uDoCopy = pfile_in_zip_read_info->stream.avail_in ; 1.991 + 1.992 + for (i = 0; i < uDoCopy; i++) 1.993 + *(pfile_in_zip_read_info->stream.next_out+i) = 1.994 + *(pfile_in_zip_read_info->stream.next_in+i); 1.995 + 1.996 + pfile_in_zip_read_info->crc32 = crc32(pfile_in_zip_read_info->crc32, 1.997 + pfile_in_zip_read_info->stream.next_out, 1.998 + uDoCopy); 1.999 + pfile_in_zip_read_info->rest_read_uncompressed -= uDoCopy; 1.1000 + pfile_in_zip_read_info->stream.avail_in -= uDoCopy; 1.1001 + pfile_in_zip_read_info->stream.avail_out -= uDoCopy; 1.1002 + pfile_in_zip_read_info->stream.next_out += uDoCopy; 1.1003 + pfile_in_zip_read_info->stream.next_in += uDoCopy; 1.1004 + pfile_in_zip_read_info->stream.total_out += uDoCopy; 1.1005 + iRead += uDoCopy; 1.1006 + } 1.1007 + else 1.1008 + { 1.1009 + uLong uTotalOutBefore, uTotalOutAfter; 1.1010 + const Bytef *bufBefore; 1.1011 + uLong uOutThis; 1.1012 + int flush = Z_SYNC_FLUSH; 1.1013 + 1.1014 + uTotalOutBefore = pfile_in_zip_read_info->stream.total_out; 1.1015 + bufBefore = pfile_in_zip_read_info->stream.next_out; 1.1016 + 1.1017 + /* 1.1018 + if ((pfile_in_zip_read_info->rest_read_uncompressed == 1.1019 + pfile_in_zip_read_info->stream.avail_out) && 1.1020 + (pfile_in_zip_read_info->rest_read_compressed == 0)) 1.1021 + flush = Z_FINISH; 1.1022 + */ 1.1023 + err = inflate(&pfile_in_zip_read_info->stream, flush); 1.1024 + 1.1025 + uTotalOutAfter = pfile_in_zip_read_info->stream.total_out; 1.1026 + uOutThis = uTotalOutAfter-uTotalOutBefore; 1.1027 + 1.1028 + pfile_in_zip_read_info->crc32 = 1.1029 + crc32(pfile_in_zip_read_info->crc32, bufBefore, 1.1030 + (uInt)(uOutThis)); 1.1031 + 1.1032 + pfile_in_zip_read_info->rest_read_uncompressed -= 1.1033 + uOutThis; 1.1034 + 1.1035 + iRead += (uInt)(uTotalOutAfter - uTotalOutBefore); 1.1036 + 1.1037 + if (err == Z_STREAM_END) 1.1038 + return (iRead == 0) ? UNZ_EOF : iRead; 1.1039 + if (err != Z_OK) 1.1040 + break; 1.1041 + } 1.1042 + } 1.1043 + 1.1044 + if (err == Z_OK) 1.1045 + return iRead; 1.1046 + return err; 1.1047 +} 1.1048 + 1.1049 +/* 1.1050 + Give the current position in uncompressed data 1.1051 + */ 1.1052 +extern z_off_t ZEXPORT unztell(unzFile file) 1.1053 +{ 1.1054 + unz_s*s; 1.1055 + file_in_zip_read_info_s*pfile_in_zip_read_info; 1.1056 + if (file == NULL) 1.1057 + return UNZ_PARAMERROR; 1.1058 + s = (unz_s *)file; 1.1059 + pfile_in_zip_read_info = s->pfile_in_zip_read; 1.1060 + 1.1061 + if (pfile_in_zip_read_info == NULL) 1.1062 + return UNZ_PARAMERROR; 1.1063 + 1.1064 + return (z_off_t)pfile_in_zip_read_info->stream.total_out; 1.1065 +} 1.1066 + 1.1067 +/* 1.1068 + return 1 if the end of file was reached, 0 elsewhere 1.1069 + */ 1.1070 +extern int ZEXPORT unzeof(unzFile file) 1.1071 +{ 1.1072 + unz_s*s; 1.1073 + file_in_zip_read_info_s*pfile_in_zip_read_info; 1.1074 + if (file == NULL) 1.1075 + return UNZ_PARAMERROR; 1.1076 + s = (unz_s *)file; 1.1077 + pfile_in_zip_read_info = s->pfile_in_zip_read; 1.1078 + 1.1079 + if (pfile_in_zip_read_info == NULL) 1.1080 + return UNZ_PARAMERROR; 1.1081 + 1.1082 + if (pfile_in_zip_read_info->rest_read_uncompressed == 0) 1.1083 + return 1; 1.1084 + else 1.1085 + return 0; 1.1086 +} 1.1087 + 1.1088 +/* 1.1089 + Read extra field from the current file (opened by unzOpenCurrentFile) 1.1090 + This is the local-header version of the extra field (sometimes, there is 1.1091 + more info in the local-header version than in the central-header) 1.1092 + 1.1093 + if buf==NULL, it return the size of the local extra field that can be read 1.1094 + 1.1095 + if buf!=NULL, len is the size of the buffer, the extra header is copied in 1.1096 + buf. 1.1097 + the return value is the number of bytes copied in buf, or (if <0) 1.1098 + the error code 1.1099 + */ 1.1100 +extern int ZEXPORT unzGetLocalExtrafield(unzFile file, voidp buf, unsigned len) 1.1101 +{ 1.1102 + unz_s*s; 1.1103 + file_in_zip_read_info_s*pfile_in_zip_read_info; 1.1104 + uInt read_now; 1.1105 + uLong size_to_read; 1.1106 + 1.1107 + if (file == NULL) 1.1108 + return UNZ_PARAMERROR; 1.1109 + s = (unz_s *)file; 1.1110 + pfile_in_zip_read_info = s->pfile_in_zip_read; 1.1111 + 1.1112 + if (pfile_in_zip_read_info == NULL) 1.1113 + return UNZ_PARAMERROR; 1.1114 + 1.1115 + size_to_read = (pfile_in_zip_read_info->size_local_extrafield - 1.1116 + pfile_in_zip_read_info->pos_local_extrafield); 1.1117 + 1.1118 + if (buf == NULL) 1.1119 + return (int)size_to_read; 1.1120 + 1.1121 + if (len > size_to_read) 1.1122 + read_now = (uInt)size_to_read; 1.1123 + else 1.1124 + read_now = (uInt)len ; 1.1125 + 1.1126 + if (read_now == 0) 1.1127 + return 0; 1.1128 + 1.1129 + if (fseek(pfile_in_zip_read_info->file, 1.1130 + pfile_in_zip_read_info->offset_local_extrafield + 1.1131 + pfile_in_zip_read_info->pos_local_extrafield, SEEK_SET) != 0) 1.1132 + return UNZ_ERRNO; 1.1133 + 1.1134 + if (fread(buf, (uInt)size_to_read, 1, pfile_in_zip_read_info->file) != 1) 1.1135 + return UNZ_ERRNO; 1.1136 + 1.1137 + return (int)read_now; 1.1138 +} 1.1139 + 1.1140 +/* 1.1141 + Close the file in zip opened with unzipOpenCurrentFile 1.1142 + Return UNZ_CRCERROR if all the file was read but the CRC is not good 1.1143 + */ 1.1144 +extern int ZEXPORT unzCloseCurrentFile(unzFile file) 1.1145 +{ 1.1146 + int err = UNZ_OK; 1.1147 + 1.1148 + unz_s*s; 1.1149 + file_in_zip_read_info_s*pfile_in_zip_read_info; 1.1150 + if (file == NULL) 1.1151 + return UNZ_PARAMERROR; 1.1152 + s = (unz_s *)file; 1.1153 + pfile_in_zip_read_info = s->pfile_in_zip_read; 1.1154 + 1.1155 + if (pfile_in_zip_read_info == NULL) 1.1156 + return UNZ_PARAMERROR; 1.1157 + 1.1158 + if (pfile_in_zip_read_info->rest_read_uncompressed == 0) 1.1159 + { 1.1160 + if (pfile_in_zip_read_info->crc32 != pfile_in_zip_read_info->crc32_wait) 1.1161 + err = UNZ_CRCERROR; 1.1162 + } 1.1163 + 1.1164 + TRYFREE(pfile_in_zip_read_info->read_buffer); 1.1165 + pfile_in_zip_read_info->read_buffer = NULL; 1.1166 + if (pfile_in_zip_read_info->stream_initialised) 1.1167 + inflateEnd(&pfile_in_zip_read_info->stream); 1.1168 + 1.1169 + pfile_in_zip_read_info->stream_initialised = 0; 1.1170 + TRYFREE(pfile_in_zip_read_info); 1.1171 + 1.1172 + s->pfile_in_zip_read = NULL; 1.1173 + 1.1174 + return err; 1.1175 +} 1.1176 + 1.1177 +/* 1.1178 + Get the global comment string of the ZipFile, in the szComment buffer. 1.1179 + uSizeBuf is the size of the szComment buffer. 1.1180 + return the number of byte copied or an error code <0 1.1181 + */ 1.1182 +extern int ZEXPORT unzGetGlobalComment(unzFile file, 1.1183 + char *szComment, 1.1184 + uLong uSizeBuf) 1.1185 +{ 1.1186 + //int err=UNZ_OK; 1.1187 + unz_s*s; 1.1188 + uLong uReadThis ; 1.1189 + if (file == NULL) 1.1190 + return UNZ_PARAMERROR; 1.1191 + s = (unz_s *)file; 1.1192 + 1.1193 + uReadThis = uSizeBuf; 1.1194 + if (uReadThis > s->gi.size_comment) 1.1195 + uReadThis = s->gi.size_comment; 1.1196 + 1.1197 + if (fseek(s->file, s->central_pos+22, SEEK_SET) != 0) 1.1198 + return UNZ_ERRNO; 1.1199 + 1.1200 + if (uReadThis > 0) 1.1201 + { 1.1202 + *szComment = '\0'; 1.1203 + if (fread(szComment, (uInt)uReadThis, 1, s->file) != 1) 1.1204 + return UNZ_ERRNO; 1.1205 + } 1.1206 + 1.1207 + if ((szComment != NULL) && (uSizeBuf > s->gi.size_comment)) 1.1208 + *(szComment+s->gi.size_comment) = '\0'; 1.1209 + return (int)uReadThis; 1.1210 +} 1.1211 +