Mercurial > hg > truffle
annotate src/share/vm/gc_implementation/g1/sparsePRT.hpp @ 12233:40136aa2cdb1
8010722: assert: failed: heap size is too big for compressed oops
Summary: Use conservative assumptions of required alignment for the various garbage collector components into account when determining the maximum heap size that supports compressed oops. Using this conservative value avoids several circular dependencies in the calculation.
Reviewed-by: stefank, dholmes
author | tschatzl |
---|---|
date | Wed, 11 Sep 2013 16:25:02 +0200 |
parents | 5c93c1f61226 |
children | de6a9e811145 |
rev | line source |
---|---|
342 | 1 /* |
6842
b9a9ed0f8eeb
7197424: update copyright year to match last edit in jdk8 hotspot repository
mikael
parents:
6197
diff
changeset
|
2 * Copyright (c) 2001, 2012, Oracle and/or its affiliates. All rights reserved. |
342 | 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
4 * | |
5 * This code is free software; you can redistribute it and/or modify it | |
6 * under the terms of the GNU General Public License version 2 only, as | |
7 * published by the Free Software Foundation. | |
8 * | |
9 * This code is distributed in the hope that it will be useful, but WITHOUT | |
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | |
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | |
12 * version 2 for more details (a copy is included in the LICENSE file that | |
13 * accompanied this code). | |
14 * | |
15 * You should have received a copy of the GNU General Public License version | |
16 * 2 along with this work; if not, write to the Free Software Foundation, | |
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. | |
18 * | |
1552
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
1261
diff
changeset
|
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA |
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
1261
diff
changeset
|
20 * or visit www.oracle.com if you need additional information or have any |
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
1261
diff
changeset
|
21 * questions. |
342 | 22 * |
23 */ | |
24 | |
1972 | 25 #ifndef SHARE_VM_GC_IMPLEMENTATION_G1_SPARSEPRT_HPP |
26 #define SHARE_VM_GC_IMPLEMENTATION_G1_SPARSEPRT_HPP | |
27 | |
28 #include "gc_implementation/g1/g1CollectedHeap.inline.hpp" | |
29 #include "gc_implementation/g1/heapRegion.hpp" | |
30 #include "memory/allocation.hpp" | |
31 #include "memory/cardTableModRefBS.hpp" | |
32 #include "runtime/mutex.hpp" | |
33 #include "utilities/globalDefinitions.hpp" | |
34 | |
342 | 35 // Sparse remembered set for a heap region (the "owning" region). Maps |
36 // indices of other regions to short sequences of cards in the other region | |
37 // that might contain pointers into the owner region. | |
38 | |
39 // These tables only expand while they are accessed in parallel -- | |
40 // deletions may be done in single-threaded code. This allows us to allow | |
41 // unsynchronized reads/iterations, as long as expansions caused by | |
42 // insertions only enqueue old versions for deletions, but do not delete | |
43 // old versions synchronously. | |
44 | |
6197 | 45 class SparsePRTEntry: public CHeapObj<mtGC> { |
342 | 46 public: |
47 enum SomePublicConstants { | |
1261
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
48 NullEntry = -1, |
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
49 UnrollFactor = 4 |
342 | 50 }; |
51 private: | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
52 RegionIdx_t _region_ind; |
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
53 int _next_index; |
1261
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
54 CardIdx_t _cards[1]; |
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
55 // WARNING: Don't put any data members beyond this line. Card array has, in fact, variable length. |
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
56 // It should always be the last data member. |
342 | 57 public: |
1261
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
58 // Returns the size of the entry, used for entry allocation. |
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
59 static size_t size() { return sizeof(SparsePRTEntry) + sizeof(CardIdx_t) * (cards_num() - 1); } |
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
60 // Returns the size of the card array. |
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
61 static int cards_num() { |
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
62 // The number of cards should be a multiple of 4, because that's our current |
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
63 // unrolling factor. |
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
64 static const int s = MAX2<int>(G1RSetSparseRegionEntries & ~(UnrollFactor - 1), UnrollFactor); |
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
65 return s; |
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
66 } |
342 | 67 |
68 // Set the region_ind to the given value, and delete all cards. | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
69 inline void init(RegionIdx_t region_ind); |
342 | 70 |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
71 RegionIdx_t r_ind() const { return _region_ind; } |
342 | 72 bool valid_entry() const { return r_ind() >= 0; } |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
73 void set_r_ind(RegionIdx_t rind) { _region_ind = rind; } |
342 | 74 |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
75 int next_index() const { return _next_index; } |
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
76 int* next_index_addr() { return &_next_index; } |
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
77 void set_next_index(int ni) { _next_index = ni; } |
342 | 78 |
79 // Returns "true" iff the entry contains the given card index. | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
80 inline bool contains_card(CardIdx_t card_index) const; |
342 | 81 |
82 // Returns the number of non-NULL card entries. | |
83 inline int num_valid_cards() const; | |
84 | |
85 // Requires that the entry not contain the given card index. If there is | |
86 // space available, add the given card index to the entry and return | |
87 // "true"; otherwise, return "false" to indicate that the entry is full. | |
88 enum AddCardResult { | |
89 overflow, | |
90 found, | |
91 added | |
92 }; | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
93 inline AddCardResult add_card(CardIdx_t card_index); |
342 | 94 |
95 // Copy the current entry's cards into "cards". | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
96 inline void copy_cards(CardIdx_t* cards) const; |
342 | 97 // Copy the current entry's cards into the "_card" array of "e." |
98 inline void copy_cards(SparsePRTEntry* e) const; | |
99 | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
100 inline CardIdx_t card(int i) const { return _cards[i]; } |
342 | 101 }; |
102 | |
103 | |
6197 | 104 class RSHashTable : public CHeapObj<mtGC> { |
342 | 105 |
106 friend class RSHashTableIter; | |
107 | |
108 enum SomePrivateConstants { | |
109 NullEntry = -1 | |
110 }; | |
111 | |
112 size_t _capacity; | |
113 size_t _capacity_mask; | |
114 size_t _occupied_entries; | |
115 size_t _occupied_cards; | |
116 | |
117 SparsePRTEntry* _entries; | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
118 int* _buckets; |
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
119 int _free_region; |
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
120 int _free_list; |
342 | 121 |
122 // Requires that the caller hold a lock preventing parallel modifying | |
123 // operations, and that the the table be less than completely full. If | |
124 // an entry for "region_ind" is already in the table, finds it and | |
125 // returns its address; otherwise returns "NULL." | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
126 SparsePRTEntry* entry_for_region_ind(RegionIdx_t region_ind) const; |
342 | 127 |
128 // Requires that the caller hold a lock preventing parallel modifying | |
129 // operations, and that the the table be less than completely full. If | |
130 // an entry for "region_ind" is already in the table, finds it and | |
131 // returns its address; otherwise allocates, initializes, inserts and | |
132 // returns a new entry for "region_ind". | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
133 SparsePRTEntry* entry_for_region_ind_create(RegionIdx_t region_ind); |
342 | 134 |
135 // Returns the index of the next free entry in "_entries". | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
136 int alloc_entry(); |
342 | 137 // Declares the entry "fi" to be free. (It must have already been |
138 // deleted from any bucket lists. | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
139 void free_entry(int fi); |
342 | 140 |
141 public: | |
142 RSHashTable(size_t capacity); | |
143 ~RSHashTable(); | |
144 | |
145 // Attempts to ensure that the given card_index in the given region is in | |
146 // the sparse table. If successful (because the card was already | |
147 // present, or because it was successfullly added) returns "true". | |
148 // Otherwise, returns "false" to indicate that the addition would | |
149 // overflow the entry for the region. The caller must transfer these | |
150 // entries to a larger-capacity representation. | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
151 bool add_card(RegionIdx_t region_id, CardIdx_t card_index); |
342 | 152 |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
153 bool get_cards(RegionIdx_t region_id, CardIdx_t* cards); |
1261
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
154 |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
155 bool delete_entry(RegionIdx_t region_id); |
342 | 156 |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
157 bool contains_card(RegionIdx_t region_id, CardIdx_t card_index) const; |
342 | 158 |
159 void add_entry(SparsePRTEntry* e); | |
160 | |
1261
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
161 SparsePRTEntry* get_entry(RegionIdx_t region_id); |
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
162 |
342 | 163 void clear(); |
164 | |
165 size_t capacity() const { return _capacity; } | |
166 size_t capacity_mask() const { return _capacity_mask; } | |
167 size_t occupied_entries() const { return _occupied_entries; } | |
168 size_t occupied_cards() const { return _occupied_cards; } | |
169 size_t mem_size() const; | |
170 | |
1261
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
171 SparsePRTEntry* entry(int i) const { return (SparsePRTEntry*)((char*)_entries + SparsePRTEntry::size() * i); } |
342 | 172 |
173 void print(); | |
174 }; | |
175 | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
176 // ValueObj because will be embedded in HRRS iterator. |
549
fe3d7c11b4b7
6700941: G1: allocation spec missing for some G1 classes
apetrusenko
parents:
342
diff
changeset
|
177 class RSHashTableIter VALUE_OBJ_CLASS_SPEC { |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
178 int _tbl_ind; // [-1, 0.._rsht->_capacity) |
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
179 int _bl_ind; // [-1, 0.._rsht->_capacity) |
1261
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
180 short _card_ind; // [0..SparsePRTEntry::cards_num()) |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
181 RSHashTable* _rsht; |
342 | 182 |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
183 // If the bucket list pointed to by _bl_ind contains a card, sets |
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
184 // _bl_ind to the index of that entry, and returns the card. |
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
185 // Otherwise, returns SparseEntry::NullEntry. |
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
186 CardIdx_t find_first_card_in_list(); |
342 | 187 |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
188 // Computes the proper card index for the card whose offset in the |
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
189 // current region (as indicated by _bl_ind) is "ci". |
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
190 // This is subject to errors when there is iteration concurrent with |
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
191 // modification, but these errors should be benign. |
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
192 size_t compute_card_ind(CardIdx_t ci); |
342 | 193 |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
194 public: |
10182
5c93c1f61226
8011724: G1: Stack allocate instances of HeapRegionRemSetIterator
johnc
parents:
6842
diff
changeset
|
195 RSHashTableIter(RSHashTable* rsht) : |
5c93c1f61226
8011724: G1: Stack allocate instances of HeapRegionRemSetIterator
johnc
parents:
6842
diff
changeset
|
196 _tbl_ind(RSHashTable::NullEntry), // So that first increment gets to 0. |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
197 _bl_ind(RSHashTable::NullEntry), |
1261
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
198 _card_ind((SparsePRTEntry::cards_num() - 1)), |
10182
5c93c1f61226
8011724: G1: Stack allocate instances of HeapRegionRemSetIterator
johnc
parents:
6842
diff
changeset
|
199 _rsht(rsht) {} |
342 | 200 |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
201 bool has_next(size_t& card_index); |
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
202 }; |
342 | 203 |
204 // Concurrent accesss to a SparsePRT must be serialized by some external | |
205 // mutex. | |
206 | |
207 class SparsePRTIter; | |
2173 | 208 class SparsePRTCleanupTask; |
342 | 209 |
549
fe3d7c11b4b7
6700941: G1: allocation spec missing for some G1 classes
apetrusenko
parents:
342
diff
changeset
|
210 class SparsePRT VALUE_OBJ_CLASS_SPEC { |
2173 | 211 friend class SparsePRTCleanupTask; |
212 | |
342 | 213 // Iterations are done on the _cur hash table, since they only need to |
214 // see entries visible at the start of a collection pause. | |
215 // All other operations are done using the _next hash table. | |
216 RSHashTable* _cur; | |
217 RSHashTable* _next; | |
218 | |
219 HeapRegion* _hr; | |
220 | |
221 enum SomeAdditionalPrivateConstants { | |
222 InitialCapacity = 16 | |
223 }; | |
224 | |
225 void expand(); | |
226 | |
227 bool _expanded; | |
228 | |
229 bool expanded() { return _expanded; } | |
230 void set_expanded(bool b) { _expanded = b; } | |
231 | |
232 SparsePRT* _next_expanded; | |
233 | |
234 SparsePRT* next_expanded() { return _next_expanded; } | |
235 void set_next_expanded(SparsePRT* nxt) { _next_expanded = nxt; } | |
236 | |
2173 | 237 bool should_be_on_expanded_list(); |
238 | |
342 | 239 static SparsePRT* _head_expanded_list; |
240 | |
241 public: | |
242 SparsePRT(HeapRegion* hr); | |
243 | |
244 ~SparsePRT(); | |
245 | |
246 size_t occupied() const { return _next->occupied_cards(); } | |
247 size_t mem_size() const; | |
248 | |
249 // Attempts to ensure that the given card_index in the given region is in | |
250 // the sparse table. If successful (because the card was already | |
251 // present, or because it was successfullly added) returns "true". | |
252 // Otherwise, returns "false" to indicate that the addition would | |
253 // overflow the entry for the region. The caller must transfer these | |
254 // entries to a larger-capacity representation. | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
255 bool add_card(RegionIdx_t region_id, CardIdx_t card_index); |
342 | 256 |
257 // If the table hold an entry for "region_ind", Copies its | |
258 // cards into "cards", which must be an array of length at least | |
1261
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
259 // "SparePRTEntry::cards_num()", and returns "true"; otherwise, |
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
260 // returns "false". |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
261 bool get_cards(RegionIdx_t region_ind, CardIdx_t* cards); |
342 | 262 |
1261
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
263 // Return the pointer to the entry associated with the given region. |
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
264 SparsePRTEntry* get_entry(RegionIdx_t region_ind); |
0414c1049f15
6923991: G1: improve scalability of RSet scanning
iveresov
parents:
1045
diff
changeset
|
265 |
342 | 266 // If there is an entry for "region_ind", removes it and return "true"; |
267 // otherwise returns "false." | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
268 bool delete_entry(RegionIdx_t region_ind); |
342 | 269 |
270 // Clear the table, and reinitialize to initial capacity. | |
271 void clear(); | |
272 | |
273 // Ensure that "_cur" and "_next" point to the same table. | |
274 void cleanup(); | |
275 | |
276 // Clean up all tables on the expanded list. Called single threaded. | |
277 static void cleanup_all(); | |
617
0db4adb6e914
6810698: G1: two small bugs in the sparse remembered sets
tonyp
parents:
549
diff
changeset
|
278 RSHashTable* cur() const { return _cur; } |
342 | 279 |
280 static void add_to_expanded_list(SparsePRT* sprt); | |
281 static SparsePRT* get_from_expanded_list(); | |
282 | |
2173 | 283 // The purpose of these three methods is to help the GC workers |
284 // during the cleanup pause to recreate the expanded list, purging | |
285 // any tables from it that belong to regions that are freed during | |
286 // cleanup (if we don't purge those tables, there is a race that | |
287 // causes various crashes; see CR 7014261). | |
288 // | |
289 // We chose to recreate the expanded list, instead of purging | |
290 // entries from it by iterating over it, to avoid this serial phase | |
291 // at the end of the cleanup pause. | |
292 // | |
293 // The three methods below work as follows: | |
294 // * reset_for_cleanup_tasks() : Nulls the expanded list head at the | |
295 // start of the cleanup pause. | |
296 // * do_cleanup_work() : Called by the cleanup workers for every | |
297 // region that is not free / is being freed by the cleanup | |
298 // pause. It creates a list of expanded tables whose head / tail | |
299 // are on the thread-local SparsePRTCleanupTask object. | |
300 // * finish_cleanup_task() : Called by the cleanup workers after | |
301 // they complete their cleanup task. It adds the local list into | |
302 // the global expanded list. It assumes that the | |
303 // ParGCRareEvent_lock is being held to ensure MT-safety. | |
304 static void reset_for_cleanup_tasks(); | |
305 void do_cleanup_work(SparsePRTCleanupTask* sprt_cleanup_task); | |
306 static void finish_cleanup_task(SparsePRTCleanupTask* sprt_cleanup_task); | |
307 | |
807
d44bdab1c03d
6843694: G1: assert(index < _vs.committed_size(),"bad index"), g1BlockOffsetTable.inline.hpp:55
johnc
parents:
628
diff
changeset
|
308 bool contains_card(RegionIdx_t region_id, CardIdx_t card_index) const { |
342 | 309 return _next->contains_card(region_id, card_index); |
310 } | |
311 }; | |
312 | |
1884
9f4848ebbabd
6992189: G1: inconsistent base used in sparse rem set iterator
tonyp
parents:
1552
diff
changeset
|
313 class SparsePRTIter: public RSHashTableIter { |
342 | 314 public: |
10182
5c93c1f61226
8011724: G1: Stack allocate instances of HeapRegionRemSetIterator
johnc
parents:
6842
diff
changeset
|
315 SparsePRTIter(const SparsePRT* sprt) : |
5c93c1f61226
8011724: G1: Stack allocate instances of HeapRegionRemSetIterator
johnc
parents:
6842
diff
changeset
|
316 RSHashTableIter(sprt->cur()) {} |
5c93c1f61226
8011724: G1: Stack allocate instances of HeapRegionRemSetIterator
johnc
parents:
6842
diff
changeset
|
317 |
342 | 318 bool has_next(size_t& card_index) { |
319 return RSHashTableIter::has_next(card_index); | |
320 } | |
321 }; | |
1972 | 322 |
2173 | 323 // This allows each worker during a cleanup pause to create a |
324 // thread-local list of sparse tables that have been expanded and need | |
325 // to be processed at the beginning of the next GC pause. This lists | |
326 // are concatenated into the single expanded list at the end of the | |
327 // cleanup pause. | |
328 class SparsePRTCleanupTask VALUE_OBJ_CLASS_SPEC { | |
329 private: | |
330 SparsePRT* _head; | |
331 SparsePRT* _tail; | |
332 | |
333 public: | |
334 SparsePRTCleanupTask() : _head(NULL), _tail(NULL) { } | |
335 | |
336 void add(SparsePRT* sprt); | |
337 SparsePRT* head() { return _head; } | |
338 SparsePRT* tail() { return _tail; } | |
339 }; | |
340 | |
1972 | 341 #endif // SHARE_VM_GC_IMPLEMENTATION_G1_SPARSEPRT_HPP |