[NTOS:OB] Rename object types to their official names to satisfy WinDbg
[reactos.git] / ntoskrnl / ob / obhandle.c
index 346ea5b..057cdec 100644 (file)
@@ -118,7 +118,7 @@ ObpReferenceProcessObjectByHandle(IN HANDLE Handle,
 
             /* Reference ourselves */
             ObjectHeader = OBJECT_TO_OBJECT_HEADER(Process);
 
             /* Reference ourselves */
             ObjectHeader = OBJECT_TO_OBJECT_HEADER(Process);
-            InterlockedIncrement(&ObjectHeader->PointerCount);
+            InterlockedIncrementSizeT(&ObjectHeader->PointerCount);
 
             /* Return the pointer */
             *Object = Process;
 
             /* Return the pointer */
             *Object = Process;
@@ -135,7 +135,7 @@ ObpReferenceProcessObjectByHandle(IN HANDLE Handle,
 
             /* Reference ourselves */
             ObjectHeader = OBJECT_TO_OBJECT_HEADER(Thread);
 
             /* Reference ourselves */
             ObjectHeader = OBJECT_TO_OBJECT_HEADER(Thread);
-            InterlockedExchangeAdd(&ObjectHeader->PointerCount, 1);
+            InterlockedIncrementSizeT(&ObjectHeader->PointerCount);
 
             /* No audit mask */
             *AuditMask = 0;
 
             /* No audit mask */
             *AuditMask = 0;
@@ -188,7 +188,7 @@ ObpReferenceProcessObjectByHandle(IN HANDLE Handle,
         *Object = &ObjectHeader->Body;
 
         /* Add a reference */
         *Object = &ObjectHeader->Body;
 
         /* Add a reference */
-        InterlockedExchangeAdd(&ObjectHeader->PointerCount, 1);
+        InterlockedIncrementSizeT(&ObjectHeader->PointerCount);
 
         /* Unlock the handle */
         ExUnlockHandleTableEntry(HandleTable, HandleEntry);
 
         /* Unlock the handle */
         ExUnlockHandleTableEntry(HandleTable, HandleEntry);
@@ -484,7 +484,22 @@ NTSTATUS
 NTAPI
 ObpValidateAccessMask(IN PACCESS_STATE AccessState)
 {
 NTAPI
 ObpValidateAccessMask(IN PACCESS_STATE AccessState)
 {
-    /* TODO */
+    PISECURITY_DESCRIPTOR SecurityDescriptor;
+
+    /* We're only interested if the object for this access state has an SD */
+    SecurityDescriptor = AccessState->SecurityDescriptor;
+    if (SecurityDescriptor)
+    {
+        /* Check if the SD has a system ACL but hasn't been granted access to get/set it */
+        if ((SecurityDescriptor->Control & SE_SACL_PRESENT) &&
+            !(AccessState->PreviouslyGrantedAccess & ACCESS_SYSTEM_SECURITY))
+        {
+            /* We're gonna need access */
+            AccessState->RemainingDesiredAccess |= ACCESS_SYSTEM_SECURITY;
+        }
+    }
+
+    /* This can't fail */
     return STATUS_SUCCESS;
 }
 
     return STATUS_SUCCESS;
 }
 
@@ -541,7 +556,7 @@ ObpDecrementHandleCount(IN PVOID ObjectBody,
     ProcessHandleCount = 0;
 
     /* Decrement the handle count */
     ProcessHandleCount = 0;
 
     /* Decrement the handle count */
-    NewCount = InterlockedDecrement(&ObjectHeader->HandleCount);
+    NewCount = InterlockedDecrementSizeT(&ObjectHeader->HandleCount);
 
     /* Check if we're out of handles and this was an exclusive object */
     if (!(NewCount) && (ObjectHeader->Flags & OB_FLAG_EXCLUSIVE))
 
     /* Check if we're out of handles and this was an exclusive object */
     if (!(NewCount) && (ObjectHeader->Flags & OB_FLAG_EXCLUSIVE))
@@ -683,7 +698,7 @@ ObpCloseHandleTableEntry(IN PHANDLE_TABLE HandleTable,
     Body = &ObjectHeader->Body;
     GrantedAccess = HandleEntry->GrantedAccess;
     OBTRACE(OB_HANDLE_DEBUG,
     Body = &ObjectHeader->Body;
     GrantedAccess = HandleEntry->GrantedAccess;
     OBTRACE(OB_HANDLE_DEBUG,
-            "%s - Closing handle: %lx for %p. HC PC %lx %lx\n",
+            "%s - Closing handle: %p for %p. HC PC %lx %lx\n",
             __FUNCTION__,
             Handle,
             Body,
             __FUNCTION__,
             Handle,
             Body,
@@ -753,7 +768,7 @@ ObpCloseHandleTableEntry(IN PHANDLE_TABLE HandleTable,
 
     /* Return to caller */
     OBTRACE(OB_HANDLE_DEBUG,
 
     /* Return to caller */
     OBTRACE(OB_HANDLE_DEBUG,
-            "%s - Closed handle: %lx for %p.\n",
+            "%s - Closed handle: %p for %p.\n",
             __FUNCTION__,
             Handle,
             Body);
             __FUNCTION__,
             Handle,
             Body);
@@ -807,6 +822,7 @@ ObpIncrementHandleCount(IN PVOID Object,
     KIRQL CalloutIrql;
     KPROCESSOR_MODE ProbeMode;
     ULONG Total;
     KIRQL CalloutIrql;
     KPROCESSOR_MODE ProbeMode;
     ULONG Total;
+    POBJECT_HEADER_NAME_INFO NameInfo;
     PAGED_CODE();
 
     /* Get the object header and type */
     PAGED_CODE();
 
     /* Get the object header and type */
@@ -872,6 +888,16 @@ ObpIncrementHandleCount(IN PVOID Object,
         goto Quickie;
     }
 
         goto Quickie;
     }
 
+    /* Check for exclusive kernel object */
+    NameInfo = OBJECT_HEADER_TO_NAME_INFO(ObjectHeader);
+    if ((NameInfo) && (NameInfo->QueryReferences & OB_FLAG_KERNEL_EXCLUSIVE) &&
+        (ProbeMode != KernelMode))
+    {
+        /* Caller is not kernel, but the object is kernel exclusive */
+        Status = STATUS_ACCESS_DENIED;
+        goto Quickie;
+    }
+
     /*
      * Check if this is an object that went from 0 handles back to existence,
      * but doesn't have an open procedure, only a close procedure. This means
     /*
      * Check if this is an object that went from 0 handles back to existence,
      * but doesn't have an open procedure, only a close procedure. This means
@@ -938,7 +964,7 @@ ObpIncrementHandleCount(IN PVOID Object,
     }
 
     /* Increase the handle count */
     }
 
     /* Increase the handle count */
-    InterlockedIncrement(&ObjectHeader->HandleCount);
+    InterlockedIncrementSizeT(&ObjectHeader->HandleCount);
     ProcessHandleCount = 0;
 
     /* Check if we have a handle database */
     ProcessHandleCount = 0;
 
     /* Check if we have a handle database */
@@ -1165,7 +1191,7 @@ ObpIncrementUnnamedHandleCount(IN PVOID Object,
     }
 
     /* Increase the handle count */
     }
 
     /* Increase the handle count */
-    InterlockedIncrement(&ObjectHeader->HandleCount);
+    InterlockedIncrementSizeT(&ObjectHeader->HandleCount);
     ProcessHandleCount = 0;
 
     /* Check if we have a handle database */
     ProcessHandleCount = 0;
 
     /* Check if we have a handle database */
@@ -1360,8 +1386,8 @@ ObpCreateUnnamedHandle(IN PVOID Object,
     if (AdditionalReferences)
     {
         /* Add them to the header */
     if (AdditionalReferences)
     {
         /* Add them to the header */
-        InterlockedExchangeAdd(&ObjectHeader->PointerCount,
-                               AdditionalReferences);
+        InterlockedExchangeAddSizeT(&ObjectHeader->PointerCount,
+                                    AdditionalReferences);
     }
 
     /* Save the access mask */
     }
 
     /* Save the access mask */
@@ -1399,7 +1425,7 @@ ObpCreateUnnamedHandle(IN PVOID Object,
 
         /* Trace and return */
         OBTRACE(OB_HANDLE_DEBUG,
 
         /* Trace and return */
         OBTRACE(OB_HANDLE_DEBUG,
-                "%s - Returning Handle: %lx HC PC %lx %lx\n",
+                "%s - Returning Handle: %p HC PC %lx %lx\n",
                 __FUNCTION__,
                 Handle,
                 ObjectHeader->HandleCount,
                 __FUNCTION__,
                 Handle,
                 ObjectHeader->HandleCount,
@@ -1411,8 +1437,8 @@ ObpCreateUnnamedHandle(IN PVOID Object,
     if (AdditionalReferences)
     {
         /* Dereference it as many times as required */
     if (AdditionalReferences)
     {
         /* Dereference it as many times as required */
-        InterlockedExchangeAdd(&ObjectHeader->PointerCount,
-                               -(LONG)AdditionalReferences);
+        InterlockedExchangeAddSizeT(&ObjectHeader->PointerCount,
+                                    -(LONG)AdditionalReferences);
     }
 
     /* Decrement the handle count and detach */
     }
 
     /* Decrement the handle count and detach */
@@ -1577,7 +1603,8 @@ ObpCreateHandle(IN OB_OPEN_REASON OpenReason,
     if (AdditionalReferences)
     {
         /* Add them to the header */
     if (AdditionalReferences)
     {
         /* Add them to the header */
-        InterlockedExchangeAdd(&ObjectHeader->PointerCount, AdditionalReferences);
+        InterlockedExchangeAddSizeT(&ObjectHeader->PointerCount,
+                                    AdditionalReferences);
     }
 
     /* Now we can release the object */
     }
 
     /* Now we can release the object */
@@ -1645,7 +1672,7 @@ ObpCreateHandle(IN OB_OPEN_REASON OpenReason,
 
         /* Trace and return */
         OBTRACE(OB_HANDLE_DEBUG,
 
         /* Trace and return */
         OBTRACE(OB_HANDLE_DEBUG,
-                "%s - Returning Handle: %lx HC PC %lx %lx\n",
+                "%s - Returning Handle: %p HC PC %lx %lx\n",
                 __FUNCTION__,
                 Handle,
                 ObjectHeader->HandleCount,
                 __FUNCTION__,
                 Handle,
                 ObjectHeader->HandleCount,
@@ -1666,8 +1693,8 @@ ObpCreateHandle(IN OB_OPEN_REASON OpenReason,
         if (AdditionalReferences > 1)
         {
             /* Dereference it many times */
         if (AdditionalReferences > 1)
         {
             /* Dereference it many times */
-            InterlockedExchangeAdd(&ObjectHeader->PointerCount,
-                                  -(LONG)(AdditionalReferences - 1));
+            InterlockedExchangeAddSizeT(&ObjectHeader->PointerCount,
+                                        -(LONG)(AdditionalReferences - 1));
         }
 
         /* Dereference the object one last time */
         }
 
         /* Dereference the object one last time */
@@ -1708,13 +1735,13 @@ ObpCloseHandle(IN HANDLE Handle,
     PEPROCESS Process = PsGetCurrentProcess();
     PAGED_CODE();
     OBTRACE(OB_HANDLE_DEBUG,
     PEPROCESS Process = PsGetCurrentProcess();
     PAGED_CODE();
     OBTRACE(OB_HANDLE_DEBUG,
-            "%s - Closing handle: %lx\n", __FUNCTION__, Handle);
+            "%s - Closing handle: %p\n", __FUNCTION__, Handle);
 
     if (AccessMode == KernelMode && Handle == (HANDLE)-1)
         return STATUS_INVALID_HANDLE;
 
     /* Check if we're dealing with a kernel handle */
 
     if (AccessMode == KernelMode && Handle == (HANDLE)-1)
         return STATUS_INVALID_HANDLE;
 
     /* Check if we're dealing with a kernel handle */
-    if (ObIsKernelHandle(Handle, AccessMode))
+    if (ObpIsKernelHandle(Handle, AccessMode))
     {
         /* Use the kernel table and convert the handle */
         HandleTable = ObpKernelHandleTable;
     {
         /* Use the kernel table and convert the handle */
         HandleTable = ObpKernelHandleTable;
@@ -1803,7 +1830,7 @@ ObpCloseHandle(IN HANDLE Handle,
 
     /* Return status */
     OBTRACE(OB_HANDLE_DEBUG,
 
     /* Return status */
     OBTRACE(OB_HANDLE_DEBUG,
-            "%s - Closed handle: %lx S: %lx\n",
+            "%s - Closed handle: %p S: %lx\n",
             __FUNCTION__, Handle, Status);
     return Status;
 }
             __FUNCTION__, Handle, Status);
     return Status;
 }
@@ -1946,7 +1973,7 @@ ObpDuplicateHandleCallback(IN PEPROCESS Process,
         ObjectHeader = ObpGetHandleObject(HandleTableEntry);
 
         /* Increment the pointer count */
         ObjectHeader = ObpGetHandleObject(HandleTableEntry);
 
         /* Increment the pointer count */
-        InterlockedIncrement(&ObjectHeader->PointerCount);
+        InterlockedIncrementSizeT(&ObjectHeader->PointerCount);
 
         /* Release the handle lock */
         ExUnlockHandleTableEntry(HandleTable, OldEntry);
 
         /* Release the handle lock */
         ExUnlockHandleTableEntry(HandleTable, OldEntry);
@@ -1978,25 +2005,79 @@ ObpDuplicateHandleCallback(IN PEPROCESS Process,
     return Ret;
 }
 
     return Ret;
 }
 
+/*++
+* @name ObClearProcessHandleTable
+*
+*     The ObClearProcessHandleTable routine clears the handle table
+*     of the given process.
+*
+* @param Process
+*        The process of which the handle table should be cleared.
+*
+* @return None.
+*
+* @remarks None.
+*
+*--*/
 VOID
 NTAPI
 ObClearProcessHandleTable(IN PEPROCESS Process)
 {
 VOID
 NTAPI
 ObClearProcessHandleTable(IN PEPROCESS Process)
 {
-    /* FIXME */
+    PHANDLE_TABLE HandleTable;
+    OBP_CLOSE_HANDLE_CONTEXT Context;
+    KAPC_STATE ApcState;
+    BOOLEAN AttachedToProcess = FALSE;
+
+    ASSERT(Process);
+
+    /* Ensure the handle table doesn't go away while we use it */
+    HandleTable = ObReferenceProcessHandleTable(Process);
+    if (!HandleTable) return;
+
+    /* Attach to the current process if needed */
+    if (PsGetCurrentProcess() != Process)
+    {
+        KeStackAttachProcess(&Process->Pcb, &ApcState);
+        AttachedToProcess = TRUE;
+    }
+
+    /* Enter a critical region */
+    KeEnterCriticalRegion();
+
+    /* Fill out the context */
+    Context.AccessMode = UserMode;
+    Context.HandleTable = HandleTable;
+
+    /* Sweep the handle table to close all handles */
+    ExSweepHandleTable(HandleTable,
+                       ObpCloseHandleCallback,
+                       &Context);
+
+    /* Leave the critical region */
+    KeLeaveCriticalRegion();
+
+    /* Detach if needed */
+    if (AttachedToProcess)
+        KeUnstackDetachProcess(&ApcState);
+
+    /* Let the handle table go */
+    ObDereferenceProcessHandleTable(Process);
 }
 
 /*++
 }
 
 /*++
-* @name ObpCreateHandleTable
+* @name ObInitProcess
 *
 *
-*     The ObpCreateHandleTable routine <FILLMEIN>
+*     The ObInitProcess routine initializes the handle table for the process
+*     to be initialized, by either creating a new one or duplicating it from
+*     the parent process.
 *
 * @param Parent
 *
 * @param Parent
-*        <FILLMEIN>.
+*        A parent process (optional).
 *
 * @param Process
 *
 * @param Process
-*        <FILLMEIN>.
+*        The process to initialize.
 *
 *
-* @return <FILLMEIN>.
+* @return Success or failure.
 *
 * @remarks None.
 *
 *
 * @remarks None.
 *
@@ -2059,14 +2140,16 @@ ObInitProcess(IN PEPROCESS Parent OPTIONAL,
 /*++
 * @name ObKillProcess
 *
 /*++
 * @name ObKillProcess
 *
-*     The ObKillProcess routine <FILLMEIN>
+*     The ObKillProcess routine performs rundown operations on the process,
+*     then clears and destroys its handle table.
 *
 * @param Process
 *
 * @param Process
-*        <FILLMEIN>.
+*        The process to be killed.
 *
 * @return None.
 *
 *
 * @return None.
 *
-* @remarks None.
+* @remarks Called by the Object Manager cleanup code (kernel)
+*          when a process is to be destroyed.
 *
 *--*/
 VOID
 *
 *--*/
 VOID
@@ -2139,9 +2222,11 @@ ObDuplicateObject(IN PEPROCESS SourceProcess,
     PHANDLE_TABLE HandleTable;
     OBJECT_HANDLE_INFORMATION HandleInformation;
     ULONG AuditMask;
     PHANDLE_TABLE HandleTable;
     OBJECT_HANDLE_INFORMATION HandleInformation;
     ULONG AuditMask;
+    BOOLEAN KernelHandle = FALSE;
+
     PAGED_CODE();
     OBTRACE(OB_HANDLE_DEBUG,
     PAGED_CODE();
     OBTRACE(OB_HANDLE_DEBUG,
-            "%s - Duplicating handle: %lx for %p into %p\n",
+            "%s - Duplicating handle: %p for %p into %p\n",
             __FUNCTION__,
             SourceHandle,
             SourceProcess,
             __FUNCTION__,
             SourceHandle,
             SourceProcess,
@@ -2211,6 +2296,14 @@ ObDuplicateObject(IN PEPROCESS SourceProcess,
         return Status;
     }
 
         return Status;
     }
 
+    /* Create a kernel handle if asked, but only in the system process */
+    if (PreviousMode == KernelMode &&
+        HandleAttributes & OBJ_KERNEL_HANDLE &&
+        TargetProcess == PsInitialSystemProcess)
+    {
+        KernelHandle = TRUE;
+    }
+
     /* Get the target handle table */
     HandleTable = ObReferenceProcessHandleTable(TargetProcess);
     if (!HandleTable)
     /* Get the target handle table */
     HandleTable = ObReferenceProcessHandleTable(TargetProcess);
     if (!HandleTable)
@@ -2365,6 +2458,12 @@ ObDuplicateObject(IN PEPROCESS SourceProcess,
         Status = STATUS_INSUFFICIENT_RESOURCES;
     }
 
         Status = STATUS_INSUFFICIENT_RESOURCES;
     }
 
+    /* Mark it as a kernel handle if requested */
+    if (KernelHandle)
+    {
+        NewHandle = ObMarkHandleAsKernelHandle(NewHandle);
+    }
+
     /* Return the handle */
     if (TargetHandle) *TargetHandle = NewHandle;
 
     /* Return the handle */
     if (TargetHandle) *TargetHandle = NewHandle;
 
@@ -2374,7 +2473,7 @@ ObDuplicateObject(IN PEPROCESS SourceProcess,
 
     /* Return status */
     OBTRACE(OB_HANDLE_DEBUG,
 
     /* Return status */
     OBTRACE(OB_HANDLE_DEBUG,
-            "%s - Duplicated handle: %lx for %p into %p. Source: %p HC PC %lx %lx\n",
+            "%s - Duplicated handle: %p for %p into %p. Source: %p HC PC %lx %lx\n",
             __FUNCTION__,
             NewHandle,
             SourceProcess,
             __FUNCTION__,
             NewHandle,
             SourceProcess,
@@ -2431,7 +2530,7 @@ ObOpenObjectByName(IN POBJECT_ATTRIBUTES ObjectAttributes,
 {
     PVOID Object = NULL;
     UNICODE_STRING ObjectName;
 {
     PVOID Object = NULL;
     UNICODE_STRING ObjectName;
-    NTSTATUS Status;
+    NTSTATUS Status, Status2;
     POBJECT_HEADER ObjectHeader;
     PGENERIC_MAPPING GenericMapping = NULL;
     OB_OPEN_REASON OpenReason;
     POBJECT_HEADER ObjectHeader;
     PGENERIC_MAPPING GenericMapping = NULL;
     OB_OPEN_REASON OpenReason;
@@ -2456,6 +2555,7 @@ ObOpenObjectByName(IN POBJECT_ATTRIBUTES ObjectAttributes,
 
     /* Capture all the info */
     Status = ObpCaptureObjectCreateInformation(ObjectAttributes,
 
     /* Capture all the info */
     Status = ObpCaptureObjectCreateInformation(ObjectAttributes,
+                                               AccessMode,
                                                AccessMode,
                                                TRUE,
                                                &TempBuffer->ObjectCreateInfo,
                                                AccessMode,
                                                TRUE,
                                                &TempBuffer->ObjectCreateInfo,
@@ -2490,6 +2590,15 @@ ObOpenObjectByName(IN POBJECT_ATTRIBUTES ObjectAttributes,
             TempBuffer->ObjectCreateInfo.SecurityDescriptor;
     }
 
             TempBuffer->ObjectCreateInfo.SecurityDescriptor;
     }
 
+    /* Validate the access mask */
+    Status = ObpValidateAccessMask(PassedAccessState);
+    if (!NT_SUCCESS(Status))
+    {
+        /* Cleanup after lookup */
+        ObpReleaseLookupContext(&TempBuffer->LookupContext);
+        goto Cleanup;
+    }
+
     /* Now do the lookup */
     Status = ObpLookupObjectName(TempBuffer->ObjectCreateInfo.RootDirectory,
                                  &ObjectName,
     /* Now do the lookup */
     Status = ObpLookupObjectName(TempBuffer->ObjectCreateInfo.RootDirectory,
                                  &ObjectName,
@@ -2547,17 +2656,21 @@ ObOpenObjectByName(IN POBJECT_ATTRIBUTES ObjectAttributes,
     else
     {
         /* Create the actual handle now */
     else
     {
         /* Create the actual handle now */
-        Status = ObpCreateHandle(OpenReason,
-                                 Object,
-                                 ObjectType,
-                                 PassedAccessState,
-                                 0,
-                                 TempBuffer->ObjectCreateInfo.Attributes,
-                                 &TempBuffer->LookupContext,
-                                 AccessMode,
-                                 NULL,
-                                 Handle);
-        if (!NT_SUCCESS(Status)) ObDereferenceObject(Object);
+        Status2 = ObpCreateHandle(OpenReason,
+                                  Object,
+                                  ObjectType,
+                                  PassedAccessState,
+                                  0,
+                                  TempBuffer->ObjectCreateInfo.Attributes,
+                                  &TempBuffer->LookupContext,
+                                  AccessMode,
+                                  NULL,
+                                  Handle);
+        if (!NT_SUCCESS(Status2))
+        {
+            ObDereferenceObject(Object);
+            Status = Status2;
+        }
     }
 
 Cleanup:
     }
 
 Cleanup:
@@ -2841,7 +2954,7 @@ ObInsertObject(IN PVOID Object,
     if (!(ObjectHeader->Flags & OB_FLAG_CREATE_INFO))
     {
         /* Display warning and break into debugger */
     if (!(ObjectHeader->Flags & OB_FLAG_CREATE_INFO))
     {
         /* Display warning and break into debugger */
-        DPRINT1("OB: Attempting to insert existing object %08x\n", Object);
+        DPRINT1("OB: Attempting to insert existing object %p\n", Object);
         DbgBreakPoint();
 
         /* Allow debugger to continue */
         DbgBreakPoint();
 
         /* Allow debugger to continue */
@@ -2982,7 +3095,7 @@ ObInsertObject(IN PVOID Object,
             {
                 /* Check if this was a symbolic link */
                 if (OBJECT_TO_OBJECT_HEADER(InsertObject)->Type ==
             {
                 /* Check if this was a symbolic link */
                 if (OBJECT_TO_OBJECT_HEADER(InsertObject)->Type ==
-                    ObSymbolicLinkType)
+                    ObpSymbolicLinkObjectType)
                 {
                     /* Dereference it */
                     ObDereferenceObject(InsertObject);
                 {
                     /* Dereference it */
                     ObDereferenceObject(InsertObject);
@@ -3016,7 +3129,7 @@ ObInsertObject(IN PVOID Object,
         else
         {
             /* Check if this is a symbolic link */
         else
         {
             /* Check if this is a symbolic link */
-            if (ObjectType == ObSymbolicLinkType)
+            if (ObjectType == ObpSymbolicLinkObjectType)
             {
                 /* Create the internal name */
                 ObpCreateSymbolicLinkName(Object);
             {
                 /* Create the internal name */
                 ObpCreateSymbolicLinkName(Object);
@@ -3161,6 +3274,80 @@ ObInsertObject(IN PVOID Object,
     return RealStatus;
 }
 
     return RealStatus;
 }
 
+/*++
+* @name ObSetHandleAttributes
+* @implemented NT5.1
+*
+*     The ObSetHandleAttributes routine <FILLMEIN>
+*
+* @param Handle
+*        <FILLMEIN>.
+*
+* @param HandleFlags
+*        <FILLMEIN>.
+*
+* @param PreviousMode
+*        <FILLMEIN>.
+*
+* @return <FILLMEIN>.
+*
+* @remarks None.
+*
+*--*/
+NTSTATUS
+NTAPI
+ObSetHandleAttributes(IN HANDLE Handle,
+                      IN POBJECT_HANDLE_ATTRIBUTE_INFORMATION HandleFlags,
+                      IN KPROCESSOR_MODE PreviousMode)
+{
+    OBP_SET_HANDLE_ATTRIBUTES_CONTEXT SetHandleAttributesContext;
+    BOOLEAN Result, AttachedToSystemProcess = FALSE;
+    PHANDLE_TABLE HandleTable;
+    KAPC_STATE ApcState;
+    PAGED_CODE();
+
+    /* Check if this is a kernel handle */
+    if (ObpIsKernelHandle(Handle, PreviousMode))
+    {
+        /* Use the kernel table and convert the handle */
+        HandleTable = ObpKernelHandleTable;
+        Handle = ObKernelHandleToHandle(Handle);
+
+        /* Check if we're not in the system process */
+        if (PsGetCurrentProcess() != PsInitialSystemProcess)
+        {
+            /* Attach to the system process */
+            KeStackAttachProcess(&PsInitialSystemProcess->Pcb, &ApcState);
+            AttachedToSystemProcess = TRUE;
+        }
+    }
+    else
+    {
+        /* Get the current process' handle table */
+        HandleTable = PsGetCurrentProcess()->ObjectTable;
+    }
+
+    /* Initialize the handle attribute context */
+    SetHandleAttributesContext.PreviousMode = PreviousMode;
+    SetHandleAttributesContext.Information = *HandleFlags;
+
+    /* Invoke the ObpSetHandleAttributes callback */
+    Result = ExChangeHandle(HandleTable,
+                            Handle,
+                            ObpSetHandleAttributes,
+                            (ULONG_PTR)&SetHandleAttributesContext);
+
+    /* Did we attach to the system process? */
+    if (AttachedToSystemProcess)
+    {
+        /* Detach from it */
+        KeUnstackDetachProcess(&ApcState);
+    }
+
+    /* Return the result as an NTSTATUS value */
+    return Result ? STATUS_SUCCESS : STATUS_ACCESS_DENIED;
+}
+
 /*++
 * @name ObCloseHandle
 * @implemented NT5.1
 /*++
 * @name ObCloseHandle
 * @implemented NT5.1
@@ -3224,7 +3411,7 @@ NtDuplicateObject(IN HANDLE SourceProcessHandle,
     KPROCESSOR_MODE PreviousMode = ExGetPreviousMode();
     NTSTATUS Status;
     OBTRACE(OB_HANDLE_DEBUG,
     KPROCESSOR_MODE PreviousMode = ExGetPreviousMode();
     NTSTATUS Status;
     OBTRACE(OB_HANDLE_DEBUG,
-            "%s - Duplicating handle: %lx for %lx into %lx.\n",
+            "%s - Duplicating handle: %p for %p into %p.\n",
             __FUNCTION__,
             SourceHandle,
             SourceProcessHandle,
             __FUNCTION__,
             SourceHandle,
             SourceProcessHandle,
@@ -3255,7 +3442,7 @@ NtDuplicateObject(IN HANDLE SourceProcessHandle,
                                        PreviousMode,
                                        (PVOID*)&SourceProcess,
                                        NULL);
                                        PreviousMode,
                                        (PVOID*)&SourceProcess,
                                        NULL);
-    if (!NT_SUCCESS(Status)) return(Status);
+    if (!NT_SUCCESS(Status)) return Status;
 
     /* Check if got a target handle */
     if (TargetProcessHandle)
 
     /* Check if got a target handle */
     if (TargetProcessHandle)
@@ -3314,7 +3501,7 @@ NtDuplicateObject(IN HANDLE SourceProcessHandle,
 
     /* Dereference the processes */
     OBTRACE(OB_HANDLE_DEBUG,
 
     /* Dereference the processes */
     OBTRACE(OB_HANDLE_DEBUG,
-            "%s - Duplicated handle: %lx into %lx S %lx\n",
+            "%s - Duplicated handle: %p into %p S %lx\n",
             __FUNCTION__,
             hTarget,
             TargetProcessHandle,
             __FUNCTION__,
             hTarget,
             TargetProcessHandle,
@@ -3324,13 +3511,12 @@ NtDuplicateObject(IN HANDLE SourceProcessHandle,
     return Status;
 }
 
     return Status;
 }
 
-#undef ObIsKernelHandle
 BOOLEAN
 NTAPI
 ObIsKernelHandle(IN HANDLE Handle)
 {
 BOOLEAN
 NTAPI
 ObIsKernelHandle(IN HANDLE Handle)
 {
-    /* We know we're kernel mode, so just check for the kernel handle flag */
-    return (BOOLEAN)(((ULONG_PTR)Handle & KERNEL_HANDLE_FLAG) != 0);
+    /* Use the inlined version. We know we are in kernel mode. */
+    return ObpIsKernelHandle(Handle, KernelMode);
 }
 
 /* EOF */
 }
 
 /* EOF */