implemented sweeping of handle tables
[reactos.git] / reactos / ntoskrnl / ob / handle.c
index fc0ddeb..153ff10 100644 (file)
 #define NDEBUG
 #include <internal/debug.h>
 
-#define EX_OBJ_TO_HDR(eob) ((POBJECT_HEADER)((ULONG_PTR)(eob) &                \
-  ~(EX_HANDLE_ENTRY_PROTECTFROMCLOSE | EX_HANDLE_ENTRY_INHERITABLE |           \
-  EX_HANDLE_ENTRY_AUDITONCLOSE)))
-#define EX_HTE_TO_HDR(hte) ((POBJECT_HEADER)((ULONG_PTR)((hte)->u1.Object) &   \
-  ~(EX_HANDLE_ENTRY_PROTECTFROMCLOSE | EX_HANDLE_ENTRY_INHERITABLE |           \
-  EX_HANDLE_ENTRY_AUDITONCLOSE)))
-
 #define GENERIC_ANY (GENERIC_READ | GENERIC_WRITE | GENERIC_EXECUTE | GENERIC_ALL)
 
 /* GLOBALS *****************************************************************/
 
 PHANDLE_TABLE ObpKernelHandleTable = NULL;
 
+/* TEMPORARY HACK. DO NOT REMOVE -- Alex */
+NTSTATUS
+STDCALL
+ExpDesktopCreate(PVOID ObjectBody,
+                 PVOID Parent,
+                 PWSTR RemainingPath,
+                 POBJECT_CREATE_INFORMATION ObjectCreateInformation);
+
 /* FUNCTIONS ***************************************************************/
 
 static VOID
@@ -53,18 +54,23 @@ ObpDecrementHandleCount(PVOID ObjectBody)
 {
   POBJECT_HEADER ObjectHeader = BODY_TO_HEADER(ObjectBody);
   LONG NewHandleCount = InterlockedDecrement(&ObjectHeader->HandleCount);
+  DPRINT("Header: %x\n", ObjectHeader);
+  DPRINT("NewHandleCount: %x\n", NewHandleCount);
+  DPRINT("HEADER_TO_OBJECT_NAME: %x\n", HEADER_TO_OBJECT_NAME(ObjectHeader));
 
-  if ((ObjectHeader->ObjectType != NULL) &&
-      (ObjectHeader->ObjectType->Close != NULL))
+  if ((ObjectHeader->Type != NULL) &&
+      (ObjectHeader->Type->TypeInfo.CloseProcedure != NULL))
   {
     /* the handle count should be decremented but we pass the previous value
        to the callback */
-    ObjectHeader->ObjectType->Close(ObjectBody, NewHandleCount + 1);
+    ObjectHeader->Type->TypeInfo.CloseProcedure(ObjectBody, NewHandleCount + 1);
   }
 
   if(NewHandleCount == 0)
   {
-    if(ObjectHeader->Parent != NULL && !ObjectHeader->Permanent)
+    if(HEADER_TO_OBJECT_NAME(ObjectHeader) && 
+       HEADER_TO_OBJECT_NAME(ObjectHeader)->Directory != NULL &&
+       !(ObjectHeader->Flags & OB_FLAG_PERMANENT))
     {
       /* delete the object from the namespace when the last handle got closed.
          Only do this if it's actually been inserted into the namespace and
@@ -79,12 +85,12 @@ ObpDecrementHandleCount(PVOID ObjectBody)
 
 
 NTSTATUS
+NTAPI
 ObpQueryHandleAttributes(HANDLE Handle,
                         POBJECT_HANDLE_ATTRIBUTE_INFORMATION HandleInfo)
 {
   PHANDLE_TABLE HandleTable;
   PHANDLE_TABLE_ENTRY HandleTableEntry;
-  LONG ExHandle;
 
   PAGED_CODE();
 
@@ -93,18 +99,17 @@ ObpQueryHandleAttributes(HANDLE Handle,
   if(ObIsKernelHandle(Handle, ExGetPreviousMode()))
   {
     HandleTable = ObpKernelHandleTable;
-    ExHandle = HANDLE_TO_EX_HANDLE(ObKernelHandleToHandle(Handle));
+    Handle = ObKernelHandleToHandle(Handle);
   }
   else
   {
     HandleTable = PsGetCurrentProcess()->ObjectTable;
-    ExHandle = HANDLE_TO_EX_HANDLE(Handle);
   }
 
   KeEnterCriticalRegion();
 
   HandleTableEntry = ExMapHandleToPointer(HandleTable,
-                                          ExHandle);
+                                          Handle);
   if (HandleTableEntry == NULL)
     {
       KeLeaveCriticalRegion();
@@ -124,12 +129,12 @@ ObpQueryHandleAttributes(HANDLE Handle,
 
 
 NTSTATUS
+NTAPI
 ObpSetHandleAttributes(HANDLE Handle,
                       POBJECT_HANDLE_ATTRIBUTE_INFORMATION HandleInfo)
 {
   PHANDLE_TABLE HandleTable;
   PHANDLE_TABLE_ENTRY HandleTableEntry;
-  LONG ExHandle;
 
   PAGED_CODE();
 
@@ -138,18 +143,17 @@ ObpSetHandleAttributes(HANDLE Handle,
   if(ObIsKernelHandle(Handle, ExGetPreviousMode()))
   {
     HandleTable = ObpKernelHandleTable;
-    ExHandle = HANDLE_TO_EX_HANDLE(ObKernelHandleToHandle(Handle));
+    Handle = ObKernelHandleToHandle(Handle);
   }
   else
   {
     HandleTable = PsGetCurrentProcess()->ObjectTable;
-    ExHandle = HANDLE_TO_EX_HANDLE(Handle);
   }
 
   KeEnterCriticalRegion();
 
   HandleTableEntry = ExMapHandleToPointer(HandleTable,
-                                          ExHandle);
+                                          Handle);
   if (HandleTableEntry == NULL)
     {
       KeLeaveCriticalRegion();
@@ -184,7 +188,6 @@ ObpDeleteHandle(PHANDLE_TABLE HandleTable,
    PHANDLE_TABLE_ENTRY HandleEntry;
    PVOID Body;
    POBJECT_HEADER ObjectHeader;
-   LONG ExHandle = HANDLE_TO_EX_HANDLE(Handle);
 
    PAGED_CODE();
 
@@ -193,7 +196,7 @@ ObpDeleteHandle(PHANDLE_TABLE HandleTable,
    KeEnterCriticalRegion();
 
    HandleEntry = ExMapHandleToPointer(HandleTable,
-                                      ExHandle);
+                                      Handle);
    if(HandleEntry != NULL)
    {
      if(HandleEntry->u1.ObAttributes & EX_HANDLE_ENTRY_PROTECTFROMCLOSE)
@@ -207,14 +210,14 @@ ObpDeleteHandle(PHANDLE_TABLE HandleTable,
      }
 
      ObjectHeader = EX_HTE_TO_HDR(HandleEntry);
-     Body = HEADER_TO_BODY(ObjectHeader);
+     Body = &ObjectHeader->Body;
 
      ObpDecrementHandleCount(Body);
 
      /* destroy and unlock the handle entry */
      ExDestroyHandleByEntry(HandleTable,
                             HandleEntry,
-                            ExHandle);
+                            Handle);
 
      KeLeaveCriticalRegion();
 
@@ -226,6 +229,7 @@ ObpDeleteHandle(PHANDLE_TABLE HandleTable,
 
 
 NTSTATUS
+NTAPI
 ObDuplicateObject(PEPROCESS SourceProcess,
                  PEPROCESS TargetProcess,
                  HANDLE SourceHandle,
@@ -239,9 +243,8 @@ ObDuplicateObject(PEPROCESS SourceProcess,
   HANDLE_TABLE_ENTRY NewHandleEntry;
   PVOID ObjectBody;
   POBJECT_HEADER ObjectHeader;
-  LONG ExTargetHandle;
-  LONG ExSourceHandle;
   ULONG NewHandleCount;
+  HANDLE NewTargetHandle;
 
   PAGED_CODE();
 
@@ -255,12 +258,10 @@ ObDuplicateObject(PEPROCESS SourceProcess,
     SourceHandleTable = SourceProcess->ObjectTable;
   }
 
-  ExSourceHandle = HANDLE_TO_EX_HANDLE(SourceHandle);
-
   KeEnterCriticalRegion();
 
   SourceHandleEntry = ExMapHandleToPointer(SourceHandleTable,
-                                           ExSourceHandle);
+                                           SourceHandle);
   if (SourceHandleEntry == NULL)
     {
       KeLeaveCriticalRegion();
@@ -268,7 +269,7 @@ ObDuplicateObject(PEPROCESS SourceProcess,
     }
 
   ObjectHeader = EX_HTE_TO_HDR(SourceHandleEntry);
-  ObjectBody = HEADER_TO_BODY(ObjectHeader);
+  ObjectBody = &ObjectHeader->Body;
 
   NewHandleEntry.u1.Object = SourceHandleEntry->u1.Object;
   if(InheritHandle)
@@ -287,7 +288,7 @@ ObDuplicateObject(PEPROCESS SourceProcess,
     if (DesiredAccess & GENERIC_ANY)
     {
       RtlMapGenericMask(&DesiredAccess,
-                        ObjectHeader->ObjectType->Mapping);
+                        &ObjectHeader->Type->TypeInfo.GenericMapping);
     }
     NewHandleEntry.u2.GrantedAccess = DesiredAccess;
   }
@@ -310,9 +311,9 @@ ObDuplicateObject(PEPROCESS SourceProcess,
   KeLeaveCriticalRegion();
 
   /* attempt to create the new handle */
-  ExTargetHandle = ExCreateHandle(TargetProcess->ObjectTable,
-                                  &NewHandleEntry);
-  if (ExTargetHandle != EX_INVALID_HANDLE)
+  NewTargetHandle = ExCreateHandle(TargetProcess->ObjectTable,
+                                   &NewHandleEntry);
+  if (NewTargetHandle != NULL)
   {
     if (Options & DUPLICATE_CLOSE_SOURCE)
     {
@@ -322,7 +323,7 @@ ObDuplicateObject(PEPROCESS SourceProcess,
 
     ObDereferenceObject(ObjectBody);
 
-    *TargetHandle = EX_HANDLE_TO_HANDLE(ExTargetHandle);
+    *TargetHandle = NewTargetHandle;
 
     return STATUS_SUCCESS;
   }
@@ -349,8 +350,8 @@ NtDuplicateObject (IN       HANDLE          SourceProcessHandle,
                   IN   HANDLE          TargetProcessHandle,
                   OUT  PHANDLE         TargetHandle  OPTIONAL,
                   IN   ACCESS_MASK     DesiredAccess,
-                  IN   BOOLEAN         InheritHandle,
-                  ULONG                Options)
+                  IN   ULONG           InheritHandle,
+                  IN   ULONG           Options)
 /*
  * FUNCTION: Copies a handle from one process space to another
  * ARGUMENTS:
@@ -390,9 +391,7 @@ NtDuplicateObject (IN       HANDLE          SourceProcessHandle,
    {
      _SEH_TRY
      {
-       ProbeForWrite(TargetHandle,
-                     sizeof(HANDLE),
-                     sizeof(ULONG));
+       ProbeForWriteHandle(TargetHandle);
      }
      _SEH_HANDLE
      {
@@ -456,14 +455,14 @@ NtDuplicateObject (IN     HANDLE          SourceProcessHandle,
            if (DesiredAccess & GENERIC_ANY)
            {
              RtlMapGenericMask(&DesiredAccess,
-                               ObjectType->Mapping);
+                               &ObjectType->TypeInfo.GenericMapping);
            }
          }
-         Status = ObCreateHandle(TargetProcess,
-                                 ObjectBody,
-                                 DesiredAccess,
-                                 InheritHandle,
-                                 &hTarget);
+         Status = ObpCreateHandle(TargetProcess,
+                                  ObjectBody,
+                                  DesiredAccess,
+                                  InheritHandle,
+                                  &hTarget);
 
          ObDereferenceObject(ObjectBody);
 
@@ -505,10 +504,10 @@ NtDuplicateObject (IN     HANDLE          SourceProcessHandle,
 }
 
 static VOID STDCALL
-DeleteHandleCallback(PHANDLE_TABLE HandleTable,
-                     PVOID Object,
-                     ULONG GrantedAccess,
-                     PVOID Context)
+SweepHandleCallback(PHANDLE_TABLE HandleTable,
+                    PVOID Object,
+                    ULONG GrantedAccess,
+                    PVOID Context)
 {
   POBJECT_HEADER ObjectHeader;
   PVOID ObjectBody;
@@ -516,7 +515,7 @@ DeleteHandleCallback(PHANDLE_TABLE HandleTable,
   PAGED_CODE();
 
   ObjectHeader = EX_OBJ_TO_HDR(Object);
-  ObjectBody = HEADER_TO_BODY(ObjectHeader);
+  ObjectBody = &ObjectHeader->Body;
 
   ObpDecrementHandleCount(ObjectBody);
 }
@@ -537,14 +536,16 @@ DuplicateHandleCallback(PHANDLE_TABLE HandleTable,
     ObjectHeader = EX_HTE_TO_HDR(HandleTableEntry);
     if(InterlockedIncrement(&ObjectHeader->HandleCount) == 1)
     {
-      ObReferenceObject(HEADER_TO_BODY(ObjectHeader));
+      ObReferenceObject(&ObjectHeader->Body);
     }
   }
 
   return Ret;
 }
 
-VOID ObCreateHandleTable(PEPROCESS Parent,
+VOID
+NTAPI
+ObCreateHandleTable(PEPROCESS Parent,
                         BOOLEAN Inherit,
                         PEPROCESS Process)
 /*
@@ -579,14 +580,18 @@ ObKillProcess(PEPROCESS Process)
 {
    PAGED_CODE();
 
-   ExDestroyHandleTable(Process->ObjectTable,
-                        DeleteHandleCallback,
-                        Process);
+   /* FIXME - Temporary hack: sweep and destroy here, needs to be fixed!!! */
+   ExSweepHandleTable(Process->ObjectTable,
+                      SweepHandleCallback,
+                      Process);
+   ExDestroyHandleTable(Process->ObjectTable);
+   Process->ObjectTable = NULL;
 }
 
 
 NTSTATUS
-ObCreateHandle(PEPROCESS Process,
+NTAPI
+ObpCreateHandle(PEPROCESS Process,
               PVOID ObjectBody,
               ACCESS_MASK GrantedAccess,
               BOOLEAN Inherit,
@@ -601,11 +606,11 @@ ObCreateHandle(PEPROCESS Process,
 {
    HANDLE_TABLE_ENTRY NewEntry;
    POBJECT_HEADER ObjectHeader;
-   LONG ExHandle;
+   HANDLE Handle;
 
    PAGED_CODE();
 
-   DPRINT("ObCreateHandle(Process %x, obj %x)\n",Process,ObjectBody);
+   DPRINT("ObpCreateHandle(Process %x, obj %x)\n",Process,ObjectBody);
 
    ASSERT(Process);
    ASSERT(ObjectBody);
@@ -623,7 +628,7 @@ ObCreateHandle(PEPROCESS Process,
    if (GrantedAccess & GENERIC_ANY)
      {
        RtlMapGenericMask(&GrantedAccess,
-                        ObjectHeader->ObjectType->Mapping);
+                        &ObjectHeader->Type->TypeInfo.GenericMapping);
      }
 
    NewEntry.u1.Object = ObjectHeader;
@@ -633,10 +638,10 @@ ObCreateHandle(PEPROCESS Process,
      NewEntry.u1.ObAttributes &= ~EX_HANDLE_ENTRY_INHERITABLE;
    NewEntry.u2.GrantedAccess = GrantedAccess;
 
-   ExHandle = ExCreateHandle(Process->ObjectTable,
-                             &NewEntry);
-   DPRINT("ObCreateHandle(0x%x)==0x%x [HT:0x%x]\n", ObjectHeader, *HandleReturn, Process->ObjectTable);
-   if(ExHandle != EX_INVALID_HANDLE)
+   Handle = ExCreateHandle(Process->ObjectTable,
+                           &NewEntry);
+   DPRINT("ObCreateHandle(0x%x)==0x%x [HT:0x%x]\n", ObjectHeader, Handle, Process->ObjectTable);
+   if(Handle != NULL)
    {
      if(InterlockedIncrement(&ObjectHeader->HandleCount) == 1)
      {
@@ -646,7 +651,7 @@ ObCreateHandle(PEPROCESS Process,
                                 UserMode);
      }
 
-     *HandleReturn = EX_HANDLE_TO_HANDLE(ExHandle);
+     *HandleReturn = Handle;
 
      return STATUS_SUCCESS;
    }
@@ -664,7 +669,6 @@ ObQueryObjectAuditingByHandle(IN HANDLE Handle,
 {
   PHANDLE_TABLE_ENTRY HandleEntry;
   PEPROCESS Process;
-  LONG ExHandle = HANDLE_TO_EX_HANDLE(Handle);
 
   PAGED_CODE();
 
@@ -675,7 +679,7 @@ ObQueryObjectAuditingByHandle(IN HANDLE Handle,
   KeEnterCriticalRegion();
 
   HandleEntry = ExMapHandleToPointer(Process->ObjectTable,
-                                     ExHandle);
+                                     Handle);
   if(HandleEntry != NULL)
   {
     *GenerateOnClose = (HandleEntry->u1.ObAttributes & EX_HANDLE_ENTRY_AUDITONCLOSE) != 0;
@@ -723,7 +727,6 @@ ObReferenceObjectByHandle(HANDLE Handle,
    PVOID ObjectBody;
    ACCESS_MASK GrantedAccess;
    ULONG Attributes;
-   LONG ExHandle;
 
    PAGED_CODE();
 
@@ -731,6 +734,10 @@ ObReferenceObjectByHandle(HANDLE Handle,
           "ObjectType %x, AccessMode %d, Object %x)\n",Handle,DesiredAccess,
           ObjectType,AccessMode,Object);
 
+   if (Handle == NULL)
+     {
+       return STATUS_INVALID_HANDLE;
+     }
    /*
     * Handle special handle names
     */
@@ -790,18 +797,17 @@ ObReferenceObjectByHandle(HANDLE Handle,
    if(ObIsKernelHandle(Handle, AccessMode))
    {
       HandleTable = ObpKernelHandleTable;
-      ExHandle = HANDLE_TO_EX_HANDLE(ObKernelHandleToHandle(Handle));
+      Handle = ObKernelHandleToHandle(Handle);
    }
    else
    {
       HandleTable = PsGetCurrentProcess()->ObjectTable;
-      ExHandle = HANDLE_TO_EX_HANDLE(Handle);
    }
 
    KeEnterCriticalRegion();
 
    HandleEntry = ExMapHandleToPointer(HandleTable,
-                                     ExHandle);
+                                     Handle);
    if (HandleEntry == NULL)
      {
         KeLeaveCriticalRegion();
@@ -810,13 +816,13 @@ ObReferenceObjectByHandle(HANDLE Handle,
      }
 
    ObjectHeader = EX_HTE_TO_HDR(HandleEntry);
-   ObjectBody = HEADER_TO_BODY(ObjectHeader);
+   ObjectBody = &ObjectHeader->Body;
 
    DPRINT("locked1: ObjectHeader: 0x%x [HT:0x%x]\n", ObjectHeader, HandleTable);
 
-   if (ObjectType != NULL && ObjectType != ObjectHeader->ObjectType)
+   if (ObjectType != NULL && ObjectType != ObjectHeader->Type)
      {
-        DPRINT("ObjectType mismatch: %wZ vs %wZ (handle 0x%x)\n", &ObjectType->TypeName, ObjectHeader->ObjectType ? &ObjectHeader->ObjectType->TypeName : NULL, Handle);
+        DPRINT("ObjectType mismatch: %wZ vs %wZ (handle 0x%x)\n", &ObjectType->Name, ObjectHeader->Type ? &ObjectHeader->Type->Name : NULL, Handle);
 
         ExUnlockHandleTableEntry(HandleTable,
                                  HandleEntry);
@@ -830,7 +836,7 @@ ObReferenceObjectByHandle(HANDLE Handle,
    if (DesiredAccess & GENERIC_ANY)
      {
         RtlMapGenericMask(&DesiredAccess,
-                          BODY_TO_HEADER(ObjectBody)->ObjectType->Mapping);
+                          &BODY_TO_HEADER(ObjectBody)->Type->TypeInfo.GenericMapping);
      }
 
    GrantedAccess = HandleEntry->u2.GrantedAccess;
@@ -925,31 +931,224 @@ NtClose(IN HANDLE Handle)
 /*
  * @implemented
  */
-NTSTATUS STDCALL
+NTSTATUS 
+STDCALL
 ObInsertObject(IN PVOID Object,
-              IN PACCESS_STATE PassedAccessState OPTIONAL,
-              IN ACCESS_MASK DesiredAccess,
-              IN ULONG AdditionalReferences,
-              OUT PVOID* ReferencedObject OPTIONAL,
-              OUT PHANDLE Handle)
+               IN PACCESS_STATE PassedAccessState OPTIONAL,
+               IN ACCESS_MASK DesiredAccess,
+               IN ULONG AdditionalReferences,
+               OUT PVOID* ReferencedObject OPTIONAL,
+               OUT PHANDLE Handle)
 {
-  POBJECT_HEADER ObjectHeader;
-  ACCESS_MASK Access;
+    POBJECT_CREATE_INFORMATION ObjectCreateInfo;
+    POBJECT_HEADER Header;
+    POBJECT_HEADER_NAME_INFO ObjectNameInfo;
+    PVOID FoundObject = NULL;
+    POBJECT_HEADER FoundHeader = NULL;
+    NTSTATUS Status = STATUS_SUCCESS;
+    UNICODE_STRING RemainingPath;
+    BOOLEAN ObjectAttached = FALSE; 
+    PSECURITY_DESCRIPTOR NewSecurityDescriptor = NULL;
+    SECURITY_SUBJECT_CONTEXT SubjectContext;
+
+    PAGED_CODE();
+    
+    /* Get the Header and Create Info */
+    DPRINT("ObInsertObject: %x\n", Object);
+    Header = BODY_TO_HEADER(Object);
+    ObjectCreateInfo = Header->ObjectCreateInfo;
+    ObjectNameInfo = HEADER_TO_OBJECT_NAME(Header);
+    
+    /* First try to find the Object */
+    if (ObjectNameInfo && ObjectNameInfo->Name.Buffer)
+    {
+        DPRINT("Object has a name. Trying to find it: %wZ.\n", &ObjectNameInfo->Name);
+        Status = ObFindObject(ObjectCreateInfo,
+                              &ObjectNameInfo->Name,
+                              &FoundObject,
+                              &RemainingPath,
+                              NULL);
+        DPRINT("FoundObject: %x, Path: %wZ\n", FoundObject, &RemainingPath);
+        if (!NT_SUCCESS(Status))
+        {
+            DPRINT1("ObFindObject() failed! (Status 0x%x)\n", Status);
+            return Status;
+        }
+        
+        if (FoundObject)
+        {
+            DPRINT("Getting header: %x\n", FoundObject);
+            FoundHeader = BODY_TO_HEADER(FoundObject);
+        }
+        
+        if (FoundHeader && RemainingPath.Buffer == NULL)
+        {
+            DPRINT("Object exists\n");
+            ObDereferenceObject(FoundObject);
+            return STATUS_OBJECT_NAME_COLLISION;
+        }
+    }
+    else
+    {
+        DPRINT("No name, empty remaining path\n");
+        RtlInitUnicodeString(&RemainingPath, NULL);
+    }
 
-  PAGED_CODE();
+    if (FoundHeader && FoundHeader->Type == ObDirectoryType &&
+        RemainingPath.Buffer)
+    {
+        /* The name was changed so let's update it */
+        /* FIXME: TEMPORARY HACK This will go in ObFindObject in the next commit */
+        PVOID NewName;
+        PWSTR BufferPos = RemainingPath.Buffer;
+        ULONG Delta = 0;
+        
+        ObpAddEntryDirectory(FoundObject, Header, NULL);
+        ObjectAttached = TRUE;
+        
+        ObjectNameInfo = HEADER_TO_OBJECT_NAME(Header);
+        
+        if (BufferPos[0] == L'\\')
+        {
+            BufferPos++;
+            Delta = sizeof(WCHAR);
+        }
+        NewName = ExAllocatePool(NonPagedPool, RemainingPath.MaximumLength - Delta);
+        RtlMoveMemory(NewName, BufferPos, RemainingPath.MaximumLength - Delta);
+        if (ObjectNameInfo->Name.Buffer) ExFreePool(ObjectNameInfo->Name.Buffer);
+        ObjectNameInfo->Name.Buffer = NewName;
+        ObjectNameInfo->Name.Length = RemainingPath.Length - Delta;
+        ObjectNameInfo->Name.MaximumLength = RemainingPath.MaximumLength - Delta;
+        DPRINT("Name: %S\n", ObjectNameInfo->Name.Buffer);
+    }
+
+    if ((Header->Type == IoFileObjectType) ||
+        (Header->Type == ExDesktopObjectType) ||
+        (Header->Type->TypeInfo.OpenProcedure != NULL))
+    {    
+        DPRINT("About to call Open Routine\n");
+        if (Header->Type == IoFileObjectType)
+        {
+            /* TEMPORARY HACK. DO NOT TOUCH -- Alex */
+            DPRINT("Calling IopCreateFile: %x\n", FoundObject);
+            Status = IopCreateFile(&Header->Body,
+                                   FoundObject,
+                                   RemainingPath.Buffer,            
+                                   ObjectCreateInfo);
+            DPRINT("Called IopCreateFile: %x\n", Status);
+                                   
+        }
+        else if (Header->Type == ExDesktopObjectType)
+        {
+            /* TEMPORARY HACK. DO NOT TOUCH -- Alex */
+            DPRINT("Calling ExpDesktopCreate\n");
+            Status = ExpDesktopCreate(&Header->Body,
+                                      FoundObject,
+                                      RemainingPath.Buffer,            
+                                      ObjectCreateInfo);
+        }
+        else if (Header->Type->TypeInfo.OpenProcedure != NULL)
+        {
+            DPRINT("Calling %x\n", Header->Type->TypeInfo.OpenProcedure);
+            Status = Header->Type->TypeInfo.OpenProcedure(ObCreateHandle,
+                                                                &Header->Body,
+                                                                NULL,
+                                                                0,
+                                                                0);
+        }
+
+        if (!NT_SUCCESS(Status))
+        {
+            DPRINT("Create Failed\n");
+            if (ObjectAttached == TRUE)
+            {
+                ObpRemoveEntryDirectory(Header);
+            }
+            if (FoundObject)
+            {
+                ObDereferenceObject(FoundObject);
+            }
+            RtlFreeUnicodeString(&RemainingPath);
+            return Status;
+        }
+    }
 
-  Access = DesiredAccess;
-  ObjectHeader = BODY_TO_HEADER(Object);
+    RtlFreeUnicodeString(&RemainingPath);
+  
+    DPRINT("Security Assignment in progress\n");  
+    SeCaptureSubjectContext(&SubjectContext);
+
+    /* Build the new security descriptor */
+    Status = SeAssignSecurity((FoundHeader != NULL) ? FoundHeader->SecurityDescriptor : NULL,
+                           (ObjectCreateInfo != NULL) ? ObjectCreateInfo->SecurityDescriptor : NULL,
+                           &NewSecurityDescriptor,
+                           (Header->Type == ObDirectoryType),
+                           &SubjectContext,
+                           &Header->Type->TypeInfo.GenericMapping,
+                           PagedPool);
+
+    if (NT_SUCCESS(Status))
+    {
+        DPRINT("NewSecurityDescriptor %p\n", NewSecurityDescriptor);
 
-  return(ObCreateHandle(PsGetCurrentProcess(),
-                       Object,
-                       Access,
-                       ObjectHeader->Inherit,
-                       Handle));
+        if (Header->Type->TypeInfo.SecurityProcedure != NULL)
+        {
+            /* Call the security method */
+            Status = Header->Type->TypeInfo.SecurityProcedure(&Header->Body,
+                                                                    AssignSecurityDescriptor,
+                                                                    0,
+                                                                    NewSecurityDescriptor,
+                                                                    NULL,
+                                                                    NULL,
+                                                                    NonPagedPool,
+                                                                    NULL);
+        }
+        else
+        {
+            /* Assign the security descriptor to the object header */
+            Status = ObpAddSecurityDescriptor(NewSecurityDescriptor,
+                                              &Header->SecurityDescriptor);
+            DPRINT("Object security descriptor %p\n", Header->SecurityDescriptor);
+        }
+
+        /* Release the new security descriptor */
+        SeDeassignSecurity(&NewSecurityDescriptor);
+    }
+
+    DPRINT("Security Complete\n");
+    SeReleaseSubjectContext(&SubjectContext);
+        
+    /* Create the Handle */
+    /* HACKHACK: Because of ROS's incorrect startup, this can be called
+     * without a valid Process until I finalize the startup patch,
+     * so don't create a handle if this is the case. We also don't create
+     * a handle if Handle is NULL when the Registry Code calls it, because
+     * the registry code totally bastardizes the Ob and needs to be fixed
+     */
+    DPRINT("Creating handle\n");
+    if (Handle != NULL)
+    {
+        Status = ObpCreateHandle(PsGetCurrentProcess(),
+                                 &Header->Body,
+                                 DesiredAccess,
+                                 ObjectCreateInfo->Attributes & OBJ_INHERIT,
+                                 Handle);
+        DPRINT("handle Created: %d. refcount. handlecount %d %d\n",
+                 *Handle, Header->PointerCount, Header->HandleCount);
+    }
+    
+    /* We can delete the Create Info now */
+    Header->ObjectCreateInfo = NULL;
+    ObpReleaseCapturedAttributes(ObjectCreateInfo);
+    ExFreePool(ObjectCreateInfo);
+    
+    DPRINT("Status %x\n", Status);
+    return Status;
 }
 
 
 ULONG
+NTAPI
 ObpGetHandleCountByHandleTable(PHANDLE_TABLE HandleTable)
 {
   return HandleTable->HandleCount;
@@ -1000,7 +1199,7 @@ ObFindHandleForObject(IN PEPROCESS Process,
                       IN POBJECT_HANDLE_INFORMATION HandleInformation,
                       OUT PHANDLE HandleReturn)
 {
-  UNIMPLEMENTED;
+  DPRINT("ObFindHandleForObject is unimplemented!\n");
   return STATUS_UNSUCCESSFUL;
 }
 
@@ -1026,7 +1225,7 @@ ObpGetNextHandleByProcessCount(PSYSTEM_HANDLE_TABLE_ENTRY_INFO pshi,
 
 //      pshi->GrantedAccess;
 //      pshi->Object;
-//      pshi->ObjectTypeIndex;
+//      pshi->TypeIndex;
 //      pshi->HandleAttributes;
 
 //      KeReleaseSpinLock( &Process->HandleTable.ListLock, oldIrql );