diff options
author | Mark Adler <madler@alumni.caltech.edu> | 2011-09-09 23:24:43 -0700 |
---|---|---|
committer | Mark Adler <madler@alumni.caltech.edu> | 2011-09-09 23:24:43 -0700 |
commit | 6b8233bfe00e79134cb1b84fc49d4f750a797f79 (patch) | |
tree | ca2b03b0169568681dc3d9c823e9f0bc4417d6b5 /contrib/minizip/mztools.c | |
parent | 0484693e1723bbab791c56f95597bd7dbe867d03 (diff) | |
download | zlib-1.2.2.3.tar.gz zlib-1.2.2.3.tar.bz2 zlib-1.2.2.3.zip |
zlib 1.2.2.3v1.2.2.3
Diffstat (limited to 'contrib/minizip/mztools.c')
-rw-r--r-- | contrib/minizip/mztools.c | 562 |
1 files changed, 281 insertions, 281 deletions
diff --git a/contrib/minizip/mztools.c b/contrib/minizip/mztools.c index c1266bc..bc5c798 100644 --- a/contrib/minizip/mztools.c +++ b/contrib/minizip/mztools.c | |||
@@ -1,281 +1,281 @@ | |||
1 | /* | 1 | /* |
2 | Additional tools for Minizip | 2 | Additional tools for Minizip |
3 | Code: Xavier Roche '2004 | 3 | Code: Xavier Roche '2004 |
4 | License: Same as ZLIB (www.gzip.org) | 4 | License: Same as ZLIB (www.gzip.org) |
5 | */ | 5 | */ |
6 | 6 | ||
7 | /* Code */ | 7 | /* Code */ |
8 | #include <stdio.h> | 8 | #include <stdio.h> |
9 | #include <stdlib.h> | 9 | #include <stdlib.h> |
10 | #include <string.h> | 10 | #include <string.h> |
11 | #include "zlib.h" | 11 | #include "zlib.h" |
12 | #include "unzip.h" | 12 | #include "unzip.h" |
13 | 13 | ||
14 | #define READ_8(adr) ((unsigned char)*(adr)) | 14 | #define READ_8(adr) ((unsigned char)*(adr)) |
15 | #define READ_16(adr) ( READ_8(adr) | (READ_8(adr+1) << 8) ) | 15 | #define READ_16(adr) ( READ_8(adr) | (READ_8(adr+1) << 8) ) |
16 | #define READ_32(adr) ( READ_16(adr) | (READ_16((adr)+2) << 16) ) | 16 | #define READ_32(adr) ( READ_16(adr) | (READ_16((adr)+2) << 16) ) |
17 | 17 | ||
18 | #define WRITE_8(buff, n) do { \ | 18 | #define WRITE_8(buff, n) do { \ |
19 | *((unsigned char*)(buff)) = (unsigned char) ((n) & 0xff); \ | 19 | *((unsigned char*)(buff)) = (unsigned char) ((n) & 0xff); \ |
20 | } while(0) | 20 | } while(0) |
21 | #define WRITE_16(buff, n) do { \ | 21 | #define WRITE_16(buff, n) do { \ |
22 | WRITE_8((unsigned char*)(buff), n); \ | 22 | WRITE_8((unsigned char*)(buff), n); \ |
23 | WRITE_8(((unsigned char*)(buff)) + 1, (n) >> 8); \ | 23 | WRITE_8(((unsigned char*)(buff)) + 1, (n) >> 8); \ |
24 | } while(0) | 24 | } while(0) |
25 | #define WRITE_32(buff, n) do { \ | 25 | #define WRITE_32(buff, n) do { \ |
26 | WRITE_16((unsigned char*)(buff), (n) & 0xffff); \ | 26 | WRITE_16((unsigned char*)(buff), (n) & 0xffff); \ |
27 | WRITE_16((unsigned char*)(buff) + 2, (n) >> 16); \ | 27 | WRITE_16((unsigned char*)(buff) + 2, (n) >> 16); \ |
28 | } while(0) | 28 | } while(0) |
29 | 29 | ||
30 | extern int ZEXPORT unzRepair(file, fileOut, fileOutTmp, nRecovered, bytesRecovered) | 30 | extern int ZEXPORT unzRepair(file, fileOut, fileOutTmp, nRecovered, bytesRecovered) |
31 | const char* file; | 31 | const char* file; |
32 | const char* fileOut; | 32 | const char* fileOut; |
33 | const char* fileOutTmp; | 33 | const char* fileOutTmp; |
34 | uLong* nRecovered; | 34 | uLong* nRecovered; |
35 | uLong* bytesRecovered; | 35 | uLong* bytesRecovered; |
36 | { | 36 | { |
37 | int err = Z_OK; | 37 | int err = Z_OK; |
38 | FILE* fpZip = fopen(file, "rb"); | 38 | FILE* fpZip = fopen(file, "rb"); |
39 | FILE* fpOut = fopen(fileOut, "wb"); | 39 | FILE* fpOut = fopen(fileOut, "wb"); |
40 | FILE* fpOutCD = fopen(fileOutTmp, "wb"); | 40 | FILE* fpOutCD = fopen(fileOutTmp, "wb"); |
41 | if (fpZip != NULL && fpOut != NULL) { | 41 | if (fpZip != NULL && fpOut != NULL) { |
42 | int entries = 0; | 42 | int entries = 0; |
43 | uLong totalBytes = 0; | 43 | uLong totalBytes = 0; |
44 | char header[30]; | 44 | char header[30]; |
45 | char filename[256]; | 45 | char filename[256]; |
46 | char extra[1024]; | 46 | char extra[1024]; |
47 | int offset = 0; | 47 | int offset = 0; |
48 | int offsetCD = 0; | 48 | int offsetCD = 0; |
49 | while ( fread(header, 1, 30, fpZip) == 30 ) { | 49 | while ( fread(header, 1, 30, fpZip) == 30 ) { |
50 | int currentOffset = offset; | 50 | int currentOffset = offset; |
51 | 51 | ||
52 | /* File entry */ | 52 | /* File entry */ |
53 | if (READ_32(header) == 0x04034b50) { | 53 | if (READ_32(header) == 0x04034b50) { |
54 | unsigned int version = READ_16(header + 4); | 54 | unsigned int version = READ_16(header + 4); |
55 | unsigned int gpflag = READ_16(header + 6); | 55 | unsigned int gpflag = READ_16(header + 6); |
56 | unsigned int method = READ_16(header + 8); | 56 | unsigned int method = READ_16(header + 8); |
57 | unsigned int filetime = READ_16(header + 10); | 57 | unsigned int filetime = READ_16(header + 10); |
58 | unsigned int filedate = READ_16(header + 12); | 58 | unsigned int filedate = READ_16(header + 12); |
59 | unsigned int crc = READ_32(header + 14); /* crc */ | 59 | unsigned int crc = READ_32(header + 14); /* crc */ |
60 | unsigned int cpsize = READ_32(header + 18); /* compressed size */ | 60 | unsigned int cpsize = READ_32(header + 18); /* compressed size */ |
61 | unsigned int uncpsize = READ_32(header + 22); /* uncompressed sz */ | 61 | unsigned int uncpsize = READ_32(header + 22); /* uncompressed sz */ |
62 | unsigned int fnsize = READ_16(header + 26); /* file name length */ | 62 | unsigned int fnsize = READ_16(header + 26); /* file name length */ |
63 | unsigned int extsize = READ_16(header + 28); /* extra field length */ | 63 | unsigned int extsize = READ_16(header + 28); /* extra field length */ |
64 | filename[0] = extra[0] = '\0'; | 64 | filename[0] = extra[0] = '\0'; |
65 | 65 | ||
66 | /* Header */ | 66 | /* Header */ |
67 | if (fwrite(header, 1, 30, fpOut) == 30) { | 67 | if (fwrite(header, 1, 30, fpOut) == 30) { |
68 | offset += 30; | 68 | offset += 30; |
69 | } else { | 69 | } else { |
70 | err = Z_ERRNO; | 70 | err = Z_ERRNO; |
71 | break; | 71 | break; |
72 | } | 72 | } |
73 | 73 | ||
74 | /* Filename */ | 74 | /* Filename */ |
75 | if (fnsize > 0) { | 75 | if (fnsize > 0) { |
76 | if (fread(filename, 1, fnsize, fpZip) == fnsize) { | 76 | if (fread(filename, 1, fnsize, fpZip) == fnsize) { |
77 | if (fwrite(filename, 1, fnsize, fpOut) == fnsize) { | 77 | if (fwrite(filename, 1, fnsize, fpOut) == fnsize) { |
78 | offset += fnsize; | 78 | offset += fnsize; |
79 | } else { | 79 | } else { |
80 | err = Z_ERRNO; | 80 | err = Z_ERRNO; |
81 | break; | 81 | break; |
82 | } | 82 | } |
83 | } else { | 83 | } else { |
84 | err = Z_ERRNO; | 84 | err = Z_ERRNO; |
85 | break; | 85 | break; |
86 | } | 86 | } |
87 | } else { | 87 | } else { |
88 | err = Z_STREAM_ERROR; | 88 | err = Z_STREAM_ERROR; |
89 | break; | 89 | break; |
90 | } | 90 | } |
91 | 91 | ||
92 | /* Extra field */ | 92 | /* Extra field */ |
93 | if (extsize > 0) { | 93 | if (extsize > 0) { |
94 | if (fread(extra, 1, extsize, fpZip) == extsize) { | 94 | if (fread(extra, 1, extsize, fpZip) == extsize) { |
95 | if (fwrite(extra, 1, extsize, fpOut) == extsize) { | 95 | if (fwrite(extra, 1, extsize, fpOut) == extsize) { |
96 | offset += extsize; | 96 | offset += extsize; |
97 | } else { | 97 | } else { |
98 | err = Z_ERRNO; | 98 | err = Z_ERRNO; |
99 | break; | 99 | break; |
100 | } | 100 | } |
101 | } else { | 101 | } else { |
102 | err = Z_ERRNO; | 102 | err = Z_ERRNO; |
103 | break; | 103 | break; |
104 | } | 104 | } |
105 | } | 105 | } |
106 | 106 | ||
107 | /* Data */ | 107 | /* Data */ |
108 | { | 108 | { |
109 | int dataSize = cpsize; | 109 | int dataSize = cpsize; |
110 | if (dataSize == 0) { | 110 | if (dataSize == 0) { |
111 | dataSize = uncpsize; | 111 | dataSize = uncpsize; |
112 | } | 112 | } |
113 | if (dataSize > 0) { | 113 | if (dataSize > 0) { |
114 | char* data = malloc(dataSize); | 114 | char* data = malloc(dataSize); |
115 | if (data != NULL) { | 115 | if (data != NULL) { |
116 | if ((int)fread(data, 1, dataSize, fpZip) == dataSize) { | 116 | if ((int)fread(data, 1, dataSize, fpZip) == dataSize) { |
117 | if ((int)fwrite(data, 1, dataSize, fpOut) == dataSize) { | 117 | if ((int)fwrite(data, 1, dataSize, fpOut) == dataSize) { |
118 | offset += dataSize; | 118 | offset += dataSize; |
119 | totalBytes += dataSize; | 119 | totalBytes += dataSize; |
120 | } else { | 120 | } else { |
121 | err = Z_ERRNO; | 121 | err = Z_ERRNO; |
122 | } | 122 | } |
123 | } else { | 123 | } else { |
124 | err = Z_ERRNO; | 124 | err = Z_ERRNO; |
125 | } | 125 | } |
126 | free(data); | 126 | free(data); |
127 | if (err != Z_OK) { | 127 | if (err != Z_OK) { |
128 | break; | 128 | break; |
129 | } | 129 | } |
130 | } else { | 130 | } else { |
131 | err = Z_MEM_ERROR; | 131 | err = Z_MEM_ERROR; |
132 | break; | 132 | break; |
133 | } | 133 | } |
134 | } | 134 | } |
135 | } | 135 | } |
136 | 136 | ||
137 | /* Central directory entry */ | 137 | /* Central directory entry */ |
138 | { | 138 | { |
139 | char header[46]; | 139 | char header[46]; |
140 | char* comment = ""; | 140 | char* comment = ""; |
141 | int comsize = (int) strlen(comment); | 141 | int comsize = (int) strlen(comment); |
142 | WRITE_32(header, 0x02014b50); | 142 | WRITE_32(header, 0x02014b50); |
143 | WRITE_16(header + 4, version); | 143 | WRITE_16(header + 4, version); |
144 | WRITE_16(header + 6, version); | 144 | WRITE_16(header + 6, version); |
145 | WRITE_16(header + 8, gpflag); | 145 | WRITE_16(header + 8, gpflag); |
146 | WRITE_16(header + 10, method); | 146 | WRITE_16(header + 10, method); |
147 | WRITE_16(header + 12, filetime); | 147 | WRITE_16(header + 12, filetime); |
148 | WRITE_16(header + 14, filedate); | 148 | WRITE_16(header + 14, filedate); |
149 | WRITE_32(header + 16, crc); | 149 | WRITE_32(header + 16, crc); |
150 | WRITE_32(header + 20, cpsize); | 150 | WRITE_32(header + 20, cpsize); |
151 | WRITE_32(header + 24, uncpsize); | 151 | WRITE_32(header + 24, uncpsize); |
152 | WRITE_16(header + 28, fnsize); | 152 | WRITE_16(header + 28, fnsize); |
153 | WRITE_16(header + 30, extsize); | 153 | WRITE_16(header + 30, extsize); |
154 | WRITE_16(header + 32, comsize); | 154 | WRITE_16(header + 32, comsize); |
155 | WRITE_16(header + 34, 0); /* disk # */ | 155 | WRITE_16(header + 34, 0); /* disk # */ |
156 | WRITE_16(header + 36, 0); /* int attrb */ | 156 | WRITE_16(header + 36, 0); /* int attrb */ |
157 | WRITE_32(header + 38, 0); /* ext attrb */ | 157 | WRITE_32(header + 38, 0); /* ext attrb */ |
158 | WRITE_32(header + 42, currentOffset); | 158 | WRITE_32(header + 42, currentOffset); |
159 | /* Header */ | 159 | /* Header */ |
160 | if (fwrite(header, 1, 46, fpOutCD) == 46) { | 160 | if (fwrite(header, 1, 46, fpOutCD) == 46) { |
161 | offsetCD += 46; | 161 | offsetCD += 46; |
162 | 162 | ||
163 | /* Filename */ | 163 | /* Filename */ |
164 | if (fnsize > 0) { | 164 | if (fnsize > 0) { |
165 | if (fwrite(filename, 1, fnsize, fpOutCD) == fnsize) { | 165 | if (fwrite(filename, 1, fnsize, fpOutCD) == fnsize) { |
166 | offsetCD += fnsize; | 166 | offsetCD += fnsize; |
167 | } else { | 167 | } else { |
168 | err = Z_ERRNO; | 168 | err = Z_ERRNO; |
169 | break; | 169 | break; |
170 | } | 170 | } |
171 | } else { | 171 | } else { |
172 | err = Z_STREAM_ERROR; | 172 | err = Z_STREAM_ERROR; |
173 | break; | 173 | break; |
174 | } | 174 | } |
175 | 175 | ||
176 | /* Extra field */ | 176 | /* Extra field */ |
177 | if (extsize > 0) { | 177 | if (extsize > 0) { |
178 | if (fwrite(extra, 1, extsize, fpOutCD) == extsize) { | 178 | if (fwrite(extra, 1, extsize, fpOutCD) == extsize) { |
179 | offsetCD += extsize; | 179 | offsetCD += extsize; |
180 | } else { | 180 | } else { |
181 | err = Z_ERRNO; | 181 | err = Z_ERRNO; |
182 | break; | 182 | break; |
183 | } | 183 | } |
184 | } | 184 | } |
185 | 185 | ||
186 | /* Comment field */ | 186 | /* Comment field */ |
187 | if (comsize > 0) { | 187 | if (comsize > 0) { |
188 | if ((int)fwrite(comment, 1, comsize, fpOutCD) == comsize) { | 188 | if ((int)fwrite(comment, 1, comsize, fpOutCD) == comsize) { |
189 | offsetCD += comsize; | 189 | offsetCD += comsize; |
190 | } else { | 190 | } else { |
191 | err = Z_ERRNO; | 191 | err = Z_ERRNO; |
192 | break; | 192 | break; |
193 | } | 193 | } |
194 | } | 194 | } |
195 | 195 | ||
196 | 196 | ||
197 | } else { | 197 | } else { |
198 | err = Z_ERRNO; | 198 | err = Z_ERRNO; |
199 | break; | 199 | break; |
200 | } | 200 | } |
201 | } | 201 | } |
202 | 202 | ||
203 | /* Success */ | 203 | /* Success */ |
204 | entries++; | 204 | entries++; |
205 | 205 | ||
206 | } else { | 206 | } else { |
207 | break; | 207 | break; |
208 | } | 208 | } |
209 | } | 209 | } |
210 | 210 | ||
211 | /* Final central directory */ | 211 | /* Final central directory */ |
212 | { | 212 | { |
213 | int entriesZip = entries; | 213 | int entriesZip = entries; |
214 | char header[22]; | 214 | char header[22]; |
215 | char* comment = ""; // "ZIP File recovered by zlib/minizip/mztools"; | 215 | char* comment = ""; // "ZIP File recovered by zlib/minizip/mztools"; |
216 | int comsize = (int) strlen(comment); | 216 | int comsize = (int) strlen(comment); |
217 | if (entriesZip > 0xffff) { | 217 | if (entriesZip > 0xffff) { |
218 | entriesZip = 0xffff; | 218 | entriesZip = 0xffff; |
219 | } | 219 | } |
220 | WRITE_32(header, 0x06054b50); | 220 | WRITE_32(header, 0x06054b50); |
221 | WRITE_16(header + 4, 0); /* disk # */ | 221 | WRITE_16(header + 4, 0); /* disk # */ |
222 | WRITE_16(header + 6, 0); /* disk # */ | 222 | WRITE_16(header + 6, 0); /* disk # */ |
223 | WRITE_16(header + 8, entriesZip); /* hack */ | 223 | WRITE_16(header + 8, entriesZip); /* hack */ |
224 | WRITE_16(header + 10, entriesZip); /* hack */ | 224 | WRITE_16(header + 10, entriesZip); /* hack */ |
225 | WRITE_32(header + 12, offsetCD); /* size of CD */ | 225 | WRITE_32(header + 12, offsetCD); /* size of CD */ |
226 | WRITE_32(header + 16, offset); /* offset to CD */ | 226 | WRITE_32(header + 16, offset); /* offset to CD */ |
227 | WRITE_16(header + 20, comsize); /* comment */ | 227 | WRITE_16(header + 20, comsize); /* comment */ |
228 | 228 | ||
229 | /* Header */ | 229 | /* Header */ |
230 | if (fwrite(header, 1, 22, fpOutCD) == 22) { | 230 | if (fwrite(header, 1, 22, fpOutCD) == 22) { |
231 | 231 | ||
232 | /* Comment field */ | 232 | /* Comment field */ |
233 | if (comsize > 0) { | 233 | if (comsize > 0) { |
234 | if ((int)fwrite(comment, 1, comsize, fpOutCD) != comsize) { | 234 | if ((int)fwrite(comment, 1, comsize, fpOutCD) != comsize) { |
235 | err = Z_ERRNO; | 235 | err = Z_ERRNO; |
236 | } | 236 | } |
237 | } | 237 | } |
238 | 238 | ||
239 | } else { | 239 | } else { |
240 | err = Z_ERRNO; | 240 | err = Z_ERRNO; |
241 | } | 241 | } |
242 | } | 242 | } |
243 | 243 | ||
244 | /* Final merge (file + central directory) */ | 244 | /* Final merge (file + central directory) */ |
245 | fclose(fpOutCD); | 245 | fclose(fpOutCD); |
246 | if (err == Z_OK) { | 246 | if (err == Z_OK) { |
247 | fpOutCD = fopen(fileOutTmp, "rb"); | 247 | fpOutCD = fopen(fileOutTmp, "rb"); |
248 | if (fpOutCD != NULL) { | 248 | if (fpOutCD != NULL) { |
249 | int nRead; | 249 | int nRead; |
250 | char buffer[8192]; | 250 | char buffer[8192]; |
251 | while ( (nRead = fread(buffer, 1, sizeof(buffer), fpOutCD)) > 0) { | 251 | while ( (nRead = (int)fread(buffer, 1, sizeof(buffer), fpOutCD)) > 0) { |
252 | if ((int)fwrite(buffer, 1, nRead, fpOut) != nRead) { | 252 | if ((int)fwrite(buffer, 1, nRead, fpOut) != nRead) { |
253 | err = Z_ERRNO; | 253 | err = Z_ERRNO; |
254 | break; | 254 | break; |
255 | } | 255 | } |
256 | } | 256 | } |
257 | fclose(fpOutCD); | 257 | fclose(fpOutCD); |
258 | } | 258 | } |
259 | } | 259 | } |
260 | 260 | ||
261 | /* Close */ | 261 | /* Close */ |
262 | fclose(fpZip); | 262 | fclose(fpZip); |
263 | fclose(fpOut); | 263 | fclose(fpOut); |
264 | 264 | ||
265 | /* Wipe temporary file */ | 265 | /* Wipe temporary file */ |
266 | (void)remove(fileOutTmp); | 266 | (void)remove(fileOutTmp); |
267 | 267 | ||
268 | /* Number of recovered entries */ | 268 | /* Number of recovered entries */ |
269 | if (err == Z_OK) { | 269 | if (err == Z_OK) { |
270 | if (nRecovered != NULL) { | 270 | if (nRecovered != NULL) { |
271 | *nRecovered = entries; | 271 | *nRecovered = entries; |
272 | } | 272 | } |
273 | if (bytesRecovered != NULL) { | 273 | if (bytesRecovered != NULL) { |
274 | *bytesRecovered = totalBytes; | 274 | *bytesRecovered = totalBytes; |
275 | } | 275 | } |
276 | } | 276 | } |
277 | } else { | 277 | } else { |
278 | err = Z_STREAM_ERROR; | 278 | err = Z_STREAM_ERROR; |
279 | } | 279 | } |
280 | return err; | 280 | return err; |
281 | } | 281 | } |