192 } bits;
193 };
194
195 union SefCpuid7Eax {
196 uint32_t value;
197 };
198
199 union SefCpuid7Ebx {
200 uint32_t value;
201 struct {
202 uint32_t fsgsbase : 1,
203 : 2,
204 bmi1 : 1,
205 : 1,
206 avx2 : 1,
207 : 2,
208 bmi2 : 1,
209 erms : 1,
210 : 1,
211 rtm : 1,
212 : 7,
213 adx : 1,
214 : 12;
215 } bits;
216 };
217
218 union XemXcr0Eax {
219 uint32_t value;
220 struct {
221 uint32_t x87 : 1,
222 sse : 1,
223 ymm : 1,
224 : 29;
225 } bits;
226 };
227
228 protected:
229 static int _cpu;
230 static int _model;
231 static int _stepping;
232 static int _cpuFeatures; // features returned by the "cpuid" instruction
233 // 0 if this instruction is not available
234 static const char* _features_str;
235
236 static address _cpuinfo_segv_addr; // address of instruction which causes SEGV
237 static address _cpuinfo_cont_addr; // address of instruction after the one which causes SEGV
238
239 enum {
240 CPU_CX8 = (1 << 0), // next bits are from cpuid 1 (EDX)
241 CPU_CMOV = (1 << 1),
242 CPU_FXSR = (1 << 2),
243 CPU_HT = (1 << 3),
244 CPU_MMX = (1 << 4),
245 CPU_3DNOW_PREFETCH = (1 << 5), // Processor supports 3dnow prefetch and prefetchw instructions
246 // may not necessarily support other 3dnow instructions
247 CPU_SSE = (1 << 6),
248 CPU_SSE2 = (1 << 7),
249 CPU_SSE3 = (1 << 8), // SSE3 comes from cpuid 1 (ECX)
250 CPU_SSSE3 = (1 << 9),
251 CPU_SSE4A = (1 << 10),
252 CPU_SSE4_1 = (1 << 11),
253 CPU_SSE4_2 = (1 << 12),
254 CPU_POPCNT = (1 << 13),
255 CPU_LZCNT = (1 << 14),
256 CPU_TSC = (1 << 15),
257 CPU_TSCINV = (1 << 16),
258 CPU_AVX = (1 << 17),
259 CPU_AVX2 = (1 << 18),
260 CPU_AES = (1 << 19),
261 CPU_ERMS = (1 << 20), // enhanced 'rep movsb/stosb' instructions
262 CPU_CLMUL = (1 << 21), // carryless multiply for CRC
263 CPU_BMI1 = (1 << 22),
264 CPU_BMI2 = (1 << 23),
265 CPU_RTM = (1 << 24), // Restricted Transactional Memory instructions
266 CPU_ADX = (1 << 25)
267 } cpuFeatureFlags;
268
269 enum {
270 // AMD
271 CPU_FAMILY_AMD_11H = 0x11,
272 // Intel
273 CPU_FAMILY_INTEL_CORE = 6,
274 CPU_MODEL_NEHALEM = 0x1e,
275 CPU_MODEL_NEHALEM_EP = 0x1a,
276 CPU_MODEL_NEHALEM_EX = 0x2e,
277 CPU_MODEL_WESTMERE = 0x25,
278 CPU_MODEL_WESTMERE_EP = 0x2c,
279 CPU_MODEL_WESTMERE_EX = 0x2f,
280 CPU_MODEL_SANDYBRIDGE = 0x2a,
281 CPU_MODEL_SANDYBRIDGE_EP = 0x2d,
282 CPU_MODEL_IVYBRIDGE_EP = 0x3a,
283 CPU_MODEL_HASWELL_E3 = 0x3c,
284 CPU_MODEL_HASWELL_E7 = 0x3f,
285 CPU_MODEL_BROADWELL = 0x3d
286 } cpuExtendedFamily;
287
288 // cpuid information block. All info derived from executing cpuid with
289 // various function numbers is stored here. Intel and AMD info is
290 // merged in this block: accessor methods disentangle it.
291 //
292 // The info block is laid out in subblocks of 4 dwords corresponding to
293 // eax, ebx, ecx and edx, whether or not they contain anything useful.
294 struct CpuidInfo {
295 // cpuid function 0
296 uint32_t std_max_function;
297 uint32_t std_vendor_name_0;
298 uint32_t std_vendor_name_1;
299 uint32_t std_vendor_name_2;
300
301 // cpuid function 1
302 StdCpuid1Eax std_cpuid1_eax;
303 StdCpuid1Ebx std_cpuid1_ebx;
304 StdCpuid1Ecx std_cpuid1_ecx;
305 StdCpuid1Edx std_cpuid1_edx;
359 ExtCpuid5Ex ext_cpuid5_edx; // L1 instruction cache info (AMD)
360
361 // cpuid function 0x80000007
362 uint32_t ext_cpuid7_eax; // reserved
363 uint32_t ext_cpuid7_ebx; // reserved
364 uint32_t ext_cpuid7_ecx; // reserved
365 ExtCpuid7Edx ext_cpuid7_edx; // tscinv
366
367 // cpuid function 0x80000008
368 uint32_t ext_cpuid8_eax; // unused currently
369 uint32_t ext_cpuid8_ebx; // reserved
370 ExtCpuid8Ecx ext_cpuid8_ecx;
371 uint32_t ext_cpuid8_edx; // reserved
372
373 // extended control register XCR0 (the XFEATURE_ENABLED_MASK register)
374 XemXcr0Eax xem_xcr0_eax;
375 uint32_t xem_xcr0_edx; // reserved
376
377 // Space to save ymm registers after signal handle
378 int ymm_save[8*4]; // Save ymm0, ymm7, ymm8, ymm15
379 };
380
381 // The actual cpuid info block
382 static CpuidInfo _cpuid_info;
383
384 // Extractors and predicates
385 static uint32_t extended_cpu_family() {
386 uint32_t result = _cpuid_info.std_cpuid1_eax.bits.family;
387 result += _cpuid_info.std_cpuid1_eax.bits.ext_family;
388 return result;
389 }
390
391 static uint32_t extended_cpu_model() {
392 uint32_t result = _cpuid_info.std_cpuid1_eax.bits.model;
393 result |= _cpuid_info.std_cpuid1_eax.bits.ext_model << 4;
394 return result;
395 }
396
397 static uint32_t cpu_stepping() {
398 uint32_t result = _cpuid_info.std_cpuid1_eax.bits.stepping;
399 return result;
400 }
401
402 static uint logical_processor_count() {
403 uint result = threads_per_core();
404 return result;
405 }
406
407 static uint32_t feature_flags() {
408 uint32_t result = 0;
409 if (_cpuid_info.std_cpuid1_edx.bits.cmpxchg8 != 0)
410 result |= CPU_CX8;
411 if (_cpuid_info.std_cpuid1_edx.bits.cmov != 0)
412 result |= CPU_CMOV;
413 if (_cpuid_info.std_cpuid1_edx.bits.fxsr != 0 || (is_amd() &&
414 _cpuid_info.ext_cpuid1_edx.bits.fxsr != 0))
415 result |= CPU_FXSR;
416 // HT flag is set for multi-core processors also.
417 if (threads_per_core() > 1)
418 result |= CPU_HT;
419 if (_cpuid_info.std_cpuid1_edx.bits.mmx != 0 || (is_amd() &&
420 _cpuid_info.ext_cpuid1_edx.bits.mmx != 0))
421 result |= CPU_MMX;
422 if (_cpuid_info.std_cpuid1_edx.bits.sse != 0)
423 result |= CPU_SSE;
424 if (_cpuid_info.std_cpuid1_edx.bits.sse2 != 0)
425 result |= CPU_SSE2;
426 if (_cpuid_info.std_cpuid1_ecx.bits.sse3 != 0)
427 result |= CPU_SSE3;
428 if (_cpuid_info.std_cpuid1_ecx.bits.ssse3 != 0)
429 result |= CPU_SSSE3;
430 if (_cpuid_info.std_cpuid1_ecx.bits.sse4_1 != 0)
431 result |= CPU_SSE4_1;
432 if (_cpuid_info.std_cpuid1_ecx.bits.sse4_2 != 0)
433 result |= CPU_SSE4_2;
434 if (_cpuid_info.std_cpuid1_ecx.bits.popcnt != 0)
435 result |= CPU_POPCNT;
436 if (_cpuid_info.std_cpuid1_ecx.bits.avx != 0 &&
437 _cpuid_info.std_cpuid1_ecx.bits.osxsave != 0 &&
438 _cpuid_info.xem_xcr0_eax.bits.sse != 0 &&
439 _cpuid_info.xem_xcr0_eax.bits.ymm != 0) {
440 result |= CPU_AVX;
441 if (_cpuid_info.sef_cpuid7_ebx.bits.avx2 != 0)
442 result |= CPU_AVX2;
443 }
444 if(_cpuid_info.sef_cpuid7_ebx.bits.bmi1 != 0)
445 result |= CPU_BMI1;
446 if (_cpuid_info.std_cpuid1_edx.bits.tsc != 0)
447 result |= CPU_TSC;
448 if (_cpuid_info.ext_cpuid7_edx.bits.tsc_invariance != 0)
449 result |= CPU_TSCINV;
450 if (_cpuid_info.std_cpuid1_ecx.bits.aes != 0)
451 result |= CPU_AES;
452 if (_cpuid_info.sef_cpuid7_ebx.bits.erms != 0)
453 result |= CPU_ERMS;
454 if (_cpuid_info.std_cpuid1_ecx.bits.clmul != 0)
455 result |= CPU_CLMUL;
456 if (_cpuid_info.sef_cpuid7_ebx.bits.rtm != 0)
457 result |= CPU_RTM;
458
459 // AMD features.
460 if (is_amd()) {
461 if ((_cpuid_info.ext_cpuid1_edx.bits.tdnow != 0) ||
462 (_cpuid_info.ext_cpuid1_ecx.bits.prefetchw != 0))
467 result |= CPU_SSE4A;
468 }
469 // Intel features.
470 if(is_intel()) {
471 if(_cpuid_info.sef_cpuid7_ebx.bits.adx != 0)
472 result |= CPU_ADX;
473 if(_cpuid_info.sef_cpuid7_ebx.bits.bmi2 != 0)
474 result |= CPU_BMI2;
475 if(_cpuid_info.ext_cpuid1_ecx.bits.lzcnt_intel != 0)
476 result |= CPU_LZCNT;
477 // for Intel, ecx.bits.misalignsse bit (bit 8) indicates support for prefetchw
478 if (_cpuid_info.ext_cpuid1_ecx.bits.misalignsse != 0) {
479 result |= CPU_3DNOW_PREFETCH;
480 }
481 }
482
483 return result;
484 }
485
486 static bool os_supports_avx_vectors() {
487 if (!supports_avx()) {
488 return false;
489 }
490 // Verify that OS save/restore all bits of AVX registers
491 // during signal processing.
492 int nreg = 2 LP64_ONLY(+2);
493 for (int i = 0; i < 8 * nreg; i++) { // 32 bytes per ymm register
494 if (_cpuid_info.ymm_save[i] != ymm_test_value()) {
495 return false;
496 }
497 }
498 return true;
499 }
500
501 static void get_processor_features();
502
503 public:
504 // Offsets for cpuid asm stub
505 static ByteSize std_cpuid0_offset() { return byte_offset_of(CpuidInfo, std_max_function); }
506 static ByteSize std_cpuid1_offset() { return byte_offset_of(CpuidInfo, std_cpuid1_eax); }
507 static ByteSize dcp_cpuid4_offset() { return byte_offset_of(CpuidInfo, dcp_cpuid4_eax); }
508 static ByteSize sef_cpuid7_offset() { return byte_offset_of(CpuidInfo, sef_cpuid7_eax); }
509 static ByteSize ext_cpuid1_offset() { return byte_offset_of(CpuidInfo, ext_cpuid1_eax); }
510 static ByteSize ext_cpuid5_offset() { return byte_offset_of(CpuidInfo, ext_cpuid5_eax); }
511 static ByteSize ext_cpuid7_offset() { return byte_offset_of(CpuidInfo, ext_cpuid7_eax); }
512 static ByteSize ext_cpuid8_offset() { return byte_offset_of(CpuidInfo, ext_cpuid8_eax); }
513 static ByteSize tpl_cpuidB0_offset() { return byte_offset_of(CpuidInfo, tpl_cpuidB0_eax); }
514 static ByteSize tpl_cpuidB1_offset() { return byte_offset_of(CpuidInfo, tpl_cpuidB1_eax); }
515 static ByteSize tpl_cpuidB2_offset() { return byte_offset_of(CpuidInfo, tpl_cpuidB2_eax); }
516 static ByteSize xem_xcr0_offset() { return byte_offset_of(CpuidInfo, xem_xcr0_eax); }
517 static ByteSize ymm_save_offset() { return byte_offset_of(CpuidInfo, ymm_save); }
518
519 // The value used to check ymm register after signal handle
520 static int ymm_test_value() { return 0xCAFEBABE; }
521
522 static void get_cpu_info_wrapper();
523 static void set_cpuinfo_segv_addr(address pc) { _cpuinfo_segv_addr = pc; }
524 static bool is_cpuinfo_segv_addr(address pc) { return _cpuinfo_segv_addr == pc; }
525 static void set_cpuinfo_cont_addr(address pc) { _cpuinfo_cont_addr = pc; }
526 static address cpuinfo_cont_addr() { return _cpuinfo_cont_addr; }
527
528 static void clean_cpuFeatures() { _cpuFeatures = 0; }
529 static void set_avx_cpuFeatures() { _cpuFeatures = (CPU_SSE | CPU_SSE2 | CPU_AVX); }
530
531
532 // Initialization
533 static void initialize();
534
535 // Override Abstract_VM_Version implementation
536 static bool use_biased_locking();
537
538 // Asserts
539 static void assert_is_initialized() {
540 assert(_cpuid_info.std_cpuid1_eax.bits.family != 0, "VM_Version not initialized");
541 }
542
543 //
544 // Processor family:
545 // 3 - 386
546 // 4 - 486
547 // 5 - Pentium
548 // 6 - PentiumPro, Pentium II, Celeron, Xeon, Pentium III, Athlon,
549 // Pentium M, Core Solo, Core Duo, Core2 Duo
620 static bool supports_fxsr() { return (_cpuFeatures & CPU_FXSR) != 0; }
621 static bool supports_ht() { return (_cpuFeatures & CPU_HT) != 0; }
622 static bool supports_mmx() { return (_cpuFeatures & CPU_MMX) != 0; }
623 static bool supports_sse() { return (_cpuFeatures & CPU_SSE) != 0; }
624 static bool supports_sse2() { return (_cpuFeatures & CPU_SSE2) != 0; }
625 static bool supports_sse3() { return (_cpuFeatures & CPU_SSE3) != 0; }
626 static bool supports_ssse3() { return (_cpuFeatures & CPU_SSSE3)!= 0; }
627 static bool supports_sse4_1() { return (_cpuFeatures & CPU_SSE4_1) != 0; }
628 static bool supports_sse4_2() { return (_cpuFeatures & CPU_SSE4_2) != 0; }
629 static bool supports_popcnt() { return (_cpuFeatures & CPU_POPCNT) != 0; }
630 static bool supports_avx() { return (_cpuFeatures & CPU_AVX) != 0; }
631 static bool supports_avx2() { return (_cpuFeatures & CPU_AVX2) != 0; }
632 static bool supports_tsc() { return (_cpuFeatures & CPU_TSC) != 0; }
633 static bool supports_aes() { return (_cpuFeatures & CPU_AES) != 0; }
634 static bool supports_erms() { return (_cpuFeatures & CPU_ERMS) != 0; }
635 static bool supports_clmul() { return (_cpuFeatures & CPU_CLMUL) != 0; }
636 static bool supports_rtm() { return (_cpuFeatures & CPU_RTM) != 0; }
637 static bool supports_bmi1() { return (_cpuFeatures & CPU_BMI1) != 0; }
638 static bool supports_bmi2() { return (_cpuFeatures & CPU_BMI2) != 0; }
639 static bool supports_adx() { return (_cpuFeatures & CPU_ADX) != 0; }
640 // Intel features
641 static bool is_intel_family_core() { return is_intel() &&
642 extended_cpu_family() == CPU_FAMILY_INTEL_CORE; }
643
644 static bool is_intel_tsc_synched_at_init() {
645 if (is_intel_family_core()) {
646 uint32_t ext_model = extended_cpu_model();
647 if (ext_model == CPU_MODEL_NEHALEM_EP ||
648 ext_model == CPU_MODEL_WESTMERE_EP ||
649 ext_model == CPU_MODEL_SANDYBRIDGE_EP ||
650 ext_model == CPU_MODEL_IVYBRIDGE_EP) {
651 // <= 2-socket invariant tsc support. EX versions are usually used
652 // in > 2-socket systems and likely don't synchronize tscs at
653 // initialization.
654 // Code that uses tsc values must be prepared for them to arbitrarily
655 // jump forward or backward.
656 return true;
657 }
658 }
659 return false;
|
192 } bits;
193 };
194
195 union SefCpuid7Eax {
196 uint32_t value;
197 };
198
199 union SefCpuid7Ebx {
200 uint32_t value;
201 struct {
202 uint32_t fsgsbase : 1,
203 : 2,
204 bmi1 : 1,
205 : 1,
206 avx2 : 1,
207 : 2,
208 bmi2 : 1,
209 erms : 1,
210 : 1,
211 rtm : 1,
212 : 4,
213 avx512f : 1,
214 avx512dq : 1,
215 : 1,
216 adx : 1,
217 : 6,
218 avx512pf : 1,
219 avx512er : 1,
220 avx512cd : 1,
221 : 1,
222 avx512bw : 1,
223 avx512vl : 1;
224 } bits;
225 };
226
227 union XemXcr0Eax {
228 uint32_t value;
229 struct {
230 uint32_t x87 : 1,
231 sse : 1,
232 ymm : 1,
233 : 2,
234 opmask : 1,
235 zmm512 : 1,
236 zmm32 : 1,
237 : 24;
238 } bits;
239 };
240
241 protected:
242 static int _cpu;
243 static int _model;
244 static int _stepping;
245 static uint64_t _cpuFeatures; // features returned by the "cpuid" instruction
246 // 0 if this instruction is not available
247 static const char* _features_str;
248
249 static address _cpuinfo_segv_addr; // address of instruction which causes SEGV
250 static address _cpuinfo_cont_addr; // address of instruction after the one which causes SEGV
251
252 enum {
253 CPU_CX8 = (1 << 0), // next bits are from cpuid 1 (EDX)
254 CPU_CMOV = (1 << 1),
255 CPU_FXSR = (1 << 2),
256 CPU_HT = (1 << 3),
257 CPU_MMX = (1 << 4),
258 CPU_3DNOW_PREFETCH = (1 << 5), // Processor supports 3dnow prefetch and prefetchw instructions
259 // may not necessarily support other 3dnow instructions
260 CPU_SSE = (1 << 6),
261 CPU_SSE2 = (1 << 7),
262 CPU_SSE3 = (1 << 8), // SSE3 comes from cpuid 1 (ECX)
263 CPU_SSSE3 = (1 << 9),
264 CPU_SSE4A = (1 << 10),
265 CPU_SSE4_1 = (1 << 11),
266 CPU_SSE4_2 = (1 << 12),
267 CPU_POPCNT = (1 << 13),
268 CPU_LZCNT = (1 << 14),
269 CPU_TSC = (1 << 15),
270 CPU_TSCINV = (1 << 16),
271 CPU_AVX = (1 << 17),
272 CPU_AVX2 = (1 << 18),
273 CPU_AES = (1 << 19),
274 CPU_ERMS = (1 << 20), // enhanced 'rep movsb/stosb' instructions
275 CPU_CLMUL = (1 << 21), // carryless multiply for CRC
276 CPU_BMI1 = (1 << 22),
277 CPU_BMI2 = (1 << 23),
278 CPU_RTM = (1 << 24), // Restricted Transactional Memory instructions
279 CPU_ADX = (1 << 25),
280 CPU_AVX512F = (1 << 26), // AVX 512bit foundation instructions
281 CPU_AVX512DQ = (1 << 27),
282 CPU_AVX512PF = (1 << 28),
283 CPU_AVX512ER = (1 << 29),
284 CPU_AVX512CD = (1 << 30),
285 CPU_AVX512BW = (1 << 31)
286 } cpuFeatureFlags;
287
288 #define CPU_AVX512VL 0x100000000 // EVEX instructions with smaller vector length : enums are limited to 32bit
289
290 enum {
291 // AMD
292 CPU_FAMILY_AMD_11H = 0x11,
293 // Intel
294 CPU_FAMILY_INTEL_CORE = 6,
295 CPU_MODEL_NEHALEM = 0x1e,
296 CPU_MODEL_NEHALEM_EP = 0x1a,
297 CPU_MODEL_NEHALEM_EX = 0x2e,
298 CPU_MODEL_WESTMERE = 0x25,
299 CPU_MODEL_WESTMERE_EP = 0x2c,
300 CPU_MODEL_WESTMERE_EX = 0x2f,
301 CPU_MODEL_SANDYBRIDGE = 0x2a,
302 CPU_MODEL_SANDYBRIDGE_EP = 0x2d,
303 CPU_MODEL_IVYBRIDGE_EP = 0x3a,
304 CPU_MODEL_HASWELL_E3 = 0x3c,
305 CPU_MODEL_HASWELL_E7 = 0x3f,
306 CPU_MODEL_BROADWELL = 0x3d,
307 CPU_MODEL_SKYLAKE = CPU_MODEL_HASWELL_E3
308 } cpuExtendedFamily;
309
310 // cpuid information block. All info derived from executing cpuid with
311 // various function numbers is stored here. Intel and AMD info is
312 // merged in this block: accessor methods disentangle it.
313 //
314 // The info block is laid out in subblocks of 4 dwords corresponding to
315 // eax, ebx, ecx and edx, whether or not they contain anything useful.
316 struct CpuidInfo {
317 // cpuid function 0
318 uint32_t std_max_function;
319 uint32_t std_vendor_name_0;
320 uint32_t std_vendor_name_1;
321 uint32_t std_vendor_name_2;
322
323 // cpuid function 1
324 StdCpuid1Eax std_cpuid1_eax;
325 StdCpuid1Ebx std_cpuid1_ebx;
326 StdCpuid1Ecx std_cpuid1_ecx;
327 StdCpuid1Edx std_cpuid1_edx;
381 ExtCpuid5Ex ext_cpuid5_edx; // L1 instruction cache info (AMD)
382
383 // cpuid function 0x80000007
384 uint32_t ext_cpuid7_eax; // reserved
385 uint32_t ext_cpuid7_ebx; // reserved
386 uint32_t ext_cpuid7_ecx; // reserved
387 ExtCpuid7Edx ext_cpuid7_edx; // tscinv
388
389 // cpuid function 0x80000008
390 uint32_t ext_cpuid8_eax; // unused currently
391 uint32_t ext_cpuid8_ebx; // reserved
392 ExtCpuid8Ecx ext_cpuid8_ecx;
393 uint32_t ext_cpuid8_edx; // reserved
394
395 // extended control register XCR0 (the XFEATURE_ENABLED_MASK register)
396 XemXcr0Eax xem_xcr0_eax;
397 uint32_t xem_xcr0_edx; // reserved
398
399 // Space to save ymm registers after signal handle
400 int ymm_save[8*4]; // Save ymm0, ymm7, ymm8, ymm15
401
402 // Space to save zmm registers after signal handle
403 int zmm_save[16*4]; // Save zmm0, zmm7, zmm8, zmm31
404 };
405
406 // The actual cpuid info block
407 static CpuidInfo _cpuid_info;
408
409 // Extractors and predicates
410 static uint32_t extended_cpu_family() {
411 uint32_t result = _cpuid_info.std_cpuid1_eax.bits.family;
412 result += _cpuid_info.std_cpuid1_eax.bits.ext_family;
413 return result;
414 }
415
416 static uint32_t extended_cpu_model() {
417 uint32_t result = _cpuid_info.std_cpuid1_eax.bits.model;
418 result |= _cpuid_info.std_cpuid1_eax.bits.ext_model << 4;
419 return result;
420 }
421
422 static uint32_t cpu_stepping() {
423 uint32_t result = _cpuid_info.std_cpuid1_eax.bits.stepping;
424 return result;
425 }
426
427 static uint logical_processor_count() {
428 uint result = threads_per_core();
429 return result;
430 }
431
432 static uint64_t feature_flags() {
433 uint64_t result = 0;
434 if (_cpuid_info.std_cpuid1_edx.bits.cmpxchg8 != 0)
435 result |= CPU_CX8;
436 if (_cpuid_info.std_cpuid1_edx.bits.cmov != 0)
437 result |= CPU_CMOV;
438 if (_cpuid_info.std_cpuid1_edx.bits.fxsr != 0 || (is_amd() &&
439 _cpuid_info.ext_cpuid1_edx.bits.fxsr != 0))
440 result |= CPU_FXSR;
441 // HT flag is set for multi-core processors also.
442 if (threads_per_core() > 1)
443 result |= CPU_HT;
444 if (_cpuid_info.std_cpuid1_edx.bits.mmx != 0 || (is_amd() &&
445 _cpuid_info.ext_cpuid1_edx.bits.mmx != 0))
446 result |= CPU_MMX;
447 if (_cpuid_info.std_cpuid1_edx.bits.sse != 0)
448 result |= CPU_SSE;
449 if (_cpuid_info.std_cpuid1_edx.bits.sse2 != 0)
450 result |= CPU_SSE2;
451 if (_cpuid_info.std_cpuid1_ecx.bits.sse3 != 0)
452 result |= CPU_SSE3;
453 if (_cpuid_info.std_cpuid1_ecx.bits.ssse3 != 0)
454 result |= CPU_SSSE3;
455 if (_cpuid_info.std_cpuid1_ecx.bits.sse4_1 != 0)
456 result |= CPU_SSE4_1;
457 if (_cpuid_info.std_cpuid1_ecx.bits.sse4_2 != 0)
458 result |= CPU_SSE4_2;
459 if (_cpuid_info.std_cpuid1_ecx.bits.popcnt != 0)
460 result |= CPU_POPCNT;
461 if (_cpuid_info.std_cpuid1_ecx.bits.avx != 0 &&
462 _cpuid_info.std_cpuid1_ecx.bits.osxsave != 0 &&
463 _cpuid_info.xem_xcr0_eax.bits.sse != 0 &&
464 _cpuid_info.xem_xcr0_eax.bits.ymm != 0) {
465 result |= CPU_AVX;
466 if (_cpuid_info.sef_cpuid7_ebx.bits.avx2 != 0)
467 result |= CPU_AVX2;
468 if (_cpuid_info.sef_cpuid7_ebx.bits.avx512f != 0 &&
469 _cpuid_info.xem_xcr0_eax.bits.opmask != 0 &&
470 _cpuid_info.xem_xcr0_eax.bits.zmm512 != 0 &&
471 _cpuid_info.xem_xcr0_eax.bits.zmm32 != 0) {
472 result |= CPU_AVX512F;
473 if (_cpuid_info.sef_cpuid7_ebx.bits.avx512cd != 0)
474 result |= CPU_AVX512CD;
475 if (_cpuid_info.sef_cpuid7_ebx.bits.avx512dq != 0)
476 result |= CPU_AVX512DQ;
477 if (_cpuid_info.sef_cpuid7_ebx.bits.avx512pf != 0)
478 result |= CPU_AVX512PF;
479 if (_cpuid_info.sef_cpuid7_ebx.bits.avx512er != 0)
480 result |= CPU_AVX512ER;
481 if (_cpuid_info.sef_cpuid7_ebx.bits.avx512bw != 0)
482 result |= CPU_AVX512BW;
483 if (_cpuid_info.sef_cpuid7_ebx.bits.avx512vl != 0)
484 result |= CPU_AVX512VL;
485 }
486 }
487 if(_cpuid_info.sef_cpuid7_ebx.bits.bmi1 != 0)
488 result |= CPU_BMI1;
489 if (_cpuid_info.std_cpuid1_edx.bits.tsc != 0)
490 result |= CPU_TSC;
491 if (_cpuid_info.ext_cpuid7_edx.bits.tsc_invariance != 0)
492 result |= CPU_TSCINV;
493 if (_cpuid_info.std_cpuid1_ecx.bits.aes != 0)
494 result |= CPU_AES;
495 if (_cpuid_info.sef_cpuid7_ebx.bits.erms != 0)
496 result |= CPU_ERMS;
497 if (_cpuid_info.std_cpuid1_ecx.bits.clmul != 0)
498 result |= CPU_CLMUL;
499 if (_cpuid_info.sef_cpuid7_ebx.bits.rtm != 0)
500 result |= CPU_RTM;
501
502 // AMD features.
503 if (is_amd()) {
504 if ((_cpuid_info.ext_cpuid1_edx.bits.tdnow != 0) ||
505 (_cpuid_info.ext_cpuid1_ecx.bits.prefetchw != 0))
510 result |= CPU_SSE4A;
511 }
512 // Intel features.
513 if(is_intel()) {
514 if(_cpuid_info.sef_cpuid7_ebx.bits.adx != 0)
515 result |= CPU_ADX;
516 if(_cpuid_info.sef_cpuid7_ebx.bits.bmi2 != 0)
517 result |= CPU_BMI2;
518 if(_cpuid_info.ext_cpuid1_ecx.bits.lzcnt_intel != 0)
519 result |= CPU_LZCNT;
520 // for Intel, ecx.bits.misalignsse bit (bit 8) indicates support for prefetchw
521 if (_cpuid_info.ext_cpuid1_ecx.bits.misalignsse != 0) {
522 result |= CPU_3DNOW_PREFETCH;
523 }
524 }
525
526 return result;
527 }
528
529 static bool os_supports_avx_vectors() {
530 bool retVal = false;
531 if (supports_evex()) {
532 // Verify that OS save/restore all bits of EVEX registers
533 // during signal processing.
534 int nreg = 2 LP64_ONLY(+2);
535 retVal = true;
536 for (int i = 0; i < 16 * nreg; i++) { // 64 bytes per zmm register
537 if (_cpuid_info.zmm_save[i] != ymm_test_value()) {
538 retVal = false;
539 break;
540 }
541 }
542 } else if (supports_avx()) {
543 // Verify that OS save/restore all bits of AVX registers
544 // during signal processing.
545 int nreg = 2 LP64_ONLY(+2);
546 retVal = true;
547 for (int i = 0; i < 8 * nreg; i++) { // 32 bytes per ymm register
548 if (_cpuid_info.ymm_save[i] != ymm_test_value()) {
549 retVal = false;
550 break;
551 }
552 }
553 }
554 return retVal;
555 }
556
557 static void get_processor_features();
558
559 public:
560 // Offsets for cpuid asm stub
561 static ByteSize std_cpuid0_offset() { return byte_offset_of(CpuidInfo, std_max_function); }
562 static ByteSize std_cpuid1_offset() { return byte_offset_of(CpuidInfo, std_cpuid1_eax); }
563 static ByteSize dcp_cpuid4_offset() { return byte_offset_of(CpuidInfo, dcp_cpuid4_eax); }
564 static ByteSize sef_cpuid7_offset() { return byte_offset_of(CpuidInfo, sef_cpuid7_eax); }
565 static ByteSize ext_cpuid1_offset() { return byte_offset_of(CpuidInfo, ext_cpuid1_eax); }
566 static ByteSize ext_cpuid5_offset() { return byte_offset_of(CpuidInfo, ext_cpuid5_eax); }
567 static ByteSize ext_cpuid7_offset() { return byte_offset_of(CpuidInfo, ext_cpuid7_eax); }
568 static ByteSize ext_cpuid8_offset() { return byte_offset_of(CpuidInfo, ext_cpuid8_eax); }
569 static ByteSize tpl_cpuidB0_offset() { return byte_offset_of(CpuidInfo, tpl_cpuidB0_eax); }
570 static ByteSize tpl_cpuidB1_offset() { return byte_offset_of(CpuidInfo, tpl_cpuidB1_eax); }
571 static ByteSize tpl_cpuidB2_offset() { return byte_offset_of(CpuidInfo, tpl_cpuidB2_eax); }
572 static ByteSize xem_xcr0_offset() { return byte_offset_of(CpuidInfo, xem_xcr0_eax); }
573 static ByteSize ymm_save_offset() { return byte_offset_of(CpuidInfo, ymm_save); }
574 static ByteSize zmm_save_offset() { return byte_offset_of(CpuidInfo, zmm_save); }
575
576 // The value used to check ymm register after signal handle
577 static int ymm_test_value() { return 0xCAFEBABE; }
578
579 static void get_cpu_info_wrapper();
580 static void set_cpuinfo_segv_addr(address pc) { _cpuinfo_segv_addr = pc; }
581 static bool is_cpuinfo_segv_addr(address pc) { return _cpuinfo_segv_addr == pc; }
582 static void set_cpuinfo_cont_addr(address pc) { _cpuinfo_cont_addr = pc; }
583 static address cpuinfo_cont_addr() { return _cpuinfo_cont_addr; }
584
585 static void clean_cpuFeatures() { _cpuFeatures = 0; }
586 static void set_avx_cpuFeatures() { _cpuFeatures = (CPU_SSE | CPU_SSE2 | CPU_AVX); }
587 static void set_evex_cpuFeatures() { _cpuFeatures = (CPU_AVX512F | CPU_SSE | CPU_SSE2 ); }
588
589
590 // Initialization
591 static void initialize();
592
593 // Override Abstract_VM_Version implementation
594 static bool use_biased_locking();
595
596 // Asserts
597 static void assert_is_initialized() {
598 assert(_cpuid_info.std_cpuid1_eax.bits.family != 0, "VM_Version not initialized");
599 }
600
601 //
602 // Processor family:
603 // 3 - 386
604 // 4 - 486
605 // 5 - Pentium
606 // 6 - PentiumPro, Pentium II, Celeron, Xeon, Pentium III, Athlon,
607 // Pentium M, Core Solo, Core Duo, Core2 Duo
678 static bool supports_fxsr() { return (_cpuFeatures & CPU_FXSR) != 0; }
679 static bool supports_ht() { return (_cpuFeatures & CPU_HT) != 0; }
680 static bool supports_mmx() { return (_cpuFeatures & CPU_MMX) != 0; }
681 static bool supports_sse() { return (_cpuFeatures & CPU_SSE) != 0; }
682 static bool supports_sse2() { return (_cpuFeatures & CPU_SSE2) != 0; }
683 static bool supports_sse3() { return (_cpuFeatures & CPU_SSE3) != 0; }
684 static bool supports_ssse3() { return (_cpuFeatures & CPU_SSSE3)!= 0; }
685 static bool supports_sse4_1() { return (_cpuFeatures & CPU_SSE4_1) != 0; }
686 static bool supports_sse4_2() { return (_cpuFeatures & CPU_SSE4_2) != 0; }
687 static bool supports_popcnt() { return (_cpuFeatures & CPU_POPCNT) != 0; }
688 static bool supports_avx() { return (_cpuFeatures & CPU_AVX) != 0; }
689 static bool supports_avx2() { return (_cpuFeatures & CPU_AVX2) != 0; }
690 static bool supports_tsc() { return (_cpuFeatures & CPU_TSC) != 0; }
691 static bool supports_aes() { return (_cpuFeatures & CPU_AES) != 0; }
692 static bool supports_erms() { return (_cpuFeatures & CPU_ERMS) != 0; }
693 static bool supports_clmul() { return (_cpuFeatures & CPU_CLMUL) != 0; }
694 static bool supports_rtm() { return (_cpuFeatures & CPU_RTM) != 0; }
695 static bool supports_bmi1() { return (_cpuFeatures & CPU_BMI1) != 0; }
696 static bool supports_bmi2() { return (_cpuFeatures & CPU_BMI2) != 0; }
697 static bool supports_adx() { return (_cpuFeatures & CPU_ADX) != 0; }
698 static bool supports_evex() { return (_cpuFeatures & CPU_AVX512F) != 0; }
699 static bool supports_avx512dq() { return (_cpuFeatures & CPU_AVX512DQ) != 0; }
700 static bool supports_avx512pf() { return (_cpuFeatures & CPU_AVX512PF) != 0; }
701 static bool supports_avx512er() { return (_cpuFeatures & CPU_AVX512ER) != 0; }
702 static bool supports_avx512cd() { return (_cpuFeatures & CPU_AVX512CD) != 0; }
703 static bool supports_avx512bw() { return (_cpuFeatures & CPU_AVX512BW) != 0; }
704 static bool supports_avx512vl() { return (_cpuFeatures & CPU_AVX512VL) != 0; }
705 // Intel features
706 static bool is_intel_family_core() { return is_intel() &&
707 extended_cpu_family() == CPU_FAMILY_INTEL_CORE; }
708
709 static bool is_intel_tsc_synched_at_init() {
710 if (is_intel_family_core()) {
711 uint32_t ext_model = extended_cpu_model();
712 if (ext_model == CPU_MODEL_NEHALEM_EP ||
713 ext_model == CPU_MODEL_WESTMERE_EP ||
714 ext_model == CPU_MODEL_SANDYBRIDGE_EP ||
715 ext_model == CPU_MODEL_IVYBRIDGE_EP) {
716 // <= 2-socket invariant tsc support. EX versions are usually used
717 // in > 2-socket systems and likely don't synchronize tscs at
718 // initialization.
719 // Code that uses tsc values must be prepared for them to arbitrarily
720 // jump forward or backward.
721 return true;
722 }
723 }
724 return false;
|