source: trunk/dll/objcnr.c@ 1402

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

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

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 12.1 KB
RevLine 
[159]1
2/***********************************************************************
3
4 $Id: objcnr.c 1402 2009-03-14 17:17:59Z gyoung $
5
6 Object containers
7
8 Copyright (c) 1993-98 M. Kimes
[1394]9 Copyright (c) 2005, 2009 Steven H. Levine
[159]10
11 24 May 05 SHL Rework for CNRITEM.szSubject
[349]12 13 Jul 06 SHL Use Runtime_Error
[488]13 01 Sep 06 SHL Do not complain for normal cancel
[517]14 19 Oct 06 SHL Correct . and .. detect
[531]15 03 Nov 06 SHL Renames
[574]16 22 Mar 07 GKY Use QWL_USER
[751]17 01 Aug 07 SHL Rework to sync with CNRITEM mods
[756]18 03 Aug 07 GKY Enlarged and made setable everywhere Findbuf (speed file loading)
[775]19 06 Aug 07 GKY Reduce DosSleep times (ticket 148)
[783]20 13 Aug 07 SHL Avoid realloc - not needed; sanitize code
21 13 Aug 07 SHL Move #pragma alloc_text to end for OpenWatcom compat
[787]22 14 Aug 07 SHL Revert ProcessDir DosSleep to 0
[985]23 29 Feb 08 GKY Use xfree where appropriate
[1335]24 10 Dec 08 SHL Integrate exception handler support
[1402]25 08 Mar 09 GKY Additional strings move to PCSZs
[159]26
27***********************************************************************/
28
[907]29#include <stdlib.h>
30#include <string.h>
31#include <ctype.h>
[1335]32// #include <process.h> // _beginthread
[907]33
[2]34#define INCL_DOS
35#define INCL_WIN
[783]36#define INCL_DOSERRORS
[841]37#define INCL_LONGLONG
[2]38
[1188]39#include "fm3dll.h"
[1225]40#include "fm3dll2.h" // #define's for UM_*, control id's, etc.
[1211]41#include "draglist.h" // Data declaration(s)
42#include "info.h" // Data declaration(s)
43#include "init.h" // Data declaration(s)
44#include "notebook.h" // Data declaration(s)
45#include "newview.h" // Data declarations
[2]46#include "fm3dlg.h"
47#include "fm3str.h"
[1163]48#include "errutil.h" // Dos_Error...
49#include "strutil.h" // GetPString
50#include "objcnr.h"
[1188]51#include "notify.h" // Notify
52#include "wrappers.h" // xDosFindNext
[1163]53#include "select.h" // ExpandAll
[1188]54#include "valid.h" // IsRoot
55#include "misc.h" // PostMsg
[1017]56#include "fortify.h"
[1335]57#include "excputil.h" // xbeginthread
[1017]58
[551]59typedef struct
60{
[2]61 CHAR *filename;
[551]62 HWND hwndCnr;
[2]63 CHAR *stopflag;
[551]64}
65DIRSIZE;
[2]66
[551]67typedef struct
68{
[2]69 CHAR *dirname;
[551]70 CHAR stopflag;
71 BOOL dying;
72 BOOL working;
73}
74TEMP;
[2]75
[349]76#pragma data_seg(DATA1)
[2]77
[349]78static PSZ pszSrcFile = __FILE__;
[2]79
[349]80static HWND objcnrwnd;
[2]81
[783]82static VOID ProcessDir(HWND hwndCnr,
[1335]83 CHAR *filename,
84 PCNRITEM pciParent,
85 CHAR *stopflag)
[349]86{
[551]87 CHAR maskstr[CCHMAXPATH], *endpath, *p;
[783]88 ULONG ulFindCnt, ulFindMax;
89 ULONG ulBufBytes;
[551]90 HDIR hdir;
[841]91 PFILEFINDBUF3L pffbArray;
[551]92 APIRET rc;
93 RECORDINSERT ri;
94 PCNRITEM pciP;
[783]95 HPOINTER hptr;
[2]96
[841]97 ulBufBytes = sizeof(FILEFINDBUF3L) * FilesToGet;
[783]98 pffbArray = xmalloc(ulBufBytes, pszSrcFile, __LINE__);
99 if (!pffbArray)
[1163]100 return; // Error already reported
[551]101 strcpy(maskstr, filename);
102 if (maskstr[strlen(maskstr) - 1] != '\\')
103 strcat(maskstr, "\\");
[2]104 endpath = &maskstr[strlen(maskstr)];
[551]105 strcat(maskstr, "*");
[2]106 hdir = HDIR_CREATE;
[783]107 ulFindCnt = 1;
[838]108 rc = xDosFindFirst(filename, &hdir,
[1335]109 FILE_NORMAL | FILE_READONLY | FILE_ARCHIVED |
110 FILE_SYSTEM | FILE_HIDDEN | MUST_HAVE_DIRECTORY,
111 pffbArray, ulBufBytes, &ulFindCnt, FIL_STANDARDL);
[551]112 if (!rc)
[2]113 DosFindClose(hdir);
[783]114 // work around furshluginer FAT root bug
115 else if (IsRoot(filename))
116 rc = 0;
[2]117
[783]118 if ((!rc && (pffbArray->attrFile & FILE_DIRECTORY))) {
[731]119 pciP = WinSendMsg(hwndCnr,
[1335]120 CM_ALLOCRECORD,
121 MPFROMLONG(EXTRA_RECORD_BYTES),
122 MPFROMLONG(1));
[551]123 if (!pciP) {
[1402]124 Win_Error(hwndCnr, HWND_DESKTOP, pszSrcFile, __LINE__, PCSZ_CM_ALLOCRECORD);
[1039]125 free(pffbArray);
[2]126 return;
127 }
[730]128 pciP->pszFileName = xstrdup(filename, pszSrcFile, __LINE__);
[751]129 pciP->pszDispAttr = NullStr;
130 pciP->pszSubject = NullStr;
[762]131 pciP->pszLongName = NullStr;
[551]132 if (strlen(filename) < 4)
[751]133 pciP->pszDisplayName = pciP->pszFileName;
[2]134 else {
[730]135 p = strrchr(pciP->pszFileName, '\\');
[551]136 if (!p)
[1335]137 pciP->pszDisplayName = pciP->pszFileName;
[551]138 else if (*(p + 1))
[1335]139 p++;
[751]140 pciP->pszDisplayName = p;
[2]141 }
[751]142 pciP->rc.pszIcon = pciP->pszDisplayName;
[551]143 if (fForceUpper)
[730]144 strupr(pciP->pszFileName);
[551]145 else if (fForceLower)
[730]146 strlwr(pciP->pszFileName);
[2]147 pciP->rc.flRecordAttr |= CRA_RECORDREADONLY;
148 }
149 else {
[1039]150 free(pffbArray);
[783]151 Dos_Error(MB_ENTER, rc, HWND_DESKTOP, pszSrcFile, __LINE__,
[1335]152 GetPString(IDS_CANTFINDDIRTEXT), filename);
[2]153 return;
154 }
155
[783]156 hptr = WinLoadFileIcon(pciP->pszFileName, FALSE);
157 if (hptr)
158 pciP->rc.hptrIcon = hptr;
159
[1163]160 if (!pciP->rc.hptrIcon || pciP->rc.hptrIcon == hptrFile) /* OS/2 bug bug bug bug */
[2]161 pciP->rc.hptrIcon = hptrDir;
[783]162
[551]163 memset(&ri, 0, sizeof(RECORDINSERT));
164 ri.cb = sizeof(RECORDINSERT);
165 ri.pRecordOrder = (PRECORDCORE) CMA_END;
166 ri.pRecordParent = (PRECORDCORE) pciParent;
167 ri.zOrder = (USHORT) CMA_TOP;
[771]168 ri.cRecordsInsert = 1;
[551]169 ri.fInvalidateRecord = TRUE;
170 if (!WinSendMsg(hwndCnr, CM_INSERTRECORD, MPFROMP(pciP), MPFROMP(&ri))) {
[1039]171 free(pffbArray);
[2]172 return;
173 }
174 hdir = HDIR_CREATE;
[551]175 if (!isalpha(*maskstr) || maskstr[1] != ':' || maskstr[2] != '\\' ||
176 ((driveflags[toupper(*maskstr) - 'A'] & DRIVE_REMOTE) && fRemoteBug))
[783]177 ulFindMax = 1;
[2]178 else
[783]179 ulFindMax = FilesToGet;
180 ulFindCnt = ulFindMax;
[838]181 rc = xDosFindFirst(maskstr, &hdir,
[1335]182 FILE_NORMAL | FILE_READONLY | FILE_ARCHIVED |
183 FILE_SYSTEM | FILE_HIDDEN | MUST_HAVE_DIRECTORY,
184 pffbArray, ulBufBytes, &ulFindCnt, FIL_STANDARDL);
[551]185 if (!rc) {
[841]186 PFILEFINDBUF3L pffbFile;
[551]187 ULONG x;
[2]188
[551]189 while (!rc) {
[783]190 pffbFile = pffbArray;
191 for (x = 0; x < ulFindCnt; x++) {
[1335]192 if (*stopflag)
193 break;
194 if ((pffbFile->attrFile & FILE_DIRECTORY) &&
195 // Skip . and ..
196 (pffbFile->achName[0] != '.' ||
197 (pffbFile->achName[1] &&
198 (pffbFile->achName[1] != '.' || pffbFile->achName[2])))) {
199 strcpy(endpath, pffbFile->achName);
200 ProcessDir(hwndCnr, maskstr, pciP, stopflag);
201 }
202 if (!pffbFile->oNextEntryOffset)
203 break;
204 pffbFile = (PFILEFINDBUF3L)((PBYTE)pffbFile + pffbFile->oNextEntryOffset);
[783]205 } // for
[1163]206 DosSleep(0); // Let's others at same priority get some work done
[551]207 if (*stopflag)
[1335]208 break;
[783]209 ulFindCnt = ulFindMax;
[850]210 rc = xDosFindNext(hdir, pffbArray, ulBufBytes, &ulFindCnt, FIL_STANDARDL);
[783]211 } // while
[2]212 DosFindClose(hdir);
213 }
[783]214
215 if (rc && rc != ERROR_NO_MORE_FILES) {
216 Dos_Error(MB_ENTER, rc, HWND_DESKTOP, pszSrcFile, __LINE__,
[1335]217 GetPString(IDS_CANTFINDDIRTEXT), filename);
[783]218 }
219
[1039]220 free(pffbArray);
[551]221 WinSendMsg(hwndCnr, CM_INVALIDATERECORD, MPFROMP(&pciP),
[1335]222 MPFROM2SHORT(1, 0));
[2]223}
224
[551]225static VOID FillCnrsThread(VOID * args)
[349]226{
[551]227 HAB hab;
228 HMQ hmq;
[783]229 DIRSIZE *dirsize = (DIRSIZE *)args;
[2]230
[1038]231# ifdef FORTIFY
232 Fortify_EnterScope();
[1063]233# endif
[783]234 if (!dirsize) {
[1398]235 Runtime_Error(pszSrcFile, __LINE__, NULL);
[2]236 return;
[783]237 }
[2]238
239 DosError(FERR_DISABLEHARDERR);
240
241 hab = WinInitialize(0);
[551]242 if (hab) {
243 hmq = WinCreateMsgQueue(hab, 0);
244 if (hmq) {
245 WinCancelShutdown(hmq, TRUE);
246 ProcessDir(dirsize->hwndCnr, dirsize->filename, (PCNRITEM) NULL,
[1335]247 dirsize->stopflag);
[2]248 DosPostEventSem(CompactSem);
249 WinDestroyMsgQueue(hmq);
250 }
251 WinTerminate(hab);
252 }
[551]253 PostMsg(WinQueryWindow(dirsize->hwndCnr, QW_PARENT), UM_CONTAINER_FILLED,
[1335]254 MPVOID, MPVOID);
[1039]255 free(dirsize);
[1017]256# ifdef FORTIFY
257 Fortify_LeaveScope();
[1063]258# endif
[2]259}
260
[551]261MRESULT EXPENTRY ObjCnrDlgProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
[349]262{
[2]263 TEMP *data;
264
[551]265 switch (msg) {
266 case WM_INITDLG:
267 if (objcnrwnd) {
268 Runtime_Error(pszSrcFile, __LINE__, "objcnrwnd set");
269 WinSetWindowPos(objcnrwnd, HWND_TOP, 0, 0, 0, 0,
[1335]270 SWP_RESTORE | SWP_SHOW | SWP_ACTIVATE | SWP_ZORDER);
[551]271 WinDismissDlg(hwnd, 0);
272 break;
273 }
274 if (!mp2) {
275 Runtime_Error(pszSrcFile, __LINE__, "mp2 NULL");
276 WinDismissDlg(hwnd, 0);
277 break;
278 }
279 objcnrwnd = hwnd;
280 data = xmallocz(sizeof(TEMP), pszSrcFile, __LINE__);
281 if (!data) {
282 WinDismissDlg(hwnd, 0);
283 break;
284 }
[1009]285 data->dirname = (CHAR *)mp2;
[574]286 WinSetWindowPtr(hwnd, QWL_USER, (PVOID) data);
[551]287 if (*data->dirname)
288 WinSetDlgItemText(hwnd, OBJCNR_DIR, data->dirname);
289 {
290 DIRSIZE *dirsize;
[1063]291# ifdef FORTIFY
292 Fortify_EnterScope();
293# endif
[551]294 dirsize = xmalloc(sizeof(DIRSIZE), pszSrcFile, __LINE__);
295 if (!dirsize) {
[1335]296 WinDismissDlg(hwnd, 0);
297 break;
[2]298 }
[1009]299 dirsize->stopflag = (CHAR *)&data->stopflag;
[551]300 dirsize->filename = data->dirname;
301 dirsize->hwndCnr = WinWindowFromID(hwnd, OBJCNR_CNR);
[1335]302 if (xbeginthread(FillCnrsThread,
303 65536 * 8,
304 dirsize,
305 pszSrcFile,
306 __LINE__) == -1)
307 {
308 free(dirsize);
[1063]309# ifdef FORTIFY
[1335]310 Fortify_LeaveScope();
[1063]311# endif
[1335]312 WinDismissDlg(hwnd, 0);
313 break;
[349]314 }
[551]315 else
[1335]316 data->working = TRUE;
[551]317 }
318 PostMsg(hwnd, UM_SETUP, MPVOID, MPVOID);
319 break;
[2]320
[551]321 case UM_SETUP:
322 // WinEnableWindowUpdate(WinWindowFromID(hwnd,OBJCNR_CNR),FALSE);
323 {
324 CNRINFO cnri;
[2]325
[551]326 memset(&cnri, 0, sizeof(CNRINFO));
327 cnri.cb = sizeof(CNRINFO);
328 WinSendDlgItemMsg(hwnd, OBJCNR_CNR, CM_QUERYCNRINFO,
[1335]329 MPFROMP(&cnri), MPFROMLONG(sizeof(CNRINFO)));
[551]330 cnri.cyLineSpacing = 0;
331 cnri.cxTreeIndent = 12L;
[1394]332 cnri.pszCnrTitle = (PSZ)GetPString(IDS_WORKINGTEXT);
[551]333 cnri.flWindowAttr = CV_TREE | CV_FLOW |
[1335]334 CA_CONTAINERTITLE | CA_TITLESEPARATOR | CA_TREELINE;
[551]335 if (WinQueryWindowUShort(hwnd, QWS_ID) == QTREE_FRAME)
[1335]336 cnri.flWindowAttr |= CV_MINI;
[551]337 WinSendDlgItemMsg(hwnd, OBJCNR_CNR, CM_SETCNRINFO, MPFROMP(&cnri),
[1335]338 MPFROMLONG(CMA_FLWINDOWATTR | CMA_LINESPACING |
339 CMA_CXTREEINDENT));
[551]340 }
341 return 0;
[2]342
[551]343 case UM_CONTAINER_FILLED:
344 WinSetDlgItemText(hwnd, OBJCNR_NOTE, NullStr);
[2]345// WinEnableWindowUpdate(WinWindowFromID(hwnd,OBJCNR_CNR),TRUE);
[551]346 WinSendDlgItemMsg(hwnd, OBJCNR_CNR, CM_INVALIDATERECORD, MPVOID,
[1335]347 MPFROM2SHORT(0, CMA_ERASE | CMA_INVALIDATE));
[551]348 data = INSTDATA(hwnd);
349 if (data) {
350 data->working = FALSE;
351 if (data->dying)
[1335]352 WinDismissDlg(hwnd, 0);
[551]353 {
[1335]354 PCNRITEM pci;
355 USHORT id;
[2]356
[1335]357 id = WinQueryWindowUShort(hwnd, QWS_ID);
358 pci = (PCNRITEM) WinSendDlgItemMsg(hwnd, OBJCNR_CNR,
359 CM_QUERYRECORD,
360 MPVOID,
361 MPFROM2SHORT(CMA_FIRST,
362 CMA_ITEMORDER));
363 if (pci && (INT) pci != -1) {
364 ExpandAll(WinWindowFromID(hwnd, OBJCNR_CNR), TRUE, pci);
365 if (id == QTREE_FRAME)
366 pci = (PCNRITEM) WinSendDlgItemMsg(hwnd, OBJCNR_CNR,
367 CM_QUERYRECORD,
368 MPFROMP(pci),
369 MPFROM2SHORT(CMA_FIRSTCHILD,
370 CMA_ITEMORDER));
371 }
372 if ((!pci || (INT) pci == -1) && id == QTREE_FRAME) {
373 Notify(GetPString(IDS_NODIRSUNDERTEXT));
374 WinDismissDlg(hwnd, 0);
375 break;
376 }
[2]377 }
[551]378 }
379 return 0;
[2]380
[551]381 case WM_CONTROL:
382 switch (SHORT1FROMMP(mp1)) {
383 case OBJCNR_CNR:
384 if (SHORT2FROMMP(mp1) == CN_ENTER) {
[2]385
[1335]386 PCNRITEM pci = (PCNRITEM) ((PNOTIFYRECORDENTER) mp2)->pRecord;
[2]387
[1335]388 if (pci && (INT) pci != -1)
389 WinSendDlgItemMsg(hwnd, DID_OK, BM_CLICK, MPVOID, MPVOID);
[2]390 }
[551]391 break;
392 }
393 return 0;
[2]394
[551]395 case WM_COMMAND:
396 switch (SHORT1FROMMP(mp1)) {
397 case IDM_HELP:
398 if (hwndHelp) {
[2]399
[1335]400 USHORT id;
[2]401
[1335]402 id = WinQueryWindowUShort(hwnd, QWS_ID);
[2]403
[1335]404 if (id == QTREE_FRAME)
405 WinSendMsg(hwndHelp, HM_DISPLAY_HELP,
406 MPFROM2SHORT(HELP_QUICKTREE, 0),
407 MPFROMSHORT(HM_RESOURCEID));
408 else
409 WinSendMsg(hwndHelp, HM_DISPLAY_HELP,
410 MPFROM2SHORT(HELP_OBJECTPATH, 0),
411 MPFROMSHORT(HM_RESOURCEID));
[551]412 }
413 break;
[2]414
[551]415 case OBJCNR_DESKTOP:
416 case DID_OK:
417 data = INSTDATA(hwnd);
418 if (data) {
[2]419
[1335]420 PCNRITEM pci;
[2]421
[1335]422 if (data->working) {
423 Runtime_Error(pszSrcFile, __LINE__, "working unexpected");
424 break;
425 }
426 if (SHORT1FROMMP(mp1) == OBJCNR_DESKTOP) {
427 WinDismissDlg(hwnd, 2);
428 break;
429 }
430 pci = (PCNRITEM) WinSendDlgItemMsg(hwnd, OBJCNR_CNR,
431 CM_QUERYRECORDEMPHASIS,
432 MPFROMLONG(CMA_FIRST),
433 MPFROMSHORT(CRA_CURSORED));
434 if (pci && (INT) pci != -1)
435 strcpy(data->dirname, pci->pszFileName);
436 WinDismissDlg(hwnd, 1);
[2]437 }
[551]438 break;
[2]439
[551]440 case DID_CANCEL:
[2]441 data = INSTDATA(hwnd);
[551]442 if (data) {
[1335]443 if (data->working) {
444 data->dying = (CHAR)TRUE;
445 data->stopflag = (CHAR)0xff;
446 break;
447 }
448 WinDismissDlg(hwnd, 0);
[551]449 }
[2]450 break;
[551]451 }
452 return 0;
453
454 case WM_DESTROY:
455 objcnrwnd = (HWND) 0;
456 data = INSTDATA(hwnd);
[1009]457 xfree(data, pszSrcFile, __LINE__);
[551]458 break;
[2]459 }
[551]460 return WinDefDlgProc(hwnd, msg, mp1, mp2);
[2]461}
[783]462
463#pragma alloc_text(OBJCNR,ProcessDir,FillCnrsThread,ObjCnrDlgProc)
Note: See TracBrowser for help on using the repository browser.