src/share/vm/gc_implementation/g1/concurrentMark.hpp
Print this page
rev 3708 : 8000244: G1: Ergonomically set MarkStackSize and use virtual space for global marking stack
Summary: Set the value of MarkStackSize to a value based on the number of parallel marking threads with a reasonable minimum. Expand the marking stack if we have to restart marking due to an overflow up to a reasonable maximum. Allocate the underlying space for the marking stack from virtual memory.
Reviewed-by: jmasa
rev 3709 : imported patch reuse-old-marking-stack
*** 61,71 ****
VirtualSpace _virtual_space; // underlying the bit map
BitMap _bm; // the bit map itself
public:
// constructor
! CMBitMapRO(ReservedSpace rs, int shifter);
enum { do_yield = true };
// inquiries
HeapWord* startWord() const { return _bmStartWord; }
--- 61,71 ----
VirtualSpace _virtual_space; // underlying the bit map
BitMap _bm; // the bit map itself
public:
// constructor
! CMBitMapRO(int shifter);
enum { do_yield = true };
// inquiries
HeapWord* startWord() const { return _bmStartWord; }
*** 115,126 ****
class CMBitMap : public CMBitMapRO {
public:
// constructor
! CMBitMap(ReservedSpace rs, int shifter) :
! CMBitMapRO(rs, shifter) {}
// write marks
void mark(HeapWord* addr) {
assert(_bmStartWord <= addr && addr < (_bmStartWord + _bmWordSize),
"outside underlying space?");
--- 115,129 ----
class CMBitMap : public CMBitMapRO {
public:
// constructor
! CMBitMap(int shifter) :
! CMBitMapRO(shifter) {}
!
! // Allocates the back store for the marking bitmap
! bool allocate(ReservedSpace heap_rs);
// write marks
void mark(HeapWord* addr) {
assert(_bmStartWord <= addr && addr < (_bmStartWord + _bmWordSize),
"outside underlying space?");
*** 153,181 ****
// the run. If there is no "1" bit at or after "addr", return an empty
// MemRegion.
MemRegion getAndClearMarkedRegion(HeapWord* addr, HeapWord* end_addr);
};
! // Represents a marking stack used by the CM collector.
! // Ideally this should be GrowableArray<> just like MSC's marking stack(s).
class CMMarkStack VALUE_OBJ_CLASS_SPEC {
ConcurrentMark* _cm;
oop* _base; // bottom of stack
jint _index; // one more than last occupied index
jint _capacity; // max #elements
jint _saved_index; // value of _index saved at start of GC
NOT_PRODUCT(jint _max_depth;) // max depth plumbed during run
bool _overflow;
DEBUG_ONLY(bool _drain_in_progress;)
DEBUG_ONLY(bool _drain_in_progress_yields;)
public:
CMMarkStack(ConcurrentMark* cm);
~CMMarkStack();
! void allocate(size_t size);
oop pop() {
if (!isEmpty()) {
return _base[--_index] ;
}
--- 156,192 ----
// the run. If there is no "1" bit at or after "addr", return an empty
// MemRegion.
MemRegion getAndClearMarkedRegion(HeapWord* addr, HeapWord* end_addr);
};
! // Represents a marking stack used by ConcurrentMarking in the G1 collector.
class CMMarkStack VALUE_OBJ_CLASS_SPEC {
+ ReservedSpace _rs;
+ VirtualSpace _virtual_space; // Underlying backing store for actual stack
ConcurrentMark* _cm;
oop* _base; // bottom of stack
jint _index; // one more than last occupied index
jint _capacity; // max #elements
jint _saved_index; // value of _index saved at start of GC
NOT_PRODUCT(jint _max_depth;) // max depth plumbed during run
bool _overflow;
+ bool _should_expand;
DEBUG_ONLY(bool _drain_in_progress;)
DEBUG_ONLY(bool _drain_in_progress_yields;)
public:
CMMarkStack(ConcurrentMark* cm);
~CMMarkStack();
! #ifndef PRODUCT
! jint max_depth() const {
! return _max_depth;
! }
! #endif
!
! bool allocate(size_t capacity);
oop pop() {
if (!isEmpty()) {
return _base[--_index] ;
}
*** 234,243 ****
--- 245,260 ----
int maxElems() { return _capacity; }
bool overflow() { return _overflow; }
void clear_overflow() { _overflow = false; }
+ bool should_expand() const { return _should_expand; }
+ void set_should_expand();
+
+ // Expand the stack, typically in response to an overflow condition
+ void expand();
+
int size() { return _index; }
void setEmpty() { _index = 0; clear_overflow(); }
// Record the current index.
*** 342,351 ****
--- 359,369 ----
};
class ConcurrentMarkThread;
class ConcurrentMark: public CHeapObj<mtGC> {
+ friend class CMMarkStack;
friend class ConcurrentMarkThread;
friend class CMTask;
friend class CMBitMapClosure;
friend class CMGlobalObjectClosure;
friend class CMRemarkTask;
*** 575,584 ****
--- 593,605 ----
// Card index of the bottom of the G1 heap. Used for biasing indices into
// the card bitmaps.
intptr_t _heap_bottom_card_num;
+ // Set to true when initialization is complete
+ bool _completed_initialization;
+
public:
// Manipulation of the global mark stack.
// Notice that the first mark_stack_push is CAS-based, whereas the
// two below are Mutex-based. This is OK since the first one is only
// called during evacuation pauses and doesn't compete with the
*** 634,644 ****
// Attempts to steal an object from the task queues of other tasks
bool try_stealing(uint worker_id, int* hash_seed, oop& obj) {
return _task_queues->steal(worker_id, hash_seed, obj);
}
! ConcurrentMark(ReservedSpace rs, uint max_regions);
~ConcurrentMark();
ConcurrentMarkThread* cmThread() { return _cmThread; }
CMBitMapRO* prevMarkBitMap() const { return _prevMarkBitMap; }
--- 655,665 ----
// Attempts to steal an object from the task queues of other tasks
bool try_stealing(uint worker_id, int* hash_seed, oop& obj) {
return _task_queues->steal(worker_id, hash_seed, obj);
}
! ConcurrentMark(G1CollectedHeap* g1h, ReservedSpace heap_rs);
~ConcurrentMark();
ConcurrentMarkThread* cmThread() { return _cmThread; }
CMBitMapRO* prevMarkBitMap() const { return _prevMarkBitMap; }
*** 905,914 ****
--- 926,940 ----
// Similar to the above routine but we don't know the heap region that
// contains the object to be marked/counted, which this routine looks up.
// Should *not* be called from parallel code.
inline bool mark_and_count(oop obj);
+ // Returns true if initialization was successfully completed.
+ bool completed_initialization() const {
+ return _completed_initialization;
+ }
+
protected:
// Clear all the per-task bitmaps and arrays used to store the
// counting data.
void clear_all_count_data();