# HG changeset patch # User lana # Date 1474569140 0 # Node ID b4b4c1119f39f3c2bbb3eeacf5e8a6e3ea61d61d # Parent 4f1591515aef46a9b4788c0927f95154bd6f3d01# Parent 20cec2b18e9a971f0e0ced3f1ace9594d895f6c1 Merge diff -r 4f1591515aef -r b4b4c1119f39 hotspot/make/test/JtregNative.gmk --- a/hotspot/make/test/JtregNative.gmk Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/make/test/JtregNative.gmk Thu Sep 22 18:32:20 2016 +0000 @@ -44,6 +44,7 @@ $(HOTSPOT_TOPDIR)/test/native_sanity \ $(HOTSPOT_TOPDIR)/test/runtime/jni/8025979 \ $(HOTSPOT_TOPDIR)/test/runtime/jni/8033445 \ + $(HOTSPOT_TOPDIR)/test/runtime/jni/checked \ $(HOTSPOT_TOPDIR)/test/runtime/jni/ToStringInInterfaceTest \ $(HOTSPOT_TOPDIR)/test/runtime/modules/getModuleJNI \ $(HOTSPOT_TOPDIR)/test/runtime/SameObject \ diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/cpu/aarch64/vm/interp_masm_aarch64.cpp --- a/hotspot/src/cpu/aarch64/vm/interp_masm_aarch64.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/cpu/aarch64/vm/interp_masm_aarch64.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -326,7 +326,8 @@ } void InterpreterMacroAssembler::push_l(Register r) { - str(r, pre(esp, 2 * -wordSize)); + str(zr, pre(esp, -wordSize)); + str(r, pre(esp, -wordsize)); } void InterpreterMacroAssembler::pop_f(FloatRegister r) { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/cpu/aarch64/vm/sharedRuntime_aarch64.cpp --- a/hotspot/src/cpu/aarch64/vm/sharedRuntime_aarch64.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/cpu/aarch64/vm/sharedRuntime_aarch64.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -2041,6 +2041,11 @@ __ verify_oop(r0); } + if (CheckJNICalls) { + // clear_pending_jni_exception_check + __ str(zr, Address(rthread, JavaThread::pending_jni_exception_check_fn_offset())); + } + if (!is_critical_native) { // reset handle block __ ldr(r2, Address(rthread, JavaThread::active_handles_offset())); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/cpu/aarch64/vm/templateInterpreterGenerator_aarch64.cpp --- a/hotspot/src/cpu/aarch64/vm/templateInterpreterGenerator_aarch64.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/cpu/aarch64/vm/templateInterpreterGenerator_aarch64.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -1355,6 +1355,11 @@ // reset_last_Java_frame __ reset_last_Java_frame(true); + if (CheckJNICalls) { + // clear_pending_jni_exception_check + __ str(zr, Address(rthread, JavaThread::pending_jni_exception_check_fn_offset())); + } + // reset handle block __ ldr(t, Address(rthread, JavaThread::active_handles_offset())); __ str(zr, Address(t, JNIHandleBlock::top_offset_in_bytes())); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/cpu/sparc/vm/globals_sparc.hpp --- a/hotspot/src/cpu/sparc/vm/globals_sparc.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/cpu/sparc/vm/globals_sparc.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -57,10 +57,12 @@ #ifdef _LP64 // Stack slots are 2X larger in LP64 than in the 32 bit VM. +define_pd_global(intx, CompilerThreadStackSize, 1024); define_pd_global(intx, ThreadStackSize, 1024); define_pd_global(intx, VMThreadStackSize, 1024); #define DEFAULT_STACK_SHADOW_PAGES (20 DEBUG_ONLY(+2)) #else +define_pd_global(intx, CompilerThreadStackSize, 512); define_pd_global(intx, ThreadStackSize, 512); define_pd_global(intx, VMThreadStackSize, 512); #define DEFAULT_STACK_SHADOW_PAGES (6 DEBUG_ONLY(+2)) diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/cpu/sparc/vm/interp_masm_sparc.cpp --- a/hotspot/src/cpu/sparc/vm/interp_masm_sparc.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/cpu/sparc/vm/interp_masm_sparc.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -359,7 +359,7 @@ #ifdef _LP64 stx(l, r1, offset); // store something more useful here - debug_only(stx(G0, r1, offset+Interpreter::stackElementSize);) + stx(G0, r1, offset+Interpreter::stackElementSize); #else st(l, r1, offset); st(l->successor(), r1, offset + Interpreter::stackElementSize); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/cpu/sparc/vm/sharedRuntime_sparc.cpp --- a/hotspot/src/cpu/sparc/vm/sharedRuntime_sparc.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/cpu/sparc/vm/sharedRuntime_sparc.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -2765,6 +2765,11 @@ __ verify_oop(I0); } + if (CheckJNICalls) { + // clear_pending_jni_exception_check + __ st_ptr(G0, G2_thread, JavaThread::pending_jni_exception_check_fn_offset()); + } + if (!is_critical_native) { // reset handle block __ ld_ptr(G2_thread, in_bytes(JavaThread::active_handles_offset()), L5); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/cpu/sparc/vm/sparc.ad --- a/hotspot/src/cpu/sparc/vm/sparc.ad Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/cpu/sparc/vm/sparc.ad Thu Sep 22 18:32:20 2016 +0000 @@ -2921,6 +2921,26 @@ __ cmp( Rold, O7 ); %} + // raw int cas without using tmp register for compareAndExchange + enc_class enc_casi_exch( iRegP mem, iRegL old, iRegL new) %{ + Register Rmem = reg_to_register_object($mem$$reg); + Register Rold = reg_to_register_object($old$$reg); + Register Rnew = reg_to_register_object($new$$reg); + + MacroAssembler _masm(&cbuf); + __ cas(Rmem, Rold, Rnew); + %} + + // 64-bit cas without using tmp register for compareAndExchange + enc_class enc_casx_exch( iRegP mem, iRegL old, iRegL new) %{ + Register Rmem = reg_to_register_object($mem$$reg); + Register Rold = reg_to_register_object($old$$reg); + Register Rnew = reg_to_register_object($new$$reg); + + MacroAssembler _masm(&cbuf); + __ casx(Rmem, Rold, Rnew); + %} + enc_class enc_lflags_ne_to_boolean( iRegI res ) %{ Register Rres = reg_to_register_object($res$$reg); @@ -7105,6 +7125,7 @@ instruct compareAndSwapL_bool(iRegP mem_ptr, iRegL oldval, iRegL newval, iRegI res, o7RegI tmp1, flagsReg ccr ) %{ predicate(VM_Version::supports_cx8()); match(Set res (CompareAndSwapL mem_ptr (Binary oldval newval))); + match(Set res (WeakCompareAndSwapL mem_ptr (Binary oldval newval))); effect( USE mem_ptr, KILL ccr, KILL tmp1); format %{ "MOV $newval,O7\n\t" @@ -7121,6 +7142,7 @@ instruct compareAndSwapI_bool(iRegP mem_ptr, iRegI oldval, iRegI newval, iRegI res, o7RegI tmp1, flagsReg ccr ) %{ match(Set res (CompareAndSwapI mem_ptr (Binary oldval newval))); + match(Set res (WeakCompareAndSwapI mem_ptr (Binary oldval newval))); effect( USE mem_ptr, KILL ccr, KILL tmp1); format %{ "MOV $newval,O7\n\t" @@ -7139,6 +7161,7 @@ predicate(VM_Version::supports_cx8()); #endif match(Set res (CompareAndSwapP mem_ptr (Binary oldval newval))); + match(Set res (WeakCompareAndSwapP mem_ptr (Binary oldval newval))); effect( USE mem_ptr, KILL ccr, KILL tmp1); format %{ "MOV $newval,O7\n\t" @@ -7159,6 +7182,7 @@ instruct compareAndSwapN_bool(iRegP mem_ptr, iRegN oldval, iRegN newval, iRegI res, o7RegI tmp1, flagsReg ccr ) %{ match(Set res (CompareAndSwapN mem_ptr (Binary oldval newval))); + match(Set res (WeakCompareAndSwapN mem_ptr (Binary oldval newval))); effect( USE mem_ptr, KILL ccr, KILL tmp1); format %{ "MOV $newval,O7\n\t" @@ -7172,6 +7196,54 @@ ins_pipe( long_memory_op ); %} +instruct compareAndExchangeI(iRegP mem_ptr, iRegI oldval, iRegI newval) +%{ + match(Set newval (CompareAndExchangeI mem_ptr (Binary oldval newval))); + effect( USE mem_ptr ); + + format %{ + "CASA [$mem_ptr],$oldval,$newval\t! If $oldval==[$mem_ptr] Then store $newval into [$mem_ptr] and set $newval=[$mem_ptr]\n\t" + %} + ins_encode( enc_casi_exch(mem_ptr, oldval, newval) ); + ins_pipe( long_memory_op ); +%} + +instruct compareAndExchangeL(iRegP mem_ptr, iRegL oldval, iRegL newval) +%{ + match(Set newval (CompareAndExchangeL mem_ptr (Binary oldval newval))); + effect( USE mem_ptr ); + + format %{ + "CASXA [$mem_ptr],$oldval,$newval\t! If $oldval==[$mem_ptr] Then store $newval into [$mem_ptr] and set $newval=[$mem_ptr]\n\t" + %} + ins_encode( enc_casx_exch(mem_ptr, oldval, newval) ); + ins_pipe( long_memory_op ); +%} + +instruct compareAndExchangeP(iRegP mem_ptr, iRegP oldval, iRegP newval) +%{ + match(Set newval (CompareAndExchangeP mem_ptr (Binary oldval newval))); + effect( USE mem_ptr ); + + format %{ + "CASXA [$mem_ptr],$oldval,$newval\t! If $oldval==[$mem_ptr] Then store $newval into [$mem_ptr] and set $newval=[$mem_ptr]\n\t" + %} + ins_encode( enc_casx_exch(mem_ptr, oldval, newval) ); + ins_pipe( long_memory_op ); +%} + +instruct compareAndExchangeN(iRegP mem_ptr, iRegN oldval, iRegN newval) +%{ + match(Set newval (CompareAndExchangeN mem_ptr (Binary oldval newval))); + effect( USE mem_ptr ); + + format %{ + "CASA [$mem_ptr],$oldval,$newval\t! If $oldval==[$mem_ptr] Then store $newval into [$mem_ptr] and set $newval=[$mem_ptr]\n\t" + %} + ins_encode( enc_casi_exch(mem_ptr, oldval, newval) ); + ins_pipe( long_memory_op ); +%} + instruct xchgI( memory mem, iRegI newval) %{ match(Set newval (GetAndSetI mem newval)); format %{ "SWAP [$mem],$newval" %} diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/cpu/sparc/vm/templateInterpreterGenerator_sparc.cpp --- a/hotspot/src/cpu/sparc/vm/templateInterpreterGenerator_sparc.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/cpu/sparc/vm/templateInterpreterGenerator_sparc.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -1487,6 +1487,11 @@ __ set(_thread_in_Java, G3_scratch); __ st(G3_scratch, thread_state); + if (CheckJNICalls) { + // clear_pending_jni_exception_check + __ st_ptr(G0, G2_thread, JavaThread::pending_jni_exception_check_fn_offset()); + } + // reset handle block __ ld_ptr(G2_thread, JavaThread::active_handles_offset(), G3_scratch); __ st(G0, G3_scratch, JNIHandleBlock::top_offset_in_bytes()); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/cpu/x86/vm/interp_masm_x86.cpp --- a/hotspot/src/cpu/x86/vm/interp_masm_x86.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/cpu/x86/vm/interp_masm_x86.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -611,7 +611,8 @@ void InterpreterMacroAssembler::push_l(Register r) { subptr(rsp, 2 * wordSize); - movq(Address(rsp, 0), r); + movptr(Address(rsp, Interpreter::expr_offset_in_bytes(0)), r ); + movptr(Address(rsp, Interpreter::expr_offset_in_bytes(1)), NULL_WORD ); } void InterpreterMacroAssembler::pop(TosState state) { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/cpu/x86/vm/macroAssembler_x86.cpp --- a/hotspot/src/cpu/x86/vm/macroAssembler_x86.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/cpu/x86/vm/macroAssembler_x86.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -8131,8 +8131,7 @@ jmp(FALSE_LABEL); clear_vector_masking(); // closing of the stub context for programming mask registers - } - else { + } else { movl(result, len); // copy if (UseAVX == 2 && UseSSE >= 2) { @@ -8169,8 +8168,7 @@ bind(COMPARE_TAIL); // len is zero movl(len, result); // Fallthru to tail compare - } - else if (UseSSE42Intrinsics) { + } else if (UseSSE42Intrinsics) { // With SSE4.2, use double quad vector compare Label COMPARE_WIDE_VECTORS, COMPARE_TAIL; @@ -10748,7 +10746,10 @@ // save length for return push(len); + // 8165287: EVEX version disabled for now, needs to be refactored as + // it is returning incorrect results. if ((UseAVX > 2) && // AVX512 + 0 && VM_Version::supports_avx512vlbw() && VM_Version::supports_bmi2()) { @@ -11067,10 +11068,11 @@ bind(below_threshold); bind(copy_new_tail); - if (UseAVX > 2) { + if ((UseAVX > 2) && + VM_Version::supports_avx512vlbw() && + VM_Version::supports_bmi2()) { movl(tmp2, len); - } - else { + } else { movl(len, tmp2); } andl(tmp2, 0x00000007); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/cpu/x86/vm/sharedRuntime_x86_32.cpp --- a/hotspot/src/cpu/x86/vm/sharedRuntime_x86_32.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/cpu/x86/vm/sharedRuntime_x86_32.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -2236,6 +2236,11 @@ __ verify_oop(rax); } + if (CheckJNICalls) { + // clear_pending_jni_exception_check + __ movptr(Address(thread, JavaThread::pending_jni_exception_check_fn_offset()), NULL_WORD); + } + if (!is_critical_native) { // reset handle block __ movptr(rcx, Address(thread, JavaThread::active_handles_offset())); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/cpu/x86/vm/sharedRuntime_x86_64.cpp --- a/hotspot/src/cpu/x86/vm/sharedRuntime_x86_64.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/cpu/x86/vm/sharedRuntime_x86_64.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -2589,6 +2589,11 @@ __ verify_oop(rax); } + if (CheckJNICalls) { + // clear_pending_jni_exception_check + __ movptr(Address(r15_thread, JavaThread::pending_jni_exception_check_fn_offset()), NULL_WORD); + } + if (!is_critical_native) { // reset handle block __ movptr(rcx, Address(r15_thread, JavaThread::active_handles_offset())); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/cpu/x86/vm/templateInterpreterGenerator_x86.cpp --- a/hotspot/src/cpu/x86/vm/templateInterpreterGenerator_x86.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/cpu/x86/vm/templateInterpreterGenerator_x86.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -1169,6 +1169,11 @@ // reset_last_Java_frame __ reset_last_Java_frame(thread, true); + if (CheckJNICalls) { + // clear_pending_jni_exception_check + __ movptr(Address(thread, JavaThread::pending_jni_exception_check_fn_offset()), NULL_WORD); + } + // reset handle block __ movptr(t, Address(thread, JavaThread::active_handles_offset())); __ movl(Address(t, JNIHandleBlock::top_offset_in_bytes()), (int32_t)NULL_WORD); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/jdk.hotspot.agent/share/classes/sun/jvm/hotspot/utilities/GrowableArray.java --- a/hotspot/src/jdk.hotspot.agent/share/classes/sun/jvm/hotspot/utilities/GrowableArray.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/jdk.hotspot.agent/share/classes/sun/jvm/hotspot/utilities/GrowableArray.java Thu Sep 22 18:32:20 2016 +0000 @@ -65,4 +65,7 @@ super(addr); virtualConstructor = v; } + public Address getData() { + return dataField.getValue(getAddress()); + } } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/CompilerToVM.java --- a/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/CompilerToVM.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/CompilerToVM.java Thu Sep 22 18:32:20 2016 +0000 @@ -366,8 +366,8 @@ * {@code exactReceiver}. * * @param caller the caller or context type used to perform access checks - * @return the link-time resolved method (might be abstract) or {@code 0} if it can not be - * linked + * @return the link-time resolved method (might be abstract) or {@code null} if it is either a + * signature polymorphic method or can not be linked. */ native HotSpotResolvedJavaMethodImpl resolveMethod(HotSpotResolvedObjectTypeImpl exactReceiver, HotSpotResolvedJavaMethodImpl method, HotSpotResolvedObjectTypeImpl caller); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/HotSpotConstantPool.java --- a/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/HotSpotConstantPool.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/HotSpotConstantPool.java Thu Sep 22 18:32:20 2016 +0000 @@ -722,7 +722,7 @@ /** * Determines if {@code type} contains signature polymorphic methods. */ - private static boolean isSignaturePolymorphicHolder(final HotSpotResolvedObjectTypeImpl type) { + static boolean isSignaturePolymorphicHolder(final ResolvedJavaType type) { String name = type.getName(); if (signaturePolymorphicHolders == null) { signaturePolymorphicHolders = compilerToVM().getSignaturePolymorphicHolders(); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/HotSpotResolvedObjectTypeImpl.java --- a/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/HotSpotResolvedObjectTypeImpl.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/HotSpotResolvedObjectTypeImpl.java Thu Sep 22 18:32:20 2016 +0000 @@ -24,6 +24,7 @@ import static java.util.Objects.requireNonNull; import static jdk.vm.ci.hotspot.CompilerToVM.compilerToVM; +import static jdk.vm.ci.hotspot.HotSpotConstantPool.isSignaturePolymorphicHolder; import static jdk.vm.ci.hotspot.HotSpotJVMCIRuntime.runtime; import static jdk.vm.ci.hotspot.HotSpotVMConfig.config; import static jdk.vm.ci.hotspot.UnsafeAccess.UNSAFE; @@ -426,7 +427,7 @@ // Methods can only be resolved against concrete types return null; } - if (method.isConcrete() && method.getDeclaringClass().equals(this) && method.isPublic()) { + if (method.isConcrete() && method.getDeclaringClass().equals(this) && method.isPublic() && !isSignaturePolymorphicHolder(method.getDeclaringClass())) { return method; } if (!method.getDeclaringClass().isAssignableFrom(this)) { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.meta/src/jdk/vm/ci/meta/ResolvedJavaType.java --- a/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.meta/src/jdk/vm/ci/meta/ResolvedJavaType.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.meta/src/jdk/vm/ci/meta/ResolvedJavaType.java Thu Sep 22 18:32:20 2016 +0000 @@ -209,8 +209,8 @@ * * @param method the method to select the implementation of * @param callerType the caller or context type used to perform access checks - * @return the method that would be selected at runtime (might be abstract) or {@code null} if - * it can not be resolved + * @return the link-time resolved method (might be abstract) or {@code null} if it is either a + * signature polymorphic method or can not be linked. */ ResolvedJavaMethod resolveMethod(ResolvedJavaMethod method, ResolvedJavaType callerType); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os/aix/vm/os_aix.cpp --- a/hotspot/src/os/aix/vm/os_aix.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os/aix/vm/os_aix.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -847,7 +847,8 @@ return 0; } -bool os::create_thread(Thread* thread, ThreadType thr_type, size_t stack_size) { +bool os::create_thread(Thread* thread, ThreadType thr_type, + size_t req_stack_size) { assert(thread->osthread() == NULL, "caller responsible"); @@ -880,37 +881,12 @@ guarantee(pthread_attr_setsuspendstate_np(&attr, PTHREAD_CREATE_SUSPENDED_NP) == 0, "???"); // calculate stack size if it's not specified by caller - if (stack_size == 0) { - stack_size = os::Aix::default_stack_size(thr_type); - - switch (thr_type) { - case os::java_thread: - // Java threads use ThreadStackSize whose default value can be changed with the flag -Xss. - assert(JavaThread::stack_size_at_create() > 0, "this should be set"); - stack_size = JavaThread::stack_size_at_create(); - break; - case os::compiler_thread: - if (CompilerThreadStackSize > 0) { - stack_size = (size_t)(CompilerThreadStackSize * K); - break; - } // else fall through: - // use VMThreadStackSize if CompilerThreadStackSize is not defined - case os::vm_thread: - case os::pgc_thread: - case os::cgc_thread: - case os::watcher_thread: - if (VMThreadStackSize > 0) stack_size = (size_t)(VMThreadStackSize * K); - break; - } - } - - stack_size = MAX2(stack_size, os::Aix::min_stack_allowed); + size_t stack_size = os::Posix::get_initial_stack_size(thr_type, req_stack_size); pthread_attr_setstacksize(&attr, stack_size); pthread_t tid; int ret = pthread_create(&tid, &attr, (void* (*)(void*)) thread_native_entry, thread); - char buf[64]; if (ret == 0) { log_info(os, thread)("Thread started (pthread id: " UINTX_FORMAT ", attributes: %s). ", @@ -3593,32 +3569,11 @@ Aix::signal_sets_init(); Aix::install_signal_handlers(); - // Check minimum allowable stack size for thread creation and to initialize - // the java system classes, including StackOverflowError - depends on page - // size. Add two 4K pages for compiler2 recursion in main thread. - // Add in 4*BytesPerWord 4K pages to account for VM stack during - // class initialization depending on 32 or 64 bit VM. - os::Aix::min_stack_allowed = MAX2(os::Aix::min_stack_allowed, - JavaThread::stack_guard_zone_size() + - JavaThread::stack_shadow_zone_size() + - (4*BytesPerWord COMPILER2_PRESENT(+2)) * 4 * K); - - os::Aix::min_stack_allowed = align_size_up(os::Aix::min_stack_allowed, os::vm_page_size()); - - size_t threadStackSizeInBytes = ThreadStackSize * K; - if (threadStackSizeInBytes != 0 && - threadStackSizeInBytes < os::Aix::min_stack_allowed) { - tty->print_cr("\nThe stack size specified is too small, " - "Specify at least %dk", - os::Aix::min_stack_allowed / K); + // Check and sets minimum stack sizes against command line options + if (Posix::set_minimum_stack_sizes() == JNI_ERR) { return JNI_ERR; } - // Make the stack size a multiple of the page size so that - // the yellow/red zones can be guarded. - // Note that this can be 0, if no default stacksize was set. - JavaThread::set_stack_size_at_create(round_to(threadStackSizeInBytes, vm_page_size())); - if (UseNUMA) { UseNUMA = false; warning("NUMA optimizations are not available on this OS."); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os/aix/vm/os_aix.hpp --- a/hotspot/src/os/aix/vm/os_aix.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os/aix/vm/os_aix.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1999, 2016, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 2013, 2016 SAP SE. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * @@ -140,14 +140,6 @@ // libpthread version string static void libpthread_init(); - // Minimum stack size a thread can be created with (allowing - // the VM to completely create the thread and enter user code) - static size_t min_stack_allowed; - - // Return default stack size or guard size for the specified thread type - static size_t default_stack_size(os::ThreadType thr_type); - static size_t default_guard_size(os::ThreadType thr_type); - // Function returns true if we run on OS/400 (pase), false if we run // on AIX. static bool on_pase() { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os/bsd/vm/os_bsd.cpp --- a/hotspot/src/os/bsd/vm/os_bsd.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os/bsd/vm/os_bsd.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -734,7 +734,8 @@ return 0; } -bool os::create_thread(Thread* thread, ThreadType thr_type, size_t stack_size) { +bool os::create_thread(Thread* thread, ThreadType thr_type, + size_t req_stack_size) { assert(thread->osthread() == NULL, "caller responsible"); // Allocate the OSThread object @@ -757,32 +758,7 @@ pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); // calculate stack size if it's not specified by caller - if (stack_size == 0) { - stack_size = os::Bsd::default_stack_size(thr_type); - - switch (thr_type) { - case os::java_thread: - // Java threads use ThreadStackSize which default value can be - // changed with the flag -Xss - assert(JavaThread::stack_size_at_create() > 0, "this should be set"); - stack_size = JavaThread::stack_size_at_create(); - break; - case os::compiler_thread: - if (CompilerThreadStackSize > 0) { - stack_size = (size_t)(CompilerThreadStackSize * K); - break; - } // else fall through: - // use VMThreadStackSize if CompilerThreadStackSize is not defined - case os::vm_thread: - case os::pgc_thread: - case os::cgc_thread: - case os::watcher_thread: - if (VMThreadStackSize > 0) stack_size = (size_t)(VMThreadStackSize * K); - break; - } - } - - stack_size = MAX2(stack_size, os::Bsd::min_stack_allowed); + size_t stack_size = os::Posix::get_initial_stack_size(thr_type, req_stack_size); pthread_attr_setstacksize(&attr, stack_size); ThreadState state; @@ -3502,32 +3478,11 @@ Bsd::signal_sets_init(); Bsd::install_signal_handlers(); - // Check minimum allowable stack size for thread creation and to initialize - // the java system classes, including StackOverflowError - depends on page - // size. Add two 4K pages for compiler2 recursion in main thread. - // Add in 4*BytesPerWord 4K pages to account for VM stack during - // class initialization depending on 32 or 64 bit VM. - os::Bsd::min_stack_allowed = MAX2(os::Bsd::min_stack_allowed, - JavaThread::stack_guard_zone_size() + - JavaThread::stack_shadow_zone_size() + - (4*BytesPerWord COMPILER2_PRESENT(+2)) * 4 * K); - - os::Bsd::min_stack_allowed = align_size_up(os::Bsd::min_stack_allowed, os::vm_page_size()); - - size_t threadStackSizeInBytes = ThreadStackSize * K; - if (threadStackSizeInBytes != 0 && - threadStackSizeInBytes < os::Bsd::min_stack_allowed) { - tty->print_cr("\nThe stack size specified is too small, " - "Specify at least %dk", - os::Bsd::min_stack_allowed/ K); + // Check and sets minimum stack sizes against command line options + if (Posix::set_minimum_stack_sizes() == JNI_ERR) { return JNI_ERR; } - // Make the stack size a multiple of the page size so that - // the yellow/red zones can be guarded. - JavaThread::set_stack_size_at_create(round_to(threadStackSizeInBytes, - vm_page_size())); - if (MaxFDLimit) { // set the number of file descriptors to max. print out error // if getrlimit/setrlimit fails but continue regardless. diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os/bsd/vm/os_bsd.hpp --- a/hotspot/src/os/bsd/vm/os_bsd.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os/bsd/vm/os_bsd.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1999, 2016, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -120,14 +120,6 @@ static struct sigaction *get_chained_signal_action(int sig); static bool chained_handler(int sig, siginfo_t* siginfo, void* context); - // Minimum stack size a thread can be created with (allowing - // the VM to completely create the thread and enter user code) - static size_t min_stack_allowed; - - // Return default stack size or guard size for the specified thread type - static size_t default_stack_size(os::ThreadType thr_type); - static size_t default_guard_size(os::ThreadType thr_type); - // Real-time clock functions static void clock_init(void); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os/linux/vm/os_linux.cpp --- a/hotspot/src/os/linux/vm/os_linux.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os/linux/vm/os_linux.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -701,7 +701,7 @@ } bool os::create_thread(Thread* thread, ThreadType thr_type, - size_t stack_size) { + size_t req_stack_size) { assert(thread->osthread() == NULL, "caller responsible"); // Allocate the OSThread object @@ -723,34 +723,8 @@ pthread_attr_init(&attr); pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); - // stack size // calculate stack size if it's not specified by caller - if (stack_size == 0) { - stack_size = os::Linux::default_stack_size(thr_type); - - switch (thr_type) { - case os::java_thread: - // Java threads use ThreadStackSize which default value can be - // changed with the flag -Xss - assert(JavaThread::stack_size_at_create() > 0, "this should be set"); - stack_size = JavaThread::stack_size_at_create(); - break; - case os::compiler_thread: - if (CompilerThreadStackSize > 0) { - stack_size = (size_t)(CompilerThreadStackSize * K); - break; - } // else fall through: - // use VMThreadStackSize if CompilerThreadStackSize is not defined - case os::vm_thread: - case os::pgc_thread: - case os::cgc_thread: - case os::watcher_thread: - if (VMThreadStackSize > 0) stack_size = (size_t)(VMThreadStackSize * K); - break; - } - } - - stack_size = MAX2(stack_size, os::Linux::min_stack_allowed); + size_t stack_size = os::Posix::get_initial_stack_size(thr_type, req_stack_size); pthread_attr_setstacksize(&attr, stack_size); // glibc guard page @@ -956,10 +930,9 @@ // bogus value for initial thread. void os::Linux::capture_initial_stack(size_t max_size) { // stack size is the easy part, get it from RLIMIT_STACK - size_t stack_size; struct rlimit rlim; getrlimit(RLIMIT_STACK, &rlim); - stack_size = rlim.rlim_cur; + size_t stack_size = rlim.rlim_cur; // 6308388: a bug in ld.so will relocate its own .data section to the // lower end of primordial stack; reduce ulimit -s value a little bit @@ -4793,32 +4766,10 @@ Linux::signal_sets_init(); Linux::install_signal_handlers(); - // Check minimum allowable stack size for thread creation and to initialize - // the java system classes, including StackOverflowError - depends on page - // size. Add two 4K pages for compiler2 recursion in main thread. - // Add in 4*BytesPerWord 4K pages to account for VM stack during - // class initialization depending on 32 or 64 bit VM. - os::Linux::min_stack_allowed = MAX2(os::Linux::min_stack_allowed, - JavaThread::stack_guard_zone_size() + - JavaThread::stack_shadow_zone_size() + - (4*BytesPerWord COMPILER2_PRESENT(+2)) * 4 * K); - - os::Linux::min_stack_allowed = align_size_up(os::Linux::min_stack_allowed, os::vm_page_size()); - - size_t threadStackSizeInBytes = ThreadStackSize * K; - if (threadStackSizeInBytes != 0 && - threadStackSizeInBytes < os::Linux::min_stack_allowed) { - tty->print_cr("\nThe stack size specified is too small, " - "Specify at least " SIZE_FORMAT "k", - os::Linux::min_stack_allowed/ K); + // Check and sets minimum stack sizes against command line options + if (Posix::set_minimum_stack_sizes() == JNI_ERR) { return JNI_ERR; } - - // Make the stack size a multiple of the page size so that - // the yellow/red zones can be guarded. - JavaThread::set_stack_size_at_create(round_to(threadStackSizeInBytes, - vm_page_size())); - Linux::capture_initial_stack(JavaThread::stack_size_at_create()); #if defined(IA32) diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os/linux/vm/os_linux.hpp --- a/hotspot/src/os/linux/vm/os_linux.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os/linux/vm/os_linux.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1999, 2016, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -170,12 +170,8 @@ static void libpthread_init(); static bool libnuma_init(); static void* libnuma_dlsym(void* handle, const char* name); - // Minimum stack size a thread can be created with (allowing - // the VM to completely create the thread and enter user code) - static size_t min_stack_allowed; - // Return default stack size or guard size for the specified thread type - static size_t default_stack_size(os::ThreadType thr_type); + // Return default guard size for the specified thread type static size_t default_guard_size(os::ThreadType thr_type); static void capture_initial_stack(size_t max_size); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os/posix/vm/os_posix.cpp --- a/hotspot/src/os/posix/vm/os_posix.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os/posix/vm/os_posix.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -1099,6 +1099,123 @@ return buf; } +// Check minimum allowable stack sizes for thread creation and to initialize +// the java system classes, including StackOverflowError - depends on page +// size. Add two 4K pages for compiler2 recursion in main thread. +// Add in 4*BytesPerWord 4K pages to account for VM stack during +// class initialization depending on 32 or 64 bit VM. +jint os::Posix::set_minimum_stack_sizes() { + _java_thread_min_stack_allowed = MAX2(_java_thread_min_stack_allowed, + JavaThread::stack_guard_zone_size() + + JavaThread::stack_shadow_zone_size() + + (4 * BytesPerWord COMPILER2_PRESENT(+ 2)) * 4 * K); + + _java_thread_min_stack_allowed = align_size_up(_java_thread_min_stack_allowed, vm_page_size()); + + size_t stack_size_in_bytes = ThreadStackSize * K; + if (stack_size_in_bytes != 0 && + stack_size_in_bytes < _java_thread_min_stack_allowed) { + // The '-Xss' and '-XX:ThreadStackSize=N' options both set + // ThreadStackSize so we go with "Java thread stack size" instead + // of "ThreadStackSize" to be more friendly. + tty->print_cr("\nThe Java thread stack size specified is too small. " + "Specify at least " SIZE_FORMAT "k", + _java_thread_min_stack_allowed / K); + return JNI_ERR; + } + +#ifdef SOLARIS + // For 64kbps there will be a 64kb page size, which makes + // the usable default stack size quite a bit less. Increase the + // stack for 64kb (or any > than 8kb) pages, this increases + // virtual memory fragmentation (since we're not creating the + // stack on a power of 2 boundary. The real fix for this + // should be to fix the guard page mechanism. + + if (vm_page_size() > 8*K) { + stack_size_in_bytes = (stack_size_in_bytes != 0) + ? stack_size_in_bytes + + JavaThread::stack_red_zone_size() + + JavaThread::stack_yellow_zone_size() + : 0; + ThreadStackSize = stack_size_in_bytes/K; + } +#endif // SOLARIS + + // Make the stack size a multiple of the page size so that + // the yellow/red zones can be guarded. + JavaThread::set_stack_size_at_create(round_to(stack_size_in_bytes, + vm_page_size())); + + _compiler_thread_min_stack_allowed = align_size_up(_compiler_thread_min_stack_allowed, vm_page_size()); + + stack_size_in_bytes = CompilerThreadStackSize * K; + if (stack_size_in_bytes != 0 && + stack_size_in_bytes < _compiler_thread_min_stack_allowed) { + tty->print_cr("\nThe CompilerThreadStackSize specified is too small. " + "Specify at least " SIZE_FORMAT "k", + _compiler_thread_min_stack_allowed / K); + return JNI_ERR; + } + + _vm_internal_thread_min_stack_allowed = align_size_up(_vm_internal_thread_min_stack_allowed, vm_page_size()); + + stack_size_in_bytes = VMThreadStackSize * K; + if (stack_size_in_bytes != 0 && + stack_size_in_bytes < _vm_internal_thread_min_stack_allowed) { + tty->print_cr("\nThe VMThreadStackSize specified is too small. " + "Specify at least " SIZE_FORMAT "k", + _vm_internal_thread_min_stack_allowed / K); + return JNI_ERR; + } + return JNI_OK; +} + +// Called when creating the thread. The minimum stack sizes have already been calculated +size_t os::Posix::get_initial_stack_size(ThreadType thr_type, size_t req_stack_size) { + size_t stack_size; + if (req_stack_size == 0) { + stack_size = default_stack_size(thr_type); + } else { + stack_size = req_stack_size; + } + + switch (thr_type) { + case os::java_thread: + // Java threads use ThreadStackSize which default value can be + // changed with the flag -Xss + if (req_stack_size == 0 && JavaThread::stack_size_at_create() > 0) { + // no requested size and we have a more specific default value + stack_size = JavaThread::stack_size_at_create(); + } + stack_size = MAX2(stack_size, + _java_thread_min_stack_allowed); + break; + case os::compiler_thread: + if (req_stack_size == 0 && CompilerThreadStackSize > 0) { + // no requested size and we have a more specific default value + stack_size = (size_t)(CompilerThreadStackSize * K); + } + stack_size = MAX2(stack_size, + _compiler_thread_min_stack_allowed); + break; + case os::vm_thread: + case os::pgc_thread: + case os::cgc_thread: + case os::watcher_thread: + default: // presume the unknown thr_type is a VM internal + if (req_stack_size == 0 && VMThreadStackSize > 0) { + // no requested size and we have a more specific default value + stack_size = (size_t)(VMThreadStackSize * K); + } + + stack_size = MAX2(stack_size, + _vm_internal_thread_min_stack_allowed); + break; + } + + return stack_size; +} os::WatcherThreadCrashProtection::WatcherThreadCrashProtection() { assert(Thread::current()->is_Watcher_thread(), "Must be WatcherThread"); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os/posix/vm/os_posix.hpp --- a/hotspot/src/os/posix/vm/os_posix.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os/posix/vm/os_posix.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1999, 2014, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1999, 2016, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -42,7 +42,18 @@ static void print_libversion_info(outputStream* st); static void print_load_average(outputStream* st); + // Minimum stack size a thread can be created with (allowing + // the VM to completely create the thread and enter user code) + static size_t _compiler_thread_min_stack_allowed; + static size_t _java_thread_min_stack_allowed; + static size_t _vm_internal_thread_min_stack_allowed; + public: + // Return default stack size for the specified thread type + static size_t default_stack_size(os::ThreadType thr_type); + // Check and sets minimum stack sizes + static jint set_minimum_stack_sizes(); + static size_t get_initial_stack_size(ThreadType thr_type, size_t req_stack_size); // Returns true if signal is valid. static bool is_valid_signal(int sig); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os/solaris/vm/os_solaris.cpp --- a/hotspot/src/os/solaris/vm/os_solaris.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os/solaris/vm/os_solaris.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -917,8 +917,15 @@ return buf; } +// return default stack size for thr_type +size_t os::Posix::default_stack_size(os::ThreadType thr_type) { + // default stack size when not specified by caller is 1M (2M for LP64) + size_t s = (BytesPerWord >> 2) * K * K; + return s; +} + bool os::create_thread(Thread* thread, ThreadType thr_type, - size_t stack_size) { + size_t req_stack_size) { // Allocate the OSThread object OSThread* osthread = new OSThread(NULL, NULL); if (osthread == NULL) { @@ -953,31 +960,8 @@ tty->print_cr("In create_thread, creating a %s thread\n", thrtyp); } - // Calculate stack size if it's not specified by caller. - if (stack_size == 0) { - // The default stack size 1M (2M for LP64). - stack_size = (BytesPerWord >> 2) * K * K; - - switch (thr_type) { - case os::java_thread: - // Java threads use ThreadStackSize which default value can be changed with the flag -Xss - if (JavaThread::stack_size_at_create() > 0) stack_size = JavaThread::stack_size_at_create(); - break; - case os::compiler_thread: - if (CompilerThreadStackSize > 0) { - stack_size = (size_t)(CompilerThreadStackSize * K); - break; - } // else fall through: - // use VMThreadStackSize if CompilerThreadStackSize is not defined - case os::vm_thread: - case os::pgc_thread: - case os::cgc_thread: - case os::watcher_thread: - if (VMThreadStackSize > 0) stack_size = (size_t)(VMThreadStackSize * K); - break; - } - } - stack_size = MAX2(stack_size, os::Solaris::min_stack_allowed); + // calculate stack size if it's not specified by caller + size_t stack_size = os::Posix::get_initial_stack_size(thr_type, req_stack_size); // Initial state is ALLOCATED but not INITIALIZED osthread->set_state(ALLOCATED); @@ -4400,7 +4384,12 @@ // Constant minimum stack size allowed. It must be at least // the minimum of what the OS supports (thr_min_stack()), and // enough to allow the thread to get to user bytecode execution. - Solaris::min_stack_allowed = MAX2(thr_min_stack(), Solaris::min_stack_allowed); + Posix::_compiler_thread_min_stack_allowed = MAX2(thr_min_stack(), + Posix::_compiler_thread_min_stack_allowed); + Posix::_java_thread_min_stack_allowed = MAX2(thr_min_stack(), + Posix::_java_thread_min_stack_allowed); + Posix::_vm_internal_thread_min_stack_allowed = MAX2(thr_min_stack(), + Posix::_vm_internal_thread_min_stack_allowed); // dynamic lookup of functions that may not be available in our lowest // supported Solaris release @@ -4445,47 +4434,11 @@ log_info(os)("Memory Serialize Page address: " INTPTR_FORMAT, p2i(mem_serialize_page)); } - // Check minimum allowable stack size for thread creation and to initialize - // the java system classes, including StackOverflowError - depends on page - // size. Add two 4K pages for compiler2 recursion in main thread. - // Add in 4*BytesPerWord 4K pages to account for VM stack during - // class initialization depending on 32 or 64 bit VM. - os::Solaris::min_stack_allowed = MAX2(os::Solaris::min_stack_allowed, - JavaThread::stack_guard_zone_size() + - JavaThread::stack_shadow_zone_size() + - (4*BytesPerWord COMPILER2_PRESENT(+2)) * 4 * K); - - os::Solaris::min_stack_allowed = align_size_up(os::Solaris::min_stack_allowed, os::vm_page_size()); - - size_t threadStackSizeInBytes = ThreadStackSize * K; - if (threadStackSizeInBytes != 0 && - threadStackSizeInBytes < os::Solaris::min_stack_allowed) { - tty->print_cr("\nThe stack size specified is too small, Specify at least %dk", - os::Solaris::min_stack_allowed/K); + // Check and sets minimum stack sizes against command line options + if (Posix::set_minimum_stack_sizes() == JNI_ERR) { return JNI_ERR; } - // For 64kbps there will be a 64kb page size, which makes - // the usable default stack size quite a bit less. Increase the - // stack for 64kb (or any > than 8kb) pages, this increases - // virtual memory fragmentation (since we're not creating the - // stack on a power of 2 boundary. The real fix for this - // should be to fix the guard page mechanism. - - if (vm_page_size() > 8*K) { - threadStackSizeInBytes = (threadStackSizeInBytes != 0) - ? threadStackSizeInBytes + - JavaThread::stack_red_zone_size() + - JavaThread::stack_yellow_zone_size() - : 0; - ThreadStackSize = threadStackSizeInBytes/K; - } - - // Make the stack size a multiple of the page size so that - // the yellow/red zones can be guarded. - JavaThread::set_stack_size_at_create(round_to(threadStackSizeInBytes, - vm_page_size())); - Solaris::libthread_init(); if (UseNUMA) { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os/solaris/vm/os_solaris.hpp --- a/hotspot/src/os/solaris/vm/os_solaris.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os/solaris/vm/os_solaris.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -292,10 +292,6 @@ static jint _os_thread_limit; static volatile jint _os_thread_count; - // Minimum stack size a thread can be created with (allowing - // the VM to completely create the thread and enter user code) - - static size_t min_stack_allowed; // Stack overflow handling diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os/windows/vm/os_windows.cpp --- a/hotspot/src/os/windows/vm/os_windows.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os/windows/vm/os_windows.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -4215,7 +4215,7 @@ min_stack_allowed = align_size_up(min_stack_allowed, os::vm_page_size()); if (actual_reserve_size < min_stack_allowed) { - tty->print_cr("\nThe stack size specified is too small, " + tty->print_cr("\nThe Java thread stack size specified is too small. " "Specify at least %dk", min_stack_allowed / K); return JNI_ERR; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/aix_ppc/vm/globals_aix_ppc.hpp --- a/hotspot/src/os_cpu/aix_ppc/vm/globals_aix_ppc.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/aix_ppc/vm/globals_aix_ppc.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2002, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2002, 2016, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 2012, 2015 SAP SE. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * @@ -33,10 +33,6 @@ define_pd_global(intx, ThreadStackSize, 2048); // 0 => use system default define_pd_global(intx, VMThreadStackSize, 2048); -// if we set CompilerThreadStackSize to a value different than 0, it will -// be used in os::create_thread(). Otherwise, due the strange logic in os::create_thread(), -// the stack size for compiler threads will default to VMThreadStackSize, although it -// is defined to 4M in os::Aix::default_stack_size()! define_pd_global(intx, CompilerThreadStackSize, 4096); // Allow extra space in DEBUG builds for asserts. diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/aix_ppc/vm/os_aix_ppc.cpp --- a/hotspot/src/os_cpu/aix_ppc/vm/os_aix_ppc.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/aix_ppc/vm/os_aix_ppc.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -192,8 +192,10 @@ intptr_t* csp = (intptr_t*) *((intptr_t*) os::current_stack_pointer()); // hack. frame topframe(csp, (address)0x8); - // return sender of current topframe which hopefully has pc != NULL. - return os::get_sender_for_C_frame(&topframe); + // Return sender of sender of current topframe which hopefully + // both have pc != NULL. + frame tmp = os::get_sender_for_C_frame(&topframe); + return os::get_sender_for_C_frame(&tmp); } // Utility functions @@ -533,23 +535,17 @@ //////////////////////////////////////////////////////////////////////////////// // thread stack -size_t os::Aix::min_stack_allowed = 128*K; +size_t os::Posix::_compiler_thread_min_stack_allowed = 128 * K; +size_t os::Posix::_java_thread_min_stack_allowed = 128 * K; +size_t os::Posix::_vm_internal_thread_min_stack_allowed = 128 * K; // return default stack size for thr_type -size_t os::Aix::default_stack_size(os::ThreadType thr_type) { +size_t os::Posix::default_stack_size(os::ThreadType thr_type) { // default stack size (compiler thread needs larger stack) - // Notice that the setting for compiler threads here have no impact - // because of the strange 'fallback logic' in os::create_thread(). - // Better set CompilerThreadStackSize in globals_.hpp if you want to - // specify a different stack size for compiler threads! size_t s = (thr_type == os::compiler_thread ? 4 * M : 1 * M); return s; } -size_t os::Aix::default_guard_size(os::ThreadType thr_type) { - return 2 * page_size(); -} - ///////////////////////////////////////////////////////////////////////////// // helper functions for fatal error handler diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/bsd_x86/vm/globals_bsd_x86.hpp --- a/hotspot/src/os_cpu/bsd_x86/vm/globals_bsd_x86.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/bsd_x86/vm/globals_bsd_x86.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -31,9 +31,11 @@ // define_pd_global(bool, DontYieldALot, false); #ifdef AMD64 +define_pd_global(intx, CompilerThreadStackSize, 1024); define_pd_global(intx, ThreadStackSize, 1024); // 0 => use system default define_pd_global(intx, VMThreadStackSize, 1024); #else +define_pd_global(intx, CompilerThreadStackSize, 512); // ThreadStackSize 320 allows a couple of test cases to run while // keeping the number of threads that can be created high. System // default ThreadStackSize appears to be 512 which is too big. @@ -41,7 +43,6 @@ define_pd_global(intx, VMThreadStackSize, 512); #endif // AMD64 -define_pd_global(intx, CompilerThreadStackSize, 0); define_pd_global(size_t, JVMInvokeMethodSlack, 8192); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/bsd_x86/vm/os_bsd_x86.cpp --- a/hotspot/src/os_cpu/bsd_x86/vm/os_bsd_x86.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/bsd_x86/vm/os_bsd_x86.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -838,9 +838,13 @@ // thread stack #ifdef AMD64 -size_t os::Bsd::min_stack_allowed = 64 * K; +size_t os::Posix::_compiler_thread_min_stack_allowed = 64 * K; +size_t os::Posix::_java_thread_min_stack_allowed = 64 * K; +size_t os::Posix::_vm_internal_thread_min_stack_allowed = 64 * K; #else -size_t os::Bsd::min_stack_allowed = (48 DEBUG_ONLY(+4))*K; +size_t os::Posix::_compiler_thread_min_stack_allowed = (48 DEBUG_ONLY(+ 4)) * K; +size_t os::Posix::_java_thread_min_stack_allowed = (48 DEBUG_ONLY(+ 4)) * K; +size_t os::Posix::_vm_internal_thread_min_stack_allowed = (48 DEBUG_ONLY(+ 4)) * K; #ifdef __GNUC__ #define GET_GS() ({int gs; __asm__ volatile("movw %%gs, %w0":"=q"(gs)); gs&0xffff;}) @@ -849,7 +853,7 @@ #endif // AMD64 // return default stack size for thr_type -size_t os::Bsd::default_stack_size(os::ThreadType thr_type) { +size_t os::Posix::default_stack_size(os::ThreadType thr_type) { // default stack size (compiler thread needs larger stack) #ifdef AMD64 size_t s = (thr_type == os::compiler_thread ? 4 * M : 1 * M); @@ -859,11 +863,6 @@ return s; } -size_t os::Bsd::default_guard_size(os::ThreadType thr_type) { - // Creating guard page is very expensive. Java thread has HotSpot - // guard page, only enable glibc guard page for non-Java threads. - return (thr_type == java_thread ? 0 : page_size()); -} // Java thread: // diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/bsd_zero/vm/os_bsd_zero.cpp --- a/hotspot/src/os_cpu/bsd_zero/vm/os_bsd_zero.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/bsd_zero/vm/os_bsd_zero.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -282,9 +282,11 @@ /////////////////////////////////////////////////////////////////////////////// // thread stack -size_t os::Bsd::min_stack_allowed = 64 * K; +size_t os::Posix::_compiler_thread_min_stack_allowed = 64 * K; +size_t os::Posix::_java_thread_min_stack_allowed = 64 * K; +size_t os::Posix::_vm_internal_thread_min_stack_allowed = 64 * K; -size_t os::Bsd::default_stack_size(os::ThreadType thr_type) { +size_t os::Posix::default_stack_size(os::ThreadType thr_type) { #ifdef _LP64 size_t s = (thr_type == os::compiler_thread ? 4 * M : 1 * M); #else @@ -293,12 +295,6 @@ return s; } -size_t os::Bsd::default_guard_size(os::ThreadType thr_type) { - // Only enable glibc guard pages for non-Java threads - // (Java threads have HotSpot guard pages) - return (thr_type == java_thread ? 0 : page_size()); -} - static void current_stack_region(address *bottom, size_t *size) { address stack_bottom; address stack_top; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/linux_aarch64/vm/globals_linux_aarch64.hpp --- a/hotspot/src/os_cpu/linux_aarch64/vm/globals_linux_aarch64.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/linux_aarch64/vm/globals_linux_aarch64.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2000, 2010, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 2014, Red Hat Inc. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * @@ -33,7 +33,7 @@ define_pd_global(intx, ThreadStackSize, 2048); // 0 => use system default define_pd_global(intx, VMThreadStackSize, 2048); -define_pd_global(intx, CompilerThreadStackSize, 0); +define_pd_global(intx, CompilerThreadStackSize, 2048); define_pd_global(uintx,JVMInvokeMethodSlack, 8192); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/linux_aarch64/vm/os_linux_aarch64.cpp --- a/hotspot/src/os_cpu/linux_aarch64/vm/os_linux_aarch64.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/linux_aarch64/vm/os_linux_aarch64.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -473,10 +473,12 @@ //////////////////////////////////////////////////////////////////////////////// // thread stack -size_t os::Linux::min_stack_allowed = 64 * K; +size_t os::Posix::_compiler_thread_min_stack_allowed = 64 * K; +size_t os::Posix::_java_thread_min_stack_allowed = 64 * K; +size_t os::Posix::_vm_internal_thread_min_stack_allowed = 64 * K; // return default stack size for thr_type -size_t os::Linux::default_stack_size(os::ThreadType thr_type) { +size_t os::Posix::default_stack_size(os::ThreadType thr_type) { // default stack size (compiler thread needs larger stack) size_t s = (thr_type == os::compiler_thread ? 4 * M : 1 * M); return s; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/linux_ppc/vm/globals_linux_ppc.hpp --- a/hotspot/src/os_cpu/linux_ppc/vm/globals_linux_ppc.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/linux_ppc/vm/globals_linux_ppc.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2002, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2002, 2016, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 2012, 2015 SAP SE. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * @@ -33,10 +33,6 @@ define_pd_global(intx, ThreadStackSize, 2048); // 0 => use system default define_pd_global(intx, VMThreadStackSize, 2048); -// if we set CompilerThreadStackSize to a value different than 0, it will -// be used in os::create_thread(). Otherwise, due the strange logic in os::create_thread(), -// the stack size for compiler threads will default to VMThreadStackSize, although it -// is defined to 4M in os::Linux::default_stack_size()! define_pd_global(intx, CompilerThreadStackSize, 4096); // Allow extra space in DEBUG builds for asserts. diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/linux_ppc/vm/os_linux_ppc.cpp --- a/hotspot/src/os_cpu/linux_ppc/vm/os_linux_ppc.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/linux_ppc/vm/os_linux_ppc.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -205,8 +205,10 @@ intptr_t* csp = (intptr_t*) *((intptr_t*) os::current_stack_pointer()); // hack. frame topframe(csp, (address)0x8); - // return sender of current topframe which hopefully has pc != NULL. - return os::get_sender_for_C_frame(&topframe); + // Return sender of sender of current topframe which hopefully + // both have pc != NULL. + frame tmp = os::get_sender_for_C_frame(&topframe); + return os::get_sender_for_C_frame(&tmp); } // Utility functions @@ -533,15 +535,13 @@ //////////////////////////////////////////////////////////////////////////////// // thread stack -size_t os::Linux::min_stack_allowed = 128*K; +size_t os::Posix::_compiler_thread_min_stack_allowed = 128 * K; +size_t os::Posix::_java_thread_min_stack_allowed = 128 * K; +size_t os::Posix::_vm_internal_thread_min_stack_allowed = 128 * K; // return default stack size for thr_type -size_t os::Linux::default_stack_size(os::ThreadType thr_type) { +size_t os::Posix::default_stack_size(os::ThreadType thr_type) { // default stack size (compiler thread needs larger stack) - // Notice that the setting for compiler threads here have no impact - // because of the strange 'fallback logic' in os::create_thread(). - // Better set CompilerThreadStackSize in globals_.hpp if you want to - // specify a different stack size for compiler threads! size_t s = (thr_type == os::compiler_thread ? 4 * M : 1024 * K); return s; } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/linux_sparc/vm/globals_linux_sparc.hpp --- a/hotspot/src/os_cpu/linux_sparc/vm/globals_linux_sparc.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/linux_sparc/vm/globals_linux_sparc.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -31,7 +31,6 @@ // define_pd_global(size_t, JVMInvokeMethodSlack, 12288); -define_pd_global(intx, CompilerThreadStackSize, 0); // Used on 64 bit platforms for UseCompressedOops base address define_pd_global(size_t, HeapBaseMinAddress, CONST64(4)*G); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/linux_sparc/vm/os_linux_sparc.cpp --- a/hotspot/src/os_cpu/linux_sparc/vm/os_linux_sparc.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/linux_sparc/vm/os_linux_sparc.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -726,10 +726,12 @@ /////////////////////////////////////////////////////////////////////////////// // thread stack -size_t os::Linux::min_stack_allowed = 128 * K; +size_t os::Posix::_compiler_thread_min_stack_allowed = 128 * K; +size_t os::Posix::_java_thread_min_stack_allowed = 128 * K; +size_t os::Posix::_vm_internal_thread_min_stack_allowed = 128 * K; // return default stack size for thr_type -size_t os::Linux::default_stack_size(os::ThreadType thr_type) { +size_t os::Posix::default_stack_size(os::ThreadType thr_type) { // default stack size (compiler thread needs larger stack) size_t s = (thr_type == os::compiler_thread ? 4 * M : 1 * M); return s; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/linux_x86/vm/globals_linux_x86.hpp --- a/hotspot/src/os_cpu/linux_x86/vm/globals_linux_x86.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/linux_x86/vm/globals_linux_x86.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -30,9 +30,11 @@ define_pd_global(bool, DontYieldALot, false); #ifdef AMD64 +define_pd_global(intx, CompilerThreadStackSize, 1024); define_pd_global(intx, ThreadStackSize, 1024); // 0 => use system default define_pd_global(intx, VMThreadStackSize, 1024); #else +define_pd_global(intx, CompilerThreadStackSize, 512); // ThreadStackSize 320 allows a couple of test cases to run while // keeping the number of threads that can be created high. System // default ThreadStackSize appears to be 512 which is too big. @@ -40,8 +42,6 @@ define_pd_global(intx, VMThreadStackSize, 512); #endif // AMD64 -define_pd_global(intx, CompilerThreadStackSize, 0); - define_pd_global(size_t, JVMInvokeMethodSlack, 8192); // Used on 64 bit platforms for UseCompressedOops base address diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/linux_x86/vm/os_linux_x86.cpp --- a/hotspot/src/os_cpu/linux_x86/vm/os_linux_x86.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/linux_x86/vm/os_linux_x86.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -676,13 +676,17 @@ // thread stack #ifdef AMD64 -size_t os::Linux::min_stack_allowed = 64 * K; +size_t os::Posix::_compiler_thread_min_stack_allowed = 64 * K; +size_t os::Posix::_java_thread_min_stack_allowed = 64 * K; +size_t os::Posix::_vm_internal_thread_min_stack_allowed = 64 * K; #else -size_t os::Linux::min_stack_allowed = (48 DEBUG_ONLY(+4))*K; +size_t os::Posix::_compiler_thread_min_stack_allowed = (48 DEBUG_ONLY(+ 4)) * K; +size_t os::Posix::_java_thread_min_stack_allowed = (48 DEBUG_ONLY(+ 4)) * K; +size_t os::Posix::_vm_internal_thread_min_stack_allowed = (48 DEBUG_ONLY(+ 4)) * K; #endif // AMD64 // return default stack size for thr_type -size_t os::Linux::default_stack_size(os::ThreadType thr_type) { +size_t os::Posix::default_stack_size(os::ThreadType thr_type) { // default stack size (compiler thread needs larger stack) #ifdef AMD64 size_t s = (thr_type == os::compiler_thread ? 4 * M : 1 * M); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/linux_zero/vm/os_linux_zero.cpp --- a/hotspot/src/os_cpu/linux_zero/vm/os_linux_zero.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/linux_zero/vm/os_linux_zero.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -307,9 +307,11 @@ /////////////////////////////////////////////////////////////////////////////// // thread stack -size_t os::Linux::min_stack_allowed = 64 * K; +size_t os::Posix::_compiler_thread_min_stack_allowed = 64 * K; +size_t os::Posix::_java_thread_min_stack_allowed = 64 * K; +size_t os::Posix::_vm_internal_thread_min_stack_allowed = 64 * K; -size_t os::Linux::default_stack_size(os::ThreadType thr_type) { +size_t os::Posix::default_stack_size(os::ThreadType thr_type) { #ifdef _LP64 size_t s = (thr_type == os::compiler_thread ? 4 * M : 1 * M); #else diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/solaris_sparc/vm/globals_solaris_sparc.hpp --- a/hotspot/src/os_cpu/solaris_sparc/vm/globals_solaris_sparc.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/solaris_sparc/vm/globals_solaris_sparc.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -31,7 +31,6 @@ // define_pd_global(size_t, JVMInvokeMethodSlack, 12288); -define_pd_global(intx, CompilerThreadStackSize, 0); // Used on 64 bit platforms for UseCompressedOops base address #ifdef _LP64 diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/solaris_sparc/vm/os_solaris_sparc.cpp --- a/hotspot/src/os_cpu/solaris_sparc/vm/os_solaris_sparc.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/solaris_sparc/vm/os_solaris_sparc.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -84,9 +84,13 @@ // Minimum stack size for the VM. It's easier to document a constant // but it's different for x86 and sparc because the page sizes are different. #ifdef _LP64 -size_t os::Solaris::min_stack_allowed = 128*K; +size_t os::Posix::_compiler_thread_min_stack_allowed = 128 * K; +size_t os::Posix::_java_thread_min_stack_allowed = 128 * K; +size_t os::Posix::_vm_internal_thread_min_stack_allowed = 128 * K; #else -size_t os::Solaris::min_stack_allowed = 96*K; +size_t os::Posix::_compiler_thread_min_stack_allowed = 96 * K; +size_t os::Posix::_java_thread_min_stack_allowed = 96 * K; +size_t os::Posix::_vm_internal_thread_min_stack_allowed = 96 * K; #endif int os::Solaris::max_register_window_saves_before_flushing() { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/solaris_x86/vm/globals_solaris_x86.hpp --- a/hotspot/src/os_cpu/solaris_x86/vm/globals_solaris_x86.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/solaris_x86/vm/globals_solaris_x86.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -30,10 +30,12 @@ define_pd_global(bool, DontYieldALot, true); // Determined in the design center #ifdef AMD64 +define_pd_global(intx, CompilerThreadStackSize, 1024); define_pd_global(intx, ThreadStackSize, 1024); // 0 => use system default define_pd_global(intx, VMThreadStackSize, 1024); define_pd_global(size_t, JVMInvokeMethodSlack, 8*K); #else +define_pd_global(intx, CompilerThreadStackSize, 512); // ThreadStackSize 320 allows a couple of test cases to run while // keeping the number of threads that can be created high. define_pd_global(intx, ThreadStackSize, 320); @@ -41,7 +43,6 @@ define_pd_global(size_t, JVMInvokeMethodSlack, 10*K); #endif // AMD64 -define_pd_global(intx, CompilerThreadStackSize, 0); // Used on 64 bit platforms for UseCompressedOops base address define_pd_global(size_t, HeapBaseMinAddress, 2*G); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/os_cpu/solaris_x86/vm/os_solaris_x86.cpp --- a/hotspot/src/os_cpu/solaris_x86/vm/os_solaris_x86.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/os_cpu/solaris_x86/vm/os_solaris_x86.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -86,15 +86,19 @@ #define MAX_PATH (2 * K) -// Minimum stack size for the VM. It's easier to document a constant value +// Minimum stack sizes for the VM. It's easier to document a constant value // but it's different for x86 and sparc because the page sizes are different. #ifdef AMD64 -size_t os::Solaris::min_stack_allowed = 224*K; +size_t os::Posix::_compiler_thread_min_stack_allowed = 394 * K; +size_t os::Posix::_java_thread_min_stack_allowed = 224 * K; +size_t os::Posix::_vm_internal_thread_min_stack_allowed = 224 * K; #define REG_SP REG_RSP #define REG_PC REG_RIP #define REG_FP REG_RBP #else -size_t os::Solaris::min_stack_allowed = 64*K; +size_t os::Posix::_compiler_thread_min_stack_allowed = 64 * K; +size_t os::Posix::_java_thread_min_stack_allowed = 64 * K; +size_t os::Posix::_vm_internal_thread_min_stack_allowed = 64 * K; #define REG_SP UESP #define REG_PC EIP #define REG_FP EBP diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/c1/c1_LIRGenerator.cpp --- a/hotspot/src/share/vm/c1/c1_LIRGenerator.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/c1/c1_LIRGenerator.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -2410,6 +2410,15 @@ #endif // INCLUDE_ALL_GCS if (x->is_volatile() && os::is_MP()) __ membar_acquire(); + + /* Normalize boolean value returned by unsafe operation, i.e., value != 0 ? value = true : value false. */ + if (type == T_BOOLEAN) { + LabelObj* equalZeroLabel = new LabelObj(); + __ cmp(lir_cond_equal, value, 0); + __ branch(lir_cond_equal, T_BOOLEAN, equalZeroLabel->label()); + __ move(LIR_OprFact::intConst(1), value); + __ branch_destination(equalZeroLabel->label()); + } } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/c1/c1_Runtime1.cpp --- a/hotspot/src/share/vm/c1/c1_Runtime1.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/c1/c1_Runtime1.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -576,9 +576,8 @@ // normal bytecode execution. thread->clear_exception_oop_and_pc(); - Handle original_exception(thread, exception()); - - continuation = SharedRuntime::compute_compiled_exc_handler(nm, pc, exception, false, false); + bool recursive_exception = false; + continuation = SharedRuntime::compute_compiled_exc_handler(nm, pc, exception, false, false, recursive_exception); // If an exception was thrown during exception dispatch, the exception oop may have changed thread->set_exception_oop(exception()); thread->set_exception_pc(pc); @@ -586,8 +585,9 @@ // the exception cache is used only by non-implicit exceptions // Update the exception cache only when there didn't happen // another exception during the computation of the compiled - // exception handler. - if (continuation != NULL && original_exception() == exception()) { + // exception handler. Checking for exception oop equality is not + // sufficient because some exceptions are pre-allocated and reused. + if (continuation != NULL && !recursive_exception) { nm->add_handler_for_exception_and_pc(exception, pc, continuation); } } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/classfile/verificationType.hpp --- a/hotspot/src/share/vm/classfile/verificationType.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/classfile/verificationType.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2003, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -95,7 +95,8 @@ Category2_2nd = (Category2_2ndFlag << 1 * BitsPerByte) | Primitive, // Primitive values (type descriminator stored in most-signifcant bytes) - Bogus = (ITEM_Bogus << 2 * BitsPerByte) | Category1, + // Bogus needs the " | Primitive". Else, is_reference(Bogus) returns TRUE. + Bogus = (ITEM_Bogus << 2 * BitsPerByte) | Primitive, Boolean = (ITEM_Boolean << 2 * BitsPerByte) | Category1, Byte = (ITEM_Byte << 2 * BitsPerByte) | Category1, Short = (ITEM_Short << 2 * BitsPerByte) | Category1, diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/code/codeCache.cpp --- a/hotspot/src/share/vm/code/codeCache.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/code/codeCache.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -1305,7 +1305,7 @@ event.set_entryCount(heap->blob_count()); event.set_methodCount(heap->nmethod_count()); event.set_adaptorCount(heap->adapter_count()); - event.set_unallocatedCapacity(heap->unallocated_capacity()/K); + event.set_unallocatedCapacity(heap->unallocated_capacity()); event.set_fullCount(heap->full_count()); event.commit(); } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/gc/g1/g1CollectionSet.cpp --- a/hotspot/src/share/vm/gc/g1/g1CollectionSet.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/gc/g1/g1CollectionSet.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -32,6 +32,7 @@ #include "gc/g1/heapRegionSet.hpp" #include "logging/logStream.hpp" #include "utilities/debug.hpp" +#include "utilities/quickSort.hpp" G1CollectorState* G1CollectionSet::collector_state() { return _g1->collector_state(); @@ -396,6 +397,16 @@ return time_remaining_ms; } +static int compare_region_idx(const uint a, const uint b) { + if (a > b) { + return 1; + } else if (a == b) { + return 0; + } else { + return -1; + } +} + void G1CollectionSet::finalize_old_part(double time_remaining_ms) { double non_young_start_time_sec = os::elapsedTime(); double predicted_old_time_ms = 0.0; @@ -493,6 +504,8 @@ double non_young_end_time_sec = os::elapsedTime(); phase_times()->record_non_young_cset_choice_time_ms((non_young_end_time_sec - non_young_start_time_sec) * 1000.0); + + QuickSort::sort(_collection_set_regions, (int)_collection_set_cur_length, compare_region_idx, true); } #ifdef ASSERT diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/gc/g1/g1ConcurrentMark.cpp --- a/hotspot/src/share/vm/gc/g1/g1ConcurrentMark.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/gc/g1/g1ConcurrentMark.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -1904,7 +1904,8 @@ assert(_g1h->is_in_g1_reserved(finger), "invariant"); HeapRegion* curr_region = _g1h->heap_region_containing(finger); - + // Make sure that the reads below do not float before loading curr_region. + OrderAccess::loadload(); // Above heap_region_containing may return NULL as we always scan claim // until the end of the heap. In this case, just jump to the next region. HeapWord* end = curr_region != NULL ? curr_region->end() : finger + HeapRegion::GrainWords; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/gc/g1/g1MarkSweep.cpp --- a/hotspot/src/share/vm/gc/g1/g1MarkSweep.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/gc/g1/g1MarkSweep.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -132,9 +132,16 @@ MarkingCodeBlobClosure follow_code_closure(&GenMarkSweep::follow_root_closure, !CodeBlobToOopClosure::FixRelocations); { G1RootProcessor root_processor(g1h, 1); - root_processor.process_strong_roots(&GenMarkSweep::follow_root_closure, - &GenMarkSweep::follow_cld_closure, - &follow_code_closure); + if (ClassUnloading) { + root_processor.process_strong_roots(&GenMarkSweep::follow_root_closure, + &GenMarkSweep::follow_cld_closure, + &follow_code_closure); + } else { + root_processor.process_all_roots_no_string_table( + &GenMarkSweep::follow_root_closure, + &GenMarkSweep::follow_cld_closure, + &follow_code_closure); + } } { @@ -157,7 +164,7 @@ // This is the point where the entire marking should have completed. assert(GenMarkSweep::_marking_stack.is_empty(), "Marking should have completed"); - { + if (ClassUnloading) { GCTraceTime(Debug, gc, phases) trace("Class Unloading", gc_timer()); // Unload classes and purge the SystemDictionary. diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/gc/g1/g1RootProcessor.cpp --- a/hotspot/src/share/vm/gc/g1/g1RootProcessor.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/gc/g1/g1RootProcessor.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -83,6 +83,7 @@ } process_vm_roots(closures, phase_times, worker_i); + process_string_table_roots(closures, phase_times, worker_i); { // Now the CM ref_processor roots. @@ -191,19 +192,34 @@ void G1RootProcessor::process_all_roots(OopClosure* oops, CLDClosure* clds, - CodeBlobClosure* blobs) { + CodeBlobClosure* blobs, + bool process_string_table) { AllRootsClosures closures(oops, clds); process_java_roots(&closures, NULL, 0); process_vm_roots(&closures, NULL, 0); - if (!_process_strong_tasks.is_task_claimed(G1RP_PS_CodeCache_oops_do)) { - CodeCache::blobs_do(blobs); + if (process_string_table) { + process_string_table_roots(&closures, NULL, 0); } + process_code_cache_roots(blobs, NULL, 0); _process_strong_tasks.all_tasks_completed(n_workers()); } +void G1RootProcessor::process_all_roots(OopClosure* oops, + CLDClosure* clds, + CodeBlobClosure* blobs) { + process_all_roots(oops, clds, blobs, true); +} + +void G1RootProcessor::process_all_roots_no_string_table(OopClosure* oops, + CLDClosure* clds, + CodeBlobClosure* blobs) { + assert(!ClassUnloading, "Should only be used when class unloading is disabled"); + process_all_roots(oops, clds, blobs, false); +} + void G1RootProcessor::process_java_roots(G1RootClosures* closures, G1GCPhaseTimes* phase_times, uint worker_i) { @@ -280,14 +296,23 @@ SystemDictionary::roots_oops_do(strong_roots, weak_roots); } } +} - { - G1GCParPhaseTimesTracker x(phase_times, G1GCPhaseTimes::StringTableRoots, worker_i); - // All threads execute the following. A specific chunk of buckets - // from the StringTable are the individual tasks. - if (weak_roots != NULL) { - StringTable::possibly_parallel_oops_do(weak_roots); - } +void G1RootProcessor::process_string_table_roots(G1RootClosures* closures, + G1GCPhaseTimes* phase_times, + uint worker_i) { + assert(closures->weak_oops() != NULL, "Should only be called when all roots are processed"); + G1GCParPhaseTimesTracker x(phase_times, G1GCPhaseTimes::StringTableRoots, worker_i); + // All threads execute the following. A specific chunk of buckets + // from the StringTable are the individual tasks. + StringTable::possibly_parallel_oops_do(closures->weak_oops()); +} + +void G1RootProcessor::process_code_cache_roots(CodeBlobClosure* code_closure, + G1GCPhaseTimes* phase_times, + uint worker_i) { + if (!_process_strong_tasks.is_task_claimed(G1RP_PS_CodeCache_oops_do)) { + CodeCache::blobs_do(code_closure); } } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/gc/g1/g1RootProcessor.hpp --- a/hotspot/src/share/vm/gc/g1/g1RootProcessor.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/gc/g1/g1RootProcessor.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -73,6 +73,11 @@ void worker_has_discovered_all_strong_classes(); void wait_until_all_strong_classes_discovered(); + void process_all_roots(OopClosure* oops, + CLDClosure* clds, + CodeBlobClosure* blobs, + bool process_string_table); + void process_java_roots(G1RootClosures* closures, G1GCPhaseTimes* phase_times, uint worker_i); @@ -81,6 +86,14 @@ G1GCPhaseTimes* phase_times, uint worker_i); + void process_string_table_roots(G1RootClosures* closures, + G1GCPhaseTimes* phase_times, + uint worker_i); + + void process_code_cache_roots(CodeBlobClosure* code_closure, + G1GCPhaseTimes* phase_times, + uint worker_i); + public: G1RootProcessor(G1CollectedHeap* g1h, uint n_workers); @@ -99,6 +112,13 @@ CLDClosure* clds, CodeBlobClosure* blobs); + // Apply oops, clds and blobs to strongly and weakly reachable roots in the system, + // the only thing different from process_all_roots is that we skip the string table + // to avoid keeping every string live when doing class unloading. + void process_all_roots_no_string_table(OopClosure* oops, + CLDClosure* clds, + CodeBlobClosure* blobs); + // Number of worker threads used by the root processor. uint n_workers() const; }; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/gc/g1/heapRegionManager.cpp --- a/hotspot/src/share/vm/gc/g1/heapRegionManager.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/gc/g1/heapRegionManager.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -123,6 +123,7 @@ for (uint i = start; i < start + num_regions; i++) { if (_regions.get_by_index(i) == NULL) { HeapRegion* new_hr = new_heap_region(i); + OrderAccess::storestore(); _regions.set_by_index(i, new_hr); _allocated_heapregions_length = MAX2(_allocated_heapregions_length, i + 1); } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/gc/shared/gcTrace.cpp --- a/hotspot/src/share/vm/gc/shared/gcTrace.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/gc/shared/gcTrace.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -185,8 +185,10 @@ } #if INCLUDE_ALL_GCS -void G1MMUTracer::report_mmu(double timeSlice, double gcTime, double maxTime) { - send_g1_mmu_event(timeSlice, gcTime, maxTime); +void G1MMUTracer::report_mmu(double time_slice_sec, double gc_time_sec, double max_time_sec) { + send_g1_mmu_event(time_slice_sec * MILLIUNITS, + gc_time_sec * MILLIUNITS, + max_time_sec * MILLIUNITS); } void G1NewTracer::report_yc_type(G1YCType type) { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/gc/shared/gcTrace.hpp --- a/hotspot/src/share/vm/gc/shared/gcTrace.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/gc/shared/gcTrace.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -235,10 +235,10 @@ #if INCLUDE_ALL_GCS class G1MMUTracer : public AllStatic { - static void send_g1_mmu_event(double timeSlice, double gcTime, double maxTime); + static void send_g1_mmu_event(double time_slice_ms, double gc_time_ms, double max_time_ms); public: - static void report_mmu(double timeSlice, double gcTime, double maxTime); + static void report_mmu(double time_slice_sec, double gc_time_sec, double max_time_sec); }; class G1NewTracer : public YoungGCTracer { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/gc/shared/gcTraceSend.cpp --- a/hotspot/src/share/vm/gc/shared/gcTraceSend.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/gc/shared/gcTraceSend.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -200,13 +200,13 @@ } } -void G1MMUTracer::send_g1_mmu_event(double timeSlice, double gcTime, double maxTime) { +void G1MMUTracer::send_g1_mmu_event(double time_slice_ms, double gc_time_ms, double max_time_ms) { EventG1MMU e; if (e.should_commit()) { e.set_gcId(GCId::current()); - e.set_timeSlice(timeSlice); - e.set_gcTime(gcTime); - e.set_maxGcTime(maxTime); + e.set_timeSlice(time_slice_ms); + e.set_gcTime(gc_time_ms); + e.set_pauseTarget(max_time_ms); e.commit(); } } @@ -281,10 +281,10 @@ evt.set_targetOccupancy(target_occupancy); evt.set_thresholdPercentage(target_occupancy > 0 ? ((double)threshold / target_occupancy) : 0.0); evt.set_currentOccupancy(current_occupancy); - evt.set_lastAllocationSize(last_allocation_size); - evt.set_lastAllocationDuration(last_allocation_duration); - evt.set_lastAllocationRate(last_allocation_duration != 0.0 ? last_allocation_size / last_allocation_duration : 0.0); - evt.set_lastMarkingLength(last_marking_length); + evt.set_recentMutatorAllocationSize(last_allocation_size); + evt.set_recentMutatorDuration(last_allocation_duration * MILLIUNITS); + evt.set_recentAllocationRate(last_allocation_duration != 0.0 ? last_allocation_size / last_allocation_duration : 0.0); + evt.set_lastMarkingDuration(last_marking_length * MILLIUNITS); evt.commit(); } } @@ -301,11 +301,11 @@ evt.set_gcId(GCId::current()); evt.set_threshold(threshold); evt.set_thresholdPercentage(internal_target_occupancy > 0 ? ((double)threshold / internal_target_occupancy) : 0.0); - evt.set_internalTargetOccupancy(internal_target_occupancy); + evt.set_ihopTargetOccupancy(internal_target_occupancy); evt.set_currentOccupancy(current_occupancy); evt.set_additionalBufferSize(additional_buffer_size); evt.set_predictedAllocationRate(predicted_allocation_rate); - evt.set_predictedMarkingLength(predicted_marking_length); + evt.set_predictedMarkingDuration(predicted_marking_length * MILLIUNITS); evt.set_predictionActive(prediction_active); evt.commit(); } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/gc/shared/workerManager.hpp --- a/hotspot/src/share/vm/gc/shared/workerManager.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/gc/shared/workerManager.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2016 Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/interpreter/interpreterRuntime.cpp --- a/hotspot/src/share/vm/interpreter/interpreterRuntime.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/interpreter/interpreterRuntime.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -576,27 +576,39 @@ // compute auxiliary field attributes TosState state = as_TosState(info.field_type()); - // Put instructions on final fields are not resolved. This is required so we throw - // exceptions at the correct place (when the instruction is actually invoked). + // Resolution of put instructions on final fields is delayed. That is required so that + // exceptions are thrown at the correct place (when the instruction is actually invoked). // If we do not resolve an instruction in the current pass, leaving the put_code // set to zero will cause the next put instruction to the same field to reresolve. + + // Resolution of put instructions to final instance fields with invalid updates (i.e., + // to final instance fields with updates originating from a method different than ) + // is inhibited. A putfield instruction targeting an instance final field must throw + // an IllegalAccessError if the instruction is not in an instance + // initializer method . If resolution were not inhibited, a putfield + // in an initializer method could be resolved in the initializer. Subsequent + // putfield instructions to the same field would then use cached information. + // As a result, those instructions would not pass through the VM. That is, + // checks in resolve_field_access() would not be executed for those instructions + // and the required IllegalAccessError would not be thrown. // // Also, we need to delay resolving getstatic and putstatic instructions until the // class is initialized. This is required so that access to the static // field will call the initialization function every time until the class // is completely initialized ala. in 2.17.5 in JVM Specification. InstanceKlass* klass = InstanceKlass::cast(info.field_holder()); - bool uninitialized_static = ((bytecode == Bytecodes::_getstatic || bytecode == Bytecodes::_putstatic) && - !klass->is_initialized()); - - Bytecodes::Code put_code = (Bytecodes::Code)0; - if (is_put && !info.access_flags().is_final() && !uninitialized_static) { - put_code = ((is_static) ? Bytecodes::_putstatic : Bytecodes::_putfield); - } + bool uninitialized_static = is_static && !klass->is_initialized(); + bool has_initialized_final_update = info.field_holder()->major_version() >= 53 && + info.has_initialized_final_update(); + assert(!(has_initialized_final_update && !info.access_flags().is_final()), "Fields with initialized final updates must be final"); Bytecodes::Code get_code = (Bytecodes::Code)0; + Bytecodes::Code put_code = (Bytecodes::Code)0; if (!uninitialized_static) { get_code = ((is_static) ? Bytecodes::_getstatic : Bytecodes::_getfield); + if ((is_put && !has_initialized_final_update) || !info.access_flags().is_final()) { + put_code = ((is_static) ? Bytecodes::_putstatic : Bytecodes::_putfield); + } } cp_cache_entry->set_field( diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/jvmci/jvmciCompilerToVM.cpp --- a/hotspot/src/share/vm/jvmci/jvmciCompilerToVM.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/jvmci/jvmciCompilerToVM.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -768,6 +768,11 @@ Symbol* h_name = method->name(); Symbol* h_signature = method->signature(); + if (MethodHandles::is_signature_polymorphic_method(method())) { + // Signature polymorphic methods are already resolved, JVMCI just returns NULL in this case. + return NULL; + } + LinkInfo link_info(h_resolved, h_name, h_signature, caller_klass); methodHandle m; // Only do exact lookup if receiver klass has been linked. Otherwise, @@ -782,7 +787,7 @@ } if (m.is_null()) { - // Return NULL only if there was a problem with lookup (uninitialized class, etc.) + // Return NULL if there was a problem with lookup (uninitialized class, etc.) return NULL; } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/jvmci/jvmciRuntime.cpp --- a/hotspot/src/share/vm/jvmci/jvmciRuntime.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/jvmci/jvmciRuntime.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -313,13 +313,18 @@ // normal bytecode execution. thread->clear_exception_oop_and_pc(); - continuation = SharedRuntime::compute_compiled_exc_handler(cm, pc, exception, false, false); + bool recursive_exception = false; + continuation = SharedRuntime::compute_compiled_exc_handler(cm, pc, exception, false, false, recursive_exception); // If an exception was thrown during exception dispatch, the exception oop may have changed thread->set_exception_oop(exception()); thread->set_exception_pc(pc); // the exception cache is used only by non-implicit exceptions - if (continuation != NULL && !SharedRuntime::deopt_blob()->contains(continuation)) { + // Update the exception cache only when there didn't happen + // another exception during the computation of the compiled + // exception handler. Checking for exception oop equality is not + // sufficient because some exceptions are pre-allocated and reused. + if (continuation != NULL && !recursive_exception && !SharedRuntime::deopt_blob()->contains(continuation)) { cm->add_handler_for_exception_and_pc(exception, pc, continuation); } } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/oops/klass.cpp --- a/hotspot/src/share/vm/oops/klass.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/oops/klass.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -431,6 +431,12 @@ if (clean_alive_klasses && current->is_instance_klass()) { InstanceKlass* ik = InstanceKlass::cast(current); ik->clean_weak_instanceklass_links(is_alive); + + // JVMTI RedefineClasses creates previous versions that are not in + // the class hierarchy, so process them here. + while ((ik = ik->previous_versions()) != NULL) { + ik->clean_weak_instanceklass_links(is_alive); + } } } } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/opto/graphKit.cpp --- a/hotspot/src/share/vm/opto/graphKit.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/opto/graphKit.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -2172,10 +2172,9 @@ java_bc() == Bytecodes::_instanceof || java_bc() == Bytecodes::_aastore) { ciProfileData* data = method()->method_data()->bci_to_data(bci()); - bool maybe_null = data == NULL ? true : data->as_BitData()->null_seen(); + maybe_null = data == NULL ? true : data->as_BitData()->null_seen(); } return record_profile_for_speculation(n, exact_kls, maybe_null); - return n; } /** diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/opto/library_call.cpp --- a/hotspot/src/share/vm/opto/library_call.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/opto/library_call.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -2475,6 +2475,28 @@ // load value switch (type) { case T_BOOLEAN: + { + // Normalize the value returned by getBoolean in the following cases + if (mismatched || + heap_base_oop == top() || // - heap_base_oop is NULL or + (can_access_non_heap && alias_type->field() == NULL) // - heap_base_oop is potentially NULL + // and the unsafe access is made to large offset + // (i.e., larger than the maximum offset necessary for any + // field access) + ) { + IdealKit ideal = IdealKit(this); +#define __ ideal. + IdealVariable normalized_result(ideal); + __ declarations_done(); + __ set(normalized_result, p); + __ if_then(p, BoolTest::ne, ideal.ConI(0)); + __ set(normalized_result, ideal.ConI(1)); + ideal.end_if(); + final_sync(ideal); + p = __ value(normalized_result); +#undef __ + } + } case T_CHAR: case T_BYTE: case T_SHORT: diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/opto/runtime.cpp --- a/hotspot/src/share/vm/opto/runtime.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/opto/runtime.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -1349,17 +1349,23 @@ force_unwind ? NULL : nm->handler_for_exception_and_pc(exception, pc); if (handler_address == NULL) { - Handle original_exception(thread, exception()); - handler_address = SharedRuntime::compute_compiled_exc_handler(nm, pc, exception, force_unwind, true); + bool recursive_exception = false; + handler_address = SharedRuntime::compute_compiled_exc_handler(nm, pc, exception, force_unwind, true, recursive_exception); assert (handler_address != NULL, "must have compiled handler"); // Update the exception cache only when the unwind was not forced // and there didn't happen another exception during the computation of the - // compiled exception handler. - if (!force_unwind && original_exception() == exception()) { + // compiled exception handler. Checking for exception oop equality is not + // sufficient because some exceptions are pre-allocated and reused. + if (!force_unwind && !recursive_exception) { nm->add_handler_for_exception_and_pc(exception,pc,handler_address); } } else { - assert(handler_address == SharedRuntime::compute_compiled_exc_handler(nm, pc, exception, force_unwind, true), "Must be the same"); +#ifdef ASSERT + bool recursive_exception = false; + address computed_address = SharedRuntime::compute_compiled_exc_handler(nm, pc, exception, force_unwind, true, recursive_exception); + vmassert(recursive_exception || (handler_address == computed_address), "Handler address inconsistency: " PTR_FORMAT " != " PTR_FORMAT, + p2i(handler_address), p2i(computed_address)); +#endif } } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/prims/jvm.h --- a/hotspot/src/share/vm/prims/jvm.h Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/prims/jvm.h Thu Sep 22 18:32:20 2016 +0000 @@ -196,7 +196,8 @@ * java.lang.StackWalker */ enum { - JVM_STACKWALK_FILL_CLASS_REFS_ONLY = 0x2, + JVM_STACKWALK_FILL_CLASS_REFS_ONLY = 0x02, + JVM_STACKWALK_GET_CALLER_CLASS = 0x04, JVM_STACKWALK_SHOW_HIDDEN_FRAMES = 0x20, JVM_STACKWALK_FILL_LIVE_STACK_FRAMES = 0x100 }; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/prims/jvmtiEventController.cpp --- a/hotspot/src/share/vm/prims/jvmtiEventController.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/prims/jvmtiEventController.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -96,7 +96,7 @@ static const jlong THREAD_FILTERED_EVENT_BITS = INTERP_EVENT_BITS | EXCEPTION_BITS | MONITOR_BITS | BREAKPOINT_BIT | CLASS_LOAD_BIT | CLASS_PREPARE_BIT | THREAD_END_BIT; static const jlong NEED_THREAD_LIFE_EVENTS = THREAD_FILTERED_EVENT_BITS | THREAD_START_BIT; -static const jlong EARLY_EVENT_BITS = CLASS_FILE_LOAD_HOOK_BIT | +static const jlong EARLY_EVENT_BITS = CLASS_FILE_LOAD_HOOK_BIT | CLASS_LOAD_BIT | CLASS_PREPARE_BIT | VM_START_BIT | VM_INIT_BIT | VM_DEATH_BIT | NATIVE_METHOD_BIND_BIT | THREAD_START_BIT | THREAD_END_BIT | COMPILED_METHOD_LOAD_BIT | COMPILED_METHOD_UNLOAD_BIT | diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/prims/jvmtiExport.cpp diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/prims/stackwalk.cpp --- a/hotspot/src/share/vm/prims/stackwalk.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/prims/stackwalk.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -113,7 +113,10 @@ int bci = stream.bci(); if (method == NULL) continue; - if (!ShowHiddenFrames && StackWalk::skip_hidden_frames(mode)) { + + // skip hidden frames for default StackWalker option (i.e. SHOW_HIDDEN_FRAMES + // not set) and when StackWalker::getCallerClass is called + if (!ShowHiddenFrames && (skip_hidden_frames(mode) || get_caller_class(mode))) { if (method->is_hidden()) { if (TraceStackWalk) { tty->print(" hidden method: "); method->print_short_name(); @@ -139,7 +142,14 @@ Handle stackFrame(frames_array->obj_at(index)); fill_stackframe(stackFrame, method, bci); } else { - assert (use_frames_array(mode) == false, "Bad mode for get caller class"); + assert (use_frames_array(mode) == false, "Bad mode for filling in Class object"); + if (get_caller_class(mode) && index == start_index && method->caller_sensitive()) { + ResourceMark rm(THREAD); + THROW_MSG_0(vmSymbols::java_lang_UnsupportedOperationException(), + err_msg("StackWalker::getCallerClass called from @CallerSensitive %s method", + method->name_and_sig_as_C_string())); + } + frames_array->obj_at_put(index, method->method_holder()->java_mirror()); } if (++frames_decoded >= max_nframes) break; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/prims/stackwalk.hpp --- a/hotspot/src/share/vm/prims/stackwalk.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/prims/stackwalk.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -82,6 +82,9 @@ static void fill_live_stackframe(Handle stackFrame, const methodHandle& method, int bci, javaVFrame* jvf, TRAPS); + static inline bool get_caller_class(int mode) { + return (mode & JVM_STACKWALK_GET_CALLER_CLASS) != 0; + } static inline bool skip_hidden_frames(int mode) { return (mode & JVM_STACKWALK_SHOW_HIDDEN_FRAMES) == 0; } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/prims/unsafe.cpp --- a/hotspot/src/share/vm/prims/unsafe.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/prims/unsafe.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -150,14 +150,23 @@ } template - T normalize(T x) { + T normalize_for_write(T x) { return x; } - jboolean normalize(jboolean x) { + jboolean normalize_for_write(jboolean x) { return x & 1; } + template + T normalize_for_read(T x) { + return x; + } + + jboolean normalize_for_read(jboolean x) { + return x != 0; + } + /** * Helper class to wrap memory accesses in JavaThread::doing_unsafe_access() */ @@ -196,7 +205,7 @@ T* p = (T*)addr(); - T x = *p; + T x = normalize_for_read(*p); return x; } @@ -207,7 +216,7 @@ T* p = (T*)addr(); - *p = normalize(x); + *p = normalize_for_write(x); } @@ -223,7 +232,7 @@ T x = OrderAccess::load_acquire((volatile T*)p); - return x; + return normalize_for_read(x); } template @@ -232,7 +241,7 @@ T* p = (T*)addr(); - OrderAccess::release_store_fence((volatile T*)p, normalize(x)); + OrderAccess::release_store_fence((volatile T*)p, normalize_for_write(x)); } @@ -256,7 +265,7 @@ jlong* p = (jlong*)addr(); - Atomic::store(normalize(x), p); + Atomic::store(normalize_for_write(x), p); } #endif }; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/prims/whitebox.cpp --- a/hotspot/src/share/vm/prims/whitebox.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/prims/whitebox.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -894,6 +894,7 @@ } ThreadToNativeFromVM ttnfv(thread); // can't be in VM when we call JNI const char* flag_name = env->GetStringUTFChars(name, NULL); + CHECK_JNI_EXCEPTION_(env, false); Flag::Error result = (*TAt)(flag_name, value, true, true); env->ReleaseStringUTFChars(name, flag_name); return (result == Flag::SUCCESS); @@ -906,6 +907,7 @@ } ThreadToNativeFromVM ttnfv(thread); // can't be in VM when we call JNI const char* flag_name = env->GetStringUTFChars(name, NULL); + CHECK_JNI_EXCEPTION_(env, false); Flag::Error result = (*TAtPut)(flag_name, value, Flag::INTERNAL); env->ReleaseStringUTFChars(name, flag_name); return (result == Flag::SUCCESS); @@ -944,6 +946,7 @@ static Flag* getVMFlag(JavaThread* thread, JNIEnv* env, jstring name) { ThreadToNativeFromVM ttnfv(thread); // can't be in VM when we call JNI const char* flag_name = env->GetStringUTFChars(name, NULL); + CHECK_JNI_EXCEPTION_(env, NULL); Flag* result = Flag::find_flag(flag_name, strlen(flag_name), true, true); env->ReleaseStringUTFChars(name, flag_name); return result; @@ -1084,7 +1087,14 @@ WB_ENTRY(void, WB_SetStringVMFlag(JNIEnv* env, jobject o, jstring name, jstring value)) ThreadToNativeFromVM ttnfv(thread); // can't be in VM when we call JNI - const char* ccstrValue = (value == NULL) ? NULL : env->GetStringUTFChars(value, NULL); + const char* ccstrValue; + if (value == NULL) { + ccstrValue = NULL; + } + else { + ccstrValue = env->GetStringUTFChars(value, NULL); + CHECK_JNI_EXCEPTION(env); + } ccstr ccstrResult = ccstrValue; bool needFree; { @@ -1308,6 +1318,7 @@ jclass clazz = env->FindClass(vmSymbols::java_lang_Object()->as_C_string()); CHECK_JNI_EXCEPTION_(env, NULL); result = env->NewObjectArray(blobs.length(), clazz, NULL); + CHECK_JNI_EXCEPTION_(env, NULL); if (result == NULL) { return result; } @@ -1317,6 +1328,7 @@ jobjectArray obj = codeBlob2objectArray(thread, env, *it); CHECK_JNI_EXCEPTION_(env, NULL); env->SetObjectArrayElement(result, i, obj); + CHECK_JNI_EXCEPTION_(env, NULL); ++i; } return result; @@ -1523,6 +1535,7 @@ // can't be in VM when we call JNI ThreadToNativeFromVM ttnfv(thread); const char* flag_name = env->GetStringUTFChars(name, NULL); + CHECK_JNI_EXCEPTION_(env, false); bool result = CompilerOracle::has_option_value(mh, flag_name, *value); env->ReleaseStringUTFChars(name, flag_name); return result; @@ -1678,6 +1691,7 @@ // can't be in VM when we call JNI ThreadToNativeFromVM ttnfv(thread); const char* dir = env->GetStringUTFChars(compDirect, NULL); + CHECK_JNI_EXCEPTION_(env, 0); int ret; { ThreadInVMfromNative ttvfn(thread); // back to VM diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/prims/whitebox.hpp --- a/hotspot/src/share/vm/prims/whitebox.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/prims/whitebox.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -33,9 +33,22 @@ #include "oops/symbol.hpp" #include "runtime/interfaceSupport.hpp" +// Unconditionally clear pedantic pending JNI checks +class ClearPendingJniExcCheck : public StackObj { +private: + JavaThread* _thread; +public: + ClearPendingJniExcCheck(JNIEnv* env) : _thread(JavaThread::thread_from_jni_environment(env)) {} + ~ClearPendingJniExcCheck() { + _thread->clear_pending_jni_exception_check(); + } +}; + // Entry macro to transition from JNI to VM state. -#define WB_ENTRY(result_type, header) JNI_ENTRY(result_type, header) +#define WB_ENTRY(result_type, header) JNI_ENTRY(result_type, header) \ + ClearPendingJniExcCheck _clearCheck(env); + #define WB_END JNI_END #define WB_METHOD_DECLARE(result_type) extern "C" result_type JNICALL diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/runtime/arguments.cpp --- a/hotspot/src/share/vm/runtime/arguments.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/runtime/arguments.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -1308,35 +1308,13 @@ return true; } -// sets or adds a module name to the jdk.module.addmods property -bool Arguments::append_to_addmods_property(const char* module_name) { - const char* key = "jdk.module.addmods"; - const char* old_value = Arguments::get_property(key); - size_t buf_len = strlen(key) + strlen(module_name) + 2; - if (old_value != NULL) { - buf_len += strlen(old_value) + 1; - } - char* new_value = AllocateHeap(buf_len, mtArguments); - if (new_value == NULL) { - return false; - } - if (old_value == NULL) { - jio_snprintf(new_value, buf_len, "%s=%s", key, module_name); - } else { - jio_snprintf(new_value, buf_len, "%s=%s,%s", key, old_value, module_name); - } - bool added = add_property(new_value, UnwriteableProperty, InternalProperty); - FreeHeap(new_value); - return added; -} - #if INCLUDE_CDS void Arguments::check_unsupported_dumping_properties() { assert(DumpSharedSpaces, "this function is only used with -Xshare:dump"); const char* unsupported_properties[5] = { "jdk.module.main", "jdk.module.path", "jdk.module.upgrade.path", - "jdk.module.addmods", + "jdk.module.addmods.0", "jdk.module.limitmods" }; const char* unsupported_options[5] = { "-m", "--module-path", @@ -1687,11 +1665,6 @@ CompactibleFreeListSpaceLAB::modify_initialization(OldPLABSize, OldPLABWeight); } - if (!ClassUnloading) { - FLAG_SET_CMDLINE(bool, CMSClassUnloadingEnabled, false); - FLAG_SET_CMDLINE(bool, ExplicitGCInvokesConcurrentAndUnloadsClasses, false); - } - log_trace(gc)("MarkStackSize: %uk MarkStackSizeMax: %uk", (unsigned int) (MarkStackSize / K), (uint) (MarkStackSizeMax / K)); } #endif // INCLUDE_ALL_GCS @@ -2019,6 +1992,13 @@ // Keeping the heap 100% free is hard ;-) so limit it to 99%. FLAG_SET_ERGO(uintx, MinHeapFreeRatio, 99); } + + // If class unloading is disabled, also disable concurrent class unloading. + if (!ClassUnloading) { + FLAG_SET_CMDLINE(bool, CMSClassUnloadingEnabled, false); + FLAG_SET_CMDLINE(bool, ClassUnloadingWithConcurrentMark, false); + FLAG_SET_CMDLINE(bool, ExplicitGCInvokesConcurrentAndUnloadsClasses, false); + } #endif // INCLUDE_ALL_GCS } @@ -2566,8 +2546,8 @@ unsigned int addreads_count = 0; unsigned int addexports_count = 0; +unsigned int addmods_count = 0; unsigned int patch_mod_count = 0; -const char* add_modules_value = NULL; bool Arguments::create_property(const char* prop_name, const char* prop_value, PropertyInternal internal) { size_t prop_len = strlen(prop_name) + strlen(prop_value) + 2; @@ -2821,7 +2801,9 @@ return JNI_ENOMEM; } } else if (match_option(option, "--add-modules=", &tail)) { - add_modules_value = tail; + if (!create_numbered_property("jdk.module.addmods", tail, addmods_count++)) { + return JNI_ENOMEM; + } } else if (match_option(option, "--limit-modules=", &tail)) { if (!create_property("jdk.module.limitmods", tail, InternalProperty)) { return JNI_ENOMEM; @@ -2873,7 +2855,7 @@ char *options = strcpy(NEW_C_HEAP_ARRAY(char, strlen(tail) + 1, mtArguments), tail); add_init_agent("instrument", options, false); // java agents need module java.instrument - if (!Arguments::append_to_addmods_property("java.instrument")) { + if (!create_numbered_property("jdk.module.addmods", "java.instrument", addmods_count++)) { return JNI_ENOMEM; } } @@ -3149,7 +3131,7 @@ return JNI_EINVAL; } // management agent in module java.management - if (!Arguments::append_to_addmods_property("java.management")) { + if (!create_numbered_property("jdk.module.addmods", "java.management", addmods_count++)) { return JNI_ENOMEM; } #else @@ -3560,15 +3542,6 @@ return JNI_ERR; } - // Append the value of the last --add-modules option specified on the command line. - // This needs to be done here, to prevent overwriting possible values written - // to the jdk.module.addmods property by -javaagent and other options. - if (add_modules_value != NULL) { - if (!append_to_addmods_property(add_modules_value)) { - return JNI_ENOMEM; - } - } - // This must be done after all arguments have been processed. // java_compiler() true means set to "NONE" or empty. if (java_compiler() && !xdebug_mode()) { @@ -3617,7 +3590,8 @@ #endif #if INCLUDE_JVMCI - if (EnableJVMCI && !append_to_addmods_property("jdk.vm.ci")) { + if (EnableJVMCI && + !create_numbered_property("jdk.module.addmods", "jdk.vm.ci", addmods_count++)) { return JNI_ENOMEM; } #endif diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/runtime/arguments.hpp --- a/hotspot/src/share/vm/runtime/arguments.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/runtime/arguments.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -489,9 +489,6 @@ static int process_patch_mod_option(const char* patch_mod_tail, bool* patch_mod_javabase); - // Miscellaneous system property setter - static bool append_to_addmods_property(const char* module_name); - // Aggressive optimization flags. static jint set_aggressive_opts_flags(); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/runtime/interfaceSupport.hpp --- a/hotspot/src/share/vm/runtime/interfaceSupport.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/runtime/interfaceSupport.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -280,6 +280,7 @@ ~ThreadToNativeFromVM() { trans_from_native(_thread_in_vm); + assert(!_thread->is_pending_jni_exception_check(), "Pending JNI Exception Check"); // We don't need to clear_walkable because it will happen automagically when we return to java } }; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/runtime/os.hpp --- a/hotspot/src/share/vm/runtime/os.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/runtime/os.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -443,7 +443,7 @@ static bool create_thread(Thread* thread, ThreadType thr_type, - size_t stack_size = 0); + size_t req_stack_size = 0); static bool create_main_thread(JavaThread* thread); static bool create_attached_thread(JavaThread* thread); static void pd_start_thread(Thread* thread); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/runtime/sharedRuntime.cpp --- a/hotspot/src/share/vm/runtime/sharedRuntime.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/runtime/sharedRuntime.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -621,7 +621,7 @@ // ret_pc points into caller; we are returning caller's exception handler // for given exception address SharedRuntime::compute_compiled_exc_handler(CompiledMethod* cm, address ret_pc, Handle& exception, - bool force_unwind, bool top_frame_only) { + bool force_unwind, bool top_frame_only, bool& recursive_exception_occurred) { assert(cm != NULL, "must exist"); ResourceMark rm; @@ -677,6 +677,7 @@ // BCI of the exception handler which caused the exception to be // thrown (bugs 4307310 and 4546590). Set "exception" reference // argument to ensure that the correct exception is thrown (4870175). + recursive_exception_occurred = true; exception = Handle(THREAD, PENDING_EXCEPTION); CLEAR_PENDING_EXCEPTION; if (handler_bci >= 0) { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/runtime/sharedRuntime.hpp --- a/hotspot/src/share/vm/runtime/sharedRuntime.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/runtime/sharedRuntime.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -189,7 +189,7 @@ // exception handling and implicit exceptions static address compute_compiled_exc_handler(CompiledMethod* nm, address ret_pc, Handle& exception, - bool force_unwind, bool top_frame_only); + bool force_unwind, bool top_frame_only, bool& recursive_exception_occurred); enum ImplicitExceptionKind { IMPLICIT_NULL, IMPLICIT_DIVIDE_BY_ZERO, diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/runtime/thread.hpp --- a/hotspot/src/share/vm/runtime/thread.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/runtime/thread.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -1542,6 +1542,9 @@ static ByteSize jmp_ring_offset() { return byte_offset_of(JavaThread, _jmp_ring); } #endif // PRODUCT static ByteSize jni_environment_offset() { return byte_offset_of(JavaThread, _jni_environment); } + static ByteSize pending_jni_exception_check_fn_offset() { + return byte_offset_of(JavaThread, _pending_jni_exception_check_fn); + } static ByteSize last_Java_sp_offset() { return byte_offset_of(JavaThread, _anchor) + JavaFrameAnchor::last_Java_sp_offset(); } @@ -1615,7 +1618,11 @@ assert(_jni_active_critical >= 0, "JNI critical nesting problem?"); } - // Checked JNI, is the programmer required to check for exceptions, specify which function name + // Checked JNI: is the programmer required to check for exceptions, if so specify + // which function name. Returning to a Java frame should implicitly clear the + // pending check, this is done for Native->Java transitions (i.e. user JNI code). + // VM->Java transistions are not cleared, it is expected that JNI code enclosed + // within ThreadToNativeFromVM makes proper exception checks (i.e. VM internal). bool is_pending_jni_exception_check() const { return _pending_jni_exception_check_fn != NULL; } void clear_pending_jni_exception_check() { _pending_jni_exception_check_fn = NULL; } const char* get_pending_jni_exception_check() const { return _pending_jni_exception_check_fn; } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/services/diagnosticCommand.cpp diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/trace/traceevents.xml --- a/hotspot/src/share/vm/trace/traceevents.xml Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/trace/traceevents.xml Thu Sep 22 18:32:20 2016 +0000 @@ -315,9 +315,9 @@ - - - + + + @@ -377,29 +377,29 @@ - - - - - - - - - + + + + + + + + - - - - - - + + + + + - + diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/utilities/exceptions.cpp --- a/hotspot/src/share/vm/utilities/exceptions.cpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/utilities/exceptions.cpp Thu Sep 22 18:32:20 2016 +0000 @@ -80,7 +80,7 @@ if (h_exception()->klass() == SystemDictionary::StackOverflowError_klass()) { InstanceKlass* ik = InstanceKlass::cast(h_exception->klass()); assert(ik->is_initialized(), - "need to increase min_stack_allowed calculation"); + "need to increase java_thread_min_stack_allowed calculation"); } #endif // ASSERT @@ -227,7 +227,7 @@ Klass* k = SystemDictionary::StackOverflowError_klass(); oop e = InstanceKlass::cast(k)->allocate_instance(CHECK); exception = Handle(THREAD, e); // fill_in_stack trace does gc - assert(InstanceKlass::cast(k)->is_initialized(), "need to increase min_stack_allowed calculation"); + assert(InstanceKlass::cast(k)->is_initialized(), "need to increase java_thread_min_stack_allowed calculation"); if (StackTraceInThrowable) { java_lang_Throwable::fill_in_stack_trace(exception, method()); } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/src/share/vm/utilities/globalDefinitions_xlc.hpp --- a/hotspot/src/share/vm/utilities/globalDefinitions_xlc.hpp Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/src/share/vm/utilities/globalDefinitions_xlc.hpp Thu Sep 22 18:32:20 2016 +0000 @@ -186,6 +186,6 @@ // Inlining support #define NOINLINE -#define ALWAYSINLINE __attribute__((always_inline)) +#define ALWAYSINLINE inline __attribute__((always_inline)) #endif // SHARE_VM_UTILITIES_GLOBALDEFINITIONS_XLC_HPP diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/c2/Test6968348.java --- a/hotspot/test/compiler/c2/Test6968348.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/c2/Test6968348.java Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2010, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2010, 2016, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -38,15 +38,11 @@ import java.lang.reflect.Field; public class Test6968348 { - static Unsafe unsafe; + static Unsafe unsafe = Unsafe.getUnsafe(); static final long[] buffer = new long[4096]; static int array_long_base_offset; public static void main(String[] args) throws Exception { - Class c = Test6968348.class.getClassLoader().loadClass("jdk.internal.misc.Unsafe"); - Field f = c.getDeclaredField("theUnsafe"); - f.setAccessible(true); - unsafe = (Unsafe)f.get(c); array_long_base_offset = unsafe.arrayBaseOffset(long[].class); for (int n = 0; n < 100000; n++) { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/c2/cr8004867/TestIntUnsafeCAS.java --- a/hotspot/test/compiler/c2/cr8004867/TestIntUnsafeCAS.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/c2/cr8004867/TestIntUnsafeCAS.java Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2013, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2013, 2016, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -50,14 +50,10 @@ private static final int ALIGN_OFF = 8; private static final int UNALIGN_OFF = 5; - private static final Unsafe unsafe; + private static final Unsafe unsafe = Unsafe.getUnsafe(); private static final int BASE; static { try { - Class c = TestIntUnsafeCAS.class.getClassLoader().loadClass("jdk.internal.misc.Unsafe"); - Field f = c.getDeclaredField("theUnsafe"); - f.setAccessible(true); - unsafe = (Unsafe)f.get(c); BASE = unsafe.arrayBaseOffset(int[].class); } catch (Exception e) { InternalError err = new InternalError(); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/c2/cr8004867/TestIntUnsafeOrdered.java --- a/hotspot/test/compiler/c2/cr8004867/TestIntUnsafeOrdered.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/c2/cr8004867/TestIntUnsafeOrdered.java Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2013, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2013, 2016, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -50,14 +50,10 @@ private static final int ALIGN_OFF = 8; private static final int UNALIGN_OFF = 5; - private static final Unsafe unsafe; + private static final Unsafe unsafe = Unsafe.getUnsafe(); private static final int BASE; static { try { - Class c = Unsafe.class; - Field f = c.getDeclaredField("theUnsafe"); - f.setAccessible(true); - unsafe = (Unsafe) f.get(c); BASE = unsafe.arrayBaseOffset(int[].class); } catch (Exception e) { InternalError err = new InternalError(); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/c2/cr8004867/TestIntUnsafeVolatile.java --- a/hotspot/test/compiler/c2/cr8004867/TestIntUnsafeVolatile.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/c2/cr8004867/TestIntUnsafeVolatile.java Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2013, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2013, 2016, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -50,14 +50,10 @@ private static final int ALIGN_OFF = 8; private static final int UNALIGN_OFF = 5; - private static final Unsafe unsafe; + private static final Unsafe unsafe = Unsafe.getUnsafe(); private static final int BASE; static { try { - Class c = TestIntUnsafeVolatile.class.getClassLoader().loadClass("jdk.internal.misc.Unsafe"); - Field f = c.getDeclaredField("theUnsafe"); - f.setAccessible(true); - unsafe = (Unsafe)f.get(c); BASE = unsafe.arrayBaseOffset(int[].class); } catch (Exception e) { InternalError err = new InternalError(); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/codecache/OverflowCodeCacheTest.java --- a/hotspot/test/compiler/codecache/OverflowCodeCacheTest.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/codecache/OverflowCodeCacheTest.java Thu Sep 22 18:32:20 2016 +0000 @@ -75,6 +75,7 @@ System.out.printf("type %s%n", type); System.out.println("allocating till possible..."); ArrayList blobs = new ArrayList<>(); + int compilationActivityMode = -1; try { long addr; int size = (int) (getHeapSize() >> 7); @@ -88,13 +89,16 @@ type + " doesn't allow using " + actualType + " when overflow"); } } - Asserts.assertNotEquals(WHITE_BOX.getCompilationActivityMode(), 1 /* run_compilation*/, - "Compilation must be disabled when CodeCache(CodeHeap) overflows"); + /* now, remember compilationActivityMode to check it later, after freeing, since we + possibly have no free cache for futher work */ + compilationActivityMode = WHITE_BOX.getCompilationActivityMode(); } finally { for (Long blob : blobs) { WHITE_BOX.freeCodeBlob(blob); } } + Asserts.assertNotEquals(compilationActivityMode, 1 /* run_compilation*/, + "Compilation must be disabled when CodeCache(CodeHeap) overflows"); } private long getHeapSize() { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/cpuflags/AESIntrinsicsBase.java --- a/hotspot/test/compiler/cpuflags/AESIntrinsicsBase.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/cpuflags/AESIntrinsicsBase.java Thu Sep 22 18:32:20 2016 +0000 @@ -48,8 +48,8 @@ = {"-XX:+UnlockDiagnosticVMOptions", "-XX:+PrintIntrinsics"}; public static final String[] TEST_AES_CMD = {"-XX:+IgnoreUnrecognizedVMOptions", "-XX:+PrintFlagsFinal", - "-Xbatch", "-DcheckOutput=true", "-Dmode=CBC", - TestAESMain.class.getName()}; + "-Xbatch", "-XX:CompileThresholdScaling=0.01", "-DcheckOutput=true", "-Dmode=CBC", + TestAESMain.class.getName(), "100", "1000"}; protected AESIntrinsicsBase(BooleanSupplier predicate) { super(predicate); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/cpuflags/TestAESIntrinsicsOnSupportedConfig.java --- a/hotspot/test/compiler/cpuflags/TestAESIntrinsicsOnSupportedConfig.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/cpuflags/TestAESIntrinsicsOnSupportedConfig.java Thu Sep 22 18:32:20 2016 +0000 @@ -27,11 +27,11 @@ * @library /test/lib / * @modules java.base/jdk.internal.misc * java.management - * @ignore 8146128 * @build sun.hotspot.WhiteBox * @run driver ClassFileInstaller sun.hotspot.WhiteBox * sun.hotspot.WhiteBox$WhiteBoxPermission - * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions + * @run main/othervm/timeout=600 -Xbootclasspath/a:. + * -XX:+UnlockDiagnosticVMOptions * -XX:+WhiteBoxAPI -Xbatch * compiler.cpuflags.TestAESIntrinsicsOnSupportedConfig */ diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/intrinsics/unsafe/TestUnsafeMismatchedArrayFieldAccess.java --- a/hotspot/test/compiler/intrinsics/unsafe/TestUnsafeMismatchedArrayFieldAccess.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/intrinsics/unsafe/TestUnsafeMismatchedArrayFieldAccess.java Thu Sep 22 18:32:20 2016 +0000 @@ -27,7 +27,6 @@ * @bug 8142386 * @summary Unsafe access to an array is wrongly marked as mismatched * @modules java.base/jdk.internal.misc - * @library /test/lib * * @run main/othervm -XX:-UseOnStackReplacement -XX:-BackgroundCompilation -XX:-TieredCompilation * compiler.intrinsics.unsafe.TestUnsafeMismatchedArrayFieldAccess @@ -36,11 +35,10 @@ package compiler.intrinsics.unsafe; import jdk.internal.misc.Unsafe; -import jdk.test.lib.unsafe.UnsafeHelper; public class TestUnsafeMismatchedArrayFieldAccess { - private static final Unsafe UNSAFE = UnsafeHelper.getUnsafe(); + private static final Unsafe UNSAFE = Unsafe.getUnsafe(); static { try { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/jvmci/compilerToVM/ExecuteInstalledCodeTest.java --- a/hotspot/test/compiler/jvmci/compilerToVM/ExecuteInstalledCodeTest.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/jvmci/compilerToVM/ExecuteInstalledCodeTest.java Thu Sep 22 18:32:20 2016 +0000 @@ -19,7 +19,6 @@ * @requires (vm.simpleArch == "x64" | vm.simpleArch == "sparcv9" | vm.simpleArch == "aarch64") * @library /test/lib / * @library ../common/patches - * @ignore 8139383 * @modules java.base/jdk.internal.misc * @modules java.base/jdk.internal.org.objectweb.asm * java.base/jdk.internal.org.objectweb.asm.tree diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/jvmci/compilerToVM/GetResolvedJavaMethodTest.java --- a/hotspot/test/compiler/jvmci/compilerToVM/GetResolvedJavaMethodTest.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/jvmci/compilerToVM/GetResolvedJavaMethodTest.java Thu Sep 22 18:32:20 2016 +0000 @@ -45,7 +45,6 @@ import jdk.internal.misc.Unsafe; import jdk.test.lib.Asserts; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.vm.ci.hotspot.CompilerToVMHelper; import jdk.vm.ci.hotspot.HotSpotResolvedJavaMethod; import jdk.vm.ci.hotspot.PublicMetaspaceWrapperObject; @@ -114,7 +113,7 @@ abstract HotSpotResolvedJavaMethod getResolvedJavaMethod(); } - private static final Unsafe UNSAFE = UnsafeHelper.getUnsafe(); + private static final Unsafe UNSAFE = Unsafe.getUnsafe(); private static final WhiteBox WB = WhiteBox.getWhiteBox(); private static final Field METASPACE_METHOD_FIELD; private static final Class TEST_CLASS = GetResolvedJavaMethodTest.class; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/jvmci/compilerToVM/GetResolvedJavaTypeTest.java --- a/hotspot/test/compiler/jvmci/compilerToVM/GetResolvedJavaTypeTest.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/jvmci/compilerToVM/GetResolvedJavaTypeTest.java Thu Sep 22 18:32:20 2016 +0000 @@ -53,7 +53,6 @@ import jdk.internal.misc.Unsafe; import jdk.test.lib.Asserts; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.vm.ci.hotspot.CompilerToVMHelper; import jdk.vm.ci.hotspot.HotSpotResolvedJavaMethod; import jdk.vm.ci.hotspot.HotSpotResolvedObjectType; @@ -154,7 +153,7 @@ abstract HotSpotResolvedObjectType getResolvedJavaType(); } - private static final Unsafe UNSAFE = UnsafeHelper.getUnsafe(); + private static final Unsafe UNSAFE = Unsafe.getUnsafe(); private static final WhiteBox WB = WhiteBox.getWhiteBox(); private static final Class TEST_CLASS = GetResolvedJavaTypeTest.class; /* a compressed parameter for tested method is set to false because diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/jvmci/compilerToVM/ResolveFieldInPoolTest.java --- a/hotspot/test/compiler/jvmci/compilerToVM/ResolveFieldInPoolTest.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/jvmci/compilerToVM/ResolveFieldInPoolTest.java Thu Sep 22 18:32:20 2016 +0000 @@ -53,7 +53,6 @@ import jdk.internal.misc.Unsafe; import jdk.internal.org.objectweb.asm.Opcodes; import jdk.test.lib.Asserts; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.vm.ci.hotspot.CompilerToVMHelper; import jdk.vm.ci.hotspot.HotSpotResolvedObjectType; import jdk.vm.ci.meta.ConstantPool; @@ -69,7 +68,7 @@ */ public class ResolveFieldInPoolTest { - private static final Unsafe UNSAFE = UnsafeHelper.getUnsafe(); + private static final Unsafe UNSAFE = Unsafe.getUnsafe(); public static void main(String[] args) throws Exception { Map typeTests = new HashMap<>(); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/jvmci/compilerToVM/ResolveMethodTest.java --- a/hotspot/test/compiler/jvmci/compilerToVM/ResolveMethodTest.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/jvmci/compilerToVM/ResolveMethodTest.java Thu Sep 22 18:32:20 2016 +0000 @@ -52,7 +52,6 @@ import jdk.internal.misc.Unsafe; import jdk.test.lib.Asserts; import jdk.test.lib.Utils; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.vm.ci.hotspot.CompilerToVMHelper; import jdk.vm.ci.hotspot.HotSpotResolvedJavaMethod; import jdk.vm.ci.hotspot.HotSpotResolvedObjectType; @@ -61,7 +60,7 @@ import java.util.Set; public class ResolveMethodTest { - private static final Unsafe UNSAFE = UnsafeHelper.getUnsafe(); + private static final Unsafe UNSAFE = Unsafe.getUnsafe(); public static void main(String args[]) { ResolveMethodTest test = new ResolveMethodTest(); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/jvmci/jdk.vm.ci.runtime.test/src/jdk/vm/ci/runtime/test/TestResolvedJavaType.java --- a/hotspot/test/compiler/jvmci/jdk.vm.ci.runtime.test/src/jdk/vm/ci/runtime/test/TestResolvedJavaType.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/jvmci/jdk.vm.ci.runtime.test/src/jdk/vm/ci/runtime/test/TestResolvedJavaType.java Thu Sep 22 18:32:20 2016 +0000 @@ -25,7 +25,6 @@ * @test * @requires (vm.simpleArch == "x64" | vm.simpleArch == "sparcv9" | vm.simpleArch == "aarch64") * @library ../../../../../ - * @ignore 8161550 * @modules java.base/jdk.internal.reflect * jdk.vm.ci/jdk.vm.ci.meta * jdk.vm.ci/jdk.vm.ci.runtime @@ -74,11 +73,29 @@ /** * Tests for {@link ResolvedJavaType}. */ +@SuppressWarnings("unchecked") public class TestResolvedJavaType extends TypeUniverse { + private static final Class SIGNATURE_POLYMORPHIC_CLASS = findPolymorphicSignatureClass(); public TestResolvedJavaType() { } + private static Class findPolymorphicSignatureClass() { + Class signaturePolyAnnotation = null; + try { + for (Class clazz : TestResolvedJavaType.class.getClassLoader().loadClass("java.lang.invoke.MethodHandle").getDeclaredClasses()) { + if (clazz.getName().endsWith("PolymorphicSignature") && Annotation.class.isAssignableFrom(clazz)) { + signaturePolyAnnotation = (Class) clazz; + break; + } + } + } catch (Throwable e) { + throw new AssertionError("Could not find annotation PolymorphicSignature in java.lang.invoke.MethodHandle", e); + } + assertNotNull(signaturePolyAnnotation); + return signaturePolyAnnotation; + } + @Test public void findInstanceFieldWithOffsetTest() { for (Class c : classes) { @@ -577,8 +594,14 @@ for (Method decl : decls) { ResolvedJavaMethod m = metaAccess.lookupJavaMethod(decl); if (m.isPublic()) { - ResolvedJavaMethod i = metaAccess.lookupJavaMethod(impl); - assertEquals(m.toString(), i, type.resolveMethod(m, context)); + ResolvedJavaMethod resolvedmethod = type.resolveMethod(m, context); + if (isSignaturePolymorphic(m)) { + // Signature polymorphic methods must not be resolved + assertNull(resolvedmethod); + } else { + ResolvedJavaMethod i = metaAccess.lookupJavaMethod(impl); + assertEquals(m.toString(), i, resolvedmethod); + } } } } @@ -606,8 +629,14 @@ for (Method decl : decls) { ResolvedJavaMethod m = metaAccess.lookupJavaMethod(decl); if (m.isPublic()) { - ResolvedJavaMethod i = metaAccess.lookupJavaMethod(impl); - assertEquals(i, type.resolveConcreteMethod(m, context)); + ResolvedJavaMethod resolvedMethod = type.resolveConcreteMethod(m, context); + if (isSignaturePolymorphic(m)) { + // Signature polymorphic methods must not be resolved + assertNull(String.format("Got: %s", resolvedMethod), resolvedMethod); + } else { + ResolvedJavaMethod i = metaAccess.lookupJavaMethod(impl); + assertEquals(i, resolvedMethod); + } } } } @@ -929,4 +958,8 @@ } } } + + private static boolean isSignaturePolymorphic(ResolvedJavaMethod method) { + return method.getAnnotation(SIGNATURE_POLYMORPHIC_CLASS) != null; + } } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/loopopts/UseCountedLoopSafepoints.java --- a/hotspot/test/compiler/loopopts/UseCountedLoopSafepoints.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/loopopts/UseCountedLoopSafepoints.java Thu Sep 22 18:32:20 2016 +0000 @@ -22,51 +22,32 @@ * */ -/** - * @test - * @bug 6869327 - * @summary Test that C2 flag UseCountedLoopSafepoints ensures a safepoint is kept in a CountedLoop - * @library /test/lib - * @modules java.base/jdk.internal.misc - * @ignore 8146096 - * @run driver compiler.loopopts.UseCountedLoopSafepoints - */ - package compiler.loopopts; -import jdk.test.lib.process.OutputAnalyzer; -import jdk.test.lib.process.ProcessTools; - -import java.util.concurrent.atomic.AtomicLong; +import java.lang.reflect.Method; +import sun.hotspot.WhiteBox; +import jdk.test.lib.Asserts; +import compiler.whitebox.CompilerWhiteBoxTest; public class UseCountedLoopSafepoints { - private static final AtomicLong _num = new AtomicLong(0); + private static final WhiteBox WB = WhiteBox.getWhiteBox(); + private static final String METHOD_NAME = "testMethod"; - // Uses the fact that an EnableBiasedLocking vmop will be started - // after 500ms, while we are still in the loop. If there is a - // safepoint in the counted loop, then we will reach safepoint - // very quickly. Otherwise SafepointTimeout will be hit. + private long accum = 0; + public static void main (String args[]) throws Exception { - if (args.length == 1) { - final int loops = Integer.parseInt(args[0]); - for (int i = 0; i < loops; i++) { - _num.addAndGet(1); - } - } else { - ProcessBuilder pb = ProcessTools.createJavaProcessBuilder( - "-XX:+IgnoreUnrecognizedVMOptions", - "-XX:-TieredCompilation", - "-XX:+UseBiasedLocking", - "-XX:BiasedLockingStartupDelay=500", - "-XX:+SafepointTimeout", - "-XX:SafepointTimeoutDelay=2000", - "-XX:+UseCountedLoopSafepoints", - UseCountedLoopSafepoints.class.getName(), - "2000000000" - ); - OutputAnalyzer output = new OutputAnalyzer(pb.start()); - output.shouldNotContain("Timeout detected"); - output.shouldHaveExitValue(0); + new UseCountedLoopSafepoints().testMethod(); + Method m = UseCountedLoopSafepoints.class.getDeclaredMethod(METHOD_NAME); + String directive = "[{ match: \"" + UseCountedLoopSafepoints.class.getName().replace('.', '/') + + "." + METHOD_NAME + "\", " + "BackgroundCompilation: false }]"; + Asserts.assertTrue(WB.addCompilerDirective(directive) == 1, "Can't add compiler directive"); + Asserts.assertTrue(WB.enqueueMethodForCompilation(m, + CompilerWhiteBoxTest.COMP_LEVEL_FULL_OPTIMIZATION), "Can't enqueue method"); + } + + private void testMethod() { + for (int i = 0; i < 100; i++) { + accum += accum << 5 + accum >> 4 - accum >>> 5; } } } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/loopopts/UseCountedLoopSafepointsTest.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/hotspot/test/compiler/loopopts/UseCountedLoopSafepointsTest.java Thu Sep 22 18:32:20 2016 +0000 @@ -0,0 +1,123 @@ +/* + * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + * + */ + +/** + * @test + * @bug 6869327 + * @summary Test that C2 flag UseCountedLoopSafepoints ensures a safepoint is kept in a CountedLoop + * @library /test/lib / + * @requires vm.compMode != "Xint" & vm.flavor == "server" & (vm.opt.TieredStopAtLevel == null | vm.opt.TieredStopAtLevel == 4) + * @modules java.base/jdk.internal.misc + * @build sun.hotspot.WhiteBox + * @run driver ClassFileInstaller sun.hotspot.WhiteBox + * sun.hotspot.WhiteBox$WhiteBoxPermission + * @run driver compiler.loopopts.UseCountedLoopSafepointsTest + */ + +package compiler.loopopts; + +import jdk.test.lib.process.ProcessTools; +import jdk.test.lib.process.OutputAnalyzer; +import java.util.List; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.Collections; +import jdk.test.lib.Asserts; + +/* Idea of this test is to check if ideal graph has CountedLoopEnd->SafePoint edge in case + of UseCountedLoopSafepoint enabled and has no such edge in case it's disabled. Restricting + compilation to testMethod only will leave only one counted loop (the one in testedMethod) */ +public class UseCountedLoopSafepointsTest { + + public static void main (String args[]) { + check(true); // check ideal graph with UseCountedLoopSafepoint enabled + check(false); // ... and disabled + } + + private static void check(boolean enabled) { + OutputAnalyzer oa; + try { + oa = ProcessTools.executeTestJvm("-XX:+UnlockDiagnosticVMOptions", "-Xbootclasspath/a:.", + "-XX:" + (enabled ? "+" : "-") + "UseCountedLoopSafepoints", "-XX:+WhiteBoxAPI", + "-XX:-Inline", "-Xbatch", "-XX:+PrintIdeal", "-XX:LoopUnrollLimit=0", + "-XX:CompileOnly=" + UseCountedLoopSafepoints.class.getName() + "::testMethod", + UseCountedLoopSafepoints.class.getName()); + } catch (Exception e) { + throw new Error("Exception launching child for case enabled=" + enabled + " : " + e, e); + } + oa.shouldHaveExitValue(0); + // parse output in seach of SafePoint and CountedLoopEnd nodes + List safePoints = new ArrayList<>(); + List loopEnds = new ArrayList<>(); + for (String line : oa.getOutput().split("\\n")) { + int separatorIndex = line.indexOf("\t==="); + if (separatorIndex > -1) { + String header = line.substring(0, separatorIndex); + if (header.endsWith("\tSafePoint")) { + safePoints.add(new Node("SafePoint", line)); + } else if (header.endsWith("\tCountedLoopEnd")) { + loopEnds.add(new Node("CountedLoopEnd", line)); + } + } + } + // now, find CountedLoopEnd -> SafePoint edge + boolean found = false; + for (Node loopEnd : loopEnds) { + found |= loopEnd.to.stream() + .filter(id -> nodeListHasElementWithId(safePoints, id)) + .findAny() + .isPresent(); + } + Asserts.assertEQ(enabled, found, "Safepoint " + (found ? "" : "not ") + "found"); + } + + private static boolean nodeListHasElementWithId(List list, int id) { + return list.stream() + .filter(node -> node.id == id) + .findAny() + .isPresent(); + } + + private static class Node { + public final int id; + public final List from; + public final List to; + + public Node(String name, String str) { + List tmpFrom = new ArrayList<>(); + List tmpTo = new ArrayList<>(); + // parse string like: " $id $name === $to1 $to2 ... [[ $from1 $from2 ... ]] $anything" + // example: 318 SafePoint === 317 1 304 1 1 10 308 [[ 97 74 ]] ... + id = Integer.parseInt(str.substring(1, str.indexOf(name)).trim()); + Arrays.stream(str.substring(str.indexOf("===") + 4, str.indexOf("[[")).trim().split("\\s+")) + .map(Integer::parseInt) + .forEach(tmpTo::add); + Arrays.stream(str.substring(str.indexOf("[[") + 3, str.indexOf("]]")).trim().split("\\s+")) + .map(Integer::parseInt) + .forEach(tmpFrom::add); + this.from = Collections.unmodifiableList(tmpFrom); + this.to = Collections.unmodifiableList(tmpTo); + } + } +} diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/loopopts/superword/TestVectorizationWithInvariant.java --- a/hotspot/test/compiler/loopopts/superword/TestVectorizationWithInvariant.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/loopopts/superword/TestVectorizationWithInvariant.java Thu Sep 22 18:32:20 2016 +0000 @@ -34,7 +34,6 @@ package compiler.loopopts.superword; import jdk.internal.misc.Unsafe; -import jdk.test.lib.unsafe.UnsafeHelper; public class TestVectorizationWithInvariant { @@ -43,7 +42,7 @@ private static final long CHAR_ARRAY_OFFSET; static { - unsafe = UnsafeHelper.getUnsafe(); + unsafe = Unsafe.getUnsafe(); BYTE_ARRAY_OFFSET = unsafe.arrayBaseOffset(byte[].class); CHAR_ARRAY_OFFSET = unsafe.arrayBaseOffset(char[].class); } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/rtm/locking/TestRTMAbortRatio.java --- a/hotspot/test/compiler/rtm/locking/TestRTMAbortRatio.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/rtm/locking/TestRTMAbortRatio.java Thu Sep 22 18:32:20 2016 +0000 @@ -49,7 +49,6 @@ import jdk.internal.misc.Unsafe; import jdk.test.lib.Asserts; import jdk.test.lib.process.OutputAnalyzer; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.test.lib.cli.CommandLineOptionTest; import jdk.test.lib.cli.predicate.AndPredicate; @@ -125,7 +124,7 @@ public static class Test implements CompilableTest { private static final int TOTAL_ITERATIONS = 10000; private static final int WARMUP_ITERATIONS = 1000; - private static final Unsafe UNSAFE = UnsafeHelper.getUnsafe(); + private static final Unsafe UNSAFE = Unsafe.getUnsafe(); private final Object monitor = new Object(); // Following field have to be static in order to avoid escape analysis. @SuppressWarnings("UnsuedDeclaration") diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/rtm/locking/TestRTMAfterNonRTMDeopt.java --- a/hotspot/test/compiler/rtm/locking/TestRTMAfterNonRTMDeopt.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/rtm/locking/TestRTMAfterNonRTMDeopt.java Thu Sep 22 18:32:20 2016 +0000 @@ -51,7 +51,6 @@ import jdk.internal.misc.Unsafe; import jdk.test.lib.Asserts; import jdk.test.lib.process.OutputAnalyzer; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.test.lib.cli.CommandLineOptionTest; import jdk.test.lib.cli.predicate.AndPredicate; @@ -158,7 +157,7 @@ private static int field = 0; private static final int ITERATIONS = 10000; private static final int RANGE_CHECK_AT = ITERATIONS / 2; - private static final Unsafe UNSAFE = UnsafeHelper.getUnsafe(); + private static final Unsafe UNSAFE = Unsafe.getUnsafe(); private final Object monitor = new Object(); @Override diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/rtm/locking/TestRTMDeoptOnLowAbortRatio.java --- a/hotspot/test/compiler/rtm/locking/TestRTMDeoptOnLowAbortRatio.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/rtm/locking/TestRTMDeoptOnLowAbortRatio.java Thu Sep 22 18:32:20 2016 +0000 @@ -48,7 +48,6 @@ import jdk.internal.misc.Unsafe; import jdk.test.lib.Asserts; import jdk.test.lib.process.OutputAnalyzer; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.test.lib.cli.CommandLineOptionTest; import jdk.test.lib.cli.predicate.AndPredicate; @@ -133,7 +132,7 @@ } public static class Test implements CompilableTest { - private static final Unsafe UNSAFE = UnsafeHelper.getUnsafe(); + private static final Unsafe UNSAFE = Unsafe.getUnsafe(); private final Object monitor = new Object(); @Override diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/rtm/locking/TestRTMLockingThreshold.java --- a/hotspot/test/compiler/rtm/locking/TestRTMLockingThreshold.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/rtm/locking/TestRTMLockingThreshold.java Thu Sep 22 18:32:20 2016 +0000 @@ -49,7 +49,6 @@ import jdk.internal.misc.Unsafe; import jdk.test.lib.Asserts; import jdk.test.lib.process.OutputAnalyzer; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.test.lib.cli.CommandLineOptionTest; import jdk.test.lib.cli.predicate.AndPredicate; @@ -142,7 +141,7 @@ @SuppressWarnings("UnsuedDeclaration") private static int field = 0; private static final int TOTAL_ITERATIONS = 10000; - private static final Unsafe UNSAFE = UnsafeHelper.getUnsafe(); + private static final Unsafe UNSAFE = Unsafe.getUnsafe(); private final Object monitor = new Object(); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/rtm/locking/TestRTMTotalCountIncrRate.java --- a/hotspot/test/compiler/rtm/locking/TestRTMTotalCountIncrRate.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/rtm/locking/TestRTMTotalCountIncrRate.java Thu Sep 22 18:32:20 2016 +0000 @@ -49,7 +49,6 @@ import jdk.internal.misc.Unsafe; import jdk.test.lib.Asserts; import jdk.test.lib.process.OutputAnalyzer; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.test.lib.cli.CommandLineOptionTest; import jdk.test.lib.cli.predicate.AndPredicate; @@ -113,7 +112,7 @@ public static class Test implements CompilableTest { private static final long TOTAL_ITERATIONS = 10000L; - private static final Unsafe UNSAFE = UnsafeHelper.getUnsafe(); + private static final Unsafe UNSAFE = Unsafe.getUnsafe(); private final Object monitor = new Object(); // Following field have to be static in order to avoid escape analysis. @SuppressWarnings("UnsuedDeclaration") diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/testlibrary/rtm/XAbortProvoker.java --- a/hotspot/test/compiler/testlibrary/rtm/XAbortProvoker.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/testlibrary/rtm/XAbortProvoker.java Thu Sep 22 18:32:20 2016 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it @@ -25,7 +25,6 @@ package compiler.testlibrary.rtm; import jdk.internal.misc.Unsafe; -import jdk.test.lib.unsafe.UnsafeHelper; /** * Current RTM locking implementation force transaction abort @@ -35,7 +34,7 @@ // Following field have to be static in order to avoid escape analysis. @SuppressWarnings("UnsuedDeclaration") private static int field = 0; - private static final Unsafe UNSAFE = UnsafeHelper.getUnsafe(); + private static final Unsafe UNSAFE = Unsafe.getUnsafe(); public XAbortProvoker() { this(new Object()); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/unsafe/UnsafeOffHeapBooleanTest.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/hotspot/test/compiler/unsafe/UnsafeOffHeapBooleanTest.java Thu Sep 22 18:32:20 2016 +0000 @@ -0,0 +1,92 @@ +/* + * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ + +/* + * @test + * @bug 8161720 + * @modules java.base/jdk.internal.misc + * @run main/othervm -Xint UnsafeOffHeapBooleanTest 1 + * @run main/othervm -XX:+TieredCompilation -XX:TieredStopAtLevel=3 -Xbatch UnsafeOffHeapBooleanTest 20000 + * @run main/othervm -XX:-TieredCompilation -Xbatch UnsafeOffHeapBooleanTest 20000 + */ + + +import java.lang.reflect.Field; +import jdk.internal.misc.Unsafe; + +public class UnsafeOffHeapBooleanTest { + static boolean bool0 = false, bool1 = false, result = false; + static Unsafe UNSAFE = Unsafe.getUnsafe(); + static long offHeapMemory; + + public static void test() { + // Write two bytes to the off-heap memory location, both + // bytes correspond to the boolean value 'true'. + UNSAFE.putShort(null, offHeapMemory, (short)0x0204); + + // Read two bytes from the storage allocated above (as booleans). + bool0 = UNSAFE.getBoolean(null, offHeapMemory + 0); + bool1 = UNSAFE.getBoolean(null, offHeapMemory + 1); + result = bool0 & bool1; + } + + public static void main(String args[]) { + System.out.println("### Test started"); + + if (args.length != 1) { + throw new RuntimeException("### Test failure: test called with incorrect number of arguments"); + } + + // Allocate two bytes of storage. + offHeapMemory = UNSAFE.allocateMemory(2); + + try { + for (int i = 0; i < Integer.parseInt(args[0]); i++) { + test(); + } + + // Check if the two 'true' boolean values were normalized + // (i.e., reduced from the range 1...255 to 1). + if (!bool0 || !bool1 || !result) { + System.out.println("Some of the results below are wrong"); + System.out.println("bool0 is: " + bool0); + System.out.println("bool1 is: " + bool1); + System.out.println("bool0 & bool1 is: " + result); + System.out.println("==================================="); + throw new RuntimeException("### Test failed"); + } else { + System.out.println("Test generated correct results"); + System.out.println("bool0 is: " + bool0); + System.out.println("bool1 is: " + bool1); + System.out.println("bool0 & bool1 is: " + result); + System.out.println("==================================="); + } + } catch (NumberFormatException e) { + throw new RuntimeException("### Test failure: test called with incorrectly formatted parameter"); + } + + UNSAFE.freeMemory(offHeapMemory); + + System.out.println("### Test passed"); + } +} diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/unsafe/UnsafeOnHeapBooleanTest.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/hotspot/test/compiler/unsafe/UnsafeOnHeapBooleanTest.java Thu Sep 22 18:32:20 2016 +0000 @@ -0,0 +1,95 @@ +/* + * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ + +/* + * @test + * @bug 8161720 + * @modules java.base/jdk.internal.misc + * @run main/othervm -Xint UnsafeOnHeapBooleanTest 1 + * @run main/othervm -XX:-UseOnStackReplacement -XX:+TieredCompilation -XX:TieredStopAtLevel=3 -Xbatch UnsafeOnHeapBooleanTest 20000 + * @run main/othervm -XX:-UseOnStackReplacement -XX:-TieredCompilation -Xbatch UnsafeOnHeapBooleanTest 20000 + */ + +import java.lang.reflect.Field; +import jdk.internal.misc.Unsafe; + +public class UnsafeOnHeapBooleanTest { + static short static_v; + static boolean bool0 = false, bool1 = false, result = false; + static Unsafe UNSAFE = Unsafe.getUnsafe(); + + public static void test() { + try { + // Write two bytes into the static field + // UnsafeOnHeapBooleanTest.static_v write two values. Both + // bytes correspond to the boolean value 'true'. + Field staticVField = UnsafeOnHeapBooleanTest.class.getDeclaredField("static_v"); + Object base = UNSAFE.staticFieldBase(staticVField); + long offset = UNSAFE.staticFieldOffset(staticVField); + UNSAFE.putShort(base, offset, (short)0x0204); + + // Read two bytes from the static field + // UnsafeOnHeapBooleanTest.static_v (as booleans). + bool0 = UNSAFE.getBoolean(base, offset + 0); + bool1 = UNSAFE.getBoolean(base, offset + 1); + result = bool0 & bool1; + } catch (NoSuchFieldException e) { + throw new RuntimeException("### Test failure: static field UnsafeOnHeapBooleanTest.static_v was not found"); + } + } + + public static void main(String args[]) { + System.out.println("### Test started"); + + if (args.length != 1) { + throw new RuntimeException("### Test failure: test called with incorrect number of arguments"); + } + + try { + for (int i = 0; i < Integer.parseInt(args[0]); i++) { + test(); + } + + // Check if the two 'true' boolean values were normalized + // (i.e., reduced from the range 1...255 to 1). + if (!bool0 || !bool1 || !result) { + System.out.println("Some of the results below are wrong"); + System.out.println("bool0 is: " + bool0); + System.out.println("bool1 is: " + bool1); + System.out.println("bool0 & bool1 is: " + result); + System.out.println("==================================="); + throw new RuntimeException("### Test failed"); + } else { + System.out.println("Test generated correct results"); + System.out.println("bool0 is: " + bool0); + System.out.println("bool1 is: " + bool1); + System.out.println("bool0 & bool1 is: " + result); + System.out.println("==================================="); + } + } catch (NumberFormatException e) { + throw new RuntimeException("### Test failure: test called with incorrectly formatted parameter"); + } + + System.out.println("### Test passed"); + } +} diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/unsafe/UnsafeRaw.java --- a/hotspot/test/compiler/unsafe/UnsafeRaw.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/compiler/unsafe/UnsafeRaw.java Thu Sep 22 18:32:20 2016 +0000 @@ -35,7 +35,6 @@ import jdk.internal.misc.Unsafe; import jdk.test.lib.Utils; -import jdk.test.lib.unsafe.UnsafeHelper; import java.util.Random; @@ -82,7 +81,7 @@ } public static void main(String[] args) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); final int array_size = 128; final int element_size = 4; final int magic = 0x12345678; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/compiler/unsafe/UnsafeSmallOffsetBooleanAccessTest.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/hotspot/test/compiler/unsafe/UnsafeSmallOffsetBooleanAccessTest.java Thu Sep 22 18:32:20 2016 +0000 @@ -0,0 +1,85 @@ +/* + * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ + +/* + * @test + * @bug 8161720 + * @modules java.base/jdk.internal.misc + * @run main/othervm -XX:+IgnoreUnrecognizedVMOptions -Xbatch -XX:-TieredCompilation UnsafeSmallOffsetBooleanAccessTest + * @run main/othervm -Xbatch UnsafeSmallOffsetBooleanAccessTest + */ + +import java.util.Random; +import jdk.internal.misc.Unsafe; + +public class UnsafeSmallOffsetBooleanAccessTest { + static final Unsafe UNSAFE = Unsafe.getUnsafe(); + static final long F_OFFSET; + static final Random random = new Random(); + + static { + try { + F_OFFSET = UNSAFE.objectFieldOffset(T.class.getDeclaredField("f")); + System.out.println("The offset is: " + F_OFFSET); + } catch (Exception e) { + throw new Error(e); + } + } + + static class T { + boolean f; + } + + // Always return false in a way that is not obvious to the compiler. + public static boolean myRandom() { + if (random.nextInt(101) > 134) { + return true; + } else { + return false; + } + } + + public static boolean test(T t) { + boolean result = false; + for (int i = 0; i < 20000; i++) { + boolean random = myRandom(); + // If myRandom() returns false, access t.f. + // + // If myRandom() returns true, access virtual address + // F_OFFSET. That address is most likely not mapped, + // therefore the access will most likely cause a + // crash. We're not concerned about that, though, because + // myRandom() always returns false. However, the C2 + // compiler avoids normalization of the value returned by + // getBoolean in this case. + result = UNSAFE.getBoolean(myRandom() ? null : t, F_OFFSET); + } + return result; + } + + public static void main(String[] args) { + T t = new T(); + UNSAFE.putBoolean(t, F_OFFSET, true); + System.out.println("The result for t is: " + test(t)); + } +} diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/gc/arguments/TestMaxMinHeapFreeRatioFlags.java --- a/hotspot/test/gc/arguments/TestMaxMinHeapFreeRatioFlags.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/gc/arguments/TestMaxMinHeapFreeRatioFlags.java Thu Sep 22 18:32:20 2016 +0000 @@ -37,7 +37,6 @@ import jdk.test.lib.process.OutputAnalyzer; import jdk.test.lib.process.ProcessTools; import jdk.test.lib.Utils; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; public class TestMaxMinHeapFreeRatioFlags { @@ -134,7 +133,7 @@ */ public static class RatioVerifier { - private static final Unsafe unsafe = UnsafeHelper.getUnsafe(); + private static final Unsafe unsafe = Unsafe.getUnsafe(); // Size of byte array that will be allocated public static final int CHUNK_SIZE = 1024; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/gc/arguments/TestTargetSurvivorRatioFlag.java --- a/hotspot/test/gc/arguments/TestTargetSurvivorRatioFlag.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/gc/arguments/TestTargetSurvivorRatioFlag.java Thu Sep 22 18:32:20 2016 +0000 @@ -46,7 +46,6 @@ import jdk.test.lib.process.OutputAnalyzer; import jdk.test.lib.process.ProcessTools; import jdk.test.lib.Utils; -import jdk.test.lib.unsafe.UnsafeHelper; import sun.hotspot.WhiteBox; /* In order to test that TargetSurvivorRatio affects survivor space occupancy @@ -249,7 +248,7 @@ public static class TargetSurvivorRatioVerifier { static final WhiteBox wb = WhiteBox.getWhiteBox(); - static final Unsafe unsafe = UnsafeHelper.getUnsafe(); + static final Unsafe unsafe = Unsafe.getUnsafe(); // Desired size of memory allocated at once public static final int CHUNK_SIZE = 1024; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/gc/class_unloading/TestClassUnloadingDisabled.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/hotspot/test/gc/class_unloading/TestClassUnloadingDisabled.java Thu Sep 22 18:32:20 2016 +0000 @@ -0,0 +1,118 @@ +/* + * Copyright (c) 2016, Oracle and/or its affiliates. All rights reqserved. + * 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 + * @key gc + * @bug 8114823 + * @requires vm.gc == null + * @requires vm.opt.ExplicitGCInvokesConcurrent != true + * @requires vm.opt.ClassUnloading != true + * @library /test/lib + * @modules java.base/jdk.internal.misc + * java.management + * @build sun.hotspot.WhiteBox + * @run main ClassFileInstaller sun.hotspot.WhiteBox + * sun.hotspot.WhiteBox$WhiteBoxPermission + * + * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI + * -XX:-ClassUnloading -XX:+UseG1GC TestClassUnloadingDisabled + * + * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI + * -XX:-ClassUnloading -XX:+UseSerialGC TestClassUnloadingDisabled + * + * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI + * -XX:-ClassUnloading -XX:+UseParallelGC TestClassUnloadingDisabled + * + * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI + * -XX:-ClassUnloading -XX:+UseConcMarkSweepGC TestClassUnloadingDisabled + */ + +import java.io.File; +import java.io.IOException; +import java.nio.file.Files; +import java.nio.file.Path; +import java.nio.file.Paths; + +import sun.hotspot.WhiteBox; + +import static jdk.test.lib.Asserts.*; + +public class TestClassUnloadingDisabled { + public static void main(String args[]) throws Exception { + final WhiteBox wb = WhiteBox.getWhiteBox(); + // Fetch the dir where the test class and the class + // to be loaded resides. + String classDir = TestClassUnloadingDisabled.class.getProtectionDomain().getCodeSource().getLocation().getPath(); + String className = "ClassToLoadUnload"; + + assertFalse(wb.isClassAlive(className), "Should not be loaded yet"); + + // The NoPDClassLoader handles loading classes in the test directory + // and loads them without a protection domain, which in some cases + // keeps the class live regardless of marking state. + NoPDClassLoader nopd = new NoPDClassLoader(classDir); + nopd.loadClass(className); + + assertTrue(wb.isClassAlive(className), "Class should be loaded"); + + // Clear the class-loader, class and object references to make + // class unloading possible. + nopd = null; + + System.gc(); + assertTrue(wb.isClassAlive(className), "Class should not have ben unloaded"); + } +} + +class NoPDClassLoader extends ClassLoader { + String path; + + NoPDClassLoader(String path) { + this.path = path; + } + + public Class loadClass(String name) throws ClassNotFoundException { + byte[] cls = null; + File f = new File(path,name + ".class"); + + // Delegate class loading if class not present in the given + // directory. + if (!f.exists()) { + return super.loadClass(name); + } + + try { + Path path = Paths.get(f.getAbsolutePath()); + cls = Files.readAllBytes(path); + } catch (IOException e) { + throw new ClassNotFoundException(name); + } + + // Define class with no protection domain and resolve it. + return defineClass(name, cls, 0, cls.length, null); + } +} + +class ClassToLoadUnload { +} diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/jprt.config --- a/hotspot/test/jprt.config Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/jprt.config Thu Sep 22 18:32:20 2016 +0000 @@ -86,12 +86,12 @@ fi # Add basic solaris system paths - path4sdk=/usr/ccs/bin:/usr/ccs/lib:/usr/bin:/bin:/usr/sfw/bin + path4sdk=/usr/bin # Find GNU make - make=/usr/sfw/bin/gmake + make=/usr/bin/gmake if [ ! -f ${make} ] ; then - make=/opt/sfw/bin/gmake + make=/usr/gnu/bin/make if [ ! -f ${make} ] ; then make=${slashjava}/devtools/${solaris_arch}/bin/gnumake fi diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/CommandLine/OptionsValidation/TestOptionsWithRanges.java --- a/hotspot/test/runtime/CommandLine/OptionsValidation/TestOptionsWithRanges.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/CommandLine/OptionsValidation/TestOptionsWithRanges.java Thu Sep 22 18:32:20 2016 +0000 @@ -89,20 +89,6 @@ excludeTestMaxRange("CICompilerCount"); /* - * JDK-8136766 - * Temporarily remove ThreadStackSize from testing because Windows can set it to 0 - * (for default OS size) but other platforms insist it must be greater than 0 - */ - excludeTestRange("ThreadStackSize"); - - /* - * Remove the flag controlling the size of the stack because the - * flag has direct influence on the physical memory usage of - * the VM. - */ - allOptionsAsMap.remove("CompilerThreadStackSize"); - - /* * Exclude MallocMaxTestWords as it is expected to exit VM at small values (>=0) */ excludeTestMinRange("MallocMaxTestWords"); @@ -124,6 +110,8 @@ excludeTestMaxRange("OldSize"); excludeTestMaxRange("ParallelGCThreads"); + excludeTestMaxRange("CompilerThreadStackSize"); + excludeTestMaxRange("ThreadStackSize"); excludeTestMaxRange("VMThreadStackSize"); /* diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/ErrorHandling/CreateCoredumpOnCrash.java --- a/hotspot/test/runtime/ErrorHandling/CreateCoredumpOnCrash.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/ErrorHandling/CreateCoredumpOnCrash.java Thu Sep 22 18:32:20 2016 +0000 @@ -34,13 +34,12 @@ import jdk.test.lib.process.ProcessTools; import jdk.test.lib.process.OutputAnalyzer; import jdk.test.lib.Platform; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; public class CreateCoredumpOnCrash { private static class Crasher { public static void main(String[] args) { - UnsafeHelper.getUnsafe().putInt(0L, 0); + Unsafe.getUnsafe().putInt(0L, 0); } } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/ErrorHandling/ProblematicFrameTest.java --- a/hotspot/test/runtime/ErrorHandling/ProblematicFrameTest.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/ErrorHandling/ProblematicFrameTest.java Thu Sep 22 18:32:20 2016 +0000 @@ -35,14 +35,13 @@ import jdk.test.lib.process.ProcessTools; import jdk.test.lib.process.OutputAnalyzer; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; public class ProblematicFrameTest { private static class Crasher { public static void main(String[] args) { - UnsafeHelper.getUnsafe().getInt(0); + Unsafe.getUnsafe().getInt(0); } } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/LocalLong/LocalLongHelper.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/hotspot/test/runtime/LocalLong/LocalLongHelper.java Thu Sep 22 18:32:20 2016 +0000 @@ -0,0 +1,99 @@ +/* + * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ + +import java.lang.reflect.Field; +import java.lang.reflect.Method; +import java.util.List; +import java.util.Set; +import java.util.stream.Collectors; +import java.lang.StackWalker.StackFrame; + +public class LocalLongHelper { + static StackWalker sw; + static Method intValue; + static Method getLocals; + static Class primitiveValueClass; + static Method primitiveType; + static Method getMethodType; + static Field memberName; + static Field offset; + + public static void main(String[] args) throws Throwable { + setupReflectionStatics(); + new LocalLongHelper().longArg(0xC0FFEE, 0x1234567890ABCDEFL); + } + + // locals[2] contains the high byte of the long argument. + public long longArg(int i, long l) throws Throwable { + List frames = sw.walk(s -> s.collect(Collectors.toList())); + Object[] locals = (Object[]) getLocals.invoke(frames.get(0)); + + int locals_2 = (int) intValue.invoke(locals[2]); + if (locals_2 != 0){ + throw new RuntimeException("Expected locals_2 == 0"); + } + return l; // Don't want l to become a dead var + } + + private static void setupReflectionStatics() throws Throwable { + Class liveStackFrameClass = Class.forName("java.lang.LiveStackFrame"); + primitiveValueClass = Class.forName("java.lang.LiveStackFrame$PrimitiveValue"); + + getLocals = liveStackFrameClass.getDeclaredMethod("getLocals"); + getLocals.setAccessible(true); + + intValue = primitiveValueClass.getDeclaredMethod("intValue"); + intValue.setAccessible(true); + + Class stackFrameInfoClass = Class.forName("java.lang.StackFrameInfo"); + memberName = stackFrameInfoClass.getDeclaredField("memberName"); + memberName.setAccessible(true); + offset = stackFrameInfoClass.getDeclaredField("bci"); + offset.setAccessible(true); + getMethodType = Class.forName("java.lang.invoke.MemberName").getDeclaredMethod("getMethodType"); + getMethodType.setAccessible(true); + + Class extendedOptionClass = Class.forName("java.lang.StackWalker$ExtendedOption"); + Method ewsNI = StackWalker.class.getDeclaredMethod("newInstance", Set.class, extendedOptionClass); + ewsNI.setAccessible(true); + Field f = extendedOptionClass.getDeclaredField("LOCALS_AND_OPERANDS"); + f.setAccessible(true); + Object localsAndOperandsOption = f.get(null); + + primitiveType = primitiveValueClass.getDeclaredMethod("type"); + primitiveType.setAccessible(true); + + sw = (StackWalker) ewsNI.invoke(null, java.util.Collections.emptySet(), localsAndOperandsOption); + } + + private static String type(Object o) throws Throwable { + if (primitiveValueClass.isInstance(o)) { + final char c = (char) primitiveType.invoke(o); + return String.valueOf(c); + } else if (o != null) { + return o.getClass().getName(); + } else { + return "null"; + } + } +} diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/LocalLong/LocalLongTest.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/hotspot/test/runtime/LocalLong/LocalLongTest.java Thu Sep 22 18:32:20 2016 +0000 @@ -0,0 +1,47 @@ +/* + * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ + + +/* + * @test LocalLongTest + * @bug 8163014 + * @modules java.base/jdk.internal.misc + * @library /test/lib + * @compile LocalLongHelper.java + * @run driver LocalLongTest + */ + +import jdk.test.lib.Platform; +import jdk.test.lib.process.ProcessTools; +import jdk.test.lib.process.OutputAnalyzer; + +public class LocalLongTest { + public static void main(String... args) throws Exception { + if (Platform.is64bit()) { + ProcessBuilder pb = ProcessTools.createJavaProcessBuilder("-Xint", + "LocalLongHelper"); + OutputAnalyzer o = new OutputAnalyzer(pb.start()); + o.shouldHaveExitValue(0); + } + }; +} diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/NMT/CheckForProperDetailStackTrace.java --- a/hotspot/test/runtime/NMT/CheckForProperDetailStackTrace.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/NMT/CheckForProperDetailStackTrace.java Thu Sep 22 18:32:20 2016 +0000 @@ -57,11 +57,6 @@ private static String expectedSymbol = "locked_create_entry_or_null"; - private static final String jdkDebug = System.getProperty("jdk.debug"); - private static boolean isSlowDebugBuild() { - return (jdkDebug.toLowerCase().equals("slowdebug")); - } - public static void main(String args[]) throws Exception { ProcessBuilder pb = ProcessTools.createJavaProcessBuilder( "-XX:+UnlockDiagnosticVMOptions", @@ -76,11 +71,12 @@ output.shouldNotContain("NativeCallStack::NativeCallStack"); output.shouldNotContain("os::get_native_stack"); - // AllocateHeap shouldn't be in the output because it is suppose to always be inlined. - // We check for that here, but allow it for Windows and Solaris slowdebug builds because - // the compiler ends up not inlining AllocateHeap. + // AllocateHeap shouldn't be in the output because it is supposed to always be inlined. + // We check for that here, but allow it for Aix, Solaris and Windows slowdebug builds + // because the compiler ends up not inlining AllocateHeap. Boolean okToHaveAllocateHeap = - isSlowDebugBuild() && (Platform.isSolaris() || Platform.isWindows()); + Platform.isSlowDebugBuild() && + (Platform.isAix() || Platform.isSolaris() || Platform.isWindows()); if (!okToHaveAllocateHeap) { output.shouldNotContain("AllocateHeap"); } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Thread/TooSmallStackSize.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/hotspot/test/runtime/Thread/TooSmallStackSize.java Thu Sep 22 18:32:20 2016 +0000 @@ -0,0 +1,198 @@ +/* + * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ + +/* + * @test + * @bug 8140520 + * @summary Setting small CompilerThreadStackSize, ThreadStackSize, and + * VMThreadStackSize values should result in an error message that shows + * the minimum stack size value for each thread type. + * @library /test/lib + * @modules java.base/jdk.internal.misc + * java.management + * @run main TooSmallStackSize + */ + +/* + * The primary purpose of this test is to make sure we can run with a + * stack smaller than the minimum without crashing. Also this test will + * determine the minimum allowed stack size for the platform (as + * provided by the JVM error message when a very small stack is used), + * and then verify that the JVM can be launched with that stack size + * without a crash or any error messages. + * + * Note: The '-Xss' and '-XX:ThreadStackSize=' options + * both control Java thread stack size. This repo's version of the test + * exercises the '-XX:ThreadStackSize' VM option. The jdk repo's version + * of the test exercises the '-Xss' option. + */ + +import jdk.test.lib.process.ProcessTools; +import jdk.test.lib.process.OutputAnalyzer; + +public class TooSmallStackSize { + /* for debugging. Normally false. */ + static final boolean verbose = false; + static final String CompilerThreadStackSizeString = "CompilerThreadStackSize"; + static final String ThreadStackSizeString = "Java thread stack size"; + static final String VMThreadStackSizeString = "VMThreadStackSize"; + + /* + * Returns the minimum stack size this platform will allowed based on the + * contents of the error message the JVM outputs when too small of a + * stack size was used. + * + * The testOutput argument must contain the result of having already run + * the JVM with too small of a stack size. + */ + static String getMinStackAllowed(String testOutput) { + /* + * The JVM output will contain in one of the lines: + * "The CompilerThreadStackSize specified is too small. Specify at least 100k" + * "The Java thread stack size specified is too small. Specify at least 100k" + * "The VMThreadStackSize specified is too small. Specify at least 100k" + * Although the actual size will vary. We need to extract this size + * string from the output and return it. + */ + String matchStr = "Specify at least "; + int match_idx = testOutput.indexOf(matchStr); + if (match_idx >= 0) { + int size_start_idx = match_idx + matchStr.length(); + int k_start_idx = testOutput.indexOf("k", size_start_idx); + // don't include the 'k'; the caller will have to + // add it back as needed. + return testOutput.substring(size_start_idx, k_start_idx); + } + + System.out.println("Expect='" + matchStr + "'"); + System.out.println("Actual: " + testOutput); + System.out.println("FAILED: Could not get the stack size from the output"); + throw new RuntimeException("test fails"); + } + + /* + * Run the JVM with the specified stack size. + * + * Returns the minimum allowed stack size gleaned from the error message, + * if there is an error message. Otherwise returns the stack size passed in. + */ + static String checkStack(String stackOption, String optionMesg, String stackSize) throws Exception { + String min_stack_allowed; + + System.out.println("*** Testing " + stackOption + stackSize); + + ProcessBuilder pb = ProcessTools.createJavaProcessBuilder( + stackOption + stackSize, + // Uncomment the following to get log output + // that shows actual thread creation sizes. + // "-Xlog:os+thread", + "-version"); + + OutputAnalyzer output = new OutputAnalyzer(pb.start()); + + if (verbose) { + System.out.println("stdout: " + output.getStdout()); + } + + if (output.getExitValue() == 0) { + // checkMinStackAllowed() is called with stackSize values + // that should be the minimum that works. This method, + // checkStack(), is called with stackSize values that + // should be too small and result in error messages. + // However, some platforms fix up a stackSize value that is + // too small into something that works so we have to allow + // for checkStack() calls that work. + System.out.println("PASSED: got exit_code == 0 with " + stackOption + stackSize); + min_stack_allowed = stackSize; + } else { + String expect = "The " + optionMesg + " specified is too small"; + if (verbose) { + System.out.println("Expect='" + expect + "'"); + } + output.shouldContain(expect); + min_stack_allowed = getMinStackAllowed(output.getStdout()); + + System.out.println("PASSED: got expected error message with " + stackOption + stackSize); + } + + return min_stack_allowed; + } + + /* + * Run the JVM with the minimum allowed stack size. This should always succeed. + */ + static void checkMinStackAllowed(String stackOption, String optionMesg, String stackSize) throws Exception { + System.out.println("*** Testing " + stackOption + stackSize); + + ProcessBuilder pb = ProcessTools.createJavaProcessBuilder( + stackOption + stackSize, + // Uncomment the following to get log output + // that shows actual thread creation sizes. + // "-Xlog:os+thread", + "-version"); + + OutputAnalyzer output = new OutputAnalyzer(pb.start()); + output.shouldHaveExitValue(0); + + System.out.println("PASSED: VM launched with " + stackOption + stackSize); + } + + public static void main(String... args) throws Exception { + /* + * The result of a 16k stack size should be a quick exit with a complaint + * that the stack size is too small. However, for some win32 builds, the + * stack is always at least 64k, and this also sometimes is the minimum + * allowed size, so we won't see an error in this case. + * + * This test case will also produce a crash on some platforms if the fix + * for 6762191 is not yet in place. + */ + checkStack("-XX:ThreadStackSize=", ThreadStackSizeString, "16"); + + /* + * Try with a 32k stack size, which is the size that the launcher will + * set to if you try setting to anything smaller. This should produce the same + * result as setting to 16k if the fix for 6762191 is in place. + */ + String min_stack_allowed = checkStack("-XX:ThreadStackSize=", ThreadStackSizeString, "32"); + + /* + * Try again with a the minimum stack size that was given in the error message + */ + checkMinStackAllowed("-XX:ThreadStackSize=", ThreadStackSizeString, min_stack_allowed); + + /* + * Now redo the same tests with the compiler thread stack size: + */ + checkStack("-XX:CompilerThreadStackSize=", CompilerThreadStackSizeString, "16"); + min_stack_allowed = checkStack("-XX:CompilerThreadStackSize=", CompilerThreadStackSizeString, "32"); + checkMinStackAllowed("-XX:CompilerThreadStackSize=", CompilerThreadStackSizeString, min_stack_allowed); + + /* + * Now redo the same tests with the VM thread stack size: + */ + checkStack("-XX:VMThreadStackSize=", VMThreadStackSizeString, "16"); + min_stack_allowed = checkStack("-XX:VMThreadStackSize=", VMThreadStackSizeString, "32"); + checkMinStackAllowed("-XX:VMThreadStackSize=", VMThreadStackSizeString, min_stack_allowed); + } +} diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/AllocateInstance.java --- a/hotspot/test/runtime/Unsafe/AllocateInstance.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/AllocateInstance.java Thu Sep 22 18:32:20 2016 +0000 @@ -30,12 +30,11 @@ * @run main AllocateInstance */ -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class AllocateInstance { - static final Unsafe UNSAFE = UnsafeHelper.getUnsafe(); + static final Unsafe UNSAFE = Unsafe.getUnsafe(); class TestClass { public boolean calledConstructor = false; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/AllocateMemory.java --- a/hotspot/test/runtime/Unsafe/AllocateMemory.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/AllocateMemory.java Thu Sep 22 18:32:20 2016 +0000 @@ -31,13 +31,12 @@ * @run main/othervm -XX:+UnlockDiagnosticVMOptions -XX:MallocMaxTestWords=100m AllocateMemory */ -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class AllocateMemory { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); // Allocate a byte, write to the location and read back the value long address = unsafe.allocateMemory(1); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/CopyMemory.java --- a/hotspot/test/runtime/Unsafe/CopyMemory.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/CopyMemory.java Thu Sep 22 18:32:20 2016 +0000 @@ -30,14 +30,13 @@ * @run main CopyMemory */ -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class CopyMemory { final static int LENGTH = 8; public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); long src = unsafe.allocateMemory(LENGTH); long dst = unsafe.allocateMemory(LENGTH); assertNotEquals(src, 0L); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/DefineClass.java --- a/hotspot/test/runtime/Unsafe/DefineClass.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/DefineClass.java Thu Sep 22 18:32:20 2016 +0000 @@ -34,13 +34,12 @@ import java.security.ProtectionDomain; import java.io.InputStream; import jdk.test.lib.InMemoryJavaCompiler; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class DefineClass { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); TestClassLoader classloader = new TestClassLoader(); ProtectionDomain pd = new ProtectionDomain(null, null); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/FieldOffset.java --- a/hotspot/test/runtime/Unsafe/FieldOffset.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/FieldOffset.java Thu Sep 22 18:32:20 2016 +0000 @@ -31,14 +31,13 @@ */ import java.lang.reflect.Field; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import java.lang.reflect.*; import static jdk.test.lib.Asserts.*; public class FieldOffset { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); Field[] fields = Test.class.getDeclaredFields(); for (int i = 0; i < fields.length; i++) { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/GetField.java --- a/hotspot/test/runtime/Unsafe/GetField.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/GetField.java Thu Sep 22 18:32:20 2016 +0000 @@ -30,14 +30,13 @@ * @run main GetField */ -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import java.lang.reflect.*; import static jdk.test.lib.Asserts.*; public class GetField { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); // Unsafe.INVALID_FIELD_OFFSET is a static final int field, // make sure getField returns the correct field Field field = Unsafe.class.getField("INVALID_FIELD_OFFSET"); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/GetPutAddress.java --- a/hotspot/test/runtime/Unsafe/GetPutAddress.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/GetPutAddress.java Thu Sep 22 18:32:20 2016 +0000 @@ -31,13 +31,12 @@ */ import jdk.test.lib.Platform; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class GetPutAddress { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); int addressSize = unsafe.addressSize(); // Ensure the size returned from Unsafe.addressSize is correct assertEquals(unsafe.addressSize(), Platform.is32bit() ? 4 : 8); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/GetPutBoolean.java --- a/hotspot/test/runtime/Unsafe/GetPutBoolean.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/GetPutBoolean.java Thu Sep 22 18:32:20 2016 +0000 @@ -31,13 +31,12 @@ */ import java.lang.reflect.Field; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class GetPutBoolean { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); Test t = new Test(); Field field = Test.class.getField("b1"); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/GetPutByte.java --- a/hotspot/test/runtime/Unsafe/GetPutByte.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/GetPutByte.java Thu Sep 22 18:32:20 2016 +0000 @@ -31,13 +31,12 @@ */ import java.lang.reflect.Field; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class GetPutByte { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); Test t = new Test(); Field field = Test.class.getField("b"); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/GetPutChar.java --- a/hotspot/test/runtime/Unsafe/GetPutChar.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/GetPutChar.java Thu Sep 22 18:32:20 2016 +0000 @@ -31,13 +31,12 @@ */ import java.lang.reflect.Field; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class GetPutChar { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); Test t = new Test(); Field field = Test.class.getField("c"); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/GetPutDouble.java --- a/hotspot/test/runtime/Unsafe/GetPutDouble.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/GetPutDouble.java Thu Sep 22 18:32:20 2016 +0000 @@ -31,13 +31,12 @@ */ import java.lang.reflect.Field; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class GetPutDouble { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); Test t = new Test(); Field field = Test.class.getField("d"); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/GetPutFloat.java --- a/hotspot/test/runtime/Unsafe/GetPutFloat.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/GetPutFloat.java Thu Sep 22 18:32:20 2016 +0000 @@ -31,13 +31,12 @@ */ import java.lang.reflect.Field; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class GetPutFloat { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); Test t = new Test(); Field field = Test.class.getField("f"); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/GetPutInt.java --- a/hotspot/test/runtime/Unsafe/GetPutInt.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/GetPutInt.java Thu Sep 22 18:32:20 2016 +0000 @@ -30,13 +30,12 @@ */ import java.lang.reflect.Field; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class GetPutInt { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); Test t = new Test(); Field field = Test.class.getField("i"); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/GetPutLong.java --- a/hotspot/test/runtime/Unsafe/GetPutLong.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/GetPutLong.java Thu Sep 22 18:32:20 2016 +0000 @@ -31,13 +31,12 @@ */ import java.lang.reflect.Field; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class GetPutLong { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); Test t = new Test(); Field field = Test.class.getField("l"); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/GetPutObject.java --- a/hotspot/test/runtime/Unsafe/GetPutObject.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/GetPutObject.java Thu Sep 22 18:32:20 2016 +0000 @@ -31,13 +31,12 @@ */ import java.lang.reflect.Field; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class GetPutObject { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); Test t = new Test(); Object o = new Object(); Field field = Test.class.getField("o"); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/GetPutShort.java --- a/hotspot/test/runtime/Unsafe/GetPutShort.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/GetPutShort.java Thu Sep 22 18:32:20 2016 +0000 @@ -31,13 +31,12 @@ */ import java.lang.reflect.Field; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class GetPutShort { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); Test t = new Test(); Field field = Test.class.getField("s"); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/GetUncompressedObject.java --- a/hotspot/test/runtime/Unsafe/GetUncompressedObject.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/GetUncompressedObject.java Thu Sep 22 18:32:20 2016 +0000 @@ -30,13 +30,12 @@ import static jdk.test.lib.Asserts.*; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; public class GetUncompressedObject { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); // Allocate some memory and fill it with non-zero values. final int size = 32; diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/NestedUnsafe.java --- a/hotspot/test/runtime/Unsafe/NestedUnsafe.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/NestedUnsafe.java Thu Sep 22 18:32:20 2016 +0000 @@ -35,7 +35,6 @@ import java.io.InputStream; import java.lang.*; import jdk.test.lib.InMemoryJavaCompiler; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; @@ -50,7 +49,7 @@ " } } "); public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); Class klass = unsafe.defineAnonymousClass(NestedUnsafe.class, klassbuf, new Object[0]); unsafe.ensureClassInitialized(klass); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/PageSize.java --- a/hotspot/test/runtime/Unsafe/PageSize.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/PageSize.java Thu Sep 22 18:32:20 2016 +0000 @@ -31,13 +31,12 @@ */ import java.lang.reflect.Field; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class PageSize { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); int pageSize = unsafe.pageSize(); for (int n = 1; n != 0; n <<= 1) { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/PrimitiveHostClass.java --- a/hotspot/test/runtime/Unsafe/PrimitiveHostClass.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/PrimitiveHostClass.java Thu Sep 22 18:32:20 2016 +0000 @@ -39,16 +39,7 @@ public class PrimitiveHostClass { - static final Unsafe U; - static { - try { - Field theUnsafe = Unsafe.class.getDeclaredField("theUnsafe"); - theUnsafe.setAccessible(true); - U = (Unsafe) theUnsafe.get(null); - } catch (Exception e) { - throw new AssertionError(e); - } - } + static final Unsafe U = Unsafe.getUnsafe(); public static void testVMAnonymousClass(Class hostClass) { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/RangeCheck.java --- a/hotspot/test/runtime/Unsafe/RangeCheck.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/RangeCheck.java Thu Sep 22 18:32:20 2016 +0000 @@ -33,7 +33,6 @@ import jdk.test.lib.process.ProcessTools; import jdk.test.lib.process.OutputAnalyzer; import jdk.test.lib.Platform; -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; @@ -60,7 +59,7 @@ public static class DummyClassWithMainRangeCheck { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); unsafe.getObject(new DummyClassWithMainRangeCheck(), Short.MAX_VALUE); } } diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/Reallocate.java --- a/hotspot/test/runtime/Unsafe/Reallocate.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/Reallocate.java Thu Sep 22 18:32:20 2016 +0000 @@ -31,13 +31,12 @@ * @run main/othervm -XX:+UnlockDiagnosticVMOptions -XX:MallocMaxTestWords=100m Reallocate */ -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class Reallocate { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); long address = unsafe.allocateMemory(1); assertNotEquals(address, 0L); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/SetMemory.java --- a/hotspot/test/runtime/Unsafe/SetMemory.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/SetMemory.java Thu Sep 22 18:32:20 2016 +0000 @@ -30,13 +30,12 @@ * @run main SetMemory */ -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class SetMemory { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); long address = unsafe.allocateMemory(1); assertNotEquals(address, 0L); unsafe.setMemory(address, 1, (byte)17); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/Unsafe/ThrowException.java --- a/hotspot/test/runtime/Unsafe/ThrowException.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/Unsafe/ThrowException.java Thu Sep 22 18:32:20 2016 +0000 @@ -30,13 +30,12 @@ * @run main ThrowException */ -import jdk.test.lib.unsafe.UnsafeHelper; import jdk.internal.misc.Unsafe; import static jdk.test.lib.Asserts.*; public class ThrowException { public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); try { unsafe.throwException(new TestException()); } catch (Throwable t) { diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/contended/Basic.java --- a/hotspot/test/runtime/contended/Basic.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/contended/Basic.java Thu Sep 22 18:32:20 2016 +0000 @@ -48,20 +48,11 @@ */ public class Basic { - private static final Unsafe U; + private static final Unsafe U = Unsafe.getUnsafe(); private static int ADDRESS_SIZE; private static int HEADER_SIZE; static { - // steal Unsafe - try { - Field unsafe = Unsafe.class.getDeclaredField("theUnsafe"); - unsafe.setAccessible(true); - U = (Unsafe) unsafe.get(null); - } catch (NoSuchFieldException | IllegalAccessException e) { - throw new IllegalStateException(e); - } - // When running with CompressedOops on 64-bit platform, the address size // reported by Unsafe is still 8, while the real reference fields are 4 bytes long. // Try to guess the reference field size with this naive trick. diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/contended/DefaultValue.java --- a/hotspot/test/runtime/contended/DefaultValue.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/contended/DefaultValue.java Thu Sep 22 18:32:20 2016 +0000 @@ -49,20 +49,11 @@ */ public class DefaultValue { - private static final Unsafe U; + private static final Unsafe U = Unsafe.getUnsafe(); private static int ADDRESS_SIZE; private static int HEADER_SIZE; static { - // steal Unsafe - try { - Field unsafe = Unsafe.class.getDeclaredField("theUnsafe"); - unsafe.setAccessible(true); - U = (Unsafe) unsafe.get(null); - } catch (NoSuchFieldException | IllegalAccessException e) { - throw new IllegalStateException(e); - } - // When running with CompressedOops on 64-bit platform, the address size // reported by Unsafe is still 8, while the real reference fields are 4 bytes long. // Try to guess the reference field size with this naive trick. diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/contended/Inheritance1.java --- a/hotspot/test/runtime/contended/Inheritance1.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/contended/Inheritance1.java Thu Sep 22 18:32:20 2016 +0000 @@ -49,20 +49,11 @@ */ public class Inheritance1 { - private static final Unsafe U; + private static final Unsafe U = Unsafe.getUnsafe(); private static int ADDRESS_SIZE; private static int HEADER_SIZE; static { - // steal Unsafe - try { - Field unsafe = Unsafe.class.getDeclaredField("theUnsafe"); - unsafe.setAccessible(true); - U = (Unsafe) unsafe.get(null); - } catch (NoSuchFieldException | IllegalAccessException e) { - throw new IllegalStateException(e); - } - // When running with CompressedOops on 64-bit platform, the address size // reported by Unsafe is still 8, while the real reference fields are 4 bytes long. // Try to guess the reference field size with this naive trick. diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/defineAnonClass/NestedUnsafe.java --- a/hotspot/test/runtime/defineAnonClass/NestedUnsafe.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/defineAnonClass/NestedUnsafe.java Thu Sep 22 18:32:20 2016 +0000 @@ -39,7 +39,6 @@ import java.lang.*; import jdk.test.lib.*; import jdk.internal.misc.Unsafe; -import jdk.test.lib.unsafe.UnsafeHelper; // Test that an anonymous class in package 'p' cannot define its own anonymous class @@ -54,7 +53,7 @@ " } } "); public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); // The anonymous class calls defineAnonymousClass creating a nested anonymous class. byte klassbuf2[] = InMemoryJavaCompiler.compile("p.TestClass2", diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/defineAnonClass/NestedUnsafe2.java --- a/hotspot/test/runtime/defineAnonClass/NestedUnsafe2.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/defineAnonClass/NestedUnsafe2.java Thu Sep 22 18:32:20 2016 +0000 @@ -39,7 +39,6 @@ import java.lang.*; import jdk.test.lib.*; import jdk.internal.misc.Unsafe; -import jdk.test.lib.unsafe.UnsafeHelper; // Test that an anonymous class that gets put in its host's package cannot define @@ -54,7 +53,7 @@ " } } "); public static void main(String args[]) throws Exception { - Unsafe unsafe = UnsafeHelper.getUnsafe(); + Unsafe unsafe = Unsafe.getUnsafe(); // The anonymous class calls defineAnonymousClass creating a nested anonymous class. byte klassbuf2[] = InMemoryJavaCompiler.compile("TestClass2", diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/jni/checked/TestCheckedJniExceptionCheck.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/hotspot/test/runtime/jni/checked/TestCheckedJniExceptionCheck.java Thu Sep 22 18:32:20 2016 +0000 @@ -0,0 +1,209 @@ +/* + * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ + +/* @test + * @bug 8164086 + * @summary regression tests for 8164086, verify correct warning from checked JNI + * @library /test/lib + * @modules java.management + * @run main/native TestCheckedJniExceptionCheck launch + */ + +import java.util.List; +import jdk.test.lib.process.ProcessTools; +import jdk.test.lib.process.OutputAnalyzer; + +public class TestCheckedJniExceptionCheck { + + static { + System.loadLibrary("TestCheckedJniExceptionCheck"); + } + + int callableMethodInvokeCount = 0; + + static final String TEST_START = "TEST STARTED"; + static final String EXPECT_WARNING_START = "EXPECT_WARNING_START"; + static final String EXPECT_WARNING_END = "EXPECT_WARNING_END"; + + static final String JNI_CHECK_EXCEPTION = "WARNING in native method: JNI call made without checking exceptions when required to from"; + + static void printExpectWarningStart(int count) { + System.out.println(EXPECT_WARNING_START + " " + count); + } + + static void printExpectWarningEnd() { + System.out.println(EXPECT_WARNING_END); + } + + public TestCheckedJniExceptionCheck() { + initMethodIds("callableMethod", "()V", + "callableNestedMethod", "(IZ)V"); + System.out.println(TEST_START); + } + + public void test() { + testSingleCallNoCheck(); + testSingleCallCheck(); + testSingleCallNoCheckMultipleTimes(); + + testMultipleCallsNoCheck(); + testMultipleCallsCheck(); + + testNestedSingleCallsNoCheck(); + testNestedSingleCallsCheck(); + testNestedMultipleCallsNoCheck(); + testNestedMultipleCallsCheck(); + } + + public void testSingleCallNoCheck() { + System.out.println("testSingleCallNoCheck start"); + callJavaFromNative(1, false); + System.out.println("testSingleCallNoCheck end"); + } + + public void testSingleCallCheck() { + System.out.println("testSingleCallCheck start"); + callJavaFromNative(1, true); + System.out.println("testSingleCallCheck end"); + } + + public void testSingleCallNoCheckMultipleTimes() { + System.out.println("testSingleCallNoCheckMultipleTimes start"); + callJavaFromNative(1, false); + callJavaFromNative(1, false); + System.out.println("testSingleCallNoCheckMultipleTimes end"); + } + + public void testMultipleCallsNoCheck() { + System.out.println("testMultipleCallsNoCheck start"); + printExpectWarningStart(1); + callJavaFromNative(2, false); + printExpectWarningEnd(); + System.out.println("testMultipleCallsNoCheck end"); + } + + public void testMultipleCallsCheck() { + System.out.println("testMultipleCallsCheck start"); + callJavaFromNative(2, true); + System.out.println("testMultipleCallsCheck end"); + } + + public void testNestedSingleCallsNoCheck() { + System.out.println("testNestedSingleCallsNoCheck start"); + callNestedJavaFromNative(1, false); + System.out.println("testNestedSingleCallsNoCheck end"); + } + + public void testNestedSingleCallsCheck() { + System.out.println("testNestedSingleCallsCheck start"); + callNestedJavaFromNative(1, true); + System.out.println("testNestedSingleCallsCheck end"); + } + + public void testNestedMultipleCallsNoCheck() { + System.out.println("testNestedMultipleCallsNoCheck start"); + printExpectWarningStart(3); + callNestedJavaFromNative(2, false); + printExpectWarningEnd(); + System.out.println("testNestedMultipleCallsNoCheck end"); + } + + public void testNestedMultipleCallsCheck() { + System.out.println("testNestedMultipleCallsCheck start"); + callNestedJavaFromNative(2, true); + System.out.println("testNestedMultipleCallsCheck end"); + } + + public void callableMethod() { + callableMethodInvokeCount++; + } + + public void callableNestedMethod(int nofCalls, boolean withExceptionChecks) { + callJavaFromNative(nofCalls, withExceptionChecks); + } + + public native void callJavaFromNative(int nofCalls, boolean withExceptionChecks); + + public native void callNestedJavaFromNative(int nofCalls, boolean withExceptionChecks); + + private native void initMethodIds(String callableMethodName, + String callableMethodSig, + String callableNestedMethodName, + String callableNestedMethodSig); + + + // Check warnings appear where they should, with start/end statements in output... + static void checkOuputForCorrectWarnings(OutputAnalyzer oa) throws RuntimeException { + List lines = oa.asLines(); + int expectedWarnings = 0; + int warningCount = 0; + int lineNo = 0; + boolean testStartLine = false; + for (String line : lines) { + lineNo++; + if (!testStartLine) { // Skip any warning before the actual test itself + testStartLine = line.startsWith(TEST_START); + continue; + } + if (line.startsWith(JNI_CHECK_EXCEPTION)) { + if (expectedWarnings == 0) { + oa.reportDiagnosticSummary(); + throw new RuntimeException("Unexpected warning at line " + lineNo); + } + warningCount++; + if (warningCount > expectedWarnings) { + oa.reportDiagnosticSummary(); + throw new RuntimeException("Unexpected warning at line " + lineNo); + } + } + else if (line.startsWith(EXPECT_WARNING_START)) { + String countStr = line.substring(EXPECT_WARNING_START.length() + 1); + expectedWarnings = Integer.parseInt(countStr); + } + else if (line.startsWith(EXPECT_WARNING_END)) { + if (warningCount != expectedWarnings) { + oa.reportDiagnosticSummary(); + throw new RuntimeException("Missing warning at line " + lineNo); + } + warningCount = 0; + expectedWarnings = 0; + } + } + /* + System.out.println("Output looks good..."); + oa.reportDiagnosticSummary(); + */ + } + + public static void main(String[] args) throws Throwable { + if (args == null || args.length == 0) { + new TestCheckedJniExceptionCheck().test(); + return; + } + + // launch and check output + checkOuputForCorrectWarnings(ProcessTools.executeTestJvm("-Xcheck:jni", + "TestCheckedJniExceptionCheck")); + } + +} diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/jni/checked/libTestCheckedJniExceptionCheck.c --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/hotspot/test/runtime/jni/checked/libTestCheckedJniExceptionCheck.c Thu Sep 22 18:32:20 2016 +0000 @@ -0,0 +1,98 @@ +/* + * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ + +#include + +static jmethodID _callable_method_id; +static jmethodID _callable_nested_method_id; + +static void check_exceptions(JNIEnv *env) { + if ((*env)->ExceptionCheck(env)) { + (*env)->ExceptionDescribe(env); + (*env)->FatalError(env, "Unexpected Exception"); + } +} + +static jmethodID get_method_id(JNIEnv *env, jclass clz, jstring jname, jstring jsig) { + jmethodID mid; + const char *name, *sig; + + name = (*env)->GetStringUTFChars(env, jname, NULL); + check_exceptions(env); + + sig = (*env)->GetStringUTFChars(env, jsig, NULL); + check_exceptions(env); + + mid = (*env)->GetMethodID(env, clz, name, sig); + check_exceptions(env); + + (*env)->ReleaseStringUTFChars(env, jname, name); + (*env)->ReleaseStringUTFChars(env, jsig, sig); + return mid; +} + +JNIEXPORT void JNICALL +Java_TestCheckedJniExceptionCheck_initMethodIds(JNIEnv *env, + jobject obj, + jstring callable_method_name, + jstring callable_method_sig, + jstring callable_nested_method_name, + jstring callable_nested_method_sig) { + jclass clz = (*env)->GetObjectClass(env, obj); + + _callable_method_id = get_method_id(env, clz, + callable_method_name, + callable_method_sig); + + _callable_nested_method_id = get_method_id(env, clz, + callable_nested_method_name, + callable_nested_method_sig); +} + +JNIEXPORT void JNICALL +Java_TestCheckedJniExceptionCheck_callJavaFromNative(JNIEnv *env, + jobject obj, + jint nofCalls, + jboolean checkExceptions) { + int i; + for (i = 0; i < nofCalls; i++) { + (*env)->CallVoidMethod(env, obj, _callable_method_id); + if (checkExceptions == JNI_TRUE) { + check_exceptions(env); + } + } +} + +JNIEXPORT void JNICALL +Java_TestCheckedJniExceptionCheck_callNestedJavaFromNative(JNIEnv *env, + jobject obj, + jint nofCalls, + jboolean checkExceptions) { + int i; + for (i = 0; i < nofCalls; i++) { + (*env)->CallVoidMethod(env, obj, _callable_nested_method_id, nofCalls, checkExceptions); + if (checkExceptions == JNI_TRUE) { + check_exceptions(env); + } + } +} diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/modules/ModuleOptionsTest.java --- a/hotspot/test/runtime/modules/ModuleOptionsTest.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/runtime/modules/ModuleOptionsTest.java Thu Sep 22 18:32:20 2016 +0000 @@ -24,8 +24,8 @@ /* * @test * @bug 8136930 - * @summary Test that the VM only recognizes the last specified --add-modules - * and --list-modules options + * @summary Test that the VM only recognizes the last specified --list-modules + * options but accumulates --add-module values. * @modules java.base/jdk.internal.misc * @library /test/lib */ @@ -38,14 +38,16 @@ public static void main(String[] args) throws Exception { - // Test that last --add-modules is the only one recognized. No exception - // should be thrown. + // Test that multiple --add-modules options are cumulative, not last one wins. + // An exception should be thrown because module i_dont_exist doesn't exist. ProcessBuilder pb = ProcessTools.createJavaProcessBuilder( "--add-modules=i_dont_exist", "--add-modules=java.base", "-version"); OutputAnalyzer output = new OutputAnalyzer(pb.start()); - output.shouldHaveExitValue(0); + output.shouldContain("ResolutionException"); + output.shouldContain("i_dont_exist"); + output.shouldHaveExitValue(1); - // Test that last --limit-modules is the only one recognized. No exception + // Test that the last --limit-modules is the only one recognized. No exception // should be thrown. pb = ProcessTools.createJavaProcessBuilder( "--limit-modules=i_dont_exist", "--limit-modules=java.base", "-version"); diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/verifier/popTopTests/PopDupTop.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/hotspot/test/runtime/verifier/popTopTests/PopDupTop.java Thu Sep 22 18:32:20 2016 +0000 @@ -0,0 +1,64 @@ +/* + * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + * + */ + +/* + * @test + * @bug 8149607 + * @summary Throw VerifyError when popping a stack element of TOP + * @compile popDupSwapTests.jasm + * @run main/othervm -Xverify:all PopDupTop + */ + +public class PopDupTop { + + public static void testClass(String class_name, String msg) throws Throwable { + try { + Class newClass = Class.forName(class_name); + throw new RuntimeException("Expected VerifyError exception not thrown for " + msg); + } catch (java.lang.VerifyError e) { + if (!e.getMessage().contains("Bad type on operand stack")) { + throw new RuntimeException( + "Unexpected VerifyError message for " + msg + ": " + e.getMessage()); + } + } + } + + public static void main(String args[]) throws Throwable { + System.out.println("Regression test for bug 8149607"); + + testClass("dup_x1", "dup_x1 of long,ref"); + testClass("dup2toptop", "dup2 of top,top"); + testClass("dup2longtop", "dup2 of long,top"); + testClass("dup2_x1", "dup2_x1 long,ref,ref"); + testClass("dup2_x2", "dup2_x2 top"); + testClass("dup2_x2_long_refs", "dup2_x2 long,ref,ref,ref"); + testClass("poptop", "pop of top"); + testClass("poptoptop", "pop of top,top"); + testClass("pop2toptop", "pop2 of top,top"); + testClass("pop2longtop", "pop2 of long,top"); + testClass("swaptoptop", "swap of top,top"); + testClass("swapinttop", "swap of int,top"); + testClass("swaptopint", "swap of top,int"); + } +} diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/runtime/verifier/popTopTests/popDupSwapTests.jasm --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/hotspot/test/runtime/verifier/popTopTests/popDupSwapTests.jasm Thu Sep 22 18:32:20 2016 +0000 @@ -0,0 +1,244 @@ +/* + * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + * + */ + +// Test that VerifyError is thrown if dup2_x1 tries to replace the filler slot +// of a category 2 value. +// The stack map is long,top,null,null. The verifier should reject dup2_x1's +// (form1) attempt to turn the stack map into long,top,null,null,null,null +public class dup2_x1 version 51:0 { + public static Method run:"()V" stack 6 locals 0 { + lconst_0; + aconst_null; + aconst_null; + dup2_x1; + return; + } +} + + +public class dup2_x2 version 51:0 { + public static Method run:"()V" stack 6 locals 0 { + iconst_0; + lconst_0; + aconst_null; + + stack_frame_type full; + stack_map int, bogus, bogus, null; + locals_map; + + dup2_x2; + return; + } +} + + +// Test that VerifyError is thrown if dup2_x2 tries to replace the filler slot +// of a category 2 value. +// The stack map is long,top,null,null,null. The verifier should reject dup2_x2's +// (form 1) attempt to turn the stack map into long,top,null,null,null,top,null. +public class dup2_x2_long_refs version 51:0 { + public static Method run:"()V" stack 6 locals 0 { + lconst_0; + aconst_null; + aconst_null; + aconst_null; + dup2_x2; + return; + } +} + + +// Test that VerifyError is thrown when dup2 is used to remove the upper +// half of a category 2 type. +public class dup2longtop version 51:0 { + public static Method main:"([Ljava/lang/String;)V" stack 5 locals 1 { + lconst_0; + iconst_0; + dup2; + return; + } +} + + +// Test that VerifyError is thrown when dup2 is used to remove top +// because top may be the upper half of a category 2 type. +public class dup2toptop version 51:0 { + public static Method main:"([Ljava/lang/String;)V" stack 5 locals 1 { + // here we have {long, top, null} + // EXECUTION: we have {long, null} + lconst_0; + aconst_null; + + stack_frame_type full; + stack_map bogus, bogus, null; + locals_map bogus; + + // VERIFIER: use form1 of dup2 - {top, top, null} -> {top, top, null, top, null} + // EXECUTION: have {long, null} - no applicable form of dup2 for such type state by JVMS ch. 6 + dup2; + + return; + } +} + + +// Test that VerifyError is thrown if dup_x1 tries to replace the filler slot +// of a category 2 value. +public class dup_x1 version 51:0 { + public static Method run:"()V" stack 6 locals 0 { + lconst_0; + aconst_null; + dup_x1; + return; + } +} + + +// Test that VerifyError is thrown when pop2 is used to remove top +// because top may be the upper half of a category 2 type. +public class pop2longtop version 51:0 +{ + + public Method regular:"()V" stack 6 locals 6 + { + lconst_0; + iconst_0; + stack_frame_type full; + stack_map long, bogus; + locals_map; + pop2; + return; + } +} // end Class pop2longtop + + + +// Test that VerifyError is thrown when pop2 is used to remove top, top +// because either top may be the upper half of a category 2 type. +public class pop2toptop version 51:0 +{ + + public Method regular:"()V" stack 6 locals 6 + { + iconst_0; + iconst_0; + stack_frame_type full; + stack_map bogus, bogus; + locals_map; + pop2; + return; + } +} // end Class pop2toptop + + + +// Test that VerifyError is thrown when pop is used to remove top +// because top may be the upper half of a category 2 type. +public class poptop version 51:0 +{ + + public Method regular:"()V" stack 2 locals 1 + { + iconst_0; + stack_frame_type full; + stack_map bogus; + pop; + return; + } +} // end Class poptop + + + +// Test that VerifyError is thrown when pop is used to remove top, top +// because either top may be the upper half of a category 2 type. +public class poptoptop version 51:0 +{ + + public Method regular:"()V" stack 2 locals 1 + { + iconst_0; + iconst_0; + stack_frame_type full; + stack_map bogus, bogus; + pop; + return; + } +} // end Class poptoptop + + + +// Test that VerifyError is thrown when swap is used to swap int, top +// because top may be the lower half of a category 2 type. +public class swapinttop version 51:0 +{ + + public Method regular:"()V" stack 6 locals 6 + { + iconst_0; + iconst_0; + stack_frame_type full; + stack_map int, bogus; + locals_map; + swap; + return; + } +} // end Class swapinttop + + + +// Test that VerifyError is thrown when swap is used to swap top, int +// because top may be the upper half of a category 2 type. +public class swaptopint version 51:0 +{ + + public Method regular:"()V" stack 6 locals 6 + { + iconst_0; + iconst_0; + stack_frame_type full; + stack_map bogus, int; + locals_map; + swap; + return; + } +} // end Class swaptopint + + + +// Test that VerifyError is thrown when swap is used to swap top, top +// because either top may be the upper half of a category 2 type. +public class swaptoptop version 51:0 +{ + + public Method regular:"()V" stack 6 locals 6 + { + iconst_0; + iconst_0; + stack_frame_type full; + stack_map bogus, bogus; + locals_map; + swap; + return; + } +} // end Class swaptoptop diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/testlibrary/ctw/Makefile --- a/hotspot/test/testlibrary/ctw/Makefile Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/testlibrary/ctw/Makefile Thu Sep 22 18:32:20 2016 +0000 @@ -40,7 +40,7 @@ JAVAC = $(JDK_HOME)/bin/javac JAR = $(JDK_HOME)/bin/jar -SRC_FILES = $(shell find $(SRC_DIR) $(TESTLIBRARY_DIR)/share/classes -name '*.java') +SRC_FILES = $(shell find $(SRC_DIR) $(TESTLIBRARY_DIR)/jdk/test/lib -name '*.java') WB_SRC_FILES = $(shell find $(TESTLIBRARY_DIR)/sun/hotspot -name '*.java') MAIN_CLASS = sun.hotspot.tools.ctw.CompileTheWorld diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/testlibrary/ctw/src/sun/hotspot/tools/ctw/PathHandler.java --- a/hotspot/test/testlibrary/ctw/src/sun/hotspot/tools/ctw/PathHandler.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/testlibrary/ctw/src/sun/hotspot/tools/ctw/PathHandler.java Thu Sep 22 18:32:20 2016 +0000 @@ -39,7 +39,7 @@ * Concrete subclasses should implement method {@link #process()}. */ public abstract class PathHandler { - private static final Unsafe UNSAFE = jdk.test.lib.unsafe.UnsafeHelper.getUnsafe(); + private static final Unsafe UNSAFE = Unsafe.getUnsafe(); private static final AtomicLong CLASS_COUNT = new AtomicLong(0L); private static volatile boolean CLASSES_LIMIT_REACHED = false; private static final Pattern JAR_IN_DIR_PATTERN diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/testlibrary/jittester/Makefile --- a/hotspot/test/testlibrary/jittester/Makefile Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/testlibrary/jittester/Makefile Thu Sep 22 18:32:20 2016 +0000 @@ -56,7 +56,6 @@ CLASSES_DIR = $(BUILD_DIR)/classes SRC_DIR = src TEST_DIR = test -DRIVER_DIR = $(TESTBASE_DIR)/jdk/test/lib/jittester/jtreg MANIFEST = manifest.mf APPLICATION_ARGS += \ --property-file $(PROPERTY_FILE) \ @@ -118,19 +117,18 @@ @rm filelist @rm -rf $(CLASSES_DIR) -copytestlibrary: $(DRIVER_DIR) - @cp -r src/jdk/test/lib/jittester/jtreg/*.java $(DRIVER_DIR) +copytestlibrary: $(TESTBASE_DIR)/jdk/test/lib/jittester/jtreg + @cp -r src/jdk/test/lib/jittester/jtreg/*.java $(TESTBASE_DIR)/jdk/test/lib/jittester/jtreg + @cp -r $(TESTLIBRARY_SRC_DIR) $(TESTBASE_DIR)/jdk/test/ testgroup: $(TESTBASE_DIR) @echo 'jittester_all = \\' > $(TESTGROUP_FILE) @echo ' /' >> $(TESTGROUP_FILE) @echo '' >> $(TESTGROUP_FILE) - @echo 'main = \\' >> $(TESTGROUP_FILE) - @echo ' Test_0.java' >> $(TESTGROUP_FILE) testroot: $(TESTBASE_DIR) @echo 'groups=TEST.groups' > $(TESTROOT_FILE) -$(TESTBASE_DIR) $(DIST_DIR) $(DRIVER_DIR): +$(TESTBASE_DIR) $(DIST_DIR) $(TESTBASE_DIR)/jdk/test/lib/jittester/jtreg: $(shell if [ ! -d $@ ]; then mkdir -p $@; fi) diff -r 4f1591515aef -r b4b4c1119f39 hotspot/test/testlibrary_tests/TestMutuallyExclusivePlatformPredicates.java --- a/hotspot/test/testlibrary_tests/TestMutuallyExclusivePlatformPredicates.java Thu Sep 22 16:41:12 2016 +0000 +++ b/hotspot/test/testlibrary_tests/TestMutuallyExclusivePlatformPredicates.java Thu Sep 22 18:32:20 2016 +0000 @@ -50,8 +50,9 @@ OS("isAix", "isLinux", "isOSX", "isSolaris", "isWindows"), VM_TYPE("isClient", "isServer", "isGraal", "isMinimal", "isZero", "isEmbedded"), MODE("isInt", "isMixed", "isComp"), - IGNORED("isDebugBuild", "shouldSAAttach", - "canPtraceAttachLinux", "canAttachOSX", "isTieredSupported"); + IGNORED("isDebugBuild", "isFastDebugBuild", "isSlowDebugBuild", + "shouldSAAttach", "canPtraceAttachLinux", "canAttachOSX", + "isTieredSupported"); public final List methodNames;