Condividi tramite


Funzione RtlCreateHeap (ntifs.h)

La routine RtlCreateHeap crea un oggetto heap che può essere utilizzato dal processo chiamante. Questa routine riserva spazio nello spazio indirizzi virtuale del processo e alloca l'archiviazione fisica per una parte iniziale specificata di questo blocco.

Sintassi

NTSYSAPI PVOID RtlCreateHeap(
  [in]           ULONG                Flags,
  [in, optional] PVOID                HeapBase,
  [in, optional] SIZE_T               ReserveSize,
  [in, optional] SIZE_T               CommitSize,
  [in, optional] PVOID                Lock,
  [in, optional] PRTL_HEAP_PARAMETERS Parameters
);

Parametri

[in] Flags

Flag che specificano attributi facoltativi dell'heap. Queste opzioni influiscono sull'accesso successivo al nuovo heap tramite chiamate alle funzioni heap (RtlAllocateHeap e RtlFreeHeap).

I chiamanti devono impostare questo parametro su zero se non sono richiesti attributi facoltativi.

Questo parametro può essere uno o più dei valori seguenti.

Valore Significato
HEAP_GENERATE_EXCEPTIONS Specifica che il sistema indicherà un errore dell'heap generando un'eccezione, ad esempio STATUS_NO_MEMORY, anziché restituire NULL.
HEAP_GROWABLE Specifica che l'heap è espandibile. Deve essere specificato se heapBase è NULL.
HEAP_NO_SERIALIZE Specifica che l'esclusione reciproca non verrà usata quando le funzioni heap allocano e liberano memoria da questo heap. Il valore predefinito, quando non viene specificato HEAP_NO_SERIALIZE, consiste nel serializzare l'accesso all'heap. La serializzazione dell'accesso heap consente a due o più thread di allocare e liberare memoria contemporaneamente dallo stesso heap.

[in, optional] HeapBase

Specifica una delle due azioni seguenti:

Se heapBase è un valore non NULL, specifica l'indirizzo di base per un blocco di memoria allocata dal chiamante da usare per l'heap.

Se heapBase è NULL, RtlCreateHeap alloca la memoria di sistema per l'heap dallo spazio indirizzi virtuale del processo.

[in, optional] ReserveSize

Se ReserveSize è un valore diverso da zero, specifica la quantità iniziale di memoria, in byte, da riservare per l'heap. RtlCreateHeap arrotonda ReserveSize fino al limite di pagina successivo e quindi riserva un blocco di tale dimensione per l'heap.

Questo parametro è facoltativo e può essere zero. La tabella seguente riepiloga l'interazione dei parametri ReserveSize e CommitSize.

Valori Risultato
ReserveSize zero, CommitSize zero 64 pagine sono inizialmente riservate all'heap. Viene eseguito inizialmente il commit di una pagina.
ReserveSize zero, CommitSize diverso da zero RtlCreateHeap imposta ReserveSize essere uguale a CommitSizee quindi arrotonda ReserveSize fino al multiplo più vicino di (PAGE_SIZE * 16).
ReserveSize diverso da zero, CommitSize zero Inizialmente viene eseguito il commit di una pagina per l'heap.
ReserveSize diverso da zero, CommitSize diverso da zero Se CommitSize è maggiore di ReserveSize, RtlCreateHeap riduce CommitSize a ReserveSize.

[in, optional] CommitSize

Se CommitSize è un valore diverso da zero, specifica la quantità iniziale di memoria, espressa in byte, per eseguire il commit per l'heap. RtlCreateHeap arrotonda CommitSize fino al limite di pagina successivo e quindi esegue il commit di un blocco di tale dimensione nello spazio indirizzi virtuale del processo per l'heap.

Questo parametro è facoltativo e può essere zero.

[in, optional] Lock

Puntatore a una struttura ERESOURCE opaca da usare come blocco delle risorse. Questo parametro è facoltativo e può essere NULL. Se fornito dal chiamante, la struttura deve essere allocata da un pool non di paging e inizializzata chiamando ExInitializeResourceLite o ExReinitializeResourceLite. Se il flag HEAP_NO_SERIALIZE è impostato, questo parametro deve essere NULL.

[in, optional] Parameters

Puntatore a una struttura RTL_HEAP_PARAMETERS che contiene parametri da applicare durante la creazione dell'heap. Questo parametro è facoltativo e può essere NULL.

Valore restituito

RtlCreateHeap restituisce un handle da usare per accedere all'heap creato.

Osservazioni

RtlCreateHeap crea un oggetto heap privato da cui il processo chiamante può allocare blocchi di memoria chiamando RtlAllocateHeap. Le dimensioni del commit iniziale determinano il numero di pagine inizialmente allocate per l'heap. Le dimensioni di riserva iniziali determinano il numero di pagine inizialmente riservate per l'heap. Le pagine riservate ma non sottoposte a commit creano un blocco nello spazio indirizzi virtuale del processo in cui l'heap può espandersi.

Se le richieste di allocazione effettuate da RtlAllocateHeap superare le dimensioni iniziali del commit dell'heap, il sistema esegue il commit di pagine aggiuntive di archiviazione fisica per l'heap, fino alle dimensioni massime dell'heap. Se l'heap non è scalabile, la dimensione massima è limitata alle dimensioni iniziali della riserva.

Se l'heap è espandibile, le dimensioni sono limitate solo dalla memoria disponibile. Se le richieste da RtlAllocateHeap superare le dimensioni correnti delle pagine di cui è stato eseguito il commit, il sistema chiama ZwAllocateVirtualMemory per ottenere la memoria necessaria, presupponendo che l'archiviazione fisica sia disponibile.

Inoltre, se l'heap non è scalabile, si verifica una limitazione assoluta: la dimensione massima di un blocco di memoria nell'heap è 0x7F000 byte. La soglia di memoria virtuale dell'heap è uguale alla dimensione massima del blocco heap o al valore della VirtualMemoryThreshold membro della struttura parametri di , a meno di . L'heap potrebbe anche dover riempire le dimensioni della richiesta per i metadati e gli scopi di allineamento, in modo che le richieste di allocare blocchi entro 4096 byte (1 pagina) della VirtualMemoryThreshold potrebbero non riuscire anche se le dimensioni massime dell'heap sono sufficienti per contenere il blocco. Per altre informazioni su VirtualMemoryThreshold, vedere i membri del parametro parameters per RtlCreateHeap.

Se l'heap è scalabile, le richieste di allocare blocchi superiori alla soglia di memoria virtuale dell'heap non hanno esito negativo automaticamente; il sistema chiama ZwAllocateVirtualMemory per ottenere la memoria necessaria per tali blocchi di grandi dimensioni.

La memoria di un oggetto heap privato è accessibile solo al processo che lo ha creato.

Il sistema usa memoria dall'heap privato per archiviare le strutture di supporto dell'heap, quindi non tutte le dimensioni dell'heap specificate sono disponibili per il processo. Ad esempio, se RtlAllocateHeap richiede 64 kilobyte (K) da un heap con una dimensione massima di 64 K, la richiesta potrebbe non riuscire a causa del sovraccarico del sistema.

Se HEAP_NO_SERIALIZE non viene specificato (impostazione predefinita semplice), l'heap serializzerà l'accesso all'interno del processo chiamante. La serializzazione garantisce l'esclusione reciproca quando due o più thread tentano di allocare o liberare contemporaneamente blocchi dallo stesso heap. La serializzazione prevede un costo di prestazioni ridotto, ma deve essere usata ogni volta che più thread allocano e liberano memoria dallo stesso heap.

L'impostazione di HEAP_NO_SERIALIZE elimina l'esclusione reciproca nell'heap. Senza serializzazione, due o più thread che usano lo stesso handle heap potrebbero tentare di allocare o liberare memoria contemporaneamente, causando probabilmente il danneggiamento nell'heap. Pertanto, HEAP_NO_SERIALIZE può essere usato in modo sicuro solo nelle situazioni seguenti:

  • Il processo ha un solo thread.

  • Il processo ha più thread, ma un solo thread chiama le funzioni dell'heap per un heap specifico.

  • Il processo ha più thread e l'applicazione fornisce il proprio meccanismo per l'esclusione reciproca in un heap specifico.

Nota

Per proteggersi da una violazione di accesso, usare la gestione delle eccezioni strutturata per proteggere qualsiasi codice che scrive o legge da un heap. Per altre informazioni sulla gestione delle eccezioni strutturate con gli accessi alla memoria, vedere Gestione delle eccezioni**.

Fabbisogno

Requisito Valore
client minimo supportato Windows XP
piattaforma di destinazione Universale
intestazione ntifs.h (include Ntifs.h)
libreria Ntoskrnl.lib
dll NtosKrnl.exe (modalità kernel); Ntdll.dll (modalità utente)
IRQL < DISPATCH_LEVEL

Vedere anche

RtlAllocateHeap

RtlDestroyHeap

RtlFreeHeap