122#if defined(__APPLE__)
124 size_t size =
sizeof(result);
125 if (sysctlbyname(
"kern.osrelease", result, &size,
nullptr, 0) == 0)
129#elif defined(__CYGWIN__)
131 if (uname(&name) == 0)
133 std::string result(name.sysname);
135 result.append(name.release);
137 result.append(name.version);
142#elif defined(linux) || defined(__linux) || defined(__linux__)
143 static std::regex pattern(
"DISTRIB_DESCRIPTION=\"(.*)\"");
146 std::ifstream stream(
"/etc/lsb-release");
147 while (getline(stream, line))
150 if (std::regex_match(line, matches, pattern))
155#elif defined(_WIN32) || defined(_WIN64)
156 static NTSTATUS(__stdcall *RtlGetVersion)(OUT PRTL_OSVERSIONINFOEXW lpVersionInformation) = (NTSTATUS(__stdcall*)(PRTL_OSVERSIONINFOEXW))GetProcAddress(GetModuleHandle(
"ntdll.dll"),
"RtlGetVersion");
157 static void(__stdcall *GetNativeSystemInfo)(OUT LPSYSTEM_INFO lpSystemInfo) = (
void(__stdcall*)(LPSYSTEM_INFO))GetProcAddress(GetModuleHandle(
"kernel32.dll"),
"GetNativeSystemInfo");
158 static BOOL(__stdcall *GetProductInfo)(IN DWORD dwOSMajorVersion, IN DWORD dwOSMinorVersion, IN DWORD dwSpMajorVersion, IN DWORD dwSpMinorVersion, OUT PDWORD pdwReturnedProductType) = (BOOL(__stdcall*)(DWORD, DWORD, DWORD, DWORD, PDWORD))GetProcAddress(GetModuleHandle(
"kernel32.dll"),
"GetProductInfo");
160 OSVERSIONINFOEXW osvi;
161 ZeroMemory(&osvi,
sizeof(OSVERSIONINFOEXW));
162 osvi.dwOSVersionInfoSize =
sizeof(OSVERSIONINFOEXW);
164 if (RtlGetVersion !=
nullptr)
166 NTSTATUS ntRtlGetVersionStatus = RtlGetVersion(&osvi);
167 if (ntRtlGetVersionStatus != STATUS_SUCCESS)
174#pragma warning(disable: 4996)
176 BOOL bOsVersionInfoEx = GetVersionExW((OSVERSIONINFOW*)&osvi);
177 if (bOsVersionInfoEx == 0)
185 ZeroMemory(&si,
sizeof(SYSTEM_INFO));
187 if (GetNativeSystemInfo !=
nullptr)
188 GetNativeSystemInfo(&si);
192 if ((osvi.dwPlatformId != VER_PLATFORM_WIN32_NT) || (osvi.dwMajorVersion <= 4))
197 std::stringstream os;
201 if (osvi.dwMajorVersion >= 6)
203 if (osvi.dwMajorVersion == 10)
205 if (osvi.dwMinorVersion == 0)
207 if (osvi.wProductType == VER_NT_WORKSTATION)
209 if (osvi.dwBuildNumber >= 22000)
216 if (osvi.dwBuildNumber >= 20348)
217 os <<
"Windows Server 2022 ";
218 else if (osvi.dwBuildNumber >= 17763)
219 os <<
"Windows Server 2019 ";
221 os <<
"Windows Server 2016 ";
225 else if (osvi.dwMajorVersion == 6)
227 if (osvi.dwMinorVersion == 3)
229 if (osvi.wProductType == VER_NT_WORKSTATION)
230 os <<
"Windows 8.1 ";
232 os <<
"Windows Server 2012 R2 ";
234 else if (osvi.dwMinorVersion == 2)
236 if (osvi.wProductType == VER_NT_WORKSTATION)
239 os <<
"Windows Server 2012 ";
241 else if (osvi.dwMinorVersion == 1)
243 if (osvi.wProductType == VER_NT_WORKSTATION)
246 os <<
"Windows Server 2008 R2 ";
248 else if (osvi.dwMinorVersion == 0)
250 if (osvi.wProductType == VER_NT_WORKSTATION)
251 os <<
"Windows Vista ";
253 os <<
"Windows Server 2008 ";
258 if ((GetProductInfo !=
nullptr) && GetProductInfo(osvi.dwMajorVersion, osvi.dwMinorVersion, 0, 0, &dwType))
262 case PRODUCT_ULTIMATE:
263 os <<
"Ultimate Edition";
265 case PRODUCT_PROFESSIONAL:
266 os <<
"Professional";
268 case PRODUCT_HOME_PREMIUM:
269 os <<
"Home Premium Edition";
271 case PRODUCT_HOME_BASIC:
272 os <<
"Home Basic Edition";
274 case PRODUCT_ENTERPRISE:
275 os <<
"Enterprise Edition";
277 case PRODUCT_BUSINESS:
278 os <<
"Business Edition";
280 case PRODUCT_STARTER:
281 os <<
"Starter Edition";
283 case PRODUCT_CLUSTER_SERVER:
284 os <<
"Cluster Server Edition";
286 case PRODUCT_DATACENTER_SERVER:
287 os <<
"Datacenter Edition";
289 case PRODUCT_DATACENTER_SERVER_CORE:
290 os <<
"Datacenter Edition (core installation)";
292 case PRODUCT_ENTERPRISE_SERVER:
293 os <<
"Enterprise Edition";
295 case PRODUCT_ENTERPRISE_SERVER_CORE:
296 os <<
"Enterprise Edition (core installation)";
298 case PRODUCT_ENTERPRISE_SERVER_IA64:
299 os <<
"Enterprise Edition for Itanium-based Systems";
301 case PRODUCT_SMALLBUSINESS_SERVER:
302 os <<
"Small Business Server";
304 case PRODUCT_SMALLBUSINESS_SERVER_PREMIUM:
305 os <<
"Small Business Server Premium Edition";
307 case PRODUCT_STANDARD_SERVER:
308 os <<
"Standard Edition";
310 case PRODUCT_STANDARD_SERVER_CORE:
311 os <<
"Standard Edition (core installation)";
313 case PRODUCT_WEB_SERVER:
314 os <<
"Web Server Edition";
319 else if ((osvi.dwMajorVersion == 5) && (osvi.dwMinorVersion == 2))
321 if (GetSystemMetrics(SM_SERVERR2))
322 os <<
"Windows Server 2003 R2, ";
323 else if (osvi.wSuiteMask & VER_SUITE_STORAGE_SERVER)
324 os <<
"Windows Storage Server 2003";
325 else if (osvi.wSuiteMask & VER_SUITE_WH_SERVER)
326 os <<
"Windows Home Server";
327 else if ((osvi.wProductType == VER_NT_WORKSTATION) && (si.wProcessorArchitecture == PROCESSOR_ARCHITECTURE_AMD64))
328 os <<
"Windows XP Professional x64 Edition";
330 os <<
"Windows Server 2003, ";
331 if (osvi.wProductType != VER_NT_WORKSTATION)
333 if (si.wProcessorArchitecture == PROCESSOR_ARCHITECTURE_IA64)
335 if (osvi.wSuiteMask & VER_SUITE_DATACENTER)
336 os <<
"Datacenter Edition for Itanium-based Systems";
337 else if (osvi.wSuiteMask & VER_SUITE_ENTERPRISE)
338 os <<
"Enterprise Edition for Itanium-based Systems";
340 else if (si.wProcessorArchitecture == PROCESSOR_ARCHITECTURE_AMD64)
342 if (osvi.wSuiteMask & VER_SUITE_DATACENTER)
343 os <<
"Datacenter x64 Edition";
344 else if (osvi.wSuiteMask & VER_SUITE_ENTERPRISE)
345 os <<
"Enterprise x64 Edition";
347 os <<
"Standard x64 Edition";
351 if (osvi.wSuiteMask & VER_SUITE_COMPUTE_SERVER)
352 os <<
"Compute Cluster Edition";
353 else if (osvi.wSuiteMask & VER_SUITE_DATACENTER)
354 os <<
"Datacenter Edition";
355 else if (osvi.wSuiteMask & VER_SUITE_ENTERPRISE)
356 os <<
"Enterprise Edition";
357 else if (osvi.wSuiteMask & VER_SUITE_BLADE)
360 os <<
"Standard Edition";
364 else if ((osvi.dwMajorVersion == 5) && (osvi.dwMinorVersion == 1))
367 if (osvi.wSuiteMask & VER_SUITE_PERSONAL)
368 os <<
"Home Edition";
370 os <<
"Professional";
372 else if ((osvi.dwMajorVersion == 5) && (osvi.dwMinorVersion == 0))
374 os <<
"Windows 2000 ";
375 if (osvi.wProductType == VER_NT_WORKSTATION)
376 os <<
"Professional";
379 if (osvi.wSuiteMask & VER_SUITE_DATACENTER)
380 os <<
"Datacenter Server";
381 else if (osvi.wSuiteMask & VER_SUITE_ENTERPRISE)
382 os <<
"Advanced Server";
389 std::wstring sp_version(osvi.szCSDVersion);
390 std::wstring_convert<std::codecvt_utf8_utf16<wchar_t>> convert;
391 if (std::wcslen(osvi.szCSDVersion) > 0)
392 os <<
" " << convert.to_bytes(sp_version.data(), sp_version.data() + sp_version.size());
395 os <<
" (build " << osvi.dwBuildNumber <<
")";
398 if (osvi.dwMajorVersion >= 6)
400 if (si.wProcessorArchitecture == PROCESSOR_ARCHITECTURE_INTEL)
402 else if (si.wProcessorArchitecture == PROCESSOR_ARCHITECTURE_AMD64)
404 else if (si.wProcessorArchitecture == PROCESSOR_ARCHITECTURE_IA64)
405 os <<
", Intel Itanium";
406 else if (si.wProcessorArchitecture == PROCESSOR_ARCHITECTURE_ARM)
408#if !defined(__MINGW32__) && !defined(__MINGW64__)
409 else if (si.wProcessorArchitecture == PROCESSOR_ARCHITECTURE_ARM64)
416 #error Unsupported platform
443 std::map<std::string, std::string> result;
444#if defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__)
448 int offset = (envar[0] ==
'=') ? 1 : 0;
449 char* separator = std::strchr(envar + offset,
'=');
450 std::string key(envar, separator - envar);
452 char* pvalue = separator + 1;
453 std::string value(pvalue);
457#elif defined(_WIN32) || defined(_WIN64)
459 auto envars =
resource(GetEnvironmentStringsW(), [](
wchar_t* penv) { FreeEnvironmentStringsW(penv); });
461 for (
const wchar_t* envar =
envars.get(); *envar != L
'\0'; )
463 int offset = (envar[0] ==
'=') ? 1 : 0;
464 const wchar_t* separator = std::wcschr(envar + offset, L
'=');
465 std::wstring key(envar, separator - envar);
467 const wchar_t* pvalue = separator + 1;
468 std::wstring value(pvalue);
472 envar = pvalue + value.size() + 1;