--- old/src/share/vm/prims/unsafe.cpp 2015-10-14 13:54:32.790440393 +0200 +++ new/src/share/vm/prims/unsafe.cpp 2015-10-14 13:54:32.700442570 +0200 @@ -121,6 +121,7 @@ if (p != NULL) { assert(byte_offset >= 0 && byte_offset <= (jlong)MAX_OBJECT_SIZE, "sane offset"); if (byte_offset == (jint)byte_offset) { + p = oopDesc::bs()->write_barrier(p); void* ptr_plus_disp = (address)p + byte_offset; assert((void*)p->obj_field_addr((jint)byte_offset) == ptr_plus_disp, "raw [ptr+disp] must be consistent with oop::field_base"); @@ -155,14 +156,17 @@ #define GET_FIELD(obj, offset, type_name, v) \ oop p = JNIHandles::resolve(obj); \ + p = oopDesc::bs()->read_barrier(p); \ type_name v = *(type_name*)index_oop_from_field_offset_long(p, offset) #define SET_FIELD(obj, offset, type_name, x) \ oop p = JNIHandles::resolve(obj); \ + p = oopDesc::bs()->write_barrier(p); \ *(type_name*)index_oop_from_field_offset_long(p, offset) = x #define GET_FIELD_VOLATILE(obj, offset, type_name, v) \ oop p = JNIHandles::resolve(obj); \ + p = oopDesc::bs()->read_barrier(p); \ if (support_IRIW_for_not_multiple_copy_atomic_cpu) { \ OrderAccess::fence(); \ } \ @@ -170,6 +174,7 @@ #define SET_FIELD_VOLATILE(obj, offset, type_name, x) \ oop p = JNIHandles::resolve(obj); \ + p = oopDesc::bs()->write_barrier(p); \ OrderAccess::release_store_fence((volatile type_name*)index_oop_from_field_offset_long(p, offset), x); @@ -181,6 +186,7 @@ UNSAFE_ENTRY(jobject, Unsafe_GetObject(JNIEnv *env, jobject unsafe, jobject obj, jlong offset)) UnsafeWrapper("Unsafe_GetObject"); oop p = JNIHandles::resolve(obj); + p = oopDesc::bs()->read_barrier(p); oop v; if (UseCompressedOops) { narrowOop n = *(narrowOop*)index_oop_from_field_offset_long(p, offset); @@ -193,7 +199,7 @@ // We could be accessing the referent field in a reference // object. If G1 is enabled then we need to register non-null // referent with the SATB barrier. - if (UseG1GC) { + if (UseG1GC || UseShenandoahGC) { bool needs_barrier = false; if (ret != NULL) { @@ -218,8 +224,8 @@ UNSAFE_ENTRY(void, Unsafe_SetObject(JNIEnv *env, jobject unsafe, jobject obj, jlong offset, jobject x_h)) UnsafeWrapper("Unsafe_SetObject"); - oop x = JNIHandles::resolve(x_h); - oop p = JNIHandles::resolve(obj); + oop x = oopDesc::bs()->read_barrier(JNIHandles::resolve(x_h)); + oop p = oopDesc::bs()->write_barrier(JNIHandles::resolve(obj)); if (UseCompressedOops) { oop_store((narrowOop*)index_oop_from_field_offset_long(p, offset), x); } else { @@ -230,6 +236,7 @@ UNSAFE_ENTRY(jobject, Unsafe_GetObjectVolatile(JNIEnv *env, jobject unsafe, jobject obj, jlong offset)) UnsafeWrapper("Unsafe_GetObjectVolatile"); oop p = JNIHandles::resolve(obj); + p = oopDesc::bs()->read_barrier(p); void* addr = index_oop_from_field_offset_long(p, offset); volatile oop v; if (UseCompressedOops) { @@ -246,6 +253,8 @@ UnsafeWrapper("Unsafe_SetObjectVolatile"); oop x = JNIHandles::resolve(x_h); oop p = JNIHandles::resolve(obj); + x = oopDesc::bs()->read_barrier(x); + p = oopDesc::bs()->write_barrier(p); void* addr = index_oop_from_field_offset_long(p, offset); OrderAccess::release(); if (UseCompressedOops) { @@ -312,7 +321,7 @@ return v; } else { - Handle p (THREAD, JNIHandles::resolve(obj)); + Handle p (THREAD, oopDesc::bs()->read_barrier(JNIHandles::resolve(obj))); jlong* addr = (jlong*)(index_oop_from_field_offset_long(p(), offset)); MutexLockerEx mu(UnsafeJlong_lock, Mutex::_no_safepoint_check_flag); jlong value = Atomic::load(addr); @@ -328,7 +337,7 @@ SET_FIELD_VOLATILE(obj, offset, jlong, x); } else { - Handle p (THREAD, JNIHandles::resolve(obj)); + Handle p (THREAD, oopDesc::bs()->write_barrier(JNIHandles::resolve(obj))); jlong* addr = (jlong*)(index_oop_from_field_offset_long(p(), offset)); MutexLockerEx mu(UnsafeJlong_lock, Mutex::_no_safepoint_check_flag); Atomic::store(x, addr); @@ -435,6 +444,8 @@ UnsafeWrapper("Unsafe_SetOrderedObject"); oop x = JNIHandles::resolve(x_h); oop p = JNIHandles::resolve(obj); + x = oopDesc::bs()->read_barrier(x); + p = oopDesc::bs()->write_barrier(p); void* addr = index_oop_from_field_offset_long(p, offset); OrderAccess::release(); if (UseCompressedOops) { @@ -456,7 +467,7 @@ SET_FIELD_VOLATILE(obj, offset, jlong, x); } else { - Handle p (THREAD, JNIHandles::resolve(obj)); + Handle p (THREAD, oopDesc::bs()->write_barrier(JNIHandles::resolve(obj))); jlong* addr = (jlong*)(index_oop_from_field_offset_long(p(), offset)); MutexLockerEx mu(UnsafeJlong_lock, Mutex::_no_safepoint_check_flag); Atomic::store(x, addr); @@ -635,6 +646,7 @@ THROW(vmSymbols::java_lang_IllegalArgumentException()); } oop base = JNIHandles::resolve(obj); + base = oopDesc::bs()->write_barrier(base); void* p = index_oop_from_field_offset_long(base, offset); Copy::fill_to_memory_atomic(p, sz, value); UNSAFE_END @@ -650,6 +662,8 @@ } oop srcp = JNIHandles::resolve(srcObj); oop dstp = JNIHandles::resolve(dstObj); + srcp = oopDesc::bs()->read_barrier(srcp); + dstp = oopDesc::bs()->write_barrier(dstp); if (dstp != NULL && !dstp->is_typeArray()) { // NYI: This works only for non-oop arrays at present. // Generalizing it would be reasonable, but requires card marking. @@ -1082,12 +1096,23 @@ UNSAFE_ENTRY(jboolean, Unsafe_CompareAndSwapObject(JNIEnv *env, jobject unsafe, jobject obj, jlong offset, jobject e_h, jobject x_h)) UnsafeWrapper("Unsafe_CompareAndSwapObject"); - oop x = JNIHandles::resolve(x_h); - oop e = JNIHandles::resolve(e_h); - oop p = JNIHandles::resolve(obj); + // We are about to write to this entry so check to see if we need to copy it. + oop p = oopDesc::bs()->write_barrier(JNIHandles::resolve(obj)); HeapWord* addr = (HeapWord *)index_oop_from_field_offset_long(p, offset); - oop res = oopDesc::atomic_compare_exchange_oop(x, addr, e, true); - jboolean success = (res == e); + oop x = JNIHandles::resolve(x_h); + x = oopDesc::bs()->read_barrier(x); + oop old = JNIHandles::resolve(e_h); + jboolean success; + if (UseShenandoahGC) { + oop expected; + do { + expected = old; + old = oopDesc::atomic_compare_exchange_oop(x, addr, expected, true); + success = (old == expected); + } while ((! success) && oopDesc::bs()->read_barrier(old) == oopDesc::bs()->read_barrier(expected)); + } else { + success = (old == oopDesc::atomic_compare_exchange_oop(x, addr, old, true)); + } if (success) update_barrier_set((void*)addr, x); return success; @@ -1095,14 +1120,15 @@ UNSAFE_ENTRY(jboolean, Unsafe_CompareAndSwapInt(JNIEnv *env, jobject unsafe, jobject obj, jlong offset, jint e, jint x)) UnsafeWrapper("Unsafe_CompareAndSwapInt"); - oop p = JNIHandles::resolve(obj); + // We are about to write to this entry so check to see if we need to copy it. + oop p = oopDesc::bs()->write_barrier(JNIHandles::resolve(obj)); jint* addr = (jint *) index_oop_from_field_offset_long(p, offset); return (jint)(Atomic::cmpxchg(x, addr, e)) == e; UNSAFE_END UNSAFE_ENTRY(jboolean, Unsafe_CompareAndSwapLong(JNIEnv *env, jobject unsafe, jobject obj, jlong offset, jlong e, jlong x)) UnsafeWrapper("Unsafe_CompareAndSwapLong"); - Handle p (THREAD, JNIHandles::resolve(obj)); + Handle p (THREAD, oopDesc::bs()->write_barrier(JNIHandles::resolve(obj))); jlong* addr = (jlong*)(index_oop_from_field_offset_long(p(), offset)); #ifdef SUPPORTS_NATIVE_CX8 return (jlong)(Atomic::cmpxchg(x, addr, e)) == e;