Details | Last modification | View Log | RSS feed
Rev | Author | Line No. | Line |
---|---|---|---|
1 | daniel-mar | 1 | #include "stdafx.h" |
2 | #pragma hdrstop |
||
3 | |||
4 | #include "ZipOp.h" |
||
5 | #include "dz_errs.h" |
||
6 | |||
7 | #undef _DZ_FILE_ |
||
8 | #define _DZ_FILE_ DZ_ZIPPRC_CPP |
||
9 | |||
10 | /* DLLzip.c * Copyright (C) 1990-1996 Mark Adler, Richard B. Wales, Jean-loup Gailly, |
||
11 | * Kai Uwe Rommel, Onno van der Linden and Igor Mandrichenko. |
||
12 | * This version modified by Chris Vleghert and Eric Engler for BCB/Delphi Zip. |
||
13 | ** distributed under LGPL license |
||
14 | |||
15 | Copyright (c) 1990-2007 Info-ZIP. All rights reserved. |
||
16 | |||
17 | See the accompanying file LICENSE, version 2007-Mar-4 or later |
||
18 | (the contents of which are also included in zip.h) for terms of use. |
||
19 | If, for some reason, all these files are missing, the Info-ZIP license |
||
20 | also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html |
||
21 | |||
22 | parts Copyright (C) 1997 Mike White, Eric W. Engler |
||
23 | ************************************************************************ |
||
24 | Copyright (C) 2009, 2010 by Russell J. Peters, Roger Aelbrecht |
||
25 | |||
26 | This file is part of TZipMaster Version 1.9. |
||
27 | |||
28 | TZipMaster is free software: you can redistribute it and/or modify |
||
29 | it under the terms of the GNU Lesser General Public License as published by |
||
30 | the Free Software Foundation, either version 3 of the License, or |
||
31 | (at your option) any later version. |
||
32 | |||
33 | TZipMaster is distributed in the hope that it will be useful, |
||
34 | but WITHOUT ANY WARRANTY; without even the implied warranty of |
||
35 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||
36 | GNU Lesser General Public License for more details. |
||
37 | |||
38 | You should have received a copy of the GNU Lesser General Public License |
||
39 | along with TZipMaster. If not, see <http://www.gnu.org/licenses/>. |
||
40 | |||
41 | contact: problems@delphizip.org (include ZipMaster in the subject). |
||
42 | updates: http://www.delphizip.org |
||
43 | DelphiZip maillist subscribe at http://www.freelists.org/list/delphizip |
||
44 | ************************************************************************ |
||
45 | */ |
||
46 | |||
47 | #include <process.h> |
||
48 | #include <signal.h> |
||
49 | #include <errno.h> |
||
50 | #include <stdlib.h> |
||
51 | #include <io.h> |
||
52 | |||
53 | // Local option flags |
||
54 | #define PURGE 0 // RCV Changed: was DELETE. (delete is also a function) |
||
55 | #define ADD 1 |
||
56 | #define UPDATE 2 |
||
57 | #define FRESHEN 3 |
||
58 | |||
59 | #define MARK_PURGE -1 |
||
60 | #define MARK_KEEP 0 |
||
61 | #define MARK_UPDATE 1 |
||
62 | #define MARK_RENAMED 2 |
||
63 | #define MARK_VERSION 3 |
||
64 | #define MARK_NEW 4 |
||
65 | |||
66 | #ifndef UNICODE |
||
67 | #define __access _access |
||
68 | #endif |
||
69 | |||
70 | // Process -o and -m options (if specified), free up malloc'ed stuff, and |
||
71 | // exit with the code e. e :: Exit code. |
||
72 | void ZipFunc::finish(void) |
||
73 | { |
||
74 | int r; // return value from trash() |
||
75 | ulg t; // latest time in zip file |
||
76 | |||
77 | ZipItem *z; // pointer into zfile list |
||
78 | |||
79 | if (flatest && fzipfile.Compare(_T("-"))) |
||
80 | { |
||
81 | diag(_T("changing time of zip file to time of latest file in it")); |
||
82 | |||
83 | // find latest time in zip file |
||
84 | if (fzfiles == NULL) |
||
85 | { |
||
86 | Notify(IWARNING, |
||
87 | _T("zip file is empty, can't make it as old as latest entry")); |
||
88 | } |
||
89 | else |
||
90 | { |
||
91 | t = 0; |
||
92 | |||
93 | for (z = fzfiles; z != NULL; z = z->nxt) // Ignore directories in time comparisons |
||
94 | if (!z->IsFolder && t < z->tim) |
||
95 | t = z->tim; |
||
96 | // set modified time of zip file to that time |
||
97 | if (t != 0) |
||
98 | stamp(fzipfile, t); |
||
99 | else |
||
100 | Notify(IWARNING, |
||
101 | _T("zip file has only directories, can't make it as old as latest entry")); |
||
102 | } |
||
103 | } |
||
104 | |||
105 | // If dispose, delete all files in the zfiles list that are marked |
||
106 | if (fdispose && !Abort_Flag) |
||
107 | { |
||
108 | // v1.6017 |
||
109 | diag(_T("deleting files that were added to zip file")); |
||
110 | |||
111 | if ((r = trash()) != DZ_ERR_GOOD) |
||
112 | DZError(r); |
||
113 | } |
||
114 | } |
||
115 | |||
116 | void ZipFunc::ZipCleanup(void) |
||
117 | { |
||
118 | delete [] fhwbuf; |
||
119 | fhwbuf = NULL; |
||
120 | |||
121 | if (ftempzip && (ftempzip != fzipfile)) |
||
122 | { |
||
123 | // using temp file |
||
124 | if (fZipOutfile) |
||
125 | { |
||
126 | delete fZipOutfile; |
||
127 | fZipOutfile = NULL; |
||
128 | } |
||
129 | |||
130 | // remove bad file - if it exists |
||
131 | EraseFile(ftempzip, false); |
||
132 | } |
||
133 | |||
134 | Close_Handle(&fhInz); |
||
135 | |||
136 | if (fZipOutfile) |
||
137 | { |
||
138 | bool wasopen = fZipOutfile->IsOpen() && fZipOutfile->IsFile; |
||
139 | delete fZipOutfile; |
||
140 | fZipOutfile = NULL; |
||
141 | // remove damaged file |
||
142 | |||
143 | if (wasopen) |
||
144 | { |
||
145 | if (Verbose) |
||
146 | Notify(IVERBOSE, _T("deleting damaged %s"), fzipfile.c_str()); |
||
147 | |||
148 | EraseFile(fzipfile, false); |
||
149 | } |
||
150 | } |
||
151 | |||
152 | ftempzip = ""; |
||
153 | } |
||
154 | |||
155 | int DriveType(const DZStrW& pth) |
||
156 | { |
||
157 | TCHAR root[3]; |
||
158 | root[0] = pth.IsEmpty() ? (char)0 : pth[0]; |
||
159 | root[1] = ':'; |
||
160 | root[2] = 0; |
||
161 | |||
162 | if (root[0] == BSLASH) |
||
163 | root[1] = 0; |
||
164 | |||
165 | return GetDriveType(root); |
||
166 | } |
||
167 | |||
168 | const char hx[16] = "0123456789ABCDEF"; |
||
169 | char hxbuf[16]; |
||
170 | char* toHex(unsigned val) |
||
171 | { |
||
172 | char* p = &hxbuf[15]; |
||
173 | *p = 0; |
||
174 | while (val) |
||
175 | { |
||
176 | *--p = hx[val & 0x0f]; |
||
177 | val >>= 4; |
||
178 | } |
||
179 | return p; |
||
180 | } |
||
181 | |||
182 | |||
183 | int __fastcall ZipFunc::NameVer(ZipItem* z) |
||
184 | { |
||
185 | int r; |
||
186 | DZStrW name = z->IName; |
||
187 | int i = name.ReverseFind(_T('.')); |
||
188 | |||
189 | if (!VerDate) |
||
190 | { |
||
191 | FILETIME now; |
||
192 | WORD d, t; |
||
193 | GetSystemTimeAsFileTime(&now); |
||
194 | |||
195 | if (FileTimeToDosDateTime(&now, &d, &t)) |
||
196 | VerDate = (d << 16) | t; |
||
197 | else |
||
198 | VerDate = z->tim; |
||
199 | } |
||
200 | |||
201 | DZStrW nx, nn(name); |
||
202 | nx = _T("}"); |
||
203 | |||
204 | if (i >= 0) |
||
205 | { |
||
206 | nn = name.Left(i); |
||
207 | nx += name.Mid(i); |
||
208 | } |
||
209 | |||
210 | i = -1; |
||
211 | |||
212 | nn.AppendFormat(_T(".{%X"), VerDate); |
||
213 | name = nn; |
||
214 | name += nx; |
||
215 | DZStrA hn = StrIntSep(name); |
||
216 | |||
217 | const XItem* n; |
||
218 | while ((n = IntList->FindName(name)) != NULL) |
||
219 | { |
||
220 | // exists |
||
221 | if (++i == MAXINT) |
||
222 | return -2; // give up |
||
223 | |||
224 | name.Format(_T("%s-%X%s"), nn.c_str(), i, nx.c_str()); |
||
225 | } |
||
226 | hn = StrIntSep(name); |
||
227 | if (Verbose < 0) |
||
228 | Notify(IVERBOSE, _T("%s versioned as %s"), z->iname, name.c_str()); |
||
229 | z->IName = name; |
||
230 | z->HName = hn; |
||
231 | // prepare header name |
||
232 | if ((r = PrepareHeaderName(z, true)) != 0) |
||
233 | return r; |
||
234 | |||
235 | if (!n) |
||
236 | n = IntList->AddNode(z); |
||
237 | |||
238 | return n ? -1 : 0; |
||
239 | } |
||
240 | |||
241 | void ZipFunc::DupName(bool fatal, const XItem* o, const XItem* n, const DZStrW name) |
||
242 | { |
||
243 | // duplicate found |
||
244 | Notify(IWARNING, _T("internal name in zip file repeated: %s"), name.c_str()); |
||
245 | Notify(IWARNING, _T(" first full name: %s"), o->xname); |
||
246 | Notify(IWARNING, _T(" second full name: %s"), n->xname); |
||
247 | |||
248 | if (fatal) |
||
249 | throw DZException(DZ_ERM_DUPNAME); |
||
250 | Notify(IWARNING, _T(" rejecting: %s"), n->xname); |
||
251 | } |
||
252 | |||
253 | int __fastcall ZipFunc::PrepareHeaderName(ZipItem* z, bool NoComment) |
||
254 | { |
||
255 | if (!NoComment) |
||
256 | { |
||
257 | // // free any old data - probably obsolete |
||
258 | // z->cextra.Empty(); |
||
259 | // z->extra.Empty(); |
||
260 | if (z->ntfs) |
||
261 | { |
||
262 | delete z->ntfs; |
||
263 | z->ntfs = NULL; |
||
264 | } |
||
265 | |||
266 | // get or change the comment |
||
267 | CB->Msg2 = z->Comment; |
||
268 | if (CB->UserCB(zacComment, z->IName) == CALLBACK_TRUE) |
||
269 | { |
||
270 | // User changed the comment |
||
271 | z->Comment.Empty(); |
||
272 | z->com = CB->Arg1; |
||
273 | |||
274 | if (z->com) |
||
275 | { |
||
276 | DZStrW tc(CB->Msg, z->com); |
||
277 | z->Comment = tc; |
||
278 | } |
||
279 | } |
||
280 | } |
||
281 | // ****** set header name and encoding |
||
282 | z->options.needutf8 = 0; |
||
283 | z->options.nameextd = z->IName.BadDOS(); |
||
284 | z->options.cmntextd = z->com && z->Comment.BadDOS(); |
||
285 | z->options.namenew = 0; |
||
286 | |||
287 | DZStrW iiname = StrIntSep(z->IName); |
||
288 | bool wantOEM = true; |
||
289 | int bad = 0; |
||
290 | if (!z->options.nameextd && !z->options.cmntextd) |
||
291 | { |
||
292 | // mimic WinZip |
||
293 | z->Enc = zeoOEM; |
||
294 | } |
||
295 | else |
||
296 | { |
||
297 | unsigned doenc = fEncodeAs; |
||
298 | if (doenc == zeoAuto) |
||
299 | { |
||
300 | doenc = zeoUPATH; |
||
301 | if (z->options.nameextd && z->options.cmntextd) |
||
302 | doenc = zeoUTF8; // recommended |
||
303 | } |
||
304 | |||
305 | z->Enc = doenc; |
||
306 | if (doenc == zeoUPATH) |
||
307 | { |
||
308 | z->HName = iiname.SafeNarrow(CP_OEM); // default oem name |
||
309 | z->options.dosflag = 2; // FAT |
||
310 | wantOEM = false; |
||
311 | } |
||
312 | else |
||
313 | if (doenc == zeoUTF8) |
||
314 | { |
||
315 | z->HName = StrToUTF8(iiname); |
||
316 | z->options.nameutf8 = 1; // so we set the flag |
||
317 | z->options.dosflag = 2; // assume header strings usable on MSDOS |
||
318 | wantOEM = false; |
||
319 | } |
||
320 | else |
||
321 | if (doenc == zeoNone) |
||
322 | { |
||
323 | z->HName = iiname.SafeNarrow(CP_ACP, bad); |
||
324 | z->options.nameutf8 = 0; // so we set the flag |
||
325 | bool ntfs = z->HName.BadDOS(); |
||
326 | if (!ntfs && z->options.cmntextd) |
||
327 | { |
||
328 | DZStrA tmp = z->Comment.SafeNarrow(CP_ACP); |
||
329 | ntfs = tmp.BadDOS(); |
||
330 | } |
||
331 | z->options.dosflag = ntfs ? 0 : 1; // assume header strings usable on NTFS |
||
332 | wantOEM = false; |
||
333 | } |
||
334 | } |
||
335 | if (wantOEM) |
||
336 | { |
||
337 | z->HName = iiname.SafeNarrow(CP_OEM, bad); // default oem name |
||
338 | z->options.dosflag = 2; // FAT |
||
339 | } |
||
340 | if (bad) |
||
341 | { |
||
342 | z->options.namenew = 1; // name was made safe |
||
343 | unsigned cp = wantOEM ? CP_OEM : CP_ACP; |
||
344 | DZStrW xname(cp, z->hname, z->HName.length()); |
||
345 | if (Verbose < 0) |
||
346 | Notify(IVERBOSE, _T("%s made safe as %hs"), iiname.c_str(), xname.c_str()); |
||
347 | } |
||
348 | #ifdef ZDEBUG |
||
349 | if (Verbose < 0) |
||
350 | { |
||
351 | Notify(ITRACE, _T("Prepare %s need %x dos %X"), z->iname, z->ver, |
||
352 | z->options.dosflag); |
||
353 | } |
||
354 | #endif |
||
355 | |||
356 | return 0; |
||
357 | } |
||
358 | |||
359 | // Add, update, freshen, or delete zip entries in a zip file. argc; /* |
||
360 | // Number of tokens in command line. argv; /* Command line tokens. |
||
361 | int ZipFunc::ZipProcess(void) |
||
362 | { |
||
363 | int a; // attributes of zip file |
||
364 | ZInt64 censtt; // start of central directory |
||
365 | |||
366 | FndItem *f; // steps through "found" linked list |
||
367 | FndItem *tempf; |
||
368 | int k; // next argument type, marked counter, comment size, entry count |
||
369 | int marks; // replaces k as marked counter |
||
370 | int r; // temporary variable |
||
371 | int err; // temporary error variable |
||
372 | ulg t; // file time, length of central directory |
||
373 | |||
374 | ZipItem *v; // temporary variable |
||
375 | ZipItem *z; // steps through "zfiles" linked list |
||
376 | const TCHAR *Actions[4] = {_T("PURGE"), _T("ADD"), _T("UPDATE"), _T("FRESHEN")}; |
||
377 | |||
378 | int DestType; // destination drive type |
||
379 | unsigned long TotFiles = 0; |
||
380 | __int64 TotSize = 0; |
||
381 | unsigned long KeptCnt = 0; // number of 'kept' files |
||
382 | __int64 KeptSize = 0; // size of 'kept' files |
||
383 | __int64 VerSize = 0; // size of 'kept' files |
||
384 | __int64 fsz; // file size; |
||
385 | int No_File; // 1.75 try if file does not exist |
||
386 | // Process arguments |
||
387 | diag(_T("processing lists")); |
||
388 | |||
389 | if (Verbose) |
||
390 | { |
||
391 | Notify(IVERBOSE, _T("action = %s"), Actions[faction]); |
||
392 | |||
393 | // zcount is no. of entries in linked-list |
||
394 | // zfiles is name of the linked-list of filenames for the archive |
||
395 | Notify(IVERBOSE, _T("zcount=%d (no. of files in ZIP already)"), fzcount); |
||
396 | } |
||
397 | |||
398 | if (!fzipbeg) |
||
399 | fjunk_sfx = 0; // nothing to junk |
||
400 | |||
401 | if (!fzfiles) |
||
402 | fadjust = 0; // nothing to adjust |
||
403 | |||
404 | |||
405 | if ((r = check_dupExt()) != DZ_ERR_GOOD) // remove duplicates in ffound |
||
406 | return DZError(r); |
||
407 | |||
408 | // Check option combinations |
||
409 | // ????? |
||
410 | if (faction == PURGE && (fdispose || frecurse || fkey)) |
||
411 | return DZError(DZ_ERM_BAD_OPTIONS); |
||
412 | |||
413 | // AllowGrow is the "allow append" indicator |
||
414 | if (!fzcount && ((faction == ADD) || (faction == UPDATE))) |
||
415 | fAllowGrow = 55; // create new file normally |
||
416 | |||
417 | // if zcount is 0, then zipfile doesn't exist, or is empty |
||
418 | if (fzcount == 0 && ((faction != ADD && faction != UPDATE) |
||
419 | || !fAllowGrow)) |
||
420 | { |
||
421 | // RCV150199 added UPDATE |
||
422 | Notify(IWARNING, _T("%s: not found or empty"), fzipfile.c_str()); |
||
423 | return 0; |
||
424 | } |
||
425 | |||
426 | if (fndlist) |
||
427 | { |
||
428 | delete fndlist; |
||
429 | fndlist = NULL; |
||
430 | } |
||
431 | |||
432 | DestType = DriveType(fzipfile); |
||
433 | |||
434 | if (Verbose < 0) |
||
435 | Notify(IVERBOSE, _T("Destination type = %d"), DestType); |
||
436 | |||
437 | // RP - check destination type - if CD set tempath to Windows Temp |
||
438 | if (ftempath.IsEmpty() && (DestType != DRIVE_FIXED && |
||
439 | DestType != DRIVE_RAMDISK)) |
||
440 | { |
||
441 | GetTempPath(2047, ftempath.GetBuffer(2047)); |
||
442 | ftempath.ReleaseBuffer(); |
||
443 | } |
||
444 | |||
445 | // If -b not specified, set temporary path to zipfile path |
||
446 | int pp; |
||
447 | |||
448 | if (ftempath.IsEmpty() && ((pp = fzipfile.ReverseFind(BSLASH)) >= 0 |
||
449 | || (pp = fzipfile.ReverseFind(_T(':'))) >= 0)) |
||
450 | { |
||
451 | if (fzipfile[pp] == _T(':')) |
||
452 | pp++; |
||
453 | |||
454 | ftempath = fzipfile.Left(pp); |
||
455 | } |
||
456 | |||
457 | // if first_listarg is 0, then we didn't got any fspecs on cmd line |
||
458 | if (fdoall && (faction == UPDATE || faction == FRESHEN)) |
||
459 | { |
||
460 | // if -update or -freshen with no args, do all, but, when present, apply |
||
461 | // filters |
||
462 | for (z = fzfiles; z != NULL; z = z->nxt) |
||
463 | z->mark = fpcount ? !ZMatch(fExcludes, z->IName) : 1; |
||
464 | } |
||
465 | |||
466 | // NOTE: "k" is being redefined below this point. Now, it going to |
||
467 | // track the no. of marked files in the "zfiles" linked list. |
||
468 | // For each marked entry in "zfiles" linked list, if not deleting, check |
||
469 | // if a corresponding "external" file exists. If updating or freshening, |
||
470 | // compare date of "external" file with entry in orig zipfile. Unmark if it |
||
471 | // external file doesn't exist or is too old, else mark it. Entries that |
||
472 | // are marked will cause that file to be rezipped. |
||
473 | diag(_T("checking marked entries")); |
||
474 | marks = 0; // Initialize marked count |
||
475 | ZipItem **zlast; // pointer to last link in "zfiles" list |
||
476 | ZipItem **verlast = &VerFiles; // pointer to last link |
||
477 | ZipItem **fndlast = &fzfound; |
||
478 | int vercount = 0; |
||
479 | for (z = fzfiles; z != NULL; z = z->nxt) |
||
480 | { |
||
481 | if (z->mark) |
||
482 | { |
||
483 | ulg FileAttr; |
||
484 | if (faction != PURGE) |
||
485 | { |
||
486 | t = zfiletime(z->FullPath(), &FileAttr, &fsz, NULL); |
||
487 | |||
488 | if ((t == 0 || t < fbefore |
||
489 | || ((faction == UPDATE || faction == FRESHEN) && |
||
490 | t <= z->tim) |
||
491 | || (fArchiveFiles && faction == FRESHEN && |
||
492 | !(FileAttr &A_ARCHIVE))) |
||
493 | ) |
||
494 | { |
||
495 | z->mark = MARK_KEEP; // keep |
||
496 | z->trash = (t && t >= fbefore); |
||
497 | // delete if -um or -fm |
||
498 | |||
499 | if (Verbose) |
||
500 | { |
||
501 | const TCHAR *expl; |
||
502 | |||
503 | if (t) |
||
504 | expl = z->trash ? _T("up to date") : _T("early"); |
||
505 | else |
||
506 | expl = _T("missing"); |
||
507 | |||
508 | Notify(0, _T("%s is %s"), z->xname, expl); |
||
509 | } |
||
510 | } |
||
511 | else |
||
512 | { |
||
513 | // replace |
||
514 | TotSize += fsz; |
||
515 | TotFiles++; |
||
516 | marks++; |
||
517 | z->mark = MARK_UPDATE; // marker for replace |
||
518 | |||
519 | if (z->options.keepver) |
||
520 | { |
||
521 | ZipItem* vz = new ZipItem(*z); |
||
522 | *(verlast) = vz; |
||
523 | verlast = &vz->nxt; |
||
524 | vz->nxt = NULL; |
||
525 | vz->Passw = fkey; |
||
526 | vz->Base = CurBase->Base; |
||
527 | vercount++; |
||
528 | } |
||
529 | } |
||
530 | } |
||
531 | else |
||
532 | { |
||
533 | // PURGE |
||
534 | marks++; // incr. number of marked entries |
||
535 | z->mark = MARK_PURGE; // marker for Purge |
||
536 | } |
||
537 | } |
||
538 | } |
||
539 | // RP - verify file specified to 'Purge' |
||
540 | if (faction == PURGE && !marks) |
||
541 | return DZError(DZ_ERM_NOTHING_TO_DO); |
||
542 | |||
543 | // Remove entries from "found" linked list if: Action is PURGE or FRESHEN |
||
544 | // or No "external" matching file is found, or if found, but is too old or |
||
545 | // The external file is equal to the ziparchive name while ziparchive name |
||
546 | // != "-" If filetime() returns any valid time, then at least we know the |
||
547 | // file was found. |
||
548 | diag(_T("checking new entries")); |
||
549 | FndItem *prev = NULL; |
||
550 | // fileio.c built the found list |
||
551 | for (f = ffound; f != NULL;) |
||
552 | { |
||
553 | if (faction == PURGE || faction == FRESHEN |
||
554 | || (t = zfiletime(f->xname, NULL, NULL, NULL)) == 0 |
||
555 | || t < fbefore |
||
556 | || (ZMatch(f->FullPath(), fzipfile))) |
||
557 | { |
||
558 | if (Verbose && t < fbefore) |
||
559 | Notify(IVERBOSE, _T("rejecting %s as too early"), f->xname); |
||
560 | |||
561 | if (Verbose < 0) |
||
562 | Notify(ITRACE, _T("expel being called for %s"), f->xname); |
||
563 | tempf = f; |
||
564 | f = f->nxt; |
||
565 | if (prev) |
||
566 | prev->nxt = f; |
||
567 | else |
||
568 | ffound = f; // new first |
||
569 | delete tempf; |
||
570 | ffcount--; |
||
571 | } |
||
572 | else // file found, and not too old. |
||
573 | { |
||
574 | prev = f; |
||
575 | f = f->nxt; // save this one, link it up. |
||
576 | } |
||
577 | } |
||
578 | if (Verbose) |
||
579 | { |
||
580 | if (ffound == NULL) |
||
581 | Notify(IVERBOSE, _T("found list empty - a")); |
||
582 | else |
||
583 | Notify(IVERBOSE, _T("found list has at least one entry - a")); |
||
584 | } |
||
585 | // 'fix' safe and header names |
||
586 | IntList = new HashListInt(ffcount + fzcount + vercount); |
||
587 | // add 'keep' files - no duplicate allowed but should not happen |
||
588 | ZipItem *prv = NULL; |
||
589 | for (z = fzfiles; z != NULL; /* z = z->nxt */) |
||
590 | { |
||
591 | FndItem *e; |
||
592 | if (z->mark >= MARK_KEEP) |
||
593 | { |
||
594 | // add internal name to list - check for duplicate |
||
595 | if ((e = (FndItem*) IntList->AddNode(z)) != 0) |
||
596 | { |
||
597 | DupName(Skipping(z->XName, DZ_ERM_DUPNAME, SKIPPED_DUP_NAME), |
||
598 | e, z, z->IName); |
||
599 | // delete later duplicate |
||
600 | ZipItem *x = z->nxt; |
||
601 | if (prv) |
||
602 | prv->nxt = x; |
||
603 | else |
||
604 | fzfiles = x; |
||
605 | delete z; |
||
606 | z = x; |
||
607 | fzcount--; |
||
608 | continue; |
||
609 | } |
||
610 | } |
||
611 | prv = z; |
||
612 | z = z->nxt; |
||
613 | } |
||
614 | |||
615 | // now new files - no duplicates |
||
616 | while ((f = ffound) != NULL) |
||
617 | { |
||
618 | ZipItem **prvlast = fndlast; // save |
||
619 | ZipItem *prvlastnxt = *(fndlast); // save |
||
620 | ZipItem *zi = new ZipItem(f); // copy as ZipItem |
||
621 | *(fndlast) = zi; |
||
622 | fndlast = &zi->nxt; |
||
623 | zi->mark = MARK_NEW; |
||
624 | ffound = f->nxt; |
||
625 | delete f; |
||
626 | |||
627 | // set comment and header name |
||
628 | if ((r = PrepareHeaderName(zi, false)) != 0) |
||
629 | return r; |
||
630 | FndItem *e; |
||
631 | if ((e = (FndItem*) IntList->AddNode(zi)) != 0) |
||
632 | { |
||
633 | DupName(Skipping(zi->XName, 0, SKIPPED_DUP_NAME), |
||
634 | e, f, f->IName); |
||
635 | // delete later duplicate |
||
636 | fndlast = prvlast; // restore |
||
637 | *(fndlast) = prvlastnxt; // restore |
||
638 | delete zi; |
||
639 | ffcount--; |
||
640 | } |
||
641 | } |
||
642 | // now rename versions to unique internal names |
||
643 | if (vercount) |
||
644 | { |
||
645 | fAllowGrow = 0; // append not allowed |
||
646 | } |
||
647 | // |
||
648 | if (fadjust <= 0) |
||
649 | fadjust = 0; |
||
650 | |||
651 | // Make sure there's something left to do |
||
652 | if (marks == 0 && fzfound == NULL && !(fzfiles != NULL && (flatest || |
||
653 | fadjust || fjunk_sfx))) |
||
654 | { |
||
655 | // FOUND WAS NULL HERE, so just figure out which error message to show |
||
656 | if (faction == UPDATE || faction == FRESHEN) |
||
657 | { |
||
658 | finish(); |
||
659 | Notify(IWARNING, _T("no files %s"), (faction == UPDATE) ? _T("updated") |
||
660 | : _T("freshened")); |
||
661 | return 0; |
||
662 | } |
||
663 | else |
||
664 | { |
||
665 | if (fzfiles == NULL && (flatest || fadjust || fjunk_sfx)) |
||
666 | return DZError(DZ_ERM_EMPTY_ZIP); |
||
667 | return DZError(DZ_ERM_NOTHING_TO_DO); |
||
668 | } |
||
669 | } |
||
670 | |||
671 | // AllowGrow is false if writing temporary file |
||
672 | fAllowGrow = (fAllowGrow && (marks == 0) |
||
673 | // is allowed and no changes to existing |
||
674 | && (fzipbeg || fzfiles != NULL) // something to append to |
||
675 | ); |
||
676 | |||
677 | // continue on to add new files |
||
678 | a = 0; |
||
679 | |||
680 | // ignore self-extracting code in front of the zip file (for -J) |
||
681 | if (fjunk_sfx) |
||
682 | fzipbeg = 0; |
||
683 | |||
684 | // Calc size of version files |
||
685 | for (z = VerFiles; z; z = z->nxt) |
||
686 | { |
||
687 | if (Abort_Flag) |
||
688 | Fatal(DZ_ERM_ABORT, 0); |
||
689 | |||
690 | VerSize += (z->siz + (ulg)(4 + LOCHEAD) + (ulg)z->nam + (ulg)z->ext); |
||
691 | |||
692 | if (z->lflg &8) |
||
693 | VerSize += 16; |
||
694 | } |
||
695 | |||
696 | // Count files and sizes which we have to Keep; RP Added |
||
697 | zlast = &fzfiles; |
||
698 | while ((z = *zlast) != NULL) |
||
699 | { |
||
700 | if (Abort_Flag) |
||
701 | Fatal(DZ_ERM_ABORT, 0); |
||
702 | |||
703 | if (!z->mark) |
||
704 | { |
||
705 | KeptSize += (z->siz + (ulg)(4 + LOCHEAD) + (ulg)z->nam + (ulg)z->ext); |
||
706 | |||
707 | if (z->lflg &8) |
||
708 | KeptSize += 16; |
||
709 | |||
710 | KeptCnt++; |
||
711 | } |
||
712 | |||
713 | zlast = &z->nxt; |
||
714 | } |
||
715 | |||
716 | //Inform(pG, 0, IDIAG, "Kept = %u %Lu Total = %Lu %Lu", KeptCnt, KeptSize, TotFiles, TotSize); |
||
717 | // Count files and sizes which we have to process; RCV Added |
||
718 | // First the files in the old zip file... |
||
719 | // RP - already calculated with new sizes |
||
720 | // And the found list... |
||
721 | z = fzfound; |
||
722 | while (z) |
||
723 | { |
||
724 | if (Abort_Flag) |
||
725 | Fatal(DZ_ERM_ABORT, 0); |
||
726 | |||
727 | TotSize += z->len; |
||
728 | TotFiles++; |
||
729 | z = z->nxt; |
||
730 | } |
||
731 | |||
732 | fhInz = INVALID_HANDLE_VALUE; |
||
733 | fOutPosn = 0; |
||
734 | |||
735 | if (!fAllowGrow) |
||
736 | { |
||
737 | // check file exists |
||
738 | No_File = _taccess(fzipfile, 0) && errno == ENOENT; |
||
739 | |||
740 | if (No_File && DestType == DRIVE_FIXED || DestType == DRIVE_RAMDISK) |
||
741 | { |
||
742 | // create file using given name |
||
743 | diag(_T("Processing - ready to create new file")); |
||
744 | fZipOutfile = new ZFile(this, fzipfile, GENERIC_WRITE, 0, NULL, |
||
745 | CREATE_NEW, FILE_ATTRIBUTE_NORMAL); |
||
746 | |||
747 | if (fZipOutfile->IsOpen()) |
||
748 | { |
||
749 | ftempzip = fzipfile; |
||
750 | fAllowGrow = -1; // new files do grow |
||
751 | } |
||
752 | else |
||
753 | if (Verbose < 0) |
||
754 | Notify(DZ_ERM_ERROR_CREATE, _T("CreateFile failed %s [%s]"), |
||
755 | fzipfile.c_str(), SysMsg().c_str()); |
||
756 | } |
||
757 | } |
||
758 | |||
759 | if (fAllowGrow > 0) |
||
760 | { |
||
761 | // zipfile is not stdout, and we are allowed to append |
||
762 | // AllowGrow is true if we're just appending (-g) |
||
763 | diag(_T("Processing - ready to open for appending")); |
||
764 | fZipOutfile = new ZFile(this, fzipfile, GENERIC_READ | GENERIC_WRITE, 0, |
||
765 | NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL); |
||
766 | |||
767 | if (!fZipOutfile->IsOpen()) |
||
768 | { |
||
769 | if (Verbose < 0) |
||
770 | Notify(DZ_ERM_ERROR_CREATE, _T("CreateFile failed 2 %s [%s]"), |
||
771 | fzipfile.c_str(), SysMsg().c_str()); |
||
772 | |||
773 | return DZError(DZ_ERM_ERROR_CREATE); |
||
774 | } |
||
775 | |||
776 | ftempzip = fzipfile; |
||
777 | |||
778 | if (fZipOutfile->SetPosition(fcenbeg, FILE_BEGIN) == -1) |
||
779 | return DZError(GetLastError() ? DZ_ERM_ERROR_SEEK : DZ_ERM_ZIP_EOF); |
||
780 | |||
781 | fOutPosn = fcenbeg; |
||
782 | } |
||
783 | |||
784 | if (!fAllowGrow) |
||
785 | { |
||
786 | diag(_T("Processing - ready to open for Exclusive Read")); |
||
787 | |||
788 | if ((fzfiles != NULL || fzipbeg) && |
||
789 | (fhInz = CreateFile(fzipfile, GENERIC_READ, 0, NULL, OPEN_EXISTING, |
||
790 | FILE_ATTRIBUTE_NORMAL | FILE_FLAG_SEQUENTIAL_SCAN, NULL)) == |
||
791 | INVALID_HANDLE_VALUE) |
||
792 | { |
||
793 | if (Verbose < 0) |
||
794 | Notify(DZ_ERM_ERROR_CREATE, _T("CreateFile failed 3 %s [%s]"), |
||
795 | fzipfile.c_str(), SysMsg().c_str()); |
||
796 | |||
797 | return DZError(DZ_ERM_ERROR_CREATE); |
||
798 | } |
||
799 | |||
800 | ftempzip = tempname(); |
||
801 | |||
802 | if (Verbose) |
||
803 | Notify(IVERBOSE, _T("Temp Filename = %s"), ftempzip.c_str()); |
||
804 | |||
805 | fZipOutfile = new ZFile(this, ftempzip, GENERIC_WRITE, 0, |
||
806 | NULL, CREATE_NEW, FILE_ATTRIBUTE_NORMAL); |
||
807 | |||
808 | if (!fZipOutfile->IsOpen()) |
||
809 | { |
||
810 | if (Verbose < 0) |
||
811 | Notify(DZ_ERR_ERROR_CREATE | ITRACE, _T("CreateFile failed 3 %s [%s]"), |
||
812 | ftempzip.c_str(), SysMsg().c_str()); |
||
813 | |||
814 | return DZError(DZ_ERM_TEMP_FAILED); |
||
815 | } |
||
816 | } |
||
817 | |||
818 | if (!fAllowGrow) |
||
819 | { |
||
820 | TotFiles += KeptCnt + vercount; |
||
821 | TotSize += KeptSize + VerSize; |
||
822 | } |
||
823 | |||
824 | // Pass total number of files and Total Filesize. |
||
825 | CB->Arg1 = TotFiles; |
||
826 | CB->UserCB(zacCount); |
||
827 | |||
828 | CB->FileSize = TotSize; |
||
829 | CB->UserCB(zacSize); |
||
830 | |||
831 | fBatchStarted = 1; |
||
832 | |||
833 | if (!fAllowGrow && fzipbeg) |
||
834 | { |
||
835 | if (Verbose) |
||
836 | Notify(IVERBOSE, _T("Copying SFX stub [%X]"), fzipbeg); |
||
837 | |||
838 | // copy a compressed file from old archive to new archive |
||
839 | CB->FileSize = fzipbeg; |
||
840 | CB->Msg = _T("SFX"); |
||
841 | CB->UserCB(zacItem); |
||
842 | |||
843 | if ((r = fcopy(fzipbeg)) != DZ_ERR_GOOD) |
||
844 | return DZError(r); |
||
845 | |||
846 | fOutPosn = fzipbeg; |
||
847 | } |
||
848 | |||
849 | // Process zip file, copying from old archive to new archive. Rezip any |
||
850 | // marked files |
||
851 | if (fzfiles != NULL) |
||
852 | diag(_T("going through old zip file")); |
||
853 | |||
854 | zlast = &fzfiles; |
||
855 | while ((z = *zlast) != NULL) |
||
856 | { |
||
857 | if (Abort_Flag) |
||
858 | Fatal(DZ_ERM_ABORT, 0); |
||
859 | |||
860 | if (z->mark == MARK_UPDATE) |
||
861 | { |
||
862 | // This file is marked |
||
863 | // if not deleting, rezip it |
||
864 | Notify(0, _T("updating: %s"), z->iname); |
||
865 | ZipItem zr = *z; // make copy |
||
866 | // update comment and name (if required) |
||
867 | if ((r = PrepareHeaderName(z, false)) != 0) |
||
868 | return r; |
||
869 | r = zipup(z); |
||
870 | int dze = DZ_ERR(r); |
||
871 | if (dze == DZ_ERR_NO_FILE_OPEN || dze == DZ_ERR_MISS || //) |
||
872 | dze == DZ_ERR_ERROR_READ || dze ==DZ_ERR_SKIPPED) |
||
873 | { |
||
874 | _TCHAR *msg; |
||
875 | |||
876 | *z = zr; // restore and try to keep |
||
877 | if (dze == DZ_ERR_NO_FILE_OPEN) |
||
878 | msg = _T("could not open for reading: %s"); |
||
879 | else if (dze == DZ_ERR_MISS) |
||
880 | msg = _T("file and directory with the same name: %s"); |
||
881 | else |
||
882 | msg = _T("skipped: %s"); |
||
883 | Notify(IWARNING, msg, z->xname); |
||
884 | CB->UserMsg(r, z->xname); |
||
885 | dze = 0; // handled that error |
||
886 | Notify(IWARNING, _T("will just use old version: %s"), z->iname); |
||
887 | if ((r = zipcopy(z)) != DZ_ERR_GOOD) |
||
888 | { |
||
889 | Notify(IERROR, _T("was copying %s"), z->iname); |
||
890 | dze = -1; // has error in r |
||
891 | } |
||
892 | else |
||
893 | z->mark = 0; |
||
894 | } |
||
895 | if (dze != DZ_ERR_GOOD) |
||
896 | return DZError(r); |
||
897 | |||
898 | zlast = &z->nxt; |
||
899 | ffiles_acted_on++; |
||
900 | } |
||
901 | else |
||
902 | if (z->mark == MARK_PURGE) |
||
903 | { |
||
904 | // desired action is DELETE, this file marked |
||
905 | Notify(0, _T("deleting: %s"), z->iname); |
||
906 | |||
907 | v = z->nxt; // delete entry from list |
||
908 | delete z; |
||
909 | *zlast = v; // link prev to next |
||
910 | fzcount--; |
||
911 | ffiles_acted_on++; |
||
912 | } |
||
913 | else // mark != 1 |
||
914 | { |
||
915 | // this file wasn't marked |
||
916 | // copy the original entry verbatim |
||
917 | if (!fAllowGrow) |
||
918 | { |
||
919 | Notify(0, _T("keeping: %s"), z->iname); |
||
920 | |||
921 | if ((r = zipcopy(z)) != DZ_ERR_GOOD) |
||
922 | { |
||
923 | Notify(IERROR, _T("was copying %s"), z->iname); |
||
924 | return DZError(r); |
||
925 | } |
||
926 | } |
||
927 | |||
928 | zlast = &z->nxt; |
||
929 | } |
||
930 | } // end while |
||
931 | |||
932 | // Process the 'Version' files |
||
933 | if (vercount) |
||
934 | { |
||
935 | if (Verbose < 0) |
||
936 | Notify(ITRACE, _T("Copying %d version entries"), vercount); |
||
937 | |||
938 | while ((z = VerFiles) != NULL) |
||
939 | { |
||
940 | if (Abort_Flag) |
||
941 | Fatal(DZ_ERM_ABORT, 0); |
||
942 | |||
943 | if (Verbose) |
||
944 | Notify(0, _T("Versioning: %s"), z->iname); |
||
945 | |||
946 | VerFiles = VerFiles->nxt; |
||
947 | z->nxt = NULL; |
||
948 | |||
949 | *zlast = z; // link to prev->nxt (allow cleanup) |
||
950 | // make new internal and header names |
||
951 | if ((r = NameVer(z)) != 0) |
||
952 | return r; |
||
953 | |||
954 | if ((r = zipVersion(z)) != DZ_ERR_GOOD) |
||
955 | { |
||
956 | Notify(IERROR, _T("was copying %s"), z->iname); |
||
957 | return DZError(r); |
||
958 | } |
||
959 | |||
960 | // "zipup" of this file was good |
||
961 | *zlast = z; |
||
962 | zlast = &z->nxt; |
||
963 | fzcount++; |
||
964 | ffiles_acted_on++; |
||
965 | } |
||
966 | } |
||
967 | |||
968 | // Process the "found" list, adding them to the zip file. |
||
969 | // This is used to add files that weren't already in the archive. |
||
970 | if (Verbose) |
||
971 | Notify(IVERBOSE, _T("Zipping up %d NEW entries from found list"), ffcount); |
||
972 | |||
973 | // For each new file to add (src names in found list), make a new entry |
||
974 | // for it in the "zfiles" linked list, zip up the new file, then remove the |
||
975 | // entry from the found list. |
||
976 | // The last item in the for loop control deallocates spc for fname that |
||
977 | // was just zipped up |
||
978 | |||
979 | while ((z = fzfound) != NULL) |
||
980 | { |
||
981 | // add a new entry to "zfiles" list, before we zip up the file. That way |
||
982 | // we'll be ready to update the ZIP file's directory later. |
||
983 | if (Abort_Flag) |
||
984 | Fatal(DZ_ERM_ABORT, 0); |
||
985 | |||
986 | fzfound = z->nxt; |
||
987 | ffcount--; |
||
988 | *zlast = z; // link to prev->nxt (allow cleanup) |
||
989 | z->nxt = NULL; |
||
990 | z->mark = MARK_NEW; |
||
991 | |||
992 | // zip it up |
||
993 | if (z->options.namenew) |
||
994 | Notify(0, _T(" adding: %s as %hs"), z->iname, z->hname); |
||
995 | else |
||
996 | Notify(0, _T(" adding: %s"), z->iname); |
||
997 | |||
998 | // This is it - try to zip up new file |
||
999 | r = zipup(z); |
||
1000 | if (r == DZ_ERR_GOOD) |
||
1001 | { |
||
1002 | // "zipup" of this file was good |
||
1003 | *zlast = z; |
||
1004 | zlast = &z->nxt; |
||
1005 | fzcount++; |
||
1006 | ffiles_acted_on++; |
||
1007 | continue; |
||
1008 | } |
||
1009 | err = DZ_ERR(r); |
||
1010 | if (err != DZ_ERR_NO_FILE_OPEN && err != DZ_ERR_MISS &&//) |
||
1011 | err != DZ_ERR_ERROR_READ && err != DZ_ERR_SKIPPED) |
||
1012 | return DZError(r); |
||
1013 | // if ((r = zipup(z)) != DZ_ERR_GOOD |
||
1014 | // && DZ_ERR(r) != DZ_ERR_NO_FILE_OPEN && DZ_ERR(r) != DZ_ERR_MISS) |
||
1015 | // return DZError(r); |
||
1016 | |||
1017 | // if (DZ_ERR(r) == DZ_ERR_NO_FILE_OPEN || DZ_ERR(r) == DZ_ERR_MISS) |
||
1018 | // if (err == DZ_ERR_NO_FILE_OPEN || err == DZ_ERR_MISS || |
||
1019 | // err == DZ_ERR_ERROR_READ || err ==DZ_ERR_SKIPPED) |
||
1020 | // if (r != DZ_ERR_GOOD) |
||
1021 | // { |
||
1022 | // if (DZ_ERR(r) == DZ_ERR_NO_FILE_OPEN) |
||
1023 | if (err == DZ_ERR_NO_FILE_OPEN) |
||
1024 | Notify(r | IWARNING, _T("could not open for reading: %s"), z->xname); |
||
1025 | else |
||
1026 | // Notify(IWARNING, _T("file and directory with the same name: %s"), z->xname); |
||
1027 | { |
||
1028 | _TCHAR *msg; |
||
1029 | if (err == DZ_ERR_MISS) |
||
1030 | msg = _T("file and directory with the same name: %s"); |
||
1031 | else |
||
1032 | msg = _T("skipped: %s"); |
||
1033 | Notify(IWARNING, msg, z->xname); |
||
1034 | } |
||
1035 | *zlast = NULL; // remove from list |
||
1036 | delete z; |
||
1037 | // } |
||
1038 | // else |
||
1039 | // { |
||
1040 | // // "zipup" of this file was good |
||
1041 | // *zlast = z; |
||
1042 | // zlast = &z->nxt; |
||
1043 | // fzcount++; |
||
1044 | // ffiles_acted_on++; |
||
1045 | // } |
||
1046 | } |
||
1047 | |||
1048 | // Write central directory and end header to temporary zip |
||
1049 | diag(_T("writing central directory")); |
||
1050 | |||
1051 | // get start of central directory |
||
1052 | // Assert(fOutPosn == SetFilePointer64(fhOutz, 0, 2), _T("invalid out posn dlz 983")); |
||
1053 | |||
1054 | censtt = fOutPosn; |
||
1055 | k = 0; // keep count of new fnames for ZIPfile's end header |
||
1056 | __int64 usiz = 0; |
||
1057 | __int64 csiz = 0; |
||
1058 | CB->Arg1 = 7; // type |
||
1059 | CB->FileSize = fzcount; |
||
1060 | |||
1061 | CB->Msg = _T("*writing central directory"); |
||
1062 | CB->UserCB(zacXItem); |
||
1063 | |||
1064 | for (z = fzfiles; z != NULL; z = z->nxt) |
||
1065 | { |
||
1066 | if ((r = putcentral(z)) != DZ_ERR_GOOD) |
||
1067 | return DZError(r); |
||
1068 | |||
1069 | usiz += z->len; |
||
1070 | csiz += z->siz; |
||
1071 | k++; |
||
1072 | |||
1073 | CB->UserXProgress(1, 7); |
||
1074 | } |
||
1075 | |||
1076 | if (k == 0) |
||
1077 | Notify(IWARNING, _T("zip file empty")); |
||
1078 | |||
1079 | if ((Verbose) && (faction == ADD) && (!fglobal_error_code) |
||
1080 | && (ffiles_acted_on > 0)) |
||
1081 | { |
||
1082 | Notify(IVERBOSE, _T("Total Bytes=%Lu, compr bytes=%Lu -> %d%% savings"), usiz, csiz, |
||
1083 | percent(usiz, csiz)); |
||
1084 | } |
||
1085 | |||
1086 | diag(_T("writing end of central directory")); |
||
1087 | // Assert(fOutPosn == SetFilePointer64(fhOutz, 0, 1), _T("invalid out posn dlz 1055")); |
||
1088 | |||
1089 | if (k && ((r = PutEnd(k, censtt)) != DZ_ERR_GOOD)) |
||
1090 | return DZError(r); |
||
1091 | |||
1092 | Close_Handle(&fhInz); |
||
1093 | |||
1094 | delete fZipOutfile; |
||
1095 | fZipOutfile = NULL; |
||
1096 | |||
1097 | // Replace old zip file with new zip file, leaving only the new one |
||
1098 | if (!fAllowGrow && (k || faction != PURGE)) |
||
1099 | { |
||
1100 | diag(_T("replacing old zip file with new zip file")); |
||
1101 | |||
1102 | if ((r = replace(fzipfile, ftempzip)) != DZ_ERR_GOOD) |
||
1103 | { |
||
1104 | Notify(IWARNING, _T("new zip file left as: %s"), ftempzip.c_str()); |
||
1105 | return DZError(r); |
||
1106 | } |
||
1107 | } |
||
1108 | |||
1109 | // 1.78.1.2 |
||
1110 | if (!k && faction == PURGE) |
||
1111 | // empty file - remove |
||
1112 | { |
||
1113 | a = flatest = 0; |
||
1114 | DeleteFile(fzipfile); |
||
1115 | |||
1116 | if (!fAllowGrow) |
||
1117 | DeleteFile(ftempzip); |
||
1118 | } |
||
1119 | if (a) |
||
1120 | setfileattr(fzipfile, a); |
||
1121 | |||
1122 | // Reset the archive bit when needed for all successfull zipped files |
||
1123 | if (fResetArchiveBit && faction != PURGE) |
||
1124 | { |
||
1125 | unsigned cnt = 0; // 1.71.0.0 added extra callbacks |
||
1126 | diag(_T("resetting archive bits")); |
||
1127 | |||
1128 | for (z = fzfiles; z != NULL; z = z->nxt) |
||
1129 | if (z->mark) |
||
1130 | cnt++; |
||
1131 | |||
1132 | if (cnt) |
||
1133 | { |
||
1134 | // new file op. |
||
1135 | // Pass total number of files. filesize. |
||
1136 | CB->Arg1 = 1; // type |
||
1137 | CB->FileSize = cnt; |
||
1138 | CB->Msg = _T("*resetting archive bits"); |
||
1139 | CB->UserCB(zacXItem); |
||
1140 | } |
||
1141 | |||
1142 | cnt = 0; |
||
1143 | |||
1144 | for (z = fzfiles; z != NULL; z = z->nxt) |
||
1145 | { |
||
1146 | if (z->mark) |
||
1147 | { |
||
1148 | if (++cnt == 30) |
||
1149 | { |
||
1150 | CB->UserXProgress(cnt, 1); |
||
1151 | cnt = 0; |
||
1152 | if (Abort_Flag) |
||
1153 | break; |
||
1154 | } |
||
1155 | |||
1156 | DZStrW fullname = z->FullPath(); |
||
1157 | |||
1158 | if (!SetFileAttributes(fullname, GetFileAttributes(fullname) |
||
1159 | &~FILE_ATTRIBUTE_ARCHIVE)) |
||
1160 | Notify(IWARNING, _T("Archive bit could not be set for: %s [%s]"), |
||
1161 | fullname.c_str(), SysMsg().c_str()); |
||
1162 | } |
||
1163 | } |
||
1164 | |||
1165 | if (cnt) |
||
1166 | CB->UserXProgress(cnt, 1); |
||
1167 | } |
||
1168 | finish(); |
||
1169 | |||
1170 | return 0; |
||
1171 | } |
||
1172 | |||
1173 | |||
1174 | |||
1175 | |||
1176 |