Fix prototype of RtlCreateHeap and respect the CommitRoutine if passed. Also fix the heap manager to be usable by kernel mode code.
Modified: trunk/reactos/include/ndk/rtlfuncs.h
Modified: trunk/reactos/include/ndk/rtltypes.h
Modified: trunk/reactos/lib/rtl/heap.c
Modified: trunk/reactos/lib/rtl/ppb.c
Modified: trunk/reactos/lib/rtl/rtl.h
Modified: trunk/reactos/w32api/include/ddk/ntifs.h

Modified: trunk/reactos/include/ndk/rtlfuncs.h
--- trunk/reactos/include/ndk/rtlfuncs.h	2005-08-01 09:23:13 UTC (rev 16938)
+++ trunk/reactos/include/ndk/rtlfuncs.h	2005-08-01 10:19:22 UTC (rev 16939)
@@ -81,10 +81,10 @@
 RtlCreateHeap(
     IN ULONG Flags,
     IN PVOID BaseAddress OPTIONAL,
-    IN ULONG SizeToReserve OPTIONAL,
-    IN ULONG SizeToCommit OPTIONAL,
+    IN SIZE_T SizeToReserve OPTIONAL,
+    IN SIZE_T SizeToCommit OPTIONAL,
     IN PVOID Lock OPTIONAL,
-    IN PRTL_HEAP_DEFINITION Definition OPTIONAL
+    IN PRTL_HEAP_PARAMETERS Parameters OPTIONAL
 );
 
 DWORD

Modified: trunk/reactos/include/ndk/rtltypes.h
--- trunk/reactos/include/ndk/rtltypes.h	2005-08-01 09:23:13 UTC (rev 16938)
+++ trunk/reactos/include/ndk/rtltypes.h	2005-08-01 10:19:22 UTC (rev 16939)
@@ -109,6 +109,15 @@
     PVOID Parameter
 );
 
+#ifndef _NTIFS_
+typedef NTSTATUS
+(NTAPI * PRTL_HEAP_COMMIT_ROUTINE) (
+    IN PVOID Base,
+    IN OUT PVOID *CommitAddress,
+    IN OUT PSIZE_T CommitSize
+);
+#endif
+
 /* TYPES *********************************************************************/
 
 typedef unsigned short RTL_ATOM;
@@ -219,12 +228,6 @@
     ULONG ModuleCount;
     DEBUG_MODULE_INFORMATION ModuleEntry[1];
 } MODULE_INFORMATION, *PMODULE_INFORMATION;
-
-typedef struct _RTL_HEAP_DEFINITION
-{
-    ULONG Length;
-    ULONG Unknown[11];
-} RTL_HEAP_DEFINITION, *PRTL_HEAP_DEFINITION;
 /* END REVIEW AREA */
 
 #ifdef _INC_EXCPT
@@ -399,6 +402,22 @@
     PRTL_ATOM_TABLE_ENTRY Buckets[1];
 } RTL_ATOM_TABLE, *PRTL_ATOM_TABLE;
 
+#ifndef _NTIFS_
+typedef struct _RTL_HEAP_PARAMETERS {
+    ULONG Length;
+    SIZE_T SegmentReserve;
+    SIZE_T SegmentCommit;
+    SIZE_T DeCommitFreeBlockThreshold;
+    SIZE_T DeCommitTotalFreeThreshold;
+    SIZE_T MaximumAllocationSize;
+    SIZE_T VirtualMemoryThreshold;
+    SIZE_T InitialCommit;
+    SIZE_T InitialReserve;
+    PRTL_HEAP_COMMIT_ROUTINE CommitRoutine;
+    SIZE_T Reserved[2];
+} RTL_HEAP_PARAMETERS, *PRTL_HEAP_PARAMETERS;
+#endif
+
 /* Let Kernel Drivers use this */
 #ifndef _WINBASE_
     typedef struct _SYSTEMTIME

Modified: trunk/reactos/lib/rtl/heap.c
--- trunk/reactos/lib/rtl/heap.c	2005-08-01 09:23:13 UTC (rev 16938)
+++ trunk/reactos/lib/rtl/heap.c	2005-08-01 10:19:22 UTC (rev 16939)
@@ -96,7 +96,7 @@
    RTL_CRITICAL_SECTION critSection;   /* Critical section for serialization */
    ULONG            flags;         /* Heap flags */
    ULONG            magic;         /* Magic number */
-   UCHAR            filler[4];     /* Make multiple of 8 bytes */
+   PRTL_HEAP_COMMIT_ROUTINE commitRoutine;
 }
 HEAP, *PHEAP;
 
@@ -301,12 +301,19 @@
    address = (PVOID)((char *)subheap + subheap->commitSize);
    commitsize = size - subheap->commitSize;
 
-   Status = NtAllocateVirtualMemory(NtCurrentProcess(),
-                                    &address,
-                                    0,
-                                    &commitsize,
-                                    MEM_COMMIT,
-                                    PAGE_EXECUTE_READWRITE);
+   if (subheap->heap->commitRoutine != NULL)
+   {
+      Status = subheap->heap->commitRoutine(subheap->heap, &address, &commitsize);
+   }
+   else
+   {
+      Status = NtAllocateVirtualMemory(NtCurrentProcess(),
+                                       &address,
+                                       0,
+                                       &commitsize,
+                                       MEM_COMMIT,
+                                       PAGE_EXECUTE_READWRITE);
+   }
    if (!NT_SUCCESS(Status))
    {
       DPRINT( "Could not commit %08lx bytes at %p for heap %p\n",
@@ -321,6 +328,7 @@
 }
 
 
+#if 0
 /***********************************************************************
  *           HEAP_Decommit
  *
@@ -356,8 +364,8 @@
    subheap->commitSize -= decommitsize;
    return TRUE;
 }
+#endif
 
-
 /***********************************************************************
  *           HEAP_CreateFreeBlock
  *
@@ -504,27 +512,14 @@
  *           HEAP_InitSubHeap
  */
 static BOOLEAN HEAP_InitSubHeap( HEAP *heap, PVOID address, ULONG flags,
-                              ULONG commitSize, ULONG totalSize )
+                                 ULONG commitSize, ULONG totalSize,
+                                 PRTL_HEAP_PARAMETERS Parameters )
 {
    SUBHEAP *subheap = (SUBHEAP *)address;
    FREE_LIST_ENTRY *pEntry;
    int i;
    NTSTATUS Status;
 
-   /* Commit memory */
-   Status = ZwAllocateVirtualMemory(NtCurrentProcess(),
-                                    &address,
-                                    0,
-                                    (PULONG)&commitSize,
-                                    MEM_COMMIT,
-                                    PAGE_EXECUTE_READWRITE);
-   if (!NT_SUCCESS(Status))
-   {
-      DPRINT("Could not commit %08lx bytes for sub-heap %p\n",
-             commitSize, address);
-      return FALSE;
-   }
-
    /* Fill the sub-heap structure */
 
    subheap = (PSUBHEAP)address;
@@ -550,6 +545,10 @@
       heap->next          = NULL;
       heap->flags         = flags;
       heap->magic         = HEAP_MAGIC;
+      if (Parameters)
+         heap->commitRoutine = Parameters->CommitRoutine;
+      else
+         heap->commitRoutine = NULL;
 
       /* Build the free lists */
 
@@ -570,6 +569,27 @@
       RtlInitializeCriticalSection( &heap->critSection );
    }
 
+   /* Commit memory */
+   if (heap->commitRoutine)
+   {
+      Status = heap->commitRoutine(heap, &address, &commitSize);
+   }
+   else
+   {
+      Status = ZwAllocateVirtualMemory(NtCurrentProcess(),
+                                       &address,
+                                       0,
+                                       &commitSize,
+                                       MEM_COMMIT,
+                                       PAGE_EXECUTE_READWRITE);
+   }
+   if (!NT_SUCCESS(Status))
+   {
+      DPRINT("Could not commit %08lx bytes for sub-heap %p\n",
+             commitSize, address);
+      return FALSE;
+   }
+
    /* Create the first free block */
 
    HEAP_CreateFreeBlock( subheap, (PUCHAR)subheap + subheap->headerSize,
@@ -586,8 +606,9 @@
  */
 static PSUBHEAP
 HEAP_CreateSubHeap(PVOID BaseAddress,
-                                   HEAP *heap, ULONG flags,
-                                   ULONG commitSize, ULONG totalSize )
+                   HEAP *heap, ULONG flags,
+                   ULONG commitSize, ULONG totalSize,
+                   PRTL_HEAP_PARAMETERS Parameters )
 {
    PVOID address;
    NTSTATUS Status;
@@ -621,8 +642,9 @@
 
    /* Initialize subheap */
 
-   if (!HEAP_InitSubHeap( heap? heap : (HEAP *)address,
-                          address, flags, commitSize, totalSize ))
+   if (!HEAP_InitSubHeap( heap ? heap : (HEAP *)address,
+                          address, flags, commitSize, totalSize,
+                          Parameters ))
    {
       if (!BaseAddress)
       {
@@ -690,7 +712,7 @@
     * might get assigned all remaining free space in HEAP_ShrinkBlock() */
    size += sizeof(SUBHEAP) + sizeof(ARENA_FREE) + HEAP_MIN_BLOCK_SIZE;
    if (!(subheap = HEAP_CreateSubHeap( NULL, heap, heap->flags, size,
-                                       max( HEAP_DEF_SIZE, size ) )))
+                                       max( HEAP_DEF_SIZE, size ), NULL )))
       return NULL;
 
    DPRINT("created new sub-heap %p of %08lx bytes for heap %p\n",
@@ -1055,10 +1077,10 @@
 HANDLE STDCALL
 RtlCreateHeap(ULONG flags,
               PVOID BaseAddress,
-              ULONG maxSize,
-              ULONG initialSize,
-              PVOID Unknown,
-              PRTL_HEAP_DEFINITION Definition)
+              SIZE_T maxSize,
+              SIZE_T initialSize,
+              PVOID Lock,
+              PRTL_HEAP_PARAMETERS Parameters)
 {
    SUBHEAP *subheap;
    HEAP *heapPtr;
@@ -1070,20 +1092,24 @@
       maxSize = HEAP_DEF_SIZE;
       flags |= HEAP_GROWABLE;
    }
-   if (!(subheap = HEAP_CreateSubHeap( BaseAddress, NULL, flags, initialSize, maxSize )))
+   if (!(subheap = HEAP_CreateSubHeap( BaseAddress, NULL, flags, initialSize,
+                                       maxSize, Parameters )))
    {
       return 0;
    }
 
-   /* link it into the per-process heap list */
-   RtlEnterCriticalSection (&RtlpProcessHeapsListLock);
+   if (RtlpGetMode() == UserMode)
+   {
+      /* link it into the per-process heap list */
+      RtlEnterCriticalSection (&RtlpProcessHeapsListLock);
 
-   heapPtr = subheap->heap;
-   heapPtr->next = (HEAP*)NtCurrentPeb()->ProcessHeaps;
-   NtCurrentPeb()->ProcessHeaps = (HANDLE)heapPtr;
-   NtCurrentPeb()->NumberOfHeaps++;
+      heapPtr = subheap->heap;
+      heapPtr->next = (HEAP*)NtCurrentPeb()->ProcessHeaps;
+      NtCurrentPeb()->ProcessHeaps = (HANDLE)heapPtr;
+      NtCurrentPeb()->NumberOfHeaps++;
 
-   RtlLeaveCriticalSection (&RtlpProcessHeapsListLock);
+      RtlLeaveCriticalSection (&RtlpProcessHeapsListLock);
+   }
 
    return (HANDLE)subheap;
 }
@@ -1112,18 +1138,21 @@
    if (!heapPtr)
       return heap;
 
-   if (heap == NtCurrentPeb()->ProcessHeap)
-      return heap; /* cannot delete the main process heap */
+   if (RtlpGetMode() == UserMode)
+   {
+      if (heap == NtCurrentPeb()->ProcessHeap)
+         return heap; /* cannot delete the main process heap */
 
-   /* remove it from the per-process list */
-   RtlEnterCriticalSection (&RtlpProcessHeapsListLock);
+      /* remove it from the per-process list */
+      RtlEnterCriticalSection (&RtlpProcessHeapsListLock);
 
-   pptr = (HEAP**)&NtCurrentPeb()->ProcessHeaps;
-   while (*pptr && *pptr != heapPtr) pptr = &(*pptr)->next;
-   if (*pptr) *pptr = (*pptr)->next;
-   NtCurrentPeb()->NumberOfHeaps--;
+      pptr = (HEAP**)&NtCurrentPeb()->ProcessHeaps;
+      while (*pptr && *pptr != heapPtr) pptr = &(*pptr)->next;
+      if (*pptr) *pptr = (*pptr)->next;
+      NtCurrentPeb()->NumberOfHeaps--;
 
-   RtlLeaveCriticalSection (&RtlpProcessHeapsListLock);
+      RtlLeaveCriticalSection (&RtlpProcessHeapsListLock);
+   }
 
    RtlDeleteCriticalSection( &heapPtr->critSection );
    subheap = &heapPtr->subheap;

Modified: trunk/reactos/lib/rtl/ppb.c
--- trunk/reactos/lib/rtl/ppb.c	2005-08-01 09:23:13 UTC (rev 16938)
+++ trunk/reactos/lib/rtl/ppb.c	2005-08-01 10:19:22 UTC (rev 16939)
@@ -22,11 +22,6 @@
 #define DENORMALIZE(x,addr) {if(x) x=(PVOID)((ULONG_PTR)(x)-(ULONG_PTR)(addr));}
 #define ALIGN(x,align)      (((ULONG)(x)+(align)-1UL)&(~((align)-1UL)))
 
-
-KPROCESSOR_MODE
-RtlpGetMode();
-
-
 /* FUNCTIONS ****************************************************************/
 
 

Modified: trunk/reactos/lib/rtl/rtl.h
--- trunk/reactos/lib/rtl/rtl.h	2005-08-01 09:23:13 UTC (rev 16938)
+++ trunk/reactos/lib/rtl/rtl.h	2005-08-01 10:19:22 UTC (rev 16939)
@@ -29,6 +29,7 @@
 
 extern PVOID RtlpAllocateMemory(UINT Bytes, ULONG Tag);
 extern VOID RtlpFreeMemory(PVOID Mem, ULONG Tag);
+extern KPROCESSOR_MODE RtlpGetMode();
 
 #define RtlpAllocateStringMemory RtlpAllocateMemory
 #define RtlpFreeStringMemory RtlpFreeMemory

Modified: trunk/reactos/w32api/include/ddk/ntifs.h
--- trunk/reactos/w32api/include/ddk/ntifs.h	2005-08-01 09:23:13 UTC (rev 16938)
+++ trunk/reactos/w32api/include/ddk/ntifs.h	2005-08-01 10:19:22 UTC (rev 16939)
@@ -1486,6 +1486,27 @@
 
 #endif
 
+typedef NTSTATUS
+(NTAPI * PRTL_HEAP_COMMIT_ROUTINE) (
+    IN PVOID  Base,
+    IN OUT PVOID  *CommitAddress,
+    IN OUT PSIZE_T  CommitSize
+);
+
+typedef struct _RTL_HEAP_PARAMETERS {
+    ULONG                     Length;
+    SIZE_T                    SegmentReserve;
+    SIZE_T                    SegmentCommit;
+    SIZE_T                    DeCommitFreeBlockThreshold;
+    SIZE_T                    DeCommitTotalFreeThreshold;
+    SIZE_T                    MaximumAllocationSize;
+    SIZE_T                    VirtualMemoryThreshold;
+    SIZE_T                    InitialCommit;
+    SIZE_T                    InitialReserve;
+    PRTL_HEAP_COMMIT_ROUTINE  CommitRoutine;
+    SIZE_T                    Reserved[2];
+} RTL_HEAP_PARAMETERS, *PRTL_HEAP_PARAMETERS;
+
 NTKERNELAPI
 BOOLEAN
 NTAPI
@@ -2171,6 +2192,18 @@
 );
 
 NTKERNELAPI
+PVOID
+NTAPI
+RtlCreateHeap (
+    IN ULONG                Flags,
+    IN PVOID                HeapBase OPTIONAL,
+    IN SIZE_T               ReserveSize OPTIONAL,
+    IN SIZE_T               CommitSize OPTIONAL,
+    IN PVOID                Lock OPTIONAL,
+    IN PRTL_HEAP_PARAMETERS Parameters OPTIONAL
+);
+
+NTKERNELAPI
 BOOLEAN
 NTAPI
 FsRtlCurrentBatchOplock (
@@ -2200,6 +2233,13 @@
 );
 
 NTKERNELAPI
+PVOID
+NTAPI
+RtlDestroyHeap(
+    IN PVOID HeapHandle
+);
+
+NTKERNELAPI
 VOID
 NTAPI
 FsRtlDissectDbcs (