src/share/vm/gc_implementation/shared/spaceDecorator.cpp

Thu, 20 Sep 2012 09:52:56 -0700

author
johnc
date
Thu, 20 Sep 2012 09:52:56 -0700
changeset 4067
b2ef234911c9
parent 2314
f95d63e2154a
child 6680
78bbf4d43a14
permissions
-rw-r--r--

7190666: G1: assert(_unused == 0) failed: Inconsistency in PLAB stats
Summary: Reset the fields in ParGCAllocBuffer, that are used for accumulating values for the ResizePLAB sensors in PLABStats, to zero after flushing the values to the PLABStats fields. Flush PLABStats values only when retiring the final allocation buffers prior to disposing of a G1ParScanThreadState object, rather than when retiring every allocation buffer.
Reviewed-by: jwilhelm, jmasa, ysr

     1 /*
     2  * Copyright (c) 2002, 2010, 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 #include "precompiled.hpp"
    26 #include "gc_implementation/shared/spaceDecorator.hpp"
    27 #include "memory/space.inline.hpp"
    28 #include "utilities/copy.hpp"
    30 // Catch-all file for utility classes
    32 #ifndef PRODUCT
    34 // Returns true is the location q matches the mangling
    35 // pattern.
    36 bool SpaceMangler::is_mangled(HeapWord* q) {
    37   // This test loses precision but is good enough
    38   return badHeapWord == (max_juint & (uintptr_t) q->value());
    39 }
    42 void SpaceMangler::set_top_for_allocations(HeapWord* v)  {
    43   if (v < end()) {
    44     assert(!CheckZapUnusedHeapArea || is_mangled(v),
    45       "The high water mark is not mangled");
    46   }
    47   _top_for_allocations = v;
    48 }
    50 // Mangle only the unused space that has not previously
    51 // been mangled and that has not been allocated since being
    52 // mangled.
    53 void SpaceMangler::mangle_unused_area() {
    54   assert(ZapUnusedHeapArea, "Mangling should not be in use");
    55   // Mangle between top and the high water mark.  Safeguard
    56   // against the space changing since top_for_allocations was
    57   // set.
    58   HeapWord* mangled_end = MIN2(top_for_allocations(), end());
    59   if (top() < mangled_end) {
    60     MemRegion mangle_mr(top(), mangled_end);
    61     SpaceMangler::mangle_region(mangle_mr);
    62     // Light weight check of mangling.
    63     check_mangled_unused_area(end());
    64   }
    65   // Complete check of unused area which is functional when
    66   // DEBUG_MANGLING is defined.
    67   check_mangled_unused_area_complete();
    68 }
    70 // A complete mangle is expected in the
    71 // exceptional case where top_for_allocations is not
    72 // properly tracking the high water mark for mangling.
    73 // This can be the case when to-space is being used for
    74 // scratch space during a mark-sweep-compact.  See
    75 // contribute_scratch() and PSMarkSweep::allocate_stacks().
    76 void SpaceMangler::mangle_unused_area_complete() {
    77   assert(ZapUnusedHeapArea, "Mangling should not be in use");
    78   MemRegion mangle_mr(top(), end());
    79   SpaceMangler::mangle_region(mangle_mr);
    80 }
    82 // Simply mangle the MemRegion mr.
    83 void SpaceMangler::mangle_region(MemRegion mr) {
    84   assert(ZapUnusedHeapArea, "Mangling should not be in use");
    85 #ifdef ASSERT
    86   if(TraceZapUnusedHeapArea) {
    87     gclog_or_tty->print("Mangling [0x%x to 0x%x)", mr.start(), mr.end());
    88   }
    89   Copy::fill_to_words(mr.start(), mr.word_size(), badHeapWord);
    90   if(TraceZapUnusedHeapArea) {
    91     gclog_or_tty->print_cr(" done");
    92   }
    93 #endif
    94 }
    96 // Check that top, top_for_allocations and the last
    97 // word of the space are mangled.  In a tight memory
    98 // situation even this light weight mangling could
    99 // cause paging by touching the end of the space.
   100 void  SpaceMangler::check_mangled_unused_area(HeapWord* limit) {
   101   if (CheckZapUnusedHeapArea) {
   102     // This method can be called while the spaces are
   103     // being reshaped so skip the test if the end of the
   104     // space is beyond the specified limit;
   105     if (end() > limit) return;
   107     assert(top() == end() ||
   108            (is_mangled(top())), "Top not mangled");
   109     assert((top_for_allocations() < top()) ||
   110            (top_for_allocations() >= end()) ||
   111            (is_mangled(top_for_allocations())),
   112            "Older unused not mangled");
   113     assert(top() == end() ||
   114            (is_mangled(end() - 1)), "End not properly mangled");
   115     // Only does checking when DEBUG_MANGLING is defined.
   116     check_mangled_unused_area_complete();
   117   }
   118 }
   120 #undef DEBUG_MANGLING
   121 // This should only be used while debugging the mangling
   122 // because of the high cost of checking the completeness.
   123 void  SpaceMangler::check_mangled_unused_area_complete() {
   124   if (CheckZapUnusedHeapArea) {
   125     assert(ZapUnusedHeapArea, "Not mangling unused area");
   126 #ifdef DEBUG_MANGLING
   127     HeapWord* q = top();
   128     HeapWord* limit = end();
   130     bool passed = true;
   131     while (q < limit) {
   132       if (!is_mangled(q)) {
   133         passed = false;
   134         break;
   135       }
   136       q++;
   137     }
   138     assert(passed, "Mangling is not complete");
   139 #endif
   140   }
   141 }
   142 #undef DEBUG_MANGLING
   143 #endif // not PRODUCT

mercurial