support kernel handles, creating them is however not yet supported
Modified: trunk/reactos/ntoskrnl/include/internal/ob.h
Modified: trunk/reactos/ntoskrnl/ob/handle.c
Modified: trunk/reactos/ntoskrnl/ps/process.c
_____
Modified: trunk/reactos/ntoskrnl/include/internal/ob.h
--- trunk/reactos/ntoskrnl/include/internal/ob.h 2005-04-11
20:27:20 UTC (rev 14592)
+++ trunk/reactos/ntoskrnl/include/internal/ob.h 2005-04-11
21:50:15 UTC (rev 14593)
@@ -242,7 +242,15 @@
extern PDIRECTORY_OBJECT NameSpaceRoot;
extern POBJECT_TYPE ObSymbolicLinkType;
+extern PHANDLE_TABLE ObpKernelHandleTable;
+#define KERNEL_HANDLE_FLAG (1 << ((sizeof(HANDLE) * 8) - 1))
+#define ObIsKernelHandle(Handle, ProcessorMode)
\
+ (((ULONG_PTR)(Handle) & KERNEL_HANDLE_FLAG) &&
\
+ ((ProcessorMode) == KernelMode))
+#define ObKernelHandleToHandle(Handle)
\
+ (HANDLE)((ULONG_PTR)(Handle) & ~KERNEL_HANDLE_FLAG)
+
VOID ObpAddEntryDirectory(PDIRECTORY_OBJECT Parent,
POBJECT_HEADER Header,
PWSTR Name);
@@ -267,10 +275,6 @@
VOID ObDeleteHandleTable(struct _EPROCESS* Process);
NTSTATUS
-ObDeleteHandle(PEPROCESS Process,
- HANDLE Handle);
-
-NTSTATUS
ObpQueryHandleAttributes(HANDLE Handle,
POBJECT_HANDLE_ATTRIBUTE_INFORMATION
HandleInfo);
_____
Modified: trunk/reactos/ntoskrnl/ob/handle.c
--- trunk/reactos/ntoskrnl/ob/handle.c 2005-04-11 20:27:20 UTC (rev
14592)
+++ trunk/reactos/ntoskrnl/ob/handle.c 2005-04-11 21:50:15 UTC (rev
14593)
@@ -42,6 +42,10 @@
#define GENERIC_ANY (GENERIC_READ | GENERIC_WRITE | GENERIC_EXECUTE |
GENERIC_ALL)
+/* GLOBALS
*****************************************************************/
+
+PHANDLE_TABLE ObpKernelHandleTable = NULL;
+
/* FUNCTIONS
***************************************************************/
VOID
@@ -51,7 +55,7 @@
ObDeleteHandleTable(Process);
}
-VOID
+static VOID
ObpDecrementHandleCount(PVOID ObjectBody)
{
POBJECT_HEADER ObjectHeader = BODY_TO_HEADER(ObjectBody);
@@ -76,19 +80,28 @@
ObpQueryHandleAttributes(HANDLE Handle,
POBJECT_HANDLE_ATTRIBUTE_INFORMATION
HandleInfo)
{
- PEPROCESS Process;
+ PHANDLE_TABLE HandleTable;
PHANDLE_TABLE_ENTRY HandleTableEntry;
- LONG ExHandle = HANDLE_TO_EX_HANDLE(Handle);
+ LONG ExHandle;
PAGED_CODE();
DPRINT("ObpQueryHandleAttributes(Handle %x)\n", Handle);
+
+ if(ObIsKernelHandle(Handle, ExGetPreviousMode()))
+ {
+ HandleTable = ObpKernelHandleTable;
+ ExHandle = HANDLE_TO_EX_HANDLE(ObKernelHandleToHandle(Handle));
+ }
+ else
+ {
+ HandleTable = PsGetCurrentProcess()->ObjectTable;
+ ExHandle = HANDLE_TO_EX_HANDLE(Handle);
+ }
KeEnterCriticalRegion();
- Process = PsGetCurrentProcess();
-
- HandleTableEntry = ExMapHandleToPointer(Process->ObjectTable,
+ HandleTableEntry = ExMapHandleToPointer(HandleTable,
ExHandle);
if (HandleTableEntry == NULL)
{
@@ -99,7 +112,7 @@
HandleInfo->Inherit = (HandleTableEntry->u1.ObAttributes &
EX_HANDLE_ENTRY_INHERITABLE) != 0;
HandleInfo->ProtectFromClose = (HandleTableEntry->u1.ObAttributes &
EX_HANDLE_ENTRY_PROTECTFROMCLOSE) != 0;
- ExUnlockHandleTableEntry(Process->ObjectTable,
+ ExUnlockHandleTableEntry(HandleTable,
HandleTableEntry);
KeLeaveCriticalRegion();
@@ -112,19 +125,28 @@
ObpSetHandleAttributes(HANDLE Handle,
POBJECT_HANDLE_ATTRIBUTE_INFORMATION HandleInfo)
{
- PEPROCESS Process;
+ PHANDLE_TABLE HandleTable;
PHANDLE_TABLE_ENTRY HandleTableEntry;
- LONG ExHandle = HANDLE_TO_EX_HANDLE(Handle);
+ LONG ExHandle;
PAGED_CODE();
DPRINT("ObpSetHandleAttributes(Handle %x)\n", Handle);
- Process = PsGetCurrentProcess();
+ if(ObIsKernelHandle(Handle, ExGetPreviousMode()))
+ {
+ HandleTable = ObpKernelHandleTable;
+ ExHandle = HANDLE_TO_EX_HANDLE(ObKernelHandleToHandle(Handle));
+ }
+ else
+ {
+ HandleTable = PsGetCurrentProcess()->ObjectTable;
+ ExHandle = HANDLE_TO_EX_HANDLE(Handle);
+ }
KeEnterCriticalRegion();
- HandleTableEntry = ExMapHandleToPointer(Process->ObjectTable,
+ HandleTableEntry = ExMapHandleToPointer(HandleTable,
ExHandle);
if (HandleTableEntry == NULL)
{
@@ -144,7 +166,7 @@
/* FIXME: Do we need to set anything in the object header??? */
- ExUnlockHandleTableEntry(Process->ObjectTable,
+ ExUnlockHandleTableEntry(HandleTable,
HandleTableEntry);
KeLeaveCriticalRegion();
@@ -153,6 +175,54 @@
}
+static NTSTATUS
+ObpDeleteHandle(PHANDLE_TABLE HandleTable,
+ HANDLE Handle)
+{
+ PHANDLE_TABLE_ENTRY HandleEntry;
+ PVOID Body;
+ POBJECT_HEADER ObjectHeader;
+ LONG ExHandle = HANDLE_TO_EX_HANDLE(Handle);
+
+ PAGED_CODE();
+
+ DPRINT("ObpDeleteHandle(Handle %x)\n",Handle);
+
+ KeEnterCriticalRegion();
+
+ HandleEntry = ExMapHandleToPointer(HandleTable,
+ ExHandle);
+ if(HandleEntry != NULL)
+ {
+ if(HandleEntry->u1.ObAttributes &
EX_HANDLE_ENTRY_PROTECTFROMCLOSE)
+ {
+ ExUnlockHandleTableEntry(HandleTable,
+ HandleEntry);
+
+ KeLeaveCriticalRegion();
+
+ return STATUS_HANDLE_NOT_CLOSABLE;
+ }
+
+ ObjectHeader = EX_HTE_TO_HDR(HandleEntry);
+ Body = HEADER_TO_BODY(ObjectHeader);
+
+ ObpDecrementHandleCount(Body);
+
+ /* destroy and unlock the handle entry */
+ ExDestroyHandleByEntry(HandleTable,
+ HandleEntry,
+ ExHandle);
+
+ KeLeaveCriticalRegion();
+
+ return STATUS_SUCCESS;
+ }
+ KeLeaveCriticalRegion();
+ return STATUS_INVALID_HANDLE;
+}
+
+
NTSTATUS
ObDuplicateObject(PEPROCESS SourceProcess,
PEPROCESS TargetProcess,
@@ -162,19 +232,32 @@
BOOLEAN InheritHandle,
ULONG Options)
{
+ PHANDLE_TABLE SourceHandleTable;
PHANDLE_TABLE_ENTRY SourceHandleEntry;
HANDLE_TABLE_ENTRY NewHandleEntry;
PVOID ObjectBody;
POBJECT_HEADER ObjectHeader;
LONG ExTargetHandle;
- LONG ExSourceHandle = HANDLE_TO_EX_HANDLE(SourceHandle);
+ LONG ExSourceHandle;
ULONG NewHandleCount;
PAGED_CODE();
+ if(ObIsKernelHandle(SourceHandle, ExGetPreviousMode()))
+ {
+ SourceHandleTable = ObpKernelHandleTable;
+ SourceHandle = ObKernelHandleToHandle(SourceHandle);
+ }
+ else
+ {
+ SourceHandleTable = SourceProcess->ObjectTable;
+ }
+
+ ExSourceHandle = HANDLE_TO_EX_HANDLE(SourceHandle);
+
KeEnterCriticalRegion();
- SourceHandleEntry = ExMapHandleToPointer(SourceProcess->ObjectTable,
+ SourceHandleEntry = ExMapHandleToPointer(SourceHandleTable,
ExSourceHandle);
if (SourceHandleEntry == NULL)
{
@@ -219,7 +302,7 @@
NewHandleCount = InterlockedIncrement(&ObjectHeader->HandleCount);
ASSERT(NewHandleCount >= 2);
- ExUnlockHandleTableEntry(SourceProcess->ObjectTable,
+ ExUnlockHandleTableEntry(SourceHandleTable,
SourceHandleEntry);
KeLeaveCriticalRegion();
@@ -231,8 +314,8 @@
{
if (Options & DUPLICATE_CLOSE_SOURCE)
{
- ObDeleteHandle(SourceProcess,
- SourceHandle);
+ ObpDeleteHandle(SourceHandleTable,
+ SourceHandle);
}
ObDereferenceObject(ObjectBody);
@@ -384,8 +467,8 @@
if (Options & DUPLICATE_CLOSE_SOURCE)
{
- ObDeleteHandle(SourceProcess,
- SourceHandle);
+ ObpDeleteHandle(SourceProcess->ObjectTable,
+ SourceHandle);
}
}
}
@@ -464,10 +547,7 @@
ObjectHeader = EX_HTE_TO_HDR(HandleTableEntry);
if(InterlockedIncrement(&ObjectHeader->HandleCount) == 1)
{
- ObReferenceObjectByPointer(HEADER_TO_BODY(ObjectHeader),
- 0,
- NULL,
- UserMode);
+ ObReferenceObject(HEADER_TO_BODY(ObjectHeader));
}
}
@@ -504,54 +584,6 @@
NTSTATUS
-ObDeleteHandle(PEPROCESS Process,
- HANDLE Handle)
-{
- PHANDLE_TABLE_ENTRY HandleEntry;
- PVOID Body;
- POBJECT_HEADER ObjectHeader;
- LONG ExHandle = HANDLE_TO_EX_HANDLE(Handle);
-
- PAGED_CODE();
-
- DPRINT("ObDeleteHandle(Handle %x)\n",Handle);
-
- KeEnterCriticalRegion();
-
- HandleEntry = ExMapHandleToPointer(Process->ObjectTable,
- ExHandle);
- if(HandleEntry != NULL)
- {
- if(HandleEntry->u1.ObAttributes &
EX_HANDLE_ENTRY_PROTECTFROMCLOSE)
- {
- ExUnlockHandleTableEntry(Process->ObjectTable,
- HandleEntry);
-
- KeLeaveCriticalRegion();
-
- return STATUS_HANDLE_NOT_CLOSABLE;
- }
-
- ObjectHeader = EX_HTE_TO_HDR(HandleEntry);
- Body = HEADER_TO_BODY(ObjectHeader);
-
- ObpDecrementHandleCount(Body);
-
- /* destroy and unlock the handle entry */
- ExDestroyHandleByEntry(Process->ObjectTable,
- HandleEntry,
- ExHandle);
-
- KeLeaveCriticalRegion();
-
- return STATUS_SUCCESS;
- }
- KeLeaveCriticalRegion();
- return STATUS_INVALID_HANDLE;
-}
-
-
-NTSTATUS
ObCreateHandle(PEPROCESS Process,
PVOID ObjectBody,
ACCESS_MASK GrantedAccess,
@@ -685,11 +717,11 @@
{
PHANDLE_TABLE_ENTRY HandleEntry;
POBJECT_HEADER ObjectHeader;
+ PHANDLE_TABLE HandleTable;
PVOID ObjectBody;
ACCESS_MASK GrantedAccess;
ULONG Attributes;
- NTSTATUS Status;
- LONG ExHandle = HANDLE_TO_EX_HANDLE(Handle);
+ LONG ExHandle;
PAGED_CODE();
@@ -703,14 +735,9 @@
if (Handle == NtCurrentProcess() &&
(ObjectType == PsProcessType || ObjectType == NULL))
{
- Status = ObReferenceObjectByPointer(PsGetCurrentProcess(),
- PROCESS_ALL_ACCESS,
- PsProcessType,
- UserMode);
- if (! NT_SUCCESS(Status))
- {
- return Status;
- }
+ PEPROCESS CurrentProcess = PsGetCurrentProcess();
+
+ ObReferenceObject(CurrentProcess);
if (HandleInformation != NULL)
{
@@ -718,8 +745,8 @@
HandleInformation->GrantedAccess = PROCESS_ALL_ACCESS;
}
- *Object = PsGetCurrentProcess();
- DPRINT("Referencing current process %x\n",
PsGetCurrentProcess());
+ *Object = CurrentProcess;
+ DPRINT("Referencing current process %x\n", CurrentProcess);
return STATUS_SUCCESS;
}
else if (Handle == NtCurrentProcess())
@@ -731,14 +758,9 @@
if (Handle == NtCurrentThread() &&
(ObjectType == PsThreadType || ObjectType == NULL))
{
- Status = ObReferenceObjectByPointer(PsGetCurrentThread(),
- THREAD_ALL_ACCESS,
- PsThreadType,
- UserMode);
- if (! NT_SUCCESS(Status))
- {
- return Status;
- }
+ PETHREAD CurrentThread = PsGetCurrentThread();
+
+ ObReferenceObject(CurrentThread);
if (HandleInformation != NULL)
{
@@ -746,7 +768,7 @@
HandleInformation->GrantedAccess = THREAD_ALL_ACCESS;
}
- *Object = PsGetCurrentThread();
+ *Object = CurrentThread;
CHECKPOINT;
return STATUS_SUCCESS;
}
@@ -763,9 +785,20 @@
DesiredAccess |= GENERIC_ALL;
}
+ if(ObIsKernelHandle(Handle, AccessMode))
+ {
+ HandleTable = ObpKernelHandleTable;
+ ExHandle = HANDLE_TO_EX_HANDLE(ObKernelHandleToHandle(Handle));
+ }
+ else
+ {
+ HandleTable = PsGetCurrentProcess()->ObjectTable;
+ ExHandle = HANDLE_TO_EX_HANDLE(Handle);
+ }
+
KeEnterCriticalRegion();
- HandleEntry =
ExMapHandleToPointer(PsGetCurrentProcess()->ObjectTable,
+ HandleEntry = ExMapHandleToPointer(HandleTable,
ExHandle);
if (HandleEntry == NULL)
{
@@ -777,13 +810,13 @@
ObjectHeader = EX_HTE_TO_HDR(HandleEntry);
ObjectBody = HEADER_TO_BODY(ObjectHeader);
- DPRINT("locked1: ObjectHeader: 0x%x [HT:0x%x]\n", ObjectHeader,
PsGetCurrentProcess()->ObjectTable);
+ DPRINT("locked1: ObjectHeader: 0x%x [HT:0x%x]\n", ObjectHeader,
HandleTable);
if (ObjectType != NULL && ObjectType != ObjectHeader->ObjectType)
{
DPRINT("ObjectType mismatch: %wZ vs %wZ (handle 0x%x)\n",
&ObjectType->TypeName, ObjectHeader->ObjectType ?
&ObjectHeader->ObjectType->TypeName : NULL, Handle);
- ExUnlockHandleTableEntry(PsGetCurrentProcess()->ObjectTable,
+ ExUnlockHandleTableEntry(HandleTable,
HandleEntry);
KeLeaveCriticalRegion();
@@ -804,7 +837,7 @@
rights than the handle can grant */
if(AccessMode != KernelMode && (~GrantedAccess & DesiredAccess))
{
- ExUnlockHandleTableEntry(PsGetCurrentProcess()->ObjectTable,
+ ExUnlockHandleTableEntry(HandleTable,
HandleEntry);
KeLeaveCriticalRegion();
@@ -814,15 +847,13 @@
return(STATUS_ACCESS_DENIED);
}
- ObReferenceObjectByPointer(ObjectBody,
- 0,
- NULL,
- UserMode);
+ ObReferenceObject(ObjectBody);
+
Attributes = HandleEntry->u1.ObAttributes &
(EX_HANDLE_ENTRY_PROTECTFROMCLOSE |
EX_HANDLE_ENTRY_INHERITABLE |
EX_HANDLE_ENTRY_AUDITONCLOSE);
- ExUnlockHandleTableEntry(PsGetCurrentProcess()->ObjectTable,
+ ExUnlockHandleTableEntry(HandleTable,
HandleEntry);
KeLeaveCriticalRegion();
@@ -858,16 +889,30 @@
NTSTATUS STDCALL
NtClose(IN HANDLE Handle)
{
+ PHANDLE_TABLE HandleTable;
NTSTATUS Status;
PAGED_CODE();
- Status = ObDeleteHandle(PsGetCurrentProcess(),
- Handle);
+ if(ObIsKernelHandle(Handle, ExGetPreviousMode()))
+ {
+ HandleTable = ObpKernelHandleTable;
+ Handle = ObKernelHandleToHandle(Handle);
+ }
+ else
+ {
+ HandleTable = PsGetCurrentProcess()->ObjectTable;
+ }
+
+ Status = ObpDeleteHandle(HandleTable,
+ Handle);
if (!NT_SUCCESS(Status))
{
-
if(((PEPROCESS)(KeGetCurrentThread()->ApcState.Process))->ExceptionPort)
+ if((ExGetPreviousMode() != KernelMode) &&
+ (PsGetCurrentProcess()->ExceptionPort))
+ {
KeRaiseUserException(Status);
+ }
return Status;
}
_____
Modified: trunk/reactos/ntoskrnl/ps/process.c
--- trunk/reactos/ntoskrnl/ps/process.c 2005-04-11 20:27:20 UTC (rev
14592)
+++ trunk/reactos/ntoskrnl/ps/process.c 2005-04-11 21:50:15 UTC (rev
14593)
@@ -286,6 +286,7 @@
PsInitClientIDManagment();
ObCreateHandleTable(NULL, FALSE, PsInitialSystemProcess);
+ ObpKernelHandleTable = PsInitialSystemProcess->ObjectTable;
Status = PsCreateCidHandle(PsInitialSystemProcess,
PsProcessType,