Commit 051f8715 authored by Eric Pouech's avatar Eric Pouech Committed by Alexandre Julliard

- implemented LdrQueryProcessModuleInformation

- rewrote VERSION_GetLinkedDllVersion() with this new function instead of accessing directly the modref list
parent 69497b3c
......@@ -759,6 +759,55 @@ NTSTATUS WINAPI LdrLoadDll(LPCWSTR path_name, DWORD flags, PUNICODE_STRING libna
}
/******************************************************************
* LdrQueryProcessModuleInformation
*
*/
NTSTATUS WINAPI LdrQueryProcessModuleInformation(PSYSTEM_MODULE_INFORMATION smi,
ULONG buf_size, ULONG* req_size)
{
SYSTEM_MODULE* sm = &smi->Modules[0];
ULONG size = sizeof(ULONG);
NTSTATUS nts = STATUS_SUCCESS;
ANSI_STRING str;
char* ptr;
WINE_MODREF* wm;
smi->ModulesCount = 0;
RtlEnterCriticalSection( &loader_section );
for ( wm = MODULE_modref_list; wm; wm = wm->next )
{
size += sizeof(*sm);
if (size <= buf_size)
{
sm->Reserved1 = 0; /* FIXME */
sm->Reserved2 = 0; /* FIXME */
sm->ImageBaseAddress = wm->ldr.BaseAddress;
sm->ImageSize = wm->ldr.SizeOfImage;
sm->Flags = wm->ldr.Flags;
sm->Id = 0; /* FIXME */
sm->Rank = 0; /* FIXME */
sm->Unknown = 0; /* FIXME */
str.Length = 0;
str.MaximumLength = MAXIMUM_FILENAME_LENGTH;
str.Buffer = sm->Name;
RtlUnicodeStringToAnsiString(&str, &wm->ldr.FullDllName, FALSE);
ptr = strrchr(sm->Name, '\\');
sm->NameOffset = (ptr != NULL) ? (ptr - (char*)sm->Name + 1) : 0;
smi->ModulesCount++;
sm++;
}
else nts = STATUS_INFO_LENGTH_MISMATCH;
}
RtlLeaveCriticalSection( &loader_section );
if (req_size) *req_size = size;
return nts;
}
/******************************************************************
* LdrShutdownProcess (NTDLL.@)
*
*/
......
......@@ -46,7 +46,7 @@
@ stdcall LdrLockLoaderLock(long ptr ptr)
@ stub LdrProcessRelocationBlock
@ stub LdrQueryImageFileExecutionOptions
@ stub LdrQueryProcessModuleInformation
@ stdcall LdrQueryProcessModuleInformation(ptr long ptr)
@ stdcall LdrShutdownProcess()
@ stdcall LdrShutdownThread()
@ stdcall LdrUnloadDll(ptr)
......
......@@ -1227,6 +1227,7 @@ NTSTATUS WINAPI LdrGetDllHandle(ULONG, ULONG, PUNICODE_STRING, HMODULE*);
NTSTATUS WINAPI LdrGetProcedureAddress(HMODULE, PANSI_STRING, ULONG, void**);
NTSTATUS WINAPI LdrLoadDll(LPCWSTR, DWORD, PUNICODE_STRING, HMODULE*);
NTSTATUS WINAPI LdrLockLoaderLock(ULONG,ULONG*,ULONG*);
NTSTATUS WINAPI LdrQueryProcessModuleInformation(SYSTEM_MODULE_INFORMATION*, ULONG, ULONG*);
NTSTATUS WINAPI LdrShutdownProcess(void);
NTSTATUS WINAPI LdrShutdownThread(void);
NTSTATUS WINAPI LdrUnloadDll(HMODULE);
......
......@@ -37,6 +37,7 @@
#include "module.h"
#include "wine/unicode.h"
#include "wine/debug.h"
#include "ntdll_misc.h"
WINE_DEFAULT_DEBUG_CHANNEL(ver);
......@@ -444,51 +445,64 @@ static DWORD VERSION_GetSystemDLLVersion( HMODULE hmod )
*/
static DWORD VERSION_GetLinkedDllVersion(void)
{
WINE_MODREF *wm;
DWORD WinVersion = NB_WINDOWS_VERSIONS;
PIMAGE_OPTIONAL_HEADER ophd;
IMAGE_NT_HEADERS *nt;
ULONG count, required;
SYSTEM_MODULE_INFORMATION* smi;
/* First check the native dlls provided. These have to be
from one windows version */
for ( wm = MODULE_modref_list; wm; wm=wm->next )
{
nt = RtlImageNtHeader(wm->ldr.BaseAddress);
ophd = &nt->OptionalHeader;
TRACE("%s: %02x.%02x/%02x.%02x/%02x.%02x/%02x.%02x\n",
wm->modname,
ophd->MajorLinkerVersion, ophd->MinorLinkerVersion,
ophd->MajorOperatingSystemVersion, ophd->MinorOperatingSystemVersion,
ophd->MajorImageVersion, ophd->MinorImageVersion,
ophd->MajorSubsystemVersion, ophd->MinorSubsystemVersion);
/* test if it is an external (native) dll */
if (!(wm->ldr.Flags & LDR_WINE_INTERNAL))
{
int i;
for (i = 0; special_dlls[i]; i++)
{
/* test if it is a special dll */
if (!strcasecmp(wm->modname, special_dlls[i]))
{
DWORD DllVersion = VERSION_GetSystemDLLVersion(wm->ldr.BaseAddress);
if (WinVersion == NB_WINDOWS_VERSIONS)
WinVersion = DllVersion;
else {
if (WinVersion != DllVersion) {
ERR("You mixed system DLLs from different windows versions! Expect a crash! (%s: expected version '%s', but is '%s')\n",
wm->modname,
VersionData[WinVersion].getVersionEx.szCSDVersion,
VersionData[DllVersion].getVersionEx.szCSDVersion);
return WIN20; /* this may let the exe exiting */
}
}
break;
}
}
}
}
smi = (SYSTEM_MODULE_INFORMATION*)&count;
LdrQueryProcessModuleInformation(smi, sizeof(count), &required);
smi = RtlAllocateHeap(ntdll_get_process_heap(), 0, required);
if (smi)
{
if (LdrQueryProcessModuleInformation(smi, required, NULL) == STATUS_SUCCESS)
{
int k;
for (k = 0; k < smi->ModulesCount; k++)
{
nt = RtlImageNtHeader(smi->Modules[k].ImageBaseAddress);
ophd = &nt->OptionalHeader;
TRACE("%s: %02x.%02x/%02x.%02x/%02x.%02x/%02x.%02x\n",
&smi->Modules[k].Name[smi->Modules[k].NameOffset],
ophd->MajorLinkerVersion, ophd->MinorLinkerVersion,
ophd->MajorOperatingSystemVersion, ophd->MinorOperatingSystemVersion,
ophd->MajorImageVersion, ophd->MinorImageVersion,
ophd->MajorSubsystemVersion, ophd->MinorSubsystemVersion);
}
/* test if it is an external (native) dll */
if (!(smi->Modules[k].Flags & LDR_WINE_INTERNAL))
{
int i;
for (i = 0; special_dlls[i]; i++)
{
/* test if it is a special dll */
if (!strcasecmp(&smi->Modules[k].Name[smi->Modules[k].NameOffset], special_dlls[i]))
{
DWORD DllVersion = VERSION_GetSystemDLLVersion(smi->Modules[k].ImageBaseAddress);
if (WinVersion == NB_WINDOWS_VERSIONS)
WinVersion = DllVersion;
else
{
if (WinVersion != DllVersion) {
ERR("You mixed system DLLs from different windows versions! Expect a crash! (%s: expected version '%s', but is '%s')\n",
&smi->Modules[k].Name[smi->Modules[k].NameOffset],
VersionData[WinVersion].getVersionEx.szCSDVersion,
VersionData[DllVersion].getVersionEx.szCSDVersion);
return WIN20; /* this may let the exe exiting */
}
}
break;
}
}
}
}
RtlFreeHeap(ntdll_get_process_heap(), 0, smi);
}
if(WinVersion != NB_WINDOWS_VERSIONS) return WinVersion;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment