[NTOS:EX]

- Blocking of the user buffer before obtaining information
- Use of ObpGetHandleObject macro for receiving ObjectHeader
- Remove duplicate NULL pointer check for HandleTableEntry

svn path=/trunk/; revision=72506
This commit is contained in:
Dmitry Chapyshev 2016-08-29 20:41:23 +00:00
parent c56713f129
commit 5168c15faa

View file

@ -1167,24 +1167,26 @@ QSI_DEF(SystemNonPagedPoolInformation)
/* Class 16 - Handle Information */ /* Class 16 - Handle Information */
QSI_DEF(SystemHandleInformation) QSI_DEF(SystemHandleInformation)
{ {
PSYSTEM_HANDLE_INFORMATION HandleInformation;
KPROCESSOR_MODE PreviousMode;
PEPROCESS Process; PEPROCESS Process;
PEPROCESS SystemProcess; PEPROCESS SystemProcess;
ULONG CurrentSize; ULONG CurrentSize;
ULONG NumberOfHandles = 0; ULONG NumberOfHandles = 0;
ULONG Index; ULONG Index;
NTSTATUS Status;
PSYSTEM_HANDLE_INFORMATION HandleInformation = PMDL Mdl;
(PSYSTEM_HANDLE_INFORMATION) Buffer;
DPRINT("NtQuerySystemInformation - SystemHandleInformation\n"); DPRINT("NtQuerySystemInformation - SystemHandleInformation\n");
/* Check user's buffer size */
if (Size < sizeof(SYSTEM_HANDLE_INFORMATION)) if (Size < sizeof(SYSTEM_HANDLE_INFORMATION))
{ {
*ReqSize = sizeof(SYSTEM_HANDLE_INFORMATION); *ReqSize = sizeof(SYSTEM_HANDLE_INFORMATION);
return STATUS_INFO_LENGTH_MISMATCH; return STATUS_INFO_LENGTH_MISMATCH;
} }
/* First Calc Size from Count. */ /* Retrieve needed buffer size to hold the list of handles */
SystemProcess = PsGetNextProcess(NULL); SystemProcess = PsGetNextProcess(NULL);
Process = SystemProcess; Process = SystemProcess;
@ -1195,19 +1197,37 @@ QSI_DEF(SystemHandleInformation)
} }
while ((Process != SystemProcess) && (Process != NULL)); while ((Process != SystemProcess) && (Process != NULL));
/* Dereference the process which was referenced by PsGetNextProcess */
if (Process != NULL) ObDereferenceObject(Process); if (Process != NULL) ObDereferenceObject(Process);
/* Calculate the current size of all handles */
CurrentSize = sizeof(SYSTEM_HANDLE_INFORMATION) + CurrentSize = sizeof(SYSTEM_HANDLE_INFORMATION) +
((sizeof(SYSTEM_HANDLE_TABLE_ENTRY_INFO) * NumberOfHandles) - ((sizeof(SYSTEM_HANDLE_TABLE_ENTRY_INFO) * NumberOfHandles) -
(sizeof(SYSTEM_HANDLE_TABLE_ENTRY_INFO))); (sizeof(SYSTEM_HANDLE_TABLE_ENTRY_INFO)));
HandleInformation->NumberOfHandles = NumberOfHandles;
*ReqSize = CurrentSize; *ReqSize = CurrentSize;
/* Check user's buffer size */
if (CurrentSize > Size) return STATUS_INFO_LENGTH_MISMATCH; if (CurrentSize > Size) return STATUS_INFO_LENGTH_MISMATCH;
/* Now get Handles from all processes. */ /* We need to lock down the memory */
PreviousMode = ExGetPreviousMode();
Status = ExLockUserBuffer(Buffer,
Size,
PreviousMode,
IoWriteAccess,
(PVOID*)&HandleInformation,
&Mdl);
if (!NT_SUCCESS(Status))
{
DPRINT1("Failed to lock the user buffer: 0x%lx\n", Status);
return Status;
}
/* Initialization of count of handles */
HandleInformation->NumberOfHandles = NumberOfHandles;
/* Now get handles from all processes. */
SystemProcess = PsGetNextProcess(NULL); SystemProcess = PsGetNextProcess(NULL);
Process = SystemProcess; Process = SystemProcess;
@ -1226,16 +1246,13 @@ QSI_DEF(SystemHandleInformation)
while ((HandleTableEntry = ExpLookupHandleTableEntry(Process->ObjectTable, Handle))) while ((HandleTableEntry = ExpLookupHandleTableEntry(Process->ObjectTable, Handle)))
{ {
/* Validate the entry */ /* Validate the entry */
if ((HandleTableEntry) && if ((HandleTableEntry->Object) &&
(HandleTableEntry->Object) &&
(HandleTableEntry->NextFreeTableEntry != -2)) (HandleTableEntry->NextFreeTableEntry != -2))
{ {
/* Lock the entry */ /* Lock the entry */
if (ExpLockHandleTableEntry(Process->ObjectTable, HandleTableEntry)) if (ExpLockHandleTableEntry(Process->ObjectTable, HandleTableEntry))
{ {
POBJECT_HEADER ObjectHeader; POBJECT_HEADER ObjectHeader = ObpGetHandleObject(HandleTableEntry);
ObjectHeader = (POBJECT_HEADER)(((ULONG_PTR) HandleTableEntry->Object) & ~OBJ_HANDLE_ATTRIBUTES);
/* Filling handle information */ /* Filling handle information */
HandleInformation->Handles[Index].UniqueProcessId = (USHORT)(ULONG_PTR) Process->UniqueProcessId; HandleInformation->Handles[Index].UniqueProcessId = (USHORT)(ULONG_PTR) Process->UniqueProcessId;
@ -1257,25 +1274,21 @@ QSI_DEF(SystemHandleInformation)
Handle.Value += sizeof(HANDLE); Handle.Value += sizeof(HANDLE);
} }
/* Leave the critical region and return callback result */ /* Leave the critical region */
KeLeaveCriticalRegion(); KeLeaveCriticalRegion();
Process = PsGetNextProcess(Process); Process = PsGetNextProcess(Process);
} }
while ((Process != SystemProcess) && (Process != NULL)); while ((Process != SystemProcess) && (Process != NULL));
/* Dereference the process which was referenced by PsGetNextProcess */
if (Process != NULL) ObDereferenceObject(Process); if (Process != NULL) ObDereferenceObject(Process);
return STATUS_SUCCESS; /* Release the locked user buffer */
ExUnlockUserBuffer(Mdl);
}
/*
SSI_DEF(SystemHandleInformation)
{
return STATUS_SUCCESS; return STATUS_SUCCESS;
} }
*/
/* Class 17 - Information */ /* Class 17 - Information */
QSI_DEF(SystemObjectInformation) QSI_DEF(SystemObjectInformation)