< prev index next >

src/share/vm/prims/unsafe.cpp

Print this page
rev 14282 : Factor out keep-alive barrier from usual pre-barrier implementations.


  28 #include "memory/allocation.inline.hpp"
  29 #include "memory/resourceArea.hpp"
  30 #include "oops/fieldStreams.hpp"
  31 #include "oops/objArrayOop.inline.hpp"
  32 #include "oops/oop.inline.hpp"
  33 #include "prims/jni.h"
  34 #include "prims/jvm.h"
  35 #include "prims/unsafe.hpp"
  36 #include "runtime/atomic.hpp"
  37 #include "runtime/globals.hpp"
  38 #include "runtime/interfaceSupport.hpp"
  39 #include "runtime/orderAccess.inline.hpp"
  40 #include "runtime/reflection.hpp"
  41 #include "runtime/vm_version.hpp"
  42 #include "services/threadService.hpp"
  43 #include "trace/tracing.hpp"
  44 #include "utilities/align.hpp"
  45 #include "utilities/copy.hpp"
  46 #include "utilities/dtrace.hpp"
  47 #include "utilities/macros.hpp"
  48 #if INCLUDE_ALL_GCS
  49 #include "gc/g1/g1SATBCardTableModRefBS.hpp"
  50 #endif // INCLUDE_ALL_GCS
  51 
  52 /**
  53  * Implementation of the jdk.internal.misc.Unsafe class
  54  */
  55 
  56 
  57 #define MAX_OBJECT_SIZE \
  58   ( arrayOopDesc::header_size(T_DOUBLE) * HeapWordSize \
  59     + ((julong)max_jint * sizeof(double)) )
  60 
  61 
  62 #define UNSAFE_ENTRY(result_type, header) \
  63   JVM_ENTRY(static result_type, header)
  64 
  65 #define UNSAFE_LEAF(result_type, header) \
  66   JVM_LEAF(static result_type, header)
  67 
  68 #define UNSAFE_END JVM_END
  69 
  70 


 280 
 281 // We could be accessing the referent field in a reference
 282 // object. If G1 is enabled then we need to register non-null
 283 // referent with the SATB barrier.
 284 
 285 #if INCLUDE_ALL_GCS
 286 static bool is_java_lang_ref_Reference_access(oop o, jlong offset) {
 287   if (offset == java_lang_ref_Reference::referent_offset && o != NULL) {
 288     Klass* k = o->klass();
 289     if (InstanceKlass::cast(k)->reference_type() != REF_NONE) {
 290       assert(InstanceKlass::cast(k)->is_subclass_of(SystemDictionary::Reference_klass()), "sanity");
 291       return true;
 292     }
 293   }
 294   return false;
 295 }
 296 #endif
 297 
 298 static void ensure_satb_referent_alive(oop o, jlong offset, oop v) {
 299 #if INCLUDE_ALL_GCS
 300   if ((UseG1GC || (UseShenandoahGC && ShenandoahSATBBarrier)) && v != NULL && is_java_lang_ref_Reference_access(o, offset)) {
 301     G1SATBCardTableModRefBS::enqueue(v);
 302   }
 303 #endif
 304 }
 305 
 306 // These functions allow a null base pointer with an arbitrary address.
 307 // But if the base pointer is non-null, the offset should make some sense.
 308 // That is, it should be in the range [0, MAX_OBJECT_SIZE].
 309 UNSAFE_ENTRY(jobject, Unsafe_GetObject(JNIEnv *env, jobject unsafe, jobject obj, jlong offset)) {
 310   oop p = JNIHandles::resolve(obj);
 311   p = oopDesc::bs()->read_barrier(p);
 312   oop v;
 313 
 314   if (UseCompressedOops) {
 315     narrowOop n = *(narrowOop*)index_oop_from_field_offset_long(p, offset);
 316     v = oopDesc::decode_heap_oop(n);
 317   } else {
 318     v = *(oop*)index_oop_from_field_offset_long(p, offset);
 319   }
 320 
 321   ensure_satb_referent_alive(p, offset, v);




  28 #include "memory/allocation.inline.hpp"
  29 #include "memory/resourceArea.hpp"
  30 #include "oops/fieldStreams.hpp"
  31 #include "oops/objArrayOop.inline.hpp"
  32 #include "oops/oop.inline.hpp"
  33 #include "prims/jni.h"
  34 #include "prims/jvm.h"
  35 #include "prims/unsafe.hpp"
  36 #include "runtime/atomic.hpp"
  37 #include "runtime/globals.hpp"
  38 #include "runtime/interfaceSupport.hpp"
  39 #include "runtime/orderAccess.inline.hpp"
  40 #include "runtime/reflection.hpp"
  41 #include "runtime/vm_version.hpp"
  42 #include "services/threadService.hpp"
  43 #include "trace/tracing.hpp"
  44 #include "utilities/align.hpp"
  45 #include "utilities/copy.hpp"
  46 #include "utilities/dtrace.hpp"
  47 #include "utilities/macros.hpp"



  48 
  49 /**
  50  * Implementation of the jdk.internal.misc.Unsafe class
  51  */
  52 
  53 
  54 #define MAX_OBJECT_SIZE \
  55   ( arrayOopDesc::header_size(T_DOUBLE) * HeapWordSize \
  56     + ((julong)max_jint * sizeof(double)) )
  57 
  58 
  59 #define UNSAFE_ENTRY(result_type, header) \
  60   JVM_ENTRY(static result_type, header)
  61 
  62 #define UNSAFE_LEAF(result_type, header) \
  63   JVM_LEAF(static result_type, header)
  64 
  65 #define UNSAFE_END JVM_END
  66 
  67 


 277 
 278 // We could be accessing the referent field in a reference
 279 // object. If G1 is enabled then we need to register non-null
 280 // referent with the SATB barrier.
 281 
 282 #if INCLUDE_ALL_GCS
 283 static bool is_java_lang_ref_Reference_access(oop o, jlong offset) {
 284   if (offset == java_lang_ref_Reference::referent_offset && o != NULL) {
 285     Klass* k = o->klass();
 286     if (InstanceKlass::cast(k)->reference_type() != REF_NONE) {
 287       assert(InstanceKlass::cast(k)->is_subclass_of(SystemDictionary::Reference_klass()), "sanity");
 288       return true;
 289     }
 290   }
 291   return false;
 292 }
 293 #endif
 294 
 295 static void ensure_satb_referent_alive(oop o, jlong offset, oop v) {
 296 #if INCLUDE_ALL_GCS
 297   if (v != NULL && is_java_lang_ref_Reference_access(o, offset)) {
 298     oopDesc::bs()->keep_alive_barrier(v);
 299   }
 300 #endif
 301 }
 302 
 303 // These functions allow a null base pointer with an arbitrary address.
 304 // But if the base pointer is non-null, the offset should make some sense.
 305 // That is, it should be in the range [0, MAX_OBJECT_SIZE].
 306 UNSAFE_ENTRY(jobject, Unsafe_GetObject(JNIEnv *env, jobject unsafe, jobject obj, jlong offset)) {
 307   oop p = JNIHandles::resolve(obj);
 308   p = oopDesc::bs()->read_barrier(p);
 309   oop v;
 310 
 311   if (UseCompressedOops) {
 312     narrowOop n = *(narrowOop*)index_oop_from_field_offset_long(p, offset);
 313     v = oopDesc::decode_heap_oop(n);
 314   } else {
 315     v = *(oop*)index_oop_from_field_offset_long(p, offset);
 316   }
 317 
 318   ensure_satb_referent_alive(p, offset, v);


< prev index next >