Expand Minimize

RtlCreateHeap routine

The RtlCreateHeap routine creates a heap object that can be used by the calling process. This routine reserves space in the virtual address space of the process and allocates physical storage for a specified initial portion of this block.

Syntax


PVOID RtlCreateHeap(
  _In_      ULONG Flags,
  _In_opt_  PVOID HeapBase,
  _In_opt_  SIZE_T ReserveSize,
  _In_opt_  SIZE_T CommitSize,
  _In_opt_  PVOID Lock,
  _In_opt_  PRTL_HEAP_PARAMETERS Parameters
);

Parameters

Flags [in]

Flags specifying optional attributes of the heap. These options affect subsequent access to the new heap through calls to the heap functions (RtlAllocateHeap and RtlFreeHeap).

Callers should set this parameter to zero if no optional attributes are requested.

This parameter can be one or more of the following values.

HEAP_GENERATE_EXCEPTIONS

Specifies that the system will indicate a heap failure by raising an exception, such as STATUS_NO_MEMORY, instead of returning NULL.

HEAP_GROWABLE

Specifies that the heap is growable. Must be specified if HeapBase is NULL.

HEAP_NO_SERIALIZE

Specifies that mutual exclusion will not be used when the heap functions allocate and free memory from this heap. The default, when HEAP_NO_SERIALIZE is not specified, is to serialize access to the heap. Serialization of heap access allows two or more threads to simultaneously allocate and free memory from the same heap.

HeapBase [in, optional]

Specifies one of two actions:

If HeapBase is a non-NULL value, it specifies the base address for a block of caller-allocated memory to use for the heap.

If HeapBase is NULL, RtlCreateHeap allocates system memory for the heap from the process's virtual address space.

ReserveSize [in, optional]

If ReserveSize is a nonzero value, it specifies the initial amount of memory, in bytes, to reserve for the heap. RtlCreateHeap rounds ReserveSize up to the next page boundary, and then reserves a block of that size for the heap.

This parameter is optional and can be zero. The following table summarizes the interaction of the ReserveSize and CommitSize parameters.

ValuesResult

ReserveSize zero, CommitSize zero

64 pages are initially reserved for the heap. One page is initially committed.

ReserveSize zero, CommitSize nonzero

RtlCreateHeap sets ReserveSize to be equal to CommitSize, and then rounds ReserveSize up to the nearest multiple of (PAGE_SIZE * 16).

ReserveSize nonzero, CommitSize zero

One page is initially committed for the heap.

ReserveSize nonzero, CommitSize nonzero

If CommitSize is greater than ReserveSize, RtlCreateHeap reduces CommitSize to ReserveSize.

 

CommitSize [in, optional]

If CommitSize is a nonzero value, it specifies the initial amount of memory, in bytes, to commit for the heap. RtlCreateHeap rounds CommitSize up to the next page boundary, and then commits a block of that size in the process's virtual address space for the heap.

This parameter is optional and can be zero.

Lock [in, optional]

Pointer to an opaque ERESOURCE structure to be used as a resource lock. This parameter is optional and can be NULL. When provided by the caller, the structure must be allocated from nonpaged pool and initialized by calling ExInitializeResourceLite or ExReinitializeResourceLite. If the HEAP_NO_SERIALIZE flag is set, this parameter must be NULL.

Parameters [in, optional]

Pointer to a RTL_HEAP_PARAMETERS structure that contains parameters to be applied when creating the heap. This parameter is optional and can be NULL.


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;

MemberValue

Length

Size, in bytes, of the RTL_HEAP_PARAMETERS structure.

SegmentReserve

Segment reserve size, in bytes. If this value is not specified, 1 MB is used.

SegmentCommit

Segment commit size, in bytes. If this value is not specified, PAGE_SIZE * 2 is used.

DeCommitFreeBlockThreshold

Decommit free block threshold, in bytes. If this value is not specified, PAGE_SIZE is used.

DeCommitTotalFreeThreshold

Decommit total free threshold, in bytes. If this value is not specified, 65536 is used.

MaximumAllocationSize

Size, in bytes, of the largest block of memory that can be allocated from the heap. If this value is not specified, the difference between the highest and lowest addresses, less one page, is used.

VirtualMemoryThreshold

Virtual memory threshold, in bytes. If this value is not specified, or if it is greater than the maximum heap block size, the maximum heap block size of 0x7F000 is used.

InitialCommit

Initial amount of memory, in bytes, to commit for the heap.

Must be less than or equal to InitialReserve.

If HeapBase and CommitRoutine are non-NULL, this parameter, which overrides the value of CommitSize, must be a nonzero value; otherwise it is ignored.

InitialReserve

Initial amount of memory, in bytes, to reserve for the heap.

If HeapBase and CommitRoutine are non-NULL, this parameter, which overrides the value of ReserveSize, must be a nonzero value; otherwise it is ignored.

CommitRoutine

Callback routine to commit pages from the heap. If this parameter is non-NULL, the heap must be nongrowable.

If HeapBase is NULL, CommitRoutine must also be NULL.

Reserved

Reserved for system use. Drivers must set this parameter to zero.

 


typedef NTSTATUS
(NTAPI * PRTL_HEAP_COMMIT_ROUTINE)(
    IN PVOID Base,
    IN OUT PVOID *CommitAddress,
    IN OUT PSIZE_T CommitSize
    );

ParameterMeaning

Base

Base address for the block of caller-allocated memory being used for the heap.

CommitAddress

Pointer to a variable that will receive the base address of the committed region of pages.

CommitSize

Pointer to a variable that will receive the actual size, in bytes, of the allocated region of pages.

 

Return value

RtlCreateHeap returns a handle to be used in accessing the created heap.

Remarks

RtlCreateHeap creates a private heap object from which the calling process can allocate memory blocks by calling RtlAllocateHeap. The initial commit size determines the number of pages that are initially allocated for the heap. The initial reserve size determines the number of pages that are initially reserved for the heap. Pages that are reserved but uncommitted create a block in the process's virtual address space into which the heap can expand.

If allocation requests made by RtlAllocateHeap exceed the heap's initial commit size, the system commits additional pages of physical storage for the heap, up to the heap's maximum size. If the heap is nongrowable, its maximum size is limited to its initial reserve size.

If the heap is growable, its size is limited only by available memory. If requests by RtlAllocateHeap exceed the current size of committed pages, the system calls ZwAllocateVirtualMemory to obtain the memory needed, assuming that the physical storage is available.

In addition, if the heap is nongrowable, an absolute limitation arises: the maximum size of a memory block in the heap is 0x7F000 bytes. The virtual memory threshold of the heap is equal to the maximum heap block size or the value of the VirtualMemoryThreshold member of the Parameters structure, whichever is less. Requests to allocate blocks larger than the virtual memory threshold will fail, even if the maximum size of the heap is large enough to contain the block.

If the heap is growable, requests to allocate blocks larger than the heap's virtual memory threshold do not automatically fail; the system calls ZwAllocateVirtualMemory to obtain the memory needed for such large blocks.

The memory of a private heap object is accessible only to the process that created it.

The system uses memory from the private heap to store heap support structures, so not all of the specified heap size is available to the process. For example, if RtlAllocateHeap requests 64 kilobytes (K) from a heap with a maximum size of 64K, the request may fail because of system overhead.

If HEAP_NO_SERIALIZE is not specified (the simple default), the heap will serialize access within the calling process. Serialization ensures mutual exclusion when two or more threads attempt to simultaneously allocate or free blocks from the same heap. There is a small performance cost to serialization, but it must be used whenever multiple threads allocate and free memory from the same heap.

Setting HEAP_NO_SERIALIZE eliminates mutual exclusion on the heap. Without serialization, two or more threads that use the same heap handle might attempt to allocate or free memory simultaneously, likely causing corruption in the heap. Therefore, HEAP_NO_SERIALIZE can safely be used only in the following situations:

  • The process has only one thread.

  • The process has multiple threads, but only one thread calls the heap functions for a specific heap.

  • The process has multiple threads, and the application provides its own mechanism for mutual exclusion to a specific heap.

Note  

To guard against an access violation, use structured exception handling to protect any code that writes to or reads from a heap. For more information about structured exception handling with memory accesses, see Handling Exceptions.

Requirements

Version

This routine is available on Microsoft Windows XP and later.

Header

Ntifs.h (include Ntifs.h)

Library

Ntoskrnl.lib

IRQL

< DISPATCH_LEVEL

See also

RtlAllocateHeap
RtlDestroyHeap
RtlFreeHeap

 

 

Send comments about this topic to Microsoft

Show:
© 2014 Microsoft