1// Windows/SystemInfo.cpp 2 3#include "StdAfx.h" 4 5#include "../../C/CpuArch.h" 6 7#include "../Common/IntToString.h" 8 9#ifdef _WIN32 10 11#include "Registry.h" 12 13#else 14 15#include <unistd.h> 16#include <sys/utsname.h> 17#ifdef __APPLE__ 18#include <sys/sysctl.h> 19#elif !defined(_AIX) 20 21#include <sys/auxv.h> 22 23// #undef AT_HWCAP // to debug 24// #undef AT_HWCAP2 // to debug 25 26/* the following patch for some debian systems. 27 Is it OK to define AT_HWCAP and AT_HWCAP2 here with these constant numbers? */ 28/* 29#if defined(__FreeBSD_kernel__) && defined(__GLIBC__) 30 #ifndef AT_HWCAP 31 #define AT_HWCAP 16 32 #endif 33 #ifndef AT_HWCAP2 34 #define AT_HWCAP2 26 35 #endif 36#endif 37*/ 38 39#ifdef MY_CPU_ARM_OR_ARM64 40#include <asm/hwcap.h> 41#endif 42#endif 43 44#ifdef __linux__ 45#include "../Windows/FileIO.h" 46#endif 47 48#endif // WIN32 49 50#include "SystemInfo.h" 51#include "System.h" 52 53using namespace NWindows; 54 55#ifdef __linux__ 56 57static bool ReadFile_to_Buffer(CFSTR fileName, CByteBuffer &buf) 58{ 59 NWindows::NFile::NIO::CInFile file; 60 if (!file.Open(fileName)) 61 return false; 62 /* 63 UInt64 size; 64 if (!file.GetLength(size)) 65 { 66 // GetLength() doesn't work "/proc/cpuinfo" 67 return false; 68 } 69 if (size >= ((UInt32)1 << 29)) 70 return false; 71 */ 72 size_t size = 0; 73 size_t addSize = ((size_t)1 << 12); 74 for (;;) 75 { 76 // printf("\nsize = %d\n", (unsigned)size); 77 buf.ChangeSize_KeepData(size + addSize, size); 78 size_t processed; 79 if (!file.ReadFull(buf + size, addSize, processed)) 80 return false; 81 if (processed == 0) 82 { 83 buf.ChangeSize_KeepData(size, size); 84 return true; 85 } 86 size += processed; 87 addSize *= 2; 88 } 89} 90 91#endif 92 93 94#if defined(_WIN32) || defined(AT_HWCAP) || defined(AT_HWCAP2) 95static void PrintHex(AString &s, UInt64 v) 96{ 97 char temp[32]; 98 ConvertUInt64ToHex(v, temp); 99 s += temp; 100} 101#endif 102 103#ifdef MY_CPU_X86_OR_AMD64 104 105Z7_NO_INLINE 106static void PrintCpuChars(AString &s, UInt32 v) 107{ 108 for (unsigned j = 0; j < 4; j++) 109 { 110 Byte b = (Byte)(v & 0xFF); 111 v >>= 8; 112 if (b == 0) 113 break; 114 if (b >= 0x20 && b <= 0x7f) 115 s += (char)b; 116 else 117 { 118 s += '['; 119 char temp[16]; 120 ConvertUInt32ToHex(b, temp); 121 s += temp; 122 s += ']'; 123 } 124 } 125} 126 127 128static void x86cpuid_to_String(AString &s) 129{ 130 s.Empty(); 131 132 UInt32 a[4]; 133 // cpuid was called already. So we don't check for cpuid availability here 134 z7_x86_cpuid(a, 0x80000000); 135 136 if (a[0] >= 0x80000004) // if (maxFunc2 >= hi+4) the full name is available 137 { 138 for (unsigned i = 0; i < 3; i++) 139 { 140 z7_x86_cpuid(a, 0x80000002 + i); 141 for (unsigned j = 0; j < 4; j++) 142 PrintCpuChars(s, a[j]); 143 } 144 } 145 146 s.Trim(); 147 148 if (s.IsEmpty()) 149 { 150 z7_x86_cpuid(a, 0); 151 for (unsigned i = 1; i < 4; i++) 152 { 153 const unsigned j = (i ^ (i >> 1)); 154 PrintCpuChars(s, a[j]); 155 } 156 s.Trim(); 157 } 158} 159 160/* 161static void x86cpuid_all_to_String(AString &s) 162{ 163 Cx86cpuid p; 164 if (!x86cpuid_CheckAndRead(&p)) 165 return; 166 s += "x86cpuid maxFunc = "; 167 s.Add_UInt32(p.maxFunc); 168 for (unsigned j = 0; j <= p.maxFunc; j++) 169 { 170 s.Add_LF(); 171 // s.Add_UInt32(j); // align 172 { 173 char temp[32]; 174 ConvertUInt32ToString(j, temp); 175 unsigned len = (unsigned)strlen(temp); 176 while (len < 8) 177 { 178 len++; 179 s.Add_Space(); 180 } 181 s += temp; 182 } 183 184 s += ":"; 185 UInt32 d[4] = { 0 }; 186 MyCPUID(j, &d[0], &d[1], &d[2], &d[3]); 187 for (unsigned i = 0; i < 4; i++) 188 { 189 char temp[32]; 190 ConvertUInt32ToHex8Digits(d[i], temp); 191 s.Add_Space(); 192 s += temp; 193 } 194 } 195} 196*/ 197 198#endif 199 200 201 202#ifdef _WIN32 203 204static const char * const k_PROCESSOR_ARCHITECTURE[] = 205{ 206 "x86" // "INTEL" 207 , "MIPS" 208 , "ALPHA" 209 , "PPC" 210 , "SHX" 211 , "ARM" 212 , "IA64" 213 , "ALPHA64" 214 , "MSIL" 215 , "x64" // "AMD64" 216 , "IA32_ON_WIN64" 217 , "NEUTRAL" 218 , "ARM64" 219 , "ARM32_ON_WIN64" 220}; 221 222#define Z7_WIN_PROCESSOR_ARCHITECTURE_INTEL 0 223#define Z7_WIN_PROCESSOR_ARCHITECTURE_AMD64 9 224 225 226#define Z7_WIN_PROCESSOR_INTEL_PENTIUM 586 227#define Z7_WIN_PROCESSOR_AMD_X8664 8664 228 229/* 230static const CUInt32PCharPair k_PROCESSOR[] = 231{ 232 { 2200, "IA64" }, 233 { 8664, "x64" } 234}; 235 236#define PROCESSOR_INTEL_386 386 237#define PROCESSOR_INTEL_486 486 238#define PROCESSOR_INTEL_PENTIUM 586 239#define PROCESSOR_INTEL_860 860 240#define PROCESSOR_INTEL_IA64 2200 241#define PROCESSOR_AMD_X8664 8664 242#define PROCESSOR_MIPS_R2000 2000 243#define PROCESSOR_MIPS_R3000 3000 244#define PROCESSOR_MIPS_R4000 4000 245#define PROCESSOR_ALPHA_21064 21064 246#define PROCESSOR_PPC_601 601 247#define PROCESSOR_PPC_603 603 248#define PROCESSOR_PPC_604 604 249#define PROCESSOR_PPC_620 620 250#define PROCESSOR_HITACHI_SH3 10003 251#define PROCESSOR_HITACHI_SH3E 10004 252#define PROCESSOR_HITACHI_SH4 10005 253#define PROCESSOR_MOTOROLA_821 821 254#define PROCESSOR_SHx_SH3 103 255#define PROCESSOR_SHx_SH4 104 256#define PROCESSOR_STRONGARM 2577 // 0xA11 257#define PROCESSOR_ARM720 1824 // 0x720 258#define PROCESSOR_ARM820 2080 // 0x820 259#define PROCESSOR_ARM920 2336 // 0x920 260#define PROCESSOR_ARM_7TDMI 70001 261#define PROCESSOR_OPTIL 18767 // 0x494f 262*/ 263 264 265/* 266static const char * const k_PF[] = 267{ 268 "FP_ERRATA" 269 , "FP_EMU" 270 , "CMPXCHG" 271 , "MMX" 272 , "PPC_MOVEMEM_64BIT" 273 , "ALPHA_BYTE" 274 , "SSE" 275 , "3DNOW" 276 , "RDTSC" 277 , "PAE" 278 , "SSE2" 279 , "SSE_DAZ" 280 , "NX" 281 , "SSE3" 282 , "CMPXCHG16B" 283 , "CMP8XCHG16" 284 , "CHANNELS" 285 , "XSAVE" 286 , "ARM_VFP_32" 287 , "ARM_NEON" 288 , "L2AT" 289 , "VIRT_FIRMWARE" 290 , "RDWRFSGSBASE" 291 , "FASTFAIL" 292 , "ARM_DIVIDE" 293 , "ARM_64BIT_LOADSTORE_ATOMIC" 294 , "ARM_EXTERNAL_CACHE" 295 , "ARM_FMAC" 296 , "RDRAND" 297 , "ARM_V8" 298 , "ARM_V8_CRYPTO" 299 , "ARM_V8_CRC32" 300 , "RDTSCP" 301 , "RDPID" 302 , "ARM_V81_ATOMIC" 303 , "MONITORX" 304}; 305*/ 306 307#endif 308 309 310static void PrintPage(AString &s, UInt64 v) 311{ 312 const char *t = "B"; 313 if ((v & 0x3ff) == 0) 314 { 315 v >>= 10; 316 t = "KB"; 317 } 318 s.Add_UInt64(v); 319 s += t; 320} 321 322#ifdef _WIN32 323 324static AString TypeToString2(const char * const table[], unsigned num, UInt32 value) 325{ 326 char sz[16]; 327 const char *p = NULL; 328 if (value < num) 329 p = table[value]; 330 if (!p) 331 { 332 ConvertUInt32ToString(value, sz); 333 p = sz; 334 } 335 return (AString)p; 336} 337 338// #if defined(Z7_LARGE_PAGES) || defined(_WIN32) 339// #ifdef _WIN32 340void PrintSize_KMGT_Or_Hex(AString &s, UInt64 v) 341{ 342 char c = 0; 343 if ((v & 0x3FF) == 0) { v >>= 10; c = 'K'; 344 if ((v & 0x3FF) == 0) { v >>= 10; c = 'M'; 345 if ((v & 0x3FF) == 0) { v >>= 10; c = 'G'; 346 if ((v & 0x3FF) == 0) { v >>= 10; c = 'T'; 347 }}}} 348 else 349 { 350 // s += "0x"; 351 PrintHex(s, v); 352 return; 353 } 354 s.Add_UInt64(v); 355 if (c) 356 s += c; 357 s += 'B'; 358} 359// #endif 360// #endif 361 362static void SysInfo_To_String(AString &s, const SYSTEM_INFO &si) 363{ 364 s += TypeToString2(k_PROCESSOR_ARCHITECTURE, Z7_ARRAY_SIZE(k_PROCESSOR_ARCHITECTURE), si.wProcessorArchitecture); 365 366 if (!( (si.wProcessorArchitecture == Z7_WIN_PROCESSOR_ARCHITECTURE_INTEL && si.dwProcessorType == Z7_WIN_PROCESSOR_INTEL_PENTIUM) 367 || (si.wProcessorArchitecture == Z7_WIN_PROCESSOR_ARCHITECTURE_AMD64 && si.dwProcessorType == Z7_WIN_PROCESSOR_AMD_X8664))) 368 { 369 s.Add_Space(); 370 // s += TypePairToString(k_PROCESSOR, Z7_ARRAY_SIZE(k_PROCESSOR), si.dwProcessorType); 371 s.Add_UInt32(si.dwProcessorType); 372 } 373 s.Add_Space(); 374 PrintHex(s, si.wProcessorLevel); 375 s.Add_Dot(); 376 PrintHex(s, si.wProcessorRevision); 377 if ((UInt64)si.dwActiveProcessorMask + 1 != ((UInt64)1 << si.dwNumberOfProcessors)) 378 if ((UInt64)si.dwActiveProcessorMask + 1 != 0 || si.dwNumberOfProcessors != sizeof(UInt64) * 8) 379 { 380 s += " act:"; 381 PrintHex(s, si.dwActiveProcessorMask); 382 } 383 s += " cpus:"; 384 s.Add_UInt32(si.dwNumberOfProcessors); 385 if (si.dwPageSize != 1 << 12) 386 { 387 s += " page:"; 388 PrintPage(s, si.dwPageSize); 389 } 390 if (si.dwAllocationGranularity != 1 << 16) 391 { 392 s += " gran:"; 393 PrintPage(s, si.dwAllocationGranularity); 394 } 395 s.Add_Space(); 396 397 const DWORD_PTR minAdd = (DWORD_PTR)si.lpMinimumApplicationAddress; 398 UInt64 maxSize = (UInt64)(DWORD_PTR)si.lpMaximumApplicationAddress + 1; 399 const UInt32 kReserveSize = ((UInt32)1 << 16); 400 if (minAdd != kReserveSize) 401 { 402 PrintSize_KMGT_Or_Hex(s, minAdd); 403 s += "-"; 404 } 405 else 406 { 407 if ((maxSize & (kReserveSize - 1)) == 0) 408 maxSize += kReserveSize; 409 } 410 PrintSize_KMGT_Or_Hex(s, maxSize); 411} 412 413#ifndef _WIN64 414EXTERN_C_BEGIN 415typedef VOID (WINAPI *Func_GetNativeSystemInfo)(LPSYSTEM_INFO lpSystemInfo); 416EXTERN_C_END 417#endif 418 419#endif 420 421#ifdef __APPLE__ 422#ifndef MY_CPU_X86_OR_AMD64 423static void Add_sysctlbyname_to_String(const char *name, AString &s) 424{ 425 size_t bufSize = 256; 426 char buf[256]; 427 if (z7_sysctlbyname_Get(name, &buf, &bufSize) == 0) 428 s += buf; 429} 430#endif 431#endif 432 433void GetSysInfo(AString &s1, AString &s2); 434void GetSysInfo(AString &s1, AString &s2) 435{ 436 s1.Empty(); 437 s2.Empty(); 438 439 #ifdef _WIN32 440 SYSTEM_INFO si; 441 GetSystemInfo(&si); 442 { 443 SysInfo_To_String(s1, si); 444 // s += " : "; 445 } 446 447 #if !defined(_WIN64) && !defined(UNDER_CE) 448 const 449 Func_GetNativeSystemInfo fn = Z7_GET_PROC_ADDRESS( 450 Func_GetNativeSystemInfo, GetModuleHandleA("kernel32.dll"), 451 "GetNativeSystemInfo"); 452 if (fn) 453 { 454 SYSTEM_INFO si2; 455 fn(&si2); 456 // if (memcmp(&si, &si2, sizeof(si)) != 0) 457 { 458 // s += " - "; 459 SysInfo_To_String(s2, si2); 460 } 461 } 462 #endif 463 #endif 464} 465 466 467void GetCpuName(AString &s); 468 469static void AddBracedString(AString &dest, AString &src) 470{ 471 if (!src.IsEmpty()) 472 { 473 AString s; 474 s += '('; 475 s += src; 476 s += ')'; 477 dest.Add_OptSpaced(s); 478 } 479} 480 481struct CCpuName 482{ 483 AString CpuName; 484 AString Revision; 485 AString Microcode; 486 AString LargePages; 487 488 void Fill(); 489 490 void Get_Revision_Microcode_LargePages(AString &s) 491 { 492 s.Empty(); 493 AddBracedString(s, Revision); 494 AddBracedString(s, Microcode); 495 s.Add_OptSpaced(LargePages); 496 } 497}; 498 499void CCpuName::Fill() 500{ 501 CpuName.Empty(); 502 Revision.Empty(); 503 Microcode.Empty(); 504 LargePages.Empty(); 505 506 AString &s = CpuName; 507 508 #ifdef MY_CPU_X86_OR_AMD64 509 { 510 #if !defined(MY_CPU_AMD64) 511 if (!z7_x86_cpuid_GetMaxFunc()) 512 s += "x86"; 513 else 514 #endif 515 { 516 x86cpuid_to_String(s); 517 { 518 UInt32 a[4]; 519 z7_x86_cpuid(a, 1); 520 char temp[16]; 521 ConvertUInt32ToHex(a[0], temp); 522 Revision += temp; 523 } 524 } 525 } 526 #elif defined(__APPLE__) 527 { 528 Add_sysctlbyname_to_String("machdep.cpu.brand_string", s); 529 } 530 #endif 531 532 533 if (s.IsEmpty()) 534 { 535 #ifdef MY_CPU_LE 536 s += "LE"; 537 #elif defined(MY_CPU_BE) 538 s += "BE"; 539 #endif 540 } 541 542 #ifdef __APPLE__ 543 { 544 AString s2; 545 UInt32 v = 0; 546 if (z7_sysctlbyname_Get_UInt32("machdep.cpu.core_count", &v) == 0) 547 { 548 s2.Add_UInt32(v); 549 s2 += 'C'; 550 } 551 if (z7_sysctlbyname_Get_UInt32("machdep.cpu.thread_count", &v) == 0) 552 { 553 s2.Add_UInt32(v); 554 s2 += 'T'; 555 } 556 if (!s2.IsEmpty()) 557 { 558 s.Add_Space_if_NotEmpty(); 559 s += s2; 560 } 561 } 562 #endif 563 564 565 #ifdef _WIN32 566 { 567 NRegistry::CKey key; 568 if (key.Open(HKEY_LOCAL_MACHINE, TEXT("HARDWARE\\DESCRIPTION\\System\\CentralProcessor\\0"), KEY_READ) == ERROR_SUCCESS) 569 { 570 LONG res[2]; 571 CByteBuffer bufs[2]; 572 { 573 for (unsigned i = 0; i < 2; i++) 574 { 575 UInt32 size = 0; 576 res[i] = key.QueryValue(i == 0 ? 577 TEXT("Previous Update Revision") : 578 TEXT("Update Revision"), bufs[i], size); 579 if (res[i] == ERROR_SUCCESS) 580 if (size != bufs[i].Size()) 581 res[i] = ERROR_SUCCESS + 1; 582 } 583 } 584 if (res[0] == ERROR_SUCCESS || res[1] == ERROR_SUCCESS) 585 { 586 for (unsigned i = 0; i < 2; i++) 587 { 588 if (i == 1) 589 Microcode += "->"; 590 if (res[i] != ERROR_SUCCESS) 591 continue; 592 const CByteBuffer &buf = bufs[i]; 593 if (buf.Size() == 8) 594 { 595 UInt32 high = GetUi32(buf); 596 if (high != 0) 597 { 598 PrintHex(Microcode, high); 599 Microcode += "."; 600 } 601 PrintHex(Microcode, GetUi32(buf + 4)); 602 } 603 } 604 } 605 } 606 } 607 #endif 608 609 610 #ifdef Z7_LARGE_PAGES 611 Add_LargePages_String(LargePages); 612 #endif 613} 614 615void AddCpuFeatures(AString &s); 616void AddCpuFeatures(AString &s) 617{ 618 #ifdef _WIN32 619 // const unsigned kNumFeatures_Extra = 32; // we check also for unknown features 620 // const unsigned kNumFeatures = Z7_ARRAY_SIZE(k_PF) + kNumFeatures_Extra; 621 const unsigned kNumFeatures = 64; 622 UInt64 flags = 0; 623 for (unsigned i = 0; i < kNumFeatures; i++) 624 { 625 if (IsProcessorFeaturePresent(i)) 626 { 627 flags += (UInt64)1 << i; 628 // s.Add_Space_if_NotEmpty(); 629 // s += TypeToString2(k_PF, Z7_ARRAY_SIZE(k_PF), i); 630 } 631 } 632 s.Add_OptSpaced("f:"); 633 PrintHex(s, flags); 634 635 #elif defined(__APPLE__) 636 { 637 UInt32 v = 0; 638 if (z7_sysctlbyname_Get_UInt32("hw.pagesize", &v) == 0) 639 { 640 s.Add_OptSpaced("PageSize:"); 641 PrintPage(s, v); 642 } 643 } 644 645 #else 646 647 const long v = sysconf(_SC_PAGESIZE); 648 if (v != -1) 649 { 650 s.Add_OptSpaced("PageSize:"); 651 PrintPage(s, (unsigned long)v); 652 } 653 654 #if !defined(_AIX) 655 656 #ifdef __linux__ 657 658 CByteBuffer buf; 659 if (ReadFile_to_Buffer("/sys/kernel/mm/transparent_hugepage/enabled", buf)) 660 // if (ReadFile_to_Buffer("/proc/cpuinfo", buf)) 661 { 662 s.Add_OptSpaced("THP:"); 663 AString s2; 664 s2.SetFrom_CalcLen((const char *)(const void *)(const Byte *)buf, (unsigned)buf.Size()); 665 const int pos = s2.Find('['); 666 if (pos >= 0) 667 { 668 const int pos2 = s2.Find(']', (unsigned)pos + 1); 669 if (pos2 >= 0) 670 { 671 s2.DeleteFrom((unsigned)pos2); 672 s2.DeleteFrontal((unsigned)pos + 1); 673 } 674 } 675 s += s2; 676 } 677 // else throw CSystemException(MY_SRes_HRESULT_FROM_WRes(errno)); 678 679 #endif 680 681 682 #ifdef AT_HWCAP 683 s.Add_OptSpaced("hwcap:"); 684 { 685 unsigned long h = getauxval(AT_HWCAP); 686 PrintHex(s, h); 687 #ifdef MY_CPU_ARM64 688 if (h & HWCAP_CRC32) s += ":CRC32"; 689 if (h & HWCAP_SHA1) s += ":SHA1"; 690 if (h & HWCAP_SHA2) s += ":SHA2"; 691 if (h & HWCAP_AES) s += ":AES"; 692 if (h & HWCAP_ASIMD) s += ":ASIMD"; 693 #elif defined(MY_CPU_ARM) 694 if (h & HWCAP_NEON) s += ":NEON"; 695 #endif 696 } 697 #endif // AT_HWCAP 698 699 #ifdef AT_HWCAP2 700 { 701 unsigned long h = getauxval(AT_HWCAP2); 702 #ifndef MY_CPU_ARM 703 if (h != 0) 704 #endif 705 { 706 s += " hwcap2:"; 707 PrintHex(s, h); 708 #ifdef MY_CPU_ARM 709 if (h & HWCAP2_CRC32) s += ":CRC32"; 710 if (h & HWCAP2_SHA1) s += ":SHA1"; 711 if (h & HWCAP2_SHA2) s += ":SHA2"; 712 if (h & HWCAP2_AES) s += ":AES"; 713 #endif 714 } 715 } 716 #endif // AT_HWCAP2 717 #endif // _AIX 718 #endif // _WIN32 719} 720 721 722#ifdef _WIN32 723#ifndef UNDER_CE 724 725EXTERN_C_BEGIN 726typedef void (WINAPI * Func_RtlGetVersion) (OSVERSIONINFOEXW *); 727EXTERN_C_END 728 729static BOOL My_RtlGetVersion(OSVERSIONINFOEXW *vi) 730{ 731 const HMODULE ntdll = ::GetModuleHandleW(L"ntdll.dll"); 732 if (!ntdll) 733 return FALSE; 734 const 735 Func_RtlGetVersion func = Z7_GET_PROC_ADDRESS( 736 Func_RtlGetVersion, ntdll, 737 "RtlGetVersion"); 738 if (!func) 739 return FALSE; 740 func(vi); 741 return TRUE; 742} 743 744#endif 745#endif 746 747 748void GetOsInfoText(AString &sRes) 749{ 750 sRes.Empty(); 751 AString s; 752 753 #ifdef _WIN32 754 #ifndef UNDER_CE 755 // OSVERSIONINFO vi; 756 OSVERSIONINFOEXW vi; 757 vi.dwOSVersionInfoSize = sizeof(vi); 758 // if (::GetVersionEx(&vi)) 759 if (My_RtlGetVersion(&vi)) 760 { 761 s += "Windows"; 762 if (vi.dwPlatformId != VER_PLATFORM_WIN32_NT) 763 s.Add_UInt32(vi.dwPlatformId); 764 s.Add_Space(); s.Add_UInt32(vi.dwMajorVersion); 765 s.Add_Dot(); s.Add_UInt32(vi.dwMinorVersion); 766 s.Add_Space(); s.Add_UInt32(vi.dwBuildNumber); 767 768 if (vi.wServicePackMajor != 0 || vi.wServicePackMinor != 0) 769 { 770 s += " SP:"; s.Add_UInt32(vi.wServicePackMajor); 771 s.Add_Dot(); s.Add_UInt32(vi.wServicePackMinor); 772 } 773 // s += " Suite:"; PrintHex(s, vi.wSuiteMask); 774 // s += " Type:"; s.Add_UInt32(vi.wProductType); 775 // s.Add_Space(); s += GetOemString(vi.szCSDVersion); 776 } 777 /* 778 { 779 s += " OEMCP:"; s.Add_UInt32(GetOEMCP()); 780 s += " ACP:"; s.Add_UInt32(GetACP()); 781 } 782 */ 783 #endif 784 #else // _WIN32 785 786 if (!s.IsEmpty()) 787 s.Add_LF(); 788 struct utsname un; 789 if (uname(&un) == 0) 790 { 791 s += un.sysname; 792 // s += " : "; s += un.nodename; // we don't want to show name of computer 793 s += " : "; s += un.release; 794 s += " : "; s += un.version; 795 s += " : "; s += un.machine; 796 797 #ifdef __APPLE__ 798 // Add_sysctlbyname_to_String("kern.version", s); 799 // it's same as "utsname.version" 800 #endif 801 } 802 #endif // _WIN32 803 804 sRes += s; 805 #ifdef MY_CPU_X86_OR_AMD64 806 { 807 AString s2; 808 GetVirtCpuid(s2); 809 if (!s2.IsEmpty()) 810 { 811 sRes += " : "; 812 sRes += s2; 813 } 814 } 815 #endif 816} 817 818 819 820void GetSystemInfoText(AString &sRes) 821{ 822 GetOsInfoText(sRes); 823 sRes.Add_LF(); 824 825 { 826 AString s, s1, s2; 827 GetSysInfo(s1, s2); 828 if (!s1.IsEmpty() || !s2.IsEmpty()) 829 { 830 s = s1; 831 if (s1 != s2 && !s2.IsEmpty()) 832 { 833 s += " - "; 834 s += s2; 835 } 836 } 837 { 838 AddCpuFeatures(s); 839 if (!s.IsEmpty()) 840 { 841 sRes += s; 842 sRes.Add_LF(); 843 } 844 } 845 } 846 { 847 AString s; 848 GetCpuName(s); 849 if (!s.IsEmpty()) 850 { 851 sRes += s; 852 sRes.Add_LF(); 853 } 854 } 855 /* 856 #ifdef MY_CPU_X86_OR_AMD64 857 { 858 AString s; 859 x86cpuid_all_to_String(s); 860 if (!s.IsEmpty()) 861 { 862 printCallback->Print(s); 863 printCallback->NewLine(); 864 } 865 } 866 #endif 867 */ 868} 869 870 871void GetCpuName(AString &s); 872void GetCpuName(AString &s) 873{ 874 CCpuName cpuName; 875 cpuName.Fill(); 876 s = cpuName.CpuName; 877 AString s2; 878 cpuName.Get_Revision_Microcode_LargePages(s2); 879 s.Add_OptSpaced(s2); 880} 881 882 883void GetCpuName_MultiLine(AString &s); 884void GetCpuName_MultiLine(AString &s) 885{ 886 CCpuName cpuName; 887 cpuName.Fill(); 888 s = cpuName.CpuName; 889 AString s2; 890 cpuName.Get_Revision_Microcode_LargePages(s2); 891 if (!s2.IsEmpty()) 892 { 893 s.Add_LF(); 894 s += s2; 895 } 896} 897 898 899#ifdef MY_CPU_X86_OR_AMD64 900 901void GetVirtCpuid(AString &s) 902{ 903 const UInt32 kHv = 0x40000000; 904 905 Z7_IF_X86_CPUID_SUPPORTED 906 { 907 UInt32 a[4]; 908 z7_x86_cpuid(a, kHv); 909 910 if (a[0] < kHv || a[0] >= kHv + (1 << 16)) 911 return; 912 { 913 { 914 for (unsigned j = 1; j < 4; j++) 915 PrintCpuChars(s, a[j]); 916 } 917 } 918 if (a[0] >= kHv + 1) 919 { 920 UInt32 d[4]; 921 z7_x86_cpuid(d, kHv + 1); 922 s += " : "; 923 PrintCpuChars(s, d[0]); 924 if (a[0] >= kHv + 2) 925 { 926 z7_x86_cpuid(d, kHv + 2); 927 s += " : "; 928 s.Add_UInt32(d[1] >> 16); 929 s.Add_Dot(); s.Add_UInt32(d[1] & 0xffff); 930 s.Add_Dot(); s.Add_UInt32(d[0]); 931 s.Add_Dot(); s.Add_UInt32(d[2]); 932 s.Add_Dot(); s.Add_UInt32(d[3] >> 24); 933 s.Add_Dot(); s.Add_UInt32(d[3] & 0xffffff); 934 } 935 /* 936 if (a[0] >= kHv + 5) 937 { 938 z7_x86_cpuid(d, kHv + 5); 939 s += " : "; 940 s.Add_UInt32(d[0]); 941 s += "p"; 942 s.Add_UInt32(d[1]); 943 s += "t"; 944 } 945 */ 946 } 947 } 948} 949 950#endif 951 952 953void GetCompiler(AString &s) 954{ 955 #ifdef __VERSION__ 956 s += __VERSION__; 957 #endif 958 959 #ifdef __GNUC__ 960 s += " GCC "; 961 s.Add_UInt32(__GNUC__); 962 s.Add_Dot(); 963 s.Add_UInt32(__GNUC_MINOR__); 964 s.Add_Dot(); 965 s.Add_UInt32(__GNUC_PATCHLEVEL__); 966 #endif 967 968 #ifdef __clang__ 969 s += " CLANG "; 970 s.Add_UInt32(__clang_major__); 971 s.Add_Dot(); 972 s.Add_UInt32(__clang_minor__); 973 #endif 974 975 #ifdef __xlC__ 976 s += " XLC "; 977 s.Add_UInt32(__xlC__ >> 8); 978 s.Add_Dot(); 979 s.Add_UInt32(__xlC__ & 0xFF); 980 #ifdef __xlC_ver__ 981 s.Add_Dot(); 982 s.Add_UInt32(__xlC_ver__ >> 8); 983 s.Add_Dot(); 984 s.Add_UInt32(__xlC_ver__ & 0xFF); 985 #endif 986 #endif 987 988 #ifdef _MSC_VER 989 s += " MSC "; 990 s.Add_UInt32(_MSC_VER); 991 #endif 992 993 #if defined(__AVX2__) 994 #define MY_CPU_COMPILE_ISA "AVX2" 995 #elif defined(__AVX__) 996 #define MY_CPU_COMPILE_ISA "AVX" 997 #elif defined(__SSE2__) 998 #define MY_CPU_COMPILE_ISA "SSE2" 999 #elif defined(_M_IX86_FP) && (_M_IX86_FP >= 2) 1000 #define MY_CPU_COMPILE_ISA "SSE2" 1001 #elif defined(__SSE__) 1002 #define MY_CPU_COMPILE_ISA "SSE" 1003 #elif defined(_M_IX86_FP) && (_M_IX86_FP >= 1) 1004 #define MY_CPU_COMPILE_ISA "SSE" 1005 #elif defined(__i686__) 1006 #define MY_CPU_COMPILE_ISA "i686" 1007 #elif defined(__i586__) 1008 #define MY_CPU_COMPILE_ISA "i586" 1009 #elif defined(__i486__) 1010 #define MY_CPU_COMPILE_ISA "i486" 1011 #elif defined(__i386__) 1012 #define MY_CPU_COMPILE_ISA "i386" 1013 #elif defined(_M_IX86_FP) 1014 #define MY_CPU_COMPILE_ISA "IA32" 1015 #endif 1016 1017 1018 #ifdef MY_CPU_COMPILE_ISA 1019 s += ':'; 1020 s.Add_OptSpaced(MY_CPU_COMPILE_ISA); 1021 #endif 1022} 1023