src/share/vm/prims/jvm.cpp

changeset 9563
2fa643465866
parent 9550
270570f695e0
parent 9562
dee6a1ce4a0c
child 9572
624a0741915c
child 9611
63ce4041b7ec
     1.1 --- a/src/share/vm/prims/jvm.cpp	Fri Nov 30 12:05:39 2018 +0000
     1.2 +++ b/src/share/vm/prims/jvm.cpp	Wed Dec 05 11:22:21 2018 +0000
     1.3 @@ -759,6 +759,79 @@
     1.4  JVM_END
     1.5  
     1.6  
     1.7 +// java.nio.Bits ///////////////////////////////////////////////////////////////
     1.8 +
     1.9 +#define MAX_OBJECT_SIZE \
    1.10 +  ( arrayOopDesc::header_size(T_DOUBLE) * HeapWordSize \
    1.11 +    + ((julong)max_jint * sizeof(double)) )
    1.12 +
    1.13 +static inline jlong field_offset_to_byte_offset(jlong field_offset) {
    1.14 +  return field_offset;
    1.15 +}
    1.16 +
    1.17 +static inline void assert_field_offset_sane(oop p, jlong field_offset) {
    1.18 +#ifdef ASSERT
    1.19 +  jlong byte_offset = field_offset_to_byte_offset(field_offset);
    1.20 +
    1.21 +  if (p != NULL) {
    1.22 +    assert(byte_offset >= 0 && byte_offset <= (jlong)MAX_OBJECT_SIZE, "sane offset");
    1.23 +    if (byte_offset == (jint)byte_offset) {
    1.24 +      void* ptr_plus_disp = (address)p + byte_offset;
    1.25 +      assert((void*)p->obj_field_addr<oop>((jint)byte_offset) == ptr_plus_disp,
    1.26 +             "raw [ptr+disp] must be consistent with oop::field_base");
    1.27 +    }
    1.28 +    jlong p_size = HeapWordSize * (jlong)(p->size());
    1.29 +    assert(byte_offset < p_size, err_msg("Unsafe access: offset " INT64_FORMAT
    1.30 +                                         " > object's size " INT64_FORMAT,
    1.31 +                                         (int64_t)byte_offset, (int64_t)p_size));
    1.32 +  }
    1.33 +#endif
    1.34 +}
    1.35 +
    1.36 +static inline void* index_oop_from_field_offset_long(oop p, jlong field_offset) {
    1.37 +  assert_field_offset_sane(p, field_offset);
    1.38 +  jlong byte_offset = field_offset_to_byte_offset(field_offset);
    1.39 +
    1.40 +  if (sizeof(char*) == sizeof(jint)) {   // (this constant folds!)
    1.41 +    return (address)p + (jint) byte_offset;
    1.42 +  } else {
    1.43 +    return (address)p +        byte_offset;
    1.44 +  }
    1.45 +}
    1.46 +
    1.47 +// This function is a leaf since if the source and destination are both in native memory
    1.48 +// the copy may potentially be very large, and we don't want to disable GC if we can avoid it.
    1.49 +// If either source or destination (or both) are on the heap, the function will enter VM using
    1.50 +// JVM_ENTRY_FROM_LEAF
    1.51 +JVM_LEAF(void, JVM_CopySwapMemory(JNIEnv *env, jobject srcObj, jlong srcOffset,
    1.52 +                                  jobject dstObj, jlong dstOffset, jlong size,
    1.53 +                                  jlong elemSize)) {
    1.54 +
    1.55 +  size_t sz = (size_t)size;
    1.56 +  size_t esz = (size_t)elemSize;
    1.57 +
    1.58 +  if (srcObj == NULL && dstObj == NULL) {
    1.59 +    // Both src & dst are in native memory
    1.60 +    address src = (address)srcOffset;
    1.61 +    address dst = (address)dstOffset;
    1.62 +
    1.63 +    Copy::conjoint_swap(src, dst, sz, esz);
    1.64 +  } else {
    1.65 +    // At least one of src/dst are on heap, transition to VM to access raw pointers
    1.66 +
    1.67 +    JVM_ENTRY_FROM_LEAF(env, void, JVM_CopySwapMemory) {
    1.68 +      oop srcp = JNIHandles::resolve(srcObj);
    1.69 +      oop dstp = JNIHandles::resolve(dstObj);
    1.70 +
    1.71 +      address src = (address)index_oop_from_field_offset_long(srcp, srcOffset);
    1.72 +      address dst = (address)index_oop_from_field_offset_long(dstp, dstOffset);
    1.73 +
    1.74 +      Copy::conjoint_swap(src, dst, sz, esz);
    1.75 +    } JVM_END
    1.76 +  }
    1.77 +} JVM_END
    1.78 +
    1.79 +
    1.80  // Misc. class handling ///////////////////////////////////////////////////////////
    1.81  
    1.82  

mercurial