Merge
This commit is contained in:
commit
9b1628d0b5
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2000, 2014, 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
|
||||
@ -19,32 +19,23 @@
|
||||
* 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.
|
||||
*
|
||||
*/
|
||||
|
||||
/*
|
||||
* @test
|
||||
* @bug 8055289
|
||||
* @library /testlibrary
|
||||
* @build UnsafeMallocLimit
|
||||
* @run main/othervm -Xmx32m -XX:NativeMemoryTracking=summary UnsafeMallocLimit
|
||||
*/
|
||||
package sun.jvm.hotspot.runtime;
|
||||
|
||||
import com.oracle.java.testlibrary.*;
|
||||
import sun.misc.Unsafe;
|
||||
import java.io.*;
|
||||
import java.util.*;
|
||||
import sun.jvm.hotspot.debugger.*;
|
||||
import sun.jvm.hotspot.types.*;
|
||||
|
||||
public class UnsafeMallocLimit {
|
||||
public class CodeCacheSweeperThread extends JavaThread {
|
||||
public CodeCacheSweeperThread(Address addr) {
|
||||
super(addr);
|
||||
}
|
||||
|
||||
public boolean isJavaThread() { return false; }
|
||||
public boolean isHiddenFromExternalView() { return true; }
|
||||
public boolean isCodeCacheSweeperThread() { return true; }
|
||||
|
||||
public static void main(String args[]) throws Exception {
|
||||
if (Platform.is32bit()) {
|
||||
Unsafe unsafe = Utils.getUnsafe();
|
||||
try {
|
||||
unsafe.allocateMemory(1 << 30);
|
||||
throw new RuntimeException("Did not get expected OOME");
|
||||
} catch (OutOfMemoryError e) {
|
||||
// Expected exception
|
||||
}
|
||||
} else {
|
||||
System.out.println("Test only valid on 32-bit platforms");
|
||||
}
|
||||
}
|
||||
}
|
@ -118,9 +118,10 @@ public class JavaThread extends Thread {
|
||||
return VM.getVM().getThreads().createJavaThreadWrapper(threadAddr);
|
||||
}
|
||||
|
||||
/** NOTE: for convenience, this differs in definition from the
|
||||
underlying VM. Only "pure" JavaThreads return true;
|
||||
CompilerThreads and JVMDIDebuggerThreads return false. FIXME:
|
||||
/** NOTE: for convenience, this differs in definition from the underlying VM.
|
||||
Only "pure" JavaThreads return true; CompilerThreads, the CodeCacheSweeperThread,
|
||||
JVMDIDebuggerThreads return false.
|
||||
FIXME:
|
||||
consider encapsulating platform-specific functionality in an
|
||||
object instead of using inheritance (which is the primary reason
|
||||
we can't traverse CompilerThreads, etc; didn't want to have, for
|
||||
|
@ -111,14 +111,15 @@ public class Thread extends VMObject {
|
||||
return allocatedBytesField.getValue(addr);
|
||||
}
|
||||
|
||||
public boolean isVMThread() { return false; }
|
||||
public boolean isJavaThread() { return false; }
|
||||
public boolean isCompilerThread() { return false; }
|
||||
public boolean isHiddenFromExternalView() { return false; }
|
||||
public boolean isJvmtiAgentThread() { return false; }
|
||||
public boolean isWatcherThread() { return false; }
|
||||
public boolean isVMThread() { return false; }
|
||||
public boolean isJavaThread() { return false; }
|
||||
public boolean isCompilerThread() { return false; }
|
||||
public boolean isCodeCacheSweeperThread() { return false; }
|
||||
public boolean isHiddenFromExternalView() { return false; }
|
||||
public boolean isJvmtiAgentThread() { return false; }
|
||||
public boolean isWatcherThread() { return false; }
|
||||
public boolean isConcurrentMarkSweepThread() { return false; }
|
||||
public boolean isServiceThread() { return false; }
|
||||
public boolean isServiceThread() { return false; }
|
||||
|
||||
/** Memory operations */
|
||||
public void oopsDo(AddressVisitor oopVisitor) {
|
||||
|
@ -120,6 +120,7 @@ public class Threads {
|
||||
virtualConstructor.addMapping("JavaThread", JavaThread.class);
|
||||
if (!VM.getVM().isCore()) {
|
||||
virtualConstructor.addMapping("CompilerThread", CompilerThread.class);
|
||||
virtualConstructor.addMapping("CodeCacheSweeperThread", CodeCacheSweeperThread.class);
|
||||
}
|
||||
// for now, use JavaThread itself. fix it later with appropriate class if needed
|
||||
virtualConstructor.addMapping("SurrogateLockerThread", JavaThread.class);
|
||||
@ -164,7 +165,7 @@ public class Threads {
|
||||
return thread;
|
||||
} catch (Exception e) {
|
||||
throw new RuntimeException("Unable to deduce type of thread from address " + threadAddr +
|
||||
" (expected type JavaThread, CompilerThread, ServiceThread, JvmtiAgentThread, or SurrogateLockerThread)", e);
|
||||
" (expected type JavaThread, CompilerThread, ServiceThread, JvmtiAgentThread, SurrogateLockerThread, or CodeCacheSweeperThread)", e);
|
||||
}
|
||||
}
|
||||
|
||||
@ -201,7 +202,7 @@ public class Threads {
|
||||
public List getPendingThreads(ObjectMonitor monitor) {
|
||||
List pendingThreads = new ArrayList();
|
||||
for (JavaThread thread = first(); thread != null; thread = thread.next()) {
|
||||
if (thread.isCompilerThread()) {
|
||||
if (thread.isCompilerThread() || thread.isCodeCacheSweeperThread()) {
|
||||
continue;
|
||||
}
|
||||
ObjectMonitor pending = thread.getCurrentPendingMonitor();
|
||||
|
@ -836,6 +836,7 @@ vmType2Class["InterpreterCodelet"] = sapkg.interpreter.InterpreterCodelet;
|
||||
// Java Threads
|
||||
vmType2Class["JavaThread"] = sapkg.runtime.JavaThread;
|
||||
vmType2Class["CompilerThread"] = sapkg.runtime.CompilerThread;
|
||||
vmType2Class["CodeCacheSweeperThread"] = sapkg.runtime.CodeCacheSweeperThread;
|
||||
vmType2Class["SurrogateLockerThread"] = sapkg.runtime.JavaThread;
|
||||
vmType2Class["DebuggerThread"] = sapkg.runtime.DebuggerThread;
|
||||
|
||||
|
@ -237,7 +237,7 @@ IRT_ENTRY(address, InterpreterRuntime::slow_signature_handler(
|
||||
// handle arguments
|
||||
// Warning: We use reg arg slot 00 temporarily to return the RegArgSignature
|
||||
// back to the code that pops the arguments into the CPU registers
|
||||
SlowSignatureHandler(m, (address)from, m->is_static() ? to+2 : to+1, to).iterate(UCONST64(-1));
|
||||
SlowSignatureHandler(m, (address)from, m->is_static() ? to+2 : to+1, to).iterate((uint64_t)CONST64(-1));
|
||||
// return result handler
|
||||
return Interpreter::result_handler(m->result_type());
|
||||
IRT_END
|
||||
|
@ -2734,12 +2734,12 @@ void MacroAssembler::biased_locking_exit (Address mark_addr, Register temp_reg,
|
||||
// box->dhw disposition - post-conditions at DONE_LABEL.
|
||||
// - Successful inflated lock: box->dhw != 0.
|
||||
// Any non-zero value suffices.
|
||||
// Consider G2_thread, rsp, boxReg, or unused_mark()
|
||||
// Consider G2_thread, rsp, boxReg, or markOopDesc::unused_mark()
|
||||
// - Successful Stack-lock: box->dhw == mark.
|
||||
// box->dhw must contain the displaced mark word value
|
||||
// - Failure -- icc.ZFlag == 0 and box->dhw is undefined.
|
||||
// The slow-path fast_enter() and slow_enter() operators
|
||||
// are responsible for setting box->dhw = NonZero (typically ::unused_mark).
|
||||
// are responsible for setting box->dhw = NonZero (typically markOopDesc::unused_mark()).
|
||||
// - Biased: box->dhw is undefined
|
||||
//
|
||||
// SPARC refworkload performance - specifically jetstream and scimark - are
|
||||
@ -2855,7 +2855,7 @@ void MacroAssembler::compiler_lock_object(Register Roop, Register Rmark,
|
||||
// If m->owner != null goto IsLocked
|
||||
// Pessimistic form: Test-and-CAS vs CAS
|
||||
// The optimistic form avoids RTS->RTO cache line upgrades.
|
||||
ld_ptr(Rmark, ObjectMonitor::owner_offset_in_bytes() - 2, Rscratch);
|
||||
ld_ptr(Rmark, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner), Rscratch);
|
||||
andcc(Rscratch, Rscratch, G0);
|
||||
brx(Assembler::notZero, false, Assembler::pn, done);
|
||||
delayed()->nop();
|
||||
@ -2864,7 +2864,7 @@ void MacroAssembler::compiler_lock_object(Register Roop, Register Rmark,
|
||||
|
||||
// Try to CAS m->owner from null to Self
|
||||
// Invariant: if we acquire the lock then _recursions should be 0.
|
||||
add(Rmark, ObjectMonitor::owner_offset_in_bytes()-2, Rmark);
|
||||
add(Rmark, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner), Rmark);
|
||||
mov(G2_thread, Rscratch);
|
||||
cas_ptr(Rmark, G0, Rscratch);
|
||||
cmp(Rscratch, G0);
|
||||
@ -2948,7 +2948,7 @@ void MacroAssembler::compiler_lock_object(Register Roop, Register Rmark,
|
||||
// Test-and-CAS vs CAS
|
||||
// Pessimistic form avoids futile (doomed) CAS attempts
|
||||
// The optimistic form avoids RTS->RTO cache line upgrades.
|
||||
ld_ptr(Rmark, ObjectMonitor::owner_offset_in_bytes() - 2, Rscratch);
|
||||
ld_ptr(Rmark, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner), Rscratch);
|
||||
andcc(Rscratch, Rscratch, G0);
|
||||
brx(Assembler::notZero, false, Assembler::pn, done);
|
||||
delayed()->nop();
|
||||
@ -2957,13 +2957,13 @@ void MacroAssembler::compiler_lock_object(Register Roop, Register Rmark,
|
||||
|
||||
// Try to CAS m->owner from null to Self
|
||||
// Invariant: if we acquire the lock then _recursions should be 0.
|
||||
add(Rmark, ObjectMonitor::owner_offset_in_bytes()-2, Rmark);
|
||||
add(Rmark, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner), Rmark);
|
||||
mov(G2_thread, Rscratch);
|
||||
cas_ptr(Rmark, G0, Rscratch);
|
||||
cmp(Rscratch, G0);
|
||||
// ST box->displaced_header = NonZero.
|
||||
// Any non-zero value suffices:
|
||||
// unused_mark(), G2_thread, RBox, RScratch, rsp, etc.
|
||||
// markOopDesc::unused_mark(), G2_thread, RBox, RScratch, rsp, etc.
|
||||
st_ptr(Rbox, Rbox, BasicLock::displaced_header_offset_in_bytes());
|
||||
// Intentional fall-through into done
|
||||
}
|
||||
@ -3031,30 +3031,30 @@ void MacroAssembler::compiler_unlock_object(Register Roop, Register Rmark,
|
||||
// Note that we use 1-0 locking by default for the inflated case. We
|
||||
// close the resultant (and rare) race by having contented threads in
|
||||
// monitorenter periodically poll _owner.
|
||||
ld_ptr(Rmark, ObjectMonitor::owner_offset_in_bytes() - 2, Rscratch);
|
||||
ld_ptr(Rmark, ObjectMonitor::recursions_offset_in_bytes() - 2, Rbox);
|
||||
ld_ptr(Rmark, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner), Rscratch);
|
||||
ld_ptr(Rmark, OM_OFFSET_NO_MONITOR_VALUE_TAG(recursions), Rbox);
|
||||
xor3(Rscratch, G2_thread, Rscratch);
|
||||
orcc(Rbox, Rscratch, Rbox);
|
||||
brx(Assembler::notZero, false, Assembler::pn, done);
|
||||
delayed()->
|
||||
ld_ptr(Rmark, ObjectMonitor::EntryList_offset_in_bytes() - 2, Rscratch);
|
||||
ld_ptr(Rmark, ObjectMonitor::cxq_offset_in_bytes() - 2, Rbox);
|
||||
ld_ptr(Rmark, OM_OFFSET_NO_MONITOR_VALUE_TAG(EntryList), Rscratch);
|
||||
ld_ptr(Rmark, OM_OFFSET_NO_MONITOR_VALUE_TAG(cxq), Rbox);
|
||||
orcc(Rbox, Rscratch, G0);
|
||||
if (EmitSync & 65536) {
|
||||
Label LSucc ;
|
||||
brx(Assembler::notZero, false, Assembler::pn, LSucc);
|
||||
delayed()->nop();
|
||||
ba(done);
|
||||
delayed()->st_ptr(G0, Rmark, ObjectMonitor::owner_offset_in_bytes() - 2);
|
||||
delayed()->st_ptr(G0, Rmark, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner));
|
||||
|
||||
bind(LSucc);
|
||||
st_ptr(G0, Rmark, ObjectMonitor::owner_offset_in_bytes() - 2);
|
||||
st_ptr(G0, Rmark, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner));
|
||||
if (os::is_MP()) { membar (StoreLoad); }
|
||||
ld_ptr(Rmark, ObjectMonitor::succ_offset_in_bytes() - 2, Rscratch);
|
||||
ld_ptr(Rmark, OM_OFFSET_NO_MONITOR_VALUE_TAG(succ), Rscratch);
|
||||
andcc(Rscratch, Rscratch, G0);
|
||||
brx(Assembler::notZero, false, Assembler::pt, done);
|
||||
delayed()->andcc(G0, G0, G0);
|
||||
add(Rmark, ObjectMonitor::owner_offset_in_bytes()-2, Rmark);
|
||||
add(Rmark, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner), Rmark);
|
||||
mov(G2_thread, Rscratch);
|
||||
cas_ptr(Rmark, G0, Rscratch);
|
||||
// invert icc.zf and goto done
|
||||
@ -3066,7 +3066,7 @@ void MacroAssembler::compiler_unlock_object(Register Roop, Register Rmark,
|
||||
brx(Assembler::notZero, false, Assembler::pn, done);
|
||||
delayed()->nop();
|
||||
ba(done);
|
||||
delayed()->st_ptr(G0, Rmark, ObjectMonitor::owner_offset_in_bytes() - 2);
|
||||
delayed()->st_ptr(G0, Rmark, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner));
|
||||
}
|
||||
|
||||
bind (LStacked);
|
||||
|
@ -60,10 +60,10 @@ static jlong* double_quadword(jlong *adr, jlong lo, jlong hi) {
|
||||
static jlong fp_signmask_pool[(4+1)*2]; // 4*128bits(data) + 128bits(alignment)
|
||||
|
||||
// Static initialization during VM startup.
|
||||
static jlong *float_signmask_pool = double_quadword(&fp_signmask_pool[1*2], CONST64(0x7FFFFFFF7FFFFFFF), CONST64(0x7FFFFFFF7FFFFFFF));
|
||||
static jlong *double_signmask_pool = double_quadword(&fp_signmask_pool[2*2], CONST64(0x7FFFFFFFFFFFFFFF), CONST64(0x7FFFFFFFFFFFFFFF));
|
||||
static jlong *float_signflip_pool = double_quadword(&fp_signmask_pool[3*2], CONST64(0x8000000080000000), CONST64(0x8000000080000000));
|
||||
static jlong *double_signflip_pool = double_quadword(&fp_signmask_pool[4*2], CONST64(0x8000000000000000), CONST64(0x8000000000000000));
|
||||
static jlong *float_signmask_pool = double_quadword(&fp_signmask_pool[1*2], CONST64(0x7FFFFFFF7FFFFFFF), CONST64(0x7FFFFFFF7FFFFFFF));
|
||||
static jlong *double_signmask_pool = double_quadword(&fp_signmask_pool[2*2], CONST64(0x7FFFFFFFFFFFFFFF), CONST64(0x7FFFFFFFFFFFFFFF));
|
||||
static jlong *float_signflip_pool = double_quadword(&fp_signmask_pool[3*2], (jlong)UCONST64(0x8000000080000000), (jlong)UCONST64(0x8000000080000000));
|
||||
static jlong *double_signflip_pool = double_quadword(&fp_signmask_pool[4*2], (jlong)UCONST64(0x8000000000000000), (jlong)UCONST64(0x8000000000000000));
|
||||
|
||||
|
||||
|
||||
|
@ -1597,7 +1597,7 @@ OopMapSet* Runtime1::generate_code_for(StubID id, StubAssembler* sasm) {
|
||||
__ movl(rdx, 0x80000000);
|
||||
__ xorl(rax, rax);
|
||||
#else
|
||||
__ mov64(rax, CONST64(0x8000000000000000));
|
||||
__ mov64(rax, UCONST64(0x8000000000000000));
|
||||
#endif // _LP64
|
||||
__ jmp(do_return);
|
||||
|
||||
|
@ -135,7 +135,7 @@ IRT_ENTRY(address, InterpreterRuntime::slow_signature_handler(JavaThread* thread
|
||||
methodHandle m(thread, (Method*)method);
|
||||
assert(m->is_native(), "sanity check");
|
||||
// handle arguments
|
||||
SlowSignatureHandler(m, (address)from, to + 1).iterate(UCONST64(-1));
|
||||
SlowSignatureHandler(m, (address)from, to + 1).iterate((uint64_t)CONST64(-1));
|
||||
// return result handler
|
||||
return Interpreter::result_handler(m->result_type());
|
||||
IRT_END
|
||||
|
@ -487,7 +487,7 @@ IRT_ENTRY(address,
|
||||
assert(m->is_native(), "sanity check");
|
||||
|
||||
// handle arguments
|
||||
SlowSignatureHandler(m, (address)from, to + 1).iterate(UCONST64(-1));
|
||||
SlowSignatureHandler(m, (address)from, to + 1).iterate((uint64_t)CONST64(-1));
|
||||
|
||||
// return result handler
|
||||
return Interpreter::result_handler(m->result_type());
|
||||
|
@ -1450,8 +1450,7 @@ void MacroAssembler::rtm_retry_lock_on_abort(Register retry_count_Reg, Register
|
||||
void MacroAssembler::rtm_retry_lock_on_busy(Register retry_count_Reg, Register box_Reg,
|
||||
Register tmp_Reg, Register scr_Reg, Label& retryLabel) {
|
||||
Label SpinLoop, SpinExit, doneRetry;
|
||||
// Clean monitor_value bit to get valid pointer
|
||||
int owner_offset = ObjectMonitor::owner_offset_in_bytes() - markOopDesc::monitor_value;
|
||||
int owner_offset = OM_OFFSET_NO_MONITOR_VALUE_TAG(owner);
|
||||
|
||||
testl(retry_count_Reg, retry_count_Reg);
|
||||
jccb(Assembler::zero, doneRetry);
|
||||
@ -1532,7 +1531,7 @@ void MacroAssembler::rtm_stack_locking(Register objReg, Register tmpReg, Registe
|
||||
// Use RTM for inflating locks
|
||||
// inputs: objReg (object to lock)
|
||||
// boxReg (on-stack box address (displaced header location) - KILLED)
|
||||
// tmpReg (ObjectMonitor address + 2(monitor_value))
|
||||
// tmpReg (ObjectMonitor address + markOopDesc::monitor_value)
|
||||
void MacroAssembler::rtm_inflated_locking(Register objReg, Register boxReg, Register tmpReg,
|
||||
Register scrReg, Register retry_on_busy_count_Reg,
|
||||
Register retry_on_abort_count_Reg,
|
||||
@ -1543,8 +1542,7 @@ void MacroAssembler::rtm_inflated_locking(Register objReg, Register boxReg, Regi
|
||||
assert(tmpReg == rax, "");
|
||||
assert(scrReg == rdx, "");
|
||||
Label L_rtm_retry, L_decrement_retry, L_on_abort;
|
||||
// Clean monitor_value bit to get valid pointer
|
||||
int owner_offset = ObjectMonitor::owner_offset_in_bytes() - markOopDesc::monitor_value;
|
||||
int owner_offset = OM_OFFSET_NO_MONITOR_VALUE_TAG(owner);
|
||||
|
||||
// Without cast to int32_t a movptr will destroy r10 which is typically obj
|
||||
movptr(Address(boxReg, 0), (int32_t)intptr_t(markOopDesc::unused_mark()));
|
||||
@ -1716,7 +1714,7 @@ void MacroAssembler::fast_lock(Register objReg, Register boxReg, Register tmpReg
|
||||
atomic_incl(ExternalAddress((address)counters->total_entry_count_addr()), scrReg);
|
||||
}
|
||||
if (EmitSync & 1) {
|
||||
// set box->dhw = unused_mark (3)
|
||||
// set box->dhw = markOopDesc::unused_mark()
|
||||
// Force all sync thru slow-path: slow_enter() and slow_exit()
|
||||
movptr (Address(boxReg, 0), (int32_t)intptr_t(markOopDesc::unused_mark()));
|
||||
cmpptr (rsp, (int32_t)NULL_WORD);
|
||||
@ -1811,7 +1809,7 @@ void MacroAssembler::fast_lock(Register objReg, Register boxReg, Register tmpReg
|
||||
jmp(DONE_LABEL);
|
||||
|
||||
bind(IsInflated);
|
||||
// The object is inflated. tmpReg contains pointer to ObjectMonitor* + 2(monitor_value)
|
||||
// The object is inflated. tmpReg contains pointer to ObjectMonitor* + markOopDesc::monitor_value
|
||||
|
||||
#if INCLUDE_RTM_OPT
|
||||
// Use the same RTM locking code in 32- and 64-bit VM.
|
||||
@ -1823,25 +1821,10 @@ void MacroAssembler::fast_lock(Register objReg, Register boxReg, Register tmpReg
|
||||
|
||||
#ifndef _LP64
|
||||
// The object is inflated.
|
||||
//
|
||||
// TODO-FIXME: eliminate the ugly use of manifest constants:
|
||||
// Use markOopDesc::monitor_value instead of "2".
|
||||
// use markOop::unused_mark() instead of "3".
|
||||
// The tmpReg value is an objectMonitor reference ORed with
|
||||
// markOopDesc::monitor_value (2). We can either convert tmpReg to an
|
||||
// objectmonitor pointer by masking off the "2" bit or we can just
|
||||
// use tmpReg as an objectmonitor pointer but bias the objectmonitor
|
||||
// field offsets with "-2" to compensate for and annul the low-order tag bit.
|
||||
//
|
||||
// I use the latter as it avoids AGI stalls.
|
||||
// As such, we write "mov r, [tmpReg+OFFSETOF(Owner)-2]"
|
||||
// instead of "mov r, [tmpReg+OFFSETOF(Owner)]".
|
||||
//
|
||||
#define OFFSET_SKEWED(f) ((ObjectMonitor::f ## _offset_in_bytes())-2)
|
||||
|
||||
// boxReg refers to the on-stack BasicLock in the current frame.
|
||||
// We'd like to write:
|
||||
// set box->_displaced_header = markOop::unused_mark(). Any non-0 value suffices.
|
||||
// set box->_displaced_header = markOopDesc::unused_mark(). Any non-0 value suffices.
|
||||
// This is convenient but results a ST-before-CAS penalty. The following CAS suffers
|
||||
// additional latency as we have another ST in the store buffer that must drain.
|
||||
|
||||
@ -1853,7 +1836,7 @@ void MacroAssembler::fast_lock(Register objReg, Register boxReg, Register tmpReg
|
||||
if (os::is_MP()) {
|
||||
lock();
|
||||
}
|
||||
cmpxchgptr(scrReg, Address(boxReg, ObjectMonitor::owner_offset_in_bytes()-2));
|
||||
cmpxchgptr(scrReg, Address(boxReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)));
|
||||
} else
|
||||
if ((EmitSync & 128) == 0) { // avoid ST-before-CAS
|
||||
movptr(scrReg, boxReg);
|
||||
@ -1862,7 +1845,7 @@ void MacroAssembler::fast_lock(Register objReg, Register boxReg, Register tmpReg
|
||||
// Using a prefetchw helps avoid later RTS->RTO upgrades and cache probes
|
||||
if ((EmitSync & 2048) && VM_Version::supports_3dnow_prefetch() && os::is_MP()) {
|
||||
// prefetchw [eax + Offset(_owner)-2]
|
||||
prefetchw(Address(tmpReg, ObjectMonitor::owner_offset_in_bytes()-2));
|
||||
prefetchw(Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)));
|
||||
}
|
||||
|
||||
if ((EmitSync & 64) == 0) {
|
||||
@ -1871,7 +1854,7 @@ void MacroAssembler::fast_lock(Register objReg, Register boxReg, Register tmpReg
|
||||
} else {
|
||||
// Can suffer RTS->RTO upgrades on shared or cold $ lines
|
||||
// Test-And-CAS instead of CAS
|
||||
movptr(tmpReg, Address (tmpReg, ObjectMonitor::owner_offset_in_bytes()-2)); // rax, = m->_owner
|
||||
movptr(tmpReg, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner))); // rax, = m->_owner
|
||||
testptr(tmpReg, tmpReg); // Locked ?
|
||||
jccb (Assembler::notZero, DONE_LABEL);
|
||||
}
|
||||
@ -1887,11 +1870,11 @@ void MacroAssembler::fast_lock(Register objReg, Register boxReg, Register tmpReg
|
||||
if (os::is_MP()) {
|
||||
lock();
|
||||
}
|
||||
cmpxchgptr(scrReg, Address(boxReg, ObjectMonitor::owner_offset_in_bytes()-2));
|
||||
cmpxchgptr(scrReg, Address(boxReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)));
|
||||
movptr(Address(scrReg, 0), 3); // box->_displaced_header = 3
|
||||
jccb (Assembler::notZero, DONE_LABEL);
|
||||
get_thread (scrReg); // beware: clobbers ICCs
|
||||
movptr(Address(boxReg, ObjectMonitor::owner_offset_in_bytes()-2), scrReg);
|
||||
movptr(Address(boxReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)), scrReg);
|
||||
xorptr(boxReg, boxReg); // set icc.ZFlag = 1 to indicate success
|
||||
|
||||
// If the CAS fails we can either retry or pass control to the slow-path.
|
||||
@ -1908,7 +1891,7 @@ void MacroAssembler::fast_lock(Register objReg, Register boxReg, Register tmpReg
|
||||
// Using a prefetchw helps avoid later RTS->RTO upgrades and cache probes
|
||||
if ((EmitSync & 2048) && VM_Version::supports_3dnow_prefetch() && os::is_MP()) {
|
||||
// prefetchw [eax + Offset(_owner)-2]
|
||||
prefetchw(Address(tmpReg, ObjectMonitor::owner_offset_in_bytes()-2));
|
||||
prefetchw(Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)));
|
||||
}
|
||||
|
||||
if ((EmitSync & 64) == 0) {
|
||||
@ -1916,7 +1899,7 @@ void MacroAssembler::fast_lock(Register objReg, Register boxReg, Register tmpReg
|
||||
xorptr (tmpReg, tmpReg);
|
||||
} else {
|
||||
// Can suffer RTS->RTO upgrades on shared or cold $ lines
|
||||
movptr(tmpReg, Address (tmpReg, ObjectMonitor::owner_offset_in_bytes()-2)); // rax, = m->_owner
|
||||
movptr(tmpReg, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner))); // rax, = m->_owner
|
||||
testptr(tmpReg, tmpReg); // Locked ?
|
||||
jccb (Assembler::notZero, DONE_LABEL);
|
||||
}
|
||||
@ -1928,7 +1911,7 @@ void MacroAssembler::fast_lock(Register objReg, Register boxReg, Register tmpReg
|
||||
if (os::is_MP()) {
|
||||
lock();
|
||||
}
|
||||
cmpxchgptr(scrReg, Address(boxReg, ObjectMonitor::owner_offset_in_bytes()-2));
|
||||
cmpxchgptr(scrReg, Address(boxReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)));
|
||||
|
||||
// If the CAS fails we can either retry or pass control to the slow-path.
|
||||
// We use the latter tactic.
|
||||
@ -1951,7 +1934,7 @@ void MacroAssembler::fast_lock(Register objReg, Register boxReg, Register tmpReg
|
||||
movptr(Address(boxReg, 0), (int32_t)intptr_t(markOopDesc::unused_mark()));
|
||||
|
||||
movptr (boxReg, tmpReg);
|
||||
movptr (tmpReg, Address(boxReg, ObjectMonitor::owner_offset_in_bytes()-2));
|
||||
movptr(tmpReg, Address(boxReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)));
|
||||
testptr(tmpReg, tmpReg);
|
||||
jccb (Assembler::notZero, DONE_LABEL);
|
||||
|
||||
@ -1959,7 +1942,7 @@ void MacroAssembler::fast_lock(Register objReg, Register boxReg, Register tmpReg
|
||||
if (os::is_MP()) {
|
||||
lock();
|
||||
}
|
||||
cmpxchgptr(r15_thread, Address(boxReg, ObjectMonitor::owner_offset_in_bytes()-2));
|
||||
cmpxchgptr(r15_thread, Address(boxReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)));
|
||||
// Intentional fall-through into DONE_LABEL ...
|
||||
#endif // _LP64
|
||||
|
||||
@ -2065,8 +2048,7 @@ void MacroAssembler::fast_unlock(Register objReg, Register boxReg, Register tmpR
|
||||
#if INCLUDE_RTM_OPT
|
||||
if (use_rtm) {
|
||||
Label L_regular_inflated_unlock;
|
||||
// Clean monitor_value bit to get valid pointer
|
||||
int owner_offset = ObjectMonitor::owner_offset_in_bytes() - markOopDesc::monitor_value;
|
||||
int owner_offset = OM_OFFSET_NO_MONITOR_VALUE_TAG(owner);
|
||||
movptr(boxReg, Address(tmpReg, owner_offset));
|
||||
testptr(boxReg, boxReg);
|
||||
jccb(Assembler::notZero, L_regular_inflated_unlock);
|
||||
@ -2102,7 +2084,7 @@ void MacroAssembler::fast_unlock(Register objReg, Register boxReg, Register tmpR
|
||||
get_thread (boxReg);
|
||||
if ((EmitSync & 4096) && VM_Version::supports_3dnow_prefetch() && os::is_MP()) {
|
||||
// prefetchw [ebx + Offset(_owner)-2]
|
||||
prefetchw(Address(tmpReg, ObjectMonitor::owner_offset_in_bytes()-2));
|
||||
prefetchw(Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)));
|
||||
}
|
||||
|
||||
// Note that we could employ various encoding schemes to reduce
|
||||
@ -2111,21 +2093,21 @@ void MacroAssembler::fast_unlock(Register objReg, Register boxReg, Register tmpR
|
||||
// In practice the chain of fetches doesn't seem to impact performance, however.
|
||||
if ((EmitSync & 65536) == 0 && (EmitSync & 256)) {
|
||||
// Attempt to reduce branch density - AMD's branch predictor.
|
||||
xorptr(boxReg, Address (tmpReg, ObjectMonitor::owner_offset_in_bytes()-2));
|
||||
orptr(boxReg, Address (tmpReg, ObjectMonitor::recursions_offset_in_bytes()-2));
|
||||
orptr(boxReg, Address (tmpReg, ObjectMonitor::EntryList_offset_in_bytes()-2));
|
||||
orptr(boxReg, Address (tmpReg, ObjectMonitor::cxq_offset_in_bytes()-2));
|
||||
xorptr(boxReg, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)));
|
||||
orptr(boxReg, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(recursions)));
|
||||
orptr(boxReg, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(EntryList)));
|
||||
orptr(boxReg, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(cxq)));
|
||||
jccb (Assembler::notZero, DONE_LABEL);
|
||||
movptr(Address (tmpReg, ObjectMonitor::owner_offset_in_bytes()-2), NULL_WORD);
|
||||
movptr(Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)), NULL_WORD);
|
||||
jmpb (DONE_LABEL);
|
||||
} else {
|
||||
xorptr(boxReg, Address (tmpReg, ObjectMonitor::owner_offset_in_bytes()-2));
|
||||
orptr(boxReg, Address (tmpReg, ObjectMonitor::recursions_offset_in_bytes()-2));
|
||||
xorptr(boxReg, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)));
|
||||
orptr(boxReg, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(recursions)));
|
||||
jccb (Assembler::notZero, DONE_LABEL);
|
||||
movptr(boxReg, Address (tmpReg, ObjectMonitor::EntryList_offset_in_bytes()-2));
|
||||
orptr(boxReg, Address (tmpReg, ObjectMonitor::cxq_offset_in_bytes()-2));
|
||||
movptr(boxReg, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(EntryList)));
|
||||
orptr(boxReg, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(cxq)));
|
||||
jccb (Assembler::notZero, CheckSucc);
|
||||
movptr(Address (tmpReg, ObjectMonitor::owner_offset_in_bytes()-2), NULL_WORD);
|
||||
movptr(Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)), NULL_WORD);
|
||||
jmpb (DONE_LABEL);
|
||||
}
|
||||
|
||||
@ -2143,7 +2125,7 @@ void MacroAssembler::fast_unlock(Register objReg, Register boxReg, Register tmpR
|
||||
|
||||
// Optional pre-test ... it's safe to elide this
|
||||
if ((EmitSync & 16) == 0) {
|
||||
cmpptr(Address (tmpReg, ObjectMonitor::succ_offset_in_bytes()-2), (int32_t)NULL_WORD);
|
||||
cmpptr(Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(succ)), (int32_t)NULL_WORD);
|
||||
jccb (Assembler::zero, LGoSlowPath);
|
||||
}
|
||||
|
||||
@ -2173,7 +2155,7 @@ void MacroAssembler::fast_unlock(Register objReg, Register boxReg, Register tmpR
|
||||
// We currently use (3), although it's likely that switching to (2)
|
||||
// is correct for the future.
|
||||
|
||||
movptr(Address (tmpReg, ObjectMonitor::owner_offset_in_bytes()-2), NULL_WORD);
|
||||
movptr(Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)), NULL_WORD);
|
||||
if (os::is_MP()) {
|
||||
if (VM_Version::supports_sse2() && 1 == FenceInstruction) {
|
||||
mfence();
|
||||
@ -2182,18 +2164,18 @@ void MacroAssembler::fast_unlock(Register objReg, Register boxReg, Register tmpR
|
||||
}
|
||||
}
|
||||
// Ratify _succ remains non-null
|
||||
cmpptr(Address (tmpReg, ObjectMonitor::succ_offset_in_bytes()-2), 0);
|
||||
cmpptr(Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(succ)), 0);
|
||||
jccb (Assembler::notZero, LSuccess);
|
||||
|
||||
xorptr(boxReg, boxReg); // box is really EAX
|
||||
if (os::is_MP()) { lock(); }
|
||||
cmpxchgptr(rsp, Address(tmpReg, ObjectMonitor::owner_offset_in_bytes()-2));
|
||||
cmpxchgptr(rsp, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)));
|
||||
jccb (Assembler::notEqual, LSuccess);
|
||||
// Since we're low on registers we installed rsp as a placeholding in _owner.
|
||||
// Now install Self over rsp. This is safe as we're transitioning from
|
||||
// non-null to non=null
|
||||
get_thread (boxReg);
|
||||
movptr(Address (tmpReg, ObjectMonitor::owner_offset_in_bytes()-2), boxReg);
|
||||
movptr(Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)), boxReg);
|
||||
// Intentional fall-through into LGoSlowPath ...
|
||||
|
||||
bind (LGoSlowPath);
|
||||
@ -2228,36 +2210,36 @@ void MacroAssembler::fast_unlock(Register objReg, Register boxReg, Register tmpR
|
||||
}
|
||||
#else // _LP64
|
||||
// It's inflated
|
||||
movptr(boxReg, Address (tmpReg, ObjectMonitor::owner_offset_in_bytes()-2));
|
||||
movptr(boxReg, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)));
|
||||
xorptr(boxReg, r15_thread);
|
||||
orptr (boxReg, Address (tmpReg, ObjectMonitor::recursions_offset_in_bytes()-2));
|
||||
orptr(boxReg, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(recursions)));
|
||||
jccb (Assembler::notZero, DONE_LABEL);
|
||||
movptr(boxReg, Address (tmpReg, ObjectMonitor::cxq_offset_in_bytes()-2));
|
||||
orptr (boxReg, Address (tmpReg, ObjectMonitor::EntryList_offset_in_bytes()-2));
|
||||
movptr(boxReg, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(cxq)));
|
||||
orptr(boxReg, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(EntryList)));
|
||||
jccb (Assembler::notZero, CheckSucc);
|
||||
movptr(Address (tmpReg, ObjectMonitor::owner_offset_in_bytes()-2), (int32_t)NULL_WORD);
|
||||
movptr(Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)), (int32_t)NULL_WORD);
|
||||
jmpb (DONE_LABEL);
|
||||
|
||||
if ((EmitSync & 65536) == 0) {
|
||||
Label LSuccess, LGoSlowPath ;
|
||||
bind (CheckSucc);
|
||||
cmpptr(Address (tmpReg, ObjectMonitor::succ_offset_in_bytes()-2), (int32_t)NULL_WORD);
|
||||
cmpptr(Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(succ)), (int32_t)NULL_WORD);
|
||||
jccb (Assembler::zero, LGoSlowPath);
|
||||
|
||||
// I'd much rather use lock:andl m->_owner, 0 as it's faster than the
|
||||
// the explicit ST;MEMBAR combination, but masm doesn't currently support
|
||||
// "ANDQ M,IMM". Don't use MFENCE here. lock:add to TOS, xchg, etc
|
||||
// are all faster when the write buffer is populated.
|
||||
movptr (Address (tmpReg, ObjectMonitor::owner_offset_in_bytes()-2), (int32_t)NULL_WORD);
|
||||
movptr(Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)), (int32_t)NULL_WORD);
|
||||
if (os::is_MP()) {
|
||||
lock (); addl (Address(rsp, 0), 0);
|
||||
}
|
||||
cmpptr(Address (tmpReg, ObjectMonitor::succ_offset_in_bytes()-2), (int32_t)NULL_WORD);
|
||||
cmpptr(Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(succ)), (int32_t)NULL_WORD);
|
||||
jccb (Assembler::notZero, LSuccess);
|
||||
|
||||
movptr (boxReg, (int32_t)NULL_WORD); // box is really EAX
|
||||
if (os::is_MP()) { lock(); }
|
||||
cmpxchgptr(r15_thread, Address(tmpReg, ObjectMonitor::owner_offset_in_bytes()-2));
|
||||
cmpxchgptr(r15_thread, Address(tmpReg, OM_OFFSET_NO_MONITOR_VALUE_TAG(owner)));
|
||||
jccb (Assembler::notEqual, LSuccess);
|
||||
// Intentional fall-through into slow-path
|
||||
|
||||
|
@ -155,7 +155,7 @@ IRT_ENTRY(address,
|
||||
|
||||
intptr_t *buf = (intptr_t *) stack->alloc(required_words * wordSize);
|
||||
SlowSignatureHandlerGenerator sshg(methodHandle(thread, method), buf);
|
||||
sshg.generate(UCONST64(-1));
|
||||
sshg.generate((uint64_t)CONST64(-1));
|
||||
|
||||
SignatureHandler *handler = sshg.handler();
|
||||
handler->finalize();
|
||||
|
@ -1641,7 +1641,8 @@ void os::jvm_path(char *buf, jint buflen) {
|
||||
char* rp = realpath((char *)dlinfo.dli_fname, buf);
|
||||
assert(rp != NULL, "error in realpath(): maybe the 'path' argument is too long?");
|
||||
|
||||
strcpy(saved_jvm_path, buf);
|
||||
strncpy(saved_jvm_path, buf, sizeof(saved_jvm_path));
|
||||
saved_jvm_path[sizeof(saved_jvm_path) - 1] = '\0';
|
||||
}
|
||||
|
||||
void os::print_jni_name_prefix_on(outputStream* st, int args_size) {
|
||||
|
@ -506,6 +506,7 @@ static void cleanup_sharedmem_resources(const char* dirname) {
|
||||
|
||||
if (!is_directory_secure(dirname)) {
|
||||
// the directory is not a secure directory
|
||||
os::closedir(dirp);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -853,6 +854,9 @@ static void mmap_attach_shared(const char* user, int vmid, PerfMemory::PerfMemor
|
||||
//
|
||||
if (!is_directory_secure(dirname)) {
|
||||
FREE_C_HEAP_ARRAY(char, dirname, mtInternal);
|
||||
if (luser != user) {
|
||||
FREE_C_HEAP_ARRAY(char, luser, mtInternal);
|
||||
}
|
||||
THROW_MSG(vmSymbols::java_lang_IllegalArgumentException(),
|
||||
"Process not found");
|
||||
}
|
||||
|
@ -1875,6 +1875,7 @@ void os::jvm_path(char *buf, jint buflen) {
|
||||
}
|
||||
|
||||
strncpy(saved_jvm_path, buf, MAXPATHLEN);
|
||||
saved_jvm_path[MAXPATHLEN - 1] = '\0';
|
||||
}
|
||||
|
||||
void os::print_jni_name_prefix_on(outputStream* st, int args_size) {
|
||||
|
@ -506,6 +506,7 @@ static void cleanup_sharedmem_resources(const char* dirname) {
|
||||
|
||||
if (!is_directory_secure(dirname)) {
|
||||
// the directory is not a secure directory
|
||||
os::closedir(dirp);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -872,6 +873,9 @@ static void mmap_attach_shared(const char* user, int vmid, PerfMemory::PerfMemor
|
||||
//
|
||||
if (!is_directory_secure(dirname)) {
|
||||
FREE_C_HEAP_ARRAY(char, dirname, mtInternal);
|
||||
if (luser != user) {
|
||||
FREE_C_HEAP_ARRAY(char, luser, mtInternal);
|
||||
}
|
||||
THROW_MSG(vmSymbols::java_lang_IllegalArgumentException(),
|
||||
"Process not found");
|
||||
}
|
||||
|
@ -355,7 +355,10 @@ void os::init_system_properties_values() {
|
||||
|
||||
// Found the full path to libjvm.so.
|
||||
// Now cut the path to <java_home>/jre if we can.
|
||||
*(strrchr(buf, '/')) = '\0'; // Get rid of /libjvm.so.
|
||||
pslash = strrchr(buf, '/');
|
||||
if (pslash != NULL) {
|
||||
*pslash = '\0'; // Get rid of /libjvm.so.
|
||||
}
|
||||
pslash = strrchr(buf, '/');
|
||||
if (pslash != NULL) {
|
||||
*pslash = '\0'; // Get rid of /{client|server|hotspot}.
|
||||
@ -1194,7 +1197,7 @@ void os::Linux::capture_initial_stack(size_t max_size) {
|
||||
i = 0;
|
||||
if (s) {
|
||||
// Skip blank chars
|
||||
do s++; while (isspace(*s));
|
||||
do { s++; } while (s && isspace(*s));
|
||||
|
||||
#define _UFM UINTX_FORMAT
|
||||
#define _DFM INTX_FORMAT
|
||||
@ -2343,6 +2346,9 @@ void os::jvm_path(char *buf, jint buflen) {
|
||||
|
||||
// Check the current module name "libjvm.so".
|
||||
p = strrchr(buf, '/');
|
||||
if (p == NULL) {
|
||||
return;
|
||||
}
|
||||
assert(strstr(p, "/libjvm") == p, "invalid library name");
|
||||
|
||||
rp = realpath(java_home_var, buf);
|
||||
@ -2376,6 +2382,7 @@ void os::jvm_path(char *buf, jint buflen) {
|
||||
}
|
||||
|
||||
strncpy(saved_jvm_path, buf, MAXPATHLEN);
|
||||
saved_jvm_path[MAXPATHLEN - 1] = '\0';
|
||||
}
|
||||
|
||||
void os::print_jni_name_prefix_on(outputStream* st, int args_size) {
|
||||
@ -5314,7 +5321,7 @@ static jlong slow_thread_cpu_time(Thread *thread, bool user_sys_cpu_time) {
|
||||
if (s == NULL) return -1;
|
||||
|
||||
// Skip blank chars
|
||||
do s++; while (isspace(*s));
|
||||
do { s++; } while (s && isspace(*s));
|
||||
|
||||
count = sscanf(s,"%c %d %d %d %d %d %lu %lu %lu %lu %lu %lu %lu",
|
||||
&cdummy, &idummy, &idummy, &idummy, &idummy, &idummy,
|
||||
|
@ -506,6 +506,7 @@ static void cleanup_sharedmem_resources(const char* dirname) {
|
||||
|
||||
if (!is_directory_secure(dirname)) {
|
||||
// the directory is not a secure directory
|
||||
os::closedir(dirp);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -872,6 +873,9 @@ static void mmap_attach_shared(const char* user, int vmid, PerfMemory::PerfMemor
|
||||
//
|
||||
if (!is_directory_secure(dirname)) {
|
||||
FREE_C_HEAP_ARRAY(char, dirname, mtInternal);
|
||||
if (luser != user) {
|
||||
FREE_C_HEAP_ARRAY(char, luser, mtInternal);
|
||||
}
|
||||
THROW_MSG(vmSymbols::java_lang_IllegalArgumentException(),
|
||||
"Process not found");
|
||||
}
|
||||
|
@ -663,7 +663,10 @@ const char* os::Posix::get_signal_name(int sig, char* out, size_t outlen) {
|
||||
}
|
||||
}
|
||||
|
||||
jio_snprintf(out, outlen, ret);
|
||||
if (out && outlen > 0) {
|
||||
strncpy(out, ret, outlen);
|
||||
out[outlen - 1] = '\0';
|
||||
}
|
||||
return out;
|
||||
}
|
||||
|
||||
|
@ -2221,6 +2221,7 @@ void os::jvm_path(char *buf, jint buflen) {
|
||||
}
|
||||
|
||||
strncpy(saved_jvm_path, buf, MAXPATHLEN);
|
||||
saved_jvm_path[MAXPATHLEN - 1] = '\0';
|
||||
}
|
||||
|
||||
|
||||
|
@ -545,6 +545,7 @@ static void cleanup_sharedmem_resources(const char* dirname) {
|
||||
|
||||
if (!is_directory_secure(dirname)) {
|
||||
// the directory is not a secure directory
|
||||
os::closedir(dirp);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -890,6 +891,9 @@ static void mmap_attach_shared(const char* user, int vmid, PerfMemory::PerfMemor
|
||||
//
|
||||
if (!is_directory_secure(dirname)) {
|
||||
FREE_C_HEAP_ARRAY(char, dirname, mtInternal);
|
||||
if (luser != user) {
|
||||
FREE_C_HEAP_ARRAY(char, luser, mtInternal);
|
||||
}
|
||||
THROW_MSG(vmSymbols::java_lang_IllegalArgumentException(),
|
||||
"Process not found");
|
||||
}
|
||||
|
@ -30,6 +30,7 @@
|
||||
|
||||
#include <windows.h>
|
||||
#include <signal.h> // SIGBREAK
|
||||
#include <stdio.h>
|
||||
|
||||
// The AttachListener thread services a queue of operations. It blocks in the dequeue
|
||||
// function until an operation is enqueued. A client enqueues an operation by creating
|
||||
@ -269,6 +270,7 @@ HANDLE Win32AttachOperation::open_pipe() {
|
||||
if (hPipe != INVALID_HANDLE_VALUE) {
|
||||
// shouldn't happen as there is a pipe created per operation
|
||||
if (::GetLastError() == ERROR_PIPE_BUSY) {
|
||||
::CloseHandle(hPipe);
|
||||
return INVALID_HANDLE_VALUE;
|
||||
}
|
||||
}
|
||||
@ -313,7 +315,8 @@ void Win32AttachOperation::complete(jint result, bufferedStream* result_stream)
|
||||
BOOL fSuccess;
|
||||
|
||||
char msg[32];
|
||||
sprintf(msg, "%d\n", result);
|
||||
_snprintf(msg, sizeof(msg), "%d\n", result);
|
||||
msg[sizeof(msg) - 1] = '\0';
|
||||
|
||||
fSuccess = write_pipe(hPipe, msg, (int)strlen(msg));
|
||||
if (fSuccess) {
|
||||
|
@ -96,7 +96,7 @@
|
||||
#include <vdmdbg.h>
|
||||
|
||||
// for timer info max values which include all bits
|
||||
#define ALL_64_BITS CONST64(0xFFFFFFFFFFFFFFFF)
|
||||
#define ALL_64_BITS CONST64(-1)
|
||||
|
||||
// For DLL loading/load error detection
|
||||
// Values of PE COFF
|
||||
@ -211,6 +211,7 @@ void os::init_system_properties_values() {
|
||||
}
|
||||
strcpy(home_path, home_dir);
|
||||
Arguments::set_java_home(home_path);
|
||||
FREE_C_HEAP_ARRAY(char, home_path, mtInternal);
|
||||
|
||||
dll_path = NEW_C_HEAP_ARRAY(char, strlen(home_dir) + strlen(bin) + 1,
|
||||
mtInternal);
|
||||
@ -220,6 +221,7 @@ void os::init_system_properties_values() {
|
||||
strcpy(dll_path, home_dir);
|
||||
strcat(dll_path, bin);
|
||||
Arguments::set_dll_dir(dll_path);
|
||||
FREE_C_HEAP_ARRAY(char, dll_path, mtInternal);
|
||||
|
||||
if (!set_boot_path('\\', ';')) {
|
||||
return;
|
||||
@ -297,6 +299,9 @@ void os::init_system_properties_values() {
|
||||
char * buf = NEW_C_HEAP_ARRAY(char, len, mtInternal);
|
||||
sprintf(buf, "%s%s", Arguments::get_java_home(), ENDORSED_DIR);
|
||||
Arguments::set_endorsed_dirs(buf);
|
||||
// (Arguments::set_endorsed_dirs() calls SystemProperty::set_value(), which
|
||||
// duplicates the input.)
|
||||
FREE_C_HEAP_ARRAY(char, buf, mtInternal);
|
||||
#undef ENDORSED_DIR
|
||||
}
|
||||
|
||||
@ -1834,6 +1839,7 @@ void os::jvm_path(char *buf, jint buflen) {
|
||||
GetModuleFileName(vm_lib_handle, buf, buflen);
|
||||
}
|
||||
strncpy(saved_jvm_path, buf, MAX_PATH);
|
||||
saved_jvm_path[MAX_PATH - 1] = '\0';
|
||||
}
|
||||
|
||||
|
||||
@ -3746,8 +3752,12 @@ HINSTANCE os::win32::load_Windows_dll(const char* name, char *ebuf,
|
||||
|
||||
// search system directory
|
||||
if ((size = GetSystemDirectory(path, pathLen)) > 0) {
|
||||
strcat(path, "\\");
|
||||
strcat(path, name);
|
||||
if (size >= pathLen) {
|
||||
return NULL; // truncated
|
||||
}
|
||||
if (jio_snprintf(path + size, pathLen - size, "\\%s", name) == -1) {
|
||||
return NULL; // truncated
|
||||
}
|
||||
if ((result = (HINSTANCE)os::dll_load(path, ebuf, ebuflen)) != NULL) {
|
||||
return result;
|
||||
}
|
||||
@ -3755,8 +3765,12 @@ HINSTANCE os::win32::load_Windows_dll(const char* name, char *ebuf,
|
||||
|
||||
// try Windows directory
|
||||
if ((size = GetWindowsDirectory(path, pathLen)) > 0) {
|
||||
strcat(path, "\\");
|
||||
strcat(path, name);
|
||||
if (size >= pathLen) {
|
||||
return NULL; // truncated
|
||||
}
|
||||
if (jio_snprintf(path + size, pathLen - size, "\\%s", name) == -1) {
|
||||
return NULL; // truncated
|
||||
}
|
||||
if ((result = (HINSTANCE)os::dll_load(path, ebuf, ebuflen)) != NULL) {
|
||||
return result;
|
||||
}
|
||||
|
@ -910,7 +910,7 @@ void os::workaround_expand_exec_shield_cs_limit() {
|
||||
*/
|
||||
char* hint = (char*) (Linux::initial_thread_stack_bottom() -
|
||||
((StackYellowPages + StackRedPages + 1) * page_size));
|
||||
char* codebuf = os::reserve_memory(page_size, hint);
|
||||
char* codebuf = os::attempt_reserve_memory_at(page_size, hint);
|
||||
if ( (codebuf == NULL) || (!os::commit_memory(codebuf, page_size, true)) ) {
|
||||
return; // No matter, we tried, best effort.
|
||||
}
|
||||
|
@ -36,8 +36,7 @@
|
||||
#include <dlfcn.h>
|
||||
#include <link.h>
|
||||
|
||||
extern "C" static int PICL_get_l1_data_cache_line_size_helper(picl_nodehdl_t nodeh, void *result);
|
||||
extern "C" static int PICL_get_l2_cache_line_size_helper(picl_nodehdl_t nodeh, void *result);
|
||||
extern "C" static int PICL_visit_cpu_helper(picl_nodehdl_t nodeh, void *result);
|
||||
|
||||
// Functions from the library we need (signatures should match those in picl.h)
|
||||
extern "C" {
|
||||
@ -130,60 +129,74 @@ class PICL {
|
||||
bool is_inconsistent() { return _state == INCONSISTENT; }
|
||||
void set_inconsistent() { _state = INCONSISTENT; }
|
||||
|
||||
static int visit(picl_nodehdl_t nodeh, const char* name, void *arg) {
|
||||
UniqueValueVisitor *state = static_cast<UniqueValueVisitor*>(arg);
|
||||
PICL* picl = state->_picl;
|
||||
assert(!state->is_inconsistent(), "Precondition");
|
||||
void visit(picl_nodehdl_t nodeh, const char* name) {
|
||||
assert(!is_inconsistent(), "Precondition");
|
||||
int curr;
|
||||
if (picl->get_int_property(nodeh, name, &curr) == PICL_SUCCESS) {
|
||||
if (!state->is_assigned()) { // first iteration
|
||||
state->set_value(curr);
|
||||
} else if (curr != state->value()) { // following iterations
|
||||
state->set_inconsistent();
|
||||
if (_picl->get_int_property(nodeh, name, &curr) == PICL_SUCCESS) {
|
||||
if (!is_assigned()) { // first iteration
|
||||
set_value(curr);
|
||||
} else if (curr != value()) { // following iterations
|
||||
set_inconsistent();
|
||||
}
|
||||
}
|
||||
if (state->is_inconsistent()) {
|
||||
}
|
||||
};
|
||||
|
||||
class CPUVisitor {
|
||||
UniqueValueVisitor _l1_visitor;
|
||||
UniqueValueVisitor _l2_visitor;
|
||||
int _limit; // number of times visit() can be run
|
||||
public:
|
||||
CPUVisitor(PICL *picl, int limit) : _l1_visitor(picl), _l2_visitor(picl), _limit(limit) {}
|
||||
static int visit(picl_nodehdl_t nodeh, void *arg) {
|
||||
CPUVisitor *cpu_visitor = static_cast<CPUVisitor*>(arg);
|
||||
UniqueValueVisitor* l1_visitor = cpu_visitor->l1_visitor();
|
||||
UniqueValueVisitor* l2_visitor = cpu_visitor->l2_visitor();
|
||||
if (!l1_visitor->is_inconsistent()) {
|
||||
l1_visitor->visit(nodeh, "l1-dcache-line-size");
|
||||
}
|
||||
if (!l2_visitor->is_inconsistent()) {
|
||||
l2_visitor->visit(nodeh, "l2-cache-line-size");
|
||||
}
|
||||
|
||||
if (l1_visitor->is_inconsistent() && l2_visitor->is_inconsistent()) {
|
||||
return PICL_WALK_TERMINATE;
|
||||
}
|
||||
cpu_visitor->_limit--;
|
||||
if (cpu_visitor->_limit <= 0) {
|
||||
return PICL_WALK_TERMINATE;
|
||||
}
|
||||
return PICL_WALK_CONTINUE;
|
||||
}
|
||||
UniqueValueVisitor* l1_visitor() { return &_l1_visitor; }
|
||||
UniqueValueVisitor* l2_visitor() { return &_l2_visitor; }
|
||||
};
|
||||
|
||||
int _L1_data_cache_line_size;
|
||||
int _L2_cache_line_size;
|
||||
public:
|
||||
static int get_l1_data_cache_line_size(picl_nodehdl_t nodeh, void *state) {
|
||||
return UniqueValueVisitor::visit(nodeh, "l1-dcache-line-size", state);
|
||||
}
|
||||
static int get_l2_cache_line_size(picl_nodehdl_t nodeh, void *state) {
|
||||
return UniqueValueVisitor::visit(nodeh, "l2-cache-line-size", state);
|
||||
static int visit_cpu(picl_nodehdl_t nodeh, void *state) {
|
||||
return CPUVisitor::visit(nodeh, state);
|
||||
}
|
||||
|
||||
PICL() : _L1_data_cache_line_size(0), _L2_cache_line_size(0), _dl_handle(NULL) {
|
||||
PICL(bool is_fujitsu) : _L1_data_cache_line_size(0), _L2_cache_line_size(0), _dl_handle(NULL) {
|
||||
if (!open_library()) {
|
||||
return;
|
||||
}
|
||||
if (_picl_initialize() == PICL_SUCCESS) {
|
||||
picl_nodehdl_t rooth;
|
||||
if (_picl_get_root(&rooth) == PICL_SUCCESS) {
|
||||
UniqueValueVisitor L1_state(this);
|
||||
// Visit all "cpu" class instances
|
||||
_picl_walk_tree_by_class(rooth, "cpu", &L1_state, PICL_get_l1_data_cache_line_size_helper);
|
||||
if (L1_state.is_initial()) { // Still initial, iteration found no values
|
||||
// Try walk all "core" class instances, it might be a Fujitsu machine
|
||||
_picl_walk_tree_by_class(rooth, "core", &L1_state, PICL_get_l1_data_cache_line_size_helper);
|
||||
const char* cpu_class = "cpu";
|
||||
// If it's a Fujitsu machine, it's a "core"
|
||||
if (is_fujitsu) {
|
||||
cpu_class = "core";
|
||||
}
|
||||
if (L1_state.is_assigned()) { // Is there a value?
|
||||
_L1_data_cache_line_size = L1_state.value();
|
||||
CPUVisitor cpu_visitor(this, os::processor_count());
|
||||
_picl_walk_tree_by_class(rooth, cpu_class, &cpu_visitor, PICL_visit_cpu_helper);
|
||||
if (cpu_visitor.l1_visitor()->is_assigned()) { // Is there a value?
|
||||
_L1_data_cache_line_size = cpu_visitor.l1_visitor()->value();
|
||||
}
|
||||
|
||||
UniqueValueVisitor L2_state(this);
|
||||
_picl_walk_tree_by_class(rooth, "cpu", &L2_state, PICL_get_l2_cache_line_size_helper);
|
||||
if (L2_state.is_initial()) {
|
||||
_picl_walk_tree_by_class(rooth, "core", &L2_state, PICL_get_l2_cache_line_size_helper);
|
||||
}
|
||||
if (L2_state.is_assigned()) {
|
||||
_L2_cache_line_size = L2_state.value();
|
||||
if (cpu_visitor.l2_visitor()->is_assigned()) {
|
||||
_L2_cache_line_size = cpu_visitor.l2_visitor()->value();
|
||||
}
|
||||
}
|
||||
_picl_shutdown();
|
||||
@ -195,11 +208,9 @@ public:
|
||||
unsigned int L2_cache_line_size() const { return _L2_cache_line_size; }
|
||||
};
|
||||
|
||||
extern "C" static int PICL_get_l1_data_cache_line_size_helper(picl_nodehdl_t nodeh, void *result) {
|
||||
return PICL::get_l1_data_cache_line_size(nodeh, result);
|
||||
}
|
||||
extern "C" static int PICL_get_l2_cache_line_size_helper(picl_nodehdl_t nodeh, void *result) {
|
||||
return PICL::get_l2_cache_line_size(nodeh, result);
|
||||
|
||||
extern "C" static int PICL_visit_cpu_helper(picl_nodehdl_t nodeh, void *result) {
|
||||
return PICL::visit_cpu(nodeh, result);
|
||||
}
|
||||
|
||||
template<typename FuncType>
|
||||
@ -418,7 +429,7 @@ int VM_Version::platform_features(int features) {
|
||||
}
|
||||
|
||||
// Figure out cache line sizes using PICL
|
||||
PICL picl;
|
||||
PICL picl((features & sparc64_family_m) != 0);
|
||||
_L1_data_cache_line_size = picl.L1_data_cache_line_size();
|
||||
_L2_cache_line_size = picl.L2_cache_line_size();
|
||||
|
||||
|
@ -455,6 +455,7 @@
|
||||
template(object_void_signature, "(Ljava/lang/Object;)V") \
|
||||
template(object_int_signature, "(Ljava/lang/Object;)I") \
|
||||
template(object_boolean_signature, "(Ljava/lang/Object;)Z") \
|
||||
template(object_object_signature, "(Ljava/lang/Object;)Ljava/lang/Object;") \
|
||||
template(string_void_signature, "(Ljava/lang/String;)V") \
|
||||
template(string_int_signature, "(Ljava/lang/String;)I") \
|
||||
template(throwable_void_signature, "(Ljava/lang/Throwable;)V") \
|
||||
@ -746,6 +747,8 @@
|
||||
do_name( isPrimitive_name, "isPrimitive") \
|
||||
do_intrinsic(_getSuperclass, java_lang_Class, getSuperclass_name, void_class_signature, F_RN) \
|
||||
do_name( getSuperclass_name, "getSuperclass") \
|
||||
do_intrinsic(_Class_cast, java_lang_Class, Class_cast_name, object_object_signature, F_R) \
|
||||
do_name( Class_cast_name, "cast") \
|
||||
\
|
||||
do_intrinsic(_getClassAccessFlags, sun_reflect_Reflection, getClassAccessFlags_name, class_int_signature, F_SN) \
|
||||
do_name( getClassAccessFlags_name, "getClassAccessFlags") \
|
||||
|
@ -714,12 +714,19 @@ void MetaspaceShared::preload_and_dump(TRAPS) {
|
||||
int class_list_path_len = (int)strlen(class_list_path_str);
|
||||
if (class_list_path_len >= 3) {
|
||||
if (strcmp(class_list_path_str + class_list_path_len - 3, "lib") != 0) {
|
||||
strcat(class_list_path_str, os::file_separator());
|
||||
strcat(class_list_path_str, "lib");
|
||||
if (class_list_path_len < JVM_MAXPATHLEN - 4) {
|
||||
jio_snprintf(class_list_path_str + class_list_path_len,
|
||||
sizeof(class_list_path_str) - class_list_path_len,
|
||||
"%slib", os::file_separator());
|
||||
class_list_path_len += 4;
|
||||
}
|
||||
}
|
||||
}
|
||||
strcat(class_list_path_str, os::file_separator());
|
||||
strcat(class_list_path_str, "classlist");
|
||||
if (class_list_path_len < JVM_MAXPATHLEN - 10) {
|
||||
jio_snprintf(class_list_path_str + class_list_path_len,
|
||||
sizeof(class_list_path_str) - class_list_path_len,
|
||||
"%sclasslist", os::file_separator());
|
||||
}
|
||||
class_list_path = class_list_path_str;
|
||||
} else {
|
||||
class_list_path = SharedClassListFile;
|
||||
|
@ -277,7 +277,7 @@ public:
|
||||
bool has_stackmap_table() const { return _stackmap_data != NULL; }
|
||||
|
||||
void init_fingerprint() {
|
||||
const uint64_t initval = CONST64(0x8000000000000000);
|
||||
const uint64_t initval = UCONST64(0x8000000000000000);
|
||||
_fingerprint = initval;
|
||||
}
|
||||
|
||||
|
@ -1730,6 +1730,25 @@ jmethodID InstanceKlass::get_jmethod_id(instanceKlassHandle ik_h, methodHandle m
|
||||
return id;
|
||||
}
|
||||
|
||||
// Figure out how many jmethodIDs haven't been allocated, and make
|
||||
// sure space for them is pre-allocated. This makes getting all
|
||||
// method ids much, much faster with classes with more than 8
|
||||
// methods, and has a *substantial* effect on performance with jvmti
|
||||
// code that loads all jmethodIDs for all classes.
|
||||
void InstanceKlass::ensure_space_for_methodids(int start_offset) {
|
||||
int new_jmeths = 0;
|
||||
int length = methods()->length();
|
||||
for (int index = start_offset; index < length; index++) {
|
||||
Method* m = methods()->at(index);
|
||||
jmethodID id = m->find_jmethod_id_or_null();
|
||||
if (id == NULL) {
|
||||
new_jmeths++;
|
||||
}
|
||||
}
|
||||
if (new_jmeths != 0) {
|
||||
Method::ensure_jmethod_ids(class_loader_data(), new_jmeths);
|
||||
}
|
||||
}
|
||||
|
||||
// Common code to fetch the jmethodID from the cache or update the
|
||||
// cache with the new jmethodID. This function should never do anything
|
||||
@ -2499,7 +2518,7 @@ const char* InstanceKlass::signature_name() const {
|
||||
// If this is an anonymous class, append a hash to make the name unique
|
||||
if (is_anonymous()) {
|
||||
intptr_t hash = (java_mirror() != NULL) ? java_mirror()->identity_hash() : 0;
|
||||
sprintf(hash_buf, "/" UINTX_FORMAT, (uintx)hash);
|
||||
jio_snprintf(hash_buf, sizeof(hash_buf), "/" UINTX_FORMAT, (uintx)hash);
|
||||
hash_len = (int)strlen(hash_buf);
|
||||
}
|
||||
|
||||
|
@ -698,6 +698,7 @@ class InstanceKlass: public Klass {
|
||||
jmethodID** to_dealloc_jmeths_p);
|
||||
static void get_jmethod_id_length_value(jmethodID* cache, size_t idnum,
|
||||
size_t *length_p, jmethodID* id_p);
|
||||
void ensure_space_for_methodids(int start_offset = 0);
|
||||
jmethodID jmethod_id_or_null(Method* method);
|
||||
|
||||
// annotations support
|
||||
|
@ -1318,6 +1318,10 @@ void Method::init_intrinsic_id() {
|
||||
vmIntrinsics::ID id = vmIntrinsics::find_id(klass_id, name_id, sig_id, flags);
|
||||
if (id != vmIntrinsics::_none) {
|
||||
set_intrinsic_id(id);
|
||||
if (id == vmIntrinsics::_Class_cast) {
|
||||
// Even if the intrinsic is rejected, we want to inline this simple method.
|
||||
set_force_inline(true);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
@ -1727,59 +1731,98 @@ void BreakpointInfo::clear(Method* method) {
|
||||
// jmethodID handling
|
||||
|
||||
// This is a block allocating object, sort of like JNIHandleBlock, only a
|
||||
// lot simpler. There aren't many of these, they aren't long, they are rarely
|
||||
// deleted and so we can do some suboptimal things.
|
||||
// lot simpler.
|
||||
// It's allocated on the CHeap because once we allocate a jmethodID, we can
|
||||
// never get rid of it.
|
||||
// It would be nice to be able to parameterize the number of methods for
|
||||
// the null_class_loader but then we'd have to turn this and ClassLoaderData
|
||||
// into templates.
|
||||
|
||||
// I feel like this brain dead class should exist somewhere in the STL
|
||||
static const int min_block_size = 8;
|
||||
|
||||
class JNIMethodBlockNode : public CHeapObj<mtClass> {
|
||||
friend class JNIMethodBlock;
|
||||
Method** _methods;
|
||||
int _number_of_methods;
|
||||
int _top;
|
||||
JNIMethodBlockNode* _next;
|
||||
|
||||
public:
|
||||
|
||||
JNIMethodBlockNode(int num_methods = min_block_size);
|
||||
|
||||
~JNIMethodBlockNode() { FREE_C_HEAP_ARRAY(Method*, _methods, mtInternal); }
|
||||
|
||||
void ensure_methods(int num_addl_methods) {
|
||||
if (_top < _number_of_methods) {
|
||||
num_addl_methods -= _number_of_methods - _top;
|
||||
if (num_addl_methods <= 0) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
if (_next == NULL) {
|
||||
_next = new JNIMethodBlockNode(MAX2(num_addl_methods, min_block_size));
|
||||
} else {
|
||||
_next->ensure_methods(num_addl_methods);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
class JNIMethodBlock : public CHeapObj<mtClass> {
|
||||
enum { number_of_methods = 8 };
|
||||
|
||||
Method* _methods[number_of_methods];
|
||||
int _top;
|
||||
JNIMethodBlock* _next;
|
||||
JNIMethodBlockNode _head;
|
||||
JNIMethodBlockNode *_last_free;
|
||||
public:
|
||||
static Method* const _free_method;
|
||||
|
||||
JNIMethodBlock() : _next(NULL), _top(0) {
|
||||
for (int i = 0; i< number_of_methods; i++) _methods[i] = _free_method;
|
||||
JNIMethodBlock(int initial_capacity = min_block_size)
|
||||
: _head(initial_capacity), _last_free(&_head) {}
|
||||
|
||||
void ensure_methods(int num_addl_methods) {
|
||||
_last_free->ensure_methods(num_addl_methods);
|
||||
}
|
||||
|
||||
Method** add_method(Method* m) {
|
||||
if (_top < number_of_methods) {
|
||||
// top points to the next free entry.
|
||||
int i = _top;
|
||||
_methods[i] = m;
|
||||
_top++;
|
||||
return &_methods[i];
|
||||
} else if (_top == number_of_methods) {
|
||||
// if the next free entry ran off the block see if there's a free entry
|
||||
for (int i = 0; i< number_of_methods; i++) {
|
||||
if (_methods[i] == _free_method) {
|
||||
_methods[i] = m;
|
||||
return &_methods[i];
|
||||
for (JNIMethodBlockNode* b = _last_free; b != NULL; b = b->_next) {
|
||||
if (b->_top < b->_number_of_methods) {
|
||||
// top points to the next free entry.
|
||||
int i = b->_top;
|
||||
b->_methods[i] = m;
|
||||
b->_top++;
|
||||
_last_free = b;
|
||||
return &(b->_methods[i]);
|
||||
} else if (b->_top == b->_number_of_methods) {
|
||||
// if the next free entry ran off the block see if there's a free entry
|
||||
for (int i = 0; i < b->_number_of_methods; i++) {
|
||||
if (b->_methods[i] == _free_method) {
|
||||
b->_methods[i] = m;
|
||||
_last_free = b;
|
||||
return &(b->_methods[i]);
|
||||
}
|
||||
}
|
||||
// Only check each block once for frees. They're very unlikely.
|
||||
// Increment top past the end of the block.
|
||||
b->_top++;
|
||||
}
|
||||
// need to allocate a next block.
|
||||
if (b->_next == NULL) {
|
||||
b->_next = _last_free = new JNIMethodBlockNode();
|
||||
}
|
||||
// Only check each block once for frees. They're very unlikely.
|
||||
// Increment top past the end of the block.
|
||||
_top++;
|
||||
}
|
||||
// need to allocate a next block.
|
||||
if (_next == NULL) {
|
||||
_next = new JNIMethodBlock();
|
||||
}
|
||||
return _next->add_method(m);
|
||||
guarantee(false, "Should always allocate a free block");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
bool contains(Method** m) {
|
||||
for (JNIMethodBlock* b = this; b != NULL; b = b->_next) {
|
||||
for (int i = 0; i< number_of_methods; i++) {
|
||||
if (&(b->_methods[i]) == m) {
|
||||
if (m == NULL) return false;
|
||||
for (JNIMethodBlockNode* b = &_head; b != NULL; b = b->_next) {
|
||||
if (b->_methods <= m && m < b->_methods + b->_number_of_methods) {
|
||||
// This is a bit of extra checking, for two reasons. One is
|
||||
// that contains() deals with pointers that are passed in by
|
||||
// JNI code, so making sure that the pointer is aligned
|
||||
// correctly is valuable. The other is that <= and > are
|
||||
// technically not defined on pointers, so the if guard can
|
||||
// pass spuriously; no modern compiler is likely to make that
|
||||
// a problem, though (and if one did, the guard could also
|
||||
// fail spuriously, which would be bad).
|
||||
ptrdiff_t idx = m - b->_methods;
|
||||
if (b->_methods + idx == m) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@ -1798,9 +1841,9 @@ class JNIMethodBlock : public CHeapObj<mtClass> {
|
||||
// During class unloading the methods are cleared, which is different
|
||||
// than freed.
|
||||
void clear_all_methods() {
|
||||
for (JNIMethodBlock* b = this; b != NULL; b = b->_next) {
|
||||
for (int i = 0; i< number_of_methods; i++) {
|
||||
_methods[i] = NULL;
|
||||
for (JNIMethodBlockNode* b = &_head; b != NULL; b = b->_next) {
|
||||
for (int i = 0; i< b->_number_of_methods; i++) {
|
||||
b->_methods[i] = NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1808,9 +1851,9 @@ class JNIMethodBlock : public CHeapObj<mtClass> {
|
||||
int count_methods() {
|
||||
// count all allocated methods
|
||||
int count = 0;
|
||||
for (JNIMethodBlock* b = this; b != NULL; b = b->_next) {
|
||||
for (int i = 0; i< number_of_methods; i++) {
|
||||
if (_methods[i] != _free_method) count++;
|
||||
for (JNIMethodBlockNode* b = &_head; b != NULL; b = b->_next) {
|
||||
for (int i = 0; i< b->_number_of_methods; i++) {
|
||||
if (b->_methods[i] != _free_method) count++;
|
||||
}
|
||||
}
|
||||
return count;
|
||||
@ -1821,6 +1864,36 @@ class JNIMethodBlock : public CHeapObj<mtClass> {
|
||||
// Something that can't be mistaken for an address or a markOop
|
||||
Method* const JNIMethodBlock::_free_method = (Method*)55;
|
||||
|
||||
JNIMethodBlockNode::JNIMethodBlockNode(int num_methods) : _next(NULL), _top(0) {
|
||||
_number_of_methods = MAX2(num_methods, min_block_size);
|
||||
_methods = NEW_C_HEAP_ARRAY(Method*, _number_of_methods, mtInternal);
|
||||
for (int i = 0; i < _number_of_methods; i++) {
|
||||
_methods[i] = JNIMethodBlock::_free_method;
|
||||
}
|
||||
}
|
||||
|
||||
void Method::ensure_jmethod_ids(ClassLoaderData* loader_data, int capacity) {
|
||||
ClassLoaderData* cld = loader_data;
|
||||
if (!SafepointSynchronize::is_at_safepoint()) {
|
||||
// Have to add jmethod_ids() to class loader data thread-safely.
|
||||
// Also have to add the method to the list safely, which the cld lock
|
||||
// protects as well.
|
||||
MutexLockerEx ml(cld->metaspace_lock(), Mutex::_no_safepoint_check_flag);
|
||||
if (cld->jmethod_ids() == NULL) {
|
||||
cld->set_jmethod_ids(new JNIMethodBlock(capacity));
|
||||
} else {
|
||||
cld->jmethod_ids()->ensure_methods(capacity);
|
||||
}
|
||||
} else {
|
||||
// At safepoint, we are single threaded and can set this.
|
||||
if (cld->jmethod_ids() == NULL) {
|
||||
cld->set_jmethod_ids(new JNIMethodBlock(capacity));
|
||||
} else {
|
||||
cld->jmethod_ids()->ensure_methods(capacity);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Add a method id to the jmethod_ids
|
||||
jmethodID Method::make_jmethod_id(ClassLoaderData* loader_data, Method* m) {
|
||||
ClassLoaderData* cld = loader_data;
|
||||
|
@ -729,6 +729,11 @@ class Method : public Metadata {
|
||||
static jmethodID make_jmethod_id(ClassLoaderData* loader_data, Method* mh);
|
||||
static void destroy_jmethod_id(ClassLoaderData* loader_data, jmethodID mid);
|
||||
|
||||
// Ensure there is enough capacity in the internal tracking data
|
||||
// structures to hold the number of jmethodIDs you plan to generate.
|
||||
// This saves substantial time doing allocations.
|
||||
static void ensure_jmethod_ids(ClassLoaderData* loader_data, int capacity);
|
||||
|
||||
// Use resolve_jmethod_id() in situations where the caller is expected
|
||||
// to provide a valid jmethodID; the only sanity checks are in asserts;
|
||||
// result guaranteed not to be NULL.
|
||||
|
@ -464,9 +464,7 @@ Node* PhaseCFG::select(Block* block, Node_List &worklist, GrowableArray<int> &re
|
||||
iop == Op_CreateEx || // Create-exception must start block
|
||||
iop == Op_CheckCastPP
|
||||
) {
|
||||
// select the node n
|
||||
// remove n from worklist and retain the order of remaining nodes
|
||||
worklist.remove((uint)i);
|
||||
worklist.map(i,worklist.pop());
|
||||
return n;
|
||||
}
|
||||
|
||||
@ -552,9 +550,7 @@ Node* PhaseCFG::select(Block* block, Node_List &worklist, GrowableArray<int> &re
|
||||
assert(idx >= 0, "index should be set");
|
||||
Node *n = worklist[(uint)idx]; // Get the winner
|
||||
|
||||
// select the node n
|
||||
// remove n from worklist and retain the order of remaining nodes
|
||||
worklist.remove((uint)idx);
|
||||
worklist.map((uint)idx, worklist.pop()); // Compress worklist
|
||||
return n;
|
||||
}
|
||||
|
||||
|
@ -268,6 +268,7 @@ class LibraryCallKit : public GraphKit {
|
||||
bool inline_fp_conversions(vmIntrinsics::ID id);
|
||||
bool inline_number_methods(vmIntrinsics::ID id);
|
||||
bool inline_reference_get();
|
||||
bool inline_Class_cast();
|
||||
bool inline_aescrypt_Block(vmIntrinsics::ID id);
|
||||
bool inline_cipherBlockChaining_AESCrypt(vmIntrinsics::ID id);
|
||||
Node* inline_cipherBlockChaining_AESCrypt_predicate(bool decrypting);
|
||||
@ -869,6 +870,8 @@ bool LibraryCallKit::try_to_inline(int predicate) {
|
||||
|
||||
case vmIntrinsics::_Reference_get: return inline_reference_get();
|
||||
|
||||
case vmIntrinsics::_Class_cast: return inline_Class_cast();
|
||||
|
||||
case vmIntrinsics::_aescrypt_encryptBlock:
|
||||
case vmIntrinsics::_aescrypt_decryptBlock: return inline_aescrypt_Block(intrinsic_id());
|
||||
|
||||
@ -3546,6 +3549,89 @@ bool LibraryCallKit::inline_native_Class_query(vmIntrinsics::ID id) {
|
||||
return true;
|
||||
}
|
||||
|
||||
//-------------------------inline_Class_cast-------------------
|
||||
bool LibraryCallKit::inline_Class_cast() {
|
||||
Node* mirror = argument(0); // Class
|
||||
Node* obj = argument(1);
|
||||
const TypeInstPtr* mirror_con = _gvn.type(mirror)->isa_instptr();
|
||||
if (mirror_con == NULL) {
|
||||
return false; // dead path (mirror->is_top()).
|
||||
}
|
||||
if (obj == NULL || obj->is_top()) {
|
||||
return false; // dead path
|
||||
}
|
||||
const TypeOopPtr* tp = _gvn.type(obj)->isa_oopptr();
|
||||
|
||||
// First, see if Class.cast() can be folded statically.
|
||||
// java_mirror_type() returns non-null for compile-time Class constants.
|
||||
ciType* tm = mirror_con->java_mirror_type();
|
||||
if (tm != NULL && tm->is_klass() &&
|
||||
tp != NULL && tp->klass() != NULL) {
|
||||
if (!tp->klass()->is_loaded()) {
|
||||
// Don't use intrinsic when class is not loaded.
|
||||
return false;
|
||||
} else {
|
||||
int static_res = C->static_subtype_check(tm->as_klass(), tp->klass());
|
||||
if (static_res == Compile::SSC_always_true) {
|
||||
// isInstance() is true - fold the code.
|
||||
set_result(obj);
|
||||
return true;
|
||||
} else if (static_res == Compile::SSC_always_false) {
|
||||
// Don't use intrinsic, have to throw ClassCastException.
|
||||
// If the reference is null, the non-intrinsic bytecode will
|
||||
// be optimized appropriately.
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Bailout intrinsic and do normal inlining if exception path is frequent.
|
||||
if (too_many_traps(Deoptimization::Reason_intrinsic)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Generate dynamic checks.
|
||||
// Class.cast() is java implementation of _checkcast bytecode.
|
||||
// Do checkcast (Parse::do_checkcast()) optimizations here.
|
||||
|
||||
mirror = null_check(mirror);
|
||||
// If mirror is dead, only null-path is taken.
|
||||
if (stopped()) {
|
||||
return true;
|
||||
}
|
||||
|
||||
// Not-subtype or the mirror's klass ptr is NULL (in case it is a primitive).
|
||||
enum { _bad_type_path = 1, _prim_path = 2, PATH_LIMIT };
|
||||
RegionNode* region = new RegionNode(PATH_LIMIT);
|
||||
record_for_igvn(region);
|
||||
|
||||
// Now load the mirror's klass metaobject, and null-check it.
|
||||
// If kls is null, we have a primitive mirror and
|
||||
// nothing is an instance of a primitive type.
|
||||
Node* kls = load_klass_from_mirror(mirror, false, region, _prim_path);
|
||||
|
||||
Node* res = top();
|
||||
if (!stopped()) {
|
||||
Node* bad_type_ctrl = top();
|
||||
// Do checkcast optimizations.
|
||||
res = gen_checkcast(obj, kls, &bad_type_ctrl);
|
||||
region->init_req(_bad_type_path, bad_type_ctrl);
|
||||
}
|
||||
if (region->in(_prim_path) != top() ||
|
||||
region->in(_bad_type_path) != top()) {
|
||||
// Let Interpreter throw ClassCastException.
|
||||
PreserveJVMState pjvms(this);
|
||||
set_control(_gvn.transform(region));
|
||||
uncommon_trap(Deoptimization::Reason_intrinsic,
|
||||
Deoptimization::Action_maybe_recompile);
|
||||
}
|
||||
if (!stopped()) {
|
||||
set_result(res);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
//--------------------------inline_native_subtype_check------------------------
|
||||
// This intrinsic takes the JNI calls out of the heart of
|
||||
// UnsafeFieldAccessorImpl.set, which improves Field.set, readObject, etc.
|
||||
@ -4611,6 +4697,10 @@ bool LibraryCallKit::inline_arraycopy() {
|
||||
Node* dest_offset = argument(3); // type: int
|
||||
Node* length = argument(4); // type: int
|
||||
|
||||
// Check for allocation before we add nodes that would confuse
|
||||
// tightly_coupled_allocation()
|
||||
AllocateArrayNode* alloc = tightly_coupled_allocation(dest, NULL);
|
||||
|
||||
// The following tests must be performed
|
||||
// (1) src and dest are arrays.
|
||||
// (2) src and dest arrays must have elements of the same BasicType
|
||||
@ -4784,7 +4874,6 @@ bool LibraryCallKit::inline_arraycopy() {
|
||||
return true;
|
||||
}
|
||||
|
||||
AllocateArrayNode* alloc = tightly_coupled_allocation(dest, NULL);
|
||||
ArrayCopyNode* ac = ArrayCopyNode::make(this, true, src, src_offset, dest, dest_offset, length, alloc != NULL,
|
||||
// Create LoadRange and LoadKlass nodes for use during macro expansion here
|
||||
// so the compiler has a chance to eliminate them: during macro expansion,
|
||||
|
@ -610,7 +610,7 @@ Node *AndLNode::Ideal(PhaseGVN *phase, bool can_reshape) {
|
||||
// convert masks which would cause a sign extension of the integer
|
||||
// value. This check includes UI2L masks (0x00000000FFFFFFFF) which
|
||||
// would be optimized away later in Identity.
|
||||
if (op == Op_ConvI2L && (mask & CONST64(0xFFFFFFFF80000000)) == 0) {
|
||||
if (op == Op_ConvI2L && (mask & UCONST64(0xFFFFFFFF80000000)) == 0) {
|
||||
Node* andi = new AndINode(in1->in(1), phase->intcon(mask));
|
||||
andi = phase->transform(andi);
|
||||
return new ConvI2LNode(andi);
|
||||
|
@ -951,8 +951,9 @@ class JNI_ArgumentPusherVaArg : public JNI_ArgumentPusher {
|
||||
|
||||
// Optimized path if we have the bitvector form of signature
|
||||
void iterate( uint64_t fingerprint ) {
|
||||
if ( fingerprint == UCONST64(-1) ) SignatureIterator::iterate();// Must be too many arguments
|
||||
else {
|
||||
if (fingerprint == (uint64_t)CONST64(-1)) {
|
||||
SignatureIterator::iterate(); // Must be too many arguments
|
||||
} else {
|
||||
_return_type = (BasicType)((fingerprint >> static_feature_size) &
|
||||
result_feature_mask);
|
||||
|
||||
@ -1022,8 +1023,9 @@ class JNI_ArgumentPusherArray : public JNI_ArgumentPusher {
|
||||
|
||||
// Optimized path if we have the bitvector form of signature
|
||||
void iterate( uint64_t fingerprint ) {
|
||||
if ( fingerprint == UCONST64(-1) ) SignatureIterator::iterate(); // Must be too many arguments
|
||||
else {
|
||||
if (fingerprint == (uint64_t)CONST64(-1)) {
|
||||
SignatureIterator::iterate(); // Must be too many arguments
|
||||
} else {
|
||||
_return_type = (BasicType)((fingerprint >> static_feature_size) &
|
||||
result_feature_mask);
|
||||
assert(fingerprint, "Fingerprint should not be 0");
|
||||
|
@ -2583,7 +2583,14 @@ ATTRIBUTE_PRINTF(3, 0)
|
||||
int jio_vsnprintf(char *str, size_t count, const char *fmt, va_list args) {
|
||||
// see bug 4399518, 4417214
|
||||
if ((intptr_t)count <= 0) return -1;
|
||||
return vsnprintf(str, count, fmt, args);
|
||||
|
||||
int result = vsnprintf(str, count, fmt, args);
|
||||
if ((result > 0 && (size_t)result >= count) || result == -1) {
|
||||
str[count - 1] = '\0';
|
||||
result = -1;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
ATTRIBUTE_PRINTF(3, 0)
|
||||
|
@ -2263,6 +2263,8 @@ JvmtiEnv::GetClassMethods(oop k_mirror, jint* method_count_ptr, jmethodID** meth
|
||||
int result_length = instanceK_h->methods()->length();
|
||||
jmethodID* result_list = (jmethodID*)jvmtiMalloc(result_length * sizeof(jmethodID));
|
||||
int index;
|
||||
bool jmethodids_found = true;
|
||||
|
||||
if (JvmtiExport::can_maintain_original_method_order()) {
|
||||
// Use the original method ordering indices stored in the class, so we can emit
|
||||
// jmethodIDs in the order they appeared in the class file
|
||||
@ -2270,14 +2272,40 @@ JvmtiEnv::GetClassMethods(oop k_mirror, jint* method_count_ptr, jmethodID** meth
|
||||
Method* m = instanceK_h->methods()->at(index);
|
||||
int original_index = instanceK_h->method_ordering()->at(index);
|
||||
assert(original_index >= 0 && original_index < result_length, "invalid original method index");
|
||||
jmethodID id = m->jmethod_id();
|
||||
jmethodID id;
|
||||
if (jmethodids_found) {
|
||||
id = m->find_jmethod_id_or_null();
|
||||
if (id == NULL) {
|
||||
// If we find an uninitialized value, make sure there is
|
||||
// enough space for all the uninitialized values we might
|
||||
// find.
|
||||
instanceK_h->ensure_space_for_methodids(index);
|
||||
jmethodids_found = false;
|
||||
id = m->jmethod_id();
|
||||
}
|
||||
} else {
|
||||
id = m->jmethod_id();
|
||||
}
|
||||
result_list[original_index] = id;
|
||||
}
|
||||
} else {
|
||||
// otherwise just copy in any order
|
||||
for (index = 0; index < result_length; index++) {
|
||||
Method* m = instanceK_h->methods()->at(index);
|
||||
jmethodID id = m->jmethod_id();
|
||||
jmethodID id;
|
||||
if (jmethodids_found) {
|
||||
id = m->find_jmethod_id_or_null();
|
||||
if (id == NULL) {
|
||||
// If we find an uninitialized value, make sure there is
|
||||
// enough space for all the uninitialized values we might
|
||||
// find.
|
||||
instanceK_h->ensure_space_for_methodids(index);
|
||||
jmethodids_found = false;
|
||||
id = m->jmethod_id();
|
||||
}
|
||||
} else {
|
||||
id = m->jmethod_id();
|
||||
}
|
||||
result_list[index] = id;
|
||||
}
|
||||
}
|
||||
|
@ -802,8 +802,7 @@ UNSAFE_END
|
||||
|
||||
static inline void throw_new(JNIEnv *env, const char *ename) {
|
||||
char buf[100];
|
||||
strcpy(buf, "java/lang/");
|
||||
strcat(buf, ename);
|
||||
jio_snprintf(buf, 100, "%s%s", "java/lang/", ename);
|
||||
jclass cls = env->FindClass(buf);
|
||||
if (env->ExceptionCheck()) {
|
||||
env->ExceptionClear();
|
||||
|
@ -282,7 +282,7 @@ WB_END
|
||||
// NMT picks it up correctly
|
||||
WB_ENTRY(jlong, WB_NMTMalloc(JNIEnv* env, jobject o, jlong size))
|
||||
jlong addr = 0;
|
||||
addr = (jlong)(uintptr_t)os::malloc(size, mtTest);
|
||||
addr = (jlong)(uintptr_t)os::malloc(size, mtTest);
|
||||
return addr;
|
||||
WB_END
|
||||
|
||||
@ -291,7 +291,7 @@ WB_END
|
||||
WB_ENTRY(jlong, WB_NMTMallocWithPseudoStack(JNIEnv* env, jobject o, jlong size, jint pseudo_stack))
|
||||
address pc = (address)(size_t)pseudo_stack;
|
||||
NativeCallStack stack(&pc, 1);
|
||||
return (jlong)os::malloc(size, mtTest, stack);
|
||||
return (jlong)(uintptr_t)os::malloc(size, mtTest, stack);
|
||||
WB_END
|
||||
|
||||
// Free the memory allocated by NMTAllocTest
|
||||
@ -326,15 +326,6 @@ WB_ENTRY(jboolean, WB_NMTIsDetailSupported(JNIEnv* env))
|
||||
return MemTracker::tracking_level() == NMT_detail;
|
||||
WB_END
|
||||
|
||||
WB_ENTRY(void, WB_NMTOverflowHashBucket(JNIEnv* env, jobject o, jlong num))
|
||||
address pc = (address)1;
|
||||
for (jlong index = 0; index < num; index ++) {
|
||||
NativeCallStack stack(&pc, 1);
|
||||
os::malloc(0, mtTest, stack);
|
||||
pc += MallocSiteTable::hash_buckets();
|
||||
}
|
||||
WB_END
|
||||
|
||||
WB_ENTRY(jboolean, WB_NMTChangeTrackingLevel(JNIEnv* env))
|
||||
// Test that we can downgrade NMT levels but not upgrade them.
|
||||
if (MemTracker::tracking_level() == NMT_off) {
|
||||
@ -365,6 +356,12 @@ WB_ENTRY(jboolean, WB_NMTChangeTrackingLevel(JNIEnv* env))
|
||||
return MemTracker::tracking_level() == NMT_minimal;
|
||||
}
|
||||
WB_END
|
||||
|
||||
WB_ENTRY(jint, WB_NMTGetHashSize(JNIEnv* env, jobject o))
|
||||
int hash_size = MallocSiteTable::hash_buckets();
|
||||
assert(hash_size > 0, "NMT hash_size should be > 0");
|
||||
return (jint)hash_size;
|
||||
WB_END
|
||||
#endif // INCLUDE_NMT
|
||||
|
||||
static jmethodID reflected_method_to_jmid(JavaThread* thread, JNIEnv* env, jobject method) {
|
||||
@ -509,16 +506,6 @@ class AlwaysFalseClosure : public BoolObjectClosure {
|
||||
|
||||
static AlwaysFalseClosure always_false;
|
||||
|
||||
class VM_WhiteBoxCleanMethodData : public VM_WhiteBoxOperation {
|
||||
public:
|
||||
VM_WhiteBoxCleanMethodData(MethodData* mdo) : _mdo(mdo) { }
|
||||
void doit() {
|
||||
_mdo->clean_method_data(&always_false);
|
||||
}
|
||||
private:
|
||||
MethodData* _mdo;
|
||||
};
|
||||
|
||||
WB_ENTRY(void, WB_ClearMethodState(JNIEnv* env, jobject o, jobject method))
|
||||
jmethodID jmid = reflected_method_to_jmid(thread, env, method);
|
||||
CHECK_JNI_EXCEPTION(env);
|
||||
@ -534,8 +521,8 @@ WB_ENTRY(void, WB_ClearMethodState(JNIEnv* env, jobject o, jobject method))
|
||||
for (int i = 0; i < arg_count; i++) {
|
||||
mdo->set_arg_modified(i, 0);
|
||||
}
|
||||
VM_WhiteBoxCleanMethodData op(mdo);
|
||||
VMThread::execute(&op);
|
||||
MutexLockerEx mu(mdo->extra_data_lock());
|
||||
mdo->clean_method_data(&always_false);
|
||||
}
|
||||
|
||||
mh->clear_not_c1_compilable();
|
||||
@ -803,20 +790,24 @@ WB_ENTRY(jobjectArray, WB_GetNMethod(JNIEnv* env, jobject o, jobject method, jbo
|
||||
ThreadToNativeFromVM ttn(thread);
|
||||
jclass clazz = env->FindClass(vmSymbols::java_lang_Object()->as_C_string());
|
||||
CHECK_JNI_EXCEPTION_(env, NULL);
|
||||
result = env->NewObjectArray(2, clazz, NULL);
|
||||
result = env->NewObjectArray(3, clazz, NULL);
|
||||
if (result == NULL) {
|
||||
return result;
|
||||
}
|
||||
|
||||
jobject obj = integerBox(thread, env, code->comp_level());
|
||||
jobject level = integerBox(thread, env, code->comp_level());
|
||||
CHECK_JNI_EXCEPTION_(env, NULL);
|
||||
env->SetObjectArrayElement(result, 0, obj);
|
||||
env->SetObjectArrayElement(result, 0, level);
|
||||
|
||||
jbyteArray insts = env->NewByteArray(insts_size);
|
||||
CHECK_JNI_EXCEPTION_(env, NULL);
|
||||
env->SetByteArrayRegion(insts, 0, insts_size, (jbyte*) code->insts_begin());
|
||||
env->SetObjectArrayElement(result, 1, insts);
|
||||
|
||||
jobject id = integerBox(thread, env, code->compile_id());
|
||||
CHECK_JNI_EXCEPTION_(env, NULL);
|
||||
env->SetObjectArrayElement(result, 2, id);
|
||||
|
||||
return result;
|
||||
WB_END
|
||||
|
||||
@ -998,9 +989,9 @@ static JNINativeMethod methods[] = {
|
||||
{CC"NMTCommitMemory", CC"(JJ)V", (void*)&WB_NMTCommitMemory },
|
||||
{CC"NMTUncommitMemory", CC"(JJ)V", (void*)&WB_NMTUncommitMemory },
|
||||
{CC"NMTReleaseMemory", CC"(JJ)V", (void*)&WB_NMTReleaseMemory },
|
||||
{CC"NMTOverflowHashBucket", CC"(J)V", (void*)&WB_NMTOverflowHashBucket},
|
||||
{CC"NMTIsDetailSupported",CC"()Z", (void*)&WB_NMTIsDetailSupported},
|
||||
{CC"NMTChangeTrackingLevel", CC"()Z", (void*)&WB_NMTChangeTrackingLevel},
|
||||
{CC"NMTGetHashSize", CC"()I", (void*)&WB_NMTGetHashSize },
|
||||
#endif // INCLUDE_NMT
|
||||
{CC"deoptimizeAll", CC"()V", (void*)&WB_DeoptimizeAll },
|
||||
{CC"deoptimizeMethod", CC"(Ljava/lang/reflect/Executable;Z)I",
|
||||
|
@ -28,6 +28,7 @@
|
||||
#include "runtime/arguments.hpp"
|
||||
#include "runtime/globals.hpp"
|
||||
#include "runtime/globals_extension.hpp"
|
||||
#include "runtime/os.hpp"
|
||||
#include "utilities/ostream.hpp"
|
||||
#include "utilities/macros.hpp"
|
||||
#include "utilities/top.hpp"
|
||||
@ -818,15 +819,12 @@ bool CommandLineFlags::ccstrAtPut(const char* name, size_t len, ccstr* value, Fl
|
||||
trace_flag_changed<EventStringFlagChanged, const char*>(name, old_value, *value, origin);
|
||||
char* new_value = NULL;
|
||||
if (*value != NULL) {
|
||||
new_value = NEW_C_HEAP_ARRAY(char, strlen(*value)+1, mtInternal);
|
||||
strcpy(new_value, *value);
|
||||
new_value = os::strdup_check_oom(*value);
|
||||
}
|
||||
result->set_ccstr(new_value);
|
||||
if (result->is_default() && old_value != NULL) {
|
||||
// Prior value is NOT heap allocated, but was a literal constant.
|
||||
char* old_value_to_free = NEW_C_HEAP_ARRAY(char, strlen(old_value)+1, mtInternal);
|
||||
strcpy(old_value_to_free, old_value);
|
||||
old_value = old_value_to_free;
|
||||
old_value = os::strdup_check_oom(old_value);
|
||||
}
|
||||
*value = old_value;
|
||||
result->set_origin(origin);
|
||||
@ -838,8 +836,7 @@ void CommandLineFlagsEx::ccstrAtPut(CommandLineFlagWithType flag, ccstr value, F
|
||||
guarantee(faddr != NULL && faddr->is_ccstr(), "wrong flag type");
|
||||
ccstr old_value = faddr->get_ccstr();
|
||||
trace_flag_changed<EventStringFlagChanged, const char*>(faddr->_name, old_value, value, origin);
|
||||
char* new_value = NEW_C_HEAP_ARRAY(char, strlen(value)+1, mtInternal);
|
||||
strcpy(new_value, value);
|
||||
char* new_value = os::strdup_check_oom(value);
|
||||
faddr->set_ccstr(new_value);
|
||||
if (!faddr->is_default() && old_value != NULL) {
|
||||
// Prior value is heap allocated so free it.
|
||||
|
@ -187,19 +187,22 @@ void InterfaceSupport::zap_dead_locals_old() {
|
||||
|
||||
# endif
|
||||
|
||||
|
||||
// invocation counter for InterfaceSupport::deoptimizeAll/zombieAll functions
|
||||
int deoptimizeAllCounter = 0;
|
||||
int zombieAllCounter = 0;
|
||||
|
||||
|
||||
void InterfaceSupport::zombieAll() {
|
||||
if (is_init_completed() && zombieAllCounter > ZombieALotInterval) {
|
||||
// This method is called by all threads when a thread make
|
||||
// transition to VM state (for example, runtime calls).
|
||||
// Divide number of calls by number of threads to avoid
|
||||
// dependence of ZombieAll events frequency on number of threads.
|
||||
int value = zombieAllCounter / Threads::number_of_threads();
|
||||
if (is_init_completed() && value > ZombieALotInterval) {
|
||||
zombieAllCounter = 0;
|
||||
VM_ZombieAll op;
|
||||
VMThread::execute(&op);
|
||||
} else {
|
||||
zombieAllCounter++;
|
||||
}
|
||||
zombieAllCounter++;
|
||||
}
|
||||
|
||||
void InterfaceSupport::unlinkSymbols() {
|
||||
@ -208,12 +211,17 @@ void InterfaceSupport::unlinkSymbols() {
|
||||
}
|
||||
|
||||
void InterfaceSupport::deoptimizeAll() {
|
||||
if (is_init_completed() ) {
|
||||
if (DeoptimizeALot && deoptimizeAllCounter > DeoptimizeALotInterval) {
|
||||
// This method is called by all threads when a thread make
|
||||
// transition to VM state (for example, runtime calls).
|
||||
// Divide number of calls by number of threads to avoid
|
||||
// dependence of DeoptimizeAll events frequency on number of threads.
|
||||
int value = deoptimizeAllCounter / Threads::number_of_threads();
|
||||
if (is_init_completed()) {
|
||||
if (DeoptimizeALot && value > DeoptimizeALotInterval) {
|
||||
deoptimizeAllCounter = 0;
|
||||
VM_DeoptimizeAll op;
|
||||
VMThread::execute(&op);
|
||||
} else if (DeoptimizeRandom && (deoptimizeAllCounter & 0x1f) == (os::random() & 0x1f)) {
|
||||
} else if (DeoptimizeRandom && (value & 0x1F) == (os::random() & 0x1F)) {
|
||||
VM_DeoptimizeAll op;
|
||||
VMThread::execute(&op);
|
||||
}
|
||||
|
@ -705,25 +705,35 @@ int JDK_Version::compare(const JDK_Version& other) const {
|
||||
}
|
||||
|
||||
void JDK_Version::to_string(char* buffer, size_t buflen) const {
|
||||
assert(buffer && buflen > 0, "call with useful buffer");
|
||||
size_t index = 0;
|
||||
|
||||
if (!is_valid()) {
|
||||
jio_snprintf(buffer, buflen, "%s", "(uninitialized)");
|
||||
} else if (is_partially_initialized()) {
|
||||
jio_snprintf(buffer, buflen, "%s", "(uninitialized) pre-1.6.0");
|
||||
} else {
|
||||
index += jio_snprintf(
|
||||
int rc = jio_snprintf(
|
||||
&buffer[index], buflen - index, "%d.%d", _major, _minor);
|
||||
if (rc == -1) return;
|
||||
index += rc;
|
||||
if (_micro > 0) {
|
||||
index += jio_snprintf(&buffer[index], buflen - index, ".%d", _micro);
|
||||
rc = jio_snprintf(&buffer[index], buflen - index, ".%d", _micro);
|
||||
}
|
||||
if (_update > 0) {
|
||||
index += jio_snprintf(&buffer[index], buflen - index, "_%02d", _update);
|
||||
rc = jio_snprintf(&buffer[index], buflen - index, "_%02d", _update);
|
||||
if (rc == -1) return;
|
||||
index += rc;
|
||||
}
|
||||
if (_special > 0) {
|
||||
index += jio_snprintf(&buffer[index], buflen - index, "%c", _special);
|
||||
rc = jio_snprintf(&buffer[index], buflen - index, "%c", _special);
|
||||
if (rc == -1) return;
|
||||
index += rc;
|
||||
}
|
||||
if (_build > 0) {
|
||||
index += jio_snprintf(&buffer[index], buflen - index, "-b%02d", _build);
|
||||
rc = jio_snprintf(&buffer[index], buflen - index, "-b%02d", _build);
|
||||
if (rc == -1) return;
|
||||
index += rc;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -228,6 +228,20 @@ class ObjectMonitor {
|
||||
static int Responsible_offset_in_bytes() { return offset_of(ObjectMonitor, _Responsible); }
|
||||
static int Spinner_offset_in_bytes() { return offset_of(ObjectMonitor, _Spinner); }
|
||||
|
||||
// ObjectMonitor references can be ORed with markOopDesc::monitor_value
|
||||
// as part of the ObjectMonitor tagging mechanism. When we combine an
|
||||
// ObjectMonitor reference with an offset, we need to remove the tag
|
||||
// value in order to generate the proper address.
|
||||
//
|
||||
// We can either adjust the ObjectMonitor reference and then add the
|
||||
// offset or we can adjust the offset that is added to the ObjectMonitor
|
||||
// reference. The latter avoids an AGI (Address Generation Interlock)
|
||||
// stall so the helper macro adjusts the offset value that is returned
|
||||
// to the ObjectMonitor reference manipulation code:
|
||||
//
|
||||
#define OM_OFFSET_NO_MONITOR_VALUE_TAG(f) \
|
||||
((ObjectMonitor::f ## _offset_in_bytes()) - markOopDesc::monitor_value)
|
||||
|
||||
// Eventually we'll make provisions for multiple callbacks, but
|
||||
// now one will suffice.
|
||||
static int (*SpinCallbackFunction)(intptr_t, int);
|
||||
|
@ -571,17 +571,6 @@ void* os::malloc(size_t size, MEMFLAGS memflags, const NativeCallStack& stack) {
|
||||
NOT_PRODUCT(inc_stat_counter(&num_mallocs, 1));
|
||||
NOT_PRODUCT(inc_stat_counter(&alloc_bytes, size));
|
||||
|
||||
#if INCLUDE_NMT
|
||||
// NMT can not track malloc allocation size > MAX_MALLOC_SIZE, which is
|
||||
// (1GB - 1) on 32-bit system. It is not an issue on 64-bit system, where
|
||||
// MAX_MALLOC_SIZE = ((1 << 62) - 1).
|
||||
// VM code does not have such large malloc allocation. However, it can come
|
||||
// Unsafe call.
|
||||
if (MemTracker::tracking_level() >= NMT_summary && size > MAX_MALLOC_SIZE) {
|
||||
return NULL;
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef ASSERT
|
||||
// checking for the WatcherThread and crash_protection first
|
||||
// since os::malloc can be called when the libjvm.{dll,so} is
|
||||
@ -652,12 +641,6 @@ void* os::realloc(void *memblock, size_t size, MEMFLAGS flags) {
|
||||
}
|
||||
|
||||
void* os::realloc(void *memblock, size_t size, MEMFLAGS memflags, const NativeCallStack& stack) {
|
||||
#if INCLUDE_NMT
|
||||
// See comments in os::malloc() above
|
||||
if (MemTracker::tracking_level() >= NMT_summary && size > MAX_MALLOC_SIZE) {
|
||||
return NULL;
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifndef ASSERT
|
||||
NOT_PRODUCT(inc_stat_counter(&num_mallocs, 1));
|
||||
|
@ -158,7 +158,7 @@ void SignatureIterator::iterate_parameters( uint64_t fingerprint ) {
|
||||
uint64_t saved_fingerprint = fingerprint;
|
||||
|
||||
// Check for too many arguments
|
||||
if ( fingerprint == UCONST64(-1) ) {
|
||||
if (fingerprint == (uint64_t)CONST64(-1)) {
|
||||
SignatureIterator::iterate_parameters();
|
||||
return;
|
||||
}
|
||||
|
@ -243,7 +243,7 @@ class Fingerprinter: public SignatureIterator {
|
||||
}
|
||||
|
||||
if (mh->size_of_parameters() > max_size_of_parameters ) {
|
||||
_fingerprint = UCONST64(-1);
|
||||
_fingerprint = (uint64_t)CONST64(-1);
|
||||
mh->constMethod()->set_fingerprint(_fingerprint);
|
||||
return _fingerprint;
|
||||
}
|
||||
|
@ -196,7 +196,6 @@ nmethod* SimpleThresholdPolicy::event(methodHandle method, methodHandle inlinee,
|
||||
// Don't trigger other compiles in testing mode
|
||||
return NULL;
|
||||
}
|
||||
nmethod *osr_nm = NULL;
|
||||
|
||||
handle_counter_overflow(method());
|
||||
if (method() != inlinee()) {
|
||||
@ -210,14 +209,16 @@ nmethod* SimpleThresholdPolicy::event(methodHandle method, methodHandle inlinee,
|
||||
if (bci == InvocationEntryBci) {
|
||||
method_invocation_event(method, inlinee, comp_level, nm, thread);
|
||||
} else {
|
||||
method_back_branch_event(method, inlinee, bci, comp_level, nm, thread);
|
||||
// method == inlinee if the event originated in the main method
|
||||
int highest_level = inlinee->highest_osr_comp_level();
|
||||
if (highest_level > comp_level) {
|
||||
osr_nm = inlinee->lookup_osr_nmethod_for(bci, highest_level, false);
|
||||
method_back_branch_event(method, inlinee, bci, comp_level, nm, thread);
|
||||
// Check if event led to a higher level OSR compilation
|
||||
nmethod* osr_nm = inlinee->lookup_osr_nmethod_for(bci, comp_level, false);
|
||||
if (osr_nm != NULL && osr_nm->comp_level() > comp_level) {
|
||||
// Perform OSR with new nmethod
|
||||
return osr_nm;
|
||||
}
|
||||
}
|
||||
return osr_nm;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// Check if the method can be compiled, change level if necessary
|
||||
|
@ -3639,7 +3639,7 @@ static OnLoadEntry_t lookup_on_load(AgentLibrary* agent,
|
||||
|
||||
if (!agent->valid()) {
|
||||
char buffer[JVM_MAXPATHLEN];
|
||||
char ebuf[1024];
|
||||
char ebuf[1024] = "";
|
||||
const char *name = agent->name();
|
||||
const char *msg = "Could not find agent library ";
|
||||
|
||||
|
@ -1594,6 +1594,7 @@ typedef TwoOopHashtable<Symbol*, mtClass> SymbolTwoOopHashtable;
|
||||
declare_type(JvmtiAgentThread, JavaThread) \
|
||||
declare_type(ServiceThread, JavaThread) \
|
||||
declare_type(CompilerThread, JavaThread) \
|
||||
declare_type(CodeCacheSweeperThread, JavaThread) \
|
||||
declare_toplevel_type(OSThread) \
|
||||
declare_toplevel_type(JavaFrameAnchor) \
|
||||
\
|
||||
|
@ -72,7 +72,7 @@ void MallocHeader::release() const {
|
||||
|
||||
MallocMemorySummary::record_free(size(), flags());
|
||||
MallocMemorySummary::record_free_malloc_header(sizeof(MallocHeader));
|
||||
if (tracking_level() == NMT_detail) {
|
||||
if (MemTracker::tracking_level() == NMT_detail) {
|
||||
MallocSiteTable::deallocation_at(size(), _bucket_idx, _pos_idx);
|
||||
}
|
||||
}
|
||||
@ -128,36 +128,18 @@ void* MallocTracker::record_malloc(void* malloc_base, size_t size, MEMFLAGS flag
|
||||
}
|
||||
|
||||
// Uses placement global new operator to initialize malloc header
|
||||
switch(level) {
|
||||
case NMT_off:
|
||||
return malloc_base;
|
||||
case NMT_minimal: {
|
||||
MallocHeader* hdr = ::new (malloc_base) MallocHeader();
|
||||
break;
|
||||
}
|
||||
case NMT_summary: {
|
||||
assert(size <= MAX_MALLOC_SIZE, "malloc size overrun for NMT");
|
||||
header = ::new (malloc_base) MallocHeader(size, flags);
|
||||
break;
|
||||
}
|
||||
case NMT_detail: {
|
||||
assert(size <= MAX_MALLOC_SIZE, "malloc size overrun for NMT");
|
||||
header = ::new (malloc_base) MallocHeader(size, flags, stack);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
ShouldNotReachHere();
|
||||
|
||||
if (level == NMT_off) {
|
||||
return malloc_base;
|
||||
}
|
||||
|
||||
header = ::new (malloc_base)MallocHeader(size, flags, stack, level);
|
||||
memblock = (void*)((char*)malloc_base + sizeof(MallocHeader));
|
||||
|
||||
// The alignment check: 8 bytes alignment for 32 bit systems.
|
||||
// 16 bytes alignment for 64-bit systems.
|
||||
assert(((size_t)memblock & (sizeof(size_t) * 2 - 1)) == 0, "Alignment check");
|
||||
|
||||
// Sanity check
|
||||
assert(get_memory_tracking_level(memblock) == level,
|
||||
"Wrong tracking level");
|
||||
|
||||
#ifdef ASSERT
|
||||
if (level > NMT_minimal) {
|
||||
// Read back
|
||||
|
@ -239,68 +239,46 @@ class MallocMemorySummary : AllStatic {
|
||||
|
||||
class MallocHeader VALUE_OBJ_CLASS_SPEC {
|
||||
#ifdef _LP64
|
||||
size_t _size : 62;
|
||||
size_t _level : 2;
|
||||
size_t _size : 64;
|
||||
size_t _flags : 8;
|
||||
size_t _pos_idx : 16;
|
||||
size_t _bucket_idx: 40;
|
||||
#define MAX_MALLOCSITE_TABLE_SIZE ((size_t)1 << 40)
|
||||
#define MAX_BUCKET_LENGTH ((size_t)(1 << 16))
|
||||
#define MAX_MALLOC_SIZE (((size_t)1 << 62) - 1)
|
||||
#else
|
||||
size_t _size : 30;
|
||||
size_t _level : 2;
|
||||
size_t _size : 32;
|
||||
size_t _flags : 8;
|
||||
size_t _pos_idx : 8;
|
||||
size_t _bucket_idx: 16;
|
||||
#define MAX_MALLOCSITE_TABLE_SIZE ((size_t)(1 << 16))
|
||||
#define MAX_BUCKET_LENGTH ((size_t)(1 << 8))
|
||||
// Max malloc size = 1GB - 1 on 32 bit system, such has total 4GB memory
|
||||
#define MAX_MALLOC_SIZE ((size_t)(1 << 30) - 1)
|
||||
#endif // _LP64
|
||||
|
||||
public:
|
||||
// Summary tracking header
|
||||
MallocHeader(size_t size, MEMFLAGS flags) {
|
||||
MallocHeader(size_t size, MEMFLAGS flags, const NativeCallStack& stack, NMT_TrackingLevel level) {
|
||||
assert(sizeof(MallocHeader) == sizeof(void*) * 2,
|
||||
"Wrong header size");
|
||||
|
||||
_level = NMT_summary;
|
||||
_flags = flags;
|
||||
set_size(size);
|
||||
MallocMemorySummary::record_malloc(size, flags);
|
||||
MallocMemorySummary::record_new_malloc_header(sizeof(MallocHeader));
|
||||
}
|
||||
// Detail tracking header
|
||||
MallocHeader(size_t size, MEMFLAGS flags, const NativeCallStack& stack) {
|
||||
assert(sizeof(MallocHeader) == sizeof(void*) * 2,
|
||||
"Wrong header size");
|
||||
|
||||
_level = NMT_detail;
|
||||
_flags = flags;
|
||||
set_size(size);
|
||||
size_t bucket_idx;
|
||||
size_t pos_idx;
|
||||
if (record_malloc_site(stack, size, &bucket_idx, &pos_idx)) {
|
||||
assert(bucket_idx <= MAX_MALLOCSITE_TABLE_SIZE, "Overflow bucket index");
|
||||
assert(pos_idx <= MAX_BUCKET_LENGTH, "Overflow bucket position index");
|
||||
_bucket_idx = bucket_idx;
|
||||
_pos_idx = pos_idx;
|
||||
if (level == NMT_minimal) {
|
||||
return;
|
||||
}
|
||||
|
||||
_flags = flags;
|
||||
set_size(size);
|
||||
if (level == NMT_detail) {
|
||||
size_t bucket_idx;
|
||||
size_t pos_idx;
|
||||
if (record_malloc_site(stack, size, &bucket_idx, &pos_idx)) {
|
||||
assert(bucket_idx <= MAX_MALLOCSITE_TABLE_SIZE, "Overflow bucket index");
|
||||
assert(pos_idx <= MAX_BUCKET_LENGTH, "Overflow bucket position index");
|
||||
_bucket_idx = bucket_idx;
|
||||
_pos_idx = pos_idx;
|
||||
}
|
||||
}
|
||||
|
||||
MallocMemorySummary::record_malloc(size, flags);
|
||||
MallocMemorySummary::record_new_malloc_header(sizeof(MallocHeader));
|
||||
}
|
||||
// Minimal tracking header
|
||||
MallocHeader() {
|
||||
assert(sizeof(MallocHeader) == sizeof(void*) * 2,
|
||||
"Wrong header size");
|
||||
|
||||
_level = (unsigned short)NMT_minimal;
|
||||
}
|
||||
|
||||
inline NMT_TrackingLevel tracking_level() const {
|
||||
return (NMT_TrackingLevel)_level;
|
||||
}
|
||||
|
||||
inline size_t size() const { return _size; }
|
||||
inline MEMFLAGS flags() const { return (MEMFLAGS)_flags; }
|
||||
@ -311,7 +289,6 @@ class MallocHeader VALUE_OBJ_CLASS_SPEC {
|
||||
|
||||
private:
|
||||
inline void set_size(size_t size) {
|
||||
assert(size <= MAX_MALLOC_SIZE, "Malloc size too large, should use virtual memory?");
|
||||
_size = size;
|
||||
}
|
||||
bool record_malloc_site(const NativeCallStack& stack, size_t size,
|
||||
@ -347,10 +324,6 @@ class MallocTracker : AllStatic {
|
||||
// Record free on specified memory block
|
||||
static void* record_free(void* memblock);
|
||||
|
||||
// Get tracking level of specified memory block
|
||||
static inline NMT_TrackingLevel get_memory_tracking_level(void* memblock);
|
||||
|
||||
|
||||
// Offset memory address to header address
|
||||
static inline void* get_base(void* memblock);
|
||||
static inline void* get_base(void* memblock, NMT_TrackingLevel level) {
|
||||
@ -361,16 +334,12 @@ class MallocTracker : AllStatic {
|
||||
// Get memory size
|
||||
static inline size_t get_size(void* memblock) {
|
||||
MallocHeader* header = malloc_header(memblock);
|
||||
assert(header->tracking_level() >= NMT_summary,
|
||||
"Wrong tracking level");
|
||||
return header->size();
|
||||
}
|
||||
|
||||
// Get memory type
|
||||
static inline MEMFLAGS get_flags(void* memblock) {
|
||||
MallocHeader* header = malloc_header(memblock);
|
||||
assert(header->tracking_level() >= NMT_summary,
|
||||
"Wrong tracking level");
|
||||
return header->flags();
|
||||
}
|
||||
|
||||
@ -394,7 +363,6 @@ class MallocTracker : AllStatic {
|
||||
static inline MallocHeader* malloc_header(void *memblock) {
|
||||
assert(memblock != NULL, "NULL pointer");
|
||||
MallocHeader* header = (MallocHeader*)((char*)memblock - sizeof(MallocHeader));
|
||||
assert(header->tracking_level() >= NMT_minimal, "Bad header");
|
||||
return header;
|
||||
}
|
||||
};
|
||||
|
@ -28,13 +28,6 @@
|
||||
#include "services/mallocTracker.hpp"
|
||||
#include "services/memTracker.hpp"
|
||||
|
||||
inline NMT_TrackingLevel MallocTracker::get_memory_tracking_level(void* memblock) {
|
||||
assert(memblock != NULL, "Sanity check");
|
||||
if (MemTracker::tracking_level() == NMT_off) return NMT_off;
|
||||
MallocHeader* header = malloc_header(memblock);
|
||||
return header->tracking_level();
|
||||
}
|
||||
|
||||
inline void* MallocTracker::get_base(void* memblock){
|
||||
return get_base(memblock, MemTracker::tracking_level());
|
||||
}
|
||||
|
@ -1333,7 +1333,7 @@ JVM_ENTRY(jobjectArray, jmm_DumpThreads(JNIEnv *env, jlongArray thread_ids, jboo
|
||||
GrowableArray<oop>* locked_monitors = frame->locked_monitors();
|
||||
for (j = 0; j < len; j++) {
|
||||
oop monitor = locked_monitors->at(j);
|
||||
assert(monitor != NULL && monitor->is_instance(), "must be a Java object");
|
||||
assert(monitor != NULL, "must be a Java object");
|
||||
monitors_array->obj_at_put(count, monitor);
|
||||
depths_array->int_at_put(count, depth);
|
||||
count++;
|
||||
@ -1343,7 +1343,7 @@ JVM_ENTRY(jobjectArray, jmm_DumpThreads(JNIEnv *env, jlongArray thread_ids, jboo
|
||||
GrowableArray<oop>* jni_locked_monitors = stacktrace->jni_locked_monitors();
|
||||
for (j = 0; j < jni_locked_monitors->length(); j++) {
|
||||
oop object = jni_locked_monitors->at(j);
|
||||
assert(object != NULL && object->is_instance(), "must be a Java object");
|
||||
assert(object != NULL, "must be a Java object");
|
||||
monitors_array->obj_at_put(count, object);
|
||||
// Monitor locked via JNI MonitorEnter call doesn't have stack depth info
|
||||
depths_array->int_at_put(count, -1);
|
||||
|
@ -597,7 +597,7 @@ bool ThreadStackTrace::is_owned_monitor_on_stack(oop object) {
|
||||
GrowableArray<oop>* locked_monitors = frame->locked_monitors();
|
||||
for (int j = 0; j < len; j++) {
|
||||
oop monitor = locked_monitors->at(j);
|
||||
assert(monitor != NULL && monitor->is_instance(), "must be a Java object");
|
||||
assert(monitor != NULL, "must be a Java object");
|
||||
if (monitor == object) {
|
||||
found = true;
|
||||
break;
|
||||
|
@ -1048,7 +1048,7 @@ const int badHandleValue = 0xBC; // value used to zap
|
||||
const int badResourceValue = 0xAB; // value used to zap resource area
|
||||
const int freeBlockPad = 0xBA; // value used to pad freed blocks.
|
||||
const int uninitBlockPad = 0xF1; // value used to zap newly malloc'd blocks.
|
||||
const intptr_t badJNIHandleVal = (intptr_t) CONST64(0xFEFEFEFEFEFEFEFE); // value used to zap jni handle area
|
||||
const intptr_t badJNIHandleVal = (intptr_t) UCONST64(0xFEFEFEFEFEFEFEFE); // value used to zap jni handle area
|
||||
const juint badHeapWordVal = 0xBAADBABE; // value used to zap heap after GC
|
||||
const juint badMetaWordVal = 0xBAADFADE; // value used to zap metadata heap after GC
|
||||
const int badCodeHeapNewVal= 0xCC; // value used to zap Code heap at allocation
|
||||
|
@ -151,11 +151,11 @@ inline int g_isfinite(jdouble f) { return _finite(f); }
|
||||
// Constant for jlong (specifying an long long constant is C++ compiler specific)
|
||||
|
||||
// Build a 64bit integer constant on with Visual C++
|
||||
#define CONST64(x) (x ## i64)
|
||||
#define UCONST64(x) ((uint64_t)CONST64(x))
|
||||
#define CONST64(x) (x ## i64)
|
||||
#define UCONST64(x) (x ## ui64)
|
||||
|
||||
const jlong min_jlong = CONST64(0x8000000000000000);
|
||||
const jlong max_jlong = CONST64(0x7fffffffffffffff);
|
||||
const jlong min_jlong = (jlong)UCONST64(0x8000000000000000);
|
||||
const jlong max_jlong = CONST64(0x7fffffffffffffff);
|
||||
|
||||
//----------------------------------------------------------------------------------------------------
|
||||
// Miscellaneous
|
||||
|
@ -76,6 +76,8 @@ const char* outputStream::do_vsnprintf(char* buffer, size_t buflen,
|
||||
const char* format, va_list ap,
|
||||
bool add_cr,
|
||||
size_t& result_len) {
|
||||
assert(buflen >= 2, "buffer too small");
|
||||
|
||||
const char* result;
|
||||
if (add_cr) buflen--;
|
||||
if (!strchr(format, '%')) {
|
||||
@ -88,14 +90,21 @@ const char* outputStream::do_vsnprintf(char* buffer, size_t buflen,
|
||||
result = va_arg(ap, const char*);
|
||||
result_len = strlen(result);
|
||||
if (add_cr && result_len >= buflen) result_len = buflen-1; // truncate
|
||||
} else if (vsnprintf(buffer, buflen, format, ap) >= 0) {
|
||||
result = buffer;
|
||||
result_len = strlen(result);
|
||||
} else {
|
||||
DEBUG_ONLY(warning("increase O_BUFLEN in ostream.hpp -- output truncated");)
|
||||
// Handle truncation:
|
||||
// posix: upon truncation, vsnprintf returns number of bytes which
|
||||
// would have been written (excluding terminating zero) had the buffer
|
||||
// been large enough
|
||||
// windows: upon truncation, vsnprintf returns -1
|
||||
const int written = vsnprintf(buffer, buflen, format, ap);
|
||||
result = buffer;
|
||||
result_len = buflen - 1;
|
||||
buffer[result_len] = 0;
|
||||
if (written < (int) buflen && written >= 0) {
|
||||
result_len = written;
|
||||
} else {
|
||||
DEBUG_ONLY(warning("increase O_BUFLEN in ostream.hpp -- output truncated");)
|
||||
result_len = buflen - 1;
|
||||
buffer[result_len] = 0;
|
||||
}
|
||||
}
|
||||
if (add_cr) {
|
||||
if (result != buffer) {
|
||||
|
@ -975,11 +975,13 @@ void VMError::report_and_die() {
|
||||
// Run error reporting to determine whether or not to report the crash.
|
||||
if (!transmit_report_done && should_report_bug(first_error->_id)) {
|
||||
transmit_report_done = true;
|
||||
FILE* hs_err = os::open(log.fd(), "r");
|
||||
const int fd2 = ::dup(log.fd());
|
||||
FILE* const hs_err = ::fdopen(fd2, "r");
|
||||
if (NULL != hs_err) {
|
||||
ErrorReporter er;
|
||||
er.call(hs_err, buffer, O_BUFLEN);
|
||||
}
|
||||
::fclose(hs_err);
|
||||
}
|
||||
|
||||
if (log.fd() != defaultStream::output_fd()) {
|
||||
|
@ -30,3 +30,4 @@
|
||||
keys=cte_test jcmd nmt regression gc stress
|
||||
|
||||
groups=TEST.groups [closed/TEST.groups]
|
||||
requires.properties=sun.arch.data.model
|
||||
|
@ -87,7 +87,6 @@ needs_jdk = \
|
||||
runtime/NMT/SummarySanityCheck.java \
|
||||
runtime/NMT/ThreadedMallocTestType.java \
|
||||
runtime/NMT/ThreadedVirtualAllocTestType.java \
|
||||
runtime/NMT/UnsafeMallocLimit.java \
|
||||
runtime/NMT/VirtualAllocCommitUncommitRecommit.java \
|
||||
runtime/NMT/VirtualAllocTestType.java \
|
||||
runtime/RedefineObject/TestRedefineObject.java \
|
||||
@ -479,6 +478,7 @@ hotspot_compiler_3 = \
|
||||
compiler/intrinsics/mathexact/SubExactILoopDependentTest.java \
|
||||
compiler/intrinsics/stringequals/TestStringEqualsBadLength.java \
|
||||
compiler/intrinsics/unsafe/UnsafeGetAddressTest.java \
|
||||
compiler/intrinsics/classcast/NullCheckDroppingsTest.java \
|
||||
compiler/jsr292/ConcurrentClassLoadingTest.java \
|
||||
compiler/jsr292/CreatesInterfaceDotEqualsCallInfo.java \
|
||||
compiler/loopopts/TestLogSum.java \
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,13 +25,20 @@
|
||||
* @test
|
||||
* @bug 6896617
|
||||
* @summary Optimize sun.nio.cs.ISO_8859_1$Encode.encodeArrayLoop() with SSE instructions on x86
|
||||
* @library /testlibrary
|
||||
* @run main/othervm/timeout=1200 -Xbatch -Xmx256m Test6896617
|
||||
*
|
||||
*/
|
||||
|
||||
import java.util.*;
|
||||
import java.nio.*;
|
||||
import java.nio.charset.*;
|
||||
import com.oracle.java.testlibrary.Utils;
|
||||
import java.nio.ByteBuffer;
|
||||
import java.nio.CharBuffer;
|
||||
import java.nio.charset.Charset;
|
||||
import java.nio.charset.CharsetDecoder;
|
||||
import java.nio.charset.CharsetEncoder;
|
||||
import java.nio.charset.CodingErrorAction;
|
||||
import java.util.Arrays;
|
||||
import java.util.Random;
|
||||
|
||||
public class Test6896617 {
|
||||
final static int SIZE = 256;
|
||||
@ -54,7 +61,7 @@ public class Test6896617 {
|
||||
sun.nio.cs.ArrayDecoder arrdec = (sun.nio.cs.ArrayDecoder)dec;
|
||||
|
||||
// Populate char[] with chars which can be encoded by ISO_8859_1 (<= 0xFF)
|
||||
Random rnd = new Random(0);
|
||||
Random rnd = Utils.getRandomInstance();
|
||||
int maxchar = 0xFF;
|
||||
char[] a = new char[SIZE];
|
||||
byte[] b = new byte[SIZE];
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2011, 2014, 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
|
||||
@ -26,11 +26,13 @@
|
||||
* @test
|
||||
* @bug 7100757
|
||||
* @summary The BitSet.nextSetBit() produces incorrect result in 32bit VM on Sparc
|
||||
*
|
||||
* @library /testlibrary
|
||||
* @run main/timeout=300 Test7100757
|
||||
*/
|
||||
|
||||
import java.util.*;
|
||||
import com.oracle.java.testlibrary.Utils;
|
||||
import java.util.BitSet;
|
||||
import java.util.Random;
|
||||
|
||||
public class Test7100757 {
|
||||
|
||||
@ -39,7 +41,7 @@ public class Test7100757 {
|
||||
public static void main(String[] args) {
|
||||
|
||||
BitSet bs = new BitSet(NBITS);
|
||||
Random rnd = new Random();
|
||||
Random rnd = Utils.getRandomInstance();
|
||||
long[] ra = new long[(NBITS+63)/64];
|
||||
|
||||
for(int l=0; l < 5000000; l++) {
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2012, 2014, 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
|
||||
@ -26,13 +26,14 @@
|
||||
* Micro-benchmark for Math.pow() and Math.exp()
|
||||
*/
|
||||
|
||||
import java.util.*;
|
||||
import com.oracle.java.testlibrary.Utils;
|
||||
import java.util.Random;
|
||||
|
||||
public class Test7177917 {
|
||||
|
||||
static double d;
|
||||
|
||||
static Random r = new Random(0);
|
||||
static final Random R = Utils.getRandomInstance();
|
||||
|
||||
static long m_pow(double[][] values) {
|
||||
double res = 0;
|
||||
@ -59,10 +60,10 @@ public class Test7177917 {
|
||||
static double[][] pow_values(int nb) {
|
||||
double[][] res = new double[nb][2];
|
||||
for (int i = 0; i < nb; i++) {
|
||||
double ylogx = (1 + (r.nextDouble() * 2045)) - 1023; // 2045 rather than 2046 as a safety margin
|
||||
double x = Math.abs(Double.longBitsToDouble(r.nextLong()));
|
||||
double ylogx = (1 + (R.nextDouble() * 2045)) - 1023; // 2045 rather than 2046 as a safety margin
|
||||
double x = Math.abs(Double.longBitsToDouble(R.nextLong()));
|
||||
while (x != x) {
|
||||
x = Math.abs(Double.longBitsToDouble(r.nextLong()));
|
||||
x = Math.abs(Double.longBitsToDouble(R.nextLong()));
|
||||
}
|
||||
double logx = Math.log(x) / Math.log(2);
|
||||
double y = ylogx / logx;
|
||||
@ -76,7 +77,7 @@ public class Test7177917 {
|
||||
static double[] exp_values(int nb) {
|
||||
double[] res = new double[nb];
|
||||
for (int i = 0; i < nb; i++) {
|
||||
double ylogx = (1 + (r.nextDouble() * 2045)) - 1023; // 2045 rather than 2046 as a safety margin
|
||||
double ylogx = (1 + (R.nextDouble() * 2045)) - 1023; // 2045 rather than 2046 as a safety margin
|
||||
double x = Math.E;
|
||||
double logx = Math.log(x) / Math.log(2);
|
||||
double y = ylogx / logx;
|
||||
|
@ -26,15 +26,13 @@
|
||||
* @author Tom Deneau
|
||||
*/
|
||||
|
||||
import com.oracle.java.testlibrary.Utils;
|
||||
import java.security.AlgorithmParameters;
|
||||
import java.util.Random;
|
||||
import javax.crypto.Cipher;
|
||||
import javax.crypto.KeyGenerator;
|
||||
import javax.crypto.SecretKey;
|
||||
import javax.crypto.spec.IvParameterSpec;
|
||||
import javax.crypto.spec.SecretKeySpec;
|
||||
import java.security.AlgorithmParameters;
|
||||
|
||||
import java.util.Random;
|
||||
import java.util.Arrays;
|
||||
|
||||
abstract public class TestAESBase {
|
||||
int msgSize = Integer.getInteger("msgSize", 646);
|
||||
@ -59,7 +57,7 @@ abstract public class TestAESBase {
|
||||
byte[] expectedEncode;
|
||||
byte[] decode;
|
||||
byte[] expectedDecode;
|
||||
Random random = new Random(0);
|
||||
final Random random = Utils.getRandomInstance();
|
||||
Cipher cipher;
|
||||
Cipher dCipher;
|
||||
AlgorithmParameters algParams;
|
||||
|
@ -26,6 +26,7 @@
|
||||
* @test
|
||||
* @bug 7184394
|
||||
* @summary add intrinsics to use AES instructions
|
||||
* @library /testlibrary
|
||||
*
|
||||
* @run main/othervm/timeout=600 -Xbatch -DcheckOutput=true -Dmode=CBC TestAESMain
|
||||
* @run main/othervm/timeout=600 -Xbatch -DcheckOutput=true -Dmode=CBC -DencInputOffset=1 TestAESMain
|
||||
|
@ -1,4 +1,3 @@
|
||||
//package com.polytechnik.utils;
|
||||
/*
|
||||
* (C) Vladislav Malyshkin 2010
|
||||
* This file is under GPL version 3.
|
||||
@ -14,10 +13,14 @@
|
||||
* @test
|
||||
* @bug 8005956
|
||||
* @summary C2: assert(!def_outside->member(r)) failed: Use of external LRG overlaps the same LRG defined in this block
|
||||
*
|
||||
* @library /testlibrary
|
||||
* @run main/timeout=300 PolynomialRoot
|
||||
*/
|
||||
|
||||
import com.oracle.java.testlibrary.Utils;
|
||||
import java.util.Arrays;
|
||||
import java.util.Random;
|
||||
|
||||
public class PolynomialRoot {
|
||||
|
||||
|
||||
@ -57,7 +60,7 @@ private static final boolean PRINT_DEBUG=false;
|
||||
|
||||
public static int root4(final double [] p,final double [] re_root,final double [] im_root)
|
||||
{
|
||||
if(PRINT_DEBUG) System.err.println("=====================root4:p="+java.util.Arrays.toString(p));
|
||||
if (PRINT_DEBUG) { System.err.println("=====================root4:p=" + Arrays.toString(p)); }
|
||||
final double vs=p[4];
|
||||
if(PRINT_DEBUG) System.err.println("p[4]="+p[4]);
|
||||
if(!(Math.abs(vs)>EPS))
|
||||
@ -367,7 +370,7 @@ public static int root4(final double [] p,final double [] re_root,final double [
|
||||
|
||||
|
||||
|
||||
static void setRandomP(final double [] p,final int n,java.util.Random r)
|
||||
static void setRandomP(final double [] p, final int n, Random r)
|
||||
{
|
||||
if(r.nextDouble()<0.1)
|
||||
{
|
||||
@ -465,7 +468,7 @@ public static int root4(final double [] p,final double [] re_root,final double [
|
||||
|
||||
static void testRoots(final int n,
|
||||
final int n_tests,
|
||||
final java.util.Random rn,
|
||||
final Random rn,
|
||||
final double eps)
|
||||
{
|
||||
final double [] p=new double [n+1];
|
||||
@ -763,7 +766,7 @@ public static int root4(final double [] p,final double [] re_root,final double [
|
||||
final long t0=System.currentTimeMillis();
|
||||
final double eps=1e-6;
|
||||
//checkRoots();
|
||||
final java.util.Random r=new java.util.Random(-1381923);
|
||||
final Random r = Utils.getRandomInstance();
|
||||
printSpecialValues();
|
||||
|
||||
final int n_tests=100000;
|
||||
|
@ -22,13 +22,17 @@
|
||||
*
|
||||
*/
|
||||
|
||||
import java.util.*;
|
||||
import com.oracle.java.testlibrary.Asserts;
|
||||
import com.oracle.java.testlibrary.OutputAnalyzer;
|
||||
import com.oracle.java.testlibrary.ProcessTools;
|
||||
import com.oracle.java.testlibrary.Utils;
|
||||
import java.io.IOException;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Paths;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
|
||||
import com.oracle.java.testlibrary.*;
|
||||
import java.util.Collections;
|
||||
import java.util.LinkedList;
|
||||
import java.util.List;
|
||||
import java.util.Random;
|
||||
|
||||
/**
|
||||
* Test runner that invokes all methods implemented by particular Expr
|
||||
@ -69,7 +73,7 @@ public class BMITestRunner {
|
||||
String... additionalVMOpts)
|
||||
throws Throwable {
|
||||
|
||||
int seed = new Random().nextInt();
|
||||
int seed = Utils.getRandomInstance().nextInt();
|
||||
int iterations = DEFAULT_ITERATIONS_COUNT;
|
||||
|
||||
for (String testOption : testOpts) {
|
||||
@ -81,8 +85,6 @@ public class BMITestRunner {
|
||||
}
|
||||
}
|
||||
|
||||
System.out.println("Running test with seed: " + seed);
|
||||
|
||||
OutputAnalyzer intOutput = runTest(expr, VMMode.INT,
|
||||
additionalVMOpts,
|
||||
seed, iterations);
|
||||
@ -139,9 +141,9 @@ public class BMITestRunner {
|
||||
|
||||
Collections.addAll(vmOpts, new String[] {
|
||||
"-XX:+DisplayVMOutputToStderr",
|
||||
"-D" + Utils.SEED_PROPERTY_NAME + "=" + seed,
|
||||
Executor.class.getName(),
|
||||
expr.getName(),
|
||||
new Integer(seed).toString(),
|
||||
new Integer(iterations).toString()
|
||||
});
|
||||
|
||||
@ -179,16 +181,15 @@ public class BMITestRunner {
|
||||
public static class Executor {
|
||||
|
||||
/**
|
||||
* Usage: BMITestRunner$Executor <ExprClassName> <seed> <iterations>
|
||||
* Usage: BMITestRunner$Executor <ExprClassName> <iterations>
|
||||
*/
|
||||
public static void main(String args[]) throws Exception {
|
||||
@SuppressWarnings("unchecked")
|
||||
Class<? extends Expr> exprClass =
|
||||
(Class<? extends Expr>)Class.forName(args[0]);
|
||||
Expr expr = exprClass.getConstructor().newInstance();
|
||||
Random rng = new Random(Integer.valueOf(args[1]));
|
||||
int iterations = Integer.valueOf(args[2]);
|
||||
runTests(expr, iterations, rng);
|
||||
int iterations = Integer.valueOf(args[1]);
|
||||
runTests(expr, iterations, Utils.getRandomInstance());
|
||||
}
|
||||
|
||||
|
||||
|
@ -0,0 +1,346 @@
|
||||
/*
|
||||
* Copyright (c) 2014, 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.
|
||||
*/
|
||||
|
||||
/*
|
||||
* @test NullCheckDroppingsTest
|
||||
* @bug 8054492
|
||||
* @summary "Casting can result in redundant null checks in generated code"
|
||||
* @library /testlibrary /testlibrary/whitebox /testlibrary/com/oracle/java/testlibrary
|
||||
* @build NullCheckDroppingsTest
|
||||
* @run main ClassFileInstaller sun.hotspot.WhiteBox
|
||||
* sun.hotspot.WhiteBox$WhiteBoxPermission
|
||||
* @run main ClassFileInstaller com.oracle.java.testlibrary.Platform
|
||||
* @run main/othervm -Xbootclasspath/a:. -XX:+IgnoreUnrecognizedVMOptions -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI
|
||||
* -Xmixed -XX:-BackgroundCompilation -XX:-TieredCompilation -XX:CompileThreshold=1000
|
||||
* -XX:CompileCommand=exclude,NullCheckDroppingsTest::runTest NullCheckDroppingsTest
|
||||
*/
|
||||
|
||||
import sun.hotspot.WhiteBox;
|
||||
import sun.hotspot.code.NMethod;
|
||||
import com.oracle.java.testlibrary.Platform;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
import java.lang.invoke.MethodHandle;
|
||||
import java.lang.invoke.MethodHandles;
|
||||
import java.lang.invoke.MethodType;
|
||||
import java.util.function.BiFunction;
|
||||
|
||||
public class NullCheckDroppingsTest {
|
||||
|
||||
private static final WhiteBox WHITE_BOX = WhiteBox.getWhiteBox();
|
||||
|
||||
static final BiFunction<Class, Object, Object> fCast = (c, o) -> c.cast(o);
|
||||
|
||||
static final MethodHandle SET_SSINK;
|
||||
static final MethodHandle MH_CAST;
|
||||
|
||||
static {
|
||||
try {
|
||||
SET_SSINK = MethodHandles.lookup().findSetter(NullCheckDroppingsTest.class, "ssink", String.class);
|
||||
MH_CAST = MethodHandles.lookup().findVirtual(Class.class,
|
||||
"cast",
|
||||
MethodType.methodType(Object.class, Object.class));
|
||||
}
|
||||
catch (Exception e) {
|
||||
throw new Error(e);
|
||||
}
|
||||
}
|
||||
|
||||
static volatile String svalue = "A";
|
||||
static volatile String snull = null;
|
||||
static volatile Integer iobj = new Integer(0);
|
||||
static volatile int[] arr = new int[2];
|
||||
static volatile Class objClass = String.class;
|
||||
static volatile Class nullClass = null;
|
||||
|
||||
String ssink;
|
||||
Integer isink;
|
||||
int[] asink;
|
||||
|
||||
public static void main(String[] args) throws Exception {
|
||||
|
||||
// Only test C2 in Server VM
|
||||
if (!Platform.isServer()) {
|
||||
return;
|
||||
}
|
||||
// Make sure background compilation is disabled
|
||||
if (WHITE_BOX.getBooleanVMFlag("BackgroundCompilation")) {
|
||||
throw new AssertionError("Background compilation enabled");
|
||||
}
|
||||
// Make sure Tiered compilation is disabled
|
||||
if (WHITE_BOX.getBooleanVMFlag("TieredCompilation")) {
|
||||
throw new AssertionError("Tiered compilation enabled");
|
||||
}
|
||||
|
||||
Method methodClassCast = NullCheckDroppingsTest.class.getDeclaredMethod("testClassCast", String.class);
|
||||
Method methodMHCast = NullCheckDroppingsTest.class.getDeclaredMethod("testMHCast", String.class);
|
||||
Method methodMHSetter = NullCheckDroppingsTest.class.getDeclaredMethod("testMHSetter", String.class);
|
||||
Method methodFunction = NullCheckDroppingsTest.class.getDeclaredMethod("testFunction", String.class);
|
||||
|
||||
NullCheckDroppingsTest t = new NullCheckDroppingsTest();
|
||||
t.runTest(methodClassCast, false);
|
||||
t.runTest(methodMHCast, false);
|
||||
t.runTest(methodMHSetter, false);
|
||||
t.runTest(methodFunction, false);
|
||||
|
||||
// Edge cases
|
||||
Method methodClassCastNull = NullCheckDroppingsTest.class.getDeclaredMethod("testClassCastNull", String.class);
|
||||
Method methodNullClassCast = NullCheckDroppingsTest.class.getDeclaredMethod("testNullClassCast", String.class);
|
||||
Method methodClassCastObj = NullCheckDroppingsTest.class.getDeclaredMethod("testClassCastObj", Object.class);
|
||||
Method methodObjClassCast = NullCheckDroppingsTest.class.getDeclaredMethod("testObjClassCast", String.class);
|
||||
Method methodVarClassCast = NullCheckDroppingsTest.class.getDeclaredMethod("testVarClassCast", String.class);
|
||||
Method methodClassCastInt = NullCheckDroppingsTest.class.getDeclaredMethod("testClassCastInt", Object.class);
|
||||
Method methodIntClassCast = NullCheckDroppingsTest.class.getDeclaredMethod("testIntClassCast", Object.class);
|
||||
Method methodClassCastint = NullCheckDroppingsTest.class.getDeclaredMethod("testClassCastint", Object.class);
|
||||
Method methodintClassCast = NullCheckDroppingsTest.class.getDeclaredMethod("testintClassCast", Object.class);
|
||||
Method methodClassCastPrim = NullCheckDroppingsTest.class.getDeclaredMethod("testClassCastPrim", Object.class);
|
||||
Method methodPrimClassCast = NullCheckDroppingsTest.class.getDeclaredMethod("testPrimClassCast", Object.class);
|
||||
|
||||
t.runTest(methodClassCastNull, false);
|
||||
t.runTest(methodNullClassCast, false);
|
||||
t.runTest(methodClassCastObj, false);
|
||||
t.runTest(methodObjClassCast, true);
|
||||
t.runTest(methodVarClassCast, true);
|
||||
t.runTest(methodClassCastInt, false);
|
||||
t.runTest(methodIntClassCast, true);
|
||||
t.runTest(methodClassCastint, false);
|
||||
t.runTest(methodintClassCast, false);
|
||||
t.runTest(methodClassCastPrim, false);
|
||||
t.runTest(methodPrimClassCast, true);
|
||||
}
|
||||
|
||||
void testClassCast(String s) {
|
||||
try {
|
||||
ssink = String.class.cast(s);
|
||||
} catch (Throwable t) {
|
||||
throw new Error(t);
|
||||
}
|
||||
}
|
||||
|
||||
void testClassCastNull(String s) {
|
||||
try {
|
||||
ssink = String.class.cast(null);
|
||||
} catch (Throwable t) {
|
||||
throw new Error(t);
|
||||
}
|
||||
}
|
||||
|
||||
void testNullClassCast(String s) {
|
||||
try {
|
||||
ssink = (String)nullClass.cast(s);
|
||||
throw new AssertionError("NullPointerException is not thrown");
|
||||
} catch (NullPointerException t) {
|
||||
// Ignore NullPointerException
|
||||
} catch (Throwable t) {
|
||||
throw new Error(t);
|
||||
}
|
||||
}
|
||||
|
||||
void testClassCastObj(Object s) {
|
||||
try {
|
||||
ssink = String.class.cast(s);
|
||||
} catch (Throwable t) {
|
||||
throw new Error(t);
|
||||
}
|
||||
}
|
||||
|
||||
void testObjClassCast(String s) {
|
||||
try {
|
||||
ssink = (String)objClass.cast(s);
|
||||
} catch (Throwable t) {
|
||||
throw new Error(t);
|
||||
}
|
||||
}
|
||||
|
||||
void testVarClassCast(String s) {
|
||||
Class cl = (s == null) ? null : String.class;
|
||||
try {
|
||||
ssink = (String)cl.cast(svalue);
|
||||
if (s == null) {
|
||||
throw new AssertionError("NullPointerException is not thrown");
|
||||
}
|
||||
} catch (NullPointerException t) {
|
||||
// Ignore NullPointerException
|
||||
} catch (Throwable t) {
|
||||
throw new Error(t);
|
||||
}
|
||||
}
|
||||
|
||||
void testClassCastInt(Object s) {
|
||||
try {
|
||||
ssink = String.class.cast(iobj);
|
||||
throw new AssertionError("ClassCastException is not thrown");
|
||||
} catch (ClassCastException t) {
|
||||
// Ignore ClassCastException: Cannot cast java.lang.Integer to java.lang.String
|
||||
} catch (Throwable t) {
|
||||
throw new Error(t);
|
||||
}
|
||||
}
|
||||
|
||||
void testIntClassCast(Object s) {
|
||||
try {
|
||||
isink = Integer.class.cast(s);
|
||||
if (s != null) {
|
||||
throw new AssertionError("ClassCastException is not thrown");
|
||||
}
|
||||
} catch (ClassCastException t) {
|
||||
// Ignore ClassCastException: Cannot cast java.lang.String to java.lang.Integer
|
||||
} catch (Throwable t) {
|
||||
throw new Error(t);
|
||||
}
|
||||
}
|
||||
|
||||
void testClassCastint(Object s) {
|
||||
try {
|
||||
ssink = String.class.cast(45);
|
||||
throw new AssertionError("ClassCastException is not thrown");
|
||||
} catch (ClassCastException t) {
|
||||
// Ignore ClassCastException: Cannot cast java.lang.Integer to java.lang.String
|
||||
} catch (Throwable t) {
|
||||
throw new Error(t);
|
||||
}
|
||||
}
|
||||
|
||||
void testintClassCast(Object s) {
|
||||
try {
|
||||
isink = int.class.cast(s);
|
||||
if (s != null) {
|
||||
throw new AssertionError("ClassCastException is not thrown");
|
||||
}
|
||||
} catch (ClassCastException t) {
|
||||
// Ignore ClassCastException: Cannot cast java.lang.String to java.lang.Integer
|
||||
} catch (Throwable t) {
|
||||
throw new Error(t);
|
||||
}
|
||||
}
|
||||
|
||||
void testClassCastPrim(Object s) {
|
||||
try {
|
||||
ssink = String.class.cast(arr);
|
||||
throw new AssertionError("ClassCastException is not thrown");
|
||||
} catch (ClassCastException t) {
|
||||
// Ignore ClassCastException: Cannot cast [I to java.lang.String
|
||||
} catch (Throwable t) {
|
||||
throw new Error(t);
|
||||
}
|
||||
}
|
||||
|
||||
void testPrimClassCast(Object s) {
|
||||
try {
|
||||
asink = int[].class.cast(s);
|
||||
if (s != null) {
|
||||
throw new AssertionError("ClassCastException is not thrown");
|
||||
}
|
||||
} catch (ClassCastException t) {
|
||||
// Ignore ClassCastException: Cannot cast java.lang.String to [I
|
||||
} catch (Throwable t) {
|
||||
throw new Error(t);
|
||||
}
|
||||
}
|
||||
|
||||
void testMHCast(String s) {
|
||||
try {
|
||||
ssink = (String) (Object) MH_CAST.invokeExact(String.class, (Object) s);
|
||||
} catch (Throwable t) {
|
||||
throw new Error(t);
|
||||
}
|
||||
}
|
||||
|
||||
void testMHSetter(String s) {
|
||||
try {
|
||||
SET_SSINK.invokeExact(this, s);
|
||||
} catch (Throwable t) {
|
||||
throw new Error(t);
|
||||
}
|
||||
}
|
||||
|
||||
void testFunction(String s) {
|
||||
try {
|
||||
ssink = (String) fCast.apply(String.class, s);
|
||||
} catch (Throwable t) {
|
||||
throw new Error(t);
|
||||
}
|
||||
}
|
||||
|
||||
void runTest(Method method, boolean deopt) {
|
||||
if (method == null) {
|
||||
throw new AssertionError("method was not found");
|
||||
}
|
||||
// Ensure method is compiled
|
||||
WHITE_BOX.testSetDontInlineMethod(method, true);
|
||||
for (int i = 0; i < 3000; i++) {
|
||||
try {
|
||||
method.invoke(this, svalue);
|
||||
} catch (Exception e) {
|
||||
throw new Error("Unexpected exception: ", e);
|
||||
}
|
||||
}
|
||||
NMethod nm = getNMethod(method);
|
||||
|
||||
// Passing null should cause a de-optimization
|
||||
// if method is compiled with a null-check.
|
||||
try {
|
||||
method.invoke(this, snull);
|
||||
} catch (Exception e) {
|
||||
throw new Error("Unexpected exception: ", e);
|
||||
}
|
||||
checkDeoptimization(method, nm, deopt);
|
||||
}
|
||||
|
||||
static NMethod getNMethod(Method test) {
|
||||
// Because background compilation is disabled, method should now be compiled
|
||||
if (!WHITE_BOX.isMethodCompiled(test)) {
|
||||
throw new AssertionError(test + " not compiled");
|
||||
}
|
||||
|
||||
NMethod nm = NMethod.get(test, false); // not OSR nmethod
|
||||
if (nm == null) {
|
||||
throw new AssertionError(test + " missing nmethod?");
|
||||
}
|
||||
if (nm.comp_level != 4) {
|
||||
throw new AssertionError(test + " compiled by not C2: " + nm);
|
||||
}
|
||||
return nm;
|
||||
}
|
||||
|
||||
static void checkDeoptimization(Method method, NMethod nmOrig, boolean deopt) {
|
||||
// Check deoptimization event (intrinsic Class.cast() works).
|
||||
if (WHITE_BOX.isMethodCompiled(method) == deopt) {
|
||||
throw new AssertionError(method + " was" + (deopt ? " not" : "") + " deoptimized");
|
||||
}
|
||||
if (deopt) {
|
||||
return;
|
||||
}
|
||||
// Ensure no recompilation when no deoptimization is expected.
|
||||
NMethod nm = NMethod.get(method, false); // not OSR nmethod
|
||||
if (nm == null) {
|
||||
throw new AssertionError(method + " missing nmethod?");
|
||||
}
|
||||
if (nm.comp_level != 4) {
|
||||
throw new AssertionError(method + " compiled by not C2: " + nm);
|
||||
}
|
||||
if (nm.compile_id != nmOrig.compile_id) {
|
||||
throw new AssertionError(method + " was recompiled: old nmethod=" + nmOrig + ", new nmethod=" + nm);
|
||||
}
|
||||
}
|
||||
}
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8024924
|
||||
* @summary Test constant addExact
|
||||
* @library /testlibrary
|
||||
* @compile AddExactIConstantTest.java Verify.java
|
||||
* @run main AddExactIConstantTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8024924
|
||||
* @summary Test non constant addExact
|
||||
* @library /testlibrary
|
||||
* @compile AddExactILoadTest.java Verify.java
|
||||
* @run main AddExactILoadTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8024924
|
||||
* @summary Test non constant addExact
|
||||
* @library /testlibrary
|
||||
* @compile AddExactILoopDependentTest.java Verify.java
|
||||
* @run main AddExactILoopDependentTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8024924
|
||||
* @summary Test non constant addExact
|
||||
* @library /testlibrary
|
||||
* @compile AddExactINonConstantTest.java Verify.java
|
||||
* @run main AddExactINonConstantTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,11 +25,15 @@
|
||||
* @test
|
||||
* @bug 8025657
|
||||
* @summary Test repeating addExact
|
||||
* @library /testlibrary
|
||||
* @compile AddExactIRepeatTest.java Verify.java
|
||||
* @run main AddExactIRepeatTest
|
||||
*
|
||||
*/
|
||||
|
||||
import com.oracle.java.testlibrary.Utils;
|
||||
import java.util.Random;
|
||||
|
||||
public class AddExactIRepeatTest {
|
||||
public static void main(String[] args) {
|
||||
runTest(new Verify.AddExactI());
|
||||
@ -44,7 +48,7 @@ public class AddExactIRepeatTest {
|
||||
}
|
||||
|
||||
public static void runTest(Verify.BinaryMethod method) {
|
||||
java.util.Random rnd = new java.util.Random();
|
||||
Random rnd = Utils.getRandomInstance();
|
||||
for (int i = 0; i < 50000; ++i) {
|
||||
int x = Integer.MAX_VALUE - 10;
|
||||
int y = Integer.MAX_VALUE - 10 + rnd.nextInt(5);
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test constant addExact
|
||||
* @library /testlibrary
|
||||
* @compile AddExactLConstantTest.java Verify.java
|
||||
* @run main AddExactLConstantTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test non constant addExact
|
||||
* @library /testlibrary
|
||||
* @compile AddExactLNonConstantTest.java Verify.java
|
||||
* @run main AddExactLNonConstantTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test decrementExact
|
||||
* @library /testlibrary
|
||||
* @compile DecExactITest.java Verify.java
|
||||
* @run main DecExactITest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test decrementExact
|
||||
* @library /testlibrary
|
||||
* @compile DecExactLTest.java Verify.java
|
||||
* @run main DecExactLTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test incrementExact
|
||||
* @library /testlibrary
|
||||
* @compile IncExactITest.java Verify.java
|
||||
* @run main IncExactITest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test incrementExact
|
||||
* @library /testlibrary
|
||||
* @compile IncExactLTest.java Verify.java
|
||||
* @run main IncExactLTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test constant multiplyExact
|
||||
* @library /testlibrary
|
||||
* @compile MulExactIConstantTest.java Verify.java
|
||||
* @run main MulExactIConstantTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test multiplyExact
|
||||
* @library /testlibrary
|
||||
* @compile MulExactILoadTest.java Verify.java
|
||||
* @run main MulExactILoadTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test loop dependent multiplyExact
|
||||
* @library /testlibrary
|
||||
* @compile MulExactILoopDependentTest.java Verify.java
|
||||
* @run main MulExactILoopDependentTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test non constant multiplyExact
|
||||
* @library /testlibrary
|
||||
* @compile MulExactINonConstantTest.java Verify.java
|
||||
* @run main MulExactINonConstantTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,11 +25,15 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test repeating multiplyExact
|
||||
* @library /testlibrary
|
||||
* @compile MulExactIRepeatTest.java Verify.java
|
||||
* @run main MulExactIRepeatTest
|
||||
*
|
||||
*/
|
||||
|
||||
import com.oracle.java.testlibrary.Utils;
|
||||
import java.util.Random;
|
||||
|
||||
public class MulExactIRepeatTest {
|
||||
public static void main(String[] args) {
|
||||
runTest(new Verify.MulExactI());
|
||||
@ -44,7 +48,7 @@ public class MulExactIRepeatTest {
|
||||
}
|
||||
|
||||
public static void runTest(Verify.BinaryMethod method) {
|
||||
java.util.Random rnd = new java.util.Random();
|
||||
Random rnd = Utils.getRandomInstance();
|
||||
for (int i = 0; i < 50000; ++i) {
|
||||
int x = Integer.MAX_VALUE - 10;
|
||||
int y = Integer.MAX_VALUE - 10 + rnd.nextInt(5);
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test constant mulExact
|
||||
* @library /testlibrary
|
||||
* @compile MulExactLConstantTest.java Verify.java
|
||||
* @run main MulExactLConstantTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test non constant mulExact
|
||||
* @library /testlibrary
|
||||
* @compile MulExactLNonConstantTest.java Verify.java
|
||||
* @run main MulExactLNonConstantTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test constant negExact
|
||||
* @library /testlibrary
|
||||
* @compile NegExactIConstantTest.java Verify.java
|
||||
* @run main NegExactIConstantTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test negExact
|
||||
* @library /testlibrary
|
||||
* @compile NegExactILoadTest.java Verify.java
|
||||
* @run main NegExactILoadTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test negExact loop dependent
|
||||
* @library /testlibrary
|
||||
* @compile NegExactILoopDependentTest.java Verify.java
|
||||
* @run main NegExactILoopDependentTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test non constant negExact
|
||||
* @library /testlibrary
|
||||
* @compile NegExactINonConstantTest.java Verify.java
|
||||
* @run main NegExactINonConstantTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test constant negExact
|
||||
* @library /testlibrary
|
||||
* @compile NegExactLConstantTest.java Verify.java
|
||||
* @run main NegExactLConstantTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test constant negExact
|
||||
* @library /testlibrary
|
||||
* @compile NegExactLNonConstantTest.java Verify.java
|
||||
* @run main NegExactLNonConstantTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test subtractExact as condition
|
||||
* @library /testlibrary
|
||||
* @compile SubExactICondTest.java Verify.java
|
||||
* @run main SubExactICondTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test constant subtractExact
|
||||
* @library /testlibrary
|
||||
* @compile SubExactIConstantTest.java Verify.java
|
||||
* @run main SubExactIConstantTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test non constant subtractExact
|
||||
* @library /testlibrary
|
||||
* @compile SubExactILoadTest.java Verify.java
|
||||
* @run main SubExactILoadTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test non constant subtractExact
|
||||
* @library /testlibrary
|
||||
* @compile SubExactILoopDependentTest.java Verify.java
|
||||
* @run main SubExactILoopDependentTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,6 +25,7 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test non constant subtractExact
|
||||
* @library /testlibrary
|
||||
* @compile SubExactINonConstantTest.java Verify.java
|
||||
* @run main SubExactINonConstantTest
|
||||
*
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2013, 2014, 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
|
||||
@ -25,12 +25,14 @@
|
||||
* @test
|
||||
* @bug 8026844
|
||||
* @summary Test repeating subtractExact
|
||||
* @library /testlibrary
|
||||
* @compile SubExactIRepeatTest.java Verify.java
|
||||
* @run main SubExactIRepeatTest
|
||||
*
|
||||
*/
|
||||
|
||||
import java.lang.ArithmeticException;
|
||||
import com.oracle.java.testlibrary.Utils;
|
||||
import java.util.Random;
|
||||
|
||||
public class SubExactIRepeatTest {
|
||||
public static void main(String[] args) {
|
||||
@ -46,7 +48,7 @@ public class SubExactIRepeatTest {
|
||||
}
|
||||
|
||||
public static void runTest(Verify.BinaryMethod method) {
|
||||
java.util.Random rnd = new java.util.Random();
|
||||
Random rnd = Utils.getRandomInstance();
|
||||
for (int i = 0; i < 50000; ++i) {
|
||||
int x = Integer.MIN_VALUE + 10;
|
||||
int y = Integer.MAX_VALUE - 10 + rnd.nextInt(5);
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user