Details | Last modification | View Log | RSS feed
Rev | Author | Line No. | Line |
---|---|---|---|
1 | daniel-mar | 1 | #include "stdafx.h" |
2 | #pragma hdrstop |
||
3 | #include "zipOp.h" |
||
4 | #include "dz_errs.h" |
||
5 | |||
6 | #undef _DZ_FILE_ |
||
7 | #define _DZ_FILE_ DZ_ZIPSEL_CPP |
||
8 | |||
9 | /* |
||
10 | ZipSel.cpp - common definitions and functions |
||
11 | |||
12 | Copyright (c) 1990-2007 Info-ZIP. All rights reserved. |
||
13 | |||
14 | See the accompanying file LICENSE, version 2007-Mar-4 or later |
||
15 | (the contents of which are also included in zip.h) for terms of use. |
||
16 | If, for some reason, all these files are missing, the Info-ZIP license |
||
17 | also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html |
||
18 | |||
19 | parts Copyright (C) 1997 Mike White, Eric W. Engler |
||
20 | ************************************************************************ |
||
21 | Copyright (C) 2009, 2010 by Russell J. Peters, Roger Aelbrecht |
||
22 | |||
23 | This file is part of TZipMaster Version 1.9. |
||
24 | |||
25 | TZipMaster is free software: you can redistribute it and/or modify |
||
26 | it under the terms of the GNU Lesser General Public License as published by |
||
27 | the Free Software Foundation, either version 3 of the License, or |
||
28 | (at your option) any later version. |
||
29 | |||
30 | TZipMaster is distributed in the hope that it will be useful, |
||
31 | but WITHOUT ANY WARRANTY; without even the implied warranty of |
||
32 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||
33 | GNU Lesser General Public License for more details. |
||
34 | |||
35 | You should have received a copy of the GNU Lesser General Public License |
||
36 | along with TZipMaster. If not, see <http://www.gnu.org/licenses/>. |
||
37 | |||
38 | contact: problems@delphizip.org (include ZipMaster in the subject). |
||
39 | updates: http://www.delphizip.org |
||
40 | DelphiZip maillist subscribe at http://www.freelists.org/list/delphizip |
||
41 | ************************************************************************/ |
||
42 | #if 0 |
||
43 | // ** moved to DzOp |
||
44 | DZStrW ZipOp::ConvExclFilters(const DZStrW & filters) |
||
45 | { |
||
46 | DZStrW exc; |
||
47 | if (filters.IsEmpty()) |
||
48 | return exc; |
||
49 | int n = 0; |
||
50 | if (filters[0] == _T('|')) |
||
51 | { |
||
52 | exc = _T("|"); |
||
53 | n++; |
||
54 | } |
||
55 | int len = filters.length(); |
||
56 | while (n < len) |
||
57 | { |
||
58 | int nx = filters.Find(_T('|'), n+1); |
||
59 | if (nx < 0) |
||
60 | nx = len + 1; |
||
61 | DZStrW comp = filters.Mid(n, nx - n); |
||
62 | n = nx + 1; |
||
63 | comp.Trim(); |
||
64 | DZStrW p = ex2IntForm(comp, true); |
||
65 | |||
66 | if (!p.IsEmpty()) |
||
67 | { |
||
68 | if (!exc.IsEmpty()) |
||
69 | exc += _T('|'); |
||
70 | exc += p; |
||
71 | } |
||
72 | } |
||
73 | return exc; |
||
74 | } |
||
75 | |||
76 | DZStrW ZipOp::MakeExclFilters(void) |
||
77 | { |
||
78 | DZStrW exc; |
||
79 | int n = 0; |
||
80 | while (true) |
||
81 | { |
||
82 | DZStrW arg = CB->UserArg(zcbFSpecArgsExcl, n, 0); |
||
83 | |||
84 | if (arg.IsEmpty()) |
||
85 | break; |
||
86 | |||
87 | if (!exc.IsEmpty()) |
||
88 | exc += _T('|'); |
||
89 | exc += arg; |
||
90 | n++; |
||
91 | } |
||
92 | |||
93 | return ConvExclFilters(exc); |
||
94 | } |
||
95 | #endif |
||
96 | |||
97 | int ZipOp::MakeSpecials(void) |
||
98 | { |
||
99 | DZStrW delims(_T(":;,")); |
||
100 | |||
101 | ZFilter *spcl, *top = 0; |
||
102 | DZStrW s, l, e, o; |
||
103 | int len, v, cnt = 0; |
||
104 | int posn, nxt; |
||
105 | e = CB->UserArg(zcbSpecials, 0, 0); |
||
106 | |||
107 | len = e.length(); |
||
108 | if (len && Verbose < 0) |
||
109 | Notify(IVERBOSE, _T("Do not compress: \"%s\""), e.c_str()); |
||
110 | posn = 0; |
||
111 | |||
112 | while (posn < len) |
||
113 | { |
||
114 | nxt = e.FindOneOf(delims, posn); |
||
115 | |||
116 | if (nxt < 0) |
||
117 | nxt = len; |
||
118 | |||
119 | int ol = nxt - posn; |
||
120 | o = e.Mid(posn, ol).Trim(); |
||
121 | posn = nxt + 1; |
||
122 | if (o.IsEmpty()) |
||
123 | continue; |
||
124 | |||
125 | v = 0; // level |
||
126 | int n = o.Find(_T('|')); |
||
127 | |||
128 | if (n > 0) |
||
129 | { |
||
130 | l = o.Mid(n + 1).TrimLeft(); |
||
131 | o = o.Left(n - 1).TrimRight(); |
||
132 | |||
133 | if (o.IsEmpty()) |
||
134 | continue; |
||
135 | |||
136 | if (!l.IsEmpty()) |
||
137 | v = ((int)l[0]) & 15; |
||
138 | } |
||
139 | |||
140 | // make filter |
||
141 | o.Insert(0, _T('*')); |
||
142 | |||
143 | spcl = new ZFilter(o); |
||
144 | |||
145 | spcl->Level = v; |
||
146 | |||
147 | if (fSpecials == NULL) |
||
148 | fSpecials = spcl; |
||
149 | else |
||
150 | top->Next = spcl; |
||
151 | |||
152 | top = spcl; |
||
153 | |||
154 | cnt++; |
||
155 | } |
||
156 | |||
157 | return cnt; |
||
158 | } |
||
159 | |||
160 | /* =========================================================================== */ |
||
161 | //#ifdef CRYPT |
||
162 | int ZipOp::GetUserPW(void) |
||
163 | { |
||
164 | if (fuser_key && *(fuser_key)) |
||
165 | return DZ_ERR_GOOD; |
||
166 | |||
167 | // get password from user |
||
168 | diag(_T("DLL was not passed a password")); |
||
169 | |||
170 | CB->Arg1 = 1; // request cnt |
||
171 | if (CB->UserCB(zacPassword) == CALLBACK_TRUE) |
||
172 | { |
||
173 | DZStrW pw(CB->Msg, PWLEN); |
||
174 | fkey = fuser_key = AddPW(pw, false); |
||
175 | } |
||
176 | else |
||
177 | return DZ_ERM_PASSWORD_CANCEL; |
||
178 | |||
179 | if (Verbose) |
||
180 | Notify(IVERBOSE, _T("passwords match: %s"), fkey); |
||
181 | |||
182 | return DZ_ERR_GOOD; |
||
183 | } |
||
184 | //#endif |
||
185 | |||
186 | /* =========================================================================== |
||
187 | select files to be processed |
||
188 | */ |
||
189 | int ZipOp::ZipSelect(const DllCommands *C) |
||
190 | { |
||
191 | int r; // temporary variable |
||
192 | long g_before = fbefore; // 1.74 global 'before' |
||
193 | int g_recurse = frecurse; |
||
194 | int g_level = C->fLevel; |
||
195 | g_level = g_level < 0 ? 0 : (g_level > 9 ? 9 : g_level); |
||
196 | bool encrypt; |
||
197 | int argno; |
||
198 | |||
199 | #ifdef DEBUG |
||
200 | fToTest = 0; |
||
201 | fTested = 0; |
||
202 | #endif |
||
203 | fOldFAT = IsFileSystemOldFAT(fRootDir); |
||
204 | MakeSpecials(); |
||
205 | DZStrW g_excludes = MakeExclFilters(); // Process arguments |
||
206 | if (Verbose < 0) |
||
207 | Notify(IVERBOSE, _T("Exclude: \"%s\""), g_excludes.c_str()); |
||
208 | diag(_T("ready to read zip file")); |
||
209 | |||
210 | // the read will be done in file: zipfile.c |
||
211 | if ((r = readzipfile()) != DZ_ERR_GOOD) |
||
212 | { |
||
213 | diag(_T("err returned from \"readzipfile\"")); |
||
214 | return DZError(r); |
||
215 | } |
||
216 | |||
217 | if (faction == UPDATE || faction == FRESHEN) |
||
218 | fdoall = 1; |
||
219 | |||
220 | r = 0; |
||
221 | |||
222 | bool ExcChanged = true; |
||
223 | DZStrW arg, spec, pwd, opt, tmp, theArg; |
||
224 | |||
225 | for (argno = 0; !r; argno++) |
||
226 | { |
||
227 | spec.Empty(); |
||
228 | pwd.Empty(); |
||
229 | if (ExcChanged) |
||
230 | { |
||
231 | fExcludes = g_excludes; |
||
232 | if (Verbose < 0) |
||
233 | Notify(IVERBOSE, _T("Exclude now: \"%s\""), fExcludes.c_str()); |
||
234 | ExcChanged = false; |
||
235 | } |
||
236 | arg = CB->UserArg(zcbFSpecArgs, argno, 0); |
||
237 | |||
238 | arg.TrimLeft(); |
||
239 | if (arg.IsEmpty()) |
||
240 | break; // ran out of args |
||
241 | |||
242 | // reset globals |
||
243 | fkey = 0; |
||
244 | frecurse = g_recurse; |
||
245 | flevel = g_level; |
||
246 | fbefore = g_before; |
||
247 | encrypt = fGEncrypt; |
||
248 | AddBase(fRootDir, true); |
||
249 | AddPW(fGPassword, true); |
||
250 | |||
251 | unsigned index = 0; |
||
252 | TCHAR ch = arg[0]; |
||
253 | if (ch == ZForceNoRecurse || ch == ZForceRecurse) |
||
254 | { |
||
255 | index = 1; |
||
256 | frecurse = (ch == ZForceNoRecurse)? 0 : 1; |
||
257 | } |
||
258 | |||
259 | theArg = GetArg(arg, index, true); |
||
260 | int ffnerr = CleanPath(theArg, spec);//, checkA); |
||
261 | if (ffnerr < 0 || spec.IsEmpty()) |
||
262 | { |
||
263 | Notify(IWARNING, _T("skipping invalid search spec %s"), arg.c_str()); |
||
264 | if (Skipping(arg, 0, SKIPPED_BAD_NAME)) |
||
265 | Fatal(DZ_ERM_SKIPPED, 2); |
||
266 | continue; |
||
267 | } |
||
268 | // check switches |
||
269 | while (arg[index] == '/') |
||
270 | { |
||
271 | // process switches |
||
272 | theArg = GetArg(arg, ++index, true); |
||
273 | if (theArg.length() < 1) |
||
274 | continue; |
||
275 | ch = theArg[0]; // the switch |
||
276 | if (ch > _T('z') || ch < _T('A')) |
||
277 | continue; // invalid |
||
278 | if (ch >= _T('a')) |
||
279 | ch &= 0xDF; // uppercase |
||
280 | |||
281 | if (theArg[1] == _T(':')) |
||
282 | { |
||
283 | switch (ch) |
||
284 | { |
||
285 | case _T('C'): |
||
286 | if (_istdigit(theArg[2])) |
||
287 | { |
||
288 | // new compression level |
||
289 | flevel = theArg[2] - _T('0'); |
||
290 | } |
||
291 | break; |
||
292 | case _T('F'): |
||
293 | // new base |
||
294 | theArg = theArg.Mid(2); |
||
295 | if (theArg.IsEmpty()) |
||
296 | { |
||
297 | // use current dir |
||
298 | if (!GetFullPathName(_T(".\\"), MAX_PATH, theArg.GetBuffer(MAX_PATH), NULL)) |
||
299 | throw DZFatalException(DZ_ERM_MEMORY); |
||
300 | theArg.ReleaseBuffer(); |
||
301 | } |
||
302 | if (theArg.LastChar() != BSLASH) |
||
303 | theArg += BSLASH; |
||
304 | |||
305 | if (!CleanPath(theArg, tmp))//, checkA)) |
||
306 | { |
||
307 | AddBase(tmp, true); |
||
308 | |||
309 | if (Verbose < 0) |
||
310 | Notify(IWARNING, _T("Root dir now %s"), tmp.c_str()); |
||
311 | } |
||
312 | break; |
||
313 | case _T('E'): |
||
314 | tmp = ConvExclFilters(theArg.Mid(2)); |
||
315 | if (tmp.IsEmpty()) |
||
316 | fNoExtChk = 1; |
||
317 | else |
||
318 | if (tmp[0] == _T('|')) |
||
319 | tmp = g_excludes + tmp; // append the new ones |
||
320 | fExcludes = tmp; |
||
321 | ExcChanged = true; |
||
322 | |||
323 | if (Verbose < 0) |
||
324 | Notify(IVERBOSE, _T("Exclude now: \"%s\""), fExcludes.c_str()); |
||
325 | break; |
||
326 | default: |
||
327 | if (Verbose < 0) |
||
328 | Notify(IWARNING, _T("Ignoring invalid switch %s"), theArg.c_str()); |
||
329 | } |
||
330 | continue; |
||
331 | } |
||
332 | if (ch == _T('S')) |
||
333 | { |
||
334 | if (theArg.length() == 1) |
||
335 | { |
||
336 | frecurse = 1; |
||
337 | frecurse = 1; |
||
338 | } |
||
339 | if (theArg.length() == 2 && theArg[1] == _T('-')) |
||
340 | { |
||
341 | frecurse = 0; |
||
342 | } |
||
343 | continue; |
||
344 | } |
||
345 | if (Verbose < 0) |
||
346 | Notify(IWARNING, _T("Ignoring invalid switch %s"), theArg.c_str()); |
||
347 | } |
||
348 | if (arg[index] == ZPasswordFollows) |
||
349 | { |
||
350 | pwd = arg.Mid(++index); |
||
351 | encrypt = !pwd.IsEmpty(); |
||
352 | } |
||
353 | |||
354 | fpcount = fExcludes.IsEmpty() ? 0 : 1; |
||
355 | |||
356 | //#ifdef CRYPT |
||
357 | if (encrypt) |
||
358 | { |
||
359 | // use global unless there is override |
||
360 | if (pwd.IsEmpty()) |
||
361 | fkey = AddPW(fGPassword, true); |
||
362 | else |
||
363 | fkey = AddPW(pwd, true); |
||
364 | |||
365 | if (!fkey || !*(fkey)) |
||
366 | { |
||
367 | // use global |
||
368 | if ((r = GetUserPW()) != DZ_ERR_GOOD) |
||
369 | break; |
||
370 | |||
371 | fkey = fuser_key; |
||
372 | } |
||
373 | } |
||
374 | //#endif |
||
375 | fOldFAT = IsFileSystemOldFAT(spec); |
||
376 | |||
377 | fdoall = 0; // do selected |
||
378 | if (Is_Drv(spec) < 0) |
||
379 | { |
||
380 | if (Verbose < 0) |
||
381 | Notify(IVERBOSE, _T("Collecting stream %s"), spec.c_str()); |
||
382 | |||
383 | r = procname(spec, false); |
||
384 | } |
||
385 | else |
||
386 | { |
||
387 | if ((faction == ADD) || (faction == UPDATE)) |
||
388 | { |
||
389 | if (Verbose < 0) |
||
390 | Notify(IVERBOSE, _T("Collecting %s %s"), spec.c_str(), |
||
391 | (frecurse ? _T("recurse") : _T(" "))); |
||
392 | |||
393 | r = Wild(spec); |
||
394 | } |
||
395 | else // Freshen or Delete - must be internal file |
||
396 | { |
||
397 | if (Verbose < 0) |
||
398 | Notify(IVERBOSE, _T("collecting %s %s"), spec.c_str(), |
||
399 | (frecurse ? _T("recurse") : _T(" "))); |
||
400 | |||
401 | r = procname(spec, frecurse); |
||
402 | } |
||
403 | } |
||
404 | |||
405 | if (r != DZ_ERR_GOOD && |
||
406 | (DZ_ERR(r) == DZ_ERR_MISS || DZ_ERR(r) == DZ_ERR_INVAL_NAME)) |
||
407 | { |
||
408 | /* this occurs if new file wasn't found */ |
||
409 | Notify(r, _T("File specification \"%s\" skipped"), spec.c_str()); |
||
410 | // r = DZ_ERR_GOOD; |
||
411 | if (Skipping(arg, 0, |
||
412 | (DZ_ERR(r) == DZ_ERR_MISS) ? SKIPPED_NO_FILES : SKIPPED_BAD_NAME)) |
||
413 | r = DZ_ERM_SKIPPED; |
||
414 | else |
||
415 | r = DZ_ERR_GOOD; |
||
416 | // } |
||
417 | } |
||
418 | |||
419 | if (r) |
||
420 | return DZError(r); |
||
421 | if (Abort_Flag) |
||
422 | Fatal(DZ_ERM_ABORT, 0); |
||
423 | } |
||
424 | //#ifdef DEBUG |
||
425 | // if (Verbose) |
||
426 | // Notify(IDIAG, "Filter tests - did %Lu of %Lu", fTested, fToTest); |
||
427 | //#endif |
||
428 | return DZ_ERR_GOOD; |
||
429 | } |
||
430 | |||
431 | |||
432 | |||
433 | |||
434 |