--- a/hotspot/src/cpu/ppc/vm/templateTable_ppc_64.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/cpu/ppc/vm/templateTable_ppc_64.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -143,7 +143,6 @@
}
break;
case BarrierSet::ModRef:
- case BarrierSet::Other:
ShouldNotReachHere();
break;
default:
--- a/hotspot/src/cpu/sparc/vm/templateTable_sparc.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/cpu/sparc/vm/templateTable_sparc.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -115,7 +115,6 @@
}
break;
case BarrierSet::ModRef:
- case BarrierSet::Other:
ShouldNotReachHere();
break;
default :
--- a/hotspot/src/cpu/x86/vm/templateTable_x86_32.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/cpu/x86/vm/templateTable_x86_32.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -185,7 +185,6 @@
}
break;
case BarrierSet::ModRef:
- case BarrierSet::Other:
if (val == noreg) {
__ movptr(obj, NULL_WORD);
} else {
--- a/hotspot/src/cpu/x86/vm/templateTable_x86_64.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/cpu/x86/vm/templateTable_x86_64.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -189,7 +189,6 @@
}
break;
case BarrierSet::ModRef:
- case BarrierSet::Other:
if (val == noreg) {
__ store_heap_oop_null(obj);
} else {
--- a/hotspot/src/share/vm/c1/c1_LIRGenerator.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/c1/c1_LIRGenerator.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -1432,7 +1432,6 @@
// No pre barriers
break;
case BarrierSet::ModRef:
- case BarrierSet::Other:
// No pre barriers
break;
default :
@@ -1454,7 +1453,6 @@
CardTableModRef_post_barrier(addr, new_val);
break;
case BarrierSet::ModRef:
- case BarrierSet::Other:
// No post barriers
break;
default :
--- a/hotspot/src/share/vm/gc_implementation/g1/g1CollectedHeap.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1CollectedHeap.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -3525,9 +3525,14 @@
size_t card_index;
while (hrrs.has_next(card_index)) {
jbyte* card_ptr = (jbyte*)bs->byte_for_index(card_index);
- if (*card_ptr != CardTableModRefBS::dirty_card_val()) {
- *card_ptr = CardTableModRefBS::dirty_card_val();
- _dcq.enqueue(card_ptr);
+ // The remembered set might contain references to already freed
+ // regions. Filter out such entries to avoid failing card table
+ // verification.
+ if (!g1h->heap_region_containing(bs->addr_for(card_ptr))->is_free()) {
+ if (*card_ptr != CardTableModRefBS::dirty_card_val()) {
+ *card_ptr = CardTableModRefBS::dirty_card_val();
+ _dcq.enqueue(card_ptr);
+ }
}
}
r->rem_set()->clear_locked();
--- a/hotspot/src/share/vm/gc_implementation/g1/g1CollectorPolicy.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1CollectorPolicy.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -139,6 +139,8 @@
_survivor_cset_region_length(0),
_old_cset_region_length(0),
+ _sigma(G1ConfidencePercent / 100.0),
+
_collection_set(NULL),
_collection_set_bytes_used_before(0),
@@ -161,17 +163,8 @@
_gc_overhead_perc(0.0) {
- uintx confidence_perc = G1ConfidencePercent;
- // Put an artificial ceiling on this so that it's not set to a silly value.
- if (confidence_perc > 100) {
- confidence_perc = 100;
- warning("G1ConfidencePercent is set to a value that is too large, "
- "it's been updated to %u", confidence_perc);
- }
- // '_sigma' must be initialized before the SurvRateGroups below because they
- // indirecty access '_sigma' trough the 'this' pointer in their constructor.
- _sigma = (double) confidence_perc / 100.0;
-
+ // SurvRateGroups below must be initialized after '_sigma' because they
+ // indirectly access '_sigma' through this object passed to their constructor.
_short_lived_surv_rate_group =
new SurvRateGroup(this, "Short Lived", G1YoungSurvRateNumRegionsSummary);
_survivor_surv_rate_group =
--- a/hotspot/src/share/vm/gc_implementation/g1/g1HotCardCache.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1HotCardCache.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -36,11 +36,10 @@
if (default_use_cache()) {
_use_cache = true;
- _hot_cache_size = (1 << G1ConcRSLogCacheSize);
+ _hot_cache_size = (size_t)1 << G1ConcRSLogCacheSize;
_hot_cache = NEW_C_HEAP_ARRAY(jbyte*, _hot_cache_size, mtGC);
- _n_hot = 0;
- _hot_cache_idx = 0;
+ reset_hot_cache_internal();
// For refining the cards in the hot cache in parallel
_hot_cache_par_chunk_size = ClaimChunkSize;
@@ -64,26 +63,21 @@
// return it for immediate refining.
return card_ptr;
}
-
// Otherwise, the card is hot.
- jbyte* res = NULL;
- MutexLockerEx x(HotCardCache_lock, Mutex::_no_safepoint_check_flag);
- if (_n_hot == _hot_cache_size) {
- res = _hot_cache[_hot_cache_idx];
- _n_hot--;
- }
+ size_t index = Atomic::add(1, &_hot_cache_idx) - 1;
+ size_t masked_index = index & (_hot_cache_size - 1);
+ jbyte* current_ptr = _hot_cache[masked_index];
- // Now _n_hot < _hot_cache_size, and we can insert at _hot_cache_idx.
- _hot_cache[_hot_cache_idx] = card_ptr;
- _hot_cache_idx++;
-
- if (_hot_cache_idx == _hot_cache_size) {
- // Wrap around
- _hot_cache_idx = 0;
- }
- _n_hot++;
-
- return res;
+ // Try to store the new card pointer into the cache. Compare-and-swap to guard
+ // against the unlikely event of a race resulting in another card pointer to
+ // have already been written to the cache. In this case we will return
+ // card_ptr in favor of the other option, which would be starting over. This
+ // should be OK since card_ptr will likely be the older card already when/if
+ // this ever happens.
+ jbyte* previous_ptr = (jbyte*)Atomic::cmpxchg_ptr(card_ptr,
+ &_hot_cache[masked_index],
+ current_ptr);
+ return (previous_ptr == current_ptr) ? previous_ptr : card_ptr;
}
void G1HotCardCache::drain(uint worker_i,
@@ -96,38 +90,38 @@
assert(_hot_cache != NULL, "Logic");
assert(!use_cache(), "cache should be disabled");
- int start_idx;
-
- while ((start_idx = _hot_cache_par_claimed_idx) < _n_hot) { // read once
- int end_idx = start_idx + _hot_cache_par_chunk_size;
- if (start_idx ==
- Atomic::cmpxchg(end_idx, &_hot_cache_par_claimed_idx, start_idx)) {
- // The current worker has successfully claimed the chunk [start_idx..end_idx)
- end_idx = MIN2(end_idx, _n_hot);
- for (int i = start_idx; i < end_idx; i++) {
- jbyte* card_ptr = _hot_cache[i];
- if (card_ptr != NULL) {
- if (g1rs->refine_card(card_ptr, worker_i, true)) {
- // The part of the heap spanned by the card contains references
- // that point into the current collection set.
- // We need to record the card pointer in the DirtyCardQueueSet
- // that we use for such cards.
- //
- // The only time we care about recording cards that contain
- // references that point into the collection set is during
- // RSet updating while within an evacuation pause.
- // In this case worker_i should be the id of a GC worker thread
- assert(SafepointSynchronize::is_at_safepoint(), "Should be at a safepoint");
- assert(worker_i < ParallelGCThreads,
- err_msg("incorrect worker id: %u", worker_i));
+ while (_hot_cache_par_claimed_idx < _hot_cache_size) {
+ size_t end_idx = Atomic::add(_hot_cache_par_chunk_size,
+ &_hot_cache_par_claimed_idx);
+ size_t start_idx = end_idx - _hot_cache_par_chunk_size;
+ // The current worker has successfully claimed the chunk [start_idx..end_idx)
+ end_idx = MIN2(end_idx, _hot_cache_size);
+ for (size_t i = start_idx; i < end_idx; i++) {
+ jbyte* card_ptr = _hot_cache[i];
+ if (card_ptr != NULL) {
+ if (g1rs->refine_card(card_ptr, worker_i, true)) {
+ // The part of the heap spanned by the card contains references
+ // that point into the current collection set.
+ // We need to record the card pointer in the DirtyCardQueueSet
+ // that we use for such cards.
+ //
+ // The only time we care about recording cards that contain
+ // references that point into the collection set is during
+ // RSet updating while within an evacuation pause.
+ // In this case worker_i should be the id of a GC worker thread
+ assert(SafepointSynchronize::is_at_safepoint(), "Should be at a safepoint");
+ assert(worker_i < ParallelGCThreads,
+ err_msg("incorrect worker id: %u", worker_i));
- into_cset_dcq->enqueue(card_ptr);
- }
+ into_cset_dcq->enqueue(card_ptr);
}
+ } else {
+ break;
}
}
}
+
// The existing entries in the hot card cache, which were just refined
// above, are discarded prior to re-enabling the cache near the end of the GC.
}
--- a/hotspot/src/share/vm/gc_implementation/g1/g1HotCardCache.hpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1HotCardCache.hpp Thu Feb 05 12:23:29 2015 +0100
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -54,21 +54,30 @@
// code, increasing throughput.
class G1HotCardCache: public CHeapObj<mtGC> {
- G1CollectedHeap* _g1h;
+
+ G1CollectedHeap* _g1h;
+
+ bool _use_cache;
+
+ G1CardCounts _card_counts;
// The card cache table
- jbyte** _hot_cache;
+ jbyte** _hot_cache;
- int _hot_cache_size;
- int _n_hot;
- int _hot_cache_idx;
+ size_t _hot_cache_size;
+
+ int _hot_cache_par_chunk_size;
- int _hot_cache_par_chunk_size;
- volatile int _hot_cache_par_claimed_idx;
+ // Avoids false sharing when concurrently updating _hot_cache_idx or
+ // _hot_cache_par_claimed_idx. These are never updated at the same time
+ // thus it's not necessary to separate them as well
+ char _pad_before[DEFAULT_CACHE_LINE_SIZE];
- bool _use_cache;
+ volatile size_t _hot_cache_idx;
- G1CardCounts _card_counts;
+ volatile size_t _hot_cache_par_claimed_idx;
+
+ char _pad_after[DEFAULT_CACHE_LINE_SIZE];
// The number of cached cards a thread claims when flushing the cache
static const int ClaimChunkSize = 32;
@@ -113,16 +122,25 @@
void reset_hot_cache() {
assert(SafepointSynchronize::is_at_safepoint(), "Should be at a safepoint");
assert(Thread::current()->is_VM_thread(), "Current thread should be the VMthread");
- _hot_cache_idx = 0; _n_hot = 0;
+ if (default_use_cache()) {
+ reset_hot_cache_internal();
+ }
}
- bool hot_cache_is_empty() { return _n_hot == 0; }
-
// Zeros the values in the card counts table for entire committed heap
void reset_card_counts();
// Zeros the values in the card counts table for the given region
void reset_card_counts(HeapRegion* hr);
+
+ private:
+ void reset_hot_cache_internal() {
+ assert(_hot_cache != NULL, "Logic");
+ _hot_cache_idx = 0;
+ for (size_t i = 0; i < _hot_cache_size; i++) {
+ _hot_cache[i] = NULL;
+ }
+ }
};
#endif // SHARE_VM_GC_IMPLEMENTATION_G1_G1HOTCARDCACHE_HPP
--- a/hotspot/src/share/vm/gc_implementation/g1/g1SATBCardTableModRefBS.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1SATBCardTableModRefBS.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2001, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2001, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -32,11 +32,8 @@
#include "runtime/orderAccess.inline.hpp"
#include "runtime/thread.inline.hpp"
-G1SATBCardTableModRefBS::G1SATBCardTableModRefBS(MemRegion whole_heap) :
- CardTableModRefBS(whole_heap)
-{
- _kind = G1SATBCT;
-}
+G1SATBCardTableModRefBS::G1SATBCardTableModRefBS(MemRegion whole_heap, BarrierSet::Name kind) :
+ CardTableModRefBS(whole_heap, kind) { }
void G1SATBCardTableModRefBS::enqueue(oop pre_val) {
// Nulls should have been already filtered.
@@ -132,11 +129,10 @@
G1SATBCardTableLoggingModRefBS::
G1SATBCardTableLoggingModRefBS(MemRegion whole_heap) :
- G1SATBCardTableModRefBS(whole_heap),
+ G1SATBCardTableModRefBS(whole_heap, BarrierSet::G1SATBCTLogging),
_dcqs(JavaThread::dirty_card_queue_set()),
_listener()
{
- _kind = G1SATBCTLogging;
_listener.set_card_table(this);
}
--- a/hotspot/src/share/vm/gc_implementation/g1/g1SATBCardTableModRefBS.hpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1SATBCardTableModRefBS.hpp Thu Feb 05 12:23:29 2015 +0100
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2001, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2001, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -43,6 +43,9 @@
g1_young_gen = CT_MR_BS_last_reserved << 1
};
+ G1SATBCardTableModRefBS(MemRegion whole_heap, BarrierSet::Name kind);
+ ~G1SATBCardTableModRefBS() { }
+
public:
static int g1_young_card_val() { return g1_young_gen; }
@@ -50,8 +53,6 @@
// pre-marking object graph.
static void enqueue(oop pre_val);
- G1SATBCardTableModRefBS(MemRegion whole_heap);
-
bool is_a(BarrierSet::Name bsn) {
return bsn == BarrierSet::G1SATBCT || CardTableModRefBS::is_a(bsn);
}
--- a/hotspot/src/share/vm/gc_implementation/g1/heapRegion.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/gc_implementation/g1/heapRegion.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2001, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2001, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -420,7 +420,7 @@
oop obj;
HeapWord* next = cur;
- while (next <= start) {
+ do {
cur = next;
obj = oop(cur);
if (obj->klass_or_null() == NULL) {
@@ -429,45 +429,38 @@
}
// Otherwise...
next = cur + block_size(cur);
- }
+ } while (next <= start);
// If we finish the above loop...We have a parseable object that
// begins on or before the start of the memory region, and ends
// inside or spans the entire region.
-
- assert(obj == oop(cur), "sanity");
assert(cur <= start, "Loop postcondition");
assert(obj->klass_or_null() != NULL, "Loop postcondition");
- assert((cur + block_size(cur)) > start, "Loop postcondition");
- if (!g1h->is_obj_dead(obj)) {
- obj->oop_iterate(cl, mr);
- }
-
- while (cur < end) {
+ do {
obj = oop(cur);
+ assert((cur + block_size(cur)) > (HeapWord*)obj, "Loop invariant");
if (obj->klass_or_null() == NULL) {
// Ran into an unparseable point.
return cur;
- };
+ }
- // Otherwise:
- next = cur + block_size(cur);
+ // Advance the current pointer. "obj" still points to the object to iterate.
+ cur = cur + block_size(cur);
if (!g1h->is_obj_dead(obj)) {
- if (next < end || !obj->is_objArray()) {
- // This object either does not span the MemRegion
- // boundary, or if it does it's not an array.
- // Apply closure to whole object.
+ // Non-objArrays are sometimes marked imprecise at the object start. We
+ // always need to iterate over them in full.
+ // We only iterate over object arrays in full if they are completely contained
+ // in the memory region.
+ if (!obj->is_objArray() || (((HeapWord*)obj) >= start && cur <= end)) {
obj->oop_iterate(cl);
} else {
- // This obj is an array that spans the boundary.
- // Stop at the boundary.
obj->oop_iterate(cl, mr);
}
}
- cur = next;
- }
+ } while (cur < end);
+
return NULL;
}
--- a/hotspot/src/share/vm/gc_implementation/parallelScavenge/cardTableExtension.hpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/gc_implementation/parallelScavenge/cardTableExtension.hpp Thu Feb 05 12:23:29 2015 +0100
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2001, 2010, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2001, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -54,7 +54,7 @@
};
CardTableExtension(MemRegion whole_heap) :
- CardTableModRefBS(whole_heap) { }
+ CardTableModRefBS(whole_heap, BarrierSet::CardTableModRef) { }
// Too risky for the 4/10/02 putback
// BarrierSet::Name kind() { return BarrierSet::CardTableExtension; }
--- a/hotspot/src/share/vm/gc_interface/gcCause.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/gc_interface/gcCause.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -103,6 +103,9 @@
case _last_ditch_collection:
return "Last ditch collection";
+ case _dcmd_gc_run:
+ return "Diagnostic Command";
+
case _last_gc_cause:
return "ILLEGAL VALUE - last gc cause - ILLEGAL VALUE";
--- a/hotspot/src/share/vm/gc_interface/gcCause.hpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/gc_interface/gcCause.hpp Thu Feb 05 12:23:29 2015 +0100
@@ -74,6 +74,9 @@
_g1_humongous_allocation,
_last_ditch_collection,
+
+ _dcmd_gc_run,
+
_last_gc_cause
};
--- a/hotspot/src/share/vm/memory/barrierSet.hpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/memory/barrierSet.hpp Thu Feb 05 12:23:29 2015 +0100
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2000, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -39,9 +39,7 @@
CardTableModRef,
CardTableExtension,
G1SATBCT,
- G1SATBCTLogging,
- Other,
- Uninit
+ G1SATBCTLogging
};
enum Flags {
@@ -57,9 +55,11 @@
static const int _max_covered_regions = 2;
Name _kind;
+ BarrierSet(Name kind) : _kind(kind) { }
+ ~BarrierSet() { }
+
public:
- BarrierSet() { _kind = Uninit; }
// To get around prohibition on RTTI.
BarrierSet::Name kind() { return _kind; }
virtual bool is_a(BarrierSet::Name bsn) = 0;
--- a/hotspot/src/share/vm/memory/cardTableModRefBS.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/memory/cardTableModRefBS.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2000, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -53,8 +53,8 @@
return align_size_up(_guard_index + 1, MAX2(_page_size, granularity));
}
-CardTableModRefBS::CardTableModRefBS(MemRegion whole_heap) :
- ModRefBarrierSet(),
+CardTableModRefBS::CardTableModRefBS(MemRegion whole_heap, BarrierSet::Name kind) :
+ ModRefBarrierSet(kind),
_whole_heap(whole_heap),
_guard_index(0),
_guard_region(),
@@ -72,8 +72,6 @@
_lowest_non_clean_base_chunk_index(NULL),
_last_LNC_resizing_collection(NULL)
{
- _kind = BarrierSet::CardTableModRef;
-
assert((uintptr_t(_whole_heap.start()) & (card_size - 1)) == 0, "heap must start at card boundary");
assert((uintptr_t(_whole_heap.end()) & (card_size - 1)) == 0, "heap must end at card boundary");
--- a/hotspot/src/share/vm/memory/cardTableModRefBS.hpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/memory/cardTableModRefBS.hpp Thu Feb 05 12:23:29 2015 +0100
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2000, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -284,20 +284,22 @@
return bsn == BarrierSet::CardTableModRef || ModRefBarrierSet::is_a(bsn);
}
- CardTableModRefBS(MemRegion whole_heap);
- ~CardTableModRefBS();
-
virtual void initialize();
// *** Barrier set functions.
bool has_write_ref_pre_barrier() { return false; }
+protected:
+
+ CardTableModRefBS(MemRegion whole_heap, BarrierSet::Name kind);
+ ~CardTableModRefBS();
+
// Record a reference update. Note that these versions are precise!
// The scanning code has to handle the fact that the write barrier may be
// either precise or imprecise. We make non-virtual inline variants of
// these functions here for performance.
-protected:
+
void write_ref_field_work(oop obj, size_t offset, oop newVal);
virtual void write_ref_field_work(void* field, oop newVal, bool release = false);
public:
@@ -478,7 +480,7 @@
bool card_may_have_been_dirty(jbyte cv);
public:
CardTableModRefBSForCTRS(MemRegion whole_heap) :
- CardTableModRefBS(whole_heap) {}
+ CardTableModRefBS(whole_heap, BarrierSet::CardTableModRef) {}
void set_CTRS(CardTableRS* rs) { _rs = rs; }
};
--- a/hotspot/src/share/vm/memory/modRefBarrierSet.hpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/memory/modRefBarrierSet.hpp Thu Feb 05 12:23:29 2015 +0100
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2000, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -37,8 +37,6 @@
class ModRefBarrierSet: public BarrierSet {
public:
- ModRefBarrierSet() { _kind = BarrierSet::ModRef; }
-
bool is_a(BarrierSet::Name bsn) {
return bsn == BarrierSet::ModRef;
}
@@ -59,7 +57,12 @@
void read_ref_field(void* field) {}
void read_prim_field(HeapWord* field, size_t bytes) {}
+
protected:
+
+ ModRefBarrierSet(BarrierSet::Name kind) : BarrierSet(kind) { }
+ ~ModRefBarrierSet() { }
+
virtual void write_ref_field_work(void* field, oop new_val, bool release = false) = 0;
public:
void write_prim_field(HeapWord* field, size_t bytes,
--- a/hotspot/src/share/vm/opto/graphKit.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/opto/graphKit.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -1528,7 +1528,6 @@
case BarrierSet::ModRef:
break;
- case BarrierSet::Other:
default :
ShouldNotReachHere();
@@ -1547,7 +1546,6 @@
case BarrierSet::ModRef:
return true; // There is no pre-barrier
- case BarrierSet::Other:
default :
ShouldNotReachHere();
}
@@ -1578,7 +1576,6 @@
case BarrierSet::ModRef:
break;
- case BarrierSet::Other:
default :
ShouldNotReachHere();
--- a/hotspot/src/share/vm/runtime/arguments.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/runtime/arguments.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -57,18 +57,6 @@
#define DEFAULT_VENDOR_URL_BUG "http://bugreport.java.com/bugreport/crash.jsp"
#define DEFAULT_JAVA_LAUNCHER "generic"
-// Disable options not supported in this release, with a warning if they
-// were explicitly requested on the command-line
-#define UNSUPPORTED_OPTION(opt, description) \
-do { \
- if (opt) { \
- if (FLAG_IS_CMDLINE(opt)) { \
- warning(description " is disabled in this release."); \
- } \
- FLAG_SET_DEFAULT(opt, false); \
- } \
-} while(0)
-
#define UNSUPPORTED_GC_OPTION(gc) \
do { \
if (gc) { \
@@ -2316,6 +2304,7 @@
status = status && verify_percentage(G1MaxNewSizePercent, "G1MaxNewSizePercent");
status = status && verify_interval(G1NewSizePercent, 0, G1MaxNewSizePercent, "G1NewSizePercent");
+ status = status && verify_percentage(G1ConfidencePercent, "G1ConfidencePercent");
status = status && verify_percentage(InitiatingHeapOccupancyPercent,
"InitiatingHeapOccupancyPercent");
status = status && verify_min_value(G1RefProcDrainInterval, 1,
@@ -3853,6 +3842,8 @@
#endif
#endif
+ ArgumentsExt::report_unsupported_options();
+
#ifndef PRODUCT
if (TraceBytecodesAt != 0) {
TraceBytecodes = true;
--- a/hotspot/src/share/vm/runtime/arguments.hpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/runtime/arguments.hpp Thu Feb 05 12:23:29 2015 +0100
@@ -632,4 +632,16 @@
return check_gc_consistency_user();
}
+// Disable options not supported in this release, with a warning if they
+// were explicitly requested on the command-line
+#define UNSUPPORTED_OPTION(opt, description) \
+do { \
+ if (opt) { \
+ if (FLAG_IS_CMDLINE(opt)) { \
+ warning(description " is disabled in this release."); \
+ } \
+ FLAG_SET_DEFAULT(opt, false); \
+ } \
+} while(0)
+
#endif // SHARE_VM_RUNTIME_ARGUMENTS_HPP
--- a/hotspot/src/share/vm/runtime/arguments_ext.hpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/runtime/arguments_ext.hpp Thu Feb 05 12:23:29 2015 +0100
@@ -37,6 +37,7 @@
// no additional parsing needed in Arguments::parse() for the option.
// Otherwise returns false.
static inline bool process_options(const JavaVMOption *option) { return false; }
+ static inline void report_unsupported_options() { }
};
void ArgumentsExt::select_gc_ergonomically() {
--- a/hotspot/src/share/vm/runtime/mutexLocker.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/runtime/mutexLocker.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -120,7 +120,6 @@
Mutex* OldSets_lock = NULL;
Monitor* RootRegionScan_lock = NULL;
Mutex* MMUTracker_lock = NULL;
-Mutex* HotCardCache_lock = NULL;
Monitor* GCTaskManager_lock = NULL;
@@ -199,7 +198,6 @@
def(OldSets_lock , Mutex , leaf , true, Monitor::_safepoint_check_never);
def(RootRegionScan_lock , Monitor, leaf , true, Monitor::_safepoint_check_never);
def(MMUTracker_lock , Mutex , leaf , true, Monitor::_safepoint_check_never);
- def(HotCardCache_lock , Mutex , special , true, Monitor::_safepoint_check_never);
def(EvacFailureStack_lock , Mutex , nonleaf , true, Monitor::_safepoint_check_never);
def(StringDedupQueue_lock , Monitor, leaf, true, Monitor::_safepoint_check_never);
--- a/hotspot/src/share/vm/runtime/mutexLocker.hpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/runtime/mutexLocker.hpp Thu Feb 05 12:23:29 2015 +0100
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -122,7 +122,6 @@
extern Monitor* RootRegionScan_lock; // used to notify that the CM threads have finished scanning the IM snapshot regions
extern Mutex* MMUTracker_lock; // protects the MMU
// tracker data structures
-extern Mutex* HotCardCache_lock; // protects the hot card cache
extern Mutex* Management_lock; // a lock used to serialize JVM management
extern Monitor* Service_lock; // a lock used for service thread operation
--- a/hotspot/src/share/vm/runtime/vmStructs.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/runtime/vmStructs.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -2228,7 +2228,6 @@
declare_constant(BarrierSet::CardTableExtension) \
declare_constant(BarrierSet::G1SATBCT) \
declare_constant(BarrierSet::G1SATBCTLogging) \
- declare_constant(BarrierSet::Other) \
\
declare_constant(BlockOffsetSharedArray::LogN) \
declare_constant(BlockOffsetSharedArray::LogN_words) \
--- a/hotspot/src/share/vm/services/diagnosticCommand.cpp Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/src/share/vm/services/diagnosticCommand.cpp Thu Feb 05 12:23:29 2015 +0100
@@ -267,7 +267,7 @@
void SystemGCDCmd::execute(DCmdSource source, TRAPS) {
if (!DisableExplicitGC) {
- Universe::heap()->collect(GCCause::_java_lang_system_gc);
+ Universe::heap()->collect(GCCause::_dcmd_gc_run);
} else {
output()->print_cr("Explicit GC is disabled, no GC has been performed.");
}
--- a/hotspot/test/TEST.groups Wed Feb 04 18:22:46 2015 -0800
+++ b/hotspot/test/TEST.groups Thu Feb 05 12:23:29 2015 +0100
@@ -225,6 +225,7 @@
gc/arguments/TestAlignmentToUseLargePages.java \
gc/arguments/TestG1HeapRegionSize.java \
gc/arguments/TestG1HeapSizeFlags.java \
+ gc/arguments/TestG1PercentageOptions.java \
gc/arguments/TestMaxHeapSizeTools.java \
gc/arguments/TestMaxNewSize.java \
gc/arguments/TestParallelGCThreads.java \
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/gc/arguments/TestG1PercentageOptions.java Thu Feb 05 12:23:29 2015 +0100
@@ -0,0 +1,89 @@
+/*
+* Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+*
+* This code is free software; you can redistribute it and/or modify it
+* under the terms of the GNU General Public License version 2 only, as
+* published by the Free Software Foundation.
+*
+* This code is distributed in the hope that it will be useful, but WITHOUT
+* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+* version 2 for more details (a copy is included in the LICENSE file that
+* accompanied this code).
+*
+* You should have received a copy of the GNU General Public License version
+* 2 along with this work; if not, write to the Free Software Foundation,
+* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+*
+* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+* or visit www.oracle.com if you need additional information or have any
+* questions.
+*/
+
+/*
+ * @test TestG1PercentageOptions
+ * @key gc
+ * @bug 8068942
+ * @summary Test argument processing of various percentage options
+ * @library /testlibrary
+ * @run driver TestG1PercentageOptions
+ */
+
+import com.oracle.java.testlibrary.*;
+
+public class TestG1PercentageOptions {
+
+ private static final class OptionDescription {
+ public final String name;
+ public final String[] valid;
+ public final String[] invalid;
+
+ OptionDescription(String name_, String[] valid_, String[] invalid_) {
+ name = name_;
+ valid = valid_;
+ invalid = invalid_;
+ }
+ }
+
+ private static final String[] defaultValid = new String[] {
+ "0", "1", "50", "95", "100" };
+ private static final String[] defaultInvalid = new String[] {
+ "-10", "110", "bad" };
+
+ // All of the G1 product arguments that are percentages.
+ private static final OptionDescription[] percentOptions = new OptionDescription[] {
+ new OptionDescription("G1ConfidencePercent", defaultValid, defaultInvalid)
+ // Other percentage options are not yet validated by argument processing.
+ };
+
+ private static void check(String flag, boolean is_valid) throws Exception {
+ String[] flags = new String[] { "-XX:+UseG1GC", flag, "-version" };
+ ProcessBuilder pb = ProcessTools.createJavaProcessBuilder(flags);
+ OutputAnalyzer output = new OutputAnalyzer(pb.start());
+ if (is_valid) {
+ output.shouldHaveExitValue(0);
+ } else {
+ output.shouldHaveExitValue(1);
+ }
+ }
+
+ private static
+ void check(String name, String value, boolean is_valid) throws Exception {
+ check("-XX:" + name + "=" + value, is_valid);
+ }
+
+ public static void main(String args[]) throws Exception {
+ for (OptionDescription option : percentOptions) {
+ for (String value : option.valid) {
+ check(option.name, value, true);
+ }
+ for (String value : option.invalid) {
+ check(option.name, value, false);
+ }
+ check("-XX:" + option.name, false);
+ check("-XX:+" + option.name, false);
+ check("-XX:-" + option.name, false);
+ }
+ }
+}