C 语言

关注公众号 jb51net

关闭
首页 > 软件编程 > C 语言 > C++获取硬件参数

C++获取硬件参数的示例详解

作者:阿征学IT

这篇文章主要为大家详细介绍了如何使用C++获取硬件参数,文中的示例代码讲解详细,感兴趣的小伙伴可以跟随小编一起学习一下

分别显示

cpu参数

显卡参数

硬盘参数

内存信息(随机存储器容量)

代码

#include <iostream>
#include <comdef.h>
#include <Wbemidl.h>
 
#pragma comment(lib, "wbemuuid.lib")
 
void QueryWMI(IWbemServices* pSvc, const wchar_t* query, const wchar_t* propertyName) {
    IEnumWbemClassObject* pEnumerator = NULL;
    HRESULT hres = pSvc->ExecQuery(
        bstr_t("WQL"),
        bstr_t(query),
        WBEM_FLAG_FORWARD_ONLY | WBEM_FLAG_RETURN_IMMEDIATELY,
        NULL,
        &pEnumerator);
 
    if (FAILED(hres)) {
        std::cerr << "Query failed. Error code = 0x" << std::hex << hres << std::endl;
        return;
    }
 
    IWbemClassObject* pclsObj = NULL;
    ULONG uReturn = 0;
 
    while (pEnumerator) {
        HRESULT hr = pEnumerator->Next(WBEM_INFINITE, 1, &pclsObj, &uReturn);
 
        if (0 == uReturn) {
            break;
        }
 
        VARIANT vtProp;
        hr = pclsObj->Get(propertyName, 0, &vtProp, 0, 0);
        if (SUCCEEDED(hr) && vtProp.vt != VT_NULL) {
            std::wcout << propertyName << L" : " << vtProp.bstrVal << std::endl;
        }
        else {
            std::wcout << propertyName << L" : Not available" << std::endl;
        }
        VariantClear(&vtProp);
 
        pclsObj->Release();
    }
 
    pEnumerator->Release();
}
 
int main() {
    HRESULT hres;
 
    // Initialize COM.
    hres = CoInitializeEx(0, COINIT_MULTITHREADED);
    if (FAILED(hres)) {
        std::cerr << "Failed to initialize COM library. Error code = 0x" << std::hex << hres << std::endl;
        return 1;
    }
 
    // Initialize security.
    hres = CoInitializeSecurity(
        NULL,
        -1,
        NULL,
        NULL,
        RPC_C_AUTHN_LEVEL_DEFAULT,
        RPC_C_IMP_LEVEL_IMPERSONATE,
        NULL,
        EOAC_NONE,
        NULL);
 
    if (FAILED(hres)) {
        std::cerr << "Failed to initialize security. Error code = 0x" << std::hex << hres << std::endl;
        CoUninitialize();
        return 1;
    }
 
    IWbemLocator* pLoc = NULL;
    hres = CoCreateInstance(
        CLSID_WbemLocator,
        0,
        CLSCTX_INPROC_SERVER,
        IID_IWbemLocator, (LPVOID*)&pLoc);
 
    if (FAILED(hres)) {
        std::cerr << "Failed to create IWbemLocator object. Error code = 0x" << std::hex << hres << std::endl;
        CoUninitialize();
        return 1;
    }
 
    IWbemServices* pSvc = NULL;
    hres = pLoc->ConnectServer(
        _bstr_t(L"ROOT\\CIMV2"),
        NULL,
        NULL,
        0,
        NULL,
        0,
        0,
        &pSvc);
 
    if (FAILED(hres)) {
        std::cerr << "Could not connect. Error code = 0x" << std::hex << hres << std::endl;
        pLoc->Release();
        CoUninitialize();
        return 1;
    }
 
    hres = CoSetProxyBlanket(
        pSvc,
        RPC_C_AUTHN_WINNT,
        RPC_C_AUTHZ_NONE,
        NULL,
        RPC_C_AUTHN_LEVEL_CALL,
        RPC_C_IMP_LEVEL_IMPERSONATE,
        NULL,
        EOAC_NONE);
 
    if (FAILED(hres)) {
        std::cerr << "Could not set proxy blanket. Error code = 0x" << std::hex << hres << std::endl;
        pSvc->Release();
        pLoc->Release();
        CoUninitialize();
        return 1;
    }
 
    // Query hardware information
    std::wcout << L"CPU Information:" << std::endl;
    QueryWMI(pSvc, L"SELECT Name, NumberOfCores, MaxClockSpeed FROM Win32_Processor", L"Name");
 
    std::wcout << L"\nGPU Information:" << std::endl;
    QueryWMI(pSvc, L"SELECT Name, AdapterRAM, DriverVersion FROM Win32_VideoController", L"Name");
 
    std::wcout << L"\nDisk Information:" << std::endl;
    QueryWMI(pSvc, L"SELECT Model, Size, InterfaceType FROM Win32_DiskDrive", L"Model");
 
    std::wcout << L"\nMemory Information:" << std::endl;
    QueryWMI(pSvc, L"SELECT Capacity, Speed, Manufacturer FROM Win32_PhysicalMemory", L"Capacity");
 
    // Cleanup
    pSvc->Release();
    pLoc->Release();
    CoUninitialize();
 
    return 0;
}

头文件部分

iostream:用于输入输出操作(std::wcout)。

comdef.h 和 Wbemidl.h:支持 COM(Component Object Model)和 WMI(Windows Management Instrumentation)接口。

#pragma comment(lib, "wbemuuid.lib"):将 wbemuuid.lib 动态链接库包含到项目中,这是 WMI 所需的库。

函数部分

QueryWMI 函数

这是一个通用的函数,用于执行 WMI 查询并获取指定属性的信息。

void QueryWMI(IWbemServices* pSvc, const wchar_t* query, const wchar_t* propertyName) {
    IEnumWbemClassObject* pEnumerator = NULL;
    HRESULT hres = pSvc->ExecQuery(
        bstr_t("WQL"),  // 使用 WMI Query Language (WQL)
        bstr_t(query),  // 执行查询字符串
        WBEM_FLAG_FORWARD_ONLY | WBEM_FLAG_RETURN_IMMEDIATELY,
        NULL,
        &pEnumerator);

输入参数

pSvc:WMI 服务接口,用于执行查询。

query:WMI 查询字符串,例如 SELECT Name FROM Win32_Processor。

propertyName:要获取的属性名,例如 Name。

WMI 查询:

使用 IWbemServices::ExecQuery 执行 WQL 查询。

WBEM_FLAG_FORWARD_ONLY 和 WBEM_FLAG_RETURN_IMMEDIATELY 是优化标志,用于快速返回结果。

if (FAILED(hres)) {
    std::cerr << "Query failed. Error code = 0x" << std::hex << hres << std::endl;
    return;
}

检查查询是否成功,如果失败,打印错误代码。

遍历查询结果

while (pEnumerator) {
    HRESULT hr = pEnumerator->Next(WBEM_INFINITE, 1, &pclsObj, &uReturn);
    if (0 == uReturn) {
        break;
    }

使用 IEnumWbemClassObject::Next 获取查询结果,逐条处理

WBEM_INFINITE 指定无限等待时间

获取指定属性值

VARIANT vtProp;
hr = pclsObj->Get(propertyName, 0, &vtProp, 0, 0);
if (SUCCEEDED(hr) && vtProp.vt != VT_NULL) {
    std::wcout << propertyName << L" : " << vtProp.bstrVal << std::endl;
} else {
    std::wcout << propertyName << L" : Not available" << std::endl;
}
VariantClear(&vtProp);

调用 IWbemClassObject::Get 获取指定属性值

成功:打印属性值

失败或属性值为空:打印 "Not available"。

用 VariantClear 释放变量的内存。

Main 函数

一,初始化 COM

hres = CoInitializeEx(0, COINIT_MULTITHREADED);

二,设置安全性

hres = CoInitializeSecurity(
    NULL,
    -1,
    NULL,
    NULL,
    RPC_C_AUTHN_LEVEL_DEFAULT,
    RPC_C_IMP_LEVEL_IMPERSONATE,
    NULL,
    EOAC_NONE,
    NULL);

配置 COM 安全性,确保当前进程有足够权限访问 WMI。

RPC_C_IMP_LEVEL_IMPERSONATE:允许服务器模拟客户端

三,创建 WMI 接口对象

IWbemLocator* pLoc = NULL;
hres = CoCreateInstance(
    CLSID_WbemLocator,
    0,
    CLSCTX_INPROC_SERVER,
    IID_IWbemLocator, (LPVOID*)&pLoc);

使用 CoCreateInstance 创建 IWbemLocator 对象。该对象用于连接到 WMI 服务。

四,连接到 WMI 服务

hres = pLoc->ConnectServer(
    _bstr_t(L"ROOT\\CIMV2"),
    NULL,
    NULL,
    0,
    NULL,
    0,
    0,
    &pSvc);

连接到 ROOT\CIMV2 命名空间,这是获取硬件信息的常用命名空间。

pSvc 是连接后的服务接口。

五,设置代理

hres = CoSetProxyBlanket(
    pSvc,
    RPC_C_AUTHN_WINNT,
    RPC_C_AUTHZ_NONE,
    NULL,
    RPC_C_AUTHN_LEVEL_CALL,
    RPC_C_IMP_LEVEL_IMPERSONATE,
    NULL,
    EOAC_NONE);

配置代理,为调用的 WMI 服务接口提供身份验证

六,查询硬件信息

std::wcout << L"CPU Information:" << std::endl;
QueryWMI(pSvc, L"SELECT Name, NumberOfCores, MaxClockSpeed FROM Win32_Processor", L"Name");
 
std::wcout << L"\nGPU Information:" << std::endl;
QueryWMI(pSvc, L"SELECT Name, AdapterRAM, DriverVersion FROM Win32_VideoController", L"Name");
 
std::wcout << L"\nDisk Information:" << std::endl;
QueryWMI(pSvc, L"SELECT Model, Size, InterfaceType FROM Win32_DiskDrive", L"Model");
 
std::wcout << L"\nMemory Information:" << std::endl;
QueryWMI(pSvc, L"SELECT Capacity, Speed, Manufacturer FROM Win32_PhysicalMemory", L"Capacity");

调用 QueryWMI 函数分别获取 CPU、GPU、硬盘和内存的硬件信息。 

七,清理

pSvc->Release();
pLoc->Release();
CoUninitialize();

释放 IWbemServices 和 IWbemLocator 接口。调用 CoUninitialize 关闭 COM。

运行结果如下

以上就是C++获取硬件参数的示例详解的详细内容,更多关于C++获取硬件参数的资料请关注脚本之家其它相关文章!

您可能感兴趣的文章:
阅读全文