在GetVersion/GetVersionEx已经被弃用的情况下,如何获取Win8.1的操作系统版本?

10
我有一些情景需要知道操作系统的主/次版本和构建号等信息。
从Windows 8.1开始,GetVersion和GetVersionEx已被弃用,声明如下:
[GetVersion/GetVersionEx 可能在Windows 8.1之后的版本中被更改或不可用。请使用Version Helper函数]
没有任何version helper APIs可以帮助我获取操作系统版本号,而只能帮助我验证或了解我的版本是否与某个特定版本相同或以上。有什么办法吗?

1
我从未见过微软删除一个API函数,即使它已被弃用,所以如果你想要继续使用它,我会建议你这样做。只需注意,在Windows的后续版本中,除非您的清单指定与当前版本兼容性,否则它会关于版本号进行欺骗。 - Jonathan Potter
2
有WMI的Win32_OperatingSystem类。 - Alex K.
@Alex说的很好。你总是可以从kernel32中读取版本资源。 - David Heffernan
你在这里的情况是什么?另外,参见此 Stack Overflow 线程:https://dev59.com/SGEh5IYBdhLWcg3whT7T。 - Chuck Walbourn
@AlexK。我认为你应该将它作为答案添加到这个问题中,因为没有一个答案在谈论WMI查询。 - Ram
3个回答

6
API GetVersionEx() 在Windows 8.1+中仍然可用,但微软已经更改了其功能。来自MSDN的消息(我强调):

随着 Windows 8.1 的发布,GetVersionEx API的行为在其返回的操作系统版本值方面发生了更改。GetVersionEx函数返回的值现在取决于应用程序是否已启动

未针对Windows 8.1创建清单的应用程序将返回Windows 8操作系统版本值(6.2)。一旦将应用程序针对特定操作系统版本进行了清单处理,GetVersionEx在未来发布中始终会返回该应用程序所针对的版本。请参考针对Windows 8.1定位您的应用程序,以便为Windows 8.1创建清单。

您需要做的是向应用程序(.exe/.dll)二进制文件添加正确的GUID(通过清单XML信息)。换句话说,如果明确声明您的应用程序支持8.1,则在Windows 8.1上运行时,GetVersionEx()将返回正确的信息;否则,它将欺骗您

请参阅面向Windows 8.1定位您的应用程序,了解GUID列表。此外,在这里这里也有相关信息。

懒人专属GUID列表

  • Vista / Server 2008: {e2011457-1546-43c5-a5fe-008deee3d3f0}
  • Windows 7 / Server 2008 R2: {35138b9a-5d96-4fbd-8e2d-a2440225f93a}
  • Windows 8 / Server 2012: {4a2f28e3-53b9-4441-ba9c-d69d4a4a6e38}
  • Windows 8.1 / Server 2012 R2 : {1f676c76-80e1-4239-95bb-83d0f6d0da78}
  • Windows 10 / Server 2016: {8e0f7a12-bfb3-4fe8-b9a5-48fd50a15a9a}

关于Windows Server 2019,我不确定是否已发布新的GUID。如果您了解更多信息,请评论!


如果我的应用程序没有清单文件会怎样? - Abhishek Jain
您可以在项目设置中简单地添加一个。例如,请参见此处:http://msdn.microsoft.com/zh-cn/library/ms235229(v=vs.110).aspx - NuSkooler
8
请记住,如果您不经常更新应用程序,最终您的清单将不包括“最新”的Windows版本,您会得到一个版本错误。 - Chuck Walbourn
1
请记住,除非您在最新版本上更新和测试应用程序,否则很可能会出现故障。例如:GetVersionEx()停止按预期工作。这是WAD。 - NuSkooler
为了针对Windows 8.1,您需要在源文件中包含应用程序清单或包含_NT_TARGET_VERSION=$(_NT_TARGET_VERSION_LATEST)。问题是将include _NT_TARGET_VERSION放在哪个源文件中? - Abhishek Jain

0

有一个名为GetProductInfo的新函数,返回版本信息。

如果您想测试特定版本,应使用VerifyVersionInfo

很容易创建一个结构来检查特定操作系统版本是否正在运行。 VerifyVersionInfo需要两个版本结构,您可以轻松检查VER_GREATER_EQUAL和VER_LESS_EQUAL

还要注意,如果在兼容性部分为您的清单定义了正确的支持的操作系统条目,则GetVersionEx不会在Windows 8.1系统上说谎。但它可能会在将来的操作系统版本中说谎!

请参见针对Windows 8.1定位您的应用程序以获取GUID列表。 还在此处中介绍。

应用程序清单的GUID列表

  • Vista:{e2011457-1546-43c5-a5fe-008deee3d3f0}
  • Windows 7:{35138b9a-5d96-4fbd-8e2d-a2440225f93a}
  • Windows 8:{4a2f28e3-53b9-4441-ba9c-d69d4a4a6e38}
  • Windows 8.1:{1f676c76-80e1-4239-95bb-83d0f6d0da78}
  • Windows 10:{8e0f7a12-bfb3-4fe8-b9a5-48fd50a15a9a}

我想获取正在运行我的程序的操作系统的主要版本号、次要版本号和构建号。如何使用GetProductInfo和VerifyVersionInfo来获取? - Abhishek Jain
您可以使用VerifyVersionInfo获取服务包的主要版本号。我不知道任何情况下SP内部的操作系统构建号会有所不同... - xMRi
10
GetProductInfo() 函数不返回操作系统版本信息。你需要传入所需的操作系统版本,它会返回操作系统的产品类型(如商业、企业、数据中心等)。这在文档中已经明确说明:"检索本地计算机上操作系统的产品类型,并将该类型映射到指定操作系统支持的产品类型。" - Remy Lebeau

-11

请查看codeproject.com上的这篇文章,它在Windows 8上运行得非常完美:

1)下载.DLL并将其添加到您的项目中。

2)使用此代码获取操作系统信息

StringBuilder sb = new StringBuilder(String.Empty);
sb.AppendLine("Operation System Information");
sb.AppendLine("----------------------------");
sb.AppendLine(String.Format("Name = {0}", OSVersionInfo.Name));
sb.AppendLine(String.Format("Edition = {0}", OSVersionInfo.Edition));
if (OSVersionInfo.ServicePack!=string.Empty)
sb.AppendLine(String.Format("Service Pack = {0}", OSVersionInfo.ServicePack));
else
sb.AppendLine("Service Pack = None");
sb.AppendLine(String.Format("Version = {0}", OSVersionInfo.VersionString));
sb.AppendLine(String.Format("ProcessorBits = {0}", OSVersionInfo.ProcessorBits));
sb.AppendLine(String.Format("OSBits = {0}", OSVersionInfo.OSBits));
sb.AppendLine(String.Format("ProgramBits = {0}", OSVersionInfo.ProgramBits));

textBox1.Text = sb.ToString();

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接