在Windows SDK 10.0.19041.0中缺失D3DKMTQueryStatistics,如何获取进程GPU使用率?
如何在Windows SDK 10.0.19041.0中获取进程GPU使用率
由于D3DKMTQueryStatistics在较新的Windows SDK(包括10.0.19041.0)中已被移除,推荐使用以下几种官方兼容的替代方案:
1. 使用DXGI 1.4的IDXGIAdapter3::QueryVideoMemoryInfo
这是微软推荐的现代方法,支持Windows 10 1607及以上版本,你的SDK版本完全符合要求。通过该接口可以获取指定进程的视频内存使用数据,结合时间差计算使用率:
#include <dxgi1_4.h> #pragma comment(lib, "dxgi.lib") HRESULT GetProcessGPUUsage(DWORD processId, float& usage) { HRESULT hr = S_OK; IDXGIFactory4* pFactory = nullptr; hr = CreateDXGIFactory1(IID_PPV_ARGS(&pFactory)); if (FAILED(hr)) return hr; IDXGIAdapter3* pAdapter = nullptr; for (UINT i = 0; pFactory->EnumAdapters1(i, reinterpret_cast<IDXGIAdapter**>(&pAdapter)) != DXGI_ERROR_NOT_FOUND; ++i) { DXGI_QUERY_VIDEO_MEMORY_INFO info; hr = pAdapter->QueryVideoMemoryInfo(processId, DXGI_MEMORY_SEGMENT_GROUP_LOCAL, &info); if (SUCCEEDED(hr)) { // 实际使用时需记录上一次的查询结果,结合时间间隔计算使用率 // 示例简化为当前内存占预算的比例 usage = static_cast<float>(info.CurrentUsage) / info.Budget * 100.0f; break; } pAdapter->Release(); } pFactory->Release(); if (pAdapter) pAdapter->Release(); return hr; }
2. 使用Windows性能计数器(PDH API)
通过系统自带的性能计数器可以直接获取进程级GPU指标,无需依赖DXGI:
#include <pdh.h> #pragma comment(lib, "pdh.lib") BOOL GetProcessGPUUsagePdh(DWORD processId, float& usage) { PDH_HQUERY hQuery = nullptr; PDH_HCOUNTER hCounter = nullptr; WCHAR counterPath[256]; swprintf_s(counterPath, L"\\GPU Engine(*engtype_3D)\\Process Memory Usage %d", processId); if (PdhOpenQuery(nullptr, 0, &hQuery) != ERROR_SUCCESS) return FALSE; if (PdhAddCounter(hQuery, counterPath, 0, &hCounter) != ERROR_SUCCESS) { PdhCloseQuery(hQuery); return FALSE; } // 第一次采集基准数据 PdhCollectQueryData(hQuery); Sleep(1000); // 等待1秒获取差值 PdhCollectQueryData(hQuery); PDH_FMT_COUNTERVALUE counterValue; if (PdhGetFormattedCounterValue(hCounter, PDH_FMT_FLOAT, nullptr, &counterValue) == ERROR_SUCCESS) { usage = counterValue.floatValue; } else { usage = 0.0f; PdhCloseQuery(hQuery); return FALSE; } PdhCloseQuery(hQuery); return TRUE; }
注意:计数器路径可能因GPU硬件型号或系统版本略有调整,可通过性能监视器(perfmon.exe)确认具体路径。
3. 手动调用D3DKMTQueryStatistics(不推荐)
如果必须使用该底层函数,可以手动导入d3dkmthk.dll中的实现,但存在兼容性风险(未来系统版本可能移除):
// 手动定义函数原型和结构体(需参考旧版SDK定义) typedef struct _D3DKMT_QUERYSTATISTICS { // 结构体成员需与旧版定义一致,此处省略具体字段 } D3DKMT_QUERYSTATISTICS; typedef NTSTATUS(WINAPI* PFND3DKMTQUERYSTATISTICS)(const D3DKMT_QUERYSTATISTICS*); PFND3DKMTQUERYSTATISTICS pD3DKMTQueryStatistics = nullptr; HMODULE hD3dKmtHk = LoadLibrary(L"d3dkmthk.dll"); if (hD3dKmtHk) { pD3DKMTQueryStatistics = (PFND3DKMTQUERYSTATISTICS)GetProcAddress(hD3dKmtHk, "D3DKMTQueryStatistics"); } // 调用时需自行填充结构体参数,注意权限和兼容性
内容的提问来源于stack exchange,提问作者Meldryt
相关产品推荐
相关产品推荐

