Changeset 4090 for branches/GRACE/src/win32k/pe2lx/pe2lx.cpp
- Timestamp:
- Aug 25, 2000, 6:47:28 AM (25 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
branches/GRACE/src/win32k/pe2lx/pe2lx.cpp
r4076 r4090 1 /* $Id: pe2lx.cpp,v 1.18.4. 7 2000-08-24 01:36:26 bird Exp $1 /* $Id: pe2lx.cpp,v 1.18.4.8 2000-08-25 04:47:26 bird Exp $ 2 2 * 3 3 * Pe2Lx class implementation. Ring 0 and Ring 3 … … 95 95 #ifdef RING0 96 96 #include "ldrCalls.h" /* ldr* calls. (ldrRead) */ 97 #include "avl.h" /* AVL tree. (ldr.h need it) */ 98 #include "ldr.h" /* ldr helpers. (ldrGetExePath) */ 99 #include "env.h" /* Environment helpers. */ 97 100 #endif 98 101 #include "modulebase.h" /* ModuleBase class definitions, ++. */ … … 173 176 LONG Pe2Lx::cLoadedModules; /* Count of existing objects. Updated by constructor and destructor. */ 174 177 const char * Pe2Lx::pszOdin32Path; /* Odin32 base path (include a slash). */ 178 ULONG Pe2Lx::cchOdin32Path; /* Odin32 base path length. */ 175 179 SFN Pe2Lx::sfnKernel32; /* Odin32 Kernel32 filehandle. */ 176 180 … … 1308 1312 * @returns OS2 return code. 1309 1313 * pLdrLv->lv_sfn is set to filename handle. 1310 * @param pach Modname Pointer to modulename. Not zero terminated!1311 * @param cch Modname Modulename length.1314 * @param pachFilename Pointer to filename. Not zero terminated! 1315 * @param cchFilename Filename length. 1312 1316 * @param pLdrLv Loader local variables? (Struct from KERNEL.SDF) 1313 * @param pf lPointer to flags which are passed on to ldrOpen.1317 * @param pful Pointer to flags which are passed on to ldrOpen. 1314 1318 * @sketch 1315 1319 * This is roughly what the original ldrOpenPath does: … … 1324 1328 * endif 1325 1329 */ 1326 ULONG Pe2Lx::openPath(PCHAR pach Modname, USHORT cchModname, ldrlv_t *pLdrLv, PULONG pfl) /* (ldrOpenPath) */1330 ULONG Pe2Lx::openPath(PCHAR pachFilename, USHORT cchFilename, ldrlv_t *pLdrLv, PULONG pful) /* (ldrOpenPath) */ 1327 1331 { 1328 1332 #ifdef RING0 1329 #if 1 1330 initOdin32Path(); 1331 return ldrOpenPath(pachModname, cchModname, pLdrLv, pfl); 1333 1334 /* 1335 * Mark the SFN invalid in the case of error. 1336 * Initiate the Odin32 Path static variable and call worker. 1337 */ 1338 return openPath2(pachFilename, cchFilename, pLdrLv, pful, initOdin32Path()); 1339 1332 1340 #else 1333 1341 NOREF(pachFilename); 1342 NOREF(cchFilename); 1343 NOREF(pLdrLv); 1344 NOREF(pful); 1345 return ERROR_NOT_SUPPORTED; 1346 #endif 1347 } 1348 1349 1350 /** 1351 * openPath2 - Worker for openPath which is also used by initOdin32Path. 1352 * 1353 * @returns OS2 return code. 1354 * pLdrLv->lv_sfn is set to filename handle. 1355 * @param pachFilename Pointer to filename. Not zero terminated! 1356 * @param cchFilename Filename length. 1357 * @param pLdrLv Loader local variables? (Struct from KERNEL.SDF) 1358 * @param pful Pointer to flags which are passed on to ldrOpen. 1359 * @param fOdin32PathValid Flag indicating that the pszOdin32Path is valid or not. 1360 * @sketch 1361 * This is roughly what the original ldrOpenPath does: 1362 * if !CLASS_GLOBAL or miniifs then 1363 * ldrOpen(pachModName) 1364 * else 1365 * loop until no more libpath elements 1366 * get next libpath element and add it to the modname. 1367 * try open the modname 1368 * if successfull then break the loop. 1369 * endloop 1370 * endif 1371 */ 1372 ULONG Pe2Lx::openPath2(PCHAR pachFilename, USHORT cchFilename, ldrlv_t *pLdrLv, PULONG pful, BOOL fOdin32PathValid) 1373 { 1374 #ifdef RING0 1375 1376 APIRET rc; /* Returncode. */ 1377 ULONG cchExt; /* Count of chars in additional extention. (0 if extention exists.) */ 1334 1378 1335 1379 /* These defines sets the order the paths and pathlists are examined. */ … … 1340 1384 #define FINDDLL_WINDIR 5 1341 1385 #define FINDDLL_PATH 6 1342 #define FINDDLL_BEGINLIBPATH 7 1343 #define FINDDLL_LIBPATH 8 1344 #define FINDDLL_ENDLIBPATH 9 1386 #define FINDDLL_BEGINLIBPATH 7 /* uses ldrOpenPath */ 1387 #define FINDDLL_LIBPATH 8 /* uses ldrOpenPath */ 1388 #define FINDDLL_ENDLIBPATH 9 /* uses ldrOpenPath */ 1345 1389 #define FINDDLL_FIRST FINDDLL_EXECUTABLEDIR 1346 #define FINDDLL_LAST FINDDLL_ ENDLIBPATH1390 #define FINDDLL_LAST FINDDLL_PATH 1347 1391 1348 1392 struct _LocalVars 1349 1393 { 1350 1394 char sz[CCHMAXPATH]; 1395 char szPath[CCHMAXPATH]; 1351 1396 } *pVars; 1352 1397 1353 1398 1354 /* 1399 /** @sketch 1355 1400 * Mark the SFN invalid in the case of error. 1356 * Initiate the Odin32 Path static variable.1357 1401 * Allocate memory for local variables. 1402 * Check for extention. 1358 1403 */ 1359 1404 pLdrLv->lv_sfn = 0xffff; 1360 initOdin32Path();1361 1405 pVars = (struct _LocalVars*)rmalloc(sizeof(struct _LocalVars)); 1362 1406 if (pVars == NULL) 1363 1407 return ERROR_NOT_ENOUGH_MEMORY; 1364 1408 1365 /* init stuff */ 1366 1367 1409 cchExt = cchFilename - 1; 1410 while (cchExt != 0 && pachFilename[cchExt] != '.') 1411 cchExt--; 1412 cchExt = cchExt != 0 ? 0 : 4; 1368 1413 1369 1414 … … 1373 1418 for (int iPath = FINDDLL_FIRST; iPath <= FINDDLL_LAST; iPath++) 1374 1419 { 1375 APIRET rc; /* Returncode from OS/2 APIs. */ 1376 const char * pszPath; /* Pointer to the path being examined. */ 1420 char * pszPath; /* Pointer to the path being examined. */ 1377 1421 1378 1422 /** @sketch … … 1382 1426 { 1383 1427 case FINDDLL_EXECUTABLEDIR: 1384 if (pszAltPath) 1385 pszPath = strcpy(plv->szPath, pszAltPath); 1386 else 1387 { 1388 /* ASSUMES: getFullPath allways returns a fully qualified 1389 * path, ie. with at least one backslash. and that all 1390 * slashes are backslashes! 1391 */ 1392 if (!WinExe) continue; 1393 pszPath = strcpy(plv->szPath, WinExe->getFullPath()); 1394 } 1395 psz = strrchr(plv->szPath, '\\'); 1396 dassert(psz, ("KERNEL32:Win32ImageBase::findDll(%s, 0x%08x, %d): " 1397 "WinExe->getFullPath returned a path not fully qualified: %s", 1398 pszFileName, pszFullName, cchFullName, pszPath)); 1399 if (psz) 1400 *psz = '\0'; 1401 else 1428 if ((pszPath = ldrGetExePath(pVars->szPath, TRUE)) == NULL) 1402 1429 continue; 1403 1430 break; … … 1408 1435 1409 1436 case FINDDLL_SYSTEM32DIR: 1410 pszPath = InternalGetSystemDirectoryA(); 1437 if (!fOdin32PathValid) 1438 continue; 1439 pszPath = pVars->szPath; 1440 strcpy(pszPath, pszOdin32Path); 1441 strcpy(pszPath + cchOdin32Path, "System32"); 1411 1442 break; 1412 1443 1413 1444 case FINDDLL_SYSTEM16DIR: 1414 #if 1 1415 continue; /* Skip this index */ 1416 #else 1417 pszPath = InternalGetWindowsDirectoryA(); 1418 strcpy(plv->sz2, InternalGetWindowsDirectoryA()); 1419 strcat(plv->sz2, "\SYSTEM"); 1445 if (!fOdin32PathValid) 1446 continue; 1447 pszPath = pVars->szPath; 1448 strcpy(pszPath, pszOdin32Path); 1449 strcpy(pszPath + cchOdin32Path, "System"); 1420 1450 break; 1421 #endif1422 1451 1423 1452 case FINDDLL_WINDIR: 1424 pszPath = InternalGetWindowsDirectoryA(); 1453 if (!fOdin32PathValid) 1454 continue; 1455 pszPath = pVars->szPath; 1456 strcpy(pszPath, pszOdin32Path); 1457 pszPath[cchOdin32Path - 1] = '\0'; /* remove slash */ 1425 1458 break; 1426 1459 1427 1460 case FINDDLL_PATH: 1428 pszPath = getenv("PATH"); 1461 pszPath = (char*)GetEnv(TRUE); 1462 if (pszPath == NULL) 1463 continue; 1464 pszPath = (char*)ScanEnv(pszPath, "PATH"); 1429 1465 break; 1430 1466 1467 #if 0 1431 1468 case FINDDLL_BEGINLIBPATH: 1432 rc = DosQueryExtLIBPATH(plv->szPath, BEGIN_LIBPATH); 1433 if (rc != NO_ERROR) 1434 { 1435 dassert(rc == NO_ERROR, ("KERNEL32:Win32ImageBase::findDll(%s, 0x%08x, %d): " 1436 "DosQueryExtLIBPATH failed with rc=%d, iPath=%d", 1437 pszFileName, pszFullName, cchFullName, rc, iPath)); 1469 pszPath = ptda_GetBeginLibpath()... ; 1470 if (pszPath == NULL) 1438 1471 continue; 1439 }1440 pszPath = plv->szPath;1441 1472 break; 1442 1473 1443 1474 case FINDDLL_LIBPATH: 1444 rc = DosQueryHeaderInfo(NULLHANDLE, 0, plv->szPath, sizeof(plv->szPath), QHINF_LIBPATH);1445 if (rc != NO_ERROR)1446 { 1447 dassert(rc == NO_ERROR, ("KERNEL32:Win32ImageBase::findDll(%s, 0x%08x, %d): "1448 "DosQueryHeaderInfo failed with rc=%d, iPath=%d",1449 pszFileName, pszFullName, cchFullName, rc, iPath));1475 pszPath = *pLdrLibPath; 1476 break; 1477 1478 case FINDDLL_ENDLIBPATH: 1479 pszPath = ptda_GetEndLibpath()... ; 1480 if (pszPath == NULL) 1450 1481 continue; 1451 }1452 pszPath = plv->szPath;1453 1482 break; 1454 1455 case FINDDLL_ENDLIBPATH: 1456 rc = DosQueryExtLIBPATH(plv->szPath, END_LIBPATH); 1457 if (rc != NO_ERROR) 1458 { 1459 dassert(rc == NO_ERROR, ("KERNEL32:Win32ImageBase::findDll(%s, 0x%08x, %d): " 1460 "DosQueryExtLIBPATH failed with rc=%d, iPath=%d", 1461 pszFileName, pszFullName, cchFullName, rc, iPath)); 1462 continue; 1463 } 1464 pszPath = plv->szPath; 1465 break; 1466 1483 #endif 1467 1484 default: /* !internalerror! */ 1468 goto end; 1485 printIPE(("Pe2Lx::openPath(%.*s,..): iPath is %d which is invalid.\n", cchFilename, pachFilename, iPath)); 1486 rfree(pVars); 1487 return ERROR_FILE_NOT_FOUND; 1469 1488 } 1470 1489 … … 1476 1495 while (pszPath != NULL && *pszPath != '\0') 1477 1496 { 1478 HDIR hDir; /* Find handle used when calling FindFirst. */1479 ULONG culFiles; /* Number of files to find / found. */1480 1497 char * pszNext; /* Pointer to the next pathlist path */ 1481 1498 int cch; /* Length of path (including the slash after the slash is added). */ 1482 1499 1483 1500 /** @sketch 1484 * Find the end of the path .1485 * Copy the path into the plv->sz buffer.1486 * Set pszNext.1501 * Find the end of the path and set pszNext. 1502 * Uncount any trailing slash. 1503 * Check that the filename fits within the buffer (and OS/2 filelength limits). 1487 1504 */ 1488 1505 pszNext = strchr(pszPath, ';'); … … 1495 1512 cch = strlen(pszPath); 1496 1513 1497 if (cch + cchFileName + 1 >= sizeof(plv->sz)) /* assertion */ 1514 if (pszPath[cch - 1] == '\\' || pszPath[cch-1] == '/') 1515 cch--; 1516 1517 if (cch == 0 || cch + cchFilename + 2 + cchExt > sizeof(pVars->sz)) /* assertion */ 1498 1518 { 1499 dassert(cch + cchFileName + 1 < sizeof(plv->sz), ("KERNEL32:Win32ImageBase::findDll(%s, 0x%08x, %d): "1500 "cch (%d) + cchFileName (%d) + 1 < sizeof(plv->sz) (%d) - paths too long!, iPath=%d",1501 pszFileName, pszFullName, cchFullName, cch, cchFileName, sizeof(plv->sz), iPath)); 1519 printErr(("Pe2Lx::openPath(%.*s,..): cch (%d) + cchFilename (%d) + 2 + cchExt (%d) > sizeof(pVars->sz) (%d) - path's too long!, iPath=%d", 1520 cchFilename, pachFilename, cch, cchExt, cchFilename, sizeof(pVars->sz), iPath)); 1521 1502 1522 pszPath = pszNext; 1503 1523 continue; 1504 1524 } 1505 memcpy(plv->sz, pszPath, cch); //arg! Someone made strncpy not work as supposed!1506 1525 1507 1526 1508 1527 /** @sketch 1528 * Copy the path into the pVars->sz buffer. 1509 1529 * Add a '\\' and the filename (pszFullname) to the path; 1510 1530 * then we'll have a fullpath. 1511 1531 */ 1512 plv->sz[cch++] = '\\'; 1513 strcpy(&plv->sz[cch], pszFullName); 1532 memcpy(pVars->sz, pszPath, cch); 1533 pVars->sz[cch++] = '\\'; 1534 memcpy(&pVars->sz[cch], pachFilename, cchFilename); 1535 if (cchExt != 0) 1536 memcpy(&pVars->sz[cch + cchFilename], ".DLL", 5); 1537 else 1538 pVars->sz[cch + cchFilename] = '\0'; 1514 1539 1515 1540 1516 1541 /** @sketch 1517 * Use DosFindFirst to check if the file exists. 1518 * IF the file exists THEN 1519 * Query Fullpath using OS/2 API. 1520 * IF unsuccessful THEN return relative name. 1521 * Check that the fullname buffer is large enough. 1522 * Copy the filename found to the fullname buffer. 1523 * ENDIF 1524 * IF successful THEN uppercase the fullname buffer. 1525 * goto end 1526 * ENDIF 1542 * Try open the file using myLdrOpen. 1543 * Return if successfully opened or if fatal error. 1527 1544 */ 1528 hDir = HDIR_CREATE; 1529 culFiles = 1; 1530 rc = DosFindFirst(plv->sz, &hDir, FILE_NORMAL, 1531 &plv->findbuf3, sizeof(plv->findbuf3), 1532 &culFiles, FIL_STANDARD); 1533 DosFindClose(hDir); 1534 if (culFiles >= 1 && rc == NO_ERROR) 1545 rc = myldrOpen(&pLdrLv->lv_sfn, pVars->sz, pful); 1546 switch (rc) 1535 1547 { 1536 /* Return full path - we'll currently return a relative path. */ 1537 rc = DosQueryPathInfo(plv->sz, FIL_QUERYFULLNAME, pszFullName, cchFullName); 1538 fRet = rc == NO_ERROR; 1539 if (!fRet) 1540 { 1541 /* Return a relative path - probably better that failing... */ 1542 dassert(rc == NO_ERROR, ("KERNEL32:Win32ImageBase::findDll(%s, 0x%08x, %d): " 1543 "rc = %d", 1544 pszFileName, pszFullName, cchFullName, rc)); 1545 1546 if (cch + cchFileName + 1 <= cchFullName) 1547 { 1548 strcpy(pszFullName, plv->sz); 1549 strcpy(pszFullName + cch, plv->findbuf3.achName); 1550 fRet = TRUE; 1551 } 1552 else 1553 { 1554 dassert(cch + cchFileName + 1 > cchFullName, ("KERNEL32:Win32ImageBase::findDll(%s, 0x%08x, %d): " 1555 "cch (%d) + cchFileName (%d) + 1 < cchFullName (%d); %s", 1556 pszFileName, pszFullName, cchFullName, cch, cchFileName, cchFullName, plv->sz)); 1557 } 1558 } 1559 if (fRet) strupr(pszFullName); 1560 goto end; 1548 /* these errors are ignored */ 1549 case ERROR_FILE_NOT_FOUND: case ERROR_PATH_NOT_FOUND: case ERROR_ACCESS_DENIED: case ERROR_INVALID_ACCESS: 1550 case ERROR_INVALID_DRIVE: case ERROR_NOT_DOS_DISK: case ERROR_REM_NOT_LIST: case ERROR_BAD_NETPATH: 1551 case ERROR_NETWORK_BUSY: case ERROR_DEV_NOT_EXIST: case ERROR_TOO_MANY_CMDS: case ERROR_ADAP_HDW_ERR: 1552 case ERROR_UNEXP_NET_ERR: case ERROR_BAD_REM_ADAP: case ERROR_NETNAME_DELETED: case ERROR_BAD_DEV_TYPE: 1553 case ERROR_NETWORK_ACCESS_DENIED: case ERROR_BAD_NET_NAME: case ERROR_TOO_MANY_SESS: case ERROR_REQ_NOT_ACCEP: 1554 case ERROR_INVALID_PASSWORD: case ERROR_OPEN_FAILED: case ERROR_INVALID_NAME: case ERROR_FILENAME_EXCED_RANGE: 1555 case ERROR_VC_DISCONNECTED: 1556 rc = ERROR_FILE_NOT_FOUND; 1557 pszPath = pszNext; 1558 break; 1559 1560 /* all errors and success is let out here */ 1561 case NO_ERROR: 1562 default: 1563 rfree(pVars); 1564 return rc; 1561 1565 } 1562 1566 1567 /** @sketch 1568 * Advance to the next path part 1569 */ 1563 1570 pszPath = pszNext; 1564 1571 } … … 1566 1573 1567 1574 1568 end:1569 1575 /* 1570 1576 * Cleanup: free local variables. 1577 * Since we haven't found the file yet we'll return thru ldrOpenPath. 1571 1578 */ 1572 free(plv); 1573 return fRet; 1574 1575 1576 1577 1578 1579 return ldrOpenPath(pachModname, cchModname, pLdrLv, pfl); 1580 #endif 1579 rfree(pVars); 1580 return ldrOpenPath(pachFilename, cchFilename, pLdrLv, pful); 1581 1581 1582 #else 1582 NOREF(pach Modname);1583 NOREF(cch Modname);1583 NOREF(pachFilename); 1584 NOREF(cchFilename); 1584 1585 NOREF(pLdrLv); 1585 NOREF(pf l);1586 NOREF(pful); 1586 1587 return ERROR_NOT_SUPPORTED; 1587 1588 #endif 1588 1589 } 1589 1590 1591 1590 1592 1591 … … 4690 4689 * Initiates the odin32path. 4691 4690 * @returns Success indicator. 4692 * @sketch 4691 * @sketch If allready inited ok Then do nothing return TRUE. 4692 * 4693 * Check if KERNEL32 is loaded using ldrFindModule. 4694 * If loaded then set path according to the smte_path and return. 4695 * 4696 * If the path is set to something then return TRUE. (ie. the following method is allready applied.) 4697 * 4698 * Use odinPath2 to locate the KERNEL32 module in the LIBPATHs. The 4699 * win32k loaders are temporarily disabled. Path is returned in 4700 * the ldrpFileNameBuf buffer. 4701 * If found the Then set path according to ldrpFileNameBuf and return 4702 * 4703 * Fail returning FALSE. 4693 4704 * @status 4694 4705 * @author knut st. osmundsen (knut.stange.osmundsen@mynd.no) … … 4736 4747 * 4737 4748 * For the time being: 4738 * We'll use ldrOpenPathto do this, but we'll have to4749 * We'll use odinPath2 to do this, but we'll have to 4739 4750 * disable the win32k.sys overloading temporarily. 4740 4751 */ … … 4746 4757 options.fNoLoader = TRUE; 4747 4758 lv.lv_class = CLASS_GLOBAL; 4748 rc = ldrOpenPath("KERNEL32", 8, (ldrlv_t*)SSToDS(&lv), (PULONG)SSToDS(&ful));4759 rc = openPath2("KERNEL32", 8, (ldrlv_t*)SSToDS(&lv), (PULONG)SSToDS(&ful), FALSE); 4749 4760 options.fNoLoader = ul; 4750 4761 if (rc == NO_ERROR) … … 4761 4772 } 4762 4773 4763 return rc == NO_ERROR; 4764 #else 4774 #endif 4765 4775 return FALSE; 4766 #endif4767 4776 } 4768 4777 … … 4780 4789 BOOL Pe2Lx::setOdin32Path(const char *psz) 4781 4790 { 4782 const char * pszEnd; 4783 char * pszPath; 4791 const char * psz2; 4784 4792 4785 4793 /* … … 4787 4795 * and one directory up. We assume a fully qualified path. 4788 4796 */ 4789 pszEnd = psz + strlen(psz) - 1; 4790 while (pszEnd > psz && *pszEnd != '\\' && *pszEnd != '/' && *pszEnd != ':') 4791 pszEnd--; 4792 pszEnd--; 4793 while (pszEnd > psz && *pszEnd != '\\' && *pszEnd != '/' && *pszEnd != ':') 4794 pszEnd--; 4795 if (pszEnd > psz) 4796 { 4797 psz2 = psz + strlen(psz) - 1; 4798 while (psz2 > psz && *psz2 != '\\' && *psz2 != '/' && *psz2 != ':') 4799 psz2--; 4800 psz2--; 4801 while (psz2 > psz && *psz2 != '\\' && *psz2 != '/' && *psz2 != ':') 4802 psz2--; 4803 if (psz2 > psz) 4804 { 4805 char *pszPath; 4797 4806 /* 4798 4807 * Free old path (if any) and allocate space for a new path. … … 4802 4811 if (pszOdin32Path) 4803 4812 rfree((void*)pszOdin32Path); 4804 if (*pszEnd == ':') //in case someone installed odin in a root directory. 4805 pszEnd++; 4806 pszEnd++; //include the slash 4807 pszPath = (char*)rmalloc(pszEnd - psz); 4813 if (*psz2 == ':') //in case someone installed odin in a root directory. 4814 psz2++; 4815 psz2++; //include the slash 4816 cchOdin32Path = psz2 - psz; 4817 pszPath = (char*)rmalloc((size_t)cchOdin32Path); 4808 4818 if (pszPath == NULL) return FALSE; 4809 memcpy(pszPath, psz, pszEnd - psz);4810 pszPath[ pszEnd - psz] = '\0';4819 memcpy(pszPath, psz, (size_t)cchOdin32Path); 4820 pszPath[cchOdin32Path] = '\0'; 4811 4821 pszOdin32Path = pszPath; 4812 4822
Note:
See TracChangeset
for help on using the changeset viewer.