108 109 void G1RemSetSummary::subtract_from(G1RemSetSummary* other) { 110 assert(other != NULL, "just checking"); 111 assert(remset() == other->remset(), "just checking"); 112 assert(_num_vtimes == other->_num_vtimes, "just checking"); 113 114 _num_refined_cards = other->num_concurrent_refined_cards() - _num_refined_cards; 115 116 _num_processed_buf_mutator = other->num_processed_buf_mutator() - _num_processed_buf_mutator; 117 _num_processed_buf_rs_threads = other->num_processed_buf_rs_threads() - _num_processed_buf_rs_threads; 118 119 _num_coarsenings = other->num_coarsenings() - _num_coarsenings; 120 121 for (uint i = 0; i < _num_vtimes; i++) { 122 set_rs_thread_vtime(i, other->rs_thread_vtime(i) - rs_thread_vtime(i)); 123 } 124 125 _sampling_thread_vtime = other->sampling_thread_vtime() - _sampling_thread_vtime; 126 } 127 128 class HRRSStatsIter: public HeapRegionClosure { 129 size_t _occupied; 130 131 size_t _total_rs_mem_sz; 132 size_t _max_rs_mem_sz; 133 HeapRegion* _max_rs_mem_sz_region; 134 135 size_t _total_code_root_mem_sz; 136 size_t _max_code_root_mem_sz; 137 HeapRegion* _max_code_root_mem_sz_region; 138 public: 139 HRRSStatsIter() : 140 _occupied(0), 141 _total_rs_mem_sz(0), 142 _max_rs_mem_sz(0), 143 _max_rs_mem_sz_region(NULL), 144 _total_code_root_mem_sz(0), 145 _max_code_root_mem_sz(0), 146 _max_code_root_mem_sz_region(NULL) 147 {} 148 149 bool doHeapRegion(HeapRegion* r) { 150 HeapRegionRemSet* hrrs = r->rem_set(); 151 152 // HeapRegionRemSet::mem_size() includes the 153 // size of the strong code roots 154 size_t rs_mem_sz = hrrs->mem_size(); 155 if (rs_mem_sz > _max_rs_mem_sz) { 156 _max_rs_mem_sz = rs_mem_sz; 157 _max_rs_mem_sz_region = r; 158 } 159 _total_rs_mem_sz += rs_mem_sz; 160 161 size_t code_root_mem_sz = hrrs->strong_code_roots_mem_size(); 162 if (code_root_mem_sz > _max_code_root_mem_sz) { 163 _max_code_root_mem_sz = code_root_mem_sz; 164 _max_code_root_mem_sz_region = r; 165 } 166 _total_code_root_mem_sz += code_root_mem_sz; 167 168 size_t occ = hrrs->occupied(); 169 _occupied += occ; 170 return false; 171 } 172 size_t total_rs_mem_sz() { return _total_rs_mem_sz; } 173 size_t max_rs_mem_sz() { return _max_rs_mem_sz; } 174 HeapRegion* max_rs_mem_sz_region() { return _max_rs_mem_sz_region; } 175 size_t total_code_root_mem_sz() { return _total_code_root_mem_sz; } 176 size_t max_code_root_mem_sz() { return _max_code_root_mem_sz; } 177 HeapRegion* max_code_root_mem_sz_region() { return _max_code_root_mem_sz_region; } 178 size_t occupied() { return _occupied; } 179 }; 180 181 double calc_percentage(size_t numerator, size_t denominator) { 182 if (denominator != 0) { 183 return (double)numerator / denominator * 100.0; 184 } else { 185 return 0.0f; 186 } 187 } 188 189 void G1RemSetSummary::print_on(outputStream* out) { 190 out->print_cr("\n Concurrent RS processed "SIZE_FORMAT" cards", 191 num_concurrent_refined_cards()); 192 out->print_cr(" Of %d completed buffers:", num_processed_buf_total()); 193 out->print_cr(" %8d (%5.1f%%) by concurrent RS threads.", 194 num_processed_buf_total(), 195 calc_percentage(num_processed_buf_rs_threads(), num_processed_buf_total())); 196 out->print_cr(" %8d (%5.1f%%) by mutator threads.", 197 num_processed_buf_mutator(), 198 calc_percentage(num_processed_buf_mutator(), num_processed_buf_total())); 199 out->print_cr(" Concurrent RS threads times (s)"); 200 out->print(" "); 201 for (uint i = 0; i < _num_vtimes; i++) { 202 out->print(" %5.2f", rs_thread_vtime(i)); 203 } 204 out->cr(); 205 out->print_cr(" Concurrent sampling threads times (s)"); 206 out->print_cr(" %5.2f", sampling_thread_vtime()); 207 208 HRRSStatsIter blk; 209 G1CollectedHeap::heap()->heap_region_iterate(&blk); 210 // RemSet stats 211 out->print_cr(" Total heap region rem set sizes = "SIZE_FORMAT"K." 212 " Max = "SIZE_FORMAT"K.", 213 blk.total_rs_mem_sz()/K, blk.max_rs_mem_sz()/K); 214 out->print_cr(" Static structures = "SIZE_FORMAT"K," 215 " free_lists = "SIZE_FORMAT"K.", 216 HeapRegionRemSet::static_mem_size() / K, 217 HeapRegionRemSet::fl_mem_size() / K); 218 out->print_cr(" "SIZE_FORMAT" occupied cards represented.", 219 blk.occupied()); 220 HeapRegion* max_rs_mem_sz_region = blk.max_rs_mem_sz_region(); 221 HeapRegionRemSet* max_rs_rem_set = max_rs_mem_sz_region->rem_set(); 222 out->print_cr(" Max size region = "HR_FORMAT", " 223 "size = "SIZE_FORMAT "K, occupied = "SIZE_FORMAT"K.", 224 HR_FORMAT_PARAMS(max_rs_mem_sz_region), 225 (max_rs_rem_set->mem_size() + K - 1)/K, 226 (max_rs_rem_set->occupied() + K - 1)/K); 227 out->print_cr(" Did %d coarsenings.", num_coarsenings()); 228 // Strong code root stats 229 out->print_cr(" Total heap region code-root set sizes = "SIZE_FORMAT"K." 230 " Max = "SIZE_FORMAT"K.", 231 blk.total_code_root_mem_sz()/K, blk.max_code_root_mem_sz()/K); 232 HeapRegion* max_code_root_mem_sz_region = blk.max_code_root_mem_sz_region(); 233 HeapRegionRemSet* max_code_root_rem_set = max_code_root_mem_sz_region->rem_set(); 234 out->print_cr(" Max size region = "HR_FORMAT", " 235 "size = "SIZE_FORMAT "K, num_elems = "SIZE_FORMAT".", 236 HR_FORMAT_PARAMS(max_code_root_mem_sz_region), 237 (max_code_root_rem_set->strong_code_roots_mem_size() + K - 1)/K, 238 (max_code_root_rem_set->strong_code_roots_list_length())); 239 } | 108 109 void G1RemSetSummary::subtract_from(G1RemSetSummary* other) { 110 assert(other != NULL, "just checking"); 111 assert(remset() == other->remset(), "just checking"); 112 assert(_num_vtimes == other->_num_vtimes, "just checking"); 113 114 _num_refined_cards = other->num_concurrent_refined_cards() - _num_refined_cards; 115 116 _num_processed_buf_mutator = other->num_processed_buf_mutator() - _num_processed_buf_mutator; 117 _num_processed_buf_rs_threads = other->num_processed_buf_rs_threads() - _num_processed_buf_rs_threads; 118 119 _num_coarsenings = other->num_coarsenings() - _num_coarsenings; 120 121 for (uint i = 0; i < _num_vtimes; i++) { 122 set_rs_thread_vtime(i, other->rs_thread_vtime(i) - rs_thread_vtime(i)); 123 } 124 125 _sampling_thread_vtime = other->sampling_thread_vtime() - _sampling_thread_vtime; 126 } 127 128 static double percent_of(size_t numerator, size_t denominator) { 129 if (denominator != 0) { 130 return (double)numerator / denominator * 100.0f; 131 } else { 132 return 0.0f; 133 } 134 } 135 136 static size_t round_to_K(size_t value) { 137 return value / K; 138 } 139 140 class RegionTypeCounter VALUE_OBJ_CLASS_SPEC { 141 private: 142 const char* _name; 143 144 size_t _rs_mem_size; 145 size_t _cards_occupied; 146 size_t _amount; 147 148 size_t _code_root_mem_size; 149 size_t _code_root_elems; 150 151 double rs_mem_size_percent_of(size_t total) { 152 return percent_of(_rs_mem_size, total); 153 } 154 155 double cards_occupied_percent_of(size_t total) { 156 return percent_of(_cards_occupied, total); 157 } 158 159 double code_root_mem_size_percent_of(size_t total) { 160 return percent_of(_code_root_mem_size, total); 161 } 162 163 double code_root_elems_percent_of(size_t total) { 164 return percent_of(_code_root_elems, total); 165 } 166 167 size_t amount() const { return _amount; } 168 169 public: 170 171 RegionTypeCounter(const char* name) : _name(name), _rs_mem_size(0), _cards_occupied(0), 172 _amount(0), _code_root_mem_size(0), _code_root_elems(0) { } 173 174 void add(size_t rs_mem_size, size_t cards_occupied, size_t code_root_mem_size, 175 size_t code_root_elems) { 176 _rs_mem_size += rs_mem_size; 177 _cards_occupied += cards_occupied; 178 _code_root_mem_size += code_root_mem_size; 179 _code_root_elems += code_root_elems; 180 _amount++; 181 } 182 183 size_t rs_mem_size() const { return _rs_mem_size; } 184 size_t cards_occupied() const { return _cards_occupied; } 185 186 size_t code_root_mem_size() const { return _code_root_mem_size; } 187 size_t code_root_elems() const { return _code_root_elems; } 188 189 void print_rs_mem_info_on(outputStream * out, size_t total) { 190 out->print_cr(" %8dK (%5.1f%%) by %zd %s regions", round_to_K(rs_mem_size()), rs_mem_size_percent_of(total), amount(), _name); 191 } 192 193 void print_cards_occupied_info_on(outputStream * out, size_t total) { 194 out->print_cr(" %8d (%5.1f%%) entries by %zd %s regions", cards_occupied(), cards_occupied_percent_of(total), amount(), _name); 195 } 196 197 void print_code_root_mem_info_on(outputStream * out, size_t total) { 198 out->print_cr(" %8dK (%5.1f%%) by %zd %s regions", round_to_K(code_root_mem_size()), code_root_mem_size_percent_of(total), amount(), _name); 199 } 200 201 void print_code_root_elems_info_on(outputStream * out, size_t total) { 202 out->print_cr(" %8d (%5.1f%%) elements by %zd %s regions", code_root_elems(), code_root_elems_percent_of(total), amount(), _name); 203 } 204 }; 205 206 207 class HRRSStatsIter: public HeapRegionClosure { 208 private: 209 RegionTypeCounter _young; 210 RegionTypeCounter _humonguous; 211 RegionTypeCounter _free; 212 RegionTypeCounter _old; 213 RegionTypeCounter _all; 214 215 size_t _max_rs_mem_sz; 216 HeapRegion* _max_rs_mem_sz_region; 217 218 size_t total_rs_mem_sz() const { return _all.rs_mem_size(); } 219 size_t total_cards_occupied() const { return _all.cards_occupied(); } 220 221 size_t max_rs_mem_sz() const { return _max_rs_mem_sz; } 222 HeapRegion* max_rs_mem_sz_region() const { return _max_rs_mem_sz_region; } 223 224 size_t _max_code_root_mem_sz; 225 HeapRegion* _max_code_root_mem_sz_region; 226 227 size_t total_code_root_mem_sz() const { return _all.code_root_mem_size(); } 228 size_t total_code_root_elems() const { return _all.code_root_elems(); } 229 230 size_t max_code_root_mem_sz() const { return _max_code_root_mem_sz; } 231 HeapRegion* max_code_root_mem_sz_region() const { return _max_code_root_mem_sz_region; } 232 233 public: 234 HRRSStatsIter() : _all("All"), _young("Young"), _humonguous("Humonguous"), 235 _free("Free"), _old("Old"), _max_code_root_mem_sz_region(NULL), _max_rs_mem_sz_region(NULL), 236 _max_rs_mem_sz(0), _max_code_root_mem_sz(0) 237 {} 238 239 bool doHeapRegion(HeapRegion* r) { 240 HeapRegionRemSet* hrrs = r->rem_set(); 241 242 // HeapRegionRemSet::mem_size() includes the 243 // size of the strong code roots 244 size_t rs_mem_sz = hrrs->mem_size(); 245 if (rs_mem_sz > _max_rs_mem_sz) { 246 _max_rs_mem_sz = rs_mem_sz; 247 _max_rs_mem_sz_region = r; 248 } 249 size_t occ = hrrs->occupied(); 250 size_t code_root_mem_sz = hrrs->strong_code_roots_mem_size(); 251 if (code_root_mem_sz > max_code_root_mem_sz()) { 252 _max_code_root_mem_sz_region = r; 253 } 254 size_t code_root_elems = hrrs->strong_code_roots_list_length(); 255 256 _all.add(rs_mem_sz, occ, code_root_mem_sz, code_root_elems); 257 if (r->is_young()) { 258 _young.add(rs_mem_sz, occ, code_root_mem_sz, code_root_elems); 259 } else if (r->isHumongous()) { 260 _humonguous.add(rs_mem_sz, occ, code_root_mem_sz, code_root_elems); 261 } else if (r->is_empty()) { 262 _free.add(rs_mem_sz, occ, code_root_mem_sz, code_root_elems); 263 } else { 264 _old.add(rs_mem_sz, occ, code_root_mem_sz, code_root_elems); 265 } 266 267 return false; 268 } 269 270 #define FOR_ALL_REGION_COUNTERS(fn) \ 271 for (RegionTypeCounter** current = &counters[0]; *current != NULL; current++) { \ 272 (*current)->fn; \ 273 } 274 275 void print_summary_on(outputStream* out) { 276 RegionTypeCounter* counters[] = { &_young, &_humonguous, &_free, &_old, NULL }; 277 278 out->print_cr("\n Current rem set statistics"); 279 out->print_cr(" Total per region rem sets sizes = "SIZE_FORMAT"K." 280 " Max = "SIZE_FORMAT"K.", 281 round_to_K(total_rs_mem_sz()), round_to_K(max_rs_mem_sz())); 282 283 FOR_ALL_REGION_COUNTERS(print_rs_mem_info_on(out, total_rs_mem_sz())); 284 285 out->print_cr(" Static structures = "SIZE_FORMAT"K," 286 " free_lists = "SIZE_FORMAT"K.", 287 round_to_K(HeapRegionRemSet::static_mem_size()), 288 round_to_K(HeapRegionRemSet::fl_mem_size())); 289 290 out->print_cr(" "SIZE_FORMAT" occupied cards represented.", 291 total_cards_occupied()); 292 FOR_ALL_REGION_COUNTERS(print_cards_occupied_info_on(out, total_cards_occupied())); 293 294 // Largest sized rem set region statistics 295 HeapRegionRemSet* rem_set = max_rs_mem_sz_region()->rem_set(); 296 out->print_cr(" Region with largest rem set = "HR_FORMAT", " 297 "size = "SIZE_FORMAT "K, occupied = "SIZE_FORMAT"K.", 298 HR_FORMAT_PARAMS(max_rs_mem_sz_region()), 299 round_to_K(rem_set->mem_size()), 300 round_to_K(rem_set->occupied())); 301 302 // Strong code root statistics 303 HeapRegionRemSet* max_code_root_rem_set = max_code_root_mem_sz_region()->rem_set(); 304 out->print_cr(" Total heap region code root sets sizes = "SIZE_FORMAT"K." 305 " Max = "SIZE_FORMAT"K.", 306 round_to_K(total_code_root_mem_sz()), 307 round_to_K(max_code_root_rem_set->strong_code_roots_mem_size())); 308 FOR_ALL_REGION_COUNTERS(print_code_root_mem_info_on(out, total_code_root_mem_sz())); 309 310 out->print_cr(" "SIZE_FORMAT" code roots represented.", 311 total_code_root_elems()); 312 FOR_ALL_REGION_COUNTERS(print_code_root_elems_info_on(out, total_code_root_elems())); 313 314 out->print_cr(" Region with largest amount of code roots = "HR_FORMAT", " 315 "size = "SIZE_FORMAT "K, num_elems = "SIZE_FORMAT".", 316 HR_FORMAT_PARAMS(max_code_root_mem_sz_region()), 317 round_to_K(max_code_root_rem_set->strong_code_roots_mem_size()), 318 round_to_K(max_code_root_rem_set->strong_code_roots_list_length())); 319 } 320 321 #undef FOR_ALL_REGION_COUNTERS 322 }; 323 324 void G1RemSetSummary::print_on(outputStream* out) { 325 out->print_cr("\n Recent concurrent refinement statistics"); 326 out->print_cr(" Processed "SIZE_FORMAT" cards", 327 num_concurrent_refined_cards()); 328 out->print_cr(" Of %d completed buffers:", num_processed_buf_total()); 329 out->print_cr(" %8d (%5.1f%%) by concurrent RS threads.", 330 num_processed_buf_total(), 331 percent_of(num_processed_buf_rs_threads(), num_processed_buf_total())); 332 out->print_cr(" %8d (%5.1f%%) by mutator threads.", 333 num_processed_buf_mutator(), 334 percent_of(num_processed_buf_mutator(), num_processed_buf_total())); 335 out->print_cr(" Did %d coarsenings.", num_coarsenings()); 336 out->print_cr(" Concurrent RS threads times (s)"); 337 out->print(" "); 338 for (uint i = 0; i < _num_vtimes; i++) { 339 out->print(" %5.2f", rs_thread_vtime(i)); 340 } 341 out->cr(); 342 out->print_cr(" Concurrent sampling threads times (s)"); 343 out->print_cr(" %5.2f", sampling_thread_vtime()); 344 345 HRRSStatsIter blk; 346 G1CollectedHeap::heap()->heap_region_iterate(&blk); 347 blk.print_summary_on(out); 348 } |