source: trunk/dll/seeall.c @ 766

Last change on this file since 766 was 766, checked in by Gregg Young, 13 years ago

format cleanup

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 114.6 KB
Line 
1
2/***********************************************************************
3
4  $Id: seeall.c 766 2007-08-05 20:21:20Z gyoung $
5
6  See all matching files
7
8  Copyright (c) 1993-98 M. Kimes
9  Copyright (c) 2001, 2006 Steven H. Levine
10
11  16 Oct 02 SHL Handle large partitions
12  25 Nov 03 SHL StartSeeAll: avoid forgetting startpath
13  06 Dec 03 SHL StartSeeAll: correct malloc arg oops
14  23 May 05 SHL Use QWL_USER
15  25 May 05 SHL Use ULONGLONG and CommaFmtULL
16  05 Jun 05 SHL Use QWL_USER
17  06 Jun 05 SHL Drop unused code
18  29 May 06 SHL Comments
19  17 Jul 06 SHL Use Runtime_Error
20  19 Oct 06 SHL Correct . and .. detect
21  03 Nov 06 SHL Renames
22  03 Nov 06 SHL Count thread usage
23  30 Mar 07 GKY Remove GetPString for window class names
24  03 Aug 07 GKY Enlarged and made setable everywhere Findbuf (speed file loading)
25
26***********************************************************************/
27
28#define INCL_DOS
29#define INCL_DOSERRORS
30#define INCL_WIN
31#define INCL_GPI
32#define INCL_LONGLONG
33#include <os2.h>
34
35#include <stdlib.h>
36#include <stdio.h>
37#include <string.h>
38#include <ctype.h>
39#include <process.h>
40
41#include "fm3dll.h"
42#include "fm3dlg.h"
43#include "fm3str.h"
44
45#pragma data_seg(DATA2)
46
47static PSZ pszSrcFile = __FILE__;
48
49#pragma alloc_text(SEEALL,comparefullnames,comparenames,comparesizes)
50#pragma alloc_text(SEEALL,comparedates,compareexts,SeeStatusProc)
51#pragma alloc_text(SEEALL,InitWindow,PaintLine,SeeAllWndProc)
52#pragma alloc_text(SEEALL,UpdateList,CollectList,ReSort,Mark)
53#pragma alloc_text(SEEALL,BuildAList,RemoveDeleted,SeeFrameWndProc,FilterList)
54#pragma alloc_text(SEEALL2,SeeObjWndProc,MakeSeeObjWinThread,FindDupes,DupeDlgProc)
55#pragma alloc_text(SEEALL3,FreeAllFilesList,DoADir,FindAllThread,AFDrvsWndProc)
56#pragma alloc_text(SEEALL3,StartSeeAll)
57
58typedef struct
59{
60  CHAR *fullname, *filename;
61  USHORT attrFile, flags;
62  FDATE date;
63  FTIME time;
64  ULONG cbFile, CRC;
65}
66ALLFILES;
67
68#define AF_SELECTED     0x0001
69#define AF_DELETED      0x0002
70#define AF_FILTERED     0x0004
71#define AF_DUPE         0x0008
72#define AF_CRCED        0x0010
73
74#define AFM_MARK        0
75#define AFM_UNMARK      1
76#define AFM_INVERT      2
77#define AFM_MARKDELETED 3
78#define AFM_FILTER      4
79
80#define DP_NAMES        0x0001
81#define DP_DATES        0x0002
82#define DP_SIZES        0x0004
83#define DP_CRCS         0x0008
84#define DP_EXTS         0x0010
85
86#define FIXED_FONT_LCID 5
87
88#define COLORS_MAX                   8
89
90#define COLORS_CURSOREDNORMALBACK    0
91#define COLORS_CURSOREDSELECTEDBACK  1
92#define COLORS_NORMALBACK            2
93#define COLORS_SELECTEDBACK          3
94#define COLORS_SELECTEDNORMALFORE    4
95#define COLORS_NORMALFORE            5
96#define COLORS_READONLYFORE          6
97#define COLORS_SYSTEMFORE            7
98
99static LONG Colors[COLORS_MAX] = { COLR_WHITE, COLR_DARKGRAY, COLR_PALEGRAY,
100  COLR_BLACK, COLR_WHITE, COLR_BLACK,
101  COLR_DARKBLUE, COLR_DARKRED
102};
103
104typedef int (FNSORT) (const void *, const void *);
105typedef FNSORT *PFNSORT;
106
107typedef struct
108{
109  USHORT size;
110  USHORT dupeflags;
111  ALLFILES *afhead;
112  ALLFILES **afindex;
113  ULONG affiles;
114  ULONG afalloc;
115  ULONG afFilesToGet;
116  ULONG longest;
117  ULONG longestw;
118  ULONG topfile;
119  ULONG cursored;
120  ULONG selected;
121  ULONGLONG ullSelectedBytes;
122  ULONG afifiles;
123  ULONG lastselected;
124  ULONG lastdirection;
125  ULONG multiplier;
126  ULONG lasttime;
127  CHAR stopflag;
128  CHAR abDrvFlags[26];
129  CHAR szCommonName[CCHMAXPATH];
130  CHAR szFindPath[CCHMAXPATH];
131  LONG lMaxAscender;
132  LONG lMaxDescender;
133  LONG lMaxHeight;
134  LONG maxx;
135  LONG horzscroll;
136  BOOL fullnames;
137  BOOL invertsort;
138  BOOL mousecaptured;
139  HMTX hmtxScan;
140  HWND hvscroll;
141  HWND hhscroll;
142  HWND hwndMenu;
143  HWND hwndObj;
144  HWND hwndClient;
145  HWND hwndPopup;
146  HWND hwndStatus;
147  HWND hwndFrame;
148  HPS hps;
149  PFNSORT pfnCompare;
150  MASK mask;
151  FATTRS fattrs;
152  LONG aulColors[8];
153  BOOL killme;
154}
155ALLDATA;
156
157static BOOL Fullnames = FALSE;
158static BOOL Firsttime = TRUE;
159static BOOL SortReverse;
160static USHORT Codepage, SortType;
161static FATTRS Fattrs;
162
163extern LONG CRCFile(CHAR * filename, INT * error);
164
165MRESULT EXPENTRY DupeDlgProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
166{
167  switch (msg) {
168  case WM_INITDLG:
169    {
170      USHORT flags = SHORT1FROMMP(mp2);
171
172      WinCheckButton(hwnd, DUPE_NAMES, ((flags & DP_NAMES) != 0));
173      WinCheckButton(hwnd, DUPE_DATES, ((flags & DP_NAMES) != 0));
174      WinCheckButton(hwnd, DUPE_SIZES, ((flags & DP_NAMES) != 0));
175      WinCheckButton(hwnd, DUPE_CRCS, ((flags & DP_NAMES) != 0));
176      if (!(flags & DP_NAMES))
177        WinEnableWindow(WinWindowFromID(hwnd, DUPE_EXTS), FALSE);
178    }
179    break;
180
181  case WM_CONTROL:
182    switch (SHORT1FROMMP(mp1)) {
183    case DUPE_NAMES:
184      if (WinQueryButtonCheckstate(hwnd, DUPE_NAMES))
185        WinEnableWindow(WinWindowFromID(hwnd, DUPE_EXTS), TRUE);
186      else {
187        WinCheckButton(hwnd, DUPE_EXTS, FALSE);
188        WinEnableWindow(WinWindowFromID(hwnd, DUPE_EXTS), FALSE);
189      }
190      break;
191    case DUPE_SIZES:
192      if (!WinQueryButtonCheckstate(hwnd, DUPE_SIZES))
193        WinCheckButton(hwnd, DUPE_CRCS, FALSE);
194      break;
195    case DUPE_CRCS:
196      if (WinQueryButtonCheckstate(hwnd, DUPE_CRCS))
197        WinCheckButton(hwnd, DUPE_SIZES, TRUE);
198      break;
199    }
200    return 0;
201
202  case WM_COMMAND:
203    switch (SHORT1FROMMP(mp1)) {
204    case DID_OK:
205      {
206        USHORT flags = 0;
207
208        if (WinQueryButtonCheckstate(hwnd, DUPE_NAMES)) {
209          flags |= DP_NAMES;
210          if (WinQueryButtonCheckstate(hwnd, DUPE_EXTS))
211            flags |= DP_EXTS;
212        }
213        if (WinQueryButtonCheckstate(hwnd, DUPE_DATES))
214          flags |= DP_DATES;
215        if (WinQueryButtonCheckstate(hwnd, DUPE_SIZES)) {
216          flags |= DP_SIZES;
217          if (WinQueryButtonCheckstate(hwnd, DUPE_CRCS))
218            flags |= (DP_CRCS | DP_SIZES);
219        }
220        if (!flags)
221          saymsg(MB_ENTER,
222                 hwnd,
223                 GetPString(IDS_ERRORTEXT),
224                 "%s", GetPString(IDS_CHECKONETEXT));
225        else
226          WinDismissDlg(hwnd, flags);
227      }
228      break;
229
230    case DID_CANCEL:
231      WinDismissDlg(hwnd, 0);
232      break;
233
234    case IDM_HELP:
235      if (hwndHelp)
236        WinSendMsg(hwndHelp, HM_DISPLAY_HELP,
237                   MPFROM2SHORT(HELP_DUPES, 0), MPFROMSHORT(HM_RESOURCEID));
238      break;
239    }
240    return 0;
241  }
242  return WinDefDlgProc(hwnd, msg, mp1, mp2);
243}
244
245static ULONG NumLines(RECTL * rcl, ALLDATA * ad)
246{
247  ULONG numlines;
248
249  numlines = (rcl->yTop - rcl->yBottom) / ad->lMaxHeight;
250  if (ad->lMaxDescender && numlines &&
251      ((rcl->yTop - rcl->yBottom) -
252       (numlines * ad->lMaxHeight) <= ad->lMaxDescender))
253    numlines--;
254  return numlines;
255}
256
257MRESULT EXPENTRY SeeObjWndProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
258{
259  switch (msg) {
260  case UM_MASSACTION:
261    {
262      CHAR **files = NULL, **list = (CHAR **) mp2, path[CCHMAXPATH];
263      INT numfiles = 0, numalloc = 0, plen = 0;
264      HWND hwndFrame = WinQueryWindowULong(hwnd, QWL_USER);
265      CHAR message[CCHMAXPATH * 2], wildname[CCHMAXPATH];
266      register INT x;
267      register CHAR *p, *pp;
268      BOOL dontask = FALSE, wildcarding = FALSE,
269        overold = FALSE, overnew = FALSE;
270
271      if (!list || !list[0])
272        goto Abort;
273      *path = *wildname = 0;
274
275      switch (SHORT1FROMMP(mp1)) {
276      case IDM_MOVEPRESERVE:
277        {
278          CHAR preserve[CCHMAXPATH], *end;
279
280          mp1 = MPFROM2SHORT(IDM_MOVE, SHORT2FROMMP(mp1));
281          strcpy(preserve, list[0] + 2);
282          end = strrchr(preserve, '\\');
283          if (end) {
284            end++;
285            for (x = 1; list[x]; x++) {
286              p = preserve;
287              pp = list[x] + 2;
288              while (p < end && toupper(*p) == toupper(*pp)) {
289                p++;
290                pp++;
291              }
292              if (*p == '\\')
293                p++;
294              if (p < end)
295                end = p;
296            }
297            *end = 0;
298          }
299          else
300            *preserve = 0;
301          plen = strlen(preserve);
302          if (plen)
303            plen += 2;
304        }
305        break;
306      case IDM_COPYPRESERVE:
307        {
308          CHAR preserve[CCHMAXPATH], *end;
309
310          mp1 = MPFROM2SHORT(IDM_COPY, SHORT2FROMMP(mp1));
311          strcpy(preserve, list[0] + 2);
312          end = strrchr(preserve, '\\');
313          if (end) {
314            end++;
315            for (x = 1; list[x]; x++) {
316              p = preserve;
317              pp = list[x] + 2;
318              while (p < end && toupper(*p) == toupper(*pp)) {
319                p++;
320                pp++;
321              }
322              if (*p == '\\')
323                p++;
324              if (p < end)
325                end = p;
326            }
327            *end = 0;
328          }
329          else
330            *preserve = 0;
331          plen = strlen(preserve);
332          if (plen)
333            plen += 2;
334        }
335        break;
336      case IDM_WILDMOVE:
337        wildcarding = TRUE;
338        mp1 = MPFROM2SHORT(IDM_MOVE, SHORT2FROMMP(mp1));
339        break;
340      case IDM_WILDRENAME:
341        wildcarding = TRUE;
342        mp1 = MPFROM2SHORT(IDM_RENAME, SHORT2FROMMP(mp1));
343        break;
344      case IDM_WILDCOPY:
345        wildcarding = TRUE;
346        mp1 = MPFROM2SHORT(IDM_COPY, SHORT2FROMMP(mp1));
347        break;
348      }
349
350      switch (SHORT1FROMMP(mp1)) {
351      case IDM_OBJECT:
352      case IDM_SHADOW:
353        {
354          APIRET rc;
355
356          GetDesktopName(path, sizeof(path));
357          rc = WinDlgBox(HWND_DESKTOP,
358                         hwndFrame,
359                         ObjCnrDlgProc,
360                         FM3ModHandle, OBJCNR_FRAME, MPFROMP(path));
361          if (rc) {
362            if (rc > 1)
363              strcpy(path, "<WP_DESKTOP>");
364          }
365          else {
366            FreeList(list);
367            break;
368          }
369          MakeShadows(hwndFrame,
370                      list, (SHORT1FROMMP(mp1) == IDM_SHADOW), path, NULL);
371        }
372        FreeList(list);
373        break;
374
375      case IDM_PRINT:
376        {
377          LISTINFO *li;
378
379          li = xmallocz(sizeof(LISTINFO), pszSrcFile, __LINE__);
380          if (li) {
381            li->hwndS = WinWindowFromID(hwndFrame, FID_CLIENT);
382            li->type = IDM_PRINT;
383            li->list = list;
384            if (WinDlgBox(HWND_DESKTOP,
385                          li->hwndS,
386                          PrintDlgProc,
387                          FM3ModHandle, PRN_FRAME, MPFROMP(li))) {
388              if (li && li->list && li->list[0]) {
389                strcpy(li->targetpath, printer);
390                if (_beginthread(PrintListThread, NULL, 65536, (PVOID) li) ==
391                    -1) {
392                  Runtime_Error(pszSrcFile, __LINE__,
393                                GetPString(IDS_COULDNTSTARTTHREADTEXT));
394                  FreeListInfo(li);
395                }
396              }
397            }
398          }
399        }
400        break;
401
402      case IDM_EAS:
403        if (WinDlgBox(HWND_DESKTOP,
404                      hwndFrame,
405                      DisplayEAsProc, FM3ModHandle, EA_FRAME, (PVOID) list)) {
406          if (!PostMsg(WinWindowFromID(hwndFrame, FID_CLIENT),
407                       UM_UPDATERECORDLIST, MPFROMP(list), MPVOID))
408            FreeList(list);
409        }
410        else
411          FreeList(list);
412        break;
413
414      case IDM_INFO:
415        if (WinDlgBox(HWND_DESKTOP,
416                      hwndFrame,
417                      FileInfoProc,
418                      FM3ModHandle, FLE_FRAME, (PVOID) list) == 2) {
419          if (!PostMsg(WinWindowFromID(hwndFrame, FID_CLIENT),
420                       UM_UPDATERECORDLIST, MPFROMP(list), MPVOID))
421            FreeList(list);
422        }
423        else
424          FreeList(list);
425        break;
426
427      case IDM_ARCHIVE:
428        {
429          DIRCNRDATA ad;
430          CHAR szBuffer[1025];
431
432          memset(&ad, 0, sizeof(ad));
433          ad.namecanchange = 1;
434          ad.info = arcsighead;         // Hide dups
435          if (!WinDlgBox(HWND_DESKTOP,
436                         hwndFrame,
437                         SBoxDlgProc,
438                         FM3ModHandle,
439                         ASEL_FRAME, (PVOID) & ad.info) || !ad.info) {
440            /* we blew it */
441            FreeList(list);
442            break;
443          }
444          if (!ad.info->create &&
445              !ad.info->move &&
446              !ad.info->createwdirs &&
447              !ad.info->movewdirs && !ad.info->createrecurse) {
448            FreeList(list);
449            break;
450          }
451          if (!WinDlgBox(HWND_DESKTOP, hwndFrame, ArchiveDlgProc, FM3ModHandle, ARCH_FRAME, (PVOID) & ad) || !*ad.arcname || !*ad.command) {    /* we blew it */
452            FreeList(list);
453            break;
454          }
455          /* build the sucker */
456          strcpy(szBuffer, ad.command);
457          strcat(szBuffer, " ");
458          strcat(szBuffer, ad.arcname);
459          p = &szBuffer[strlen(szBuffer)];
460          if (ad.mask.szMask) {
461            strcat(szBuffer, " ");
462            strcat(szBuffer, ad.mask.szMask);
463          }
464          strcat(szBuffer, " ");
465          x = 0;
466          while (list[x]) {
467
468            FILESTATUS3 fsa;
469            BOOL spaces;
470
471            if (needs_quoting(list[x])) {
472              spaces = TRUE;
473              strcat(szBuffer, "\"");
474            }
475            else
476              spaces = FALSE;
477            strcat(szBuffer, list[x]);
478            memset(&fsa, 0, sizeof(fsa));
479            DosError(FERR_DISABLEHARDERR);
480            DosQueryPathInfo(list[x], FIL_STANDARD,
481                             &fsa, (ULONG) sizeof(fsa));
482            if (fsa.attrFile & FILE_DIRECTORY) {
483              if (szBuffer[strlen(szBuffer) - 1] != '\\')
484                strcat(szBuffer, "\\");
485              strcat(szBuffer, "*");
486            }
487            if (spaces)
488              strcat(szBuffer, "\"");
489            x++;
490            if (!list[x] || strlen(szBuffer) + strlen(list[x]) + 5 > 1024) {
491              runemf2(SEPARATE | WINDOWED |
492                      ((fArcStuffVisible) ? 0 :
493                       (BACKGROUND | MINIMIZED)) |
494                      WAIT, HWND_DESKTOP, NULL, NULL, "%s", szBuffer);
495              DosSleep(1);
496              *p = 0;
497            }
498            strcat(szBuffer, " ");
499          }
500          AddToList(ad.arcname, &files, &numfiles, &numalloc);
501        }
502        if (!PostMsg(WinWindowFromID(hwndFrame, FID_CLIENT),
503                     UM_UPDATERECORDLIST, MPFROMP(list), MPVOID))
504          FreeList(list);
505        break;
506
507      case IDM_ATTRS:
508        {
509          LISTINFO li;
510
511          memset(&li, 0, sizeof(li));
512          li.list = list;
513          if (WinDlgBox(HWND_DESKTOP,
514                        hwndFrame,
515                        AttrListDlgProc,
516                        FM3ModHandle, ATR_FRAME, MPFROMP(&li))) {
517            if (li.list && li.list[0]) {
518              if (!PostMsg(WinWindowFromID(hwndFrame, FID_CLIENT),
519                           UM_UPDATERECORDLIST, MPFROMP(li.list), MPVOID))
520                FreeList(li.list);
521            }
522          }
523          else
524            FreeList(list);
525        }
526        break;
527
528      case IDM_MOVE:
529      case IDM_COPY:
530        if (!*path)
531          strcpy(path, targetdir);
532        if (!*path)
533          strcpy(path, list[0]);
534        MakeValidDir(path);
535      RetryPath:
536        if (SHORT1FROMMP(mp1) == IDM_MOVE) {
537          if (!WinDlgBox(HWND_DESKTOP,
538                         hwndFrame,
539                         WalkMoveDlgProc,
540                         FM3ModHandle, WALK_FRAME, MPFROMP(path)) || !*path) {
541            FreeList(list);
542            goto Abort;
543          }
544        }
545        else {
546          if (!WinDlgBox(HWND_DESKTOP,
547                         hwndFrame,
548                         WalkCopyDlgProc,
549                         FM3ModHandle, WALK_FRAME, MPFROMP(path)) || !*path) {
550            FreeList(list);
551            goto Abort;
552          }
553        }
554        if (driveflags[toupper(*path) - 'A'] & DRIVE_NOTWRITEABLE) {
555          saymsg(MB_CANCEL,
556                 hwndFrame,
557                 GetPString(IDS_ERRORTEXT),
558                 "%s", GetPString(IDS_NOTWRITENOTARGETTEXT));
559          goto RetryPath;
560        }
561        /* intentional fallthru */
562      case IDM_RENAME:
563        {
564          CHAR newname[CCHMAXPATH], *moving, *move, *moved;
565          APIRET rc;
566          INT type;
567          FILESTATUS4 fs4;
568          BOOL isnewer, existed;
569
570          for (x = 0; list[x]; x++) {
571          Retry:
572            type = (SHORT1FROMMP(mp1) == IDM_RENAME) ? MOVE :
573              (SHORT1FROMMP(mp1) == IDM_MOVE) ? MOVE :
574              (SHORT1FROMMP(mp1) == IDM_WPSMOVE) ? WPSMOVE :
575              (SHORT1FROMMP(mp1) == IDM_WPSCOPY) ? WPSCOPY : COPY;
576            moving = (SHORT1FROMMP(mp1) == IDM_RENAME) ?
577              GetPString(IDS_RENAMINGTEXT) :
578              (SHORT1FROMMP(mp1) == IDM_MOVE ||
579               SHORT1FROMMP(mp1) == IDM_WPSMOVE) ?
580              GetPString(IDS_MOVINGTEXT) : GetPString(IDS_COPYINGTEXT);
581            move = (SHORT1FROMMP(mp1) == IDM_RENAME) ?
582              GetPString(IDS_RENAMETEXT) :
583              (SHORT1FROMMP(mp1) == IDM_MOVE ||
584               SHORT1FROMMP(mp1) == IDM_WPSMOVE) ?
585              GetPString(IDS_MOVETEXT) : GetPString(IDS_COPYTEXT);
586            moved = (SHORT1FROMMP(mp1) == IDM_RENAME) ?
587              GetPString(IDS_RENAMEDTEXT) :
588              (SHORT1FROMMP(mp1) == IDM_MOVE ||
589               SHORT1FROMMP(mp1) == IDM_WPSMOVE) ?
590              GetPString(IDS_MOVEDTEXT) : GetPString(IDS_COPIEDTEXT);
591            if (*path) {
592              strcpy(newname, path);
593              if (newname[strlen(newname) - 1] != '\\')
594                strcat(newname, "\\");
595              if (plen)
596                p = list[x] + plen;
597              else {
598                p = strrchr(list[x], '\\');
599                if (p)
600                  p++;
601                else
602                  p = list[x];
603              }
604              strcat(newname, p);
605            }
606            else
607              strcpy(newname, list[x]);
608            if ((wildcarding || SHORT1FROMMP(mp1) == IDM_RENAME) && *wildname) {
609
610              CHAR testname[CCHMAXPATH];
611
612              strcpy(testname, wildname);
613              if (AdjustWildcardName(newname, testname))
614                strcpy(newname, testname);
615            }
616            existed = (IsFile(newname) != -1);
617            isnewer = IsNewer(list[x], newname);
618            if (existed && SHORT1FROMMP(mp1) != IDM_RENAME && dontask) {
619              if (!overold && !overnew)
620                break;
621              if (!overold && !isnewer)
622                break;
623              if (!overnew && isnewer)
624                break;
625            }
626            if ((SHORT1FROMMP(mp1) == IDM_RENAME &&
627                 (!dontask || !*wildname)) ||
628                (!dontask && existed) ||
629                (!dontask && wildcarding) ||
630                (IsFile(newname) == 0 && IsFile(list[x]) == 1)) {
631
632              MOVEIT mv;
633
634              memset(&mv, 0, sizeof(mv));
635              mv.rename = (SHORT1FROMMP(mp1) == IDM_RENAME);
636              mv.source = list[x];
637              strcpy(mv.target, newname);
638              rc = WinDlgBox(HWND_DESKTOP,
639                             hwndFrame,
640                             RenameProc,
641                             FM3ModHandle, REN_FRAME, (PVOID) & mv);
642              if (!rc) {
643                FreeList(list);
644                goto Abort;
645              }
646              DosSleep(1);
647              if (mv.skip || !*mv.target)
648                break;
649              if (mv.dontask)
650                dontask = TRUE;
651              if (mv.overold)
652                overold = TRUE;
653              if (mv.overnew)
654                overnew = TRUE;
655              if (wildcarding || SHORT1FROMMP(mp1) == IDM_RENAME) {
656                p = strrchr(mv.target, '\\');
657                if (p && (strchr(p, '*') || strchr(p, '?'))) {
658                  strcpy(wildname, mv.target);
659                  AdjustWildcardName(list[x], mv.target);
660                }
661                else
662                  *wildname = 0;
663              }
664              strcpy(newname, mv.target);
665              existed = (IsFile(newname) != -1);
666              isnewer = IsNewer(list[x], newname);
667              if (!mv.overwrite) {
668                if (existed && SHORT1FROMMP(mp1) != IDM_RENAME && dontask) {
669                  if (!overold && !overnew)
670                    break;
671                  if (!overold && !isnewer)
672                    break;
673                  if (!overnew && isnewer)
674                    break;
675                }
676              }
677            }
678            if (!stricmp(list[x], newname))
679              break;
680            sprintf(message,
681                    " %s \"%s\" %s \"%s\"",
682                    moving, list[x], GetPString(IDS_TOTEXT), newname);
683            WinSetWindowText(WinWindowFromID(hwndFrame, SEEALL_STATUS),
684                             message);
685            if (fRealIdle)
686              priority_idle();
687            if (plen) {
688              /* make directory/ies, if required */
689
690              CHAR dirpart[CCHMAXPATH];
691
692              strcpy(dirpart, newname);
693              p = strrchr(dirpart, '\\');
694              if (p) {
695                *p = 0;
696                if (p > dirpart + 3)
697                  MassMkdir((hwndMain) ? hwndMain : (HWND) 0, dirpart);
698              }
699            }
700            rc = docopyf(type, list[x], "%s", newname);
701            priority_normal();
702            if (rc) {
703              if ((rc == ERROR_DISK_FULL ||
704                   rc == ERROR_HANDLE_DISK_FULL) &&
705                  isalpha(*newname) &&
706                  (driveflags[toupper(*newname) - 'A'] & DRIVE_REMOVABLE) &&
707                  !(driveflags[toupper(*newname) - 'A'] & DRIVE_NOTWRITEABLE)
708                  && toupper(*newname) != toupper(*list[x])
709                  && !DosQueryPathInfo(list[x], FIL_QUERYEASIZE, &fs4,
710                                       sizeof(fs4))
711                  && !(fs4.attrFile & FILE_DIRECTORY)) {
712
713                FSALLOCATE fsa;
714                ULONG clFreeBytes;
715                CHAR *ptr;
716                INT cntr;
717
718                WinSetWindowText(WinWindowFromID(hwndFrame, SEEALL_STATUS),
719                                 GetPString(IDS_FITTINGTEXT));
720                DosError(FERR_DISABLEHARDERR);
721                if (!DosQueryFSInfo(toupper(*newname) - '@',
722                                    FSIL_ALLOC, &fsa, sizeof(fsa))) {
723                  // Assume <2GB since file did not fit
724                  clFreeBytes = fsa.cUnitAvail * fsa.cSectorUnit *
725                    fsa.cbSector;
726                  if (clFreeBytes) {
727                    // Find item that will fit in available space
728                    for (cntr = x + 1; list[cntr]; cntr++) {
729                      DosError(FERR_DISABLEHARDERR);
730                      if (!DosQueryPathInfo(list[cntr],
731                                            FIL_QUERYEASIZE,
732                                            &fs4, sizeof(fs4)) &&
733                          !(fs4.attrFile & FILE_DIRECTORY) &&
734                          // fixme to use CBLIST_TO_EASIZE?
735                          fs4.cbFile + fs4.cbList <= clFreeBytes) {
736                        // Swap with failing item
737                        ptr = list[x];
738                        list[x] = list[cntr];
739                        list[cntr] = ptr;
740                        goto Retry;
741                      }
742                    }
743                    WinSetWindowText(WinWindowFromID(hwndFrame,
744                                                     SEEALL_STATUS),
745                                     GetPString(IDS_COULDNTFITTEXT));
746                  }
747                }
748                rc = saymsg(MB_ABORTRETRYIGNORE | MB_ICONEXCLAMATION,
749                            hwndFrame,
750                            GetPString(IDS_DISKFULLTEXT),
751                            "%s", GetPString(IDS_ANOTHERDISKTEXT));
752                if (rc == MBID_RETRY)
753                  goto Retry;
754                if (rc == MBID_ABORT) {
755                  FreeList(list);
756                  goto Abort;
757                }
758              }
759              else {
760                if (LogFileHandle)
761                  fprintf(LogFileHandle,
762                          GetPString(IDS_LOGTOFAILEDTEXT),
763                          move, list[x], newname, rc);
764                rc = Dos_Error(MB_ENTERCANCEL,
765                               rc,
766                               hwndFrame,
767                               pszSrcFile,
768                               __LINE__,
769                               "%s %s \"%s\" %s\"%s\" %s.",
770                               move,
771                               GetPString(IDS_OFTEXT),
772                               list[x],
773                               GetPString(IDS_TOTEXT),
774                               newname, GetPString(IDS_FAILEDTEXT));
775                if (rc == MBID_CANCEL) {
776                  FreeList(list);
777                  goto Abort;
778                }
779              }
780            }
781            else {
782              if (LogFileHandle)
783                fprintf(LogFileHandle,
784                        "%s \"%s\" %s \"%s\"\n",
785                        moved, list[x], GetPString(IDS_TOTEXT), newname);
786              AddToList(newname, &files, &numfiles, &numalloc);
787            }
788          }
789        }
790        if (SHORT1FROMMP(mp1) != IDM_COPY) {
791          if (!PostMsg(WinWindowFromID(hwndFrame, FID_CLIENT),
792                       UM_UPDATERECORDLIST, MPFROMP(list), MPVOID))
793            FreeList(list);
794        }
795        else
796          FreeList(list);
797        break;
798
799      case IDM_UUDECODE:
800        for (x = 0; list[x]; x++)
801          UUD(list[x], NULL);
802        break;
803
804      case IDM_EXTRACT:
805        for (x = 0; list[x]; x++) {
806
807          EXTRDATA ex;
808          BOOL maskspaces = FALSE;
809
810          memset(&ex, 0, sizeof(ex));
811          ex.info = find_type(list[x], NULL);
812          if (!ex.info || (!ex.info->extract && !ex.info->exwdirs))
813            break;
814          ex.size = sizeof(ex);
815          ex.arcname = list[x];
816          strcpy(ex.masks, "*");
817          if (!WinDlgBox(HWND_DESKTOP,
818                         hwndFrame,
819                         ExtractDlgProc,
820                         FM3ModHandle,
821                         EXT_FRAME,
822                         (PVOID) & ex) ||
823              !ex.ret || !*ex.command || !*ex.arcname || !*ex.extractdir)
824            break;
825          if (IsFile(ex.extractdir) != 0)
826            Runtime_Error(pszSrcFile, __LINE__, "directory expected");
827          else {
828            if (needs_quoting(ex.masks) && !strchr(ex.masks, '\"'))
829              maskspaces = TRUE;
830            runemf2(SEPARATE | WINDOWED |
831                    ((fArcStuffVisible) ? 0 :
832                     (BACKGROUND | MINIMIZED)),
833                    HWND_DESKTOP,
834                    ex.extractdir,
835                    NULL,
836                    "%s %s %s%s%s",
837                    ex.command,
838                    ex.arcname,
839                    (maskspaces) ? "\"" : NullStr,
840                    (*ex.masks) ? ex.masks : "*",
841                    (maskspaces) ? "\"" : NullStr);
842          }
843        }
844        // fixme to not leak?
845        if (!PostMsg(WinWindowFromID(hwndFrame, FID_CLIENT),
846                     UM_UPDATERECORDLIST, MPFROMP(list), MPVOID))
847          FreeList(list);
848        break;
849
850      case IDM_SUBJECT:
851        for (x = 0; list[x]; x++) {
852
853          INT ret;
854
855          if (IsFile(list[x]) == 1) {
856            ret = Subject(hwndFrame, list[x]);
857            if (!ret)
858              break;
859          }
860        }
861        if (!PostMsg(WinWindowFromID(hwndFrame, FID_CLIENT),
862                     UM_UPDATERECORDLIST, MPFROMP(list), MPVOID))
863          FreeList(list);
864        break;
865
866      case IDM_OPENDEFAULT:
867      case IDM_OPENSETTINGS:
868        for (x = 0; list[x]; x++) {
869          if (IsFile(list[x]) != -1) {
870
871            CHAR *s;
872
873            switch (SHORT1FROMMP(mp1)) {
874            case IDM_OPENSETTINGS:
875              s = Settings;
876              break;
877            default:
878              s = Default;
879              break;
880            }
881            OpenObject(list[x], s, hwndFrame);
882          }
883        }
884        FreeList(list);
885        break;
886
887      case IDM_DELETE:
888      case IDM_PERMDELETE:
889        {
890          CHECKLIST cl;
891          INT isdir = 0, sysdir = 0, ro = 0, hs = 0;
892          FILESTATUS3 fsa;
893          CHAR prompt[CCHMAXPATH * 3];
894          APIRET error;
895
896          for (x = 0; list[x]; x++) {
897            if (IsRoot(list[x])) {
898              list = RemoveFromList(list, list[x]);
899              if (!list)
900                break;
901              x--;
902              continue;
903            }
904            DosError(FERR_DISABLEHARDERR);
905            if (DosQueryPathInfo(list[x], FIL_STANDARD, &fsa, sizeof(fsa))) {
906              list = RemoveFromList(list, list[x]);
907              if (!list)
908                break;
909              x--;
910              continue;
911            }
912            if (fsa.attrFile & FILE_DIRECTORY) {
913              isdir++;
914              if (stristr(list[x], ":\\OS2\\") ||
915                  !stricmp(list[x] + 1, ":\\OS2"))
916                sysdir++;
917            }
918            else {
919              if (fsa.attrFile & (FILE_HIDDEN | FILE_SYSTEM))
920                hs++;
921              if (fsa.attrFile & FILE_READONLY)
922                ro++;
923            }
924          }
925          if (!list)
926            break;
927          if (fConfirmDelete || isdir) {
928            memset(&cl, 0, sizeof(cl));
929            cl.size = sizeof(cl);
930            cl.list = list;
931            cl.prompt = prompt;
932            cl.flags |= CHECK_FILES;
933            cl.cmd = SHORT1FROMMP(mp1);
934            sprintf(prompt,
935                    GetPString(IDS_DELPROMPT1TEXT),
936                    (SHORT1FROMMP(mp1) == IDM_DELETE) ?
937                    NullStr :
938                    GetPString(IDS_PERMANENTLYTEXT), &"s"[list[1] == NULL]);
939            if (isdir) {
940              sprintf(&prompt[strlen(prompt)],
941                      GetPString(IDS_DELPROMPT2TEXT),
942                      isdir,
943                      (isdir > 1) ?
944                      GetPString(IDS_ARETEXT) :
945                      GetPString(IDS_ISTEXT),
946                      (isdir == 1) ?
947                      GetPString(IDS_ATEXT) :
948                      NullStr,
949                      (isdir > 1) ?
950                      GetPString(IDS_IESTEXT) : GetPString(IDS_YTEXT));
951              if (sysdir)
952                sprintf(&prompt[strlen(prompt)],
953                        GetPString(IDS_DELPROMPT3TEXT),
954                        sysdir,
955                        (sysdir == 1) ?
956                        GetPString(IDS_YTEXT) : GetPString(IDS_IESTEXT));
957            }
958            if (ro)
959              sprintf(&prompt[strlen(prompt)],
960                      GetPString(IDS_DELPROMPT4TEXT),
961                      ro,
962                      &"s"[ro == 1],
963                      (ro > 1) ?
964                      GetPString(IDS_ARETEXT) : GetPString(IDS_ISTEXT));
965            if (hs)
966              sprintf(&prompt[strlen(prompt)],
967                      GetPString(IDS_DELPROMPT5TEXT),
968                      hs,
969                      &"s"[hs == 1],
970                      (hs > 1) ?
971                      GetPString(IDS_ARETEXT) : GetPString(IDS_ISTEXT));
972            if (ro || hs || sysdir)
973              DosBeep(300, 100);
974            strcat(prompt, GetPString(IDS_DELPROMPT6TEXT));
975            if (!WinDlgBox(HWND_DESKTOP,
976                           WinWindowFromID(hwndFrame, FID_CLIENT),
977                           CheckListProc,
978                           FM3ModHandle, CHECK_FRAME, MPFROMP(&cl)))
979              break;
980            list = cl.list;
981            if (!list || !list[0])
982              break;
983          }
984          for (x = 0; list[x]; x++) {
985            fsa.attrFile = 0;
986            DosError(FERR_DISABLEHARDERR);
987            DosQueryPathInfo(list[x], FIL_STANDARD, &fsa, sizeof(fsa));
988            if (fsa.attrFile & FILE_DIRECTORY) {
989              sprintf(prompt, GetPString(IDS_DELETINGTEXT), list[x]);
990              WinSetWindowText(WinWindowFromID(hwndFrame, SEEALL_STATUS),
991                               prompt);
992              error = (APIRET) wipeallf("%s%s*",
993                                        list[x],
994                                        (*list[x] &&
995                                         list[x][strlen(list[x]) - 1] !=
996                                         '\\') ? "\\" : NullStr);
997              DosError(FERR_DISABLEHARDERR);
998              if (!error)
999                error = DosDeleteDir(list[x]);
1000              else
1001                DosDeleteDir(list[x]);
1002            }
1003            else {
1004              DosError(FERR_DISABLEHARDERR);
1005              if (SHORT1FROMMP(mp1) == IDM_DELETE)
1006                error = DosDelete(list[x]);
1007              else
1008                error = DosForceDelete(list[x]);
1009              if (error) {
1010                DosError(FERR_DISABLEHARDERR);
1011                make_deleteable(list[x]);
1012                if (SHORT1FROMMP(mp1) == IDM_DELETE)
1013                  error = DosDelete(list[x]);
1014                else
1015                  error = DosForceDelete(list[x]);
1016              }
1017            }
1018            if (error) {
1019              if (LogFileHandle)
1020                fprintf(LogFileHandle,
1021                        GetPString(IDS_DELETEFAILED1TEXT), list[x], error);
1022              if (Dos_Error(MB_ENTERCANCEL,
1023                            error,
1024                            hwndFrame,
1025                            pszSrcFile,
1026                            __LINE__,
1027                            GetPString(IDS_DELETEFAILED2TEXT),
1028                            list[x]) == MBID_CANCEL)
1029                break;
1030            }
1031            else if (LogFileHandle)
1032              fprintf(LogFileHandle,
1033                      "%s\n", GetPString(IDS_DELETEDTEXT), list[x]);
1034            AddToList(list[x], &files, &numfiles, &numalloc);
1035          }
1036        }
1037        FreeList(list);
1038        break;
1039
1040      case IDM_SAVETOLIST:
1041        if (list) {
1042          WinDlgBox(HWND_DESKTOP,
1043                    WinWindowFromID(hwndFrame, FID_CLIENT),
1044                    SaveAllListDlgProc,
1045                    FM3ModHandle, SAV_FRAME, MPFROMP(list));
1046          FreeList(list);
1047        }
1048        break;
1049
1050      case IDM_SAVETOCLIP:
1051      case IDM_APPENDTOCLIP:
1052        if (list) {
1053          ListToClipboardHab(WinQueryAnchorBlock(hwnd),
1054                             list, (SHORT1FROMMP(mp1) == IDM_APPENDTOCLIP));
1055          FreeList(list);
1056        }
1057        break;
1058
1059      default:
1060        if (list)
1061          FreeList(list);
1062        break;
1063      }
1064
1065      switch (SHORT1FROMMP(mp1)) {
1066      case IDM_MOVE:
1067      case IDM_COPY:
1068      case IDM_RENAME:
1069        sprintf(message,
1070                GetPString(IDS_OPSCOMPLETETEXT),
1071                (SHORT1FROMMP(mp1) == IDM_MOVE) ?
1072                GetPString(IDS_MOVETEXT) :
1073                (SHORT1FROMMP(mp1) == IDM_COPY) ?
1074                GetPString(IDS_COPYTEXT) :
1075                (SHORT1FROMMP(mp1) == IDM_WPSMOVE) ?
1076                GetPString(IDS_WPSMOVETEXT) :
1077                (SHORT1FROMMP(mp1) == IDM_WPSCOPY) ?
1078                GetPString(IDS_WPSCOPYTEXT) :
1079                GetPString(IDS_RENAMETEXT),
1080                &"s"[x == 1],
1081                (SHORT1FROMMP(mp1) == IDM_MOVE ||
1082                 SHORT1FROMMP(mp1) == IDM_COPY ||
1083                 SHORT1FROMMP(mp1) == IDM_WPSMOVE ||
1084                 SHORT1FROMMP(mp1) == IDM_WPSCOPY) ?
1085                GetPString(IDS_TOTEXT) :
1086                NullStr,
1087                (SHORT1FROMMP(mp1) == IDM_MOVE ||
1088                 SHORT1FROMMP(mp1) == IDM_COPY ||
1089                 SHORT1FROMMP(mp1) == IDM_WPSMOVE ||
1090                 SHORT1FROMMP(mp1) == IDM_WPSCOPY) ?
1091                path :
1092                NullStr,
1093                (x != 1) ? GetPString(IDS_ARETEXT) : GetPString(IDS_ISTEXT));
1094        WinSetWindowText(WinWindowFromID(hwndFrame, SEEALL_STATUS), message);
1095        if (toupper(*path) < 'C')
1096          DosBeep(1000, 25);
1097        DosSleep(33L);
1098        break;
1099
1100      default:
1101        break;
1102      }
1103    Abort:
1104      if (files) {
1105        if (!PostMsg(WinWindowFromID(hwndFrame, FID_CLIENT),
1106                     UM_UPDATERECORDLIST, MPFROMP(files), MPVOID))
1107          FreeList(files);
1108      }
1109      PostMsg(WinWindowFromID(hwndFrame, FID_CLIENT),
1110              UM_RESCAN, MPVOID, MPVOID);
1111    }
1112    return 0;
1113
1114  case WM_CLOSE:
1115    WinDestroyWindow(hwnd);
1116    break;
1117
1118  case WM_DESTROY:
1119    if (!PostMsg((HWND) 0, WM_QUIT, MPVOID, MPVOID))
1120      WinSendMsg((HWND) 0, WM_QUIT, MPVOID, MPVOID);
1121    break;
1122  }
1123  return WinDefWindowProc(hwnd, msg, mp1, mp2);
1124}
1125
1126static VOID MakeSeeObjWinThread(VOID * args)
1127{
1128  HAB hab2;
1129  HMQ hmq2;
1130  HWND hwndObj;
1131  ALLDATA *ad = (ALLDATA *) args;
1132  QMSG qmsg2;
1133
1134  if (ad) {
1135    hab2 = WinInitialize(0);
1136    if (hab2) {
1137      hmq2 = WinCreateMsgQueue(hab2, 256);
1138      if (hmq2) {
1139        DosError(FERR_DISABLEHARDERR);
1140        WinRegisterClass(hab2,
1141                         WC_OBJECTWINDOW,
1142                         SeeObjWndProc, 0, sizeof(PVOID));
1143        hwndObj = WinCreateWindow(HWND_OBJECT,
1144                                  WC_OBJECTWINDOW,
1145                                  (PSZ) NULL,
1146                                  0,
1147                                  0,
1148                                  0,
1149                                  0,
1150                                  0, 0, HWND_TOP, SEEALL_OBJ, NULL, NULL);
1151        if (!hwndObj) {
1152          Win_Error2(HWND_OBJECT, HWND_DESKTOP, pszSrcFile, __LINE__,
1153                     IDS_WINCREATEWINDOW);
1154          if (!PostMsg(ad->hwndClient, WM_CLOSE, MPVOID, MPVOID))
1155            WinSendMsg(ad->hwndClient, WM_CLOSE, MPVOID, MPVOID);
1156        }
1157        else {
1158          ad->hwndObj = hwndObj;
1159          WinSetWindowULong(hwndObj, QWL_USER, ad->hwndFrame);
1160          priority_normal();
1161          while (WinGetMsg(hab2, &qmsg2, (HWND) 0, 0, 0))
1162            WinDispatchMsg(hab2, &qmsg2);
1163          WinDestroyWindow(hwndObj);
1164        }
1165        WinDestroyMsgQueue(hmq2);
1166      }
1167      else
1168        WinTerminate(hab2);
1169    }
1170  }
1171}
1172
1173static VOID SelectMask(HWND hwnd, BOOL deselect)
1174{
1175  MASK mask;
1176  register ULONG x, y, z;
1177  BOOL ret;
1178  ALLDATA *pAD = WinQueryWindowPtr(hwnd, QWL_USER);
1179
1180  memset(&mask, 0, sizeof(mask));
1181  mask.fNoAttribs = FALSE;
1182  mask.fNoDirs = TRUE;
1183  mask.attrFile = pAD->mask.attrFile;
1184  mask.antiattr = pAD->mask.antiattr;
1185  mask.fIsSeeAll = TRUE;
1186  strcpy(mask.prompt,
1187         GetPString((!deselect) ?
1188                    IDS_SELECTFILTERTEXT : IDS_DESELECTFILTERTEXT));
1189  if (WinDlgBox(HWND_DESKTOP,
1190                hwnd,
1191                PickMaskDlgProc,
1192                FM3ModHandle,
1193                MSK_FRAME,
1194                MPFROMP(&mask)) &&
1195      (*mask.szMask ||
1196       mask.attrFile != pAD->mask.attrFile ||
1197       mask.antiattr != pAD->mask.antiattr)) {
1198    for (x = 0; x < pAD->afifiles; x++) {
1199      y = (pAD->invertsort) ? (pAD->afifiles - 1) - x : x;
1200      ret = FALSE;
1201      if (mask.pszMasks[1]) {
1202        for (z = 0; mask.pszMasks[z]; z++) {
1203          if (*mask.pszMasks[z]) {
1204            if (*mask.pszMasks[z] != '/') {
1205              if (wildcard((strchr(mask.pszMasks[z], '\\') ||
1206                            strchr(mask.pszMasks[z], ':')) ?
1207                           pAD->afindex[y]->fullname : pAD->afindex[y]->
1208                           filename, mask.pszMasks[z], FALSE))
1209                ret = TRUE;
1210            }
1211            else {
1212              if (wildcard((strchr(mask.pszMasks[z], '\\') ||
1213                            strchr(mask.pszMasks[z], ':')) ?
1214                           pAD->afindex[y]->fullname : pAD->afindex[y]->
1215                           filename, mask.pszMasks[y] + 1, FALSE)) {
1216                ret = FALSE;
1217                break;
1218              }
1219            }
1220          }
1221        }
1222      }
1223      else if (*mask.szMask) {
1224        if (wildcard((strchr(mask.szMask, '\\') ||
1225                      strchr(mask.szMask, ':')) ?
1226                     pAD->afindex[y]->fullname : pAD->afindex[y]->filename,
1227                     mask.szMask, FALSE))
1228          ret = TRUE;
1229      }
1230      else
1231        ret = TRUE;
1232      if (ret) {
1233        if ((!(mask.attrFile & FILE_HIDDEN)
1234             && (pAD->afindex[y]->attrFile & FILE_HIDDEN))
1235            || (!(mask.attrFile & FILE_SYSTEM)
1236                && (pAD->afindex[y]->attrFile & FILE_SYSTEM))
1237            || (!(mask.attrFile & FILE_READONLY)
1238                && (pAD->afindex[y]->attrFile & FILE_READONLY))
1239            || (!(mask.attrFile & FILE_ARCHIVED)
1240                && (pAD->afindex[y]->attrFile & FILE_ARCHIVED)))
1241          ret = FALSE;
1242        else
1243          if (((mask.antiattr & FILE_HIDDEN)
1244               && !(pAD->afindex[y]->attrFile & FILE_HIDDEN))
1245              || ((mask.antiattr & FILE_SYSTEM)
1246                  && !(pAD->afindex[y]->attrFile & FILE_SYSTEM))
1247              || ((mask.antiattr & FILE_READONLY)
1248                  && !(pAD->afindex[y]->attrFile & FILE_READONLY))
1249              || ((mask.antiattr & FILE_ARCHIVED)
1250                  && !(pAD->afindex[y]->attrFile & FILE_ARCHIVED)))
1251          ret = FALSE;
1252      }
1253      if (ret) {
1254        if (deselect) {
1255          if (pAD->afindex[y]->flags & AF_SELECTED) {
1256            pAD->selected--;
1257            pAD->ullSelectedBytes -= pAD->afindex[y]->cbFile;
1258            pAD->afindex[y]->flags &= ~AF_SELECTED;
1259          }
1260        }
1261        else {
1262          if (~pAD->afindex[y]->flags & AF_SELECTED) {
1263            pAD->selected++;
1264            pAD->ullSelectedBytes += pAD->afindex[y]->cbFile;
1265            pAD->afindex[y]->flags |= AF_SELECTED;
1266          }
1267        }
1268      }
1269    }                                   // for
1270  }
1271}
1272
1273static VOID CollectList(HWND hwnd, CHAR ** list)
1274{
1275  if (!Collector) {
1276    if (hwndMain && !fExternalCollector && !strcmp(realappname, FM3Str)) {
1277
1278      HWND hwndC;
1279      SWP swp;
1280
1281      if (!fAutoTile)
1282        GetNextWindowPos(hwndMain, &swp, NULL, NULL);
1283      hwndC = StartCollector(hwndMain, 4);
1284      if (hwndC) {
1285        if (!fAutoTile)
1286          WinSetWindowPos(hwndC, HWND_TOP, swp.x, swp.y,
1287                          swp.cx, swp.cy, SWP_MOVE | SWP_SIZE |
1288                          SWP_SHOW | SWP_ZORDER);
1289        else
1290          TileChildren(hwndMain, TRUE);
1291        WinSetWindowPos(hwndC, HWND_TOP, 0, 0, 0, 0, SWP_ACTIVATE);
1292        DosSleep(250);
1293      }
1294    }
1295    else {
1296      StartCollector(HWND_DESKTOP, 4);
1297      DosSleep(250);
1298    }
1299  }
1300  if (!PostMsg(hwnd, WM_COMMAND, MPFROM2SHORT(IDM_COLLECTOR, 0),
1301               MPFROMP(list)))
1302    FreeList(list);
1303}
1304
1305static VOID FreeAllFilesList(HWND hwnd)
1306{
1307  ALLDATA *ad = WinQueryWindowPtr(hwnd, QWL_USER);
1308  register ULONG x;
1309
1310  if (ad->afhead && ad->affiles) {
1311    for (x = 0; x < ad->affiles; x++) {
1312      if (ad->afhead[x].fullname)
1313        free(ad->afhead[x].fullname);
1314    }
1315    free(ad->afhead);
1316    ad->afhead = NULL;
1317    if (ad->afindex)
1318      free(ad->afindex);
1319    ad->afindex = NULL;
1320  }
1321  DosPostEventSem(CompactSem);
1322  ad->afalloc = ad->afifiles = ad->affiles = ad->longest = ad->longestw =
1323    ad->maxx = ad->horzscroll = 0;
1324}
1325
1326static CHAR **BuildAList(HWND hwnd)
1327{
1328  ALLDATA *ad = WinQueryWindowPtr(hwnd, QWL_USER);
1329  ULONG x;
1330  ULONG y;
1331  ULONG z = 0;
1332  CHAR **list = NULL;
1333  INT numfiles = 0;
1334  INT numalloc = 0;
1335  INT error;
1336
1337  if (ad->selected) {
1338    for (x = 0; x < ad->afifiles; x++) {
1339      y = (ad->invertsort) ? (ad->afifiles - 1) - x : x;
1340      if (ad->afindex[y]->flags & AF_SELECTED) {
1341        error = AddToList(ad->afindex[y]->fullname, &list,
1342                          &numfiles, &numalloc);
1343        if (error)
1344          break;
1345        z++;
1346        if (z >= ad->selected)
1347          break;
1348      }
1349    }
1350  }
1351  return list;
1352}
1353
1354static BOOL Mark(HWND hwnd, INT command, CHAR ** list)
1355{
1356  /* Marks only unfiltered files */
1357
1358  ALLDATA *pAD = WinQueryWindowPtr(hwnd, QWL_USER);
1359  register ULONG x, y, z;
1360  BOOL ret = TRUE;
1361  BOOL didone = FALSE;
1362
1363  for (x = 0; x < pAD->afifiles; x++) {
1364    y = (pAD->invertsort) ? (pAD->afifiles - 1) - x : x;
1365    if (list) {
1366      ret = FALSE;
1367      for (z = 0; list[z]; z++) {
1368        if (!stricmp(list[z], pAD->afindex[y]->fullname)) {
1369          ret = TRUE;
1370          break;
1371        }
1372      }
1373    }
1374    if (ret) {
1375      didone = TRUE;
1376      if (command == AFM_UNMARK) {
1377        if (pAD->afindex[y]->flags & AF_SELECTED) {
1378          pAD->selected--;
1379          pAD->ullSelectedBytes -= pAD->afindex[y]->cbFile;
1380          pAD->afindex[y]->flags &= ~AF_SELECTED;
1381        }
1382      }
1383      else if (command == AFM_MARK) {
1384        if (~pAD->afindex[y]->flags & AF_SELECTED) {
1385          pAD->selected++;
1386          pAD->ullSelectedBytes += pAD->afindex[y]->cbFile;
1387          pAD->afindex[y]->flags |= AF_SELECTED;
1388        }
1389      }
1390      else if (command == AFM_INVERT) {
1391        if (pAD->afindex[y]->flags & AF_SELECTED) {
1392          pAD->selected--;
1393          pAD->ullSelectedBytes -= pAD->afindex[y]->cbFile;
1394          pAD->afindex[y]->flags &= ~AF_SELECTED;
1395        }
1396        else {
1397          pAD->selected++;
1398          pAD->ullSelectedBytes += pAD->afindex[y]->cbFile;
1399          pAD->afindex[y]->flags |= AF_SELECTED;
1400        }
1401      }
1402      else if (command == AFM_MARKDELETED) {
1403        if (pAD->afindex[y]->flags & AF_SELECTED)
1404          pAD->afindex[y]->flags |= AF_DELETED;
1405      }
1406      else if (command == AFM_FILTER) {
1407        if (pAD->afindex[y]->flags & AF_SELECTED)
1408          pAD->afindex[y]->flags |= AF_FILTERED;
1409      }
1410    }
1411  }                                     // for x
1412  return didone;
1413}
1414
1415static BOOL UpdateList(HWND hwnd, CHAR ** list)
1416{
1417  /* Updates files in the list */
1418
1419  ALLDATA *ad = WinQueryWindowPtr(hwnd, QWL_USER);
1420  register ULONG x, z;
1421  BOOL ret, didone = FALSE;
1422  FILEFINDBUF3 ffb;
1423  ULONG nm;
1424  HDIR hdir;
1425  CHAR *p;
1426
1427  if (list) {
1428    for (z = 0; list[z] && !ad->stopflag; z++) {
1429      ret = FALSE;
1430      for (x = 0; x < ad->affiles; x++) {
1431        if (!stricmp(list[z], ad->afhead[x].fullname)) {
1432          ret = TRUE;
1433          break;
1434        }
1435      }
1436      if (ret) {
1437        didone = TRUE;
1438        hdir = HDIR_CREATE;
1439        nm = 1;
1440        if (!DosFindFirst(list[z], &hdir, FILE_NORMAL | FILE_ARCHIVED |
1441                          FILE_DIRECTORY | FILE_READONLY | FILE_SYSTEM |
1442                          FILE_HIDDEN, &ffb, sizeof(ffb), &nm,
1443                          FIL_STANDARD)) {
1444          DosFindClose(hdir);
1445          if (!(ffb.attrFile & FILE_DIRECTORY)) {
1446            ad->afhead[x].attrFile = (USHORT) ffb.attrFile;
1447            ad->afhead[x].cbFile = ffb.cbFile;
1448            ad->afhead[x].date = ffb.fdateLastWrite;
1449            ad->afhead[x].time = ffb.ftimeLastWrite;
1450          }
1451          else
1452            ad->afhead[x].flags |= AF_DELETED;
1453        }
1454        else
1455          ad->afhead[x].flags |= AF_DELETED;
1456      }
1457      else if (isalpha(*list[z]) && ad->abDrvFlags[toupper(*list[z]) - 'A']) {
1458        didone = TRUE;
1459        hdir = HDIR_CREATE;
1460        nm = 1;
1461        if (!DosFindFirst(list[z], &hdir, FILE_NORMAL | FILE_ARCHIVED |
1462                          FILE_DIRECTORY | FILE_READONLY | FILE_SYSTEM |
1463                          FILE_HIDDEN, &ffb, sizeof(ffb), &nm,
1464                          FIL_STANDARD)) {
1465          DosFindClose(hdir);
1466          if (!(ffb.attrFile & FILE_DIRECTORY)) {
1467            if (!ad->afalloc || ad->affiles > ad->afalloc - 1) {
1468
1469              ALLFILES *temp, **templ;
1470
1471              temp =
1472                xrealloc(ad->afhead, (ad->afalloc + 1) * sizeof(ALLFILES),
1473                         pszSrcFile, __LINE__);
1474              if (!temp) {
1475                ad->stopflag = 1;
1476                break;
1477              }
1478              else {
1479                ad->afhead = temp;
1480                templ =
1481                  xrealloc(ad->afindex,
1482                           (ad->afalloc + 1) * sizeof(ALLFILES *), pszSrcFile,
1483                           __LINE__);
1484                if (!templ) {
1485                  ad->stopflag = 1;
1486                  break;
1487                }
1488                else
1489                  ad->afindex = templ;
1490                ad->afalloc++;
1491              }
1492            }
1493            ad->afhead[ad->affiles].fullname =
1494              xstrdup(list[z], pszSrcFile, __LINE__);
1495            if (ad->afhead[ad->affiles].fullname) {
1496              p = strrchr(ad->afhead[ad->affiles].fullname, '\\');
1497              if (!p)
1498                p = ad->afhead[ad->affiles].fullname;
1499              else
1500                p++;
1501              ad->afhead[ad->affiles].filename = p;
1502              ad->afhead[ad->affiles].cbFile = ffb.cbFile;
1503              ad->afhead[ad->affiles].date = ffb.fdateLastWrite;
1504              ad->afhead[ad->affiles].time = ffb.ftimeLastWrite;
1505              ad->afhead[ad->affiles].attrFile = (USHORT) ffb.attrFile;
1506              ad->afhead[ad->affiles].flags = 0;
1507              if (ad->longest < strlen(ad->afhead[ad->affiles].filename))
1508                ad->longest = strlen(ad->afhead[ad->affiles].filename);
1509              if (ad->longestw < strlen(ad->afhead[ad->affiles].fullname))
1510                ad->longestw = strlen(ad->afhead[ad->affiles].fullname);
1511
1512              ad->affiles++;
1513            }
1514            else {
1515              // saymsg(MB_ENTER,HWND_DESKTOP,DEBUG_STRING,"Strdup failed.");
1516              ad->stopflag = 1;
1517              break;
1518            }
1519          }
1520        }
1521      }
1522    }
1523  }
1524  return didone;
1525}
1526
1527static int comparefullnames(const void *v1, const void *v2)
1528{
1529  ALLFILES *d1 = *(ALLFILES **) v1;
1530  ALLFILES *d2 = *(ALLFILES **) v2;
1531  int ret;
1532
1533  ret = stricmp(d1->fullname, d2->fullname);
1534  return ret;
1535}
1536
1537static int comparenames(const void *v1, const void *v2)
1538{
1539  ALLFILES *d1 = *(ALLFILES **) v1;
1540  ALLFILES *d2 = *(ALLFILES **) v2;
1541  int ret;
1542
1543  ret = stricmp(d1->filename, d2->filename);
1544  if (!ret)
1545    ret = comparefullnames(v1, v2);
1546  return ret;
1547}
1548
1549static int compareexts(const void *v1, const void *v2)
1550{
1551  ALLFILES *d1 = *(ALLFILES **) v1;
1552  ALLFILES *d2 = *(ALLFILES **) v2;
1553  register CHAR *p1, *p2;
1554  int ret;
1555
1556  p1 = strrchr(d1->filename, '.');
1557  p2 = strrchr(d2->filename, '.');
1558  if (!p1)
1559    p1 = NullStr;
1560  else
1561    p1++;
1562  if (!p2)
1563    p2 = NullStr;
1564  else
1565    p2++;
1566  ret = stricmp(p1, p2);
1567  if (!ret)
1568    ret = comparenames(v1, v2);
1569  return ret;
1570}
1571
1572static int comparesizes(const void *v1, const void *v2)
1573{
1574  ALLFILES *d1 = *(ALLFILES **) v1;
1575  ALLFILES *d2 = *(ALLFILES **) v2;
1576  int ret;
1577
1578  ret = (d1->cbFile > d2->cbFile) ? 1 : (d1->cbFile == d2->cbFile) ? 0 : -1;
1579  if (!ret)
1580    ret = comparenames(v1, v2);
1581  return ret;
1582}
1583
1584static int comparedates(const void *v1, const void *v2)
1585{
1586  ALLFILES *d1 = *(ALLFILES **) v1;
1587  ALLFILES *d2 = *(ALLFILES **) v2;
1588  int ret;
1589
1590  ret = (d1->date.year > d2->date.year) ? 1 :
1591    (d1->date.year < d2->date.year) ? -1 :
1592    (d1->date.month > d2->date.month) ? 1 :
1593    (d1->date.month < d2->date.month) ? -1 :
1594    (d1->date.day > d2->date.day) ? 1 :
1595    (d1->date.day < d2->date.day) ? -1 :
1596    (d1->time.hours > d2->time.hours) ? 1 :
1597    (d1->time.hours < d2->time.hours) ? -1 :
1598    (d1->time.minutes > d2->time.minutes) ? 1 :
1599    (d1->time.minutes < d2->time.minutes) ? -1 :
1600    (d1->time.twosecs > d2->time.twosecs) ? 1 :
1601    (d1->time.twosecs < d2->time.twosecs) ? -1 : 0;
1602
1603  if (!ret)
1604    ret = comparenames(v1, v2);
1605  return ret;
1606}
1607
1608static VOID ReSort(HWND hwnd)
1609{
1610  ALLDATA *pAD = WinQueryWindowPtr(hwnd, QWL_USER);
1611  register ULONG x, y;
1612
1613  pAD->selected = 0;
1614  pAD->ullSelectedBytes = 0;
1615  for (x = 0, y = 0; x < pAD->affiles; x++) {
1616    if (!(pAD->afhead[x].flags & (AF_DELETED | AF_FILTERED))) {
1617      if (pAD->afhead[x].flags & AF_SELECTED) {
1618        pAD->selected++;
1619        pAD->ullSelectedBytes += pAD->afhead[x].cbFile;
1620      }
1621      pAD->afindex[y++] = &(pAD->afhead[x]);
1622    }
1623  }                                     // for x
1624  pAD->afifiles = y;
1625  PostMsg(hwnd, UM_SETUP3, MPVOID, MPVOID);
1626  if (!pAD->stopflag && pAD->pfnCompare && pAD->afifiles) {
1627    WinSendMsg(hwnd, UM_RESCAN, MPFROMLONG(1), MPVOID);
1628    qsort(pAD->afindex, pAD->afifiles, sizeof(ALLFILES *), pAD->pfnCompare);
1629  }
1630}
1631
1632VOID FindDupes(VOID * args)
1633{
1634  register ULONG x, z;
1635  register CHAR *px, *pz;
1636  CHAR s[80];
1637  INT error;
1638  HWND hwnd = (HWND) args;
1639  HAB hab2 = (HAB) 0;
1640  HMQ hmq2 = (HMQ) 0;
1641  ALLDATA *ad = WinQueryWindowPtr(hwnd, QWL_USER);
1642
1643  if (!DosRequestMutexSem(ad->hmtxScan, SEM_INDEFINITE_WAIT)) {
1644    priority_normal();
1645    hab2 = WinInitialize(0);
1646    if (hab2) {
1647      hmq2 = WinCreateMsgQueue(hab2, 0);
1648      if (hmq2) {
1649        WinCancelShutdown(hmq2, TRUE);
1650        IncrThreadUsage();
1651        if (ad->cursored <= ad->afifiles) {
1652          for (x = 0; x < ad->affiles; x++)
1653            ad->afhead[x].flags &= (~(AF_DUPE | AF_SELECTED));
1654          DosSleep(1);
1655          for (x = 0; x < ad->affiles && !ad->stopflag; x++) {
1656            if (!(ad->afhead[x].flags & (AF_DUPE | AF_FILTERED))) {
1657              if (!(x % 50)) {
1658                sprintf(s,
1659                        GetPString(IDS_DUPECHECKINGOFTEXT), x, ad->affiles);
1660                WinSetWindowText(ad->hwndStatus, s);
1661              }
1662              for (z = 0; z < ad->affiles && !ad->stopflag; z++) {
1663                if (x != z
1664                    && !(ad->afhead[z].flags & (AF_DUPE | AF_FILTERED))) {
1665                  if (ad->dupeflags & DP_SIZES) {
1666                    if (ad->afhead[x].cbFile != ad->afhead[z].cbFile)
1667                      goto SkipNonDupe;
1668                  }
1669                  if (ad->dupeflags & DP_DATES) {
1670                    if (*(INT *) & ad->afhead[x].date !=
1671                        *(INT *) & ad->afhead[z].date ||
1672                        *(INT *) & ad->afhead[x].time !=
1673                        *(INT *) & ad->afhead[z].time)
1674                      goto SkipNonDupe;
1675                  }
1676                  if (ad->dupeflags & DP_NAMES) {
1677                    if (ad->dupeflags & DP_EXTS) {
1678                      px = strrchr(ad->afhead[x].filename, '.');
1679                      pz = strrchr(ad->afhead[z].filename, '.');
1680                      if ((px || pz) && (!px || !pz))
1681                        goto SkipNonDupe;
1682                      if (px) {
1683                        *px = 0;
1684                        *pz = 0;
1685                      }
1686                    }
1687                    if (stricmp(ad->afhead[x].filename,
1688                                ad->afhead[z].filename)) {
1689                      if (ad->dupeflags & DP_EXTS) {
1690                        if (px) {
1691                          *px = '.';
1692                          *pz = '.';
1693                        }
1694                      }
1695                      goto SkipNonDupe;
1696                    }
1697                    if (ad->dupeflags & DP_EXTS) {
1698                      if (px) {
1699                        *px = '.';
1700                        *pz = '.';
1701                      }
1702                    }
1703                  }
1704                  if (ad->dupeflags & DP_CRCS) {
1705                    if (!(ad->afhead[x].flags & AF_CRCED)) {
1706                      ad->afhead[x].CRC = CRCFile(ad->afhead[x].fullname,
1707                                                  &error);
1708                      if (!error)
1709                        ad->afhead[x].flags |= AF_CRCED;
1710                    }
1711                    if (!(ad->afhead[z].flags & AF_CRCED)) {
1712                      ad->afhead[z].CRC = CRCFile(ad->afhead[z].fullname,
1713                                                  &error);
1714                      if (!error)
1715                        ad->afhead[z].flags |= AF_CRCED;
1716                    }
1717                    if ((ad->afhead[x].flags & AF_CRCED) &&
1718                        (ad->afhead[z].flags & AF_CRCED)) {
1719                      if (ad->afhead[x].CRC != ad->afhead[z].CRC)
1720                        goto SkipNonDupe;
1721                    }
1722                    DosSleep(1);
1723                  }
1724                  ad->afhead[x].flags |= AF_DUPE;
1725                  ad->afhead[z].flags |= AF_DUPE;
1726                SkipNonDupe:
1727                  ;
1728                }
1729              }
1730              DosSleep(1);
1731            }
1732          }
1733          for (x = 0; x < ad->affiles && !ad->stopflag; x++) {
1734            if (!(ad->afhead[x].flags & AF_DUPE))
1735              ad->afhead[x].flags |= AF_FILTERED;
1736          }
1737          ReSort(hwnd);
1738          WinInvalidateRect(hwnd, NULL, FALSE);
1739        }
1740      }
1741    }
1742    PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
1743    DosReleaseMutexSem(ad->hmtxScan);
1744  }                                     // if got sem
1745  if (hmq2) {
1746    PostMsg(hwnd, UM_CONTAINER_FILLED, MPVOID, MPVOID);
1747    WinDestroyMsgQueue(hmq2);
1748  }
1749  if (hab2) {
1750    DecrThreadUsage();
1751    WinTerminate(hab2);
1752  }
1753}
1754
1755static VOID FilterList(HWND hwnd)
1756{
1757  register ULONG x, z;
1758  BOOL ret;
1759  ALLDATA *ad = WinQueryWindowPtr(hwnd, QWL_USER);
1760  CHAR *p;
1761
1762  if (ad->cursored <= ad->afifiles) {
1763    x = ad->cursored - 1;
1764    x = (ad->invertsort) ? (ad->afifiles - 1) - x : x;
1765    p = strrchr(ad->afindex[x]->filename, '.');
1766    if (p) {
1767      strcpy(ad->mask.szMask, "*");
1768      strcat(ad->mask.szMask, p);
1769    }
1770  }
1771  *(ad->mask.prompt) = 0;
1772  ad->mask.fIsSeeAll = TRUE;
1773  if (WinDlgBox(HWND_DESKTOP, hwnd, PickMaskDlgProc,
1774                FM3ModHandle, MSK_FRAME, MPFROMP(&ad->mask))) {
1775    for (x = 0; x < ad->affiles; x++) {
1776      ret = FALSE;
1777      if (ad->mask.pszMasks[1]) {
1778        for (z = 0; ad->mask.pszMasks[z]; z++) {
1779          if (*ad->mask.pszMasks[z]) {
1780            if (*ad->mask.pszMasks[z] != '/') {
1781              if (wildcard((strchr(ad->mask.pszMasks[z], '\\') ||
1782                            strchr(ad->mask.pszMasks[z], ':')) ?
1783                           ad->afhead[x].fullname : ad->afhead[x].filename,
1784                           ad->mask.pszMasks[z], FALSE))
1785                ret = TRUE;
1786            }
1787            else {
1788              if (wildcard((strchr(ad->mask.pszMasks[z], '\\') ||
1789                            strchr(ad->mask.pszMasks[z], ':')) ?
1790                           ad->afhead[x].fullname : ad->afhead[x].filename,
1791                           ad->mask.pszMasks[z] + 1, FALSE)) {
1792                ret = FALSE;
1793                break;
1794              }
1795            }
1796          }
1797        }
1798      }
1799      else if (*ad->mask.szMask) {
1800        if (wildcard((strchr(ad->mask.szMask, '\\') ||
1801                      strchr(ad->mask.szMask, ':')) ?
1802                     ad->afhead[x].fullname : ad->afhead[x].filename,
1803                     ad->mask.szMask, FALSE))
1804          ret = TRUE;
1805      }
1806      else
1807        ret = TRUE;
1808
1809      if (ret) {
1810        if ((!(ad->mask.attrFile & FILE_HIDDEN)
1811             && (ad->afhead[x].attrFile & FILE_HIDDEN))
1812            || (!(ad->mask.attrFile & FILE_SYSTEM)
1813                && (ad->afhead[x].attrFile & FILE_SYSTEM))
1814            || (!(ad->mask.attrFile & FILE_READONLY)
1815                && (ad->afhead[x].attrFile & FILE_READONLY))
1816            || (!(ad->mask.attrFile & FILE_ARCHIVED)
1817                && (ad->afhead[x].attrFile & FILE_ARCHIVED)))
1818          ret = FALSE;
1819        else
1820          if (((ad->mask.antiattr & FILE_HIDDEN)
1821               && !(ad->afhead[x].attrFile & FILE_HIDDEN))
1822              || ((ad->mask.antiattr & FILE_SYSTEM)
1823                  && !(ad->afhead[x].attrFile & FILE_SYSTEM))
1824              || ((ad->mask.antiattr & FILE_READONLY)
1825                  && !(ad->afhead[x].attrFile & FILE_READONLY))
1826              || ((ad->mask.antiattr & FILE_ARCHIVED)
1827                  && !(ad->afhead[x].attrFile & FILE_ARCHIVED)))
1828          ret = FALSE;
1829      }
1830
1831      if (!ret)
1832        ad->afhead[x].flags |= AF_FILTERED;
1833      else
1834        ad->afhead[x].flags &= (~AF_FILTERED);
1835    }
1836    ReSort(hwnd);
1837    PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
1838    WinInvalidateRect(hwnd, NULL, FALSE);
1839  }
1840}
1841
1842static ULONG RemoveDeleted(HWND hwnd)
1843{
1844  ALLDATA *pAD = WinQueryWindowPtr(hwnd, QWL_USER);
1845  ULONG oldaffiles = pAD->affiles;
1846  register ULONG x, y;
1847
1848  for (x = 0; x < pAD->affiles; x++) {
1849    if (pAD->afhead[x].flags & AF_DELETED) {
1850      for (y = x; y < pAD->affiles; y++) {
1851        if (~pAD->afhead[y].flags & AF_DELETED)
1852          break;
1853        if (pAD->afhead[y].flags & AF_SELECTED &&
1854            ~pAD->afhead[y].flags & AF_FILTERED) {
1855          pAD->selected--;
1856          pAD->ullSelectedBytes -= pAD->afhead[y].cbFile;
1857        }
1858        free(pAD->afhead[y].fullname);
1859      }
1860      memmove(&(pAD->afhead[x]), &(pAD->afhead[y]),
1861              (pAD->affiles - y) * sizeof(ALLFILES));
1862      pAD->affiles -= (y - x);
1863    }
1864  }                                     // for x
1865  if (pAD->affiles != oldaffiles) {
1866
1867    ALLFILES *tempa, **templ;
1868
1869    if (!pAD->affiles)
1870      FreeAllFilesList(hwnd);
1871    else {
1872      tempa =
1873        xrealloc(pAD->afhead, pAD->affiles * sizeof(ALLFILES), pszSrcFile,
1874                 __LINE__);
1875      if (tempa) {
1876        pAD->afhead = tempa;
1877        pAD->afalloc = pAD->affiles;
1878      }
1879      templ =
1880        xrealloc(pAD->afindex, pAD->affiles * sizeof(ALLFILES *), pszSrcFile,
1881                 __LINE__);
1882      if (templ)
1883        pAD->afindex = templ;
1884      DosPostEventSem(CompactSem);
1885      ReSort(hwnd);
1886    }
1887  }
1888  return pAD->affiles;
1889}
1890
1891static VOID DoADir(HWND hwnd, CHAR * pathname)
1892{
1893  ALLDATA *ad = WinQueryWindowPtr(hwnd, QWL_USER);
1894  CHAR *filename, *enddir;
1895  FILEFINDBUF3 *pffb, *ffb;
1896  HDIR hdir = HDIR_CREATE;
1897  ULONG nm, uL;
1898  register ULONG x;
1899  register PBYTE fb;
1900
1901  filename = xmalloc(CCHMAXPATH, pszSrcFile, __LINE__);
1902  if (!filename)
1903    return;
1904
1905  uL = ad->afFilesToGet;
1906  if (fRemoteBug && isalpha(*pathname) && pathname[1] == ':' &&
1907      pathname[2] == '\\' &&
1908      (driveflags[toupper(*pathname) - 'A'] & DRIVE_REMOTE))
1909    uL = 1;
1910  pffb = xmalloc(sizeof(FILEFINDBUF3) * uL, pszSrcFile, __LINE__);
1911  if (!pffb) {
1912    free(filename);
1913    return;
1914  }
1915  nm = uL;
1916  strcpy(filename, pathname);
1917  enddir = &filename[strlen(filename) - 1];
1918  if (*enddir != '\\') {
1919    enddir++;
1920    *enddir = '\\';
1921  }
1922  enddir++;
1923  strcpy(enddir, "*");
1924  DosError(FERR_DISABLEHARDERR);
1925  if (!DosFindFirst(filename, &hdir, FILE_NORMAL | FILE_ARCHIVED |
1926                    FILE_READONLY | FILE_DIRECTORY | FILE_SYSTEM |
1927                    FILE_HIDDEN, pffb, sizeof(FILEFINDBUF3) * nm, &nm,
1928                    FIL_STANDARD)) {
1929    do {
1930      priority_normal();
1931      fb = (PBYTE) pffb;
1932      for (x = 0; x < nm; x++) {
1933        ffb = (FILEFINDBUF3 *) fb;
1934        if (ffb->attrFile & FILE_DIRECTORY) {
1935          // Skip . and ..
1936          if (ffb->achName[0] != '.' ||
1937              (ffb->achName[1] &&
1938               (ffb->achName[1] != '.' || ffb->achName[2]))) {
1939            strcpy(enddir, ffb->achName);
1940            DoADir(hwnd, filename);
1941          }
1942        }
1943        else {
1944          *enddir = 0;
1945          strcpy(enddir, ffb->achName);
1946          if (!ad->afalloc || ad->affiles > ad->afalloc - 1) {
1947
1948            ALLFILES *temp;
1949
1950            temp = xrealloc(ad->afhead, (ad->afalloc + 1000) *
1951                            sizeof(ALLFILES), pszSrcFile, __LINE__);
1952            if (!temp) {
1953              ad->stopflag = 1;
1954              break;
1955            }
1956            else {
1957              ad->afhead = temp;
1958              if (ad->stopflag)
1959                break;
1960              ad->afalloc += 1000;
1961            }
1962          }
1963          ad->afhead[ad->affiles].fullname =
1964            xstrdup(filename, pszSrcFile, __LINE__);
1965          if (!ad->afhead[ad->affiles].fullname) {
1966            ad->stopflag = 1;
1967            break;
1968          }
1969          else {
1970            ad->afhead[ad->affiles].filename =
1971              ad->afhead[ad->affiles].fullname + (enddir - filename);
1972            ad->afhead[ad->affiles].cbFile = ffb->cbFile;
1973            ad->afhead[ad->affiles].date = ffb->fdateLastWrite;
1974            ad->afhead[ad->affiles].time = ffb->ftimeLastWrite;
1975            ad->afhead[ad->affiles].attrFile = (USHORT) ffb->attrFile;
1976            ad->afhead[ad->affiles].flags = 0;
1977            ad->affiles++;
1978            if (ad->longest < ffb->cchName)
1979              ad->longest = ffb->cchName;
1980            if (ad->longestw < ffb->cchName + (enddir - filename))
1981              ad->longestw = ffb->cchName + (enddir - filename);
1982          }
1983        }
1984        fb += ffb->oNextEntryOffset;
1985      }
1986      nm = uL;
1987    } while (!ad->stopflag &&
1988             !DosFindNext(hdir, pffb, sizeof(FILEFINDBUF3) * nm, &nm));
1989    DosFindClose(hdir);
1990  }
1991  free(pffb);
1992  free(filename);
1993}
1994
1995static VOID FindAllThread(VOID * args)
1996{
1997  ULONG ulDriveNum, ulDriveMap, x;
1998  CHAR startname[] = " :\\";
1999  HWND hwnd = (HWND) args;
2000  HAB hab2 = (HAB) 0;
2001  HMQ hmq2 = (HMQ) 0;
2002  ALLDATA *ad = WinQueryWindowPtr(hwnd, QWL_USER);
2003
2004  if (!DosRequestMutexSem(ad->hmtxScan, SEM_INDEFINITE_WAIT)) {
2005    priority_normal();
2006    hab2 = WinInitialize(0);
2007    if (hab2) {
2008      hmq2 = WinCreateMsgQueue(hab2, 0);
2009      if (hmq2) {
2010        WinCancelShutdown(hmq2, TRUE);
2011        IncrThreadUsage();
2012        ad->afFilesToGet = FilesToGet;
2013        if (!*ad->szFindPath) {
2014          DosError(FERR_DISABLEHARDERR);
2015          if (!DosQCurDisk(&ulDriveNum, &ulDriveMap)) {
2016            for (x = 2; x < 26 && !ad->stopflag; x++) {
2017              if ((ulDriveMap & (1 << x)) && ad->abDrvFlags[x]) {
2018                *startname = (CHAR) (x + 'A');
2019                DoADir(hwnd, startname);
2020                PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
2021                DosSleep(1);
2022              }
2023            }
2024          }
2025        }
2026        else
2027          DoADir(hwnd, ad->szFindPath);
2028        DosPostEventSem(CompactSem);
2029      }
2030    }
2031    if (ad->afalloc != ad->affiles) {
2032
2033      ALLFILES *tempa, **templ;
2034
2035      tempa =
2036        xrealloc(ad->afhead, sizeof(ALLFILES) * ad->affiles, pszSrcFile,
2037                 __LINE__);
2038      if (tempa) {
2039        ad->afhead = tempa;
2040        ad->afalloc = ad->affiles;
2041      }
2042      templ =
2043        xrealloc(ad->afindex, sizeof(ALLFILES *) * ad->affiles, pszSrcFile,
2044                 __LINE__);
2045      if (templ)
2046        ad->afindex = templ;
2047      DosPostEventSem(CompactSem);
2048    }
2049
2050    if (!ad->stopflag) {
2051      PostMsg(hwnd, UM_RESCAN, MPFROMLONG(1), MPVOID);
2052      ReSort(hwnd);
2053    }
2054    DosReleaseMutexSem(ad->hmtxScan);
2055  }
2056  if (hmq2) {
2057    PostMsg(hwnd, UM_CONTAINER_FILLED, MPVOID, MPVOID);
2058    WinDestroyMsgQueue(hmq2);
2059  }
2060  if (hab2) {
2061    DecrThreadUsage();
2062    WinTerminate(hab2);
2063  }
2064}
2065
2066MRESULT EXPENTRY AFDrvsWndProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
2067{
2068  switch (msg) {
2069  case WM_INITDLG:
2070    if (mp2) {
2071
2072      ULONG ulDriveNum, ulDriveMap, x;
2073      CHAR startname[] = " :";
2074      SHORT sSelect;
2075      ALLDATA *ad;
2076
2077      ad = (ALLDATA *) mp2;
2078      WinSetWindowPtr(hwnd, QWL_USER, mp2);
2079      DosError(FERR_DISABLEHARDERR);
2080      if (!DosQCurDisk(&ulDriveNum, &ulDriveMap)) {
2081        for (x = 2; x < 26 && !ad->stopflag; x++) {
2082          if (!(driveflags[x] & (DRIVE_IGNORE | DRIVE_INVALID))) {
2083            if (ulDriveMap & (1 << x)) {
2084              *startname = (CHAR) (x + 'A');
2085              sSelect = (SHORT) WinSendDlgItemMsg(hwnd, DRVS_LISTBOX,
2086                                                  LM_INSERTITEM,
2087                                                  MPFROM2SHORT(LIT_END, 0),
2088                                                  MPFROMP(startname));
2089              if (sSelect >= 0 && ad->abDrvFlags[x])
2090                WinSendDlgItemMsg(hwnd, DRVS_LISTBOX, LM_SELECTITEM,
2091                                  MPFROM2SHORT(sSelect, 0), MPFROMLONG(TRUE));
2092            }
2093          }
2094        }
2095      }
2096    }
2097    else
2098      WinDismissDlg(hwnd, 0);
2099    break;
2100
2101  case WM_CONTROL:
2102    switch (SHORT1FROMMP(mp1)) {
2103    case DRVS_LISTBOX:
2104      switch (SHORT2FROMMP(mp1)) {
2105      case LN_ENTER:
2106        PostMsg(hwnd, WM_COMMAND, MPFROM2SHORT(DID_OK, 0), MPVOID);
2107        break;
2108      }
2109      break;
2110    }
2111    return 0;
2112
2113  case WM_COMMAND:
2114    switch (SHORT1FROMMP(mp1)) {
2115    case DID_OK:
2116      {
2117        INT x;
2118        SHORT sSelect;
2119        CHAR filename[3];
2120        ALLDATA *ad = WinQueryWindowPtr(hwnd, QWL_USER);
2121
2122        memset(ad->abDrvFlags, 0, sizeof(ad->abDrvFlags));
2123        sSelect = (SHORT) WinSendDlgItemMsg(hwnd, DRVS_LISTBOX,
2124                                            LM_QUERYSELECTION,
2125                                            MPFROM2SHORT(LIT_FIRST, 0),
2126                                            MPVOID);
2127        while (sSelect >= 0) {
2128          *filename = 0;
2129          if (WinSendDlgItemMsg(hwnd, DRVS_LISTBOX, LM_QUERYITEMTEXT,
2130                                MPFROM2SHORT(sSelect, 2),
2131                                MPFROMP(filename)) && *filename)
2132            ad->abDrvFlags[*filename - 'A'] = 1;
2133          sSelect = (SHORT) WinSendDlgItemMsg(hwnd, DRVS_LISTBOX,
2134                                              LM_QUERYSELECTION,
2135                                              MPFROM2SHORT(sSelect, 0),
2136                                              MPVOID);
2137        }
2138        for (x = 2; x < 26; x++) {
2139          if (ad->abDrvFlags[x]) {
2140            WinDismissDlg(hwnd, 1);
2141            return 0;
2142          }
2143        }
2144      }
2145      WinDismissDlg(hwnd, 0);
2146      break;
2147
2148    case IDM_HELP:
2149      if (hwndHelp)
2150        WinSendMsg(hwndHelp, HM_DISPLAY_HELP,
2151                   MPFROM2SHORT(HELP_DRVSWND, 0), MPFROMSHORT(HM_RESOURCEID));
2152      break;
2153
2154    case DID_CANCEL:
2155      WinDismissDlg(hwnd, 0);
2156      break;
2157    }
2158    return 0;
2159  }
2160  return WinDefDlgProc(hwnd, msg, mp1, mp2);
2161}
2162
2163static HPS InitWindow(HWND hwnd)
2164{
2165  ALLDATA *ad = WinQueryWindowPtr(hwnd, QWL_USER);
2166  HPS hps = (HPS) 0;
2167  SIZEL sizel;
2168  FONTMETRICS FontMetrics;
2169
2170  if (ad) {
2171    sizel.cx = sizel.cy = 0;
2172    hps = GpiCreatePS(WinQueryAnchorBlock(hwnd), WinOpenWindowDC(hwnd),
2173                      (PSIZEL) & sizel, PU_PELS | GPIF_DEFAULT | GPIT_MICRO |
2174                      GPIA_ASSOC);
2175    if (hps) {
2176      GpiSetCp(hps, (ULONG) ad->fattrs.usCodePage);
2177      GpiCreateLogFont(hps, NULL, FIXED_FONT_LCID, &ad->fattrs);
2178      GpiSetCharSet(hps, FIXED_FONT_LCID);
2179      GpiQueryFontMetrics(hps, sizeof(FontMetrics), &FontMetrics);
2180      ad->fattrs.lAveCharWidth = FontMetrics.lAveCharWidth;
2181      ad->fattrs.lMaxBaselineExt = FontMetrics.lMaxBaselineExt;
2182      ad->lMaxAscender = max(FontMetrics.lMaxAscender, 0);
2183      ad->lMaxDescender = max(FontMetrics.lMaxDescender, 0);
2184      ad->lMaxHeight = ad->lMaxDescender + ad->lMaxAscender;
2185      if (ad->fattrs.usCodePage != FontMetrics.usCodePage) {
2186        ad->fattrs.usCodePage = FontMetrics.usCodePage;
2187        Codepage = ad->fattrs.usCodePage;
2188        PrfWriteProfileData(fmprof,
2189                            appname,
2190                            "Seeall.Codepage",
2191                            &ad->fattrs.usCodePage, sizeof(USHORT));
2192      }
2193      else if (ad->fattrs.usCodePage) {
2194
2195        HMQ hmq;
2196        ULONG cps[50], len, x;
2197
2198        if (!DosQueryCp(sizeof(cps), cps, &len)) {
2199          for (x = 0; x < len / sizeof(ULONG); x++) {
2200            if (cps[x] == (ULONG) ad->fattrs.usCodePage) {
2201              hmq = WinQueryWindowULong(hwnd, QWL_HMQ);
2202              WinSetCp(hmq, ad->fattrs.usCodePage);
2203              break;
2204            }
2205          }
2206        }
2207        DosSetProcessCp((ULONG) ad->fattrs.usCodePage);
2208      }
2209      GpiSetBackMix(hps, BM_OVERPAINT);
2210    }
2211  }
2212  return (hps);
2213}
2214
2215static VOID PaintLine(HWND hwnd, HPS hps, ULONG whichfile, ULONG topfile,
2216                      RECTL * Rectl)
2217{
2218
2219  ALLDATA *ad = WinQueryWindowPtr(hwnd, QWL_USER);
2220  POINTL ptl;
2221  CHAR szBuff[CCHMAXPATH + 80];
2222  ULONG len, y;
2223
2224  y = (ad->invertsort) ? (ad->afifiles - 1) - whichfile : whichfile;
2225  ptl.y = (Rectl->yTop -
2226           (ad->lMaxHeight * (((whichfile + 1) - topfile) + 1)));
2227  ptl.x = ad->horzscroll;
2228  if (ptl.y < Rectl->yBottom || ptl.y > Rectl->yTop || y > ad->afifiles)
2229    return;
2230  GpiSetBackMix(hps, BM_OVERPAINT);
2231  if (ad->afindex[y]->flags & AF_SELECTED) {
2232    GpiSetColor(hps, standardcolors[Colors[COLORS_SELECTEDNORMALFORE]]);
2233    GpiSetBackColor(hps, (whichfile == ad->cursored - 1) ?
2234                    standardcolors[Colors[COLORS_CURSOREDSELECTEDBACK]] :
2235                    standardcolors[Colors[COLORS_SELECTEDBACK]]);
2236  }
2237  else {
2238    GpiSetColor(hps,
2239                ((ad->afindex[y]->attrFile & (FILE_SYSTEM | FILE_HIDDEN)) !=
2240                 0) ? standardcolors[Colors[COLORS_SYSTEMFORE]] : ((ad->
2241                                                                    afindex
2242                                                                    [y]->
2243                                                                    attrFile &
2244                                                                    FILE_READONLY)
2245                                                                   !=
2246                                                                   0) ?
2247                standardcolors[Colors[COLORS_READONLYFORE]] :
2248                standardcolors[Colors[COLORS_NORMALFORE]]);
2249    GpiSetBackColor(hps,
2250                    (whichfile ==
2251                     ad->cursored -
2252                     1) ? standardcolors[Colors[COLORS_CURSOREDNORMALBACK]] :
2253                    standardcolors[Colors[COLORS_NORMALBACK]]);
2254  }
2255  len = sprintf(szBuff,
2256                "%c%-*.*s  %-12lu  %c%c%c%c%c  %04u/%02u/%02u %02u:%02u:%02u ",
2257                (whichfile == ad->cursored - 1) ? '>' : ' ',
2258                (ad->fullnames) ? ad->longestw : ad->longest,
2259                (ad->fullnames) ? ad->longestw : ad->longest,
2260                (ad->fullnames) ? ad->afindex[y]->fullname :
2261                ad->afindex[y]->filename,
2262                ad->afindex[y]->cbFile,
2263                "-A"[((ad->afindex[y]->attrFile & FILE_ARCHIVED) != 0)],
2264                "-R"[((ad->afindex[y]->attrFile & FILE_READONLY) != 0)],
2265                "-H"[((ad->afindex[y]->attrFile & FILE_HIDDEN) != 0)],
2266                "-S"[((ad->afindex[y]->attrFile & FILE_SYSTEM) != 0)],
2267                "-D"[((ad->afindex[y]->attrFile & FILE_DIRECTORY) != 0)],
2268                ad->afindex[y]->date.year + 1980,
2269                ad->afindex[y]->date.month,
2270                ad->afindex[y]->date.day,
2271                ad->afindex[y]->time.hours,
2272                ad->afindex[y]->time.minutes,
2273                ad->afindex[y]->time.twosecs * 2);
2274  GpiCharStringAt(hps, &ptl, len, szBuff);
2275  GpiQueryCurrentPosition(hps, &ptl);
2276  if (ptl.x + abs(ad->horzscroll) > ad->maxx) {
2277    ad->maxx = ptl.x + abs(ad->horzscroll);
2278    WinSendMsg(ad->hhscroll, SBM_SETTHUMBSIZE,
2279               MPFROM2SHORT((SHORT) Rectl->xRight, (SHORT) ad->maxx), MPVOID);
2280  }
2281}
2282
2283MRESULT EXPENTRY SeeStatusProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
2284{
2285  switch (msg) {
2286  case WM_CREATE:
2287    return CommonTextProc(hwnd, msg, mp1, mp2);
2288
2289  case WM_SETFOCUS:
2290    if (mp2)
2291      PostMsg(hwnd, UM_FOCUSME, MPVOID, MPVOID);
2292    break;
2293
2294  case WM_PAINT:
2295    {
2296      SWP swp;
2297      POINTL ptl;
2298      HPS hps;
2299
2300      PaintRecessedWindow(hwnd, (HPS) 0, FALSE, FALSE);
2301      hps = WinGetPS(WinQueryWindow(hwnd, QW_PARENT));
2302      if (hps) {
2303        WinQueryWindowPos(hwnd, &swp);
2304        ptl.x = swp.x - 1;
2305        ptl.y = swp.y + swp.cy + 2;
2306        GpiMove(hps, &ptl);
2307        GpiSetColor(hps, CLR_WHITE);
2308        ptl.x = swp.x + swp.cx;
2309        GpiLine(hps, &ptl);
2310        WinReleasePS(hps);
2311      }
2312    }
2313    break;
2314
2315  case UM_FOCUSME:
2316    WinSetFocus(HWND_DESKTOP, WinWindowFromID(WinQueryWindow(hwnd, QW_PARENT),
2317                                              FID_CLIENT));
2318    return 0;
2319  }
2320  return PFNWPStatic(hwnd, msg, mp1, mp2);
2321}
2322
2323MRESULT EXPENTRY SeeFrameWndProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
2324{
2325  PFNWP oldproc = (PFNWP) WinQueryWindowPtr(hwnd, QWL_USER);
2326
2327  switch (msg) {
2328  case WM_BUTTON1UP:
2329  case WM_BUTTON2UP:
2330  case WM_BUTTON3UP:
2331  case WM_MOUSEMOVE:
2332  case WM_CHORD:
2333    shiftstate = (SHORT2FROMMP(mp2) & (KC_SHIFT | KC_ALT | KC_CTRL));
2334    break;
2335
2336  case WM_CHAR:
2337    shiftstate = (SHORT1FROMMP(mp1) & (KC_SHIFT | KC_ALT | KC_CTRL));
2338    break;
2339
2340  case WM_CALCFRAMERECT:
2341    {
2342      MRESULT mr;
2343      PRECTL prectl;
2344
2345      mr = oldproc(hwnd, msg, mp1, mp2);
2346
2347      /*
2348       * Calculate the position of the client rectangle.
2349       * Otherwise,  we'll see a lot of redraw when we move the
2350       * client during WM_FORMATFRAME.
2351       */
2352
2353      if (mr && mp2) {
2354        prectl = (PRECTL) mp1;
2355        prectl->yBottom += 22;
2356        prectl->yTop -= 24;
2357      }
2358      return mr;
2359    }
2360
2361  case WM_FORMATFRAME:
2362    {
2363      SHORT sCount;
2364      PSWP pswp, pswpClient, pswpNew;
2365
2366      sCount = (SHORT) oldproc(hwnd, msg, mp1, mp2);
2367
2368      /*
2369       * Reformat the frame to "squeeze" the client
2370       * and make room for status window sibling beneath
2371       */
2372
2373      pswp = (PSWP) mp1;
2374      {
2375        SHORT x;
2376
2377        for (x = 0; x < sCount; x++) {
2378          if (WinQueryWindowUShort(pswp->hwnd, QWS_ID) == FID_CLIENT) {
2379            pswpClient = pswp;
2380            break;
2381          }
2382          pswp++;
2383        }
2384      }
2385      pswpNew = (PSWP) mp1 + sCount;
2386      *pswpNew = *pswpClient;
2387      pswpNew->hwnd = WinWindowFromID(hwnd, SEEALL_STATUS);
2388      pswpNew->x = pswpClient->x + 2;
2389      pswpNew->y = pswpClient->y + 2;
2390      pswpNew->cx = pswpClient->cx - 3;
2391      pswpNew->cy = 20;
2392      pswpClient->y = pswpNew->y + pswpNew->cy + 3;
2393      pswpClient->cy = (pswpClient->cy - pswpNew->cy) - 5;
2394      sCount++;
2395      return MRFROMSHORT(sCount);
2396    }
2397
2398  case WM_QUERYFRAMECTLCOUNT:
2399    {
2400      SHORT sCount;
2401
2402      sCount = (SHORT) oldproc(hwnd, msg, mp1, mp2);
2403      sCount++;
2404      return MRFROMSHORT(sCount);
2405    }
2406  }
2407  return oldproc(hwnd, msg, mp1, mp2);
2408}
2409
2410MRESULT EXPENTRY SeeAllWndProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
2411{
2412  ALLDATA *pAD = WinQueryWindowPtr(hwnd, QWL_USER);
2413
2414  switch (msg) {
2415  case WM_CREATE:
2416    // fprintf(stderr,"Seeall: WM_CREATE\n");
2417    WinSetWindowPtr(hwnd, QWL_USER, NULL);
2418    pAD = xmallocz(sizeof(ALLDATA), pszSrcFile, __LINE__);
2419    if (pAD) {
2420      HWND hwndFrame;
2421
2422      pAD->size = sizeof(ALLDATA);
2423      hwndFrame = WinQueryWindow(hwnd, QW_PARENT);
2424      pAD->hwndFrame = hwndFrame;
2425      pAD->mask.attrFile = FILE_READONLY | FILE_HIDDEN |
2426        FILE_SYSTEM | FILE_ARCHIVED;
2427      pAD->mask.fNoDirs = TRUE;
2428      *(pAD->mask.prompt) = 0;
2429      WinSetWindowPtr(hwnd, QWL_USER, (PVOID) pAD);
2430      pAD->pfnCompare = comparenames;
2431      if (Firsttime) {
2432
2433        ULONG size;
2434
2435        size = sizeof(USHORT);
2436        PrfQueryProfileData(fmprof,
2437                            appname,
2438                            "Seeall.Codepage", (PVOID) & Codepage, &size);
2439        size = sizeof(BOOL);
2440        PrfQueryProfileData(fmprof,
2441                            appname,
2442                            "Seeall.Fullnames", (PVOID) & Fullnames, &size);
2443        size = sizeof(USHORT);
2444        PrfQueryProfileData(fmprof,
2445                            appname,
2446                            "Seeall.Sort", (PVOID) & SortType, &size);
2447        size = sizeof(BOOL);
2448        PrfQueryProfileData(fmprof,
2449                            appname,
2450                            "Seeall.SortReverse",
2451                            (PVOID) & SortReverse, &size);
2452        memset(&Fattrs, 0, sizeof(Fattrs));
2453        size = sizeof(Fattrs);
2454        Fattrs.usRecordLength = sizeof(Fattrs);
2455        Fattrs.lMaxBaselineExt = 16;
2456        Fattrs.lAveCharWidth = 8;
2457        Fattrs.usCodePage = Codepage;
2458        strcpy(Fattrs.szFacename, GetPString(IDS_SYSMONOTEXT));
2459        PrfQueryProfileData(fmprof,
2460                            appname,
2461                            "Seeall.Fattrs", (PVOID) & Fattrs, &size);
2462        size = sizeof(LONG) * COLORS_MAX;
2463        PrfQueryProfileData(fmprof,
2464                            appname, "Seeall.Colors", (PVOID) Colors, &size);
2465        Firsttime = FALSE;
2466      }
2467      switch (SortType) {
2468      case IDM_SORTEASIZE:
2469        pAD->pfnCompare = (PFNSORT) NULL;
2470        break;
2471      case IDM_SORTNAME:
2472        pAD->pfnCompare = comparefullnames;
2473        break;
2474      case IDM_SORTFILENAME:
2475        pAD->pfnCompare = comparenames;
2476        break;
2477      case IDM_SORTSIZE:
2478        pAD->pfnCompare = comparesizes;
2479        break;
2480      case IDM_SORTLWDATE:
2481        pAD->pfnCompare = comparedates;
2482        break;
2483      case IDM_SORTFIRST:
2484        pAD->pfnCompare = compareexts;
2485        break;
2486      }
2487      pAD->invertsort = SortReverse;
2488      pAD->fattrs = Fattrs;
2489      pAD->fullnames = Fullnames;
2490      pAD->stopflag = 0;
2491      pAD->cursored = pAD->topfile = 1;
2492      pAD->fattrs.usCodePage = Codepage;
2493      memcpy(pAD->aulColors, Colors, sizeof(LONG) * COLORS_MAX);
2494      pAD->hwndMenu = WinWindowFromID(hwndFrame, FID_MENU);
2495      SetConditionalCascade(pAD->hwndMenu, IDM_DELETESUBMENU,
2496                            (fDefaultDeletePerm) ?
2497                            IDM_PERMDELETE : IDM_DELETE);
2498      SetConditionalCascade(pAD->hwndMenu, IDM_MOVEMENU, IDM_MOVE);
2499      SetConditionalCascade(pAD->hwndMenu, IDM_COPYMENU, IDM_COPY);
2500      SetConditionalCascade(pAD->hwndMenu, IDM_OPENSUBMENU, IDM_OPENDEFAULT);
2501      SetConditionalCascade(pAD->hwndMenu, IDM_OBJECTSUBMENU, IDM_SHADOW);
2502      if (fWorkPlace) {
2503        WinSendMsg(pAD->hwndMenu, MM_DELETEITEM,
2504                   MPFROM2SHORT(IDM_OPENSUBMENU, TRUE), MPVOID);
2505        WinSendMsg(pAD->hwndMenu, MM_DELETEITEM,
2506                   MPFROM2SHORT(IDM_OBJECTSUBMENU, TRUE), MPVOID);
2507      }
2508      pAD->hwndClient = hwnd;
2509      pAD->hps = InitWindow(hwnd);
2510      pAD->hvscroll = WinWindowFromID(hwndFrame, FID_VERTSCROLL);
2511      pAD->hhscroll = WinWindowFromID(hwndFrame, FID_HORZSCROLL);
2512      pAD->multiplier = 1;
2513      if (_beginthread(MakeSeeObjWinThread, NULL, 122880, (PVOID) pAD) == -1)
2514        Runtime_Error(pszSrcFile, __LINE__,
2515                      GetPString(IDS_COULDNTSTARTTHREADTEXT));
2516      else {
2517        if (!DosCreateMutexSem(NULL, &pAD->hmtxScan, 0, FALSE)) {
2518          pAD->hwndStatus = WinCreateWindow(hwndFrame,
2519                                            WC_SEESTATUS,
2520                                            NullStr,
2521                                            WS_VISIBLE | SS_TEXT |
2522                                            DT_LEFT | DT_VCENTER,
2523                                            0,
2524                                            0,
2525                                            0,
2526                                            0,
2527                                            hwndFrame,
2528                                            HWND_TOP,
2529                                            SEEALL_STATUS, NULL, NULL);
2530          if (!pAD->hwndStatus)
2531            Win_Error2(hwndFrame, hwnd, pszSrcFile, __LINE__,
2532                       IDS_WINCREATEWINDOW);
2533          else {
2534            PFNWP oldproc;
2535
2536            oldproc = WinSubclassWindow(hwndFrame, SeeFrameWndProc);
2537            WinSetWindowPtr(hwndFrame, QWL_USER, (PVOID) oldproc);
2538          }
2539          break;
2540        }
2541      }
2542    }
2543    PostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
2544    break;
2545
2546  case UM_SETUP5:
2547    // fprintf(stderr,"Seeall: UM_SETUP5\n");
2548    if (pAD) {
2549      if (mp1 && *((CHAR *) mp1))
2550        strcpy(pAD->szFindPath, (CHAR *) mp1);
2551      else {
2552        if (!WinDlgBox(HWND_DESKTOP, hwnd, AFDrvsWndProc,
2553                       FM3ModHandle, DRVS_FRAME, (PVOID) pAD)) {
2554          PostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
2555          return 0;
2556        }
2557      }
2558      if (_beginthread(FindAllThread, NULL, 524288, (PVOID) hwnd) == -1) {
2559        Runtime_Error(pszSrcFile, __LINE__,
2560                      GetPString(IDS_COULDNTSTARTTHREADTEXT));
2561        PostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
2562      }
2563      else {
2564        DosSleep(100);
2565        PostMsg(hwnd, UM_SETUP, MPVOID, MPVOID);
2566        PostMsg(hwnd, UM_SETUP2, MPVOID, MPVOID);
2567      }
2568    }
2569    else
2570      PostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
2571    return 0;
2572
2573  case UM_UPDATERECORDLIST:
2574    if (mp1) {
2575
2576      APIRET rc;
2577
2578      rc = DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN);
2579      if (!rc) {
2580        WinSetPointer(HWND_DESKTOP, hptrBusy);
2581        if (UpdateList(hwnd, mp1)) {
2582          FreeList(mp1);
2583          RemoveDeleted(hwnd);
2584          ReSort(hwnd);
2585          WinInvalidateRect(hwnd, NULL, FALSE);
2586        }
2587        DosReleaseMutexSem(pAD->hmtxScan);
2588        WinSetPointer(HWND_DESKTOP, hptrArrow);
2589      }
2590    }
2591    return 0;
2592
2593  case UM_SETUP2:
2594// fprintf(stderr,"Seeall: UM_SETUP2\n");
2595    if (pAD) {
2596
2597      CHAR s[256];
2598      BOOL once = FALSE;
2599      ULONG x, ulDriveNum, ulDriveMap;
2600
2601      strcpy(s, GetPString(IDS_SEEALLTITLETEXT));
2602      if (!*pAD->szFindPath) {
2603        DosError(FERR_DISABLEHARDERR);
2604        if (!DosQCurDisk(&ulDriveNum, &ulDriveMap)) {
2605          for (x = 2; x < 26 && !pAD->stopflag; x++) {
2606            if ((ulDriveMap & (1 << x)) && pAD->abDrvFlags[x]) {
2607              sprintf(&s[strlen(s)], "%s%c:", (once) ? ", " : " (", x + 'A');
2608              once = TRUE;
2609            }
2610          }
2611          if (once)
2612            strcat(s, ")");
2613        }
2614      }
2615      else {
2616        strcat(s, " (");
2617        strcat(s, pAD->szFindPath);
2618        strcat(s, ")");
2619      }
2620      WinSetWindowText(WinQueryWindow(hwnd, QW_PARENT), s);
2621    }
2622    return 0;
2623
2624  case UM_SETUP3:
2625// fprintf(stderr,"Seeall: UM_SETUP3\n");
2626    if (pAD) {
2627      pAD->multiplier = pAD->afifiles / 32767;
2628      if (pAD->multiplier * 32767 != pAD->afifiles)
2629        pAD->multiplier++;
2630      if (!pAD->multiplier)
2631        pAD->multiplier++;
2632      {
2633        RECTL Rectl;
2634        ULONG numlines;
2635
2636        WinQueryWindowRect(hwnd, &Rectl);
2637        numlines = NumLines(&Rectl, pAD);
2638        if (numlines) {
2639          WinSendMsg(pAD->hhscroll, SBM_SETTHUMBSIZE,
2640                     MPFROM2SHORT((SHORT) Rectl.xRight, (SHORT) pAD->maxx),
2641                     MPVOID);
2642          WinSendMsg(pAD->hvscroll, SBM_SETTHUMBSIZE,
2643                     MPFROM2SHORT((SHORT) numlines,
2644                                  (SHORT) min(pAD->afifiles, 32767)),
2645                     MPFROM2SHORT(1, pAD->afifiles + 1));
2646          WinSendMsg(pAD->hhscroll, SBM_SETSCROLLBAR,
2647                     MPFROMSHORT((SHORT) abs(pAD->horzscroll)),
2648                     MPFROM2SHORT(0, (SHORT) (pAD->maxx - Rectl.xRight)));
2649          WinSendMsg(pAD->hvscroll, SBM_SETSCROLLBAR,
2650                     MPFROMSHORT((SHORT) (pAD->topfile / pAD->multiplier)),
2651                     MPFROM2SHORT(1,
2652                                  (SHORT) (pAD->afifiles / pAD->multiplier) -
2653                                  (numlines - 1)));
2654          if (pAD->afifiles - pAD->topfile < numlines) {
2655            pAD->topfile = ((pAD->afifiles - pAD->topfile) - numlines);
2656            WinInvalidateRect(hwnd, NULL, FALSE);
2657          }
2658        }
2659      }
2660    }
2661    return 0;
2662
2663  case UM_SETUP4:
2664    // fprintf(stderr,"Seeall: UM_SETUP4\n");
2665    if (pAD)
2666      pAD->killme = TRUE;
2667    else
2668      PostMsg((HWND) 0, WM_QUIT, MPVOID, MPVOID);
2669    return 0;
2670
2671  case UM_RESCAN:
2672    // fprintf(stderr,"Seeall: UM_RESCAN\n");
2673    if (pAD && !pAD->stopflag) {
2674      if (DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN)) {
2675        CHAR s[CCHMAXPATH + 80], tm[34];
2676
2677        if (mp1) {
2678          strcpy(s, GetPString(IDS_SORTINGTEXT));
2679          if (pAD->afifiles) {
2680            commafmt(tm, sizeof(tm), pAD->afifiles);
2681            strcat(s, tm);
2682          }
2683        }
2684        else {
2685          strcpy(s, GetPString(IDS_WORKINGTEXT));
2686          if (pAD->affiles) {
2687            commafmt(tm, sizeof(tm), pAD->affiles);
2688            strcat(s, tm);
2689          }
2690        }
2691        if (mp2) {
2692          strcat(s, " ");
2693          strcat(s, (CHAR *) mp2);
2694        }
2695        WinSetWindowText(pAD->hwndStatus, s);
2696      }
2697      else {
2698        CHAR s[(CCHMAXPATH * 2) + 80], tm[34], ts[34], tb[34];
2699        ULONG y;
2700
2701        if (mp1) {
2702          strcpy(s, GetPString(IDS_SORTINGTEXT));
2703          if (pAD->afifiles) {
2704            commafmt(tm, sizeof(tm), pAD->afifiles);
2705            strcat(s, tm);
2706          }
2707          if (mp2) {
2708            strcat(s, " ");
2709            strcat(s, (CHAR *) mp2);
2710          }
2711        }
2712        else if (pAD->afifiles) {
2713          y = (pAD->invertsort) ? (pAD->afifiles - 1) - (pAD->cursored - 1) :
2714            pAD->cursored - 1;
2715          commafmt(tm, sizeof(tm), pAD->afifiles);
2716          commafmt(ts, sizeof(ts), pAD->selected);
2717          CommaFmtULL(tb, sizeof(tb), pAD->ullSelectedBytes, ' ');
2718          sprintf(s,
2719                  " %s %s%s%s  %s %s (%s)  %s %s",
2720                  tm,
2721                  GetPString(IDS_FILETEXT),
2722                  &"s"[pAD->afifiles == 1],
2723                  (*pAD->mask.szMask ||
2724                   (pAD->mask.attrFile & (~FILE_DIRECTORY)) !=
2725                   (ALLATTRS & (~FILE_DIRECTORY)) ||
2726                   pAD->mask.antiattr) ?
2727                  GetPString(IDS_FILTEREDTEXT) :
2728                  NullStr,
2729                  ts,
2730                  GetPString(IDS_SELECTEDTEXT),
2731                  tb, GetPString(IDS_CURRTEXT), pAD->afindex[y]->fullname);
2732        }
2733        else
2734          sprintf(s,
2735                  GetPString(IDS_NOFILESPSTEXT),
2736                  (*pAD->mask.szMask ||
2737                   (pAD->mask.attrFile & (~FILE_DIRECTORY)) !=
2738                   (ALLATTRS & (~FILE_DIRECTORY)) ||
2739                   pAD->mask.antiattr) ?
2740                  GetPString(IDS_FILTEREDTEXT) : NullStr);
2741        WinSetWindowText(pAD->hwndStatus, s);
2742        DosReleaseMutexSem(pAD->hmtxScan);
2743      }
2744    }
2745    return 0;
2746
2747  case UM_SETUP:
2748    // fprintf(stderr,"Seeall: UM_SETUP\n");
2749    if (pAD) {
2750      WinSendMsg(pAD->hvscroll, SBM_SETTHUMBSIZE, MPFROM2SHORT(1, 1), MPVOID);
2751      WinSendMsg(pAD->hhscroll, SBM_SETTHUMBSIZE, MPFROM2SHORT(1, 1), MPVOID);
2752      WinSetActiveWindow(HWND_DESKTOP, WinQueryWindow(hwnd, QW_PARENT));
2753    }
2754    return 0;
2755
2756  case WM_CHAR:
2757    shiftstate = (SHORT1FROMMP(mp1) & (KC_SHIFT | KC_ALT | KC_CTRL));
2758    if (pAD && !(SHORT1FROMMP(mp1) & KC_KEYUP)) {
2759
2760      register ULONG x;
2761      ULONG numlines, y, wascursored = pAD->cursored, thistime, len;
2762      BOOL found = FALSE;
2763      RECTL rcl;
2764
2765      WinQueryWindowRect(hwnd, &rcl);
2766      numlines = NumLines(&rcl, pAD);
2767      if (numlines) {
2768        if (SHORT1FROMMP(mp1) & KC_VIRTUALKEY) {
2769          pAD->lasttime = 0;
2770          *pAD->szCommonName = 0;
2771          switch (SHORT2FROMMP(mp2)) {
2772          case VK_DELETE:
2773            if ((shiftstate & KC_CTRL) == KC_CTRL)
2774              PostMsg(hwnd, WM_COMMAND, MPFROM2SHORT(IDM_PERMDELETE, 0),
2775                      MPVOID);
2776            else if ((shiftstate & KC_SHIFT) == KC_SHIFT)
2777              PostMsg(hwnd, WM_COMMAND, MPFROM2SHORT(IDM_SAVETOCLIP, 0),
2778                      MPVOID);
2779            else
2780              PostMsg(hwnd, WM_COMMAND, MPFROM2SHORT(IDM_DELETE, 0), MPVOID);
2781            break;
2782          case VK_LEFT:
2783            WinSendMsg(hwnd, WM_HSCROLL, MPFROM2SHORT(FID_HORZSCROLL, 0),
2784                       MPFROM2SHORT(0, SB_LINELEFT));
2785            break;
2786          case VK_RIGHT:
2787            WinSendMsg(hwnd, WM_HSCROLL, MPFROM2SHORT(FID_HORZSCROLL, 0),
2788                       MPFROM2SHORT(0, SB_LINERIGHT));
2789            break;
2790          case VK_PAGEUP:
2791            WinSendMsg(hwnd, WM_VSCROLL, MPFROM2SHORT(FID_VERTSCROLL, 0),
2792                       MPFROM2SHORT(0, SB_PAGEUP));
2793            break;
2794          case VK_PAGEDOWN:
2795            WinSendMsg(hwnd, WM_VSCROLL, MPFROM2SHORT(FID_VERTSCROLL, 0),
2796                       MPFROM2SHORT(0, SB_PAGEDOWN));
2797            break;
2798          case VK_UP:
2799            if (pAD->cursored > 1) {
2800              if (shiftstate & KC_SHIFT)
2801                WinSendMsg(hwnd, WM_BUTTON1CLICK,
2802                           MPFROM2SHORT(pAD->fattrs.lAveCharWidth + 2,
2803                                        ((rcl.yTop - (pAD->lMaxHeight *
2804                                                      ((pAD->cursored) -
2805                                                       pAD->topfile))) -
2806                                         pAD->lMaxDescender) - 1),
2807                           MPFROM2SHORT(TRUE, 0));
2808              pAD->cursored--;
2809              if (pAD->cursored < pAD->topfile) {
2810                PaintLine(hwnd, pAD->hps, pAD->cursored, pAD->topfile, &rcl);
2811                WinSendMsg(hwnd, WM_VSCROLL, MPFROM2SHORT(FID_VERTSCROLL, 0),
2812                           MPFROM2SHORT(0, SB_LINEUP));
2813              }
2814              else {
2815                PaintLine(hwnd, pAD->hps, pAD->cursored - 1, pAD->topfile,
2816                          &rcl);
2817                PaintLine(hwnd, pAD->hps, pAD->cursored, pAD->topfile, &rcl);
2818              }
2819              PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
2820            }
2821            break;
2822          case VK_DOWN:
2823            if (pAD->cursored < pAD->afifiles
2824                && pAD->cursored < pAD->topfile + numlines) {
2825              if (shiftstate & KC_SHIFT)
2826                WinSendMsg(hwnd, WM_BUTTON1CLICK,
2827                           MPFROM2SHORT(pAD->fattrs.lAveCharWidth + 2,
2828                                        ((rcl.yTop - (pAD->lMaxHeight *
2829                                                      ((pAD->cursored) -
2830                                                       pAD->topfile))) -
2831                                         pAD->lMaxDescender) - 1),
2832                           MPFROM2SHORT(TRUE, 0));
2833              pAD->cursored++;
2834              if (pAD->cursored >= pAD->topfile + numlines) {
2835                PaintLine(hwnd, pAD->hps, pAD->cursored - 2, pAD->topfile,
2836                          &rcl);
2837                WinSendMsg(hwnd, WM_VSCROLL, MPFROM2SHORT(FID_VERTSCROLL, 0),
2838                           MPFROM2SHORT(0, SB_LINEDOWN));
2839              }
2840              else {
2841                PaintLine(hwnd, pAD->hps, pAD->cursored - 1, pAD->topfile,
2842                          &rcl);
2843                PaintLine(hwnd, pAD->hps, pAD->cursored - 2, pAD->topfile,
2844                          &rcl);
2845              }
2846              PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
2847            }
2848            break;
2849          case VK_END:
2850            if ((shiftstate & KC_CTRL) ||
2851                pAD->cursored == (pAD->topfile - 1) + numlines) {
2852              pAD->cursored = pAD->afifiles;
2853              pAD->topfile = (pAD->afifiles + 1) - numlines;
2854              if (pAD->topfile > pAD->afifiles)
2855                pAD->topfile = 1;
2856              WinInvalidateRect(hwnd, NULL, FALSE);
2857            }
2858            else {
2859              pAD->cursored = (pAD->topfile - 1) + numlines;
2860              if (pAD->cursored > pAD->afifiles)
2861                pAD->cursored = pAD->afifiles;
2862              PaintLine(hwnd, pAD->hps, pAD->cursored - 1, pAD->topfile,
2863                        &rcl);
2864              PaintLine(hwnd, pAD->hps, wascursored - 1, pAD->topfile, &rcl);
2865              PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
2866            }
2867            break;
2868          case VK_HOME:
2869            if ((shiftstate & KC_CTRL) || pAD->cursored == pAD->topfile) {
2870              pAD->topfile = 1;
2871              pAD->cursored = 1;
2872              WinInvalidateRect(hwnd, NULL, FALSE);
2873            }
2874            else {
2875              pAD->cursored = pAD->topfile;
2876              PaintLine(hwnd, pAD->hps, pAD->cursored - 1, pAD->topfile,
2877                        &rcl);
2878              PaintLine(hwnd, pAD->hps, wascursored - 1, pAD->topfile, &rcl);
2879              PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
2880            }
2881            break;
2882          case VK_SPACE:
2883            WinSendMsg(hwnd, WM_BUTTON1CLICK,
2884                       MPFROM2SHORT(pAD->fattrs.lAveCharWidth + 2,
2885                                    ((rcl.yTop - (pAD->lMaxHeight *
2886                                                  ((pAD->cursored) -
2887                                                   pAD->topfile))) -
2888                                     pAD->lMaxDescender) - 1),
2889                       MPFROM2SHORT(TRUE, 0));
2890            break;
2891          case VK_NEWLINE:
2892          case VK_ENTER:
2893            WinSendMsg(hwnd, WM_BUTTON1DBLCLK,
2894                       MPFROM2SHORT(pAD->fattrs.lAveCharWidth + 2,
2895                                    ((rcl.yTop - (pAD->lMaxHeight *
2896                                                  ((pAD->cursored) -
2897                                                   pAD->topfile))) -
2898                                     pAD->lMaxDescender) - 1), MPFROM2SHORT(0,
2899                                                                            0));
2900            break;
2901          }
2902        }
2903        else if (SHORT1FROMMP(mp1) & KC_CHAR) {
2904          switch (SHORT1FROMMP(mp2)) {
2905          case '\x1b':
2906          case '\r':
2907          case '\n':
2908            WinSendMsg(hwnd, WM_BUTTON1DBLCLK,
2909                       MPFROM2SHORT(pAD->fattrs.lAveCharWidth + 2,
2910                                    (rcl.yTop - (pAD->lMaxHeight *
2911                                                 ((pAD->cursored) -
2912                                                  pAD->topfile))) - 1),
2913                       MPFROM2SHORT(0, 0));
2914            pAD->lasttime = 0;
2915            *pAD->szCommonName = 0;
2916            break;
2917          default:
2918            thistime = WinQueryMsgTime(WinQueryAnchorBlock(hwnd));
2919            if (thistime > pAD->lasttime + 1000)
2920              *pAD->szCommonName = 0;
2921            pAD->lasttime = thistime;
2922          KbdRetry:
2923            len = strlen(pAD->szCommonName);
2924            if (len >= CCHMAXPATH - 1) {
2925              *pAD->szCommonName = 0;
2926              len = 0;
2927            }
2928            pAD->szCommonName[len] = toupper(SHORT1FROMMP(mp2));
2929            pAD->szCommonName[len + 1] = 0;
2930            for (x = pAD->cursored - (len > 0); x < pAD->afifiles; x++) {
2931              y = (pAD->invertsort) ? (pAD->afifiles - 1) - x : x;
2932              if (pAD->fullnames) {
2933                if (!strnicmp(pAD->afindex[y]->fullname, pAD->szCommonName,
2934                              len + 1)) {
2935                  found = TRUE;
2936                  break;
2937                }
2938              }
2939              else {
2940                if (!strnicmp(pAD->afindex[y]->filename, pAD->szCommonName,
2941                              len + 1)) {
2942                  found = TRUE;
2943                  break;
2944                }
2945              }
2946            }
2947            if (!found) {
2948              for (x = 0; x < pAD->cursored - (len > 0); x++) {
2949                y = (pAD->invertsort) ? (pAD->afifiles - 1) - x : x;
2950                if (pAD->fullnames) {
2951                  if (!strnicmp(pAD->afindex[y]->fullname, pAD->szCommonName,
2952                                len + 1)) {
2953                    found = TRUE;
2954                    break;
2955                  }
2956                }
2957                else {
2958                  if (!strnicmp(pAD->afindex[y]->filename, pAD->szCommonName,
2959                                len + 1)) {
2960                    found = TRUE;
2961                    break;
2962                  }
2963                }
2964              }
2965            }
2966            if (found) {
2967              if (x + 1 != pAD->cursored) {
2968                pAD->cursored = x + 1;
2969                if (pAD->cursored >= pAD->topfile &&
2970                    pAD->cursored < pAD->topfile + numlines &&
2971                    wascursored != pAD->cursored) {
2972                  PaintLine(hwnd, pAD->hps, pAD->cursored - 1, pAD->topfile,
2973                            &rcl);
2974                  PaintLine(hwnd, pAD->hps, wascursored - 1, pAD->topfile,
2975                            &rcl);
2976                }
2977                else {
2978                  if (pAD->cursored < numlines)
2979                    pAD->topfile = 1;
2980                  else if (pAD->cursored >
2981                           (pAD->afifiles + 1) - (numlines / 2))
2982                    pAD->topfile = (pAD->afifiles + 1) - numlines;
2983                  else
2984                    pAD->topfile = pAD->cursored - (numlines / 2);
2985                  WinInvalidateRect(hwnd, NULL, FALSE);
2986                }
2987              }
2988            }
2989            else {
2990              *pAD->szCommonName = 0;
2991              pAD->lasttime = 0;
2992              if (len)                  // retry as first letter if no match
2993                goto KbdRetry;
2994            }
2995            break;
2996          }
2997        }
2998      }
2999    }
3000    break;
3001
3002  case DM_PRINTOBJECT:
3003    return MRFROMLONG(DRR_TARGET);
3004
3005  case DM_DISCARDOBJECT:
3006    return MRFROMLONG(DRR_TARGET);
3007
3008  case WM_BEGINDRAG:
3009    {
3010      CHAR **list;
3011
3012      list = BuildAList(hwnd);
3013      if (!list)
3014        Runtime_Error(pszSrcFile, __LINE__, "no data");
3015      else {
3016        WinSetWindowText(pAD->hwndStatus, GetPString(IDS_DRAGGINGFILESTEXT));
3017        DragList(hwnd, (HWND) 0, list, TRUE);
3018        FreeList(list);
3019        PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
3020      }
3021    }
3022    break;
3023
3024  case WM_BUTTON1MOTIONSTART:
3025    if (pAD && !pAD->stopflag &&
3026        !DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN)) {
3027      pAD->mousecaptured = TRUE;
3028      pAD->lastselected = (ULONG) - 1;
3029      pAD->lastdirection = 0;
3030      WinSetCapture(HWND_DESKTOP, hwnd);
3031      DosReleaseMutexSem(pAD->hmtxScan);
3032      WinSendMsg(hwnd, WM_BUTTON1CLICK, mp1, MPFROM2SHORT(TRUE, 0));
3033    }
3034    break;
3035
3036  case WM_MOUSEMOVE:
3037    shiftstate = (SHORT2FROMMP(mp2) & (KC_SHIFT | KC_ALT | KC_CTRL));
3038    if (pAD && pAD->mousecaptured) {
3039
3040      ULONG numlines, whichfile, y, x;
3041      LONG inc;
3042      RECTL Rectl;
3043      POINTS pts;
3044      BOOL outofwindow = FALSE;
3045
3046      WinQueryWindowRect(hwnd, &Rectl);
3047      numlines = NumLines(&Rectl, pAD);
3048      if (numlines) {
3049        pts.x = SHORT1FROMMP(mp1);
3050        pts.y = SHORT2FROMMP(mp1);
3051        if (pts.y < 0) {
3052          WinSendMsg(hwnd, WM_VSCROLL, MPFROM2SHORT(FID_VERTSCROLL, 0),
3053                     MPFROM2SHORT(0, SB_LINEDOWN));
3054          pts.y = 1;
3055          outofwindow = TRUE;
3056        }
3057        else if (pts.y > Rectl.yTop - Rectl.yBottom) {
3058          WinSendMsg(hwnd, WM_VSCROLL, MPFROM2SHORT(FID_VERTSCROLL, 0),
3059                     MPFROM2SHORT(0, SB_LINEUP));
3060          pts.y = (Rectl.yTop - Rectl.yBottom) - 1;
3061          outofwindow = TRUE;
3062        }
3063        whichfile = ((Rectl.yTop - Rectl.yBottom) -
3064                     ((LONG) pts.y + pAD->lMaxDescender)) / pAD->lMaxHeight;
3065        if (whichfile > numlines - 1)
3066          whichfile = numlines - 1;
3067        whichfile += (pAD->topfile - 1);
3068        y = (pAD->invertsort) ? (pAD->afifiles - 1) - whichfile : whichfile;
3069        if (y < pAD->afifiles && pAD->lastselected != whichfile) {
3070          if (pAD->lastselected != (ULONG) - 1) {
3071            inc = (pAD->lastselected < whichfile) ? 1 : -1;
3072            for (x = pAD->lastselected + inc;
3073                 x != whichfile && x < pAD->afifiles;
3074                 (pAD->lastselected < whichfile) ? x++ : x--) {
3075              y = (pAD->invertsort) ? (pAD->afifiles - 1) - x : x;
3076              if (pAD->afindex[y]->flags & AF_SELECTED) {
3077                pAD->afindex[y]->flags &= ~AF_SELECTED;
3078                pAD->selected--;
3079                pAD->ullSelectedBytes -= pAD->afindex[y]->cbFile;
3080              }
3081              else {
3082                pAD->afindex[y]->flags |= AF_SELECTED;
3083                pAD->selected++;
3084                pAD->ullSelectedBytes += pAD->afindex[y]->cbFile;
3085              }
3086              PaintLine(hwnd, pAD->hps, x, pAD->topfile, &Rectl);
3087            }
3088          }
3089          WinSendMsg(hwnd, WM_BUTTON1CLICK, MPFROM2SHORT(pts.x, pts.y),
3090                     MPFROM2SHORT(TRUE, 0));
3091        }
3092      }
3093      if (outofwindow) {
3094
3095        POINTL ptl;
3096
3097        WinQueryPointerPos(HWND_DESKTOP, &ptl);
3098        WinMapWindowPoints(HWND_DESKTOP, hwnd, &ptl, 1);
3099        if ((SHORT) ptl.y == (SHORT) SHORT2FROMMP(mp1) &&
3100            (SHORT) ptl.x == (SHORT) SHORT1FROMMP(mp1) &&
3101            ((SHORT) ptl.y < 0 || ptl.y > (Rectl.yTop - Rectl.yBottom))) {
3102          PostMsg(hwnd, UM_MOUSEMOVE, mp1, MPVOID);
3103          DosSleep(1);
3104        }
3105      }
3106    }
3107    break;
3108
3109  case UM_MOUSEMOVE:
3110    if (pAD && pAD->mousecaptured) {
3111
3112      POINTL ptl;
3113      RECTL Rectl;
3114
3115      WinQueryWindowRect(hwnd, &Rectl);
3116      WinQueryPointerPos(HWND_DESKTOP, &ptl);
3117      WinMapWindowPoints(HWND_DESKTOP, hwnd, &ptl, 1);
3118      if ((SHORT) ptl.y == (SHORT) SHORT2FROMMP(mp1) &&
3119          (SHORT) ptl.x == (SHORT) SHORT1FROMMP(mp1) &&
3120          ((SHORT) ptl.y < 0 || ptl.y > (Rectl.yTop - Rectl.yBottom))) {
3121        DosSleep(1);
3122        PostMsg(hwnd, WM_MOUSEMOVE, mp1, MPFROM2SHORT(TRUE, 0));
3123      }
3124    }
3125    return 0;
3126
3127  case WM_BUTTON1UP:
3128  case WM_BUTTON1MOTIONEND:
3129    if (pAD) {
3130      pAD->mousecaptured = FALSE;
3131      pAD->lastselected = (ULONG) - 1;
3132      pAD->lastdirection = 0;
3133      WinSetCapture(HWND_DESKTOP, NULLHANDLE);
3134    }
3135    break;
3136
3137  case WM_BUTTON1CLICK:
3138  case WM_BUTTON1DBLCLK:
3139    shiftstate = (SHORT2FROMMP(mp2) & (KC_SHIFT | KC_ALT | KC_CTRL));
3140    if (pAD && !pAD->stopflag &&
3141        !DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN)) {
3142
3143      ULONG numlines, whichfile, y, wascursored;
3144      RECTL Rectl;
3145      POINTS pts;
3146
3147      if (pAD->afifiles) {
3148        WinQueryWindowRect(hwnd, &Rectl);
3149        numlines = NumLines(&Rectl, pAD);
3150        if (numlines) {
3151          pts.x = SHORT1FROMMP(mp1);
3152          pts.y = SHORT2FROMMP(mp1);
3153          whichfile = ((Rectl.yTop - Rectl.yBottom) -
3154                       ((LONG) pts.y + pAD->lMaxDescender)) / pAD->lMaxHeight;
3155          if (whichfile > numlines - 1)
3156            whichfile = numlines - 1;
3157          whichfile += (pAD->topfile - 1);
3158          if (whichfile + 1 > pAD->afifiles)
3159            break;
3160          y = (pAD->invertsort) ? (pAD->afifiles - 1) - whichfile : whichfile;
3161          wascursored = pAD->cursored;
3162          pAD->cursored = whichfile + 1;
3163          if (pAD->cursored != wascursored)
3164            PaintLine(hwnd, pAD->hps, wascursored - 1, pAD->topfile, &Rectl);
3165          if (y < pAD->afifiles) {
3166            if (msg == WM_BUTTON1CLICK || fUnHilite) {
3167              if (pAD->afindex[y]->flags & AF_SELECTED) {
3168                pAD->afindex[y]->flags &= ~AF_SELECTED;
3169                pAD->selected--;
3170                pAD->ullSelectedBytes -= pAD->afindex[y]->cbFile;
3171              }
3172              else {
3173                pAD->afindex[y]->flags |= AF_SELECTED;
3174                pAD->selected++;
3175                pAD->ullSelectedBytes += pAD->afindex[y]->cbFile;
3176              }
3177              PaintLine(hwnd, pAD->hps, whichfile, pAD->topfile, &Rectl);
3178              PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
3179            }
3180          }
3181          if (msg == WM_BUTTON1CLICK) {
3182            if (pAD->lastselected != (ULONG) - 1) {
3183              if (whichfile > pAD->lastselected)
3184                pAD->lastdirection = 1;
3185              else
3186                pAD->lastdirection = 2;
3187            }
3188            else
3189              pAD->lastdirection = 0;
3190            pAD->lastselected = whichfile;
3191          }
3192          else
3193            DefaultViewKeys(hwnd, pAD->hwndFrame, HWND_DESKTOP, NULL,
3194                            pAD->afindex[y]->fullname);
3195        }
3196      }
3197      DosReleaseMutexSem(pAD->hmtxScan);
3198    }
3199    break;
3200
3201  case WM_MENUEND:
3202    if (pAD && (HWND) mp2 == pAD->hwndPopup) {
3203      WinDestroyWindow(pAD->hwndPopup);
3204      pAD->hwndPopup = (HWND) 0;
3205    }
3206    break;
3207
3208  case WM_CONTEXTMENU:
3209    if (pAD) {
3210      if (!pAD->hwndPopup) {
3211        pAD->hwndPopup =
3212          WinLoadMenu(HWND_DESKTOP, FM3ModHandle, SEEALL_POPUP);
3213        if (pAD->hwndPopup) {
3214          WinSetPresParam(pAD->hwndPopup, PP_FONTNAMESIZE,
3215                          (ULONG) strlen(GetPString(IDS_8HELVTEXT)) + 1,
3216                          (PVOID) GetPString(IDS_8HELVTEXT));
3217          SetConditionalCascade(pAD->hwndPopup,
3218                                IDM_DELETESUBMENU,
3219                                (fDefaultDeletePerm) ?
3220                                IDM_PERMDELETE : IDM_DELETE);
3221          SetConditionalCascade(pAD->hwndPopup, IDM_MOVEMENU, IDM_MOVE);
3222          SetConditionalCascade(pAD->hwndPopup, IDM_COPYMENU, IDM_COPY);
3223          SetConditionalCascade(pAD->hwndPopup, IDM_OPENSUBMENU,
3224                                IDM_OPENDEFAULT);
3225          SetConditionalCascade(pAD->hwndMenu, IDM_OBJECTSUBMENU, IDM_SHADOW);
3226          if (fWorkPlace) {
3227            WinSendMsg(pAD->hwndPopup, MM_DELETEITEM,
3228                       MPFROM2SHORT(IDM_OPENSUBMENU, TRUE), MPVOID);
3229            WinSendMsg(pAD->hwndPopup, MM_DELETEITEM,
3230                       MPFROM2SHORT(IDM_OBJECTSUBMENU, TRUE), MPVOID);
3231          }
3232        }
3233      }
3234      if (pAD->hwndPopup) {
3235
3236        APIRET rc;
3237
3238        rc = DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN);
3239        WinEnableMenuItem(pAD->hwndPopup, IDM_EAS, (rc == 0 &&
3240                                                    pAD->selected != 0));
3241        WinEnableMenuItem(pAD->hwndPopup, IDM_UUDECODE, (rc == 0 &&
3242                                                         pAD->selected != 0));
3243        WinEnableMenuItem(pAD->hwndPopup, IDM_EXTRACT, (rc == 0 &&
3244                                                        pAD->selected != 0));
3245        WinEnableMenuItem(pAD->hwndPopup, IDM_ARCHIVE, (rc == 0 &&
3246                                                        pAD->selected != 0));
3247        WinEnableMenuItem(pAD->hwndPopup, IDM_MOVEMENU, (rc == 0 &&
3248                                                         pAD->selected != 0));
3249        WinEnableMenuItem(pAD->hwndPopup, IDM_COPYMENU, (rc == 0 &&
3250                                                         pAD->selected != 0));
3251        WinEnableMenuItem(pAD->hwndPopup, IDM_RENAME, (rc == 0 &&
3252                                                       pAD->selected != 0));
3253        WinEnableMenuItem(pAD->hwndPopup, IDM_PRINT, (rc == 0 &&
3254                                                      pAD->selected != 0));
3255        WinEnableMenuItem(pAD->hwndPopup, IDM_SUBJECT, (rc == 0 &&
3256                                                        pAD->selected != 0));
3257        WinEnableMenuItem(pAD->hwndPopup, IDM_OPENSUBMENU, (rc == 0 &&
3258                                                            pAD->selected !=
3259                                                            0));
3260        WinEnableMenuItem(pAD->hwndPopup, IDM_OBJECTSUBMENU,
3261                          (rc == 0 && pAD->selected != 0));
3262        WinEnableMenuItem(pAD->hwndPopup, IDM_DELETESUBMENU,
3263                          (rc == 0 && pAD->selected != 0));
3264        WinEnableMenuItem(pAD->hwndPopup, IDM_INFO,
3265                          (rc == 0 && pAD->selected != 0));
3266        WinEnableMenuItem(pAD->hwndPopup, IDM_ATTRS,
3267                          (rc == 0 && pAD->selected != 0));
3268        WinEnableMenuItem(pAD->hwndPopup, IDM_COLLECT,
3269                          (rc == 0 && pAD->selected != 0));
3270        WinEnableMenuItem(pAD->hwndPopup, IDM_SAVETOCLIP,
3271                          (rc == 0 && pAD->selected != 0));
3272        WinEnableMenuItem(pAD->hwndPopup, IDM_APPENDTOCLIP,
3273                          (rc == 0 && pAD->selected != 0));
3274        WinEnableMenuItem(pAD->hwndPopup, IDM_SAVETOLIST,
3275                          (rc == 0 && pAD->selected != 0));
3276        WinEnableMenuItem(pAD->hwndPopup, IDM_REMOVE,
3277                          (rc == 0 && pAD->selected != 0));
3278        WinEnableMenuItem(pAD->hwndPopup, IDM_HIDEALL,
3279                          (rc == 0 && pAD->selected != 0));
3280        WinEnableMenuItem(pAD->hwndPopup, IDM_SELECTALL,
3281                          (rc == 0 && pAD->afifiles != 0));
3282        WinEnableMenuItem(pAD->hwndPopup, IDM_SELECTMASK,
3283                          (rc == 0 && pAD->afifiles != 0));
3284        WinEnableMenuItem(pAD->hwndPopup, IDM_DESELECTALL,
3285                          (rc == 0 && pAD->afifiles != 0));
3286        WinEnableMenuItem(pAD->hwndPopup, IDM_DESELECTMASK,
3287                          (rc == 0 && pAD->afifiles != 0));
3288        WinEnableMenuItem(pAD->hwndPopup, IDM_INVERT,
3289                          (rc == 0 && pAD->afifiles != 0));
3290        WinEnableMenuItem(pAD->hwndPopup, IDM_FILTER,
3291                          (rc == 0 && pAD->affiles != 0));
3292        if (!rc)
3293          DosReleaseMutexSem(pAD->hmtxScan);
3294        if (WinPopupMenu(hwnd, hwnd, pAD->hwndPopup, SHORT1FROMMP(mp1),
3295                         SHORT2FROMMP(mp1), 0,
3296                         PU_HCONSTRAIN | PU_VCONSTRAIN |
3297                         PU_KEYBOARD | PU_MOUSEBUTTON1))
3298          CenterOverWindow(pAD->hwndPopup);
3299      }
3300    }
3301    break;
3302
3303  case UM_CONTAINER_FILLED:
3304    if (pAD) {
3305      pAD->stopflag = 0;
3306      pAD->topfile = 1;
3307      pAD->cursored = 1;
3308      pAD->multiplier = 1;
3309      if (!pAD->afifiles) {
3310        DosBeep(250, 50);
3311        PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
3312      }
3313      else {
3314        DosBeep(1000, 25);
3315        WinInvalidateRect(hwnd, NULL, FALSE);
3316        PostMsg(hwnd, UM_SETUP3, MPVOID, MPVOID);
3317      }
3318      WinSetWindowPos(WinQueryWindow(hwnd, QW_PARENT), HWND_TOP, 0, 0, 0, 0,
3319                      SWP_SHOW | SWP_RESTORE | SWP_ACTIVATE | SWP_ZORDER);
3320    }
3321    return 0;
3322
3323  case WM_ERASEBACKGROUND:
3324    WinFillRect((HPS) mp1, (PRECTL) mp2,
3325                standardcolors[Colors[COLORS_NORMALBACK]]);
3326    return 0;
3327
3328  case WM_PAINT:
3329    // fprintf(stderr,"Seeall: WM_PAINT\n");
3330    if (pAD) {
3331
3332      HPS hpsp;
3333      RECTL Rectl;
3334      POINTL ptl;
3335      register ULONG x;
3336      ULONG y, len, numlines;
3337      CHAR szBuff[CCHMAXPATH + 80];
3338      BOOL inverted, hidsys, reado, wascursored;
3339
3340      hpsp = WinBeginPaint(hwnd, pAD->hps, &Rectl);
3341      WinFillRect(hpsp, &Rectl, standardcolors[Colors[COLORS_NORMALBACK]]);
3342      if (!pAD->stopflag &&
3343          !DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN)) {
3344        WinQueryWindowRect(hwnd, &Rectl);
3345        numlines = NumLines(&Rectl, pAD);
3346        if (pAD->afifiles && numlines) {
3347          if (pAD->topfile > (pAD->afifiles + 1) - numlines)
3348            pAD->topfile = (pAD->afifiles + 1) - numlines;
3349          if (pAD->topfile > pAD->afifiles)
3350            pAD->topfile = 1;
3351          if (!pAD->topfile)
3352            pAD->topfile = 1;
3353          if (pAD->cursored < pAD->topfile)
3354            pAD->cursored = pAD->topfile;
3355          else if (pAD->cursored > (pAD->topfile + numlines) - 1)
3356            pAD->cursored = (pAD->topfile + numlines) - 1;
3357          if (pAD->cursored > pAD->afifiles)
3358            pAD->cursored = pAD->afifiles;
3359        }
3360        else
3361          pAD->topfile = pAD->cursored = 1;
3362        if (numlines && pAD->afifiles) {
3363          GpiSetBackMix(hpsp, BM_OVERPAINT);
3364          wascursored = TRUE;
3365          for (x = pAD->topfile - 1; x < pAD->afifiles; x++) {
3366            ptl.x = pAD->horzscroll;
3367            if (wascursored) {          /* reestablish normal colors */
3368              GpiSetColor(pAD->hps,
3369                          standardcolors[Colors[COLORS_NORMALFORE]]);
3370              GpiSetBackColor(pAD->hps,
3371                              standardcolors[Colors[COLORS_NORMALBACK]]);
3372              wascursored = inverted = hidsys = reado = FALSE;
3373            }
3374            if (x == pAD->cursored - 1)
3375              wascursored = TRUE;
3376            y = (pAD->invertsort) ? (pAD->afifiles - 1) - x : x;
3377            ptl.y = (Rectl.yTop -
3378                     (pAD->lMaxHeight * (((x + 1) - pAD->topfile) + 1)));
3379            if (ptl.y - pAD->lMaxDescender <= 0)
3380              break;
3381            if (pAD->afindex[y]->flags & AF_SELECTED) {
3382              if (!inverted) {
3383                GpiSetColor(pAD->hps,
3384                            standardcolors[Colors
3385                                           [COLORS_SELECTEDNORMALFORE]]);
3386                GpiSetBackColor(pAD->hps,
3387                                (wascursored) ?
3388                                standardcolors[Colors
3389                                               [COLORS_CURSOREDSELECTEDBACK]]
3390                                :
3391                                standardcolors[Colors[COLORS_SELECTEDBACK]]);
3392                inverted = TRUE;
3393              }
3394            }
3395            else if (inverted ||
3396                     ((pAD->afindex[y]->attrFile &
3397                       (FILE_SYSTEM | FILE_HIDDEN)) != 0) != hidsys ||
3398                     ((pAD->afindex[y]->attrFile & FILE_READONLY) != 0) !=
3399                     reado) {
3400              if (pAD->afindex[y]->attrFile & (FILE_SYSTEM | FILE_HIDDEN)) {
3401                GpiSetColor(pAD->hps,
3402                            standardcolors[Colors[COLORS_SYSTEMFORE]]);
3403                hidsys = TRUE;
3404              }
3405              else if ((pAD->afindex[y]->attrFile & FILE_READONLY) != 0) {
3406                GpiSetColor(pAD->hps,
3407                            standardcolors[Colors[COLORS_READONLYFORE]]);
3408                reado = TRUE;
3409              }
3410              else
3411                GpiSetColor(pAD->hps,
3412                            standardcolors[Colors[COLORS_NORMALFORE]]);
3413              GpiSetBackColor(pAD->hps,
3414                              (wascursored) ?
3415                              standardcolors[Colors
3416                                             [COLORS_CURSOREDNORMALBACK]] :
3417                              standardcolors[Colors[COLORS_NORMALBACK]]);
3418              inverted = FALSE;
3419            }
3420            else if (wascursored)
3421              GpiSetBackColor(pAD->hps,
3422                              standardcolors[Colors
3423                                             [COLORS_CURSOREDNORMALBACK]]);
3424            len =
3425              sprintf(szBuff,
3426                      "%c%-*.*s  %-12lu  %c%c%c%c%c  %04u/%02u/%02u %02u:%02u:%02u ",
3427                      (wascursored) ? '>' : ' ',
3428                      (pAD->fullnames) ? pAD->longestw : pAD->longest,
3429                      (pAD->fullnames) ? pAD->longestw : pAD->longest,
3430                      (pAD->fullnames) ? pAD->afindex[y]->fullname : pAD->
3431                      afindex[y]->filename, pAD->afindex[y]->cbFile,
3432                      "-A"[((pAD->afindex[y]->attrFile & FILE_ARCHIVED) !=
3433                            0)],
3434                      "-R"[((pAD->afindex[y]->attrFile & FILE_READONLY) !=
3435                            0)],
3436                      "-H"[((pAD->afindex[y]->attrFile & FILE_HIDDEN) != 0)],
3437                      "-S"[((pAD->afindex[y]->attrFile & FILE_SYSTEM) != 0)],
3438                      "-D"[((pAD->afindex[y]->attrFile & FILE_DIRECTORY) !=
3439                            0)], pAD->afindex[y]->date.year + 1980,
3440                      pAD->afindex[y]->date.month, pAD->afindex[y]->date.day,
3441                      pAD->afindex[y]->time.hours,
3442                      pAD->afindex[y]->time.minutes,
3443                      pAD->afindex[y]->time.twosecs * 2);
3444            GpiCharStringAt(hpsp, &ptl, len, szBuff);
3445            GpiQueryCurrentPosition(hpsp, &ptl);
3446            if (ptl.x + abs(pAD->horzscroll) > pAD->maxx) {
3447              pAD->maxx = ptl.x + abs(pAD->horzscroll);
3448              WinSendMsg(pAD->hhscroll, SBM_SETTHUMBSIZE,
3449                         MPFROM2SHORT((SHORT) Rectl.xRight,
3450                                      (SHORT) pAD->maxx), MPVOID);
3451            }
3452          }
3453        }
3454        DosReleaseMutexSem(pAD->hmtxScan);
3455      }
3456      WinEndPaint(hpsp);
3457      PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
3458      if (!pAD->stopflag)
3459        WinSendMsg(pAD->hvscroll, SBM_SETSCROLLBAR,
3460                   MPFROMSHORT((SHORT) (pAD->topfile / pAD->multiplier)),
3461                   MPFROM2SHORT(1,
3462                                (SHORT) (pAD->afifiles / pAD->multiplier) -
3463                                (numlines - 1)));
3464      WinSendMsg(pAD->hhscroll, SBM_SETSCROLLBAR,
3465                 MPFROMSHORT((SHORT) abs(pAD->horzscroll)),
3466                 MPFROM2SHORT(0, (SHORT) (pAD->maxx - Rectl.xRight)));
3467      WinSendMsg(pAD->hhscroll, SBM_SETTHUMBSIZE,
3468                 MPFROM2SHORT((SHORT) Rectl.xRight, (SHORT) pAD->maxx),
3469                 MPVOID);
3470    }
3471    break;
3472
3473  case WM_HSCROLL:
3474    {
3475      RECTL rectl;
3476      BOOL invalidate = TRUE;
3477
3478      WinQueryWindowRect(hwnd, &rectl);
3479      switch (SHORT2FROMMP(mp2)) {
3480      case SB_PAGERIGHT:
3481        if (abs(pAD->horzscroll) < pAD->maxx - rectl.xRight) {
3482          pAD->horzscroll -= rectl.xRight;
3483          if (abs(pAD->horzscroll) > pAD->maxx - rectl.xRight)
3484            pAD->horzscroll = -(pAD->maxx - rectl.xRight);
3485        }
3486        break;
3487
3488      case SB_PAGELEFT:
3489        if (pAD->horzscroll < 0) {
3490          pAD->horzscroll += rectl.xRight;
3491          if (pAD->horzscroll > 0)
3492            pAD->horzscroll = 0;
3493        }
3494        break;
3495
3496      case SB_LINERIGHT:
3497        if (abs(pAD->horzscroll) < pAD->maxx - rectl.xRight)
3498          pAD->horzscroll -= pAD->fattrs.lAveCharWidth;
3499        break;
3500
3501      case SB_LINELEFT:
3502        if (pAD->horzscroll < 0)
3503          pAD->horzscroll += pAD->fattrs.lAveCharWidth;
3504        break;
3505
3506      case SB_SLIDERTRACK:
3507        pAD->horzscroll = SHORT1FROMMP(mp2);
3508        pAD->horzscroll = -(pAD->horzscroll);
3509        if (pAD->horzscroll > 0)
3510          pAD->horzscroll = 0;
3511        if (abs(pAD->horzscroll) > pAD->maxx - rectl.xRight)
3512          pAD->horzscroll = -(pAD->maxx - rectl.xRight);
3513        break;
3514
3515      default:
3516        invalidate = FALSE;
3517        break;
3518      }
3519      if (invalidate)
3520        WinInvalidateRect(hwnd, NULL, FALSE);
3521    }
3522    break;
3523
3524  case WM_VSCROLL:
3525// fprintf(stderr,"Seeall: WM_VSCROLL\n");
3526    if (pAD && !pAD->stopflag &&
3527        !DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN)) {
3528
3529      ULONG numlines, wascursored;
3530      RECTL rcl;
3531
3532      if (pAD->afifiles) {
3533        WinQueryWindowRect(hwnd, &rcl);
3534        numlines = NumLines(&rcl, pAD);
3535        if (numlines) {
3536          wascursored = pAD->cursored;
3537          switch (SHORT2FROMMP(mp2)) {
3538          case SB_PAGEUP:
3539            if (pAD->topfile > 1) {
3540              pAD->topfile -= numlines;
3541              if (pAD->topfile > pAD->afifiles ||
3542                  pAD->topfile > (pAD->afifiles + 1) - numlines)
3543                pAD->topfile = 1;
3544              if (pAD->cursored > pAD->topfile + numlines)
3545                pAD->cursored = pAD->topfile + numlines;
3546              if (pAD->cursored > pAD->afifiles)
3547                pAD->cursored = pAD->afifiles;
3548              WinInvalidateRect(hwnd, NULL, FALSE);
3549            }
3550            break;
3551          case SB_PAGEDOWN:
3552            if (pAD->topfile <= pAD->afifiles - numlines) {
3553              pAD->topfile += numlines;
3554              if (pAD->topfile > (pAD->afifiles + 1) - numlines)
3555                pAD->topfile = (pAD->afifiles + 1) - numlines;
3556              if (pAD->cursored < pAD->topfile)
3557                pAD->cursored = pAD->topfile;
3558              if (pAD->cursored > (pAD->topfile + numlines) - 1)
3559                pAD->cursored = (pAD->topfile + numlines) - 1;
3560              if (pAD->cursored > pAD->afifiles)
3561                pAD->cursored = pAD->afifiles;
3562              WinInvalidateRect(hwnd, NULL, FALSE);
3563            }
3564            break;
3565          case SB_LINEDOWN:
3566            if (pAD->topfile <= pAD->afifiles - numlines) {
3567
3568              RECTL Rectl, iRectl;
3569
3570              pAD->topfile++;
3571              if (pAD->cursored < pAD->topfile)
3572                pAD->cursored = pAD->topfile;
3573              else if (pAD->cursored > (pAD->topfile + numlines) - 1)
3574                pAD->cursored = (pAD->topfile + numlines) - 1;
3575              if (pAD->cursored > pAD->afifiles)
3576                pAD->cursored = pAD->afifiles;
3577              WinQueryWindowRect(hwnd, &Rectl);
3578              WinScrollWindow(hwnd, 0, pAD->lMaxHeight,
3579                              NULL, NULL, NULLHANDLE, &iRectl, 0);
3580              WinFillRect(pAD->hps, &iRectl,
3581                          standardcolors[Colors[COLORS_NORMALBACK]]);
3582              PaintLine(hwnd, pAD->hps, (pAD->topfile + numlines) - 2,
3583                        pAD->topfile, &Rectl);
3584              if (pAD->cursored != pAD->topfile + numlines)
3585                PaintLine(hwnd, pAD->hps, pAD->cursored - 1, pAD->topfile,
3586                          &Rectl);
3587              if (wascursored != pAD->cursored
3588                  && wascursored < pAD->topfile + numlines
3589                  && wascursored >= pAD->topfile)
3590                PaintLine(hwnd, pAD->hps, wascursored - 1, pAD->topfile,
3591                          &Rectl);
3592              if (wascursored != pAD->cursored)
3593                PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
3594              WinSendMsg(pAD->hhscroll, SBM_SETSCROLLBAR,
3595                         MPFROMSHORT((SHORT) abs(pAD->horzscroll)),
3596                         MPFROM2SHORT(0, (SHORT) (pAD->maxx - Rectl.xRight)));
3597              WinSendMsg(pAD->hvscroll, SBM_SETSCROLLBAR,
3598                         MPFROMSHORT((SHORT) (pAD->topfile /
3599                                              pAD->multiplier)),
3600                         MPFROM2SHORT(1, (SHORT) (pAD->afifiles /
3601                                                  pAD->multiplier) -
3602                                      (numlines - 1)));
3603            }
3604            break;
3605          case SB_LINEUP:
3606            if (pAD->topfile > 1) {
3607
3608              RECTL Rectl, iRectl;
3609
3610              pAD->topfile--;
3611              if (pAD->cursored < pAD->topfile)
3612                pAD->cursored = pAD->topfile;
3613              else if (pAD->cursored > (pAD->topfile + numlines) - 1)
3614                pAD->cursored = (pAD->topfile + numlines) - 1;
3615              if (pAD->cursored > pAD->afifiles)
3616                pAD->cursored = pAD->afifiles;
3617              WinQueryWindowRect(hwnd, &Rectl);
3618              WinScrollWindow(hwnd, 0, -pAD->lMaxHeight,
3619                              NULL, NULL, NULLHANDLE, &iRectl, 0);
3620              WinFillRect(pAD->hps, &iRectl,
3621                          standardcolors[Colors[COLORS_NORMALBACK]]);
3622              iRectl = Rectl;
3623              iRectl.yTop -= ((numlines * pAD->lMaxHeight) +
3624                              pAD->lMaxDescender);
3625              WinFillRect(pAD->hps, &iRectl,
3626                          standardcolors[pAD->aulColors[COLORS_NORMALBACK]]);
3627              PaintLine(hwnd, pAD->hps, pAD->topfile - 1, pAD->topfile,
3628                        &Rectl);
3629              if (pAD->cursored != pAD->topfile)
3630                PaintLine(hwnd, pAD->hps, pAD->cursored - 1, pAD->topfile,
3631                          &Rectl);
3632              if (pAD->cursored != wascursored && wascursored >= pAD->topfile
3633                  && wascursored < pAD->topfile + numlines)
3634                PaintLine(hwnd, pAD->hps, wascursored - 1, pAD->topfile,
3635                          &Rectl);
3636              if (pAD->cursored != wascursored)
3637                PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
3638              WinSendMsg(pAD->hhscroll, SBM_SETSCROLLBAR,
3639                         MPFROMSHORT((SHORT) abs(pAD->horzscroll)),
3640                         MPFROM2SHORT(0, (SHORT) (pAD->maxx - Rectl.xRight)));
3641              WinSendMsg(pAD->hvscroll, SBM_SETSCROLLBAR,
3642                         MPFROMSHORT((SHORT) (pAD->topfile /
3643                                              pAD->multiplier)),
3644                         MPFROM2SHORT(1, (SHORT) (pAD->afifiles /
3645                                                  pAD->multiplier) -
3646                                      (numlines - 1)));
3647            }
3648            break;
3649          case SB_SLIDERTRACK:
3650            if ((SHORT1FROMMP(mp2) >= 1) ||
3651                (SHORT1FROMMP(mp2)) <= pAD->afifiles) {
3652              pAD->topfile = (ULONG) SHORT1FROMMP(mp2) * pAD->multiplier;
3653              if (pAD->topfile > (pAD->afifiles + 1) - numlines)
3654                pAD->topfile = (pAD->afifiles + 1) - numlines;
3655              if (!pAD->topfile)
3656                pAD->topfile = 1;
3657              if (pAD->cursored < pAD->topfile)
3658                pAD->cursored = pAD->topfile;
3659              else if (pAD->cursored > pAD->topfile + numlines)
3660                pAD->cursored = pAD->topfile + numlines;
3661              if (pAD->cursored > pAD->afifiles)
3662                pAD->cursored = pAD->afifiles;
3663              WinInvalidateRect(hwnd, NULL, FALSE);
3664            }
3665            else
3666              WinAlarm(HWND_DESKTOP, WA_NOTE);
3667            break;
3668          }
3669        }
3670      }
3671      DosReleaseMutexSem(pAD->hmtxScan);
3672    }
3673    break;
3674
3675  case WM_INITMENU:
3676    if (pAD) {
3677      switch (SHORT1FROMMP(mp1)) {
3678      case IDM_FILESMENU:
3679        {
3680          APIRET rc;
3681
3682          rc = DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN);
3683          WinEnableMenuItem((HWND) mp2, IDM_DUPES, (rc == 0));
3684          WinEnableMenuItem((HWND) mp2, IDM_COLLECT, (rc == 0 &&
3685                                                      pAD->selected != 0));
3686          WinEnableMenuItem((HWND) mp2, IDM_SAVETOCLIP, (rc == 0 &&
3687                                                         pAD->selected != 0));
3688          WinEnableMenuItem((HWND) mp2, IDM_APPENDTOCLIP, (rc == 0 &&
3689                                                           pAD->selected !=
3690                                                           0));
3691          WinEnableMenuItem((HWND) mp2, IDM_SAVETOLIST,
3692                            (rc == 0 && pAD->selected != 0));
3693          WinEnableMenuItem((HWND) mp2, IDM_REMOVE,
3694                            (rc == 0 && pAD->selected != 0));
3695          WinEnableMenuItem((HWND) mp2, IDM_HIDEALL,
3696                            (rc == 0 && pAD->selected != 0));
3697          WinEnableMenuItem((HWND) mp2, IDM_DELETESUBMENU,
3698                            (rc == 0 && pAD->selected != 0));
3699          WinEnableMenuItem((HWND) mp2, IDM_INFO,
3700                            (rc == 0 && pAD->selected != 0));
3701          WinEnableMenuItem((HWND) mp2, IDM_ATTRS,
3702                            (rc == 0 && pAD->selected != 0));
3703          WinEnableMenuItem((HWND) mp2, IDM_EAS,
3704                            (rc == 0 && pAD->selected != 0));
3705          WinEnableMenuItem((HWND) mp2, IDM_UUDECODE,
3706                            (rc == 0 && pAD->selected != 0));
3707          WinEnableMenuItem((HWND) mp2, IDM_EXTRACT,
3708                            (rc == 0 && pAD->selected != 0));
3709          WinEnableMenuItem((HWND) mp2, IDM_ARCHIVE,
3710                            (rc == 0 && pAD->selected != 0));
3711          WinEnableMenuItem((HWND) mp2, IDM_MOVEMENU,
3712                            (rc == 0 && pAD->selected != 0));
3713          WinEnableMenuItem((HWND) mp2, IDM_COPYMENU,
3714                            (rc == 0 && pAD->selected != 0));
3715          WinEnableMenuItem((HWND) mp2, IDM_RENAME,
3716                            (rc == 0 && pAD->selected != 0));
3717          WinEnableMenuItem((HWND) mp2, IDM_PRINT,
3718                            (rc == 0 && pAD->selected != 0));
3719          WinEnableMenuItem((HWND) mp2, IDM_SUBJECT,
3720                            (rc == 0 && pAD->selected != 0));
3721          WinEnableMenuItem((HWND) mp2, IDM_OPENSUBMENU,
3722                            (rc == 0 && pAD->selected != 0));
3723          WinEnableMenuItem((HWND) mp2, IDM_OBJECTSUBMENU,
3724                            (rc == 0 && pAD->selected != 0));
3725          if (!rc)
3726            DosReleaseMutexSem(pAD->hmtxScan);
3727        }
3728        break;
3729
3730      case IDM_SELECTSUBMENU:
3731        {
3732          APIRET rc;
3733
3734          rc = DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN);
3735          WinEnableMenuItem((HWND) mp2, IDM_SELECTALL, (rc == 0 &&
3736                                                        pAD->afifiles != 0 &&
3737                                                        (pAD->afifiles !=
3738                                                         pAD->selected ||
3739                                                         !pAD->selected)));
3740          WinEnableMenuItem((HWND) mp2, IDM_SELECTMASK, (rc == 0 &&
3741                                                         pAD->afifiles != 0 &&
3742                                                         (pAD->afifiles !=
3743                                                          pAD->selected ||
3744                                                          !pAD->selected)));
3745          WinEnableMenuItem((HWND) mp2, IDM_DESELECTALL, (rc == 0 &&
3746                                                          pAD->afifiles != 0
3747                                                          && pAD->selected));
3748          WinEnableMenuItem((HWND) mp2, IDM_DESELECTMASK,
3749                            (rc == 0 && pAD->afifiles != 0) && pAD->selected);
3750          WinEnableMenuItem((HWND) mp2, IDM_INVERT,
3751                            (rc == 0 && pAD->afifiles != 0));
3752          if (!rc)
3753            DosReleaseMutexSem(pAD->hmtxScan);
3754        }
3755        break;
3756
3757      case IDM_SORTSUBMENU:
3758        {
3759          APIRET rc;
3760
3761          rc = DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN);
3762          WinEnableMenuItem((HWND) mp2, IDM_SORTNAME, (rc == 0));
3763          WinEnableMenuItem((HWND) mp2, IDM_SORTEASIZE, (rc == 0));
3764          WinEnableMenuItem((HWND) mp2, IDM_SORTSIZE, (rc == 0));
3765          WinEnableMenuItem((HWND) mp2, IDM_SORTLWDATE, (rc == 0));
3766          WinEnableMenuItem((HWND) mp2, IDM_SORTFILENAME, (rc == 0));
3767          WinEnableMenuItem((HWND) mp2, IDM_SORTFIRST, (rc == 0));
3768          if (!rc)
3769            DosReleaseMutexSem(pAD->hmtxScan);
3770        }
3771        WinCheckMenuItem((HWND) mp2, IDM_SORTNAME,
3772                         (pAD->pfnCompare == comparefullnames));
3773        WinCheckMenuItem((HWND) mp2, IDM_SORTEASIZE,
3774                         (pAD->pfnCompare == (PFNSORT) NULL));
3775        WinCheckMenuItem((HWND) mp2, IDM_SORTSIZE,
3776                         (pAD->pfnCompare == comparesizes));
3777        WinCheckMenuItem((HWND) mp2, IDM_SORTLWDATE,
3778                         (pAD->pfnCompare == comparedates));
3779        WinCheckMenuItem((HWND) mp2, IDM_SORTFILENAME,
3780                         (pAD->pfnCompare == comparenames));
3781        WinCheckMenuItem((HWND) mp2, IDM_SORTREVERSE, pAD->invertsort);
3782        WinCheckMenuItem((HWND) mp2, IDM_SORTFIRST,
3783                         (pAD->pfnCompare == compareexts));
3784        break;
3785
3786      case IDM_VIEWSMENU:
3787        {
3788          APIRET rc;
3789
3790          rc = DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN);
3791          WinEnableMenuItem((HWND) mp2, IDM_RESCAN, (rc == 0));
3792          WinEnableMenuItem((HWND) mp2, IDM_FILTER, (rc == 0 &&
3793                                                     pAD->affiles != 0));
3794          if (!rc)
3795            DosReleaseMutexSem(pAD->hmtxScan);
3796        }
3797        WinCheckMenuItem((HWND) mp2, IDM_SHOWLNAMES, pAD->fullnames);
3798        break;
3799      }
3800    }
3801    break;
3802
3803  case WM_COMMAND:
3804    if (!pAD)
3805      return 0;
3806    switch (SHORT1FROMMP(mp1)) {
3807    case IDM_SETTARGET:
3808      SetTargetDir(hwnd, FALSE);
3809      break;
3810
3811    case IDM_DUPES:
3812      if (!pAD->stopflag &&
3813          !DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN)) {
3814        pAD->dupeflags = (USHORT) WinDlgBox(HWND_DESKTOP,
3815                                            hwnd,
3816                                            DupeDlgProc,
3817                                            FM3ModHandle,
3818                                            DUPE_FRAME,
3819                                            MPFROM2SHORT(pAD->dupeflags, 0));
3820        if (pAD->dupeflags) {
3821          if (_beginthread(FindDupes, NULL, 65536, (PVOID) hwnd) == -1)
3822            Runtime_Error(pszSrcFile, __LINE__,
3823                          GetPString(IDS_COULDNTSTARTTHREADTEXT));
3824        }
3825        DosReleaseMutexSem(pAD->hmtxScan);
3826      }
3827      break;
3828
3829    case IDM_COLORPALETTE:
3830      {
3831        COLORS co;
3832        LONG temp[COLORS_MAX];
3833
3834        memset(&co, 0, sizeof(co));
3835        co.size = sizeof(co);
3836        co.numcolors = COLORS_MAX;
3837        co.colors = pAD->aulColors;
3838        co.descriptions = IDS_SACOLORS1TEXT;
3839        co.origs = temp;
3840        co.prompt = IDS_SACOLORSPROMPTTEXT;
3841        memcpy(temp, pAD->aulColors, sizeof(LONG) * COLORS_MAX);
3842        if (WinDlgBox(HWND_DESKTOP,
3843                      hwnd,
3844                      ColorDlgProc,
3845                      FM3ModHandle, COLOR_FRAME, (PVOID) & co)) {
3846          memcpy(Colors, pAD->aulColors, sizeof(LONG) * COLORS_MAX);
3847          PrfWriteProfileData(fmprof,
3848                              appname,
3849                              "Seeall.Colors",
3850                              &pAD->aulColors, sizeof(LONG) * COLORS_MAX);
3851          WinInvalidateRect(hwnd, NULL, FALSE);
3852        }
3853      }
3854      break;
3855
3856    case IDM_CODEPAGE:
3857      {
3858        INT cp;
3859
3860        cp = PickCodepage(hwnd);
3861        if (cp != -1) {
3862          pAD->fattrs.usCodePage = (USHORT) cp;
3863          Codepage = pAD->fattrs.usCodePage;
3864          PrfWriteProfileData(fmprof,
3865                              appname,
3866                              "Seeall.Codepage",
3867                              &pAD->fattrs.usCodePage, sizeof(USHORT));
3868          GpiDeleteSetId(pAD->hps, FIXED_FONT_LCID);
3869          GpiAssociate(pAD->hps, 0);
3870          GpiDestroyPS(pAD->hps);
3871          pAD->hps = InitWindow(hwnd);
3872          pAD->maxx = pAD->horzscroll = 0;
3873          WinInvalidateRect(hwnd, NULL, FALSE);
3874        }
3875      }
3876      break;
3877
3878    case IDM_FONTPALETTE:
3879      SetMLEFont(hwnd, &pAD->fattrs, 11);
3880      PrfWriteProfileData(fmprof,
3881                          appname,
3882                          "Seeall.Fattrs", &pAD->fattrs, sizeof(pAD->fattrs));
3883      Fattrs = pAD->fattrs;
3884      GpiDeleteSetId(pAD->hps, FIXED_FONT_LCID);
3885      GpiAssociate(pAD->hps, 0);
3886      GpiDestroyPS(pAD->hps);
3887      pAD->hps = InitWindow(hwnd);
3888      pAD->maxx = pAD->horzscroll = 0;
3889      WinInvalidateRect(hwnd, NULL, FALSE);
3890      break;
3891
3892    case IDM_SHOWLNAMES:
3893      pAD->fullnames = (pAD->fullnames) ? FALSE : TRUE;
3894      PrfWriteProfileData(fmprof,
3895                          appname,
3896                          "Seeall.Fullnames", &pAD->fullnames, sizeof(BOOL));
3897      Fullnames = pAD->fullnames;
3898      pAD->maxx = pAD->horzscroll = 0;
3899      WinInvalidateRect(hwnd, NULL, FALSE);
3900      break;
3901
3902    case IDM_SORTREVERSE:
3903      pAD->invertsort = (pAD->invertsort) ? FALSE : TRUE;
3904      SortReverse = pAD->invertsort;
3905      PrfWriteProfileData(fmprof,
3906                          appname,
3907                          "Seeall.SortReverse",
3908                          (PVOID) & pAD->invertsort, sizeof(BOOL));
3909      WinInvalidateRect(hwnd, NULL, FALSE);
3910      break;
3911
3912    case IDM_SORTEASIZE:
3913    case IDM_SORTNAME:
3914    case IDM_SORTFILENAME:
3915    case IDM_SORTSIZE:
3916    case IDM_SORTLWDATE:
3917    case IDM_SORTFIRST:
3918      if (!pAD->stopflag &&
3919          !DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN)) {
3920        {
3921          USHORT dummy = SHORT1FROMMP(mp1);
3922
3923          PrfWriteProfileData(fmprof,
3924                              appname,
3925                              "Seeall.Sort", (PVOID) & dummy, sizeof(USHORT));
3926          SortType = SHORT1FROMMP(mp1);
3927        }
3928        WinSetPointer(HWND_DESKTOP, hptrBusy);
3929        WinSendMsg(hwnd, UM_RESCAN, MPFROMLONG(1), MPVOID);
3930        switch (SHORT1FROMMP(mp1)) {
3931        case IDM_SORTEASIZE:
3932          pAD->pfnCompare = (PFNSORT) NULL;
3933          ReSort(hwnd);
3934          break;
3935
3936        case IDM_SORTNAME:
3937          pAD->pfnCompare = comparefullnames;
3938          ReSort(hwnd);
3939          break;
3940
3941        case IDM_SORTFILENAME:
3942          pAD->pfnCompare = comparenames;
3943          ReSort(hwnd);
3944          break;
3945
3946        case IDM_SORTSIZE:
3947          pAD->pfnCompare = comparesizes;
3948          ReSort(hwnd);
3949          break;
3950
3951        case IDM_SORTLWDATE:
3952          pAD->pfnCompare = comparedates;
3953          ReSort(hwnd);
3954          break;
3955
3956        case IDM_SORTFIRST:
3957          pAD->pfnCompare = compareexts;
3958          ReSort(hwnd);
3959          break;
3960        }
3961        WinSetPointer(HWND_DESKTOP, hptrArrow);
3962        DosReleaseMutexSem(pAD->hmtxScan);
3963        WinInvalidateRect(hwnd, NULL, FALSE);
3964      }
3965      break;
3966
3967    case IDM_FILTER:
3968      if (!pAD->stopflag &&
3969          !DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN)) {
3970        FilterList(hwnd);
3971        DosReleaseMutexSem(pAD->hmtxScan);
3972      }
3973      break;
3974
3975    case IDM_RESCAN:
3976      if (!pAD->stopflag &&
3977          !DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN)) {
3978
3979        CHAR tempflags[26];
3980
3981        memcpy(tempflags, pAD->abDrvFlags, sizeof(tempflags));
3982        if (!WinDlgBox(HWND_DESKTOP, hwnd, AFDrvsWndProc, FM3ModHandle,
3983                       DRVS_FRAME, (PVOID) pAD)) {
3984          memcpy(pAD->abDrvFlags, tempflags, sizeof(tempflags));
3985          *pAD->szFindPath = 0;
3986          DosReleaseMutexSem(pAD->hmtxScan);
3987          break;
3988        }
3989        WinSendMsg(pAD->hhscroll, SBM_SETTHUMBSIZE, MPFROM2SHORT(1, 1),
3990                   MPVOID);
3991        WinSendMsg(pAD->hvscroll, SBM_SETTHUMBSIZE, MPFROM2SHORT(1, 1),
3992                   MPVOID);
3993        pAD->topfile = 1;
3994        pAD->cursored = 1;
3995        pAD->selected = 0;
3996        pAD->ullSelectedBytes = 0;
3997        pAD->maxx = pAD->horzscroll = 0;
3998        FreeAllFilesList(hwnd);
3999        pAD->stopflag = 0;
4000        if (_beginthread(FindAllThread, NULL, 524288, (PVOID) hwnd) == -1) {
4001          Runtime_Error(pszSrcFile, __LINE__,
4002                        GetPString(IDS_COULDNTSTARTTHREADTEXT));
4003          WinDestroyWindow(WinQueryWindow(hwnd, QW_PARENT));
4004          DosReleaseMutexSem(pAD->hmtxScan);
4005        }
4006        else {
4007          DosReleaseMutexSem(pAD->hmtxScan);
4008          DosSleep(100);
4009          WinInvalidateRect(hwnd, NULL, FALSE);
4010          PostMsg(hwnd, UM_SETUP2, MPVOID, MPVOID);
4011          PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
4012        }
4013      }
4014      break;
4015
4016    case IDM_DELETE:
4017    case IDM_PERMDELETE:
4018    case IDM_SELECTALL:
4019    case IDM_DESELECTALL:
4020    case IDM_INVERT:
4021    case IDM_SELECTMASK:
4022    case IDM_DESELECTMASK:
4023    case IDM_REMOVE:
4024    case IDM_HIDEALL:
4025    case IDM_COLLECT:
4026    case IDM_COLLECTOR:
4027    case IDM_SAVETOCLIP:
4028    case IDM_APPENDTOCLIP:
4029    case IDM_SAVETOLIST:
4030    case IDM_INFO:
4031    case IDM_ATTRS:
4032    case IDM_MOVE:
4033    case IDM_COPY:
4034    case IDM_RENAME:
4035    case IDM_MOVEPRESERVE:
4036    case IDM_COPYPRESERVE:
4037    case IDM_WILDMOVE:
4038    case IDM_WILDCOPY:
4039    case IDM_SUBJECT:
4040    case IDM_EAS:
4041    case IDM_PRINT:
4042    case IDM_ARCHIVE:
4043    case IDM_EXTRACT:
4044    case IDM_UUDECODE:
4045    case IDM_SHADOW:
4046    case IDM_OBJECT:
4047    case IDM_OPENSETTINGS:
4048    case IDM_OPENDEFAULT:
4049      if (!pAD->stopflag &&
4050          !DosRequestMutexSem(pAD->hmtxScan, SEM_IMMEDIATE_RETURN)) {
4051        switch (SHORT1FROMMP(mp1)) {
4052        case IDM_SELECTALL:
4053        case IDM_DESELECTALL:
4054        case IDM_INVERT:
4055        case IDM_HIDEALL:
4056        case IDM_REMOVE:
4057          Mark(hwnd, (SHORT1FROMMP(mp1) == IDM_DESELECTALL) ?
4058               AFM_UNMARK : (SHORT1FROMMP(mp1) == IDM_INVERT) ?
4059               AFM_INVERT : (SHORT1FROMMP(mp1) == IDM_HIDEALL) ?
4060               AFM_FILTER : (SHORT1FROMMP(mp1) == IDM_REMOVE) ?
4061               AFM_MARKDELETED : 0, NULL);
4062          if (SHORT1FROMMP(mp1) == IDM_REMOVE ||
4063              SHORT1FROMMP(mp1) == IDM_HIDEALL) {
4064            if (SHORT1FROMMP(mp1) == IDM_REMOVE)
4065              RemoveDeleted(hwnd);
4066            else
4067              ReSort(hwnd);
4068          }
4069          WinInvalidateRect(hwnd, NULL, FALSE);
4070          break;
4071
4072        case IDM_SELECTMASK:
4073        case IDM_DESELECTMASK:
4074          SelectMask(hwnd, (SHORT1FROMMP(mp1) == IDM_DESELECTMASK));
4075          WinInvalidateRect(hwnd, NULL, FALSE);
4076          break;
4077
4078        case IDM_DELETE:
4079        case IDM_PERMDELETE:
4080        case IDM_APPENDTOCLIP:
4081        case IDM_SAVETOCLIP:
4082        case IDM_SAVETOLIST:
4083        case IDM_COLLECT:
4084        case IDM_INFO:
4085        case IDM_ATTRS:
4086        case IDM_MOVE:
4087        case IDM_COPY:
4088        case IDM_RENAME:
4089        case IDM_MOVEPRESERVE:
4090        case IDM_COPYPRESERVE:
4091        case IDM_WILDMOVE:
4092        case IDM_WILDCOPY:
4093        case IDM_SUBJECT:
4094        case IDM_PRINT:
4095        case IDM_EAS:
4096        case IDM_ARCHIVE:
4097        case IDM_EXTRACT:
4098        case IDM_SHADOW:
4099        case IDM_OBJECT:
4100        case IDM_OPENSETTINGS:
4101        case IDM_OPENDEFAULT:
4102        case IDM_UUDECODE:
4103          {
4104            CHAR **list = BuildAList(hwnd);
4105
4106            if (!list)
4107              Runtime_Error(pszSrcFile, __LINE__, "no data");
4108            else {
4109              switch (SHORT1FROMMP(mp1)) {
4110              case IDM_COLLECT:
4111                CollectList(hwnd, list);
4112                break;
4113              case IDM_DELETE:
4114              case IDM_PERMDELETE:
4115              case IDM_APPENDTOCLIP:
4116              case IDM_SAVETOCLIP:
4117              case IDM_SAVETOLIST:
4118              case IDM_INFO:
4119              case IDM_ATTRS:
4120              case IDM_MOVE:
4121              case IDM_COPY:
4122              case IDM_RENAME:
4123              case IDM_MOVEPRESERVE:
4124              case IDM_COPYPRESERVE:
4125              case IDM_WILDMOVE:
4126              case IDM_WILDCOPY:
4127              case IDM_SUBJECT:
4128              case IDM_PRINT:
4129              case IDM_EAS:
4130              case IDM_ARCHIVE:
4131              case IDM_EXTRACT:
4132              case IDM_UUDECODE:
4133              case IDM_OBJECT:
4134              case IDM_SHADOW:
4135              case IDM_OPENSETTINGS:
4136              case IDM_OPENDEFAULT:
4137                if (!PostMsg(pAD->hwndObj, UM_MASSACTION, mp1, MPFROMP(list)))
4138                  FreeList(list);
4139                break;
4140              }
4141              if (fUnHilite) {
4142                Mark(hwnd, AFM_UNMARK, NULL);
4143                WinInvalidateRect(hwnd, NULL, FALSE);
4144              }
4145            }
4146          }
4147          break;
4148
4149        case IDM_COLLECTOR:
4150          if (mp2) {
4151
4152            CHAR **list = mp2;
4153
4154            if (Collector) {
4155              if (!PostMsg(Collector, WM_COMMAND,
4156                           MPFROM2SHORT(IDM_COLLECTOR, 0), MPFROMP(list)))
4157                FreeList(list);
4158              else if (fUnHilite) {
4159                Mark(hwnd, AFM_UNMARK, NULL);
4160                WinInvalidateRect(hwnd, NULL, FALSE);
4161              }
4162            }
4163            else
4164              FreeList(list);
4165          }
4166          break;
4167        }
4168        DosReleaseMutexSem(pAD->hmtxScan);
4169      }
4170      else if (SHORT1FROMMP(mp1) == IDM_COLLECTOR) {
4171        DosSleep(100);
4172        if (!PostMsg(hwnd, msg, mp1, mp2))
4173          WinSendMsg(hwnd, msg, mp1, mp2);
4174      }
4175      break;
4176
4177    case IDM_HELP:
4178      if (hwndHelp)
4179        WinSendMsg(hwndHelp,
4180                   HM_DISPLAY_HELP,
4181                   MPFROM2SHORT(HELP_SEEALL, 0), MPFROMSHORT(HM_RESOURCEID));
4182      break;
4183    }
4184    return 0;
4185
4186  case WM_SIZE:
4187// fprintf(stderr,"Seeall: WM_SIZE\n");
4188    PostMsg(hwnd, UM_SETUP3, MPVOID, MPVOID);
4189    break;
4190
4191  case WM_CLOSE:
4192// fprintf(stderr,"Seeall: WM_CLOSE\n");
4193    if (pAD)
4194      pAD->stopflag = 1;
4195    WinDestroyWindow(WinQueryWindow(hwnd, QW_PARENT));
4196    return 0;
4197
4198  case WM_DESTROY:
4199// fprintf(stderr,"Seeall: WM_DESTROY\n");
4200    if (pAD) {
4201      pAD->stopflag = 1;
4202      if (pAD->hmtxScan) {
4203        DosRequestMutexSem(pAD->hmtxScan, 15000);
4204        DosCloseMutexSem(pAD->hmtxScan);
4205      }
4206      if (pAD->hwndPopup)
4207        WinDestroyWindow(pAD->hwndPopup);
4208      if (pAD->hwndObj) {
4209        if (!PostMsg(pAD->hwndObj, WM_CLOSE, MPVOID, MPVOID))
4210          WinSendMsg(pAD->hwndObj, WM_CLOSE, MPVOID, MPVOID);
4211      }
4212      if (pAD->hps) {
4213        GpiDeleteSetId(pAD->hps, FIXED_FONT_LCID);
4214        GpiAssociate(pAD->hps, 0);
4215        GpiDestroyPS(pAD->hps);
4216      }
4217      if (pAD->killme) {
4218        if (!PostMsg((HWND) 0, WM_QUIT, MPVOID, MPVOID))
4219          WinSendMsg((HWND) 0, WM_QUIT, MPVOID, MPVOID);
4220      }
4221      FreeAllFilesList(hwnd);
4222      free(pAD);
4223    }
4224    break;
4225  }
4226
4227  return WinDefWindowProc(hwnd, msg, mp1, mp2);
4228}
4229
4230HWND StartSeeAll(HWND hwndParent, BOOL standalone,      // called by applet
4231                 CHAR * pszStartPath)   // pathname or NULL
4232{
4233  HWND hwndFrame = (HWND) 0, hwndClient;
4234  ULONG FrameFlags = FCF_TITLEBAR | FCF_SYSMENU |
4235    FCF_SIZEBORDER | FCF_MINMAX |
4236    FCF_NOBYTEALIGN | FCF_VERTSCROLL |
4237    FCF_MENU | FCF_ICON | FCF_ACCELTABLE | FCF_HORZSCROLL;
4238
4239  if (ParentIsDesktop(hwndParent, hwndParent))
4240    FrameFlags |= (FCF_TASKLIST | FCF_SHELLPOSITION);
4241  hwndFrame = WinCreateStdWindow(hwndParent,
4242                                 WS_VISIBLE,
4243                                 &FrameFlags,
4244                                 WC_SEEALL,
4245                                 GetPString(IDS_SEEALLTITLETEXT),
4246                                 WS_VISIBLE | fwsAnimate,
4247                                 FM3ModHandle, SEEALL_FRAME, &hwndClient);
4248  if (hwndFrame) {
4249    static CHAR *pszDir;
4250
4251    if (standalone) {
4252      if (!PostMsg(WinWindowFromID(hwndFrame, FID_CLIENT),
4253                   UM_SETUP4, MPVOID, MPVOID)) {
4254        PostMsg((HWND) 0, WM_QUIT, MPVOID, MPVOID);
4255        return (HWND) 0;
4256      }
4257    }
4258    if (pszStartPath) {
4259      // Needs to be static for other thread
4260      if (!pszDir)
4261        pszDir = xmalloc(CCHMAXPATH, pszSrcFile, __LINE__);
4262      if (pszDir) {
4263        strcpy(pszDir, pszStartPath);
4264        pszStartPath = pszDir;
4265      }
4266    }
4267    PostMsg(WinWindowFromID(hwndFrame, FID_CLIENT),
4268            UM_SETUP5, MPFROMP(pszStartPath), MPVOID);
4269  }
4270  else if (standalone)
4271    PostMsg((HWND) 0, WM_QUIT, MPVOID, MPVOID);
4272  return hwndFrame;
4273}
Note: See TracBrowser for help on using the repository browser.