< prev index next >

src/hotspot/share/gc/shared/c2/barrierSetC2.cpp

Print this page

692 }
693 
694 Node* BarrierSetC2::atomic_xchg_at(C2AtomicParseAccess& access, Node* new_val, const Type* value_type) const {
695   C2AccessFence fence(access);
696   resolve_address(access);
697   return atomic_xchg_at_resolved(access, new_val, value_type);
698 }
699 
700 Node* BarrierSetC2::atomic_add_at(C2AtomicParseAccess& access, Node* new_val, const Type* value_type) const {
701   C2AccessFence fence(access);
702   resolve_address(access);
703   return atomic_add_at_resolved(access, new_val, value_type);
704 }
705 
706 int BarrierSetC2::arraycopy_payload_base_offset(bool is_array) {
707   // Exclude the header but include array length to copy by 8 bytes words.
708   // Can't use base_offset_in_bytes(bt) since basic type is unknown.
709   int base_off = is_array ? arrayOopDesc::length_offset_in_bytes() :
710                             instanceOopDesc::base_offset_in_bytes();
711   // base_off:
712   // 8  - 32-bit VM or 64-bit VM, compact headers

713   // 12 - 64-bit VM, compressed klass
714   // 16 - 64-bit VM, normal klass
715   if (base_off % BytesPerLong != 0) {
716     assert(UseCompressedClassPointers, "");
717     assert(!UseCompactObjectHeaders, "");
718     if (is_array) {
719       // Exclude length to copy by 8 bytes words.
720       base_off += sizeof(int);
721     } else {
722       // Include klass to copy by 8 bytes words.
723       base_off = instanceOopDesc::klass_offset_in_bytes();




724     }
725     assert(base_off % BytesPerLong == 0, "expect 8 bytes alignment");
726   }
727   return base_off;
728 }
729 
730 void BarrierSetC2::clone(GraphKit* kit, Node* src_base, Node* dst_base, Node* size, bool is_array) const {
731   int base_off = arraycopy_payload_base_offset(is_array);
732   Node* payload_size = size;
733   Node* offset = kit->MakeConX(base_off);
734   payload_size = kit->gvn().transform(new SubXNode(payload_size, offset));
735   if (is_array) {
736     // Ensure the array payload size is rounded up to the next BytesPerLong
737     // multiple when converting to double-words. This is necessary because array
738     // size does not include object alignment padding, so it might not be a
739     // multiple of BytesPerLong for sub-long element types.
740     payload_size = kit->gvn().transform(new AddXNode(payload_size, kit->MakeConX(BytesPerLong - 1)));
741   }
742   payload_size = kit->gvn().transform(new URShiftXNode(payload_size, kit->intcon(LogBytesPerLong)));
743   ArrayCopyNode* ac = ArrayCopyNode::make(kit, false, src_base, offset, dst_base, offset, payload_size, true, false);
744   if (is_array) {
745     ac->set_clone_array();

692 }
693 
694 Node* BarrierSetC2::atomic_xchg_at(C2AtomicParseAccess& access, Node* new_val, const Type* value_type) const {
695   C2AccessFence fence(access);
696   resolve_address(access);
697   return atomic_xchg_at_resolved(access, new_val, value_type);
698 }
699 
700 Node* BarrierSetC2::atomic_add_at(C2AtomicParseAccess& access, Node* new_val, const Type* value_type) const {
701   C2AccessFence fence(access);
702   resolve_address(access);
703   return atomic_add_at_resolved(access, new_val, value_type);
704 }
705 
706 int BarrierSetC2::arraycopy_payload_base_offset(bool is_array) {
707   // Exclude the header but include array length to copy by 8 bytes words.
708   // Can't use base_offset_in_bytes(bt) since basic type is unknown.
709   int base_off = is_array ? arrayOopDesc::length_offset_in_bytes() :
710                             instanceOopDesc::base_offset_in_bytes();
711   // base_off:
712   // 4  - compact headers
713   // 8  - 32-bit VM
714   // 12 - 64-bit VM, compressed klass
715   // 16 - 64-bit VM, normal klass
716   if (base_off % BytesPerLong != 0) {
717     assert(UseCompressedClassPointers, "");

718     if (is_array) {
719       // Exclude length to copy by 8 bytes words.
720       base_off += sizeof(int);
721     } else {
722       if (UseCompactObjectHeaders) {
723         base_off = 0; /* FIXME */
724       } else {
725         // Include klass to copy by 8 bytes words.
726         base_off = instanceOopDesc::klass_offset_in_bytes();
727       }
728     }
729     assert(base_off % BytesPerLong == 0 || UseCompactObjectHeaders, "expect 8 bytes alignment");
730   }
731   return base_off;
732 }
733 
734 void BarrierSetC2::clone(GraphKit* kit, Node* src_base, Node* dst_base, Node* size, bool is_array) const {
735   int base_off = arraycopy_payload_base_offset(is_array);
736   Node* payload_size = size;
737   Node* offset = kit->MakeConX(base_off);
738   payload_size = kit->gvn().transform(new SubXNode(payload_size, offset));
739   if (is_array) {
740     // Ensure the array payload size is rounded up to the next BytesPerLong
741     // multiple when converting to double-words. This is necessary because array
742     // size does not include object alignment padding, so it might not be a
743     // multiple of BytesPerLong for sub-long element types.
744     payload_size = kit->gvn().transform(new AddXNode(payload_size, kit->MakeConX(BytesPerLong - 1)));
745   }
746   payload_size = kit->gvn().transform(new URShiftXNode(payload_size, kit->intcon(LogBytesPerLong)));
747   ArrayCopyNode* ac = ArrayCopyNode::make(kit, false, src_base, offset, dst_base, offset, payload_size, true, false);
748   if (is_array) {
749     ac->set_clone_array();
< prev index next >