source: trunk/dll/copyf.c@ 1421

Last change on this file since 1421 was 1402, checked in by Gregg Young, 17 years ago

Remove variable aurgs from docopy & unlinkf (not used); Move more strings to PCSZs and string table; Move PCSZs to compile time initialization; Fix hang on startup caused by a drive scan and a dircnr scan trying to update a drive in the tree at the same time (related to the "treeswitch options); Code cleanup mainly removal of old printfs, SayMsgs, DbgMsg and unneeded %s.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 23.1 KB
Line 
1
2/***********************************************************************
3
4 $Id: copyf.c 1402 2009-03-14 17:17:59Z gyoung $
5
6 Copy functions
7
8 Copyright (c) 1993-98 M. Kimes
9 Copyright (c) 2001, 2008 Steven H.Levine
10
11 14 Sep 02 SHL Drop obsolete debug code
12 14 Oct 02 SHL Drop obsolete debug code
13 10 Nov 02 SHL docopyf - don't forget to terminate longname
14 optimize longname logic
15 01 Aug 04 SHL Rework lstrip/rstrip usage
16 28 May 05 SHL Drop debug code
17 14 Jul 06 SHL Use Runtime_Error
18 20 Aug 07 GKY Move #pragma alloc_text to end for OpenWatcom compat
19 01 Sep 07 GKY Use xDosSetPathInfo to fix case where FS3 buffer crosses 64k boundry
20 29 Feb 08 GKY Use xfree where appropriate
21 19 Jul 08 GKY Modify MakeTempName for use making temp directory names
22 08 Mar 09 GKY Removed variable aurguments from docopyf and unlinkf (not used)
23
24***********************************************************************/
25
26#include <stdlib.h>
27#include <string.h>
28#include <stdarg.h>
29#include <ctype.h>
30
31#define INCL_DOS
32#define INCL_DOSERRORS
33#define INCL_WIN
34#define INCL_LONGLONG
35
36#include "fm3dll.h"
37#include "fm3dll2.h" // #define's for UM_*, control id's, etc.
38#include "killproc.h" // Data declaration(s)
39#include "notebook.h" // Data declaration(s)
40#include "info.h" // Data declaration(s)
41#include "init.h" // Data declaration(s)
42#include "arccnrs.h"
43#include "fm3str.h"
44#include "errutil.h" // Dos_Error...
45#include "strutil.h" // GetPString
46#include "copyf.h"
47#include "literal.h" // fixup
48#include "misc.h" // Broadcast
49#include "valid.h" // MakeFullName
50#include "wrappers.h" // xDosSetPathInfo
51#include "strips.h" // bstrip
52#include "fortify.h"
53
54static PSZ pszSrcFile = __FILE__;
55
56static CHAR *GetLongName(CHAR * oldname, CHAR * buffer);
57static CHAR *TruncName(CHAR * oldname, CHAR * buffer);
58
59//static CHAR default_disk(VOID);
60//static INT unlink_allf(CHAR * string, ...);
61
62#ifndef WinMoveObject
63HOBJECT APIENTRY WinMoveObject(HOBJECT hObjectofObject,
64 HOBJECT hObjectofDest, ULONG ulReserved);
65#endif
66#ifndef WinCopyObject
67HOBJECT APIENTRY WinCopyObject(HOBJECT hObjectofObject,
68 HOBJECT hObjectofDest, ULONG ulReserved);
69#endif
70
71char *MakeTempName(char *buffer, char *temproot, INT type)
72{
73 FILESTATUS3 fs3;
74 APIRET rc;
75 char *p, *o;
76
77 if (strlen(buffer) > 3 && buffer[strlen(buffer) - 1] != '\\')
78 strcat(buffer, "\\");
79 p = o = buffer + strlen(buffer);
80 switch (type) {
81 case 0:
82 sprintf(p, "%08lx.%03lx", rand() & 4095L, mypid);
83 break;
84 case 1:
85 sprintf(p, "%s%04lx.%03lx", "$FM2", rand() & 4095L, mypid);
86 break;
87 case 2:
88 sprintf(p, "%s.%03x", temproot, (rand() & 4095));
89 break;
90 default:
91 break;
92 }
93 p = buffer + (strlen(buffer) - 1);
94 for (;;) {
95 DosError(FERR_DISABLEHARDERR);
96 rc = DosQueryPathInfo(buffer, FIL_STANDARD, &fs3, sizeof(fs3));
97 if (rc == ERROR_DISK_CHANGE) {
98 DosError(FERR_ENABLEHARDERR);
99 rc = DosQueryPathInfo(buffer, FIL_STANDARD, &fs3, sizeof(fs3));
100 }
101 if (rc)
102 break;
103 Loop:
104 if (p < o) {
105 *buffer = 0;
106 return NULL;
107 }
108 if ((*p) + 1 < 'Z' + 1) {
109 (*p)++;
110 while (strchr("*?<>\":/\\|+=;,[]. ", *p))
111 (*p)++;
112 *p = toupper(*p);
113 }
114 else {
115 p--;
116 if (p >= o && *p == '.')
117 p--;
118 goto Loop;
119 }
120 }
121 return buffer;
122}
123
124CHAR *TruncName(CHAR * oldname, CHAR * buffer)
125{
126 CHAR *p, *f, *s, *o;
127 FILESTATUS3 fs3;
128 APIRET rc;
129
130 if (!buffer || !oldname || !*oldname) {
131 if (buffer)
132 *buffer = 0;
133 return NULL;
134 }
135 strcpy(buffer, oldname);
136 f = strrchr(buffer, '\\');
137 if (!f)
138 f = strrchr(buffer, '/');
139 if (!f)
140 f = buffer;
141 else
142 f++;
143 p = f;
144 o = p;
145 f = oldname + (f - buffer);
146 strupr(buffer);
147 while (*f == '.') /* skip leading '.'s */
148 f++;
149 s = f;
150 while (*f && *f != '.' && f < s + 8) { /* skip past rootname */
151 *p = toupper(*f);
152 p++;
153 f++;
154 }
155 while (*f == '.')
156 f++;
157 s = f;
158 f = strrchr(f, '.');
159 if (f) {
160 while (*f == '.')
161 f++;
162 }
163 if (f && *(f + 1))
164 s = f;
165 else
166 f = s;
167 if (*f) {
168 *p = '.';
169 p++;
170 while (*f && *f != '.' && f < s + 3) {
171 *p = toupper(*f);
172 p++;
173 f++;
174 }
175 }
176 *p = 0;
177
178 p = o;
179 while (*p) {
180 if (strchr("*?<>\":/\\|+=;,[] ", *p) || *p < 0x20)
181 *p = '_';
182 if (*p == '.' && *(p + 1) == '.')
183 *(p + 1) = '_';
184 p++;
185 }
186
187 p = o + (strlen(o) - 1);
188 for (;;) {
189 DosError(FERR_DISABLEHARDERR);
190 rc = DosQueryPathInfo(buffer, FIL_STANDARD, &fs3, sizeof(fs3));
191 if (rc == ERROR_DISK_CHANGE) {
192 DosError(FERR_ENABLEHARDERR);
193 rc = DosQueryPathInfo(buffer, FIL_STANDARD, &fs3, sizeof(fs3));
194 }
195 if (rc)
196 break;
197 Loop:
198 if (p < o) {
199 *buffer = 0;
200 return NULL;
201 }
202 if ((*p) + 1 < 'Z' + 1) {
203 (*p)++;
204 while (strchr("*?<>\":/\\|+=;,[]. ", *p))
205 (*p)++;
206 *p = toupper(*p);
207 }
208 else {
209 p--;
210 if (p >= o && *p == '.')
211 p--;
212 goto Loop;
213 }
214 }
215 return buffer;
216}
217
218CHAR *GetLongName(CHAR * oldname, CHAR * longname)
219{
220 if (!longname)
221 return NULL;
222 *longname = 0;
223 if (!oldname || !*oldname)
224 return NULL;
225 if (IsFullName(oldname)) {
226
227 APIRET rc;
228 EAOP2 eaop;
229 PGEA2LIST pgealist;
230 PFEA2LIST pfealist;
231 PGEA2 pgea;
232 PFEA2 pfea;
233 CHAR *value;
234
235 strcpy(longname, oldname);
236 value = longname;
237 while (*value) {
238 if (*value == '/')
239 *value = '\\';
240 value++;
241 }
242 value = strrchr(longname, '\\');
243 if (value) {
244 value++;
245 *value = 0;
246 }
247 pgealist = xmallocz(sizeof(GEA2LIST) + 32, pszSrcFile, __LINE__);
248 if (pgealist) {
249 pgea = &pgealist->list[0];
250 strcpy(pgea->szName, LONGNAME);
251 pgea->cbName = strlen(pgea->szName);
252 pgea->oNextEntryOffset = 0L;
253 pgealist->cbList = (sizeof(GEA2LIST) + pgea->cbName);
254 pfealist = xmallocz(1536, pszSrcFile, __LINE__);
255 if (pfealist) {
256 pfealist->cbList = 1024;
257 eaop.fpGEA2List = pgealist;
258 eaop.fpFEA2List = pfealist;
259 eaop.oError = 0L;
260 DosError(FERR_DISABLEHARDERR);
261 rc = DosQueryPathInfo(oldname,
262 FIL_QUERYEASFROMLIST,
263 (PVOID) & eaop, (ULONG) sizeof(EAOP2));
264 if (!rc) {
265 pfea = &eaop.fpFEA2List->list[0];
266 value = pfea->szName + pfea->cbName + 1;
267 value[pfea->cbValue] = 0;
268 if (*(USHORT *) value == EAT_ASCII)
269 strncat(longname,
270 value + (sizeof(USHORT) * 2),
271 CCHMAXPATH - strlen(longname));
272 longname[CCHMAXPATH - 1] = 0;
273 }
274 free(pfealist);
275 }
276 free(pgealist);
277 }
278 }
279 return longname;
280}
281
282BOOL ZapLongName(char *filename)
283{
284 return WriteLongName(filename, "");
285}
286
287BOOL WriteLongName(CHAR * filename, CHAR * longname)
288{
289 APIRET rc;
290 EAOP2 eaop;
291 PFEA2LIST pfealist = NULL;
292 ULONG ealen;
293 USHORT len;
294 CHAR *eaval, *p;
295
296 if (!filename || !*filename || !longname)
297 return FALSE;
298 p = strrchr(longname, '\\');
299 if (p)
300 memmove(longname, p + 1, strlen(p + 1) + 1);
301 p = strrchr(longname, '/');
302 if (p)
303 memmove(longname, p + 1, strlen(p + 1) + 1);
304 bstrip(longname);
305 len = strlen(longname);
306 if (len)
307 ealen = sizeof(FEA2LIST) + 10 + len + 4;
308 else
309 ealen = sizeof(FEALIST) + 10;
310 rc = DosAllocMem((PPVOID) & pfealist,
311 ealen + 32L, OBJ_TILE | PAG_COMMIT | PAG_READ | PAG_WRITE);
312 if (rc)
313 Dos_Error(MB_CANCEL, rc, HWND_DESKTOP, pszSrcFile, __LINE__,
314 GetPString(IDS_OUTOFMEMORY));
315 else {
316 memset(pfealist, 0, ealen + 1);
317 pfealist->cbList = ealen;
318 pfealist->list[0].oNextEntryOffset = 0;
319 pfealist->list[0].fEA = 0;
320 pfealist->list[0].cbName = 9;
321 strcpy(pfealist->list[0].szName, LONGNAME);
322 if (len) {
323 eaval = pfealist->list[0].szName + 10;
324 *(USHORT *) eaval = (USHORT) EAT_ASCII;
325 eaval += sizeof(USHORT);
326 *(USHORT *) eaval = (USHORT) len;
327 eaval += sizeof(USHORT);
328 memcpy(eaval, longname, len);
329 pfealist->list[0].cbValue = len + (sizeof(USHORT) * 2);
330 }
331 else
332 pfealist->list[0].cbValue = 0;
333 eaop.fpGEA2List = (PGEA2LIST) 0;
334 eaop.fpFEA2List = pfealist;
335 eaop.oError = 0L;
336 DosError(FERR_DISABLEHARDERR);
337 rc = xDosSetPathInfo(filename, FIL_QUERYEASIZE,
338 &eaop, sizeof(eaop), DSPI_WRTTHRU);
339 DosFreeMem(pfealist);
340 if (rc)
341 return FALSE;
342 }
343 return TRUE;
344}
345
346BOOL AdjustWildcardName(CHAR * oldname, CHAR * newname)
347{
348 BOOL ret = FALSE;
349
350 /* NOTE: newname should be CCHMAXPATH chars long! */
351
352 if (strchr(newname, '*') || strchr(newname, '?')) {
353
354 CHAR srce[CCHMAXPATHCOMP], dest[CCHMAXPATHCOMP], result[CCHMAXPATHCOMP],
355 *p;
356
357 p = strrchr(newname, '\\');
358 if (p && *(p + 1)) {
359 strcpy(dest, p + 1);
360 p = strrchr(oldname, '\\');
361 if (p && *(p + 1)) {
362 strcpy(srce, p + 1);
363 DosError(FERR_DISABLEHARDERR);
364 if (!DosEditName(1L, srce, dest, (PBYTE)result, (ULONG)sizeof(result))) {
365 p = strrchr(newname, '\\');
366 p++;
367 strcpy(p, result);
368 ret = TRUE;
369 }
370 }
371 }
372 }
373 return ret;
374}
375
376#if 0 // JBS 11 Sep 08
377CHAR default_disk(VOID)
378{
379 ULONG ulDriveNum, ulDriveMap;
380
381 DosError(FERR_DISABLEHARDERR);
382 DosQCurDisk(&ulDriveNum, &ulDriveMap);
383 return (CHAR) toupper((INT) ulDriveNum) + '@';
384}
385#endif
386
387#ifdef NEVER
388
389APIRET docopyallf(INT type, CHAR * oldname, CHAR * newname, ...)
390{
391 FILEFINDBUF3 fb;
392 ULONG nm;
393 HDIR hdir;
394 APIRET rc = 0;
395 CHAR *enddir, fullname[CCHMAXPATH];
396
397 va_start(ap, newname);
398 vsprintf(fullname, newname, ap);
399 va_end(ap);
400
401 DosError(FERR_DISABLEHARDERR);
402 if (!DosFindFirst(oldname)) {
403 do {
404
405 /* build target name */
406
407 if (fb.attrFile & FILE_DIRECTORY) {
408 DosError(FERR_ENABLEHARDERR);
409 rc = DosCreateDir();
410 if (rc == ERROR_INVALID_NAME || rc == ERROR_FILENAME_EXCED_RANGE) {
411
412 /* truncate directory name */
413 /* create that directory */
414 /* update containers for name used */
415
416 }
417 rc = docopyallf(type,, "%s",); /* recurse */
418 }
419 else
420 // docopyf changed this won't work rc = docopyf(type,, "%s",); /* copy file */
421 DosError(FERR_DISABLEHARDERR);
422 } while (!rc && !DosFindNext());
423 DosFindClose(hdir);
424 }
425 else
426 rc = ERROR_FILE_NOT_FOUND;
427 return rc;
428}
429
430#endif
431
432APIRET docopyf(INT type, CHAR *oldname, CHAR *newname)
433{
434 /*
435 * returns:
436 * 0: success
437 * -1: bad string parameter(s)
438 * -2: source didn't exist
439 * -3: bad type
440 * anything else: API return
441 */
442
443 CHAR longname[CCHMAXPATH], shortname[CCHMAXPATH];
444 CHAR olddisk, newdisk, dir[CCHMAXPATH], *p, *pp;
445 APIRET ret = -1, rc;
446 FILESTATUS3L st, st2, dummy;
447 BOOL diskchange = FALSE, zaplong = FALSE;
448
449 *shortname = *dir = 0;
450
451 if (!oldname || !*oldname || !*newname) /* bad string args */
452 return (APIRET) - 1;
453
454 DosError(FERR_DISABLEHARDERR);
455 if (DosQueryPathInfo(oldname, FIL_STANDARDL, &st, sizeof(FILESTATUS3L)))
456 return (APIRET) - 2; /* no source */
457
458 AdjustWildcardName(oldname, newname);
459 MakeFullName(oldname);
460 MakeFullName(newname);
461 olddisk = toupper(*oldname); /* source drive */
462 newdisk = toupper(*newname); /* destination drive */
463 if (!(driveflags[toupper(*oldname) - 'A'] & DRIVE_NOLONGNAMES))
464 *longname = 0;
465 else {
466 GetLongName(oldname, longname);
467 if (*longname) {
468 p = RootName(longname);
469 if (p != longname)
470 memmove(longname, p, strlen(p) + 1);
471 }
472 }
473 /* If root name changed make sure longname EA goes away */
474 p = RootName(oldname);
475 pp = RootName(newname);
476 if (stricmp(p, pp)) {
477 zaplong = TRUE;
478 }
479
480 DosError(FERR_DISABLEHARDERR);
481 switch (type) {
482 case WPSMOVE:
483 {
484 HOBJECT hobjsrc;
485 HOBJECT hobjdest;
486
487 ret = ERROR_FILE_NOT_FOUND;
488 hobjsrc = WinQueryObject(oldname);
489 if (hobjsrc) {
490 strcpy(dir, newname);
491 p = strrchr(dir, '\\');
492 if (p < dir + 3)
493 p++;
494 *p = 0;
495 ret = ERROR_PATH_NOT_FOUND;
496 hobjdest = WinQueryObject(dir);
497 if (hobjdest) {
498 ret = ERROR_GEN_FAILURE;
499 hobjsrc = WinMoveObject(hobjsrc, hobjdest, 0);
500 if (hobjsrc)
501 ret = 0;
502 }
503 }
504 }
505 return ret;
506
507 case WPSCOPY:
508 {
509 HOBJECT hobjsrc;
510 HOBJECT hobjdest;
511
512 ret = ERROR_FILE_NOT_FOUND;
513 hobjsrc = WinQueryObject(oldname);
514 if (hobjsrc) {
515 strcpy(dir, newname);
516 p = strrchr(dir, '\\');
517 if (p < dir + 3)
518 p++;
519 *p = 0;
520 ret = ERROR_PATH_NOT_FOUND;
521 hobjdest = WinQueryObject(dir);
522 if (hobjdest) {
523 ret = ERROR_GEN_FAILURE;
524 hobjsrc = WinCopyObject(hobjsrc, hobjdest, 0);
525 if (hobjsrc)
526 ret = 0;
527 }
528 }
529 }
530 return ret;
531
532 case MOVE:
533 *dir = 0;
534 if (olddisk == newdisk) { /* same drive */
535 /* make temporary copy in case move fails */
536 if (IsFile(newname) != -1 && stricmp(oldname, newname)) {
537 strcpy(dir, newname);
538 p = strrchr(dir, '\\');
539 if (p)
540 *p = 0;
541 strcat(dir, "\\");
542 MakeTempName(dir, NULL, 0);
543 if (DosMove(newname, dir))
544 *dir = 0;
545 }
546 DosError(FERR_DISABLEHARDERR);
547 ret = DosMove(oldname, newname); /* move it */
548 if (ret && *dir) { /* failed -- clean up */
549 DosError(FERR_DISABLEHARDERR);
550 if (!DosMove(dir, newname))
551 Broadcast((HAB) 0, hwndMain, UM_UPDATERECORD, MPFROMP(dir), MPVOID);
552 }
553 else if (!ret && *dir) {
554 if (!IsFile(dir)) {
555 if (!strchr(dir, '?') && !strchr(dir, '*'))
556 wipeallf("%s\\*", dir);
557 DosError(FERR_DISABLEHARDERR);
558 if (DosDeleteDir(dir)) {
559 make_deleteable(dir);
560 DosDeleteDir(dir);
561 }
562 }
563 else if (IsFile(dir) > 0) {
564 DosError(FERR_DISABLEHARDERR);
565 if (DosForceDelete(dir)) {
566 make_deleteable(dir);
567 DosForceDelete(dir);
568 }
569 if (zaplong)
570 ZapLongName(dir);
571 Broadcast((HAB) 0, hwndMain, UM_UPDATERECORD, MPFROMP(dir), MPVOID);
572 }
573 }
574 }
575 else { /* different drives */
576 DosError(FERR_DISABLEHARDERR);
577 ret = DosCopy(oldname, newname, DCPY_EXISTING); /* <=-NOTE! */
578 if (ret == ERROR_DISK_CHANGE) {
579 DosError(FERR_ENABLEHARDERR);
580 ret = DosCopy(oldname, newname, DCPY_EXISTING);
581 diskchange = TRUE;
582 }
583 if (ret == ERROR_INVALID_NAME || ret == ERROR_FILENAME_EXCED_RANGE) {
584 if (TruncName(newname, shortname)) { /* make 8.3 filename */
585 DosError(FERR_DISABLEHARDERR);
586 ret = DosCopy(oldname, shortname, DCPY_EXISTING);
587 if (!ret) { /* success -- write longname ea */
588 WriteLongName(shortname, newname);
589 strcpy(newname, shortname);
590 /* broadcast fixup msg to windows */
591 Broadcast((HAB) 0,
592 hwndMain, UM_UPDATERECORD, MPFROMP(shortname), MPVOID);
593 }
594 }
595 }
596 else if (!ret && *longname) {
597
598 CHAR fixname[CCHMAXPATH];
599
600 strcpy(fixname, newname);
601 p = strrchr(fixname, '\\');
602 if (p) {
603 p++;
604 *p = 0;
605 }
606 strcat(fixname, longname);
607 DosError(FERR_DISABLEHARDERR);
608 DosMove(newname, fixname);
609 strcpy(newname, fixname);
610 if (zaplong)
611 ZapLongName(fixname);
612 Broadcast((HAB) 0,
613 hwndMain, UM_UPDATERECORD, MPFROMP(fixname), MPVOID);
614 }
615 if (!ret) { /* double-check success */
616 DosError(FERR_DISABLEHARDERR);
617 rc = DosQueryPathInfo(newname,
618 FIL_STANDARDL, &st2, sizeof(FILESTATUS3L));
619 if (rc == ERROR_DISK_CHANGE) {
620 DosError(FERR_ENABLEHARDERR);
621 rc = DosQueryPathInfo(newname,
622 FIL_STANDARDL, &st2, sizeof(FILESTATUS3L));
623 }
624 if (!rc && st2.cbFile == st.cbFile) { /* seems to have worked... */
625 DosError(FERR_DISABLEHARDERR);
626 if (diskchange) {
627 DosError(FERR_ENABLEHARDERR);
628 DosQueryPathInfo(oldname, FIL_STANDARDL, &dummy, sizeof(FILESTATUS3L)); /* force disk change */
629 }
630 if (!(st2.attrFile & FILE_DIRECTORY)) /* erase file */
631 unlinkf(oldname);
632 else { /* remove directory */
633 wipeallf("%s\\*", oldname);
634 DosError(FERR_DISABLEHARDERR);
635 if (DosDeleteDir(oldname)) {
636 make_deleteable(oldname);
637 DosDeleteDir(oldname);
638 }
639 }
640 }
641 }
642 }
643 return ret;
644
645 case COPY:
646 DosError(FERR_DISABLEHARDERR);
647 ret = DosCopy(oldname, newname, DCPY_EXISTING); /* <=-NOTE! */
648 if (ret == ERROR_DISK_CHANGE) {
649 DosError(FERR_ENABLEHARDERR);
650 ret = DosCopy(oldname, newname, DCPY_EXISTING);
651 diskchange = TRUE;
652 }
653 if (ret == ERROR_INVALID_NAME || ret == ERROR_FILENAME_EXCED_RANGE) {
654 if (TruncName(newname, shortname)) {
655 DosError((diskchange) ? FERR_ENABLEHARDERR : FERR_DISABLEHARDERR);
656 ret = DosCopy(oldname, shortname, DCPY_EXISTING);
657 if (!ret) {
658 WriteLongName(shortname, newname);
659 strcpy(newname, shortname);
660 Broadcast((HAB) 0,
661 hwndMain, UM_UPDATERECORD, MPFROMP(shortname), MPVOID);
662 }
663 }
664 }
665 else if (!ret && *longname) {
666
667 CHAR fixname[CCHMAXPATH];
668
669 strcpy(fixname, newname);
670 p = strrchr(fixname, '\\');
671 if (p) {
672 p++;
673 *p = 0;
674 }
675 strcat(fixname, longname);
676 DosError(FERR_DISABLEHARDERR);
677 DosMove(newname, fixname);
678 if (zaplong)
679 ZapLongName(fixname);
680 Broadcast((HAB) 0, hwndMain, UM_UPDATERECORD, MPFROMP(fixname), MPVOID);
681 }
682 return ret;
683
684 default: /* shouldn't happen */
685 Runtime_Error(pszSrcFile, __LINE__, "bad case %u", type);
686 break;
687 }
688 return (APIRET) - 3; /* bad type */
689}
690
691INT make_deleteable(CHAR * filename)
692{
693 INT ret = -1;
694 FILESTATUS3 fsi;
695
696 DosError(FERR_DISABLEHARDERR);
697 if (!DosQueryPathInfo(filename, FIL_STANDARD, &fsi, sizeof(fsi))) {
698 fsi.attrFile = 0;
699 DosError(FERR_DISABLEHARDERR);
700 if (!xDosSetPathInfo(filename, FIL_STANDARD, &fsi, sizeof(fsi), 0))
701 ret = 0;
702 }
703 return ret;
704}
705
706INT wipeallf(CHAR *string, ...)
707{
708 /* unlink everything from directory on down... */
709
710 FILEFINDBUF3 *f;
711 HDIR search_handle;
712 ULONG num_matches;
713 CHAR *p, *ss, *str;
714 CHAR s[CCHMAXPATH], mask[257];
715 va_list ap;
716 INT rc;
717
718 va_start(ap, string);
719 vsprintf(s, string, ap);
720 va_end(ap);
721
722 if (!*s)
723 return -1;
724 p = s;
725 while ((p = strchr(p, '/')) != NULL) {
726 *p = '\\';
727 p++;
728 }
729
730 str = xstrdup(s, pszSrcFile, __LINE__);
731 if (!str)
732 return -1;
733
734 { /* safety net -- disallow deleting a root dir or partial name */
735 CHAR temp;
736
737 p = strrchr(str, '\\');
738 if (p) {
739 p++;
740 temp = *p;
741 *p = 0;
742 if (IsRoot(str) || !IsFullName(str)) {
743 /* under no circumstances! */
744 Runtime_Error(pszSrcFile, __LINE__, "bad name %s", str);
745 free(str);
746 return -1;
747 }
748 *p = temp;
749 }
750 }
751
752 p = s;
753 p = strrchr(s, '\\'); /* strip s to just path */
754 if (!p)
755 p = strrchr(s, ':');
756 if (p) {
757 p++;
758 strncpy(mask, p, 256);
759 mask[256] = 0;
760 *p = 0;
761 }
762 else {
763 *mask = 0;
764 *s = 0;
765 }
766
767 ss = xmalloc(CCHMAXPATH, pszSrcFile, __LINE__);
768 f = xmalloc(sizeof(FILEFINDBUF3), pszSrcFile, __LINE__);
769 if (!ss || !f) {
770 xfree(ss, pszSrcFile, __LINE__);
771 xfree(f, pszSrcFile, __LINE__);
772 free(str);
773 return -1;
774 }
775
776 search_handle = HDIR_CREATE;
777 num_matches = 1;
778
779 DosError(FERR_DISABLEHARDERR);
780 if (!DosFindFirst(str, &search_handle, FILE_NORMAL | FILE_DIRECTORY |
781 FILE_SYSTEM | FILE_READONLY | FILE_HIDDEN | FILE_ARCHIVED,
782 f, sizeof(FILEFINDBUF3), &num_matches, FIL_STANDARD)) {
783
784 strcpy(ss, s);
785 p = &ss[strlen(ss)];
786
787 do {
788 strcpy(p, f->achName);
789 if (f->attrFile & FILE_DIRECTORY) {
790 if (strcmp(f->achName, ".") && strcmp(f->achName, "..")) {
791 wipeallf("%s/%s", ss, mask); /* recurse to wipe files */
792 DosError(FERR_DISABLEHARDERR);
793 if (DosDeleteDir(ss)) { /* remove directory */
794 make_deleteable(ss);
795 DosError(FERR_DISABLEHARDERR);
796 DosDeleteDir(ss);
797 }
798 }
799 }
800 else {
801 DosError(FERR_DISABLEHARDERR);
802 if (DosForceDelete(ss)) {
803 make_deleteable(ss);
804 DosError(FERR_DISABLEHARDERR);
805 rc = (INT) DosForceDelete(ss);
806 if (rc)
807 return rc;
808 }
809 }
810 num_matches = 1;
811 DosError(FERR_DISABLEHARDERR);
812 } while (!DosFindNext(search_handle, f, sizeof(FILEFINDBUF3),
813 &num_matches));
814 DosFindClose(search_handle);
815 }
816
817 free(f);
818 free(ss);
819 free(str);
820 return 0;
821}
822
823#if 0 // JBS 11 Sep 08
824INT unlink_allf(CHAR * string, ...)
825{
826 /* wildcard delete */
827
828 FILEFINDBUF3 *f;
829 HDIR search_handle;
830 ULONG num_matches;
831 CHAR *p, *ss, *str;
832 CHAR s[CCHMAXPATH];
833 va_list ap;
834
835 va_start(ap, string);
836 vsprintf(s, string, ap);
837 va_end(ap);
838
839 if (!*s)
840 return -1;
841 p = s;
842 while ((p = strchr(p, '/')) != NULL) {
843 *p = '\\';
844 p++;
845 }
846
847 str = xstrdup(s, pszSrcFile, __LINE__);
848 if (!str)
849 return -1;
850
851 p = s;
852 p = strrchr(s, '\\'); /* strip s to just path */
853 if (!p)
854 p = strrchr(s, ':');
855 if (p) {
856 p++;
857 *p = 0;
858 }
859 else
860 *s = 0;
861
862 ss = xmalloc(CCHMAXPATH, pszSrcFile, __LINE__);
863 f = xmalloc(sizeof(FILEFINDBUF3), pszSrcFile, __LINE__);
864 if (!ss || !f) {
865 xfree(ss, pszSrcFile, __LINE__);
866 xfree(f, pszSrcFile, __LINE__);
867 free(str);
868 return -1;
869 }
870
871 search_handle = HDIR_CREATE;
872 num_matches = 1;
873
874 DosError(FERR_DISABLEHARDERR);
875 if (!DosFindFirst(str, &search_handle, FILE_NORMAL, f,
876 sizeof(FILEFINDBUF3), &num_matches, FIL_STANDARD)) {
877
878 strcpy(ss, s);
879 p = &ss[strlen(ss)];
880
881 do {
882 strcpy(p, f->achName);
883 unlinkf("%s", ss);
884 num_matches = 1;
885 DosError(FERR_DISABLEHARDERR);
886 } while (!DosFindNext(search_handle, f, sizeof(FILEFINDBUF3),
887 &num_matches));
888 DosFindClose(search_handle);
889 }
890
891 free(f);
892 free(ss);
893 free(str);
894 return 0;
895}
896#endif
897
898INT unlinkf(CHAR *string)
899{
900
901 if (!strstr(string, ArcTempRoot)) {
902 DosError(FERR_DISABLEHARDERR);
903 if (DosDelete(string)) {
904 make_deleteable(string);
905 DosError(FERR_DISABLEHARDERR);
906 return DosDelete(string);
907 }
908 }
909 else {
910 DosError(FERR_DISABLEHARDERR);
911 if (DosForceDelete(string)) {
912 make_deleteable(string);
913 DosError(FERR_DISABLEHARDERR);
914 return DosForceDelete(string);
915 }
916 }
917 return 0;
918}
919
920#pragma alloc_text(LONGNAMES,TruncName,GetLongName,WriteLongName)
921#pragma alloc_text(LONGNAMES,ZapLongName,AdjustWildcardName)
922#pragma alloc_text(COPYF,default_disk,docopyf,MakeTempName)
923#pragma alloc_text(UNLINKF,unlinkf,unlink_allf,make_deleteable,wipeallf)
Note: See TracBrowser for help on using the repository browser.