--- a/hotspot/src/cpu/x86/vm/vm_version_x86.cpp Tue Dec 13 17:10:52 2011 -0800
+++ b/hotspot/src/cpu/x86/vm/vm_version_x86.cpp Wed Dec 14 14:54:38 2011 -0800
@@ -50,7 +50,7 @@
VM_Version::CpuidInfo VM_Version::_cpuid_info = { 0, };
static BufferBlob* stub_blob;
-static const int stub_size = 400;
+static const int stub_size = 500;
extern "C" {
typedef void (*getPsrInfo_stub_t)(void*);
@@ -73,7 +73,7 @@
const uint32_t CPU_FAMILY_486 = (4 << CPU_FAMILY_SHIFT);
Label detect_486, cpu486, detect_586, std_cpuid1, std_cpuid4;
- Label ext_cpuid1, ext_cpuid5, done;
+ Label sef_cpuid, ext_cpuid, ext_cpuid1, ext_cpuid5, done;
StubCodeMark mark(this, "VM_Version", "getPsrInfo_stub");
# define __ _masm->
@@ -229,6 +229,41 @@
__ movl(Address(rsi, 8), rcx);
__ movl(Address(rsi,12), rdx);
+ //
+ // Check if OS has enabled XGETBV instruction to access XCR0
+ // (OSXSAVE feature flag) and CPU supports AVX
+ //
+ __ andl(rcx, 0x18000000);
+ __ cmpl(rcx, 0x18000000);
+ __ jccb(Assembler::notEqual, sef_cpuid);
+
+ //
+ // XCR0, XFEATURE_ENABLED_MASK register
+ //
+ __ xorl(rcx, rcx); // zero for XCR0 register
+ __ xgetbv();
+ __ lea(rsi, Address(rbp, in_bytes(VM_Version::xem_xcr0_offset())));
+ __ movl(Address(rsi, 0), rax);
+ __ movl(Address(rsi, 4), rdx);
+
+ //
+ // cpuid(0x7) Structured Extended Features
+ //
+ __ bind(sef_cpuid);
+ __ movl(rax, 7);
+ __ cmpl(rax, Address(rbp, in_bytes(VM_Version::std_cpuid0_offset()))); // Is cpuid(0x7) supported?
+ __ jccb(Assembler::greater, ext_cpuid);
+
+ __ xorl(rcx, rcx);
+ __ cpuid();
+ __ lea(rsi, Address(rbp, in_bytes(VM_Version::sef_cpuid7_offset())));
+ __ movl(Address(rsi, 0), rax);
+ __ movl(Address(rsi, 4), rbx);
+
+ //
+ // Extended cpuid(0x80000000)
+ //
+ __ bind(ext_cpuid);
__ movl(rax, 0x80000000);
__ cpuid();
__ cmpl(rax, 0x80000000); // Is cpuid(0x80000001) supported?
@@ -359,13 +394,19 @@
if (UseSSE < 1)
_cpuFeatures &= ~CPU_SSE;
+ if (UseAVX < 2)
+ _cpuFeatures &= ~CPU_AVX2;
+
+ if (UseAVX < 1)
+ _cpuFeatures &= ~CPU_AVX;
+
if (logical_processors_per_package() == 1) {
// HT processor could be installed on a system which doesn't support HT.
_cpuFeatures &= ~CPU_HT;
}
char buf[256];
- jio_snprintf(buf, sizeof(buf), "(%u cores per cpu, %u threads per core) family %d model %d stepping %d%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s",
+ jio_snprintf(buf, sizeof(buf), "(%u cores per cpu, %u threads per core) family %d model %d stepping %d%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s",
cores_per_cpu(), threads_per_core(),
cpu_family(), _model, _stepping,
(supports_cmov() ? ", cmov" : ""),
@@ -379,6 +420,8 @@
(supports_sse4_1() ? ", sse4.1" : ""),
(supports_sse4_2() ? ", sse4.2" : ""),
(supports_popcnt() ? ", popcnt" : ""),
+ (supports_avx() ? ", avx" : ""),
+ (supports_avx2() ? ", avx2" : ""),
(supports_mmx_ext() ? ", mmxext" : ""),
(supports_3dnow_prefetch() ? ", 3dnowpref" : ""),
(supports_lzcnt() ? ", lzcnt": ""),
@@ -389,17 +432,24 @@
// UseSSE is set to the smaller of what hardware supports and what
// the command line requires. I.e., you cannot set UseSSE to 2 on
// older Pentiums which do not support it.
- if( UseSSE > 4 ) UseSSE=4;
- if( UseSSE < 0 ) UseSSE=0;
- if( !supports_sse4_1() ) // Drop to 3 if no SSE4 support
+ if (UseSSE > 4) UseSSE=4;
+ if (UseSSE < 0) UseSSE=0;
+ if (!supports_sse4_1()) // Drop to 3 if no SSE4 support
UseSSE = MIN2((intx)3,UseSSE);
- if( !supports_sse3() ) // Drop to 2 if no SSE3 support
+ if (!supports_sse3()) // Drop to 2 if no SSE3 support
UseSSE = MIN2((intx)2,UseSSE);
- if( !supports_sse2() ) // Drop to 1 if no SSE2 support
+ if (!supports_sse2()) // Drop to 1 if no SSE2 support
UseSSE = MIN2((intx)1,UseSSE);
- if( !supports_sse () ) // Drop to 0 if no SSE support
+ if (!supports_sse ()) // Drop to 0 if no SSE support
UseSSE = 0;
+ if (UseAVX > 2) UseAVX=2;
+ if (UseAVX < 0) UseAVX=0;
+ if (!supports_avx2()) // Drop to 1 if no AVX2 support
+ UseAVX = MIN2((intx)1,UseAVX);
+ if (!supports_avx ()) // Drop to 0 if no AVX support
+ UseAVX = 0;
+
// On new cpus instructions which update whole XMM register should be used
// to prevent partial register stall due to dependencies on high half.
//
@@ -534,6 +584,9 @@
if (FLAG_IS_DEFAULT(UsePopCountInstruction)) {
UsePopCountInstruction = true;
}
+ } else if (UsePopCountInstruction) {
+ warning("POPCNT instruction is not available on this CPU");
+ FLAG_SET_DEFAULT(UsePopCountInstruction, false);
}
#ifdef COMPILER2
@@ -605,7 +658,11 @@
if (PrintMiscellaneous && Verbose) {
tty->print_cr("Logical CPUs per core: %u",
logical_processors_per_package());
- tty->print_cr("UseSSE=%d",UseSSE);
+ tty->print("UseSSE=%d",UseSSE);
+ if (UseAVX > 0) {
+ tty->print(" UseAVX=%d",UseAVX);
+ }
+ tty->cr();
tty->print("Allocation");
if (AllocatePrefetchStyle <= 0 || UseSSE == 0 && !supports_3dnow_prefetch()) {
tty->print_cr(": no prefetching");