Leaked source code of windows server 2003
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.

1457 lines
38 KiB

  1. /*++
  2. Copyright (c) 1998 Microsoft Corporation
  3. Module Name:
  4. register.c
  5. Abstract:
  6. Terminal server register command support functions
  7. Author:
  8. Revision History:
  9. --*/
  10. #include "precomp.h"
  11. #pragma hdrstop
  12. //
  13. // Terminal Server 4.0 has a feature that allows DLL's to be registered SYSTEM
  14. // global. This means all named objects are in the system name space. Such
  15. // a DLL is identified by a bit set in LoaderFlags in the image header.
  16. //
  17. // This module supports this feature by redirecting WIN32 named object API's
  18. // for DLL's with this bit set to a set of functions inside of
  19. // tsappcmp.dll. These stub functions will process the object name and
  20. // call the real kernel32.dll WIN32 functions.
  21. //
  22. // The redirection is accomplished by updating the Import Address Table (IAT)
  23. // after the loader has snapped its thunks. This results in no modification
  24. // of the underlying program or DLL, just updating of the run time system
  25. // linkage table for this process.
  26. //
  27. // ***This only occurs on Terminal Server, and for applications or DLL's
  28. // with this bit set***
  29. //
  30. // \nt\public\sdk\inc\ntimage.h
  31. // GlobalFlags in image, currently not used
  32. #define IMAGE_LOADER_FLAGS_SYSTEM_GLOBAL 0x01000000
  33. #define GLOBALPATHA "Global\\"
  34. #define GLOBALPATHW L"Global\\"
  35. #define GLOBALPATHSIZE 7 * sizeof( WCHAR );
  36. extern DWORD g_dwFlags;
  37. enum {
  38. Index_Func_CreateEventA = 0,
  39. Index_Func_CreateEventW,
  40. Index_Func_OpenEventA,
  41. Index_Func_OpenEventW,
  42. Index_Func_CreateSemaphoreA,
  43. Index_Func_CreateSemaphoreW,
  44. Index_Func_OpenSemaphoreA,
  45. Index_Func_OpenSemaphoreW,
  46. Index_Func_CreateMutexA,
  47. Index_Func_CreateMutexW,
  48. Index_Func_OpenMutexA,
  49. Index_Func_OpenMutexW,
  50. Index_Func_CreateFileMappingA,
  51. Index_Func_CreateFileMappingW,
  52. Index_Func_OpenFileMappingA,
  53. Index_Func_OpenFileMappingW
  54. };
  55. enum {
  56. Index_Func_LoadLibraryA = 0,
  57. Index_Func_LoadLibraryW ,
  58. Index_Func_LoadLibraryExA ,
  59. Index_Func_LoadLibraryExW
  60. };
  61. typedef struct _LDR_TABLE {
  62. struct _LDR_TABLE *pNext;
  63. PLDR_DATA_TABLE_ENTRY pItem;
  64. } LDR_TABLE;
  65. LDR_TABLE g_LDR_TABLE_LIST_HEAD;
  66. typedef HANDLE ( APIENTRY Func_CreateEventA )( LPSECURITY_ATTRIBUTES lpEventAttributes, BOOL bManualReset, BOOL bInitialState, LPCSTR lpName );
  67. HANDLE
  68. APIENTRY
  69. TCreateEventA(
  70. LPSECURITY_ATTRIBUTES lpEventAttributes,
  71. BOOL bManualReset,
  72. BOOL bInitialState,
  73. LPCSTR lpName
  74. );
  75. typedef HANDLE ( APIENTRY Func_CreateEventW) ( LPSECURITY_ATTRIBUTES lpEventAttributes, BOOL bManualReset, BOOL bInitialState, LPCWSTR lpName );
  76. HANDLE
  77. APIENTRY
  78. TCreateEventW(
  79. LPSECURITY_ATTRIBUTES lpEventAttributes,
  80. BOOL bManualReset,
  81. BOOL bInitialState,
  82. LPCWSTR lpName
  83. );
  84. typedef HANDLE ( APIENTRY Func_OpenEventA) ( DWORD dwDesiredAccess, BOOL bInheritHandle, LPCSTR lpName );
  85. HANDLE
  86. APIENTRY
  87. TOpenEventA(
  88. DWORD dwDesiredAccess,
  89. BOOL bInheritHandle,
  90. LPCSTR lpName
  91. );
  92. typedef HANDLE ( APIENTRY Func_OpenEventW ) ( DWORD dwDesiredAccess, BOOL bInheritHandle, LPCWSTR lpName );
  93. HANDLE
  94. APIENTRY
  95. TOpenEventW(
  96. DWORD dwDesiredAccess,
  97. BOOL bInheritHandle,
  98. LPCWSTR lpName
  99. );
  100. typedef HANDLE ( APIENTRY Func_CreateSemaphoreA) ( LPSECURITY_ATTRIBUTES lpSemaphoreAttributes, LONG lInitialCount, LONG lMaximumCount, LPCSTR lpName );
  101. HANDLE
  102. APIENTRY
  103. TCreateSemaphoreA(
  104. LPSECURITY_ATTRIBUTES lpSemaphoreAttributes,
  105. LONG lInitialCount,
  106. LONG lMaximumCount,
  107. LPCSTR lpName
  108. );
  109. typedef HANDLE ( APIENTRY Func_CreateSemaphoreW) ( LPSECURITY_ATTRIBUTES lpSemaphoreAttributes, LONG lInitialCount, LONG lMaximumCount, LPCWSTR lpName ) ;
  110. HANDLE
  111. APIENTRY
  112. TCreateSemaphoreW(
  113. LPSECURITY_ATTRIBUTES lpSemaphoreAttributes,
  114. LONG lInitialCount,
  115. LONG lMaximumCount,
  116. LPCWSTR lpName
  117. ) ;
  118. typedef HANDLE ( APIENTRY Func_OpenSemaphoreA) ( DWORD dwDesiredAccess, BOOL bInheritHandle, LPCSTR lpName );
  119. HANDLE
  120. APIENTRY
  121. TOpenSemaphoreA(
  122. DWORD dwDesiredAccess,
  123. BOOL bInheritHandle,
  124. LPCSTR lpName
  125. );
  126. typedef HANDLE ( APIENTRY Func_OpenSemaphoreW ) ( DWORD dwDesiredAccess, BOOL bInheritHandle, LPCWSTR lpName );
  127. HANDLE
  128. APIENTRY
  129. TOpenSemaphoreW(
  130. DWORD dwDesiredAccess,
  131. BOOL bInheritHandle,
  132. LPCWSTR lpName
  133. );
  134. typedef HANDLE ( APIENTRY Func_CreateMutexA ) ( LPSECURITY_ATTRIBUTES lpMutexAttributes, BOOL bInitialOwner, LPCSTR lpName );
  135. HANDLE
  136. APIENTRY
  137. TCreateMutexA(
  138. LPSECURITY_ATTRIBUTES lpMutexAttributes,
  139. BOOL bInitialOwner,
  140. LPCSTR lpName
  141. );
  142. typedef HANDLE ( APIENTRY Func_CreateMutexW) ( LPSECURITY_ATTRIBUTES lpMutexAttributes, BOOL bInitialOwner, LPCWSTR lpName );
  143. HANDLE
  144. APIENTRY
  145. TCreateMutexW(
  146. LPSECURITY_ATTRIBUTES lpMutexAttributes,
  147. BOOL bInitialOwner,
  148. LPCWSTR lpName
  149. );
  150. typedef HANDLE ( APIENTRY Func_OpenMutexA ) ( DWORD dwDesiredAccess, BOOL bInheritHandle, LPCSTR lpName );
  151. HANDLE
  152. APIENTRY
  153. TOpenMutexA(
  154. DWORD dwDesiredAccess,
  155. BOOL bInheritHandle,
  156. LPCSTR lpName
  157. );
  158. typedef HANDLE ( APIENTRY Func_OpenMutexW) ( DWORD dwDesiredAccess, BOOL bInheritHandle, LPCWSTR lpName );
  159. HANDLE
  160. APIENTRY
  161. TOpenMutexW(
  162. DWORD dwDesiredAccess,
  163. BOOL bInheritHandle,
  164. LPCWSTR lpName
  165. );
  166. typedef HANDLE ( APIENTRY Func_CreateFileMappingA) ( HANDLE hFile, LPSECURITY_ATTRIBUTES lpFileMappingAttributes, DWORD flProtect, DWORD dwMaximumSizeHigh, DWORD dwMaximumSizeLow, LPCSTR lpName );
  167. HANDLE
  168. APIENTRY
  169. TCreateFileMappingA(
  170. HANDLE hFile,
  171. LPSECURITY_ATTRIBUTES lpFileMappingAttributes,
  172. DWORD flProtect,
  173. DWORD dwMaximumSizeHigh,
  174. DWORD dwMaximumSizeLow,
  175. LPCSTR lpName
  176. );
  177. typedef HANDLE ( APIENTRY Func_CreateFileMappingW ) ( HANDLE hFile, LPSECURITY_ATTRIBUTES lpFileMappingAttributes, DWORD flProtect, DWORD dwMaximumSizeHigh, DWORD dwMaximumSizeLow, LPCWSTR lpName );
  178. HANDLE
  179. APIENTRY
  180. TCreateFileMappingW(
  181. HANDLE hFile,
  182. LPSECURITY_ATTRIBUTES lpFileMappingAttributes,
  183. DWORD flProtect,
  184. DWORD dwMaximumSizeHigh,
  185. DWORD dwMaximumSizeLow,
  186. LPCWSTR lpName
  187. );
  188. typedef HANDLE ( APIENTRY Func_OpenFileMappingA ) ( DWORD dwDesiredAccess, BOOL bInheritHandle, LPCSTR lpName ) ;
  189. HANDLE
  190. APIENTRY
  191. TOpenFileMappingA(
  192. DWORD dwDesiredAccess,
  193. BOOL bInheritHandle,
  194. LPCSTR lpName
  195. ) ;
  196. typedef HANDLE ( APIENTRY Func_OpenFileMappingW ) ( DWORD dwDesiredAccess, BOOL bInheritHandle, LPCWSTR lpName );
  197. HANDLE
  198. APIENTRY
  199. TOpenFileMappingW(
  200. DWORD dwDesiredAccess,
  201. BOOL bInheritHandle,
  202. LPCWSTR lpName
  203. ) ;
  204. typedef HMODULE ( WINAPI Func_LoadLibraryExA )(LPCSTR , HANDLE , DWORD );
  205. HMODULE
  206. TLoadLibraryExA(
  207. LPCSTR lpLibFileName,
  208. HANDLE hFile,
  209. DWORD dwFlags
  210. );
  211. typedef HMODULE ( WINAPI Func_LoadLibraryExW )( LPCWSTR , HANDLE , DWORD );
  212. HMODULE
  213. TLoadLibraryExW(
  214. LPCWSTR lpwLibFileName,
  215. HANDLE hFile,
  216. DWORD dwFlags
  217. );
  218. typedef HMODULE ( WINAPI Func_LoadLibraryA )( LPCSTR );
  219. HMODULE
  220. TLoadLibraryA(
  221. LPCSTR lpLibFileName
  222. );
  223. typedef HMODULE ( WINAPI Func_LoadLibraryW )( LPCWSTR );
  224. HMODULE
  225. TLoadLibraryW(
  226. LPCWSTR lpwLibFileName
  227. ) ;
  228. typedef struct _TSAPPCMP_API_HOOK_TABLE
  229. {
  230. PVOID orig; // original API to hook
  231. PVOID hook; // new hook for that API
  232. WCHAR name[ 22 * sizeof( WCHAR ) ]; // longest func name
  233. } TSAPPCMP_API_HOOK_TABLE, PTSAPPCMP_API_HOOK_TABLE;
  234. #define NUM_OF_OBJECT_NAME_FUNCS_TO_HOOK 16
  235. TSAPPCMP_API_HOOK_TABLE ObjectNameFuncsToHook[ NUM_OF_OBJECT_NAME_FUNCS_TO_HOOK ] =
  236. {
  237. {NULL, TCreateEventA, L"TCreateEventA" },
  238. {NULL, TCreateEventW, L"TCreateEventW" },
  239. {NULL, TOpenEventA, L"TOpenEventA" },
  240. {NULL, TOpenEventW, L"TOpenEventW" },
  241. {NULL, TCreateSemaphoreA, L"TCreateSemaphoreA" },
  242. {NULL, TCreateSemaphoreW, L"TCreateSemaphoreW" },
  243. {NULL, TOpenSemaphoreA, L"TOpenSemaphoreA" },
  244. {NULL, TOpenSemaphoreW, L"TOpenSemaphoreW" },
  245. {NULL, TCreateMutexA, L"TCreateMutexA" },
  246. {NULL, TCreateMutexW, L"TCreateMutexW" },
  247. {NULL, TOpenMutexA, L"TOpenMutexA" },
  248. {NULL, TOpenMutexW, L"TOpenMutexW" },
  249. {NULL, TCreateFileMappingA, L"TCreateFileMappingA" },
  250. {NULL, TCreateFileMappingW, L"TCreateFileMappingW" },
  251. {NULL, TOpenFileMappingA, L"TOpenFileMappingA" },
  252. {NULL, TOpenFileMappingW, L"TOpenFileMappingW" },
  253. };
  254. #define NUM_OF_LOAD_LIB_FUNCS_TO_HOOK 4
  255. TSAPPCMP_API_HOOK_TABLE LoadLibFuncsToHook[ NUM_OF_LOAD_LIB_FUNCS_TO_HOOK ] =
  256. {
  257. {NULL , TLoadLibraryA , L"TLoadLibraryA" },
  258. {NULL , TLoadLibraryW , L"TLoadLibraryW" },
  259. {NULL , TLoadLibraryExA , L"TLoadLibraryExA" },
  260. {NULL , TLoadLibraryExW , L"TLoadLibraryExW" }
  261. };
  262. BOOL
  263. TsWalkProcessDlls();
  264. //
  265. // we don't want to support the load-lib and object name redirection hack on ia64 machines.
  266. //
  267. BOOLEAN Is_X86_OS()
  268. {
  269. SYSTEM_INFO SystemInfo;
  270. BOOLEAN bReturn = FALSE;
  271. ZeroMemory(&SystemInfo, sizeof(SystemInfo));
  272. GetSystemInfo(&SystemInfo);
  273. if ( SystemInfo.wProcessorArchitecture == PROCESSOR_ARCHITECTURE_INTEL )
  274. {
  275. bReturn = TRUE;
  276. }
  277. return bReturn;
  278. }
  279. // See if pEntry is already in our list, if so, then we have already
  280. // processed this image, return FALSE
  281. // Else, add entry to this list and return TRUE so that it is processed this time around.
  282. BOOLEAN ShouldEntryBeProcessed( PLDR_DATA_TABLE_ENTRY pEntry )
  283. {
  284. LDR_TABLE *pCurrent, *pNew ;
  285. // initialize our pointers to point to the head of the list
  286. pCurrent = g_LDR_TABLE_LIST_HEAD.pNext ;
  287. while (pCurrent)
  288. {
  289. if ( pEntry == pCurrent->pItem)
  290. {
  291. return FALSE;
  292. }
  293. pCurrent = pCurrent->pNext;
  294. }
  295. // we need to add to our list
  296. pNew = LocalAlloc( LMEM_FIXED, sizeof( LDR_TABLE ) );
  297. pCurrent = g_LDR_TABLE_LIST_HEAD.pNext ;
  298. if (pNew)
  299. {
  300. pNew->pItem = pEntry;
  301. pNew->pNext = pCurrent;
  302. g_LDR_TABLE_LIST_HEAD.pNext = pNew; // add to the head
  303. return TRUE;
  304. }
  305. else
  306. {
  307. return FALSE;
  308. }
  309. }
  310. // Free memory allocated for the LDR_TABLE
  311. void FreeLDRTable()
  312. {
  313. LDR_TABLE *pCurrent, *pTmp;
  314. pCurrent = g_LDR_TABLE_LIST_HEAD.pNext ;
  315. while ( pCurrent )
  316. {
  317. pTmp = pCurrent;
  318. pCurrent = pCurrent->pNext;
  319. LocalFree( pTmp );
  320. }
  321. if ( g_dwFlags & DEBUG_IAT )
  322. {
  323. DbgPrint("tsappcmp: done with FreeLDRTable() \n");
  324. }
  325. }
  326. LPSTR
  327. GlobalizePathA(
  328. LPCSTR pPath
  329. )
  330. /*++
  331. Routine Description:
  332. Convert an ANSI path to a GLOBAL path
  333. --*/
  334. {
  335. DWORD Len;
  336. LPSTR pNewPath;
  337. if( pPath == NULL ) {
  338. return( NULL );
  339. }
  340. //
  341. // Add code to determine if per object
  342. // override is in effect and do not globalize
  343. //
  344. Len = strlen(pPath) + GLOBALPATHSIZE + 1;
  345. pNewPath = LocalAlloc(LMEM_FIXED, Len);
  346. if( pNewPath == NULL ) {
  347. return( NULL );
  348. }
  349. strcpy( pNewPath, GLOBALPATHA );
  350. strcat( pNewPath, pPath );
  351. return( pNewPath );
  352. }
  353. LPWSTR
  354. GlobalizePathW(
  355. LPCWSTR pPath
  356. )
  357. /*++
  358. Routine Description:
  359. Convert a WCHAR path to a GLOBAL path
  360. --*/
  361. {
  362. DWORD Len;
  363. LPWSTR pNewPath;
  364. if( pPath == NULL ) {
  365. return( NULL );
  366. }
  367. //
  368. // Add code to determine if per object
  369. // override is in effect and do not globalize.
  370. //
  371. Len = wcslen(pPath) + GLOBALPATHSIZE + 1;
  372. Len *= sizeof(WCHAR);
  373. pNewPath = LocalAlloc(LMEM_FIXED, Len);
  374. if( pNewPath == NULL ) {
  375. return( NULL );
  376. }
  377. wcscpy( pNewPath, GLOBALPATHW );
  378. wcscat( pNewPath, pPath );
  379. return( pNewPath );
  380. }
  381. // Thunks for WIN32 named object functions
  382. HANDLE
  383. APIENTRY
  384. TCreateEventA(
  385. LPSECURITY_ATTRIBUTES lpEventAttributes,
  386. BOOL bManualReset,
  387. BOOL bInitialState,
  388. LPCSTR lpName
  389. )
  390. /*++
  391. Routine Description:
  392. ANSI thunk to CreateEventW
  393. --*/
  394. {
  395. HANDLE h;
  396. LPSTR pNewPath = GlobalizePathA(lpName);
  397. h = ( ( Func_CreateEventA *) ObjectNameFuncsToHook[ Index_Func_CreateEventA ].orig )( lpEventAttributes, bManualReset, bInitialState, pNewPath );
  398. // h = CreateEventA( lpEventAttributes, bManualReset, bInitialState, pNewPath );
  399. if( pNewPath ) LocalFree(pNewPath);
  400. return h;
  401. }
  402. HANDLE
  403. APIENTRY
  404. TCreateEventW(
  405. LPSECURITY_ATTRIBUTES lpEventAttributes,
  406. BOOL bManualReset,
  407. BOOL bInitialState,
  408. LPCWSTR lpName
  409. )
  410. {
  411. HANDLE h;
  412. LPWSTR pNewPath = GlobalizePathW(lpName);
  413. if ( g_dwFlags & DEBUG_IAT )
  414. {
  415. if( pNewPath )
  416. DbgPrint("TCreateEventW: Thunked, New name %ws\n",pNewPath);
  417. }
  418. h = ( ( Func_CreateEventW *) ObjectNameFuncsToHook[ Index_Func_CreateEventW ].orig ) ( lpEventAttributes, bManualReset, bInitialState, pNewPath );
  419. // h = CreateEventW( lpEventAttributes, bManualReset, bInitialState, pNewPath );
  420. if( pNewPath ) LocalFree(pNewPath);
  421. return h;
  422. }
  423. HANDLE
  424. APIENTRY
  425. TOpenEventA(
  426. DWORD dwDesiredAccess,
  427. BOOL bInheritHandle,
  428. LPCSTR lpName
  429. )
  430. /*++
  431. Routine Description:
  432. ANSI thunk to OpenNamedEventW
  433. --*/
  434. {
  435. HANDLE h;
  436. LPSTR pNewPath = GlobalizePathA(lpName);
  437. h = ( ( Func_OpenEventA *) ObjectNameFuncsToHook[ Index_Func_OpenEventA ].orig )( dwDesiredAccess, bInheritHandle, pNewPath );
  438. // h = OpenEventA( dwDesiredAccess, bInheritHandle, pNewPath );
  439. if( pNewPath ) LocalFree(pNewPath);
  440. return h;
  441. }
  442. HANDLE
  443. APIENTRY
  444. TOpenEventW(
  445. DWORD dwDesiredAccess,
  446. BOOL bInheritHandle,
  447. LPCWSTR lpName
  448. )
  449. {
  450. HANDLE h;
  451. LPWSTR pNewPath = GlobalizePathW(lpName);
  452. h = ( ( Func_OpenEventW *) ObjectNameFuncsToHook[ Index_Func_OpenEventW ].orig ) ( dwDesiredAccess, bInheritHandle, pNewPath );
  453. // h = OpenEventW( dwDesiredAccess, bInheritHandle, pNewPath );
  454. if( pNewPath ) LocalFree(pNewPath);
  455. return h;
  456. }
  457. HANDLE
  458. APIENTRY
  459. TCreateSemaphoreA(
  460. LPSECURITY_ATTRIBUTES lpSemaphoreAttributes,
  461. LONG lInitialCount,
  462. LONG lMaximumCount,
  463. LPCSTR lpName
  464. )
  465. /*++
  466. Routine Description:
  467. ANSI thunk to CreateSemaphoreW
  468. --*/
  469. {
  470. HANDLE h;
  471. LPSTR pNewPath = GlobalizePathA(lpName);
  472. h = ( ( Func_CreateSemaphoreA *) ObjectNameFuncsToHook[ Index_Func_CreateSemaphoreA ].orig )( lpSemaphoreAttributes, lInitialCount, lMaximumCount, pNewPath );
  473. // h = CreateSemaphoreA( lpSemaphoreAttributes, lInitialCount, lMaximumCount, pNewPath );
  474. if( pNewPath ) LocalFree(pNewPath);
  475. return h;
  476. }
  477. HANDLE
  478. APIENTRY
  479. TCreateSemaphoreW(
  480. LPSECURITY_ATTRIBUTES lpSemaphoreAttributes,
  481. LONG lInitialCount,
  482. LONG lMaximumCount,
  483. LPCWSTR lpName
  484. )
  485. {
  486. HANDLE h;
  487. LPWSTR pNewPath = GlobalizePathW(lpName);
  488. h = ( ( Func_CreateSemaphoreW *) ObjectNameFuncsToHook[ Index_Func_CreateSemaphoreW ].orig ) ( lpSemaphoreAttributes, lInitialCount, lMaximumCount, pNewPath );
  489. // h = CreateSemaphoreW( lpSemaphoreAttributes, lInitialCount, lMaximumCount, pNewPath );
  490. if( pNewPath ) LocalFree(pNewPath);
  491. return h;
  492. }
  493. HANDLE
  494. APIENTRY
  495. TOpenSemaphoreA(
  496. DWORD dwDesiredAccess,
  497. BOOL bInheritHandle,
  498. LPCSTR lpName
  499. )
  500. /*++
  501. Routine Description:
  502. ANSI thunk to OpenSemaphoreW
  503. --*/
  504. {
  505. HANDLE h;
  506. LPSTR pNewPath = GlobalizePathA(lpName);
  507. h = ( ( Func_OpenSemaphoreA *) ObjectNameFuncsToHook[ Index_Func_OpenSemaphoreA ].orig ) ( dwDesiredAccess, bInheritHandle, pNewPath );
  508. // h = OpenSemaphoreA( dwDesiredAccess, bInheritHandle, pNewPath );
  509. if( pNewPath ) LocalFree(pNewPath);
  510. return h;
  511. }
  512. HANDLE
  513. APIENTRY
  514. TOpenSemaphoreW(
  515. DWORD dwDesiredAccess,
  516. BOOL bInheritHandle,
  517. LPCWSTR lpName
  518. )
  519. {
  520. HANDLE h;
  521. LPWSTR pNewPath = GlobalizePathW(lpName);
  522. h = ( ( Func_OpenSemaphoreW *) ObjectNameFuncsToHook[ Index_Func_OpenSemaphoreW ].orig ) ( dwDesiredAccess, bInheritHandle, pNewPath );
  523. // h = OpenSemaphoreW( dwDesiredAccess, bInheritHandle, pNewPath );
  524. if( pNewPath ) LocalFree(pNewPath);
  525. return h;
  526. }
  527. HANDLE
  528. APIENTRY
  529. TCreateMutexA(
  530. LPSECURITY_ATTRIBUTES lpMutexAttributes,
  531. BOOL bInitialOwner,
  532. LPCSTR lpName
  533. )
  534. /*++
  535. Routine Description:
  536. ANSI thunk to CreateMutexW
  537. --*/
  538. {
  539. HANDLE h;
  540. LPSTR pNewPath = GlobalizePathA(lpName);
  541. h = ( ( Func_CreateMutexA *) ObjectNameFuncsToHook[ Index_Func_CreateMutexA ].orig ) ( lpMutexAttributes, bInitialOwner, pNewPath );
  542. // h = CreateMutexA( lpMutexAttributes, bInitialOwner, pNewPath );
  543. if( pNewPath ) LocalFree(pNewPath);
  544. return h;
  545. }
  546. HANDLE
  547. APIENTRY
  548. TCreateMutexW(
  549. LPSECURITY_ATTRIBUTES lpMutexAttributes,
  550. BOOL bInitialOwner,
  551. LPCWSTR lpName
  552. )
  553. {
  554. HANDLE h;
  555. LPWSTR pNewPath = GlobalizePathW(lpName);
  556. h = ( ( Func_CreateMutexW *) ObjectNameFuncsToHook[ Index_Func_CreateMutexW ].orig ) ( lpMutexAttributes, bInitialOwner, pNewPath );
  557. // h = CreateMutexW( lpMutexAttributes, bInitialOwner, pNewPath );
  558. if( pNewPath ) LocalFree(pNewPath);
  559. return h;
  560. }
  561. HANDLE
  562. APIENTRY
  563. TOpenMutexA(
  564. DWORD dwDesiredAccess,
  565. BOOL bInheritHandle,
  566. LPCSTR lpName
  567. )
  568. /*++
  569. Routine Description:
  570. ANSI thunk to OpenMutexW
  571. --*/
  572. {
  573. HANDLE h;
  574. LPSTR pNewPath = GlobalizePathA(lpName);
  575. h = ( ( Func_OpenMutexA *) ObjectNameFuncsToHook[ Index_Func_OpenMutexA ].orig ) ( dwDesiredAccess, bInheritHandle, pNewPath );
  576. // h = OpenMutexA( dwDesiredAccess, bInheritHandle, pNewPath );
  577. if( pNewPath ) LocalFree(pNewPath);
  578. return h;
  579. }
  580. HANDLE
  581. APIENTRY
  582. TOpenMutexW(
  583. DWORD dwDesiredAccess,
  584. BOOL bInheritHandle,
  585. LPCWSTR lpName
  586. )
  587. {
  588. HANDLE h;
  589. LPWSTR pNewPath = GlobalizePathW(lpName);
  590. h = ( ( Func_OpenMutexW *) ObjectNameFuncsToHook[ Index_Func_OpenMutexW ].orig ) ( dwDesiredAccess, bInheritHandle, pNewPath );
  591. // h = OpenMutexW( dwDesiredAccess, bInheritHandle, pNewPath );
  592. if( pNewPath ) LocalFree(pNewPath);
  593. return h;
  594. }
  595. HANDLE
  596. APIENTRY
  597. TCreateFileMappingA(
  598. HANDLE hFile,
  599. LPSECURITY_ATTRIBUTES lpFileMappingAttributes,
  600. DWORD flProtect,
  601. DWORD dwMaximumSizeHigh,
  602. DWORD dwMaximumSizeLow,
  603. LPCSTR lpName
  604. )
  605. /*++
  606. Routine Description:
  607. ANSI thunk to CreateFileMappingW
  608. --*/
  609. {
  610. HANDLE h;
  611. LPSTR pNewPath = GlobalizePathA(lpName);
  612. h = ( ( Func_CreateFileMappingA *) ObjectNameFuncsToHook[ Index_Func_CreateFileMappingA ].orig )( hFile, lpFileMappingAttributes, flProtect, dwMaximumSizeHigh, dwMaximumSizeLow, pNewPath );
  613. // h = CreateFileMappingA( hFile, lpFileMappingAttributes, flProtect, dwMaximumSizeHigh, dwMaximumSizeLow, pNewPath );
  614. if( pNewPath ) LocalFree(pNewPath);
  615. return h;
  616. }
  617. HANDLE
  618. APIENTRY
  619. TCreateFileMappingW(
  620. HANDLE hFile,
  621. LPSECURITY_ATTRIBUTES lpFileMappingAttributes,
  622. DWORD flProtect,
  623. DWORD dwMaximumSizeHigh,
  624. DWORD dwMaximumSizeLow,
  625. LPCWSTR lpName
  626. )
  627. {
  628. HANDLE h;
  629. LPWSTR pNewPath = GlobalizePathW(lpName);
  630. h = ( ( Func_CreateFileMappingW *) ObjectNameFuncsToHook[ Index_Func_CreateFileMappingW ].orig ) ( hFile, lpFileMappingAttributes, flProtect, dwMaximumSizeHigh, dwMaximumSizeLow, pNewPath );
  631. // h = CreateFileMappingW( hFile, lpFileMappingAttributes, flProtect, dwMaximumSizeHigh, dwMaximumSizeLow, pNewPath );
  632. if( pNewPath ) LocalFree(pNewPath);
  633. return h;
  634. }
  635. HANDLE
  636. APIENTRY
  637. TOpenFileMappingA(
  638. DWORD dwDesiredAccess,
  639. BOOL bInheritHandle,
  640. LPCSTR lpName
  641. )
  642. /*++
  643. Routine Description:
  644. ANSI thunk to OpenFileMappingW
  645. --*/
  646. {
  647. HANDLE h;
  648. LPSTR pNewPath = GlobalizePathA(lpName);
  649. h = ( ( Func_OpenFileMappingA *) ObjectNameFuncsToHook[ Index_Func_OpenFileMappingA ].orig ) ( dwDesiredAccess, bInheritHandle, pNewPath );
  650. // h = OpenFileMappingA( dwDesiredAccess, bInheritHandle, pNewPath );
  651. if( pNewPath ) LocalFree(pNewPath);
  652. return h;
  653. }
  654. HANDLE
  655. APIENTRY
  656. TOpenFileMappingW(
  657. DWORD dwDesiredAccess,
  658. BOOL bInheritHandle,
  659. LPCWSTR lpName
  660. )
  661. {
  662. HANDLE h;
  663. LPWSTR pNewPath = GlobalizePathW(lpName);
  664. h = ( ( Func_OpenFileMappingW *) ObjectNameFuncsToHook[ Index_Func_OpenFileMappingW ].orig ) ( dwDesiredAccess, bInheritHandle, pNewPath );
  665. // h = OpenFileMappingW( dwDesiredAccess, bInheritHandle, pNewPath );
  666. if( pNewPath ) LocalFree(pNewPath);
  667. return h;
  668. }
  669. HMODULE
  670. TLoadLibraryExA(
  671. LPCSTR lpLibFileName,
  672. HANDLE hFile,
  673. DWORD dwFlags
  674. )
  675. {
  676. HMODULE h;
  677. h = ( (Func_LoadLibraryExA *)(LoadLibFuncsToHook[Index_Func_LoadLibraryExA ].orig) )( lpLibFileName, hFile, dwFlags );
  678. // h = LoadLibraryExA( lpLibFileName, hFile, dwFlags );
  679. if( h ) {
  680. if(!TsWalkProcessDlls())
  681. {
  682. FreeLibrary(h);
  683. return NULL;
  684. }
  685. }
  686. return( h );
  687. }
  688. HMODULE TLoadLibraryExW(
  689. LPCWSTR lpwLibFileName,
  690. HANDLE hFile,
  691. DWORD dwFlags
  692. )
  693. {
  694. HMODULE h;
  695. h = ( ( Func_LoadLibraryExW *) LoadLibFuncsToHook[Index_Func_LoadLibraryExW ].orig )( lpwLibFileName, hFile, dwFlags );
  696. // h = LoadLibraryExW( lpwLibFileName, hFile, dwFlags );
  697. if( h ) {
  698. if(!TsWalkProcessDlls())
  699. {
  700. FreeLibrary(h);
  701. return NULL;
  702. }
  703. }
  704. return( h );
  705. }
  706. HMODULE
  707. TLoadLibraryA(
  708. LPCSTR lpLibFileName
  709. )
  710. /*++
  711. Routine Description:
  712. Re-walk all the DLL's in the process since a new set of DLL's may
  713. have been loaded.
  714. We must rewalk all since the new DLL lpLibFileName may bring in
  715. other DLL's by import reference.
  716. --*/
  717. {
  718. HMODULE h;
  719. h = ( ( Func_LoadLibraryA *) LoadLibFuncsToHook[Index_Func_LoadLibraryA ].orig )( lpLibFileName );
  720. // h = LoadLibraryA( lpLibFileName );
  721. if( h ) {
  722. if(!TsWalkProcessDlls())
  723. {
  724. FreeLibrary(h);
  725. return NULL;
  726. }
  727. }
  728. return( h );
  729. }
  730. HMODULE
  731. TLoadLibraryW(
  732. LPCWSTR lpwLibFileName
  733. )
  734. /*++
  735. Routine Description:
  736. Re-walk all the DLL's in the process since a new set of DLL's may
  737. have been loaded.
  738. We must rewalk all since the new DLL lpLibFileName may bring in
  739. other DLL's by import reference.
  740. --*/
  741. {
  742. HMODULE h;
  743. h = ( ( Func_LoadLibraryW * )LoadLibFuncsToHook[Index_Func_LoadLibraryW ].orig )( lpwLibFileName );
  744. // h = LoadLibraryW( lpwLibFileName );
  745. if( h ) {
  746. if(!TsWalkProcessDlls())
  747. {
  748. FreeLibrary(h);
  749. return NULL;
  750. }
  751. }
  752. return( h );
  753. }
  754. BOOL
  755. TsRedirectRegisteredImage(
  756. PLDR_DATA_TABLE_ENTRY LdrDataTableEntry ,
  757. BOOLEAN redirectObjectNameFunctions,
  758. BOOLEAN redirectLoadLibraryFunctions
  759. );
  760. BOOL
  761. TsWalkProcessDlls()
  762. /*++
  763. Routine Description:
  764. Walk all the DLL's in the process and redirect WIN32 named object
  765. functions for any that are registered SYSTEM global.
  766. This function is intended to be called at tsappcmp.dll init time
  767. to process all DLL's loaded before us.
  768. A hook is installed by tsappcmp.dll to process DLL's that load
  769. after this call.
  770. --*/
  771. {
  772. PLDR_DATA_TABLE_ENTRY Entry;
  773. PLIST_ENTRY Head,Next;
  774. PIMAGE_NT_HEADERS NtHeaders;
  775. UNICODE_STRING ThisDLLName;
  776. BOOLEAN rc;
  777. RtlInitUnicodeString( &ThisDLLName, TEXT("TSAPPCMP.DLL")) ;
  778. RtlEnterCriticalSection((PRTL_CRITICAL_SECTION)NtCurrentPeb()->LoaderLock);
  779. __try
  780. {
  781. Head = &NtCurrentPeb()->Ldr->InLoadOrderModuleList;
  782. Next = Head->Flink;
  783. while ( Next != Head )
  784. {
  785. Entry = CONTAINING_RECORD(Next, LDR_DATA_TABLE_ENTRY, InLoadOrderLinks);
  786. Next = Next->Flink;
  787. rc = ShouldEntryBeProcessed( Entry );
  788. if (rc)
  789. {
  790. if ( (SSIZE_T)Entry->DllBase < 0 )
  791. {
  792. // Not hooking kernel-mode DLL
  793. if ( g_dwFlags & DEBUG_IAT )
  794. {
  795. DbgPrint(" > Not hooking kernel mode DLL : %wZ\n",&Entry->BaseDllName);
  796. }
  797. continue;
  798. }
  799. if ( g_dwFlags & DEBUG_IAT )
  800. {
  801. if( Entry->BaseDllName.Buffer )
  802. DbgPrint("tsappcmp: examining %wZ\n",&Entry->BaseDllName);
  803. }
  804. //
  805. // when we unload, the memory order links flink field is nulled.
  806. // this is used to skip the entry pending list removal.
  807. //
  808. if ( !Entry->InMemoryOrderLinks.Flink ) {
  809. continue;
  810. }
  811. NtHeaders = RtlImageNtHeader( Entry->DllBase );
  812. if( NtHeaders == NULL ) {
  813. continue;
  814. }
  815. if( NtHeaders->OptionalHeader.DllCharacteristics & IMAGE_DLLCHARACTERISTICS_TERMINAL_SERVER_AWARE)
  816. {
  817. if ( g_dwFlags & DEBUG_IAT )
  818. {
  819. DbgPrint("tsappcmp: %wZ is ts-aware, we are exiting TsWalkProcessDlls() now\n",&Entry->BaseDllName);
  820. }
  821. return TRUE; // we do not mess around with the IAT of TS-aware apps.
  822. }
  823. if (Entry->BaseDllName.Buffer && !RtlCompareUnicodeString(&Entry->BaseDllName, &ThisDLLName, TRUE)) {
  824. continue;
  825. }
  826. if( NtHeaders->OptionalHeader.LoaderFlags & IMAGE_LOADER_FLAGS_SYSTEM_GLOBAL )
  827. {
  828. // 2nd param is redirectObjectNameFunctions
  829. // 3rd param is redirectLoadLibraryFunctions
  830. if(!TsRedirectRegisteredImage( Entry , TRUE, TRUE )) // hooks object name and loadl lib funcs ( all of them )
  831. {
  832. return FALSE;
  833. }
  834. }
  835. else
  836. {
  837. if (! (g_dwFlags & TERMSRV_COMPAT_DONT_PATCH_IN_LOAD_LIBS ) )
  838. {
  839. // 2nd param is redirectObjectNameFunctions
  840. // 3rd param is redirectLoadLibraryFunctions
  841. if(!TsRedirectRegisteredImage( Entry , FALSE, TRUE )) // only hook lib funcs ( comment error earlier_)
  842. {
  843. return FALSE;
  844. }
  845. }
  846. }
  847. }
  848. else
  849. {
  850. if ( g_dwFlags & DEBUG_IAT )
  851. {
  852. if( Entry->BaseDllName.Buffer )
  853. DbgPrint("tsappcmp: SKIPPING already walked image : %wZ\n",&Entry->BaseDllName);
  854. }
  855. }
  856. }
  857. }
  858. __finally
  859. {
  860. RtlLeaveCriticalSection((PRTL_CRITICAL_SECTION)NtCurrentPeb()->LoaderLock);
  861. }
  862. return TRUE;
  863. }
  864. BOOL ImageIsTsAware()
  865. {
  866. PIMAGE_NT_HEADERS NtHeader = RtlImageNtHeader( NtCurrentPeb()->ImageBaseAddress );
  867. if ((NtHeader) && (NtHeader->OptionalHeader.DllCharacteristics & IMAGE_DLLCHARACTERISTICS_TERMINAL_SERVER_AWARE))
  868. {
  869. return TRUE;
  870. }
  871. else
  872. {
  873. return FALSE;
  874. }
  875. }
  876. BOOL
  877. InitRegisterSupport()
  878. /*++
  879. Routine Description:
  880. Initialize the register command support by walking
  881. all DLL's and inserting our thunks.
  882. --*/
  883. {
  884. int i;
  885. g_LDR_TABLE_LIST_HEAD.pNext = NULL;
  886. if (!Is_X86_OS() )
  887. {
  888. DbgPrint("Object name redirection not supported on non-x86 platforms\n");
  889. return TRUE;
  890. }
  891. if ( ! ImageIsTsAware() )
  892. {
  893. if ( g_dwFlags & DEBUG_IAT )
  894. {
  895. DbgPrint("InitRegisterSupport() called with dwFlags = 0x%lx\n", g_dwFlags);
  896. }
  897. LoadLibFuncsToHook[ Index_Func_LoadLibraryA ].orig = LoadLibraryA;
  898. LoadLibFuncsToHook[ Index_Func_LoadLibraryW ].orig = LoadLibraryW;
  899. LoadLibFuncsToHook[ Index_Func_LoadLibraryExA ].orig = LoadLibraryExA;
  900. LoadLibFuncsToHook[ Index_Func_LoadLibraryExW ].orig = LoadLibraryExW;
  901. ObjectNameFuncsToHook[ Index_Func_CreateEventA ].orig = CreateEventA;
  902. ObjectNameFuncsToHook[ Index_Func_CreateEventW ].orig = CreateEventW;
  903. ObjectNameFuncsToHook[ Index_Func_OpenEventA ].orig = OpenEventA;
  904. ObjectNameFuncsToHook[ Index_Func_OpenEventW ].orig = OpenEventW;
  905. ObjectNameFuncsToHook[ Index_Func_CreateSemaphoreA ].orig = CreateSemaphoreA;
  906. ObjectNameFuncsToHook[ Index_Func_CreateSemaphoreW ].orig = CreateSemaphoreW;
  907. ObjectNameFuncsToHook[ Index_Func_OpenSemaphoreA ].orig = OpenSemaphoreA;
  908. ObjectNameFuncsToHook[ Index_Func_OpenSemaphoreW ].orig = OpenSemaphoreW;
  909. ObjectNameFuncsToHook[ Index_Func_CreateMutexA ].orig = CreateMutexA;
  910. ObjectNameFuncsToHook[ Index_Func_CreateMutexW ].orig = CreateMutexW;
  911. ObjectNameFuncsToHook[ Index_Func_OpenMutexA ].orig = OpenMutexA;
  912. ObjectNameFuncsToHook[ Index_Func_OpenMutexW ].orig = OpenMutexW;
  913. ObjectNameFuncsToHook[ Index_Func_CreateFileMappingA ].orig = CreateFileMappingA;
  914. ObjectNameFuncsToHook[ Index_Func_CreateFileMappingW ].orig = CreateFileMappingW;
  915. ObjectNameFuncsToHook[ Index_Func_OpenFileMappingA ].orig = OpenFileMappingA;
  916. ObjectNameFuncsToHook[ Index_Func_OpenFileMappingW ].orig = OpenFileMappingW;
  917. if ( g_dwFlags & DEBUG_IAT )
  918. {
  919. for (i = 0; i < NUM_OF_LOAD_LIB_FUNCS_TO_HOOK ; ++i)
  920. {
  921. DbgPrint(" Use %ws at index = %2d for an indirect call to 0x%lx \n", LoadLibFuncsToHook[i].name, i, LoadLibFuncsToHook[i].orig );
  922. }
  923. for (i = 0; i < NUM_OF_OBJECT_NAME_FUNCS_TO_HOOK ; ++i)
  924. {
  925. DbgPrint(" Use %ws at index = %2d for an indirect call to 0x%lx \n", ObjectNameFuncsToHook[i].name, i, ObjectNameFuncsToHook[i].orig );
  926. }
  927. }
  928. return TsWalkProcessDlls();
  929. }
  930. else
  931. {
  932. return TRUE; // nothing to do!
  933. }
  934. }
  935. BOOL
  936. TsRedirectRegisteredImage(
  937. PLDR_DATA_TABLE_ENTRY LdrDataTableEntry ,
  938. BOOLEAN redirectObjectNameFunctions,
  939. BOOLEAN redirectLoadLibraryFunctions
  940. )
  941. {
  942. /*++
  943. Routine Description:
  944. Redirect WIN32 named object functions from kernel32.dll to tsappcmp.dll
  945. --*/
  946. PIMAGE_DOS_HEADER pIDH;
  947. PIMAGE_NT_HEADERS pINTH;
  948. PIMAGE_IMPORT_DESCRIPTOR pIID;
  949. PIMAGE_NT_HEADERS NtHeaders;
  950. PBYTE pDllBase;
  951. DWORD dwImportTableOffset;
  952. DWORD dwOldProtect, dwOldProtect2;
  953. SIZE_T dwProtectSize;
  954. NTSTATUS status;
  955. //
  956. // Determine the location and size of the IAT. If found, scan the
  957. // IAT address to see if any are pointing to RtlAllocateHeap. If so
  958. // replace when with a pointer to a unique thunk function that will
  959. // replace the tag with a unique tag for this image.
  960. //
  961. if ( g_dwFlags & DEBUG_IAT )
  962. {
  963. if( LdrDataTableEntry->BaseDllName.Buffer )
  964. DbgPrint("tsappcmp: walking %wZ\n",&LdrDataTableEntry->BaseDllName);
  965. }
  966. pDllBase = LdrDataTableEntry->DllBase;
  967. pIDH = (PIMAGE_DOS_HEADER)pDllBase;
  968. //
  969. // Get the import table
  970. //
  971. pINTH = (PIMAGE_NT_HEADERS)(pDllBase + pIDH->e_lfanew);
  972. dwImportTableOffset = pINTH->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress;
  973. if (dwImportTableOffset == 0) {
  974. //
  975. // No import table found. This is probably ntdll.dll
  976. //
  977. return TRUE;
  978. }
  979. if ( g_dwFlags & DEBUG_IAT )
  980. {
  981. DbgPrint("\n > pDllBase = 0x%lx, IAT offset = 0x%lx \n", pDllBase, dwImportTableOffset );
  982. }
  983. pIID = (PIMAGE_IMPORT_DESCRIPTOR)(pDllBase + dwImportTableOffset);
  984. //
  985. // Loop through the import table and search for the APIs that we want to patch
  986. //
  987. while (TRUE)
  988. {
  989. LPSTR pszImportEntryModule;
  990. PIMAGE_THUNK_DATA pITDA;
  991. // Return if no first thunk (terminating condition)
  992. if (pIID->FirstThunk == 0) {
  993. break;
  994. }
  995. if ( g_dwFlags & DEBUG_IAT )
  996. {
  997. DbgPrint(" > pIID->FirstThunk = 0x%lx \n", pIID->FirstThunk );
  998. }
  999. pszImportEntryModule = (LPSTR)(pDllBase + pIID->Name);
  1000. //
  1001. // We have APIs to hook for this module!
  1002. //
  1003. pITDA = (PIMAGE_THUNK_DATA)(pDllBase + (DWORD)pIID->FirstThunk);
  1004. if ( g_dwFlags & DEBUG_IAT )
  1005. {
  1006. DbgPrint(" >> PITDA = 0x%lx \n", pITDA );
  1007. }
  1008. while (TRUE) {
  1009. DWORD dwDllIndex;
  1010. PVOID dwFuncAddr;
  1011. int i;
  1012. //
  1013. // Done with all the imports from this module? (terminating condition)
  1014. //
  1015. if (pITDA->u1.Ordinal == 0)
  1016. {
  1017. if ( g_dwFlags & DEBUG_IAT )
  1018. {
  1019. DbgPrint(" >> Existing inner loop with PITDA = 0x%lx \n", pITDA );
  1020. }
  1021. break;
  1022. }
  1023. // Make the code page writable and overwrite new function pointer in import table
  1024. dwProtectSize = sizeof(DWORD);
  1025. dwFuncAddr = (PVOID)&pITDA->u1.Function;
  1026. status = NtProtectVirtualMemory(NtCurrentProcess(),
  1027. (PVOID)&dwFuncAddr,
  1028. &dwProtectSize,
  1029. PAGE_READWRITE,
  1030. &dwOldProtect);
  1031. if (NT_SUCCESS(status))
  1032. {
  1033. // hook API of interest.
  1034. if (redirectObjectNameFunctions)
  1035. {
  1036. for (i = 0; i < NUM_OF_OBJECT_NAME_FUNCS_TO_HOOK ; i ++)
  1037. {
  1038. if ( ObjectNameFuncsToHook[i].orig == (PVOID) pITDA->u1.Function )
  1039. {
  1040. (PVOID)pITDA->u1.Function = ObjectNameFuncsToHook[i].hook;
  1041. if ( g_dwFlags & DEBUG_IAT )
  1042. {
  1043. DbgPrint(" > Func was hooked : 0x%lx thru %ws \n", ObjectNameFuncsToHook[i].orig ,
  1044. ObjectNameFuncsToHook[i].name );
  1045. }
  1046. }
  1047. }
  1048. }
  1049. if (redirectLoadLibraryFunctions )
  1050. {
  1051. for (i = 0; i < NUM_OF_LOAD_LIB_FUNCS_TO_HOOK ; i ++)
  1052. {
  1053. if ( LoadLibFuncsToHook[i].orig == (PVOID) pITDA->u1.Function )
  1054. {
  1055. (PVOID)pITDA->u1.Function = LoadLibFuncsToHook[i].hook;
  1056. if ( g_dwFlags & DEBUG_IAT )
  1057. {
  1058. DbgPrint(" > Func was hooked : 0x%lx thru %ws \n", LoadLibFuncsToHook[i].orig ,
  1059. LoadLibFuncsToHook[i].name );
  1060. }
  1061. }
  1062. }
  1063. }
  1064. dwProtectSize = sizeof(DWORD);
  1065. status = NtProtectVirtualMemory(NtCurrentProcess(),
  1066. (PVOID)&dwFuncAddr,
  1067. &dwProtectSize,
  1068. dwOldProtect,
  1069. &dwOldProtect2);
  1070. if (!NT_SUCCESS(status))
  1071. {
  1072. DbgPrint((" > Failed to change back the protection\n"));
  1073. return FALSE;
  1074. }
  1075. }
  1076. else
  1077. {
  1078. DbgPrint(" > Failed 0x%X to change protection to PAGE_READWRITE. Addr 0x%lx \n", status, &(pITDA->u1.Function) );
  1079. return FALSE;
  1080. }
  1081. pITDA++;
  1082. }
  1083. pIID++;
  1084. }
  1085. return TRUE;
  1086. }
  1087. #if 0
  1088. void
  1089. TsLoadDllCallback(
  1090. PLDR_DATA_TABLE_ENTRY Entry
  1091. )
  1092. /*++
  1093. Routine Description:
  1094. This function is called when a new DLL is loaded.
  1095. It is registered as a callback from LDR, same as WX86
  1096. Hook goes into ntos\dll\ldrsnap.c,LdrpRunInitializeRoutines()
  1097. This function is currently not used since a hook on LoadLibrary
  1098. is used instead to avoid modifications to ntdll.dll.
  1099. --*/
  1100. {
  1101. PIMAGE_NT_HEADERS NtHeaders;
  1102. NtHeaders = RtlImageNtHeader( Entry->DllBase );
  1103. if( NtHeaders == NULL ) {
  1104. return;
  1105. }
  1106. if( NtHeaders->OptionalHeader.LoaderFlags & IMAGE_LOADER_FLAGS_SYSTEM_GLOBAL ) {
  1107. TsRedirectRegisteredImage( Entry );
  1108. }
  1109. return;
  1110. }
  1111. #endif