|
|
/*++
Copyright (c) 1990 Microsoft Corporation
Module Name:
lmem.c
Abstract:
This module contains the Win32 Local Memory Management APIs
Author:
Steve Wood (stevewo) 24-Sep-1990
Revision History:
--*/
#include "basedll.h"
void BaseDllInitializeMemoryManager( VOID ) { BaseHeap = RtlProcessHeap(); RtlInitializeHandleTable( 0xFFFF, sizeof( BASE_HANDLE_TABLE_ENTRY ), &BaseHeapHandleTable ); NtQuerySystemInformation(SystemRangeStartInformation, &SystemRangeStart, sizeof(SystemRangeStart), NULL); }
#if i386
#pragma optimize("y",off)
#endif
HLOCAL WINAPI LocalAlloc( UINT uFlags, SIZE_T uBytes ) { PBASE_HANDLE_TABLE_ENTRY HandleEntry; HANDLE hMem; ULONG Flags; LPSTR p;
if (uFlags & ~LMEM_VALID_FLAGS) { SetLastError( ERROR_INVALID_PARAMETER ); return( NULL ); }
Flags = 0; if (uFlags & LMEM_ZEROINIT) { Flags |= HEAP_ZERO_MEMORY; }
if (!(uFlags & LMEM_MOVEABLE)) { p = RtlAllocateHeap( BaseHeap, MAKE_TAG( LMEM_TAG ) | Flags, uBytes ); if (p == NULL) { SetLastError( ERROR_NOT_ENOUGH_MEMORY ); }
return( p ); }
RtlLockHeap( BaseHeap ); Flags |= HEAP_NO_SERIALIZE | HEAP_SETTABLE_USER_VALUE | BASE_HEAP_FLAG_MOVEABLE; try { p = NULL; HandleEntry = (PBASE_HANDLE_TABLE_ENTRY)RtlAllocateHandle( &BaseHeapHandleTable, NULL ); if (HandleEntry == NULL) { SetLastError( ERROR_NOT_ENOUGH_MEMORY ); goto Fail; }
hMem = (HANDLE)&HandleEntry->Object; if (uBytes != 0) { p = (LPSTR)RtlAllocateHeap( BaseHeap, MAKE_TAG( LMEM_TAG ) | Flags, uBytes ); if (p == NULL) { HandleEntry->Flags = RTL_HANDLE_ALLOCATED; RtlFreeHandle( &BaseHeapHandleTable, (PRTL_HANDLE_TABLE_ENTRY)HandleEntry ); HandleEntry = NULL; SetLastError( ERROR_NOT_ENOUGH_MEMORY ); } else { RtlSetUserValueHeap( BaseHeap, HEAP_NO_SERIALIZE, p, hMem ); } } else { p = NULL; } Fail: ; } except (EXCEPTION_EXECUTE_HANDLER) { p = NULL; BaseSetLastNTError( GetExceptionCode() ); }
RtlUnlockHeap( BaseHeap );
if (HandleEntry != NULL) { if (HandleEntry->Object = p) { HandleEntry->Flags = RTL_HANDLE_ALLOCATED; } else { HandleEntry->Flags = RTL_HANDLE_ALLOCATED | BASE_HANDLE_DISCARDED; }
if (uFlags & LMEM_DISCARDABLE) { HandleEntry->Flags |= BASE_HANDLE_DISCARDABLE; }
if (uFlags & LMEM_MOVEABLE) { HandleEntry->Flags |= BASE_HANDLE_MOVEABLE; }
p = (LPSTR)hMem; }
return( (HANDLE)p ); }
HLOCAL WINAPI LocalReAlloc( HLOCAL hMem, SIZE_T uBytes, UINT uFlags ) { PBASE_HANDLE_TABLE_ENTRY HandleEntry; LPSTR p; ULONG Flags;
if ((uFlags & ~(LMEM_VALID_FLAGS | LMEM_MODIFY)) || ((uFlags & LMEM_DISCARDABLE) && !(uFlags & LMEM_MODIFY)) ) { #if DBG
DbgPrint( "*** LocalReAlloc( %lx ) - invalid flags\n", uFlags ); BaseHeapBreakPoint(); #endif
SetLastError( ERROR_INVALID_PARAMETER ); return( NULL ); }
Flags = 0; if (uFlags & LMEM_ZEROINIT) { Flags |= HEAP_ZERO_MEMORY; } if (!(uFlags & LMEM_MOVEABLE)) { Flags |= HEAP_REALLOC_IN_PLACE_ONLY; }
RtlLockHeap( BaseHeap ); Flags |= HEAP_NO_SERIALIZE; try { if ((ULONG_PTR)hMem & BASE_HANDLE_MARK_BIT) { HandleEntry = (PBASE_HANDLE_TABLE_ENTRY) CONTAINING_RECORD( hMem, BASE_HANDLE_TABLE_ENTRY, Object );
if (!RtlIsValidHandle( &BaseHeapHandleTable, (PRTL_HANDLE_TABLE_ENTRY)HandleEntry )) { #if DBG
DbgPrint( "*** LocalReAlloc( %lx ) - invalid handle\n", hMem ); BaseHeapBreakPoint(); #endif
SetLastError( ERROR_INVALID_HANDLE ); hMem = NULL; } else if (uFlags & LMEM_MODIFY) { if (uFlags & LMEM_DISCARDABLE) { HandleEntry->Flags |= BASE_HANDLE_DISCARDABLE; } else { HandleEntry->Flags &= ~BASE_HANDLE_DISCARDABLE; } } else { p = HandleEntry->Object; if (uBytes == 0) { hMem = NULL; if (p != NULL) { if ((uFlags & LMEM_MOVEABLE) && HandleEntry->LockCount == 0) { if (RtlFreeHeap( BaseHeap, Flags | HEAP_NO_SERIALIZE, p )) { HandleEntry->Object = NULL; HandleEntry->Flags |= BASE_HANDLE_DISCARDED; hMem = (HANDLE)&HandleEntry->Object; } } else { #if DBG
DbgPrint( "*** LocalReAlloc( %lx ) - failing with locked handle\n", &HandleEntry->Object ); BaseHeapBreakPoint(); #endif
} } else { hMem = (HANDLE)&HandleEntry->Object; } } else { Flags |= HEAP_SETTABLE_USER_VALUE | BASE_HEAP_FLAG_MOVEABLE; if (p == NULL) { p = RtlAllocateHeap( BaseHeap, MAKE_TAG( LMEM_TAG ) | Flags, uBytes ); if (p != NULL) { RtlSetUserValueHeap( BaseHeap, HEAP_NO_SERIALIZE, p, hMem ); } } else { if (!(uFlags & LMEM_MOVEABLE) && HandleEntry->LockCount != 0 ) { Flags |= HEAP_REALLOC_IN_PLACE_ONLY; } else { Flags &= ~HEAP_REALLOC_IN_PLACE_ONLY; }
p = RtlReAllocateHeap( BaseHeap, MAKE_TAG( LMEM_TAG ) | Flags, p, uBytes ); }
if (p != NULL) { HandleEntry->Object = p; HandleEntry->Flags &= ~BASE_HANDLE_DISCARDED; } else { hMem = NULL; SetLastError( ERROR_NOT_ENOUGH_MEMORY ); } } } } else if (!(uFlags & LMEM_MODIFY)) { hMem = RtlReAllocateHeap( BaseHeap, MAKE_TAG( LMEM_TAG ) | Flags, (PVOID)hMem, uBytes ); if (hMem == NULL) { SetLastError( ERROR_NOT_ENOUGH_MEMORY ); } } } except (EXCEPTION_EXECUTE_HANDLER) { hMem = NULL; BaseSetLastNTError( GetExceptionCode() ); }
RtlUnlockHeap( BaseHeap );
return( (LPSTR)hMem ); }
PVOID WINAPI LocalLock( HLOCAL hMem ) { PBASE_HANDLE_TABLE_ENTRY HandleEntry; LPSTR p;
if ((ULONG_PTR)hMem & BASE_HANDLE_MARK_BIT) { RtlLockHeap( BaseHeap );
try { HandleEntry = (PBASE_HANDLE_TABLE_ENTRY) CONTAINING_RECORD( hMem, BASE_HANDLE_TABLE_ENTRY, Object );
if (!RtlIsValidHandle( &BaseHeapHandleTable, (PRTL_HANDLE_TABLE_ENTRY)HandleEntry )) { #if DBG
DbgPrint( "*** LocalLock( %lx ) - invalid handle\n", hMem ); BaseHeapBreakPoint(); #endif
SetLastError( ERROR_INVALID_HANDLE ); p = NULL; } else { p = HandleEntry->Object; if (p != NULL) { if (HandleEntry->LockCount++ == LMEM_LOCKCOUNT) { HandleEntry->LockCount--; } } else { SetLastError( ERROR_DISCARDED ); } } } except (EXCEPTION_EXECUTE_HANDLER) { p = NULL; BaseSetLastNTError( GetExceptionCode() ); }
RtlUnlockHeap( BaseHeap );
return( p ); } else { if ( (ULONG_PTR)hMem >= SystemRangeStart ) { return NULL; } return( (LPSTR)hMem ); } }
HLOCAL WINAPI LocalHandle( LPCVOID pMem ) { HANDLE Handle; ULONG Flags;
RtlLockHeap( BaseHeap ); try { Handle = NULL; if (!RtlGetUserInfoHeap( BaseHeap, HEAP_NO_SERIALIZE, (LPVOID)pMem, &Handle, &Flags )) { SetLastError( ERROR_INVALID_HANDLE ); } else if (Handle == NULL || !(Flags & BASE_HEAP_FLAG_MOVEABLE)) { Handle = (HANDLE)pMem; } } except (EXCEPTION_EXECUTE_HANDLER) { BaseSetLastNTError( GetExceptionCode() ); }
RtlUnlockHeap( BaseHeap );
return( Handle ); }
BOOL WINAPI LocalUnlock( HLOCAL hMem ) { PBASE_HANDLE_TABLE_ENTRY HandleEntry; BOOL Result;
Result = FALSE; if ((ULONG_PTR)hMem & BASE_HANDLE_MARK_BIT) { RtlLockHeap( BaseHeap ); try { HandleEntry = (PBASE_HANDLE_TABLE_ENTRY) CONTAINING_RECORD( hMem, BASE_HANDLE_TABLE_ENTRY, Object );
if (!RtlIsValidHandle( &BaseHeapHandleTable, (PRTL_HANDLE_TABLE_ENTRY)HandleEntry )) { #if DBG
DbgPrint( "*** LocalUnlock( %lx ) - invalid handle\n", hMem ); BaseHeapBreakPoint(); #endif
SetLastError( ERROR_INVALID_HANDLE ); } else if (HandleEntry->LockCount-- == 0) { HandleEntry->LockCount++; SetLastError( ERROR_NOT_LOCKED ); } else if (HandleEntry->LockCount != 0) { Result = TRUE; } else { SetLastError( NO_ERROR ); } } except (EXCEPTION_EXECUTE_HANDLER) { BaseSetLastNTError( GetExceptionCode() ); }
RtlUnlockHeap( BaseHeap ); } else { SetLastError( ERROR_NOT_LOCKED ); }
return( Result ); }
SIZE_T WINAPI LocalSize( HLOCAL hMem ) { PBASE_HANDLE_TABLE_ENTRY HandleEntry; PVOID Handle; ULONG Flags; SIZE_T uSize;
uSize = MAXULONG_PTR; Flags = 0; RtlLockHeap( BaseHeap ); try { if (!((ULONG_PTR)hMem & BASE_HANDLE_MARK_BIT)) { Handle = NULL; if (!RtlGetUserInfoHeap( BaseHeap, Flags, hMem, &Handle, &Flags )) { } else if (Handle == NULL || !(Flags & BASE_HEAP_FLAG_MOVEABLE)) { uSize = RtlSizeHeap( BaseHeap, HEAP_NO_SERIALIZE, (PVOID)hMem ); } else { hMem = Handle; } }
if ((ULONG_PTR)hMem & BASE_HANDLE_MARK_BIT) { HandleEntry = (PBASE_HANDLE_TABLE_ENTRY) CONTAINING_RECORD( hMem, BASE_HANDLE_TABLE_ENTRY, Object );
if (!RtlIsValidHandle( &BaseHeapHandleTable, (PRTL_HANDLE_TABLE_ENTRY)HandleEntry )) { #if DBG
DbgPrint( "*** LocalSize( %lx ) - invalid handle\n", hMem ); BaseHeapBreakPoint(); #endif
SetLastError( ERROR_INVALID_HANDLE ); } else if (HandleEntry->Flags & BASE_HANDLE_DISCARDED) { uSize = HandleEntry->Size; } else { uSize = RtlSizeHeap( BaseHeap, HEAP_NO_SERIALIZE, HandleEntry->Object ); } } } except (EXCEPTION_EXECUTE_HANDLER) { BaseSetLastNTError( GetExceptionCode() ); }
RtlUnlockHeap( BaseHeap );
if (uSize == MAXULONG_PTR) { SetLastError( ERROR_INVALID_HANDLE ); return 0; } else { return uSize; } }
UINT WINAPI LocalFlags( HLOCAL hMem ) { PBASE_HANDLE_TABLE_ENTRY HandleEntry; HANDLE Handle; ULONG Flags; UINT uFlags;
uFlags = LMEM_INVALID_HANDLE; RtlLockHeap( BaseHeap ); try { if (!((ULONG_PTR)hMem & BASE_HANDLE_MARK_BIT)) { Handle = NULL; Flags = 0; if (!RtlGetUserInfoHeap( BaseHeap, Flags, hMem, &Handle, &Flags )) { } else if (Handle == NULL || !(Flags & BASE_HEAP_FLAG_MOVEABLE)) { uFlags = 0; } else { hMem = Handle; } }
if ((ULONG_PTR)hMem & BASE_HANDLE_MARK_BIT) { HandleEntry = (PBASE_HANDLE_TABLE_ENTRY) CONTAINING_RECORD( hMem, BASE_HANDLE_TABLE_ENTRY, Object );
if (RtlIsValidHandle( &BaseHeapHandleTable, (PRTL_HANDLE_TABLE_ENTRY)HandleEntry )) { uFlags = HandleEntry->LockCount & LMEM_LOCKCOUNT; if (HandleEntry->Flags & BASE_HANDLE_DISCARDED) { uFlags |= LMEM_DISCARDED; }
if (HandleEntry->Flags & BASE_HANDLE_DISCARDABLE) { uFlags |= LMEM_DISCARDABLE; } } }
if (uFlags == LMEM_INVALID_HANDLE) { #if DBG
DbgPrint( "*** LocalFlags( %lx ) - invalid handle\n", hMem ); BaseHeapBreakPoint(); #endif
SetLastError( ERROR_INVALID_HANDLE ); } } except (EXCEPTION_EXECUTE_HANDLER) { BaseSetLastNTError( GetExceptionCode() ); }
RtlUnlockHeap( BaseHeap );
return( uFlags ); }
HLOCAL WINAPI LocalFree( HLOCAL hMem ) { PBASE_HANDLE_TABLE_ENTRY HandleEntry; LPSTR p;
try { if (!((ULONG_PTR)hMem & BASE_HANDLE_MARK_BIT)) { if (RtlFreeHeap( BaseHeap, 0, (PVOID)hMem ) ) { return NULL; } else { SetLastError( ERROR_INVALID_HANDLE ); return hMem; } } } except (EXCEPTION_EXECUTE_HANDLER) { BaseSetLastNTError( GetExceptionCode() ); return hMem; }
RtlLockHeap( BaseHeap ); try { if ((ULONG_PTR)hMem & BASE_HANDLE_MARK_BIT) { HandleEntry = (PBASE_HANDLE_TABLE_ENTRY) CONTAINING_RECORD( hMem, BASE_HANDLE_TABLE_ENTRY, Object );
if (!RtlIsValidHandle( &BaseHeapHandleTable, (PRTL_HANDLE_TABLE_ENTRY)HandleEntry )) { #if DBG
DbgPrint( "*** LocalFree( %lx ) - invalid handle\n", hMem ); BaseHeapBreakPoint(); #endif
SetLastError( ERROR_INVALID_HANDLE ); p = NULL; } else { #if DBG
if (HandleEntry->LockCount != 0) { DbgPrint( "BASE: LocalFree called with a locked object.\n" ); BaseHeapBreakPoint(); } #endif
p = HandleEntry->Object; RtlFreeHandle( &BaseHeapHandleTable, (PRTL_HANDLE_TABLE_ENTRY)HandleEntry ); if (p == NULL) { hMem = NULL; } } } else { p = (LPSTR)hMem; }
if (p != NULL) { if (RtlFreeHeap( BaseHeap, HEAP_NO_SERIALIZE, p )) { hMem = NULL; } else { SetLastError( ERROR_INVALID_HANDLE ); } } } except (EXCEPTION_EXECUTE_HANDLER) { BaseSetLastNTError( GetExceptionCode() ); }
RtlUnlockHeap( BaseHeap );
return( hMem ); }
SIZE_T WINAPI LocalCompact( UINT uMinFree ) { return RtlCompactHeap( BaseHeap, 0 ); }
SIZE_T WINAPI LocalShrink( HLOCAL hMem, UINT cbNewSize ) { return RtlCompactHeap( BaseHeap, 0 ); }
HANDLE WINAPI HeapCreate( DWORD flOptions, SIZE_T dwInitialSize, SIZE_T dwMaximumSize ) { HANDLE hHeap; ULONG GrowthThreshold; ULONG Flags;
Flags = (flOptions & (HEAP_GENERATE_EXCEPTIONS | HEAP_NO_SERIALIZE)) | HEAP_CLASS_1; GrowthThreshold = 0;
if (dwMaximumSize < BASE_SYSINFO.PageSize) {
if (dwMaximumSize == 0) {
GrowthThreshold = BASE_SYSINFO.PageSize * 16; Flags |= HEAP_GROWABLE; } else { dwMaximumSize = BASE_SYSINFO.PageSize; } }
if (GrowthThreshold == 0 && dwInitialSize > dwMaximumSize) { dwMaximumSize = dwInitialSize; }
hHeap = (HANDLE)RtlCreateHeap( Flags, NULL, dwMaximumSize, dwInitialSize, 0, NULL ); if (hHeap == NULL) { SetLastError( ERROR_NOT_ENOUGH_MEMORY ); }
return( hHeap ); }
BOOL WINAPI HeapDestroy( HANDLE hHeap ) { if (RtlDestroyHeap( (PVOID)hHeap ) == NULL ) { return( TRUE ); } else { SetLastError( ERROR_INVALID_HANDLE ); return( FALSE ); } }
BOOL WINAPI HeapExtend( HANDLE hHeap, DWORD dwFlags, LPVOID lpBase, DWORD dwBytes ) { NTSTATUS Status;
Status = RtlExtendHeap( hHeap, dwFlags, lpBase, dwBytes ); if (NT_SUCCESS( Status )) { return TRUE; } else { BaseSetLastNTError( Status ); } return FALSE; }
WINBASEAPI DWORD WINAPI HeapCreateTagsW( HANDLE hHeap, DWORD dwFlags, LPCWSTR lpTagPrefix, LPCWSTR lpTagNames ) { return RtlCreateTagHeap( hHeap, dwFlags, (PWSTR)lpTagPrefix, (PWSTR)lpTagNames ); }
WINBASEAPI LPCWSTR WINAPI HeapQueryTagW( HANDLE hHeap, DWORD dwFlags, WORD wTagIndex, BOOL bResetCounters, LPHEAP_TAG_INFO TagInfo ) { ASSERT( sizeof(RTL_HEAP_TAG_INFO) == sizeof(HEAP_TAG_INFO) ); return RtlQueryTagHeap( hHeap, dwFlags, wTagIndex, (BOOLEAN)bResetCounters, (PRTL_HEAP_TAG_INFO)TagInfo ); }
BOOL WINAPI HeapSummary( HANDLE hHeap, DWORD dwFlags, LPHEAP_SUMMARY lpSummary ) { NTSTATUS Status; RTL_HEAP_USAGE HeapInfo;
if (lpSummary->cb != sizeof( *lpSummary )) { SetLastError( ERROR_INVALID_PARAMETER ); return FALSE; }
HeapInfo.Length = sizeof( HeapInfo ); Status = RtlUsageHeap( hHeap, dwFlags & ~(HEAP_USAGE_ALLOCATED_BLOCKS | HEAP_USAGE_FREE_BUFFER ), &HeapInfo ); if (NT_SUCCESS( Status )) { lpSummary->cbAllocated = HeapInfo.BytesAllocated; lpSummary->cbCommitted = HeapInfo.BytesCommitted; return TRUE; } else { BaseSetLastNTError( Status ); return FALSE; } }
BOOL WINAPI HeapUsage( HANDLE hHeap, DWORD dwFlags, BOOL bFirstCall, BOOL bLastCall, PHEAP_USAGE lpUsage ) { NTSTATUS Status;
if (lpUsage->cb != sizeof( *lpUsage ) || (bFirstCall & bLastCall)) { SetLastError( ERROR_INVALID_PARAMETER ); return FALSE; }
dwFlags &= ~(HEAP_USAGE_ALLOCATED_BLOCKS | HEAP_USAGE_FREE_BUFFER );
if (bLastCall) { dwFlags |= HEAP_USAGE_FREE_BUFFER; } else { dwFlags |= HEAP_USAGE_ALLOCATED_BLOCKS; if (bFirstCall) { RtlZeroMemory( (&lpUsage->cb)+1, sizeof( *lpUsage ) - sizeof( lpUsage->cb ) ); } }
ASSERT( sizeof(RTL_HEAP_USAGE) == sizeof(HEAP_USAGE) ); Status = RtlUsageHeap( hHeap, dwFlags, (PRTL_HEAP_USAGE)lpUsage ); if (NT_SUCCESS( Status )) { if (Status == STATUS_MORE_ENTRIES) { return TRUE; } else { SetLastError( NO_ERROR ); return FALSE; } } else { BaseSetLastNTError( Status ); return FALSE; } }
BOOL WINAPI HeapValidate( HANDLE hHeap, DWORD dwFlags, LPVOID lpMem ) { return RtlValidateHeap( hHeap, dwFlags, lpMem ); }
HANDLE WINAPI GetProcessHeap( VOID ) { return RtlProcessHeap(); }
WINBASEAPI DWORD WINAPI GetProcessHeaps( DWORD NumberOfHeaps, PHANDLE ProcessHeaps ) { return RtlGetProcessHeaps( NumberOfHeaps, ProcessHeaps ); }
WINBASEAPI SIZE_T WINAPI HeapCompact( HANDLE hHeap, DWORD dwFlags ) { return RtlCompactHeap( hHeap, dwFlags ); }
WINBASEAPI BOOL WINAPI HeapLock( HANDLE hHeap ) { return RtlLockHeap( hHeap ); }
WINBASEAPI BOOL WINAPI HeapUnlock( HANDLE hHeap ) { return RtlUnlockHeap( hHeap ); }
WINBASEAPI BOOL WINAPI HeapWalk( HANDLE hHeap, LPPROCESS_HEAP_ENTRY lpEntry ) { RTL_HEAP_WALK_ENTRY Entry; NTSTATUS Status;
if (lpEntry->lpData == NULL) { Entry.DataAddress = NULL; Status = RtlWalkHeap( hHeap, &Entry ); } else { Entry.DataAddress = lpEntry->lpData; Entry.SegmentIndex = lpEntry->iRegionIndex; if (lpEntry->wFlags & PROCESS_HEAP_REGION) { Entry.Flags = RTL_HEAP_SEGMENT; } else if (lpEntry->wFlags & PROCESS_HEAP_UNCOMMITTED_RANGE) { Entry.Flags = RTL_HEAP_UNCOMMITTED_RANGE; Entry.DataSize = lpEntry->cbData; } else if (lpEntry->wFlags & PROCESS_HEAP_ENTRY_BUSY) { Entry.Flags = RTL_HEAP_BUSY; } else { Entry.Flags = 0; }
Status = RtlWalkHeap( hHeap, &Entry ); }
if (NT_SUCCESS( Status )) { lpEntry->lpData = Entry.DataAddress; lpEntry->cbData = (DWORD)Entry.DataSize; lpEntry->cbOverhead = Entry.OverheadBytes; lpEntry->iRegionIndex = Entry.SegmentIndex; if (Entry.Flags & RTL_HEAP_BUSY) { lpEntry->wFlags = PROCESS_HEAP_ENTRY_BUSY; if (Entry.Flags & BASE_HEAP_FLAG_DDESHARE) { lpEntry->wFlags |= PROCESS_HEAP_ENTRY_DDESHARE; }
if (Entry.Flags & BASE_HEAP_FLAG_MOVEABLE) { lpEntry->wFlags |= PROCESS_HEAP_ENTRY_MOVEABLE; lpEntry->Block.hMem = (HLOCAL)Entry.Block.Settable; }
memset( lpEntry->Block.dwReserved, 0, sizeof( lpEntry->Block.dwReserved ) ); } else if (Entry.Flags & RTL_HEAP_SEGMENT) { lpEntry->wFlags = PROCESS_HEAP_REGION; lpEntry->Region.dwCommittedSize = Entry.Segment.CommittedSize; lpEntry->Region.dwUnCommittedSize = Entry.Segment.UnCommittedSize; lpEntry->Region.lpFirstBlock = Entry.Segment.FirstEntry; lpEntry->Region.lpLastBlock = Entry.Segment.LastEntry; } else if (Entry.Flags & RTL_HEAP_UNCOMMITTED_RANGE) { lpEntry->wFlags = PROCESS_HEAP_UNCOMMITTED_RANGE; memset( &lpEntry->Region, 0, sizeof( lpEntry->Region ) ); } else { lpEntry->wFlags = 0; }
return TRUE; } else { BaseSetLastNTError( Status ); return FALSE; } }
WINBASEAPI BOOL WINAPI HeapSetInformation ( IN PVOID HeapHandle, IN HEAP_INFORMATION_CLASS HeapInformationClass, IN PVOID HeapInformation OPTIONAL, IN SIZE_T HeapInformationLength OPTIONAL ) { NTSTATUS Status;
Status = RtlSetHeapInformation( HeapHandle, HeapInformationClass, HeapInformation, HeapInformationLength ); if (NT_SUCCESS( Status )) { return TRUE; } else { BaseSetLastNTError( Status ); } return FALSE; }
WINBASEAPI BOOL WINAPI HeapQueryInformation ( IN PVOID HeapHandle, IN HEAP_INFORMATION_CLASS HeapInformationClass, OUT PVOID HeapInformation OPTIONAL, IN SIZE_T HeapInformationLength OPTIONAL, OUT PSIZE_T ReturnLength OPTIONAL ) { NTSTATUS Status;
Status = RtlQueryHeapInformation( HeapHandle, HeapInformationClass, HeapInformation, HeapInformationLength, ReturnLength ); if (NT_SUCCESS( Status )) { return TRUE; } else { BaseSetLastNTError( Status ); } return FALSE; }
#if DBG
VOID BaseHeapBreakPoint( VOID ) { if (NtCurrentPeb()->BeingDebugged) { #if i386
_asm { int 3 } #else
DbgBreakPoint(); #endif
} } #endif
|