source: trunk/dll/arccnrs.c@ 1220

Last change on this file since 1220 was 1220, checked in by John Small, 17 years ago

Ticket 187: Moved typedef's and some #define's from fm3dll.h

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 102.1 KB
RevLine 
[27]1
2/***********************************************************************
3
4 $Id: arccnrs.c 1220 2008-09-13 23:09:45Z jbs $
5
[123]6 Archive containers
7
[28]8 Copyright (c) 1993-98 M. Kimes
[907]9 Copyright (c) 2001, 2008 Steven H. Levine
[27]10
[130]11 11 Jun 02 SHL Ensure archive name not garbage
12 22 May 03 SHL ArcObjWndProc: fix UM_RESCAN now that we understand it
13 01 Aug 04 SHL Rework lstrip/rstrip usage
14 23 May 05 SHL Use QWL_USER
[156]15 25 May 05 SHL Rename comnam to szCommonName and fix typo
16 25 May 05 SHL Use ULONGLONG and CommaFmtULL
[212]17 05 Jun 05 SHL Drop obsolete, localize
18 05 Jun 05 SHL Correct last sort logic
19 05 Jun 05 SHL Use QWL_USER
[229]20 22 Jun 05 SHL ArcSort: correct typo in last sort fix
[249]21 13 Aug 05 SHL FillArcCnr: optimize
[300]22 08 Dec 05 SHL FillArcCnr: allow list start and end markers to be empty (i.e. tar)
23 08 Dec 05 SHL ArcCnrWndProc: suppress IDM_EXTRACT if no simple extract (i.e. tar)
24 30 Dec 05 SHL ArcCnrWndProc: correct date/time column display setup
25 29 May 06 SHL Comments
[358]26 14 Jul 06 SHL Use Runtime_Error
[367]27 26 Jul 06 SHL Correct SelectAll usage
[406]28 29 Jul 06 SHL Use xfgets_bstripcr
[423]29 31 Jul 06 SHL Lower priority for archives with more than 1000 entries
[426]30 02 Aug 06 SHL Add logic to stop processing large archives
[460]31 23 Aug 06 SHL Integrate John Small's switch list title logic
[531]32 03 Nov 06 SHL Renames
[562]33 14 Mar 07 SHL ArcObjWndProc/UM_ENTER: delay before starting viewer
[593]34 30 Mar 07 GKY Remove GetPString for window class names
[618]35 06 Apr 07 GKY Work around PM DragInfo and DrgFreeISH limit
[606]36 06 Apr 07 GKY Add some error checking in drag/drop
[618]37 20 Apr 07 SHL Sync with NumItemsToUnhilite mods
[627]38 21 Apr 07 GKY Find FM2Utils by path or utils directory
[672]39 12 May 07 SHL Use dcd->ulItemsToUnHilite; sync with UnHilite arg mods
[688]40 10 Jun 07 GKY Add CheckPmDrgLimit including IsFm2Window as part of work around PM drag limit
[696]41 16 Jun 07 SHL Use DosQueryAppType not DosQAppType
[751]42 02 Aug 07 SHL Sync with ARCITEM mods
[773]43 06 Aug 07 SHL Use BldFullPathName and BldQuotedFileName
44 06 Aug 07 SHL Move BldQuotedFileName and BldQuotedFullPathNamehere
45 to be near primary caller
[775]46 06 Aug 07 GKY Reduce DosSleep times (ticket 148)
[793]47 20 Aug 07 GKY Move #pragma alloc_text to end for OpenWatcom compat
[814]48 26 Aug 07 GKY DosSleep(1) in loops changed to (0)
[872]49 22 Nov 07 GKY Use CopyPresParams to fix presparam inconsistencies in menus
[897]50 30 Dec 07 GKY Use TestCDates for sort by date
[917]51 10 Jan 08 SHL Sync with CfgDlgProc mods
[946]52 10 Feb 08 GKY Implement bubble help for bitmap menu items
[953]53 15 Feb 08 SHL Sync with settings menu rework
[985]54 29 Feb 08 GKY Use xfree where appropriate
[1068]55 14 Jul 08 JBS Ticket 126: Add support for WPS open default & open settings in arccnrs
[1069]56 16 Jul 08 GKY Fix trap on viewing multiple files from an archive (misplaced free)
[1082]57 16 Jul 08 GKY Use TMP directory for temp files if present. Use MakeTempName
[1104]58 19 Jul 08 GKY Replace save_dir2(dir) with pFM2SaveDirectory
[1120]59 25 Aug 08 GKY Check TMP directory space warn if lee than 5 MiB prevent archiver from opening if
60 less than 10 KiB (It hangs and can't be closed)
[618]61
[27]62***********************************************************************/
63
[907]64#include <stdlib.h> // free..
[2]65#include <string.h>
66#include <ctype.h>
[907]67#include <direct.h> // rmdir
68#include <share.h> // SH_DENYWR
69#include <limits.h> // ULONG_MAX
[689]70#include <process.h> // _beginthread
[762]71
72#if 0
[751]73#include <malloc.h> // _heapchk
[762]74#endif
[156]75
[907]76#define INCL_DOS
77#define INCL_DOSERRORS
78#define INCL_WIN
79#define INCL_LONGLONG
80
[1183]81#include "fm3dll.h"
[1220]82#include "fm3dll2.h" // #define's for UM_*, control id's, etc.
83#include "arccnrs.h"
84#include "makelist.h" // Typedef
85#include "colors.h" // Typedef
[1203]86#include "mainwnd2.h" // Data declaration(s)
87#include "grep.h" // Data declaration(s)
88#include "dircnrs.h" // Data declaration(s)
89#include "info.h" // Data declaration(s)
90#include "init.h" // Data declaration(s)
[2]91#include "fm3dlg.h"
92#include "fm3str.h"
93#include "mle.h"
[907]94#include "pathutil.h" // BldFullPathName
95#include "filldir.h" // EmptyCnr...
96#include "errutil.h" // Dos_Error...
97#include "strutil.h" // GetPString
[953]98#include "notebook.h" // CfgDlgProc
[1160]99#include "worker.h" // Action, MassAction
100#include "avv.h" // ArcReviewDlgProc, rewrite_archiverbb2
101#include "chklist.h" // CenterOverWindow, CheckListProc
102#include "common.h" // CommonCreateTextChildren, CommonFrameWndProc, CommonTextPaint
[1183]103 // CommonTextButton
104#include "draglist.h" // DoFileDrag, DragOne
[1160]105#include "valid.h" // GetDesktopName, TestCDates
[1183]106#include "mainwnd.h" // GetNextWindowPos, MakeBubble, TopWindowName
[1160]107#include "objwin.h" // MakeObjWin
108#include "shadow.h" // MakeShadows
109#include "objcnr.h" // ObjCnrDlgProc
110#include "printer.h" // PrintListThread
111#include "srchpath.h" // RunFM2Util
[1183]112#include "misc.h" // Broadcast, CheckMenu, CurrentRecord, SayFilter, SaySort
113 // DrawTargetEmphasis, IsFm2Window
[1160]114#include "select.h" // SelectAll, SelectList
115#include "findrec.h" // ShowCnrRecord
116#include "walkem.h" // WalkExtractDlgProc
[1183]117#include "droplist.h" // AcceptOneDrop, CheckPmDrgLimit, DropHelp, GetOneDrop
118#include "archive.h" // ArchiveDlgProc
119#include "common.h" // CommonTextProc
120#include "presparm.h" // CopyPresParams
121#include "defview.h" // DefaultViewKeys
122#include "systemf.h" // ExecOnList
123#include "filter.h" // PickMaskDlgProc
124#include "avl.h" // SBoxDlgProc
125#include "mkdir.h" // SetDir
126#include "collect.h" // StartCollector
127#include "viewer.h" // StartMLEEditor
128#include "newview.h" // StartViewer
129#include "commafmt.h" // commafmt
130#include "copyf.h" // unlinkf
131#include "literal.h" // wildcard
132#include "wrappers.h" // xrealloc
[1160]133#include "misc.h" // AdjustCnrColVis, QuickPopup, SetSortChecks, SwitchCommand
134#include "select.h" // DeselectAll, InvertAll
[1183]135#include "strips.h" // bstrip
136#include "dirs.h" // save_dir2
[1011]137#include "fortify.h"
[2]138
[1220]139#define ARCFLAGS_REALDIR 0x00000001
140#define ARCFLAGS_PSEUDODIR 0x00000002
141#define CON_COLS 6
142#define EXTRA_ARCRECORD_BYTES (sizeof(ARCITEM) - sizeof(MINIRECORDCORE))
143
144
[2]145#pragma data_seg(DATA1)
[1203]146static INT DefArcSortFlags;
[358]147
[1203]148// Data definitions
[358]149static PSZ pszSrcFile = __FILE__;
[1203]150#pragma data_seg(GLOBAL1)
151HWND ArcCnrMenu;
152HWND ArcMenu;
153CHAR ArcTempRoot[CCHMAXPATH];
154BOOL fArcStuffVisible;
[358]155
[1203]156#pragma data_seg(GLOBAL2)
157CHAR lastextractpath[CCHMAXPATH];
158ULONGLONG ullDATFileSpaceNeeded;
159
[551]160static MRESULT EXPENTRY ArcErrProc(HWND hwnd, ULONG msg, MPARAM mp1,
161 MPARAM mp2)
[172]162{
[2]163 ARCDUMP *ad;
[773]164 CHAR szQuotedArcName[CCHMAXPATH];
[2]165
[551]166 switch (msg) {
167 case WM_INITDLG:
168 if (!mp2)
169 WinDismissDlg(hwnd, 0);
170 else {
171 ad = (ARCDUMP *) mp2;
172 WinSetWindowPtr(hwnd, QWL_USER, ad);
173 if (ad->errmsg)
174 WinSetDlgItemText(hwnd, ARCERR_TEXT, ad->errmsg);
175 if (!ad->info->test)
176 WinEnableWindow(WinWindowFromID(hwnd, ARCERR_TEST), FALSE);
177 if (ad->listname) {
178 MLEsetlimit(WinWindowFromID(hwnd, ARCERR_MLE), -1L);
179 MLEsetformat(WinWindowFromID(hwnd, ARCERR_MLE), MLFIE_NOTRANS);
180 MLEsetcurpos(WinWindowFromID(hwnd, ARCERR_MLE),
181 MLEgetlen(WinWindowFromID(hwnd, ARCERR_MLE)));
182 MLEinsert(WinWindowFromID(hwnd, ARCERR_MLE),
183 GetPString(IDS_ARCHIVERREPORTTEXT));
184 MLEinsertfile(WinWindowFromID(hwnd, ARCERR_MLE), ad->listname);
[2]185 }
[551]186 }
187 break;
188
189 case WM_COMMAND:
190 switch (SHORT1FROMMP(mp1)) {
191 case DID_CANCEL:
192 WinDismissDlg(hwnd, 0);
[2]193 break;
194
[551]195 case IDM_HELP:
196 if (hwndHelp) {
197 WinSendMsg(hwndHelp, HM_DISPLAY_HELP,
198 MPFROM2SHORT(HELP_ARCERR, 0), MPFROMSHORT(HM_RESOURCEID));
199 }
200 break;
[2]201
[551]202 case DID_OK:
203 ad = WinQueryWindowPtr(hwnd, QWL_USER);
204 WinDlgBox(HWND_DESKTOP, hwnd, ArcReviewDlgProc, FM3ModHandle,
205 AD_FRAME, MPFROMP(ad));
206 WinDismissDlg(hwnd, 0);
207 break;
[2]208
[551]209 case ARCERR_VIEW:
210 ad = WinQueryWindowPtr(hwnd, QWL_USER);
211 {
212 CHAR *list[2];
[2]213
[551]214 list[0] = ad->arcname;
215 list[1] = NULL;
216 if (TestBinary(ad->arcname)) {
217 if (*binview)
218 ExecOnList((HWND) 0, binview, WINDOWED | SEPARATE, NULL, list,
[888]219 NULL, pszSrcFile, __LINE__);
[551]220 else
221 StartMLEEditor(HWND_DESKTOP, 16 + 4 + 1, ad->arcname, hwnd);
222 }
223 else {
224 if (*viewer) {
225 ExecOnList((HWND) 0, viewer, WINDOWED | SEPARATE |
[907]226 (fViewChild ? CHILD : 0),
227 NULL, list, NULL, pszSrcFile, __LINE__);
[551]228 }
229 else
230 StartMLEEditor(HWND_DESKTOP, 8 + 4 + 1, ad->arcname, hwnd);
231 }
232 }
233 break;
[2]234
[551]235 case ARCERR_TEST:
236 ad = WinQueryWindowPtr(hwnd, QWL_USER);
237 runemf2(SEPARATEKEEP | WINDOWED | MAXIMIZED,
[888]238 hwnd, pszSrcFile, __LINE__, NULL, NULL,
[773]239 "%s %s",
240 ad->info->test,
241 BldQuotedFileName(szQuotedArcName, ad->arcname));
[551]242 break;
243 }
244 return 0;
[2]245 }
[551]246 return WinDefDlgProc(hwnd, msg, mp1, mp2);
[2]247}
248
[551]249static SHORT APIENTRY ArcSort(PMINIRECORDCORE pmrc1, PMINIRECORDCORE pmrc2,
250 PVOID pStorage)
[172]251{
[551]252 PARCITEM pai1 = (PARCITEM) pmrc1;
253 PARCITEM pai2 = (PARCITEM) pmrc2;
254 DIRCNRDATA *pdcd = (DIRCNRDATA *) pStorage;
255 SHORT ret = 0;
256 CHAR *pext, *ppext;
257 INT sortFlags;
[2]258
[423]259 if (!pdcd) {
[212]260 HWND hwndCnr = pai1->hwndCnr;
[551]261
262 pdcd = WinQueryWindowPtr(hwndCnr, QWL_USER);
[358]263 if (!pdcd) {
[377]264 Runtime_Error2(pszSrcFile, __LINE__, IDS_NODATATEXT);
[212]265 return ret;
266 }
267 }
268
269 sortFlags = pdcd->sortFlags; // Optimize
270
[423]271 if (sortFlags) {
[551]272 switch (sortFlags & (~SORT_REVERSE)) {
273 case SORT_FIRSTEXTENSION:
[730]274 pext = strchr(pai1->pszFileName, '.');
275 ppext = strchr(pai2->pszFileName, '.');
[551]276 if (!pext)
277 pext = NullStr;
278 if (!ppext)
279 ppext = NullStr;
280 ret = stricmp(pext, ppext);
281 break;
[2]282
[551]283 case SORT_LASTEXTENSION:
[730]284 pext = strrchr(pai1->pszFileName, '.');
285 ppext = strrchr(pai2->pszFileName, '.');
[551]286 if (!pext)
287 pext = NullStr;
288 if (!ppext)
289 ppext = NullStr;
290 ret = stricmp(pext, ppext);
291 break;
[2]292
[551]293 case SORT_LWDATE:
[897]294 ret = TestCDates(&pai1->date, &pai1->time,
[907]295 &pai2->date, &pai2->time);
296 /*(pai1->date.year < pai2->date.year) ? 1 :
[551]297 (pai1->date.year > pai2->date.year) ? -1 :
298 (pai1->date.month < pai2->date.month) ? 1 :
299 (pai1->date.month > pai2->date.month) ? -1 :
300 (pai1->date.day < pai2->date.day) ? 1 :
301 (pai1->date.day > pai2->date.day) ? -1 :
302 (pai1->time.hours < pai2->time.hours) ? 1 :
303 (pai1->time.hours > pai2->time.hours) ? -1 :
304 (pai1->time.minutes < pai2->time.minutes) ? 1 :
305 (pai1->time.minutes > pai2->time.minutes) ? -1 :
306 (pai1->time.seconds < pai2->time.seconds) ? 1 :
[897]307 (pai1->time.seconds > pai2->time.seconds) ? -1 : 0;*/
[551]308 break;
[2]309
[551]310 case SORT_SIZE:
311 ret =
312 (pai1->cbFile < pai2->cbFile) ? 1 : (pai1->cbFile ==
313 pai2->cbFile) ? 0 : -1;
314 if (!ret)
315 ret =
316 (pai1->cbComp < pai2->cbComp) ? 1 : (pai1->cbComp ==
317 pai2->cbComp) ? 0 : -1;
318 break;
[2]319
[551]320 case SORT_EASIZE:
321 ret =
322 (pai1->cbComp < pai2->cbComp) ? 1 : (pai1->cbComp ==
323 pai2->cbComp) ? 0 : -1;
324 if (!ret)
325 ret =
326 (pai1->cbFile < pai2->cbFile) ? 1 : (pai1->cbFile ==
327 pai2->cbFile) ? 0 : -1;
328 break;
[2]329 }
[423]330 if (!ret)
[730]331 ret = (SHORT) stricmp(pai1->pszFileName, pai2->pszFileName);
[423]332 if (ret && (sortFlags & SORT_REVERSE))
[562]333 ret = ret > 0 ? -1 : 1;
[2]334 return ret;
335 }
[730]336 return (SHORT) stricmp(pai1->pszFileName, pai2->pszFileName);
[2]337}
338
[551]339static INT APIENTRY ArcFilter(PMINIRECORDCORE rmini, PVOID arg)
[172]340{
[551]341 DIRCNRDATA *dcd = (DIRCNRDATA *) arg;
342 PARCITEM r;
343 register INT x;
344 INT ret = FALSE;
[2]345
[423]346 if (dcd && *dcd->mask.szMask) {
[551]347 r = (PARCITEM) rmini;
[423]348 if (dcd->mask.pszMasks[1]) {
[551]349 for (x = 0; dcd->mask.pszMasks[x]; x++) {
350 if (*dcd->mask.pszMasks[x]) {
351 if (*dcd->mask.pszMasks[x] != '/') {
[730]352 if (wildcard(r->pszFileName, dcd->mask.pszMasks[x], FALSE))
[551]353 ret = TRUE;
354 }
355 else {
[730]356 if (wildcard(r->pszFileName, dcd->mask.pszMasks[x] + 1, FALSE)) {
[551]357 ret = FALSE;
358 break;
359 }
360 }
361 }
[2]362 }
363 }
364 else {
[730]365 if (wildcard(r->pszFileName, dcd->mask.szMask, FALSE))
[551]366 ret = TRUE;
[2]367 }
368 }
369 else
370 ret = TRUE;
371 return ret;
372}
373
[551]374static MRESULT EXPENTRY ArcFrameWndProc(HWND hwnd, ULONG msg, MPARAM mp1,
375 MPARAM mp2)
[172]376{
[551]377 return CommonFrameWndProc(ARC_CNR, hwnd, msg, mp1, mp2);
[2]378}
379
[551]380static BOOL IsArcThere(HWND hwnd, CHAR * arcname)
[172]381{
[423]382 if (arcname) {
383 if (IsFile(arcname) != 1) {
[551]384 saymsg(MB_CANCEL, hwnd,
385 GetPString(IDS_SAYWHATTEXT),
386 GetPString(IDS_ARCNOTTHERETEXT), arcname);
[2]387 return FALSE;
388 }
389 return TRUE;
390 }
391 return FALSE;
392}
393
[751]394/**
395 * Free storage associated with archive container item
396 * Caller is responsible for correcting pointers
397 */
398
399static VOID FreeArcItemData(PARCITEM pai)
400{
401 // DbgMsg(pszSrcFile, __LINE__, "FreeArcItemData %p", pai);
[762]402 PSZ psz;
[751]403
[762]404 if (pai->pszFileName && pai->pszFileName != NullStr) {
405 psz = pai->pszFileName;
[1077]406 pai->pszFileName = NULL; // 08 Jul 08 SHL was NulStr
[762]407 free(psz);
408 }
[751]409}
410
411/**
[762]412 * Remove item(s) from archive container and free associated storage if requested
413 * @param paiFirst points to first item to remove or NULL to remove all
414 * @param usCnt is remove count or 0 to remove all
[751]415 */
416
[762]417static VOID RemoveArcItems(HWND hwnd, PARCITEM paiFirst, USHORT usCnt, USHORT usFlags)
[751]418{
[762]419 INT remaining = usCnt;
420 PARCITEM pai;
421
422 if ((usCnt && !paiFirst) || (!usCnt && paiFirst))
423 Runtime_Error(pszSrcFile, __LINE__, "paiFirst %p usCnt %u mismatch", paiFirst, usCnt);
424 else {
425 // Free our buffers if free requested
426 if (usFlags & CMA_FREE) {
427 if (paiFirst)
428 pai = paiFirst;
429 else {
[751]430 pai = (PARCITEM)WinSendMsg(hwnd, CM_QUERYRECORD, MPVOID,
431 MPFROM2SHORT(CMA_FIRST, CMA_ITEMORDER));
[762]432 if ((INT)pai == -1) {
[751]433 Win_Error(hwnd, HWND_DESKTOP, pszSrcFile, __LINE__,"CM_QUERYRECORD");
[762]434 remaining = -1;
435 pai = NULL;
[751]436 }
437 }
[762]438 while (pai) {
439 FreeArcItemData(pai);
440 pai = (PARCITEM)pai->rc.preccNextRecord;
441 if (remaining && --remaining == 0)
442 break;
443 }
[751]444 }
445 }
446
[762]447 // DbgMsg(pszSrcFile, __LINE__, "RemoveArcItems %p %u %s", pai, usCnt, pai->pszFileName);
[751]448
[762]449 if (remaining != - 1) {
450 remaining = (INT)WinSendMsg(hwnd, CM_REMOVERECORD, MPFROMP(&paiFirst), MPFROM2SHORT(usCnt, usFlags));
451 if (remaining == -1) {
[751]452 // Win_Error2(hwnd, HWND_DESKTOP, pszSrcFile, __LINE__,IDS_CMREMOVEERRTEXT);
[762]453 Win_Error(hwnd, HWND_DESKTOP, pszSrcFile, __LINE__,"CM_REMOVERECORD hwnd %x pai %p cnt %u", hwnd, paiFirst, usCnt);
[751]454 }
455 }
456}
457
458/**
[762]459 * Empty all records from an archive container and
460 * free associated storage and free up field infos
[751]461 */
462
463static VOID EmptyArcCnr(HWND hwnd)
464{
[773]465#if 0 // fixme to be gone or to be configurable
[751]466 {
467 int state = _heapchk();
468 if (state != _HEAPOK)
469 Runtime_Error(pszSrcFile, __LINE__, "heap corrupted %d", state);
[762]470 else
471 DbgMsg(pszSrcFile, __LINE__, "_memavl %u", _memavl());
[751]472 }
473#endif
474
475 // Remove all ARCITEM records
476 RemoveArcItems(hwnd, NULL, 0, CMA_FREE);
477
478 // Use common code to remove rest
479 EmptyCnr(hwnd);
480}
481
[423]482//== FillArcCnr() generate archive content list and fill container window ==
483
[551]484static INT FillArcCnr(HWND hwndCnr, CHAR * arcname, ARC_TYPE ** arcinfo,
485 ULONGLONG * pullTotalBytes, volatile PCHAR pStopFlag)
[44]486{
[551]487 FILE *fp;
488 HFILE oldstdout;
489 HFILE newstdout;
490 CHAR s[CCHMAXPATH * 2], lonename[CCHMAXPATH + 2],
[1082]491 *nsize, *osize, *fdate, *fname, *p, *pp, *arctemp;
[551]492 BOOL gotstart;
493 BOOL gotend;
494 BOOL wasquote;
[773]495 BOOL nomove = FALSE; // fixme to be gone?
[551]496 INT highest = 0, x, counter = 0, numarcfiles = 0;
497 PARCITEM lastpai;
498 ARC_TYPE *info;
499 ARC_TYPE *tinfo;
500 ULONG apptype;
501 APIRET rc;
[2]502
[423]503 if (!arcname || !arcinfo)
[2]504 return 0;
[300]505
[2]506 info = *arcinfo;
[423]507 if (!info)
[551]508 info = find_type(arcname, NULL);
[1082]509 arctemp = xmallocz(CCHMAXPATH, pszSrcFile, __LINE__);
[1120]510 if (CheckDriveSpaceAvail(ArcTempRoot, ullDATFileSpaceNeeded, ullTmpSpaceNeeded) == 1)
511 saymsg(MB_OK,
512 HWND_DESKTOP,
513 NullStr,
514 GetPString(IDS_ARCTMPDRIVESPACELIMITED),
515 ArcTempRoot);
[1082]516 MakeTempName(arctemp, ArcTempRoot, 2);
[300]517
[1120]518
[2]519ReTry:
520
521#ifdef DEBUG
[27]522 if (info && info->id)
[551]523 WinSetWindowText(WinQueryWindow
524 (WinQueryWindow(hwndCnr, QW_PARENT), QW_PARENT),
525 info->id);
[2]526#endif
527
528 tinfo = NULL;
529 numarcfiles = counter = highest = 0;
530 gotstart = gotend = FALSE;
531 lastpai = NULL;
[156]532 *pullTotalBytes = 0;
[358]533 if (!info || !info->list)
[377]534 Runtime_Error2(pszSrcFile, __LINE__, IDS_NODATATEXT);
[358]535 else {
[751]536 RemoveArcItems(hwndCnr, NULL, 0, CMA_FREE | CMA_INVALIDATE | CMA_ERASE);
[2]537 *arcinfo = info;
538 highest = info->osizepos;
[423]539 if (info->nsizepos > highest)
[2]540 highest = info->nsizepos;
[423]541 if (info->fdpos > highest)
[2]542 highest = info->fdpos;
[423]543 if (info->fnpos > highest)
[2]544 highest = info->fnpos;
[423]545 if (highest > 50) {
[551]546 saymsg(MB_ENTER | MB_ICONEXCLAMATION, HWND_DESKTOP,
547 GetPString(IDS_SHAMETEXT), "%s", GetPString(IDS_BUNGEDUPTEXT));
[423]548 }
549 if (info->fnpos == -1)
[2]550 highest = 32767;
[300]551
[2]552 DosError(FERR_DISABLEHARDERR);
553 DosForceDelete(arctemp);
554 DosError(FERR_DISABLEHARDERR);
[300]555
[551]556 strcpy(s, info->list);
557 p = strchr(s, ' ');
[423]558 if (p)
[2]559 *p = 0;
560 DosError(FERR_DISABLEHARDERR);
[696]561 if (!DosQueryAppType(s, &apptype) &&
[563]562 (apptype & FAPPTYP_DOS ||
563 apptype & FAPPTYP_WINDOWSREAL ||
564 apptype & FAPPTYP_WINDOWSPROT ||
565 apptype & FAPPTYP_WINDOWSPROT31)) {
[2]566 p = GetCmdSpec(TRUE);
567 runemf2(SEPARATE | INVISIBLE | MINIMIZED | BACKGROUND | WAIT,
[888]568 hwndCnr, pszSrcFile, __LINE__, NULL, "DOS_BACKGROUND_EXECUTION=1",
[773]569 "%s /C %s %s >%s",
570 p, // shell
571 info->list, // list command
572 BldQuotedFileName(s, arcname),
[562]573 arctemp);
[2]574 }
575 else {
[551]576 fp = xfopen(arctemp, "w", pszSrcFile, __LINE__);
[1082]577 if (!fp) {
578 xfree(arctemp, pszSrcFile, __LINE__);
579 return 0;
580 }
[358]581 else {
[551]582 newstdout = -1;
583 DosError(FERR_DISABLEHARDERR);
584 rc = DosDupHandle(fileno(stdout), &newstdout);
585 if (rc) {
586 Dos_Error(MB_CANCEL, rc, hwndCnr, pszSrcFile, __LINE__,
[1082]587 "DosDupHandle");
588 xfree(arctemp, pszSrcFile, __LINE__);
[551]589 return 0;
[358]590 }
591 else {
[551]592 oldstdout = fileno(stdout);
593 DosError(FERR_DISABLEHARDERR);
594 rc = DosDupHandle(fileno(fp), &oldstdout);
595 if (rc) {
596 Dos_Error(MB_CANCEL, rc, hwndCnr, pszSrcFile, __LINE__,
597 "DosDupHandle");
[1082]598 xfree(arctemp, pszSrcFile, __LINE__);
599 return 0;
[358]600 }
601 else {
[551]602 runemf2(SEPARATE | INVISIBLE | FULLSCREEN | BACKGROUND | WAIT,
[888]603 hwndCnr, pszSrcFile, __LINE__, NULL, NULL,
[773]604 "%s %s",
605 info->list,
606 BldQuotedFileName(s, arcname));
[551]607 oldstdout = fileno(stdout);
608 DosError(FERR_DISABLEHARDERR);
609 DosDupHandle(newstdout, &oldstdout);
610 DosClose(newstdout);
611 fclose(fp);
612 }
613 }
[2]614 }
615 }
[300]616
[2]617 DosError(FERR_DISABLEHARDERR);
[551]618 fp = _fsopen(arctemp, "r", SH_DENYWR);
[300]619
[358]620 if (fp) {
[300]621 gotstart = !info->startlist || !*info->startlist; // If list has no start marker
622
[551]623 while (!feof(fp) && !gotend && !*pStopFlag) {
624 if (!xfgets_bstripcr(s, sizeof(s), fp, pszSrcFile, __LINE__))
625 break;
626 if (!gotstart) {
627 if (!strcmp(s, info->startlist))
628 gotstart = TRUE;
629 }
630 else if (info->endlist && !strcmp(s, info->endlist))
631 gotend = TRUE;
632 else {
[300]633 /* add to container */
[551]634 fname = NULL;
635 bstrip(s);
636 if (info->nameisfirst) {
637 strncpy(lonename, s, CCHMAXPATH + 2);
638 lonename[CCHMAXPATH + 1] = 0;
639 fname = lonename;
640 if (!xfgets_bstripcr(s, sizeof(s), fp, pszSrcFile, __LINE__))
641 break;
642 if (*fname == '\"') {
643 memmove(fname, fname + 1, strlen(fname) + 1);
644 p = strchr(fname, '\"');
645 if (p)
646 *p = 0;
647 }
648 }
649 nsize = NULL;
650 osize = fdate = NullStr;
651 p = s;
652 for (x = 0; x <= highest; x++) {
653 pp = p;
654 while (*pp && (*pp == ' ' || *pp == '\t')) /* skip leading */
655 pp++;
656 if (!*pp)
657 break;
658 wasquote = FALSE;
659 p = pp;
660 while (*p && (wasquote ||
661 ((x != info->fnpos || !info->nameislast) ?
662 (*p != ' ' && *p != '\t') : TRUE))) {
663 if (*p == '\"') {
664 if (!wasquote) {
665 wasquote = TRUE;
666 memmove(p, p + 1, strlen(p));
667 while (*p == ' ' || *p == '\t')
668 p++;
669 }
670 else {
671 memmove(p, p + 1, strlen(p));
672 break;
673 }
674 }
675 else if (*p)
676 p++;
677 }
678 if (*p) {
679 *p = 0;
680 p++;
681 }
682 if (x == info->nsizepos)
683 nsize = pp;
684 else if (x == info->osizepos)
685 osize = pp;
686 else if (x == info->fdpos) {
687 fdate = pp;
688 if (info->fdflds > 1 && info->fdflds < 24) {
689 INT y;
[2]690
[551]691 if (*p) {
692 p--;
693 *p = ' ';
694 for (y = 0; y < info->fdflds - 1; y++) {
695 while (*p && (*p == ' ' || *p == '\t'))
696 p++;
697 while (*p && (*p != ' ' && *p != '\t'))
698 p++;
699 x++;
700 }
701 if (*p) {
702 *p = 0;
703 p++;
704 }
705 }
706 }
707 }
708 else if (x == info->fnpos) {
709 fname = pp;
710 if (pp && *pp == '*' && !*(pp + 1)) /* workaround for LH.EXE */
711 fname = NULL;
712 if (info->nameislast)
713 break;
714 }
715 else if ((!p || !*p) && info->fnpos == -1) {
716 fname = pp;
717 break;
718 }
719 }
720 if (info->nameisnext) {
721 if (!xfgets_bstripcr
722 (lonename, sizeof(lonename), fp, pszSrcFile, __LINE__))
723 break;
724 fname = lonename;
725 }
[423]726 // fixme to complain?
[551]727 if (fname && *fname) {
[2]728
[551]729 RECORDINSERT ri;
730 PARCITEM pai;
[2]731
732#ifdef DEBUG
[551]733 saymsg(MB_ENTER, hwndCnr, DEBUG_STRING,
734 "fname: %s\r\rpp: %s\r\rp: %s\r\rlonename: %s\r\rhighest: %ld\r\rx: %ld\r\rfdate: %s",
[562]735 fname ? fname : "NULL",
736 pp ? pp : "NULL",
737 p ? p : "NULL",
[551]738 lonename, highest, x, (fdate) ? fdate : "NULL");
[2]739#endif
740
[551]741 pai = WinSendMsg(hwndCnr,
742 CM_ALLOCRECORD,
743 MPFROMLONG(EXTRA_ARCRECORD_BYTES),
744 MPFROMLONG(1L));
745 if (!pai) {
[358]746 Runtime_Error(pszSrcFile, __LINE__, "CM_ALLOCRECORD");
747 break;
748 }
749 else {
[551]750 memset(pai, 0, sizeof(ARCITEM));
751 pai->hwndCnr = hwndCnr;
752 if (*fname == '*') {
753 fname++;
754 pai->flags = ARCFLAGS_REALDIR;
[358]755 }
[551]756 if (fname[strlen(fname) - 1] == '\\' ||
757 fname[strlen(fname) - 1] == '/')
758 pai->flags = ARCFLAGS_REALDIR;
[730]759 pai->pszFileName = xstrdup(fname,pszSrcFile, __LINE__);
[762]760 pai->pszDisplayName = pai->pszFileName;
761 pai->rc.pszIcon = pai->pszDisplayName;
[551]762 if (fdate)
763 strcpy(pai->szDate, fdate);
[730]764 // pai->pszFileName = pai->pszFileName;
[551]765 pai->rc.pszIcon = pai->pszFileName;
[562]766 pai->rc.hptrIcon = (pai->flags & ARCFLAGS_REALDIR) != 0 ?
[551]767 hptrDir : hptrFile;
768 pai->pszDate = pai->szDate;
769 if (osize)
770 pai->cbFile = atol(osize);
771 if (nsize)
772 pai->cbComp = atol(nsize);
773 if (info->datetype && fdate && *fdate)
774 ArcDateTime(fdate, info->datetype, &pai->date, &pai->time);
775 memset(&ri, 0, sizeof(RECORDINSERT));
776 ri.cb = sizeof(RECORDINSERT);
777 ri.pRecordOrder = (PRECORDCORE) CMA_END;
778 ri.pRecordParent = (PRECORDCORE) NULL;
779 ri.zOrder = (USHORT) CMA_TOP;
780 ri.cRecordsInsert = 1L;
781 ri.fInvalidateRecord = FALSE;
782 if (WinSendMsg(hwndCnr,
783 CM_INSERTRECORD, MPFROMP(pai), MPFROMP(&ri))) {
784 *pullTotalBytes += pai->cbFile;
785 }
786 numarcfiles++;
787 if (!(++counter % 50)) {
788 if (!lastpai)
789 lastpai = pai;
790 WinSendMsg(hwndCnr,
791 CM_INVALIDATERECORD,
792 lastpai,
793 MPFROM2SHORT(10, CMA_ERASE | CMA_REPOSITION));
794 lastpai = pai;
795 }
[426]796 // Avoid hogging system for large archive
797 if (numarcfiles == 100)
[551]798 priority_idle();
799 }
800 }
801 }
802 } // while !eof
[300]803
[2]804 fclose(fp);
[300]805
[426]806 if (*pStopFlag)
[551]807 numarcfiles = 0; // Request close
808 else if (!numarcfiles || !gotstart
809 || (!gotend && info->endlist && *info->endlist)) {
[423]810 // Oops
[551]811 ARCDUMP ad;
812 CHAR errstr[CCHMAXPATH + 256];
[2]813
[423]814 // Try for alternate archiver
[551]815 tinfo = info;
816 do {
817 tinfo = tinfo->next;
818 if (tinfo)
819 tinfo = find_type(arcname, tinfo);
820 if (tinfo) {
821 DosError(FERR_DISABLEHARDERR);
822 DosForceDelete(arctemp);
823 info = tinfo;
824 goto ReTry;
825 }
826 } while (tinfo);
827 DosBeep(750, 50); // wake up user
828 sprintf(errstr, GetPString(IDS_ARCERRORINFOTEXT),
829 arcname,
[562]830 !gotstart ? GetPString(IDS_NOGOTSTARTTEXT) : NullStr,
831 !numarcfiles ? GetPString(IDS_NOARCFILESFOUNDTEXT) :
[551]832 NullStr,
[562]833 !gotend ? GetPString(IDS_NOENDOFLISTTEXT) : NullStr);
[551]834 memset(&ad, 0, sizeof(ARCDUMP));
835 ad.info = info;
836 strcpy(ad.listname, arctemp);
837 strcpy(ad.arcname, arcname);
838 ad.errmsg = errstr;
839 WinDlgBox(HWND_DESKTOP,
840 hwndCnr,
841 ArcErrProc, FM3ModHandle, ARCERR_FRAME, MPFROMP(&ad));
[2]842 }
[249]843 else if (!nomove && tinfo) {
844 /* if we got a false hit, move working hit to top */
[551]845 tinfo = info->next;
846 info->next = arcsighead;
847 arcsighead->prev = info;
848 if (tinfo)
849 tinfo->next->prev = info->prev;
850 info->prev->next = tinfo;
851 info->prev = NULL;
852 arcsighead = info;
853 rewrite_archiverbb2(NULL); // Rewrite with warning
[2]854 }
[551]855 } // if opened
[426]856
[2]857 DosError(FERR_DISABLEHARDERR);
858 DosForceDelete(arctemp);
[1082]859 xfree(arctemp, pszSrcFile, __LINE__);
[2]860 }
861
[426]862 if (numarcfiles)
[423]863 priority_normal();
864
[2]865 return numarcfiles;
866}
867
[551]868MRESULT EXPENTRY ArcTextProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
[172]869{
[551]870 static BOOL emphasized = FALSE;
871 static HWND hwndButtonPopup = (HWND) 0;
872 static ULONG timestamp = ULONG_MAX;
873 static USHORT lastid = 0;
[2]874
[551]875 switch (msg) {
876 case WM_CREATE:
877 return CommonTextProc(hwnd, msg, mp1, mp2);
[2]878
[551]879 case WM_COMMAND:
880 return WinSendMsg(WinWindowFromID(WinQueryWindow(hwnd, QW_PARENT),
881 ARC_CNR), msg, mp1, mp2);
[2]882
[551]883 case UM_CONTEXTMENU:
884 case WM_CONTEXTMENU:
885 {
886 USHORT id;
[2]887
[551]888 id = WinQueryWindowUShort(hwnd, QWS_ID);
889 switch (id) {
890 case DIR_SELECTED:
891 case DIR_VIEW:
892 case DIR_SORT:
893 {
894 POINTL ptl = { 0, 0 };
895 SWP swp;
896 DIRCNRDATA *dcd;
[2]897
[551]898 if (hwndButtonPopup)
899 WinDestroyWindow(hwndButtonPopup);
900 if (id == DIR_SELECTED)
901 id = DIR_RESTORE;
902 if (id == lastid) {
[2]903
[551]904 ULONG check;
[2]905
[551]906 DosQuerySysInfo(QSV_MS_COUNT, QSV_MS_COUNT, &check,
907 sizeof(check));
908 if (check < timestamp + 500) {
909 lastid = 0;
910 goto MenuAbort;
911 }
912 }
913 hwndButtonPopup = WinLoadMenu(HWND_DESKTOP, FM3ModHandle, id);
914 if (hwndButtonPopup) {
915 WinSetWindowUShort(hwndButtonPopup, QWS_ID, id);
916 dcd = WinQueryWindowPtr(WinWindowFromID(WinQueryWindow(hwnd,
917 QW_PARENT),
918 ARC_CNR), QWL_USER);
919 if (id == DIR_SORT) {
920 if (dcd)
921 SetSortChecks(hwndButtonPopup, dcd->sortFlags);
922 WinSendMsg(hwndButtonPopup,
923 MM_DELETEITEM,
924 MPFROM2SHORT(IDM_SORTNONE, FALSE), MPVOID);
925 WinSendMsg(hwndButtonPopup,
926 MM_DELETEITEM,
927 MPFROM2SHORT(IDM_SORTNAME, FALSE), MPVOID);
928 WinSendMsg(hwndButtonPopup,
929 MM_DELETEITEM,
930 MPFROM2SHORT(IDM_SORTLADATE, FALSE), MPVOID);
931 WinSendMsg(hwndButtonPopup,
932 MM_DELETEITEM,
933 MPFROM2SHORT(IDM_SORTCRDATE, FALSE), MPVOID);
934 WinSendMsg(hwndButtonPopup,
935 MM_DELETEITEM,
936 MPFROM2SHORT(IDM_SORTDIRSFIRST, FALSE), MPVOID);
937 WinSendMsg(hwndButtonPopup,
938 MM_DELETEITEM,
939 MPFROM2SHORT(IDM_SORTDIRSLAST, FALSE), MPVOID);
940 WinSendMsg(hwndButtonPopup,
941 MM_DELETEITEM,
942 MPFROM2SHORT(IDM_SORTSUBJECT, FALSE), MPVOID);
943 WinSendMsg(hwndButtonPopup,
944 MM_SETITEMTEXT,
945 MPFROM2SHORT(IDM_SORTEASIZE, 0),
946 MPFROMP(GetPString(IDS_COMPRESSEDSIZEMENUTEXT)));
947 WinSendMsg(hwndButtonPopup,
948 MM_SETITEMTEXT,
949 MPFROM2SHORT(IDM_SORTLWDATE, 0),
950 MPFROMP(GetPString(IDS_DATEMENUTEXT)));
951 }
952 ptl.x = 0;
953 if (WinPopupMenu(HWND_OBJECT,
954 HWND_OBJECT,
955 hwndButtonPopup, -32767, -32767, 0, 0)) {
956 WinQueryWindowPos(hwndButtonPopup, &swp);
957 ptl.y = -(swp.cy + 2);
958 }
959 else {
960 WinQueryWindowPos(hwnd, &swp);
961 ptl.y = swp.cy + 2;
962 }
963 if (WinPopupMenu(hwnd,
964 hwnd,
965 hwndButtonPopup,
966 ptl.x,
967 ptl.y,
968 0,
969 PU_HCONSTRAIN | PU_VCONSTRAIN |
970 PU_KEYBOARD | PU_MOUSEBUTTON1)) {
971 CenterOverWindow(hwndButtonPopup);
972 PaintRecessedWindow(hwnd, (HPS) 0, FALSE, FALSE);
973 }
974 }
975 }
976 break;
977 default:
978 PostMsg(WinWindowFromID(WinQueryWindow(hwnd, QW_PARENT),
979 ARC_CNR),
980 WM_CONTROL, MPFROM2SHORT(ARC_CNR, CN_CONTEXTMENU), MPVOID);
981 break;
[2]982 }
[551]983 }
984 MenuAbort:
985 if (msg == UM_CONTEXTMENU)
986 return 0;
987 break;
[2]988
[551]989 case WM_MENUEND:
990 if (hwndButtonPopup == (HWND) mp2) {
991 lastid = WinQueryWindowUShort((HWND) mp2, QWS_ID);
992 WinDestroyWindow(hwndButtonPopup);
993 hwndButtonPopup = (HWND) 0;
994 DosQuerySysInfo(QSV_MS_COUNT, QSV_MS_COUNT, &timestamp,
995 sizeof(timestamp));
996 switch (lastid) {
997 case DIR_VIEW:
998 case DIR_SORT:
999 case DIR_RESTORE:
1000 case DIR_SELECTED:
1001 PaintRecessedWindow(hwnd, (HPS) 0, TRUE, FALSE);
1002 break;
[2]1003 }
[551]1004 }
1005 break;
[2]1006
[551]1007 case WM_MOUSEMOVE:
1008 {
1009 USHORT id = WinQueryWindowUShort(hwnd, QWS_ID);
1010 char *s = NULL;
[2]1011
[551]1012 if (fOtherHelp) {
1013 if ((!hwndBubble ||
1014 WinQueryWindowULong(hwndBubble, QWL_USER) != hwnd) &&
1015 !WinQueryCapture(HWND_DESKTOP)) {
1016 switch (id) {
1017 case DIR_TOTALS:
1018 s = GetPString(IDS_ARCCNRTOTALSHELPTEXT);
1019 break;
1020 case DIR_SELECTED:
1021 s = GetPString(IDS_ARCCNRSELECTEDHELPTEXT);
1022 break;
1023 case DIR_VIEW:
1024 s = GetPString(IDS_ARCCNRVIEWHELPTEXT);
1025 break;
1026 case DIR_SORT:
1027 s = GetPString(IDS_DIRCNRSORTHELP);
1028 break;
1029 case DIR_FILTER:
1030 s = GetPString(IDS_DIRCNRFILTERHELP);
1031 break;
1032 case DIR_FOLDERICON:
1033 s = GetPString(IDS_ARCCNRFOLDERHELPTEXT);
1034 break;
1035 default:
1036 break;
1037 }
1038 if (s)
1039 MakeBubble(hwnd, TRUE, s);
1040 else if (hwndBubble)
1041 WinDestroyWindow(hwndBubble);
1042 }
[2]1043 }
[551]1044 switch (id) {
1045 case DIR_FILTER:
1046 case DIR_SORT:
1047 case DIR_VIEW:
1048 case DIR_SELECTED:
1049 case DIR_FOLDERICON:
1050 return CommonTextButton(hwnd, msg, mp1, mp2);
1051 }
1052 }
1053 break;
[2]1054
[551]1055 case WM_BUTTON3UP:
1056 case WM_BUTTON1UP:
1057 case WM_BUTTON1DOWN:
1058 case WM_BUTTON3DOWN:
1059 {
1060 USHORT id;
[2]1061
[551]1062 id = WinQueryWindowUShort(hwnd, QWS_ID);
1063 switch (id) {
1064 case DIR_FILTER:
1065 case DIR_SORT:
1066 case DIR_VIEW:
1067 case DIR_SELECTED:
1068 case DIR_FOLDERICON:
1069 return CommonTextButton(hwnd, msg, mp1, mp2);
[2]1070 }
[551]1071 }
1072 break;
[2]1073
[551]1074 case UM_CLICKED:
1075 case UM_CLICKED3:
1076 {
1077 USHORT id, cmd = 0;
[2]1078
[551]1079 id = WinQueryWindowUShort(hwnd, QWS_ID);
1080 switch (id) {
1081 case DIR_FOLDERICON:
1082 switch (msg) {
1083 case WM_BUTTON3CLICK:
1084 case WM_CHORD:
1085 cmd = IDM_RESCAN;
1086 break;
1087 default:
1088 if ((SHORT2FROMMP(mp2) & KC_ALT) != 0)
1089 cmd = IDM_WINDOWDLG;
1090 else
1091 cmd = IDM_WALKDIR;
1092 break;
1093 }
1094 break;
1095 case DIR_VIEW:
1096 case DIR_SORT:
1097 case DIR_SELECTED:
1098 PostMsg(hwnd, UM_CONTEXTMENU, MPVOID, MPVOID);
1099 break;
1100 case DIR_FILTER:
1101 cmd = IDM_FILTER;
1102 break;
1103 default:
1104 break;
[2]1105 }
[551]1106 if (cmd)
1107 PostMsg(WinWindowFromID(WinQueryWindow(hwnd, QW_PARENT),
1108 ARC_CNR),
1109 WM_COMMAND, MPFROM2SHORT(cmd, 0), MPVOID);
1110 }
1111 return 0;
[2]1112
[551]1113 case WM_BEGINDRAG:
1114 case DM_DROP:
1115 case DM_DRAGOVER:
1116 case DM_DRAGLEAVE:
1117 case DM_DROPHELP:
1118 if (msg == DM_DRAGOVER) {
1119 if (!emphasized) {
1120 emphasized = TRUE;
1121 DrawTargetEmphasis(hwnd, emphasized);
[2]1122 }
[551]1123 }
1124 else if (msg != WM_BEGINDRAG) {
1125 if (emphasized) {
1126 emphasized = FALSE;
1127 DrawTargetEmphasis(hwnd, emphasized);
[2]1128 }
[551]1129 }
1130 switch (WinQueryWindowUShort(hwnd, QWS_ID)) {
1131 case DIR_FOLDERICON:
1132 switch (msg) {
1133 case DM_DRAGOVER:
[618]1134 if (AcceptOneDrop(hwnd, mp1, mp2))
[551]1135 return MRFROM2SHORT(DOR_DROP, DO_MOVE);
[562]1136 return MRFROM2SHORT(DOR_NODROP, 0); /* Drop not valid */
[551]1137 case DM_DROPHELP:
1138 DropHelp(mp1, mp2, hwnd, GetPString(IDS_ARCCNRFOLDERDROPHELPTEXT));
1139 return 0;
1140 case DM_DROP:
1141 {
1142 char szFrom[CCHMAXPATH + 2];
[2]1143
[551]1144 if (emphasized) {
1145 emphasized = FALSE;
1146 DrawTargetEmphasis(hwnd, emphasized);
1147 }
[618]1148 if (GetOneDrop(hwnd, mp1, mp2, szFrom, sizeof(szFrom)))
[551]1149 WinSendMsg(WinWindowFromID(WinQueryWindow(hwnd, QW_PARENT),
1150 ARC_CNR),
1151 WM_COMMAND,
1152 MPFROM2SHORT(IDM_SWITCH, 0), MPFROMP(szFrom));
1153 }
1154 return 0;
1155 default:
1156 return PFNWPStatic(hwnd, msg, mp1, mp2);
1157 }
1158 default:
1159 {
1160 CNRDRAGINFO cnd;
1161 USHORT dcmd;
[2]1162
[551]1163 switch (msg) {
1164 case DM_DROP:
1165 dcmd = CN_DROP;
1166 break;
1167 case DM_DRAGOVER:
1168 dcmd = CN_DRAGOVER;
1169 break;
1170 case DM_DRAGLEAVE:
1171 dcmd = CN_DRAGLEAVE;
1172 break;
1173 case DM_DROPHELP:
1174 dcmd = CN_DROPHELP;
1175 break;
1176 case WM_BEGINDRAG:
1177 dcmd = CN_INITDRAG;
1178 break;
1179 }
1180 cnd.pDragInfo = (PDRAGINFO) mp1;
1181 cnd.pRecord = NULL;
1182 return WinSendMsg(WinQueryWindow(hwnd, QW_PARENT),
1183 WM_CONTROL,
1184 MPFROM2SHORT(ARC_CNR, dcmd), MPFROMP(&cnd));
[2]1185 }
[551]1186 }
[2]1187 }
[551]1188 return PFNWPStatic(hwnd, msg, mp1, mp2);
[2]1189}
1190
[551]1191MRESULT EXPENTRY ArcClientWndProc(HWND hwnd, ULONG msg, MPARAM mp1,
1192 MPARAM mp2)
1193{
[2]1194
[551]1195 switch (msg) {
1196 case UM_CONTAINERHWND:
1197 return MRFROMLONG(WinWindowFromID(hwnd, ARC_CNR));
[2]1198
[551]1199 case UM_VIEWSMENU:
1200 // fixme to disble menu items as needed
[872]1201 return MRFROMLONG(CheckMenu(hwnd, &ArcCnrMenu, ARCCNR_POPUP));
[2]1202
[551]1203 case UM_FILESMENU:
1204 // fixme to disble menu items as needed
[872]1205 return MRFROMLONG(CheckMenu(hwnd, &ArcMenu, ARC_POPUP));
[2]1206
[551]1207 case MM_PORTHOLEINIT:
1208 case WM_INITMENU:
1209 case UM_INITMENU:
1210 case UM_COMMAND:
1211 case UM_LOADFILE:
1212 case UM_UPDATERECORD:
1213 case UM_UPDATERECORDLIST:
1214 case WM_COMMAND:
1215 case WM_CONTROL:
1216 case WM_CLOSE:
1217 return WinSendMsg(WinWindowFromID(hwnd, ARC_CNR), msg, mp1, mp2);
[2]1218
[551]1219 case WM_PSETFOCUS:
1220 case WM_SETFOCUS:
1221 if (mp2)
1222 PostMsg(hwnd, UM_FOCUSME, MPVOID, MPVOID);
1223 break;
[2]1224
[551]1225 case UM_FOCUSME:
1226 WinSetFocus(HWND_DESKTOP, WinWindowFromID(hwnd, ARC_CNR));
1227 break;
[2]1228
[551]1229 case WM_PAINT:
1230 {
1231 HPS hps;
1232 RECTL rcl;
[2]1233
[551]1234 hps = WinBeginPaint(hwnd, (HPS) 0, NULL);
1235 if (hps) {
1236 WinQueryWindowRect(hwnd, &rcl);
1237 WinFillRect(hps, &rcl, CLR_PALEGRAY);
1238 CommonTextPaint(hwnd, hps);
1239 WinEndPaint(hps);
[2]1240 }
[551]1241 }
1242 break;
[2]1243
[551]1244 case UM_SIZE:
1245 case WM_SIZE:
1246 if (msg == UM_SIZE) {
[2]1247
[551]1248 SWP swp;
[2]1249
[551]1250 WinQueryWindowPos(hwnd, &swp);
1251 mp1 = MPFROM2SHORT(swp.cx, swp.cy);
1252 mp2 = MPFROM2SHORT(swp.cx, swp.cy);
1253 }
1254 {
1255 USHORT cx, cy, bx;
[2]1256
[551]1257 cx = SHORT1FROMMP(mp2);
1258 cy = SHORT2FROMMP(mp2);
1259 WinSetWindowPos(WinWindowFromID(hwnd, ARC_CNR), HWND_TOP,
1260 0,
1261 22, cx, cy - (24 + 22), SWP_SHOW | SWP_MOVE | SWP_SIZE);
1262 WinSetWindowPos(WinWindowFromID(hwnd, ARC_EXTRACTDIR), HWND_TOP,
1263 0, 0, cx, 22, SWP_SHOW | SWP_MOVE | SWP_SIZE);
1264 WinSetWindowPos(WinWindowFromID(hwnd, DIR_FOLDERICON), HWND_TOP,
1265 2, cy - 22, 24, 20, SWP_SHOW | SWP_MOVE | SWP_SIZE);
1266 WinSetWindowPos(WinWindowFromID(hwnd, DIR_TOTALS), HWND_TOP,
1267 29,
1268 cy - 22,
1269 (cx / 3) - 2, 20, SWP_SHOW | SWP_MOVE | SWP_SIZE);
1270 WinSetWindowPos(WinWindowFromID(hwnd, DIR_SELECTED), HWND_TOP,
1271 29 + (cx / 3) + 2,
1272 cy - 22,
1273 (cx / 3) - 2, 20, SWP_SHOW | SWP_MOVE | SWP_SIZE);
1274 bx = (cx - (29 + (((cx / 3) + 2) * 2))) / 3;
1275 WinSetWindowPos(WinWindowFromID(hwnd, DIR_VIEW), HWND_TOP,
1276 29 + (((cx / 3) + 2) * 2),
1277 cy - 22, bx - 4, 20, SWP_SHOW | SWP_MOVE | SWP_SIZE);
1278 WinSetWindowPos(WinWindowFromID(hwnd, DIR_SORT), HWND_TOP,
1279 29 + (((cx / 3) + 2) * 2) + bx,
1280 cy - 22, bx - 4, 20, SWP_SHOW | SWP_MOVE | SWP_SIZE);
1281 WinSetWindowPos(WinWindowFromID(hwnd, DIR_FILTER), HWND_TOP,
1282 29 + (((cx / 3) + 2) * 2) + (bx * 2),
1283 cy - 22, bx - 4, 20, SWP_SHOW | SWP_MOVE | SWP_SIZE);
1284 }
1285 CommonTextPaint(hwnd, (HPS) 0);
1286 if (msg == UM_SIZE) {
1287 WinSetWindowPos(WinQueryWindow(hwnd, QW_PARENT), HWND_TOP, 0, 0, 0, 0,
1288 SWP_SHOW | SWP_ZORDER | SWP_ACTIVATE);
1289 return 0;
1290 }
1291 break;
[2]1292 }
[551]1293 return WinDefWindowProc(hwnd, msg, mp1, mp2);
[2]1294}
1295
[551]1296MRESULT EXPENTRY ArcObjWndProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
[172]1297{
[2]1298 DIRCNRDATA *dcd;
[358]1299 PSZ psz;
[773]1300 CHAR szQuotedArcName[CCHMAXPATH];
1301 CHAR szQuotedMemberName[CCHMAXPATH];
[2]1302
[551]1303 switch (msg) {
[1077]1304 case WM_CREATE:
1305 DbgMsg(pszSrcFile, __LINE__, "WM_CREATE mp1 %p mp2 %p", mp1, mp2); // 18 Jul 08 SHL fixme
1306 break;
1307
[551]1308 case DM_PRINTOBJECT:
1309 case DM_DISCARDOBJECT:
1310 dcd = INSTDATA(hwnd);
1311 if (dcd) {
[2]1312
[551]1313 LISTINFO *li;
1314 CNRDRAGINFO cni;
[2]1315
[551]1316 cni.pRecord = NULL;
1317 cni.pDragInfo = (PDRAGINFO) mp1;
1318 li = DoFileDrop(dcd->hwndCnr,
[762]1319 dcd->directory, FALSE, MPVOID, MPFROMP(&cni));
[687]1320 CheckPmDrgLimit(cni.pDragInfo);
[551]1321 if (li) {
1322 li->type = (msg == DM_DISCARDOBJECT) ? IDM_DELETE : IDM_PRINT;
1323 if (!li->list ||
1324 !li->list[0] || !PostMsg(hwnd, UM_ACTION, MPFROMP(li), MPVOID))
1325 FreeListInfo(li);
1326 else
1327 return MRFROMLONG(DRR_SOURCE);
[2]1328 }
[551]1329 }
1330 return MRFROMLONG(DRR_TARGET);
[2]1331
[551]1332 case DM_RENDERPREPARE:
1333 return (MRESULT) TRUE;
[2]1334
[551]1335 case DM_RENDER:
1336 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
1337 if (dcd && dcd->info && dcd->info->extract && dcd->arcname) {
[2]1338
[551]1339 PDRAGTRANSFER pdt = (PDRAGTRANSFER) mp1;
1340 CHAR filename[CCHMAXPATH];
1341 ULONG len;
[2]1342
[551]1343 if (pdt->hwndClient && pdt->pditem && pdt->hstrSelectedRMF &&
1344 pdt->hstrRenderToName) {
1345 if (pdt->usOperation == DO_COPY || pdt->usOperation == DO_MOVE) {
1346 *filename = 0;
1347 len = DrgQueryStrName(pdt->hstrSelectedRMF, CCHMAXPATH, filename);
1348 filename[len] = 0;
1349 if (!strnicmp(filename, "OS2FILE,", 8)) {
1350 // saymsg(MB_ENTER,HWND_DESKTOP,DEBUG_STRING,"RMF = \"%s\"",filename);
1351 }
1352 else {
1353 *filename = 0;
1354 len =
1355 DrgQueryStrName(pdt->hstrRenderToName, CCHMAXPATH, filename);
1356 filename[len] = 0;
1357 if (len && *filename) {
1358 psz = xstrdup(filename, pszSrcFile, __LINE__);
1359 if (psz) {
1360 PostMsg(hwnd, UM_RENDER, MPFROMP(pdt), MPFROMP(psz));
1361 return (MRESULT) TRUE;
1362 }
1363 }
[358]1364 else {
[551]1365 // saymsg(MB_ENTER,HWND_DESKTOP,DEBUG_STRING,"No render-to name given.");
[358]1366 }
1367 }
[551]1368 }
1369 pdt->fsReply = DMFL_RENDERRETRY;
[2]1370 }
[551]1371 }
1372 return (MRESULT) FALSE;
[2]1373
[551]1374 case UM_RENDER:
1375 {
1376 PDRAGTRANSFER pdt = (PDRAGTRANSFER) mp1;
1377 USHORT usRes = DMFL_RENDERFAIL;
[2]1378
[551]1379 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
1380 if (dcd && dcd->info && dcd->info->extract && dcd->arcname) {
[2]1381
[551]1382 CHAR *filename = (CHAR *) mp2, *p;
1383 ULONG len;
1384 CHAR membername[CCHMAXPATH], construct[CCHMAXPATH * 2];
[2]1385
[551]1386 *membername = 0;
1387 len = DrgQueryStrName(pdt->pditem->hstrSourceName,
1388 CCHMAXPATH, membername);
1389 membername[len] = 0;
1390 if (*membername && len && filename) {
1391 unlinkf("%s", filename);
1392 strcpy(construct, filename);
1393 p = strrchr(filename, '\\');
1394 if (!p)
1395 *construct = 0;
1396 else {
1397 if (p == filename || *(p - 1) == ':')
1398 p++;
1399 *p = 0;
1400 }
1401 // saymsg(MB_ENTER,HWND_DESKTOP,DEBUG_STRING,"%s %s %s\r[%s]",dcd->info->extract,dcd->arcname,membername,construct);
1402 runemf2(SEPARATE | WINDOWED | WAIT |
[888]1403 (fArcStuffVisible ? 0 : BACKGROUND | MINIMIZED),
1404 dcd->hwndClient, pszSrcFile, __LINE__, construct, NULL,
[773]1405 "%s %s %s",
[551]1406 dcd->info->extract,
[773]1407 BldQuotedFileName(szQuotedArcName, dcd->arcname),
1408 BldQuotedFileName(szQuotedMemberName, membername));
1409 BldFullPathName(construct, construct, membername);
[551]1410 if (IsFile(construct) != -1) {
1411 rename(construct, filename);
1412 unlinkf("%s", construct);
1413 if (IsFile(filename) != -1)
1414 usRes = DMFL_RENDEROK;
1415 }
1416 }
[2]1417 }
[1009]1418 xfree((CHAR *)mp2, pszSrcFile, __LINE__);
[551]1419 PostMsg(pdt->hwndClient, DM_RENDERCOMPLETE, MPFROMP(pdt),
1420 MPFROM2SHORT(usRes, 0));
1421 }
1422 return 0;
[2]1423
[551]1424 case UM_SETUP:
[1077]1425# ifdef FORTIFY
1426 Fortify_EnterScope();
1427# endif
[551]1428 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
1429 if (!dcd) {
1430 Runtime_Error2(pszSrcFile, __LINE__, IDS_NODATATEXT);
1431 PostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
1432 }
1433 else {
[1077]1434# ifdef FORTIFY
[1078]1435 Fortify_BecomeOwner(dcd);
[1077]1436# endif
[551]1437 /* set unique id */
1438 WinSetWindowUShort(hwnd, QWS_ID, ARCOBJ_FRAME + (ARC_FRAME - dcd->id));
1439 dcd->hwndObject = hwnd; // pass back hwnd
1440 if (ParentIsDesktop(hwnd, dcd->hwndParent))
[771]1441 DosSleep(100); //05 Aug 07 GKY 250 // Avoid race?
[551]1442 }
1443 return 0;
1444
1445 case UM_RESCAN:
1446 /*
1447 * populate container
1448 */
1449 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
1450 if (dcd) {
1451 if (mp1)
1452 strcpy(dcd->arcname, (CHAR *) mp1); // Update name on request
1453 dcd->ullTotalBytes = dcd->totalfiles =
1454 dcd->selectedfiles = dcd->selectedbytes = 0;
1455 WinSetDlgItemText(dcd->hwndClient, DIR_TOTALS, "0");
1456 WinSetDlgItemText(dcd->hwndClient, DIR_SELECTED, "0 / 0k");
1457 dcd->totalfiles = FillArcCnr(dcd->hwndCnr,
1458 dcd->arcname,
1459 &dcd->info,
1460 &dcd->ullTotalBytes, &dcd->stopflag);
1461 if (!dcd->totalfiles)
1462 PostMsg(dcd->hwndCnr, WM_CLOSE, MPVOID, MPVOID);
[423]1463 else {
[551]1464 dcd->arcfilled = TRUE;
1465 if (!PostMsg(dcd->hwndCnr, UM_RESCAN, MPVOID, MPVOID))
1466 WinSendMsg(dcd->hwndCnr, UM_RESCAN, MPVOID, MPVOID);
1467 PostMsg(dcd->hwndCnr, UM_SETUP2, MPVOID, MPVOID);
1468 WinSendMsg(dcd->hwndCnr,
1469 CM_INVALIDATERECORD,
1470 MPVOID, MPFROM2SHORT(0, CMA_ERASE | CMA_REPOSITION));
[2]1471 }
[551]1472 }
1473 return 0;
[2]1474
[551]1475 case UM_SELECT:
1476 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
1477 if (dcd) {
1478 switch (SHORT1FROMMP(mp1)) {
1479 case IDM_SELECTALL:
1480 case IDM_SELECTALLFILES:
1481 SelectAll(dcd->hwndCnr, TRUE, TRUE, NULL, NULL, TRUE);
1482 break;
1483 case IDM_DESELECTALL:
1484 case IDM_DESELECTALLFILES:
1485 DeselectAll(dcd->hwndCnr, TRUE, TRUE, NULL, NULL, TRUE);
1486 break;
1487 case IDM_DESELECTMASK:
1488 case IDM_SELECTMASK:
1489 {
1490 MASK mask;
1491 PARCITEM pci = (PARCITEM) mp2;
[2]1492
[551]1493 memset(&mask, 0, sizeof(MASK));
1494 mask.fNoAttribs = TRUE;
1495 mask.fNoDirs = TRUE;
1496 strcpy(mask.prompt,
1497 GetPString((SHORT1FROMMP(mp1) == IDM_SELECTMASK) ?
1498 IDS_SELECTFILTERTEXT : IDS_DESELECTFILTERTEXT));
1499 if (pci && (INT) pci != -1)
[730]1500 strcpy(mask.szMask, pci->pszFileName);
[551]1501 if (WinDlgBox(HWND_DESKTOP, dcd->hwndCnr, PickMaskDlgProc,
1502 FM3ModHandle, MSK_FRAME, MPFROMP(&mask))) {
1503 if (SHORT1FROMMP(mp1) == IDM_SELECTMASK)
1504 SelectAll(dcd->hwndCnr, TRUE, TRUE, mask.szMask, NULL, FALSE);
1505 else
1506 DeselectAll(dcd->hwndCnr, TRUE, TRUE, mask.szMask, NULL, FALSE);
1507 }
1508 }
[2]1509
[551]1510 case IDM_INVERT:
1511 InvertAll(dcd->hwndCnr);
1512 break;
[2]1513 }
[551]1514 }
1515 return 0;
[2]1516
[551]1517 case UM_ENTER:
1518 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
1519 if (dcd) {
[2]1520
[551]1521 CHAR *s = (CHAR *) mp1, *p, *pp, filename[CCHMAXPATH];
[2]1522
[551]1523 if (s) {
1524 if (!dcd->info->extract) {
1525 Runtime_Error(pszSrcFile, __LINE__, "no extract");
[1039]1526 free(s);
[551]1527 return 0;
1528 }
[773]1529 runemf2(SEPARATE | WINDOWED | WAIT |
[888]1530 (fArcStuffVisible ? 0 : BACKGROUND | MINIMIZED),
1531 dcd->hwndClient, pszSrcFile, __LINE__, dcd->workdir, NULL,
[773]1532 "%s %s %s",
[562]1533 dcd->info->exwdirs ? dcd->info->exwdirs :
1534 dcd->info->extract,
[773]1535 BldQuotedFileName(szQuotedArcName, dcd->arcname),
1536 BldQuotedFileName(szQuotedMemberName, s));
[551]1537 if (!dcd->info->exwdirs) {
1538 p = s;
1539 p = strrchr(s, '\\');
1540 pp = strrchr(s, '/');
1541 if (p && pp)
1542 p = max(p, pp);
1543 else if (!p)
1544 p = pp;
1545 if (p)
1546 memmove(s, p + 1, strlen(p + 1));
1547 }
1548 sprintf(filename, "%s\\%s", dcd->workdir, s);
1549 p = filename;
1550 while (*p) {
1551 if (*p == '/')
1552 *p = '\\';
1553 p++;
1554 }
[562]1555 // printf("%s %d UM_ENTER %s %s\n",__FILE__, __LINE__,filename, s); fflush(stdout); // 10 Mar 07 SHL hang
[1039]1556 free(s);
[562]1557 if (IsFile(filename) == 1) {
[1082]1558#if 1 // 06 Oct 07 SHL fixme to be gone - set to 0 for ticket #58 testing
[570]1559 if (fViewChild && fArcStuffVisible)
[835]1560 DosSleep(100); // Allow unzip session to finish closing 14 Mar 07 SHL
[907]1561#endif
[551]1562 WinSendMsg(dcd->hwndCnr, UM_ENTER, MPFROMP(filename), MPVOID);
[562]1563 }
[2]1564 }
[551]1565 }
1566 return 0;
[2]1567
[551]1568 case UM_COMMAND:
1569 if (mp1) {
1570 if (PostMsg(hwnd, UM_ACTION, mp1, mp2))
1571 return (MRESULT) TRUE;
1572 }
1573 return 0;
[2]1574
[551]1575 case UM_ACTION:
1576 DosError(FERR_DISABLEHARDERR);
1577 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
1578 if (dcd) {
[2]1579
[551]1580 LISTINFO *li = (LISTINFO *) mp1;
1581 register INT x;
[2]1582
[551]1583 if (li && li->list && li->list[0]) {
[1077]1584 printf("%x/r", li->type); fflush(stdout);
[551]1585 switch (li->type) {
1586 case IDM_ARCHIVE:
1587 case IDM_ARCHIVEM:
1588 {
1589 DIRCNRDATA ad;
1590 CHAR szBuffer[1025], *p;
[2]1591
[551]1592 if (!li->list[1] && !stricmp(li->list[0], dcd->arcname)) {
1593 Runtime_Error(pszSrcFile, __LINE__, "arc to self");
1594 break;
1595 }
1596 ad = *dcd;
1597 ad.namecanchange = 0;
1598 ad.fmoving = (li->type == IDM_ARCHIVEM);
1599 if (!WinDlgBox(HWND_DESKTOP, dcd->hwndClient, ArchiveDlgProc, FM3ModHandle, ARCH_FRAME, (PVOID) & ad) || !*ad.arcname || !*ad.command) /* we blew it */
1600 break;
1601 /* build the sucker */
1602 strcpy(szBuffer, ad.command);
1603 strcat(szBuffer, " ");
[773]1604
1605 BldQuotedFileName(szBuffer + strlen(szBuffer), ad.arcname);
1606
1607 p = &szBuffer[strlen(szBuffer)]; // Remeber where archiver name ends
1608
[551]1609 if (ad.mask.szMask) {
1610 strcat(szBuffer, " ");
[773]1611
1612 BldQuotedFileName(szBuffer + strlen(szBuffer), ad.mask.szMask);
[551]1613 }
1614 strcat(szBuffer, " ");
1615 x = 0;
[773]1616
1617 // Run commands avoiding command line overflow
[551]1618 while (li->list[x]) {
[773]1619
1620 if (IsFile(li->list[x]))
[907]1621 BldQuotedFileName(szBuffer + strlen(szBuffer), li->list[x]);
[773]1622 else
[907]1623 BldQuotedFullPathName(szBuffer + strlen(szBuffer), li->list[x], "*");
[773]1624
[551]1625 x++;
1626 if (!li->list[x] || strlen(szBuffer) +
[1004]1627 strlen(li->list[x]) + 5 > MaxComLineStrg) {
[551]1628 runemf2(SEPARATE | WINDOWED |
[907]1629 (fArcStuffVisible ? 0 : BACKGROUND | MINIMIZED) |
1630 WAIT, hwnd, pszSrcFile, __LINE__,
1631 NULL, NULL, "%s", szBuffer);
[551]1632 *p = 0;
1633 }
1634 strcat(szBuffer, " ");
[773]1635 } // while
1636
[551]1637 PostMsg(dcd->hwndCnr, UM_RESCAN, MPFROMSHORT(1), MPVOID);
1638 Broadcast(WinQueryAnchorBlock(hwnd),
1639 hwndMain, UM_UPDATERECORD, MPFROMP(ad.arcname), MPVOID);
1640 Broadcast(WinQueryAnchorBlock(hwnd),
1641 hwndMain,
1642 UM_UPDATERECORDLIST, MPFROMP(li->list), MPVOID);
1643 }
1644 break;
[2]1645
[551]1646 case IDM_REFRESH:
1647 case IDM_DELETE:
1648 {
[1077]1649 CHAR *endofit;
1650 PSZ pszCmdLine;
[551]1651 INT z;
1652 CHECKLIST ck;
1653 CHAR prompt[CCHMAXPATH + 257];
[2]1654
[551]1655 if (!dcd->info->delete)
1656 break;
1657 memset(&ck, 0, sizeof(ck));
1658 ck.size = sizeof(ck);
1659 ck.list = li->list;
1660 ck.cmd = li->type;
1661 ck.prompt = prompt;
1662 sprintf(prompt, GetPString(IDS_ARCCNRDELREFTEXT),
1663 (li->type == IDM_DELETE) ?
1664 GetPString(IDS_DELETELOWERTEXT) :
1665 GetPString(IDS_REFRESHLOWERTEXT),
1666 &"s"[li->list[1] == NULL],
1667 dcd->arcname,
1668 (li->type == IDM_DELETE) ?
1669 GetPString(IDS_DELETELOWERTEXT) :
1670 GetPString(IDS_REFRESHLOWERTEXT));
1671 if (!WinDlgBox(HWND_DESKTOP, hwnd, CheckListProc,
1672 FM3ModHandle, CHECK_FRAME, MPFROMP(&ck)))
1673 break;
1674 li->list = ck.list;
1675 if (!li->list || !li->list[0])
[1077]1676 break;
1677 pszCmdLine = xmallocz(MaxComLineStrg, pszSrcFile, __LINE__);
1678 if (!pszCmdLine)
1679 break;
[1040]1680 strcpy(pszCmdLine, li->type == IDM_DELETE ?
[773]1681 dcd->info->delete :
1682 dcd->info->create);
[1040]1683 strcat(pszCmdLine, " ");
1684 BldQuotedFileName(pszCmdLine + strlen(pszCmdLine), dcd->arcname);
1685 endofit = &pszCmdLine[strlen(pszCmdLine)];
[551]1686 z = 0;
1687 do {
1688 for (x = z; li->list[x] &&
[1040]1689 strlen(pszCmdLine) + strlen(li->list[x]) < 999; x++) {
1690 strcat(pszCmdLine, " ");
1691 BldQuotedFileName(pszCmdLine + strlen(pszCmdLine), li->list[x]);
[551]1692 }
1693 z = x;
[773]1694 runemf2(SEPARATE | WINDOWED | WAIT |
[888]1695 (fArcStuffVisible ? 0 : BACKGROUND | MINIMIZED),
[1040]1696 hwnd, pszSrcFile, __LINE__, NullStr, NULL, "%s", pszCmdLine);
[1077]1697 *endofit = 0;
1698 free(pszCmdLine);
[551]1699 } while (li->list[x]);
1700 PostMsg(dcd->hwndCnr, UM_RESCAN, MPFROMSHORT(1), MPVOID);
1701 Broadcast(WinQueryAnchorBlock(hwnd),
1702 hwndMain,
1703 UM_UPDATERECORD, MPFROMP(dcd->arcname), MPVOID);
1704 }
1705 break;
[2]1706
[551]1707 case IDM_PRINT:
1708 case IDM_VIRUSSCAN:
1709 case IDM_VIEW:
1710 case IDM_MCIPLAY:
1711 case IDM_VIEWARCHIVE:
1712 case IDM_VIEWTEXT:
1713 case IDM_VIEWBINARY:
1714 case IDM_EDIT:
1715 case IDM_EDITTEXT:
1716 case IDM_EDITBINARY:
1717 case IDM_EXEC:
1718 case IDM_EXTRACTWDIRS:
1719 case IDM_EXTRACT:
[1068]1720 case IDM_OPENDEFAULT:
1721 case IDM_OPENSETTINGS:
[551]1722 {
[1077]1723 CHAR *endofit, *ptr;
1724 PSZ pszCmdLine;
[551]1725 INT z;
1726 if ((li->type == IDM_EXTRACT && !li->info->extract) ||
1727 ((li->type == IDM_VIEW || li->type == IDM_VIEWTEXT ||
1728 li->type == IDM_VIEWBINARY || li->type == IDM_EDIT ||
1729 li->type == IDM_VIEWARCHIVE || li->type == IDM_EDITTEXT ||
1730 li->type == IDM_EDITBINARY || li->type == IDM_MCIPLAY) &&
1731 (!li->info->extract && !li->info->exwdirs)) ||
1732 (li->type != IDM_EXTRACT && li->type != IDM_EDIT &&
1733 li->type != IDM_VIEW && li->type != IDM_VIEWTEXT &&
1734 li->type != IDM_VIEWBINARY &&
1735 li->type != IDM_VIEWARCHIVE &&
1736 li->type != IDM_EDITTEXT &&
1737 li->type != IDM_EDITBINARY &&
1738 li->type != IDM_MCIPLAY && !li->info->exwdirs)) {
1739 Runtime_Error(pszSrcFile, __LINE__, "no cmd for request");
1740 break;
1741 }
1742 if (li->type == IDM_EXTRACT || li->type == IDM_EXTRACTWDIRS) {
[2]1743
[551]1744 CHAR fullname[CCHMAXPATH * 2];
1745 CHAR **exfiles = NULL;
[907]1746 UINT numfiles = 0, numalloc = 0;
[2]1747
[551]1748 for (x = 0; li->list[x]; x++) {
[773]1749 BldFullPathName(fullname, li->targetpath, li->list[x]);
[551]1750 if (IsFile(fullname) != -1) {
1751 AddToList(li->list[x], &exfiles, &numfiles, &numalloc);
1752 li->list = RemoveFromList(li->list, li->list[x]);
1753 if (!li->list)
1754 break;
1755 x--;
1756 }
1757 }
1758 if (exfiles && numfiles) {
[2]1759
[551]1760 CHECKLIST ckl;
1761 CHAR prompt[(CCHMAXPATH * 2) + 256];
[2]1762
[551]1763 memset(&ckl, 0, sizeof(ckl));
1764 ckl.size = sizeof(ckl);
1765 ckl.list = exfiles;
1766 ckl.prompt = prompt;
1767 ckl.cmd = li->type;
1768 sprintf(prompt,
1769 GetPString(IDS_REPLACEWARNTEXT),
1770 &"s"[numfiles == 1],
1771 li->arcname, &"s"[numfiles != 1], li->targetpath);
1772 if (!WinDlgBox(HWND_DESKTOP, hwnd, CheckListProc,
1773 FM3ModHandle, CHECK_FRAME, MPFROMP(&ckl))) {
1774 if (ckl.list)
1775 FreeList(ckl.list);
1776 break;
1777 }
1778 else if (ckl.list)
1779 li->list = CombineLists(li->list, ckl.list);
1780 }
1781 }
1782 if (!li->list || !li->list[0])
[1077]1783 break;
1784 pszCmdLine = xmallocz(MaxComLineStrg, pszSrcFile, __LINE__);
1785 if (!pszCmdLine)
1786 break;
[1040]1787 strcpy(pszCmdLine,
[773]1788 (li->type == IDM_EXTRACT ||
1789 ((li->type == IDM_VIEW ||
1790 li->type == IDM_VIEWTEXT ||
1791 li->type == IDM_VIEWBINARY ||
1792 li->type == IDM_VIEWARCHIVE ||
1793 li->type == IDM_PRINT ||
1794 li->type == IDM_EDIT ||
1795 li->type == IDM_EDITTEXT ||
[1068]1796 li->type == IDM_OPENDEFAULT ||
1797 li->type == IDM_OPENSETTINGS ||
1798 (li->type == IDM_EDITBINARY && // JBS No way for this () to be true??
[773]1799 li->type == IDM_MCIPLAY)) &&
1800 !li->info->exwdirs)) ?
1801 li->info->extract :
1802 li->info->exwdirs);
[1040]1803 strcat(pszCmdLine, " ");
1804 BldQuotedFileName(pszCmdLine + strlen(pszCmdLine), li->arcname);
1805 endofit = &pszCmdLine[strlen(pszCmdLine)];
[888]1806 z = 0;
1807 do {
1808 for (x = z; li->list[x] &&
[1069]1809 strlen(pszCmdLine) + strlen(li->list[x]) < MaxComLineStrg - 1 ; x++) {
[1040]1810 strcat(pszCmdLine, " ");
1811 BldQuotedFileName(pszCmdLine + strlen(pszCmdLine), li->list[x]);
[551]1812 ptr = li->list[x];
1813 while (*ptr) {
1814 if (*ptr == '/')
1815 *ptr = '\\';
1816 ptr++;
1817 }
1818 }
1819 z = x;
1820 runemf2(SEPARATE | WINDOWED |
[888]1821 (fArcStuffVisible ? 0 : BACKGROUND | MINIMIZED) |
[907]1822 WAIT, hwnd, pszSrcFile, __LINE__,
[1077]1823 li->targetpath, NULL, "%s", pszCmdLine);
[551]1824 *endofit = 0;
1825 } while (li->list[x]);
1826 if (li->type == IDM_EXTRACT || li->type == IDM_EXTRACTWDIRS) {
1827 /* update windows */
1828 for (x = 0; li->list[x]; x++) {
[2]1829
[551]1830 CHAR *temp, *p;
[2]1831
[551]1832 temp = li->list[x];
1833 p = temp;
1834 while (*p) {
1835 if (*p == '/')
1836 *p = '\\';
1837 p++;
1838 }
[1017]1839 p = xmalloc(strlen(temp) + strlen(li->targetpath) + 2,
1840 pszSrcFile, __LINE__);
[1077]1841 if (p) {
1842 BldFullPathName(p, li->targetpath, temp);
[551]1843 li->list[x] = p;
[1039]1844 free(temp);
[551]1845 }
1846 }
1847 if (fFolderAfterExtract) {
[2]1848
[551]1849 CHAR objectpath[CCHMAXPATH], *p;
1850 APIRET rc;
[2]1851
[551]1852 GetDesktopName(objectpath, sizeof(objectpath));
1853 rc = WinDlgBox(HWND_DESKTOP, dcd->hwndParent, ObjCnrDlgProc,
1854 FM3ModHandle, OBJCNR_FRAME,
1855 MPFROMP(objectpath));
1856 if (rc) {
1857 if (rc > 1)
1858 strcpy(objectpath, "<WP_DESKTOP>");
1859 p = NULL;
1860 if (li->arcname) {
1861 p = strrchr(li->arcname, '\\');
1862 if (p)
1863 p++;
1864 }
1865 MakeShadows(dcd->hwndParent, li->list, 2, objectpath, p);
1866 }
1867 }
1868 Broadcast(WinQueryAnchorBlock(hwnd),
1869 hwndMain,
1870 UM_UPDATERECORDLIST, MPFROMP(li->list), MPVOID);
1871 }
1872 else if (li->type == IDM_EXEC)
1873 ExecOnList(hwnd,
1874 li->runfile,
1875 WINDOWED | SEPARATEKEEP | PROMPT,
1876 li->targetpath,
[907]1877 NULL, GetPString(IDS_EXECARCFILETITLETEXT),
1878 pszSrcFile, __LINE__);
[551]1879 else if (li->type == IDM_VIRUSSCAN)
1880 ExecOnList(hwnd, virus, PROMPT | WINDOWED | SEPARATEKEEP,
1881 li->targetpath, NULL,
[907]1882 GetPString(IDS_VIRUSSCANARCHIVETITLETEXT),
1883 pszSrcFile, __LINE__);
[551]1884 else if (li->type == IDM_VIEW || li->type == IDM_VIEWTEXT ||
1885 li->type == IDM_VIEWBINARY || li->type == IDM_EDIT ||
1886 li->type == IDM_EDITTEXT ||
1887 li->type == IDM_VIEWARCHIVE ||
1888 li->type == IDM_EDITBINARY ||
[1068]1889 li->type == IDM_OPENDEFAULT ||
1890 li->type == IDM_OPENSETTINGS ||
[551]1891 li->type == IDM_MCIPLAY || li->type == IDM_PRINT) {
[2]1892
[551]1893 CHAR *temp, *p;
1894 for (x = 0; li->list[x]; x++) {
1895 if (!li->info->exwdirs) {
1896 temp = li->list[x];
1897 p = strrchr(li->list[x], '\\');
1898 if (p) {
1899 p++;
1900 li->list[x] = xstrdup(p, pszSrcFile, __LINE__);
1901 if (!li->list[x])
1902 li->list[x] = temp;
1903 else {
[1032]1904 xfree(temp, pszSrcFile, __LINE__);
[551]1905 }
1906 }
[1077]1907 }
[1040]1908 BldFullPathName(pszCmdLine, li->targetpath, li->list[x]);
[551]1909 temp = li->list[x];
[1077]1910 li->list[x] = xstrdup(pszCmdLine, pszSrcFile, __LINE__);
[551]1911 if (!li->list[x])
1912 li->list[x] = temp;
1913 else
[1032]1914 xfree(temp, pszSrcFile, __LINE__);
[1077]1915 }
1916 free(pszCmdLine);
[551]1917 if (li->type == IDM_VIEW || li->type == IDM_EDIT) {
[2]1918
[551]1919 BOOL isit = TestBinary(li->list[0]);
[2]1920
[551]1921 if (isit) {
1922 if (li->type == IDM_VIEW)
1923 li->type = IDM_VIEWBINARY;
1924 else
1925 li->type = IDM_EDITBINARY;
1926 }
1927 else {
1928 if (li->type == IDM_VIEW)
1929 li->type = IDM_VIEWTEXT;
1930 else
1931 li->type = IDM_EDITTEXT;
1932 }
1933 }
1934 if (li->type == IDM_MCIPLAY) {
[2]1935
[1077]1936 FILE *fp;
1937 CHAR szTempFile[CCHMAXPATH];
[2]1938
[1077]1939 BldFullPathName(szTempFile, pTmpDir, "$FM2PLAY.$$$");
[1073]1940 fp = xfopen(szTempFile, "w", pszSrcFile, __LINE__);
[551]1941 if (fp) {
1942 fprintf(fp, "%s", ";AV/2-built FM2Play listfile\n");
1943 for (x = 0; li->list[x]; x++)
1944 fprintf(fp, "%s\n", li->list[x]);
1945 fprintf(fp, ";end\n");
[1077]1946 fclose(fp);
1947 strrev(szTempFile);
1948 strcat(szTempFile, "@/");
1949 strrev(szTempFile);
[1073]1950 RunFM2Util("FM2PLAY.EXE", szTempFile);
[762]1951 }
[551]1952 }
1953 else if (li->type == IDM_PRINT) {
1954 strcpy(li->targetpath, printer);
1955 if (_beginthread(PrintListThread, NULL, 65536, (PVOID) li) !=
1956 -1) {
1957 Runtime_Error(pszSrcFile, __LINE__,
1958 GetPString(IDS_COULDNTSTARTTHREADTEXT));
1959 li = NULL;
1960 }
1961 }
1962 else if (li->type == IDM_VIEWARCHIVE) {
[2]1963
[551]1964 ARC_TYPE *info;
[2]1965
[551]1966 for (x = 0; li->list[x]; x++) {
1967 if (IsFile(li->list[x]) == 1) {
1968 info = NULL; // Do not hide dups - fixme to know why?
1969 if (WinDlgBox(HWND_DESKTOP, HWND_DESKTOP,
1970 SBoxDlgProc, FM3ModHandle, ASEL_FRAME,
1971 (PVOID) & info) && info) {
1972 StartArcCnr(HWND_DESKTOP,
1973 HWND_DESKTOP, li->list[x], 4, info);
1974 }
1975 }
1976 }
1977 }
1978 else if ((li->type == IDM_VIEWTEXT && *viewer) ||
1979 (li->type == IDM_VIEWBINARY && *binview) ||
1980 (li->type == IDM_EDITTEXT && *editor) ||
1981 (li->type == IDM_EDITBINARY && *bined)) {
[814]1982 DosSleep(32); //05 Aug 07 GKY 100
[551]1983 ExecOnList(hwnd, ((li->type == IDM_VIEWTEXT) ? viewer :
1984 (li->type == IDM_VIEWBINARY) ? binview :
1985 (li->type == IDM_EDITTEXT) ? editor :
1986 bined),
1987 WINDOWED | SEPARATE, li->targetpath, li->list,
[888]1988 NULL, pszSrcFile, __LINE__);
[551]1989 }
[1068]1990 else if (li->type == IDM_OPENDEFAULT ||
1991 li->type == IDM_OPENSETTINGS) {
1992 WORKER *wk;
[1077]1993# ifdef FORTIFY
1994 Fortify_EnterScope();
1995# endif
[1068]1996 wk = xmallocz(sizeof(WORKER), pszSrcFile, __LINE__);
1997 if (!wk)
[1077]1998 FreeListInfo(li);
[1068]1999 else {
[1077]2000 wk->size = sizeof(WORKER);
2001 wk->hwndCnr = dcd->hwndCnr;
2002 wk->hwndParent = dcd->hwndParent;
2003 wk->hwndFrame = dcd->hwndFrame;
2004 wk->hwndClient = dcd->hwndClient;
2005 wk->li = li;
2006 strcpy(wk->directory, dcd->directory);
2007 if (_beginthread(Action, NULL, 122880, (PVOID) wk) == -1) {
2008 Runtime_Error(pszSrcFile, __LINE__,
2009 GetPString(IDS_COULDNTSTARTTHREADTEXT));
2010 free(wk);
2011 FreeListInfo((LISTINFO *) mp1);
2012 }
2013 }
2014# ifdef FORTIFY
2015 Fortify_LeaveScope();
2016# endif
[1068]2017 }
[551]2018 else {
2019 if (li->hwnd) {
[2]2020
[551]2021 ULONG viewtype;
[2]2022
[551]2023 for (x = 0; li->list[x]; x++) {
2024 if (x == 0) {
2025 if (li->type == IDM_VIEWBINARY ||
2026 li->type == IDM_EDITBINARY)
2027 viewtype = 16;
2028 else
2029 viewtype = 8;
2030 }
2031 else
2032 viewtype = 0;
[1077]2033# ifdef FORTIFY
2034 Fortify_EnterScope();
2035# endif
[551]2036 temp = xstrdup(li->list[x], pszSrcFile, __LINE__);
2037 if (temp) {
2038 if (!PostMsg(WinQueryWindow(li->hwnd, QW_PARENT),
2039 UM_LOADFILE,
2040 MPFROMLONG(4L +
2041 (li->type == IDM_VIEWTEXT ||
2042 li->type == IDM_VIEWBINARY) +
2043 viewtype), MPFROMP(temp)))
2044 free(temp);
2045 }
[1077]2046# ifdef FORTIFY
2047 DosSleep(1); // Allow MassAction to take ownership
2048 Fortify_LeaveScope();
2049# endif
[551]2050 }
2051 }
2052 }
2053 }
2054 }
2055 break;
[2]2056
[551]2057 case IDM_FIND:
2058 {
[907]2059 UINT numfiles = 0, numalloced = 0;
[551]2060 CHAR **list2 = NULL, fullname[CCHMAXPATH * 2], *p;
[2]2061
[551]2062 for (x = 0; li->list[x]; x++) {
2063 p = li->list[x];
2064 while (*p) {
2065 if (*p == '/')
2066 *p = '\\';
2067 p++;
2068 }
[773]2069 BldFullPathName(fullname, dcd->directory, li->list[x]);
[551]2070 if (IsFile(fullname) != -1)
2071 if (AddToList(fullname, &list2, &numfiles, &numalloced))
2072 break;
2073 if (strchr(li->list[x], '\\')) {
2074 p = strrchr(li->list[x], '\\');
2075 if (p) {
2076 p++;
2077 if (*p) {
[773]2078 BldFullPathName(fullname, dcd->directory, p);
[551]2079 if (IsFile(fullname) != -1)
2080 if (AddToList(fullname, &list2, &numfiles, &numalloced))
2081 break;
2082 }
2083 }
2084 }
2085 }
2086 if (!numfiles || !list2)
2087 Runtime_Error(pszSrcFile, __LINE__, "no files or list");
2088 else {
2089 WinSendMsg(dcd->hwndCnr, WM_COMMAND,
2090 MPFROM2SHORT(IDM_COLLECTOR, 0), MPVOID);
[814]2091 DosSleep(10); //05 Aug 07 GKY 128
[551]2092 if (Collector) {
2093 if (!PostMsg(Collector, WM_COMMAND,
2094 MPFROM2SHORT(IDM_COLLECTOR, 0), MPFROMP(list2)))
2095 FreeList(list2);
2096 }
2097 else
2098 FreeList(list2);
2099 }
2100 }
2101 break;
2102 }
[2]2103 }
[1068]2104 if (li->type != IDM_OPENDEFAULT && li->type != IDM_OPENSETTINGS)
2105 {
[1077]2106 FreeListInfo(li);
[1068]2107 }
[551]2108 }
2109 return 0;
[2]2110
[551]2111 case WM_CLOSE:
2112 WinDestroyWindow(hwnd);
2113 break;
[2]2114
[551]2115 case WM_DESTROY:
2116 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
2117 if (dcd) {
2118 if (*dcd->workdir) {
[771]2119 DosSleep(16); //05 Aug 07 GKY 33
[551]2120 wipeallf("%s\\*", dcd->workdir);
2121 if (rmdir(dcd->workdir)) {
[771]2122 DosSleep(100); //05 Aug 07 GKY 256
[551]2123 wipeallf("%s\\*", dcd->workdir);
2124 rmdir(dcd->workdir);
2125 }
[2]2126 }
[551]2127 FreeList(dcd->lastselection);
2128 WinSendMsg(dcd->hwndCnr, UM_CLOSE, MPVOID, MPVOID);
[1039]2129 free(dcd);
[1063]2130# ifdef FORTIFY
[1077]2131 Fortify_LeaveScope();
2132# endif
[551]2133 WinSetWindowPtr(dcd->hwndCnr, QWL_USER, NULL);
2134 }
2135 if (!PostMsg((HWND) 0, WM_QUIT, MPVOID, MPVOID))
2136 WinSendMsg((HWND) 0, WM_QUIT, MPVOID, MPVOID);
2137 break;
2138 } // switch
2139 return WinDefWindowProc(hwnd, msg, mp1, mp2);
[2]2140}
2141
[551]2142static MRESULT EXPENTRY ArcCnrWndProc(HWND hwnd, ULONG msg, MPARAM mp1,
2143 MPARAM mp2)
[172]2144{
[672]2145 DIRCNRDATA *dcd = INSTDATA(hwnd);
[773]2146 CHAR szQuotedArcName[CCHMAXPATH];
[2]2147
[551]2148 switch (msg) {
2149 case DM_PRINTOBJECT:
2150 case DM_DISCARDOBJECT:
2151 if (dcd)
2152 return WinSendMsg(dcd->hwndObject, msg, mp1, mp2);
2153 else
2154 return MRFROMLONG(DRR_TARGET);
[2]2155
[551]2156 case WM_CHAR:
2157 shiftstate = (SHORT1FROMMP(mp1) & (KC_SHIFT | KC_ALT | KC_CTRL));
2158 if (SHORT1FROMMP(mp1) & KC_KEYUP)
2159 return (MRESULT) TRUE;
2160 if (SHORT1FROMMP(mp1) & KC_VIRTUALKEY) {
2161 switch (SHORT2FROMMP(mp2)) {
2162 case VK_DELETE:
2163 PostMsg(hwnd, WM_COMMAND, MPFROM2SHORT(IDM_DELETE, 0), MPVOID);
2164 break;
[2]2165 }
[551]2166 }
2167 if (shiftstate || fNoSearch)
2168 break;
2169 if (SHORT1FROMMP(mp1) & KC_CHAR) {
[2]2170
[551]2171 ULONG thistime, len;
2172 SEARCHSTRING srch;
2173 PCNRITEM pci;
[2]2174
[551]2175 if (!dcd)
2176 break;
2177 switch (SHORT1FROMMP(mp2)) {
2178 case '\x1b':
2179 case '\r':
2180 case '\n':
2181 dcd->lasttime = 0;
2182 *dcd->szCommonName = 0;
2183 break;
2184 default:
2185 thistime = WinQueryMsgTime(WinQueryAnchorBlock(hwnd));
2186 if (thistime > dcd->lasttime + 1250)
2187 *dcd->szCommonName = 0;
2188 dcd->lasttime = thistime;
2189 if (SHORT1FROMMP(mp2) == ' ' && !*dcd->szCommonName)
2190 break;
2191 KbdRetry:
2192 len = strlen(dcd->szCommonName);
2193 if (len >= CCHMAXPATH - 1) {
2194 *dcd->szCommonName = 0;
2195 len = 0;
2196 }
2197 dcd->szCommonName[len] = toupper(SHORT1FROMMP(mp2));
2198 dcd->szCommonName[len + 1] = 0;
2199 memset(&srch, 0, sizeof(SEARCHSTRING));
2200 srch.cb = (ULONG) sizeof(SEARCHSTRING);
2201 srch.pszSearch = dcd->szCommonName;
2202 srch.fsPrefix = TRUE;
2203 srch.fsCaseSensitive = FALSE;
2204 srch.usView = CV_ICON;
2205 pci = WinSendMsg(hwnd,
2206 CM_SEARCHSTRING,
2207 MPFROMP(&srch), MPFROMLONG(CMA_FIRST));
[1120]2208 if (pci && (INT) pci != -1) {
[2]2209
[1120]2210 USHORT attrib = CRA_CURSORED;
[2]2211
[1120]2212
[551]2213 /* make found item current item */
2214 if (!stricmp(pci->pszFileName, dcd->szCommonName))
2215 attrib |= CRA_SELECTED;
2216 WinSendMsg(hwnd,
2217 CM_SETRECORDEMPHASIS,
2218 MPFROMP(pci), MPFROM2SHORT(TRUE, attrib));
2219 /* make sure that record shows in viewport */
2220 ShowCnrRecord(hwnd, (PMINIRECORDCORE) pci);
2221 return (MRESULT) TRUE;
2222 }
2223 else {
2224 if (SHORT1FROMMP(mp2) == ' ') {
2225 dcd->szCommonName[len] = 0;
2226 break;
2227 }
2228 *dcd->szCommonName = 0;
2229 dcd->lasttime = 0;
2230 if (len) // retry as first letter if no match
2231 goto KbdRetry;
2232 }
2233 break;
[2]2234 }
[551]2235 }
2236 break;
[2]2237
[551]2238 case WM_MOUSEMOVE:
2239 case WM_BUTTON1UP:
2240 case WM_BUTTON2UP:
2241 case WM_BUTTON3UP:
2242 case WM_CHORD:
2243 shiftstate = (SHORT2FROMMP(mp2) & (KC_SHIFT | KC_ALT | KC_CTRL));
2244 break;
[2]2245
[551]2246 case WM_BUTTON1MOTIONEND:
2247 {
2248 CNRINFO cnri;
[2]2249
[551]2250 memset(&cnri, 0, sizeof(CNRINFO));
2251 cnri.cb = sizeof(CNRINFO);
2252 if (WinSendMsg(hwnd,
2253 CM_QUERYCNRINFO,
2254 MPFROMP(&cnri), MPFROMLONG(sizeof(CNRINFO)))) {
2255 if (cnri.flWindowAttr & CV_DETAIL)
2256 PrfWriteProfileData(fmprof,
2257 appname,
2258 "ArcCnrSplitBar",
2259 (PVOID) & cnri.xVertSplitbar, sizeof(LONG));
[2]2260 }
[551]2261 }
2262 break;
[2]2263
[551]2264 case WM_PRESPARAMCHANGED:
2265 PresParamChanged(hwnd, "ArcCnr", mp1, mp2);
2266 break;
[2]2267
[551]2268 case UM_UPDATERECORD:
2269 case UM_UPDATERECORDLIST:
2270 if (dcd && !IsArcThere(hwnd, dcd->arcname))
2271 PostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
2272 return 0;
[2]2273
[551]2274 case WM_SETFOCUS:
2275 /*
2276 * put name of our window (archive name) on status line
2277 */
2278 if (dcd && hwndStatus && mp2)
2279 WinSendMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
2280 break;
[2]2281
[551]2282 case UM_SETUP2:
2283 if (dcd && dcd->info) {
2284 if (dcd->info->fdpos == -1 || !dcd->info->datetype)
2285 dcd->sortFlags &= (~SORT_LWDATE);
2286 if (dcd->info->nsizepos == -1)
2287 dcd->sortFlags &= (~SORT_EASIZE);
2288 if (dcd->info->osizepos == -1)
2289 dcd->sortFlags &= (~SORT_SIZE);
2290 AdjustCnrColVis(hwnd,
2291 GetPString(IDS_OLDSIZECOLTEXT),
2292 dcd->info->osizepos != -1, FALSE);
2293 AdjustCnrColVis(hwnd,
2294 GetPString(IDS_NEWSIZECOLTEXT),
2295 dcd->info->nsizepos != -1, FALSE);
2296 // Display unsullied date/time string if type 0
2297 AdjustCnrColVis(hwnd,
2298 GetPString(IDS_DATETIMECOLTEXT),
2299 dcd->info->fdpos != -1 && !dcd->info->datetype, FALSE);
2300 // Display parsed date/time columns if type specified
2301 AdjustCnrColVis(hwnd,
2302 GetPString(IDS_TIMECOLTEXT),
2303 dcd->info->fdpos != -1 && dcd->info->datetype, FALSE);
2304 AdjustCnrColVis(hwnd,
2305 GetPString(IDS_DATECOLTEXT),
2306 dcd->info->fdpos != -1 && dcd->info->datetype, FALSE);
2307 WinSendMsg(hwnd, CM_INVALIDATEDETAILFIELDINFO, MPVOID, MPVOID);
2308 }
2309 return 0;
[2]2310
[551]2311 case UM_RESCAN:
2312 if (dcd) {
2313 CNRINFO cnri;
2314 CHAR s[CCHMAXPATH * 2], tb[81], tf[81];
2315 PARCITEM pci;
[2]2316
[551]2317 if (mp1) {
2318 PostMsg(dcd->hwndObject, UM_RESCAN, MPVOID, MPVOID);
2319 return 0;
2320 }
2321 memset(&cnri, 0, sizeof(CNRINFO));
2322 cnri.cb = sizeof(CNRINFO);
2323 WinSendMsg(hwnd,
2324 CM_QUERYCNRINFO,
2325 MPFROMP(&cnri), MPFROMLONG(sizeof(CNRINFO)));
2326 dcd->totalfiles = cnri.cRecords;
2327 commafmt(tf, sizeof(tf), dcd->selectedfiles);
2328 if (dcd->ullTotalBytes)
2329 CommaFmtULL(tb, sizeof(tb), dcd->selectedbytes, 'K');
2330 else
2331 *tb = 0;
2332 sprintf(s, "%s%s%s", tf, *tb ? " / " : NullStr, tb);
2333 WinSetDlgItemText(dcd->hwndClient, DIR_SELECTED, s);
2334 commafmt(tf, sizeof(tf), dcd->totalfiles);
2335 if (dcd->ullTotalBytes)
2336 CommaFmtULL(tb, sizeof(tb), dcd->ullTotalBytes, 'K');
2337 else
2338 *tb = 0;
2339 sprintf(s, "%s%s%s", tf, *tb ? " / " : NullStr, tb);
2340 WinSetDlgItemText(dcd->hwndClient, DIR_TOTALS, s);
2341 if (hwndStatus &&
2342 dcd->hwndFrame == WinQueryActiveWindow(dcd->hwndParent)) {
2343 sprintf(s, " [%s%s%s]%s%s%s %s",
2344 tf,
[156]2345 *tb ? " / " : NullStr,
[551]2346 tb,
[562]2347 *dcd->mask.szMask ? " (" : NullStr,
2348 *dcd->mask.szMask ? dcd->mask.szMask : NullStr,
2349 *dcd->mask.szMask ? ")" : NullStr, dcd->arcname);
[551]2350 WinSetWindowText(hwndStatus, s);
2351 if (!ParentIsDesktop(hwnd, dcd->hwndParent)) {
2352 pci = WinSendMsg(hwnd,
2353 CM_QUERYRECORDEMPHASIS,
2354 MPFROMLONG(CMA_FIRST), MPFROMSHORT(CRA_CURSORED));
[1120]2355 if (pci && (INT) pci != -1) {
[551]2356 if (fSplitStatus && hwndStatus2) {
2357 if (dcd->ullTotalBytes)
2358 CommaFmtULL(tb, sizeof(tb), pci->cbFile, ' ');
2359 else
2360 *tb = 0;
2361 sprintf(s, "%s%s%s%s",
2362 *tb ? " " : NullStr,
[730]2363 tb, *tb ? " " : NullStr, pci->pszFileName);
[551]2364 WinSetWindowText(hwndStatus2, s);
2365 }
2366 if (fMoreButtons)
[730]2367 WinSetWindowText(hwndName, pci->pszFileName);
[551]2368 }
2369 else {
2370 WinSetWindowText(hwndStatus2, NullStr);
2371 WinSetWindowText(hwndName, NullStr);
2372 }
2373 WinSetWindowText(hwndDate, NullStr);
2374 WinSetWindowText(hwndAttr, NullStr);
2375 }
[2]2376 }
[563]2377 if ((dcd->arcfilled && !dcd->totalfiles) ||
[762]2378 !IsArcThere(hwnd, dcd->arcname))
[551]2379 PostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
2380 }
2381 return 0;
2382
2383 case UM_SETUP:
2384 if (!dcd) {
2385 Runtime_Error2(pszSrcFile, __LINE__, IDS_NODATATEXT);
2386 PostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
[2]2387 return 0;
[551]2388 }
2389 else {
2390 if (!dcd->hwndObject) {
2391 /*
2392 * first time through -- set things up
2393 */
2394 {
2395 CHAR *p, *pp;
2396 ULONG z, was;
2397 APIRET rc;
[2]2398
[551]2399 rc = DosCreateDir(dcd->workdir, 0);
2400 if (rc) {
2401 if (rc == ERROR_ACCESS_DENIED) {
2402 p = strrchr(dcd->workdir, '.');
2403 if (p) {
2404 p++;
2405 pp = p;
2406 was = strtoul(p, &pp, 16);
2407 for (z = 0; z < 99; z++) {
2408 was++;
2409 sprintf(p, "%03x");
2410 rc = DosCreateDir(dcd->workdir, 0);
2411 if (!rc || rc != ERROR_ACCESS_DENIED)
2412 break;
2413 }
2414 }
2415 }
2416 if (rc)
2417 PostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
2418 return 0;
2419 }
2420 }
2421 RestorePresParams(hwnd, "ArcCnr");
2422 dcd->mask.fNoAttribs = TRUE;
2423 dcd->mask.fNoDirs = TRUE;
2424 *dcd->mask.prompt = 0;
2425 {
2426 PFIELDINFO pfi, pfiLastLeftCol;
2427 ULONG numcols = CON_COLS;
2428 CNRINFO cnri;
2429 ULONG size;
[2]2430
[551]2431 pfi = WinSendMsg(hwnd,
2432 CM_ALLOCDETAILFIELDINFO,
2433 MPFROMLONG(numcols), NULL);
2434 if (pfi) {
[2]2435
[551]2436 PFIELDINFO pfiFirst;
2437 FIELDINFOINSERT fii;
[2]2438
[551]2439 pfiFirst = pfi;
2440 pfi->flData = CFA_STRING | CFA_LEFT | CFA_FIREADONLY;
2441 pfi->flTitle = CFA_CENTER;
2442 pfi->pTitleData = GetPString(IDS_FILENAMECOLTEXT);
[739]2443 pfi->offStruct = FIELDOFFSET(ARCITEM, pszDisplayName);
[551]2444 pfiLastLeftCol = pfi;
2445 pfi = pfi->pNextFieldInfo;
2446 pfi->flData =
2447 CFA_ULONG | CFA_RIGHT | CFA_SEPARATOR | CFA_FIREADONLY;
2448 pfi->flTitle = CFA_CENTER;
2449 pfi->pTitleData = GetPString(IDS_OLDSIZECOLTEXT);
2450 pfi->offStruct = FIELDOFFSET(ARCITEM, cbFile);
2451 pfi = pfi->pNextFieldInfo;
2452 pfi->flData =
2453 CFA_ULONG | CFA_RIGHT | CFA_SEPARATOR | CFA_FIREADONLY;
2454 pfi->flTitle = CFA_CENTER;
2455 pfi->pTitleData = GetPString(IDS_NEWSIZECOLTEXT);
2456 pfi->offStruct = FIELDOFFSET(ARCITEM, cbComp);
2457 pfi = pfi->pNextFieldInfo;
2458 pfi->flData =
2459 CFA_STRING | CFA_CENTER | CFA_SEPARATOR | CFA_FIREADONLY;
2460 pfi->flTitle = CFA_CENTER | CFA_FITITLEREADONLY;
2461 pfi->pTitleData = GetPString(IDS_DATETIMECOLTEXT);
2462 pfi->offStruct = FIELDOFFSET(ARCITEM, pszDate);
2463 pfi = pfi->pNextFieldInfo;
2464 pfi->flData = CFA_DATE | CFA_RIGHT | CFA_FIREADONLY;
2465 pfi->flTitle = CFA_CENTER;
2466 pfi->pTitleData = GetPString(IDS_DATECOLTEXT);
2467 pfi->offStruct = FIELDOFFSET(ARCITEM, date);
2468 pfi = pfi->pNextFieldInfo;
2469 pfi->flData = CFA_TIME | CFA_RIGHT | CFA_FIREADONLY;
2470 pfi->flTitle = CFA_CENTER | CFA_FITITLEREADONLY;
2471 pfi->pTitleData = GetPString(IDS_TIMECOLTEXT);
2472 pfi->offStruct = FIELDOFFSET(ARCITEM, time);
2473 memset(&fii, 0, sizeof(FIELDINFOINSERT));
2474 fii.cb = sizeof(FIELDINFOINSERT);
2475 fii.pFieldInfoOrder = (PFIELDINFO) CMA_FIRST;
2476 fii.cFieldInfoInsert = (SHORT) numcols;
2477 fii.fInvalidateFieldInfo = TRUE;
2478 WinSendMsg(hwnd,
2479 CM_INSERTDETAILFIELDINFO,
2480 MPFROMP(pfiFirst), MPFROMP(&fii));
2481 PostMsg(hwnd, UM_SETUP2, MPVOID, MPVOID);
[2]2482
[551]2483 memset(&cnri, 0, sizeof(cnri));
2484 cnri.cb = sizeof(CNRINFO);
2485 cnri.pFieldInfoLast = pfiLastLeftCol;
2486 cnri.xVertSplitbar = DIR_SPLITBAR_OFFSET + 32;
[2]2487
[551]2488 size = sizeof(LONG);
2489 PrfQueryProfileData(fmprof, appname, "ArcCnrSplitBar",
2490 &cnri.xVertSplitbar, &size);
2491 if (cnri.xVertSplitbar <= 0)
2492 cnri.xVertSplitbar = DIR_SPLITBAR_OFFSET + 32;
[2]2493
[551]2494 cnri.flWindowAttr &= (~(CV_ICON | CV_TREE | CV_TEXT | CV_NAME));
2495 cnri.flWindowAttr |= (CV_DETAIL | CA_DETAILSVIEWTITLES | CV_FLOW);
2496 cnri.flWindowAttr &= (~(CA_ORDEREDTARGETEMPH |
2497 CA_MIXEDTARGETEMPH));
2498 cnri.pSortRecord = (PVOID) ArcSort;
2499 WinSendMsg(hwnd,
2500 CM_SETCNRINFO,
2501 MPFROMP(&cnri),
2502 MPFROMLONG(CMA_PFIELDINFOLAST |
2503 CMA_XVERTSPLITBAR |
2504 CMA_PSORTRECORD | CMA_FLWINDOWATTR));
2505 }
2506 }
2507 WinSendMsg(hwnd, CM_SORTRECORD, MPFROMP(ArcSort), MPFROMP(dcd));
2508 if (_beginthread(MakeObjWin, NULL, 245760, (PVOID) dcd) == -1) {
2509 Runtime_Error(pszSrcFile, __LINE__,
2510 GetPString(IDS_COULDNTSTARTTHREADTEXT));
2511 PostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
2512 return 0;
2513 }
2514 else
[766]2515 DosSleep(1);
[551]2516 SayFilter(WinWindowFromID(WinQueryWindow(hwnd, QW_PARENT),
2517 DIR_FILTER), &dcd->mask, TRUE);
2518 SaySort(WinWindowFromID(WinQueryWindow(hwnd, QW_PARENT),
2519 DIR_SORT), dcd->sortFlags, TRUE);
2520 DefArcSortFlags = dcd->sortFlags; // Remember for new windows
[2]2521 }
[551]2522 }
2523 return 0;
[2]2524
[551]2525 case UM_SETDIR:
2526 if (dcd) {
[2]2527
[551]2528 CHAR s[CCHMAXPATH], *p;
2529 ULONG ret = 0;
[2]2530
[551]2531 WinQueryDlgItemText(dcd->hwndClient, ARC_EXTRACTDIR, CCHMAXPATH, s);
2532 bstrip(s);
2533 MakeFullName(s);
2534 if (*s) {
2535 while ((p = strchr(s, '/')) != NULL)
2536 *p = '\\';
2537 while (strlen(s) > 3 && s[strlen(s) - 1] == '\\')
2538 s[strlen(s) - 1] = 0;
2539 if (stricmp(s, dcd->directory)) {
2540 if (IsFullName(s)) {
2541 if (driveflags[toupper(*s) - 'A'] &
2542 (DRIVE_NOTWRITEABLE | DRIVE_IGNORE | DRIVE_INVALID)) {
2543 Runtime_Error(pszSrcFile, __LINE__, "drive %s bad", s);
2544 WinSetDlgItemText(dcd->hwndClient,
2545 ARC_EXTRACTDIR, dcd->directory);
2546 return 0;
2547 }
2548 }
2549 if (!SetDir(dcd->hwndParent, hwnd, s, 0)) {
2550 if (stricmp(dcd->directory, s)) {
2551 DosEnterCritSec();
2552 strcpy(lastextractpath, s);
2553 DosExitCritSec();
2554 }
2555 strcpy(dcd->directory, s);
2556 if ((!isalpha(*s) || s[1] != ':') && *s != '.')
2557 saymsg(MB_ENTER | MB_ICONASTERISK,
2558 hwnd,
2559 GetPString(IDS_WARNINGTEXT),
2560 GetPString(IDS_SPECIFYDRIVETEXT));
2561 }
2562 else
2563 ret = 1;
2564 }
[2]2565 }
[551]2566 WinSetDlgItemText(dcd->hwndClient, ARC_EXTRACTDIR, dcd->directory);
2567 return (MRESULT) ret;
2568 }
2569 return 0;
2570
2571 case UM_ENTER:
2572 if (WinSendMsg(hwnd, UM_SETDIR, MPVOID, MPVOID))
[2]2573 return 0;
[551]2574 SetShiftState();
2575 if (dcd && (CHAR *) mp1) {
[2]2576
[551]2577 SWP swp;
2578 CHAR *filename = mp1;
[2]2579
[551]2580 if (IsFile(filename) != 1)
2581 return 0;
2582 WinQueryWindowPos(dcd->hwndFrame, &swp);
2583 DefaultViewKeys(hwnd, dcd->hwndFrame, dcd->hwndParent, &swp, filename);
2584 if (fUnHilite)
[672]2585 UnHilite(hwnd, FALSE, &dcd->lastselection, 0);
[551]2586 }
2587 return 0;
[2]2588
[551]2589 case WM_MENUEND:
2590 if (dcd) {
[2]2591
[551]2592 HWND hwndMenu = (HWND) mp2;
[2]2593
[551]2594 if (hwndMenu == ArcCnrMenu || hwndMenu == ArcMenu) {
2595 MarkAll(hwnd, TRUE, FALSE, TRUE);
2596 if (dcd->cnremphasized) {
2597 WinSendMsg(hwnd,
2598 CM_SETRECORDEMPHASIS,
2599 MPVOID, MPFROM2SHORT(FALSE, CRA_SOURCE));
2600 dcd->cnremphasized = FALSE;
2601 }
[2]2602 }
[551]2603 }
2604 break;
[2]2605
[551]2606 case MM_PORTHOLEINIT:
2607 if (dcd) {
2608 switch (SHORT1FROMMP(mp1)) {
2609 case 0:
2610 case 1:
2611 {
2612 ULONG wmsg;
[2]2613
[562]2614 wmsg = SHORT1FROMMP(mp1) == 0 ? UM_FILESMENU : UM_VIEWSMENU;
[551]2615 PortholeInit((HWND) WinSendMsg(dcd->hwndClient,
2616 wmsg, MPVOID, MPVOID), mp1, mp2);
2617 }
2618 break;
[2]2619 }
[551]2620 }
2621 break;
[2]2622
[551]2623 case UM_INITMENU:
2624 case WM_INITMENU:
2625 if (dcd) {
2626 switch (SHORT1FROMMP(mp1)) {
2627 case IDM_FILESMENU:
2628 if (dcd->info) {
2629 WinEnableMenuItem((HWND) mp2,
2630 IDM_DELETE, dcd->info->delete != NULL);
2631 WinEnableMenuItem((HWND) mp2, IDM_TEST, dcd->info->test != NULL);
2632 WinEnableMenuItem((HWND) mp2,
2633 IDM_EXTRACT, dcd->info->extract != NULL);
2634 WinEnableMenuItem((HWND) mp2,
2635 IDM_EXTRACTWDIRS, dcd->info->exwdirs != NULL);
2636 WinEnableMenuItem((HWND) mp2,
2637 IDM_ARCEXTRACTWDIRS, dcd->info->exwdirs != NULL);
2638 WinEnableMenuItem((HWND) mp2,
2639 IDM_ARCEXTRACTWDIRSEXIT,
2640 dcd->info->exwdirs != NULL);
2641 }
2642 break;
[2]2643
[551]2644 case IDM_VIEWSMENU:
2645 WinCheckMenuItem((HWND) mp2,
[562]2646 IDM_MINIICONS, (dcd->flWindowAttr & CV_MINI) != 0);
[551]2647 WinEnableMenuItem((HWND) mp2,
2648 IDM_RESELECT, (dcd->lastselection != NULL));
2649 break;
[2]2650
[551]2651 case IDM_COMMANDSMENU:
2652 SetupCommandMenu((HWND) mp2, hwnd);
2653 break;
[2]2654
[551]2655 case IDM_SORTSUBMENU:
2656 SetSortChecks((HWND) mp2, dcd->sortFlags);
2657 break;
[2]2658
[551]2659 case IDM_WINDOWSMENU:
2660 /*
2661 * add switchlist entries to end of pulldown menu
2662 */
[562]2663 SetupWinList((HWND)mp2,
2664 hwndMain ? hwndMain : (HWND)0, dcd->hwndFrame);
[551]2665 break;
[2]2666 }
[551]2667 dcd->hwndLastMenu = (HWND) mp2;
2668 }
2669 if (msg == WM_INITMENU)
2670 break;
2671 return 0;
[2]2672
[551]2673 case UM_LOADFILE:
2674 if (dcd && mp2) {
[2]2675
[1037]2676 HWND hwnd;
[2]2677
[1037]2678 if ((INT)mp1 == 5 || (INT)mp1 == 13 || (INT)mp1 == 21)
[1077]2679 hwnd = StartViewer(HWND_DESKTOP, (INT)mp1,
2680 (CHAR *)mp2, dcd->hwndFrame);
[1037]2681 else
[1077]2682 hwnd = StartMLEEditor(dcd->hwndParent,
2683 (INT)mp1, (CHAR *)mp2, dcd->hwndFrame);
[1039]2684 free((CHAR *)mp2);
[1037]2685 return MRFROMLONG(hwnd);
[551]2686 }
2687 return 0;
2688
2689 case UM_COMMAND:
2690 if (mp1) {
2691 if (dcd) {
2692 if (!PostMsg(dcd->hwndObject, UM_COMMAND, mp1, mp2)) {
2693 Runtime_Error(pszSrcFile, __LINE__, "post");
2694 FreeListInfo((LISTINFO *) mp1);
2695 }
2696 else
2697 return (MRESULT) TRUE;
[2]2698 }
[551]2699 else
2700 FreeListInfo((LISTINFO *) mp1);
2701 }
2702 return 0;
[2]2703
[551]2704 case UM_OPENWINDOWFORME:
2705 if (dcd) {
2706 if (mp1 && !IsFile((CHAR *) mp1)) {
2707 OpenDirCnr((HWND) 0, hwndMain, dcd->hwndFrame, FALSE, (char *)mp1);
[2]2708 }
[1120]2709 else if (mp1 && IsFile(mp1) == 1 &&
2710 CheckDriveSpaceAvail(ArcTempRoot, ullDATFileSpaceNeeded, ullTmpSpaceNeeded) != 2) {
[551]2711 StartArcCnr(HWND_DESKTOP,
2712 dcd->hwndFrame, (CHAR *) mp1, 4, (ARC_TYPE *) mp2);
2713 }
2714 }
2715 return 0;
[2]2716
[551]2717 case WM_COMMAND:
2718 DosError(FERR_DISABLEHARDERR);
2719 if (dcd) {
2720 if (SwitchCommand(dcd->hwndLastMenu, SHORT1FROMMP(mp1)))
2721 return 0;
2722 if (WinSendMsg(hwnd, UM_SETDIR, MPVOID, MPVOID))
2723 return 0;
2724 if (!IsArcThere(hwnd, dcd->arcname)) {
2725 PostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
2726 return 0;
[2]2727 }
[551]2728 switch (SHORT1FROMMP(mp1)) {
2729 case IDM_TREEVIEW:
[2]2730
[551]2731 break;
[2]2732
[551]2733 case IDM_CONTEXTMENU:
2734 {
2735 PCNRITEM pci;
[2]2736
[551]2737 pci = (PCNRITEM) CurrentRecord(hwnd);
2738 PostMsg(hwnd,
2739 WM_CONTROL,
2740 MPFROM2SHORT(ARC_CNR, CN_CONTEXTMENU), MPFROMP(pci));
2741 }
2742 break;
[2]2743
[551]2744 case IDM_NEXTWINDOW:
2745 case IDM_PREVWINDOW:
2746 {
2747 HWND hwndActive;
[2]2748
[551]2749 hwndActive = WinQueryFocus(HWND_DESKTOP);
2750 WinSetFocus(HWND_DESKTOP,
[563]2751 hwndActive == hwnd ?
[762]2752 WinWindowFromID(dcd->hwndClient, ARC_EXTRACTDIR) :
2753 hwnd);
[551]2754 }
2755 break;
[2]2756
[551]2757 case IDM_FOLDERAFTEREXTRACT:
[562]2758 fFolderAfterExtract = fFolderAfterExtract ? FALSE : TRUE;
[551]2759 PrfWriteProfileData(fmprof, appname, "FolderAfterExtract",
2760 &fFolderAfterExtract, sizeof(BOOL));
2761 break;
[2]2762
[551]2763 case IDM_SHOWSELECT:
[872]2764 QuickPopup(hwnd, dcd, CheckMenu(hwnd, &ArcCnrMenu, ARCCNR_POPUP),
[551]2765 IDM_SELECTSUBMENU);
2766 break;
[2]2767
[551]2768 case IDM_SHOWSORT:
[872]2769 QuickPopup(hwnd, dcd, CheckMenu(hwnd, &ArcCnrMenu, ARCCNR_POPUP),
[551]2770 IDM_SORTSUBMENU);
2771 break;
[2]2772
[953]2773 case IDM_ARCHIVERSETTINGS:
[551]2774 if (!ParentIsDesktop(dcd->hwndParent, dcd->hwndParent))
[917]2775 PostMsg(dcd->hwndParent, msg, MPFROMLONG(IDM_ARCHIVERSETTINGS), mp2);
2776 else {
[551]2777 WinDlgBox(HWND_DESKTOP,
2778 hwnd,
[917]2779 CfgDlgProc,
2780 FM3ModHandle,
2781 CFG_FRAME,
2782 MPFROMLONG(IDM_ARCHIVERSETTINGS));
2783 }
[551]2784 break;
[2]2785
[551]2786 case IDM_RESCAN:
2787 dcd->ullTotalBytes = dcd->totalfiles =
2788 dcd->selectedfiles = dcd->selectedbytes = 0;
2789 WinSetDlgItemText(dcd->hwndClient, DIR_TOTALS, "0");
2790 WinSetDlgItemText(dcd->hwndClient, DIR_SELECTED, "0 / 0k");
2791 dcd->totalfiles = FillArcCnr(dcd->hwndCnr,
2792 dcd->arcname,
2793 &dcd->info,
2794 &dcd->ullTotalBytes, &dcd->stopflag);
2795 PostMsg(dcd->hwndCnr, UM_RESCAN, MPVOID, MPVOID);
2796 PostMsg(dcd->hwndCnr, UM_SETUP2, MPVOID, MPVOID);
2797 WinSendMsg(dcd->hwndCnr,
2798 CM_INVALIDATERECORD,
2799 MPVOID, MPFROM2SHORT(0, CMA_ERASE | CMA_REPOSITION));
2800 break;
[2]2801
[551]2802 case IDM_RESELECT:
2803 SelectList(hwnd, TRUE, FALSE, FALSE, NULL, NULL, dcd->lastselection);
2804 break;
[2]2805
[551]2806 case IDM_HELP:
2807 if (hwndHelp)
2808 WinSendMsg(hwndHelp,
2809 HM_DISPLAY_HELP,
2810 MPFROM2SHORT(HELP_ARCLIST, 0),
2811 MPFROMSHORT(HM_RESOURCEID));
2812 break;
[2]2813
[551]2814 case IDM_WINDOWDLG:
2815 if (!ParentIsDesktop(dcd->hwndParent, dcd->hwndFrame))
2816 PostMsg(dcd->hwndParent,
2817 UM_COMMAND, MPFROM2SHORT(IDM_WINDOWDLG, 0), MPVOID);
2818 break;
[2]2819
[551]2820 case IDM_SELECTALL:
2821 case IDM_SELECTALLFILES:
2822 case IDM_DESELECTALL:
2823 case IDM_DESELECTALLFILES:
2824 case IDM_SELECTMASK:
2825 case IDM_DESELECTMASK:
2826 case IDM_INVERT:
2827 {
2828 PARCITEM pci;
[2]2829
[551]2830 pci = (PARCITEM) WinSendMsg(hwnd,
2831 CM_QUERYRECORDEMPHASIS,
2832 MPFROMLONG(CMA_FIRST),
2833 MPFROMSHORT(CRA_CURSORED));
2834 if ((INT) pci == -1)
2835 pci = NULL;
2836 if (SHORT1FROMMP(mp1) == IDM_HIDEALL) {
2837 if (pci) {
2838 if (!(pci->rc.flRecordAttr & CRA_SELECTED))
2839 pci->rc.flRecordAttr |= CRA_FILTERED;
2840 WinSendMsg(hwnd,
2841 CM_INVALIDATERECORD,
2842 MPFROMP(&pci),
2843 MPFROM2SHORT(1, CMA_ERASE | CMA_REPOSITION));
2844 break;
2845 }
2846 }
2847 PostMsg(dcd->hwndObject, UM_SELECT, mp1, MPFROMP(pci));
2848 }
2849 break;
[2]2850
[551]2851 case IDM_SORTSMARTNAME:
2852 case IDM_SORTNAME:
2853 case IDM_SORTFILENAME:
2854 case IDM_SORTSIZE:
2855 case IDM_SORTEASIZE:
2856 case IDM_SORTFIRST:
2857 case IDM_SORTLAST:
2858 case IDM_SORTLWDATE:
2859 dcd->sortFlags &= SORT_REVERSE;
2860 /* intentional fallthru */
2861 case IDM_SORTREVERSE:
2862 switch (SHORT1FROMMP(mp1)) {
2863 case IDM_SORTSMARTNAME:
2864 case IDM_SORTFILENAME:
2865 dcd->sortFlags |= SORT_FILENAME;
2866 break;
2867 case IDM_SORTSIZE:
2868 dcd->sortFlags |= SORT_SIZE;
2869 break;
2870 case IDM_SORTEASIZE:
2871 dcd->sortFlags |= SORT_EASIZE;
2872 break;
2873 case IDM_SORTFIRST:
2874 dcd->sortFlags |= SORT_FIRSTEXTENSION;
2875 break;
2876 case IDM_SORTLAST:
2877 dcd->sortFlags |= SORT_LASTEXTENSION;
2878 break;
2879 case IDM_SORTLWDATE:
2880 dcd->sortFlags |= SORT_LWDATE;
2881 break;
2882 case IDM_SORTREVERSE:
2883 if (dcd->sortFlags & SORT_REVERSE)
2884 dcd->sortFlags &= (~SORT_REVERSE);
2885 else
2886 dcd->sortFlags |= SORT_REVERSE;
2887 break;
2888 }
2889 WinSendMsg(hwnd, CM_SORTRECORD, MPFROMP(ArcSort), MPFROMP(dcd));
2890 SaySort(WinWindowFromID(WinQueryWindow(hwnd, QW_PARENT),
2891 DIR_SORT), dcd->sortFlags, TRUE);
2892 DefArcSortFlags = dcd->sortFlags; // Remember for new windows
2893 break;
[2]2894
[551]2895 case IDM_COLLECTOR:
2896 if (!Collector) {
2897 HWND hwndC;
2898 SWP swp;
[2]2899
[551]2900 if (ParentIsDesktop(hwnd, dcd->hwndParent) && !fAutoTile &&
2901 (!fExternalCollector && !strcmp(realappname, FM3Str)))
2902 GetNextWindowPos(dcd->hwndParent, &swp, NULL, NULL);
[563]2903 hwndC = StartCollector(fExternalCollector ||
2904 strcmp(realappname, FM3Str) ?
2905 HWND_DESKTOP : dcd->hwndParent, 4);
[551]2906 if (hwndC) {
2907 if (!ParentIsDesktop(hwnd, dcd->hwndParent) && !fAutoTile &&
2908 (!fExternalCollector && !strcmp(realappname, FM3Str)))
2909 WinSetWindowPos(hwndC,
2910 HWND_TOP,
2911 swp.x,
2912 swp.y,
2913 swp.cx,
2914 swp.cy,
2915 SWP_MOVE | SWP_SIZE | SWP_SHOW | SWP_ZORDER);
2916 else if (!ParentIsDesktop(hwnd, dcd->hwndParent) &&
2917 fAutoTile && !strcmp(realappname, FM3Str)) {
2918 TileChildren(dcd->hwndParent, TRUE);
2919 }
2920 WinSetWindowPos(hwndC, HWND_TOP, 0, 0, 0, 0, SWP_ACTIVATE);
[771]2921 DosSleep(100); //05 Aug 07 GKY 128
[551]2922 }
2923 }
2924 else
2925 StartCollector(dcd->hwndParent, 4);
2926 break;
[2]2927
[551]2928 case IDM_ARCEXTRACTEXIT:
2929 case IDM_ARCEXTRACT:
2930 if (dcd->info->extract)
2931 runemf2(SEPARATE | WINDOWED |
[888]2932 (fArcStuffVisible ? 0 : BACKGROUND | MINIMIZED),
[907]2933 hwnd, pszSrcFile, __LINE__,
2934 dcd->directory, NULL, "%s %s", dcd->info->extract,
[773]2935 BldQuotedFileName(szQuotedArcName, dcd->arcname));
[551]2936 if (SHORT1FROMMP(mp1) == IDM_ARCEXTRACTEXIT)
2937 PostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
2938 break;
[2]2939
[551]2940 case IDM_ARCEXTRACTWDIRSEXIT:
2941 case IDM_ARCEXTRACTWDIRS:
2942 if (dcd->info->exwdirs)
2943 runemf2(SEPARATE | WINDOWED |
[888]2944 (fArcStuffVisible ? 0 : BACKGROUND | MINIMIZED),
[907]2945 hwnd, pszSrcFile, __LINE__,
2946 dcd->directory, NULL, "%s %s",
[551]2947 dcd->info->exwdirs,
[773]2948 BldQuotedFileName(szQuotedArcName, dcd->arcname));
[551]2949 if (SHORT1FROMMP(mp1) == IDM_ARCEXTRACTWDIRSEXIT)
2950 PostMsg(hwnd, WM_CLOSE, MPVOID, MPVOID);
2951 break;
[2]2952
[551]2953 case IDM_RESORT:
2954 WinSendMsg(hwnd, CM_SORTRECORD, MPFROMP(ArcSort), MPFROMP(dcd));
2955 break;
[2]2956
[551]2957 case IDM_FILTER:
2958 {
2959 BOOL empty = FALSE;
2960 PARCITEM pci;
[2]2961
[551]2962 if (!*dcd->mask.szMask) {
2963 empty = TRUE;
2964 pci = (PARCITEM) CurrentRecord(hwnd);
[730]2965 if (pci && strchr(pci->pszFileName, '.'))
2966 strcpy(dcd->mask.szMask, pci->pszFileName);
[551]2967 }
[2]2968
[551]2969 if (WinDlgBox(HWND_DESKTOP, hwnd, PickMaskDlgProc,
2970 FM3ModHandle, MSK_FRAME, MPFROMP(&dcd->mask))) {
2971 WinSendMsg(hwnd, CM_FILTER, MPFROMP(ArcFilter), MPFROMP(dcd));
2972 PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
2973 }
2974 else if (empty)
2975 *dcd->mask.szMask = 0;
2976 SayFilter(WinWindowFromID(WinQueryWindow(hwnd, QW_PARENT),
2977 DIR_FILTER), &dcd->mask, TRUE);
2978 }
2979 break;
[2]2980
[551]2981 case IDM_SWITCH:
2982 if (mp2) {
2983 if (stricmp(dcd->directory, (CHAR *) mp2)) {
2984 DosEnterCritSec();
2985 strcpy(lastextractpath, (CHAR *) mp2);
2986 MakeValidDir(lastextractpath);
2987 DosExitCritSec();
2988 }
2989 strcpy(dcd->directory, (CHAR *) mp2);
2990 MakeValidDir(dcd->directory);
2991 WinSetWindowText(dcd->hwndExtract, dcd->directory);
2992 }
2993 break;
[2]2994
[551]2995 case IDM_WALKDIR:
2996 {
2997 CHAR newdir[CCHMAXPATH];
[2]2998
[551]2999 strcpy(newdir, dcd->directory);
3000 if (!WinDlgBox(HWND_DESKTOP, dcd->hwndParent, WalkExtractDlgProc,
3001 FM3ModHandle, WALK_FRAME,
3002 MPFROMP(newdir)) || !*newdir)
3003 break;
3004 if (stricmp(newdir, dcd->directory)) {
3005 strcpy(dcd->directory, newdir);
3006 if (stricmp(lastextractpath, newdir))
3007 strcpy(lastextractpath, newdir);
3008 WinSetWindowText(dcd->hwndExtract, dcd->directory);
3009 }
3010 }
3011 break;
[2]3012
[551]3013 case IDM_TEST:
3014 if (dcd->info->test)
3015 runemf2(SEPARATEKEEP | WINDOWED | MAXIMIZED,
[888]3016 hwnd, pszSrcFile, __LINE__, NULL, NULL,
[773]3017 "%s %s",dcd->info->test,
3018 BldQuotedFileName(szQuotedArcName, dcd->arcname));
[551]3019 break;
[2]3020
[551]3021 case IDM_REFRESH:
3022 case IDM_DELETE:
3023 case IDM_PRINT:
3024 case IDM_VIEW:
3025 case IDM_VIEWTEXT:
3026 case IDM_VIEWBINARY:
3027 case IDM_VIEWARCHIVE:
3028 case IDM_EDIT:
3029 case IDM_EDITTEXT:
3030 case IDM_EDITBINARY:
3031 case IDM_EXTRACT:
3032 case IDM_EXTRACTWDIRS:
3033 case IDM_FIND:
3034 case IDM_EXEC:
3035 case IDM_VIRUSSCAN:
[1068]3036 case IDM_OPENDEFAULT:
3037 case IDM_OPENSETTINGS:
[1069]3038 case IDM_MCIPLAY:
[551]3039 {
3040 LISTINFO *li;
[1077]3041# ifdef FORTIFY
3042 Fortify_EnterScope();
3043# endif
[551]3044 li = xmallocz(sizeof(LISTINFO), pszSrcFile, __LINE__);
3045 if (li) {
3046 li->type = SHORT1FROMMP(mp1);
3047 li->hwnd = hwnd;
3048 li->list = BuildArcList(hwnd);
3049 if (li->type == IDM_REFRESH) {
[2]3050
[551]3051 CHAR s[CCHMAXPATH], *p;
3052 INT x, y;
[2]3053
[551]3054 for (x = 0; li->list && li->list[x]; x++) {
[773]3055 BldFullPathName(s, dcd->workdir, li->list[x]);
[551]3056 if (IsFile(s) != 1) {
[1039]3057 free(li->list[x]);
[551]3058 li->list[x] = NULL;
3059 for (y = x; li->list[y]; y++)
3060 li->list[y] = li->list[y + 1];
3061 li->list =
3062 xrealloc(li->list, y * sizeof(CHAR *), pszSrcFile,
3063 __LINE__);
3064 x--;
3065 }
3066 else {
3067 p = xstrdup(s, pszSrcFile, __LINE__);
3068 if (p) {
[1039]3069 free(li->list[x]);
[551]3070 li->list[x] = p;
3071 }
3072 }
3073 } // for
3074 }
3075 strcpy(li->arcname, dcd->arcname);
3076 li->info = dcd->info;
3077 {
3078 PARCITEM pai;
[2]3079
[551]3080 if (SHORT1FROMMP(mp1) != IDM_EXEC)
3081 pai = (PARCITEM) CurrentRecord(hwnd);
3082 else
3083 pai = (PARCITEM) WinSendMsg(hwnd, CM_QUERYRECORDEMPHASIS,
3084 MPFROMLONG(CMA_FIRST),
3085 MPFROMSHORT(CRA_CURSORED));
3086 if (pai && (INT) pai != -1)
[730]3087 strcpy(li->runfile, pai->pszFileName);
[551]3088 else
3089 strcpy(li->runfile, li->list[0]);
3090 }
3091 switch (SHORT1FROMMP(mp1)) {
3092 case IDM_VIEW:
3093 case IDM_VIEWTEXT:
3094 case IDM_VIEWBINARY:
3095 case IDM_VIEWARCHIVE:
3096 case IDM_EDIT:
3097 case IDM_EDITTEXT:
3098 case IDM_EDITBINARY:
3099 case IDM_EXEC:
3100 case IDM_PRINT:
3101 case IDM_VIRUSSCAN:
[1068]3102 case IDM_OPENDEFAULT:
[1077]3103 case IDM_OPENSETTINGS:
3104 case IDM_MCIPLAY:
[551]3105 strcpy(li->targetpath, dcd->workdir);
3106 break;
3107 default:
3108 strcpy(li->targetpath, dcd->directory);
3109 break;
3110 }
3111 if (li->list) {
3112 if (!PostMsg(dcd->hwndObject, UM_ACTION, MPFROMP(li), MPVOID)) {
3113 Runtime_Error(pszSrcFile, __LINE__, "post");
3114 FreeListInfo(li);
3115 }
3116 else if (fUnHilite && SHORT1FROMMP(mp1) != IDM_EDIT)
[672]3117 UnHilite(hwnd, TRUE, &dcd->lastselection, 0);
[551]3118 }
[1077]3119 else {
[1039]3120 free(li);
[1077]3121 }
[551]3122 }
[1077]3123# ifdef FORTIFY
3124 Fortify_LeaveScope();
3125# endif
[551]3126 }
3127 break;
[2]3128 }
[551]3129 }
3130 return 0;
[2]3131
[551]3132 case WM_CONTROL:
3133 DosError(FERR_DISABLEHARDERR);
3134 if (dcd) {
3135 switch (SHORT2FROMMP(mp1)) {
3136 case CN_BEGINEDIT:
3137 PostMsg(hwnd, CM_CLOSEEDIT, MPVOID, MPVOID);
3138 break;
[2]3139
[551]3140 case CN_ENDEDIT:
3141 if (!((PCNREDITDATA) mp2)->pRecord) {
[2]3142
[551]3143 PFIELDINFO pfi = ((PCNREDITDATA) mp2)->pFieldInfo;
3144 USHORT cmd = 0;
[2]3145
[739]3146 if (!pfi || pfi->offStruct == FIELDOFFSET(ARCITEM, pszDisplayName))
[551]3147 cmd = IDM_SORTSMARTNAME;
3148 else if (pfi->offStruct == FIELDOFFSET(ARCITEM, cbFile))
3149 cmd = IDM_SORTSIZE;
3150 else if (pfi->offStruct == FIELDOFFSET(ARCITEM, cbComp))
3151 cmd = IDM_SORTEASIZE;
3152 else if (pfi->offStruct == FIELDOFFSET(ARCITEM, date))
3153 cmd = IDM_SORTLWDATE;
3154 else if (pfi->offStruct == FIELDOFFSET(ARCITEM, time))
3155 cmd = IDM_SORTLWDATE;
3156 if (cmd)
3157 PostMsg(hwnd, WM_COMMAND, MPFROM2SHORT(cmd, 0), MPVOID);
3158 }
3159 break;
[2]3160
[551]3161 case CN_DROPHELP:
3162 saymsg(MB_ENTER, hwnd,
3163 GetPString(IDS_DROPHELPHDRTEXT),
3164 GetPString(IDS_ARCCNRDROPHELPTEXT), dcd->arcname);
3165 return 0;
[2]3166
[551]3167 case CN_DRAGLEAVE:
3168 if (mp2) {
[2]3169
[551]3170 PDRAGINFO pDInfo;
[2]3171
[551]3172 pDInfo = ((PCNRDRAGINFO) mp2)->pDragInfo;
[562]3173 DrgAccessDraginfo(pDInfo); /* Access DRAGINFO */
3174 DrgFreeDraginfo(pDInfo); /* Free DRAGINFO */
[551]3175 }
3176 return 0;
[2]3177
[551]3178 case CN_DRAGAFTER:
3179 case CN_DRAGOVER:
3180 if (mp2) {
[2]3181
[773]3182 PDRAGITEM pDItem; /* Pointer to DRAGITEM */
3183 PDRAGINFO pDInfo; /* Pointer to DRAGINFO */
[551]3184 PARCITEM pci;
[2]3185
[551]3186 pci = (PARCITEM) ((PCNRDRAGINFO) mp2)->pRecord;
3187 if (SHORT1FROMMP(mp1) == CN_DRAGAFTER)
3188 pci = NULL;
3189 pDInfo = ((PCNRDRAGINFO) mp2)->pDragInfo;
[562]3190 DrgAccessDraginfo(pDInfo); /* Access DRAGINFO */
[551]3191 if (*dcd->arcname) {
3192 if ((driveflags[toupper(*dcd->arcname) - 'A'] &
3193 DRIVE_NOTWRITEABLE) || !dcd->info || !dcd->info->create) {
3194 DrgFreeDraginfo(pDInfo);
3195 return MRFROM2SHORT(DOR_NEVERDROP, 0);
3196 }
3197 }
3198 if (pci) {
3199 DrgFreeDraginfo(pDInfo);
3200 return MRFROM2SHORT(DOR_NODROP, 0);
3201 }
[562]3202 pDItem = DrgQueryDragitemPtr(pDInfo, /* Access DRAGITEM */
3203 0); /* Index to DRAGITEM */
[551]3204 if (DrgVerifyRMF(pDItem, /* Check valid rendering */
[562]3205 DRM_OS2FILE, /* mechanisms and data */
[551]3206 NULL) && !(pDItem->fsControl & DC_PREPARE)) {
[773]3207 DrgFreeDraginfo(pDInfo); /* Free DRAGINFO */
[562]3208 return MRFROM2SHORT(DOR_DROP, /* Return okay to drop */
3209 fCopyDefault ? DO_COPY : DO_MOVE);
[551]3210 }
[562]3211 DrgFreeDraginfo(pDInfo); /* Free DRAGINFO */
[551]3212 }
[562]3213 return (MRFROM2SHORT(DOR_NEVERDROP, 0)); /* Drop not valid */
[2]3214
[551]3215 case CN_INITDRAG:
3216 if (mp2) {
[2]3217
[551]3218 BOOL wasemphasized = FALSE;
3219 PCNRDRAGINIT pcd = (PCNRDRAGINIT) mp2;
3220 PARCITEM pci;
[2]3221
[551]3222 if (pcd) {
3223 pci = (PARCITEM) pcd->pRecord;
3224 if (pci) {
3225 if (pci->rc.flRecordAttr & CRA_SELECTED)
3226 wasemphasized = TRUE;
3227 if (!ParentIsDesktop(hwnd, dcd->hwndParent) &&
3228 fSplitStatus && hwndStatus2)
3229 WinSetWindowText(hwndStatus2, GetPString(IDS_DRAGARCMEMTEXT));
3230 if (DoFileDrag(hwnd,
3231 dcd->hwndObject,
3232 mp2, dcd->arcname, NULL, TRUE)) {
[672]3233 if ((fUnHilite && wasemphasized) || dcd->ulItemsToUnHilite)
3234 UnHilite(hwnd, TRUE, &dcd->lastselection, dcd->ulItemsToUnHilite);
[551]3235 }
3236 if (!ParentIsDesktop(hwnd, dcd->hwndParent) &&
3237 fSplitStatus && hwndStatus2) {
3238 PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
3239 }
3240 }
3241 else {
3242 if (!ParentIsDesktop(hwnd, dcd->hwndParent) &&
3243 fSplitStatus && hwndStatus2)
3244 WinSetWindowText(hwndStatus2,
3245 GetPString(IDS_DRAGARCFILETEXT));
3246 DragOne(hwnd, dcd->hwndObject, dcd->arcname, FALSE);
3247 if (!ParentIsDesktop(hwnd, dcd->hwndParent) &&
3248 fSplitStatus && hwndStatus2)
3249 PostMsg(hwnd, UM_RESCAN, MPVOID, MPVOID);
3250 }
3251 }
3252 }
3253 return 0;
[2]3254
[551]3255 case CN_DROP:
3256 if (mp2) {
[2]3257
[551]3258 LISTINFO *li;
[2]3259
[551]3260 DosBeep(500, 100); // fixme to know why beep?
3261 li = DoFileDrop(hwnd, dcd->arcname, FALSE, mp1, mp2);
[762]3262 DosBeep(50, 100); // fixme to know why beep?
3263 CheckPmDrgLimit(((PCNRDRAGINFO)mp2)->pDragInfo);
[551]3264 if (li) {
[562]3265 li->type = li->type == DO_MOVE ? IDM_ARCHIVEM : IDM_ARCHIVE;
[551]3266 strcpy(li->targetpath, dcd->arcname);
3267 if (!li->list ||
3268 !li->list[0] ||
3269 !PostMsg(dcd->hwndObject, UM_ACTION, MPFROMP(li), MPVOID))
3270 FreeListInfo(li);
3271 }
3272 }
3273 return 0;
[2]3274
[551]3275 case CN_CONTEXTMENU:
3276 {
3277 PARCITEM pci = (PARCITEM) mp2;
[2]3278
[551]3279 if (pci) {
3280 WinSendMsg(hwnd, CM_SETRECORDEMPHASIS, MPFROMP(pci),
3281 MPFROM2SHORT(TRUE, CRA_CURSORED));
3282 MarkAll(hwnd, FALSE, FALSE, TRUE);
[872]3283 dcd->hwndLastMenu = CheckMenu(hwnd, &ArcMenu, ARC_POPUP);
[551]3284 }
3285 else {
[872]3286 dcd->hwndLastMenu = CheckMenu(hwnd, &ArcCnrMenu, ARCCNR_POPUP);
[551]3287 if (dcd->hwndLastMenu && !dcd->cnremphasized) {
3288 WinSendMsg(hwnd, CM_SETRECORDEMPHASIS, MPVOID,
3289 MPFROM2SHORT(TRUE, CRA_SOURCE));
3290 dcd->cnremphasized = TRUE;
3291 }
3292 }
3293 if (dcd->hwndLastMenu) {
3294 if (dcd->hwndLastMenu == ArcCnrMenu) {
3295 if (dcd->flWindowAttr & CV_MINI)
3296 WinCheckMenuItem(dcd->hwndLastMenu, IDM_MINIICONS, TRUE);
3297 }
3298 WinCheckMenuItem(dcd->hwndLastMenu, IDM_FOLDERAFTEREXTRACT,
3299 fFolderAfterExtract);
3300 if (!PopupMenu(hwnd, hwnd, dcd->hwndLastMenu)) {
3301 if (dcd->cnremphasized) {
3302 WinSendMsg(hwnd, CM_SETRECORDEMPHASIS, MPVOID,
3303 MPFROM2SHORT(FALSE, CRA_SOURCE));
3304 dcd->cnremphasized = TRUE;
3305 }
3306 MarkAll(hwnd, TRUE, FALSE, TRUE);
3307 }
3308 }
3309 }
3310 break;
[2]3311
[551]3312 case CN_EMPHASIS:
3313 if (mp2) {
[2]3314
[551]3315 PNOTIFYRECORDEMPHASIS pre = mp2;
3316 PARCITEM pci;
3317 CHAR s[CCHMAXPATHCOMP + 91], tf[81], tb[81];
[2]3318
[562]3319 pci = (PARCITEM)(pre ? pre->pRecord : NULL);
[551]3320 if (!pci) {
3321 if (!ParentIsDesktop(hwnd, dcd->hwndParent)) {
3322 if (hwndStatus2)
3323 WinSetWindowText(hwndStatus2, NullStr);
3324 if (fMoreButtons)
3325 WinSetWindowText(hwndName, NullStr);
3326 }
3327 break;
3328 }
3329 if (pre->fEmphasisMask & CRA_SELECTED) {
3330 if (pci->rc.flRecordAttr & CRA_SELECTED) {
3331 dcd->selectedbytes += pci->cbFile;
3332 dcd->selectedfiles++;
3333 }
3334 else if (dcd->selectedfiles) {
3335 dcd->selectedbytes -= pci->cbFile;
3336 dcd->selectedfiles--;
3337 }
3338 commafmt(tf, sizeof(tf), dcd->selectedfiles);
3339 if (dcd->ullTotalBytes)
3340 CommaFmtULL(tb, sizeof(tb), dcd->selectedbytes, ' ');
3341 else
3342 *tb = 0;
3343 sprintf(s, "%s%s%s", tf, *tb ? " / " : NullStr, tb);
3344 WinSetDlgItemText(dcd->hwndClient, DIR_SELECTED, s);
3345 }
3346 else if (WinQueryActiveWindow(dcd->hwndParent) ==
3347 dcd->hwndFrame &&
3348 !ParentIsDesktop(hwnd, dcd->hwndParent)) {
3349 if (pre->fEmphasisMask & CRA_CURSORED) {
3350 if (pci->rc.flRecordAttr & CRA_CURSORED) {
3351 if (fSplitStatus && hwndStatus2) {
3352 if (dcd->ullTotalBytes)
3353 CommaFmtULL(tb, sizeof(tb), pci->cbFile, ' ');
3354 else
3355 *tb = 0;
3356 sprintf(s, "%s%s%s%s",
3357 *tb ? " " : NullStr,
[730]3358 tb, *tb ? " " : NullStr, pci->pszFileName);
[551]3359 WinSetWindowText(hwndStatus2, s);
3360 }
3361 if (fMoreButtons)
[730]3362 WinSetWindowText(hwndName, pci->pszFileName);
[551]3363 }
3364 }
3365 }
3366 }
3367 break;
[2]3368
[551]3369 case CN_ENTER:
3370 if (mp2) {
[2]3371
[551]3372 PARCITEM pci = (PARCITEM) ((PNOTIFYRECORDENTER) mp2)->pRecord;
[2]3373
[551]3374 if (pci) {
[2]3375
[551]3376 CHAR *s;
[2]3377
[551]3378 if ((pci->rc.flRecordAttr & CRA_INUSE) ||
3379 (pci->flags & (ARCFLAGS_REALDIR | ARCFLAGS_PSEUDODIR)))
3380 break;
[730]3381 s = xstrdup(pci->pszFileName, pszSrcFile, __LINE__);
[551]3382 if (s) {
3383 if (!PostMsg(dcd->hwndObject, UM_ENTER, MPFROMP(s), MPVOID)) {
3384 Runtime_Error(pszSrcFile, __LINE__, "post");
[1039]3385 free(s);
[551]3386 }
3387 }
3388 }
3389 }
3390 break;
[2]3391 }
[551]3392 }
3393 return 0;
[2]3394
[551]3395 case UM_FOLDUP:
3396 if (!PostMsg((HWND) 0, WM_QUIT, MPVOID, MPVOID))
3397 DosExit(EXIT_PROCESS, 1);
3398 return 0;
[2]3399
[551]3400 case UM_CLOSE:
3401 WinDestroyWindow(WinQueryWindow(WinQueryWindow(hwnd, QW_PARENT),
3402 QW_PARENT));
3403 return 0;
[2]3404
[551]3405 case WM_SAVEAPPLICATION:
3406 if (dcd && ParentIsDesktop(hwnd, dcd->hwndParent)) {
3407 SWP swp;
[2]3408
[551]3409 WinQueryWindowPos(dcd->hwndFrame, &swp);
3410 if (!(swp.fl & (SWP_HIDE | SWP_MINIMIZE | SWP_MAXIMIZE)))
3411 PrfWriteProfileData(fmprof, appname, "AV2SizePos", &swp, sizeof(swp));
3412 }
3413 break;
[2]3414
[551]3415 case WM_CLOSE:
3416 WinSendMsg(hwnd, WM_SAVEAPPLICATION, MPVOID, MPVOID);
3417 if (dcd)
3418 dcd->stopflag++;
3419 if (dcd && dcd->hwndObject) {
3420 if (!PostMsg(dcd->hwndObject, WM_CLOSE, MPVOID, MPVOID))
3421 WinSendMsg(dcd->hwndObject, WM_CLOSE, MPVOID, MPVOID);
3422 }
3423 // In case object window frees dcd
3424 dcd = WinQueryWindowPtr(hwnd, QWL_USER);
3425 if (!dcd ||
3426 (!dcd->dontclose &&
3427 !dcd->amextracted && ParentIsDesktop(hwnd, dcd->hwndParent))) {
3428 if (!PostMsg(hwnd, UM_FOLDUP, MPVOID, MPVOID))
3429 WinSendMsg(hwnd, UM_FOLDUP, MPVOID, MPVOID);
3430 }
3431 return 0;
3432
3433 case WM_DESTROY:
3434 if (ArcMenu)
3435 WinDestroyWindow(ArcMenu);
3436 if (ArcCnrMenu)
3437 WinDestroyWindow(ArcCnrMenu);
3438 ArcMenu = ArcCnrMenu = (HWND) 0;
[751]3439 EmptyArcCnr(hwnd);
[1120]3440# ifdef FORTIFY
3441 Fortify_LeaveScope();
3442# endif
[551]3443 break;
[2]3444 }
[705]3445 if (dcd && dcd->oldproc){
3446 return dcd->oldproc(hwnd, msg, mp1, mp2);
3447 }
3448 else
3449 return PFNWPCnr(hwnd, msg, mp1, mp2);
[2]3450}
3451
[942]3452MRESULT EXPENTRY ArcCnrMenuProc(HWND hwnd, ULONG msg, MPARAM mp1,
3453 MPARAM mp2)
3454{
3455 PFNWP oldMenuProc = WinQueryWindowPtr(hwnd, QWL_USER);
3456 static short sLastMenuitem;
3457
3458 switch (msg) {
3459 case WM_MOUSEMOVE: {
3460 if (fOtherHelp) {
[953]3461 RECTL rectl;
3462 SHORT i, sCurrentMenuitem;
3463 SHORT MenuItems = 10;
3464 SHORT asMenuIDs[10] = {IDM_VIEW,
3465 IDM_DELETE,
3466 IDM_EXEC,
3467 IDM_EXTRACT,
3468 IDM_TEST,
3469 IDM_VIRUSSCAN,
3470 IDM_RESCAN,
3471 IDM_WALKDIR,
3472 IDM_FILTER,
3473 0};
3474 char *szHelpString = NULL;
[942]3475
3476
[953]3477 for (i=0; i<MenuItems; i++) {
3478 sCurrentMenuitem = asMenuIDs[i];
3479 oldMenuProc(hwnd,MM_QUERYITEMRECT,
3480 MPFROM2SHORT(asMenuIDs[i], FALSE),
3481 &rectl);
[942]3482
[953]3483 if (MOUSEMSG(&msg)->x > rectl.xLeft &&
3484 MOUSEMSG(&msg)->x < rectl.xRight &&
3485 MOUSEMSG(&msg)->y > rectl.yBottom &&
3486 MOUSEMSG(&msg)->y < rectl.yTop)
3487 break;
3488 } // for
[942]3489
3490
[953]3491 switch (sCurrentMenuitem) {
3492 case 0:
3493 break;
3494 case IDM_VIEW:
3495 szHelpString = GetPString(IDS_ARCCNRVIEWMENUHELP);
3496 break;
3497 case IDM_DELETE:
3498 szHelpString = GetPString(IDS_ARCCNRDELETEMENUHELP);
3499 break;
3500 case IDM_EXEC:
3501 szHelpString = GetPString(IDS_ARCCNREXECMENUHELP);
3502 break;
3503 case IDM_EXTRACT:
3504 szHelpString = GetPString(IDS_ARCCNREXTRACTMENUHELP);
3505 break;
3506 case IDM_TEST:
3507 szHelpString = GetPString(IDS_ARCCNRTESTMENUHELP);
3508 break;
3509 case IDM_VIRUSSCAN:
3510 szHelpString = GetPString(IDS_ARCCNRVIRUSMENUHELP);
3511 break;
3512 case IDM_RESCAN:
3513 szHelpString = GetPString(IDS_ARCCNRRESCANMENUHELP);
3514 break;
3515 case IDM_WALKDIR:
3516 szHelpString = GetPString(IDS_ARCCNRWALKDIRMENUHELP);
3517 break;
3518 case IDM_FILTER:
3519 szHelpString = GetPString(IDS_ARCCNRFILTERMENUHELP);
3520 break;
3521 default:
3522 break;
3523 }
[942]3524
[953]3525 if (sLastMenuitem != sCurrentMenuitem && szHelpString) {
3526 sLastMenuitem = sCurrentMenuitem;
3527 MakeBubble(hwnd, TRUE, szHelpString);
3528 }
3529 else if (hwndBubble && !sCurrentMenuitem){
3530 sLastMenuitem = sCurrentMenuitem;
3531 WinDestroyWindow(hwndBubble);
3532 }
[942]3533 }
3534 }
3535 }
3536 return oldMenuProc(hwnd, msg, mp1, mp2);
3537}
3538
[551]3539HWND StartArcCnr(HWND hwndParent, HWND hwndCaller, CHAR * arcname, INT flags,
3540 ARC_TYPE * sinfo)
[212]3541{
[2]3542 /*
3543 * bitmapped flags:
3544 * 1 = am extracted from another archive
3545 * 4 = don't kill proc on close
3546 */
3547
[551]3548 HWND hwndFrame = (HWND) 0, hwndClient;
3549 ULONG FrameFlags = FCF_TITLEBAR | FCF_SYSMENU |
3550 FCF_SIZEBORDER | FCF_MINMAX | FCF_ICON | FCF_NOBYTEALIGN | FCF_ACCELTABLE;
3551 USHORT id;
3552 DIRCNRDATA *dcd;
3553 ARC_TYPE *info = sinfo;
3554 CHAR title[MAXNAMEL + 1] = "AV/2 - ";
3555 CHAR fullname[CCHMAXPATH + 8], *p, temp;
[2]3556 static USHORT idinc = 0;
3557
[423]3558 if (!idinc)
[2]3559 idinc = (rand() % 256);
[551]3560 if (ParentIsDesktop(hwndParent, hwndParent))
[2]3561 FrameFlags |= (FCF_TASKLIST | FCF_MENU);
[423]3562 if (arcname) {
[2]3563 DosError(FERR_DISABLEHARDERR);
[423]3564 if (DosQueryPathInfo(arcname,
[551]3565 FIL_QUERYFULLNAME, fullname, sizeof(fullname)))
3566 strcpy(fullname, arcname);
[2]3567 p = fullname;
[551]3568 while (*p) {
[423]3569 if (*p == '/')
[551]3570 *p = '\\';
[2]3571 p++;
3572 }
[423]3573 if (!info)
[551]3574 info = find_type(fullname, arcsighead);
[423]3575 if (!info)
[2]3576 return hwndFrame;
[551]3577 if (strlen(title) + strlen(fullname) > MAXNAMEL) {
3578 p = title + strlen(title);
3579 strncpy(p, fullname, MAXNAMEL / 2 - 5);
3580 strcpy(p + MAXNAMEL / 2 - 5, "...");
3581 strcat(title, fullname + strlen(fullname) - (MAXNAMEL / 2 - 5));
[460]3582 }
[551]3583 else {
3584 strcat(title, fullname);
[460]3585 }
[2]3586 hwndFrame = WinCreateStdWindow(hwndParent,
[551]3587 WS_VISIBLE,
3588 &FrameFlags,
[593]3589 WC_ARCCONTAINER,
[551]3590 title,
3591 WS_VISIBLE | fwsAnimate,
3592 FM3ModHandle, ARC_FRAME, &hwndClient);
[423]3593 if (hwndFrame && hwndClient) {
[2]3594 id = ARC_FRAME + idinc++;
[423]3595 if (idinc > 512)
[551]3596 idinc = 0;
3597 WinSetWindowUShort(hwndFrame, QWS_ID, id);
[1063]3598# ifdef FORTIFY
3599 Fortify_EnterScope();
[1077]3600# endif
[551]3601 dcd = xmallocz(sizeof(DIRCNRDATA), pszSrcFile, __LINE__);
[358]3602 if (!dcd) {
[551]3603 PostMsg(hwndClient, WM_CLOSE, MPVOID, MPVOID);
3604 hwndFrame = (HWND) 0;
[358]3605 }
3606 else {
[551]3607 dcd->size = sizeof(DIRCNRDATA);
3608 dcd->id = id;
3609 dcd->type = ARC_FRAME;
[1082]3610 if (!pTmpDir)
[1104]3611 strcpy(dcd->workdir, pFM2SaveDirectory);
[1082]3612 MakeTempName(dcd->workdir, ArcTempRoot, 2);
3613 /*if (dcd->workdir[strlen(dcd->workdir) - 1] != '\\')
[1077]3614 strcat(dcd->workdir, "\\");
3615 sprintf(dcd->workdir + strlen(dcd->workdir), "%s.%03x",
3616 ArcTempRoot, (clock() & 4095));
3617 else
3618 sprintf(dcd->workdir, "%s.%03x",
[1082]3619 ArcTempRoot, (clock() & 4095));*/
[551]3620 strcpy(dcd->arcname, fullname);
3621 if (*extractpath) {
3622 if (!strcmp(extractpath, "*")) {
3623 p = strrchr(fullname, '\\');
3624 if (p) {
3625 if (p < fullname + 3)
3626 p++;
3627 temp = *p;
3628 *p = 0;
3629 strcpy(dcd->directory, fullname);
3630 *p = temp;
3631 }
3632 }
3633 else
3634 strcpy(dcd->directory, extractpath);
3635 }
3636 if (!*dcd->directory && *lastextractpath) {
3637 DosEnterCritSec();
3638 strcpy(dcd->directory, lastextractpath);
3639 DosExitCritSec();
3640 }
3641 if (!*dcd->directory) {
3642 if (!ParentIsDesktop(hwndParent, hwndParent))
3643 TopWindowName(hwndParent, hwndCaller, dcd->directory);
3644 if (!*dcd->directory) {
3645 p = strrchr(fullname, '\\');
3646 if (p) {
3647 if (p < fullname + 3)
3648 p++;
3649 *p = 0;
3650 strcpy(dcd->directory, fullname);
3651 }
3652 }
3653 }
3654 if (!*dcd->directory ||
3655 IsFile(dcd->directory) ||
3656 (isalpha(*dcd->directory) &&
3657 (driveflags[toupper(*dcd->directory) - 'A'] &
3658 DRIVE_NOTWRITEABLE)))
[1104]3659 strcpy(dcd->directory, pFM2SaveDirectory);
[562]3660 dcd->hwndParent = hwndParent ? hwndParent : HWND_DESKTOP;
[551]3661 dcd->hwndFrame = hwndFrame;
3662 dcd->hwndClient = hwndClient;
[562]3663 dcd->amextracted = (flags & 1) != 0;
3664 dcd->dontclose = (flags & 4) != 0;
[551]3665 dcd->info = info;
3666 dcd->sortFlags = DefArcSortFlags;
3667 {
3668 PFNWP oldproc;
[2]3669
[551]3670 oldproc = WinSubclassWindow(hwndFrame, (PFNWP) ArcFrameWndProc);
3671 WinSetWindowPtr(hwndFrame, QWL_USER, (PVOID) oldproc);
[358]3672 }
[551]3673 dcd->hwndCnr = WinCreateWindow(hwndClient,
3674 WC_CONTAINER,
3675 NULL,
3676 CCS_AUTOPOSITION | CCS_MINIICONS |
3677 CCS_MINIRECORDCORE | ulCnrType |
3678 WS_VISIBLE,
3679 0,
3680 0,
3681 0,
3682 0,
3683 hwndClient,
3684 HWND_TOP, (ULONG) ARC_CNR, NULL, NULL);
3685 if (!dcd->hwndCnr) {
3686 Win_Error2(hwndClient, hwndClient, pszSrcFile, __LINE__,
3687 IDS_WINCREATEWINDOW);
3688 PostMsg(hwndClient, WM_CLOSE, MPVOID, MPVOID);
[1077]3689 free(dcd);
[551]3690 hwndFrame = (HWND) 0;
3691 }
[358]3692 else {
[551]3693 WinSetWindowPtr(dcd->hwndCnr, QWL_USER, (PVOID) dcd);
3694 dcd->oldproc = WinSubclassWindow(dcd->hwndCnr,
3695 (PFNWP) ArcCnrWndProc);
3696 {
3697 USHORT ids[] = { DIR_TOTALS, DIR_SELECTED, DIR_VIEW, DIR_SORT,
3698 DIR_FILTER, DIR_FOLDERICON, 0
3699 };
[2]3700
[551]3701 CommonCreateTextChildren(dcd->hwndClient,
[593]3702 WC_ARCSTATUS, ids);
[551]3703 }
3704 WinEnableWindow(WinWindowFromID(dcd->hwndClient, DIR_VIEW), FALSE);
3705 dcd->hwndExtract = WinCreateWindow(dcd->hwndClient,
3706 WC_ENTRYFIELD,
3707 NULL,
3708 ES_AUTOSCROLL,
3709 0,
3710 0,
3711 0,
3712 0,
3713 dcd->hwndClient,
3714 HWND_TOP,
3715 ARC_EXTRACTDIR, NULL, NULL);
3716 WinSendMsg(dcd->hwndExtract,
3717 EM_SETTEXTLIMIT, MPFROM2SHORT(CCHMAXPATH, 0), MPVOID);
3718 WinSetWindowText(dcd->hwndExtract, dcd->directory);
3719 if (!PostMsg(dcd->hwndCnr, UM_SETUP, MPVOID, MPVOID))
3720 WinSendMsg(dcd->hwndCnr, UM_SETUP, MPVOID, MPVOID);
[953]3721 if (FrameFlags & FCF_MENU) {
3722 PFNWP oldmenuproc;
3723 HWND hwndMenu = WinWindowFromID(hwndFrame, FID_MENU);
[942]3724
3725 oldmenuproc = WinSubclassWindow(hwndMenu, (PFNWP) ArcCnrMenuProc);
3726 WinSetWindowPtr(hwndMenu, QWL_USER, (PVOID) oldmenuproc);
[551]3727 if (!fToolbar) {
[2]3728
[551]3729 if (hwndMenu) {
3730 WinSendMsg(hwndMenu, MM_DELETEITEM,
3731 MPFROM2SHORT(IDM_VIEW, FALSE), MPVOID);
3732 WinSendMsg(hwndMenu, MM_DELETEITEM,
3733 MPFROM2SHORT(IDM_EXEC, FALSE), MPVOID);
3734 WinSendMsg(hwndMenu, MM_DELETEITEM,
3735 MPFROM2SHORT(IDM_RESCAN, FALSE), MPVOID);
3736 WinSendMsg(hwndMenu, MM_DELETEITEM,
3737 MPFROM2SHORT(IDM_DELETE, FALSE), MPVOID);
3738 WinSendMsg(hwndMenu, MM_DELETEITEM,
3739 MPFROM2SHORT(IDM_EXTRACT, FALSE), MPVOID);
3740 WinSendMsg(hwndMenu, MM_DELETEITEM,
3741 MPFROM2SHORT(IDM_TEST, FALSE), MPVOID);
3742 WinSendMsg(hwndMenu, MM_DELETEITEM,
3743 MPFROM2SHORT(IDM_VIRUSSCAN, FALSE), MPVOID);
3744 WinSendMsg(hwndMenu, MM_DELETEITEM,
3745 MPFROM2SHORT(IDM_WALKDIR, FALSE), MPVOID);
3746 WinSendMsg(hwndMenu, MM_DELETEITEM,
3747 MPFROM2SHORT(IDM_FILTER, FALSE), MPVOID);
3748 }
3749 }
3750 }
3751 if (FrameFlags & FCF_TASKLIST) {
[2]3752
[551]3753 SWP swp, swpD;
3754 ULONG size = sizeof(swp);
3755 LONG cxScreen, cyScreen;
[2]3756
[551]3757 WinQueryTaskSizePos(WinQueryAnchorBlock(hwndFrame), 0, &swp);
3758 if (PrfQueryProfileData(fmprof,
3759 appname, "AV2SizePos", &swpD, &size)) {
3760 cxScreen = WinQuerySysValue(HWND_DESKTOP, SV_CXSCREEN);
3761 cyScreen = WinQuerySysValue(HWND_DESKTOP, SV_CYSCREEN);
3762 if (swp.x + swpD.cx > cxScreen)
3763 swp.x = cxScreen - swpD.cx;
3764 if (swp.y + swpD.cy > cyScreen)
3765 swp.y = cyScreen - swpD.cy;
3766 swp.cx = swpD.cx;
3767 swp.cy = swpD.cy;
3768 }
3769 WinSetWindowPos(hwndFrame,
3770 HWND_TOP,
3771 swp.x,
3772 swp.y,
3773 swp.cx,
3774 swp.cy,
3775 SWP_SIZE | SWP_MOVE | SWP_SHOW | SWP_ZORDER |
3776 SWP_ACTIVATE);
3777 }
3778 }
[2]3779 }
[1077]3780# ifdef FORTIFY
3781 Fortify_LeaveScope();
3782# endif
[2]3783 }
3784 }
3785 return hwndFrame;
3786}
[793]3787
3788#pragma alloc_text(ARCCNRS,ArcCnrWndProc,ArcObjWndProc,ArcClientWndProc,BldQuotedFullPathName)
3789#pragma alloc_text(ARCCNRS,ArcTextProc,FillArcCnr,ArcFilter,BldQuotedFileName)
3790#pragma alloc_text(ARCCNRS,ArcSort,ArcFrameWndProc,IsArcThere,ArcErrProc)
3791#pragma alloc_text(STARTUP,StartArcCnr)
Note: See TracBrowser for help on using the repository browser.