mirror of
https://github.com/reactos/reactos.git
synced 2025-04-04 20:50:41 +00:00
Dmitry Philippov <shedon@mail.ru>
- The EngLoadImage and EngUnloadImage functions have been fixed to store handles of loaded drivers. EngLoadImage should not fail if a driver is already loaded, it should return a handle of the already loaded driver instead. - The gpDxFuncs variable has been redefined. Earlier, memory was not allocated for this variable, thus resulting in memory corruption. svn path=/trunk/; revision=31416
This commit is contained in:
parent
41e2d7b240
commit
a6ca74e2cf
4 changed files with 82 additions and 12 deletions
|
@ -8,7 +8,7 @@
|
|||
#include <reactos/drivers/directx/dxeng.h>
|
||||
|
||||
/* From ddraw.c */
|
||||
extern PDRVFN gpDxFuncs;
|
||||
extern DRVFN gpDxFuncs[];
|
||||
|
||||
typedef BOOL (NTAPI* PGD_DDSETGAMMARAMP)(HANDLE, HDC, LPVOID);
|
||||
typedef BOOL (NTAPI* PGD_DDRELEASEDC)(HANDLE);
|
||||
|
|
|
@ -25,6 +25,16 @@
|
|||
#define NDEBUG
|
||||
#include <debug.h>
|
||||
|
||||
|
||||
typedef struct _DRIVERS
|
||||
{
|
||||
LIST_ENTRY ListEntry;
|
||||
HANDLE ImageHandle;
|
||||
UNICODE_STRING DriverName;
|
||||
}DRIVERS, *PDRIVERS;
|
||||
|
||||
extern LIST_ENTRY GlobalDriverListHead;
|
||||
|
||||
/*
|
||||
* Blatantly stolen from ldr/utils.c in ntdll. I can't link ntdll from
|
||||
* here, though.
|
||||
|
@ -189,14 +199,47 @@ HANDLE
|
|||
STDCALL
|
||||
EngLoadImage (LPWSTR DriverName)
|
||||
{
|
||||
SYSTEM_GDI_DRIVER_INFORMATION GdiDriverInfo;
|
||||
NTSTATUS Status;
|
||||
HANDLE hImageHandle = NULL;
|
||||
SYSTEM_GDI_DRIVER_INFORMATION GdiDriverInfo;
|
||||
NTSTATUS Status;
|
||||
|
||||
RtlInitUnicodeString(&GdiDriverInfo.DriverName, DriverName);
|
||||
Status = ZwSetSystemInformation(SystemLoadGdiDriverInformation, &GdiDriverInfo, sizeof(SYSTEM_GDI_DRIVER_INFORMATION));
|
||||
if (!NT_SUCCESS(Status)) return NULL;
|
||||
RtlInitUnicodeString(&GdiDriverInfo.DriverName, DriverName);
|
||||
if( !IsListEmpty(&GlobalDriverListHead) )
|
||||
{
|
||||
PLIST_ENTRY CurrentEntry = GlobalDriverListHead.Flink;
|
||||
PDRIVERS Current;
|
||||
/* probably the driver was already loaded, let's try to find it out */
|
||||
while( CurrentEntry != &GlobalDriverListHead )
|
||||
{
|
||||
Current = CONTAINING_RECORD(CurrentEntry, DRIVERS, ListEntry);
|
||||
if( Current && (0 == RtlCompareUnicodeString(&GdiDriverInfo.DriverName, &Current->DriverName, FALSE)) ) {
|
||||
hImageHandle = Current->ImageHandle;
|
||||
break;
|
||||
}
|
||||
CurrentEntry = CurrentEntry->Flink;
|
||||
};
|
||||
}
|
||||
|
||||
return (HANDLE)GdiDriverInfo.ImageAddress;
|
||||
if( !hImageHandle )
|
||||
{
|
||||
/* the driver was not loaded before, so let's do that */
|
||||
Status = ZwSetSystemInformation(SystemLoadGdiDriverInformation, &GdiDriverInfo, sizeof(SYSTEM_GDI_DRIVER_INFORMATION));
|
||||
if (!NT_SUCCESS(Status)) {
|
||||
DPRINT1("ZwSetSystemInformation faild with status 0x%lx\n", Status);
|
||||
}
|
||||
else {
|
||||
hImageHandle = (HANDLE)GdiDriverInfo.ImageAddress;
|
||||
PDRIVERS DriverInfo = ExAllocatePool(PagedPool, sizeof(DRIVERS));
|
||||
DriverInfo->DriverName.MaximumLength = GdiDriverInfo.DriverName.MaximumLength;
|
||||
DriverInfo->DriverName.Length = GdiDriverInfo.DriverName.Length;
|
||||
DriverInfo->DriverName.Buffer = ExAllocatePool(PagedPool, GdiDriverInfo.DriverName.MaximumLength);
|
||||
RtlCopyUnicodeString(&DriverInfo->DriverName, &GdiDriverInfo.DriverName);
|
||||
DriverInfo->ImageHandle = hImageHandle;
|
||||
InsertHeadList(&GlobalDriverListHead, &DriverInfo->ListEntry);
|
||||
}
|
||||
}
|
||||
|
||||
return hImageHandle;
|
||||
}
|
||||
|
||||
|
||||
|
@ -226,7 +269,8 @@ EngUnloadImage ( IN HANDLE hModule )
|
|||
{
|
||||
NTSTATUS Status;
|
||||
|
||||
DPRINT1("hModule=%x\n", hModule);
|
||||
DPRINT1("hModule=%x\n", hModule);
|
||||
|
||||
Status = ZwSetSystemInformation(SystemUnloadGdiDriverInformation,
|
||||
&hModule, sizeof(HANDLE));
|
||||
|
||||
|
@ -235,6 +279,30 @@ EngUnloadImage ( IN HANDLE hModule )
|
|||
DPRINT1("%s: ZwSetSystemInformation failed with status %x.",
|
||||
__FUNCTION__, Status);
|
||||
}
|
||||
else
|
||||
{
|
||||
/* remove from the list */
|
||||
if( !IsListEmpty(&GlobalDriverListHead) )
|
||||
{
|
||||
PLIST_ENTRY CurrentEntry = GlobalDriverListHead.Flink;
|
||||
PDRIVERS Current;
|
||||
/* probably the driver was already loaded, let's try to find it out */
|
||||
while( CurrentEntry != &GlobalDriverListHead )
|
||||
{
|
||||
Current = CONTAINING_RECORD(CurrentEntry, DRIVERS, ListEntry);
|
||||
|
||||
if( Current ) {
|
||||
if(Current->ImageHandle == hModule) {
|
||||
ExFreePool(Current->DriverName.Buffer);
|
||||
RemoveEntryList(&Current->ListEntry);
|
||||
ExFreePool(Current);
|
||||
break;
|
||||
}
|
||||
}
|
||||
CurrentEntry = CurrentEntry->Flink;
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* EOF */
|
||||
|
|
|
@ -33,6 +33,8 @@ BOOL INTERNAL_CALL GDI_CleanupForProcess (PGDI_HANDLE_TABLE HandleTable, struct
|
|||
PGDI_HANDLE_TABLE GdiHandleTable = NULL;
|
||||
PSECTION_OBJECT GdiTableSection = NULL;
|
||||
|
||||
LIST_ENTRY GlobalDriverListHead;
|
||||
|
||||
HANDLE GlobalUserHeap = NULL;
|
||||
PSECTION_OBJECT GlobalUserHeapSection = NULL;
|
||||
|
||||
|
@ -402,6 +404,8 @@ DriverEntry (
|
|||
return STATUS_UNSUCCESSFUL;
|
||||
}
|
||||
|
||||
/* Initialize a list of loaded drivers in Win32 subsystem */
|
||||
InitializeListHead(&GlobalDriverListHead);
|
||||
|
||||
Status = InitUserImpl();
|
||||
if (!NT_SUCCESS(Status))
|
||||
|
|
|
@ -18,8 +18,8 @@ PGD_DXDDCLEANUPDXGRAPHICS gpfnCleanupDxGraphics = NULL;
|
|||
extern DRVFN gaEngFuncs;
|
||||
extern ULONG gcEngFuncs;
|
||||
|
||||
PDRVFN gpDxFuncs;
|
||||
HANDLE ghDxGraphics;
|
||||
DRVFN gpDxFuncs[DXG_INDEX_DxDdIoctl];
|
||||
HANDLE ghDxGraphics = NULL;
|
||||
ULONG gdwDirectDrawContext;
|
||||
|
||||
|
||||
|
@ -126,7 +126,6 @@ HANDLE
|
|||
STDCALL
|
||||
NtGdiDdCreateDirectDrawObject(HDC hdc)
|
||||
{
|
||||
|
||||
PGD_DDCREATEDIRECTDRAWOBJECT pfnDdCreateDirectDrawObject = NULL;
|
||||
NTSTATUS Status;
|
||||
PEPROCESS Proc = NULL;
|
||||
|
@ -152,7 +151,6 @@ NtGdiDdCreateDirectDrawObject(HDC hdc)
|
|||
|
||||
DPRINT1("Calling dxg.sys DdCreateDirectDrawObject\n");
|
||||
return pfnDdCreateDirectDrawObject(hdc);
|
||||
|
||||
}
|
||||
|
||||
/*++
|
||||
|
|
Loading…
Reference in a new issue