/*
* Copyright (C) 2009 David McPaul
*
* includes code from sysinfo.c which is
* Copyright 2004-2008, Axel Dörfler, axeld@pinc-software.de.
* Copyright (c) 2002, Carlos Hasan, for Haiku.
*
* All rights reserved. Distributed under the terms of the MIT License.
*/
#include "CpuCapabilities.h"
#include <string.h>
#include <cpu_type.h>
CPUCapabilities::~CPUCapabilities()
{
}
CPUCapabilities::CPUCapabilities()
: fCapabilities(0)
{
#if defined(__i386__) || defined(__x86_64__)
_SetIntelCapabilities();
#endif
}
#if defined(__i386__) || defined(__x86_64__)
void
CPUCapabilities::_SetIntelCapabilities()
{
cpuid_info baseInfo;
cpuid_info cpuInfo;
int32 maxStandardFunction, maxExtendedFunction = 0;
if (get_cpuid(&baseInfo, 0L, 0L) != B_OK) {
// this CPU doesn't support cpuid
return;
}
maxStandardFunction = baseInfo.eax_0.max_eax;
if (maxStandardFunction >= 500) {
maxStandardFunction = 0; /* old Pentium sample chips has cpu signature here */
}
/* Extended cpuid */
get_cpuid(&cpuInfo, 0x80000000, 0L);
// extended cpuid is only supported if max_eax is greater than the service id
if (cpuInfo.eax_0.max_eax > 0x80000000) {
maxExtendedFunction = cpuInfo.eax_0.max_eax & 0xff;
}
if (maxStandardFunction > 0) {
get_cpuid(&cpuInfo, 1L, 0L);
if (cpuInfo.eax_1.features & (1UL << 23)) {
fCapabilities = CAPABILITY_MMX;
}
if (cpuInfo.eax_1.features & (1UL << 25)) {
fCapabilities = CAPABILITY_SSE1;
}
if (cpuInfo.eax_1.features & (1UL << 26)) {
fCapabilities = CAPABILITY_SSE2;
}
if (maxStandardFunction >= 1) {
/* Extended features */
if (cpuInfo.eax_1.extended_features & (1UL << 0)) {
fCapabilities = CAPABILITY_SSE3;
}
if (cpuInfo.eax_1.extended_features & (1UL << 9)) {
fCapabilities = CAPABILITY_SSSE3;
}
if (cpuInfo.eax_1.extended_features & (1UL << 19)) {
fCapabilities = CAPABILITY_SSE41;
}
if (cpuInfo.eax_1.extended_features & (1UL << 20)) {
fCapabilities = CAPABILITY_SSE42;
}
}
}
}
#endif // __i386__ || __x86_64__
bool
CPUCapabilities::HasMMX()
{
return fCapabilities >= CAPABILITY_MMX;
}
bool
CPUCapabilities::HasSSE1()
{
return fCapabilities >= CAPABILITY_SSE1;
}
bool
CPUCapabilities::HasSSE2()
{
return fCapabilities >= CAPABILITY_SSE2;
}
bool
CPUCapabilities::HasSSE3()
{
return fCapabilities >= CAPABILITY_SSE3;
}
bool
CPUCapabilities::HasSSSE3()
{
return fCapabilities >= CAPABILITY_SSSE3;
}
bool
CPUCapabilities::HasSSE41()
{
return fCapabilities >= CAPABILITY_SSE41;
}
bool
CPUCapabilities::HasSSE42()
{
return fCapabilities >= CAPABILITY_SSE42;
}
void
CPUCapabilities::PrintCapabilities()
{
static const char *CapArray[8] = {
"", "MMX", "SSE1", "SSE2", "SSE3", "SSSE3", "SSE4.1", "SSE4.2"
};
printf("CPU is capable of running ");
if (fCapabilities > 0) {
for (uint32 i = 1; i <= fCapabilities; i++)
printf("%s ",CapArray[i]);
} else {
printf("no extensions");
}
printf("\n");
}
↑ V547 Expression 'maxStandardFunction >= 1' is always true.