522 int worker_i) : |
518 int worker_i) : |
523 _g1(g1h), _g1_rem_set(rs), _from(NULL), |
519 _g1(g1h), _g1_rem_set(rs), _from(NULL), |
524 _record_refs_into_cset(record_refs_into_cset), |
520 _record_refs_into_cset(record_refs_into_cset), |
525 _push_ref_cl(push_ref_cl), _worker_i(worker_i) { } |
521 _push_ref_cl(push_ref_cl), _worker_i(worker_i) { } |
526 |
522 |
527 bool G1RemSet::concurrentRefineOneCard_impl(jbyte* card_ptr, int worker_i, |
523 // Returns true if the given card contains references that point |
528 bool check_for_refs_into_cset) { |
524 // into the collection set, if we're checking for such references; |
|
525 // false otherwise. |
|
526 |
|
527 bool G1RemSet::refine_card(jbyte* card_ptr, int worker_i, |
|
528 bool check_for_refs_into_cset) { |
|
529 |
|
530 // If the card is no longer dirty, nothing to do. |
|
531 if (*card_ptr != CardTableModRefBS::dirty_card_val()) { |
|
532 // No need to return that this card contains refs that point |
|
533 // into the collection set. |
|
534 return false; |
|
535 } |
|
536 |
529 // Construct the region representing the card. |
537 // Construct the region representing the card. |
530 HeapWord* start = _ct_bs->addr_for(card_ptr); |
538 HeapWord* start = _ct_bs->addr_for(card_ptr); |
531 // And find the region containing it. |
539 // And find the region containing it. |
532 HeapRegion* r = _g1->heap_region_containing(start); |
540 HeapRegion* r = _g1->heap_region_containing(start); |
533 assert(r != NULL, "unexpected null"); |
541 if (r == NULL) { |
|
542 // Again no need to return that this card contains refs that |
|
543 // point into the collection set. |
|
544 return false; // Not in the G1 heap (might be in perm, for example.) |
|
545 } |
|
546 |
|
547 // Why do we have to check here whether a card is on a young region, |
|
548 // given that we dirty young regions and, as a result, the |
|
549 // post-barrier is supposed to filter them out and never to enqueue |
|
550 // them? When we allocate a new region as the "allocation region" we |
|
551 // actually dirty its cards after we release the lock, since card |
|
552 // dirtying while holding the lock was a performance bottleneck. So, |
|
553 // as a result, it is possible for other threads to actually |
|
554 // allocate objects in the region (after the acquire the lock) |
|
555 // before all the cards on the region are dirtied. This is unlikely, |
|
556 // and it doesn't happen often, but it can happen. So, the extra |
|
557 // check below filters out those cards. |
|
558 if (r->is_young()) { |
|
559 return false; |
|
560 } |
|
561 |
|
562 // While we are processing RSet buffers during the collection, we |
|
563 // actually don't want to scan any cards on the collection set, |
|
564 // since we don't want to update remebered sets with entries that |
|
565 // point into the collection set, given that live objects from the |
|
566 // collection set are about to move and such entries will be stale |
|
567 // very soon. This change also deals with a reliability issue which |
|
568 // involves scanning a card in the collection set and coming across |
|
569 // an array that was being chunked and looking malformed. Note, |
|
570 // however, that if evacuation fails, we have to scan any objects |
|
571 // that were not moved and create any missing entries. |
|
572 if (r->in_collection_set()) { |
|
573 return false; |
|
574 } |
|
575 |
|
576 // The result from the hot card cache insert call is either: |
|
577 // * pointer to the current card |
|
578 // (implying that the current card is not 'hot'), |
|
579 // * null |
|
580 // (meaning we had inserted the card ptr into the "hot" card cache, |
|
581 // which had some headroom), |
|
582 // * a pointer to a "hot" card that was evicted from the "hot" cache. |
|
583 // |
|
584 |
|
585 G1HotCardCache* hot_card_cache = _cg1r->hot_card_cache(); |
|
586 if (hot_card_cache->use_cache()) { |
|
587 assert(!check_for_refs_into_cset, "sanity"); |
|
588 assert(!SafepointSynchronize::is_at_safepoint(), "sanity"); |
|
589 |
|
590 card_ptr = hot_card_cache->insert(card_ptr); |
|
591 if (card_ptr == NULL) { |
|
592 // There was no eviction. Nothing to do. |
|
593 return false; |
|
594 } |
|
595 |
|
596 start = _ct_bs->addr_for(card_ptr); |
|
597 r = _g1->heap_region_containing(start); |
|
598 if (r == NULL) { |
|
599 // Not in the G1 heap |
|
600 return false; |
|
601 } |
|
602 |
|
603 // Checking whether the region we got back from the cache |
|
604 // is young here is inappropriate. The region could have been |
|
605 // freed, reallocated and tagged as young while in the cache. |
|
606 // Hence we could see its young type change at any time. |
|
607 } |
534 |
608 |
535 // Don't use addr_for(card_ptr + 1) which can ask for |
609 // Don't use addr_for(card_ptr + 1) which can ask for |
536 // a card beyond the heap. This is not safe without a perm |
610 // a card beyond the heap. This is not safe without a perm |
537 // gen at the upper end of the heap. |
611 // gen at the upper end of the heap. |
538 HeapWord* end = start + CardTableModRefBS::card_size_in_words; |
612 HeapWord* end = start + CardTableModRefBS::card_size_in_words; |
608 } |
682 } |
609 } else { |
683 } else { |
610 _conc_refine_cards++; |
684 _conc_refine_cards++; |
611 } |
685 } |
612 |
686 |
613 return trigger_cl.triggered(); |
687 // This gets set to true if the card being refined has |
614 } |
688 // references that point into the collection set. |
615 |
689 bool has_refs_into_cset = trigger_cl.triggered(); |
616 bool G1RemSet::concurrentRefineOneCard(jbyte* card_ptr, int worker_i, |
690 |
617 bool check_for_refs_into_cset) { |
691 // We should only be detecting that the card contains references |
618 // If the card is no longer dirty, nothing to do. |
692 // that point into the collection set if the current thread is |
619 if (*card_ptr != CardTableModRefBS::dirty_card_val()) { |
693 // a GC worker thread. |
620 // No need to return that this card contains refs that point |
694 assert(!has_refs_into_cset || SafepointSynchronize::is_at_safepoint(), |
621 // into the collection set. |
|
622 return false; |
|
623 } |
|
624 |
|
625 // Construct the region representing the card. |
|
626 HeapWord* start = _ct_bs->addr_for(card_ptr); |
|
627 // And find the region containing it. |
|
628 HeapRegion* r = _g1->heap_region_containing(start); |
|
629 if (r == NULL) { |
|
630 // Again no need to return that this card contains refs that |
|
631 // point into the collection set. |
|
632 return false; // Not in the G1 heap (might be in perm, for example.) |
|
633 } |
|
634 // Why do we have to check here whether a card is on a young region, |
|
635 // given that we dirty young regions and, as a result, the |
|
636 // post-barrier is supposed to filter them out and never to enqueue |
|
637 // them? When we allocate a new region as the "allocation region" we |
|
638 // actually dirty its cards after we release the lock, since card |
|
639 // dirtying while holding the lock was a performance bottleneck. So, |
|
640 // as a result, it is possible for other threads to actually |
|
641 // allocate objects in the region (after the acquire the lock) |
|
642 // before all the cards on the region are dirtied. This is unlikely, |
|
643 // and it doesn't happen often, but it can happen. So, the extra |
|
644 // check below filters out those cards. |
|
645 if (r->is_young()) { |
|
646 return false; |
|
647 } |
|
648 // While we are processing RSet buffers during the collection, we |
|
649 // actually don't want to scan any cards on the collection set, |
|
650 // since we don't want to update remebered sets with entries that |
|
651 // point into the collection set, given that live objects from the |
|
652 // collection set are about to move and such entries will be stale |
|
653 // very soon. This change also deals with a reliability issue which |
|
654 // involves scanning a card in the collection set and coming across |
|
655 // an array that was being chunked and looking malformed. Note, |
|
656 // however, that if evacuation fails, we have to scan any objects |
|
657 // that were not moved and create any missing entries. |
|
658 if (r->in_collection_set()) { |
|
659 return false; |
|
660 } |
|
661 |
|
662 // Should we defer processing the card? |
|
663 // |
|
664 // Previously the result from the insert_cache call would be |
|
665 // either card_ptr (implying that card_ptr was currently "cold"), |
|
666 // null (meaning we had inserted the card ptr into the "hot" |
|
667 // cache, which had some headroom), or a "hot" card ptr |
|
668 // extracted from the "hot" cache. |
|
669 // |
|
670 // Now that the _card_counts cache in the ConcurrentG1Refine |
|
671 // instance is an evicting hash table, the result we get back |
|
672 // could be from evicting the card ptr in an already occupied |
|
673 // bucket (in which case we have replaced the card ptr in the |
|
674 // bucket with card_ptr and "defer" is set to false). To avoid |
|
675 // having a data structure (updates to which would need a lock) |
|
676 // to hold these unprocessed dirty cards, we need to immediately |
|
677 // process card_ptr. The actions needed to be taken on return |
|
678 // from cache_insert are summarized in the following table: |
|
679 // |
|
680 // res defer action |
|
681 // -------------------------------------------------------------- |
|
682 // null false card evicted from _card_counts & replaced with |
|
683 // card_ptr; evicted ptr added to hot cache. |
|
684 // No need to process res; immediately process card_ptr |
|
685 // |
|
686 // null true card not evicted from _card_counts; card_ptr added |
|
687 // to hot cache. |
|
688 // Nothing to do. |
|
689 // |
|
690 // non-null false card evicted from _card_counts & replaced with |
|
691 // card_ptr; evicted ptr is currently "cold" or |
|
692 // caused an eviction from the hot cache. |
|
693 // Immediately process res; process card_ptr. |
|
694 // |
|
695 // non-null true card not evicted from _card_counts; card_ptr is |
|
696 // currently cold, or caused an eviction from hot |
|
697 // cache. |
|
698 // Immediately process res; no need to process card_ptr. |
|
699 |
|
700 |
|
701 jbyte* res = card_ptr; |
|
702 bool defer = false; |
|
703 |
|
704 // This gets set to true if the card being refined has references |
|
705 // that point into the collection set. |
|
706 bool oops_into_cset = false; |
|
707 |
|
708 if (_cg1r->use_cache()) { |
|
709 jbyte* res = _cg1r->cache_insert(card_ptr, &defer); |
|
710 if (res != NULL && (res != card_ptr || defer)) { |
|
711 start = _ct_bs->addr_for(res); |
|
712 r = _g1->heap_region_containing(start); |
|
713 if (r != NULL) { |
|
714 // Checking whether the region we got back from the cache |
|
715 // is young here is inappropriate. The region could have been |
|
716 // freed, reallocated and tagged as young while in the cache. |
|
717 // Hence we could see its young type change at any time. |
|
718 // |
|
719 // Process card pointer we get back from the hot card cache. This |
|
720 // will check whether the region containing the card is young |
|
721 // _after_ checking that the region has been allocated from. |
|
722 oops_into_cset = concurrentRefineOneCard_impl(res, worker_i, |
|
723 false /* check_for_refs_into_cset */); |
|
724 // The above call to concurrentRefineOneCard_impl is only |
|
725 // performed if the hot card cache is enabled. This cache is |
|
726 // disabled during an evacuation pause - which is the only |
|
727 // time when we need know if the card contains references |
|
728 // that point into the collection set. Also when the hot card |
|
729 // cache is enabled, this code is executed by the concurrent |
|
730 // refine threads - rather than the GC worker threads - and |
|
731 // concurrentRefineOneCard_impl will return false. |
|
732 assert(!oops_into_cset, "should not see true here"); |
|
733 } |
|
734 } |
|
735 } |
|
736 |
|
737 if (!defer) { |
|
738 oops_into_cset = |
|
739 concurrentRefineOneCard_impl(card_ptr, worker_i, check_for_refs_into_cset); |
|
740 // We should only be detecting that the card contains references |
|
741 // that point into the collection set if the current thread is |
|
742 // a GC worker thread. |
|
743 assert(!oops_into_cset || SafepointSynchronize::is_at_safepoint(), |
|
744 "invalid result at non safepoint"); |
695 "invalid result at non safepoint"); |
745 } |
696 |
746 return oops_into_cset; |
697 return has_refs_into_cset; |
747 } |
698 } |
748 |
699 |
749 class HRRSStatsIter: public HeapRegionClosure { |
700 class HRRSStatsIter: public HeapRegionClosure { |
750 size_t _occupied; |
701 size_t _occupied; |
751 size_t _total_mem_sz; |
702 size_t _total_mem_sz; |