11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12 * version 2 for more details (a copy is included in the LICENSE file that 13 * accompanied this code). 14 * 15 * You should have received a copy of the GNU General Public License version 16 * 2 along with this work; if not, write to the Free Software Foundation, 17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 18 * 19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 20 * or visit www.oracle.com if you need additional information or have any 21 * questions. 22 * 23 */ 24 25 #include "precompiled.hpp" 26 #include "classfile/vmSymbols.hpp" 27 #include "utilities/macros.hpp" 28 #if INCLUDE_ALL_GCS 29 #include "gc_implementation/g1/g1SATBCardTableModRefBS.hpp" 30 #endif // INCLUDE_ALL_GCS 31 #include "jfr/jfrEvents.hpp" 32 #include "memory/allocation.inline.hpp" 33 #include "prims/jni.h" 34 #include "prims/jvm.h" 35 #include "runtime/globals.hpp" 36 #include "runtime/interfaceSupport.hpp" 37 #include "runtime/prefetch.inline.hpp" 38 #include "runtime/orderAccess.inline.hpp" 39 #include "runtime/reflection.hpp" 40 #include "runtime/synchronizer.hpp" 41 #include "services/threadService.hpp" 42 #include "utilities/copy.hpp" 43 #include "utilities/dtrace.hpp" 44 45 PRAGMA_FORMAT_MUTE_WARNINGS_FOR_GCC 46 47 /* 48 * Implementation of class sun.misc.Unsafe 49 */ 50 51 #ifndef USDT2 1219 1220 UNSAFE_ENTRY(jboolean, Unsafe_CompareAndSwapLong(JNIEnv *env, jobject unsafe, jobject obj, jlong offset, jlong e, jlong x)) 1221 UnsafeWrapper("Unsafe_CompareAndSwapLong"); 1222 Handle p (THREAD, JNIHandles::resolve(obj)); 1223 jlong* addr = (jlong*)(index_oop_from_field_offset_long(p(), offset)); 1224 #ifdef SUPPORTS_NATIVE_CX8 1225 return (jlong)(Atomic::cmpxchg(x, addr, e)) == e; 1226 #else 1227 if (VM_Version::supports_cx8()) 1228 return (jlong)(Atomic::cmpxchg(x, addr, e)) == e; 1229 else { 1230 jboolean success = false; 1231 MutexLockerEx mu(UnsafeJlong_lock, Mutex::_no_safepoint_check_flag); 1232 jlong val = Atomic::load(addr); 1233 if (val == e) { Atomic::store(x, addr); success = true; } 1234 return success; 1235 } 1236 #endif 1237 UNSAFE_END 1238 1239 static void post_thread_park_event(EventThreadPark* event, const oop obj, jlong timeout_nanos, jlong until_epoch_millis) { 1240 assert(event != NULL, "invariant"); 1241 assert(event->should_commit(), "invariant"); 1242 event->set_parkedClass((obj != NULL) ? obj->klass() : NULL); 1243 event->set_timeout(timeout_nanos); 1244 event->set_until(until_epoch_millis); 1245 event->set_address((obj != NULL) ? (u8)cast_from_oop<uintptr_t>(obj) : 0); 1246 event->commit(); 1247 } 1248 1249 UNSAFE_ENTRY(void, Unsafe_Park(JNIEnv *env, jobject unsafe, jboolean isAbsolute, jlong time)) 1250 UnsafeWrapper("Unsafe_Park"); 1251 EventThreadPark event; 1252 #ifndef USDT2 1253 HS_DTRACE_PROBE3(hotspot, thread__park__begin, thread->parker(), (int) isAbsolute, time); 1254 #else /* USDT2 */ 1255 HOTSPOT_THREAD_PARK_BEGIN( 1256 (uintptr_t) thread->parker(), (int) isAbsolute, time); 1257 #endif /* USDT2 */ 1258 JavaThreadParkedState jtps(thread, time != 0); 1259 thread->parker()->park(isAbsolute != 0, time); 1260 #ifndef USDT2 1261 HS_DTRACE_PROBE1(hotspot, thread__park__end, thread->parker()); 1262 #else /* USDT2 */ 1263 HOTSPOT_THREAD_PARK_END( 1264 (uintptr_t) thread->parker()); 1265 #endif /* USDT2 */ 1266 if (event.should_commit()) { 1267 const oop obj = thread->current_park_blocker(); 1268 if (time == 0) { 1269 post_thread_park_event(&event, obj, min_jlong, min_jlong); 1270 } else { 1271 if (isAbsolute != 0) { 1272 post_thread_park_event(&event, obj, min_jlong, time); 1273 } else { 1274 post_thread_park_event(&event, obj, time, min_jlong); 1275 } 1276 } 1277 } 1278 UNSAFE_END 1279 1280 UNSAFE_ENTRY(void, Unsafe_Unpark(JNIEnv *env, jobject unsafe, jobject jthread)) 1281 UnsafeWrapper("Unsafe_Unpark"); 1282 Parker* p = NULL; 1283 if (jthread != NULL) { 1284 oop java_thread = JNIHandles::resolve_non_null(jthread); 1285 if (java_thread != NULL) { 1286 jlong lp = java_lang_Thread::park_event(java_thread); 1287 if (lp != 0) { 1288 // This cast is OK even though the jlong might have been read 1289 // non-atomically on 32bit systems, since there, one word will 1290 // always be zero anyway and the value set is always the same 1291 p = (Parker*)addr_from_java(lp); 1292 } else { 1293 // Grab lock if apparently null or using older version of library 1294 MutexLocker mu(Threads_lock); 1295 java_thread = JNIHandles::resolve_non_null(jthread); 1296 if (java_thread != NULL) { 1297 JavaThread* thr = java_lang_Thread::thread(java_thread); | 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12 * version 2 for more details (a copy is included in the LICENSE file that 13 * accompanied this code). 14 * 15 * You should have received a copy of the GNU General Public License version 16 * 2 along with this work; if not, write to the Free Software Foundation, 17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 18 * 19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 20 * or visit www.oracle.com if you need additional information or have any 21 * questions. 22 * 23 */ 24 25 #include "precompiled.hpp" 26 #include "classfile/vmSymbols.hpp" 27 #include "utilities/macros.hpp" 28 #if INCLUDE_ALL_GCS 29 #include "gc_implementation/g1/g1SATBCardTableModRefBS.hpp" 30 #endif // INCLUDE_ALL_GCS 31 #if INCLUDE_JFR 32 #include "jfr/jfrEvents.hpp" 33 #endif 34 #include "memory/allocation.inline.hpp" 35 #include "prims/jni.h" 36 #include "prims/jvm.h" 37 #include "runtime/globals.hpp" 38 #include "runtime/interfaceSupport.hpp" 39 #include "runtime/prefetch.inline.hpp" 40 #include "runtime/orderAccess.inline.hpp" 41 #include "runtime/reflection.hpp" 42 #include "runtime/synchronizer.hpp" 43 #include "services/threadService.hpp" 44 #include "utilities/copy.hpp" 45 #include "utilities/dtrace.hpp" 46 47 PRAGMA_FORMAT_MUTE_WARNINGS_FOR_GCC 48 49 /* 50 * Implementation of class sun.misc.Unsafe 51 */ 52 53 #ifndef USDT2 1221 1222 UNSAFE_ENTRY(jboolean, Unsafe_CompareAndSwapLong(JNIEnv *env, jobject unsafe, jobject obj, jlong offset, jlong e, jlong x)) 1223 UnsafeWrapper("Unsafe_CompareAndSwapLong"); 1224 Handle p (THREAD, JNIHandles::resolve(obj)); 1225 jlong* addr = (jlong*)(index_oop_from_field_offset_long(p(), offset)); 1226 #ifdef SUPPORTS_NATIVE_CX8 1227 return (jlong)(Atomic::cmpxchg(x, addr, e)) == e; 1228 #else 1229 if (VM_Version::supports_cx8()) 1230 return (jlong)(Atomic::cmpxchg(x, addr, e)) == e; 1231 else { 1232 jboolean success = false; 1233 MutexLockerEx mu(UnsafeJlong_lock, Mutex::_no_safepoint_check_flag); 1234 jlong val = Atomic::load(addr); 1235 if (val == e) { Atomic::store(x, addr); success = true; } 1236 return success; 1237 } 1238 #endif 1239 UNSAFE_END 1240 1241 #if INCLUDE_JFR 1242 static void post_thread_park_event(EventThreadPark* event, const oop obj, jlong timeout_nanos, jlong until_epoch_millis) { 1243 assert(event != NULL, "invariant"); 1244 assert(event->should_commit(), "invariant"); 1245 event->set_parkedClass((obj != NULL) ? obj->klass() : NULL); 1246 event->set_timeout(timeout_nanos); 1247 event->set_until(until_epoch_millis); 1248 event->set_address((obj != NULL) ? (u8)cast_from_oop<uintptr_t>(obj) : 0); 1249 event->commit(); 1250 } 1251 #endif 1252 1253 UNSAFE_ENTRY(void, Unsafe_Park(JNIEnv *env, jobject unsafe, jboolean isAbsolute, jlong time)) 1254 UnsafeWrapper("Unsafe_Park"); 1255 #if INCLUDE_JFR 1256 EventThreadPark event; 1257 #endif 1258 #ifndef USDT2 1259 HS_DTRACE_PROBE3(hotspot, thread__park__begin, thread->parker(), (int) isAbsolute, time); 1260 #else /* USDT2 */ 1261 HOTSPOT_THREAD_PARK_BEGIN( 1262 (uintptr_t) thread->parker(), (int) isAbsolute, time); 1263 #endif /* USDT2 */ 1264 JavaThreadParkedState jtps(thread, time != 0); 1265 thread->parker()->park(isAbsolute != 0, time); 1266 #ifndef USDT2 1267 HS_DTRACE_PROBE1(hotspot, thread__park__end, thread->parker()); 1268 #else /* USDT2 */ 1269 HOTSPOT_THREAD_PARK_END( 1270 (uintptr_t) thread->parker()); 1271 #endif /* USDT2 */ 1272 #if INCLUDE_JFR 1273 if (event.should_commit()) { 1274 const oop obj = thread->current_park_blocker(); 1275 if (time == 0) { 1276 post_thread_park_event(&event, obj, min_jlong, min_jlong); 1277 } else { 1278 if (isAbsolute != 0) { 1279 post_thread_park_event(&event, obj, min_jlong, time); 1280 } else { 1281 post_thread_park_event(&event, obj, time, min_jlong); 1282 } 1283 } 1284 } 1285 #endif 1286 UNSAFE_END 1287 1288 UNSAFE_ENTRY(void, Unsafe_Unpark(JNIEnv *env, jobject unsafe, jobject jthread)) 1289 UnsafeWrapper("Unsafe_Unpark"); 1290 Parker* p = NULL; 1291 if (jthread != NULL) { 1292 oop java_thread = JNIHandles::resolve_non_null(jthread); 1293 if (java_thread != NULL) { 1294 jlong lp = java_lang_Thread::park_event(java_thread); 1295 if (lp != 0) { 1296 // This cast is OK even though the jlong might have been read 1297 // non-atomically on 32bit systems, since there, one word will 1298 // always be zero anyway and the value set is always the same 1299 p = (Parker*)addr_from_java(lp); 1300 } else { 1301 // Grab lock if apparently null or using older version of library 1302 MutexLocker mu(Threads_lock); 1303 java_thread = JNIHandles::resolve_non_null(jthread); 1304 if (java_thread != NULL) { 1305 JavaThread* thr = java_lang_Thread::thread(java_thread); |