src/share/vm/gc_implementation/g1/heapRegion.inline.hpp

Print this page
rev 6592 : [mq]: 8047818.reviews

*** 29,70 **** #include "gc_implementation/g1/g1CollectedHeap.hpp" #include "gc_implementation/g1/heapRegion.hpp" #include "memory/space.hpp" #include "runtime/atomic.inline.hpp" ! inline HeapWord* G1OffsetTableContigSpace::cas_allocate_inner(size_t size) { HeapWord* obj = top(); ! do { ! if (pointer_delta(end(), obj) >= size) { HeapWord* new_top = obj + size; ! HeapWord* result = (HeapWord*)Atomic::cmpxchg_ptr(new_top, &_top, obj); ! if (result == obj) { assert(is_aligned(obj) && is_aligned(new_top), "checking alignment"); return obj; - } - obj = result; } else { - break; - } - } while (true); return NULL; } ! inline HeapWord* G1OffsetTableContigSpace::allocate_inner(size_t size) { HeapWord* obj = top(); ! if (pointer_delta(end(), obj) >= size) { HeapWord* new_top = obj + size; assert(is_aligned(obj) && is_aligned(new_top), "checking alignment"); - set_top(new_top); return obj; } return NULL; } - inline HeapWord* G1OffsetTableContigSpace::allocate(size_t size) { ! HeapWord* res = allocate_inner(size); if (res != NULL) { _offsets.alloc_block(res, size); } return res; } --- 29,75 ---- #include "gc_implementation/g1/g1CollectedHeap.hpp" #include "gc_implementation/g1/heapRegion.hpp" #include "memory/space.hpp" #include "runtime/atomic.inline.hpp" ! // This version requires locking. ! inline HeapWord* G1OffsetTableContigSpace::allocate_impl(size_t size, ! HeapWord* const end_value) { HeapWord* obj = top(); ! if (pointer_delta(end_value, obj) >= size) { HeapWord* new_top = obj + size; ! set_top(new_top); assert(is_aligned(obj) && is_aligned(new_top), "checking alignment"); return obj; } else { return NULL; + } } ! // This version is lock-free. ! inline HeapWord* G1OffsetTableContigSpace::par_allocate_impl(size_t size, ! HeapWord* const end_value) { ! do { HeapWord* obj = top(); ! if (pointer_delta(end_value, obj) >= size) { HeapWord* new_top = obj + size; + HeapWord* result = (HeapWord*)Atomic::cmpxchg_ptr(new_top, top_addr(), obj); + // result can be one of two: + // the old top value: the exchange succeeded + // otherwise: the new value of the top is returned. + if (result == obj) { assert(is_aligned(obj) && is_aligned(new_top), "checking alignment"); return obj; } + } else { return NULL; + } + } while (true); } inline HeapWord* G1OffsetTableContigSpace::allocate(size_t size) { ! HeapWord* res = allocate_impl(size, end()); if (res != NULL) { _offsets.alloc_block(res, size); } return res; }
*** 102,117 **** } } inline HeapWord* HeapRegion::par_allocate_no_bot_updates(size_t word_size) { assert(is_young(), "we can only skip BOT updates on young regions"); ! return cas_allocate_inner(word_size); } inline HeapWord* HeapRegion::allocate_no_bot_updates(size_t word_size) { assert(is_young(), "we can only skip BOT updates on young regions"); ! return allocate_inner(word_size); } inline void HeapRegion::note_start_of_marking() { _next_marked_bytes = 0; _next_top_at_mark_start = top(); --- 107,122 ---- } } inline HeapWord* HeapRegion::par_allocate_no_bot_updates(size_t word_size) { assert(is_young(), "we can only skip BOT updates on young regions"); ! return par_allocate_impl(word_size, end()); } inline HeapWord* HeapRegion::allocate_no_bot_updates(size_t word_size) { assert(is_young(), "we can only skip BOT updates on young regions"); ! return allocate_impl(word_size, end()); } inline void HeapRegion::note_start_of_marking() { _next_marked_bytes = 0; _next_top_at_mark_start = top();