EndSideClient/xiaozhi-sharp/XiaoZhiSharp/Utils/SystemResourceMonitor.cs
2025-10-11 18:25:59 +08:00

777 lines
29 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

using Hardware.Info;
using NAudio.CoreAudioApi;
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Net.NetworkInformation;
using System.Runtime.InteropServices;
using System.Threading.Tasks;
namespace XiaoZhiSharp.Utils
{
/// <summary>
/// 主程序类
/// 提供用户界面和主循环
/// </summary>
public class SystemMonitorTest
{
private static void getVolume()
{
MMDeviceEnumerator enumerator = new MMDeviceEnumerator();
// 获取默认扬声器设备
MMDevice defaultSpeaker = enumerator.GetDefaultAudioEndpoint(DataFlow.Render, Role.Multimedia);
float speakerVolume = defaultSpeaker.AudioEndpointVolume.MasterVolumeLevelScalar;
// 获取默认麦克风设备
MMDevice defaultMicrophone = enumerator.GetDefaultAudioEndpoint(DataFlow.Capture, Role.Communications);
float microphoneVolume = defaultMicrophone.AudioEndpointVolume.MasterVolumeLevelScalar;
Console.WriteLine("扬声器音量:" + speakerVolume + "\n" + "麦克风音量:" + microphoneVolume);
}
private static void HardwareInfoLib(bool test)
{
getVolume();
IHardwareInfo hardwareInfo = new Hardware.Info.HardwareInfo();
hardwareInfo.RefreshOperatingSystem();
hardwareInfo.RefreshMemoryStatus();
hardwareInfo.RefreshBatteryList();
hardwareInfo.RefreshBIOSList();
hardwareInfo.RefreshComputerSystemList();
hardwareInfo.RefreshCPUList(includePercentProcessorTime: test);
hardwareInfo.RefreshDriveList();
hardwareInfo.RefreshKeyboardList();
hardwareInfo.RefreshMemoryList();
hardwareInfo.RefreshMonitorList();
hardwareInfo.RefreshMotherboardList();
hardwareInfo.RefreshMouseList();
hardwareInfo.RefreshNetworkAdapterList(includeBytesPerSec: test, includeNetworkAdapterConfiguration: test);
hardwareInfo.RefreshPrinterList();
hardwareInfo.RefreshSoundDeviceList();
hardwareInfo.RefreshVideoControllerList();
//hardwareInfo.RefreshAll();
Console.WriteLine(hardwareInfo.OperatingSystem);
Console.WriteLine(hardwareInfo.MemoryStatus);
foreach (var hardware in hardwareInfo.BatteryList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.BiosList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.ComputerSystemList)
Console.WriteLine(hardware);
foreach (var cpu in hardwareInfo.CpuList)
{
Console.WriteLine(cpu);
foreach (var cpuCore in cpu.CpuCoreList)
Console.WriteLine(cpuCore);
}
foreach (var drive in hardwareInfo.DriveList)
{
Console.WriteLine(drive);
foreach (var partition in drive.PartitionList)
{
Console.WriteLine(partition);
foreach (var volume in partition.VolumeList)
Console.WriteLine(volume);
}
}
foreach (var hardware in hardwareInfo.KeyboardList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.MemoryList)
Console.WriteLine(hardware);
if (hardwareInfo.MemoryList.Count > 0)
{
var memoryStatus = hardwareInfo.MemoryStatus;
//memoryStatus.
// 计算内存占用率
double usagePercentage = ((double)memoryStatus.TotalPhysical - memoryStatus.AvailablePhysical) /
memoryStatus.TotalPhysical * 100;
Console.WriteLine($"总物理内存: {FormatBytes(memoryStatus.TotalPhysical)}");
Console.WriteLine($"可用内存: {FormatBytes(memoryStatus.AvailablePhysical)}");
Console.WriteLine($"已用内存: {FormatBytes(memoryStatus.TotalPhysical - memoryStatus.AvailablePhysical)}");
Console.WriteLine($"内存占用率: {usagePercentage:F2}%");
}
else
{
Console.WriteLine("无法获取内存信息");
}
foreach (var hardware in hardwareInfo.MonitorList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.MotherboardList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.MouseList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.NetworkAdapterList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.PrinterList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.SoundDeviceList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.VideoControllerList)
Console.WriteLine(hardware);
foreach (var address in Hardware.Info.HardwareInfo.GetLocalIPv4Addresses(NetworkInterfaceType.Ethernet, OperationalStatus.Up))
Console.WriteLine(address);
Console.WriteLine();
foreach (var address in Hardware.Info.HardwareInfo.GetLocalIPv4Addresses(NetworkInterfaceType.Wireless80211))
Console.WriteLine(address);
Console.WriteLine();
foreach (var address in Hardware.Info.HardwareInfo.GetLocalIPv4Addresses(OperationalStatus.Up))
Console.WriteLine(address);
Console.WriteLine();
foreach (var address in Hardware.Info.HardwareInfo.GetLocalIPv4Addresses())
Console.WriteLine(address);
Console.ReadLine();
}
/// <summary>
/// 主入口点
/// </summary>
public static async Task RunTest(string[] args)
{
HardwareInfoLib(true);
HardwareInfoLib(false);
Console.WriteLine("系统监控工具 - 按任意键退出");
Console.WriteLine("==========================================");
// 创建系统监控器实例
var monitor = new OSSystemMonitor();
// 主监控循环
while (!Console.KeyAvailable)
{
try
{
// 异步获取系统信息
var info = await monitor.GetSystemInfoAsync();
// 显示系统信息
Console.WriteLine($"操作系统: {info.OSPlatform}");
var cpuUsage = $"CPU使用率: {info.CpuUsage}-";
if (cpuUsage.EndsWith("%%"))
{
}
Console.WriteLine(cpuUsage);
Console.WriteLine($"内存使用: {FormatBytes((ulong)info.UsedMemory)} / {FormatBytes((ulong)info.TotalMemory)} ({info.MemoryUsage}%)");
Console.WriteLine($"磁盘使用: {FormatBytes((ulong)info.UsedDiskSpace)} / {FormatBytes((ulong)info.TotalDiskSpace)} ({info.DiskUsage}%)");
Console.WriteLine("==========================================");
// 等待2秒后更新
await Task.Delay(500);
// 移动光标到开头,覆盖上次的输出
if (Console.CursorTop >= 5)
{
Console.SetCursorPosition(0, Console.CursorTop - 5);
}
}
catch (Exception ex)
{
// 显示错误信息并继续运行
Console.WriteLine($"错误: {ex.Message}");
await Task.Delay(500);
}
}
}
/// <summary>
/// 格式化字节数为易读的字符串
/// 自动选择合适的单位B, KB, MB, GB, TB
/// </summary>
/// <param name="bytes">字节数</param>
/// <returns>格式化后的字符串</returns>
private static string FormatBytes(ulong bytes)
{
if (bytes == 0) return "0 B";
string[] suffixes = { "B", "KB", "MB", "GB", "TB" };
int counter = 0;
decimal number = bytes;
// 循环除以1024直到找到合适的单位
while (Math.Round(number / 1024) >= 1 && counter < suffixes.Length - 1)
{
number /= 1024;
counter++;
}
// 返回格式化后的字符串保留1位小数
return $"{number:n1} {suffixes[counter]}";
}
}
/// <summary>
/// 系统信息数据模型类
/// 用于存储和传递CPU、内存、磁盘的使用信息
/// </summary>
public class OSSystemInfo
{
/// <summary>CPU使用率百分比</summary>
public double CpuUsage { get; set; }
/// <summary>内存使用率百分比</summary>
public double MemoryUsage { get; set; }
/// <summary>总物理内存大小(字节)</summary>
public long TotalMemory { get; set; }
/// <summary>已使用内存大小(字节)</summary>
public long UsedMemory { get; set; }
/// <summary>磁盘使用率百分比</summary>
public double DiskUsage { get; set; }
/// <summary>总磁盘空间大小(字节)</summary>
public long TotalDiskSpace { get; set; }
/// <summary>已使用磁盘空间大小(字节)</summary>
public long UsedDiskSpace { get; set; }
/// <summary>可用磁盘空间大小(字节)</summary>
public long AvailableDiskSpace { get; set; }
/// <summary>操作系统平台名称</summary>
public string OSPlatform { get; set; } = "";
}
/// <summary>
/// 系统监控器类
/// 提供跨平台的CPU、内存、磁盘使用率监控功能
/// </summary>
public class OSSystemMonitor
{
// 用于计算CPU使用率的时间戳和处理器时间
private DateTime _lastCpuTime;
private TimeSpan _lastTotalProcessorTime;
private Process _process;
// 用于Linux系统CPU使用率计算的缓存值
private ulong _lastTotalCpuTime = 0;
private ulong _lastTotalIdle = 0;
/// <summary>
/// 构造函数,初始化监控器
/// </summary>
public OSSystemMonitor()
{
// 获取当前进程实例,用于计算进程相关的系统资源使用情况
_process = Process.GetCurrentProcess();
// 初始化时间戳用于后续计算CPU使用率
_lastCpuTime = DateTime.Now;
_lastTotalProcessorTime = _process.TotalProcessorTime;
}
/// <summary>
/// 异步获取系统信息
/// 同时获取CPU、内存、磁盘的使用信息
/// </summary>
/// <returns>包含系统信息的OSSystemInfo对象</returns>
public async Task<OSSystemInfo> GetSystemInfoAsync()
{
var info = new OSSystemInfo
{
OSPlatform = GetOSPlatform()
};
// 使用Task.WhenAll并行获取各项系统信息提高效率
await Task.WhenAll(
Task.Run(() => info.CpuUsage = GetCpuUsage()),
Task.Run(() => GetMemoryInfo(info)),
Task.Run(() => GetDiskInfo(info))
);
return info;
}
/// <summary>
/// 获取CPU使用率
/// 根据操作系统平台调用不同的实现
/// </summary>
/// <returns>CPU使用率百分比</returns>
private double GetCpuUsage()
{
if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
{
return GetWindowsCpuUsage();
}
else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux) ||
RuntimeInformation.IsOSPlatform(OSPlatform.OSX))
{
return GetLinuxCpuUsage();
}
return 0; // 未知平台返回0
}
/// <summary>
/// Windows平台获取CPU使用率
/// 使用PerformanceCounter性能计数器
/// </summary>
/// <returns>CPU使用率百分比</returns>
private double GetWindowsCpuUsage()
{
try
{
// 创建性能计数器实例,监控总处理器时间
using (var cpuCounter = new PerformanceCounter("Processor", "% Processor Time", "_Total"))
{
// 首次调用NextValue()初始化计数器,返回的值通常不准确
cpuCounter.NextValue();
// 等待1秒让计数器收集足够的数据
System.Threading.Thread.Sleep(1000);
// 第二次调用获取准确的CPU使用率
return Math.Round(cpuCounter.NextValue(), 2);
}
}
catch
{
// 如果性能计数器不可用,使用备用的计算方法
return CalculateCpuUsage();
}
}
/// <summary>
/// 备用的CPU使用率计算方法
/// 通过计算进程的处理器时间变化来估算CPU使用率
/// </summary>
/// <returns>估算的CPU使用率百分比</returns>
private double CalculateCpuUsage()
{
var currentTime = DateTime.Now;
var currentTotalProcessorTime = _process.TotalProcessorTime;
// 计算时间间隔内使用的CPU时间毫秒
var cpuUsedMs = (currentTotalProcessorTime - _lastTotalProcessorTime).TotalMilliseconds;
// 计算经过的总时间(毫秒)
var totalMsPassed = (currentTime - _lastCpuTime).TotalMilliseconds;
// 更新上一次的时间戳
_lastCpuTime = currentTime;
_lastTotalProcessorTime = currentTotalProcessorTime;
// 避免除以零错误
if (totalMsPassed == 0) return 0;
// 计算CPU使用率使用的CPU时间 / (CPU核心数 * 总时间)
var cpuUsageTotal = cpuUsedMs / (Environment.ProcessorCount * totalMsPassed);
// 转换为百分比并四舍五入到两位小数
return Math.Round(cpuUsageTotal * 100, 2);
}
/// <summary>
/// Linux平台获取CPU使用率
/// 通过解析/proc/stat文件来计算
/// </summary>
/// <returns>CPU使用率百分比</returns>
private double GetLinuxCpuUsage()
{
try
{
// 读取/proc/stat文件包含CPU统计信息
var lines = File.ReadAllLines("/proc/stat");
// 查找以"cpu "开头的行总CPU统计
var cpuLine = lines.FirstOrDefault(l => l.StartsWith("cpu "));
if (cpuLine == null) return 0;
// 分割字符串,移除空条目
var values = cpuLine.Split(' ', StringSplitOptions.RemoveEmptyEntries);
if (values.Length < 8) return 0;
// 解析各个时间字段单位jiffies通常为10ms
var user = ulong.Parse(values[1]); // 用户模式时间
var nice = ulong.Parse(values[2]); // 低优先级用户模式时间
var system = ulong.Parse(values[3]); // 系统模式时间
var idle = ulong.Parse(values[4]); // 空闲时间
var iowait = ulong.Parse(values[5]); // I/O等待时间
var irq = ulong.Parse(values[6]); // 中断处理时间
var softirq = ulong.Parse(values[7]); // 软中断处理时间
// 计算总CPU时间和总空闲时间
var totalCpuTime = user + nice + system + idle + iowait + irq + softirq;
var totalIdle = idle + iowait;
// 如果是第一次调用初始化缓存值并等待1秒后重新计算
if (_lastTotalCpuTime == 0)
{
_lastTotalCpuTime = totalCpuTime;
_lastTotalIdle = totalIdle;
System.Threading.Thread.Sleep(1000);
return GetLinuxCpuUsage(); // 递归调用获取第二次读数
}
// 计算两次读数之间的差值
var totalCpuDiff = totalCpuTime - _lastTotalCpuTime;
var totalIdleDiff = totalIdle - _lastTotalIdle;
// 更新缓存值
_lastTotalCpuTime = totalCpuTime;
_lastTotalIdle = totalIdle;
// 避免除以零错误
if (totalCpuDiff == 0) return 0;
// 计算CPU使用率(1 - 空闲时间比例) * 100
var cpuUsage = (1.0 - (double)totalIdleDiff / totalCpuDiff) * 100;
return Math.Round(cpuUsage, 2);
}
catch
{
// 如果读取/proc/stat失败使用备用的计算方法
return CalculateCpuUsage();
}
}
/// <summary>
/// 获取内存信息并填充到OSSystemInfo对象
/// 根据操作系统平台调用不同的实现
/// </summary>
/// <param name="info">要填充的OSSystemInfo对象</param>
private void GetMemoryInfo(OSSystemInfo info)
{
if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
{
GetWindowsMemoryInfo(info);
}
else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux) ||
RuntimeInformation.IsOSPlatform(OSPlatform.OSX))
{
GetLinuxMemoryInfo(info);
}
}
/// <summary>
/// Windows平台获取内存信息
/// 使用PerformanceCounter性能计数器
/// </summary>
/// <param name="info">要填充的OSSystemInfo对象</param>
private void GetWindowsMemoryInfo(OSSystemInfo info)
{
try
{
// 使用性能计数器获取可用内存字节数
using (var memCounter = new PerformanceCounter("Memory", "Available Bytes"))
{
var availableMemory = memCounter.NextValue();
var totalMemory = GetTotalPhysicalMemory();
info.TotalMemory = totalMemory;
info.UsedMemory = totalMemory - (long)availableMemory;
// 计算内存使用率百分比
if (totalMemory > 0)
{
info.MemoryUsage = Math.Round((double)info.UsedMemory / totalMemory * 100, 2);
}
else
{
info.MemoryUsage = 0;
}
}
}
catch
{
// 如果性能计数器不可用使用Windows API备选方案
GetWindowsMemoryInfoAlternative(info);
}
}
/// <summary>
/// Windows平台备用的内存信息获取方法
/// 使用Windows API GlobalMemoryStatusEx
/// </summary>
/// <param name="info">要填充的OSSystemInfo对象</param>
private void GetWindowsMemoryInfoAlternative(OSSystemInfo info)
{
try
{
// 创建内存状态结构体
var memoryStatus = new MEMORYSTATUSEX();
memoryStatus.dwLength = (uint)Marshal.SizeOf(typeof(MEMORYSTATUSEX));
// 调用Windows API获取内存状态
if (GlobalMemoryStatusEx(ref memoryStatus))
{
info.TotalMemory = (long)memoryStatus.ullTotalPhys;
info.UsedMemory = (long)(memoryStatus.ullTotalPhys - memoryStatus.ullAvailPhys);
// 计算内存使用率百分比
if (info.TotalMemory > 0)
{
info.MemoryUsage = Math.Round((double)info.UsedMemory / info.TotalMemory * 100, 2);
}
else
{
info.MemoryUsage = 0;
}
}
}
catch
{
// 如果所有方法都失败,使用进程工作集作为近似值
info.TotalMemory = GetTotalPhysicalMemory();
info.UsedMemory = Environment.WorkingSet;
if (info.TotalMemory > 0)
{
info.MemoryUsage = Math.Round((double)info.UsedMemory / info.TotalMemory * 100, 2);
}
else
{
info.MemoryUsage = 0;
}
}
}
/// <summary>
/// Linux平台获取内存信息
/// 通过解析/proc/meminfo文件
/// </summary>
/// <param name="info">要填充的OSSystemInfo对象</param>
private void GetLinuxMemoryInfo(OSSystemInfo info)
{
try
{
// 读取/proc/meminfo文件包含内存统计信息
var lines = File.ReadAllLines("/proc/meminfo");
var memInfo = new Dictionary<string, long>();
// 解析每行数据
foreach (var line in lines)
{
var parts = line.Split(':', StringSplitOptions.RemoveEmptyEntries);
if (parts.Length == 2)
{
var key = parts[0].Trim();
var valueString = parts[1].Trim().Split(' ')[0];
// 转换值文件中的单位是KB转换为字节
if (long.TryParse(valueString, out long value))
{
memInfo[key] = value * 1024;
}
}
}
// 优先使用MemAvailable更准确反映可用内存
if (memInfo.ContainsKey("MemTotal") && memInfo.ContainsKey("MemAvailable"))
{
info.TotalMemory = memInfo["MemTotal"];
info.UsedMemory = memInfo["MemTotal"] - memInfo["MemAvailable"];
if (info.TotalMemory > 0)
{
info.MemoryUsage = Math.Round((double)info.UsedMemory / info.TotalMemory * 100, 2);
}
}
else if (memInfo.ContainsKey("MemTotal") && memInfo.ContainsKey("MemFree"))
{
// 如果没有MemAvailable使用MemFree作为近似值
info.TotalMemory = memInfo["MemTotal"];
info.UsedMemory = memInfo["MemTotal"] - memInfo["MemFree"];
if (info.TotalMemory > 0)
{
info.MemoryUsage = Math.Round((double)info.UsedMemory / info.TotalMemory * 100, 2);
}
}
}
catch
{
// 发生错误时清零相关字段
info.MemoryUsage = 0;
info.TotalMemory = 0;
info.UsedMemory = 0;
}
}
/// <summary>
/// 获取磁盘信息并填充到OSSystemInfo对象
/// 自动识别系统盘Windows或根分区Linux
/// </summary>
/// <param name="info">要填充的OSSystemInfo对象</param>
private void GetDiskInfo(OSSystemInfo info)
{
try
{
DriveInfo systemDrive;
if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
{
// Windows选择系统目录所在的驱动器
systemDrive = DriveInfo.GetDrives()
.FirstOrDefault(d => d.IsReady &&
d.Name.Equals(Path.GetPathRoot(Environment.SystemDirectory),
StringComparison.OrdinalIgnoreCase));
}
else
{
// Linux/macOS首先尝试找到根目录所在的驱动器
systemDrive = DriveInfo.GetDrives()
.FirstOrDefault(d => d.IsReady && d.RootDirectory.FullName == "/");
// 如果没找到根分区,选择第一个可用的固定驱动器
systemDrive ??= DriveInfo.GetDrives()
.FirstOrDefault(d => d.IsReady && d.DriveType == DriveType.Fixed);
}
// 如果找到系统盘且就绪,读取磁盘信息
if (systemDrive != null && systemDrive.IsReady)
{
info.TotalDiskSpace = systemDrive.TotalSize;
info.AvailableDiskSpace = systemDrive.AvailableFreeSpace;
info.UsedDiskSpace = systemDrive.TotalSize - systemDrive.AvailableFreeSpace;
// 计算磁盘使用率百分比
if (systemDrive.TotalSize > 0)
{
info.DiskUsage = Math.Round((double)info.UsedDiskSpace / systemDrive.TotalSize * 100, 2);
}
else
{
info.DiskUsage = 0;
}
}
}
catch
{
// 发生错误时清零相关字段
info.DiskUsage = 0;
info.TotalDiskSpace = 0;
info.UsedDiskSpace = 0;
info.AvailableDiskSpace = 0;
}
}
/// <summary>
/// 获取总物理内存大小
/// 跨平台实现支持Windows和Linux
/// </summary>
/// <returns>总物理内存字节数</returns>
private long GetTotalPhysicalMemory()
{
if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
{
try
{
// Windows平台使用GlobalMemoryStatusEx API
var memoryStatus = new MEMORYSTATUSEX();
memoryStatus.dwLength = (uint)Marshal.SizeOf(typeof(MEMORYSTATUSEX));
if (GlobalMemoryStatusEx(ref memoryStatus))
{
return (long)memoryStatus.ullTotalPhys;
}
}
catch
{
// 忽略错误返回0
}
}
else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux) ||
RuntimeInformation.IsOSPlatform(OSPlatform.OSX))
{
try
{
// Linux/macOS平台读取/proc/meminfo文件
var lines = File.ReadAllLines("/proc/meminfo");
var totalLine = lines.FirstOrDefault(l => l.StartsWith("MemTotal"));
if (totalLine != null)
{
var parts = totalLine.Split(':', StringSplitOptions.RemoveEmptyEntries);
if (parts.Length == 2)
{
var valueString = parts[1].Trim().Split(' ')[0];
if (long.TryParse(valueString, out long value))
{
return value * 1024; // 转换为字节
}
}
}
}
catch
{
// 忽略错误返回0
}
}
return 0; // 默认返回0
}
/// <summary>
/// 获取操作系统平台名称
/// </summary>
/// <returns>操作系统平台名称字符串</returns>
private string GetOSPlatform()
{
if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
return "Windows";
if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux))
return "Linux";
if (RuntimeInformation.IsOSPlatform(OSPlatform.OSX))
return "macOS";
return "Unknown";
}
// Windows API 结构体,用于获取内存状态信息
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]
private struct MEMORYSTATUSEX
{
public uint dwLength; // 结构体大小
public uint dwMemoryLoad; // 内存使用率百分比
public ulong ullTotalPhys; // 总物理内存
public ulong ullAvailPhys; // 可用物理内存
public ulong ullTotalPageFile; // 总页面文件大小
public ulong ullAvailPageFile; // 可用页面文件大小
public ulong ullTotalVirtual; // 总虚拟内存
public ulong ullAvailVirtual; // 可用虚拟内存
public ulong ullAvailExtendedVirtual; // 可用扩展虚拟内存
}
// Windows API 函数导入,用于获取全局内存状态
[DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
[return: MarshalAs(UnmanagedType.Bool)]
private static extern bool GlobalMemoryStatusEx(ref MEMORYSTATUSEX lpBuffer);
}
}