Sat, 06 Oct 2012 01:17:44 -0700
7127708: G1: change task num types from int to uint in concurrent mark
Summary: Change the type of various task num fields, parameters etc to unsigned and rename them to be more consistent with the other collectors. Code changes were also reviewed by Vitaly Davidovich.
Reviewed-by: johnc
Contributed-by: Kaushik Srenevasan <kaushik@twitter.com>
1 /*
2 * Copyright (c) 2011, 2012, Oracle and/or its affiliates. All rights reserved.
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 *
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 *
23 */
25 #ifndef SHARE_VM_GC_IMPLEMENTATION_G1_HEAPREGIONSET_HPP
26 #define SHARE_VM_GC_IMPLEMENTATION_G1_HEAPREGIONSET_HPP
28 #include "gc_implementation/g1/heapRegion.hpp"
30 // Large buffer for some cases where the output might be larger than normal.
31 #define HRS_ERR_MSG_BUFSZ 512
32 typedef FormatBuffer<HRS_ERR_MSG_BUFSZ> hrs_err_msg;
34 // Set verification will be forced either if someone defines
35 // HEAP_REGION_SET_FORCE_VERIFY to be 1, or in builds in which
36 // asserts are compiled in.
37 #ifndef HEAP_REGION_SET_FORCE_VERIFY
38 #define HEAP_REGION_SET_FORCE_VERIFY defined(ASSERT)
39 #endif // HEAP_REGION_SET_FORCE_VERIFY
41 //////////////////// HeapRegionSetBase ////////////////////
43 // Base class for all the classes that represent heap region sets. It
44 // contains the basic attributes that each set needs to maintain
45 // (e.g., length, region num, used bytes sum) plus any shared
46 // functionality (e.g., verification).
48 class hrs_ext_msg;
50 typedef enum {
51 HRSPhaseNone,
52 HRSPhaseEvacuation,
53 HRSPhaseCleanup,
54 HRSPhaseFullGC
55 } HRSPhase;
57 class HRSPhaseSetter;
59 class HeapRegionSetBase VALUE_OBJ_CLASS_SPEC {
60 friend class hrs_ext_msg;
61 friend class HRSPhaseSetter;
62 friend class VMStructs;
64 protected:
65 static uint _unrealistically_long_length;
67 // The number of regions added to the set. If the set contains
68 // only humongous regions, this reflects only 'starts humongous'
69 // regions and does not include 'continues humongous' ones.
70 uint _length;
72 // The total number of regions represented by the set. If the set
73 // does not contain humongous regions, this should be the same as
74 // _length. If the set contains only humongous regions, this will
75 // include the 'continues humongous' regions.
76 uint _region_num;
78 // We don't keep track of the total capacity explicitly, we instead
79 // recalculate it based on _region_num and the heap region size.
81 // The sum of used bytes in the all the regions in the set.
82 size_t _total_used_bytes;
84 const char* _name;
86 bool _verify_in_progress;
87 uint _calc_length;
88 uint _calc_region_num;
89 size_t _calc_total_capacity_bytes;
90 size_t _calc_total_used_bytes;
92 // This is here so that it can be used in the subclasses to assert
93 // something different depending on which phase the GC is in. This
94 // can be particularly helpful in the check_mt_safety() methods.
95 static HRSPhase _phase;
97 // Only used by HRSPhaseSetter.
98 static void clear_phase();
99 static void set_phase(HRSPhase phase);
101 // verify_region() is used to ensure that the contents of a region
102 // added to / removed from a set are consistent. Different sets
103 // make different assumptions about the regions added to them. So
104 // each set can override verify_region_extra(), which is called
105 // from verify_region(), and do any extra verification it needs to
106 // perform in that.
107 virtual const char* verify_region_extra(HeapRegion* hr) { return NULL; }
108 bool verify_region(HeapRegion* hr,
109 HeapRegionSetBase* expected_containing_set);
111 // Indicates whether all regions in the set should be humongous or
112 // not. Only used during verification.
113 virtual bool regions_humongous() = 0;
115 // Indicates whether all regions in the set should be empty or
116 // not. Only used during verification.
117 virtual bool regions_empty() = 0;
119 // Subclasses can optionally override this to do MT safety protocol
120 // checks. It is called in an assert from all methods that perform
121 // updates on the set (and subclasses should also call it too).
122 virtual bool check_mt_safety() { return true; }
124 // fill_in_ext_msg() writes the the values of the set's attributes
125 // in the custom err_msg (hrs_ext_msg). fill_in_ext_msg_extra()
126 // allows subclasses to append further information.
127 virtual void fill_in_ext_msg_extra(hrs_ext_msg* msg) { }
128 void fill_in_ext_msg(hrs_ext_msg* msg, const char* message);
130 // It updates the fields of the set to reflect hr being added to
131 // the set.
132 inline void update_for_addition(HeapRegion* hr);
134 // It updates the fields of the set to reflect hr being added to
135 // the set and tags the region appropriately.
136 inline void add_internal(HeapRegion* hr);
138 // It updates the fields of the set to reflect hr being removed
139 // from the set.
140 inline void update_for_removal(HeapRegion* hr);
142 // It updates the fields of the set to reflect hr being removed
143 // from the set and tags the region appropriately.
144 inline void remove_internal(HeapRegion* hr);
146 // It clears all the fields of the sets. Note: it will not iterate
147 // over the set and remove regions from it. It assumes that the
148 // caller has already done so. It will literally just clear the fields.
149 virtual void clear();
151 HeapRegionSetBase(const char* name);
153 public:
154 static void set_unrealistically_long_length(uint len);
156 const char* name() { return _name; }
158 uint length() { return _length; }
160 bool is_empty() { return _length == 0; }
162 uint region_num() { return _region_num; }
164 size_t total_capacity_bytes() {
165 return (size_t) region_num() << HeapRegion::LogOfHRGrainBytes;
166 }
168 size_t total_used_bytes() { return _total_used_bytes; }
170 virtual void verify();
171 void verify_start();
172 void verify_next_region(HeapRegion* hr);
173 void verify_end();
175 #if HEAP_REGION_SET_FORCE_VERIFY
176 void verify_optional() {
177 verify();
178 }
179 #else // HEAP_REGION_SET_FORCE_VERIFY
180 void verify_optional() { }
181 #endif // HEAP_REGION_SET_FORCE_VERIFY
183 virtual void print_on(outputStream* out, bool print_contents = false);
184 };
186 // Customized err_msg for heap region sets. Apart from a
187 // assert/guarantee-specific message it also prints out the values of
188 // the fields of the associated set. This can be very helpful in
189 // diagnosing failures.
191 class hrs_ext_msg : public hrs_err_msg {
192 public:
193 hrs_ext_msg(HeapRegionSetBase* set, const char* message) : hrs_err_msg("") {
194 set->fill_in_ext_msg(this, message);
195 }
196 };
198 class HRSPhaseSetter {
199 public:
200 HRSPhaseSetter(HRSPhase phase) {
201 HeapRegionSetBase::set_phase(phase);
202 }
203 ~HRSPhaseSetter() {
204 HeapRegionSetBase::clear_phase();
205 }
206 };
208 // These two macros are provided for convenience, to keep the uses of
209 // these two asserts a bit more concise.
211 #define hrs_assert_mt_safety_ok(_set_) \
212 do { \
213 assert((_set_)->check_mt_safety(), hrs_ext_msg((_set_), "MT safety")); \
214 } while (0)
216 #define hrs_assert_region_ok(_set_, _hr_, _expected_) \
217 do { \
218 assert((_set_)->verify_region((_hr_), (_expected_)), \
219 hrs_ext_msg((_set_), "region verification")); \
220 } while (0)
222 //////////////////// HeapRegionSet ////////////////////
224 #define hrs_assert_sets_match(_set1_, _set2_) \
225 do { \
226 assert(((_set1_)->regions_humongous() == \
227 (_set2_)->regions_humongous()) && \
228 ((_set1_)->regions_empty() == (_set2_)->regions_empty()), \
229 hrs_err_msg("the contents of set %s and set %s should match", \
230 (_set1_)->name(), (_set2_)->name())); \
231 } while (0)
233 // This class represents heap region sets whose members are not
234 // explicitly tracked. It's helpful to group regions using such sets
235 // so that we can reason about all the region groups in the heap using
236 // the same interface (namely, the HeapRegionSetBase API).
238 class HeapRegionSet : public HeapRegionSetBase {
239 protected:
240 virtual const char* verify_region_extra(HeapRegion* hr) {
241 if (hr->next() != NULL) {
242 return "next() should always be NULL as we do not link the regions";
243 }
245 return HeapRegionSetBase::verify_region_extra(hr);
246 }
248 HeapRegionSet(const char* name) : HeapRegionSetBase(name) {
249 clear();
250 }
252 public:
253 // It adds hr to the set. The region should not be a member of
254 // another set.
255 inline void add(HeapRegion* hr);
257 // It removes hr from the set. The region should be a member of
258 // this set.
259 inline void remove(HeapRegion* hr);
261 // It removes a region from the set. Instead of updating the fields
262 // of the set to reflect this removal, it accumulates the updates
263 // in proxy_set. The idea is that proxy_set is thread-local to
264 // avoid multiple threads updating the fields of the set
265 // concurrently and having to synchronize. The method
266 // update_from_proxy() will update the fields of the set from the
267 // proxy_set.
268 inline void remove_with_proxy(HeapRegion* hr, HeapRegionSet* proxy_set);
270 // After multiple calls to remove_with_proxy() the updates to the
271 // fields of the set are accumulated in proxy_set. This call
272 // updates the fields of the set from proxy_set.
273 void update_from_proxy(HeapRegionSet* proxy_set);
274 };
276 //////////////////// HeapRegionLinkedList ////////////////////
278 // A set that links all the regions added to it in a singly-linked
279 // list. We should try to avoid doing operations that iterate over
280 // such lists in performance critical paths. Typically we should
281 // add / remove one region at a time or concatenate two lists. All
282 // those operations are done in constant time.
284 class HeapRegionLinkedListIterator;
286 class HeapRegionLinkedList : public HeapRegionSetBase {
287 friend class HeapRegionLinkedListIterator;
289 private:
290 HeapRegion* _head;
291 HeapRegion* _tail;
293 // These are provided for use by the friend classes.
294 HeapRegion* head() { return _head; }
295 HeapRegion* tail() { return _tail; }
297 protected:
298 virtual void fill_in_ext_msg_extra(hrs_ext_msg* msg);
300 // See the comment for HeapRegionSetBase::clear()
301 virtual void clear();
303 HeapRegionLinkedList(const char* name) : HeapRegionSetBase(name) {
304 clear();
305 }
307 public:
308 // It adds hr to the list as the new head. The region should not be
309 // a member of another set.
310 inline void add_as_head(HeapRegion* hr);
312 // It adds hr to the list as the new tail. The region should not be
313 // a member of another set.
314 inline void add_as_tail(HeapRegion* hr);
316 // It removes and returns the head of the list. It assumes that the
317 // list is not empty so it will return a non-NULL value.
318 inline HeapRegion* remove_head();
320 // Convenience method.
321 inline HeapRegion* remove_head_or_null();
323 // It moves the regions from from_list to this list and empties
324 // from_list. The new regions will appear in the same order as they
325 // were in from_list and be linked in the beginning of this list.
326 void add_as_head(HeapRegionLinkedList* from_list);
328 // It moves the regions from from_list to this list and empties
329 // from_list. The new regions will appear in the same order as they
330 // were in from_list and be linked in the end of this list.
331 void add_as_tail(HeapRegionLinkedList* from_list);
333 // It empties the list by removing all regions from it.
334 void remove_all();
336 // It removes all regions in the list that are pending for removal
337 // (i.e., they have been tagged with "pending_removal"). The list
338 // must not be empty, target_count should reflect the exact number
339 // of regions that are pending for removal in the list, and
340 // target_count should be > 1 (currently, we never need to remove a
341 // single region using this).
342 void remove_all_pending(uint target_count);
344 virtual void verify();
346 virtual void print_on(outputStream* out, bool print_contents = false);
347 };
349 //////////////////// HeapRegionLinkedListIterator ////////////////////
351 // Iterator class that provides a convenient way to iterate over the
352 // regions of a HeapRegionLinkedList instance.
354 class HeapRegionLinkedListIterator : public StackObj {
355 private:
356 HeapRegionLinkedList* _list;
357 HeapRegion* _curr;
359 public:
360 bool more_available() {
361 return _curr != NULL;
362 }
364 HeapRegion* get_next() {
365 assert(more_available(),
366 "get_next() should be called when more regions are available");
368 // If we are going to introduce a count in the iterator we should
369 // do the "cycle" check.
371 HeapRegion* hr = _curr;
372 assert(_list->verify_region(hr, _list), "region verification");
373 _curr = hr->next();
374 return hr;
375 }
377 HeapRegionLinkedListIterator(HeapRegionLinkedList* list)
378 : _curr(NULL), _list(list) {
379 _curr = list->head();
380 }
381 };
383 #endif // SHARE_VM_GC_IMPLEMENTATION_G1_HEAPREGIONSET_HPP