, , Charles Bailey :
public class MemoryAnalyzer {
public long GetLargestFreeRegionSize() {
SYSTEM_INFO sysInfo;
GetSystemInfo(out sysInfo);
var procMinAddress = sysInfo.minimumApplicationAddress;
var procMaxAddress = sysInfo.maximumApplicationAddress;
var procMinAddressL = (long)procMinAddress;
var procMaxAddressL = (long)procMaxAddress;
var process = Process.GetCurrentProcess();
var processHandle = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_WM_READ, false, process.Id);
long maxFreeRegionSize = 0;
while (procMinAddressL < procMaxAddressL) {
const int memBasicInfoSize = 28;
MEMORY_BASIC_INFORMATION memBasicInfo;
VirtualQueryEx(processHandle, procMinAddress, out memBasicInfo, memBasicInfoSize);
if (memBasicInfo.State == MEM_FREE) {
maxFreeRegionSize = Math.Max(maxFreeRegionSize, memBasicInfo.RegionSize);
}
procMinAddressL += memBasicInfo.RegionSize;
procMinAddress = new IntPtr(procMinAddressL);
}
return maxFreeRegionSize;
}
#region Win32
const int PROCESS_QUERY_INFORMATION = 0x0400;
const int PROCESS_WM_READ = 0x0010;
const int MEM_FREE = 0x10000;
[DllImport("kernel32.dll")]
public static extern IntPtr OpenProcess(int dwDesiredAccess, bool bInheritHandle, int dwProcessId);
[DllImport("kernel32.dll")]
public static extern bool ReadProcessMemory(int hProcess, int lpBaseAddress, byte[] lpBuffer, int dwSize, ref int lpNumberOfBytesRead);
[DllImport("kernel32.dll")]
static extern void GetSystemInfo(out SYSTEM_INFO lpSystemInfo);
[DllImport("kernel32.dll", SetLastError = true)]
static extern int VirtualQueryEx(IntPtr hProcess, IntPtr lpAddress, out MEMORY_BASIC_INFORMATION lpBuffer, uint dwLength);
public struct MEMORY_BASIC_INFORMATION {
public int BaseAddress;
public int AllocationBase;
public int AllocationProtect;
public int RegionSize;
public int State;
public int Protect;
public int lType;
}
public struct SYSTEM_INFO {
public ushort processorArchitecture;
ushort reserved;
public uint pageSize;
public IntPtr minimumApplicationAddress;
public IntPtr maximumApplicationAddress;
public IntPtr activeProcessorMask;
public uint numberOfProcessors;
public uint processorType;
public uint allocationGranularity;
public ushort processorLevel;
public ushort processorRevision;
}
#endregion
}