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.

285 lines
8.2 KiB

  1. /********************************************************************
  2. *
  3. * Module Name : lpk_init.cxx
  4. *
  5. * The module handles the Dll entry point and intialization routines.
  6. *
  7. * Created : Oct 21, 1996
  8. * Author : Samer Arafeh [samera]
  9. *
  10. * Copyright (c) 1996, Microsoft Corporation. All rights reserved.
  11. *
  12. **********************************************************************/
  13. #include "precomp.hxx"
  14. /***************************************************************************\
  15. * FindStartOfString
  16. *
  17. * Searches the unicode res string for the specified pattern.
  18. *
  19. * History:
  20. * 2-Jan-1998 SamerA Created.
  21. \***************************************************************************/
  22. PWSTR FindStartOfString(
  23. PWSTR pwszToFind,
  24. ULONG uLenToFind,
  25. PWSTR pResourceData,
  26. ULONG uSearchLen)
  27. {
  28. ULONG i=0,j=0;
  29. PWSTR pwszMatch=pResourceData ;
  30. if ( uLenToFind > uSearchLen ) {
  31. return NULL;
  32. }
  33. while ( i<uSearchLen ) {
  34. if ( (pwszToFind[j] == pwszMatch[i]) &&
  35. ((uSearchLen-i+1) >= uLenToFind ) ) {
  36. while ( j<uLenToFind ) {
  37. if ( pwszToFind[j] != pwszMatch[i] ) {
  38. j=0;
  39. break;
  40. }
  41. ++j;
  42. ++i;
  43. }
  44. if (j == uLenToFind) {
  45. //
  46. // Clear NULLs
  47. //
  48. while ( pwszMatch[i] == L'\0' )
  49. ++i;
  50. return &pwszMatch[i];
  51. }
  52. continue;
  53. }
  54. ++i;
  55. }
  56. return NULL;
  57. }
  58. /***************************************************************************\
  59. * LpkCheckForMirrorSignature
  60. *
  61. * Reetreives a pointer to the version resource section of the
  62. * current executable. It checks if the 'FileDescription' field
  63. * contains double LRM at the beginning to indicate a localized Mirrored
  64. * App that requires mirroring. If signature is found, then
  65. * SetProcessDefaultLayout is automatically called to apply mirroring for
  66. * the current process.
  67. *
  68. * History:
  69. * 2-Jan-1998 SamerA Created.
  70. \***************************************************************************/
  71. BOOL LpkCheckForMirrorSignature( void )
  72. {
  73. NTSTATUS status = STATUS_UNSUCCESSFUL;
  74. PVOID pImageBase,pResourceData;
  75. PIMAGE_RESOURCE_DATA_ENTRY pImageResource;
  76. ULONG uResourceSize;
  77. ULONG_PTR resIdPath[ 3 ];
  78. WCHAR *pwchDescritpion;
  79. WCHAR wchVersionVar[] = L"FileDescription";
  80. //
  81. // Get the current executable handle
  82. //
  83. pImageBase = NtCurrentPeb()->ImageBaseAddress;
  84. if ( NULL == pImageBase ) {
  85. return NT_SUCCESS(status);
  86. }
  87. //
  88. // Find the version resource. Search for neutral resource, this way
  89. // the MUI resource redirection code is activated, and the MUI
  90. // resource will be selected, if available.
  91. //
  92. resIdPath[0] = (ULONG_PTR) RT_VERSION ;
  93. resIdPath[1] = (ULONG_PTR) 1;
  94. resIdPath[2] = (ULONG_PTR) MAKELANGID( LANG_NEUTRAL , SUBLANG_NEUTRAL );
  95. // try {
  96. //
  97. // Bug #246044 WeiWu 12/07/00
  98. // Due to #173609 bug fix, resource loader no longer by default redirects
  99. // version resource searching to MUI alternative modules
  100. // So, we have to use LDR_FIND_RESOURCE_LANGUAGE_REDIRECT_VERSION to force version redirection
  101. //
  102. status = LdrFindResourceEx_U(
  103. LDR_FIND_RESOURCE_LANGUAGE_REDIRECT_VERSION,
  104. pImageBase,
  105. resIdPath,
  106. 3,
  107. &pImageResource
  108. );
  109. // }
  110. // except( EXCEPTION_EXECUTE_HANDLER )
  111. // {
  112. // status = GetExceptionCode();
  113. // }
  114. if ( NT_SUCCESS(status) ) {
  115. //
  116. // Load the resource into memory
  117. //
  118. // try {
  119. status = LdrAccessResource( pImageBase ,
  120. pImageResource,
  121. &pResourceData,
  122. &uResourceSize
  123. );
  124. // }
  125. // except( EXCEPTION_EXECUTE_HANDLER )
  126. // {
  127. // status = GetExceptionCode();
  128. // }
  129. if ( NT_SUCCESS(status) ) {
  130. //
  131. // Now we have the Version Info of the current
  132. // executable.
  133. //
  134. // Let's read the FileDescription and check
  135. // if this image needs to be mirrored by
  136. // calling NtUserSetProcessDefaultLayout()
  137. //
  138. pwchDescritpion = FindStartOfString( wchVersionVar ,
  139. (sizeof(wchVersionVar)/sizeof(WCHAR)) ,
  140. (WCHAR*)pResourceData ,
  141. uResourceSize/sizeof(WCHAR));
  142. if ( pwchDescritpion &&
  143. (0x200e == pwchDescritpion[0]) &&
  144. (0x200e == pwchDescritpion[1]) ) {
  145. SetProcessDefaultLayout( LAYOUT_RTL );
  146. }
  147. }
  148. }
  149. //
  150. // return status of operation
  151. //
  152. return NT_SUCCESS(status);
  153. }
  154. /*************************************************************
  155. *
  156. * LPK Dll Initialization Routines
  157. *
  158. **************************************************************/
  159. /**********************************************************************
  160. LpkDllInitialize( HANDLE hDll , DWORD dwReason , PVOID pvSituation )
  161. hDll : Handle to Dll
  162. dwReason : Process attach, thread attach, ...etc
  163. pvSituation : Load-time or Run-time Dynalink
  164. This is the initialization procedure called when LPK.DLL gets loaded
  165. into a process address space
  166. History :
  167. Oct 21, 1996 -by- Samer Arafeh [samera]
  168. ***********************************************************************/
  169. extern "C" BOOL LpkDllInitialize(HINSTANCE hDll, DWORD dwReason, PVOID pvSituation)
  170. {
  171. BOOL bRet = TRUE ;
  172. UNREFERENCED_PARAMETER(pvSituation) ;
  173. switch( dwReason )
  174. {
  175. /* Process Attachment : when a process first maps the LPK.DLL to its address space,
  176. do the one time initialization. */
  177. case DLL_PROCESS_ATTACH:
  178. {
  179. // Disable calling our DLL when new threads are created within the process
  180. // context that we are mapped in. This is a useful optimization since
  181. // we are not handlling DLL_THREAD_ATTACH
  182. DisableThreadLibraryCalls( hDll ) ;
  183. LpkPresent(); // Tell Uniscribe that the LPK is present.
  184. }
  185. break ;
  186. case DLL_THREAD_ATTACH:
  187. break ;
  188. case DLL_THREAD_DETACH:
  189. break ;
  190. case DLL_PROCESS_DETACH:
  191. break ;
  192. }
  193. return bRet ;
  194. }
  195. //////////////////////////////////////////////////////////////////////////////
  196. // GDI32 will call this function at loading time and should return TRUE //
  197. //////////////////////////////////////////////////////////////////////////////
  198. BOOL LpkInitialize (DWORD dwLPKShapingDLLs) {
  199. HRESULT hr;
  200. hr = ScriptGetProperties(&g_ppScriptProperties, &g_iMaxScript);
  201. if (FAILED(hr)) {
  202. return FALSE;
  203. }
  204. // InitNLS is returning true any way, but I prefered to stay checking it just in case
  205. // somebody changed the code indise it.
  206. if (!InitNLS()) {
  207. return FALSE;
  208. }
  209. // in case of low memory InitializeCriticalSectionAndSpinCount return FALSE.
  210. // we didn't use InitializeCriticalSection because it may throw exception in the low memory
  211. // condition and should be catched be try-except block.
  212. if (!InitializeCriticalSectionAndSpinCount(&csFontIdCache, 0))
  213. {
  214. return FALSE;
  215. }
  216. LpkCheckForMirrorSignature();
  217. g_dwLoadedShapingDLLs = dwLPKShapingDLLs;
  218. // We don't call the GDI intialization for the font linking here because in the CSRSS
  219. // process the LPK intailization will be done before the Gre GDI intailization.
  220. g_iUseFontLinking = -1;
  221. g_ACP = GetACP();
  222. // Prepare the FontID cache.
  223. g_cCachedFontsID = 0; // # of cahced font ID.
  224. g_pCurrentAvailablePos = 0; // where can we cache next font ID.
  225. return TRUE;
  226. }