comparison src/share/vm/c1/c1_Runtime1.cpp @ 113:ba764ed4b6f2

6420645: Create a vm that uses compressed oops for up to 32gb heapsizes Summary: Compressed oops in instances, arrays, and headers. Code contributors are coleenp, phh, never, swamyv Reviewed-by: jmasa, kamg, acorn, tbell, kvn, rasbold
author coleenp
date Sun, 13 Apr 2008 17:43:42 -0400
parents a61af66fc99e
children d1605aabd0a1 37f87013dfd8
comparison
equal deleted inserted replaced
110:a49a647afe9a 113:ba764ed4b6f2
1072 // for now we just print out the block id 1072 // for now we just print out the block id
1073 tty->print("%d ", block_id); 1073 tty->print("%d ", block_id);
1074 JRT_END 1074 JRT_END
1075 1075
1076 1076
1077 // Array copy return codes.
1078 enum {
1079 ac_failed = -1, // arraycopy failed
1080 ac_ok = 0 // arraycopy succeeded
1081 };
1082
1083
1084 template <class T> int obj_arraycopy_work(oopDesc* src, T* src_addr,
1085 oopDesc* dst, T* dst_addr,
1086 int length) {
1087
1088 // For performance reasons, we assume we are using a card marking write
1089 // barrier. The assert will fail if this is not the case.
1090 // Note that we use the non-virtual inlineable variant of write_ref_array.
1091 BarrierSet* bs = Universe::heap()->barrier_set();
1092 assert(bs->has_write_ref_array_opt(),
1093 "Barrier set must have ref array opt");
1094 if (src == dst) {
1095 // same object, no check
1096 Copy::conjoint_oops_atomic(src_addr, dst_addr, length);
1097 bs->write_ref_array(MemRegion((HeapWord*)dst_addr,
1098 (HeapWord*)(dst_addr + length)));
1099 return ac_ok;
1100 } else {
1101 klassOop bound = objArrayKlass::cast(dst->klass())->element_klass();
1102 klassOop stype = objArrayKlass::cast(src->klass())->element_klass();
1103 if (stype == bound || Klass::cast(stype)->is_subtype_of(bound)) {
1104 // Elements are guaranteed to be subtypes, so no check necessary
1105 Copy::conjoint_oops_atomic(src_addr, dst_addr, length);
1106 bs->write_ref_array(MemRegion((HeapWord*)dst_addr,
1107 (HeapWord*)(dst_addr + length)));
1108 return ac_ok;
1109 }
1110 }
1111 return ac_failed;
1112 }
1113
1077 // fast and direct copy of arrays; returning -1, means that an exception may be thrown 1114 // fast and direct copy of arrays; returning -1, means that an exception may be thrown
1078 // and we did not copy anything 1115 // and we did not copy anything
1079 JRT_LEAF(int, Runtime1::arraycopy(oopDesc* src, int src_pos, oopDesc* dst, int dst_pos, int length)) 1116 JRT_LEAF(int, Runtime1::arraycopy(oopDesc* src, int src_pos, oopDesc* dst, int dst_pos, int length))
1080 #ifndef PRODUCT 1117 #ifndef PRODUCT
1081 _generic_arraycopy_cnt++; // Slow-path oop array copy 1118 _generic_arraycopy_cnt++; // Slow-path oop array copy
1082 #endif 1119 #endif
1083
1084 enum {
1085 ac_failed = -1, // arraycopy failed
1086 ac_ok = 0 // arraycopy succeeded
1087 };
1088 1120
1089 if (src == NULL || dst == NULL || src_pos < 0 || dst_pos < 0 || length < 0) return ac_failed; 1121 if (src == NULL || dst == NULL || src_pos < 0 || dst_pos < 0 || length < 0) return ac_failed;
1090 if (!dst->is_array() || !src->is_array()) return ac_failed; 1122 if (!dst->is_array() || !src->is_array()) return ac_failed;
1091 if ((unsigned int) arrayOop(src)->length() < (unsigned int)src_pos + (unsigned int)length) return ac_failed; 1123 if ((unsigned int) arrayOop(src)->length() < (unsigned int)src_pos + (unsigned int)length) return ac_failed;
1092 if ((unsigned int) arrayOop(dst)->length() < (unsigned int)dst_pos + (unsigned int)length) return ac_failed; 1124 if ((unsigned int) arrayOop(dst)->length() < (unsigned int)dst_pos + (unsigned int)length) return ac_failed;
1103 // Potential problem: memmove is not guaranteed to be word atomic 1135 // Potential problem: memmove is not guaranteed to be word atomic
1104 // Revisit in Merlin 1136 // Revisit in Merlin
1105 memmove(dst_addr, src_addr, length << l2es); 1137 memmove(dst_addr, src_addr, length << l2es);
1106 return ac_ok; 1138 return ac_ok;
1107 } else if (src->is_objArray() && dst->is_objArray()) { 1139 } else if (src->is_objArray() && dst->is_objArray()) {
1108 oop* src_addr = objArrayOop(src)->obj_at_addr(src_pos); 1140 if (UseCompressedOops) { // will need for tiered
1109 oop* dst_addr = objArrayOop(dst)->obj_at_addr(dst_pos); 1141 narrowOop *src_addr = objArrayOop(src)->obj_at_addr<narrowOop>(src_pos);
1110 // For performance reasons, we assume we are using a card marking write 1142 narrowOop *dst_addr = objArrayOop(dst)->obj_at_addr<narrowOop>(dst_pos);
1111 // barrier. The assert will fail if this is not the case. 1143 return obj_arraycopy_work(src, src_addr, dst, dst_addr, length);
1112 // Note that we use the non-virtual inlineable variant of write_ref_array.
1113 BarrierSet* bs = Universe::heap()->barrier_set();
1114 assert(bs->has_write_ref_array_opt(),
1115 "Barrier set must have ref array opt");
1116 if (src == dst) {
1117 // same object, no check
1118 Copy::conjoint_oops_atomic(src_addr, dst_addr, length);
1119 bs->write_ref_array(MemRegion((HeapWord*)dst_addr,
1120 (HeapWord*)(dst_addr + length)));
1121 return ac_ok;
1122 } else { 1144 } else {
1123 klassOop bound = objArrayKlass::cast(dst->klass())->element_klass(); 1145 oop *src_addr = objArrayOop(src)->obj_at_addr<oop>(src_pos);
1124 klassOop stype = objArrayKlass::cast(src->klass())->element_klass(); 1146 oop *dst_addr = objArrayOop(dst)->obj_at_addr<oop>(dst_pos);
1125 if (stype == bound || Klass::cast(stype)->is_subtype_of(bound)) { 1147 return obj_arraycopy_work(src, src_addr, dst, dst_addr, length);
1126 // Elements are guaranteed to be subtypes, so no check necessary
1127 Copy::conjoint_oops_atomic(src_addr, dst_addr, length);
1128 bs->write_ref_array(MemRegion((HeapWord*)dst_addr,
1129 (HeapWord*)(dst_addr + length)));
1130 return ac_ok;
1131 }
1132 } 1148 }
1133 } 1149 }
1134 return ac_failed; 1150 return ac_failed;
1135 JRT_END 1151 JRT_END
1136 1152