mirror of
https://github.com/openjdk/jdk.git
synced 2025-08-28 15:24:43 +02:00
Merge
This commit is contained in:
commit
c6d81e192d
117 changed files with 1100 additions and 464 deletions
|
@ -1,5 +1,5 @@
|
|||
suite = {
|
||||
"mxversion" : "5.6.11",
|
||||
"mxversion" : "5.6.16",
|
||||
"name" : "jvmci",
|
||||
"url" : "http://openjdk.java.net/projects/graal",
|
||||
"developer" : {
|
||||
|
|
|
@ -14928,7 +14928,22 @@ instruct string_equals(iRegP_R1 str1, iRegP_R3 str2, iRegI_R4 cnt,
|
|||
ins_pipe(pipe_class_memory);
|
||||
%}
|
||||
|
||||
instruct array_equals(iRegP_R1 ary1, iRegP_R2 ary2, iRegI_R0 result,
|
||||
instruct array_equalsB(iRegP_R1 ary1, iRegP_R2 ary2, iRegI_R0 result,
|
||||
iRegP_R10 tmp, rFlagsReg cr)
|
||||
%{
|
||||
predicate(((AryEqNode*)n)->encoding() == StrIntrinsicNode::LL);
|
||||
match(Set result (AryEq ary1 ary2));
|
||||
effect(KILL tmp, USE_KILL ary1, USE_KILL ary2, KILL cr);
|
||||
|
||||
format %{ "Array Equals $ary1,ary2 -> $result // KILL $tmp" %}
|
||||
ins_encode %{
|
||||
__ byte_arrays_equals($ary1$$Register, $ary2$$Register,
|
||||
$result$$Register, $tmp$$Register);
|
||||
%}
|
||||
ins_pipe(pipe_class_memory);
|
||||
%}
|
||||
|
||||
instruct array_equalsC(iRegP_R1 ary1, iRegP_R2 ary2, iRegI_R0 result,
|
||||
iRegP_R10 tmp, rFlagsReg cr)
|
||||
%{
|
||||
predicate(((AryEqNode*)n)->encoding() == StrIntrinsicNode::UU);
|
||||
|
|
|
@ -40,11 +40,7 @@ define_pd_global(bool, ImplicitNullChecks, true); // Generate code for im
|
|||
define_pd_global(bool, TrapBasedNullChecks, false);
|
||||
define_pd_global(bool, UncommonNullCast, true); // Uncommon-trap NULLs past to check cast
|
||||
|
||||
#if defined(COMPILER2) || INCLUDE_JVMCI
|
||||
define_pd_global(intx, CodeEntryAlignment, 64);
|
||||
#else
|
||||
define_pd_global(intx, CodeEntryAlignment, 16);
|
||||
#endif // COMPILER2
|
||||
define_pd_global(intx, OptoLoopAlignment, 16);
|
||||
define_pd_global(intx, InlineFrequencyCount, 100);
|
||||
|
||||
|
|
|
@ -127,7 +127,10 @@ int MacroAssembler::pd_patch_instruction_size(address branch, address target) {
|
|||
Instruction_aarch64::extract(insn2, 4, 0)) {
|
||||
// movk #imm16<<32
|
||||
Instruction_aarch64::patch(branch + 4, 20, 5, (uint64_t)target >> 32);
|
||||
offset &= (1<<20)-1;
|
||||
long dest = ((long)target & 0xffffffffL) | ((long)branch & 0xffff00000000L);
|
||||
long pc_page = (long)branch >> 12;
|
||||
long adr_page = (long)dest >> 12;
|
||||
offset = adr_page - pc_page;
|
||||
instructions = 2;
|
||||
}
|
||||
}
|
||||
|
@ -3993,11 +3996,12 @@ void MacroAssembler::adrp(Register reg1, const Address &dest, unsigned long &byt
|
|||
if (offset_high >= -(1<<20) && offset_low < (1<<20)) {
|
||||
_adrp(reg1, dest.target());
|
||||
} else {
|
||||
unsigned long pc_page = (unsigned long)pc() >> 12;
|
||||
long offset = dest_page - pc_page;
|
||||
offset = (offset & ((1<<20)-1)) << 12;
|
||||
_adrp(reg1, pc()+offset);
|
||||
movk(reg1, (unsigned long)dest.target() >> 32, 32);
|
||||
unsigned long target = (unsigned long)dest.target();
|
||||
unsigned long adrp_target
|
||||
= (target & 0xffffffffUL) | ((unsigned long)pc() & 0xffff00000000UL);
|
||||
|
||||
_adrp(reg1, (address)adrp_target);
|
||||
movk(reg1, target >> 32, 32);
|
||||
}
|
||||
byte_offset = (unsigned long)dest.target() & 0xfff;
|
||||
}
|
||||
|
@ -4552,6 +4556,82 @@ void MacroAssembler::string_equals(Register str1, Register str2,
|
|||
BLOCK_COMMENT("} string_equals");
|
||||
}
|
||||
|
||||
|
||||
void MacroAssembler::byte_arrays_equals(Register ary1, Register ary2,
|
||||
Register result, Register tmp1)
|
||||
{
|
||||
Register cnt1 = rscratch1;
|
||||
Register cnt2 = rscratch2;
|
||||
Register tmp2 = rscratch2;
|
||||
|
||||
Label SAME, DIFFER, NEXT, TAIL07, TAIL03, TAIL01;
|
||||
|
||||
int length_offset = arrayOopDesc::length_offset_in_bytes();
|
||||
int base_offset = arrayOopDesc::base_offset_in_bytes(T_BYTE);
|
||||
|
||||
BLOCK_COMMENT("byte_arrays_equals {");
|
||||
|
||||
// different until proven equal
|
||||
mov(result, false);
|
||||
|
||||
// same array?
|
||||
cmp(ary1, ary2);
|
||||
br(Assembler::EQ, SAME);
|
||||
|
||||
// ne if either null
|
||||
cbz(ary1, DIFFER);
|
||||
cbz(ary2, DIFFER);
|
||||
|
||||
// lengths ne?
|
||||
ldrw(cnt1, Address(ary1, length_offset));
|
||||
ldrw(cnt2, Address(ary2, length_offset));
|
||||
cmp(cnt1, cnt2);
|
||||
br(Assembler::NE, DIFFER);
|
||||
|
||||
lea(ary1, Address(ary1, base_offset));
|
||||
lea(ary2, Address(ary2, base_offset));
|
||||
|
||||
subs(cnt1, cnt1, 8);
|
||||
br(LT, TAIL07);
|
||||
|
||||
BIND(NEXT);
|
||||
ldr(tmp1, Address(post(ary1, 8)));
|
||||
ldr(tmp2, Address(post(ary2, 8)));
|
||||
subs(cnt1, cnt1, 8);
|
||||
eor(tmp1, tmp1, tmp2);
|
||||
cbnz(tmp1, DIFFER);
|
||||
br(GE, NEXT);
|
||||
|
||||
BIND(TAIL07); // 0-7 bytes left, cnt1 = #bytes left - 4
|
||||
tst(cnt1, 0b100);
|
||||
br(EQ, TAIL03);
|
||||
ldrw(tmp1, Address(post(ary1, 4)));
|
||||
ldrw(tmp2, Address(post(ary2, 4)));
|
||||
cmp(tmp1, tmp2);
|
||||
br(NE, DIFFER);
|
||||
|
||||
BIND(TAIL03); // 0-3 bytes left, cnt1 = #bytes left - 4
|
||||
tst(cnt1, 0b10);
|
||||
br(EQ, TAIL01);
|
||||
ldrh(tmp1, Address(post(ary1, 2)));
|
||||
ldrh(tmp2, Address(post(ary2, 2)));
|
||||
cmp(tmp1, tmp2);
|
||||
br(NE, DIFFER);
|
||||
BIND(TAIL01); // 0-1 byte left
|
||||
tst(cnt1, 0b01);
|
||||
br(EQ, SAME);
|
||||
ldrb(tmp1, ary1);
|
||||
ldrb(tmp2, ary2);
|
||||
cmp(tmp1, tmp2);
|
||||
br(NE, DIFFER);
|
||||
|
||||
BIND(SAME);
|
||||
mov(result, true);
|
||||
BIND(DIFFER); // result already set
|
||||
|
||||
BLOCK_COMMENT("} byte_arrays_equals");
|
||||
}
|
||||
|
||||
// Compare char[] arrays aligned to 4 bytes
|
||||
void MacroAssembler::char_arrays_equals(Register ary1, Register ary2,
|
||||
Register result, Register tmp1)
|
||||
|
|
|
@ -1191,6 +1191,8 @@ public:
|
|||
Register tmp1);
|
||||
void char_arrays_equals(Register ary1, Register ary2,
|
||||
Register result, Register tmp1);
|
||||
void byte_arrays_equals(Register ary1, Register ary2,
|
||||
Register result, Register tmp1);
|
||||
void encode_iso_array(Register src, Register dst,
|
||||
Register len, Register result,
|
||||
FloatRegister Vtmp1, FloatRegister Vtmp2,
|
||||
|
|
|
@ -786,12 +786,19 @@ class StubGenerator: public StubCodeGenerator {
|
|||
int offset;
|
||||
const Register t0 = r3, t1 = r4, t2 = r5, t3 = r6,
|
||||
t4 = r7, t5 = r10, t6 = r11, t7 = r12;
|
||||
const Register stride = r13;
|
||||
|
||||
assert_different_registers(rscratch1, t0, t1, t2, t3, t4, t5, t6, t7);
|
||||
assert_different_registers(s, d, count, rscratch1);
|
||||
|
||||
Label again, large, small;
|
||||
__ align(6);
|
||||
const char *stub_name;
|
||||
if (direction == copy_forwards)
|
||||
stub_name = "foward_copy_longs";
|
||||
else
|
||||
stub_name = "backward_copy_longs";
|
||||
StubCodeMark mark(this, "StubRoutines", stub_name);
|
||||
__ align(CodeEntryAlignment);
|
||||
__ bind(start);
|
||||
__ cmp(count, 8);
|
||||
__ br(Assembler::LO, small);
|
||||
|
@ -836,7 +843,7 @@ class StubGenerator: public StubCodeGenerator {
|
|||
|
||||
__ ret(lr);
|
||||
|
||||
__ align(6);
|
||||
__ align(CodeEntryAlignment);
|
||||
__ bind(large);
|
||||
|
||||
// Fill 8 registers
|
||||
|
@ -845,10 +852,18 @@ class StubGenerator: public StubCodeGenerator {
|
|||
__ ldp(t4, t5, Address(s, 6 * unit));
|
||||
__ ldp(t6, t7, Address(__ pre(s, 8 * unit)));
|
||||
|
||||
int prefetch = PrefetchCopyIntervalInBytes;
|
||||
bool use_stride = false;
|
||||
if (direction == copy_backwards) {
|
||||
use_stride = prefetch > 256;
|
||||
prefetch = -prefetch;
|
||||
if (use_stride) __ mov(stride, prefetch);
|
||||
}
|
||||
|
||||
__ bind(again);
|
||||
|
||||
if (direction == copy_forwards && PrefetchCopyIntervalInBytes > 0)
|
||||
__ prfm(Address(s, PrefetchCopyIntervalInBytes), PLDL1KEEP);
|
||||
if (PrefetchCopyIntervalInBytes > 0)
|
||||
__ prfm(use_stride ? Address(s, stride) : Address(s, prefetch), PLDL1KEEP);
|
||||
|
||||
__ stp(t0, t1, Address(d, 2 * unit));
|
||||
__ ldp(t0, t1, Address(s, 2 * unit));
|
||||
|
@ -962,7 +977,7 @@ class StubGenerator: public StubCodeGenerator {
|
|||
__ lea(d, Address(d, count, Address::lsl(exact_log2(-step))));
|
||||
}
|
||||
|
||||
Label done, tail;
|
||||
Label tail;
|
||||
|
||||
__ cmp(count, 16/granularity);
|
||||
__ br(Assembler::LO, tail);
|
||||
|
@ -987,7 +1002,8 @@ class StubGenerator: public StubCodeGenerator {
|
|||
}
|
||||
// rscratch2 is the byte adjustment needed to align s.
|
||||
__ cbz(rscratch2, aligned);
|
||||
__ lsr(rscratch2, rscratch2, exact_log2(granularity));
|
||||
int shift = exact_log2(granularity);
|
||||
if (shift) __ lsr(rscratch2, rscratch2, shift);
|
||||
__ sub(count, count, rscratch2);
|
||||
|
||||
#if 0
|
||||
|
@ -1150,8 +1166,11 @@ class StubGenerator: public StubCodeGenerator {
|
|||
// caller can pass a 64-bit byte count here (from Unsafe.copyMemory)
|
||||
BLOCK_COMMENT("Entry:");
|
||||
}
|
||||
__ cmp(d, s);
|
||||
__ br(Assembler::LS, nooverlap_target);
|
||||
|
||||
// use fwd copy when (d-s) above_equal (count*size)
|
||||
__ sub(rscratch1, d, s);
|
||||
__ cmp(rscratch1, count, Assembler::LSL, exact_log2(size));
|
||||
__ br(Assembler::HS, nooverlap_target);
|
||||
|
||||
if (is_oop) {
|
||||
__ push(RegSet::of(d, count), sp);
|
||||
|
|
|
@ -120,7 +120,14 @@ void VM_Version::get_processor_features() {
|
|||
FLAG_SET_DEFAULT(AllocatePrefetchStepSize, 64);
|
||||
FLAG_SET_DEFAULT(PrefetchScanIntervalInBytes, 256);
|
||||
FLAG_SET_DEFAULT(PrefetchFieldsAhead, 256);
|
||||
if (FLAG_IS_DEFAULT(PrefetchCopyIntervalInBytes))
|
||||
FLAG_SET_DEFAULT(PrefetchCopyIntervalInBytes, 256);
|
||||
if ((PrefetchCopyIntervalInBytes & 7) || (PrefetchCopyIntervalInBytes >= 32768)) {
|
||||
warning("PrefetchCopyIntervalInBytes must be a multiple of 8 and < 32768");
|
||||
PrefetchCopyIntervalInBytes &= ~7;
|
||||
if (PrefetchCopyIntervalInBytes >= 32768)
|
||||
PrefetchCopyIntervalInBytes = 32760;
|
||||
}
|
||||
|
||||
unsigned long auxv = getauxval(AT_HWCAP);
|
||||
|
||||
|
|
|
@ -45,13 +45,6 @@ void VM_Version::initialize() {
|
|||
if( cache_line_size > AllocatePrefetchStepSize )
|
||||
AllocatePrefetchStepSize = cache_line_size;
|
||||
|
||||
assert(AllocatePrefetchLines > 0, "invalid value");
|
||||
if( AllocatePrefetchLines < 1 ) // set valid value in product VM
|
||||
AllocatePrefetchLines = 3;
|
||||
assert(AllocateInstancePrefetchLines > 0, "invalid value");
|
||||
if( AllocateInstancePrefetchLines < 1 ) // set valid value in product VM
|
||||
AllocateInstancePrefetchLines = 1;
|
||||
|
||||
AllocatePrefetchDistance = allocate_prefetch_distance();
|
||||
AllocatePrefetchStyle = allocate_prefetch_style();
|
||||
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
* Copyright (c) 2003, 2015, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
|
@ -114,15 +114,20 @@ class RegisterSaver {
|
|||
|
||||
OopMap* RegisterSaver::save_live_registers(MacroAssembler* masm, int additional_frame_words,
|
||||
int* total_frame_words, bool verify_fpu, bool save_vectors) {
|
||||
int vect_words = 0;
|
||||
int num_xmm_regs = XMMRegisterImpl::number_of_registers;
|
||||
int ymm_bytes = num_xmm_regs * 16;
|
||||
int zmm_bytes = num_xmm_regs * 32;
|
||||
#ifdef COMPILER2
|
||||
if (save_vectors) {
|
||||
assert(UseAVX > 0, "512bit vectors are supported only with EVEX");
|
||||
assert(MaxVectorSize == 64, "only 512bit vectors are supported now");
|
||||
// Save upper half of ZMM/YMM registers :
|
||||
vect_words = 8 * 16 / wordSize;
|
||||
additional_frame_words += vect_words;
|
||||
assert(UseAVX > 0, "up to 512bit vectors are supported with EVEX");
|
||||
assert(MaxVectorSize <= 64, "up to 512bit vectors are supported now");
|
||||
// Save upper half of YMM registers
|
||||
int vect_bytes = ymm_bytes;
|
||||
if (UseAVX > 2) {
|
||||
// Save upper half of ZMM registers as well
|
||||
vect_bytes += zmm_bytes;
|
||||
}
|
||||
additional_frame_words += vect_bytes / wordSize;
|
||||
}
|
||||
#else
|
||||
assert(!save_vectors, "vectors are generated only by C2");
|
||||
|
@ -185,13 +190,14 @@ OopMap* RegisterSaver::save_live_registers(MacroAssembler* masm, int additional_
|
|||
|
||||
off = xmm0_off;
|
||||
delta = xmm1_off - off;
|
||||
if(UseSSE == 1) { // Save the XMM state
|
||||
if(UseSSE == 1) {
|
||||
// Save the XMM state
|
||||
for (int n = 0; n < num_xmm_regs; n++) {
|
||||
__ movflt(Address(rsp, off*wordSize), as_XMMRegister(n));
|
||||
off += delta;
|
||||
}
|
||||
} else if(UseSSE >= 2) {
|
||||
// Save whole 128bit (16 bytes) XMM regiters
|
||||
// Save whole 128bit (16 bytes) XMM registers
|
||||
for (int n = 0; n < num_xmm_regs; n++) {
|
||||
__ movdqu(Address(rsp, off*wordSize), as_XMMRegister(n));
|
||||
off += delta;
|
||||
|
@ -199,13 +205,14 @@ OopMap* RegisterSaver::save_live_registers(MacroAssembler* masm, int additional_
|
|||
}
|
||||
|
||||
if (save_vectors) {
|
||||
assert(vect_words*wordSize == 128, "");
|
||||
__ subptr(rsp, 128); // Save upper half of YMM registes
|
||||
__ subptr(rsp, ymm_bytes);
|
||||
// Save upper half of YMM registers
|
||||
for (int n = 0; n < num_xmm_regs; n++) {
|
||||
__ vextractf128h(Address(rsp, n*16), as_XMMRegister(n));
|
||||
}
|
||||
if (UseAVX > 2) {
|
||||
__ subptr(rsp, 256); // Save upper half of ZMM registes
|
||||
__ subptr(rsp, zmm_bytes);
|
||||
// Save upper half of ZMM registers
|
||||
for (int n = 0; n < num_xmm_regs; n++) {
|
||||
__ vextractf64x4h(Address(rsp, n*32), as_XMMRegister(n), 1);
|
||||
}
|
||||
|
@ -255,50 +262,59 @@ OopMap* RegisterSaver::save_live_registers(MacroAssembler* masm, int additional_
|
|||
|
||||
void RegisterSaver::restore_live_registers(MacroAssembler* masm, bool restore_vectors) {
|
||||
int num_xmm_regs = XMMRegisterImpl::number_of_registers;
|
||||
int ymm_bytes = num_xmm_regs * 16;
|
||||
int zmm_bytes = num_xmm_regs * 32;
|
||||
// Recover XMM & FPU state
|
||||
int additional_frame_bytes = 0;
|
||||
#ifdef COMPILER2
|
||||
if (restore_vectors) {
|
||||
assert(UseAVX > 0, "512bit vectors are supported only with EVEX");
|
||||
assert(MaxVectorSize == 64, "only 512bit vectors are supported now");
|
||||
additional_frame_bytes = 128;
|
||||
assert(UseAVX > 0, "up to 512bit vectors are supported with EVEX");
|
||||
assert(MaxVectorSize <= 64, "up to 512bit vectors are supported now");
|
||||
// Save upper half of YMM registers
|
||||
additional_frame_bytes = ymm_bytes;
|
||||
if (UseAVX > 2) {
|
||||
// Save upper half of ZMM registers as well
|
||||
additional_frame_bytes += zmm_bytes;
|
||||
}
|
||||
}
|
||||
#else
|
||||
assert(!restore_vectors, "vectors are generated only by C2");
|
||||
#endif
|
||||
|
||||
if (restore_vectors) {
|
||||
assert(additional_frame_bytes == 128, "");
|
||||
if (UseAVX > 2) {
|
||||
// Restore upper half of ZMM registers.
|
||||
for (int n = 0; n < num_xmm_regs; n++) {
|
||||
__ vinsertf64x4h(as_XMMRegister(n), Address(rsp, n*32), 1);
|
||||
}
|
||||
__ addptr(rsp, additional_frame_bytes*2); // Save upper half of ZMM registes
|
||||
}
|
||||
// Restore upper half of YMM registes.
|
||||
for (int n = 0; n < num_xmm_regs; n++) {
|
||||
__ vinsertf128h(as_XMMRegister(n), Address(rsp, n*16));
|
||||
}
|
||||
__ addptr(rsp, additional_frame_bytes); // Save upper half of YMM registes
|
||||
}
|
||||
|
||||
int off = xmm0_off;
|
||||
int delta = xmm1_off - off;
|
||||
|
||||
if (UseSSE == 1) {
|
||||
// Restore XMM registers
|
||||
assert(additional_frame_bytes == 0, "");
|
||||
for (int n = 0; n < num_xmm_regs; n++) {
|
||||
__ movflt(as_XMMRegister(n), Address(rsp, off*wordSize));
|
||||
off += delta;
|
||||
}
|
||||
} else if (UseSSE >= 2) {
|
||||
// additional_frame_bytes only populated for the restore_vector case, else it is 0
|
||||
// Restore whole 128bit (16 bytes) XMM registers. Do this before restoring YMM and
|
||||
// ZMM because the movdqu instruction zeros the upper part of the XMM register.
|
||||
for (int n = 0; n < num_xmm_regs; n++) {
|
||||
__ movdqu(as_XMMRegister(n), Address(rsp, off*wordSize+additional_frame_bytes));
|
||||
off += delta;
|
||||
}
|
||||
}
|
||||
|
||||
if (restore_vectors) {
|
||||
if (UseAVX > 2) {
|
||||
// Restore upper half of ZMM registers.
|
||||
for (int n = 0; n < num_xmm_regs; n++) {
|
||||
__ vinsertf64x4h(as_XMMRegister(n), Address(rsp, n*32), 1);
|
||||
}
|
||||
__ addptr(rsp, zmm_bytes);
|
||||
}
|
||||
// Restore upper half of YMM registers.
|
||||
for (int n = 0; n < num_xmm_regs; n++) {
|
||||
__ vinsertf128h(as_XMMRegister(n), Address(rsp, n*16));
|
||||
}
|
||||
__ addptr(rsp, ymm_bytes);
|
||||
}
|
||||
|
||||
__ pop_FPU_state();
|
||||
__ addptr(rsp, FPU_regs_live*wordSize); // Pop FPU registers
|
||||
|
||||
|
@ -306,7 +322,6 @@ void RegisterSaver::restore_live_registers(MacroAssembler* masm, bool restore_ve
|
|||
__ popa();
|
||||
// Get the rbp, described implicitly by the frame sender code (no oopMap)
|
||||
__ pop(rbp);
|
||||
|
||||
}
|
||||
|
||||
void RegisterSaver::restore_result_registers(MacroAssembler* masm) {
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
* Copyright (c) 2003, 2015, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
|
@ -150,8 +150,8 @@ OopMap* RegisterSaver::save_live_registers(MacroAssembler* masm, int additional_
|
|||
}
|
||||
#if defined(COMPILER2) || INCLUDE_JVMCI
|
||||
if (save_vectors) {
|
||||
assert(UseAVX > 0, "512bit vectors are supported only with EVEX");
|
||||
assert(MaxVectorSize == 64, "only 512bit vectors are supported now");
|
||||
assert(UseAVX > 0, "up to 512bit vectors are supported with EVEX");
|
||||
assert(MaxVectorSize <= 64, "up to 512bit vectors are supported now");
|
||||
}
|
||||
#else
|
||||
assert(!save_vectors, "vectors are generated only by C2 and JVMCI");
|
||||
|
@ -176,18 +176,18 @@ OopMap* RegisterSaver::save_live_registers(MacroAssembler* masm, int additional_
|
|||
|
||||
// push cpu state handles this on EVEX enabled targets
|
||||
if (save_vectors) {
|
||||
// Save upper half of YMM registes(0..15)
|
||||
// Save upper half of YMM registers(0..15)
|
||||
int base_addr = XSAVE_AREA_YMM_BEGIN;
|
||||
for (int n = 0; n < 16; n++) {
|
||||
__ vextractf128h(Address(rsp, base_addr+n*16), as_XMMRegister(n));
|
||||
}
|
||||
if (VM_Version::supports_evex()) {
|
||||
// Save upper half of ZMM registes(0..15)
|
||||
// Save upper half of ZMM registers(0..15)
|
||||
base_addr = XSAVE_AREA_ZMM_BEGIN;
|
||||
for (int n = 0; n < 16; n++) {
|
||||
__ vextractf64x4h(Address(rsp, base_addr+n*32), as_XMMRegister(n), 1);
|
||||
}
|
||||
// Save full ZMM registes(16..num_xmm_regs)
|
||||
// Save full ZMM registers(16..num_xmm_regs)
|
||||
base_addr = XSAVE_AREA_UPPERBANK;
|
||||
off = 0;
|
||||
int vector_len = Assembler::AVX_512bit;
|
||||
|
@ -321,8 +321,8 @@ void RegisterSaver::restore_live_registers(MacroAssembler* masm, bool restore_ve
|
|||
|
||||
#if defined(COMPILER2) || INCLUDE_JVMCI
|
||||
if (restore_vectors) {
|
||||
assert(UseAVX > 0, "512bit vectors are supported only with EVEX");
|
||||
assert(MaxVectorSize == 64, "only 512bit vectors are supported now");
|
||||
assert(UseAVX > 0, "up to 512bit vectors are supported with EVEX");
|
||||
assert(MaxVectorSize <= 64, "up to 512bit vectors are supported now");
|
||||
}
|
||||
#else
|
||||
assert(!restore_vectors, "vectors are generated only by C2");
|
||||
|
@ -330,18 +330,18 @@ void RegisterSaver::restore_live_registers(MacroAssembler* masm, bool restore_ve
|
|||
|
||||
// On EVEX enabled targets everything is handled in pop fpu state
|
||||
if (restore_vectors) {
|
||||
// Restore upper half of YMM registes (0..15)
|
||||
// Restore upper half of YMM registers (0..15)
|
||||
int base_addr = XSAVE_AREA_YMM_BEGIN;
|
||||
for (int n = 0; n < 16; n++) {
|
||||
__ vinsertf128h(as_XMMRegister(n), Address(rsp, base_addr+n*16));
|
||||
}
|
||||
if (VM_Version::supports_evex()) {
|
||||
// Restore upper half of ZMM registes (0..15)
|
||||
// Restore upper half of ZMM registers (0..15)
|
||||
base_addr = XSAVE_AREA_ZMM_BEGIN;
|
||||
for (int n = 0; n < 16; n++) {
|
||||
__ vinsertf64x4h(as_XMMRegister(n), Address(rsp, base_addr+n*32), 1);
|
||||
}
|
||||
// Restore full ZMM registes(16..num_xmm_regs)
|
||||
// Restore full ZMM registers(16..num_xmm_regs)
|
||||
base_addr = XSAVE_AREA_UPPERBANK;
|
||||
int vector_len = Assembler::AVX_512bit;
|
||||
int off = 0;
|
||||
|
@ -351,7 +351,7 @@ void RegisterSaver::restore_live_registers(MacroAssembler* masm, bool restore_ve
|
|||
}
|
||||
} else {
|
||||
if (VM_Version::supports_evex()) {
|
||||
// Restore upper bank of ZMM registes(16..31) for double/float usage
|
||||
// Restore upper bank of ZMM registers(16..31) for double/float usage
|
||||
int base_addr = XSAVE_AREA_UPPERBANK;
|
||||
int off = 0;
|
||||
for (int n = 16; n < num_xmm_regs; n++) {
|
||||
|
|
|
@ -1163,13 +1163,6 @@ void VM_Version::get_processor_features() {
|
|||
if( cache_line_size > AllocatePrefetchStepSize )
|
||||
AllocatePrefetchStepSize = cache_line_size;
|
||||
|
||||
assert(AllocatePrefetchLines > 0, "invalid value");
|
||||
if( AllocatePrefetchLines < 1 ) // set valid value in product VM
|
||||
AllocatePrefetchLines = 3;
|
||||
assert(AllocateInstancePrefetchLines > 0, "invalid value");
|
||||
if( AllocateInstancePrefetchLines < 1 ) // set valid value in product VM
|
||||
AllocateInstancePrefetchLines = 1;
|
||||
|
||||
AllocatePrefetchDistance = allocate_prefetch_distance();
|
||||
AllocatePrefetchStyle = allocate_prefetch_style();
|
||||
|
||||
|
@ -1183,7 +1176,9 @@ void VM_Version::get_processor_features() {
|
|||
}
|
||||
if (supports_sse4_2() && supports_ht()) { // Nehalem based cpus
|
||||
AllocatePrefetchDistance = 192;
|
||||
AllocatePrefetchLines = 4;
|
||||
if (FLAG_IS_DEFAULT(AllocatePrefetchLines)) {
|
||||
FLAG_SET_DEFAULT(AllocatePrefetchLines, 4);
|
||||
}
|
||||
}
|
||||
#ifdef COMPILER2
|
||||
if (supports_sse4_2()) {
|
||||
|
|
|
@ -76,14 +76,14 @@ public class AArch64 extends Architecture {
|
|||
public static final Register zr = r31;
|
||||
public static final Register sp = r31;
|
||||
|
||||
public static final Register[] cpuRegisters = {
|
||||
// @formatter:off
|
||||
public static final Register[] cpuRegisters = {
|
||||
r0, r1, r2, r3, r4, r5, r6, r7,
|
||||
r8, r9, r10, r11, r12, r13, r14, r15,
|
||||
r16, r17, r18, r19, r20, r21, r22, r23,
|
||||
r24, r25, r26, r27, r28, r29, r30, r31
|
||||
// @formatter:on
|
||||
};
|
||||
// @formatter:on
|
||||
|
||||
public static final RegisterCategory SIMD = new RegisterCategory("SIMD");
|
||||
|
||||
|
@ -121,17 +121,17 @@ public class AArch64 extends Architecture {
|
|||
public static final Register v30 = new Register(62, 30, "v30", SIMD);
|
||||
public static final Register v31 = new Register(63, 31, "v31", SIMD);
|
||||
|
||||
public static final Register[] simdRegisters = {
|
||||
// @formatter:off
|
||||
public static final Register[] simdRegisters = {
|
||||
v0, v1, v2, v3, v4, v5, v6, v7,
|
||||
v8, v9, v10, v11, v12, v13, v14, v15,
|
||||
v16, v17, v18, v19, v20, v21, v22, v23,
|
||||
v24, v25, v26, v27, v28, v29, v30, v31
|
||||
// @formatter:on
|
||||
};
|
||||
// @formatter:on
|
||||
|
||||
public static final Register[] allRegisters = {
|
||||
// @formatter:off
|
||||
public static final Register[] allRegisters = {
|
||||
r0, r1, r2, r3, r4, r5, r6, r7,
|
||||
r8, r9, r10, r11, r12, r13, r14, r15,
|
||||
r16, r17, r18, r19, r20, r21, r22, r23,
|
||||
|
@ -141,14 +141,14 @@ public class AArch64 extends Architecture {
|
|||
v8, v9, v10, v11, v12, v13, v14, v15,
|
||||
v16, v17, v18, v19, v20, v21, v22, v23,
|
||||
v24, v25, v26, v27, v28, v29, v30, v31
|
||||
// @formatter:on
|
||||
};
|
||||
// @formatter:on
|
||||
|
||||
/**
|
||||
* Basic set of CPU features mirroring what is returned from the cpuid instruction. See:
|
||||
* {@code VM_Version::cpuFeatureFlags}.
|
||||
*/
|
||||
public static enum CPUFeature {
|
||||
public enum CPUFeature {
|
||||
FP,
|
||||
ASIMD,
|
||||
EVTSTRM,
|
||||
|
@ -166,7 +166,7 @@ public class AArch64 extends Architecture {
|
|||
/**
|
||||
* Set of flags to control code emission.
|
||||
*/
|
||||
public static enum Flag {
|
||||
public enum Flag {
|
||||
UseBarriersForVolatile,
|
||||
UseCRC32,
|
||||
UseNeon
|
||||
|
|
|
@ -58,13 +58,13 @@ public enum AArch64Kind implements PlatformKind {
|
|||
private final AArch64Kind scalar;
|
||||
private final EnumKey<AArch64Kind> key = new EnumKey<>(this);
|
||||
|
||||
private AArch64Kind(int size) {
|
||||
AArch64Kind(int size) {
|
||||
this.size = size;
|
||||
this.scalar = this;
|
||||
this.vectorLength = 1;
|
||||
}
|
||||
|
||||
private AArch64Kind(int size, AArch64Kind scalar) {
|
||||
AArch64Kind(int size, AArch64Kind scalar) {
|
||||
this.size = size;
|
||||
this.scalar = scalar;
|
||||
|
||||
|
|
|
@ -169,7 +169,7 @@ public class AMD64 extends Architecture {
|
|||
* Basic set of CPU features mirroring what is returned from the cpuid instruction. See:
|
||||
* {@code VM_Version::cpuFeatureFlags}.
|
||||
*/
|
||||
public static enum CPUFeature {
|
||||
public enum CPUFeature {
|
||||
CX8,
|
||||
CMOV,
|
||||
FXSR,
|
||||
|
@ -210,7 +210,7 @@ public class AMD64 extends Architecture {
|
|||
/**
|
||||
* Set of flags to control code emission.
|
||||
*/
|
||||
public static enum Flag {
|
||||
public enum Flag {
|
||||
UseCountLeadingZerosInstruction,
|
||||
UseCountTrailingZerosInstruction
|
||||
}
|
||||
|
|
|
@ -74,13 +74,13 @@ public enum AMD64Kind implements PlatformKind {
|
|||
private final AMD64Kind scalar;
|
||||
private final EnumKey<AMD64Kind> key = new EnumKey<>(this);
|
||||
|
||||
private AMD64Kind(int size) {
|
||||
AMD64Kind(int size) {
|
||||
this.size = size;
|
||||
this.scalar = this;
|
||||
this.vectorLength = 1;
|
||||
}
|
||||
|
||||
private AMD64Kind(int size, AMD64Kind scalar) {
|
||||
AMD64Kind(int size, AMD64Kind scalar) {
|
||||
this.size = size;
|
||||
this.scalar = scalar;
|
||||
|
||||
|
|
|
@ -23,7 +23,7 @@
|
|||
package jdk.vm.ci.code;
|
||||
|
||||
/**
|
||||
* Class representing a exception with a stack trace of the currently processed position in the
|
||||
* Class representing an exception with a stack trace of the currently processed position in the
|
||||
* compiled Java program instead of the stack trace of the compiler. The exception of the compiler
|
||||
* is saved as the cause of this exception.
|
||||
*/
|
||||
|
@ -36,7 +36,7 @@ public abstract class SourceStackTrace extends BailoutException {
|
|||
private static final long serialVersionUID = 6279381376051787907L;
|
||||
|
||||
@Override
|
||||
public final synchronized Throwable fillInStackTrace() {
|
||||
public synchronized Throwable fillInStackTrace() {
|
||||
assert elements != null;
|
||||
setStackTrace(elements);
|
||||
return this;
|
||||
|
|
|
@ -49,7 +49,7 @@ public enum HotSpotCallingConventionType implements CallingConvention.Type {
|
|||
|
||||
public static final Type[] VALUES = values();
|
||||
|
||||
private HotSpotCallingConventionType(boolean out) {
|
||||
HotSpotCallingConventionType(boolean out) {
|
||||
this.out = out;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -24,6 +24,7 @@ package jdk.vm.ci.hotspot;
|
|||
|
||||
import jdk.vm.ci.code.BytecodeFrame;
|
||||
import jdk.vm.ci.code.CompiledCode;
|
||||
import jdk.vm.ci.code.StackSlot;
|
||||
import jdk.vm.ci.code.site.DataPatch;
|
||||
import jdk.vm.ci.code.site.Infopoint;
|
||||
import jdk.vm.ci.code.site.Site;
|
||||
|
@ -99,9 +100,9 @@ public class HotSpotCompiledCode implements CompiledCode {
|
|||
protected final int totalFrameSize;
|
||||
|
||||
/**
|
||||
* Offset in bytes for the custom stack area (relative to sp).
|
||||
* The deopt rescue slot. Must be non-null if there is a safepoint in the method.
|
||||
*/
|
||||
protected final int customStackAreaOffset;
|
||||
protected final StackSlot deoptRescueSlot;
|
||||
|
||||
public static class Comment {
|
||||
|
||||
|
@ -115,7 +116,7 @@ public class HotSpotCompiledCode implements CompiledCode {
|
|||
}
|
||||
|
||||
public HotSpotCompiledCode(String name, byte[] targetCode, int targetCodeSize, Site[] sites, Assumption[] assumptions, ResolvedJavaMethod[] methods, Comment[] comments, byte[] dataSection,
|
||||
int dataSectionAlignment, DataPatch[] dataSectionPatches, boolean isImmutablePIC, int totalFrameSize, int customStackAreaOffset) {
|
||||
int dataSectionAlignment, DataPatch[] dataSectionPatches, boolean isImmutablePIC, int totalFrameSize, StackSlot deoptRescueSlot) {
|
||||
this.name = name;
|
||||
this.targetCode = targetCode;
|
||||
this.targetCodeSize = targetCodeSize;
|
||||
|
@ -129,7 +130,7 @@ public class HotSpotCompiledCode implements CompiledCode {
|
|||
this.dataSectionPatches = dataSectionPatches;
|
||||
this.isImmutablePIC = isImmutablePIC;
|
||||
this.totalFrameSize = totalFrameSize;
|
||||
this.customStackAreaOffset = customStackAreaOffset;
|
||||
this.deoptRescueSlot = deoptRescueSlot;
|
||||
|
||||
assert validateFrames();
|
||||
}
|
||||
|
|
|
@ -22,6 +22,7 @@
|
|||
*/
|
||||
package jdk.vm.ci.hotspot;
|
||||
|
||||
import jdk.vm.ci.code.StackSlot;
|
||||
import jdk.vm.ci.code.site.DataPatch;
|
||||
import jdk.vm.ci.code.site.Site;
|
||||
import jdk.vm.ci.inittimer.SuppressFBWarnings;
|
||||
|
@ -55,9 +56,9 @@ public final class HotSpotCompiledNmethod extends HotSpotCompiledCode {
|
|||
@SuppressFBWarnings(value = "UWF_UNWRITTEN_FIELD", justification = "set by the VM") private String installationFailureMessage;
|
||||
|
||||
public HotSpotCompiledNmethod(String name, byte[] targetCode, int targetCodeSize, Site[] sites, Assumption[] assumptions, ResolvedJavaMethod[] methods, Comment[] comments, byte[] dataSection,
|
||||
int dataSectionAlignment, DataPatch[] dataSectionPatches, boolean isImmutablePIC, int totalFrameSize, int customStackAreaOffset, HotSpotResolvedJavaMethod method, int entryBCI,
|
||||
int dataSectionAlignment, DataPatch[] dataSectionPatches, boolean isImmutablePIC, int totalFrameSize, StackSlot deoptRescueSlot, HotSpotResolvedJavaMethod method, int entryBCI,
|
||||
int id, long jvmciEnv, boolean hasUnsafeAccess) {
|
||||
super(name, targetCode, targetCodeSize, sites, assumptions, methods, comments, dataSection, dataSectionAlignment, dataSectionPatches, isImmutablePIC, totalFrameSize, customStackAreaOffset);
|
||||
super(name, targetCode, targetCodeSize, sites, assumptions, methods, comments, dataSection, dataSectionAlignment, dataSectionPatches, isImmutablePIC, totalFrameSize, deoptRescueSlot);
|
||||
this.method = method;
|
||||
this.entryBCI = entryBCI;
|
||||
this.id = id;
|
||||
|
|
|
@ -126,7 +126,7 @@ final class HotSpotConstantPool implements ConstantPool, HotSpotProxified, Metas
|
|||
private static final int InternalMin = config().jvmConstantInternalMin;
|
||||
private static final int InternalMax = config().jvmConstantInternalMax;
|
||||
|
||||
private JVM_CONSTANT(int tag) {
|
||||
JVM_CONSTANT(int tag) {
|
||||
this.tag = tag;
|
||||
}
|
||||
|
||||
|
@ -171,7 +171,7 @@ final class HotSpotConstantPool implements ConstantPool, HotSpotProxified, Metas
|
|||
int lastCpi = Integer.MIN_VALUE;
|
||||
JavaType javaType;
|
||||
|
||||
public LookupTypeCacheElement(int lastCpi, JavaType javaType) {
|
||||
LookupTypeCacheElement(int lastCpi, JavaType javaType) {
|
||||
super();
|
||||
this.lastCpi = lastCpi;
|
||||
this.javaType = javaType;
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
* Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2015, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
|
@ -22,7 +22,9 @@
|
|||
*/
|
||||
package jdk.vm.ci.hotspot;
|
||||
|
||||
public class HotSpotForeignCallTarget {
|
||||
import jdk.vm.ci.meta.InvokeTarget;
|
||||
|
||||
public class HotSpotForeignCallTarget implements InvokeTarget {
|
||||
|
||||
/**
|
||||
* The entry point address of this call's target.
|
||||
|
|
|
@ -43,6 +43,7 @@ import jdk.vm.ci.code.CompiledCode;
|
|||
import jdk.vm.ci.code.InstalledCode;
|
||||
import jdk.vm.ci.common.JVMCIError;
|
||||
import jdk.vm.ci.inittimer.InitTimer;
|
||||
import jdk.vm.ci.inittimer.SuppressFBWarnings;
|
||||
import jdk.vm.ci.meta.JVMCIMetaAccessContext;
|
||||
import jdk.vm.ci.meta.JavaKind;
|
||||
import jdk.vm.ci.meta.JavaType;
|
||||
|
@ -115,7 +116,7 @@ public final class HotSpotJVMCIRuntime implements HotSpotJVMCIRuntimeProvider, H
|
|||
private boolean isDefault;
|
||||
private final String help;
|
||||
|
||||
private Option(Class<?> type, Object defaultValue, String help) {
|
||||
Option(Class<?> type, Object defaultValue, String help) {
|
||||
assert Character.isUpperCase(name().charAt(0)) : "Option name must start with upper-case letter: " + name();
|
||||
this.type = type;
|
||||
this.value = UNINITIALIZED;
|
||||
|
@ -123,6 +124,7 @@ public final class HotSpotJVMCIRuntime implements HotSpotJVMCIRuntimeProvider, H
|
|||
this.help = help;
|
||||
}
|
||||
|
||||
@SuppressFBWarnings(value = "ES_COMPARING_STRINGS_WITH_EQ", justification = "sentinel must be String since it's a static final in an enum")
|
||||
private Object getValue() {
|
||||
if (value == UNINITIALIZED) {
|
||||
String propertyValue = VM.getSavedProperty(JVMCI_OPTION_PROPERTY_PREFIX + name());
|
||||
|
|
|
@ -38,7 +38,7 @@ class HotSpotMemoryAccessProviderImpl implements HotSpotMemoryAccessProvider, Ho
|
|||
|
||||
protected final HotSpotJVMCIRuntimeProvider runtime;
|
||||
|
||||
public HotSpotMemoryAccessProviderImpl(HotSpotJVMCIRuntimeProvider runtime) {
|
||||
HotSpotMemoryAccessProviderImpl(HotSpotJVMCIRuntimeProvider runtime) {
|
||||
this.runtime = runtime;
|
||||
}
|
||||
|
||||
|
|
|
@ -413,7 +413,7 @@ public final class HotSpotMethodData {
|
|||
private static final int COUNTER_DATA_SIZE = cellIndexToOffset(1);
|
||||
private static final int COUNTER_DATA_COUNT_OFFSET = cellIndexToOffset(config.methodDataCountOffset);
|
||||
|
||||
public CounterData() {
|
||||
CounterData() {
|
||||
super(Tag.CounterData, COUNTER_DATA_SIZE);
|
||||
}
|
||||
|
||||
|
@ -442,7 +442,7 @@ public final class HotSpotMethodData {
|
|||
protected static final int TAKEN_COUNT_OFFSET = cellIndexToOffset(config.jumpDataTakenOffset);
|
||||
protected static final int TAKEN_DISPLACEMENT_OFFSET = cellIndexToOffset(config.jumpDataDisplacementOffset);
|
||||
|
||||
public JumpData() {
|
||||
JumpData() {
|
||||
super(Tag.JumpData, JUMP_DATA_SIZE);
|
||||
}
|
||||
|
||||
|
@ -476,7 +476,7 @@ public final class HotSpotMethodData {
|
|||
final long[] counts;
|
||||
final long totalCount;
|
||||
|
||||
public RawItemProfile(int entries, T[] items, long[] counts, long totalCount) {
|
||||
RawItemProfile(int entries, T[] items, long[] counts, long totalCount) {
|
||||
this.entries = entries;
|
||||
this.items = items;
|
||||
this.counts = counts;
|
||||
|
@ -587,7 +587,7 @@ public final class HotSpotMethodData {
|
|||
|
||||
private static final int TYPE_CHECK_DATA_SIZE = cellIndexToOffset(2) + TYPE_DATA_ROW_SIZE * config.typeProfileWidth;
|
||||
|
||||
public ReceiverTypeData() {
|
||||
ReceiverTypeData() {
|
||||
super(Tag.ReceiverTypeData, TYPE_CHECK_DATA_SIZE);
|
||||
}
|
||||
|
||||
|
@ -612,7 +612,7 @@ public final class HotSpotMethodData {
|
|||
private static final int VIRTUAL_CALL_DATA_FIRST_METHOD_OFFSET = TYPE_DATA_FIRST_TYPE_OFFSET + TYPE_DATA_ROW_SIZE * config.typeProfileWidth;
|
||||
private static final int VIRTUAL_CALL_DATA_FIRST_METHOD_COUNT_OFFSET = TYPE_DATA_FIRST_TYPE_COUNT_OFFSET + TYPE_DATA_ROW_SIZE * config.typeProfileWidth;
|
||||
|
||||
public VirtualCallData() {
|
||||
VirtualCallData() {
|
||||
super(Tag.VirtualCallData, VIRTUAL_CALL_DATA_SIZE);
|
||||
}
|
||||
|
||||
|
@ -714,7 +714,7 @@ public final class HotSpotMethodData {
|
|||
|
||||
private static class VirtualCallTypeData extends VirtualCallData {
|
||||
|
||||
public VirtualCallTypeData() {
|
||||
VirtualCallTypeData() {
|
||||
super(Tag.VirtualCallTypeData, 0);
|
||||
}
|
||||
|
||||
|
@ -730,7 +730,7 @@ public final class HotSpotMethodData {
|
|||
private static final int RET_DATA_ROW_SIZE = cellsToBytes(3);
|
||||
private static final int RET_DATA_SIZE = cellIndexToOffset(1) + RET_DATA_ROW_SIZE * config.bciProfileWidth;
|
||||
|
||||
public RetData() {
|
||||
RetData() {
|
||||
super(Tag.RetData, RET_DATA_SIZE);
|
||||
}
|
||||
}
|
||||
|
@ -740,7 +740,7 @@ public final class HotSpotMethodData {
|
|||
private static final int BRANCH_DATA_SIZE = cellIndexToOffset(3);
|
||||
private static final int NOT_TAKEN_COUNT_OFFSET = cellIndexToOffset(config.branchDataNotTakenOffset);
|
||||
|
||||
public BranchData() {
|
||||
BranchData() {
|
||||
super(Tag.BranchData, BRANCH_DATA_SIZE);
|
||||
}
|
||||
|
||||
|
@ -773,7 +773,7 @@ public final class HotSpotMethodData {
|
|||
private static final int ARRAY_DATA_LENGTH_OFFSET = cellIndexToOffset(config.arrayDataArrayLenOffset);
|
||||
protected static final int ARRAY_DATA_START_OFFSET = cellIndexToOffset(config.arrayDataArrayStartOffset);
|
||||
|
||||
public ArrayData(Tag tag, int staticSize) {
|
||||
ArrayData(Tag tag, int staticSize) {
|
||||
super(tag, staticSize);
|
||||
}
|
||||
|
||||
|
@ -800,7 +800,7 @@ public final class HotSpotMethodData {
|
|||
private static final int MULTI_BRANCH_DATA_FIRST_COUNT_OFFSET = ARRAY_DATA_START_OFFSET + cellsToBytes(0);
|
||||
private static final int MULTI_BRANCH_DATA_FIRST_DISPLACEMENT_OFFSET = ARRAY_DATA_START_OFFSET + cellsToBytes(1);
|
||||
|
||||
public MultiBranchData() {
|
||||
MultiBranchData() {
|
||||
super(Tag.MultiBranchData, MULTI_BRANCH_DATA_SIZE);
|
||||
}
|
||||
|
||||
|
@ -882,13 +882,13 @@ public final class HotSpotMethodData {
|
|||
|
||||
private static final int ARG_INFO_DATA_SIZE = cellIndexToOffset(1);
|
||||
|
||||
public ArgInfoData() {
|
||||
ArgInfoData() {
|
||||
super(Tag.ArgInfoData, ARG_INFO_DATA_SIZE);
|
||||
}
|
||||
}
|
||||
|
||||
private static class UnknownProfileData extends AbstractMethodData {
|
||||
public UnknownProfileData(Tag tag) {
|
||||
UnknownProfileData(Tag tag) {
|
||||
super(tag, 0);
|
||||
}
|
||||
|
||||
|
|
|
@ -56,7 +56,7 @@ public interface HotSpotMethodDataAccessor {
|
|||
|
||||
private final int value;
|
||||
|
||||
private Tag(int value) {
|
||||
Tag(int value) {
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
|
|
|
@ -34,7 +34,7 @@ final class HotSpotMethodUnresolved extends HotSpotMethod {
|
|||
private final Signature signature;
|
||||
protected JavaType holder;
|
||||
|
||||
public HotSpotMethodUnresolved(String name, Signature signature, JavaType holder) {
|
||||
HotSpotMethodUnresolved(String name, Signature signature, JavaType holder) {
|
||||
super(name);
|
||||
this.holder = holder;
|
||||
this.signature = signature;
|
||||
|
|
|
@ -56,7 +56,7 @@ class HotSpotResolvedJavaFieldImpl implements HotSpotResolvedJavaField, HotSpotP
|
|||
public static class FieldLocationIdentity extends LocationIdentity {
|
||||
HotSpotResolvedJavaField inner;
|
||||
|
||||
public FieldLocationIdentity(HotSpotResolvedJavaFieldImpl inner) {
|
||||
FieldLocationIdentity(HotSpotResolvedJavaFieldImpl inner) {
|
||||
this.inner = inner;
|
||||
}
|
||||
|
||||
|
|
|
@ -33,7 +33,6 @@ import java.lang.reflect.Array;
|
|||
import java.lang.reflect.Constructor;
|
||||
import java.lang.reflect.Method;
|
||||
import java.lang.reflect.Modifier;
|
||||
import java.net.URL;
|
||||
import java.nio.ByteOrder;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
|
@ -49,7 +48,6 @@ import jdk.vm.ci.meta.Constant;
|
|||
import jdk.vm.ci.meta.JavaConstant;
|
||||
import jdk.vm.ci.meta.JavaKind;
|
||||
import jdk.vm.ci.meta.JavaType;
|
||||
import jdk.vm.ci.meta.MetaUtil;
|
||||
import jdk.vm.ci.meta.ModifiersProvider;
|
||||
import jdk.vm.ci.meta.ResolvedJavaField;
|
||||
import jdk.vm.ci.meta.ResolvedJavaMethod;
|
||||
|
@ -555,7 +553,7 @@ final class HotSpotResolvedObjectTypeImpl extends HotSpotResolvedJavaType implem
|
|||
*
|
||||
* @param index index to the fields array
|
||||
*/
|
||||
public FieldInfo(int index) {
|
||||
FieldInfo(int index) {
|
||||
HotSpotVMConfig config = config();
|
||||
// Get Klass::_fields
|
||||
final long metaspaceFields = UNSAFE.getAddress(getMetaspaceKlass() + config.instanceKlassFieldsOffset);
|
||||
|
@ -838,12 +836,6 @@ final class HotSpotResolvedObjectTypeImpl extends HotSpotResolvedJavaType implem
|
|||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public URL getClassFilePath() {
|
||||
Class<?> cls = mirror();
|
||||
return cls.getResource(MetaUtil.getSimpleName(cls, true).replace('.', '$') + ".class");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isLocal() {
|
||||
return mirror().isLocalClass();
|
||||
|
|
|
@ -27,7 +27,6 @@ import static java.util.Objects.requireNonNull;
|
|||
import java.lang.annotation.Annotation;
|
||||
import java.lang.reflect.Array;
|
||||
import java.lang.reflect.Modifier;
|
||||
import java.net.URL;
|
||||
|
||||
import jdk.vm.ci.common.JVMCIError;
|
||||
import jdk.vm.ci.meta.Assumptions.AssumptionResult;
|
||||
|
@ -239,11 +238,6 @@ public final class HotSpotResolvedPrimitiveType extends HotSpotResolvedJavaType
|
|||
return kind.toJavaClass();
|
||||
}
|
||||
|
||||
@Override
|
||||
public URL getClassFilePath() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isLocal() {
|
||||
return false;
|
||||
|
|
|
@ -360,7 +360,7 @@ public class HotSpotVMConfig {
|
|||
|
||||
private final long address;
|
||||
|
||||
public VMFields(long address) {
|
||||
VMFields(long address) {
|
||||
this.address = address;
|
||||
}
|
||||
|
||||
|
@ -477,7 +477,7 @@ public class HotSpotVMConfig {
|
|||
|
||||
private final long address;
|
||||
|
||||
public VMTypes(long address) {
|
||||
VMTypes(long address) {
|
||||
this.address = address;
|
||||
}
|
||||
|
||||
|
@ -580,7 +580,7 @@ public class HotSpotVMConfig {
|
|||
|
||||
private final long address;
|
||||
|
||||
public VMIntConstants(long address) {
|
||||
VMIntConstants(long address) {
|
||||
this.address = address;
|
||||
}
|
||||
|
||||
|
@ -639,7 +639,7 @@ public class HotSpotVMConfig {
|
|||
|
||||
private final long address;
|
||||
|
||||
public VMLongConstants(long address) {
|
||||
VMLongConstants(long address) {
|
||||
this.address = address;
|
||||
}
|
||||
|
||||
|
@ -698,7 +698,7 @@ public class HotSpotVMConfig {
|
|||
|
||||
private final long address;
|
||||
|
||||
public VMAddresses(long address) {
|
||||
VMAddresses(long address) {
|
||||
this.address = address;
|
||||
}
|
||||
|
||||
|
@ -753,7 +753,7 @@ public class HotSpotVMConfig {
|
|||
private final long nameOffset;
|
||||
private final long addrOffset;
|
||||
|
||||
public Flags(HashMap<String, VMFields.Field> vmStructs, HashMap<String, VMTypes.Type> vmTypes) {
|
||||
Flags(HashMap<String, VMFields.Field> vmStructs, HashMap<String, VMTypes.Type> vmTypes) {
|
||||
address = vmStructs.get("Flag::flags").getValue();
|
||||
entrySize = vmTypes.get("Flag").getSize();
|
||||
typeOffset = vmStructs.get("Flag::_type").getOffset();
|
||||
|
|
|
@ -59,7 +59,7 @@ public enum DeoptimizationAction {
|
|||
|
||||
private final boolean invalidatesCompilation;
|
||||
|
||||
private DeoptimizationAction(boolean invalidatesCompilation) {
|
||||
DeoptimizationAction(boolean invalidatesCompilation) {
|
||||
this.invalidatesCompilation = invalidatesCompilation;
|
||||
}
|
||||
|
||||
|
|
|
@ -72,7 +72,7 @@ public enum JavaKind {
|
|||
private final Class<?> boxedJavaClass;
|
||||
private final int slotCount;
|
||||
|
||||
private JavaKind(char typeChar, String javaName, int slotCount, boolean isStackInt, Class<?> primitiveJavaClass, Class<?> boxedJavaClass) {
|
||||
JavaKind(char typeChar, String javaName, int slotCount, boolean isStackInt, Class<?> primitiveJavaClass, Class<?> boxedJavaClass) {
|
||||
this.typeChar = typeChar;
|
||||
this.javaName = javaName;
|
||||
this.slotCount = slotCount;
|
||||
|
|
|
@ -57,7 +57,7 @@ import java.util.ArrayList;
|
|||
*/
|
||||
public final class LIRKind {
|
||||
|
||||
private static enum IllegalKind implements PlatformKind {
|
||||
private enum IllegalKind implements PlatformKind {
|
||||
ILLEGAL;
|
||||
|
||||
private final EnumKey<IllegalKind> key = new EnumKey<>(this);
|
||||
|
|
|
@ -35,7 +35,7 @@ public interface MethodHandleAccessProvider {
|
|||
* Identification for methods defined on the class {@link MethodHandle} that are processed by
|
||||
* the {@link MethodHandleAccessProvider}.
|
||||
*/
|
||||
public enum IntrinsicMethod {
|
||||
enum IntrinsicMethod {
|
||||
/** The method {@code MethodHandle.invokeBasic}. */
|
||||
INVOKE_BASIC,
|
||||
/** The method {@code MethodHandle.linkToStatic}. */
|
||||
|
|
|
@ -33,7 +33,7 @@ public interface PlatformKind {
|
|||
|
||||
}
|
||||
|
||||
public class EnumKey<E extends Enum<E>> implements Key {
|
||||
class EnumKey<E extends Enum<E>> implements Key {
|
||||
private final Enum<E> e;
|
||||
|
||||
public EnumKey(Enum<E> e) {
|
||||
|
|
|
@ -23,7 +23,6 @@
|
|||
package jdk.vm.ci.meta;
|
||||
|
||||
import java.lang.annotation.Annotation;
|
||||
import java.net.URL;
|
||||
|
||||
import jdk.vm.ci.meta.Assumptions.AssumptionResult;
|
||||
|
||||
|
@ -307,11 +306,6 @@ public interface ResolvedJavaType extends JavaType, ModifiersProvider {
|
|||
*/
|
||||
String getSourceFileName();
|
||||
|
||||
/**
|
||||
* Returns the class file path - if available - of this type, or {@code null}.
|
||||
*/
|
||||
URL getClassFilePath();
|
||||
|
||||
/**
|
||||
* Returns {@code true} if the type is a local type.
|
||||
*/
|
||||
|
|
|
@ -47,13 +47,13 @@ public enum SPARCKind implements PlatformKind {
|
|||
private final SPARCKind scalar;
|
||||
private final EnumKey<SPARCKind> key = new EnumKey<>(this);
|
||||
|
||||
private SPARCKind(int size) {
|
||||
SPARCKind(int size) {
|
||||
this.size = size;
|
||||
this.scalar = this;
|
||||
this.vectorLength = 1;
|
||||
}
|
||||
|
||||
private SPARCKind(int size, SPARCKind scalar) {
|
||||
SPARCKind(int size, SPARCKind scalar) {
|
||||
this.size = size;
|
||||
this.scalar = scalar;
|
||||
|
||||
|
|
|
@ -72,7 +72,7 @@ ciField::ciField(ciInstanceKlass* klass, int index): _known_to_link_with_put(NUL
|
|||
|
||||
assert(ciObjectFactory::is_initialized(), "not a shared field");
|
||||
|
||||
assert(klass->get_instanceKlass()->is_linked(), "must be linked before using its constan-pool");
|
||||
assert(klass->get_instanceKlass()->is_linked(), "must be linked before using its constant-pool");
|
||||
|
||||
constantPoolHandle cpool(thread, klass->get_instanceKlass()->constants());
|
||||
|
||||
|
@ -106,10 +106,31 @@ ciField::ciField(ciInstanceKlass* klass, int index): _known_to_link_with_put(NUL
|
|||
// even though we may not need to.
|
||||
int holder_index = cpool->klass_ref_index_at(index);
|
||||
bool holder_is_accessible;
|
||||
ciInstanceKlass* declared_holder =
|
||||
ciEnv::current(thread)->get_klass_by_index(cpool, holder_index,
|
||||
|
||||
ciKlass* generic_declared_holder = ciEnv::current(thread)->get_klass_by_index(cpool, holder_index,
|
||||
holder_is_accessible,
|
||||
klass)->as_instance_klass();
|
||||
klass);
|
||||
|
||||
if (generic_declared_holder->is_array_klass()) {
|
||||
// If the declared holder of the field is an array class, assume that
|
||||
// the canonical holder of that field is java.lang.Object. Arrays
|
||||
// do not have fields; java.lang.Object is the only supertype of an
|
||||
// array type that can declare fields and is therefore the canonical
|
||||
// holder of the array type.
|
||||
//
|
||||
// Furthermore, the compilers assume that java.lang.Object does not
|
||||
// have any fields. Therefore, the field is not looked up. Instead,
|
||||
// the method returns partial information that will trigger special
|
||||
// handling in ciField::will_link and will result in a
|
||||
// java.lang.NoSuchFieldError exception being thrown by the compiled
|
||||
// code (the expected behavior in this case).
|
||||
_holder = ciEnv::current(thread)->Object_klass();
|
||||
_offset = -1;
|
||||
_is_constant = false;
|
||||
return;
|
||||
}
|
||||
|
||||
ciInstanceKlass* declared_holder = generic_declared_holder->as_instance_klass();
|
||||
|
||||
// The declared holder of this field may not have been loaded.
|
||||
// Bail out with partial field information.
|
||||
|
|
|
@ -1494,7 +1494,7 @@ void CodeCache::print_summary(outputStream* st, bool detailed) {
|
|||
}
|
||||
|
||||
void CodeCache::print_codelist(outputStream* st) {
|
||||
assert_locked_or_safepoint(CodeCache_lock);
|
||||
MutexLockerEx mu(CodeCache_lock, Mutex::_no_safepoint_check_flag);
|
||||
|
||||
NMethodIterator iter;
|
||||
while(iter.next_alive()) {
|
||||
|
@ -1508,9 +1508,8 @@ void CodeCache::print_codelist(outputStream* st) {
|
|||
}
|
||||
|
||||
void CodeCache::print_layout(outputStream* st) {
|
||||
assert_locked_or_safepoint(CodeCache_lock);
|
||||
MutexLockerEx mu(CodeCache_lock, Mutex::_no_safepoint_check_flag);
|
||||
ResourceMark rm;
|
||||
|
||||
print_summary(st, true);
|
||||
}
|
||||
|
||||
|
|
|
@ -322,9 +322,12 @@ address ExceptionCache::test_address(address addr) {
|
|||
|
||||
bool ExceptionCache::add_address_and_handler(address addr, address handler) {
|
||||
if (test_address(addr) == handler) return true;
|
||||
if (count() < cache_size) {
|
||||
set_pc_at(count(),addr);
|
||||
set_handler_at(count(), handler);
|
||||
|
||||
int index = count();
|
||||
if (index < cache_size) {
|
||||
set_pc_at(index, addr);
|
||||
set_handler_at(index, handler);
|
||||
OrderAccess::storestore();
|
||||
increment_count();
|
||||
return true;
|
||||
}
|
||||
|
|
|
@ -466,9 +466,16 @@ CompileQueue* CompileBroker::compile_queue(int comp_level) {
|
|||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
void CompileBroker::print_compile_queues(outputStream* st) {
|
||||
st->print_cr("Current compiles: ");
|
||||
MutexLocker locker(MethodCompileQueue_lock);
|
||||
MutexLocker locker2(Threads_lock);
|
||||
|
||||
char buf[2000];
|
||||
int buflen = sizeof(buf);
|
||||
Threads::print_threads_compiling(st, buf, buflen);
|
||||
|
||||
st->cr();
|
||||
if (_c1_compile_queue != NULL) {
|
||||
_c1_compile_queue->print(st);
|
||||
}
|
||||
|
@ -479,8 +486,7 @@ void CompileBroker::print_compile_queues(outputStream* st) {
|
|||
|
||||
void CompileQueue::print(outputStream* st) {
|
||||
assert(MethodCompileQueue_lock->owned_by_self(), "must own lock");
|
||||
st->print_cr("Contents of %s", name());
|
||||
st->print_cr("----------------------------");
|
||||
st->print_cr("%s:", name());
|
||||
CompileTask* task = _first;
|
||||
if (task == NULL) {
|
||||
st->print_cr("Empty");
|
||||
|
@ -490,7 +496,7 @@ void CompileQueue::print(outputStream* st) {
|
|||
task = task->next();
|
||||
}
|
||||
}
|
||||
st->print_cr("----------------------------");
|
||||
st->cr();
|
||||
}
|
||||
|
||||
void CompileQueue::print_tty() {
|
||||
|
@ -539,7 +545,7 @@ void CompileBroker::compilation_init(TRAPS) {
|
|||
c1_count = JVMCIHostThreads;
|
||||
}
|
||||
|
||||
if (!UseInterpreter) {
|
||||
if (!UseInterpreter || !BackgroundCompilation) {
|
||||
// Force initialization of JVMCI compiler otherwise JVMCI
|
||||
// compilations will not block until JVMCI is initialized
|
||||
ResourceMark rm;
|
||||
|
@ -1340,49 +1346,55 @@ CompileTask* CompileBroker::create_compile_task(CompileQueue* queue,
|
|||
}
|
||||
|
||||
#if INCLUDE_JVMCI
|
||||
// The number of milliseconds to wait before checking if the
|
||||
// JVMCI compiler thread is blocked.
|
||||
static const long BLOCKING_JVMCI_COMPILATION_WAIT_TIMESLICE = 500;
|
||||
// The number of milliseconds to wait before checking if
|
||||
// JVMCI compilation has made progress.
|
||||
static const long JVMCI_COMPILATION_PROGRESS_WAIT_TIMESLICE = 500;
|
||||
|
||||
// The number of successive times the above check is allowed to
|
||||
// see a blocked JVMCI compiler thread before unblocking the
|
||||
// thread waiting for the compilation to finish.
|
||||
static const int BLOCKING_JVMCI_COMPILATION_WAIT_TO_UNBLOCK_ATTEMPTS = 5;
|
||||
// The number of JVMCI compilation progress checks that must fail
|
||||
// before unblocking a thread waiting for a blocking compilation.
|
||||
static const int JVMCI_COMPILATION_PROGRESS_WAIT_ATTEMPTS = 5;
|
||||
|
||||
/**
|
||||
* Waits for a JVMCI compiler to complete a given task. This thread
|
||||
* waits until either the task completes or it sees the JVMCI compiler
|
||||
* thread is blocked for N consecutive milliseconds where N is
|
||||
* BLOCKING_JVMCI_COMPILATION_WAIT_TIMESLICE *
|
||||
* BLOCKING_JVMCI_COMPILATION_WAIT_TO_UNBLOCK_ATTEMPTS.
|
||||
* waits until either the task completes or it sees no JVMCI compilation
|
||||
* progress for N consecutive milliseconds where N is
|
||||
* JVMCI_COMPILATION_PROGRESS_WAIT_TIMESLICE *
|
||||
* JVMCI_COMPILATION_PROGRESS_WAIT_ATTEMPTS.
|
||||
*
|
||||
* @return true if this thread needs to free/recycle the task
|
||||
*/
|
||||
bool CompileBroker::wait_for_jvmci_completion(CompileTask* task, JavaThread* thread) {
|
||||
bool CompileBroker::wait_for_jvmci_completion(JVMCICompiler* jvmci, CompileTask* task, JavaThread* thread) {
|
||||
MutexLocker waiter(task->lock(), thread);
|
||||
int consecutively_blocked = 0;
|
||||
while (task->lock()->wait(!Mutex::_no_safepoint_check_flag, BLOCKING_JVMCI_COMPILATION_WAIT_TIMESLICE)) {
|
||||
int progress_wait_attempts = 0;
|
||||
int methods_compiled = jvmci->methods_compiled();
|
||||
while (!task->is_complete() && !is_compilation_disabled_forever() &&
|
||||
task->lock()->wait(!Mutex::_no_safepoint_check_flag, JVMCI_COMPILATION_PROGRESS_WAIT_TIMESLICE)) {
|
||||
CompilerThread* jvmci_compiler_thread = task->jvmci_compiler_thread();
|
||||
|
||||
bool progress;
|
||||
if (jvmci_compiler_thread != NULL) {
|
||||
JavaThreadState state;
|
||||
{
|
||||
// A JVMCI compiler thread should not disappear at this point
|
||||
// but let's be extra safe.
|
||||
MutexLocker mu(Threads_lock, thread);
|
||||
state = jvmci_compiler_thread->thread_state();
|
||||
// If the JVMCI compiler thread is not blocked, we deem it to be making progress.
|
||||
progress = jvmci_compiler_thread->thread_state() != _thread_blocked;
|
||||
} else {
|
||||
// Still waiting on JVMCI compiler queue. This thread may be holding a lock
|
||||
// that all JVMCI compiler threads are blocked on. We use the counter for
|
||||
// successful JVMCI compilations to determine whether JVMCI compilation
|
||||
// is still making progress through the JVMCI compiler queue.
|
||||
progress = jvmci->methods_compiled() != methods_compiled;
|
||||
}
|
||||
if (state == _thread_blocked) {
|
||||
if (++consecutively_blocked == BLOCKING_JVMCI_COMPILATION_WAIT_TO_UNBLOCK_ATTEMPTS) {
|
||||
|
||||
if (!progress) {
|
||||
if (++progress_wait_attempts == JVMCI_COMPILATION_PROGRESS_WAIT_ATTEMPTS) {
|
||||
if (PrintCompilation) {
|
||||
task->print(tty, "wait for blocking compilation timed out");
|
||||
}
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
consecutively_blocked = 0;
|
||||
progress_wait_attempts = 0;
|
||||
if (jvmci_compiler_thread == NULL) {
|
||||
methods_compiled = jvmci->methods_compiled();
|
||||
}
|
||||
} else {
|
||||
// Still waiting on JVMCI compiler queue
|
||||
}
|
||||
}
|
||||
task->clear_waiter();
|
||||
|
@ -1407,8 +1419,9 @@ void CompileBroker::wait_for_completion(CompileTask* task) {
|
|||
methodHandle method(thread, task->method());
|
||||
bool free_task;
|
||||
#if INCLUDE_JVMCI
|
||||
if (compiler(task->comp_level())->is_jvmci()) {
|
||||
free_task = wait_for_jvmci_completion(task, thread);
|
||||
AbstractCompiler* comp = compiler(task->comp_level());
|
||||
if (comp->is_jvmci()) {
|
||||
free_task = wait_for_jvmci_completion((JVMCICompiler*) comp, task, thread);
|
||||
} else
|
||||
#endif
|
||||
{
|
||||
|
@ -2355,10 +2368,3 @@ void CompileBroker::print_last_compile() {
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
void CompileBroker::print_compiler_threads_on(outputStream* st) {
|
||||
#ifndef PRODUCT
|
||||
st->print_cr("Compiler thread printing unimplemented.");
|
||||
st->cr();
|
||||
#endif
|
||||
}
|
||||
|
|
|
@ -32,6 +32,9 @@
|
|||
#include "runtime/perfData.hpp"
|
||||
#include "trace/tracing.hpp"
|
||||
#include "utilities/stack.hpp"
|
||||
#if INCLUDE_JVMCI
|
||||
#include "jvmci/jvmciCompiler.hpp"
|
||||
#endif
|
||||
|
||||
class nmethod;
|
||||
class nmethodLocker;
|
||||
|
@ -234,7 +237,7 @@ class CompileBroker: AllStatic {
|
|||
bool blocking);
|
||||
static void wait_for_completion(CompileTask* task);
|
||||
#if INCLUDE_JVMCI
|
||||
static bool wait_for_jvmci_completion(CompileTask* task, JavaThread* thread);
|
||||
static bool wait_for_jvmci_completion(JVMCICompiler* comp, CompileTask* task, JavaThread* thread);
|
||||
#endif
|
||||
|
||||
static void invoke_compiler_on_method(CompileTask* task);
|
||||
|
@ -350,8 +353,6 @@ public:
|
|||
// Debugging output for failure
|
||||
static void print_last_compile();
|
||||
|
||||
static void print_compiler_threads_on(outputStream* st);
|
||||
|
||||
// compiler name for debugging
|
||||
static const char* compiler_name(int comp_level);
|
||||
|
||||
|
|
|
@ -85,6 +85,7 @@ class Disassembler {
|
|||
|
||||
public:
|
||||
static bool can_decode() {
|
||||
ttyLocker tl;
|
||||
return (_decode_instructions_virtual != NULL) ||
|
||||
(_decode_instructions != NULL) ||
|
||||
load_library();
|
||||
|
|
|
@ -546,7 +546,7 @@ JVMCIEnv::CodeInstallResult CodeInstaller::install(JVMCICompiler* compiler, Hand
|
|||
// Make sure a valid compile_id is associated with every compile
|
||||
id = CompileBroker::assign_compile_id_unlocked(Thread::current(), method, entry_bci);
|
||||
}
|
||||
result = JVMCIEnv::register_method(method, nm, entry_bci, &_offsets, _custom_stack_area_offset, &buffer,
|
||||
result = JVMCIEnv::register_method(method, nm, entry_bci, &_offsets, _orig_pc_offset, &buffer,
|
||||
stack_slots, _debug_recorder->_oopmaps, &_exception_handler_table,
|
||||
compiler, _debug_recorder, _dependencies, env, id,
|
||||
has_unsafe_access, _has_wide_vector, installed_code, compiled_code, speculation_log);
|
||||
|
@ -576,7 +576,19 @@ void CodeInstaller::initialize_fields(oop target, oop compiled_code, TRAPS) {
|
|||
_code_handle = JNIHandles::make_local(HotSpotCompiledCode::targetCode(compiled_code));
|
||||
_code_size = HotSpotCompiledCode::targetCodeSize(compiled_code);
|
||||
_total_frame_size = HotSpotCompiledCode::totalFrameSize(compiled_code);
|
||||
_custom_stack_area_offset = HotSpotCompiledCode::customStackAreaOffset(compiled_code);
|
||||
|
||||
oop deoptRescueSlot = HotSpotCompiledCode::deoptRescueSlot(compiled_code);
|
||||
if (deoptRescueSlot == NULL) {
|
||||
_orig_pc_offset = -1;
|
||||
} else {
|
||||
_orig_pc_offset = StackSlot::offset(deoptRescueSlot);
|
||||
if (StackSlot::addFrameSize(deoptRescueSlot)) {
|
||||
_orig_pc_offset += _total_frame_size;
|
||||
}
|
||||
if (_orig_pc_offset < 0) {
|
||||
JVMCI_ERROR("invalid deopt rescue slot: %d", _orig_pc_offset);
|
||||
}
|
||||
}
|
||||
|
||||
// Pre-calculate the constants section size. This is required for PC-relative addressing.
|
||||
_data_section_handle = JNIHandles::make_local(HotSpotCompiledCode::dataSection(compiled_code));
|
||||
|
@ -724,6 +736,9 @@ JVMCIEnv::CodeInstallResult CodeInstaller::initialize_buffer(CodeBuffer& buffer,
|
|||
if (site_InfopointReason::SAFEPOINT() == reason || site_InfopointReason::CALL() == reason || site_InfopointReason::IMPLICIT_EXCEPTION() == reason) {
|
||||
TRACE_jvmci_4("safepoint at %i", pc_offset);
|
||||
site_Safepoint(buffer, pc_offset, site, CHECK_OK);
|
||||
if (_orig_pc_offset < 0) {
|
||||
JVMCI_ERROR_OK("method contains safepoint, but has no deopt rescue slot");
|
||||
}
|
||||
} else {
|
||||
TRACE_jvmci_4("infopoint at %i", pc_offset);
|
||||
site_Infopoint(buffer, pc_offset, site, CHECK_OK);
|
||||
|
|
|
@ -125,7 +125,7 @@ private:
|
|||
jobject _code_handle;
|
||||
jint _code_size;
|
||||
jint _total_frame_size;
|
||||
jint _custom_stack_area_offset;
|
||||
jint _orig_pc_offset;
|
||||
jint _parameter_count;
|
||||
jint _constants_size;
|
||||
#ifndef PRODUCT
|
||||
|
|
|
@ -38,7 +38,7 @@ elapsedTimer JVMCICompiler::_codeInstallTimer;
|
|||
|
||||
JVMCICompiler::JVMCICompiler() : AbstractCompiler(jvmci) {
|
||||
_bootstrapping = false;
|
||||
_methodsCompiled = 0;
|
||||
_methods_compiled = 0;
|
||||
assert(_instance == NULL, "only one instance allowed");
|
||||
_instance = this;
|
||||
}
|
||||
|
@ -99,7 +99,7 @@ void JVMCICompiler::bootstrap() {
|
|||
} while (first_round && qsize == 0);
|
||||
first_round = false;
|
||||
if (PrintBootstrap) {
|
||||
while (z < (_methodsCompiled / 100)) {
|
||||
while (z < (_methods_compiled / 100)) {
|
||||
++z;
|
||||
tty->print_raw(".");
|
||||
}
|
||||
|
@ -107,7 +107,7 @@ void JVMCICompiler::bootstrap() {
|
|||
} while (qsize != 0);
|
||||
|
||||
if (PrintBootstrap) {
|
||||
tty->print_cr(" in " JLONG_FORMAT " ms (compiled %d methods)", os::javaTimeMillis() - start, _methodsCompiled);
|
||||
tty->print_cr(" in " JLONG_FORMAT " ms (compiled %d methods)", os::javaTimeMillis() - start, _methods_compiled);
|
||||
}
|
||||
_bootstrapping = false;
|
||||
}
|
||||
|
@ -176,7 +176,7 @@ void JVMCICompiler::compile_method(const methodHandle& method, int entry_bci, JV
|
|||
env->set_failure("no nmethod produced", true);
|
||||
} else {
|
||||
env->task()->set_num_inlined_bytecodes(CompilationRequestResult::inlinedBytecodes(result_object));
|
||||
_methodsCompiled++;
|
||||
Atomic::inc(&_methods_compiled);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
|
|
|
@ -33,10 +33,10 @@ private:
|
|||
bool _bootstrapping;
|
||||
|
||||
/**
|
||||
* Number of methods compiled by JVMCI. This is not synchronized
|
||||
* so may not be 100% accurate.
|
||||
* Number of methods successfully compiled by a call to
|
||||
* JVMCICompiler::compile_method().
|
||||
*/
|
||||
volatile int _methodsCompiled;
|
||||
volatile int _methods_compiled;
|
||||
|
||||
static JVMCICompiler* _instance;
|
||||
|
||||
|
@ -80,8 +80,11 @@ public:
|
|||
// Print compilation timers and statistics
|
||||
virtual void print_timers();
|
||||
|
||||
// Print compilation statistics
|
||||
void reset_compilation_stats();
|
||||
/**
|
||||
* Gets the number of methods that have been successfully compiled by
|
||||
* a call to JVMCICompiler::compile_method().
|
||||
*/
|
||||
int methods_compiled() { return _methods_compiled; }
|
||||
|
||||
// Print compilation timers and statistics
|
||||
static void print_compilation_timers();
|
||||
|
|
|
@ -91,7 +91,7 @@ class JVMCIJavaClasses : AllStatic {
|
|||
objArrayOop_field(HotSpotCompiledCode, dataSectionPatches, "[Ljdk/vm/ci/code/site/DataPatch;") \
|
||||
boolean_field(HotSpotCompiledCode, isImmutablePIC) \
|
||||
int_field(HotSpotCompiledCode, totalFrameSize) \
|
||||
int_field(HotSpotCompiledCode, customStackAreaOffset) \
|
||||
oop_field(HotSpotCompiledCode, deoptRescueSlot, "Ljdk/vm/ci/code/StackSlot;") \
|
||||
end_class \
|
||||
start_class(HotSpotCompiledCode_Comment) \
|
||||
oop_field(HotSpotCompiledCode_Comment, text, "Ljava/lang/String;") \
|
||||
|
|
|
@ -634,6 +634,7 @@ Handle JVMCIRuntime::callStatic(const char* className, const char* methodName, c
|
|||
|
||||
void JVMCIRuntime::initialize_HotSpotJVMCIRuntime(TRAPS) {
|
||||
if (JNIHandles::resolve(_HotSpotJVMCIRuntime_instance) == NULL) {
|
||||
ResourceMark rm;
|
||||
#ifdef ASSERT
|
||||
// This should only be called in the context of the JVMCI class being initialized
|
||||
TempNewSymbol name = SymbolTable::new_symbol("jdk/vm/ci/runtime/JVMCI", CHECK);
|
||||
|
|
|
@ -61,7 +61,7 @@ Node* AddNode::Identity(PhaseGVN* phase) {
|
|||
|
||||
//------------------------------commute----------------------------------------
|
||||
// Commute operands to move loads and constants to the right.
|
||||
static bool commute( Node *add, int con_left, int con_right ) {
|
||||
static bool commute(Node *add, bool con_left, bool con_right) {
|
||||
Node *in1 = add->in(1);
|
||||
Node *in2 = add->in(2);
|
||||
|
||||
|
@ -110,8 +110,8 @@ static bool commute( Node *add, int con_left, int con_right ) {
|
|||
Node *AddNode::Ideal(PhaseGVN *phase, bool can_reshape) {
|
||||
const Type *t1 = phase->type( in(1) );
|
||||
const Type *t2 = phase->type( in(2) );
|
||||
int con_left = t1->singleton();
|
||||
int con_right = t2->singleton();
|
||||
bool con_left = t1->singleton();
|
||||
bool con_right = t2->singleton();
|
||||
|
||||
// Check for commutative operation desired
|
||||
if( commute(this,con_left,con_right) ) return this;
|
||||
|
|
|
@ -867,17 +867,18 @@ CallGenerator* CallGenerator::for_method_handle_inline(JVMState* jvms, ciMethod*
|
|||
}
|
||||
}
|
||||
// Cast reference arguments to its type.
|
||||
for (int i = 0; i < signature->count(); i++) {
|
||||
for (int i = 0, j = 0; i < signature->count(); i++) {
|
||||
ciType* t = signature->type_at(i);
|
||||
if (t->is_klass()) {
|
||||
Node* arg = kit.argument(receiver_skip + i);
|
||||
Node* arg = kit.argument(receiver_skip + j);
|
||||
const TypeOopPtr* arg_type = arg->bottom_type()->isa_oopptr();
|
||||
const Type* sig_type = TypeOopPtr::make_from_klass(t->as_klass());
|
||||
if (arg_type != NULL && !arg_type->higher_equal(sig_type)) {
|
||||
Node* cast_obj = gvn.transform(new CheckCastPPNode(kit.control(), arg, sig_type));
|
||||
kit.set_argument(receiver_skip + i, cast_obj);
|
||||
kit.set_argument(receiver_skip + j, cast_obj);
|
||||
}
|
||||
}
|
||||
j += t->size(); // long and double take two slots
|
||||
}
|
||||
|
||||
// Try to get the most accurate receiver type
|
||||
|
|
|
@ -2404,20 +2404,30 @@ bool IdealLoopTree::policy_do_remove_empty_loop( PhaseIdealLoop *phase ) {
|
|||
if (needs_guard) {
|
||||
// Check for an obvious zero trip guard.
|
||||
Node* inctrl = PhaseIdealLoop::skip_loop_predicates(cl->in(LoopNode::EntryControl));
|
||||
if (inctrl->Opcode() == Op_IfTrue) {
|
||||
if (inctrl->Opcode() == Op_IfTrue || inctrl->Opcode() == Op_IfFalse) {
|
||||
bool maybe_swapped = (inctrl->Opcode() == Op_IfFalse);
|
||||
// The test should look like just the backedge of a CountedLoop
|
||||
Node* iff = inctrl->in(0);
|
||||
if (iff->is_If()) {
|
||||
Node* bol = iff->in(1);
|
||||
if (bol->is_Bool() && bol->as_Bool()->_test._test == cl->loopexit()->test_trip()) {
|
||||
if (bol->is_Bool()) {
|
||||
BoolTest test = bol->as_Bool()->_test;
|
||||
if (maybe_swapped) {
|
||||
test._test = test.commute();
|
||||
test._test = test.negate();
|
||||
}
|
||||
if (test._test == cl->loopexit()->test_trip()) {
|
||||
Node* cmp = bol->in(1);
|
||||
if (cmp->is_Cmp() && cmp->in(1) == cl->init_trip() && cmp->in(2) == cl->limit()) {
|
||||
int init_idx = maybe_swapped ? 2 : 1;
|
||||
int limit_idx = maybe_swapped ? 1 : 2;
|
||||
if (cmp->is_Cmp() && cmp->in(init_idx) == cl->init_trip() && cmp->in(limit_idx) == cl->limit()) {
|
||||
needs_guard = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#ifndef PRODUCT
|
||||
if (PrintOpto) {
|
||||
|
@ -3048,7 +3058,7 @@ bool PhaseIdealLoop::intrinsify_fill(IdealLoopTree* lpt) {
|
|||
// state of the loop. It's safe in this case to replace it with the
|
||||
// result_mem.
|
||||
_igvn.replace_node(store->in(MemNode::Memory), result_mem);
|
||||
_igvn.replace_node(exit, result_ctrl);
|
||||
lazy_replace(exit, result_ctrl);
|
||||
_igvn.replace_node(store, result_mem);
|
||||
// Any uses the increment outside of the loop become the loop limit.
|
||||
_igvn.replace_node(head->incr(), head->limit());
|
||||
|
|
|
@ -755,8 +755,8 @@ bool PhaseIdealLoop::is_counted_loop( Node *x, IdealLoopTree *loop ) {
|
|||
set_loop(iff2, get_loop(iffalse));
|
||||
|
||||
// Lazy update of 'get_ctrl' mechanism.
|
||||
lazy_replace_proj( iffalse, iff2 );
|
||||
lazy_replace_proj( iftrue, ift2 );
|
||||
lazy_replace(iffalse, iff2);
|
||||
lazy_replace(iftrue, ift2);
|
||||
|
||||
// Swap names
|
||||
iffalse = iff2;
|
||||
|
|
|
@ -693,13 +693,18 @@ public:
|
|||
}
|
||||
|
||||
private:
|
||||
Node *get_ctrl_no_update( Node *i ) const {
|
||||
Node *get_ctrl_no_update_helper(Node *i) const {
|
||||
assert(has_ctrl(i), "should be control, not loop");
|
||||
return (Node*)(((intptr_t)_nodes[i->_idx]) & ~1);
|
||||
}
|
||||
|
||||
Node *get_ctrl_no_update(Node *i) const {
|
||||
assert( has_ctrl(i), "" );
|
||||
Node *n = (Node*)(((intptr_t)_nodes[i->_idx]) & ~1);
|
||||
Node *n = get_ctrl_no_update_helper(i);
|
||||
if (!n->in(0)) {
|
||||
// Skip dead CFG nodes
|
||||
do {
|
||||
n = (Node*)(((intptr_t)_nodes[n->_idx]) & ~1);
|
||||
n = get_ctrl_no_update_helper(n);
|
||||
} while (!n->in(0));
|
||||
n = find_non_split_ctrl(n);
|
||||
}
|
||||
|
@ -721,22 +726,15 @@ private:
|
|||
// from old_node to new_node to support the lazy update. Reference
|
||||
// replaces loop reference, since that is not needed for dead node.
|
||||
public:
|
||||
void lazy_update( Node *old_node, Node *new_node ) {
|
||||
assert( old_node != new_node, "no cycles please" );
|
||||
//old_node->set_req( 1, new_node /*NO DU INFO*/ );
|
||||
// Nodes always have DU info now, so re-use the side array slot
|
||||
// for this node to provide the forwarding pointer.
|
||||
_nodes.map( old_node->_idx, (Node*)((intptr_t)new_node + 1) );
|
||||
void lazy_update(Node *old_node, Node *new_node) {
|
||||
assert(old_node != new_node, "no cycles please");
|
||||
// Re-use the side array slot for this node to provide the
|
||||
// forwarding pointer.
|
||||
_nodes.map(old_node->_idx, (Node*)((intptr_t)new_node + 1));
|
||||
}
|
||||
void lazy_replace( Node *old_node, Node *new_node ) {
|
||||
_igvn.replace_node( old_node, new_node );
|
||||
lazy_update( old_node, new_node );
|
||||
}
|
||||
void lazy_replace_proj( Node *old_node, Node *new_node ) {
|
||||
assert( old_node->req() == 1, "use this for Projs" );
|
||||
_igvn.hash_delete(old_node); // Must hash-delete before hacking edges
|
||||
old_node->add_req( NULL );
|
||||
lazy_replace( old_node, new_node );
|
||||
void lazy_replace(Node *old_node, Node *new_node) {
|
||||
_igvn.replace_node(old_node, new_node);
|
||||
lazy_update(old_node, new_node);
|
||||
}
|
||||
|
||||
private:
|
||||
|
|
|
@ -2654,9 +2654,9 @@ bool PhaseMacroExpand::expand_macro_nodes() {
|
|||
eliminate_macro_nodes();
|
||||
|
||||
// Make sure expansion will not cause node limit to be exceeded.
|
||||
// Worst case is a macro node gets expanded into about 50 nodes.
|
||||
// Worst case is a macro node gets expanded into about 200 nodes.
|
||||
// Allow 50% more for optimization.
|
||||
if (C->check_node_count(C->macro_count() * 75, "out of nodes before macro expansion" ) )
|
||||
if (C->check_node_count(C->macro_count() * 300, "out of nodes before macro expansion" ) )
|
||||
return true;
|
||||
|
||||
// Eliminate Opaque and LoopLimit nodes. Do it after all loop optimizations.
|
||||
|
|
|
@ -472,7 +472,7 @@ void PhaseIdealLoop::do_split_if( Node *iff ) {
|
|||
|
||||
// Replace in the graph with lazy-update mechanism
|
||||
new_iff->set_req(0, new_iff); // hook self so it does not go dead
|
||||
lazy_replace_proj( ifp, ifpx );
|
||||
lazy_replace(ifp, ifpx);
|
||||
new_iff->set_req(0, region);
|
||||
|
||||
// Record bits for later xforms
|
||||
|
|
|
@ -1334,6 +1334,65 @@ Node *BoolNode::Ideal(PhaseGVN *phase, bool can_reshape) {
|
|||
return new BoolNode( ncmp, _test.negate() );
|
||||
}
|
||||
|
||||
// Change ((x & m) u<= m) or ((m & x) u<= m) to always true
|
||||
// Same with ((x & m) u< m+1) and ((m & x) u< m+1)
|
||||
if (cop == Op_CmpU &&
|
||||
cmp1->Opcode() == Op_AndI) {
|
||||
Node* bound = NULL;
|
||||
if (_test._test == BoolTest::le) {
|
||||
bound = cmp2;
|
||||
} else if (_test._test == BoolTest::lt &&
|
||||
cmp2->Opcode() == Op_AddI &&
|
||||
cmp2->in(2)->find_int_con(0) == 1) {
|
||||
bound = cmp2->in(1);
|
||||
}
|
||||
if (cmp1->in(2) == bound || cmp1->in(1) == bound) {
|
||||
return ConINode::make(1);
|
||||
}
|
||||
}
|
||||
|
||||
// Change ((x & (m - 1)) u< m) into (m > 0)
|
||||
// This is the off-by-one variant of the above
|
||||
if (cop == Op_CmpU &&
|
||||
_test._test == BoolTest::lt &&
|
||||
cmp1->Opcode() == Op_AndI) {
|
||||
Node* l = cmp1->in(1);
|
||||
Node* r = cmp1->in(2);
|
||||
for (int repeat = 0; repeat < 2; repeat++) {
|
||||
bool match = r->Opcode() == Op_AddI && r->in(2)->find_int_con(0) == -1 &&
|
||||
r->in(1) == cmp2;
|
||||
if (match) {
|
||||
// arraylength known to be non-negative, so a (arraylength != 0) is sufficient,
|
||||
// but to be compatible with the array range check pattern, use (arraylength u> 0)
|
||||
Node* ncmp = cmp2->Opcode() == Op_LoadRange
|
||||
? phase->transform(new CmpUNode(cmp2, phase->intcon(0)))
|
||||
: phase->transform(new CmpINode(cmp2, phase->intcon(0)));
|
||||
return new BoolNode(ncmp, BoolTest::gt);
|
||||
} else {
|
||||
// commute and try again
|
||||
l = cmp1->in(2);
|
||||
r = cmp1->in(1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Change (arraylength <= 0) or (arraylength == 0)
|
||||
// into (arraylength u<= 0)
|
||||
// Also change (arraylength != 0) into (arraylength u> 0)
|
||||
// The latter version matches the code pattern generated for
|
||||
// array range checks, which will more likely be optimized later.
|
||||
if (cop == Op_CmpI &&
|
||||
cmp1->Opcode() == Op_LoadRange &&
|
||||
cmp2->find_int_con(-1) == 0) {
|
||||
if (_test._test == BoolTest::le || _test._test == BoolTest::eq) {
|
||||
Node* ncmp = phase->transform(new CmpUNode(cmp1, cmp2));
|
||||
return new BoolNode(ncmp, BoolTest::le);
|
||||
} else if (_test._test == BoolTest::ne) {
|
||||
Node* ncmp = phase->transform(new CmpUNode(cmp1, cmp2));
|
||||
return new BoolNode(ncmp, BoolTest::gt);
|
||||
}
|
||||
}
|
||||
|
||||
// Change "bool eq/ne (cmp (Conv2B X) 0)" into "bool eq/ne (cmp X 0)".
|
||||
// This is a standard idiom for branching on a boolean value.
|
||||
Node *c2b = cmp1;
|
||||
|
@ -1496,4 +1555,3 @@ const Type* Log10DNode::Value(PhaseGVN* phase) const {
|
|||
double d = t1->getd();
|
||||
return TypeD::make( StubRoutines::intrinsic_log10( d ) );
|
||||
}
|
||||
|
||||
|
|
|
@ -118,12 +118,13 @@ Flag::Error AllocatePrefetchInstrConstraintFunc(intx value, bool verbose) {
|
|||
}
|
||||
|
||||
Flag::Error AllocatePrefetchStepSizeConstraintFunc(intx value, bool verbose) {
|
||||
if (value < 1 || value > max_jint) {
|
||||
intx max_value = 512;
|
||||
if (value < 1 || value > max_value) {
|
||||
CommandLineError::print(verbose,
|
||||
"AllocatePrefetchStepSize (" INTX_FORMAT ") "
|
||||
"must be between 1 and %d\n",
|
||||
AllocatePrefetchStepSize,
|
||||
max_jint);
|
||||
max_value);
|
||||
return Flag::VIOLATES_CONSTRAINT;
|
||||
}
|
||||
|
||||
|
@ -138,6 +139,24 @@ Flag::Error AllocatePrefetchStepSizeConstraintFunc(intx value, bool verbose) {
|
|||
return Flag::VIOLATES_CONSTRAINT;
|
||||
}
|
||||
|
||||
/* The limit of 64 for the quotient of AllocatePrefetchDistance and AllocatePrefetchSize
|
||||
* originates from the limit of 64 for AllocatePrefetchLines/AllocateInstancePrefetchLines.
|
||||
* If AllocatePrefetchStyle == 2, the quotient from above is used in PhaseMacroExpand::prefetch_allocation()
|
||||
* to determine the number of lines to prefetch. For other values of AllocatePrefetchStyle,
|
||||
* AllocatePrefetchDistance and AllocatePrefetchSize is used. For consistency, all these
|
||||
* quantities must have the same limit (64 in this case).
|
||||
*/
|
||||
if (AllocatePrefetchDistance / AllocatePrefetchStepSize > 64) {
|
||||
CommandLineError::print(verbose,
|
||||
"AllocatePrefetchDistance (" INTX_FORMAT ") too large or "
|
||||
"AllocatePrefetchStepSize (" INTX_FORMAT ") too small; "
|
||||
"try decreasing/increasing values so that "
|
||||
"AllocatePrefetchDistance / AllocatePrefetchStepSize <= 64\n",
|
||||
AllocatePrefetchDistance, AllocatePrefetchStepSize,
|
||||
AllocatePrefetchDistance % AllocatePrefetchStepSize);
|
||||
return Flag::VIOLATES_CONSTRAINT;
|
||||
}
|
||||
|
||||
return Flag::SUCCESS;
|
||||
}
|
||||
|
||||
|
|
|
@ -2965,16 +2965,16 @@ public:
|
|||
\
|
||||
product(intx, AllocatePrefetchLines, 3, \
|
||||
"Number of lines to prefetch ahead of array allocation pointer") \
|
||||
range(1, max_jint / 2) \
|
||||
range(1, 64) \
|
||||
\
|
||||
product(intx, AllocateInstancePrefetchLines, 1, \
|
||||
"Number of lines to prefetch ahead of instance allocation " \
|
||||
"pointer") \
|
||||
range(1, max_jint / 2) \
|
||||
range(1, 64) \
|
||||
\
|
||||
product(intx, AllocatePrefetchStepSize, 16, \
|
||||
"Step size in bytes of sequential prefetch instructions") \
|
||||
range(1, max_jint) \
|
||||
range(1, 512) \
|
||||
constraint(AllocatePrefetchStepSizeConstraintFunc,AfterMemoryInit)\
|
||||
\
|
||||
product(intx, AllocatePrefetchInstr, 0, \
|
||||
|
|
|
@ -31,6 +31,7 @@
|
|||
#include "code/codeCacheExtensions.hpp"
|
||||
#include "code/scopeDesc.hpp"
|
||||
#include "compiler/compileBroker.hpp"
|
||||
#include "compiler/compileTask.hpp"
|
||||
#include "gc/shared/gcId.hpp"
|
||||
#include "gc/shared/gcLocker.inline.hpp"
|
||||
#include "gc/shared/workgroup.hpp"
|
||||
|
@ -2884,6 +2885,20 @@ void JavaThread::print_on(outputStream *st) const {
|
|||
print_thread_state_on(st);
|
||||
_safepoint_state->print_on(st);
|
||||
#endif // PRODUCT
|
||||
if (is_Compiler_thread()) {
|
||||
CompilerThread* ct = (CompilerThread*)this;
|
||||
if (ct->task() != NULL) {
|
||||
st->print(" Compiling: ");
|
||||
ct->task()->print(st, NULL, true, false);
|
||||
} else {
|
||||
st->print(" No compile task");
|
||||
}
|
||||
st->cr();
|
||||
}
|
||||
}
|
||||
|
||||
void JavaThread::print_name_on_error(outputStream* st, char *buf, int buflen) const {
|
||||
st->print("%s", get_thread_name_string(buf, buflen));
|
||||
}
|
||||
|
||||
// Called by fatal error handler. The difference between this and
|
||||
|
@ -4386,7 +4401,6 @@ void Threads::print_on(outputStream* st, bool print_stacks,
|
|||
wt->print_on(st);
|
||||
st->cr();
|
||||
}
|
||||
CompileBroker::print_compiler_threads_on(st);
|
||||
st->flush();
|
||||
}
|
||||
|
||||
|
@ -4439,8 +4453,24 @@ void Threads::print_on_error(outputStream* st, Thread* current, char* buf,
|
|||
current->print_on_error(st, buf, buflen);
|
||||
st->cr();
|
||||
}
|
||||
st->cr();
|
||||
st->print_cr("Threads with active compile tasks:");
|
||||
print_threads_compiling(st, buf, buflen);
|
||||
}
|
||||
|
||||
void Threads::print_threads_compiling(outputStream* st, char* buf, int buflen) {
|
||||
ALL_JAVA_THREADS(thread) {
|
||||
if (thread->is_Compiler_thread()) {
|
||||
CompilerThread* ct = (CompilerThread*) thread;
|
||||
if (ct->task() != NULL) {
|
||||
thread->print_name_on_error(st, buf, buflen);
|
||||
ct->task()->print(st, NULL, true, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Internal SpinLock and Mutex
|
||||
// Based on ParkEvent
|
||||
|
||||
|
|
|
@ -1660,6 +1660,7 @@ class JavaThread: public Thread {
|
|||
void print_thread_state_on(outputStream*) const PRODUCT_RETURN;
|
||||
void print_thread_state() const PRODUCT_RETURN;
|
||||
void print_on_error(outputStream* st, char* buf, int buflen) const;
|
||||
void print_name_on_error(outputStream* st, char* buf, int buflen) const;
|
||||
void verify();
|
||||
const char* get_thread_name() const;
|
||||
private:
|
||||
|
@ -2158,6 +2159,7 @@ class Threads: AllStatic {
|
|||
print_on(tty, print_stacks, internal_format, false /* no concurrent lock printed */);
|
||||
}
|
||||
static void print_on_error(outputStream* st, Thread* current, char* buf, int buflen);
|
||||
static void print_threads_compiling(outputStream* st, char* buf, int buflen);
|
||||
|
||||
// Get Java threads that are waiting to enter a monitor. If doLock
|
||||
// is true, then Threads_lock is grabbed as needed. Otherwise, the
|
||||
|
|
|
@ -485,18 +485,6 @@ void VM_Exit::wait_if_vm_exited() {
|
|||
}
|
||||
}
|
||||
|
||||
void VM_PrintCompileQueue::doit() {
|
||||
CompileBroker::print_compile_queues(_out);
|
||||
}
|
||||
|
||||
void VM_PrintCodeList::doit() {
|
||||
CodeCache::print_codelist(_out);
|
||||
}
|
||||
|
||||
void VM_PrintCodeCache::doit() {
|
||||
CodeCache::print_layout(_out);
|
||||
}
|
||||
|
||||
#if INCLUDE_SERVICES
|
||||
void VM_PrintClassHierarchy::doit() {
|
||||
KlassHierarchy::print_class_hierarchy(_out, _print_interfaces, _print_subclasses, _classname);
|
||||
|
|
|
@ -105,9 +105,6 @@
|
|||
template(DumpHashtable) \
|
||||
template(DumpTouchedMethods) \
|
||||
template(MarkActiveNMethods) \
|
||||
template(PrintCompileQueue) \
|
||||
template(PrintCodeList) \
|
||||
template(PrintCodeCache) \
|
||||
template(PrintClassHierarchy) \
|
||||
|
||||
class VM_Operation: public CHeapObj<mtInternal> {
|
||||
|
@ -424,37 +421,6 @@ class VM_Exit: public VM_Operation {
|
|||
void doit();
|
||||
};
|
||||
|
||||
class VM_PrintCompileQueue: public VM_Operation {
|
||||
private:
|
||||
outputStream* _out;
|
||||
|
||||
public:
|
||||
VM_PrintCompileQueue(outputStream* st) : _out(st) {}
|
||||
VMOp_Type type() const { return VMOp_PrintCompileQueue; }
|
||||
Mode evaluation_mode() const { return _no_safepoint; }
|
||||
void doit();
|
||||
};
|
||||
|
||||
class VM_PrintCodeList: public VM_Operation {
|
||||
private:
|
||||
outputStream* _out;
|
||||
|
||||
public:
|
||||
VM_PrintCodeList(outputStream* st) : _out(st) {}
|
||||
VMOp_Type type() const { return VMOp_PrintCodeList; }
|
||||
void doit();
|
||||
};
|
||||
|
||||
class VM_PrintCodeCache: public VM_Operation {
|
||||
private:
|
||||
outputStream* _out;
|
||||
|
||||
public:
|
||||
VM_PrintCodeCache(outputStream* st) : _out(st) {}
|
||||
VMOp_Type type() const { return VMOp_PrintCodeCache; }
|
||||
void doit();
|
||||
};
|
||||
|
||||
#if INCLUDE_SERVICES
|
||||
class VM_PrintClassHierarchy: public VM_Operation {
|
||||
private:
|
||||
|
|
|
@ -832,18 +832,15 @@ void VMDynamicLibrariesDCmd::execute(DCmdSource source, TRAPS) {
|
|||
}
|
||||
|
||||
void CompileQueueDCmd::execute(DCmdSource source, TRAPS) {
|
||||
VM_PrintCompileQueue printCompileQueueOp(output());
|
||||
VMThread::execute(&printCompileQueueOp);
|
||||
CompileBroker::print_compile_queues(output());
|
||||
}
|
||||
|
||||
void CodeListDCmd::execute(DCmdSource source, TRAPS) {
|
||||
VM_PrintCodeList printCodeListOp(output());
|
||||
VMThread::execute(&printCodeListOp);
|
||||
CodeCache::print_codelist(output());
|
||||
}
|
||||
|
||||
void CodeCacheDCmd::execute(DCmdSource source, TRAPS) {
|
||||
VM_PrintCodeCache printCodeCacheOp(output());
|
||||
VMThread::execute(&printCodeCacheOp);
|
||||
CodeCache::print_layout(output());
|
||||
}
|
||||
|
||||
void CompilerDirectivesPrintDCmd::execute(DCmdSource source, TRAPS) {
|
||||
|
|
|
@ -24,7 +24,7 @@
|
|||
/*
|
||||
* @test TestCompilerDirectivesCompatibilityBase
|
||||
* @bug 8137167
|
||||
* @library /testlibrary /../../test/lib
|
||||
* @library /testlibrary /test/lib
|
||||
* @modules java.base/sun.misc
|
||||
* java.compiler
|
||||
* java.management
|
||||
|
|
|
@ -24,7 +24,7 @@
|
|||
/*
|
||||
* @test TestCompilerDirectivesCompatibilityCommandOff
|
||||
* @bug 8137167
|
||||
* @library /testlibrary /../../test/lib
|
||||
* @library /testlibrary /test/lib
|
||||
* @modules java.base/sun.misc
|
||||
* java.compiler
|
||||
* java.management
|
||||
|
|
|
@ -24,7 +24,7 @@
|
|||
/*
|
||||
* @test TestCompilerDirectivesCompatibilityCommandOn
|
||||
* @bug 8137167
|
||||
* @library /testlibrary /../../test/lib
|
||||
* @library /testlibrary /test/lib
|
||||
* @modules java.base/sun.misc
|
||||
* java.compiler
|
||||
* java.management
|
||||
|
|
|
@ -24,7 +24,7 @@
|
|||
/*
|
||||
* @test TestCompilerDirectivesCompatibilityFlag
|
||||
* @bug 8137167
|
||||
* @library /testlibrary /../../test/lib
|
||||
* @library /testlibrary /test/lib
|
||||
* @modules java.base/sun.misc
|
||||
* java.compiler
|
||||
* java.management
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests CompileCommand=compileonly
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @build compiler.compilercontrol.commandfile.CompileOnlyTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests CompileCommand=exclude
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @build compiler.compilercontrol.commandfile.ExcludeTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests CompileCommand=log
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @build compiler.compilercontrol.commandfile.LogTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,8 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests CompileCommand=print
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @ignore 8140354
|
||||
* @build compiler.compilercontrol.commandfile.PrintTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests CompileCommand=compileonly
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @build compiler.compilercontrol.commands.CompileOnlyTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests CompileCommand=exclude
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @build compiler.compilercontrol.commands.ExcludeTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests CompileCommand=log
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @build compiler.compilercontrol.commands.LogTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,8 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests CompileCommand=print
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @ignore 8140354
|
||||
* @build compiler.compilercontrol.commands.PrintTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests directives to be able to compile only specified methods
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @build compiler.compilercontrol.directives.CompileOnlyTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests directives to be able to exclude methods from compilation
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @build compiler.compilercontrol.directives.ExcludeTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests directives to be able to turn on LogCompilation
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @build compiler.compilercontrol.directives.LogTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,8 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests directives to be able to turn on print_assembly
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @ignore 8140354
|
||||
* @build compiler.compilercontrol.directives.PrintTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests directives to be able to add and remove directives
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @build compiler.compilercontrol.jcmd.AddAndRemoveTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests jcmd to be able to add a directive to compile only specified methods
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @build compiler.compilercontrol.jcmd.AddCompileOnlyTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests jcmd to be able to add a directive to exclude only specified methods
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @build compiler.compilercontrol.jcmd.AddExcludeTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Tests jcmd to be able to add a directive to log only specified methods
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @build compiler.compilercontrol.jcmd.AddLogTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -26,7 +26,7 @@
|
|||
* @bug 8137167
|
||||
* @summary Tests jcmd to be able to add a directive to print assembly
|
||||
* only for specified methods
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @build compiler.compilercontrol.jcmd.AddPrintAssemblyTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -26,6 +26,7 @@
|
|||
* @bug 8137167
|
||||
* @summary Tests jcmd to be able to add a directive to compile only specified methods
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @ignore 8140354
|
||||
* @build compiler.compilercontrol.jcmd.PrintDirectivesTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -27,6 +27,7 @@
|
|||
* @summary Tests jcmd to be able to add a lot of huge directive files with
|
||||
* parallel executed jcmds until timeout has reached
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @ignore 8148563
|
||||
* @build compiler.compilercontrol.jcmd.StressAddMultiThreadedTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils
|
||||
|
|
|
@ -25,7 +25,7 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Randomly generates commands with random types
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @build compiler.compilercontrol.mixed.RandomCommandsTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -25,7 +25,8 @@
|
|||
* @test
|
||||
* @bug 8137167
|
||||
* @summary Randomly generates valid commands with random types
|
||||
* @library /testlibrary /../../test/lib /compiler/testlibrary ../share /
|
||||
* @library /testlibrary /test/lib /compiler/testlibrary ../share /
|
||||
* @ignore 8140354
|
||||
* @build compiler.compilercontrol.mixed.RandomValidCommandsTest
|
||||
* pool.sub.* pool.subpack.* sun.hotspot.WhiteBox
|
||||
* compiler.testlibrary.CompilerUtils compiler.compilercontrol.share.actions.*
|
||||
|
|
|
@ -32,8 +32,8 @@ import java.util.Arrays;
|
|||
public enum Command {
|
||||
COMPILEONLY("compileonly", ".*", "-Xbatch"),
|
||||
EXCLUDE("exclude", "", "-Xbatch"),
|
||||
INLINE("inline", ".*"),
|
||||
DONTINLINE("dontinline", ""),
|
||||
INLINE("inline", ".*", "-Xbatch"),
|
||||
DONTINLINE("dontinline", "", "-Xbatch"),
|
||||
LOG("log", "", "-XX:+UnlockDiagnosticVMOptions",
|
||||
"-XX:+LogCompilation", "-XX:LogFile=" + LogProcessor.LOG_FILE),
|
||||
PRINT("print", ""),
|
||||
|
|
|
@ -27,7 +27,7 @@ import jdk.test.lib.ProcessTools;
|
|||
|
||||
/*
|
||||
* @test
|
||||
* @library /testlibrary /../../test/lib /compiler/whitebox
|
||||
* @library /testlibrary /test/lib /compiler/whitebox
|
||||
* /compiler/testlibrary /compiler/codegen/7184394
|
||||
* @modules java.base/sun.misc
|
||||
* java.management
|
||||
|
|
|
@ -28,7 +28,7 @@ import jdk.test.lib.ProcessTools;
|
|||
|
||||
/*
|
||||
* @test
|
||||
* @library /testlibrary /../../test/lib /compiler/whitebox
|
||||
* @library /testlibrary /test/lib /compiler/whitebox
|
||||
* /compiler/testlibrary /compiler/codegen/7184394
|
||||
* @modules java.base/sun.misc
|
||||
* java.management
|
||||
|
|
|
@ -24,7 +24,7 @@
|
|||
/*
|
||||
* @test
|
||||
* @bug 8138651
|
||||
* @library /testlibrary /../../test/lib
|
||||
* @library /testlibrary /test/lib
|
||||
* @build IntrinsicDisabledTest
|
||||
* @run main ClassFileInstaller sun.hotspot.WhiteBox
|
||||
* sun.hotspot.WhiteBox$WhiteBoxPermission
|
||||
|
|
|
@ -42,7 +42,7 @@ import jdk.test.lib.Platform;
|
|||
* @test
|
||||
* @bug 8130150 8131779 8139907
|
||||
* @summary Verify that the Montgomery multiply and square intrinsic works and correctly checks their arguments.
|
||||
* @library /testlibrary /../../test/lib
|
||||
* @library /testlibrary /test/lib
|
||||
* @library /testlibrary
|
||||
* @build MontgomeryMultiplyTest
|
||||
* @run main ClassFileInstaller sun.hotspot.WhiteBox
|
||||
|
|
|
@ -26,7 +26,7 @@
|
|||
* @test
|
||||
* @bug 8145336
|
||||
* @summary PPC64: fix string intrinsics after CompactStrings change
|
||||
* @library /testlibrary /../../test/lib
|
||||
* @library /testlibrary /test/lib
|
||||
* @build sun.hotspot.WhiteBox
|
||||
* @run main ClassFileInstaller sun.hotspot.WhiteBox
|
||||
* sun.hotspot.WhiteBox$WhiteBoxPermission
|
||||
|
|
75
hotspot/test/compiler/jsr292/LongReferenceCastingTest.java
Normal file
75
hotspot/test/compiler/jsr292/LongReferenceCastingTest.java
Normal file
|
@ -0,0 +1,75 @@
|
|||
/*
|
||||
* Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*
|
||||
*/
|
||||
|
||||
import java.lang.invoke.*;
|
||||
|
||||
/**
|
||||
* @test
|
||||
* @bug 8148752
|
||||
* @summary Test correct casting of MH arguments during inlining.
|
||||
* @run main LongReferenceCastingTest
|
||||
*/
|
||||
public class LongReferenceCastingTest {
|
||||
static final String MY_STRING = "myString";
|
||||
static final MethodHandle MH;
|
||||
|
||||
static {
|
||||
try {
|
||||
MethodHandles.Lookup lookup = MethodHandles.lookup();
|
||||
MethodType mt = MethodType.methodType(String.class, long.class, Object.class, String.class);
|
||||
MH = lookup.findVirtual(LongReferenceCastingTest.class, "myMethod", mt);
|
||||
} catch (Exception e) {
|
||||
throw new Error(e);
|
||||
}
|
||||
}
|
||||
|
||||
public String myMethod(long l, Object o, String s) {
|
||||
// The long argument occupies two stack slots, causing C2 to treat it as
|
||||
// two arguments and casting the fist one two long and the second one to Object.
|
||||
// As a result, Object o is casted to String and the o.toString() call is
|
||||
// inlined as String::toString(). We fail at runtime because 'o' is not a String.
|
||||
return o.toString();
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return MY_STRING;
|
||||
}
|
||||
|
||||
public static void main(String[] args) throws Exception {
|
||||
LongReferenceCastingTest test = new LongReferenceCastingTest();
|
||||
try {
|
||||
for (int i = 0; i < 20_000; ++i) {
|
||||
if (!test.invoke().equals(MY_STRING)) {
|
||||
throw new RuntimeException("Invalid string");
|
||||
}
|
||||
}
|
||||
} catch (Throwable t) {
|
||||
throw new RuntimeException("Test failed", t);
|
||||
}
|
||||
}
|
||||
|
||||
public String invoke() throws Throwable {
|
||||
return (String) MH.invokeExact(this, 0L, (Object)this, MY_STRING);
|
||||
}
|
||||
}
|
|
@ -35,6 +35,16 @@
|
|||
* -Dcompiler.jvmci.JVM_GetJVMCIRuntimeTest.positive=false
|
||||
* -XX:-EnableJVMCI
|
||||
* compiler.jvmci.JVM_GetJVMCIRuntimeTest
|
||||
* @run main/othervm -XX:+UnlockExperimentalVMOptions
|
||||
* -Dcompiler.jvmci.JVM_GetJVMCIRuntimeTest.positive=true
|
||||
* -Dcompiler.jvmci.JVM_GetJVMCIRuntimeTest.threaded=true
|
||||
* -XX:+EnableJVMCI
|
||||
* compiler.jvmci.JVM_GetJVMCIRuntimeTest
|
||||
* @run main/othervm -XX:+UnlockExperimentalVMOptions
|
||||
* -Dcompiler.jvmci.JVM_GetJVMCIRuntimeTest.positive=false
|
||||
* -Dcompiler.jvmci.JVM_GetJVMCIRuntimeTest.threaded=true
|
||||
* -XX:-EnableJVMCI
|
||||
* compiler.jvmci.JVM_GetJVMCIRuntimeTest
|
||||
|
||||
*/
|
||||
|
||||
|
@ -43,22 +53,27 @@ package compiler.jvmci;
|
|||
import jdk.vm.ci.runtime.JVMCI;
|
||||
import jdk.test.lib.Asserts;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
|
||||
public class JVM_GetJVMCIRuntimeTest {
|
||||
public class JVM_GetJVMCIRuntimeTest implements Runnable {
|
||||
private static final boolean IS_POSITIVE = Boolean.getBoolean(
|
||||
"compiler.jvmci.JVM_GetJVMCIRuntimeTest.positive");
|
||||
private static final boolean IN_THREAD = Boolean.getBoolean(
|
||||
"compiler.jvmci.JVM_GetJVMCIRuntimeTest.threaded");
|
||||
|
||||
private final Method initializeRuntime;
|
||||
|
||||
public static void main(String[] args) {
|
||||
new JVM_GetJVMCIRuntimeTest().runTest();
|
||||
public static void main(String[] args) throws Throwable {
|
||||
JVM_GetJVMCIRuntimeTest instance = new JVM_GetJVMCIRuntimeTest();
|
||||
if (IN_THREAD) {
|
||||
Thread t = new Thread(instance);
|
||||
t.start();
|
||||
t.join();
|
||||
} else {
|
||||
instance.run();
|
||||
}
|
||||
}
|
||||
|
||||
private void runTest() {
|
||||
public void run() {
|
||||
Object result;
|
||||
try {
|
||||
result = invoke();
|
||||
result = JVMCI.getRuntime();
|
||||
} catch (InternalError e) {
|
||||
if (IS_POSITIVE) {
|
||||
throw new AssertionError("unexpected exception", e);
|
||||
|
@ -70,28 +85,8 @@ public class JVM_GetJVMCIRuntimeTest {
|
|||
}
|
||||
Asserts.assertNotNull(result,
|
||||
"initializeRuntime returned null");
|
||||
Asserts.assertEQ(result, invoke(),
|
||||
Asserts.assertEQ(result, JVMCI.getRuntime(),
|
||||
"initializeRuntime returns different results");
|
||||
|
||||
}
|
||||
private Object invoke() {
|
||||
Object result;
|
||||
try {
|
||||
result = initializeRuntime.invoke(JVMCI.class);
|
||||
} catch (ReflectiveOperationException e) {
|
||||
throw new Error("can't invoke initializeRuntime", e);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
private JVM_GetJVMCIRuntimeTest() {
|
||||
Method method;
|
||||
try {
|
||||
method = JVMCI.class.getDeclaredMethod("initializeRuntime");
|
||||
method.setAccessible(true);
|
||||
} catch (NoSuchMethodException e) {
|
||||
throw new Error("can't find JVMCI::initializeRuntime", e);
|
||||
}
|
||||
initializeRuntime = method;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -92,6 +92,7 @@ public class CodeInstallationTest {
|
|||
|
||||
asm.emitPrologue();
|
||||
compiler.compile(asm);
|
||||
asm.emitEpilogue();
|
||||
|
||||
HotSpotCompiledCode code = asm.finish(resolvedMethod);
|
||||
InstalledCode installed = codeCache.addCode(resolvedMethod, code, null, null);
|
||||
|
|
|
@ -32,11 +32,13 @@ import jdk.vm.ci.code.CodeCacheProvider;
|
|||
import jdk.vm.ci.code.DebugInfo;
|
||||
import jdk.vm.ci.code.Register;
|
||||
import jdk.vm.ci.code.StackSlot;
|
||||
import jdk.vm.ci.code.site.Call;
|
||||
import jdk.vm.ci.code.site.ConstantReference;
|
||||
import jdk.vm.ci.code.site.DataPatch;
|
||||
import jdk.vm.ci.code.site.DataSectionReference;
|
||||
import jdk.vm.ci.code.site.Infopoint;
|
||||
import jdk.vm.ci.code.site.InfopointReason;
|
||||
import jdk.vm.ci.code.site.Mark;
|
||||
import jdk.vm.ci.code.site.Reference;
|
||||
import jdk.vm.ci.code.site.Site;
|
||||
import jdk.vm.ci.hotspot.HotSpotCompiledCode;
|
||||
|
@ -45,6 +47,7 @@ import jdk.vm.ci.hotspot.HotSpotCompiledNmethod;
|
|||
import jdk.vm.ci.hotspot.HotSpotConstant;
|
||||
import jdk.vm.ci.hotspot.HotSpotResolvedJavaMethod;
|
||||
import jdk.vm.ci.meta.Assumptions.Assumption;
|
||||
import jdk.vm.ci.meta.InvokeTarget;
|
||||
import jdk.vm.ci.meta.LIRKind;
|
||||
import jdk.vm.ci.meta.PlatformKind;
|
||||
import jdk.vm.ci.meta.ResolvedJavaMethod;
|
||||
|
@ -60,6 +63,11 @@ public abstract class TestAssembler {
|
|||
*/
|
||||
public abstract void emitPrologue();
|
||||
|
||||
/**
|
||||
* Emit the method epilogue code (e.g. the deopt handler).
|
||||
*/
|
||||
public abstract void emitEpilogue();
|
||||
|
||||
/**
|
||||
* Emit code to grow the stack frame.
|
||||
*
|
||||
|
@ -181,6 +189,8 @@ public abstract class TestAssembler {
|
|||
private int stackAlignment;
|
||||
private int curStackSlot;
|
||||
|
||||
private StackSlot deoptRescue;
|
||||
|
||||
protected TestAssembler(CodeCacheProvider codeCache, int initialFrameSize, int stackAlignment, PlatformKind narrowOopKind, Register... registers) {
|
||||
this.narrowOopKind = LIRKind.reference(narrowOopKind);
|
||||
|
||||
|
@ -216,6 +226,18 @@ public abstract class TestAssembler {
|
|||
return StackSlot.get(kind, -curStackSlot, true);
|
||||
}
|
||||
|
||||
protected void setDeoptRescueSlot(StackSlot deoptRescue) {
|
||||
this.deoptRescue = deoptRescue;
|
||||
}
|
||||
|
||||
protected void recordCall(InvokeTarget target, int size, boolean direct, DebugInfo debugInfo) {
|
||||
sites.add(new Call(target, code.position(), size, direct, debugInfo));
|
||||
}
|
||||
|
||||
protected void recordMark(Object id) {
|
||||
sites.add(new Mark(code.position(), id));
|
||||
}
|
||||
|
||||
protected void recordImplicitException(DebugInfo info) {
|
||||
sites.add(new Infopoint(code.position(), info, InfopointReason.IMPLICIT_EXCEPTION));
|
||||
}
|
||||
|
@ -249,7 +271,7 @@ public abstract class TestAssembler {
|
|||
byte[] finishedData = data.finish();
|
||||
DataPatch[] finishedDataPatches = dataPatches.toArray(new DataPatch[0]);
|
||||
return new HotSpotCompiledNmethod(method.getName(), finishedCode, finishedCode.length, finishedSites, new Assumption[0], new ResolvedJavaMethod[]{method}, new Comment[0], finishedData, 16,
|
||||
finishedDataPatches, false, frameSize, 0, method, 0, id, 0L, false);
|
||||
finishedDataPatches, false, frameSize, deoptRescue, method, 0, id, 0L, false);
|
||||
}
|
||||
|
||||
protected static class Buffer {
|
||||
|
|
|
@ -33,6 +33,8 @@ import jdk.vm.ci.code.site.ConstantReference;
|
|||
import jdk.vm.ci.code.site.DataSectionReference;
|
||||
import jdk.vm.ci.hotspot.HotSpotCallingConventionType;
|
||||
import jdk.vm.ci.hotspot.HotSpotConstant;
|
||||
import jdk.vm.ci.hotspot.HotSpotForeignCallTarget;
|
||||
import jdk.vm.ci.hotspot.HotSpotVMConfig;
|
||||
import jdk.vm.ci.meta.JavaKind;
|
||||
import jdk.vm.ci.meta.LIRKind;
|
||||
import jdk.vm.ci.meta.VMConstant;
|
||||
|
@ -63,6 +65,16 @@ public class AMD64TestAssembler extends TestAssembler {
|
|||
emitFatNop();
|
||||
code.emitByte(0x50 | AMD64.rbp.encoding); // PUSH rbp
|
||||
emitMove(true, AMD64.rbp, AMD64.rsp); // MOV rbp, rsp
|
||||
setDeoptRescueSlot(newStackSlot(LIRKind.value(AMD64Kind.QWORD)));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void emitEpilogue() {
|
||||
HotSpotVMConfig config = HotSpotVMConfig.config();
|
||||
recordMark(config.MARKID_DEOPT_HANDLER_ENTRY);
|
||||
recordCall(new HotSpotForeignCallTarget(config.handleDeoptStub), 5, true, null);
|
||||
code.emitByte(0xE8); // CALL rel32
|
||||
code.emitInt(0xDEADDEAD);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Add table
Add a link
Reference in a new issue