src/share/vm/gc_implementation/g1/heapRegionSet.cpp

Sat, 06 Oct 2012 01:17:44 -0700

author
johnc
date
Sat, 06 Oct 2012 01:17:44 -0700
changeset 4173
8a5ea0a9ccc4
parent 3957
a2f7274eb6ef
child 6385
58fc1b1523dc
permissions
-rw-r--r--

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>

tonyp@2472 1 /*
tonyp@3713 2 * Copyright (c) 2011, 2012, Oracle and/or its affiliates. All rights reserved.
tonyp@2472 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
tonyp@2472 4 *
tonyp@2472 5 * This code is free software; you can redistribute it and/or modify it
tonyp@2472 6 * under the terms of the GNU General Public License version 2 only, as
tonyp@2472 7 * published by the Free Software Foundation.
tonyp@2472 8 *
tonyp@2472 9 * This code is distributed in the hope that it will be useful, but WITHOUT
tonyp@2472 10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
tonyp@2472 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
tonyp@2472 12 * version 2 for more details (a copy is included in the LICENSE file that
tonyp@2472 13 * accompanied this code).
tonyp@2472 14 *
tonyp@2472 15 * You should have received a copy of the GNU General Public License version
tonyp@2472 16 * 2 along with this work; if not, write to the Free Software Foundation,
tonyp@2472 17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
tonyp@2472 18 *
tonyp@2472 19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
tonyp@2472 20 * or visit www.oracle.com if you need additional information or have any
tonyp@2472 21 * questions.
tonyp@2472 22 *
tonyp@2472 23 */
tonyp@2472 24
tonyp@2472 25 #include "precompiled.hpp"
tonyp@2472 26 #include "gc_implementation/g1/heapRegionSet.inline.hpp"
tonyp@2472 27
tonyp@3713 28 uint HeapRegionSetBase::_unrealistically_long_length = 0;
tonyp@3268 29 HRSPhase HeapRegionSetBase::_phase = HRSPhaseNone;
tonyp@2472 30
tonyp@2472 31 //////////////////// HeapRegionSetBase ////////////////////
tonyp@2472 32
tonyp@3713 33 void HeapRegionSetBase::set_unrealistically_long_length(uint len) {
tonyp@2472 34 guarantee(_unrealistically_long_length == 0, "should only be set once");
tonyp@2472 35 _unrealistically_long_length = len;
tonyp@2472 36 }
tonyp@2472 37
tonyp@2643 38 void HeapRegionSetBase::fill_in_ext_msg(hrs_ext_msg* msg, const char* message) {
tonyp@3713 39 msg->append("[%s] %s ln: %u rn: %u cy: "SIZE_FORMAT" ud: "SIZE_FORMAT,
tonyp@2472 40 name(), message, length(), region_num(),
tonyp@2472 41 total_capacity_bytes(), total_used_bytes());
tonyp@2472 42 fill_in_ext_msg_extra(msg);
tonyp@2472 43 }
tonyp@2472 44
tonyp@2472 45 bool HeapRegionSetBase::verify_region(HeapRegion* hr,
tonyp@2472 46 HeapRegionSetBase* expected_containing_set) {
tonyp@2472 47 const char* error_message = NULL;
tonyp@2472 48
tonyp@2472 49 if (!regions_humongous()) {
tonyp@2472 50 if (hr->isHumongous()) {
tonyp@2472 51 error_message = "the region should not be humongous";
tonyp@2472 52 }
tonyp@2472 53 } else {
tonyp@2472 54 if (!hr->isHumongous() || !hr->startsHumongous()) {
tonyp@2472 55 error_message = "the region should be 'starts humongous'";
tonyp@2472 56 }
tonyp@2472 57 }
tonyp@2472 58
tonyp@2472 59 if (!regions_empty()) {
tonyp@2472 60 if (hr->is_empty()) {
tonyp@2472 61 error_message = "the region should not be empty";
tonyp@2472 62 }
tonyp@2472 63 } else {
tonyp@2472 64 if (!hr->is_empty()) {
tonyp@2472 65 error_message = "the region should be empty";
tonyp@2472 66 }
tonyp@2472 67 }
tonyp@2472 68
tonyp@2472 69 #ifdef ASSERT
tonyp@2472 70 // The _containing_set field is only available when ASSERT is defined.
tonyp@2472 71 if (hr->containing_set() != expected_containing_set) {
tonyp@2472 72 error_message = "inconsistent containing set found";
tonyp@2472 73 }
tonyp@2472 74 #endif // ASSERT
tonyp@2472 75
tonyp@2472 76 const char* extra_error_message = verify_region_extra(hr);
tonyp@2472 77 if (extra_error_message != NULL) {
tonyp@2472 78 error_message = extra_error_message;
tonyp@2472 79 }
tonyp@2472 80
tonyp@2472 81 if (error_message != NULL) {
tonyp@2472 82 outputStream* out = tty;
tonyp@2472 83 out->cr();
tonyp@2472 84 out->print_cr("## [%s] %s", name(), error_message);
tonyp@2472 85 out->print_cr("## Offending Region: "PTR_FORMAT, hr);
tonyp@2472 86 out->print_cr(" "HR_FORMAT, HR_FORMAT_PARAMS(hr));
tonyp@2472 87 #ifdef ASSERT
tonyp@2472 88 out->print_cr(" containing set: "PTR_FORMAT, hr->containing_set());
tonyp@2472 89 #endif // ASSERT
tonyp@2472 90 out->print_cr("## Offending Region Set: "PTR_FORMAT, this);
tonyp@2472 91 print_on(out);
tonyp@2472 92 return false;
tonyp@2472 93 } else {
tonyp@2472 94 return true;
tonyp@2472 95 }
tonyp@2472 96 }
tonyp@2472 97
tonyp@2472 98 void HeapRegionSetBase::verify() {
tonyp@2472 99 // It's important that we also observe the MT safety protocol even
tonyp@2472 100 // for the verification calls. If we do verification without the
tonyp@2472 101 // appropriate locks and the set changes underneath our feet
tonyp@2472 102 // verification might fail and send us on a wild goose chase.
tonyp@2643 103 hrs_assert_mt_safety_ok(this);
tonyp@2472 104
tonyp@2472 105 guarantee(( is_empty() && length() == 0 && region_num() == 0 &&
tonyp@2472 106 total_used_bytes() == 0 && total_capacity_bytes() == 0) ||
tonyp@2472 107 (!is_empty() && length() >= 0 && region_num() >= 0 &&
tonyp@2472 108 total_used_bytes() >= 0 && total_capacity_bytes() >= 0),
tonyp@2643 109 hrs_ext_msg(this, "invariant"));
tonyp@2472 110
tonyp@2472 111 guarantee((!regions_humongous() && region_num() == length()) ||
tonyp@2472 112 ( regions_humongous() && region_num() >= length()),
tonyp@2643 113 hrs_ext_msg(this, "invariant"));
tonyp@2472 114
tonyp@2472 115 guarantee(!regions_empty() || total_used_bytes() == 0,
tonyp@2643 116 hrs_ext_msg(this, "invariant"));
tonyp@2472 117
tonyp@2472 118 guarantee(total_used_bytes() <= total_capacity_bytes(),
tonyp@2643 119 hrs_ext_msg(this, "invariant"));
tonyp@2472 120 }
tonyp@2472 121
tonyp@2472 122 void HeapRegionSetBase::verify_start() {
tonyp@2472 123 // See comment in verify() about MT safety and verification.
tonyp@2643 124 hrs_assert_mt_safety_ok(this);
tonyp@2472 125 assert(!_verify_in_progress,
tonyp@2643 126 hrs_ext_msg(this, "verification should not be in progress"));
tonyp@2472 127
tonyp@2472 128 // Do the basic verification first before we do the checks over the regions.
tonyp@2472 129 HeapRegionSetBase::verify();
tonyp@2472 130
tonyp@2472 131 _calc_length = 0;
tonyp@2472 132 _calc_region_num = 0;
tonyp@2472 133 _calc_total_capacity_bytes = 0;
tonyp@2472 134 _calc_total_used_bytes = 0;
tonyp@2472 135 _verify_in_progress = true;
tonyp@2472 136 }
tonyp@2472 137
tonyp@2472 138 void HeapRegionSetBase::verify_next_region(HeapRegion* hr) {
tonyp@2472 139 // See comment in verify() about MT safety and verification.
tonyp@2643 140 hrs_assert_mt_safety_ok(this);
tonyp@2472 141 assert(_verify_in_progress,
tonyp@2643 142 hrs_ext_msg(this, "verification should be in progress"));
tonyp@2472 143
tonyp@2643 144 guarantee(verify_region(hr, this), hrs_ext_msg(this, "region verification"));
tonyp@2472 145
tonyp@2472 146 _calc_length += 1;
tonyp@3957 147 _calc_region_num += hr->region_num();
tonyp@2472 148 _calc_total_capacity_bytes += hr->capacity();
tonyp@2472 149 _calc_total_used_bytes += hr->used();
tonyp@2472 150 }
tonyp@2472 151
tonyp@2472 152 void HeapRegionSetBase::verify_end() {
tonyp@2472 153 // See comment in verify() about MT safety and verification.
tonyp@2643 154 hrs_assert_mt_safety_ok(this);
tonyp@2472 155 assert(_verify_in_progress,
tonyp@2643 156 hrs_ext_msg(this, "verification should be in progress"));
tonyp@2472 157
tonyp@2472 158 guarantee(length() == _calc_length,
tonyp@3713 159 hrs_err_msg("[%s] length: %u should be == calc length: %u",
tonyp@2472 160 name(), length(), _calc_length));
tonyp@2472 161
tonyp@2472 162 guarantee(region_num() == _calc_region_num,
tonyp@3713 163 hrs_err_msg("[%s] region num: %u should be == calc region num: %u",
tonyp@2472 164 name(), region_num(), _calc_region_num));
tonyp@2472 165
tonyp@2472 166 guarantee(total_capacity_bytes() == _calc_total_capacity_bytes,
tonyp@2643 167 hrs_err_msg("[%s] capacity bytes: "SIZE_FORMAT" should be == "
tonyp@2472 168 "calc capacity bytes: "SIZE_FORMAT,
tonyp@2472 169 name(),
tonyp@2472 170 total_capacity_bytes(), _calc_total_capacity_bytes));
tonyp@2472 171
tonyp@2472 172 guarantee(total_used_bytes() == _calc_total_used_bytes,
tonyp@2643 173 hrs_err_msg("[%s] used bytes: "SIZE_FORMAT" should be == "
tonyp@2472 174 "calc used bytes: "SIZE_FORMAT,
tonyp@2472 175 name(), total_used_bytes(), _calc_total_used_bytes));
tonyp@2472 176
tonyp@2472 177 _verify_in_progress = false;
tonyp@2472 178 }
tonyp@2472 179
tonyp@3268 180 void HeapRegionSetBase::clear_phase() {
tonyp@3268 181 assert(_phase != HRSPhaseNone, "pre-condition");
tonyp@3268 182 _phase = HRSPhaseNone;
tonyp@3268 183 }
tonyp@3268 184
tonyp@3268 185 void HeapRegionSetBase::set_phase(HRSPhase phase) {
tonyp@3268 186 assert(_phase == HRSPhaseNone, "pre-condition");
tonyp@3268 187 assert(phase != HRSPhaseNone, "pre-condition");
tonyp@3268 188 _phase = phase;
tonyp@3268 189 }
tonyp@3268 190
tonyp@2472 191 void HeapRegionSetBase::print_on(outputStream* out, bool print_contents) {
tonyp@2472 192 out->cr();
tonyp@2472 193 out->print_cr("Set: %s ("PTR_FORMAT")", name(), this);
tonyp@2472 194 out->print_cr(" Region Assumptions");
tonyp@2472 195 out->print_cr(" humongous : %s", BOOL_TO_STR(regions_humongous()));
tonyp@2472 196 out->print_cr(" empty : %s", BOOL_TO_STR(regions_empty()));
tonyp@2472 197 out->print_cr(" Attributes");
tonyp@3713 198 out->print_cr(" length : %14u", length());
tonyp@3713 199 out->print_cr(" region num : %14u", region_num());
tonyp@2472 200 out->print_cr(" total capacity : "SIZE_FORMAT_W(14)" bytes",
tonyp@2472 201 total_capacity_bytes());
tonyp@2472 202 out->print_cr(" total used : "SIZE_FORMAT_W(14)" bytes",
tonyp@2472 203 total_used_bytes());
tonyp@2472 204 }
tonyp@2472 205
tonyp@2472 206 void HeapRegionSetBase::clear() {
tonyp@2472 207 _length = 0;
tonyp@2472 208 _region_num = 0;
tonyp@2472 209 _total_used_bytes = 0;
tonyp@2472 210 }
tonyp@2472 211
tonyp@2472 212 HeapRegionSetBase::HeapRegionSetBase(const char* name)
tonyp@2472 213 : _name(name), _verify_in_progress(false),
tonyp@2472 214 _calc_length(0), _calc_region_num(0),
tonyp@2472 215 _calc_total_capacity_bytes(0), _calc_total_used_bytes(0) { }
tonyp@2472 216
tonyp@2472 217 //////////////////// HeapRegionSet ////////////////////
tonyp@2472 218
tonyp@2472 219 void HeapRegionSet::update_from_proxy(HeapRegionSet* proxy_set) {
tonyp@2643 220 hrs_assert_mt_safety_ok(this);
tonyp@2643 221 hrs_assert_mt_safety_ok(proxy_set);
tonyp@2643 222 hrs_assert_sets_match(this, proxy_set);
tonyp@2472 223
tonyp@2472 224 verify_optional();
tonyp@2472 225 proxy_set->verify_optional();
tonyp@2472 226
tonyp@2472 227 if (proxy_set->is_empty()) return;
tonyp@2472 228
tonyp@2472 229 assert(proxy_set->length() <= _length,
tonyp@3713 230 hrs_err_msg("[%s] proxy set length: %u should be <= length: %u",
tonyp@2472 231 name(), proxy_set->length(), _length));
tonyp@2472 232 _length -= proxy_set->length();
tonyp@2472 233
tonyp@2472 234 assert(proxy_set->region_num() <= _region_num,
tonyp@3713 235 hrs_err_msg("[%s] proxy set region num: %u should be <= region num: %u",
tonyp@2472 236 name(), proxy_set->region_num(), _region_num));
tonyp@2472 237 _region_num -= proxy_set->region_num();
tonyp@2472 238
tonyp@2472 239 assert(proxy_set->total_used_bytes() <= _total_used_bytes,
tonyp@2643 240 hrs_err_msg("[%s] proxy set used bytes: "SIZE_FORMAT" "
tonyp@2472 241 "should be <= used bytes: "SIZE_FORMAT,
tonyp@2472 242 name(), proxy_set->total_used_bytes(),
tonyp@2472 243 _total_used_bytes));
tonyp@2472 244 _total_used_bytes -= proxy_set->total_used_bytes();
tonyp@2472 245
tonyp@2472 246 proxy_set->clear();
tonyp@2472 247
tonyp@2472 248 verify_optional();
tonyp@2472 249 proxy_set->verify_optional();
tonyp@2472 250 }
tonyp@2472 251
tonyp@2472 252 //////////////////// HeapRegionLinkedList ////////////////////
tonyp@2472 253
tonyp@2643 254 void HeapRegionLinkedList::fill_in_ext_msg_extra(hrs_ext_msg* msg) {
tonyp@2472 255 msg->append(" hd: "PTR_FORMAT" tl: "PTR_FORMAT, head(), tail());
tonyp@2472 256 }
tonyp@2472 257
tonyp@2714 258 void HeapRegionLinkedList::add_as_head(HeapRegionLinkedList* from_list) {
tonyp@2714 259 hrs_assert_mt_safety_ok(this);
tonyp@2714 260 hrs_assert_mt_safety_ok(from_list);
tonyp@2714 261
tonyp@2714 262 verify_optional();
tonyp@2714 263 from_list->verify_optional();
tonyp@2714 264
tonyp@2714 265 if (from_list->is_empty()) return;
tonyp@2714 266
tonyp@2714 267 #ifdef ASSERT
tonyp@2714 268 HeapRegionLinkedListIterator iter(from_list);
tonyp@2714 269 while (iter.more_available()) {
tonyp@2714 270 HeapRegion* hr = iter.get_next();
tonyp@2714 271 // In set_containing_set() we check that we either set the value
tonyp@2714 272 // from NULL to non-NULL or vice versa to catch bugs. So, we have
tonyp@2714 273 // to NULL it first before setting it to the value.
tonyp@2714 274 hr->set_containing_set(NULL);
tonyp@2714 275 hr->set_containing_set(this);
tonyp@2714 276 }
tonyp@2714 277 #endif // ASSERT
tonyp@2714 278
tonyp@2714 279 if (_head != NULL) {
tonyp@2714 280 assert(length() > 0 && _tail != NULL, hrs_ext_msg(this, "invariant"));
tonyp@2714 281 from_list->_tail->set_next(_head);
tonyp@2714 282 } else {
johnc@3955 283 assert(length() == 0 && _tail == NULL, hrs_ext_msg(this, "invariant"));
tonyp@2714 284 _tail = from_list->_tail;
tonyp@2714 285 }
tonyp@2714 286 _head = from_list->_head;
tonyp@2714 287
tonyp@2714 288 _length += from_list->length();
tonyp@2714 289 _region_num += from_list->region_num();
tonyp@2714 290 _total_used_bytes += from_list->total_used_bytes();
tonyp@2714 291 from_list->clear();
tonyp@2714 292
tonyp@2714 293 verify_optional();
tonyp@2714 294 from_list->verify_optional();
tonyp@2714 295 }
tonyp@2714 296
tonyp@2472 297 void HeapRegionLinkedList::add_as_tail(HeapRegionLinkedList* from_list) {
tonyp@2643 298 hrs_assert_mt_safety_ok(this);
tonyp@2643 299 hrs_assert_mt_safety_ok(from_list);
tonyp@2472 300
tonyp@2472 301 verify_optional();
tonyp@2472 302 from_list->verify_optional();
tonyp@2472 303
tonyp@2472 304 if (from_list->is_empty()) return;
tonyp@2472 305
tonyp@2472 306 #ifdef ASSERT
tonyp@2472 307 HeapRegionLinkedListIterator iter(from_list);
tonyp@2472 308 while (iter.more_available()) {
tonyp@2472 309 HeapRegion* hr = iter.get_next();
tonyp@2472 310 // In set_containing_set() we check that we either set the value
tonyp@2472 311 // from NULL to non-NULL or vice versa to catch bugs. So, we have
tonyp@2472 312 // to NULL it first before setting it to the value.
tonyp@2472 313 hr->set_containing_set(NULL);
tonyp@2472 314 hr->set_containing_set(this);
tonyp@2472 315 }
tonyp@2472 316 #endif // ASSERT
tonyp@2472 317
tonyp@2472 318 if (_tail != NULL) {
tonyp@2643 319 assert(length() > 0 && _head != NULL, hrs_ext_msg(this, "invariant"));
tonyp@2472 320 _tail->set_next(from_list->_head);
tonyp@2472 321 } else {
tonyp@2643 322 assert(length() == 0 && _head == NULL, hrs_ext_msg(this, "invariant"));
tonyp@2472 323 _head = from_list->_head;
tonyp@2472 324 }
tonyp@2472 325 _tail = from_list->_tail;
tonyp@2472 326
tonyp@2472 327 _length += from_list->length();
tonyp@2472 328 _region_num += from_list->region_num();
tonyp@2472 329 _total_used_bytes += from_list->total_used_bytes();
tonyp@2472 330 from_list->clear();
tonyp@2472 331
tonyp@2472 332 verify_optional();
tonyp@2472 333 from_list->verify_optional();
tonyp@2472 334 }
tonyp@2472 335
tonyp@2472 336 void HeapRegionLinkedList::remove_all() {
tonyp@2643 337 hrs_assert_mt_safety_ok(this);
tonyp@2472 338 verify_optional();
tonyp@2472 339
tonyp@2472 340 HeapRegion* curr = _head;
tonyp@2472 341 while (curr != NULL) {
tonyp@2643 342 hrs_assert_region_ok(this, curr, this);
tonyp@2472 343
tonyp@2472 344 HeapRegion* next = curr->next();
tonyp@2472 345 curr->set_next(NULL);
tonyp@2472 346 curr->set_containing_set(NULL);
tonyp@2472 347 curr = next;
tonyp@2472 348 }
tonyp@2472 349 clear();
tonyp@2472 350
tonyp@2472 351 verify_optional();
tonyp@2472 352 }
tonyp@2472 353
tonyp@3713 354 void HeapRegionLinkedList::remove_all_pending(uint target_count) {
tonyp@2643 355 hrs_assert_mt_safety_ok(this);
tonyp@2643 356 assert(target_count > 1, hrs_ext_msg(this, "pre-condition"));
tonyp@2643 357 assert(!is_empty(), hrs_ext_msg(this, "pre-condition"));
tonyp@2472 358
tonyp@2472 359 verify_optional();
tonyp@3713 360 DEBUG_ONLY(uint old_length = length();)
tonyp@2472 361
tonyp@2472 362 HeapRegion* curr = _head;
tonyp@2472 363 HeapRegion* prev = NULL;
tonyp@3713 364 uint count = 0;
tonyp@2472 365 while (curr != NULL) {
tonyp@2643 366 hrs_assert_region_ok(this, curr, this);
tonyp@2472 367 HeapRegion* next = curr->next();
tonyp@2472 368
tonyp@2472 369 if (curr->pending_removal()) {
tonyp@2472 370 assert(count < target_count,
tonyp@2643 371 hrs_err_msg("[%s] should not come across more regions "
tonyp@3713 372 "pending for removal than target_count: %u",
tonyp@2472 373 name(), target_count));
tonyp@2472 374
tonyp@2472 375 if (prev == NULL) {
tonyp@2643 376 assert(_head == curr, hrs_ext_msg(this, "invariant"));
tonyp@2472 377 _head = next;
tonyp@2472 378 } else {
tonyp@2643 379 assert(_head != curr, hrs_ext_msg(this, "invariant"));
tonyp@2472 380 prev->set_next(next);
tonyp@2472 381 }
tonyp@2472 382 if (next == NULL) {
tonyp@2643 383 assert(_tail == curr, hrs_ext_msg(this, "invariant"));
tonyp@2472 384 _tail = prev;
tonyp@2472 385 } else {
tonyp@2643 386 assert(_tail != curr, hrs_ext_msg(this, "invariant"));
tonyp@2472 387 }
tonyp@2472 388
tonyp@2472 389 curr->set_next(NULL);
tonyp@2472 390 remove_internal(curr);
tonyp@2472 391 curr->set_pending_removal(false);
tonyp@2472 392
tonyp@2472 393 count += 1;
tonyp@2472 394
tonyp@2472 395 // If we have come across the target number of regions we can
tonyp@2472 396 // just bail out. However, for debugging purposes, we can just
tonyp@2472 397 // carry on iterating to make sure there are not more regions
tonyp@2472 398 // tagged with pending removal.
tonyp@2472 399 DEBUG_ONLY(if (count == target_count) break;)
tonyp@2472 400 } else {
tonyp@2472 401 prev = curr;
tonyp@2472 402 }
tonyp@2472 403 curr = next;
tonyp@2472 404 }
tonyp@2472 405
tonyp@2472 406 assert(count == target_count,
tonyp@3713 407 hrs_err_msg("[%s] count: %u should be == target_count: %u",
tonyp@3713 408 name(), count, target_count));
tonyp@2472 409 assert(length() + target_count == old_length,
tonyp@2643 410 hrs_err_msg("[%s] new length should be consistent "
tonyp@3713 411 "new length: %u old length: %u target_count: %u",
tonyp@2472 412 name(), length(), old_length, target_count));
tonyp@2472 413
tonyp@2472 414 verify_optional();
tonyp@2472 415 }
tonyp@2472 416
tonyp@2472 417 void HeapRegionLinkedList::verify() {
tonyp@2472 418 // See comment in HeapRegionSetBase::verify() about MT safety and
tonyp@2472 419 // verification.
tonyp@2643 420 hrs_assert_mt_safety_ok(this);
tonyp@2472 421
tonyp@2472 422 // This will also do the basic verification too.
tonyp@2472 423 verify_start();
tonyp@2472 424
tonyp@2472 425 HeapRegion* curr = _head;
tonyp@2472 426 HeapRegion* prev1 = NULL;
tonyp@2472 427 HeapRegion* prev0 = NULL;
tonyp@3713 428 uint count = 0;
tonyp@2472 429 while (curr != NULL) {
tonyp@2472 430 verify_next_region(curr);
tonyp@2472 431
tonyp@2472 432 count += 1;
tonyp@2472 433 guarantee(count < _unrealistically_long_length,
tonyp@3713 434 hrs_err_msg("[%s] the calculated length: %u "
tonyp@2472 435 "seems very long, is there maybe a cycle? "
tonyp@2472 436 "curr: "PTR_FORMAT" prev0: "PTR_FORMAT" "
tonyp@3713 437 "prev1: "PTR_FORMAT" length: %u",
tonyp@2472 438 name(), count, curr, prev0, prev1, length()));
tonyp@2472 439
tonyp@2472 440 prev1 = prev0;
tonyp@2472 441 prev0 = curr;
tonyp@2472 442 curr = curr->next();
tonyp@2472 443 }
tonyp@2472 444
tonyp@2643 445 guarantee(_tail == prev0, hrs_ext_msg(this, "post-condition"));
tonyp@2472 446
tonyp@2472 447 verify_end();
tonyp@2472 448 }
tonyp@2472 449
tonyp@2472 450 void HeapRegionLinkedList::clear() {
tonyp@2472 451 HeapRegionSetBase::clear();
tonyp@2472 452 _head = NULL;
tonyp@2472 453 _tail = NULL;
tonyp@2472 454 }
tonyp@2472 455
tonyp@2472 456 void HeapRegionLinkedList::print_on(outputStream* out, bool print_contents) {
tonyp@2472 457 HeapRegionSetBase::print_on(out, print_contents);
tonyp@2472 458 out->print_cr(" Linking");
tonyp@2472 459 out->print_cr(" head : "PTR_FORMAT, _head);
tonyp@2472 460 out->print_cr(" tail : "PTR_FORMAT, _tail);
tonyp@2472 461
tonyp@2472 462 if (print_contents) {
tonyp@2472 463 out->print_cr(" Contents");
tonyp@2472 464 HeapRegionLinkedListIterator iter(this);
tonyp@2472 465 while (iter.more_available()) {
tonyp@2472 466 HeapRegion* hr = iter.get_next();
tonyp@2472 467 hr->print_on(out);
tonyp@2472 468 }
tonyp@2472 469 }
tonyp@2472 470 }

mercurial