1 /*
2 * Copyright Amazon.com Inc. 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 */
24
25 #ifndef SHARE_GC_SHENANDOAH_SHENANDOAHCARDSTATS_HPP
26 #define SHARE_GC_SHENANDOAH_SHENANDOAHCARDSTATS_HPP
27
28 #include "gc/shared/gc_globals.hpp"
29 #include "gc/shenandoah/shenandoahNumberSeq.hpp"
30
31 enum CardStatType {
32 DIRTY_RUN,
33 CLEAN_RUN,
34 DIRTY_CARDS,
35 CLEAN_CARDS,
36 MAX_DIRTY_RUN,
37 MAX_CLEAN_RUN,
38 DIRTY_SCAN_OBJS,
39 ALTERNATIONS,
40 MAX_CARD_STAT_TYPE
41 };
42
43 enum CardStatLogType {
44 CARD_STAT_SCAN_RS,
45 CARD_STAT_UPDATE_REFS,
46 MAX_CARD_STAT_LOG_TYPE
47 };
48
49 class ShenandoahCardStats: public CHeapObj<mtGC> {
50 private:
51 size_t _cards_in_cluster;
52 HdrSeq* _local_card_stats;
53
54 size_t _dirty_card_cnt;
55 size_t _clean_card_cnt;
56
57 size_t _max_dirty_run;
58 size_t _max_clean_run;
59
60 size_t _dirty_scan_obj_cnt;
61
62 size_t _alternation_cnt;
63
64 public:
65 ShenandoahCardStats(size_t cards_in_cluster, HdrSeq* card_stats) :
66 _cards_in_cluster(cards_in_cluster),
67 _local_card_stats(card_stats),
68 _dirty_card_cnt(0),
69 _clean_card_cnt(0),
70 _max_dirty_run(0),
71 _max_clean_run(0),
72 _dirty_scan_obj_cnt(0),
73 _alternation_cnt(0)
74 { }
75
76 ~ShenandoahCardStats() {
77 record();
78 }
79
80 void record() {
81 if (ShenandoahEnableCardStats) {
82 // Update global stats for distribution of dirty/clean cards as a percentage of chunk
83 _local_card_stats[DIRTY_CARDS].add(percent_of(_dirty_card_cnt, _cards_in_cluster));
84 _local_card_stats[CLEAN_CARDS].add(percent_of(_clean_card_cnt, _cards_in_cluster));
85
86 // Update global stats for max dirty/clean run distribution as a percentage of chunk
87 _local_card_stats[MAX_DIRTY_RUN].add(percent_of(_max_dirty_run, _cards_in_cluster));
88 _local_card_stats[MAX_CLEAN_RUN].add(percent_of(_max_clean_run, _cards_in_cluster));
89
90 // Update global stats for dirty obj scan counts
91 _local_card_stats[DIRTY_SCAN_OBJS].add(_dirty_scan_obj_cnt);
92
93 // Update global stats for alternation counts
94 _local_card_stats[ALTERNATIONS].add(_alternation_cnt);
95 }
96 }
97
98 public:
99 inline void record_dirty_run(size_t len) {
100 if (ShenandoahEnableCardStats) {
101 _alternation_cnt++;
102 if (len > _max_dirty_run) {
103 _max_dirty_run = len;
104 }
105 _dirty_card_cnt += len;
106 assert(len <= _cards_in_cluster, "Error");
107 _local_card_stats[DIRTY_RUN].add(percent_of(len, _cards_in_cluster));
108 }
109 }
110
111 inline void record_clean_run(size_t len) {
112 if (ShenandoahEnableCardStats) {
113 _alternation_cnt++;
114 if (len > _max_clean_run) {
115 _max_clean_run = len;
116 }
117 _clean_card_cnt += len;
118 assert(len <= _cards_in_cluster, "Error");
119 _local_card_stats[CLEAN_RUN].add(percent_of(len, _cards_in_cluster));
120 }
121 }
122
123 inline void record_scan_obj_cnt(size_t i) {
124 if (ShenandoahEnableCardStats) {
125 _dirty_scan_obj_cnt += i;
126 }
127 }
128
129 void log() const PRODUCT_RETURN;
130 };
131
132 #endif // SHARE_GC_SHENANDOAH_SHENANDOAHCARDSTATS_HPP