問題描述
我的目標是在我的代碼中檢測 Windows 10,它必須跨平臺以及跨不同版本的 Windows(至少 7 和更高版本)工作.Windows 提供了 IsWindows10OrGreater()
來解決這個問題,但它還有另一個問題,這個函數在以前的 Windows 版本中不存在.
My objective is to detect Windows 10 in my code which has to work cross-platform as well as across different versions of Windows (atleast 7 & up). Windows provides IsWindows10OrGreater()
to tackle this problem, but there's another issue with it, this function isn't present in previous windows versions.
您會發(fā)現無數關于此的博客和 SO 問題,以及像 this 和 getversion 等函數返回一些不同版本而不是正確版本的明顯瘋狂.
You'll find countless blogs and SO questions regarding this as well as the manifest madness where functions like this and getversion and others return some different version rather than the correct one.
例如在我的機器上 - 方法 IsWindows10OrGreater()
無法編譯(我必須安裝 Win10 SDK),并且 IsWindowsVersionOrGreater()
報告 6
作為主要版本.
For example on my machine - the method IsWindows10OrGreater()
doesn't compile(I would've to install Win10 SDK), and IsWindowsVersionOrGreater()
reports 6
as major version.
那么有沒有一種理智的多版本方法可以解決這個問題?
So is there a sane multi-version way I could solve this problem?
推薦答案
檢索真實操作系統(tǒng)版本的最直接方法是調用 RtlGetVersion.這是 GetVersionEx
和 VerifyVersionInfo
調用的,但不使用兼容性墊片.
The most straight-forward way to retrieve the true OS version is to call RtlGetVersion. It is what GetVersionEx
and VerifyVersionInfo
call, but doesn't employ the compatibility shims.
您可以使用 DDK(通過 #include <ntddk.h> 并從內核模式鏈接 NtosKrnl.lib,或從用戶模式鏈接 ntdll.lib),或者使用運行時動態(tài)鏈接,如下面的代碼片段所示:
You can either use the DDK (by #including <ntddk.h> and linking against NtosKrnl.lib from kernel mode, or ntdll.lib from user mode), or use runtime dynamic linking as in the following snippet:
typedef LONG NTSTATUS, *PNTSTATUS;
#define STATUS_SUCCESS (0x00000000)
typedef NTSTATUS (WINAPI* RtlGetVersionPtr)(PRTL_OSVERSIONINFOW);
RTL_OSVERSIONINFOW GetRealOSVersion() {
HMODULE hMod = ::GetModuleHandleW(L"ntdll.dll");
if (hMod) {
RtlGetVersionPtr fxPtr = (RtlGetVersionPtr)::GetProcAddress(hMod, "RtlGetVersion");
if (fxPtr != nullptr) {
RTL_OSVERSIONINFOW rovi = { 0 };
rovi.dwOSVersionInfoSize = sizeof(rovi);
if ( STATUS_SUCCESS == fxPtr(&rovi) ) {
return rovi;
}
}
}
RTL_OSVERSIONINFOW rovi = { 0 };
return rovi;
}
如果您需要其他信息,您可以傳遞 RTL_OSVERSIONINFOEXW 結構代替 RTL_OSVERSIONINFOW 結構(正確分配 dwOSVersionInfoSize 成員).
In case you need additional information you can pass an RTL_OSVERSIONINFOEXW structure in place of the RTL_OSVERSIONINFOW structure (properly assigning the dwOSVersionInfoSize member).
這會在 Windows 10 上返回預期結果,即使沒有附加清單也是如此.
This returns the expected result on Windows 10, even when there is no manifest attached.
順便說一句,根據可用的功能而不是操作系統(tǒng)版本提供不同的實現被普遍認為是更好的解決方案.
As an aside, it is commonly accepted as a better solution to provide different implementations based on available features rather than OS versions.
這篇關于檢測 Windows 10 版本的文章就介紹到這了,希望我們推薦的答案對大家有所幫助,也希望大家多多支持html5模板網!