source: trunk/dll/systemf.c@ 906

Last change on this file since 906 was 906, checked in by Gregg Young, 18 years ago

The basic program quoting code and some mailto cleanup.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 37.7 KB
RevLine 
[78]1
2/***********************************************************************
3
4 $Id: systemf.c 906 2008-01-06 04:21:14Z gyoung $
5
6 System Interfaces
7
8 Copyright (c) 1993-98 M. Kimes
[330]9 Copyright (c) 2003, 2006 Steven H.Levine
[78]10
[330]11 21 Nov 03 SHL Comments
12 31 Jul 04 SHL Indent -i2
13 01 Aug 04 SHL Rework lstrip/rstrip usage
14 17 Jul 06 SHL Use Runtime_Error
[373]15 26 Jul 06 SHL Use convert_nl_to_nul
[441]16 15 Aug 06 SHL More error popups
[519]17 01 Nov 06 SHL runemf2: temp fix for hung windows caused by termq errors
[540]18 03 Nov 06 SHL runemf2: rework termination queue logic to work for multiple threads
[552]19 07 Jan 07 GKY Move error strings etc. to string file
[775]20 06 Aug 07 GKY Reduce DosSleep times (ticket 148)
[793]21 20 Aug 07 GKY Move #pragma alloc_text to end for OpenWatcom compat
[78]22
[775]23
[78]24***********************************************************************/
25
[2]26#define INCL_WIN
27#define INCL_WINERRORS
28#define INCL_DOS
29#define INCL_DOSERRORS
[330]30#include <os2.h>
[2]31
32#include <stdlib.h>
33#include <stdio.h>
34#include <stdarg.h>
35#include <string.h>
36#include <ctype.h>
37#include <time.h>
[330]38
[2]39#include "fm3dll.h"
40#include "fm3dlg.h"
41#include "fm3str.h"
42
[330]43static PSZ pszSrcFile = __FILE__;
44
[105]45#define MAXSTRG (4096) /* used to build command line strings */
[2]46
[519]47//== ShowSession() bring session for foreground ==
[2]48
[105]49BOOL ShowSession(HWND hwnd, PID pid)
[78]50{
[105]51 HSWITCH hswitch;
52 SWCNTRL swctl;
53 ULONG rc;
[2]54
[519]55 hswitch = WinQuerySwitchHandle(pid ? (HWND)0 : hwnd, pid);
[441]56 if (hswitch) {
[105]57 rc = WinQuerySwitchEntry(hswitch, &swctl);
[441]58 if (!rc) {
[105]59 if (swctl.idProcess == pid && swctl.uchVisibility == SWL_VISIBLE)
60 rc = WinSwitchToProgram(hswitch);
61 if (!rc)
62 return TRUE;
[78]63 // else saymsg(MB_ENTER,HWND_DESKTOP,DEBUG_STRING,"Failed: %lu/%lx",rc,rc);
[2]64
[105]65 }
66 }
67 return FALSE;
[2]68}
69
[519]70//== ExecOnList() Invoke runemf2 for command and file/directory list ==
71
[105]72int ExecOnList(HWND hwnd, char *command, int flags, char *tpath,
[888]73 char **list, char *prompt, PCSZ pszCallingFile, UINT uiLineNumber)
[78]74{
[105]75 /* executes the command once for all files in list */
[2]76
[105]77 char path[CCHMAXPATH], commandline[2048], modpath[CCHMAXPATH], listfile[CCHMAXPATH],
78 *p, *pp, drive, *file, *ext, *dot;
[2]79 register int x;
[105]80 BOOL spaces;
[2]81
[441]82 if (!command || !*command) {
83 Runtime_Error2(pszSrcFile, __LINE__, IDS_NODATATEXT);
[105]84 return -1;
[441]85 }
[2]86 *listfile = 0;
[123]87 bstrip(command);
[2]88
89 *path = 0;
[105]90 if (tpath && *tpath)
91 strcpy(path, tpath);
[441]92 else if (*command != '<' || !strchr(command, '>')) {
[105]93 strcpy(path, command + (*command == '"'));
94 if (*command == '\"')
95 p = strchr(path, '\"');
[2]96 else
[105]97 p = strchr(path, ' ');
98 if (p)
[2]99 *p = 0;
[105]100 p = strrchr(path, '\\');
101 if (!p)
102 p = strrchr(path, ':');
[441]103 if (p) {
104 if (*p == ':') {
[105]105 p++;
106 *p = '\\';
107 p++;
[2]108 }
109 *p = 0;
110 }
111 else
112 *path = 0;
113 }
[441]114 if (!*path) {
[105]115 if (list && list[0])
116 strcpy(path, list[0]);
117 p = strrchr(path, '\\');
118 if (!p)
119 p = strrchr(path, ':');
[441]120 if (p) {
121 if (*p == ':') {
[105]122 p++;
123 *p = '\\';
124 p++;
[2]125 }
126 *p = 0;
127 }
128 else
129 *path = 0;
130 }
131 *modpath = 0;
[105]132 if (list && list[0])
133 strcpy(modpath, list[0]);
134 p = strrchr(modpath, '\\');
135 if (!p)
136 p = strrchr(modpath, ':');
[441]137 if (p) {
138 if (*p == ':') {
[2]139 p++;
140 *p = '\\';
141 p++;
142 }
143 *p = 0;
144 }
145 else
146 *modpath = 0;
[105]147 if (!*modpath)
148 strcpy(modpath, path);
149 if (*path)
[2]150 MakeFullName(path);
[105]151 if (*modpath)
[2]152 MakeFullName(modpath);
[105]153 if (IsFullName(path))
154 drive = toupper(*path);
155 else
156 drive = 0;
[2]157
[105]158 p = command; // substitue for special % sequences
[2]159
[105]160 pp = commandline;
161 *commandline = 0;
[441]162 while (*p) {
163 if (*p == '%') {
164 switch (*(p + 1)) {
[105]165 case '!': /* write list to file, add filename */
[441]166 if (list) {
167 if (!*listfile) {
[105]168 FILE *fp;
[2]169
[105]170 save_dir2(listfile);
171 if (listfile[strlen(listfile) - 1] != '\\')
172 strcat(listfile, "\\");
173 sprintf(&listfile[strlen(listfile)], "%s%03x",
[766]174 LISTTEMPROOT, (clock() & 4095));
[330]175 fp = xfopen(listfile, "w",pszSrcFile,__LINE__);
[441]176 if (fp) {
[105]177 for (x = 0; list[x]; x++)
178 {
179 fputs(list[x], fp);
180 if (list[x + 1])
181 fputc('\n', fp);
182 }
183 fclose(fp);
184 }
185 }
186 strcpy(pp, listfile);
187 pp += strlen(listfile);
188 }
189 p += 2;
190 break;
[2]191
[105]192 case 'c': /* add name of command processor */
193 {
194 char *env = GetCmdSpec(FALSE);
[2]195
[441]196 if (needs_quoting(env) && !strchr(env, '\"')) {
[105]197 *pp = '\"';
198 pp++;
199 spaces = TRUE;
200 }
201 else
202 spaces = FALSE;
203 strcpy(pp, env);
204 p += 2;
205 pp += strlen(env);
[441]206 if (spaces) {
[105]207 *pp = '\"';
208 pp++;
209 }
210 }
211 break;
[2]212
[105]213 case 't': /* add Target directory */
[441]214 if (needs_quoting(targetdir) && !strchr(targetdir, '\"')) {
[105]215 *pp = '\"';
216 pp++;
217 spaces = TRUE;
218 }
219 else
220 spaces = FALSE;
221 strcpy(pp, targetdir);
222 p += 2;
223 pp += strlen(targetdir);
[441]224 if (spaces) {
[105]225 *pp = '\"';
226 pp++;
227 }
228 break;
[2]229
[105]230 case '$': /* add drive letter */
231 if (drive)
232 *pp = drive;
[441]233 else {
[766]234 ULONG ulDriveNum = 3, ulDriveMap;
[2]235
[105]236 DosQCurDisk(&ulDriveNum, &ulDriveMap);
237 *pp = (char) (ulDriveNum + '@');
238 }
239 pp++;
240 p += 2;
241 break;
[2]242
[105]243 case 'U': /* add path of first list component */
244 case 'u':
[441]245 if (*modpath) {
246 if (needs_quoting(modpath) && !strchr(modpath, '\"')) {
[105]247 spaces = TRUE;
248 *pp = '\"';
249 pp++;
250 }
251 else
252 spaces = FALSE;
[441]253 if (*(p + 1) == 'u') {
[105]254 strcpy(pp, modpath);
255 pp += strlen(modpath);
256 }
[441]257 else {
[105]258 strcpy(pp, modpath + 2);
259 pp += strlen(modpath + 2);
260 }
[441]261 if (spaces) {
262 if (modpath[strlen(modpath) - 1] == '\\') {
[105]263 *pp = '\\';
264 pp++;
265 }
266 *pp = '\"';
267 pp++;
268 }
269 }
[441]270 else {
[105]271 char temp[CCHMAXPATH];
[2]272
[105]273 save_dir2(temp);
[441]274 if (needs_quoting(temp) && !strchr(temp, '\"')) {
[105]275 spaces = TRUE;
276 *pp = '\"';
277 pp++;
278 }
279 else
280 spaces = FALSE;
281 strcpy(pp, temp);
282 pp += strlen(temp);
[441]283 if (spaces) {
284 if (temp[strlen(temp) - 1] == '\\') {
[105]285 *pp = '\\';
286 pp++;
287 }
288 *pp = '\"';
289 pp++;
290 }
291 }
292 p += 2;
293 break;
[2]294
[105]295 case 'P': /* add path of execution */
296 case 'p':
[441]297 if (*path) {
298 if (needs_quoting(path) && !strchr(path, '\"')) {
[105]299 spaces = TRUE;
300 *pp = '\"';
301 pp++;
302 }
303 else
304 spaces = FALSE;
[441]305 if (*(p + 1) == 'p') {
[105]306 strcpy(pp, path);
307 pp += strlen(path);
308 }
[441]309 else {
[105]310 strcpy(pp, path + 2);
311 pp += strlen(path + 2);
312 }
[441]313 if (spaces) {
314 if (path[strlen(path) - 1] == '\\') {
[105]315 *pp = '\\';
316 pp++;
317 }
318 *pp = '\"';
319 pp++;
320 }
321 }
[441]322 else {
[105]323 char temp[CCHMAXPATH];
[2]324
[105]325 save_dir2(temp);
[441]326 if (needs_quoting(temp) && !strchr(temp, '\"')) {
[105]327 spaces = TRUE;
328 *pp = '\"';
329 pp++;
330 }
331 else
332 spaces = FALSE;
333 strcpy(pp, temp);
334 pp += strlen(temp);
[441]335 if (spaces) {
336 if (temp[strlen(temp) - 1] == '\\') {
[105]337 *pp = '\\';
338 pp++;
339 }
340 *pp = '\"';
341 pp++;
342 }
343 }
344 p += 2;
345 break;
[2]346
[105]347 case 'D':
[441]348 if (hwndMain) {
[105]349 PCNRITEM pci;
[2]350
[105]351 pci = (PCNRITEM) WinSendMsg(WinWindowFromID(WinWindowFromID(
352 hwndTree, FID_CLIENT), TREE_CNR),
353 CM_QUERYRECORDEMPHASIS,
354 MPFROMLONG(CMA_FIRST),
355 MPFROMSHORT(CRA_CURSORED));
[730]356 if (pci && (int) pci != -1 && *pci->pszFileName) {
357 if (needs_quoting(pci->pszFileName) &&
358 !strchr(pci->pszFileName, '\"'))
[105]359 {
360 *pp = '\"';
361 pp++;
362 spaces = TRUE;
363 }
364 else
365 spaces = FALSE;
[730]366 strcpy(pp, pci->pszFileName);
367 pp += strlen(pci->pszFileName);
[441]368 if (spaces) {
[105]369 *pp = '\"';
370 pp++;
371 }
372 }
373 }
374 p += 2;
375 break;
[2]376
[105]377 case 'd':
[441]378 if (hwndMain) {
[105]379 HENUM henum;
380 char retstr[CCHMAXPATH];
381 HWND hwndC, hwndDir;
382 USHORT id;
383 BOOL first = TRUE;
[2]384
[105]385 henum = WinBeginEnumWindows(hwndMain);
[441]386 while ((hwndC = WinGetNextWindow(henum)) != NULLHANDLE) {
387 if (hwndC != hwndTree) {
[105]388 id = WinQueryWindowUShort(hwndC, QWS_ID);
[441]389 if (id) {
[105]390 hwndDir = WinWindowFromID(hwndC, FID_CLIENT);
[441]391 if (hwndDir) {
[105]392 hwndDir = WinWindowFromID(hwndDir, DIR_CNR);
[441]393 if (hwndDir) {
[105]394 *retstr = 0;
395 WinSendMsg(hwndC, UM_CONTAINERDIR, MPFROMP(retstr), MPVOID);
[441]396 if (*retstr) {
397 if (!first) {
[105]398 *pp = ' ';
399 pp++;
400 }
401 first = FALSE;
[441]402 if (needs_quoting(retstr) && !strchr(retstr, '\"')) {
[105]403 *pp = '\"';
404 pp++;
405 spaces = TRUE;
406 }
407 else
408 spaces = FALSE;
409 strcpy(pp, retstr);
410 pp += strlen(retstr);
[441]411 if (spaces) {
[105]412 *pp = '\"';
413 pp++;
414 }
415 }
416 }
417 }
418 }
419 }
420 }
421 WinEndEnumWindows(henum);
422 }
423 p += 2;
424 break;
[2]425
[105]426 case '%':
427 *pp = '%';
428 pp++;
429 p += 2;
430 break;
[2]431
[105]432 case 'R':
433 case 'F':
434 case 'A':
435 case 'r':
436 case 'f':
437 case 'a':
438 case 'e':
[441]439 if (list) {
[105]440 for (x = 0; list[x]; x++)
441 {
442 file = strrchr(list[x], '\\');
443 if (!file)
444 file = strrchr(list[x], ':');
445 if (file)
446 file++;
447 else
448 file = list[x];
449 ext = strrchr(file, '.');
450 dot = ext;
451 if (ext)
452 ext++;
[441]453 switch (*(p + 1)) {
[105]454 case 'R':
455 case 'r':
456 if (pp + strlen(list[x]) > commandline + 1250)
457 goto BreakOut;
[441]458 if (*(p + 1) == 'r') {
[105]459 strcpy(pp, list[x]);
460 pp += strlen(list[x]);
461 }
[441]462 else {
[105]463 strcpy(pp, list[x] + 2);
464 pp += strlen(list[x] + 2);
465 }
466 break;
[2]467
[105]468 case 'F':
469 case 'f':
470 if (*(p + 1) == 'F' && dot)
471 *dot = 0;
472 if (pp + strlen(file) > commandline + 1250)
473 goto BreakOut;
[441]474 if (needs_quoting(file)) {
[105]475 spaces = TRUE;
476 *pp = '\"';
477 pp++;
478 }
479 else
480 spaces = FALSE;
481 strcpy(pp, file);
482 pp += strlen(file);
483 if (*(p + 1) == 'F' && dot)
484 *dot = '.';
[441]485 if (spaces) {
486 if (*(pp - 1) != '\"') {
[105]487 *pp = '\"';
488 pp++;
489 }
490 }
491 break;
[2]492
[105]493 case 'A':
494 case 'a':
495 if (pp + strlen(list[x]) > commandline + 1250)
496 goto BreakOut;
[441]497 if (needs_quoting(list[x]) && !strchr(list[x], '\"')) {
[105]498 spaces = TRUE;
499 *pp = '\"';
500 pp++;
501 }
502 else
503 spaces = FALSE;
[441]504 if (*(p + 1) == 'a') {
[105]505 strcpy(pp, list[x]);
506 pp += strlen(list[x]);
507 }
[441]508 else {
[105]509 strcpy(pp, list[x] + 2);
510 pp += strlen(list[x] + 2);
511 }
[441]512 if (spaces) {
513 if (list[x][strlen(list[x]) - 1] == '\\') {
[105]514 *pp = '\\';
515 pp++;
516 }
517 *pp = '\"';
518 pp++;
519 }
520 break;
[2]521
[105]522 case 'e':
[441]523 if (ext) {
[105]524 if (pp + strlen(ext) > commandline + 1250)
525 goto BreakOut;
[441]526 if (needs_quoting(ext)) {
[105]527 spaces = TRUE;
528 *pp = '\"';
529 pp++;
[2]530 }
[105]531 else
532 spaces = FALSE;
533 strcpy(pp, ext);
534 pp += strlen(ext);
[441]535 if (spaces) {
536 if (*(pp - 1) != '\"') {
[105]537 *pp = '\"';
538 pp++;
539 }
[2]540 }
[105]541 }
542 break;
543 }
[441]544 if (list[x + 1]) {
[105]545 *pp = ' ';
546 pp++;
547 }
548 }
[2]549 }
[105]550 p += 2;
551 break;
[2]552
[105]553 default:
554 *pp = *p;
555 p++;
556 pp++;
557 break;
558 }
559 }
[441]560 else {
[105]561 *pp = *p;
562 pp++;
563 p++;
564 }
565 *pp = 0;
566 }
567
[2]568BreakOut:
569
[105]570 {
571 EXECARGS ex;
572 ULONG size;
573 int ret;
[2]574
[105]575 memset(&ex, 0, sizeof(EXECARGS));
576 size = sizeof(ex.environment) - 1;
577 PrfQueryProfileData(fmprof, FM3Str, command, ex.environment, &size);
[441]578 if (flags & PROMPT) {
579 /* allow editing command line */
[105]580 ex.flags = (flags & (~PROMPT));
581 ex.commandline = commandline;
582 strcpy(ex.path, path);
583 if (prompt)
584 strcpy(ex.title, prompt);
585 ret = WinDlgBox(HWND_DESKTOP, hwnd, CmdLineDlgProc, FM3ModHandle,
586 EXEC_FRAME, &ex);
587 if (ret != 1)
588 return (ret == 0) ? -1 : -2;
589 }
590 else
591 ex.flags = flags;
592 ex.flags &= (~PROMPT);
[888]593 return runemf2(ex.flags, hwnd, pszCallingFile, uiLineNumber, path,
[105]594 (*ex.environment) ? ex.environment : NULL,
595 "%s", commandline);
596 }
[2]597}
598
[519]599//== runemf2() run requested app, return -1 if problem starting else return app rc ==
[441]600
[888]601int runemf2(int type, HWND hwnd, PCSZ pszCallingFile, UINT uiLineNumber,
602 char *pszDirectory, char *pszEnvironment,
[105]603 char *formatstring,...)
[78]604{
[105]605 /* example:
606
[2]607 * status = runemf2(SEPARATE | WINDOWED,
[888]608 * hwnd, pszCallingFile, __LINE__,
[2]609 * NullStr,
610 * NULL,
611 * "%s /C %s",
612 * getenv("COMSPEC"),
613 * batchfilename);
[105]614 *
615 * use (HWND)0 for hwnd if window handle not handy.
[888]616 * pszCallingFile and __LINE__ are used to determine caller for easier error tracking
[105]617 */
[2]618
619 /*
620 * type bitmapped flag -- see FM3DLL.H
621 */
622
[105]623 va_list parguments;
624 int ret = -1;
[540]625 RESULTCODES results;
[519]626 STARTDATA sdata;
[105]627 REQUESTDATA rq;
[562]628 ULONG ulSessID;
629 ULONG ulLength;
630 UINT ctr;
631 ULONG ulAppType;
[105]632 PID sessPID;
633 BOOL wasquote;
[540]634 char *pszPgm, *pszArgs = NULL;
635 char szObject[32] = "", *p, szSavedir[CCHMAXPATH];
636 BOOL useTermQ = FALSE;
637 char szTempdir[CCHMAXPATH];
638
[519]639 typedef struct {
640 USHORT usSessID;
641 USHORT usRC;
642 } TERMINFO;
643
[540]644 TERMINFO *pTermInfo;
[105]645 BYTE bPriority;
646 APIRET rc;
[519]647 PIB *ppib;
648 TIB *ptib;
[2]649
[540]650 // Shared by all threads
651# define TERMQ_BASE_NAME "\\QUEUES\\FM3WAIT"
652 static char szTermQName[30];
653 static HQUEUE hTermQ;
654 static HEV hTermQSem;
655
656 if (pszDirectory && *pszDirectory) {
657 if (!DosQueryPathInfo(pszDirectory,
[105]658 FIL_QUERYFULLNAME,
[540]659 szTempdir,
660 sizeof(szTempdir)))
661 pszDirectory = szTempdir;
[105]662 }
[2]663
[105]664 if (!hwnd)
665 hwnd = HWND_DESKTOP;
[2]666
[540]667 rc = DosAllocMem((PVOID)&pszPgm,
[105]668 MAXSTRG,
669 PAG_COMMIT | OBJ_TILE | PAG_READ | PAG_WRITE);
[330]670 if (rc) {
671 Dos_Error(MB_CANCEL,rc,hwnd,pszSrcFile,__LINE__,GetPString(IDS_OUTOFMEMORY));
[105]672 return -1;
[330]673 }
[2]674
[540]675 *szSavedir = 0;
[2]676
[540]677 *pszPgm = 0;
[105]678 va_start(parguments,
[888]679 formatstring);
[540]680 vsprintf(pszPgm,
[105]681 formatstring,
[888]682 parguments);
[105]683 va_end(parguments);
[906]684
[540]685 if (pszEnvironment) {
686 p = &pszEnvironment[strlen(pszEnvironment)] + 1;
[105]687 *p = 0;
[540]688 p = pszEnvironment;
[373]689 while ((p = convert_nl_to_nul(p)) != NULL)
690 ; // loop
[105]691 }
[2]692
[540]693 if (!*pszPgm) {
[105]694 p = GetCmdSpec(FALSE);
[540]695 strcpy(pszPgm, p);
696 if (!*pszPgm) {
[441]697 Runtime_Error2(pszSrcFile, __LINE__, IDS_NODATATEXT);
[105]698 return -1;
[441]699 }
[105]700 }
[2]701
[540]702 if (*pszPgm) {
703 if (*pszPgm == '<' && strchr(pszPgm, '>')) {
[441]704 /* is a workplace object */
[105]705 HOBJECT hWPSObject;
706 char temp;
[2]707
[540]708 p = strchr(pszPgm, '>');
[105]709 p++;
710 temp = *p;
[330]711 if (temp) {
[540]712 rc = DosAllocMem((PVOID)&pszArgs,
[105]713 MAXSTRG * 2,
714 PAG_COMMIT | OBJ_TILE | PAG_READ | PAG_WRITE);
[330]715 if (rc)
[540]716 Dos_Error(MB_CANCEL,rc,hwnd,pszSrcFile,__LINE__,GetPString(IDS_OUTOFMEMORY));
[330]717 }
[105]718 else
[540]719 pszArgs = NULL;
[105]720 *p = 0;
721 /* Find the handle of the WPS object */
[540]722 hWPSObject = WinQueryObject(pszPgm);
[105]723 *p = temp;
[441]724 if (hWPSObject != NULLHANDLE) {
[540]725 if (pszArgs && *p) {
726 sprintf(pszArgs,"OPEN=DEFAULT;PARAMETERS=\"%s\"",p);
727 WinSetObjectData(hWPSObject,pszArgs);
[105]728 }
729 else
[441]730 WinSetObjectData(hWPSObject,"OPEN=DEFAULT");
[105]731 ret = 0;
732 }
733 goto ObjectInterrupt;
734 }
[2]735
[773]736 if ((type & RUNTYPE_MASK) == SYNCHRONOUS ||
737 (type & RUNTYPE_MASK) == ASYNCHRONOUS ||
738 (type & RUNTYPE_MASK) == DETACHED)
[105]739 {
[540]740 strip_lead_char(" \t", pszPgm);
741 p = pszPgm;
[105]742 wasquote = FALSE;
743 while (*p &&
744 (wasquote ||
745 (*p != ' ' &&
746 *p != '\t')))
747 {
[441]748 if (*p == '\"') {
749 if (!wasquote) {
[105]750 wasquote = TRUE;
751 memmove(p,
752 p + 1,
753 strlen(p));
754 while (*p == ' ' ||
755 *p == '\t')
756 p++;
757 }
[441]758 else {
[105]759 memmove(p,
760 p + 1,
761 strlen(p));
762 break;
763 }
764 }
765 else
766 p++;
767 }
[441]768 if (*p) {
[105]769 *p = 0;
770 p++;
771 }
772 else
[540]773 p = pszPgm;
[105]774 p[strlen(p) + 1] = 0; /* double-terminate args */
[540]775 if (*pszPgm) {
776 if (!strchr(pszPgm, '\\') &&
777 !strchr(pszPgm, ':') &&
778 pszDirectory &&
779 *pszDirectory)
[105]780 {
[540]781 save_dir2(szSavedir);
782 switch_to(pszDirectory);
[105]783 }
[562]784 rc = DosQueryAppType(pszPgm,&ulAppType);
[540]785 if (!strchr(pszPgm, '\\') &&
786 !strchr(pszPgm, ':') &&
787 pszDirectory &&
788 *pszDirectory)
789 switch_to(szSavedir);
[441]790 if (rc) {
[562]791 Dos_Error(MB_CANCEL,rc,hwnd,pszSrcFile,__LINE__,
792 GetPString(IDS_DOSQAPPTYPEFAILEDTEXT),
[888]793 pszPgm, pszCallingFile, __LINE__);
[540]794 DosFreeMem(pszPgm);
795 if (pszArgs)
796 DosFreeMem(pszArgs);
[105]797 return -1;
798 }
[562]799 if (ulAppType) {
800 if (ulAppType & FAPPTYP_DLL || ulAppType & FAPPTYP_VIRTDRV ||
801 ulAppType & FAPPTYP_PHYSDRV || ulAppType & FAPPTYP_PROTDLL)
[105]802 {
[562]803 Runtime_Error(pszSrcFile, __LINE__,
804 GetPString(IDS_APPTYPEUNEXPECTEDTEXT),
[888]805 ulAppType, pszPgm, pszCallingFile, __LINE__);
[540]806 if (pszPgm)
807 DosFreeMem(pszPgm);
808 if (pszArgs)
809 DosFreeMem(pszArgs);
[105]810 return -1;
811 }
[562]812 if (ulAppType & FAPPTYP_DOS || ulAppType & FAPPTYP_WINDOWSREAL ||
813 ulAppType & FAPPTYP_WINDOWSPROT || ulAppType & FAPPTYP_WINDOWSPROT31)
[105]814 {
[562]815 Runtime_Error(pszSrcFile, __LINE__,
816 GetPString(IDS_APPTYPEUNEXPECTEDTEXT),
[888]817 ulAppType, pszPgm, pszCallingFile, __LINE__);
[540]818 if (pszPgm)
819 DosFreeMem(pszPgm);
820 if (pszArgs)
821 DosFreeMem(pszArgs);
[105]822 return -1;
823 }
824 }
[540]825 memset(&results, 0, sizeof(results));
826 if (pszDirectory && *pszDirectory) {
827 save_dir2(szSavedir);
828 switch_to(pszDirectory);
[105]829 }
[540]830 ret = DosExecPgm(szObject, sizeof(szObject),
[773]831 ((type & RUNTYPE_MASK) == ASYNCHRONOUS ? EXEC_ASYNC : 0) +
832 ((type & RUNTYPE_MASK) == DETACHED ? EXEC_BACKGROUND : 0),
[540]833 pszPgm, pszEnvironment, &results, pszPgm);
834 if (pszDirectory && *pszDirectory)
835 switch_to(szSavedir);
[330]836 if (ret) {
837 Dos_Error(MB_ENTER,ret,hwnd,pszSrcFile,__LINE__,
[888]838 GetPString(IDS_DOSEXECPGMFAILEDTEXT), pszPgm,
839 pszCallingFile, __LINE__);
[330]840 }
[105]841 }
842 }
[441]843 else {
[519]844 if (~type & FULLSCREEN)
[105]845 type |= WINDOWED;
[540]846 rc = DosAllocMem((PVOID) & pszArgs, MAXSTRG * 2,
[105]847 PAG_COMMIT | OBJ_TILE | PAG_READ | PAG_WRITE);
[441]848 if (rc) {
[540]849 Dos_Error(MB_CANCEL,rc,hwnd,pszSrcFile,__LINE__,GetPString(IDS_OUTOFMEMORY));
850 DosFreeMem(pszPgm);
[105]851 return -1;
852 }
[540]853 *pszArgs = 0;
854 memset(&sdata, 0, sizeof(sdata));
855 strip_lead_char(" \t", pszPgm);
856 p = pszPgm;
[105]857 wasquote = FALSE;
[441]858 while (*p && (wasquote || (*p != ' ' && *p != '\t'))) {
859 if (*p == '\"') {
860 if (!wasquote) {
[105]861 wasquote = TRUE;
862 memmove(p, p + 1, strlen(p));
863 while (*p == ' ' || *p == '\t')
864 p++;
865 }
[441]866 else {
[105]867 memmove(p, p + 1, strlen(p));
868 break;
869 }
870 }
871 else
872 p++;
[540]873 } // while
[441]874 if (*p) {
[105]875 *p = 0;
876 p++;
877 }
878 else
879 p = NullStr;
880 if (*p)
[540]881 strcpy(pszArgs, p);
[2]882
[540]883 p = strrchr(pszPgm, '.');
[441]884 if (p) {
[105]885 char temp[CCHMAXPATH + 1];
[2]886
[441]887 if (!stricmp(p, ".BAT")) {
[540]888 strcpy(temp, pszPgm);
889 strcpy(pszPgm, pszArgs);
890 strcpy(pszArgs, "/C ");
891 strcat(pszArgs, temp);
892 strcat(pszArgs, " ");
893 strcat(pszArgs, pszPgm);
894 strcpy(pszPgm, GetCmdSpec(TRUE)); // DOS
[105]895 }
[540]896 else if (!stricmp(p, ".CMD") || !stricmp(p, ".BTM")) {
897 // Assume 4OS2 is BTM
898 strcpy(temp, pszPgm);
899 strcpy(pszPgm, pszArgs);
900 strcpy(pszArgs, "/C ");
901 strcat(pszArgs, temp);
902 strcat(pszArgs, " ");
903 strcat(pszArgs, pszPgm);
904 strcpy(pszPgm, GetCmdSpec(FALSE)); // OS/2
[105]905 }
906 }
[2]907
[888]908 // goddamned OS/2 limit
[2]909
[540]910 if (strlen(pszPgm) + strlen(pszArgs) > 1024)
911 pszArgs[1024 - strlen(pszPgm)] = 0;
[2]912
[540]913 if (!strchr(pszPgm, '\\') &&
914 !strchr(pszPgm, ':') &&
915 pszDirectory &&
916 *pszDirectory)
[105]917 {
[540]918 save_dir2(szSavedir);
919 switch_to(pszDirectory);
[105]920 }
[562]921 rc = DosQueryAppType(pszPgm,&ulAppType);
[540]922 if (!strchr(pszPgm, '\\') &&
923 !strchr(pszPgm, ':') &&
924 pszDirectory &&
925 *pszDirectory)
926 switch_to(szSavedir);
[888]927 if (rc){
[562]928 Dos_Error(MB_CANCEL,rc,hwnd,pszSrcFile,__LINE__,
929 GetPString(IDS_DOSQAPPTYPEFAILEDTEXT),
[888]930 pszPgm, pszCallingFile, __LINE__);
[540]931 DosFreeMem(pszPgm);
932 if (pszArgs)
933 DosFreeMem(pszArgs);
[105]934 return -1;
935 }
[2]936
[562]937 if (ulAppType) {
938 if (ulAppType & (FAPPTYP_DLL | FAPPTYP_VIRTDRV | FAPPTYP_PHYSDRV | FAPPTYP_PROTDLL))
[105]939 {
[562]940 Runtime_Error(pszSrcFile, __LINE__,
941 GetPString(IDS_APPTYPEUNEXPECTEDTEXT),
[888]942 pszPgm, pszCallingFile, __LINE__);
[540]943 DosFreeMem(pszPgm);
944 if (pszArgs)
945 DosFreeMem(pszArgs);
[105]946 return -1;
947 }
[562]948 ulAppType &= ~FAPPTYP_BOUND;
949 if (ulAppType & (FAPPTYP_DOS | FAPPTYP_WINDOWSREAL | FAPPTYP_WINDOWSPROT | FAPPTYP_WINDOWSPROT31))
[105]950 {
[562]951 if (ulAppType & (FAPPTYP_WINDOWSREAL | FAPPTYP_WINDOWSPROT | FAPPTYP_WINDOWSPROT31))
[105]952 {
[540]953 if (~type & FULLSCREEN &&
[562]954 ulAppType & (FAPPTYP_WINDOWSREAL | FAPPTYP_WINDOWSPROT | FAPPTYP_WINDOWSPROT31))
[105]955 {
[540]956 ret = RunSeamless(pszPgm, pszArgs, hwnd);
957 if (pszPgm)
958 DosFreeMem(pszPgm);
959 if (pszArgs)
960 DosFreeMem(pszArgs);
[441]961 return ret ? 0 : -1;
[105]962 }
[441]963 else {
[540]964 strcat(pszPgm, " ");
965 strcat(pszPgm, pszArgs);
966 *pszArgs = 0;
[562]967 if (ulAppType & (FAPPTYP_WINDOWSPROT | FAPPTYP_WINDOWSREAL | FAPPTYP_WINDOWSPROT31))
[540]968 strcat(pszArgs, "/3 ");
969 strcat(pszArgs, pszPgm);
970 strcpy(pszPgm, "WINOS2.COM");
[105]971 }
972 }
[441]973 else {
[540]974 if (~type & FULLSCREEN) {
[105]975 type |= WINDOWED;
[562]976 ulAppType = SSF_TYPE_WINDOWEDVDM;
[105]977 }
[441]978 else {
[540]979 type &= ~WINDOWED;
[562]980 ulAppType = SSF_TYPE_VDM;
[105]981 }
982 }
983 }
[562]984 else if (ulAppType & FAPPTYP_32BIT) {
985 ulAppType &= ~FAPPTYP_32BIT;
986 if (ulAppType == FAPPTYP_WINDOWAPI)
987 ulAppType = SSF_TYPE_PM;
988 else if (ulAppType == FAPPTYP_WINDOWCOMPAT)
989 ulAppType = SSF_TYPE_WINDOWABLEVIO;
990 else if (ulAppType == FAPPTYP_NOTWINDOWCOMPAT) {
991 ulAppType = SSF_TYPE_FULLSCREEN;
[540]992 type &= ~WINDOWED;
[105]993 type |= FULLSCREEN;
994 }
995 else /* ? */
[562]996 ulAppType = SSF_TYPE_WINDOWABLEVIO;
[105]997 }
[562]998 else if (ulAppType == FAPPTYP_WINDOWAPI)
999 ulAppType = SSF_TYPE_PM;
1000 else if (ulAppType == FAPPTYP_WINDOWCOMPAT)
1001 ulAppType = SSF_TYPE_WINDOWABLEVIO;
1002 else if (ulAppType == FAPPTYP_NOTWINDOWCOMPAT) {
[540]1003 type &= ~WINDOWED;
[562]1004 ulAppType = SSF_TYPE_FULLSCREEN;
[105]1005 }
1006 else
[562]1007 ulAppType = SSF_TYPE_DEFAULT;
[540]1008 if ((type & FULLSCREEN || ~type & WINDOWED) &&
[562]1009 ulAppType == SSF_TYPE_WINDOWABLEVIO)
[105]1010 {
[562]1011 ulAppType = SSF_TYPE_FULLSCREEN;
[105]1012 }
[519]1013 // fixme parens?
[540]1014 else if (type & FULLSCREEN ||
[562]1015 (type & WINDOWED && ulAppType == SSF_TYPE_WINDOWEDVDM))
1016 {
1017 ulAppType = SSF_TYPE_VDM;
1018 }
[105]1019 }
[562]1020 if (ulAppType == SSF_TYPE_WINDOWEDVDM && type & SEPARATEKEEP) {
[519]1021 type &= ~SEPARATEKEEP;
[105]1022 type |= SEPARATE;
1023 }
[2]1024
[519]1025 DosGetInfoBlocks(&ptib, &ppib);
1026
[540]1027 if (~type & WAIT)
1028 useTermQ = FALSE;
[519]1029 else {
[540]1030 rc = 0;
1031 DosEnterCritSec();
1032 if (!hTermQ) {
1033 // Create term queue and event semaphore just once
1034 sprintf(szTermQName, TERMQ_BASE_NAME "_%x", ppib->pib_ulpid);
1035 rc = DosCreateQueue(&hTermQ, QUE_FIFO | QUE_CONVERT_ADDRESS, szTermQName);
1036 if (rc) {
1037 hTermQ = (HQUEUE)0; // Try to survive
1038 DosExitCritSec();
1039 Dos_Error(MB_CANCEL,rc,hwnd,pszSrcFile,__LINE__,"DosCreateQueue");
1040 }
1041 else {
1042 rc = DosCreateEventSem(NULL,(PHEV)&hTermQSem,0,FALSE);
1043 if (rc) {
1044 hTermQSem = (HEV)0; // Try to survive
1045 DosCloseQueue(hTermQ);
1046 hTermQ = (HQUEUE)0; // Try to survive
1047 DosExitCritSec();
1048 Dos_Error(MB_ENTER,rc,HWND_DESKTOP,pszSrcFile,__LINE__,"DoCreateEventSem");
1049 }
[562]1050 // if (!rc) fprintf(stderr,"%s %d qcreated ptib %x hTermQ %x\n",__FILE__, __LINE__,ptib,hTermQ);
[540]1051 }
1052 } // if 1st time
1053 useTermQ = hTermQ && hTermQSem;
1054 if (!rc)
1055 DosExitCritSec();
1056 } // if wait
[562]1057
1058 memset(&sdata,0,sizeof(sdata));
[519]1059 sdata.Length = sizeof(sdata);
[562]1060 sdata.Related = type & (WAIT | CHILD) ? SSF_RELATED_CHILD :
1061 SSF_RELATED_INDEPENDENT;
[519]1062 sdata.FgBg = type & BACKGROUND ? SSF_FGBG_BACK : SSF_FGBG_FORE;
1063 sdata.TraceOpt = SSF_TRACEOPT_NONE;
[540]1064 sdata.PgmName = pszPgm;
[562]1065 if (*pszArgs)
1066 sdata.PgmInputs = pszArgs;
1067 if (useTermQ)
1068 sdata.TermQ = szTermQName;
[540]1069 sdata.Environment = pszEnvironment;
[519]1070 sdata.InheritOpt = SSF_INHERTOPT_PARENT;
[562]1071 sdata.SessionType = ulAppType;
[540]1072 sdata.ObjectBuffer = szObject;
1073 sdata.ObjectBuffLen = sizeof(szObject);
[773]1074 if ((type & RUNTYPE_MASK) == SEPARATEKEEP)
[562]1075 sdata.PgmControl |= SSF_CONTROL_NOAUTOCLOSE;
1076 if (type & MAXIMIZED)
1077 sdata.PgmControl |= SSF_CONTROL_MAXIMIZE;
1078 if (type & MINIMIZED)
1079 sdata.PgmControl |= SSF_CONTROL_MINIMIZE;
1080 if (type & INVISIBLE)
1081 sdata.PgmControl |= SSF_CONTROL_INVISIBLE;
1082
[540]1083 if (pszDirectory && *pszDirectory) {
1084 save_dir2(szSavedir);
1085 switch_to(pszDirectory);
[105]1086 }
[562]1087
[563]1088 // printf("%s %d DosStartsession thread 0x%x data\n ",
[562]1089 // __FILE__, __LINE__,ptib->tib_ordinal); fflush(stdout); // 10 Mar 07 SHL hang
[563]1090 // printf(" %d %d %d %s %s %s %d %d\n %s %x %x\n",
[562]1091 // sdata.Length , sdata.Related, sdata.FgBg, sdata.PgmName,
[563]1092 // sdata.PgmInputs, sdata.TermQ, sdata.InheritOpt,
1093 // sdata.SessionType, szTermQName,
1094 // hTermQ, hTermQSem); fflush(stdout);
[519]1095 ret = DosStartSession(&sdata, &ulSessID, &sessPID);
[562]1096
[563]1097 // if (type & WAIT) {
1098 // printf("%s %d DosStartession thread 0x%x rc = %d sess = %u pid = 0x%x\n",
1099 // __FILE__, __LINE__, ptib->tib_ordinal,ret, ulSessID, sessPID); fflush(stdout); // 10 Mar 07 SHL hang
1100 // }
1101 // else {
1102 // printf("%s %d DosStartession thread 0x%x nowait rc = %d\n",
1103 // __FILE__, __LINE__, ptib->tib_ordinal,ret); fflush(stdout); // 10 Mar 07 SHL hang
1104 // }
1105
[540]1106 if (pszDirectory && *pszDirectory)
1107 switch_to(szSavedir);
[562]1108
[330]1109 if (ret && ret != ERROR_SMG_START_IN_BACKGROUND) {
1110 Dos_Error(MB_CANCEL,ret,hwnd,pszSrcFile,__LINE__,
[888]1111 GetPString(IDS_DOSSTARTSESSIONFAILEDTEXT),pszPgm,pszArgs,
1112 pszCallingFile, __LINE__);
[330]1113 }
[441]1114 else if (type & WAIT) {
[105]1115 if (!(type & (BACKGROUND | MINIMIZED | INVISIBLE)))
1116 ShowSession(hwnd, sessPID);
[2]1117
[540]1118 if (!useTermQ) {
[562]1119 STATUSDATA sd;
[540]1120 // Could not create queue - fallback - fixme to be gone?
[563]1121 // printf("%s %d waiting wo/termq\n", __FILE__, __LINE__); fflush(stdout); // 12 Mar 07 SHL hang
[2]1122
[105]1123 memset(&sd, 0, sizeof(sd));
1124 sd.Length = (USHORT) sizeof(sd);
1125 sd.SelectInd = SET_SESSION_UNCHANGED;
1126 sd.BondInd = SET_SESSION_UNCHANGED;
1127 for (ctr = 0;; ctr++)
1128 {
[771]1129 DosSleep(100);//05 Aug 07 GKY 200
[519]1130 if (DosSetSession(ulSessID, &sd)) // Check if session gone (i.e. finished)
[105]1131 break;
[519]1132 if (ctr > 10) {
[563]1133 // printf("%s %d thread 0x%x showing slow sess %u pid 0x%x\n",
1134 // __FILE__, __LINE__,ptib->tib_ordinal,ulSessID,sessPID); fflush(stdout); // 12 Mar 07 SHL
[519]1135 ShowSession(hwnd, sessPID); // Show every 2 seconds
1136 ctr = 0;
1137 }
[105]1138 }
1139 }
[441]1140 else {
[105]1141 for (ctr = 0;; ctr++)
1142 {
[540]1143 if (ctr < 20) {
1144 rc = DosReadQueue(hTermQ, &rq, &ulLength, (PPVOID)&pTermInfo, 0,
1145 DCWW_NOWAIT, &bPriority, hTermQSem);
1146 if (rc == ERROR_QUE_EMPTY) {
[771]1147 DosSleep(50);//05 Aug 07 GKY 100
[540]1148 continue;
[105]1149 }
1150 }
[441]1151 else {
[562]1152 if (ctr == 20) {
[563]1153 // printf("%s %d thread 0x%x showing slow sess %u pid 0x%x\n",
[562]1154 // __FILE__, __LINE__,ptib->tib_ordinal,ulSessID,sessPID); fflush(stdout);
[540]1155 ShowSession(hwnd, sessPID); // Show long running session
[562]1156 }
[540]1157 rc = DosReadQueue(hTermQ, &rq, &ulLength, (PPVOID)&pTermInfo, 0,
1158 DCWW_WAIT, &bPriority, 0);
1159 }
1160
1161 if (rc) {
1162 // Oh heck
1163 Dos_Error(MB_CANCEL,rc,hwnd,pszSrcFile,__LINE__,"DosReadQueue");
[771]1164 DosSleep(100);//05 Aug 07 GKY 500
[540]1165 continue;
1166 }
1167
[563]1168 // printf("%s %d DosReadQueue thread 0x%x sess %u sessRC %u rq.pid 0x%x rq.data 0x%x\n",
[562]1169 // __FILE__, __LINE__,ptib->tib_ordinal,pTermInfo->usSessID,pTermInfo->usRC,rq.pid, rq.ulData); fflush(stdout);
1170
[540]1171 if (pTermInfo->usSessID == ulSessID)
1172 break; // Our session is done
1173
[562]1174 // Requeue session for other thread
[540]1175 {
1176 static ULONG ulLastSessID;
[563]1177 // printf("%s %d requeue thread 0x%x our sess %u term sess %u term rc %u\n",
[562]1178 // __FILE__, __LINE__,ptib->tib_ordinal,ulSessID,pTermInfo->usSessID,pTermInfo->usRC); fflush(stdout);
1179 // fixme to be gone when no longer needed for debug?
[540]1180 if (ulLastSessID) {
[771]1181 DosSleep(100);//05 Aug 07 GKY 500
[540]1182 ulLastSessID = pTermInfo->usSessID;
[519]1183 }
[562]1184 // requeue term report for other thread and do not free yet
[540]1185 rc = DosWriteQueue(hTermQ, rq.ulData, ulLength,(PVOID)pTermInfo, bPriority);
1186 if (rc)
1187 Dos_Error(MB_CANCEL,rc,hwnd,pszSrcFile,__LINE__,"DosWriteQueue");
[771]1188 DosSleep(50); //05 Aug 07 GKY 100 // Let other thread see queue entry
[105]1189 }
[519]1190 } // for
[540]1191
[562]1192 ret = pTermInfo->usRC == 0; // Set 1 if rc 0 else 0
[563]1193 // printf("%s %d thread 0x%x term for sess %u\n",
1194 // __FILE__, __LINE__,ptib->tib_ordinal,ulSessID);fflush(stdout);
[540]1195 DosFreeMem(pTermInfo);
[105]1196 }
[540]1197 } // if wait
[105]1198 else if (!(type & (BACKGROUND | MINIMIZED | INVISIBLE)))
1199 ShowSession(hwnd, sessPID);
1200 }
1201 }
[2]1202
1203ObjectInterrupt:
1204
[540]1205 if (pszPgm)
1206 DosFreeMem(pszPgm);
1207 if (pszArgs)
1208 DosFreeMem(pszArgs);
[562]1209
[105]1210 return ret;
[2]1211}
1212
[519]1213//== Exec() Start application with WinStartApp ==
1214
[105]1215HAPP Exec(HWND hwndNotify, BOOL child, char *startdir, char *env,
[519]1216 PROGTYPE *progt, ULONG fl, char *formatstring,...)
[78]1217{
[105]1218 PROGDETAILS pgd;
[2]1219 register char *p;
[105]1220 char *parameters = NULL, *executable = NULL;
[519]1221 HAPP happ = (HAPP)0;
[105]1222 ULONG ulOptions = SAF_INSTALLEDCMDLINE;
1223 BOOL wasquote;
1224 va_list parguments;
[2]1225
[105]1226 if (child)
[2]1227 ulOptions |= SAF_STARTCHILDAPP;
1228
[330]1229 executable = xmallocz(MAXSTRG,pszSrcFile,__LINE__);
1230 if (executable) {
[105]1231 va_start(parguments, formatstring);
1232 vsprintf(executable, formatstring, parguments);
[2]1233 va_end(parguments);
[105]1234 strip_lead_char(" \t", executable);
[441]1235 if (*executable) {
[330]1236 parameters = xmalloc(MAXSTRG,pszSrcFile,__LINE__);
[441]1237 if (parameters) {
[105]1238 p = executable;
1239 wasquote = FALSE;
[441]1240 while (*p && (wasquote || (*p != ' ' && *p != '\t'))) {
1241 if (*p == '\"') {
1242 if (!wasquote) {
[105]1243 wasquote = TRUE;
1244 memmove(p, p + 1, strlen(p));
1245 while (*p == ' ' || *p == '\t')
1246 p++;
1247 }
[441]1248 else {
[105]1249 memmove(p, p + 1, strlen(p));
1250 break;
1251 }
1252 }
1253 else
1254 p++;
1255 }
[441]1256 if (*p) {
[105]1257 *p = 0;
1258 p++;
1259 }
1260 else
1261 p = NullStr;
1262 if (*p)
1263 strcpy(parameters, p);
[2]1264
[441]1265 if (p && (!stricmp(p, ".BAT") || !stricmp(p, ".CMD"))) {
[105]1266 char *temp;
[2]1267
[330]1268 temp = xmalloc(CCHMAXPATH * 2,pszSrcFile,__LINE__);
[441]1269 if (temp) {
1270 if (!stricmp(p, ".BAT")) {
[105]1271 strcpy(temp, executable);
1272 strcpy(executable, parameters);
1273 strcpy(parameters, "/C ");
1274 strcat(parameters, temp);
1275 strcat(parameters, " ");
1276 strcat(parameters, executable);
1277 strcpy(executable, GetCmdSpec(TRUE));
1278 }
[441]1279 else if (!stricmp(p, ".CMD")) {
[105]1280 strcpy(temp, executable);
1281 strcpy(executable, parameters);
1282 strcpy(parameters, "/C ");
1283 strcat(parameters, temp);
1284 strcat(parameters, " ");
1285 strcat(parameters, executable);
1286 strcpy(executable, GetCmdSpec(FALSE));
1287 }
1288 free(temp);
1289 }
1290 }
[2]1291
[105]1292 memset(&pgd, 0, sizeof(pgd));
1293 pgd.Length = sizeof(pgd);
1294 pgd.progt = *progt;
1295 pgd.swpInitial.fl = fl;
1296 pgd.pszEnvironment = env;
1297 pgd.pszStartupDir = startdir;
[562]1298 pgd.pszParameters = *parameters ? parameters : NULL;
[105]1299 pgd.pszExecutable = executable;
1300 pgd.swpInitial.hwndInsertBehind = HWND_TOP;
1301 happ = WinStartApp(hwndNotify, &pgd, NULL, NULL, ulOptions);
1302 free(parameters);
[2]1303 }
1304 }
1305 free(executable);
1306 }
1307 return happ;
1308}
[793]1309
[906]1310PSZ CheckApp_QuoteAddExe(PSZ pszPgm)
1311{
1312 char szTempPgm[CCHMAXPATH], tempcom[CCHMAXPATH], temparg[CCHMAXPATH];
1313 char *offset, *offsetexe, *offsetcom, *offsetcmd, *offsetbtm, *offsetbat;
1314 APIRET ret;
1315 ULONG ulAppType;
1316 char *pszChar;
1317 FILEFINDBUF3 FindBuffer;
1318 ULONG ulResultBufLen = sizeof(FILEFINDBUF3);
1319 HDIR hdirFindHandle = HDIR_CREATE;
1320 ULONG ulFindCount = 1;
1321 PSZ pszQuotedCompletePgm;
1322
1323 bstrip(pszPgm);
1324 strcpy(tempcom, pszPgm);
1325 if (tempcom[0] != '\0'){
1326 offsetexe = strstr(strlwr(pszPgm), ".exe");
1327 offsetcmd = strstr(strlwr(pszPgm), ".cmd");
1328 offsetcom = strstr(strlwr(pszPgm), ".com");
1329 offsetbtm = strstr(strlwr(pszPgm), ".btm");
1330 offsetbat = strstr(strlwr(pszPgm), ".bat");
1331 if (offsetbat){
1332 if (strstr(strlwr(pszPgm), "command ") < offsetbat)
1333 offset = pszPgm;
1334 else
1335 offset = offsetbat;
1336 }
1337 else if (offsetbtm){
1338 if (strstr(strlwr(pszPgm), "4os2 ") < offsetbtm)
1339 offset = pszPgm;
1340 else
1341 offset = offsetbtm;
1342 }
1343 else if (offsetcmd){
1344 if (strstr(strlwr(pszPgm), "cmd ") < offsetcmd ||
1345 strstr(strlwr(pszPgm), "4os2 ") < offsetcmd)
1346 offset = pszPgm;
1347 else
1348 offset = offsetcmd;
1349 }
1350 else if (offsetcom)
1351 offset = offsetcom;
1352 else if (offsetexe)
1353 offset = offsetexe;
1354 else {
1355 offset = pszPgm;
1356 }
1357 if (offset - pszPgm != 0){
1358 tempcom[offset + 4 - pszPgm] = '\0';
1359 strcpy(temparg, &pszPgm[offset + 4 - pszPgm]);
1360 /*if ((offsetexe && !offsetcom && !offsetcmd && !offsetbtm && !offsetbat) ||
1361 (offsetcom && !offsetexe && !offsetcmd && !offsetbtm && !offsetbat) ||
1362 (offsetcmd && !offsetexe && !offsetcom && !offsetbtm && !offsetbat) ||
1363 (offsetbtm && !offsetexe && !offsetcom && !offsetcmd && !offsetbat) ||
1364 (offsetbat && !offsetexe && !offsetcom && !offsetcmd && !offsetbtm))*/
1365 remove_first_occurence_of_character("\"", tempcom);
1366 if (strchr(tempcom, '\"') != strrchr(tempcom, '\"'))
1367 saymsg(MB_OK, HWND_DESKTOP,
1368 NullStr,
1369 GetPString(IDS_QUOTESINARGSTEXT),
1370 pszPgm);
1371 else
1372 remove_first_occurence_of_character("\"", tempcom);
1373 if ((temparg[0] == '\"' && temparg[1] == ' ') ||
1374 !strstr(pszPgm, "\\:")||
1375 strchr(temparg, '\"') == strrchr(temparg, '\"'))
1376 remove_first_occurence_of_character("\"", temparg);
1377 if (strchr(temparg, '\"') != strrchr(temparg, '\"'))
1378 saymsg(MB_OK, HWND_DESKTOP,
1379 NullStr,
1380 GetPString(IDS_QUOTESINARGSTEXT),
1381 pszPgm);
1382 if (!strstr(strlwr(tempcom), ".exe")) {
1383 ret = DosFindFirst(tempcom, &hdirFindHandle, FILE_NORMAL, &FindBuffer,
1384 ulResultBufLen, &ulFindCount, FIL_STANDARD);
1385 BldQuotedFileName(szTempPgm, tempcom);
1386 }
1387 else{
1388 BldQuotedFileName(szTempPgm, tempcom);
1389 ret = DosQueryAppType(tempcom, &ulAppType);
1390 }
1391 //printf("%d A", ret); fflush(stdout);
1392 if (ret) {
1393 ret = saymsg(MB_YESNO,
1394 HWND_DESKTOP,
1395 NullStr,
1396 GetPString(IDS_PROGRAMNOTFOUNDTEXT),
1397 pszPgm);
1398 if (ret == MBID_YES){
1399 if (temparg[0] != ' ')
1400 strcat(szTempPgm, " ");
1401 strcat(szTempPgm, temparg);
1402 pszQuotedCompletePgm = szTempPgm;
1403 }
1404 else{
1405 fCancelAction = TRUE;
1406 pszQuotedCompletePgm = pszPgm;
1407 }
1408 }
1409 else{
1410 if (temparg[0] != ' ')
1411 strcat(szTempPgm, " ");
1412 strcat(szTempPgm, temparg);
1413 pszQuotedCompletePgm = szTempPgm;
1414 }
1415
1416 }
1417 else if (tempcom && (!strchr(tempcom, '.') ||
1418 strrchr(tempcom, '.' ) < strrchr(tempcom, '\\'))){
1419 if (!strchr(tempcom, ' ')){
1420 while (strchr(tempcom, '\"'))
1421 remove_first_occurence_of_character("\"", tempcom);
1422 strcat(tempcom, ".exe");
1423 ret = DosFindFirst(tempcom, &hdirFindHandle, FILE_NORMAL, &FindBuffer,
1424 ulResultBufLen, &ulFindCount, FIL_STANDARD);
1425 //printf("%d", ret); fflush(stdout);
1426 }
1427 else{
1428 pszChar = tempcom;
1429 while (pszChar){
1430 while (strchr(tempcom, '\"'))
1431 remove_first_occurence_of_character("\"", tempcom);
1432 if (*pszChar == ' '){
1433 *pszChar = '\0';
1434 strcat(tempcom, ".exe");
1435 ret = DosQueryAppType(tempcom, &ulAppType);
1436 //printf("%d %s\n", ret, tempcom); fflush(stdout);
1437 if (!ret){
1438 break;
1439 }
1440 }
1441 strcpy(tempcom, pszPgm);
1442 pszChar++;
1443 }
1444 }
1445 if (!ret){
1446 BldQuotedFileName(szTempPgm, tempcom);
1447 strcpy(temparg, pszPgm + strlen(tempcom) - 3);
1448 if ((temparg[0] == '\"' && temparg[1] == ' ') ||
1449 !strstr(pszPgm, "\\:" ) ||
1450 strchr(temparg, '\"') == strrchr(temparg, '\"'))
1451 remove_first_occurence_of_character("\"", temparg);
1452 if (strchr(temparg, '\"') != strrchr(temparg, '\"'))
1453 saymsg(MB_OK, HWND_DESKTOP,
1454 NullStr,
1455 GetPString(IDS_QUOTESINARGSTEXT),
1456 pszPgm);
1457 if (temparg[0] != ' ')
1458 strcat(szTempPgm, " ");
1459 strcat(szTempPgm, temparg);
1460 pszQuotedCompletePgm = szTempPgm;
1461 }
1462 else {
1463 ret = saymsg(MB_OK,
1464 HWND_DESKTOP,
1465 NullStr,
1466 GetPString(IDS_PROGRAMNOTEXE2TEXT),
1467 pszPgm);
1468 fCancelAction = TRUE;
1469 pszQuotedCompletePgm = pszPgm;
1470 }
1471 }
1472 else {
1473 pszChar = strrchr(tempcom, '.');
1474 while (pszChar && *pszChar !=' '){
1475 pszChar++;
1476 }
1477 *pszChar = '\0';
1478 strcpy (temparg, pszPgm + strlen(tempcom));
1479 while (strchr(tempcom, '\"'))
1480 remove_first_occurence_of_character("\"", tempcom);
1481 if ((temparg[0] == '\"' && temparg[1] == ' ') ||
1482 !strstr(pszPgm, "\\:")||
1483 strchr(temparg, '\"') == strrchr(temparg, '\"'))
1484 remove_first_occurence_of_character("\"", temparg);
1485 if (strchr(temparg, '\"') != strrchr(temparg, '\"'))
1486 saymsg(MB_OK, HWND_DESKTOP,
1487 NullStr,
1488 GetPString(IDS_QUOTESINARGSTEXT),
1489 pszPgm);
1490 ret = DosFindFirst(tempcom, &hdirFindHandle, FILE_NORMAL, &FindBuffer,
1491 ulResultBufLen, &ulFindCount, FIL_STANDARD);
1492
1493 BldQuotedFileName(szTempPgm, tempcom);
1494 //printf("%d %s ", ret, tempcom); fflush(stdout);
1495 if (ret) {
1496 ret = saymsg(MB_YESNO,
1497 HWND_DESKTOP,
1498 NullStr,
1499 GetPString(IDS_PROGRAMNOTFOUNDTEXT),
1500 pszPgm);
1501 if (ret == MBID_YES){
1502 if (temparg[0] != ' ')
1503 strcat(szTempPgm, " ");
1504 strcat(szTempPgm, temparg);
1505 pszQuotedCompletePgm = szTempPgm;
1506 }
1507 else{
1508 fCancelAction = TRUE;
1509 pszQuotedCompletePgm = pszPgm;
1510 }
1511 }
1512 ret = saymsg(MB_YESNO,
1513 HWND_DESKTOP,
1514 NullStr,
1515 GetPString(IDS_PROGRAMNOTEXE3TEXT),
1516 pszPgm);
1517 if (ret == MBID_YES){
1518 if (temparg[0] != ' ')
1519 strcat(szTempPgm, " ");
1520 strcat(szTempPgm, temparg);
1521 pszQuotedCompletePgm = szTempPgm;
1522 }
1523 else{
1524 fCancelAction = TRUE;
1525 pszQuotedCompletePgm = pszPgm;
1526 }
1527 }
1528 return pszQuotedCompletePgm;
1529 }
1530 return pszPgm;
1531}
1532
[793]1533#pragma alloc_text(SYSTEMF,ShowSession,ExecOnList,runemf2)
Note: See TracBrowser for help on using the repository browser.