src/share/vm/gc_implementation/g1/concurrentMark.inline.hpp

changeset 7834
399885e13e90
parent 7830
b7c8142a9e0b
child 7994
04ff2f6cd0eb
child 9327
f96fcd9e1e1b
     1.1 --- a/src/share/vm/gc_implementation/g1/concurrentMark.inline.hpp	Wed Apr 22 14:06:49 2015 -0400
     1.2 +++ b/src/share/vm/gc_implementation/g1/concurrentMark.inline.hpp	Fri May 01 17:38:12 2015 -0400
     1.3 @@ -259,15 +259,15 @@
     1.4               ++_local_pushes );
     1.5  }
     1.6  
     1.7 -inline bool CMTask::is_below_finger(HeapWord* objAddr,
     1.8 -                                    HeapWord* global_finger) const {
     1.9 -  // If objAddr is above the global finger, then the mark bitmap scan
    1.10 +inline bool CMTask::is_below_finger(oop obj, HeapWord* global_finger) const {
    1.11 +  // If obj is above the global finger, then the mark bitmap scan
    1.12    // will find it later, and no push is needed.  Similarly, if we have
    1.13 -  // a current region and objAddr is between the local finger and the
    1.14 +  // a current region and obj is between the local finger and the
    1.15    // end of the current region, then no push is needed.  The tradeoff
    1.16    // of checking both vs only checking the global finger is that the
    1.17    // local check will be more accurate and so result in fewer pushes,
    1.18    // but may also be a little slower.
    1.19 +  HeapWord* objAddr = (HeapWord*)obj;
    1.20    if (_finger != NULL) {
    1.21      // We have a current region.
    1.22  
    1.23 @@ -277,7 +277,7 @@
    1.24      assert(_region_limit != NULL, "invariant");
    1.25      assert(_region_limit <= global_finger, "invariant");
    1.26  
    1.27 -    // True if objAddr is less than the local finger, or is between
    1.28 +    // True if obj is less than the local finger, or is between
    1.29      // the region limit and the global finger.
    1.30      if (objAddr < _finger) {
    1.31        return true;
    1.32 @@ -289,13 +289,65 @@
    1.33    return objAddr < global_finger;
    1.34  }
    1.35  
    1.36 +inline void CMTask::make_reference_grey(oop obj, HeapRegion* hr) {
    1.37 +  if (_cm->par_mark_and_count(obj, hr, _marked_bytes_array, _card_bm)) {
    1.38 +
    1.39 +    if (_cm->verbose_high()) {
    1.40 +      gclog_or_tty->print_cr("[%u] marked object " PTR_FORMAT,
    1.41 +                             _worker_id, p2i(obj));
    1.42 +    }
    1.43 +
    1.44 +    // No OrderAccess:store_load() is needed. It is implicit in the
    1.45 +    // CAS done in CMBitMap::parMark() call in the routine above.
    1.46 +    HeapWord* global_finger = _cm->finger();
    1.47 +
    1.48 +    // We only need to push a newly grey object on the mark
    1.49 +    // stack if it is in a section of memory the mark bitmap
    1.50 +    // scan has already examined.  Mark bitmap scanning
    1.51 +    // maintains progress "fingers" for determining that.
    1.52 +    //
    1.53 +    // Notice that the global finger might be moving forward
    1.54 +    // concurrently. This is not a problem. In the worst case, we
    1.55 +    // mark the object while it is above the global finger and, by
    1.56 +    // the time we read the global finger, it has moved forward
    1.57 +    // past this object. In this case, the object will probably
    1.58 +    // be visited when a task is scanning the region and will also
    1.59 +    // be pushed on the stack. So, some duplicate work, but no
    1.60 +    // correctness problems.
    1.61 +    if (is_below_finger(obj, global_finger)) {
    1.62 +      if (obj->is_typeArray()) {
    1.63 +        // Immediately process arrays of primitive types, rather
    1.64 +        // than pushing on the mark stack.  This keeps us from
    1.65 +        // adding humongous objects to the mark stack that might
    1.66 +        // be reclaimed before the entry is processed - see
    1.67 +        // selection of candidates for eager reclaim of humongous
    1.68 +        // objects.  The cost of the additional type test is
    1.69 +        // mitigated by avoiding a trip through the mark stack,
    1.70 +        // by only doing a bookkeeping update and avoiding the
    1.71 +        // actual scan of the object - a typeArray contains no
    1.72 +        // references, and the metadata is built-in.
    1.73 +        process_grey_object<false>(obj);
    1.74 +      } else {
    1.75 +        if (_cm->verbose_high()) {
    1.76 +          gclog_or_tty->print_cr("[%u] below a finger (local: " PTR_FORMAT
    1.77 +                                 ", global: " PTR_FORMAT ") pushing "
    1.78 +                                 PTR_FORMAT " on mark stack",
    1.79 +                                 _worker_id, p2i(_finger),
    1.80 +                                 p2i(global_finger), p2i(obj));
    1.81 +        }
    1.82 +        push(obj);
    1.83 +      }
    1.84 +    }
    1.85 +  }
    1.86 +}
    1.87 +
    1.88  inline void CMTask::deal_with_reference(oop obj) {
    1.89    if (_cm->verbose_high()) {
    1.90      gclog_or_tty->print_cr("[%u] we're dealing with reference = "PTR_FORMAT,
    1.91                             _worker_id, p2i((void*) obj));
    1.92    }
    1.93  
    1.94 -  ++_refs_reached;
    1.95 +  increment_refs_reached();
    1.96  
    1.97    HeapWord* objAddr = (HeapWord*) obj;
    1.98    assert(obj->is_oop_or_null(true /* ignore mark word */), "Error");
    1.99 @@ -307,55 +359,7 @@
   1.100        // anything with it).
   1.101        HeapRegion* hr = _g1h->heap_region_containing_raw(obj);
   1.102        if (!hr->obj_allocated_since_next_marking(obj)) {
   1.103 -        if (_cm->verbose_high()) {
   1.104 -          gclog_or_tty->print_cr("[%u] "PTR_FORMAT" is not considered marked",
   1.105 -                                 _worker_id, p2i((void*) obj));
   1.106 -        }
   1.107 -
   1.108 -        // we need to mark it first
   1.109 -        if (_cm->par_mark_and_count(obj, hr, _marked_bytes_array, _card_bm)) {
   1.110 -          // No OrderAccess:store_load() is needed. It is implicit in the
   1.111 -          // CAS done in CMBitMap::parMark() call in the routine above.
   1.112 -          HeapWord* global_finger = _cm->finger();
   1.113 -
   1.114 -          // We only need to push a newly grey object on the mark
   1.115 -          // stack if it is in a section of memory the mark bitmap
   1.116 -          // scan has already examined.  Mark bitmap scanning
   1.117 -          // maintains progress "fingers" for determining that.
   1.118 -          //
   1.119 -          // Notice that the global finger might be moving forward
   1.120 -          // concurrently. This is not a problem. In the worst case, we
   1.121 -          // mark the object while it is above the global finger and, by
   1.122 -          // the time we read the global finger, it has moved forward
   1.123 -          // past this object. In this case, the object will probably
   1.124 -          // be visited when a task is scanning the region and will also
   1.125 -          // be pushed on the stack. So, some duplicate work, but no
   1.126 -          // correctness problems.
   1.127 -          if (is_below_finger(objAddr, global_finger)) {
   1.128 -            if (obj->is_typeArray()) {
   1.129 -              // Immediately process arrays of primitive types, rather
   1.130 -              // than pushing on the mark stack.  This keeps us from
   1.131 -              // adding humongous objects to the mark stack that might
   1.132 -              // be reclaimed before the entry is processed - see
   1.133 -              // selection of candidates for eager reclaim of humongous
   1.134 -              // objects.  The cost of the additional type test is
   1.135 -              // mitigated by avoiding a trip through the mark stack,
   1.136 -              // by only doing a bookkeeping update and avoiding the
   1.137 -              // actual scan of the object - a typeArray contains no
   1.138 -              // references, and the metadata is built-in.
   1.139 -              process_grey_object<false>(obj);
   1.140 -            } else {
   1.141 -              if (_cm->verbose_high()) {
   1.142 -                gclog_or_tty->print_cr("[%u] below a finger (local: " PTR_FORMAT
   1.143 -                                       ", global: " PTR_FORMAT ") pushing "
   1.144 -                                       PTR_FORMAT " on mark stack",
   1.145 -                                       _worker_id, p2i(_finger),
   1.146 -                                       p2i(global_finger), p2i(objAddr));
   1.147 -              }
   1.148 -              push(obj);
   1.149 -            }
   1.150 -          }
   1.151 -        }
   1.152 +        make_reference_grey(obj, hr);
   1.153        }
   1.154      }
   1.155    }

mercurial