Author: dchapyshev
Date: Mon Aug 29 20:41:23 2016
New Revision: 72506
URL:
http://svn.reactos.org/svn/reactos?rev=72506&view=rev
Log:
[NTOS:EX]
- Blocking of the user buffer before obtaining information
- Use of ObpGetHandleObject macro for receiving ObjectHeader
- Remove duplicate NULL pointer check for HandleTableEntry
Modified:
trunk/reactos/ntoskrnl/ex/sysinfo.c
Modified: trunk/reactos/ntoskrnl/ex/sysinfo.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/ex/sysinfo.c?rev=…
==============================================================================
--- trunk/reactos/ntoskrnl/ex/sysinfo.c [iso-8859-1] (original)
+++ trunk/reactos/ntoskrnl/ex/sysinfo.c [iso-8859-1] Mon Aug 29 20:41:23 2016
@@ -1167,24 +1167,26 @@
/* Class 16 - Handle Information */
QSI_DEF(SystemHandleInformation)
{
+ PSYSTEM_HANDLE_INFORMATION HandleInformation;
+ KPROCESSOR_MODE PreviousMode;
PEPROCESS Process;
PEPROCESS SystemProcess;
ULONG CurrentSize;
ULONG NumberOfHandles = 0;
ULONG Index;
-
- PSYSTEM_HANDLE_INFORMATION HandleInformation =
- (PSYSTEM_HANDLE_INFORMATION) Buffer;
+ NTSTATUS Status;
+ PMDL Mdl;
DPRINT("NtQuerySystemInformation - SystemHandleInformation\n");
+ /* Check user's buffer size */
if (Size < sizeof(SYSTEM_HANDLE_INFORMATION))
{
*ReqSize = sizeof(SYSTEM_HANDLE_INFORMATION);
return STATUS_INFO_LENGTH_MISMATCH;
}
- /* First Calc Size from Count. */
+ /* Retrieve needed buffer size to hold the list of handles */
SystemProcess = PsGetNextProcess(NULL);
Process = SystemProcess;
@@ -1195,19 +1197,37 @@
}
while ((Process != SystemProcess) && (Process != NULL));
+ /* Dereference the process which was referenced by PsGetNextProcess */
if (Process != NULL) ObDereferenceObject(Process);
+ /* Calculate the current size of all handles */
CurrentSize = sizeof(SYSTEM_HANDLE_INFORMATION) +
((sizeof(SYSTEM_HANDLE_TABLE_ENTRY_INFO) * NumberOfHandles) -
(sizeof(SYSTEM_HANDLE_TABLE_ENTRY_INFO)));
+ *ReqSize = CurrentSize;
+
+ /* Check user's buffer size */
+ if (CurrentSize > Size) return STATUS_INFO_LENGTH_MISMATCH;
+
+ /* 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;
- *ReqSize = CurrentSize;
-
- if (CurrentSize > Size) return STATUS_INFO_LENGTH_MISMATCH;
-
- /* Now get Handles from all processes. */
+ /* Now get handles from all processes. */
SystemProcess = PsGetNextProcess(NULL);
Process = SystemProcess;
@@ -1226,16 +1246,13 @@
while ((HandleTableEntry = ExpLookupHandleTableEntry(Process->ObjectTable,
Handle)))
{
/* Validate the entry */
- if ((HandleTableEntry) &&
- (HandleTableEntry->Object) &&
+ if ((HandleTableEntry->Object) &&
(HandleTableEntry->NextFreeTableEntry != -2))
{
/* Lock the entry */
if (ExpLockHandleTableEntry(Process->ObjectTable, HandleTableEntry))
{
- POBJECT_HEADER ObjectHeader;
-
- ObjectHeader = (POBJECT_HEADER)(((ULONG_PTR)
HandleTableEntry->Object) & ~OBJ_HANDLE_ATTRIBUTES);
+ POBJECT_HEADER ObjectHeader = ObpGetHandleObject(HandleTableEntry);
/* Filling handle information */
HandleInformation->Handles[Index].UniqueProcessId =
(USHORT)(ULONG_PTR) Process->UniqueProcessId;
@@ -1257,25 +1274,21 @@
Handle.Value += sizeof(HANDLE);
}
- /* Leave the critical region and return callback result */
+ /* Leave the critical region */
KeLeaveCriticalRegion();
Process = PsGetNextProcess(Process);
}
while ((Process != SystemProcess) && (Process != NULL));
+ /* Dereference the process which was referenced by PsGetNextProcess */
if (Process != NULL) ObDereferenceObject(Process);
- return STATUS_SUCCESS;
-
-}
-/*
-SSI_DEF(SystemHandleInformation)
-{
-
- return STATUS_SUCCESS;
-}
-*/
+ /* Release the locked user buffer */
+ ExUnlockUserBuffer(Mdl);
+
+ return STATUS_SUCCESS;
+}
/* Class 17 - Information */
QSI_DEF(SystemObjectInformation)