JNIEXPORT jboolean JNICALL Java_javartm_Transaction_rtmAvailable(JNIEnv *env, jclass cls) { unsigned int eax, ebx, ecx, edx; if (__get_cpuid_max(0, NULL) >= 7) { __cpuid_count(7, 0, eax, ebx, ecx, edx); if (ebx & bit_RTM) return 1; } return 0; }
static bool avx2_support(void) { int a, b, c, d; if (__get_cpuid_max(0, NULL) < 7) { return false; } __cpuid_count(7, 0, a, b, c, d); return b & bit_AVX2; }
static void detect () { #if defined (__x86__) unsigned int sig, eax, ebx, ecx, edx; int max = __get_cpuid_max (0, &sig); if (max < 1) return; if (sig == signature_INTEL_ebx || sig == signature_AMD_ebx) { __cpuid (1, eax, ebx, ecx, edx); if (ecx & bit_RDRND) __cpu_rng = RNG_RDRAND; if (max > 7) { __cpuid_count (7, 0, eax, ebx, ecx, edx); if (ebx & bit_RDSEED) __cpu_rng = RNG_RDSEED; } } #endif }
bool process_cpu_features() { uint32_t cpuidmax = __get_cpuid_max(0, 0); bool have_cpuid = cpuidmax != 0; print_requirement("CPUID instruction", have_cpuid); if (!have_cpuid) return false; uint32_t a, b, c, d; uint32_t cpuidext = __get_cpuid(0x80000001, &a, &b, &c, &d); bool have_ext_cpuid = cpuidext != 0; print_requirement("CPUID 0x80000001", have_ext_cpuid); if (!have_ext_cpuid) return false; bool have_64bit = d & (1 << 29); print_requirement("64 bit longmode support", have_64bit); terminal_printf("cpuid[0x80000001] edx:%p ecx:%p\n", d, c); return have_64bit; }
unsigned int NOINLINE have_mpx (void) { unsigned int eax, ebx, ecx, edx; if (!__get_cpuid (1, &eax, &ebx, &ecx, &edx)) return 0; if ((ecx & bit_OSXSAVE) == bit_OSXSAVE) { if (__get_cpuid_max (0, NULL) < 7) return 0; __cpuid_count (7, 0, eax, ebx, ecx, edx); if ((ebx & bit_MPX) == bit_MPX) return 1; else return 0; } return 0; }
static int codec_choose_x86 (struct codec *codec) { #if (__x86_64__ || __i386__) && (HAVE_AVX2 || HAVE_SSSE3) unsigned int eax, ebx = 0, ecx = 0, edx; unsigned int max_level = __get_cpuid_max(0, NULL); #if HAVE_AVX2 /* Check for AVX2 support: */ if (max_level >= 7) { __cpuid_count(7, 0, eax, ebx, ecx, edx); if (ebx & bit_AVX2) { codec->enc = base64_stream_encode_avx2; codec->dec = base64_stream_decode_avx2; return 1; } } #endif #if HAVE_SSSE3 /* Check for SSSE3 support: */ if (max_level >= 1) { __cpuid(1, eax, ebx, ecx, edx); if (ecx & bit_SSSE3) { codec->enc = base64_stream_encode_ssse3; codec->dec = base64_stream_decode_ssse3; return 1; } } #endif #else (void)codec; #endif return 0; }
static inline int CPU_haveCPUID() { int has_CPUID = 0; #if defined(__GNUC__) && defined(i386) has_CPUID = __get_cpuid_max( 0, NULL ) ? 1 : 0; #elif defined(_MSC_VER) && defined(_M_IX86) __asm { pushfd ; Get original EFLAGS pop eax mov ecx, eax xor eax, 200000h ; Flip ID bit in EFLAGS push eax ; Save new EFLAGS value on stack popfd ; Replace current EFLAGS value pushfd ; Get new EFLAGS pop eax ; Store new EFLAGS in EAX xor eax, ecx ; Can not toggle ID bit, jz done ; Processor=80486 mov has_CPUID,1 ; We have CPUID support done: } #endif return has_CPUID; } static inline int CPU_getCPUIDFeatures() { int features = 0; #if defined(__GNUC__) && defined(i386) if( __get_cpuid_max( 0, NULL ) >= 1 ) { int temp, temp2, temp3; __get_cpuid( 1, &temp, &temp2, &temp3, &features ); } #elif defined(_MSC_VER) && defined(_M_IX86) __asm { xor eax, eax ; Set up for CPUID instruction cpuid ; Get and save vendor ID cmp eax, 1 ; Make sure 1 is valid input for CPUID jl done ; We dont have the CPUID instruction xor eax, eax inc eax cpuid ; Get family/model/stepping/features mov features, edx done: } #endif return features; } static inline int CPU_getCPUIDFeaturesExt() { int features = 0; #if defined(__GNUC__) && defined(i386) if( __get_cpuid_max( 0x80000000, NULL ) >= 0x80000001 ) { int temp, temp2, temp3; __get_cpuid( 0x80000001, &temp, &temp2, &temp3, &features ); } #elif defined(_MSC_VER) && defined(_M_IX86) __asm { mov eax,80000000h ; Query for extended functions cpuid ; Get extended function limit cmp eax,80000001h jl done ; Nope, we dont have function 800000001h mov eax,80000001h ; Setup extended function 800000001h cpuid ; and get the information mov features,edx done: } #endif return features; } /* * COM_CPUFeatures * * CPU features detection code, taken from SDL */ unsigned int COM_CPUFeatures( void ) { if( com_CPUFeatures == 0xFFFFFFFF ) { com_CPUFeatures = 0; if( CPU_haveCPUID() ) { int CPUIDFeatures = CPU_getCPUIDFeatures(); int CPUIDFeaturesExt = CPU_getCPUIDFeaturesExt(); if( CPUIDFeatures & 0x00000010 ) com_CPUFeatures |= QCPU_HAS_RDTSC; if( CPUIDFeatures & 0x00800000 ) com_CPUFeatures |= QCPU_HAS_MMX; if( CPUIDFeaturesExt & 0x00400000 ) com_CPUFeatures |= QCPU_HAS_MMXEXT; if( CPUIDFeaturesExt & 0x80000000 ) com_CPUFeatures |= QCPU_HAS_3DNOW; if( CPUIDFeaturesExt & 0x40000000 ) com_CPUFeatures |= QCPU_HAS_3DNOWEXT; if( CPUIDFeatures & 0x02000000 ) com_CPUFeatures |= QCPU_HAS_SSE; if( CPUIDFeatures & 0x04000000 ) com_CPUFeatures |= QCPU_HAS_SSE2; } } return com_CPUFeatures; } //======================================================== void Key_Init( void ); void Key_Shutdown( void ); void SCR_EndLoadingPlaque( void ); /* * Com_Error_f * * Just throw a fatal error to * test error shutdown procedures */ #ifndef PUBLIC_BUILD static void Com_Error_f( void ) { Com_Error( ERR_FATAL, "%s", Cmd_Argv( 1 ) ); }
InstructionSet_Internal() : nIds_{ 0 }, nExIds_{ 0 }, isIntel_{ false }, isAMD_{ false }, f_1_ECX_{ 0 }, f_1_EDX_{ 0 }, f_7_EBX_{ 0 }, f_7_ECX_{ 0 }, f_81_ECX_{ 0 }, f_81_EDX_{ 0 }, data_{}, extdata_{} { //int cpuInfo[4] = {-1}; std::array<int, 4> cpui; // Calling __cpuid with 0x0 as the function_id argument // gets the number of the highest valid function ID. #if defined(_MSC_VER) && !defined(__clang__) __cpuid(cpui.data(), 0); nIds_ = cpui[0]; #else nIds_ = __get_cpuid_max(0, NULL); #endif for (int i = 0; i <= nIds_; ++i) { #if defined(_MSC_VER) && !defined(__clang__) __cpuidex(cpui.data(), i, 0); #else int *data = cpui.data(); __cpuid_count(i, 0, data[0], data[1], data[2], data[3]); #endif data_.push_back(cpui); } // Capture vendor string char vendor[0x20]; memset(vendor, 0, sizeof(vendor)); *reinterpret_cast<int*>(vendor) = data_[0][1]; *reinterpret_cast<int*>(vendor + 4) = data_[0][3]; *reinterpret_cast<int*>(vendor + 8) = data_[0][2]; vendor_ = vendor; if (vendor_ == "GenuineIntel") { isIntel_ = true; } else if (vendor_ == "AuthenticAMD") { isAMD_ = true; } // load bitset with flags for function 0x00000001 if (nIds_ >= 1) { f_1_ECX_ = data_[1][2]; f_1_EDX_ = data_[1][3]; } // load bitset with flags for function 0x00000007 if (nIds_ >= 7) { f_7_EBX_ = data_[7][1]; f_7_ECX_ = data_[7][2]; } // Calling __cpuid with 0x80000000 as the function_id argument // gets the number of the highest valid extended ID. #if defined(_MSC_VER) && !defined(__clang__) __cpuid(cpui.data(), 0x80000000); nExIds_ = cpui[0]; #else nExIds_ = __get_cpuid_max(0x80000000, NULL); #endif char brand[0x40]; memset(brand, 0, sizeof(brand)); for (unsigned i = 0x80000000; i <= nExIds_; ++i) { #if defined(_MSC_VER) && !defined(__clang__) __cpuidex(cpui.data(), i, 0); #else int *data = cpui.data(); __cpuid_count(i, 0, data[0], data[1], data[2], data[3]); #endif extdata_.push_back(cpui); } // load bitset with flags for function 0x80000001 if (nExIds_ >= 0x80000001) { f_81_ECX_ = extdata_[1][2]; f_81_EDX_ = extdata_[1][3]; } // Interpret CPU brand string if reported if (nExIds_ >= 0x80000004) { memcpy(brand, extdata_[2].data(), sizeof(cpui)); memcpy(brand + 16, extdata_[3].data(), sizeof(cpui)); memcpy(brand + 32, extdata_[4].data(), sizeof(cpui)); brand_ = brand; } };