VirtualBox

source: vbox/trunk/src/VBox/Runtime/r3/win/RTSystemQueryOSInfo-win.cpp@ 51437

Last change on this file since 51437 was 50976, checked in by vboxsync, 11 years ago

RTSystemQueryOSInfo-win.cpp,init-win.cpp: Detect windows 8.1 correctly, it will try hide from us if we use GetVersionEx and the like. Fixed bug in service pack query where it would return ANSI strings instead of UTF-8 strings.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 15.6 KB
Line 
1/* $Id: RTSystemQueryOSInfo-win.cpp 50976 2014-04-04 19:34:38Z vboxsync $ */
2/** @file
3 * IPRT - RTSystemQueryOSInfo, generic stub.
4 */
5
6/*
7 * Copyright (C) 2008-2011 Oracle Corporation
8 *
9 * This file is part of VirtualBox Open Source Edition (OSE), as
10 * available from http://www.virtualbox.org. This file is free software;
11 * you can redistribute it and/or modify it under the terms of the GNU
12 * General Public License (GPL) as published by the Free Software
13 * Foundation, in version 2 as it comes in the "COPYING" file of the
14 * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
15 * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
16 *
17 * The contents of this file may alternatively be used under the terms
18 * of the Common Development and Distribution License Version 1.0
19 * (CDDL) only, as it comes in the "COPYING.CDDL" file of the
20 * VirtualBox OSE distribution, in which case the provisions of the
21 * CDDL are applicable instead of those of the GPL.
22 *
23 * You may elect to license modified versions of this file under the
24 * terms and conditions of either the GPL or the CDDL or both.
25 */
26
27/*******************************************************************************
28* Header Files *
29*******************************************************************************/
30#include "internal/iprt.h"
31#include <Windows.h>
32#include <WinUser.h>
33
34#include "internal-r3-win.h"
35#include <iprt/system.h>
36#include <iprt/assert.h>
37#include <iprt/string.h>
38#include <iprt/ctype.h>
39
40
41/*******************************************************************************
42* Structures and Typedefs *
43*******************************************************************************/
44
45/**
46 * These are the PRODUCT_* defines found in the Vista Platform SDK and returned
47 * by GetProductInfo().
48 *
49 * We define them ourselves because we don't necessarily have any Vista PSDK around.
50 */
51typedef enum RTWINPRODTYPE
52{
53 kRTWinProdType_UNDEFINED = 0x00000000, ///< An unknown product
54 kRTWinProdType_BUSINESS = 0x00000006, ///< Business Edition
55 kRTWinProdType_BUSINESS_N = 0x00000010, ///< Business Edition
56 kRTWinProdType_CLUSTER_SERVER = 0x00000012, ///< Cluster Server Edition
57 kRTWinProdType_DATACENTER_SERVER = 0x00000008, ///< Server Datacenter Edition (full installation)
58 kRTWinProdType_DATACENTER_SERVER_CORE = 0x0000000C, ///< Server Datacenter Edition (core installation)
59 kRTWinProdType_ENTERPRISE = 0x00000004, ///< Enterprise Edition
60 kRTWinProdType_ENTERPRISE_N = 0x0000001B, ///< Enterprise Edition
61 kRTWinProdType_ENTERPRISE_SERVER = 0x0000000A, ///< Server Enterprise Edition (full installation)
62 kRTWinProdType_ENTERPRISE_SERVER_CORE = 0x0000000E, ///< Server Enterprise Edition (core installation)
63 kRTWinProdType_ENTERPRISE_SERVER_IA64 = 0x0000000F, ///< Server Enterprise Edition for Itanium-based Systems
64 kRTWinProdType_HOME_BASIC = 0x00000002, ///< Home Basic Edition
65 kRTWinProdType_HOME_BASIC_N = 0x00000005, ///< Home Basic Edition
66 kRTWinProdType_HOME_PREMIUM = 0x00000003, ///< Home Premium Edition
67 kRTWinProdType_HOME_PREMIUM_N = 0x0000001A, ///< Home Premium Edition
68 kRTWinProdType_HOME_SERVER = 0x00000013, ///< Home Server Edition
69 kRTWinProdType_SERVER_FOR_SMALLBUSINESS = 0x00000018, ///< Server for Small Business Edition
70 kRTWinProdType_SMALLBUSINESS_SERVER = 0x00000009, ///< Small Business Server
71 kRTWinProdType_SMALLBUSINESS_SERVER_PREMIUM = 0x00000019, ///< Small Business Server Premium Edition
72 kRTWinProdType_STANDARD_SERVER = 0x00000007, ///< Server Standard Edition (full installation)
73 kRTWinProdType_STANDARD_SERVER_CORE = 0x0000000D, ///< Server Standard Edition (core installation)
74 kRTWinProdType_STARTER = 0x0000000B, ///< Starter Edition
75 kRTWinProdType_STORAGE_ENTERPRISE_SERVER = 0x00000017, ///< Storage Server Enterprise Edition
76 kRTWinProdType_STORAGE_EXPRESS_SERVER = 0x00000014, ///< Storage Server Express Edition
77 kRTWinProdType_STORAGE_STANDARD_SERVER = 0x00000015, ///< Storage Server Standard Edition
78 kRTWinProdType_STORAGE_WORKGROUP_SERVER = 0x00000016, ///< Storage Server Workgroup Edition
79 kRTWinProdType_ULTIMATE = 0x00000001, ///< Ultimate Edition
80 kRTWinProdType_ULTIMATE_N = 0x0000001C, ///< Ultimate Edition
81 kRTWinProdType_WEB_SERVER = 0x00000011, ///< Web Server Edition (full)
82 kRTWinProdType_WEB_SERVER_CORE = 0x0000001D ///< Web Server Edition (core)
83} RTWINPRODTYPE;
84
85
86/**
87 * Wrapper around the GetProductInfo API.
88 *
89 * @returns The vista type.
90 */
91static RTWINPRODTYPE rtSystemWinGetProductInfo(DWORD dwOSMajorVersion, DWORD dwOSMinorVersion, DWORD dwSpMajorVersion, DWORD dwSpMinorVersion)
92{
93 BOOL (WINAPI *pfnGetProductInfo)(DWORD, DWORD, DWORD, DWORD, PDWORD);
94 pfnGetProductInfo = (BOOL (WINAPI *)(DWORD, DWORD, DWORD, DWORD, PDWORD))GetProcAddress(GetModuleHandle("kernel32.dll"), "GetProductInfo");
95 if (pfnGetProductInfo)
96 {
97 DWORD dwProductType = kRTWinProdType_UNDEFINED;
98 if (pfnGetProductInfo(dwOSMajorVersion, dwOSMinorVersion, dwSpMajorVersion, dwSpMinorVersion, &dwProductType))
99 return (RTWINPRODTYPE)dwProductType;
100 }
101 return kRTWinProdType_UNDEFINED;
102}
103
104
105
106/**
107 * Appends the product type if available.
108 *
109 * @param pszTmp The buffer. Assumes it's big enough.
110 */
111static void rtSystemWinAppendProductType(char *pszTmp)
112{
113 RTWINPRODTYPE enmVistaType = rtSystemWinGetProductInfo(6, 0, 0, 0);
114 switch (enmVistaType)
115 {
116 case kRTWinProdType_BUSINESS: strcat(pszTmp, " Business Edition"); break;
117 case kRTWinProdType_BUSINESS_N: strcat(pszTmp, " Business Edition"); break;
118 case kRTWinProdType_CLUSTER_SERVER: strcat(pszTmp, " Cluster Server Edition"); break;
119 case kRTWinProdType_DATACENTER_SERVER: strcat(pszTmp, " Server Datacenter Edition (full installation)"); break;
120 case kRTWinProdType_DATACENTER_SERVER_CORE: strcat(pszTmp, " Server Datacenter Edition (core installation)"); break;
121 case kRTWinProdType_ENTERPRISE: strcat(pszTmp, " Enterprise Edition"); break;
122 case kRTWinProdType_ENTERPRISE_N: strcat(pszTmp, " Enterprise Edition"); break;
123 case kRTWinProdType_ENTERPRISE_SERVER: strcat(pszTmp, " Server Enterprise Edition (full installation)"); break;
124 case kRTWinProdType_ENTERPRISE_SERVER_CORE: strcat(pszTmp, " Server Enterprise Edition (core installation)"); break;
125 case kRTWinProdType_ENTERPRISE_SERVER_IA64: strcat(pszTmp, " Server Enterprise Edition for Itanium-based Systems"); break;
126 case kRTWinProdType_HOME_BASIC: strcat(pszTmp, " Home Basic Edition"); break;
127 case kRTWinProdType_HOME_BASIC_N: strcat(pszTmp, " Home Basic Edition"); break;
128 case kRTWinProdType_HOME_PREMIUM: strcat(pszTmp, " Home Premium Edition"); break;
129 case kRTWinProdType_HOME_PREMIUM_N: strcat(pszTmp, " Home Premium Edition"); break;
130 case kRTWinProdType_HOME_SERVER: strcat(pszTmp, " Home Server Edition"); break;
131 case kRTWinProdType_SERVER_FOR_SMALLBUSINESS: strcat(pszTmp, " Server for Small Business Edition"); break;
132 case kRTWinProdType_SMALLBUSINESS_SERVER: strcat(pszTmp, " Small Business Server"); break;
133 case kRTWinProdType_SMALLBUSINESS_SERVER_PREMIUM: strcat(pszTmp, " Small Business Server Premium Edition"); break;
134 case kRTWinProdType_STANDARD_SERVER: strcat(pszTmp, " Server Standard Edition (full installation)"); break;
135 case kRTWinProdType_STANDARD_SERVER_CORE: strcat(pszTmp, " Server Standard Edition (core installation)"); break;
136 case kRTWinProdType_STARTER: strcat(pszTmp, " Starter Edition"); break;
137 case kRTWinProdType_STORAGE_ENTERPRISE_SERVER: strcat(pszTmp, " Storage Server Enterprise Edition"); break;
138 case kRTWinProdType_STORAGE_EXPRESS_SERVER: strcat(pszTmp, " Storage Server Express Edition"); break;
139 case kRTWinProdType_STORAGE_STANDARD_SERVER: strcat(pszTmp, " Storage Server Standard Edition"); break;
140 case kRTWinProdType_STORAGE_WORKGROUP_SERVER: strcat(pszTmp, " Storage Server Workgroup Edition"); break;
141 case kRTWinProdType_ULTIMATE: strcat(pszTmp, " Ultimate Edition"); break;
142 case kRTWinProdType_ULTIMATE_N: strcat(pszTmp, " Ultimate Edition"); break;
143 case kRTWinProdType_WEB_SERVER: strcat(pszTmp, " Web Server Edition (full installation)"); break;
144 case kRTWinProdType_WEB_SERVER_CORE: strcat(pszTmp, " Web Server Edition (core installation)"); break;
145 case kRTWinProdType_UNDEFINED: break;
146 }
147}
148
149
150/**
151 * Services the RTSYSOSINFO_PRODUCT, RTSYSOSINFO_RELEASE
152 * and RTSYSOSINFO_SERVICE_PACK requests.
153 *
154 * @returns See RTSystemQueryOSInfo.
155 * @param enmInfo See RTSystemQueryOSInfo.
156 * @param pszInfo See RTSystemQueryOSInfo.
157 * @param cchInfo See RTSystemQueryOSInfo.
158 */
159static int rtSystemWinQueryOSVersion(RTSYSOSINFO enmInfo, char *pszInfo, size_t cchInfo)
160{
161 /*
162 * Make sure it's terminated correctly in case of error.
163 */
164 *pszInfo = '\0';
165
166 /*
167 * Check that we got the windows version at init time.
168 */
169 AssertReturn(g_WinOsInfoEx.dwOSVersionInfoSize, VERR_WRONG_ORDER);
170
171 /*
172 * Service the request.
173 */
174 char szTmp[512];
175 szTmp[0] = '\0';
176 switch (enmInfo)
177 {
178 /*
179 * The product name.
180 */
181 case RTSYSOSINFO_PRODUCT:
182 {
183 switch (g_enmWinVer)
184 {
185 case kRTWinOSType_95: strcpy(szTmp, "Windows 95"); break;
186 case kRTWinOSType_95SP1: strcpy(szTmp, "Windows 95 (Service Pack 1)"); break;
187 case kRTWinOSType_95OSR2: strcpy(szTmp, "Windows 95 (OSR 2)"); break;
188 case kRTWinOSType_98: strcpy(szTmp, "Windows 98"); break;
189 case kRTWinOSType_98SP1: strcpy(szTmp, "Windows 98 (Service Pack 1)"); break;
190 case kRTWinOSType_98SE: strcpy(szTmp, "Windows 98 (Second Edition)"); break;
191 case kRTWinOSType_ME: strcpy(szTmp, "Windows Me"); break;
192 case kRTWinOSType_NT351: strcpy(szTmp, "Windows NT 3.51"); break;
193 case kRTWinOSType_NT4: strcpy(szTmp, "Windows NT 4.0"); break;
194 case kRTWinOSType_2K: strcpy(szTmp, "Windows 2000"); break;
195 case kRTWinOSType_XP:
196 strcpy(szTmp, "Windows XP");
197 if (g_WinOsInfoEx.wSuiteMask & VER_SUITE_PERSONAL)
198 strcat(szTmp, " Home");
199 if ( g_WinOsInfoEx.wProductType == VER_NT_WORKSTATION
200 && !(g_WinOsInfoEx.wSuiteMask & VER_SUITE_PERSONAL))
201 strcat(szTmp, " Professional");
202#if 0 /** @todo fixme */
203 if (GetSystemMetrics(SM_MEDIACENTER))
204 strcat(szTmp, " Media Center");
205#endif
206 break;
207
208 case kRTWinOSType_2003: strcpy(szTmp, "Windows 2003"); break;
209 case kRTWinOSType_VISTA:
210 {
211 strcpy(szTmp, "Windows Vista");
212 rtSystemWinAppendProductType(szTmp);
213 break;
214 }
215 case kRTWinOSType_2008: strcpy(szTmp, "Windows 2008"); break;
216 case kRTWinOSType_7: strcpy(szTmp, "Windows 7"); break;
217 case kRTWinOSType_8: strcpy(szTmp, "Windows 8"); break;
218 case kRTWinOSType_81: strcpy(szTmp, "Windows 8.1"); break;
219
220 case kRTWinOSType_NT_UNKNOWN:
221 RTStrPrintf(szTmp, sizeof(szTmp), "Unknown NT v%u.%u",
222 g_WinOsInfoEx.dwMajorVersion, g_WinOsInfoEx.dwMinorVersion);
223 break;
224
225 default:
226 AssertFailed();
227 case kRTWinOSType_UNKNOWN:
228 RTStrPrintf(szTmp, sizeof(szTmp), "Unknown %d v%u.%u",
229 g_WinOsInfoEx.dwPlatformId, g_WinOsInfoEx.dwMajorVersion, g_WinOsInfoEx.dwMinorVersion);
230 break;
231 }
232 break;
233 }
234
235 /*
236 * The release.
237 */
238 case RTSYSOSINFO_RELEASE:
239 {
240 RTStrPrintf(szTmp, sizeof(szTmp), "%u.%u.%u",
241 g_WinOsInfoEx.dwMajorVersion, g_WinOsInfoEx.dwMinorVersion, g_WinOsInfoEx.dwBuildNumber);
242 break;
243 }
244
245
246 /*
247 * Get the service pack.
248 */
249 case RTSYSOSINFO_SERVICE_PACK:
250 {
251 if (g_WinOsInfoEx.wServicePackMajor)
252 {
253 if (g_WinOsInfoEx.wServicePackMinor)
254 RTStrPrintf(szTmp, sizeof(szTmp), "%u.%u",
255 (unsigned)g_WinOsInfoEx.wServicePackMajor, (unsigned)g_WinOsInfoEx.wServicePackMinor);
256 else
257 RTStrPrintf(szTmp, sizeof(szTmp), "%u",
258 (unsigned)g_WinOsInfoEx.wServicePackMajor);
259 }
260 else if (g_WinOsInfoEx.szCSDVersion[0])
261 {
262 /* just copy the entire string. */
263 char *pszTmp = szTmp;
264 int rc = RTUtf16ToUtf8Ex(g_WinOsInfoEx.szCSDVersion, RT_ELEMENTS(g_WinOsInfoEx.szCSDVersion),
265 &pszTmp, sizeof(szTmp), NULL);
266 if (RT_SUCCESS(rc))
267 RTStrStripR(szTmp);
268 else
269 szTmp[0] = '\0';
270 AssertCompile(sizeof(szTmp) > sizeof(g_WinOsInfoEx.szCSDVersion));
271 }
272 else
273 {
274 switch (g_enmWinVer)
275 {
276 case kRTWinOSType_95SP1: strcpy(szTmp, "1"); break;
277 case kRTWinOSType_98SP1: strcpy(szTmp, "1"); break;
278 default:
279 break;
280 }
281 }
282 break;
283 }
284
285 default:
286 AssertFatalFailed();
287 }
288
289 /*
290 * Copy the result to the return buffer.
291 */
292 size_t cchTmp = strlen(szTmp);
293 Assert(cchTmp < sizeof(szTmp));
294 if (cchTmp < cchInfo)
295 {
296 memcpy(pszInfo, szTmp, cchTmp + 1);
297 return VINF_SUCCESS;
298 }
299 memcpy(pszInfo, szTmp, cchInfo - 1);
300 pszInfo[cchInfo - 1] = '\0';
301 return VERR_BUFFER_OVERFLOW;
302}
303
304
305
306RTDECL(int) RTSystemQueryOSInfo(RTSYSOSINFO enmInfo, char *pszInfo, size_t cchInfo)
307{
308 /*
309 * Quick validation.
310 */
311 AssertReturn(enmInfo > RTSYSOSINFO_INVALID && enmInfo < RTSYSOSINFO_END, VERR_INVALID_PARAMETER);
312 AssertPtrReturn(pszInfo, VERR_INVALID_POINTER);
313 if (!cchInfo)
314 return VERR_BUFFER_OVERFLOW;
315
316
317 /*
318 * Handle the request.
319 */
320 switch (enmInfo)
321 {
322 case RTSYSOSINFO_PRODUCT:
323 case RTSYSOSINFO_RELEASE:
324 case RTSYSOSINFO_SERVICE_PACK:
325 return rtSystemWinQueryOSVersion(enmInfo, pszInfo, cchInfo);
326
327 case RTSYSOSINFO_VERSION:
328 default:
329 *pszInfo = '\0';
330 }
331
332 return VERR_NOT_SUPPORTED;
333}
334
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette