ReactOS 0.4.16-dev-2284-g3529151
ldrinit.c File Reference
#include <ntdll.h>
#include <compat_undoc.h>
#include <compatguid_undoc.h>
#include <debug.h>
Include dependency graph for ldrinit.c:

Go to the source code of this file.

Macros

#define NDEBUG
 
#define DEFAULT_SECURITY_COOKIE   0xBB40E64E
 
#define VALID_CONFIG_FIELD(Name)   (ConfigSize >= RTL_SIZEOF_THROUGH_FIELD(IMAGE_LOAD_CONFIG_DIRECTORY, Name))
 

Functions

static NTSTATUS (WINAPI *Kernel32ProcessInitPostImportFunction)(VOID)
 
static BOOL (WINAPI *Kernel32BaseQueryModuleData)(IN LPSTR ModuleName
 
VOID NTAPI RtlpInitializeVectoredExceptionHandling (VOID)
 
VOID NTAPI RtlpInitDeferredCriticalSection (VOID)
 
VOID NTAPI RtlInitializeHeapManager (VOID)
 
NTSTATUS NTAPI RtlpInitializeLocaleTable (VOID)
 
NTSTATUS LdrPerformRelocations (PIMAGE_NT_HEADERS NTHeaders, PVOID ImageBase)
 
NTSTATUS NTAPI RtlpInitializeActCtx (PVOID *pOldShimData)
 
NTSTATUS NTAPI LdrOpenImageFileOptionsKey (_In_ PUNICODE_STRING SubKey, _In_ BOOLEAN Wow64, _Out_ PHANDLE NewKeyHandle)
 
NTSTATUS NTAPI LdrQueryImageFileKeyOption (_In_ HANDLE KeyHandle, _In_ PCWSTR ValueName, _In_ ULONG Type, _Out_ PVOID Buffer, _In_ ULONG BufferSize, _Out_opt_ PULONG ReturnedLength)
 
NTSTATUS NTAPI LdrQueryImageFileExecutionOptionsEx (_In_ PUNICODE_STRING SubKey, _In_ PCWSTR ValueName, _In_ ULONG Type, _Out_ PVOID Buffer, _In_ ULONG BufferSize, _Out_opt_ PULONG ReturnedLength, _In_ BOOLEAN Wow64)
 
NTSTATUS NTAPI LdrQueryImageFileExecutionOptions (_In_ PUNICODE_STRING SubKey, _In_ PCWSTR ValueName, _In_ ULONG Type, _Out_ PVOID Buffer, _In_ ULONG BufferSize, _Out_opt_ PULONG ReturnedLength)
 
VOID NTAPI LdrpEnsureLoaderLockIsHeld (VOID)
 
PVOID NTAPI LdrpFetchAddressOfSecurityCookie (PVOID BaseAddress, ULONG SizeOfImage)
 
PVOID NTAPI LdrpInitSecurityCookie (PLDR_DATA_TABLE_ENTRY LdrEntry)
 
VOID NTAPI LdrpInitializeThread (IN PCONTEXT Context)
 
NTSTATUS NTAPI LdrpRunInitializeRoutines (IN PCONTEXT Context OPTIONAL)
 
NTSTATUS NTAPI LdrShutdownProcess (VOID)
 
NTSTATUS NTAPI LdrShutdownThread (VOID)
 
NTSTATUS NTAPI LdrpInitializeTls (VOID)
 
NTSTATUS NTAPI LdrpAllocateTls (VOID)
 
VOID NTAPI LdrpFreeTls (VOID)
 
NTSTATUS NTAPI LdrpInitializeExecutionOptions (PUNICODE_STRING ImagePathName, PPEB Peb, PHANDLE OptionsKey)
 
VOID NTAPI LdrpValidateImageForMp (IN PLDR_DATA_TABLE_ENTRY LdrDataTableEntry)
 
BOOLEAN NTAPI LdrpDisableProcessCompatGuidDetection (VOID)
 
VOID NTAPI LdrpInitializeProcessCompat (PVOID pProcessActctx, PVOID *pOldShimData)
 
VOID NTAPI LdrpInitializeDotLocalSupport (PRTL_USER_PROCESS_PARAMETERS ProcessParameters)
 
NTSTATUS NTAPI LdrpInitializeProcess (IN PCONTEXT Context, IN PVOID SystemArgument1)
 
VOID NTAPI LdrpInitFailure (NTSTATUS Status)
 
VOID NTAPI LdrpInit (PCONTEXT Context, PVOID SystemArgument1, PVOID SystemArgument2)
 

Variables

HANDLE ImageExecOptionsKey
 
HANDLE Wow64ExecOptionsKey
 
UNICODE_STRING ImageExecOptionsString = RTL_CONSTANT_STRING(L"\\Registry\\Machine\\Software\\Microsoft\\Windows NT\\CurrentVersion\\Image File Execution Options")
 
UNICODE_STRING Wow64OptionsString = RTL_CONSTANT_STRING(L"")
 
UNICODE_STRING NtDllString = RTL_CONSTANT_STRING(L"ntdll.dll")
 
UNICODE_STRING Kernel32String = RTL_CONSTANT_STRING(L"kernel32.dll")
 
const UNICODE_STRING LdrpDotLocal = RTL_CONSTANT_STRING(L".Local")
 
BOOLEAN LdrpInLdrInit
 
LONG LdrpProcessInitialized
 
BOOLEAN LdrpLoaderLockInit
 
BOOLEAN LdrpLdrDatabaseIsSetup
 
BOOLEAN LdrpShutdownInProgress
 
HANDLE LdrpShutdownThreadId
 
BOOLEAN LdrpDllValidation
 
PLDR_DATA_TABLE_ENTRY LdrpImageEntry
 
PUNICODE_STRING LdrpTopLevelDllBeingLoaded
 
WCHAR StringBuffer [156]
 
PTEB LdrpTopLevelDllBeingLoadedTeb
 
PLDR_DATA_TABLE_ENTRY LdrpCurrentDllInitializer
 
PLDR_DATA_TABLE_ENTRY LdrpNtDllDataTableEntry
 
static IN LPSTR Unk1
 
static IN LPSTR IN PVOID Unk2
 
static IN LPSTR IN PVOID IN PVOID Unk3
 
static IN LPSTR IN PVOID IN PVOID IN PVOID Unk4
 
RTL_BITMAP TlsBitMap
 
RTL_BITMAP TlsExpansionBitMap
 
RTL_BITMAP FlsBitMap
 
BOOLEAN LdrpImageHasTls
 
LIST_ENTRY LdrpTlsList
 
ULONG LdrpNumberOfTlsEntries
 
ULONG LdrpNumberOfProcessors
 
PVOID NtDllBase
 
LARGE_INTEGER RtlpTimeout
 
BOOLEAN RtlpTimeoutDisable
 
LIST_ENTRY LdrpHashTable [LDR_HASH_TABLE_ENTRIES]
 
HANDLE LdrpKnownDllObjectDirectory
 
UNICODE_STRING LdrpKnownDllPath
 
WCHAR LdrpKnownDllPathBuffer [128]
 
UNICODE_STRING LdrpDefaultPath
 
PEB_LDR_DATA PebLdr
 
RTL_CRITICAL_SECTION_DEBUG LdrpLoaderLockDebug
 
RTL_CRITICAL_SECTION LdrpLoaderLock
 
RTL_CRITICAL_SECTION FastPebLock
 
BOOLEAN ShowSnaps
 
ULONG LdrpFatalHardErrorCount
 
ULONG LdrpActiveUnloadCount
 
ULONG RtlpDisableHeapLookaside
 
ULONG RtlpShutdownProcessFlags
 
BOOLEAN RtlpUse16ByteSLists
 

Macro Definition Documentation

◆ DEFAULT_SECURITY_COOKIE

#define DEFAULT_SECURITY_COOKIE   0xBB40E64E

Definition at line 105 of file ldrinit.c.

◆ NDEBUG

#define NDEBUG

Definition at line 16 of file ldrinit.c.

◆ VALID_CONFIG_FIELD

#define VALID_CONFIG_FIELD (   Name)    (ConfigSize >= RTL_SIZEOF_THROUGH_FIELD(IMAGE_LOAD_CONFIG_DIRECTORY, Name))

Function Documentation

◆ BOOL()

static BOOL ( WINAPI Kernel32BaseQueryModuleData)
static

◆ LdrOpenImageFileOptionsKey()

NTSTATUS NTAPI LdrOpenImageFileOptionsKey ( _In_ PUNICODE_STRING  SubKey,
_In_ BOOLEAN  Wow64,
_Out_ PHANDLE  NewKeyHandle 
)

Definition at line 115 of file ldrinit.c.

119{
120 PHANDLE RootKeyLocation;
122 UNICODE_STRING SubKeyString;
125 PWCHAR p1;
126
127 /* Check which root key to open */
128 if (Wow64)
129 RootKeyLocation = &Wow64ExecOptionsKey;
130 else
131 RootKeyLocation = &ImageExecOptionsKey;
132
133 /* Get the current key */
134 RootKey = *RootKeyLocation;
135
136 /* Setup the object attributes */
138 Wow64 ?
141 NULL,
142 NULL);
143
144 /* Open the root key */
146 if (NT_SUCCESS(Status))
147 {
148 /* Write the key handle */
149 if (InterlockedCompareExchangePointer(RootKeyLocation, RootKey, NULL) != NULL)
150 {
151 /* Someone already opened it, use it instead */
153 RootKey = *RootKeyLocation;
154 }
155
156 /* Extract the name */
157 SubKeyString = *SubKey;
158 p1 = (PWCHAR)((ULONG_PTR)SubKeyString.Buffer + SubKeyString.Length);
159 while (SubKeyString.Length)
160 {
161 if (p1[-1] == L'\\') break;
162 p1--;
163 SubKeyString.Length -= sizeof(*p1);
164 }
165 SubKeyString.Buffer = p1;
166 SubKeyString.Length = SubKey->Length - SubKeyString.Length;
167
168 /* Setup the object attributes */
170 &SubKeyString,
172 RootKey,
173 NULL);
174
175 /* Open the setting key */
176 Status = ZwOpenKey((PHANDLE)NewKeyHandle, GENERIC_READ, &ObjectAttributes);
177 }
178
179 /* Return to caller */
180 return Status;
181}
LONG NTSTATUS
Definition: precomp.h:26
IN PUNICODE_STRING IN POBJECT_ATTRIBUTES ObjectAttributes
Definition: conport.c:36
#define NULL
Definition: types.h:112
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:33
#define GENERIC_READ
Definition: compat.h:135
#define L(x)
Definition: resources.c:13
Status
Definition: gdiplustypes.h:25
#define OBJ_CASE_INSENSITIVE
Definition: winternl.h:228
#define InterlockedCompareExchangePointer
Definition: interlocked.h:144
HANDLE ImageExecOptionsKey
Definition: ldrinit.c:22
HANDLE Wow64ExecOptionsKey
Definition: ldrinit.c:23
UNICODE_STRING ImageExecOptionsString
Definition: ldrinit.c:24
UNICODE_STRING Wow64OptionsString
Definition: ldrinit.c:25
#define InitializeObjectAttributes(p, n, a, r, s)
Definition: reg.c:106
#define KEY_ENUMERATE_SUB_KEYS
Definition: nt_native.h:1022
NTSTATUS NTAPI NtClose(IN HANDLE Handle)
Definition: obhandle.c:3402
PVOID *typedef PHANDLE
Definition: ntsecpkg.h:455
static PMEMKEY RootKey
Definition: registry.c:55
uint32_t ULONG_PTR
Definition: typedefs.h:65
uint16_t * PWCHAR
Definition: typedefs.h:56

Referenced by CreateProcessInternalW(), LdrpInitializeExecutionOptions(), and LdrQueryImageFileExecutionOptionsEx().

◆ LdrpAllocateTls()

NTSTATUS NTAPI LdrpAllocateTls ( VOID  )

Definition at line 1332 of file ldrinit.c.

1333{
1334 PTEB Teb = NtCurrentTeb();
1335 PLIST_ENTRY NextEntry, ListHead;
1336 PLDRP_TLS_DATA TlsData;
1337 SIZE_T TlsDataSize;
1338 PVOID *TlsVector;
1339
1340 /* Check if we have any entries */
1342 return STATUS_SUCCESS;
1343
1344 /* Allocate the vector array */
1345 TlsVector = RtlAllocateHeap(RtlGetProcessHeap(),
1346 0,
1347 LdrpNumberOfTlsEntries * sizeof(PVOID));
1348 if (!TlsVector) return STATUS_NO_MEMORY;
1349 Teb->ThreadLocalStoragePointer = TlsVector;
1350
1351 /* Loop the TLS Array */
1352 ListHead = &LdrpTlsList;
1353 NextEntry = ListHead->Flink;
1354 while (NextEntry != ListHead)
1355 {
1356 /* Get the entry */
1357 TlsData = CONTAINING_RECORD(NextEntry, LDRP_TLS_DATA, TlsLinks);
1358 NextEntry = NextEntry->Flink;
1359
1360 /* Allocate this vector */
1361 TlsDataSize = TlsData->TlsDirectory.EndAddressOfRawData -
1363 TlsVector[TlsData->TlsDirectory.Characteristics] = RtlAllocateHeap(RtlGetProcessHeap(),
1364 0,
1365 TlsDataSize);
1366 if (!TlsVector[TlsData->TlsDirectory.Characteristics])
1367 {
1368 /* Out of memory */
1369 return STATUS_NO_MEMORY;
1370 }
1371
1372 /* Show debug message */
1373 if (ShowSnaps)
1374 {
1375 DPRINT1("LDR: TlsVector %p Index %lu = %p copied from %x to %p\n",
1376 TlsVector,
1378 &TlsVector[TlsData->TlsDirectory.Characteristics],
1380 TlsVector[TlsData->TlsDirectory.Characteristics]);
1381 }
1382
1383 /* Copy the data */
1384 RtlCopyMemory(TlsVector[TlsData->TlsDirectory.Characteristics],
1386 TlsDataSize);
1387 }
1388
1389 /* Done */
1390 return STATUS_SUCCESS;
1391}
#define DPRINT1
Definition: precomp.h:8
PVOID NTAPI RtlAllocateHeap(IN PVOID HeapHandle, IN ULONG Flags, IN SIZE_T Size)
Definition: heap.c:616
#define STATUS_NO_MEMORY
Definition: d3dkmdt.h:51
#define NtCurrentTeb
ULONG LdrpNumberOfTlsEntries
Definition: ldrinit.c:54
LIST_ENTRY LdrpTlsList
Definition: ldrinit.c:53
BOOLEAN ShowSnaps
Definition: ldrinit.c:79
#define STATUS_SUCCESS
Definition: shellext.h:65
ULONG StartAddressOfRawData
Definition: ntimage.h:546
IMAGE_TLS_DIRECTORY TlsDirectory
Definition: ntdllp.h:29
Definition: typedefs.h:120
struct _LIST_ENTRY * Flink
Definition: typedefs.h:121
Definition: compat.h:836
PVOID ThreadLocalStoragePointer
Definition: compat.h:841
ULONG_PTR SIZE_T
Definition: typedefs.h:80
#define RtlCopyMemory(Destination, Source, Length)
Definition: typedefs.h:263
#define CONTAINING_RECORD(address, type, field)
Definition: typedefs.h:260

Referenced by LdrpInitializeThread(), and LdrpInitializeTls().

◆ LdrpDisableProcessCompatGuidDetection()

BOOLEAN NTAPI LdrpDisableProcessCompatGuidDetection ( VOID  )

Definition at line 1559 of file ldrinit.c.

1560{
1561 UNICODE_STRING PolicyKey = RTL_CONSTANT_STRING(L"\\Registry\\MACHINE\\Software\\Policies\\Microsoft\\Windows\\AppCompat");
1562 UNICODE_STRING DisableDetection = RTL_CONSTANT_STRING(L"DisableCompatGuidDetection");
1568
1569 Status = NtOpenKey(&KeyHandle, KEY_QUERY_VALUE, &PolicyKeyAttributes);
1570 if (NT_SUCCESS(Status))
1571 {
1573 &DisableDetection,
1575 &KeyInfo,
1576 sizeof(KeyInfo),
1577 &ResultLength);
1579 if ((NT_SUCCESS(Status)) &&
1580 (KeyInfo.Type == REG_DWORD) &&
1581 (KeyInfo.DataLength == sizeof(ULONG)) &&
1582 (KeyInfo.Data[0] == TRUE))
1583 {
1584 return TRUE;
1585 }
1586 }
1587 return FALSE;
1588}
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
_Must_inspect_result_ _Out_ PNDIS_STATUS _In_ NDIS_HANDLE _In_ ULONG _Out_ PNDIS_STRING _Out_ PNDIS_HANDLE KeyHandle
Definition: ndis.h:4715
NTSYSAPI NTSTATUS NTAPI NtOpenKey(OUT PHANDLE KeyHandle, IN ACCESS_MASK DesiredAccess, IN POBJECT_ATTRIBUTES ObjectAttributes)
Definition: ntapi.c:336
@ KeyValuePartialInformation
Definition: nt_native.h:1185
NTSYSAPI NTSTATUS NTAPI NtQueryValueKey(IN HANDLE KeyHandle, IN PUNICODE_STRING ValueName, IN KEY_VALUE_INFORMATION_CLASS KeyValueInformationClass, IN PVOID KeyValueInformation, IN ULONG Length, IN PULONG ResultLength)
#define KEY_QUERY_VALUE
Definition: nt_native.h:1019
#define RTL_CONSTANT_OBJECT_ATTRIBUTES(n, a)
#define REG_DWORD
Definition: sdbapi.c:615
#define RTL_CONSTANT_STRING(s)
Definition: tunneltest.c:14
uint32_t ULONG
Definition: typedefs.h:59
_Must_inspect_result_ _In_ WDFDEVICE _In_ DEVICE_REGISTRY_PROPERTY _In_ ULONG _Out_ PULONG ResultLength
Definition: wdfdevice.h:3782

Referenced by LdrpInitializeProcessCompat().

◆ LdrpEnsureLoaderLockIsHeld()

VOID NTAPI LdrpEnsureLoaderLockIsHeld ( VOID  )

Definition at line 412 of file ldrinit.c.

413{
414 // Ignored atm
415}

Referenced by LdrpCheckForKnownDll(), and LdrpRunInitializeRoutines().

◆ LdrPerformRelocations()

NTSTATUS LdrPerformRelocations ( PIMAGE_NT_HEADERS  NTHeaders,
PVOID  ImageBase 
)

◆ LdrpFetchAddressOfSecurityCookie()

PVOID NTAPI LdrpFetchAddressOfSecurityCookie ( PVOID  BaseAddress,
ULONG  SizeOfImage 
)

Definition at line 419 of file ldrinit.c.

420{
422 ULONG DirSize;
423 PVOID Cookie = NULL;
424
425 /* Check NT header first */
426 if (!RtlImageNtHeader(BaseAddress)) return NULL;
427
428 /* Get the pointer to the config directory */
430 TRUE,
432 &DirSize);
433
434 /* Check for sanity */
435 if (!ConfigDir ||
436 (DirSize != 64 && ConfigDir->Size != DirSize) ||
437 (ConfigDir->Size < 0x48))
438 return NULL;
439
440 /* Now get the cookie */
441 Cookie = (PVOID)ConfigDir->SecurityCookie;
442
443 /* Check this cookie */
445 (PCHAR)Cookie >= (PCHAR)BaseAddress + SizeOfImage)
446 {
447 Cookie = NULL;
448 }
449
450 /* Return validated security cookie */
451 return Cookie;
452}
#define RtlImageDirectoryEntryToData
Definition: compat.h:809
#define IMAGE_DIRECTORY_ENTRY_LOAD_CONFIG
Definition: compat.h:153
#define RtlImageNtHeader
Definition: compat.h:806
if(dx< 0)
Definition: linetemp.h:194
#define PCHAR
Definition: match.c:90
_In_ HANDLE _Outptr_result_bytebuffer_ ViewSize PVOID * BaseAddress
Definition: mmfuncs.h:404
void * PVOID
Definition: typedefs.h:50
char * PCHAR
Definition: typedefs.h:51
_In_opt_ PVOID _Out_ PLARGE_INTEGER Cookie
Definition: cmfuncs.h:14

Referenced by LdrpInitSecurityCookie().

◆ LdrpFreeTls()

VOID NTAPI LdrpFreeTls ( VOID  )

Definition at line 1395 of file ldrinit.c.

1396{
1397 PLIST_ENTRY ListHead, NextEntry;
1398 PLDRP_TLS_DATA TlsData;
1399 PVOID *TlsVector;
1400 PTEB Teb = NtCurrentTeb();
1401
1402 /* Get a pointer to the vector array */
1403 TlsVector = Teb->ThreadLocalStoragePointer;
1404 if (!TlsVector) return;
1405
1406 /* Loop through it */
1407 ListHead = &LdrpTlsList;
1408 NextEntry = ListHead->Flink;
1409 while (NextEntry != ListHead)
1410 {
1411 TlsData = CONTAINING_RECORD(NextEntry, LDRP_TLS_DATA, TlsLinks);
1412 NextEntry = NextEntry->Flink;
1413
1414 /* Free each entry */
1415 if (TlsVector[TlsData->TlsDirectory.Characteristics])
1416 {
1417 RtlFreeHeap(RtlGetProcessHeap(),
1418 0,
1419 TlsVector[TlsData->TlsDirectory.Characteristics]);
1420 }
1421 }
1422
1423 /* Free the array itself */
1424 RtlFreeHeap(RtlGetProcessHeap(),
1425 0,
1426 TlsVector);
1427}
BOOLEAN NTAPI RtlFreeHeap(IN PVOID HeapHandle, IN ULONG Flags, IN PVOID HeapBase)
Definition: heap.c:634

Referenced by LdrShutdownThread().

◆ LdrpInit()

VOID NTAPI LdrpInit ( PCONTEXT  Context,
PVOID  SystemArgument1,
PVOID  SystemArgument2 
)

Definition at line 2588 of file ldrinit.c.

2591{
2593 PTEB Teb = NtCurrentTeb();
2594 NTSTATUS Status, LoaderStatus = STATUS_SUCCESS;
2595 MEMORY_BASIC_INFORMATION MemoryBasicInfo;
2596 PPEB Peb = NtCurrentPeb();
2597
2598 DPRINT("LdrpInit() %p/%p\n",
2599 NtCurrentTeb()->RealClientId.UniqueProcess,
2600 NtCurrentTeb()->RealClientId.UniqueThread);
2601
2602#ifdef _WIN64
2603 /* Set the SList header usage */
2605#endif /* _WIN64 */
2606
2607 /* Check if we have a deallocation stack */
2608 if (!Teb->DeallocationStack)
2609 {
2610 /* We don't, set one */
2612 Teb->NtTib.StackLimit,
2614 &MemoryBasicInfo,
2616 NULL);
2617 if (!NT_SUCCESS(Status))
2618 {
2619 /* Fail */
2622 return;
2623 }
2624
2625 /* Set the stack */
2626 Teb->DeallocationStack = MemoryBasicInfo.AllocationBase;
2627 }
2628
2629 /* Now check if the process is already being initialized */
2631 1,
2632 0) == 1)
2633 {
2634 /* Set the timeout to 30 milliseconds */
2635 Timeout.QuadPart = Int32x32To64(30, -10000);
2636
2637 /* Make sure the status hasn't changed */
2638 while (LdrpProcessInitialized == 1)
2639 {
2640 /* Do the wait */
2642 }
2643 }
2644
2645 /* Check if we have already setup LDR data */
2646 if (!Peb->Ldr)
2647 {
2648 /* Setup the Loader Lock */
2650
2651 /* Let other code know we're initializing */
2653
2654 /* Protect with SEH */
2655 _SEH2_TRY
2656 {
2657 /* Initialize the Process */
2658 LoaderStatus = LdrpInitializeProcess(Context,
2660
2661 /* Check for success and if MinimumStackCommit was requested */
2662 if (NT_SUCCESS(LoaderStatus) && Peb->MinimumStackCommit)
2663 {
2664 /* Enforce the limit */
2665 //LdrpTouchThreadStack(Peb->MinimumStackCommit);
2667 }
2668 }
2670 {
2671 /* Fail with the SEH error */
2672 LoaderStatus = _SEH2_GetExceptionCode();
2673 }
2674 _SEH2_END;
2675
2676 /* We're not initializing anymore */
2678
2679 /* Check if init worked */
2680 if (NT_SUCCESS(LoaderStatus))
2681 {
2682 /* Set the process as Initialized */
2684 }
2685 }
2686 else
2687 {
2688 /* Loader data is there... is this a fork() ? */
2690 {
2691 /* Handle the fork() */
2692 //LoaderStatus = LdrpForkProcess();
2693 LoaderStatus = STATUS_NOT_IMPLEMENTED;
2695 }
2696 else
2697 {
2698 /* This is a new thread initializing */
2700 }
2701 }
2702
2703 /* All done, test alert the thread */
2704 NtTestAlert();
2705
2706 /* Return */
2707 if (!NT_SUCCESS(LoaderStatus))
2708 {
2709 /* Fail */
2710 LdrpInitFailure(LoaderStatus);
2711 RtlRaiseStatus(LoaderStatus);
2712 }
2713}
#define NtCurrentPeb()
Definition: FLS.c:22
#define UNIMPLEMENTED
Definition: ntoskrnl.c:15
#define STATUS_NOT_IMPLEMENTED
Definition: d3dkmdt.h:42
PPEB Peb
Definition: dllmain.c:27
#define EXCEPTION_EXECUTE_HANDLER
Definition: excpt.h:90
BOOLEAN LdrpInLdrInit
Definition: ldrinit.c:30
LONG LdrpProcessInitialized
Definition: ldrinit.c:31
NTSTATUS NTAPI LdrpInitializeProcess(IN PCONTEXT Context, IN PVOID SystemArgument1)
Definition: ldrinit.c:1777
RTL_CRITICAL_SECTION LdrpLoaderLock
Definition: ldrinit.c:68
VOID NTAPI LdrpInitFailure(NTSTATUS Status)
Definition: ldrinit.c:2570
VOID NTAPI LdrpInitializeThread(IN PCONTEXT Context)
Definition: ldrinit.c:509
BOOLEAN RtlpUse16ByteSLists
NTSYSAPI NTSTATUS NTAPI ZwDelayExecution(_In_ BOOLEAN Alertable, _In_ LARGE_INTEGER *Interval)
@ MemoryBasicInformation
Definition: mmtypes.h:183
DECLSPEC_NORETURN NTSYSAPI VOID NTAPI RtlRaiseStatus(_In_ NTSTATUS Status)
#define NtCurrentProcess()
Definition: nt_native.h:1660
#define Int32x32To64(a, b)
NTSTATUS NTAPI NtQueryVirtualMemory(IN HANDLE ProcessHandle, IN PVOID BaseAddress, IN MEMORY_INFORMATION_CLASS MemoryInformationClass, OUT PVOID MemoryInformation, IN SIZE_T MemoryInformationLength, OUT PSIZE_T ReturnLength)
Definition: virtual.c:4374
NTSTATUS NTAPI NtTestAlert(VOID)
Definition: state.c:465
static ULONG Timeout
Definition: ping.c:61
#define _SEH2_GetExceptionCode()
Definition: pseh2_64.h:181
#define _SEH2_EXCEPT(...)
Definition: pseh2_64.h:82
#define _SEH2_END
Definition: pseh2_64.h:171
#define _SEH2_TRY
Definition: pseh2_64.h:71
long __cdecl _InterlockedIncrement(_Interlocked_operand_ long volatile *_Addend)
long __cdecl _InterlockedCompareExchange(_Interlocked_operand_ long volatile *_Destination, long _Exchange, long _Comparand)
#define SharedUserData
#define DPRINT
Definition: sndvol32.h:73
PVOID StackLimit
Definition: compat.h:713
PVOID LoaderLock
Definition: ntddk_ex.h:295
PPEB_LDR_DATA Ldr
Definition: btrfs_drv.h:1912
SIZE_T MinimumStackCommit
Definition: winternl.h:550
BOOLEAN InheritedAddressSpace
Definition: ntddk_ex.h:239
NT_TIB NtTib
Definition: ntddk_ex.h:332
PVOID DeallocationStack
Definition: compat.h:878
_In_opt_ PVOID _In_opt_ PVOID SystemArgument1
Definition: ketypes.h:740
#define PF_COMPARE_EXCHANGE128
Definition: ketypes.h:190

◆ LdrpInitFailure()

VOID NTAPI LdrpInitFailure ( NTSTATUS  Status)

Definition at line 2570 of file ldrinit.c.

2571{
2573 PPEB Peb = NtCurrentPeb();
2574
2575 /* Print a debug message */
2576 DPRINT1("LDR: Process initialization failure for %wZ; NTSTATUS = %08lx\n",
2578
2579 /* Raise a hard error */
2581 {
2583 }
2584}
ULONG LdrpFatalHardErrorCount
Definition: ldrinit.c:81
NTSYSAPI NTSTATUS NTAPI ZwRaiseHardError(_In_ NTSTATUS ErrorStatus, _In_ ULONG NumberOfParameters, _In_ ULONG UnicodeStringParameterMask, _In_ PULONG_PTR Parameters, _In_ ULONG ValidResponseOptions, _Out_ PULONG Response)
@ OptionOk
Definition: extypes.h:187
#define STATUS_APP_INIT_FAILURE
Definition: ntstatus.h:655
Definition: ncftp.h:89
PRTL_USER_PROCESS_PARAMETERS ProcessParameters
Definition: btrfs_drv.h:1913
UNICODE_STRING ImagePathName
Definition: btrfs_drv.h:1901
uint32_t * PULONG_PTR
Definition: typedefs.h:65

Referenced by LdrpInit(), and LdrpInitializeProcess().

◆ LdrpInitializeDotLocalSupport()

VOID NTAPI LdrpInitializeDotLocalSupport ( PRTL_USER_PROCESS_PARAMETERS  ProcessParameters)

Definition at line 1716 of file ldrinit.c.

1717{
1718 UNICODE_STRING ImagePathName = ProcessParameters->ImagePathName;
1719 WCHAR LocalBuffer[MAX_PATH];
1720 UNICODE_STRING DotLocal;
1723
1724 RequiredSize = ImagePathName.Length + LdrpDotLocal.Length + sizeof(UNICODE_NULL);
1725 if (RequiredSize <= sizeof(LocalBuffer))
1726 {
1727 RtlInitEmptyUnicodeString(&DotLocal, LocalBuffer, sizeof(LocalBuffer));
1728 }
1730 {
1731 DotLocal.Buffer = RtlAllocateHeap(RtlGetProcessHeap(), 0, RequiredSize);
1732 DotLocal.Length = 0;
1733 DotLocal.MaximumLength = RequiredSize;
1734 if (!DotLocal.Buffer)
1735 DPRINT1("LDR: Failed to allocate memory for .local check\n");
1736 }
1737 else
1738 {
1739 DotLocal.Buffer = NULL;
1740 DotLocal.Length = 0;
1741 DotLocal.MaximumLength = 0;
1742 DPRINT1("LDR: String too big for .local check\n");
1743 }
1744
1745 if (DotLocal.Buffer)
1746 {
1747 Status = RtlAppendUnicodeStringToString(&DotLocal, &ImagePathName);
1749 if (NT_SUCCESS(Status))
1750 {
1753 }
1754
1755 if (NT_SUCCESS(Status))
1756 {
1757 if (RtlDoesFileExists_UStr(&DotLocal))
1758 {
1760 }
1761 }
1762 else
1763 {
1764 DPRINT1("LDR: Failed to append: 0x%lx\n", Status);
1765 }
1766
1767 if (DotLocal.Buffer != LocalBuffer)
1768 {
1769 RtlFreeHeap(RtlGetProcessHeap(), 0, DotLocal.Buffer);
1770 }
1771 }
1772}
#define MAX_PATH
Definition: compat.h:34
const UNICODE_STRING LdrpDotLocal
Definition: ldrinit.c:28
#define ASSERT(a)
Definition: mode.c:44
#define RTL_USER_PROCESS_PARAMETERS_PRIVATE_DLL_PATH
Definition: rtltypes.h:52
NTSYSAPI NTSTATUS NTAPI RtlAppendUnicodeStringToString(PUNICODE_STRING Destination, PUNICODE_STRING Source)
#define UNICODE_NULL
#define UNICODE_STRING_MAX_BYTES
BOOLEAN NTAPI RtlDoesFileExists_UStr(IN PUNICODE_STRING FileName)
Definition: path.c:1503
USHORT MaximumLength
Definition: env_spec_w32.h:370
_Must_inspect_result_ _In_ WDFDEVICE _In_ PWDF_DEVICE_PROPERTY_DATA _In_ ULONG _Out_ PVOID _Out_ PULONG RequiredSize
Definition: wdfdevice.h:4445
__wchar_t WCHAR
Definition: xmlstorage.h:180

Referenced by LdrpInitializeProcess().

◆ LdrpInitializeExecutionOptions()

NTSTATUS NTAPI LdrpInitializeExecutionOptions ( PUNICODE_STRING  ImagePathName,
PPEB  Peb,
PHANDLE  OptionsKey 
)

Definition at line 1431 of file ldrinit.c.

1432{
1435 ULONG ExecuteOptions, MinimumStackCommit = 0, GlobalFlag;
1436
1437 /* Return error if we were not provided a pointer where to save the options key handle */
1438 if (!OptionsKey) return STATUS_INVALID_HANDLE;
1439
1440 /* Zero initialize the options key pointer */
1441 *OptionsKey = NULL;
1442
1443 /* Open the options key */
1444 Status = LdrOpenImageFileOptionsKey(ImagePathName, 0, &KeyHandle);
1445
1446 /* Save it if it was opened successfully */
1447 if (NT_SUCCESS(Status))
1448 *OptionsKey = KeyHandle;
1449
1450 if (KeyHandle)
1451 {
1452 /* There are image specific options, read them starting with NXCOMPAT */
1454 L"ExecuteOptions",
1455 4,
1456 &ExecuteOptions,
1457 sizeof(ExecuteOptions),
1458 0);
1459
1460 if (NT_SUCCESS(Status))
1461 {
1462 /* TODO: Set execution options for the process */
1463 /*
1464 if (ExecuteOptions == 0)
1465 ExecuteOptions = 1;
1466 else
1467 ExecuteOptions = 2;
1468 ZwSetInformationProcess(NtCurrentProcess(),
1469 ProcessExecuteFlags,
1470 &ExecuteOptions,
1471 sizeof(ULONG));*/
1472
1473 }
1474
1475 /* Check if this image uses large pages */
1476 if (Peb->ImageUsesLargePages)
1477 {
1478 /* TODO: If it does, open large page key */
1480 }
1481
1482 /* Get various option values */
1484 L"DisableHeapLookaside",
1485 REG_DWORD,
1488 NULL);
1489
1491 L"ShutdownFlags",
1492 REG_DWORD,
1495 NULL);
1496
1498 L"MinimumStackCommitInBytes",
1499 REG_DWORD,
1500 &MinimumStackCommit,
1501 sizeof(MinimumStackCommit),
1502 NULL);
1503
1504 /* Update PEB's minimum stack commit if it's lower */
1505 if (Peb->MinimumStackCommit < MinimumStackCommit)
1506 Peb->MinimumStackCommit = MinimumStackCommit;
1507
1508 /* Set the global flag */
1510 L"GlobalFlag",
1511 REG_DWORD,
1512 &GlobalFlag,
1513 sizeof(GlobalFlag),
1514 NULL);
1515
1516 if (NT_SUCCESS(Status))
1517 Peb->NtGlobalFlag = GlobalFlag;
1518 else
1519 GlobalFlag = 0;
1520
1521 /* Call AVRF if necessary */
1523 {
1525 if (!NT_SUCCESS(Status))
1526 {
1527 DPRINT1("AVRF: LdrpInitializeApplicationVerifierPackage failed with %08X\n", Status);
1528 }
1529 }
1530 }
1531 else
1532 {
1533 /* There are no image-specific options, so perform global initialization */
1535 {
1536 /* Initialize app verifier package */
1538 if (!NT_SUCCESS(Status))
1539 {
1540 DPRINT1("AVRF: LdrpInitializeApplicationVerifierPackage failed with %08X\n", Status);
1541 }
1542 }
1543 }
1544
1545 return STATUS_SUCCESS;
1546}
#define STATUS_INVALID_HANDLE
Definition: d3dkmdt.h:40
#define FLG_HEAP_PAGE_ALLOCS
Definition: pstypes.h:84
#define FLG_APPLICATION_VERIFIER
Definition: pstypes.h:64
ULONG RtlpDisableHeapLookaside
Definition: ldrinit.c:91
ULONG RtlpShutdownProcessFlags
Definition: ldrinit.c:92
NTSTATUS NTAPI LdrQueryImageFileKeyOption(_In_ HANDLE KeyHandle, _In_ PCWSTR ValueName, _In_ ULONG Type, _Out_ PVOID Buffer, _In_ ULONG BufferSize, _Out_opt_ PULONG ReturnedLength)
Definition: ldrinit.c:188
NTSTATUS NTAPI LdrOpenImageFileOptionsKey(_In_ PUNICODE_STRING SubKey, _In_ BOOLEAN Wow64, _Out_ PHANDLE NewKeyHandle)
Definition: ldrinit.c:115
NTSTATUS NTAPI LdrpInitializeApplicationVerifierPackage(IN HANDLE KeyHandle, IN PPEB Peb, IN BOOLEAN SystemWide, IN BOOLEAN ReadAdvancedOptions)
ULONG NtGlobalFlag
Definition: ntddk_ex.h:270

Referenced by LdrpInitializeProcess().

◆ LdrpInitializeProcess()

NTSTATUS NTAPI LdrpInitializeProcess ( IN PCONTEXT  Context,
IN PVOID  SystemArgument1 
)

Definition at line 1777 of file ldrinit.c.

1779{
1780 RTL_HEAP_PARAMETERS HeapParameters;
1781 ULONG ComSectionSize;
1782 ANSI_STRING BaseProcessInitPostImportName = RTL_CONSTANT_STRING("BaseProcessInitPostImport");
1783 ANSI_STRING BaseQueryModuleDataName = RTL_CONSTANT_STRING("BaseQueryModuleData");
1784 PVOID OldShimData;
1786 //UNICODE_STRING LocalFileName, FullImageName;
1787 HANDLE SymLinkHandle;
1788 //ULONG DebugHeapOnly;
1789 UNICODE_STRING CommandLine, NtSystemRoot, ImagePathName, FullPath, ImageFileName, KnownDllString;
1790 PPEB Peb = NtCurrentPeb();
1791 BOOLEAN IsDotNetImage = FALSE;
1792 BOOLEAN FreeCurDir = FALSE;
1793 //HANDLE CompatKey;
1794 PRTL_USER_PROCESS_PARAMETERS ProcessParameters;
1795 //LPWSTR ImagePathBuffer;
1796 ULONG ConfigSize;
1798 HANDLE OptionsKey;
1799 ULONG HeapFlags;
1800 PIMAGE_NT_HEADERS NtHeader;
1801 LPWSTR NtDllName = NULL;
1802 NTSTATUS Status, ImportStatus;
1803 NLSTABLEINFO NlsTable;
1805 PTEB Teb = NtCurrentTeb();
1806 PLIST_ENTRY ListHead;
1807 PLIST_ENTRY NextEntry;
1808 ULONG i;
1809 PWSTR ImagePath;
1810 ULONG DebugProcessHeapOnly = 0;
1811 PLDR_DATA_TABLE_ENTRY NtLdrEntry;
1812 PWCHAR Current;
1813 ULONG ExecuteOptions = 0;
1814 PVOID ViewBase;
1815
1816 /* Set a NULL SEH Filter */
1818
1819 /* Get the image path */
1821
1822 /* Check if it's not normalized */
1824 {
1825 /* Normalize it*/
1826 ImagePath = (PWSTR)((ULONG_PTR)ImagePath + (ULONG_PTR)Peb->ProcessParameters);
1827 }
1828
1829 /* Create a unicode string for the Image Path */
1831 ImagePathName.MaximumLength = ImagePathName.Length + sizeof(WCHAR);
1832 ImagePathName.Buffer = ImagePath;
1833
1834 /* Get the NT Headers */
1836
1837 /* Get the execution options */
1838 Status = LdrpInitializeExecutionOptions(&ImagePathName, Peb, &OptionsKey);
1839
1840 /* Check if this is a .NET executable */
1842 TRUE,
1844 &ComSectionSize))
1845 {
1846 /* Remember this for later */
1847 IsDotNetImage = TRUE;
1848 }
1849
1850 /* Save the NTDLL Base address */
1852
1853 /* If this is a Native Image */
1855 {
1856 /* Then do DLL Validation */
1858 }
1859
1860 /* Save the old Shim Data */
1861 OldShimData = Peb->pShimData;
1862
1863 /* ReactOS specific: do not clear it. (Windows starts doing the same in later versions) */
1864 //Peb->pShimData = NULL;
1865
1866 /* Save the number of processors and CS timeout */
1869
1870 /* Normalize the parameters */
1871 ProcessParameters = RtlNormalizeProcessParams(Peb->ProcessParameters);
1872 if (ProcessParameters)
1873 {
1874 /* Save the Image and Command Line Names */
1875 ImageFileName = ProcessParameters->ImagePathName;
1876 CommandLine = ProcessParameters->CommandLine;
1877 }
1878 else
1879 {
1880 /* It failed, initialize empty strings */
1881 RtlInitUnicodeString(&ImageFileName, NULL);
1882 RtlInitUnicodeString(&CommandLine, NULL);
1883 }
1884
1885 /* Initialize NLS data */
1889 &NlsTable);
1890
1891 /* Reset NLS Translations */
1892 RtlResetRtlTranslations(&NlsTable);
1893
1894 /* Get the Image Config Directory */
1896 TRUE,
1898 &ConfigSize);
1899
1900 /* Setup the Heap Parameters */
1901 RtlZeroMemory(&HeapParameters, sizeof(HeapParameters));
1902 HeapFlags = HEAP_GROWABLE;
1903 HeapParameters.Length = sizeof(HeapParameters);
1904
1905 /* Check if we have Configuration Data */
1906#define VALID_CONFIG_FIELD(Name) (ConfigSize >= RTL_SIZEOF_THROUGH_FIELD(IMAGE_LOAD_CONFIG_DIRECTORY, Name))
1907 /* The 'original' load config ends after SecurityCookie */
1908 if ((LoadConfig) && ConfigSize && (VALID_CONFIG_FIELD(SecurityCookie) || ConfigSize == LoadConfig->Size))
1909 {
1910 if (ConfigSize != sizeof(IMAGE_LOAD_CONFIG_DIRECTORY))
1911 DPRINT1("WARN: Accepting different LOAD_CONFIG size!\n");
1912 else
1913 DPRINT1("Applying LOAD_CONFIG\n");
1914
1915 if (VALID_CONFIG_FIELD(GlobalFlagsSet) && LoadConfig->GlobalFlagsSet)
1916 Peb->NtGlobalFlag |= LoadConfig->GlobalFlagsSet;
1917
1918 if (VALID_CONFIG_FIELD(GlobalFlagsClear) && LoadConfig->GlobalFlagsClear)
1919 Peb->NtGlobalFlag &= ~LoadConfig->GlobalFlagsClear;
1920
1921 /* Convert the default CS timeout from milliseconds to 100ns units */
1922 if (VALID_CONFIG_FIELD(CriticalSectionDefaultTimeout) && LoadConfig->CriticalSectionDefaultTimeout)
1923 RtlpTimeout.QuadPart = Int32x32To64(LoadConfig->CriticalSectionDefaultTimeout, -10000);
1924
1925 if (VALID_CONFIG_FIELD(DeCommitFreeBlockThreshold) && LoadConfig->DeCommitFreeBlockThreshold)
1926 HeapParameters.DeCommitFreeBlockThreshold = LoadConfig->DeCommitFreeBlockThreshold;
1927
1928 if (VALID_CONFIG_FIELD(DeCommitTotalFreeThreshold) && LoadConfig->DeCommitTotalFreeThreshold)
1929 HeapParameters.DeCommitTotalFreeThreshold = LoadConfig->DeCommitTotalFreeThreshold;
1930
1931 if (VALID_CONFIG_FIELD(MaximumAllocationSize) && LoadConfig->MaximumAllocationSize)
1932 HeapParameters.MaximumAllocationSize = LoadConfig->MaximumAllocationSize;
1933
1934 if (VALID_CONFIG_FIELD(VirtualMemoryThreshold) && LoadConfig->VirtualMemoryThreshold)
1935 HeapParameters.VirtualMemoryThreshold = LoadConfig->VirtualMemoryThreshold;
1936
1937 if (VALID_CONFIG_FIELD(ProcessHeapFlags) && LoadConfig->ProcessHeapFlags)
1938 HeapFlags = LoadConfig->ProcessHeapFlags;
1939 }
1940#undef VALID_CONFIG_FIELD
1941
1942 /* Check for custom affinity mask */
1944 {
1945 /* Set it */
1949 sizeof(Peb->ImageProcessAffinityMask));
1950 }
1951
1952 /* Check if verbose debugging (ShowSnaps) was requested */
1954
1955 /* Start verbose debugging messages right now if they were requested */
1956 if (ShowSnaps)
1957 {
1958 DPRINT1("LDR: PID: 0x%p started - '%wZ'\n",
1960 &CommandLine);
1961 }
1962
1963 /* If the CS timeout is longer than 1 hour, disable it */
1964 if (RtlpTimeout.QuadPart < Int32x32To64(3600, -10000000))
1966
1967 /* Initialize Critical Section Data */
1969
1970 /* Initialize VEH Call lists */
1972
1973 /* Set TLS/FLS Bitmap data */
1977
1978 /* Initialize FLS Bitmap */
1982 RtlSetBit(&FlsBitMap, 0);
1984
1985 /* Initialize TLS Bitmap */
1989 RtlSetBit(&TlsBitMap, 0);
1994
1995 /* Initialize the Hash Table */
1996 for (i = 0; i < LDR_HASH_TABLE_ENTRIES; i++)
1997 {
1999 }
2000
2001 /* Initialize the Loader Lock */
2002 // FIXME: What's the point of initing it manually, if two lines lower
2003 // a call to RtlInitializeCriticalSection() is being made anyway?
2004 //InsertTailList(&RtlCriticalSectionList, &LdrpLoaderLock.DebugInfo->ProcessLocksList);
2005 //LdrpLoaderLock.DebugInfo->CriticalSection = &LdrpLoaderLock;
2008
2009 /* Check if User Stack Trace Database support was requested */
2011 {
2012 DPRINT1("We don't support user stack trace databases yet\n");
2013 }
2014
2015 /* Setup Fast PEB Lock */
2018 //Peb->FastPebLockRoutine = (PPEBLOCKROUTINE)RtlEnterCriticalSection;
2019 //Peb->FastPebUnlockRoutine = (PPEBLOCKROUTINE)RtlLeaveCriticalSection;
2020
2021 /* Setup Callout Lock */
2022 //RtlInitializeCriticalSection(&RtlpCalloutEntryLock);
2023
2024 /* For old executables, use 16-byte aligned heap */
2025 if ((NtHeader->OptionalHeader.MajorSubsystemVersion <= 3) &&
2026 (NtHeader->OptionalHeader.MinorSubsystemVersion < 51))
2027 {
2028 HeapFlags |= HEAP_CREATE_ALIGN_16;
2029 }
2030
2031 /* Setup the Heap */
2033 Peb->ProcessHeap = RtlCreateHeap(HeapFlags,
2034 NULL,
2037 NULL,
2038 &HeapParameters);
2039
2040 if (!Peb->ProcessHeap)
2041 {
2042 DPRINT1("Failed to create process heap\n");
2043 return STATUS_NO_MEMORY;
2044 }
2045
2047 if (!NT_SUCCESS(Status))
2048 {
2049 DPRINT1("Failed to initialize locale table\n");
2050 return Status;
2051 }
2052
2053 /* Allocate an Activation Context Stack */
2054 Status = RtlAllocateActivationContextStack(&Teb->ActivationContextStackPointer);
2055 if (!NT_SUCCESS(Status)) return Status;
2056
2057 RtlZeroMemory(&HeapParameters, sizeof(HeapParameters));
2058 HeapFlags = HEAP_GROWABLE | HEAP_CLASS_1;
2059 HeapParameters.Length = sizeof(HeapParameters);
2060 LdrpHeap = RtlCreateHeap(HeapFlags, 0, 0x10000, 0x6000, 0, &HeapParameters);
2061 if (!LdrpHeap)
2062 {
2063 DPRINT1("Failed to create loader private heap\n");
2064 return STATUS_NO_MEMORY;
2065 }
2066
2067 /* Check for Debug Heap */
2068 if (OptionsKey)
2069 {
2070 /* Query the setting */
2072 L"DebugProcessHeapOnly",
2073 REG_DWORD,
2074 &DebugProcessHeapOnly,
2075 sizeof(ULONG),
2076 NULL);
2077
2078 if (NT_SUCCESS(Status))
2079 {
2080 /* Reset DPH if requested */
2081 if (RtlpPageHeapEnabled && DebugProcessHeapOnly)
2082 {
2083 RtlpDphGlobalFlags &= ~DPH_FLAG_DLL_NOTIFY;
2085 }
2086 }
2087 }
2088
2089 /* Build the NTDLL Path */
2090 FullPath.Buffer = StringBuffer;
2091 FullPath.Length = 0;
2092 FullPath.MaximumLength = sizeof(StringBuffer);
2095 RtlAppendUnicodeToString(&FullPath, L"\\System32\\");
2096
2097 /* Open the Known DLLs directory */
2098 RtlInitUnicodeString(&KnownDllString, L"\\KnownDlls");
2100 &KnownDllString,
2102 NULL,
2103 NULL);
2107
2108 /* Check if it exists */
2109 if (NT_SUCCESS(Status))
2110 {
2111 /* Open the Known DLLs Path */
2112 RtlInitUnicodeString(&KnownDllString, L"KnownDllPath");
2114 &KnownDllString,
2117 NULL);
2118 Status = NtOpenSymbolicLinkObject(&SymLinkHandle,
2121 if (NT_SUCCESS(Status))
2122 {
2123 /* Query the path */
2127 Status = ZwQuerySymbolicLinkObject(SymLinkHandle, &LdrpKnownDllPath, NULL);
2128 NtClose(SymLinkHandle);
2129 if (!NT_SUCCESS(Status))
2130 {
2131 DPRINT1("LDR: %s - failed call to ZwQuerySymbolicLinkObject with status %x\n", "", Status);
2132 return Status;
2133 }
2134 }
2135 }
2136
2137 /* Check if we failed */
2138 if (!NT_SUCCESS(Status))
2139 {
2140 /* Assume System32 */
2143 LdrpKnownDllPath.Length -= sizeof(WCHAR);
2144 }
2145
2146 /* If we have process parameters, get the default path and current path */
2147 if (ProcessParameters)
2148 {
2149 /* Check if we have a Dll Path */
2150 if (ProcessParameters->DllPath.Length)
2151 {
2152 /* Get the path */
2153 LdrpDefaultPath = *(PUNICODE_STRING)&ProcessParameters->DllPath;
2154 }
2155 else
2156 {
2157 /* We need a valid path */
2158 DPRINT1("No valid DllPath was given!\n");
2160 }
2161
2162 /* Set the current directory */
2163 CurrentDirectory = ProcessParameters->CurrentDirectory.DosPath;
2164
2165 /* Check if it's empty or invalid */
2166 if ((!CurrentDirectory.Buffer) ||
2167 (CurrentDirectory.Buffer[0] == UNICODE_NULL) ||
2168 (!CurrentDirectory.Length))
2169 {
2170 /* Allocate space for the buffer */
2172 0,
2173 3 * sizeof(WCHAR) +
2174 sizeof(UNICODE_NULL));
2175 if (!CurrentDirectory.Buffer)
2176 {
2177 DPRINT1("LDR: LdrpInitializeProcess - unable to allocate current working directory buffer\n");
2178 // FIXME: And what?
2179 }
2180
2181 /* Copy the drive of the system root */
2183 SharedUserData->NtSystemRoot,
2184 3 * sizeof(WCHAR));
2185 CurrentDirectory.Buffer[3] = UNICODE_NULL;
2186 CurrentDirectory.Length = 3 * sizeof(WCHAR);
2187 CurrentDirectory.MaximumLength = CurrentDirectory.Length + sizeof(WCHAR);
2188
2189 FreeCurDir = TRUE;
2190 DPRINT("Using dynamically allocd curdir\n");
2191 }
2192 else
2193 {
2194 /* Use the local buffer */
2195 DPRINT("Using local system root\n");
2196 }
2197 }
2198
2199 /* Setup Loader Data */
2200 Peb->Ldr = &PebLdr;
2204 PebLdr.Length = sizeof(PEB_LDR_DATA);
2206
2207 /* Allocate a data entry for the Image */
2209
2210 /* Set it up */
2214 LdrpImageEntry->FullDllName = ImageFileName;
2215
2216 if (IsDotNetImage)
2218 else
2219 LdrpImageEntry->Flags = 0;
2220
2221 /* Check if the name is empty */
2222 if (!ImageFileName.Buffer[0])
2223 {
2224 /* Use the same Base name */
2226 }
2227 else
2228 {
2229 /* Find the last slash */
2230 Current = ImageFileName.Buffer;
2231 while (*Current)
2232 {
2233 if (*Current++ == '\\')
2234 {
2235 /* Set this path */
2236 NtDllName = Current;
2237 }
2238 }
2239
2240 /* Did we find anything? */
2241 if (!NtDllName)
2242 {
2243 /* Use the same Base name */
2245 }
2246 else
2247 {
2248 /* Setup the name */
2249 LdrpImageEntry->BaseDllName.Length = (USHORT)((ULONG_PTR)ImageFileName.Buffer + ImageFileName.Length - (ULONG_PTR)NtDllName);
2252 (ImageFileName.Length - LdrpImageEntry->BaseDllName.Length));
2253 }
2254 }
2255
2256 /* Processing done, insert it */
2259
2260 /* Now add an entry for NTDLL */
2262 NtLdrEntry->Flags = LDRP_IMAGE_DLL;
2263 NtLdrEntry->EntryPoint = LdrpFetchAddressOfEntryPoint(NtLdrEntry->DllBase);
2264 NtLdrEntry->LoadCount = -1;
2265 NtLdrEntry->EntryPointActivationContext = 0;
2266
2267 NtLdrEntry->FullDllName.Length = FullPath.Length;
2268 NtLdrEntry->FullDllName.MaximumLength = FullPath.MaximumLength;
2269 NtLdrEntry->FullDllName.Buffer = StringBuffer;
2271
2272 NtLdrEntry->BaseDllName.Length = NtDllString.Length;
2274 NtLdrEntry->BaseDllName.Buffer = NtDllString.Buffer;
2275
2276 /* Processing done, insert it */
2277 LdrpNtDllDataTableEntry = NtLdrEntry;
2278 LdrpInsertMemoryTableEntry(NtLdrEntry);
2279
2280 /* Let the world know */
2281 if (ShowSnaps)
2282 {
2283 DPRINT1("LDR: NEW PROCESS\n");
2284 DPRINT1(" Image Path: %wZ (%wZ)\n", &LdrpImageEntry->FullDllName, &LdrpImageEntry->BaseDllName);
2285 DPRINT1(" Current Directory: %wZ\n", &CurrentDirectory);
2286 DPRINT1(" Search Path: %wZ\n", &LdrpDefaultPath);
2287 }
2288
2289 /* Link the Init Order List */
2292
2293 /* Initialize Wine's active context implementation for the current process */
2294 RtlpInitializeActCtx(&OldShimData);
2295
2296 /* Set the current directory */
2298 if (!NT_SUCCESS(Status))
2299 {
2300 /* We failed, check if we should free it */
2301 if (FreeCurDir) RtlFreeUnicodeString(&CurrentDirectory);
2302
2303 /* Set it to the NT Root */
2306 }
2307 else
2308 {
2309 /* We're done with it, free it */
2310 if (FreeCurDir) RtlFreeUnicodeString(&CurrentDirectory);
2311 }
2312
2313 /* Check if we should look for a .local file */
2314 if (ProcessParameters && !(ProcessParameters->Flags & RTL_USER_PROCESS_PARAMETERS_LOCAL_DLL_PATH))
2315 {
2316 LdrpInitializeDotLocalSupport(ProcessParameters);
2317 }
2318
2319 /* Check if the Application Verifier was enabled */
2321 {
2323 if (!NT_SUCCESS(Status))
2324 {
2325 DPRINT1("LDR: AVrfInitializeVerifier failed (ntstatus 0x%x)\n", Status);
2326 return Status;
2327 }
2328
2329 }
2330
2331 if (IsDotNetImage)
2332 {
2333 /* FIXME */
2334 DPRINT1("We don't support .NET applications yet\n");
2335 }
2336
2339 {
2340 PVOID Kernel32BaseAddress;
2341 PVOID FunctionAddress;
2342
2343 Status = LdrLoadDll(NULL, NULL, &Kernel32String, &Kernel32BaseAddress);
2344
2345 if (!NT_SUCCESS(Status))
2346 {
2347 if (ShowSnaps)
2348 DPRINT1("LDR: Unable to load %wZ, Status=0x%08lx\n", &Kernel32String, Status);
2349 return Status;
2350 }
2351
2352 Status = LdrGetProcedureAddress(Kernel32BaseAddress,
2353 &BaseProcessInitPostImportName,
2354 0,
2355 &FunctionAddress);
2356
2357 if (!NT_SUCCESS(Status))
2358 {
2359 if (ShowSnaps)
2360 DPRINT1("LDR: Unable to find post-import process init function, Status=0x%08lx\n", Status);
2361 return Status;
2362 }
2363 Kernel32ProcessInitPostImportFunction = FunctionAddress;
2364
2365 Status = LdrGetProcedureAddress(Kernel32BaseAddress,
2366 &BaseQueryModuleDataName,
2367 0,
2368 &FunctionAddress);
2369
2370 if (!NT_SUCCESS(Status))
2371 {
2372 if (ShowSnaps)
2373 DPRINT1("LDR: Unable to find BaseQueryModuleData, Status=0x%08lx\n", Status);
2374 return Status;
2375 }
2376 Kernel32BaseQueryModuleData = FunctionAddress;
2377 }
2378
2379 /* Walk the IAT and load all the DLLs */
2381
2382 /* Check if relocation is needed */
2384 {
2385 DPRINT1("LDR: Performing EXE relocation\n");
2386
2387 /* Change the protection to prepare for relocation */
2388 ViewBase = Peb->ImageBaseAddress;
2389 Status = LdrpSetProtection(ViewBase, FALSE);
2390 if (!NT_SUCCESS(Status)) return Status;
2391
2392 /* Do the relocation */
2394 0LL,
2395 NULL,
2399 if (!NT_SUCCESS(Status))
2400 {
2401 DPRINT1("LdrRelocateImageWithBias() failed\n");
2402 return Status;
2403 }
2404
2405 /* Check if a start context was provided */
2406 if (Context)
2407 {
2408 DPRINT1("WARNING: Relocated EXE Context");
2409 UNIMPLEMENTED; // We should support this
2411 }
2412
2413 /* Restore the protection */
2414 Status = LdrpSetProtection(ViewBase, TRUE);
2415 if (!NT_SUCCESS(Status)) return Status;
2416 }
2417
2418 /* Lock the DLLs */
2419 ListHead = &Peb->Ldr->InLoadOrderModuleList;
2420 NextEntry = ListHead->Flink;
2421 while (ListHead != NextEntry)
2422 {
2423 NtLdrEntry = CONTAINING_RECORD(NextEntry, LDR_DATA_TABLE_ENTRY, InLoadOrderLinks);
2424 NtLdrEntry->LoadCount = -1;
2425 NextEntry = NextEntry->Flink;
2426 }
2427
2428 /* Phase 0 is done */
2430
2431 /* Check whether all static imports were properly loaded and return here */
2432 if (!NT_SUCCESS(ImportStatus)) return ImportStatus;
2433
2434 /* Following two calls are for Vista+ support, required for winesync */
2435 /* Initialize the keyed event for condition variables */
2438
2439 /* Initialize TLS */
2441 if (!NT_SUCCESS(Status))
2442 {
2443 DPRINT1("LDR: LdrpProcessInitialization failed to initialize TLS slots; status %x\n",
2444 Status);
2445 return Status;
2446 }
2447
2448 /* FIXME Mark the DLL Ranges for Stack Traces later */
2449
2450 /* Notify the debugger now */
2451 if (Peb->BeingDebugged)
2452 {
2453 /* Break */
2454 DbgBreakPoint();
2455
2456 /* Update show snaps again */
2458 }
2459
2460 /* Validate the Image for MP Usage */
2462
2463 /* Check NX options and set them */
2464 if (SharedUserData->NXSupportPolicy == NX_SUPPORT_POLICY_ALWAYSON)
2465 {
2466 ExecuteOptions = MEM_EXECUTE_OPTION_DISABLE |
2469 }
2470 else if (SharedUserData->NXSupportPolicy == NX_SUPPORT_POLICY_ALWAYSOFF)
2471 {
2473 }
2476 &ExecuteOptions,
2477 sizeof(ExecuteOptions));
2478 if (!NT_SUCCESS(Status))
2479 {
2480 DPRINT1("LDR: Could not set process execute flags 0x%x; status %x\n",
2481 ExecuteOptions, Status);
2482 }
2483
2484 // FIXME: Should be done by Application Compatibility features,
2485 // by reading the registry, etc...
2486 // For now, this is the old code from ntdll!RtlGetVersion().
2487 RtlInitEmptyUnicodeString(&Peb->CSDVersion, NULL, 0);
2488 if (((Peb->OSCSDVersion >> 8) & 0xFF) != 0)
2489 {
2490 WCHAR szCSDVersion[128];
2491 LONG i;
2492 USHORT Length = (USHORT)ARRAYSIZE(szCSDVersion) - 1;
2493 i = _snwprintf(szCSDVersion, Length,
2494 L"Service Pack %d",
2495 ((Peb->OSCSDVersion >> 8) & 0xFF));
2496 if (i < 0)
2497 {
2498 /* Null-terminate if it was overflowed */
2499 szCSDVersion[Length] = UNICODE_NULL;
2500 }
2501
2502 Length *= sizeof(WCHAR);
2503 Peb->CSDVersion.Buffer = RtlAllocateHeap(RtlGetProcessHeap(),
2504 0,
2505 Length + sizeof(UNICODE_NULL));
2506 if (Peb->CSDVersion.Buffer)
2507 {
2510
2512 szCSDVersion,
2515 }
2516 }
2517
2518 /* Check if we had Shim Data */
2519 if (OldShimData)
2520 {
2521 /* Load the Shim Engine */
2523 LdrpLoadShimEngine(OldShimData, &ImagePathName, OldShimData);
2524 }
2525 else
2526 {
2527 /* Check for Application Compatibility Goo */
2528 //LdrQueryApplicationCompatibilityGoo(hKey);
2529 DPRINT("Querying app compat hacks is missing!\n");
2530 }
2531
2532 /*
2533 * FIXME: Check for special images, SecuROM, SafeDisc and other NX-
2534 * incompatible images.
2535 */
2536
2537 /* Now call the Init Routines */
2539 if (!NT_SUCCESS(Status))
2540 {
2541 DPRINT1("LDR: LdrpProcessInitialization failed running initialization routines; status %x\n",
2542 Status);
2543 return Status;
2544 }
2545
2546 /* Notify Shim Engine */
2547 if (g_ShimsEnabled)
2548 {
2551 SE_InstallAfterInit(&ImagePathName, OldShimData);
2552 }
2553
2554 /* Check if we have a user-defined Post Process Routine */
2556 {
2557 /* Call it */
2559 }
2560
2561 /* Close the key if we have one opened */
2562 if (OptionsKey) NtClose(OptionsKey);
2563
2564 /* Return status */
2565 return Status;
2566}
#define VOID
Definition: acefi.h:82
unsigned char BOOLEAN
Definition: actypes.h:127
WCHAR CurrentDirectory[1024]
Definition: chkdsk.c:74
struct _PEB_LDR_DATA PEB_LDR_DATA
#define RtlInitializeBitMap
Definition: dbgbitmap.h:326
#define RtlSetBit
Definition: dbgbitmap.h:344
#define ARRAYSIZE(array)
Definition: filtermapper.c:47
#define SYMBOLIC_LINK_QUERY
Definition: volume.c:47
_ACRTIMP int __cdecl _snwprintf(wchar_t *, size_t, const wchar_t *,...)
Definition: wcs.c:1493
#define ULONG_PTR
Definition: config.h:101
#define InsertHeadList(ListHead, Entry)
UNICODE_STRING * PUNICODE_STRING
Definition: env_spec_w32.h:373
NTSTATUS RtlAppendUnicodeToString(IN PUNICODE_STRING Str1, IN PWSTR Str2)
Definition: string_lib.cpp:62
#define InitializeListHead(ListHead)
Definition: env_spec_w32.h:944
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
#define FLG_USER_STACK_TRACE_DB
Definition: pstypes.h:67
#define FLG_SHOW_LDR_SNAPS
Definition: pstypes.h:57
#define TLS_EXPANSION_SLOTS
Definition: pstypes.h:311
NTSYSAPI void WINAPI RtlSetUnhandledExceptionFilter(PRTL_EXCEPTION_FILTER)
NTSYSAPI void WINAPI DbgBreakPoint(void)
@ ProcessAffinityMask
Definition: winternl.h:1903
@ ProcessExecuteFlags
Definition: winternl.h:1916
PVOID NtDllBase
Definition: ldrinit.c:56
PLDR_DATA_TABLE_ENTRY LdrpImageEntry
Definition: ldrinit.c:39
VOID NTAPI LdrpInitializeDotLocalSupport(PRTL_USER_PROCESS_PARAMETERS ProcessParameters)
Definition: ldrinit.c:1716
WCHAR LdrpKnownDllPathBuffer[128]
Definition: ldrinit.c:62
UNICODE_STRING LdrpDefaultPath
Definition: ldrinit.c:63
VOID NTAPI RtlpInitDeferredCriticalSection(VOID)
Definition: critical.c:272
NTSTATUS NTAPI LdrpInitializeExecutionOptions(PUNICODE_STRING ImagePathName, PPEB Peb, PHANDLE OptionsKey)
Definition: ldrinit.c:1431
RTL_CRITICAL_SECTION FastPebLock
Definition: ldrinit.c:77
ULONG LdrpNumberOfProcessors
Definition: ldrinit.c:55
RTL_BITMAP FlsBitMap
Definition: ldrinit.c:51
RTL_BITMAP TlsBitMap
Definition: ldrinit.c:49
BOOLEAN LdrpLoaderLockInit
Definition: ldrinit.c:32
LARGE_INTEGER RtlpTimeout
Definition: critical.c:25
NTSTATUS NTAPI RtlpInitializeLocaleTable(VOID)
Definition: locale.c:529
VOID NTAPI RtlInitializeHeapManager(VOID)
Definition: libsupp.c:243
VOID NTAPI LdrpValidateImageForMp(IN PLDR_DATA_TABLE_ENTRY LdrDataTableEntry)
Definition: ldrinit.c:1550
LIST_ENTRY LdrpHashTable[LDR_HASH_TABLE_ENTRIES]
Definition: ldrinit.c:59
UNICODE_STRING LdrpKnownDllPath
Definition: ldrinit.c:61
RTL_BITMAP TlsExpansionBitMap
Definition: ldrinit.c:50
NTSTATUS NTAPI LdrpRunInitializeRoutines(IN PCONTEXT Context OPTIONAL)
Definition: ldrinit.c:652
BOOLEAN LdrpLdrDatabaseIsSetup
Definition: ldrinit.c:33
VOID NTAPI RtlpInitializeVectoredExceptionHandling(VOID)
Definition: vectoreh.c:30
WCHAR StringBuffer[156]
Definition: ldrinit.c:41
HANDLE LdrpKnownDllObjectDirectory
Definition: ldrinit.c:60
PLDR_DATA_TABLE_ENTRY LdrpNtDllDataTableEntry
Definition: ldrinit.c:44
NTSTATUS NTAPI LdrpInitializeTls(VOID)
Definition: ldrinit.c:1269
#define VALID_CONFIG_FIELD(Name)
UNICODE_STRING Kernel32String
Definition: ldrinit.c:27
BOOLEAN RtlpTimeoutDisable
Definition: critical.c:26
UNICODE_STRING NtDllString
Definition: ldrinit.c:26
NTSTATUS NTAPI RtlpInitializeActCtx(PVOID *pOldShimData)
BOOLEAN LdrpDllValidation
Definition: ldrinit.c:37
PEB_LDR_DATA PebLdr
Definition: ldrinit.c:65
NTSTATUS NTAPI DECLSPEC_HOTPATCH LdrLoadDll(_In_opt_ PWSTR SearchPath, _In_opt_ PULONG DllCharacteristics, _In_ PUNICODE_STRING DllName, _Out_ PVOID *BaseAddress)
Definition: ldrapi.c:312
NTSTATUS NTAPI LdrGetProcedureAddress(_In_ PVOID BaseAddress, _In_opt_ _When_(Ordinal==0, _Notnull_) PANSI_STRING Name, _In_opt_ _When_(Name==NULL, _In_range_(>, 0)) ULONG Ordinal, _Out_ PVOID *ProcedureAddress)
Definition: ldrapi.c:789
#define LDRP_ENTRY_PROCESSED
Definition: ldrtypes.h:48
#define LDRP_COR_IMAGE
Definition: ldrtypes.h:56
#define LDRP_IMAGE_DLL
Definition: ldrtypes.h:39
#define MEM_EXECUTE_OPTION_DISABLE
Definition: mmtypes.h:73
#define MEM_EXECUTE_OPTION_PERMANENT
Definition: mmtypes.h:76
#define MEM_EXECUTE_OPTION_DISABLE_THUNK_EMULATION
Definition: mmtypes.h:75
#define MEM_EXECUTE_OPTION_ENABLE
Definition: mmtypes.h:74
NTSYSAPI NTSTATUS NTAPI ZwOpenDirectoryObject(_Out_ PHANDLE FileHandle, _In_ ACCESS_MASK DesiredAccess, _In_ POBJECT_ATTRIBUTES ObjectAttributes)
NTSYSAPI VOID NTAPI RtlInitNlsTables(_In_ PUSHORT AnsiTableBase, _In_ PUSHORT OemTableBase, _In_ PUSHORT CaseTableBase, _Out_ PNLSTABLEINFO NlsTable)
NTSYSAPI VOID NTAPI RtlResetRtlTranslations(_In_ PNLSTABLEINFO NlsTable)
NTSYSAPI NTSTATUS NTAPI RtlSetCurrentDirectory_U(_In_ PUNICODE_STRING name)
ULONG NTAPI LdrRelocateImageWithBias(_In_ PVOID BaseAddress, _In_ LONGLONG AdditionalBias, _In_opt_ PCSTR LoaderName, _In_ ULONG Success, _In_ ULONG Conflict, _In_ ULONG Invalid)
Definition: image.c:474
NTSYSAPI NTSTATUS NTAPI RtlInitializeCriticalSection(_In_ PRTL_CRITICAL_SECTION CriticalSection)
NTSYSAPI PRTL_USER_PROCESS_PARAMETERS NTAPI RtlNormalizeProcessParams(_In_ PRTL_USER_PROCESS_PARAMETERS ProcessParameters)
#define RTL_USER_PROCESS_PARAMETERS_LOCAL_DLL_PATH
Definition: rtltypes.h:53
#define RTL_USER_PROCESS_PARAMETERS_NORMALIZED
Definition: rtltypes.h:41
#define DIRECTORY_QUERY
Definition: nt_native.h:1257
#define DIRECTORY_TRAVERSE
Definition: nt_native.h:1258
NTSYSAPI VOID NTAPI RtlInitUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString)
#define HEAP_CLASS_1
Definition: nt_native.h:1714
NTSYSAPI PVOID NTAPI RtlCreateHeap(IN ULONG Flags, IN PVOID HeapBase OPTIONAL, IN ULONG ReserveSize OPTIONAL, IN ULONG CommitSize OPTIONAL, IN PVOID Lock OPTIONAL, IN PRTL_HEAP_PARAMETERS Parameters OPTIONAL)
#define HEAP_GROWABLE
Definition: nt_native.h:1696
NTSYSAPI VOID NTAPI RtlFreeUnicodeString(PUNICODE_STRING UnicodeString)
#define HEAP_CREATE_ALIGN_16
Definition: nt_native.h:1704
_In_ ULONG _In_ ULONG _In_ ULONG Length
Definition: ntddpcm.h:102
PVOID g_pfnSE_InstallAfterInit
Definition: ldrutils.c:26
VOID NTAPI LdrpLoadShimEngine(IN PWSTR ImageName, IN PUNICODE_STRING ProcessImage, IN PVOID pShimData)
Definition: ldrutils.c:2757
ULONG RtlpDphGlobalFlags
Definition: heappage.c:108
NTSTATUS NTAPI LdrpWalkImportDescriptor(IN LPWSTR DllPath OPTIONAL, IN PLDR_DATA_TABLE_ENTRY LdrEntry)
Definition: ldrpe.c:670
NTSTATUS NTAPI AVrfInitializeVerifier(VOID)
Definition: verifier.c:672
PVOID LdrpHeap
Definition: ldrinit.c:3
#define LDR_HASH_TABLE_ENTRIES
Definition: ntdllp.h:11
VOID NTAPI RtlpInitializeThreadPooling(VOID)
VOID NTAPI LdrpInsertMemoryTableEntry(IN PLDR_DATA_TABLE_ENTRY LdrEntry)
Definition: ldrutils.c:1561
NTSTATUS NTAPI LdrpSetProtection(PVOID ViewBase, BOOLEAN Restore)
Definition: ldrutils.c:921
PVOID NTAPI LdrpFetchAddressOfEntryPoint(PVOID ImageBase)
BOOLEAN RtlpPageHeapEnabled
Definition: heappage.c:107
PLDR_DATA_TABLE_ENTRY NTAPI LdrpAllocateDataTableEntry(IN PVOID BaseAddress)
Definition: ldrutils.c:1528
BOOLEAN g_ShimsEnabled
Definition: ldrutils.c:21
VOID NTAPI RtlpInitializeKeyedEvent(VOID)
Definition: condvar.c:460
#define IMAGE_SUBSYSTEM_WINDOWS_CUI
Definition: ntimage.h:438
#define IMAGE_SUBSYSTEM_WINDOWS_GUI
Definition: ntimage.h:437
#define IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR
Definition: ntimage.h:489
#define IMAGE_SUBSYSTEM_NATIVE
Definition: ntimage.h:436
UNICODE_STRING NtSystemRoot
Definition: init.c:76
NTSTATUS NTAPI NtSetInformationProcess(_In_ HANDLE ProcessHandle, _In_ PROCESSINFOCLASS ProcessInformationClass, _In_reads_bytes_(ProcessInformationLength) PVOID ProcessInformation, _In_ ULONG ProcessInformationLength)
Definition: query.c:1389
#define STATUS_INVALID_IMAGE_FORMAT
Definition: ntstatus.h:453
#define STATUS_CONFLICTING_ADDRESSES
Definition: ntstatus.h:354
long LONG
Definition: pedump.c:60
unsigned short USHORT
Definition: pedump.c:61
static VOID LoadConfig(HWND hwndDlg, PPOWER_SCHEMES_PAGE_DATA pPageData, PPOWER_SCHEME pScheme)
Definition: powershemes.c:238
PVOID NTAPI RtlDecodeSystemPointer(IN PVOID Pointer)
Definition: process.c:439
VOID NTAPI SE_InstallAfterInit(PUNICODE_STRING ProcessImage, PVOID pShimData)
Definition: shimeng.c:1469
#define TLS_MINIMUM_AVAILABLE
Definition: ntddk_ex.h:236
HANDLE UniqueProcess
Definition: compat.h:825
UNICODE_STRING DosPath
Definition: rtltypes.h:1362
IMAGE_OPTIONAL_HEADER32 OptionalHeader
Definition: ntddk_ex.h:184
Definition: btrfs_drv.h:1876
PACTIVATION_CONTEXT EntryPointActivationContext
Definition: ldrtypes.h:167
USHORT LoadCount
Definition: ntddk_ex.h:208
PVOID EntryPoint
Definition: ntddk_ex.h:203
UNICODE_STRING FullDllName
Definition: btrfs_drv.h:1882
LIST_ENTRY InInitializationOrderLinks
Definition: ldrtypes.h:144
PVOID DllBase
Definition: btrfs_drv.h:1880
ULONG Flags
Definition: ntddk_ex.h:207
UNICODE_STRING BaseDllName
Definition: ldrtypes.h:149
LIST_ENTRY InInitializationOrderModuleList
Definition: ldrtypes.h:126
LIST_ENTRY InMemoryOrderModuleList
Definition: btrfs_drv.h:1895
ULONG Length
Definition: ntddk_ex.h:221
LIST_ENTRY InLoadOrderModuleList
Definition: ldrtypes.h:124
BOOLEAN Initialized
Definition: ntddk_ex.h:222
UNICODE_STRING CSDVersion
Definition: winternl.h:545
ULONG NumberOfProcessors
Definition: ntddk_ex.h:269
ULONG TlsBitmapBits[2]
Definition: ntddk_ex.h:260
ULONG ImageProcessAffinityMask
Definition: ntddk_ex.h:307
PVOID ImageBaseAddress
Definition: ntddk_ex.h:245
ULONG FlsBitmapBits[4]
Definition: winternl.h:560
PPS_POST_PROCESS_INIT_ROUTINE PostProcessInitRoutine
Definition: btrfs_drv.h:1916
PVOID ProcessHeap
Definition: ntddk_ex.h:249
LARGE_INTEGER CriticalSectionTimeout
Definition: ntddk_ex.h:274
ULONG TlsExpansionBitmapBits[32]
Definition: winternl.h:539
PVOID AnsiCodePageData
Definition: ntddk_ex.h:264
BYTE BeingDebugged
Definition: btrfs_drv.h:1909
PVOID FastPebLock
Definition: ntddk_ex.h:250
PVOID TlsBitmap
Definition: ntddk_ex.h:259
PVOID OemCodePageData
Definition: ntddk_ex.h:265
LIST_ENTRY FlsListHead
Definition: winternl.h:552
PRTL_BITMAP FlsBitmap
Definition: winternl.h:555
PVOID AppCompatInfo
Definition: winternl.h:544
PRTL_BITMAP TlsExpansionBitmap
Definition: winternl.h:538
PVOID UnicodeCaseTableData
Definition: ntddk_ex.h:266
ULONG DeCommitFreeBlockThreshold
Definition: nt_native.h:1673
ULONG VirtualMemoryThreshold
Definition: nt_native.h:1676
ULONG DeCommitTotalFreeThreshold
Definition: nt_native.h:1674
UNICODE_STRING CommandLine
Definition: btrfs_drv.h:1902
PVOID ActivationContextStackPointer
Definition: compat.h:854
CLIENT_ID ClientId
Definition: compat.h:839
#define LL
Definition: tui.h:166
uint16_t * PWSTR
Definition: typedefs.h:56
#define NTAPI
Definition: typedefs.h:36
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:262
#define RtlMoveMemory(Destination, Source, Length)
Definition: typedefs.h:264
#define STATUS_INVALID_PARAMETER
Definition: udferr_usr.h:135
LONGLONG QuadPart
Definition: typedefs.h:114
#define FLS_MAXIMUM_AVAILABLE
Definition: winnt_old.h:1127
#define NX_SUPPORT_POLICY_ALWAYSOFF
#define NX_SUPPORT_POLICY_ALWAYSON
WCHAR * LPWSTR
Definition: xmlstorage.h:184

Referenced by LdrpInit().

◆ LdrpInitializeProcessCompat()

VOID NTAPI LdrpInitializeProcessCompat ( PVOID  pProcessActctx,
PVOID pOldShimData 
)

Definition at line 1593 of file ldrinit.c.

1594{
1595 static const struct
1596 {
1597 const GUID* Guid;
1598 const DWORD Version;
1599 } KnownCompatGuids[] = {
1600 { &COMPAT_GUID_WIN10, _WIN32_WINNT_WIN10 },
1601 { &COMPAT_GUID_WIN81, _WIN32_WINNT_WINBLUE },
1602 { &COMPAT_GUID_WIN8, _WIN32_WINNT_WIN8 },
1603 { &COMPAT_GUID_WIN7, _WIN32_WINNT_WIN7 },
1604 { &COMPAT_GUID_VISTA, _WIN32_WINNT_VISTA },
1605 };
1606
1607 ULONG Buffer[(sizeof(COMPATIBILITY_CONTEXT_ELEMENT) * 10 + sizeof(ACTIVATION_CONTEXT_COMPATIBILITY_INFORMATION)) / sizeof(ULONG)];
1608 ACTIVATION_CONTEXT_COMPATIBILITY_INFORMATION* ContextCompatInfo;
1609 SIZE_T SizeRequired;
1611 DWORD n, cur;
1612 ReactOS_ShimData* pShimData = *pOldShimData;
1613
1614 if (pShimData)
1615 {
1616 if (pShimData->dwMagic != REACTOS_SHIMDATA_MAGIC ||
1617 pShimData->dwSize != sizeof(ReactOS_ShimData))
1618 {
1619 DPRINT1("LdrpInitializeProcessCompat: Corrupt pShimData (0x%x, %u)\n", pShimData->dwMagic, pShimData->dwSize);
1620 return;
1621 }
1622#ifdef _M_AMD64
1623 pShimData->RtlGetCurrentDirectory_U_RtlpMsysDecoy = &RtlGetCurrentDirectory_U_RtlpMsysDecoy; /* We need this private symbol for a MSYS shim */
1624#endif
1625 if (pShimData->dwRosProcessCompatVersion)
1626 {
1628 {
1629 DPRINT1("LdrpInitializeProcessCompat: ProcessCompatVersion set to ignore manifest\n");
1630 }
1631 else
1632 {
1633 DPRINT1("LdrpInitializeProcessCompat: ProcessCompatVersion already set to 0x%x\n", pShimData->dwRosProcessCompatVersion);
1634 }
1635 return;
1636 }
1637 }
1638
1639 SizeRequired = sizeof(Buffer);
1641 pProcessActctx,
1642 NULL,
1643 CompatibilityInformationInActivationContext,
1644 Buffer,
1645 sizeof(Buffer),
1646 &SizeRequired);
1647
1648 if (!NT_SUCCESS(Status))
1649 {
1650 DPRINT1("LdrpInitializeProcessCompat: Unable to query process actctx with status %x\n", Status);
1651 return;
1652 }
1653
1654 ContextCompatInfo = (ACTIVATION_CONTEXT_COMPATIBILITY_INFORMATION*)Buffer;
1655 /* No Compatibility elements present, bail out */
1656 if (ContextCompatInfo->ElementCount == 0)
1657 return;
1658
1659 /* Search for known GUIDs, starting from oldest to newest.
1660 Note that on Windows it is somewhat reversed, starting from the latest known
1661 version, going down. But we are not Windows, trying to allow a lower version,
1662 we are ReactOS trying to fake a higher version. So we interpret what Windows
1663 does as "try the closest version to the actual version", so we start with the
1664 lowest version, which is closest to Windows 2003, which we mostly are. */
1665 for (cur = RTL_NUMBER_OF(KnownCompatGuids) - 1; cur != -1; --cur)
1666 {
1667 for (n = 0; n < ContextCompatInfo->ElementCount; ++n)
1668 {
1669 if (ContextCompatInfo->Elements[n].Type == ACTCTX_COMPATIBILITY_ELEMENT_TYPE_OS &&
1670 RtlCompareMemory(&ContextCompatInfo->Elements[n].Id, KnownCompatGuids[cur].Guid, sizeof(GUID)) == sizeof(GUID))
1671 {
1673 {
1674 DPRINT1("LdrpInitializeProcessCompat: Not applying automatic fix for winver 0x%x due to policy\n", KnownCompatGuids[cur].Version);
1675 return;
1676 }
1677
1678 /* If this process did not need shim data before, allocate and store it */
1679 if (pShimData == NULL)
1680 {
1681 PPEB Peb = NtCurrentPeb();
1682
1683 ASSERT(Peb->pShimData == NULL);
1684 pShimData = RtlAllocateHeap(Peb->ProcessHeap, HEAP_ZERO_MEMORY, sizeof(*pShimData));
1685
1686 if (!pShimData)
1687 {
1688 DPRINT1("LdrpInitializeProcessCompat: Unable to allocated %u bytes\n", sizeof(*pShimData));
1689 return;
1690 }
1691
1692 pShimData->dwSize = sizeof(*pShimData);
1693 pShimData->dwMagic = REACTOS_SHIMDATA_MAGIC;
1694#ifdef _M_AMD64
1695 /* The process did not ask for shims, but we want to make sure that if the Peb->pShimData is available, the data in it is complete */
1696 pShimData->RtlGetCurrentDirectory_U_RtlpMsysDecoy = &RtlGetCurrentDirectory_U_RtlpMsysDecoy;
1697#endif
1698
1699 Peb->pShimData = pShimData;
1700 *pOldShimData = pShimData;
1701 }
1702
1703 /* Store the lowest found version, and bail out. */
1704 pShimData->dwRosProcessCompatVersion = KnownCompatGuids[cur].Version;
1705 DPRINT1("LdrpInitializeProcessCompat: Found guid for winver 0x%x in manifest from %wZ\n",
1706 KnownCompatGuids[cur].Version,
1707 &(NtCurrentPeb()->ProcessParameters->ImagePathName));
1708 return;
1709 }
1710 }
1711 }
1712}
#define RTL_NUMBER_OF(x)
Definition: RtlRegistry.c:12
Definition: bufpool.h:45
#define REACTOS_SHIMDATA_MAGIC
Definition: compat_undoc.h:19
#define HEAP_ZERO_MEMORY
Definition: compat.h:134
#define RtlCompareMemory(s1, s2, l)
Definition: env_spec_w32.h:465
unsigned long DWORD
Definition: ntddk_ex.h:95
FxCollectionEntry * cur
GLdouble n
Definition: glext.h:7729
#define REACTOS_COMPATVERSION_IGNOREMANIFEST
Definition: hsdb.c:36
NTSYSAPI NTSTATUS WINAPI RtlQueryInformationActivationContext(ULONG, HANDLE, PVOID, ULONG, PVOID, SIZE_T, SIZE_T *)
Definition: actctx.c:5572
BOOLEAN NTAPI LdrpDisableProcessCompatGuidDetection(VOID)
Definition: ldrinit.c:1559
static PVOID RtlGetCurrentDirectory_U_RtlpMsysDecoy
Definition: msys2.c:16
#define RTL_QUERY_ACTIVATION_CONTEXT_FLAG_NO_ADDREF
Definition: rtltypes.h:119
#define _WIN32_WINNT_WIN10
Definition: sdkddkver.h:32
#define _WIN32_WINNT_WINBLUE
Definition: sdkddkver.h:30
#define _WIN32_WINNT_WIN8
Definition: sdkddkver.h:29
#define _WIN32_WINNT_WIN7
Definition: sdkddkver.h:28
#define _WIN32_WINNT_VISTA
Definition: sdkddkver.h:25
DWORD dwRosProcessCompatVersion
Definition: compat_undoc.h:11
_Must_inspect_result_ _In_ WDFDEVICE _In_ LPCGUID _Out_ PINTERFACE _In_ USHORT _In_ USHORT Version
Definition: wdffdo.h:469
_Must_inspect_result_ _In_ WDFOBJECT _In_ CONST GUID * Guid
Definition: wdfobject.h:762

◆ LdrpInitializeThread()

VOID NTAPI LdrpInitializeThread ( IN PCONTEXT  Context)

Definition at line 509 of file ldrinit.c.

510{
512 PLDR_DATA_TABLE_ENTRY LdrEntry;
513 PLIST_ENTRY NextEntry, ListHead;
514 RTL_CALLER_ALLOCATED_ACTIVATION_CONTEXT_STACK_FRAME_EXTENDED ActCtx;
516 PVOID EntryPoint;
517
518 DPRINT("LdrpInitializeThread() called for %wZ (%p/%p)\n",
520 NtCurrentTeb()->RealClientId.UniqueProcess,
521 NtCurrentTeb()->RealClientId.UniqueThread);
522
523 /* Acquire the loader Lock */
525
526 /* Allocate an Activation Context Stack */
527 DPRINT("ActivationContextStack %p\n", NtCurrentTeb()->ActivationContextStackPointer);
528 Status = RtlAllocateActivationContextStack(&NtCurrentTeb()->ActivationContextStackPointer);
529 if (!NT_SUCCESS(Status))
530 {
531 DPRINT1("Warning: Unable to allocate ActivationContextStack\n");
532 }
533
534 /* Make sure we are not shutting down */
536
537 /* Allocate TLS */
539
540 /* Start at the beginning */
541 ListHead = &Peb->Ldr->InMemoryOrderModuleList;
542 NextEntry = ListHead->Flink;
543 while (NextEntry != ListHead)
544 {
545 /* Get the current entry */
546 LdrEntry = CONTAINING_RECORD(NextEntry, LDR_DATA_TABLE_ENTRY, InMemoryOrderLinks);
547
548 /* Make sure it's not ourselves */
549 if (Peb->ImageBaseAddress != LdrEntry->DllBase)
550 {
551 /* Check if we should call */
552 if (!(LdrEntry->Flags & LDRP_DONT_CALL_FOR_THREADS))
553 {
554 /* Get the entrypoint */
555 EntryPoint = LdrEntry->EntryPoint;
556
557 /* Check if we are ready to call it */
558 if ((EntryPoint) &&
559 (LdrEntry->Flags & LDRP_PROCESS_ATTACH_CALLED) &&
560 (LdrEntry->Flags & LDRP_IMAGE_DLL))
561 {
562 /* Set up the Act Ctx */
563 ActCtx.Size = sizeof(ActCtx);
564 ActCtx.Format = 1;
566
567 /* Activate the ActCtx */
568 RtlActivateActivationContextUnsafeFast(&ActCtx,
570
572 {
573 /* Check if it has TLS */
574 if (LdrEntry->TlsIndex)
575 {
576 /* Make sure we're not shutting down */
578 {
579 /* Call TLS */
581 }
582 }
583
584 /* Make sure we're not shutting down */
586 {
587 /* Call the Entrypoint */
588 DPRINT("%wZ - Calling entry point at %p for thread attaching, %p/%p\n",
589 &LdrEntry->BaseDllName, LdrEntry->EntryPoint,
590 NtCurrentTeb()->RealClientId.UniqueProcess,
591 NtCurrentTeb()->RealClientId.UniqueThread);
593 LdrEntry->DllBase,
595 NULL);
596 }
597 }
599 {
600 DPRINT1("WARNING: Exception 0x%x during LdrpCallInitRoutine(DLL_THREAD_ATTACH) for %wZ\n",
601 _SEH2_GetExceptionCode(), &LdrEntry->BaseDllName);
602 }
603 _SEH2_END;
604
605 /* Deactivate the ActCtx */
606 RtlDeactivateActivationContextUnsafeFast(&ActCtx);
607 }
608 }
609 }
610
611 /* Next entry */
612 NextEntry = NextEntry->Flink;
613 }
614
615 /* Check for TLS */
617 {
618 /* Set up the Act Ctx */
619 ActCtx.Size = sizeof(ActCtx);
620 ActCtx.Format = 1;
622
623 /* Activate the ActCtx */
624 RtlActivateActivationContextUnsafeFast(&ActCtx,
626
628 {
629 /* Do TLS callbacks */
631 }
633 {
634 /* Do nothing */
635 }
636 _SEH2_END;
637
638 /* Deactivate the ActCtx */
639 RtlDeactivateActivationContextUnsafeFast(&ActCtx);
640 }
641
642Exit:
643
644 /* Release the loader lock */
646
647 DPRINT("LdrpInitializeThread() done\n");
648}
#define DLL_THREAD_ATTACH
Definition: compat.h:132
BOOLEAN LdrpShutdownInProgress
Definition: ldrinit.c:34
BOOLEAN LdrpImageHasTls
Definition: ldrinit.c:52
NTSTATUS NTAPI LdrpAllocateTls(VOID)
Definition: ldrinit.c:1332
_In_ PCWSTR _Out_ PVOID * ActCtx
Definition: ldrtypes.h:264
#define LDRP_DONT_CALL_FOR_THREADS
Definition: ldrtypes.h:52
#define LDRP_PROCESS_ATTACH_CALLED
Definition: ldrtypes.h:53
NTSYSAPI NTSTATUS NTAPI RtlEnterCriticalSection(_In_ PRTL_CRITICAL_SECTION CriticalSection)
NTSYSAPI NTSTATUS NTAPI RtlLeaveCriticalSection(_In_ PRTL_CRITICAL_SECTION CriticalSection)
VOID NTAPI LdrpCallTlsInitializers(IN PLDR_DATA_TABLE_ENTRY LdrEntry, IN ULONG Reason)
Definition: ldrutils.c:447
BOOLEAN NTAPI LdrpCallInitRoutine(IN PDLL_INIT_ROUTINE EntryPoint, IN PVOID BaseAddress, IN ULONG Reason, IN PVOID Context)
Definition: ldrutils.c:100
static void Exit(void)
Definition: sock.c:1330
USHORT TlsIndex
Definition: ntddk_ex.h:209

Referenced by LdrpInit().

◆ LdrpInitializeTls()

NTSTATUS NTAPI LdrpInitializeTls ( VOID  )

Definition at line 1269 of file ldrinit.c.

1270{
1271 PLIST_ENTRY NextEntry, ListHead;
1272 PLDR_DATA_TABLE_ENTRY LdrEntry;
1273 PIMAGE_TLS_DIRECTORY TlsDirectory;
1274 PLDRP_TLS_DATA TlsData;
1275 ULONG Size;
1276
1277 /* Initialize the TLS List */
1279
1280 /* Loop all the modules */
1281 ListHead = &NtCurrentPeb()->Ldr->InLoadOrderModuleList;
1282 NextEntry = ListHead->Flink;
1283 while (ListHead != NextEntry)
1284 {
1285 /* Get the entry */
1286 LdrEntry = CONTAINING_RECORD(NextEntry, LDR_DATA_TABLE_ENTRY, InLoadOrderLinks);
1287 NextEntry = NextEntry->Flink;
1288
1289 /* Get the TLS directory */
1290 TlsDirectory = RtlImageDirectoryEntryToData(LdrEntry->DllBase,
1291 TRUE,
1293 &Size);
1294
1295 /* Check if we have a directory */
1296 if (!TlsDirectory) continue;
1297
1298 /* Check if the image has TLS */
1300
1301 /* Show debug message */
1302 if (ShowSnaps)
1303 {
1304 DPRINT1("LDR: Tls Found in %wZ at %p\n",
1305 &LdrEntry->BaseDllName,
1306 TlsDirectory);
1307 }
1308
1309 /* Allocate an entry */
1310 TlsData = RtlAllocateHeap(RtlGetProcessHeap(), 0, sizeof(LDRP_TLS_DATA));
1311 if (!TlsData) return STATUS_NO_MEMORY;
1312
1313 /* Lock the DLL and mark it for TLS Usage */
1314 LdrEntry->LoadCount = -1;
1315 LdrEntry->TlsIndex = -1;
1316
1317 /* Save the cached TLS data */
1318 TlsData->TlsDirectory = *TlsDirectory;
1319 InsertTailList(&LdrpTlsList, &TlsData->TlsLinks);
1320
1321 /* Update the index */
1324 }
1325
1326 /* Done setting up TLS, allocate entries */
1327 return LdrpAllocateTls();
1328}
#define InsertTailList(ListHead, Entry)
#define IMAGE_DIRECTORY_ENTRY_TLS
Definition: pedump.c:268
LIST_ENTRY TlsLinks
Definition: ntdllp.h:28
int32_t * PLONG
Definition: typedefs.h:58
_Must_inspect_result_ _In_ WDFDEVICE _In_ PWDF_DEVICE_PROPERTY_DATA _In_ DEVPROPTYPE _In_ ULONG Size
Definition: wdfdevice.h:4539

Referenced by LdrpInitializeProcess().

◆ LdrpInitSecurityCookie()

PVOID NTAPI LdrpInitSecurityCookie ( PLDR_DATA_TABLE_ENTRY  LdrEntry)

Definition at line 456 of file ldrinit.c.

457{
460 ULONG_PTR NewCookie;
461
462 /* Fetch address of the cookie */
464
465 if (Cookie)
466 {
467 /* Check if it's a default one */
469 (*Cookie == 0xBB40))
470 {
471 /* Make up a cookie from a bunch of values which may uniquely represent
472 current moment of time, environment, etc */
474
475 NewCookie = Counter.LowPart ^ Counter.HighPart;
476 NewCookie ^= (ULONG_PTR)NtCurrentTeb()->ClientId.UniqueProcess;
477 NewCookie ^= (ULONG_PTR)NtCurrentTeb()->ClientId.UniqueThread;
478
479 /* Loop like it's done in KeQueryTickCount(). We don't want to call it directly. */
480 while (SharedUserData->SystemTime.High1Time != SharedUserData->SystemTime.High2Time)
481 {
483 };
484
485 /* Calculate the milliseconds value and xor it to the cookie */
486 NewCookie ^= Int64ShrlMod32(UInt32x32To64(SharedUserData->TickCountMultiplier, SharedUserData->TickCount.LowPart), 24) +
487 (SharedUserData->TickCountMultiplier * (SharedUserData->TickCount.High1Time << 8));
488
489 /* Make the cookie 16bit if necessary */
490 if (*Cookie == 0xBB40) NewCookie &= 0xFFFF;
491
492 /* If the result is 0 or the same as we got, just subtract one from the existing value
493 and that's it */
494 if ((NewCookie == 0) || (NewCookie == *Cookie))
495 {
496 NewCookie = *Cookie - 1;
497 }
498
499 /* Set the new cookie value */
500 *Cookie = NewCookie;
501 }
502 }
503
504 return Cookie;
505}
#define UInt32x32To64(a, b)
Definition: intsafe.h:252
#define DEFAULT_SECURITY_COOKIE
Definition: ldrinit.c:105
PVOID NTAPI LdrpFetchAddressOfSecurityCookie(PVOID BaseAddress, ULONG SizeOfImage)
Definition: ldrinit.c:419
#define Int64ShrlMod32(a, b)
NTSTATUS NTAPI NtQueryPerformanceCounter(OUT PLARGE_INTEGER PerformanceCounter, OUT PLARGE_INTEGER PerformanceFrequency OPTIONAL)
Definition: profile.c:278
#define YieldProcessor
Definition: ke.h:48
ULONG SizeOfImage
Definition: ldrtypes.h:147
static LARGE_INTEGER Counter
Definition: clock.c:43
ULONG LowPart
Definition: typedefs.h:106

Referenced by LdrpRunInitializeRoutines().

◆ LdrpRunInitializeRoutines()

NTSTATUS NTAPI LdrpRunInitializeRoutines ( IN PCONTEXT Context  OPTIONAL)

Definition at line 652 of file ldrinit.c.

653{
654 PLDR_DATA_TABLE_ENTRY LocalArray[16];
655 PLIST_ENTRY ListHead;
656 PLIST_ENTRY NextEntry;
657 PLDR_DATA_TABLE_ENTRY LdrEntry, *LdrRootEntry, OldInitializer;
658 PVOID EntryPoint;
659 ULONG Count, i;
660 //ULONG BreakOnInit;
663 RTL_CALLER_ALLOCATED_ACTIVATION_CONTEXT_STACK_FRAME_EXTENDED ActCtx;
664 ULONG BreakOnDllLoad;
665 PTEB OldTldTeb;
666 BOOLEAN DllStatus;
667
668 DPRINT("LdrpRunInitializeRoutines() called for %wZ (%p/%p)\n",
670 NtCurrentTeb()->RealClientId.UniqueProcess,
671 NtCurrentTeb()->RealClientId.UniqueThread);
672
673 /* Check the Loader Lock */
675
676 /* Get the number of entries to call */
678 {
679 /* Check if we can use our local buffer */
680 if (Count > 16)
681 {
682 /* Allocate space for all the entries */
683 LdrRootEntry = RtlAllocateHeap(LdrpHeap,
684 0,
685 Count * sizeof(*LdrRootEntry));
686 if (!LdrRootEntry) return STATUS_NO_MEMORY;
687 }
688 else
689 {
690 /* Use our local array */
691 LdrRootEntry = LocalArray;
692 }
693 }
694 else
695 {
696 /* Don't need one */
697 LdrRootEntry = NULL;
698 }
699
700 /* Show debug message */
701 if (ShowSnaps)
702 {
703 DPRINT1("[%p,%p] LDR: Real INIT LIST for Process %wZ\n",
704 NtCurrentTeb()->RealClientId.UniqueThread,
705 NtCurrentTeb()->RealClientId.UniqueProcess,
707 }
708
709 /* Loop in order */
711 NextEntry = ListHead->Flink;
712 i = 0;
713 while (NextEntry != ListHead)
714 {
715 /* Get the Data Entry */
716 LdrEntry = CONTAINING_RECORD(NextEntry, LDR_DATA_TABLE_ENTRY, InInitializationOrderLinks);
717
718 /* Check if we have a Root Entry */
719 if (LdrRootEntry)
720 {
721 /* Check flags */
722 if (!(LdrEntry->Flags & LDRP_ENTRY_PROCESSED))
723 {
724 /* Setup the Cookie for the DLL */
725 LdrpInitSecurityCookie(LdrEntry);
726
727 /* Check for valid entrypoint */
728 if (LdrEntry->EntryPoint)
729 {
730 /* Write in array */
731 ASSERT(i < Count);
732 LdrRootEntry[i] = LdrEntry;
733
734 /* Display debug message */
735 if (ShowSnaps)
736 {
737 DPRINT1("[%p,%p] LDR: %wZ init routine %p\n",
738 NtCurrentTeb()->RealClientId.UniqueThread,
739 NtCurrentTeb()->RealClientId.UniqueProcess,
740 &LdrEntry->FullDllName,
741 LdrEntry->EntryPoint);
742 }
743 i++;
744 }
745 }
746 }
747
748 /* Set the flag */
749 LdrEntry->Flags |= LDRP_ENTRY_PROCESSED;
750 NextEntry = NextEntry->Flink;
751 }
752
754
755 /* If we got a context, then we have to call Kernel32 for TS support */
756 if (Context)
757 {
758 /* Check if we have one */
759 if (Kernel32ProcessInitPostImportFunction)
760 {
761 /* Call it */
762 Status = Kernel32ProcessInitPostImportFunction();
763 if (!NT_SUCCESS(Status))
764 {
765 DPRINT1("LDR: LdrpRunInitializeRoutines - Failed running kernel32 post-import function, Status=0x%08lx\n", Status);
766 }
767 }
768 /* Clear it */
769 Kernel32ProcessInitPostImportFunction = NULL;
770 }
771
772 /* No root entry? return */
773 if (!LdrRootEntry)
774 return Status;
775
776 /* Set the TLD TEB */
779
780 /* Loop */
781 i = 0;
782 while (i < Count)
783 {
784 /* Get an entry */
785 LdrEntry = LdrRootEntry[i];
786
787 /* FIXME: Verify NX Compat */
788
789 /* Move to next entry */
790 i++;
791
792 /* Get its entrypoint */
793 EntryPoint = LdrEntry->EntryPoint;
794
795 /* Are we being debugged? */
796 BreakOnDllLoad = 0;
798 {
799 /* Check if we should break on load */
801 L"BreakOnDllLoad",
802 REG_DWORD,
803 &BreakOnDllLoad,
804 sizeof(ULONG),
805 NULL);
806 if (!NT_SUCCESS(Status)) BreakOnDllLoad = 0;
807
808 /* Reset status back to STATUS_SUCCESS */
810 }
811
812 /* Break if aksed */
813 if (BreakOnDllLoad)
814 {
815 /* Check if we should show a message */
816 if (ShowSnaps)
817 {
818 DPRINT1("LDR: %wZ loaded.", &LdrEntry->BaseDllName);
819 DPRINT1(" - About to call init routine at %p\n", EntryPoint);
820 }
821
822 /* Break in debugger */
824 }
825
826 /* Make sure we have an entrypoint */
827 if (EntryPoint)
828 {
829 /* Save the old Dll Initializer and write the current one */
830 OldInitializer = LdrpCurrentDllInitializer;
831 LdrpCurrentDllInitializer = LdrEntry;
832
833 /* Set up the Act Ctx */
834 ActCtx.Size = sizeof(ActCtx);
835 ActCtx.Format = 1;
837
838 /* Activate the ActCtx */
839 RtlActivateActivationContextUnsafeFast(&ActCtx,
841
843 {
844 /* Check if it has TLS */
845 if (LdrEntry->TlsIndex && Context)
846 {
847 /* Call TLS */
849 }
850
851 /* Call the Entrypoint */
852 if (ShowSnaps)
853 {
854 DPRINT1("%wZ - Calling entry point at %p for DLL_PROCESS_ATTACH\n",
855 &LdrEntry->BaseDllName, EntryPoint);
856 }
857 DllStatus = LdrpCallInitRoutine(EntryPoint,
858 LdrEntry->DllBase,
860 Context);
861 }
863 {
864 DllStatus = FALSE;
865 DPRINT1("WARNING: Exception 0x%x during LdrpCallInitRoutine(DLL_PROCESS_ATTACH) for %wZ\n",
866 _SEH2_GetExceptionCode(), &LdrEntry->BaseDllName);
867 }
868 _SEH2_END;
869
870 /* Deactivate the ActCtx */
871 RtlDeactivateActivationContextUnsafeFast(&ActCtx);
872
873 /* Save the Current DLL Initializer */
874 LdrpCurrentDllInitializer = OldInitializer;
875
876 /* Mark the entry as processed */
878
879 /* Fail if DLL init failed */
880 if (!DllStatus)
881 {
882 DPRINT1("LDR: DLL_PROCESS_ATTACH for dll \"%wZ\" (InitRoutine: %p) failed\n",
883 &LdrEntry->BaseDllName, EntryPoint);
884
886 goto Quickie;
887 }
888 }
889 }
890
891 /* Loop in order */
893 NextEntry = NextEntry->Flink;
894 while (NextEntry != ListHead)
895 {
896 /* Get the Data Entry */
897 LdrEntry = CONTAINING_RECORD(NextEntry, LDR_DATA_TABLE_ENTRY, InInitializationOrderLinks);
898
899 /* FIXME: Verify NX Compat */
900 // LdrpCheckNXCompatibility()
901
902 /* Next entry */
903 NextEntry = NextEntry->Flink;
904 }
905
906 /* Check for TLS */
908 {
909 /* Set up the Act Ctx */
910 ActCtx.Size = sizeof(ActCtx);
911 ActCtx.Format = 1;
913
914 /* Activate the ActCtx */
915 RtlActivateActivationContextUnsafeFast(&ActCtx,
917
919 {
920 /* Do TLS callbacks */
922 }
924 {
925 /* Do nothing */
926 }
927 _SEH2_END;
928
929 /* Deactivate the ActCtx */
930 RtlDeactivateActivationContextUnsafeFast(&ActCtx);
931 }
932
933Quickie:
934 /* Restore old TEB */
936
937 /* Check if the array is in the heap */
938 if (LdrRootEntry != LocalArray)
939 {
940 /* Free the array */
941 RtlFreeHeap(LdrpHeap, 0, LdrRootEntry);
942 }
943
944 /* Return to caller */
945 DPRINT("LdrpRunInitializeRoutines() done\n");
946 return Status;
947}
#define DLL_PROCESS_ATTACH
Definition: compat.h:131
PLDR_DATA_TABLE_ENTRY LdrpCurrentDllInitializer
Definition: ldrinit.c:43
NTSTATUS NTAPI LdrQueryImageFileExecutionOptions(_In_ PUNICODE_STRING SubKey, _In_ PCWSTR ValueName, _In_ ULONG Type, _Out_ PVOID Buffer, _In_ ULONG BufferSize, _Out_opt_ PULONG ReturnedLength)
Definition: ldrinit.c:392
PVOID NTAPI LdrpInitSecurityCookie(PLDR_DATA_TABLE_ENTRY LdrEntry)
Definition: ldrinit.c:456
PTEB LdrpTopLevelDllBeingLoadedTeb
Definition: libsupp.c:20
VOID NTAPI LdrpEnsureLoaderLockIsHeld(VOID)
Definition: ldrinit.c:412
int Count
Definition: noreturn.cpp:7
ULONG NTAPI LdrpClearLoadInProgress(VOID)
Definition: ldrutils.c:2649
#define STATUS_DLL_INIT_FAILED
Definition: ntstatus.h:652
BOOLEAN ReadImageFileExecOptions
Definition: ntddk_ex.h:240

Referenced by LdrpGetProcedureAddress(), LdrpInitializeProcess(), and LdrpLoadDll().

◆ LdrpValidateImageForMp()

VOID NTAPI LdrpValidateImageForMp ( IN PLDR_DATA_TABLE_ENTRY  LdrDataTableEntry)

Definition at line 1550 of file ldrinit.c.

1551{
1552 DPRINT("LdrpValidateImageForMp is unimplemented\n");
1553 // TODO:
1554 // Scan the LockPrefixTable in the load config directory
1555}

Referenced by LdrpInitializeProcess(), and LdrpMapDll().

◆ LdrQueryImageFileExecutionOptions()

NTSTATUS NTAPI LdrQueryImageFileExecutionOptions ( _In_ PUNICODE_STRING  SubKey,
_In_ PCWSTR  ValueName,
_In_ ULONG  Type,
_Out_ PVOID  Buffer,
_In_ ULONG  BufferSize,
_Out_opt_ PULONG  ReturnedLength 
)

Definition at line 392 of file ldrinit.c.

399{
400 /* Call the newer function */
402 ValueName,
403 Type,
404 Buffer,
407 FALSE);
408}
Type
Definition: Type.h:7
_In_ ULONG _In_ BATTERY_QUERY_INFORMATION_LEVEL _In_ LONG _In_ ULONG _Out_ PULONG ReturnedLength
Definition: batclass.h:188
NTSTATUS NTAPI LdrQueryImageFileExecutionOptionsEx(_In_ PUNICODE_STRING SubKey, _In_ PCWSTR ValueName, _In_ ULONG Type, _Out_ PVOID Buffer, _In_ ULONG BufferSize, _Out_opt_ PULONG ReturnedLength, _In_ BOOLEAN Wow64)
Definition: ldrinit.c:353
_In_ WDFMEMORY _Out_opt_ size_t * BufferSize
Definition: wdfmemory.h:254
_Must_inspect_result_ _In_ WDFKEY _In_ PCUNICODE_STRING ValueName
Definition: wdfregistry.h:243

Referenced by LdrpRunInitializeRoutines(), and SmpLoadSubSystemsForMuSession().

◆ LdrQueryImageFileExecutionOptionsEx()

NTSTATUS NTAPI LdrQueryImageFileExecutionOptionsEx ( _In_ PUNICODE_STRING  SubKey,
_In_ PCWSTR  ValueName,
_In_ ULONG  Type,
_Out_ PVOID  Buffer,
_In_ ULONG  BufferSize,
_Out_opt_ PULONG  ReturnedLength,
_In_ BOOLEAN  Wow64 
)

Definition at line 353 of file ldrinit.c.

361{
364
365 /* Open a handle to the key */
367
368 /* Check for success */
369 if (NT_SUCCESS(Status))
370 {
371 /* Query the data */
373 ValueName,
374 Type,
375 Buffer,
378
379 /* Close the key */
381 }
382
383 /* Return to caller */
384 return Status;
385}

Referenced by LdrQueryImageFileExecutionOptions().

◆ LdrQueryImageFileKeyOption()

NTSTATUS NTAPI LdrQueryImageFileKeyOption ( _In_ HANDLE  KeyHandle,
_In_ PCWSTR  ValueName,
_In_ ULONG  Type,
_Out_ PVOID  Buffer,
_In_ ULONG  BufferSize,
_Out_opt_ PULONG  ReturnedLength 
)

Definition at line 188 of file ldrinit.c.

195{
196 ULONG KeyInfo[256];
197 UNICODE_STRING ValueNameString, IntegerString;
198 ULONG KeyInfoSize, ResultSize;
200 BOOLEAN FreeHeap = FALSE;
202
203 /* Build a string for the value name */
204 Status = RtlInitUnicodeStringEx(&ValueNameString, ValueName);
205 if (!NT_SUCCESS(Status)) return Status;
206
207 /* Query the value */
208 Status = ZwQueryValueKey(KeyHandle,
209 &ValueNameString,
211 KeyValueInformation,
212 sizeof(KeyInfo),
213 &ResultSize);
215 {
216 /* Our local buffer wasn't enough, allocate one */
217 KeyInfoSize = sizeof(KEY_VALUE_PARTIAL_INFORMATION) +
218 KeyValueInformation->DataLength;
219 KeyValueInformation = RtlAllocateHeap(RtlGetProcessHeap(),
220 0,
221 KeyInfoSize);
222 if (KeyValueInformation != NULL)
223 {
224 /* Try again */
225 Status = ZwQueryValueKey(KeyHandle,
226 &ValueNameString,
228 KeyValueInformation,
229 KeyInfoSize,
230 &ResultSize);
231 FreeHeap = TRUE;
232 }
233 else
234 {
235 /* Give up this time */
237 }
238 }
239
240 /* Check for success */
241 if (NT_SUCCESS(Status))
242 {
243 /* Handle binary data */
244 if (KeyValueInformation->Type == REG_BINARY)
245 {
246 /* Check validity */
247 if ((Buffer) && (KeyValueInformation->DataLength <= BufferSize))
248 {
249 /* Copy into buffer */
251 &KeyValueInformation->Data,
252 KeyValueInformation->DataLength);
253 }
254 else
255 {
257 }
258
259 /* Copy the result length */
260 if (ReturnedLength) *ReturnedLength = KeyValueInformation->DataLength;
261 }
262 else if (KeyValueInformation->Type == REG_DWORD)
263 {
264 /* Check for valid type */
265 if (KeyValueInformation->Type != Type)
266 {
267 /* Error */
269 }
270 else
271 {
272 /* Check validity */
273 if ((Buffer) &&
274 (BufferSize == sizeof(ULONG)) &&
275 (KeyValueInformation->DataLength <= BufferSize))
276 {
277 /* Copy into buffer */
279 &KeyValueInformation->Data,
280 KeyValueInformation->DataLength);
281 }
282 else
283 {
285 }
286
287 /* Copy the result length */
288 if (ReturnedLength) *ReturnedLength = KeyValueInformation->DataLength;
289 }
290 }
291 else if (KeyValueInformation->Type != REG_SZ)
292 {
293 /* We got something weird */
295 }
296 else
297 {
298 /* String, check what you requested */
299 if (Type == REG_DWORD)
300 {
301 /* Validate */
302 if (BufferSize != sizeof(ULONG))
303 {
304 /* Invalid size */
305 BufferSize = 0;
307 }
308 else
309 {
310 /* OK, we know what you want... */
311 IntegerString.Buffer = (PWSTR)KeyValueInformation->Data;
312 IntegerString.Length = (USHORT)KeyValueInformation->DataLength -
313 sizeof(WCHAR);
314 IntegerString.MaximumLength = (USHORT)KeyValueInformation->DataLength;
315 Status = RtlUnicodeStringToInteger(&IntegerString, 0, (PULONG)Buffer);
316 }
317 }
318 else
319 {
320 /* Validate */
321 if (KeyValueInformation->DataLength > BufferSize)
322 {
323 /* Invalid */
325 }
326 else
327 {
328 /* Set the size */
329 BufferSize = KeyValueInformation->DataLength;
330 }
331
332 /* Copy the string */
333 RtlMoveMemory(Buffer, &KeyValueInformation->Data, BufferSize);
334 }
335
336 /* Copy the result length */
337 if (ReturnedLength) *ReturnedLength = KeyValueInformation->DataLength;
338 }
339 }
340
341 /* Check if buffer was in heap */
342 if (FreeHeap) RtlFreeHeap(RtlGetProcessHeap(), 0, KeyValueInformation);
343
344 /* Return status */
345 return Status;
346}
#define STATUS_OBJECT_TYPE_MISMATCH
Definition: d3dkmdt.h:46
NTSYSAPI NTSTATUS WINAPI RtlInitUnicodeStringEx(PUNICODE_STRING, PCWSTR)
#define REG_SZ
Definition: layer.c:22
#define REG_BINARY
Definition: nt_native.h:1499
NTSYSAPI NTSTATUS NTAPI RtlUnicodeStringToInteger(PUNICODE_STRING String, ULONG Base, PULONG Value)
struct _KEY_VALUE_PARTIAL_INFORMATION KEY_VALUE_PARTIAL_INFORMATION
struct _KEY_VALUE_PARTIAL_INFORMATION * PKEY_VALUE_PARTIAL_INFORMATION
#define STATUS_BUFFER_OVERFLOW
Definition: shellext.h:66
uint32_t * PULONG
Definition: typedefs.h:59
#define STATUS_INFO_LENGTH_MISMATCH
Definition: udferr_usr.h:133

Referenced by AVrfReadIFEO(), CreateProcessInternalW(), LdrpInitializeExecutionOptions(), LdrpInitializeProcess(), and LdrQueryImageFileExecutionOptionsEx().

◆ LdrShutdownProcess()

NTSTATUS NTAPI LdrShutdownProcess ( VOID  )

Definition at line 954 of file ldrinit.c.

955{
957 PLDR_DATA_TABLE_ENTRY LdrEntry;
958 PLIST_ENTRY NextEntry, ListHead;
959 RTL_CALLER_ALLOCATED_ACTIVATION_CONTEXT_STACK_FRAME_EXTENDED ActCtx;
960 PVOID EntryPoint;
961
962 DPRINT("LdrShutdownProcess() called for %wZ\n", &LdrpImageEntry->BaseDllName);
964
965 /* Tell the Shim Engine */
966 if (g_ShimsEnabled)
967 {
971 }
972
973 /* Tell the world */
974 if (ShowSnaps)
975 {
976 DPRINT1("\n");
977 }
978
979 /* Set the shutdown variables */
980 LdrpShutdownThreadId = NtCurrentTeb()->RealClientId.UniqueThread;
982
983 /* Enter the Loader Lock */
985
986 /* Cleanup trace logging data (Etw) */
987 if (SharedUserData->TraceLogging)
988 {
989 /* FIXME */
990 DPRINT1("We don't support Etw yet.\n");
991 }
992
993 /* Start at the end */
995 NextEntry = ListHead->Blink;
996 while (NextEntry != ListHead)
997 {
998 /* Get the current entry */
999 LdrEntry = CONTAINING_RECORD(NextEntry, LDR_DATA_TABLE_ENTRY, InInitializationOrderLinks);
1000 NextEntry = NextEntry->Blink;
1001
1002 /* Make sure it's not ourselves */
1003 if (Peb->ImageBaseAddress != LdrEntry->DllBase)
1004 {
1005 /* Get the entrypoint */
1006 EntryPoint = LdrEntry->EntryPoint;
1007
1008 /* Check if we are ready to call it */
1009 if (EntryPoint &&
1010 (LdrEntry->Flags & LDRP_PROCESS_ATTACH_CALLED) &&
1011 LdrEntry->Flags)
1012 {
1013 /* Set up the Act Ctx */
1014 ActCtx.Size = sizeof(ActCtx);
1015 ActCtx.Format = 1;
1017
1018 /* Activate the ActCtx */
1019 RtlActivateActivationContextUnsafeFast(&ActCtx,
1020 LdrEntry->EntryPointActivationContext);
1021
1022 _SEH2_TRY
1023 {
1024 /* Check if it has TLS */
1025 if (LdrEntry->TlsIndex)
1026 {
1027 /* Call TLS */
1029 }
1030
1031 /* Call the Entrypoint */
1032 DPRINT("%wZ - Calling entry point at %p for thread detaching\n",
1033 &LdrEntry->BaseDllName, LdrEntry->EntryPoint);
1034 LdrpCallInitRoutine(EntryPoint,
1035 LdrEntry->DllBase,
1037 (PVOID)1);
1038 }
1040 {
1041 DPRINT1("WARNING: Exception 0x%x during LdrpCallInitRoutine(DLL_PROCESS_DETACH) for %wZ\n",
1042 _SEH2_GetExceptionCode(), &LdrEntry->BaseDllName);
1043 }
1044 _SEH2_END;
1045
1046 /* Deactivate the ActCtx */
1047 RtlDeactivateActivationContextUnsafeFast(&ActCtx);
1048 }
1049 }
1050 }
1051
1052 /* Check for TLS */
1053 if (LdrpImageHasTls)
1054 {
1055 /* Set up the Act Ctx */
1056 ActCtx.Size = sizeof(ActCtx);
1057 ActCtx.Format = 1;
1059
1060 /* Activate the ActCtx */
1061 RtlActivateActivationContextUnsafeFast(&ActCtx,
1063
1064 _SEH2_TRY
1065 {
1066 /* Do TLS callbacks */
1068 }
1070 {
1071 /* Do nothing */
1072 }
1073 _SEH2_END;
1074
1075 /* Deactivate the ActCtx */
1076 RtlDeactivateActivationContextUnsafeFast(&ActCtx);
1077 }
1078
1079 /* FIXME: Do Heap detection and Etw final shutdown */
1080
1081 /* Release the lock */
1083 DPRINT("LdrpShutdownProcess() done\n");
1084
1085 return STATUS_SUCCESS;
1086}
#define DLL_PROCESS_DETACH
Definition: compat.h:130
HANDLE LdrpShutdownThreadId
Definition: ldrinit.c:35
PVOID g_pfnSE_ProcessDying
Definition: ldrutils.c:27
VOID NTAPI SE_ProcessDying(VOID)
Definition: shimeng.c:1474
struct _LIST_ENTRY * Blink
Definition: typedefs.h:122

Referenced by ExitProcess().

◆ LdrShutdownThread()

NTSTATUS NTAPI LdrShutdownThread ( VOID  )

Definition at line 1093 of file ldrinit.c.

1094{
1095 PPEB Peb = NtCurrentPeb();
1096 PTEB Teb = NtCurrentTeb();
1097 PLDR_DATA_TABLE_ENTRY LdrEntry;
1098 PLIST_ENTRY NextEntry, ListHead;
1099 RTL_CALLER_ALLOCATED_ACTIVATION_CONTEXT_STACK_FRAME_EXTENDED ActCtx;
1100 PVOID EntryPoint;
1101
1102 DPRINT("LdrShutdownThread() called for %wZ\n",
1104
1105 /* Cleanup trace logging data (Etw) */
1106 if (SharedUserData->TraceLogging)
1107 {
1108 /* FIXME */
1109 DPRINT1("We don't support Etw yet.\n");
1110 }
1111
1112 /* Get the Ldr Lock */
1114
1115 /* Start at the end */
1117 NextEntry = ListHead->Blink;
1118 while (NextEntry != ListHead)
1119 {
1120 /* Get the current entry */
1121 LdrEntry = CONTAINING_RECORD(NextEntry, LDR_DATA_TABLE_ENTRY, InInitializationOrderLinks);
1122 NextEntry = NextEntry->Blink;
1123
1124 /* Make sure it's not ourselves */
1125 if (Peb->ImageBaseAddress != LdrEntry->DllBase)
1126 {
1127 /* Check if we should call */
1128 if (!(LdrEntry->Flags & LDRP_DONT_CALL_FOR_THREADS) &&
1129 (LdrEntry->Flags & LDRP_PROCESS_ATTACH_CALLED) &&
1130 (LdrEntry->Flags & LDRP_IMAGE_DLL))
1131 {
1132 /* Get the entrypoint */
1133 EntryPoint = LdrEntry->EntryPoint;
1134
1135 /* Check if we are ready to call it */
1136 if (EntryPoint)
1137 {
1138 /* Set up the Act Ctx */
1139 ActCtx.Size = sizeof(ActCtx);
1140 ActCtx.Format = 1;
1142
1143 /* Activate the ActCtx */
1144 RtlActivateActivationContextUnsafeFast(&ActCtx,
1145 LdrEntry->EntryPointActivationContext);
1146
1147 _SEH2_TRY
1148 {
1149 /* Check if it has TLS */
1150 if (LdrEntry->TlsIndex)
1151 {
1152 /* Make sure we're not shutting down */
1154 {
1155 /* Call TLS */
1157 }
1158 }
1159
1160 /* Make sure we're not shutting down */
1162 {
1163 /* Call the Entrypoint */
1164 DPRINT("%wZ - Calling entry point at %p for thread detaching\n",
1165 &LdrEntry->BaseDllName, LdrEntry->EntryPoint);
1166 LdrpCallInitRoutine(EntryPoint,
1167 LdrEntry->DllBase,
1169 NULL);
1170 }
1171 }
1173 {
1174 DPRINT1("WARNING: Exception 0x%x during LdrpCallInitRoutine(DLL_THREAD_DETACH) for %wZ\n",
1175 _SEH2_GetExceptionCode(), &LdrEntry->BaseDllName);
1176 }
1177 _SEH2_END;
1178
1179 /* Deactivate the ActCtx */
1180 RtlDeactivateActivationContextUnsafeFast(&ActCtx);
1181 }
1182 }
1183 }
1184 }
1185
1186 /* Check for TLS */
1187 if (LdrpImageHasTls)
1188 {
1189 /* Set up the Act Ctx */
1190 ActCtx.Size = sizeof(ActCtx);
1191 ActCtx.Format = 1;
1193
1194 /* Activate the ActCtx */
1195 RtlActivateActivationContextUnsafeFast(&ActCtx,
1197
1198 _SEH2_TRY
1199 {
1200 /* Do TLS callbacks */
1202 }
1204 {
1205 /* Do nothing */
1206 }
1207 _SEH2_END;
1208
1209 /* Deactivate the ActCtx */
1210 RtlDeactivateActivationContextUnsafeFast(&ActCtx);
1211 }
1212
1213 /* Free TLS */
1214 LdrpFreeTls();
1216
1217 /* Check for expansion slots */
1218 if (Teb->TlsExpansionSlots)
1219 {
1220 /* Free expansion slots */
1221 RtlFreeHeap(RtlGetProcessHeap(), 0, Teb->TlsExpansionSlots);
1222 }
1223
1224 /* Check for FLS Data */
1225 if (Teb->FlsData)
1226 {
1227 /* Mimic BaseRundownFls */
1228 ULONG n, FlsHighIndex;
1229 PRTL_FLS_DATA pFlsData;
1230 PFLS_CALLBACK_FUNCTION lpCallback;
1231
1232 pFlsData = Teb->FlsData;
1233
1235 FlsHighIndex = NtCurrentPeb()->FlsHighIndex;
1236 RemoveEntryList(&pFlsData->ListEntry);
1238
1239 for (n = 1; n <= FlsHighIndex; ++n)
1240 {
1241 lpCallback = NtCurrentPeb()->FlsCallback[n];
1242 if (lpCallback && pFlsData->Data[n])
1243 {
1244 lpCallback(pFlsData->Data[n]);
1245 }
1246 }
1247
1248 RtlFreeHeap(RtlGetProcessHeap(), 0, pFlsData);
1249 Teb->FlsData = NULL;
1250 }
1251
1252 /* Check for Fiber data */
1253 if (Teb->HasFiberData)
1254 {
1255 /* Free Fiber data*/
1256 RtlFreeHeap(RtlGetProcessHeap(), 0, Teb->NtTib.FiberData);
1257 Teb->NtTib.FiberData = NULL;
1258 }
1259
1260 /* Free the activation context stack */
1262 DPRINT("LdrShutdownThread() done\n");
1263
1264 return STATUS_SUCCESS;
1265}
#define DLL_THREAD_DETACH
Definition: compat.h:133
#define RemoveEntryList(Entry)
Definition: env_spec_w32.h:986
NTSYSAPI void WINAPI RtlReleasePebLock(void)
Definition: libsupp.c:84
NTSYSAPI void WINAPI RtlAcquirePebLock(void)
Definition: libsupp.c:74
NTSYSAPI void WINAPI RtlFreeThreadActivationContextStack(void)
Definition: actctx.c:5515
VOID NTAPI LdrpFreeTls(VOID)
Definition: ldrinit.c:1395
PVOID FiberData
Definition: compat.h:716
LIST_ENTRY ListEntry
Definition: rtltypes.h:1217
PVOID Data[RTL_FLS_MAXIMUM_AVAILABLE]
Definition: rtltypes.h:1218
PVOID * TlsExpansionSlots
Definition: compat.h:894
VOID(WINAPI * PFLS_CALLBACK_FUNCTION)(PVOID)
Definition: winbase.h:1202

◆ NTSTATUS()

static NTSTATUS ( WINAPI Kernel32ProcessInitPostImportFunction)
static

◆ RtlInitializeHeapManager()

VOID NTAPI RtlInitializeHeapManager ( VOID  )

Definition at line 243 of file libsupp.c.

244{
245}

Referenced by LdrpInitializeProcess().

◆ RtlpInitDeferredCriticalSection()

VOID NTAPI RtlpInitDeferredCriticalSection ( VOID  )

Definition at line 272 of file critical.c.

273{
274 /* Initialize the CS Protecting the List */
276
277 /* It's now safe to enter it */
279}
NTSTATUS NTAPI RtlInitializeCriticalSection(PRTL_CRITICAL_SECTION CriticalSection)
Definition: critical.c:546
static BOOLEAN RtlpCritSectInitialized
Definition: critical.c:21
static RTL_CRITICAL_SECTION RtlCriticalSectionLock
Definition: critical.c:19

Referenced by LdrpInitializeProcess().

◆ RtlpInitializeActCtx()

NTSTATUS NTAPI RtlpInitializeActCtx ( PVOID pOldShimData)

Referenced by LdrpInitializeProcess().

◆ RtlpInitializeLocaleTable()

NTSTATUS NTAPI RtlpInitializeLocaleTable ( VOID  )

Definition at line 529 of file locale.c.

530{
531 PSORT_ENTRY SortTable;
532 SIZE_T SortTableSize;
533
536
537 SortTableSize = sizeof(SortTable[0]) * ARRAYSIZE(RtlpLocaleTable);
538 SortTable = RtlAllocateHeap(RtlGetProcessHeap(), 0, SortTableSize);
539 if (SortTable == NULL)
540 {
542 }
543
544 /* Copy the LCIDs and the index */
545 for (USHORT i = 0; i < ARRAYSIZE(RtlpLocaleTable); i++)
546 {
547 SortTable[i].Lcid = RtlpLocaleTable[i].Lcid;
548 SortTable[i].Index = i;
549 }
550
551 /* Sort the table by LCID */
552 qsort(SortTable,
554 sizeof(SortTable[0]),
556
557 /* Copy the sorted indices to the global table */
558 for (USHORT i = 0; i < ARRAYSIZE(RtlpLocaleTable); i++)
559 {
560 RtlpLocaleIndexTable[i] = SortTable[i].Index;
561 }
562
563 RtlFreeHeap(RtlGetProcessHeap(), 0, SortTable);
564
565 return STATUS_SUCCESS;
566}
_ACRTIMP void __cdecl qsort(void *, size_t, size_t, int(__cdecl *)(const void *, const void *))
NTSTATUS NTAPI NtQueryDefaultLocale(IN BOOLEAN UserProfile, OUT PLCID DefaultLocaleId)
Definition: locale.c:396
static USHORT RtlpLocaleIndexTable[_ARRAYSIZE(RtlpLocaleTable)]
Definition: locale.c:506
LCID RtlpUserDefaultLcid
Definition: locale.c:23
static const LOCALE_ENTRY RtlpLocaleTable[]
Definition: locale.c:34
LCID RtlpSystemDefaultLcid
Definition: locale.c:24
static int __cdecl LcidSortEntryCompare(const void *a, const void *b)
Definition: locale.c:515
LCID Lcid
Definition: locale.c:29
Definition: locale.c:509
LCID Lcid
Definition: locale.c:510
USHORT Index
Definition: locale.c:511
#define STATUS_INSUFFICIENT_RESOURCES
Definition: udferr_usr.h:158

Referenced by LdrpInitializeProcess().

◆ RtlpInitializeVectoredExceptionHandling()

VOID NTAPI RtlpInitializeVectoredExceptionHandling ( VOID  )

Definition at line 30 of file vectoreh.c.

31{
32 /* Initialize our two lists and the common lock */
36}
LIST_ENTRY RtlpVectoredContinueList
Definition: vectoreh.c:17
RTL_CRITICAL_SECTION RtlpVectoredHandlerLock
Definition: vectoreh.c:16
LIST_ENTRY RtlpVectoredExceptionList
Definition: vectoreh.c:17

Referenced by LdrpInitializeProcess().

Variable Documentation

◆ FastPebLock

RTL_CRITICAL_SECTION FastPebLock

Definition at line 77 of file ldrinit.c.

Referenced by FlsCallback3(), LdrpInitializeProcess(), and START_TEST().

◆ FlsBitMap

RTL_BITMAP FlsBitMap

Definition at line 51 of file ldrinit.c.

Referenced by LdrpInitializeProcess().

◆ ImageExecOptionsKey

HANDLE ImageExecOptionsKey

Definition at line 22 of file ldrinit.c.

Referenced by LdrOpenImageFileOptionsKey().

◆ ImageExecOptionsString

UNICODE_STRING ImageExecOptionsString = RTL_CONSTANT_STRING(L"\\Registry\\Machine\\Software\\Microsoft\\Windows NT\\CurrentVersion\\Image File Execution Options")

Definition at line 24 of file ldrinit.c.

Referenced by DisplayImageInfo(), LdrOpenImageFileOptionsKey(), and ModifyStatus().

◆ Kernel32String

UNICODE_STRING Kernel32String = RTL_CONSTANT_STRING(L"kernel32.dll")

Definition at line 27 of file ldrinit.c.

Referenced by LdrpInitializeProcess().

◆ LdrpActiveUnloadCount

ULONG LdrpActiveUnloadCount

Definition at line 82 of file ldrinit.c.

Referenced by LdrUnloadDll().

◆ LdrpCurrentDllInitializer

PLDR_DATA_TABLE_ENTRY LdrpCurrentDllInitializer

Definition at line 43 of file ldrinit.c.

Referenced by LdrLoadDll(), and LdrpRunInitializeRoutines().

◆ LdrpDefaultPath

◆ LdrpDllValidation

BOOLEAN LdrpDllValidation

Definition at line 37 of file ldrinit.c.

Referenced by LdrpInitializeProcess().

◆ LdrpDotLocal

const UNICODE_STRING LdrpDotLocal = RTL_CONSTANT_STRING(L".Local")

Definition at line 28 of file ldrinit.c.

Referenced by LdrpInitializeDotLocalSupport().

◆ LdrpFatalHardErrorCount

ULONG LdrpFatalHardErrorCount

Definition at line 81 of file ldrinit.c.

Referenced by LdrpCreateDllSection(), LdrpInitFailure(), LdrpMapDll(), and LdrpSnapThunk().

◆ LdrpHashTable

◆ LdrpImageEntry

◆ LdrpImageHasTls

◆ LdrpInLdrInit

◆ LdrpKnownDllObjectDirectory

HANDLE LdrpKnownDllObjectDirectory

Definition at line 60 of file ldrinit.c.

Referenced by LdrpCheckForKnownDll(), LdrpInitializeProcess(), and LdrpMapDll().

◆ LdrpKnownDllPath

UNICODE_STRING LdrpKnownDllPath

Definition at line 61 of file ldrinit.c.

Referenced by LdrpCheckForKnownDll(), and LdrpInitializeProcess().

◆ LdrpKnownDllPathBuffer

WCHAR LdrpKnownDllPathBuffer[128]

Definition at line 62 of file ldrinit.c.

Referenced by LdrpInitializeProcess().

◆ LdrpLdrDatabaseIsSetup

BOOLEAN LdrpLdrDatabaseIsSetup

Definition at line 33 of file ldrinit.c.

Referenced by LdrpInitializeProcess(), and LdrpLoadDll().

◆ LdrpLoaderLock

RTL_CRITICAL_SECTION LdrpLoaderLock
Initial value:
=
{
-1,
0,
0,
0,
0
}
RTL_CRITICAL_SECTION_DEBUG LdrpLoaderLockDebug
Definition: ldrinit.c:67

Definition at line 68 of file ldrinit.c.

Referenced by LdrLockLoaderLock(), LdrpGetProcedureAddress(), LdrpInit(), LdrpInitializeProcess(), LdrpInitializeThread(), LdrpLoadDll(), LdrShutdownProcess(), LdrShutdownThread(), and LdrUnlockLoaderLock().

◆ LdrpLoaderLockDebug

RTL_CRITICAL_SECTION_DEBUG LdrpLoaderLockDebug

Definition at line 67 of file ldrinit.c.

◆ LdrpLoaderLockInit

BOOLEAN LdrpLoaderLockInit

Definition at line 32 of file ldrinit.c.

Referenced by LdrpInitializeProcess().

◆ LdrpNtDllDataTableEntry

PLDR_DATA_TABLE_ENTRY LdrpNtDllDataTableEntry

Definition at line 44 of file ldrinit.c.

Referenced by LdrpInitializeProcess().

◆ LdrpNumberOfProcessors

ULONG LdrpNumberOfProcessors

Definition at line 55 of file ldrinit.c.

Referenced by LdrpInitializeProcess(), and LdrpMapDll().

◆ LdrpNumberOfTlsEntries

ULONG LdrpNumberOfTlsEntries

Definition at line 54 of file ldrinit.c.

Referenced by LdrpAllocateTls(), and LdrpInitializeTls().

◆ LdrpProcessInitialized

LONG LdrpProcessInitialized

Definition at line 31 of file ldrinit.c.

Referenced by LdrpInit().

◆ LdrpShutdownInProgress

BOOLEAN LdrpShutdownInProgress

Definition at line 34 of file ldrinit.c.

Referenced by LdrpInitializeThread(), LdrShutdownProcess(), and LdrShutdownThread().

◆ LdrpShutdownThreadId

HANDLE LdrpShutdownThreadId

Definition at line 35 of file ldrinit.c.

Referenced by LdrShutdownProcess().

◆ LdrpTlsList

LIST_ENTRY LdrpTlsList

Definition at line 53 of file ldrinit.c.

Referenced by LdrpAllocateTls(), LdrpFreeTls(), and LdrpInitializeTls().

◆ LdrpTopLevelDllBeingLoaded

PUNICODE_STRING LdrpTopLevelDllBeingLoaded

Definition at line 40 of file ldrinit.c.

Referenced by LdrLoadDll().

◆ LdrpTopLevelDllBeingLoadedTeb

PTEB LdrpTopLevelDllBeingLoadedTeb
extern

Definition at line 20 of file libsupp.c.

Referenced by LdrpRunInitializeRoutines(), and RtlIsThreadWithinLoaderCallout().

◆ NtDllBase

PVOID NtDllBase

Definition at line 56 of file ldrinit.c.

Referenced by LdrpInitializeProcess().

◆ NtDllString

UNICODE_STRING NtDllString = RTL_CONSTANT_STRING(L"ntdll.dll")

Definition at line 26 of file ldrinit.c.

Referenced by LdrpInitializeProcess().

◆ PebLdr

PEB_LDR_DATA PebLdr

Definition at line 65 of file ldrinit.c.

Referenced by KiPrepareUserDebugData(), and LdrpInitializeProcess().

◆ RtlpDisableHeapLookaside

ULONG RtlpDisableHeapLookaside

Definition at line 91 of file ldrinit.c.

Referenced by LdrpInitializeExecutionOptions().

◆ RtlpShutdownProcessFlags

ULONG RtlpShutdownProcessFlags

Definition at line 92 of file ldrinit.c.

Referenced by LdrpInitializeExecutionOptions().

◆ RtlpTimeout

LARGE_INTEGER RtlpTimeout
extern

◆ RtlpTimeoutDisable

BOOLEAN RtlpTimeoutDisable
extern

Definition at line 26 of file critical.c.

Referenced by LdrpInitializeProcess(), and RtlpWaitForCriticalSection().

◆ RtlpUse16ByteSLists

BOOLEAN RtlpUse16ByteSLists
extern

◆ ShowSnaps

◆ StringBuffer

◆ TlsBitMap

RTL_BITMAP TlsBitMap

Definition at line 49 of file ldrinit.c.

Referenced by LdrpInitializeProcess().

◆ TlsExpansionBitMap

RTL_BITMAP TlsExpansionBitMap

Definition at line 50 of file ldrinit.c.

Referenced by LdrpInitializeProcess().

◆ Unk1

PVOID Unk1

Definition at line 47 of file ldrinit.c.

◆ Unk2

PVOID PVOID Unk2

Definition at line 47 of file ldrinit.c.

◆ Unk3

Definition at line 47 of file ldrinit.c.

◆ Unk4

Definition at line 47 of file ldrinit.c.

◆ Wow64ExecOptionsKey

HANDLE Wow64ExecOptionsKey

Definition at line 23 of file ldrinit.c.

Referenced by LdrOpenImageFileOptionsKey().

◆ Wow64OptionsString

UNICODE_STRING Wow64OptionsString = RTL_CONSTANT_STRING(L"")

Definition at line 25 of file ldrinit.c.

Referenced by LdrOpenImageFileOptionsKey().