- support for kernel handles - attach to owning process before accessing the handle table if necessary Modified: trunk/reactos/ntoskrnl/cm/ntfunc.c Modified: trunk/reactos/ntoskrnl/ex/init.c Modified: trunk/reactos/ntoskrnl/include/internal/ob.h Modified: trunk/reactos/ntoskrnl/ob/handle.c Modified: trunk/reactos/ntoskrnl/ob/namespc.c Modified: trunk/reactos/ntoskrnl/ob/object.c Modified: trunk/reactos/ntoskrnl/ps/security.c Modified: trunk/reactos/ntoskrnl/se/priv.c _____
Modified: trunk/reactos/ntoskrnl/cm/ntfunc.c --- trunk/reactos/ntoskrnl/cm/ntfunc.c 2005-12-10 15:53:27 UTC (rev 20037) +++ trunk/reactos/ntoskrnl/cm/ntfunc.c 2005-12-10 16:38:04 UTC (rev 20038) @@ -247,7 +247,7 @@
if (!NT_SUCCESS(Status)) { DPRINT1("ObpCaptureObjectAttributes() failed (Status %lx)\n", Status); - goto Cleanup; + return Status; }
PostCreateKeyInfo.CompleteName = &ObjectName; @@ -255,7 +255,6 @@ Status = CmiCallRegisteredCallbacks(RegNtPreCreateKey, &PreCreateKeyInfo); if (!NT_SUCCESS(Status)) { - ObpReleaseCapturedAttributes(&ObjectCreateInfo); goto Cleanup; }
@@ -264,7 +263,6 @@ (PVOID*)&Object, &RemainingPath, CmiKeyType); - ObpReleaseCapturedAttributes(&ObjectCreateInfo); if (!NT_SUCCESS(Status)) { PostCreateKeyInfo.Object = NULL; @@ -291,11 +289,10 @@ goto Cleanup; }
- Status = ObpCreateHandle(PsGetCurrentProcess(), - Object, - DesiredAccess, - TRUE, - &hKey); + Status = ObpCreateHandle(Object, + DesiredAccess, + ObjectCreateInfo.Attributes, + &hKey);
if (!NT_SUCCESS(Status)) DPRINT1("ObpCreateHandle failed Status 0x%x\n", Status); @@ -466,6 +463,7 @@ _SEH_END;
Cleanup: + ObpReleaseCapturedAttributes(&ObjectCreateInfo); if (Class != NULL) { ReleaseCapturedUnicodeString(&CapturedClass, @@ -1332,7 +1330,6 @@ (PVOID*)&Object, &RemainingPath, CmiKeyType); - ObpReleaseCapturedAttributes(&ObjectCreateInfo); if (!NT_SUCCESS(Status)) { DPRINT("CmpFindObject() returned 0x%08lx\n", Status); @@ -1363,17 +1360,17 @@ goto openkey_cleanup; }
- Status = ObpCreateHandle(PsGetCurrentProcess(), - Object, - DesiredAccess, - TRUE, - &hKey); + Status = ObpCreateHandle(Object, + DesiredAccess, + ObjectCreateInfo.Attributes, + &hKey);
if (!NT_SUCCESS(Status)) hKey = NULL;
openkey_cleanup:
+ ObpReleaseCapturedAttributes(&ObjectCreateInfo); PostOpenKeyInfo.Object = NT_SUCCESS(Status) ? (PVOID)Object : NULL; PostOpenKeyInfo.Status = Status; CmiCallRegisteredCallbacks (RegNtPostOpenKey, &PostOpenKeyInfo); _____
Modified: trunk/reactos/ntoskrnl/ex/init.c --- trunk/reactos/ntoskrnl/ex/init.c 2005-12-10 15:53:27 UTC (rev 20037) +++ trunk/reactos/ntoskrnl/ex/init.c 2005-12-10 16:38:04 UTC (rev 20038) @@ -429,10 +429,9 @@
RTL_USER_PROCESS_INFORMATION Info;
/* Create a handle to the process */ - Status = ObpCreateHandle(PsGetCurrentProcess(), - PsInitialSystemProcess, + Status = ObpCreateHandle(PsInitialSystemProcess, PROCESS_CREATE_PROCESS | PROCESS_CREATE_THREAD | PROCESS_QUERY_INFORMATION, - FALSE, + OBJ_KERNEL_HANDLE, &SystemProcessHandle); if(!NT_SUCCESS(Status)) { _____
Modified: trunk/reactos/ntoskrnl/include/internal/ob.h --- trunk/reactos/ntoskrnl/include/internal/ob.h 2005-12-10 15:53:27 UTC (rev 20037) +++ trunk/reactos/ntoskrnl/include/internal/ob.h 2005-12-10 16:38:04 UTC (rev 20038) @@ -51,6 +51,8 @@
((ProcessorMode) == KernelMode)) #define ObKernelHandleToHandle(Handle) \ (HANDLE)((ULONG_PTR)(Handle) & ~KERNEL_HANDLE_FLAG) +#define ObMarkHandleAsKernelHandle(Handle) \ + (HANDLE)((ULONG_PTR)(Handle) | KERNEL_HANDLE_FLAG)
extern PDIRECTORY_OBJECT NameSpaceRoot; extern POBJECT_TYPE ObSymbolicLinkType; @@ -75,10 +77,9 @@ NTSTATUS NTAPI ObpCreateHandle( - struct _EPROCESS* Process, PVOID ObjectBody, ACCESS_MASK GrantedAccess, - BOOLEAN Inherit, + ULONG HandleAttributes, PHANDLE Handle );
@@ -134,7 +135,7 @@ HANDLE SourceHandle, PHANDLE TargetHandle, ACCESS_MASK DesiredAccess, - BOOLEAN InheritHandle, + ULONG HandleAttributes, ULONG Options );
_____
Modified: trunk/reactos/ntoskrnl/ob/handle.c --- trunk/reactos/ntoskrnl/ob/handle.c 2005-12-10 15:53:27 UTC (rev 20037) +++ trunk/reactos/ntoskrnl/ob/handle.c 2005-12-10 16:38:04 UTC (rev 20038) @@ -89,42 +89,57 @@
ObpQueryHandleAttributes(HANDLE Handle, POBJECT_HANDLE_ATTRIBUTE_INFORMATION HandleInfo) { - PHANDLE_TABLE HandleTable; PHANDLE_TABLE_ENTRY HandleTableEntry; + PEPROCESS Process, CurrentProcess; + KAPC_STATE ApcState; + BOOLEAN AttachedToProcess = FALSE; + NTSTATUS Status = STATUS_SUCCESS;
PAGED_CODE();
- DPRINT("ObpQueryHandleAttributes(Handle %x)\n", Handle); + DPRINT("ObpQueryHandleAttributes(Handle %p)\n", Handle); + CurrentProcess = PsGetCurrentProcess();
+ KeEnterCriticalRegion(); + if(ObIsKernelHandle(Handle, ExGetPreviousMode())) { - HandleTable = ObpKernelHandleTable; + Process = PsInitialSystemProcess; Handle = ObKernelHandleToHandle(Handle); + + if (Process != CurrentProcess) + { + KeStackAttachProcess(&Process->Pcb, + &ApcState); + AttachedToProcess = TRUE; + } } else { - HandleTable = PsGetCurrentProcess()->ObjectTable; + Process = CurrentProcess; }
- KeEnterCriticalRegion(); - - HandleTableEntry = ExMapHandleToPointer(HandleTable, + HandleTableEntry = ExMapHandleToPointer(Process->ObjectTable, Handle); - if (HandleTableEntry == NULL) - { - KeLeaveCriticalRegion(); - return STATUS_INVALID_HANDLE; - } + if (HandleTableEntry != NULL) + { + HandleInfo->Inherit = (HandleTableEntry->u1.ObAttributes & EX_HANDLE_ENTRY_INHERITABLE) != 0; + HandleInfo->ProtectFromClose = (HandleTableEntry->u1.ObAttributes & EX_HANDLE_ENTRY_PROTECTFROMCLOSE) != 0;
- HandleInfo->Inherit = (HandleTableEntry->u1.ObAttributes & EX_HANDLE_ENTRY_INHERITABLE) != 0; - HandleInfo->ProtectFromClose = (HandleTableEntry->u1.ObAttributes & EX_HANDLE_ENTRY_PROTECTFROMCLOSE) != 0; + ExUnlockHandleTableEntry(Process->ObjectTable, + HandleTableEntry); + } + else + Status = STATUS_INVALID_HANDLE;
- ExUnlockHandleTableEntry(HandleTable, - HandleTableEntry); + if (AttachedToProcess) + { + KeUnstackDetachProcess(&ApcState); + }
KeLeaveCriticalRegion();
- return STATUS_SUCCESS; + return Status; }
@@ -133,75 +148,92 @@ ObpSetHandleAttributes(HANDLE Handle, POBJECT_HANDLE_ATTRIBUTE_INFORMATION HandleInfo) { - PHANDLE_TABLE HandleTable; PHANDLE_TABLE_ENTRY HandleTableEntry; + PEPROCESS Process, CurrentProcess; + KAPC_STATE ApcState; + BOOLEAN AttachedToProcess = FALSE; + NTSTATUS Status = STATUS_SUCCESS;
PAGED_CODE();
- DPRINT("ObpSetHandleAttributes(Handle %x)\n", Handle); + DPRINT("ObpSetHandleAttributes(Handle %p)\n", Handle); + CurrentProcess = PsGetCurrentProcess();
+ KeEnterCriticalRegion(); + if(ObIsKernelHandle(Handle, ExGetPreviousMode())) { - HandleTable = ObpKernelHandleTable; + Process = PsInitialSystemProcess; Handle = ObKernelHandleToHandle(Handle); + + if (Process != CurrentProcess) + { + KeStackAttachProcess(&Process->Pcb, + &ApcState); + AttachedToProcess = TRUE; + } } else { - HandleTable = PsGetCurrentProcess()->ObjectTable; + Process = CurrentProcess; }
- KeEnterCriticalRegion(); - - HandleTableEntry = ExMapHandleToPointer(HandleTable, + HandleTableEntry = ExMapHandleToPointer(Process->ObjectTable, Handle); - if (HandleTableEntry == NULL) - { - KeLeaveCriticalRegion(); - return STATUS_INVALID_HANDLE; - } + if (HandleTableEntry != NULL) + { + if (HandleInfo->Inherit) + HandleTableEntry->u1.ObAttributes |= EX_HANDLE_ENTRY_INHERITABLE; + else + HandleTableEntry->u1.ObAttributes &= ~EX_HANDLE_ENTRY_INHERITABLE;
- if (HandleInfo->Inherit) - HandleTableEntry->u1.ObAttributes |= EX_HANDLE_ENTRY_INHERITABLE; - else - HandleTableEntry->u1.ObAttributes &= ~EX_HANDLE_ENTRY_INHERITABLE; + if (HandleInfo->ProtectFromClose) + HandleTableEntry->u1.ObAttributes |= EX_HANDLE_ENTRY_PROTECTFROMCLOSE; + else + HandleTableEntry->u1.ObAttributes &= ~EX_HANDLE_ENTRY_PROTECTFROMCLOSE;
- if (HandleInfo->ProtectFromClose) - HandleTableEntry->u1.ObAttributes |= EX_HANDLE_ENTRY_PROTECTFROMCLOSE; + /* FIXME: Do we need to set anything in the object header??? */ + + ExUnlockHandleTableEntry(Process->ObjectTable, + HandleTableEntry); + } else - HandleTableEntry->u1.ObAttributes &= ~EX_HANDLE_ENTRY_PROTECTFROMCLOSE; + Status = STATUS_INVALID_HANDLE;
- /* FIXME: Do we need to set anything in the object header??? */ + if (AttachedToProcess) + { + KeUnstackDetachProcess(&ApcState); + }
- ExUnlockHandleTableEntry(HandleTable, - HandleTableEntry); - KeLeaveCriticalRegion();
- return STATUS_SUCCESS; + return Status; }
static NTSTATUS -ObpDeleteHandle(PHANDLE_TABLE HandleTable, - HANDLE Handle) +ObpDeleteHandle(HANDLE Handle) { PHANDLE_TABLE_ENTRY HandleEntry; PVOID Body; POBJECT_HEADER ObjectHeader; + PHANDLE_TABLE ObjectTable;
PAGED_CODE();
- DPRINT("ObpDeleteHandle(Handle %x)\n",Handle); + DPRINT("ObpDeleteHandle(Handle %p)\n",Handle);
+ ObjectTable = PsGetCurrentProcess()->ObjectTable; + KeEnterCriticalRegion();
- HandleEntry = ExMapHandleToPointer(HandleTable, + HandleEntry = ExMapHandleToPointer(ObjectTable, Handle); if(HandleEntry != NULL) { if(HandleEntry->u1.ObAttributes & EX_HANDLE_ENTRY_PROTECTFROMCLOSE) { - ExUnlockHandleTableEntry(HandleTable, + ExUnlockHandleTableEntry(ObjectTable, HandleEntry);
KeLeaveCriticalRegion(); @@ -212,13 +244,13 @@ ObjectHeader = EX_HTE_TO_HDR(HandleEntry); Body = &ObjectHeader->Body;
- ObpDecrementHandleCount(Body); - - /* destroy and unlock the handle entry */ - ExDestroyHandleByEntry(HandleTable, + /* destroy and unlock the handle entry */ + ExDestroyHandleByEntry(ObjectTable, HandleEntry, Handle);
+ ObpDecrementHandleCount(Body); + KeLeaveCriticalRegion();
return STATUS_SUCCESS; @@ -235,35 +267,48 @@ HANDLE SourceHandle, PHANDLE TargetHandle, ACCESS_MASK DesiredAccess, - BOOLEAN InheritHandle, + ULONG HandleAttributes, ULONG Options) { - PHANDLE_TABLE SourceHandleTable; PHANDLE_TABLE_ENTRY SourceHandleEntry; HANDLE_TABLE_ENTRY NewHandleEntry; + BOOLEAN AttachedToProcess = FALSE; PVOID ObjectBody; POBJECT_HEADER ObjectHeader; ULONG NewHandleCount; HANDLE NewTargetHandle; + PEPROCESS CurrentProcess; + KAPC_STATE ApcState; + NTSTATUS Status = STATUS_SUCCESS;
PAGED_CODE();
- if(ObIsKernelHandle(SourceHandle, ExGetPreviousMode())) + if(SourceProcess == NULL || + ObIsKernelHandle(SourceHandle, ExGetPreviousMode())) { - SourceHandleTable = ObpKernelHandleTable; + SourceProcess = PsInitialSystemProcess; SourceHandle = ObKernelHandleToHandle(SourceHandle); } - else - { - SourceHandleTable = SourceProcess->ObjectTable; - }
+ CurrentProcess = PsGetCurrentProcess(); + KeEnterCriticalRegion();
- SourceHandleEntry = ExMapHandleToPointer(SourceHandleTable, + if (SourceProcess != CurrentProcess) + { + KeStackAttachProcess(&SourceProcess->Pcb, + &ApcState); + AttachedToProcess = TRUE; + } + SourceHandleEntry = ExMapHandleToPointer(SourceProcess->ObjectTable, SourceHandle); if (SourceHandleEntry == NULL) { + if (AttachedToProcess) + { + KeUnstackDetachProcess(&ApcState); + } + KeLeaveCriticalRegion(); return STATUS_INVALID_HANDLE; } @@ -272,7 +317,7 @@ ObjectBody = &ObjectHeader->Body;
NewHandleEntry.u1.Object = SourceHandleEntry->u1.Object; - if(InheritHandle) + if(HandleAttributes & OBJ_INHERIT) NewHandleEntry.u1.ObAttributes |= EX_HANDLE_ENTRY_INHERITABLE; else NewHandleEntry.u1.ObAttributes &= ~EX_HANDLE_ENTRY_INHERITABLE; @@ -305,27 +350,54 @@ NewHandleCount = InterlockedIncrement(&ObjectHeader->HandleCount); ASSERT(NewHandleCount >= 2);
- ExUnlockHandleTableEntry(SourceHandleTable, + ExUnlockHandleTableEntry(SourceProcess->ObjectTable, SourceHandleEntry);
- KeLeaveCriticalRegion(); + if (AttachedToProcess) + { + KeUnstackDetachProcess(&ApcState); + AttachedToProcess = FALSE; + }
+ if (TargetProcess != CurrentProcess) + { + KeStackAttachProcess(&TargetProcess->Pcb, + &ApcState); + AttachedToProcess = TRUE; + } + /* attempt to create the new handle */ NewTargetHandle = ExCreateHandle(TargetProcess->ObjectTable, &NewHandleEntry); + if (AttachedToProcess) + { + KeUnstackDetachProcess(&ApcState); + AttachedToProcess = FALSE; + } + if (NewTargetHandle != NULL) { if (Options & DUPLICATE_CLOSE_SOURCE) { - ObpDeleteHandle(SourceHandleTable, - SourceHandle); + if (SourceProcess != CurrentProcess) + { + KeStackAttachProcess(&SourceProcess->Pcb, + &ApcState); + AttachedToProcess = TRUE; + } + + /* delete the source handle */ + ObpDeleteHandle(SourceHandle); + + if (AttachedToProcess) + { + KeUnstackDetachProcess(&ApcState); + } }
ObDereferenceObject(ObjectBody);
*TargetHandle = NewTargetHandle; - - return STATUS_SUCCESS; } else { @@ -337,8 +409,12 @@ }
ObDereferenceObject(ObjectBody); - return STATUS_UNSUCCESSFUL; + Status = STATUS_UNSUCCESSFUL; } + + KeLeaveCriticalRegion(); + + return Status; }
/* @@ -350,7 +426,7 @@ IN HANDLE TargetProcessHandle, OUT PHANDLE TargetHandle OPTIONAL, IN ACCESS_MASK DesiredAccess, - IN ULONG InheritHandle, + IN ULONG HandleAttributes, IN ULONG Options) /* * FUNCTION: Copies a handle from one process space to another @@ -364,8 +440,7 @@ * TargetHandle (OUT) = Caller should supply storage for the * duplicated handle. * DesiredAccess = The desired access to the handle. - * InheritHandle = Indicates wheter the new handle will be inheritable - * or not. + * HandleAttributes = The desired handle attributes. * Options = Specifies special actions upon duplicating the handle. * Can be one of the values DUPLICATE_CLOSE_SOURCE | * DUPLICATE_SAME_ACCESS. DUPLICATE_CLOSE_SOURCE specifies @@ -379,8 +454,11 @@ { PEPROCESS SourceProcess; PEPROCESS TargetProcess; + PEPROCESS CurrentProcess; HANDLE hTarget; + BOOLEAN AttachedToProcess = FALSE; KPROCESSOR_MODE PreviousMode; + KAPC_STATE ApcState; NTSTATUS Status = STATUS_SUCCESS;
PAGED_CODE(); @@ -428,6 +506,8 @@ return(Status); }
+ CurrentProcess = PsGetCurrentProcess(); + /* Check for magic handle first */ if (SourceHandle == NtCurrentThread() || SourceHandle == NtCurrentProcess()) @@ -458,18 +538,42 @@ &ObjectType->TypeInfo.GenericMapping); } } - Status = ObpCreateHandle(TargetProcess, - ObjectBody, + + if (TargetProcess != CurrentProcess) + { + KeStackAttachProcess(&TargetProcess->Pcb, + &ApcState); + AttachedToProcess = TRUE; + } + + Status = ObpCreateHandle(ObjectBody, DesiredAccess, - InheritHandle, + HandleAttributes, &hTarget);
+ if (AttachedToProcess) + { + KeUnstackDetachProcess(&ApcState); + AttachedToProcess = FALSE; + } + ObDereferenceObject(ObjectBody);
if (Options & DUPLICATE_CLOSE_SOURCE) { - ObpDeleteHandle(SourceProcess->ObjectTable, - SourceHandle); + if (SourceProcess != CurrentProcess) + { + KeStackAttachProcess(&SourceProcess->Pcb, + &ApcState); + AttachedToProcess = TRUE; + } + + ObpDeleteHandle(SourceHandle); + + if (AttachedToProcess) + { + KeUnstackDetachProcess(&ApcState); + } } } } @@ -480,7 +584,7 @@ SourceHandle, &hTarget, DesiredAccess, - InheritHandle, + HandleAttributes, Options); }
@@ -591,11 +695,10 @@
NTSTATUS NTAPI -ObpCreateHandle(PEPROCESS Process, - PVOID ObjectBody, - ACCESS_MASK GrantedAccess, - BOOLEAN Inherit, - PHANDLE HandleReturn) +ObpCreateHandle(PVOID ObjectBody, + ACCESS_MASK GrantedAccess, + ULONG HandleAttributes, + PHANDLE HandleReturn) /* * FUNCTION: Add a handle referencing an object * ARGUMENTS: @@ -605,18 +708,23 @@ */ { HANDLE_TABLE_ENTRY NewEntry; + PEPROCESS Process, CurrentProcess; POBJECT_HEADER ObjectHeader; HANDLE Handle; + KAPC_STATE ApcState; + BOOLEAN AttachedToProcess = FALSE;
PAGED_CODE();
- DPRINT("ObpCreateHandle(Process %x, obj %x)\n",Process,ObjectBody); + DPRINT("ObpCreateHandle(obj %p)\n",ObjectBody);
- ASSERT(Process); ASSERT(ObjectBody);
+ CurrentProcess = PsGetCurrentProcess(); + ObjectHeader = BODY_TO_HEADER(ObjectBody);
+ /* check that this is a valid kernel pointer */ ASSERT((ULONG_PTR)ObjectHeader & EX_HANDLE_ENTRY_LOCKED);
if (GrantedAccess & MAXIMUM_ALLOWED) @@ -632,23 +740,49 @@ }
NewEntry.u1.Object = ObjectHeader; - if(Inherit) + if(HandleAttributes & OBJ_INHERIT) NewEntry.u1.ObAttributes |= EX_HANDLE_ENTRY_INHERITABLE; else NewEntry.u1.ObAttributes &= ~EX_HANDLE_ENTRY_INHERITABLE; NewEntry.u2.GrantedAccess = GrantedAccess;
+ if ((HandleAttributes & OBJ_KERNEL_HANDLE) && + ExGetPreviousMode == KernelMode) + { + Process = PsInitialSystemProcess; + if (Process != CurrentProcess) + { + KeStackAttachProcess(&Process->Pcb, + &ApcState); + AttachedToProcess = TRUE; + } + } + else + { + Process = CurrentProcess; + /* mask out the OBJ_KERNEL_HANDLE attribute */ + HandleAttributes &= ~OBJ_KERNEL_HANDLE; + } + Handle = ExCreateHandle(Process->ObjectTable, &NewEntry); - DPRINT("ObCreateHandle(0x%x)==0x%x [HT:0x%x]\n", ObjectHeader, Handle, Process->ObjectTable); + + if (AttachedToProcess) + { + KeUnstackDetachProcess(&ApcState); + } + if(Handle != NULL) { + if (HandleAttributes & OBJ_KERNEL_HANDLE) + { + /* mark the handle value */ + Handle = ObMarkHandleAsKernelHandle(Handle); + } + if(InterlockedIncrement(&ObjectHeader->HandleCount) == 1) { - ObReferenceObjectByPointer(ObjectBody, - 0, - NULL, - UserMode); + ObReferenceObject(ObjectBody); }
*HandleReturn = Handle; @@ -668,16 +802,34 @@ OUT PBOOLEAN GenerateOnClose) { PHANDLE_TABLE_ENTRY HandleEntry; - PEPROCESS Process; + PEPROCESS Process, CurrentProcess; + KAPC_STATE ApcState; + BOOLEAN AttachedToProcess = FALSE; + NTSTATUS Status = STATUS_SUCCESS;
PAGED_CODE();
- DPRINT("ObQueryObjectAuditingByHandle(Handle %x)\n", Handle); + DPRINT("ObQueryObjectAuditingByHandle(Handle %p)\n", Handle);
- Process = PsGetCurrentProcess(); + CurrentProcess = PsGetCurrentProcess();
KeEnterCriticalRegion();
+ if(ObIsKernelHandle(Handle, ExGetPreviousMode())) + { + Process = PsInitialSystemProcess; + Handle = ObKernelHandleToHandle(Handle); + + if (Process != CurrentProcess) + { + KeStackAttachProcess(&Process->Pcb, + &ApcState); + AttachedToProcess = TRUE; + } + } + else + Process = CurrentProcess; + HandleEntry = ExMapHandleToPointer(Process->ObjectTable, Handle); if(HandleEntry != NULL) @@ -686,15 +838,18 @@
ExUnlockHandleTableEntry(Process->ObjectTable, HandleEntry); + } + else + Status = STATUS_INVALID_HANDLE;
- KeLeaveCriticalRegion(); - - return STATUS_SUCCESS; + if (AttachedToProcess) + { + KeUnstackDetachProcess(&ApcState); }
KeLeaveCriticalRegion();
- return STATUS_INVALID_HANDLE; + return Status; }
@@ -723,29 +878,32 @@ { PHANDLE_TABLE_ENTRY HandleEntry; POBJECT_HEADER ObjectHeader; - PHANDLE_TABLE HandleTable; PVOID ObjectBody; ACCESS_MASK GrantedAccess; ULONG Attributes; + PEPROCESS CurrentProcess, Process; + BOOLEAN AttachedToProcess = FALSE; + KAPC_STATE ApcState;
PAGED_CODE();
- DPRINT("ObReferenceObjectByHandle(Handle %x, DesiredAccess %x, " - "ObjectType %x, AccessMode %d, Object %x)\n",Handle,DesiredAccess, + DPRINT("ObReferenceObjectByHandle(Handle %p, DesiredAccess %x, " + "ObjectType %p, AccessMode %d, Object %p)\n",Handle,DesiredAccess, ObjectType,AccessMode,Object);
if (Handle == NULL) { return STATUS_INVALID_HANDLE; } + + CurrentProcess = PsGetCurrentProcess(); + /* * Handle special handle names */ if (Handle == NtCurrentProcess() && (ObjectType == PsProcessType || ObjectType == NULL)) { - PEPROCESS CurrentProcess = PsGetCurrentProcess(); - ObReferenceObject(CurrentProcess);
if (HandleInformation != NULL) @@ -755,7 +913,7 @@ }
*Object = CurrentProcess; - DPRINT("Referencing current process %x\n", CurrentProcess); + DPRINT("Referencing current process %p\n", CurrentProcess); return STATUS_SUCCESS; } else if (Handle == NtCurrentProcess()) @@ -796,37 +954,53 @@
if(ObIsKernelHandle(Handle, AccessMode)) { - HandleTable = ObpKernelHandleTable; + Process = PsInitialSystemProcess; Handle = ObKernelHandleToHandle(Handle); } else { - HandleTable = PsGetCurrentProcess()->ObjectTable; + Process = CurrentProcess; }
KeEnterCriticalRegion();
- HandleEntry = ExMapHandleToPointer(HandleTable, + if (Process != CurrentProcess) + { + KeStackAttachProcess(&Process->Pcb, + &ApcState); + AttachedToProcess = TRUE; + } + + HandleEntry = ExMapHandleToPointer(Process->ObjectTable, Handle); if (HandleEntry == NULL) { + if (AttachedToProcess) + { + KeUnstackDetachProcess(&ApcState); + } KeLeaveCriticalRegion(); - DPRINT("ExMapHandleToPointer() failed for handle 0x%x\n", Handle); + DPRINT("ExMapHandleToPointer() failed for handle 0x%p\n", Handle); return(STATUS_INVALID_HANDLE); }
ObjectHeader = EX_HTE_TO_HDR(HandleEntry); ObjectBody = &ObjectHeader->Body;
- DPRINT("locked1: ObjectHeader: 0x%x [HT:0x%x]\n", ObjectHeader, HandleTable); + DPRINT("locked1: ObjectHeader: 0x%p [HT:0x%p]\n", ObjectHeader, Process->ObjectTable);
if (ObjectType != NULL && ObjectType != ObjectHeader->Type) { - DPRINT("ObjectType mismatch: %wZ vs %wZ (handle 0x%x)\n", &ObjectType->Name, ObjectHeader->Type ? &ObjectHeader->Type->Name : NULL, Handle); + DPRINT("ObjectType mismatch: %wZ vs %wZ (handle 0x%p)\n", &ObjectType->Name, ObjectHeader->Type ? &ObjectHeader->Type->Name : NULL, Handle);
- ExUnlockHandleTableEntry(HandleTable, + ExUnlockHandleTableEntry(Process->ObjectTable, HandleEntry);
+ if (AttachedToProcess) + { + KeUnstackDetachProcess(&ApcState); + } + KeLeaveCriticalRegion();
return(STATUS_OBJECT_TYPE_MISMATCH); @@ -845,9 +1019,14 @@ rights than the handle can grant */ if(AccessMode != KernelMode && (~GrantedAccess & DesiredAccess)) { - ExUnlockHandleTableEntry(HandleTable, + ExUnlockHandleTableEntry(Process->ObjectTable, HandleEntry);
+ if (AttachedToProcess) + { + KeUnstackDetachProcess(&ApcState); + } + KeLeaveCriticalRegion();
DPRINT1("GrantedAccess: 0x%x, ~GrantedAccess: 0x%x, DesiredAccess: 0x%x, denied: 0x%x\n", GrantedAccess, ~GrantedAccess, DesiredAccess, ~GrantedAccess & DesiredAccess); @@ -861,9 +1040,14 @@
EX_HANDLE_ENTRY_INHERITABLE |
EX_HANDLE_ENTRY_AUDITONCLOSE);
- ExUnlockHandleTableEntry(HandleTable, + ExUnlockHandleTableEntry(Process->ObjectTable, HandleEntry);
+ if (AttachedToProcess) + { + KeUnstackDetachProcess(&ApcState); + } + KeLeaveCriticalRegion();
if (HandleInformation != NULL) @@ -897,27 +1081,43 @@ NTSTATUS STDCALL NtClose(IN HANDLE Handle) { - PHANDLE_TABLE HandleTable; + PEPROCESS Process, CurrentProcess; + BOOLEAN AttachedToProcess = FALSE; + KAPC_STATE ApcState; NTSTATUS Status; + KPROCESSOR_MODE PreviousMode;
PAGED_CODE();
- if(ObIsKernelHandle(Handle, ExGetPreviousMode())) + PreviousMode = ExGetPreviousMode(); + CurrentProcess = PsGetCurrentProcess(); + + if(ObIsKernelHandle(Handle, PreviousMode)) { - HandleTable = ObpKernelHandleTable; + Process = PsInitialSystemProcess; Handle = ObKernelHandleToHandle(Handle); + + if (Process != CurrentProcess) + { + KeStackAttachProcess(&Process->Pcb, + &ApcState); + AttachedToProcess = TRUE; + } } else + Process = CurrentProcess; + + Status = ObpDeleteHandle(Handle); + + if (AttachedToProcess) { - HandleTable = PsGetCurrentProcess()->ObjectTable; + KeUnstackDetachProcess(&ApcState); }
- Status = ObpDeleteHandle(HandleTable, - Handle); if (!NT_SUCCESS(Status)) { - if((ExGetPreviousMode() != KernelMode) && - (PsGetCurrentProcess()->ExceptionPort)) + if((PreviousMode != KernelMode) && + (CurrentProcess->ExceptionPort)) { KeRaiseUserException(Status); } @@ -1128,10 +1328,9 @@ DPRINT("Creating handle\n"); if (Handle != NULL) { - Status = ObpCreateHandle(PsGetCurrentProcess(), - &Header->Body, + Status = ObpCreateHandle(&Header->Body, DesiredAccess, - ObjectCreateInfo->Attributes & OBJ_INHERIT, + ObjectCreateInfo->Attributes, Handle); DPRINT("handle Created: %d. refcount. handlecount %d %d\n", *Handle, Header->PointerCount, Header->HandleCount); _____
Modified: trunk/reactos/ntoskrnl/ob/namespc.c --- trunk/reactos/ntoskrnl/ob/namespc.c 2005-12-10 15:53:27 UTC (rev 20037) +++ trunk/reactos/ntoskrnl/ob/namespc.c 2005-12-10 16:38:04 UTC (rev 20038) @@ -183,19 +183,18 @@
&Object, &RemainingPath, ObjectType); - ObpReleaseCapturedAttributes(&ObjectCreateInfo); if (ObjectName.Buffer) ExFreePool(ObjectName.Buffer); if (!NT_SUCCESS(Status)) { DPRINT("ObFindObject() failed (Status %lx)\n", Status); - return Status; + goto Cleanup; }
- DPRINT("OBject: %x, Remaining Path: %wZ\n", Object, &RemainingPath); + DPRINT("OBject: %p, Remaining Path: %wZ\n", Object, &RemainingPath); if (Object == NULL) { - RtlFreeUnicodeString(&RemainingPath); - return STATUS_UNSUCCESSFUL; + Status = STATUS_UNSUCCESSFUL; + goto Cleanup; } if (RemainingPath.Buffer != NULL) { @@ -203,19 +202,21 @@ Status = STATUS_OBJECT_NAME_NOT_FOUND; else Status =STATUS_OBJECT_PATH_NOT_FOUND; - RtlFreeUnicodeString(&RemainingPath); - ObDereferenceObject(Object); - return Status; + goto Cleanup; }
- Status = ObpCreateHandle(PsGetCurrentProcess(), - Object, - DesiredAccess, - FALSE, - Handle); [truncated at 1000 lines; 107 more skipped]