Windows下获取硬件信息的编程(CPU、硬盘、内存和启动时间等)

1. 计算CPU利用率

在Windows中计算CPU利用率的方法是使用SystemProcessorPerformanceInformation参数反复调用NtQuerySystemInformation函数,然后根据返回的IdleTime、KernelTime和UseTime值,分别使用后一次调用获得的值减去前一次调用获得的值,得到各个增量值,然后使用一个除法就可以得到CPU利用率。

这里唯一需要注意的是KernelTime成员值包含IdleTime和核心调用的使用时间。

当使用SystemBasicInformation 调用 NtQuerySystemInformation 来试图获取CPU个数时会失败,返回0xC0000004错误码,可以使用GetSystemInfo函数获得CPU的个数。

CPU利用率的计算公式如下:

100.0 * (IdleTime –PrevIdleTime) / (KernelTime + UserTime – PrevKernelTime – PrevUserTime)

注1:实际内核时间(ActualKernelTime)= KernelTime– IdleTime,内核时间-空闲时间。

注2:全部CPU时间(CpuTime)= UserTime +KernelTime,用户时间+内核时间。

int GetSystemCpuTimes(SystemCpuTimes*cputimes, int num)

{

   typedef DWORD (_stdcall *NTQSI_PROC) (int,PVOID, ULONG, PULONG);

    // dynamic linking is mandatory to use NtQuerySystemInformation

    HINSTANCE hNtDll =LoadLibrary("ntdll.dll");

    if (hNtDll == NULL) {

        fprintf(stderr, "LoadLibraryntdll.dll failed.\n");

        return -1;

    }

    // gets NtQuerySystemInformation address

    NTQSI_PROC NtQuerySystemInformation =(NTQSI_PROC)GetProcAddress(hNtDll, "NtQuerySystemInformation");

    if (NtQuerySystemInformation == NULL) {

        FreeLibrary(hNtDll);

        return -2;

    }

 

    // retrieves number of processors

    SYSTEM_INFO si;

    si.dwNumberOfProcessors = 0;

    GetSystemInfo(&si);

    if (si.dwNumberOfProcessors == 0)

        si.dwNumberOfProcessors = 1;

    // allocates an array ofSYSTEM_PROCESSOR_PERFORMANCE_INFORMATION structures, one per processor

    SYSTEM_PROCESSOR_PERFORMANCE_INFORMATION*sppi

        = newSYSTEM_PROCESSOR_PERFORMANCE_INFORMATION[si.dwNumberOfProcessors];

    if (sppi == NULL) {

        FreeLibrary(hNtDll);

        return -3;

    }

    // Get CPU time informations

    if (NtQuerySystemInformation(SystemProcessorPerformanceInformation,

        sppi, si.dwNumberOfProcessors *

sizeof(SYSTEM_PROCESSOR_PERFORMANCE_INFORMATION), NULL) != 0) {

        FreeLibrary(hNtDll);

        delete []sppi;

        return -4;

    }

    // computes system global times summingeach processor value

    for (DWORD i = 0; i <si.dwNumberOfProcessors; i++) {

        if ((int)i >= num)

            break;

        // kernel time includes idle time onwindows

        // we return only busy kernel timesubtracting

        // idle time from kernel time

        cputimes[i].user = LO_T *sppi[i].UserTime.QuadPart;

        cputimes[i].kernel = LO_T *sppi[i].KernelTime.QuadPart;

        cputimes[i].idle = LO_T *sppi[i].IdleTime.QuadPart;

        cputimes[i].total = cputimes[i].user + cputimes[i].kernel;

        cputimes[i].kernel -= cputimes[i].idle;

    }

    FreeLibrary(hNtDll);

    delete []sppi;

 

    return 0;

}

获取CPU个数

在Windows中可以使用GetSystemInfo函数来获取本机的CPU个数。

int GetNumCpus()

{

    SYSTEM_INFO system_info;

    memset(&system_info, 0x0,sizeof(system_info));

    GetSystemInfo(&system_info);

    if (system_info.dwNumberOfProcessors == 0)

        return 1;

    else

        returnsystem_info.dwNumberOfProcessors;

}

2. 获取内存使用情况

         在Windows下使用GlobalMemoryStatusEx函数来获取物理内存、虚拟内存和内存页的大小,通过总内存和空闲内存可以计算出内存使用率。

int GetVirtualMem(MemoryInfo &mi)

{

   MEMORYSTATUSEX mem_info;

   mem_info.dwLength = sizeof(mem_info);

   if (!GlobalMemoryStatusEx(&mem_info)) {

       memset(&mi, 0x0, sizeof(mi));

       return -1;

    }

   mi.avail_page_file = mem_info.ullAvailPageFile;

   mi.avail_phys = mem_info.ullAvailPhys;

   mi.avail_virtual = mem_info.ullAvailVirtual;

   mi.total_page_file = mem_info.ullTotalPageFile;

   mi.total_phys = mem_info.ullTotalPhys;

   mi.total_virtual = mem_info.ullTotalVirtual;

   mi.usage = (int)(100.0 * (mi.total_phys - mi.avail_phys) /mi.total_phys);

 

   return 0;

}

3. 硬盘使用情况

         在Windows下可以使用GetDiskFreeSpaceEx函数来获取该路径下的硬盘使用情况,使用总硬盘大小和空闲硬盘大小可以计算硬盘使用率。

int GetDiskUsage(const char *path, DiskInfo&disk_info)

{

   if (path == NULL)

       path = "C:\\";

   ULARGE_INTEGER caller, total, free;

   if (GetDiskFreeSpaceEx(path, &caller, &total, &free) == 0) {

       memset(&disk_info, 0x0, sizeof(disk_info));

       return -1;

    }

    disk_info.free= free.QuadPart;

   disk_info.total = total.QuadPart;

   disk_info.usage = (int)(100.0 * (disk_info.total - disk_info.free) /disk_info.total);

 

   return 0;

}

4. 系统启动时间

         在Windows下可以使用GetTickCount64函数来获取系统的运行时间,它输出一个64位的毫秒值,通过除以1000可以获得系统的运行秒值。

double GetSystemBootTime()

{

   return GetTickCount64() / 1000.0f; // return seconds.

}

  • 2
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值