Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

962 lines
26 KiB

  1. #include "precomp.h"
  2. #pragma hdrstop
  3. /**************************************************************************/
  4. /***** Shell Component - Script Interpreting routine **********************/
  5. /**************************************************************************/
  6. #define NEWINF
  7. extern BOOL FAddSymSectionToUpdateList(SZ);
  8. extern BOOL FUpdateAllReadSymSections(VOID);
  9. extern BOOL FFreeSymSectionsUpdateList(VOID);
  10. extern BOOL FUIEntryPoint(HANDLE, HWND, RGSZ, USHORT);
  11. int SymTabDumpCount = 0;
  12. BOOL FShellCommand( RGSZ rgszArg );
  13. BOOL FShellReturn( RGSZ rgszArg );
  14. /*
  15. ** Symbol Section Update List Element structure
  16. */
  17. typedef struct _ssule
  18. {
  19. SZ szSection;
  20. struct _ssule * pssuleNext;
  21. } SSULE;
  22. typedef SSULE * PSSULE;
  23. /*
  24. ** Global Variable for head of list for Symbol Sections to update
  25. */
  26. PSSULE pssuleSymSectionUpdateList = (PSSULE)NULL;
  27. /*
  28. ** Purpose:
  29. ** ??
  30. ** Arguments:
  31. ** none
  32. ** Returns:
  33. ** none
  34. **
  35. *************************************************************************/
  36. BOOL FAddSymSectionToUpdateList(szSection)
  37. SZ szSection;
  38. {
  39. PSSULE pssule;
  40. while ((pssule = (PSSULE)SAlloc((CB)sizeof(SSULE))) == (PSSULE)NULL)
  41. if (!FHandleOOM(hWndShell))
  42. return(fFalse);
  43. while ((pssule->szSection = SzDupl(szSection)) == (SZ)NULL)
  44. if (!FHandleOOM(hWndShell))
  45. return(fFalse);
  46. pssule->pssuleNext = pssuleSymSectionUpdateList;
  47. pssuleSymSectionUpdateList = pssule;
  48. return(fTrue);
  49. }
  50. /*
  51. ** Purpose:
  52. ** ??
  53. ** Arguments:
  54. ** none
  55. ** Returns:
  56. ** none
  57. **
  58. *************************************************************************/
  59. BOOL FUpdateAllReadSymSections(VOID)
  60. {
  61. #ifndef NEWINF
  62. PSSULE pssule = pssuleSymSectionUpdateList;
  63. while (pssule != (PSSULE)NULL)
  64. {
  65. if (!FUpdateInfSectionUsingSymTab(pssule->szSection))
  66. return(fFalse);
  67. pssule = pssule->pssuleNext;
  68. }
  69. #endif
  70. return(fTrue);
  71. }
  72. /*
  73. ** Purpose:
  74. ** ??
  75. ** Arguments:
  76. ** none
  77. ** Returns:
  78. ** none
  79. **
  80. *************************************************************************/
  81. BOOL FFreeSymSectionsUpdateList(VOID)
  82. {
  83. PSSULE pssule;
  84. while ((pssule = pssuleSymSectionUpdateList) != (PSSULE)NULL)
  85. {
  86. pssuleSymSectionUpdateList = pssule->pssuleNext;
  87. SFree(pssule->szSection);
  88. SFree(pssule);
  89. }
  90. return(fTrue);
  91. }
  92. /*
  93. ** Purpose:
  94. ** Reads and Interprets the current line in the INF file.
  95. ** Arguments:
  96. ** wParam: if not 0, line # of new current line + 1
  97. ** lParam: cc
  98. ** Returns:
  99. ** fFalse
  100. ** fTrue
  101. **
  102. **************************************************************************/
  103. BOOL FInterpretNextInfLine(WPARAM wParam,LPARAM lParam)
  104. {
  105. SPC spc;
  106. UINT cFields;
  107. UINT iField;
  108. RGSZ rgsz = (RGSZ)NULL;
  109. PFH pfh;
  110. GRC grc;
  111. CHAR FileName[MAX_PATH];
  112. Unused(lParam);
  113. PreCondition(psptShellScript != (PSPT)NULL, fFalse);
  114. PreCondition(pLocalContext()->szShlScriptSection != (SZ)NULL &&
  115. *(pLocalContext()->szShlScriptSection) != '\0' &&
  116. *(pLocalContext()->szShlScriptSection) != '[', fFalse);
  117. if(wParam) {
  118. pLocalContext()->CurrentLine = (INT)(wParam - 1);
  119. }
  120. #if 0
  121. sprintf(FileName,"C:\\SYMTAB.%03d",SymTabDumpCount);
  122. OutputDebugString("SETUPDLL: ");
  123. OutputDebugString( FileName );
  124. OutputDebugString( "\n" );
  125. SymTabDumpCount++;
  126. DumpSymbolTableToFile(FileName);
  127. #endif
  128. if (!FHandleFlowStatements(&(pLocalContext()->CurrentLine), hWndShell, pLocalContext()->szShlScriptSection, &cFields , &rgsz))
  129. return(fFalse);
  130. Assert(cFields);
  131. Assert(rgsz);
  132. switch ((spc = SpcParseString(psptShellScript, rgsz[0])))
  133. {
  134. case spcUI:
  135. SdAtNewLine(pLocalContext()->CurrentLine);
  136. if (!FUIEntryPoint(hInst, hWndShell, rgsz + 1, (USHORT)(cFields - 1)))
  137. goto LParseExitErr;
  138. break;
  139. case spcDetect:
  140. SdAtNewLine(pLocalContext()->CurrentLine);
  141. if (!FDetectEntryPoint(hInst, hWndShell, rgsz + 1,
  142. (USHORT)(cFields - 1)))
  143. goto LParseExitErr;
  144. break;
  145. case spcInstall:
  146. SdAtNewLine(pLocalContext()->CurrentLine);
  147. if (!FInstallEntryPoint(hInst, hWndShell, rgsz + 1,
  148. (USHORT)(cFields - 1)))
  149. goto LParseExitErr;
  150. break;
  151. case spcExit:
  152. SdAtNewLine(pLocalContext()->CurrentLine);
  153. if (cFields != 1)
  154. goto LScriptError;
  155. EvalAssert(FFreeRgsz(rgsz));
  156. FDestroyShellWindow() ;
  157. return(fTrue);
  158. case spcReadSyms:
  159. SdAtNewLine(pLocalContext()->CurrentLine);
  160. if (cFields == 1)
  161. goto LScriptError;
  162. case spcUpdateInf:
  163. if(spc == spcUpdateInf) {
  164. SdAtNewLine(pLocalContext()->CurrentLine);
  165. }
  166. #ifdef NEWINF
  167. if(spc == spcUpdateInf) {
  168. MessBoxSzSz("","Update-Inf encountered, no action taken");
  169. break;
  170. }
  171. #endif
  172. if (spc == spcUpdateInf &&
  173. cFields > 1)
  174. EvalAssert(FFreeSymSectionsUpdateList());
  175. for (iField = 1; iField < cFields; iField++)
  176. {
  177. RGSZ rgszCur;
  178. PSZ psz;
  179. while ((rgszCur = RgszFromSzListValue(rgsz[iField])) == (RGSZ)NULL)
  180. if (!FHandleOOM(hWndShell))
  181. goto LParseExitErr;
  182. psz = rgszCur;
  183. while (*psz != (SZ)NULL)
  184. {
  185. if (**psz == '\0' || FWhiteSpaceChp(**psz))
  186. {
  187. EvalAssert(FFreeRgsz(rgszCur));
  188. goto LScriptError;
  189. }
  190. if (FindInfSectionLine(*psz) == -1)
  191. {
  192. LoadString(hInst, IDS_ERROR, rgchBufTmpShort,
  193. cchpBufTmpShortMax);
  194. LoadString(hInst, IDS_INF_SECT_REF, rgchBufTmpLong,
  195. cchpBufTmpLongMax);
  196. EvalAssert(SzStrCat(rgchBufTmpLong,*psz) == rgchBufTmpLong);
  197. MessageBox(hWndShell, rgchBufTmpLong, rgchBufTmpShort,
  198. MB_OK | MB_ICONHAND);
  199. EvalAssert(FFreeRgsz(rgszCur));
  200. goto LParseExitErr;
  201. }
  202. while (spc == spcReadSyms &&
  203. (grc = GrcAddSymsFromInfSection(*psz)) != grcOkay)
  204. {
  205. if (EercErrorHandler(hWndShell, grc, fTrue, 0, 0, 0) !=
  206. eercRetry)
  207. {
  208. EvalAssert(FFreeRgsz(rgszCur));
  209. goto LParseExitErr;
  210. }
  211. }
  212. if (!FAddSymSectionToUpdateList(*psz))
  213. {
  214. EvalAssert(FFreeRgsz(rgszCur));
  215. goto LParseExitErr;
  216. }
  217. psz++;
  218. }
  219. EvalAssert(FFreeRgsz(rgszCur));
  220. }
  221. if (spc == spcReadSyms)
  222. break;
  223. #ifndef NEWINF
  224. if (!FUpdateAllReadSymSections())
  225. {
  226. LoadString(hInst, IDS_ERROR, rgchBufTmpShort, cchpBufTmpShortMax);
  227. LoadString(hInst, IDS_UPDATE_INF, rgchBufTmpLong,
  228. cchpBufTmpLongMax);
  229. MessageBox(hWndShell, rgchBufTmpLong, rgchBufTmpShort,
  230. MB_OK | MB_ICONHAND);
  231. goto LParseExitErr;
  232. }
  233. EvalAssert(FFreeSymSectionsUpdateList());
  234. #endif
  235. break;
  236. case spcWriteInf:
  237. SdAtNewLine(pLocalContext()->CurrentLine);
  238. if (cFields != 2 ||
  239. *(rgsz[1]) == '\0')
  240. goto LScriptError;
  241. #ifndef NEWINF
  242. while (!FWriteInfFile(rgsz[1]))
  243. if (EercErrorHandler(hWndShell, grcWriteInf, fTrue, rgsz[1], 0, 0)
  244. != eercRetry)
  245. goto LParseExitErr;
  246. #else
  247. MessBoxSzSz("","WriteInf encountered, no action taken");
  248. #endif
  249. break;
  250. case spcWriteSymTab:
  251. SdAtNewLine(pLocalContext()->CurrentLine);
  252. if((cFields != 2) || (*rgsz[1] == '\0')) {
  253. goto LScriptError;
  254. }
  255. retry_dump:
  256. if(!DumpSymbolTableToFile(rgsz[1])) {
  257. EERC eerc;
  258. if((eerc = EercErrorHandler(hWndShell,grcWriteFileErr,fFalse,rgsz[1],0,0)) == eercAbort) {
  259. goto LParseExitErr;
  260. } else if (eerc == eercRetry) {
  261. goto retry_dump;
  262. }
  263. }
  264. break;
  265. case spcSetTitle:
  266. SdAtNewLine(pLocalContext()->CurrentLine);
  267. if (cFields == 1)
  268. SetWindowText(hWndShell, "");
  269. else if (cFields == 2)
  270. SetWindowText(hWndShell, (LPSTR)(rgsz[1]));
  271. else
  272. goto LScriptError;
  273. break;
  274. case spcEnableExit:
  275. SdAtNewLine(pLocalContext()->CurrentLine);
  276. // EnableExit(fTrue);
  277. break;
  278. case spcDisableExit:
  279. SdAtNewLine(pLocalContext()->CurrentLine);
  280. // EnableExit(fFalse);
  281. break;
  282. case spcExitAndExec:
  283. SdAtNewLine(pLocalContext()->CurrentLine);
  284. if (cFields != 2)
  285. goto LScriptError;
  286. /* BLOCK */
  287. {
  288. SZ sz = rgsz[1];
  289. /* Set Working Directory for DLL loads */
  290. if (*sz != '\0' && *(sz + 1) == ':')
  291. {
  292. AnsiUpperBuff(sz, 1);
  293. if (!_chdrive(*sz - 'A' + 1))
  294. {
  295. SZ szLastSlash = NULL;
  296. sz += 2;
  297. while (*sz != '\0' && !FWhiteSpaceChp(*sz))
  298. {
  299. if (*sz == '\\')
  300. szLastSlash = sz;
  301. sz++;
  302. }
  303. if (szLastSlash != NULL)
  304. {
  305. *szLastSlash = '\0';
  306. sz = rgsz[1] + 2;
  307. if (*sz != '\0')
  308. {
  309. AnsiUpper(sz);
  310. _chdir(sz);
  311. }
  312. *szLastSlash = '\\';
  313. }
  314. }
  315. }
  316. WinExec(rgsz[1], SW_SHOWNORMAL);
  317. /* REVIEW error handling */
  318. }
  319. EvalAssert(FFreeRgsz(rgsz));
  320. FDestroyShellWindow() ;
  321. return(fTrue);
  322. case spcShell:
  323. SdAtNewLine(pLocalContext()->CurrentLine);
  324. if (cFields < 3) {
  325. goto LScriptError;
  326. }
  327. return FShellCommand( &rgsz[1] );
  328. case spcReturn:
  329. SdAtNewLine(pLocalContext()->CurrentLine);
  330. return FShellReturn( &rgsz[1] );
  331. default:
  332. SdAtNewLine(pLocalContext()->CurrentLine);
  333. goto LScriptError;
  334. }
  335. EvalAssert(FFreeRgsz(rgsz));
  336. if ((pLocalContext()->CurrentLine = FindNextLineFromInf(pLocalContext()->CurrentLine)) == -1)
  337. {
  338. LoadString(hInst, IDS_ERROR, rgchBufTmpShort, cchpBufTmpShortMax);
  339. LoadString(hInst, IDS_NEED_EXIT, rgchBufTmpLong, cchpBufTmpLongMax);
  340. MessageBox(hWndShell, rgchBufTmpLong, rgchBufTmpShort,
  341. MB_OK | MB_ICONHAND);
  342. return(fFalse);
  343. }
  344. if (spc != spcUI)
  345. PostMessage(hWndShell, (WORD)STF_SHL_INTERP, 0, 0L);
  346. return(fTrue);
  347. LScriptError:
  348. LoadString(hInst, IDS_ERROR, rgchBufTmpShort, cchpBufTmpShortMax);
  349. /* BLOCK */
  350. {
  351. USHORT iszCur = 0;
  352. SZ szCur;
  353. LoadString(hInst, IDS_SHL_CMD_ERROR, rgchBufTmpLong, cchpBufTmpLongMax);
  354. Assert(rgsz != (RGSZ)NULL);
  355. EvalAssert((szCur = *rgsz) != (SZ)NULL);
  356. while (szCur != (SZ)NULL)
  357. {
  358. if (iszCur == 0)
  359. EvalAssert(SzStrCat(rgchBufTmpLong, "\n'") == rgchBufTmpLong);
  360. else
  361. EvalAssert(SzStrCat(rgchBufTmpLong, " ") == rgchBufTmpLong);
  362. if (strlen(rgchBufTmpLong) + strlen(szCur) >
  363. (cchpBufTmpLongMax - 7))
  364. {
  365. Assert(strlen(rgchBufTmpLong) <= (cchpBufTmpLongMax - 5));
  366. EvalAssert(SzStrCat(rgchBufTmpLong, "...") == rgchBufTmpLong);
  367. break;
  368. }
  369. else
  370. EvalAssert(SzStrCat(rgchBufTmpLong, szCur) == rgchBufTmpLong);
  371. szCur = rgsz[++iszCur];
  372. }
  373. EvalAssert(SzStrCat(rgchBufTmpLong, "'") == rgchBufTmpLong);
  374. }
  375. MessageBox(hWndShell, rgchBufTmpLong, rgchBufTmpShort, MB_OK | MB_ICONHAND);
  376. LParseExitErr:
  377. if (rgsz != (RGSZ)NULL)
  378. EvalAssert(FFreeRgsz(rgsz));
  379. return(fFalse);
  380. }
  381. /*
  382. ** Purpose:
  383. ** ??
  384. ** Arguments:
  385. ** none
  386. ** Returns:
  387. ** none
  388. **
  389. *************************************************************************/
  390. BOOL FUIEntryPoint(HANDLE hInst, HWND hWnd, RGSZ rgsz,
  391. USHORT cItems)
  392. {
  393. BOOL fRetVal;
  394. ChkArg(hInst != (HANDLE)NULL, 1, fFalse);
  395. ChkArg(hWnd != (HWND)NULL, 2, fFalse);
  396. ChkArg(cItems >= 2, 4, fFalse);
  397. ChkArg(rgsz != (RGSZ)NULL &&
  398. *rgsz != (SZ)NULL &&
  399. *(rgsz + 1) != (SZ)NULL, 3, fFalse);
  400. if (CrcStringCompareI(*rgsz, "START") == crcEqual) {
  401. HANDLE hInstRes = hInst;
  402. //
  403. // See whether there is a library handle specified
  404. //
  405. if(rgsz[2] && rgsz[2][0]) {
  406. if(rgsz[2][0] != '|') {
  407. goto err;
  408. }
  409. hInstRes = LongToPtr(atol(rgsz[2] + 1));
  410. }
  411. fRetVal = FDoDialog(*(rgsz + 1), hInstRes, hWnd);
  412. UpdateWindow(hWnd);
  413. return(fRetVal);
  414. } else if (CrcStringCompareI(*rgsz, "POP") == crcEqual) {
  415. fRetVal = FKillNDialogs((USHORT)atoi(*(rgsz + 1)), fFalse);
  416. UpdateWindow(hWnd);
  417. if (fRetVal) {
  418. PostMessage(hWndShell, (WORD)STF_SHL_INTERP, 0, 0L);
  419. }
  420. return(fRetVal);
  421. }
  422. err:
  423. LoadString(hInst, IDS_ERROR, rgchBufTmpShort, cchpBufTmpShortMax);
  424. LoadString(hInst, IDS_UI_CMD_ERROR, rgchBufTmpLong, cchpBufTmpLongMax);
  425. MessageBox(hWndShell, rgchBufTmpLong, rgchBufTmpShort,
  426. MB_OK | MB_ICONHAND);
  427. UpdateWindow(hWnd);
  428. return(fFalse);
  429. }
  430. /*
  431. ** Purpose:
  432. ** Pushes a new context onto the context stack and executes the
  433. ** specified shell section of an INF file.
  434. **
  435. ** Arguments:
  436. **
  437. ** Returns:
  438. **
  439. **
  440. *************************************************************************/
  441. BOOL FShellCommand( RGSZ rgszArg )
  442. {
  443. SZ szInfFileOrg;
  444. SZ szInfFile;
  445. SZ szSection;
  446. PINFCONTEXT pNewContext;
  447. PINFTEMPINFO pTempInfo;
  448. PINFPERMINFO pPermInfo;
  449. GRC grc = grcOkay;
  450. CHAR szName[cchlFullPathMax];
  451. CHAR szFullName[cchlFullPathMax];
  452. BOOL fCreated = fFalse;
  453. INT Line;
  454. INT cArg = 0;
  455. BOOL fOkay = fTrue;
  456. SZ szNamePart;
  457. SZ p;
  458. pLocalContext()->CurrentLine++;
  459. //
  460. // Guarantee that $ShellCode is set correctly to !SHELL_CODE_OK.
  461. //
  462. while (!FAddSymbolValueToSymTab( "$ShellCode",
  463. SzFindSymbolValueInSymTab("!G:SHELL_CODE_OK") )) {
  464. if (!FHandleOOM(hWndShell)) {
  465. return(fFalse);
  466. }
  467. }
  468. //
  469. // Allocate a new context
  470. //
  471. while ( !(pNewContext = (PINFCONTEXT)SAlloc( (CB)sizeof(INFCONTEXT) )) ) {
  472. if (!FHandleOOM(hWndShell)) {
  473. return(fFalse);
  474. }
  475. }
  476. if ( **rgszArg == '\0' ) {
  477. //
  478. // Null INF file, use the one being used by the current context.
  479. //
  480. pTempInfo = pLocalInfTempInfo();
  481. pPermInfo = pLocalInfPermInfo();
  482. szInfFileOrg = SzFindSymbolValueInSymTab("STF_CONTEXTINFNAME");
  483. szInfFile = szInfFileOrg;
  484. } else {
  485. //
  486. // Determine if the desired INF file is already loaded.
  487. //
  488. szInfFileOrg = *rgszArg;
  489. PathToInfName( szInfFileOrg, szName );
  490. GetFullPathName( szInfFileOrg, cchlFullPathMax, szFullName, &szNamePart );
  491. szInfFile = szFullName;
  492. pPermInfo = NameToInfPermInfo( szName , fTrue );
  493. if ( pPermInfo ) {
  494. pTempInfo = pInfTempInfo( pGlobalContext() );
  495. while ( pTempInfo ) {
  496. if ( pTempInfo->pInfPermInfo == pPermInfo ) {
  497. break;
  498. }
  499. pTempInfo = pTempInfo->pNext;
  500. }
  501. } else {
  502. pTempInfo = NULL;
  503. }
  504. }
  505. rgszArg++;
  506. szSection = *rgszArg++;
  507. if ( pTempInfo ) {
  508. //
  509. // Reuse existing INF temp info. We just increment its reference count.
  510. //
  511. pNewContext->pInfTempInfo = pTempInfo;
  512. pTempInfo->cRef++;
  513. } else {
  514. //
  515. // We have to create a new INF temp info block for the INF.
  516. //
  517. fCreated = fTrue;
  518. while ( !(pNewContext->pInfTempInfo = (PINFTEMPINFO)CreateInfTempInfo( pPermInfo )) ) {
  519. if (!FHandleOOM(hWndShell)) {
  520. SFree(pNewContext);
  521. return(fFalse);
  522. }
  523. }
  524. //
  525. // Parse the INF file if we don't already have it parsed.
  526. //
  527. if ( pNewContext->pInfTempInfo->pParsedInf->MasterLineArray == NULL ) {
  528. while ((grc = GrcOpenInf(szInfFile, pNewContext->pInfTempInfo)) != grcOkay) {
  529. //
  530. // Could not open the INF file requested.
  531. //
  532. // If the INF file name given does not contain a path (i.e.
  533. // only the file part was given) then try to open the INF
  534. // with the same name in the directory of the global INF
  535. // file. If that fails, we try to open the INF in the
  536. // system directory.
  537. //
  538. szNamePart = szInfFileOrg;
  539. while ( p = strchr( szNamePart, '\\' ) ) {
  540. szNamePart = p+1;
  541. }
  542. strcpy( szName, szNamePart );
  543. if ( strlen( szInfFileOrg ) == strlen( szName ) ) {
  544. szInfFile = SzFindSymbolValueInSymTab("!G:STF_CONTEXTINFNAME");
  545. if ( szInfFile ) {
  546. strcpy( szFullName, szInfFile );
  547. szInfFile = szFullName;
  548. szNamePart = szInfFile;
  549. while ( p = strchr( szNamePart, '\\' ) ) {
  550. szNamePart = p+1;
  551. }
  552. strcpy( szNamePart, szName );
  553. grc = GrcOpenInf(szInfFile, pNewContext->pInfTempInfo);
  554. }
  555. if ( grc != grcOkay ) {
  556. //
  557. // Could not open that INF either, look for the INF in
  558. // the system directory
  559. //
  560. if ( GetSystemDirectory( szFullName, cchlFullPathMax ) ) {
  561. if ( szFullName[ strlen(szFullName) -1 ] != '\\' ) {
  562. strcat( szFullName, "\\" );
  563. }
  564. strcat( szFullName, szName );
  565. grc = GrcOpenInf(szFullName, pNewContext->pInfTempInfo);
  566. }
  567. }
  568. }
  569. if ( grc != grcOkay ) {
  570. FFreeInfTempInfo( pNewContext->pInfTempInfo );
  571. SFree(pNewContext);
  572. while (!FAddSymbolValueToSymTab( "$ShellCode",
  573. SzFindSymbolValueInSymTab("!G:SHELL_CODE_NO_SUCH_INF") )) {
  574. if (!FHandleOOM(hWndShell)) {
  575. return(fFalse);
  576. }
  577. }
  578. Line = pLocalContext()->CurrentLine;
  579. goto NextLine;
  580. }
  581. }
  582. }
  583. }
  584. //
  585. // We now have the INF Temp section in memory.
  586. // Push the new context onto the stack
  587. //
  588. if ( !PushContext( pNewContext ) ) {
  589. FFreeInfTempInfo(pNewContext->pInfTempInfo );
  590. SFree(pNewContext);
  591. //if ( pLocalContext() == pGlobalContext() ) {
  592. // return fFalse;
  593. //} else {
  594. while (!FAddSymbolValueToSymTab( "$ShellCode",
  595. SzFindSymbolValueInSymTab("!G:SHELL_CODE_ERROR") )) {
  596. if (!FHandleOOM(hWndShell)) {
  597. return(fFalse);
  598. }
  599. }
  600. Line = pLocalContext()->CurrentLine;
  601. goto NextLine;
  602. //}
  603. }
  604. pLocalContext()->szShlScriptSection = SzDupl( szSection );
  605. //
  606. // Get the media description list if there is a media description section
  607. //
  608. if ( fCreated &&
  609. !pLocalInfPermInfo()->psdleHead &&
  610. FindFirstLineFromInfSection("Source Media Descriptions") != -1) {
  611. while ( fOkay && ((grc = GrcFillSrcDescrListFromInf()) != grcOkay)) {
  612. //if ( pLocalContext() == pGlobalContext() ) {
  613. // if (EercErrorHandler(hWndShell, grc, fTrue, szInfFile, 0, 0)
  614. // != eercRetry) {
  615. // PopContext();
  616. // FFreeInfTempInfo(pNewContext->pInfTempInfo );
  617. // FreeContext( pNewContext );
  618. // return fFalse;
  619. // }
  620. //}
  621. PopContext();
  622. FFreeInfTempInfo(pNewContext->pInfTempInfo );
  623. FreeContext( pNewContext );
  624. while (!FAddSymbolValueToSymTab( "$ShellCode",
  625. SzFindSymbolValueInSymTab("!G:SHELL_CODE_ERROR") )) {
  626. if (!FHandleOOM(hWndShell)) {
  627. return(fFalse);
  628. }
  629. }
  630. Line = pLocalContext()->CurrentLine;
  631. goto NextLine;
  632. }
  633. }
  634. while (!FAddSymbolValueToSymTab("STF_CONTEXTINFNAME", szInfFile))
  635. if (!FHandleOOM(hWndShell)) {
  636. fOkay = fFalse;
  637. }
  638. //
  639. // Parameters are passed in the following symbols:
  640. //
  641. // $# - Number of parameters
  642. //
  643. // $0 - First parameter
  644. // $1 - Second parameter
  645. //
  646. // ... etc.
  647. //
  648. while ( fOkay && (*rgszArg != NULL) ) {
  649. sprintf( szName, "$%u", cArg );
  650. while (!FAddSymbolValueToSymTab( szName, *rgszArg)) {
  651. if (!FHandleOOM(hWndShell)) {
  652. fOkay = fFalse;
  653. break;
  654. }
  655. }
  656. cArg++;
  657. rgszArg++;
  658. }
  659. if ( fOkay ) {
  660. sprintf( szName, "%u", cArg );
  661. while (!FAddSymbolValueToSymTab( "$#", szName)) {
  662. if (!FHandleOOM(hWndShell)) {
  663. fOkay = fFalse;
  664. break;
  665. }
  666. }
  667. }
  668. if ( !fOkay ) {
  669. PopContext();
  670. FFreeInfTempInfo(pNewContext->pInfTempInfo );
  671. FreeContext( pNewContext );
  672. return fFalse;
  673. }
  674. if ((Line = FindFirstLineFromInfSection(szSection)) == -1) {
  675. //
  676. // Pop new context off the stack
  677. //
  678. PopContext();
  679. FFreeInfTempInfo( pNewContext->pInfTempInfo );
  680. FreeContext( pNewContext );
  681. //if ( pLocalContext() == pGlobalContext() ) {
  682. // return(fFalse);
  683. //} else {
  684. while (!FAddSymbolValueToSymTab( "$ShellCode",
  685. SzFindSymbolValueInSymTab("!G:SHELL_CODE_NO_SUCH_SECTION") )) {
  686. if (!FHandleOOM(hWndShell)) {
  687. return(fFalse);
  688. }
  689. }
  690. Line = pLocalContext()->CurrentLine;
  691. goto NextLine;
  692. //}
  693. }
  694. NextLine:
  695. //
  696. // Execute the specified Section in the new context
  697. //
  698. PostMessage(hWndShell, STF_SHL_INTERP, Line+1, 0L);
  699. return fTrue;
  700. }
  701. //
  702. // Storage for last return value
  703. //
  704. PSTR LastShellReturn;
  705. DWORD LastShellReturnSize;
  706. BOOL FShellReturn( RGSZ rgszArg )
  707. {
  708. PINFCONTEXT pOldContext;
  709. INT cArg = 0;
  710. BOOL fOkay = fTrue;
  711. BOOL fGlobalOkay = fTrue;
  712. CHAR szName[cchlFullPathMax];
  713. PSTR pwCur = LastShellReturn;
  714. UINT BufCnt = 0;
  715. UINT Temp;
  716. if ( pLocalContext() != pGlobalContext() ) {
  717. //
  718. // Deallocate the INF Temp Info.
  719. //
  720. FFreeInfTempInfo( pLocalInfTempInfo() );
  721. //
  722. // Pop Context from stack
  723. //
  724. pOldContext = PopContext();
  725. //
  726. // Destroy poped context
  727. //
  728. FreeContext( pOldContext );
  729. //
  730. // Results are stored in the ReturnBuffer using
  731. // the format: "<$R0>\0<$R1>\0...<$Rn>\0\0"
  732. //
  733. if(LastShellReturnSize > 1 && LastShellReturn) {
  734. LastShellReturn[0] = '\0';
  735. LastShellReturn[1] = '\0';
  736. BufCnt = 0;
  737. }
  738. //
  739. // Results are returned in the following symbols:
  740. //
  741. // $R# - Number of returned results
  742. //
  743. // $R0 - First result
  744. // $R1 - Second result
  745. //
  746. // ... etc.
  747. //
  748. while( rgszArg[cArg] != NULL) {
  749. //
  750. // Add element to return Buffer and update pointer to next
  751. // region to place an element. Make sure that element doesn't
  752. // overflow the buffer
  753. //
  754. Temp = strlen(rgszArg[cArg]) + 1;
  755. if( fGlobalOkay && (BufCnt + Temp) < LastShellReturnSize) {
  756. strcat( pwCur, rgszArg[cArg] );
  757. BufCnt += Temp;
  758. pwCur += Temp;
  759. *pwCur = '\0';
  760. } else {
  761. //
  762. // If we can not add an element to the buffer then we don't
  763. // want to just skip it, so note a reminder to stop adding
  764. // items into the global return buffer
  765. //
  766. fGlobalOkay = FALSE;
  767. }
  768. sprintf( szName, "$R%u",cArg);
  769. while (!FAddSymbolValueToSymTab( szName, rgszArg[cArg])) {
  770. if (!FHandleOOM(hWndShell)) {
  771. fOkay = fFalse;
  772. break;
  773. }
  774. }
  775. if ( !fOkay ) {
  776. break;
  777. }
  778. cArg++;
  779. }
  780. if ( fOkay ) {
  781. sprintf( szName, "%u", cArg );
  782. while (!FAddSymbolValueToSymTab( "$R#", szName)) {
  783. if (!FHandleOOM(hWndShell)) {
  784. fOkay = fFalse;
  785. break;
  786. }
  787. }
  788. }
  789. //
  790. // Resume execution at the next line of the parent context.
  791. //
  792. PostMessage(hWndShell, STF_SHL_INTERP, pLocalContext()->CurrentLine+1, 0L);
  793. }
  794. return fOkay;
  795. }