summaryrefslogtreecommitdiffstats
path: root/base/cpu.cc
diff options
context:
space:
mode:
authoragl@chromium.org <agl@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-05-28 23:28:48 +0000
committeragl@chromium.org <agl@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-05-28 23:28:48 +0000
commit26ce2f689be5eb224ecef373e661d605cd039391 (patch)
tree25155afb29634d5f09f93e0859db55c824492f54 /base/cpu.cc
parent690e14d2713691766aa29fa2c470f8f1767ac07f (diff)
downloadchromium_src-26ce2f689be5eb224ecef373e661d605cd039391.zip
chromium_src-26ce2f689be5eb224ecef373e661d605cd039391.tar.gz
chromium_src-26ce2f689be5eb224ecef373e661d605cd039391.tar.bz2
base: check XSAVE CPUID bit before xgetbv.
We follow Intel's example code for detecting whether AVX is supported by the current CPU. However, we are seeing invalid instruction crashes caused by the xgetbv instruction (see bug). I suspect these are caused by VMs incorrectly emulating the CPU. This change causes the code to additionally check the XSAVE bit in the CPUID information. From the Intel documentation for CPUID: "A value of 1 indicates that the processor supports the XSAVE/XRSTOR processor extended states feature, the XSETBV/XGETBV instructions, and XCR0." Hopefully, if the VM doesn't support xgetbv, then it doesn't set this bit. BUG=375968 Review URL: https://codereview.chromium.org/306583002 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@273393 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'base/cpu.cc')
-rw-r--r--base/cpu.cc6
1 files changed, 6 insertions, 0 deletions
diff --git a/base/cpu.cc b/base/cpu.cc
index f18b8db..dcba3b6 100644
--- a/base/cpu.cc
+++ b/base/cpu.cc
@@ -183,8 +183,14 @@ void CPU::Initialize() {
// b) XSAVE is supported by the CPU and
// c) XSAVE is enabled by the kernel.
// See http://software.intel.com/en-us/blogs/2011/04/14/is-avx-enabled
+ //
+ // In addition, we have observed some crashes with the xgetbv instruction
+ // even after following Intel's example code. (See crbug.com/375968.)
+ // Because of that, we also test the XSAVE bit because its description in
+ // the CPUID documentation suggests that it signals xgetbv support.
has_avx_ =
has_avx_hardware_ &&
+ (cpu_info[2] & 0x04000000) != 0 /* XSAVE */ &&
(cpu_info[2] & 0x08000000) != 0 /* OSXSAVE */ &&
(_xgetbv(0) & 6) == 6 /* XSAVE enabled by kernel */;
has_aesni_ = (cpu_info[2] & 0x02000000) != 0;