1.1 --- a/src/share/vm/gc_implementation/g1/g1CollectorPolicy.cpp Wed Sep 07 18:58:33 2011 -0700 1.2 +++ b/src/share/vm/gc_implementation/g1/g1CollectorPolicy.cpp Thu Sep 08 05:16:49 2011 -0400 1.3 @@ -414,7 +414,7 @@ 1.4 _concurrent_mark_cleanup_times_ms->add(0.20); 1.5 _tenuring_threshold = MaxTenuringThreshold; 1.6 // _max_survivor_regions will be calculated by 1.7 - // calculate_young_list_target_length() during initialization. 1.8 + // update_young_list_target_length() during initialization. 1.9 _max_survivor_regions = 0; 1.10 1.11 assert(GCTimeRatio > 0, 1.12 @@ -422,6 +422,18 @@ 1.13 "if a user set it to 0"); 1.14 _gc_overhead_perc = 100.0 * (1.0 / (1.0 + GCTimeRatio)); 1.15 1.16 + uintx reserve_perc = G1ReservePercent; 1.17 + // Put an artificial ceiling on this so that it's not set to a silly value. 1.18 + if (reserve_perc > 50) { 1.19 + reserve_perc = 50; 1.20 + warning("G1ReservePercent is set to a value that is too large, " 1.21 + "it's been updated to %u", reserve_perc); 1.22 + } 1.23 + _reserve_factor = (double) reserve_perc / 100.0; 1.24 + // This will be set in calculate_reserve() when the heap is expanded 1.25 + // for the first time during initialization. 1.26 + _reserve_regions = 0; 1.27 + 1.28 initialize_all(); 1.29 } 1.30 1.31 @@ -486,9 +498,7 @@ 1.32 _young_list_fixed_length = initial_region_num; 1.33 } 1.34 _free_regions_at_end_of_collection = _g1->free_regions(); 1.35 - calculate_young_list_min_length(); 1.36 - guarantee( _young_list_min_length == 0, "invariant, not enough info" ); 1.37 - calculate_young_list_target_length(); 1.38 + update_young_list_target_length(); 1.39 1.40 // We may immediately start allocating regions and placing them on the 1.41 // collection set list. Initialize the per-collection set info 1.42 @@ -496,236 +506,252 @@ 1.43 } 1.44 1.45 // Create the jstat counters for the policy. 1.46 -void G1CollectorPolicy::initialize_gc_policy_counters() 1.47 -{ 1.48 +void G1CollectorPolicy::initialize_gc_policy_counters() { 1.49 _gc_policy_counters = new GCPolicyCounters("GarbageFirst", 1, 3); 1.50 } 1.51 1.52 -void G1CollectorPolicy::calculate_young_list_min_length() { 1.53 - _young_list_min_length = 0; 1.54 - 1.55 - if (!adaptive_young_list_length()) 1.56 - return; 1.57 - 1.58 - if (_alloc_rate_ms_seq->num() > 3) { 1.59 - double now_sec = os::elapsedTime(); 1.60 - double when_ms = _mmu_tracker->when_max_gc_sec(now_sec) * 1000.0; 1.61 - double alloc_rate_ms = predict_alloc_rate_ms(); 1.62 - size_t min_regions = (size_t) ceil(alloc_rate_ms * when_ms); 1.63 - size_t current_region_num = _g1->young_list()->length(); 1.64 - _young_list_min_length = min_regions + current_region_num; 1.65 +bool G1CollectorPolicy::predict_will_fit(size_t young_length, 1.66 + double base_time_ms, 1.67 + size_t base_free_regions, 1.68 + double target_pause_time_ms) { 1.69 + if (young_length >= base_free_regions) { 1.70 + // end condition 1: not enough space for the young regions 1.71 + return false; 1.72 } 1.73 + 1.74 + double accum_surv_rate = accum_yg_surv_rate_pred((int)(young_length - 1)); 1.75 + size_t bytes_to_copy = 1.76 + (size_t) (accum_surv_rate * (double) HeapRegion::GrainBytes); 1.77 + double copy_time_ms = predict_object_copy_time_ms(bytes_to_copy); 1.78 + double young_other_time_ms = predict_young_other_time_ms(young_length); 1.79 + double pause_time_ms = base_time_ms + copy_time_ms + young_other_time_ms; 1.80 + if (pause_time_ms > target_pause_time_ms) { 1.81 + // end condition 2: prediction is over the target pause time 1.82 + return false; 1.83 + } 1.84 + 1.85 + size_t free_bytes = 1.86 + (base_free_regions - young_length) * HeapRegion::GrainBytes; 1.87 + if ((2.0 * sigma()) * (double) bytes_to_copy > (double) free_bytes) { 1.88 + // end condition 3: out-of-space (conservatively!) 1.89 + return false; 1.90 + } 1.91 + 1.92 + // success! 1.93 + return true; 1.94 } 1.95 1.96 -void G1CollectorPolicy::calculate_young_list_target_length() { 1.97 +void G1CollectorPolicy::calculate_reserve(size_t all_regions) { 1.98 + double reserve_regions_d = (double) all_regions * _reserve_factor; 1.99 + // We use ceiling so that if reserve_regions_d is > 0.0 (but 1.100 + // smaller than 1.0) we'll get 1. 1.101 + _reserve_regions = (size_t) ceil(reserve_regions_d); 1.102 +} 1.103 + 1.104 +size_t G1CollectorPolicy::calculate_young_list_desired_min_length( 1.105 + size_t base_min_length) { 1.106 + size_t desired_min_length = 0; 1.107 if (adaptive_young_list_length()) { 1.108 - size_t rs_lengths = (size_t) get_new_prediction(_rs_lengths_seq); 1.109 - calculate_young_list_target_length(rs_lengths); 1.110 - } else { 1.111 - if (full_young_gcs()) 1.112 - _young_list_target_length = _young_list_fixed_length; 1.113 - else 1.114 - _young_list_target_length = _young_list_fixed_length / 2; 1.115 + if (_alloc_rate_ms_seq->num() > 3) { 1.116 + double now_sec = os::elapsedTime(); 1.117 + double when_ms = _mmu_tracker->when_max_gc_sec(now_sec) * 1000.0; 1.118 + double alloc_rate_ms = predict_alloc_rate_ms(); 1.119 + desired_min_length = (size_t) ceil(alloc_rate_ms * when_ms); 1.120 + } else { 1.121 + // otherwise we don't have enough info to make the prediction 1.122 + } 1.123 } 1.124 - 1.125 - // Make sure we allow the application to allocate at least one 1.126 - // region before we need to do a collection again. 1.127 - size_t min_length = _g1->young_list()->length() + 1; 1.128 - _young_list_target_length = MAX2(_young_list_target_length, min_length); 1.129 - calculate_max_gc_locker_expansion(); 1.130 - calculate_survivors_policy(); 1.131 + // Here, we might want to also take into account any additional 1.132 + // constraints (i.e., user-defined minimum bound). Currently, we don't. 1.133 + return base_min_length + desired_min_length; 1.134 } 1.135 1.136 -void G1CollectorPolicy::calculate_young_list_target_length(size_t rs_lengths) { 1.137 - guarantee( adaptive_young_list_length(), "pre-condition" ); 1.138 - guarantee( !_in_marking_window || !_last_full_young_gc, "invariant" ); 1.139 - 1.140 - double start_time_sec = os::elapsedTime(); 1.141 - size_t min_reserve_perc = MAX2((size_t)2, (size_t)G1ReservePercent); 1.142 - min_reserve_perc = MIN2((size_t) 50, min_reserve_perc); 1.143 - size_t reserve_regions = 1.144 - (size_t) ((double) min_reserve_perc * (double) _g1->n_regions() / 100.0); 1.145 - 1.146 - if (full_young_gcs() && _free_regions_at_end_of_collection > 0) { 1.147 - // we are in fully-young mode and there are free regions in the heap 1.148 - 1.149 - double survivor_regions_evac_time = 1.150 - predict_survivor_regions_evac_time(); 1.151 - 1.152 - double target_pause_time_ms = _mmu_tracker->max_gc_time() * 1000.0; 1.153 - size_t pending_cards = (size_t) get_new_prediction(_pending_cards_seq); 1.154 - size_t adj_rs_lengths = rs_lengths + predict_rs_length_diff(); 1.155 - size_t scanned_cards = predict_young_card_num(adj_rs_lengths); 1.156 - double base_time_ms = predict_base_elapsed_time_ms(pending_cards, scanned_cards) 1.157 - + survivor_regions_evac_time; 1.158 - 1.159 - // the result 1.160 - size_t final_young_length = 0; 1.161 - 1.162 - size_t init_free_regions = 1.163 - MAX2((size_t)0, _free_regions_at_end_of_collection - reserve_regions); 1.164 - 1.165 - // if we're still under the pause target... 1.166 - if (base_time_ms <= target_pause_time_ms) { 1.167 - // We make sure that the shortest young length that makes sense 1.168 - // fits within the target pause time. 1.169 - size_t min_young_length = 1; 1.170 - 1.171 - if (predict_will_fit(min_young_length, base_time_ms, 1.172 - init_free_regions, target_pause_time_ms)) { 1.173 - // The shortest young length will fit within the target pause time; 1.174 - // we'll now check whether the absolute maximum number of young 1.175 - // regions will fit in the target pause time. If not, we'll do 1.176 - // a binary search between min_young_length and max_young_length 1.177 - size_t abs_max_young_length = _free_regions_at_end_of_collection - 1; 1.178 - size_t max_young_length = abs_max_young_length; 1.179 - 1.180 - if (max_young_length > min_young_length) { 1.181 - // Let's check if the initial max young length will fit within the 1.182 - // target pause. If so then there is no need to search for a maximal 1.183 - // young length - we'll return the initial maximum 1.184 - 1.185 - if (predict_will_fit(max_young_length, base_time_ms, 1.186 - init_free_regions, target_pause_time_ms)) { 1.187 - // The maximum young length will satisfy the target pause time. 1.188 - // We are done so set min young length to this maximum length. 1.189 - // The code after the loop will then set final_young_length using 1.190 - // the value cached in the minimum length. 1.191 - min_young_length = max_young_length; 1.192 - } else { 1.193 - // The maximum possible number of young regions will not fit within 1.194 - // the target pause time so let's search.... 1.195 - 1.196 - size_t diff = (max_young_length - min_young_length) / 2; 1.197 - max_young_length = min_young_length + diff; 1.198 - 1.199 - while (max_young_length > min_young_length) { 1.200 - if (predict_will_fit(max_young_length, base_time_ms, 1.201 - init_free_regions, target_pause_time_ms)) { 1.202 - 1.203 - // The current max young length will fit within the target 1.204 - // pause time. Note we do not exit the loop here. By setting 1.205 - // min = max, and then increasing the max below means that 1.206 - // we will continue searching for an upper bound in the 1.207 - // range [max..max+diff] 1.208 - min_young_length = max_young_length; 1.209 - } 1.210 - diff = (max_young_length - min_young_length) / 2; 1.211 - max_young_length = min_young_length + diff; 1.212 - } 1.213 - // the above loop found a maximal young length that will fit 1.214 - // within the target pause time. 1.215 - } 1.216 - assert(min_young_length <= abs_max_young_length, "just checking"); 1.217 - } 1.218 - final_young_length = min_young_length; 1.219 - } 1.220 - } 1.221 - // and we're done! 1.222 - 1.223 - // we should have at least one region in the target young length 1.224 - _young_list_target_length = 1.225 - final_young_length + _recorded_survivor_regions; 1.226 - 1.227 - // let's keep an eye of how long we spend on this calculation 1.228 - // right now, I assume that we'll print it when we need it; we 1.229 - // should really adde it to the breakdown of a pause 1.230 - double end_time_sec = os::elapsedTime(); 1.231 - double elapsed_time_ms = (end_time_sec - start_time_sec) * 1000.0; 1.232 - 1.233 -#ifdef TRACE_CALC_YOUNG_LENGTH 1.234 - // leave this in for debugging, just in case 1.235 - gclog_or_tty->print_cr("target = %1.1lf ms, young = " SIZE_FORMAT ", " 1.236 - "elapsed %1.2lf ms, (%s%s) " SIZE_FORMAT SIZE_FORMAT, 1.237 - target_pause_time_ms, 1.238 - _young_list_target_length 1.239 - elapsed_time_ms, 1.240 - full_young_gcs() ? "full" : "partial", 1.241 - during_initial_mark_pause() ? " i-m" : "", 1.242 - _in_marking_window, 1.243 - _in_marking_window_im); 1.244 -#endif // TRACE_CALC_YOUNG_LENGTH 1.245 - 1.246 - if (_young_list_target_length < _young_list_min_length) { 1.247 - // bummer; this means that, if we do a pause when the maximal 1.248 - // length dictates, we'll violate the pause spacing target (the 1.249 - // min length was calculate based on the application's current 1.250 - // alloc rate); 1.251 - 1.252 - // so, we have to bite the bullet, and allocate the minimum 1.253 - // number. We'll violate our target, but we just can't meet it. 1.254 - 1.255 -#ifdef TRACE_CALC_YOUNG_LENGTH 1.256 - // leave this in for debugging, just in case 1.257 - gclog_or_tty->print_cr("adjusted target length from " 1.258 - SIZE_FORMAT " to " SIZE_FORMAT, 1.259 - _young_list_target_length, _young_list_min_length); 1.260 -#endif // TRACE_CALC_YOUNG_LENGTH 1.261 - 1.262 - _young_list_target_length = _young_list_min_length; 1.263 +size_t G1CollectorPolicy::calculate_young_list_desired_max_length() { 1.264 + // Here, we might want to also take into account any additional 1.265 + // constraints (i.e., user-defined minimum bound). Currently, we 1.266 + // effectively don't set this bound. 1.267 + return _g1->n_regions(); 1.268 +} 1.269 + 1.270 +void G1CollectorPolicy::update_young_list_target_length(size_t rs_lengths) { 1.271 + if (rs_lengths == (size_t) -1) { 1.272 + // if it's set to the default value (-1), we should predict it; 1.273 + // otherwise, use the given value. 1.274 + rs_lengths = (size_t) get_new_prediction(_rs_lengths_seq); 1.275 + } 1.276 + 1.277 + // Calculate the absolute and desired min bounds. 1.278 + 1.279 + // This is how many young regions we already have (currently: the survivors). 1.280 + size_t base_min_length = recorded_survivor_regions(); 1.281 + // This is the absolute minimum young length, which ensures that we 1.282 + // can allocate one eden region in the worst-case. 1.283 + size_t absolute_min_length = base_min_length + 1; 1.284 + size_t desired_min_length = 1.285 + calculate_young_list_desired_min_length(base_min_length); 1.286 + if (desired_min_length < absolute_min_length) { 1.287 + desired_min_length = absolute_min_length; 1.288 + } 1.289 + 1.290 + // Calculate the absolute and desired max bounds. 1.291 + 1.292 + // We will try our best not to "eat" into the reserve. 1.293 + size_t absolute_max_length = 0; 1.294 + if (_free_regions_at_end_of_collection > _reserve_regions) { 1.295 + absolute_max_length = _free_regions_at_end_of_collection - _reserve_regions; 1.296 + } 1.297 + size_t desired_max_length = calculate_young_list_desired_max_length(); 1.298 + if (desired_max_length > absolute_max_length) { 1.299 + desired_max_length = absolute_max_length; 1.300 + } 1.301 + 1.302 + size_t young_list_target_length = 0; 1.303 + if (adaptive_young_list_length()) { 1.304 + if (full_young_gcs()) { 1.305 + young_list_target_length = 1.306 + calculate_young_list_target_length(rs_lengths, 1.307 + base_min_length, 1.308 + desired_min_length, 1.309 + desired_max_length); 1.310 + _rs_lengths_prediction = rs_lengths; 1.311 + } else { 1.312 + // Don't calculate anything and let the code below bound it to 1.313 + // the desired_min_length, i.e., do the next GC as soon as 1.314 + // possible to maximize how many old regions we can add to it. 1.315 } 1.316 } else { 1.317 - // we are in a partially-young mode or we've run out of regions (due 1.318 - // to evacuation failure) 1.319 - 1.320 -#ifdef TRACE_CALC_YOUNG_LENGTH 1.321 - // leave this in for debugging, just in case 1.322 - gclog_or_tty->print_cr("(partial) setting target to " SIZE_FORMAT 1.323 - _young_list_min_length); 1.324 -#endif // TRACE_CALC_YOUNG_LENGTH 1.325 - // we'll do the pause as soon as possible by choosing the minimum 1.326 - _young_list_target_length = _young_list_min_length; 1.327 + if (full_young_gcs()) { 1.328 + young_list_target_length = _young_list_fixed_length; 1.329 + } else { 1.330 + // A bit arbitrary: during partially-young GCs we allocate half 1.331 + // the young regions to try to add old regions to the CSet. 1.332 + young_list_target_length = _young_list_fixed_length / 2; 1.333 + // We choose to accept that we might go under the desired min 1.334 + // length given that we intentionally ask for a smaller young gen. 1.335 + desired_min_length = absolute_min_length; 1.336 + } 1.337 } 1.338 1.339 - _rs_lengths_prediction = rs_lengths; 1.340 + // Make sure we don't go over the desired max length, nor under the 1.341 + // desired min length. In case they clash, desired_min_length wins 1.342 + // which is why that test is second. 1.343 + if (young_list_target_length > desired_max_length) { 1.344 + young_list_target_length = desired_max_length; 1.345 + } 1.346 + if (young_list_target_length < desired_min_length) { 1.347 + young_list_target_length = desired_min_length; 1.348 + } 1.349 + 1.350 + assert(young_list_target_length > recorded_survivor_regions(), 1.351 + "we should be able to allocate at least one eden region"); 1.352 + assert(young_list_target_length >= absolute_min_length, "post-condition"); 1.353 + _young_list_target_length = young_list_target_length; 1.354 + 1.355 + update_max_gc_locker_expansion(); 1.356 } 1.357 1.358 -// This is used by: calculate_young_list_target_length(rs_length). It 1.359 -// returns true iff: 1.360 -// the predicted pause time for the given young list will not overflow 1.361 -// the target pause time 1.362 -// and: 1.363 -// the predicted amount of surviving data will not overflow the 1.364 -// the amount of free space available for survivor regions. 1.365 -// 1.366 -bool 1.367 -G1CollectorPolicy::predict_will_fit(size_t young_length, 1.368 - double base_time_ms, 1.369 - size_t init_free_regions, 1.370 - double target_pause_time_ms) { 1.371 - 1.372 - if (young_length >= init_free_regions) 1.373 - // end condition 1: not enough space for the young regions 1.374 - return false; 1.375 - 1.376 - double accum_surv_rate_adj = 0.0; 1.377 - double accum_surv_rate = 1.378 - accum_yg_surv_rate_pred((int)(young_length - 1)) - accum_surv_rate_adj; 1.379 - 1.380 - size_t bytes_to_copy = 1.381 - (size_t) (accum_surv_rate * (double) HeapRegion::GrainBytes); 1.382 - 1.383 - double copy_time_ms = predict_object_copy_time_ms(bytes_to_copy); 1.384 - 1.385 - double young_other_time_ms = 1.386 - predict_young_other_time_ms(young_length); 1.387 - 1.388 - double pause_time_ms = 1.389 - base_time_ms + copy_time_ms + young_other_time_ms; 1.390 - 1.391 - if (pause_time_ms > target_pause_time_ms) 1.392 - // end condition 2: over the target pause time 1.393 - return false; 1.394 - 1.395 - size_t free_bytes = 1.396 - (init_free_regions - young_length) * HeapRegion::GrainBytes; 1.397 - 1.398 - if ((2.0 + sigma()) * (double) bytes_to_copy > (double) free_bytes) 1.399 - // end condition 3: out of to-space (conservatively) 1.400 - return false; 1.401 - 1.402 - // success! 1.403 - return true; 1.404 +size_t 1.405 +G1CollectorPolicy::calculate_young_list_target_length(size_t rs_lengths, 1.406 + size_t base_min_length, 1.407 + size_t desired_min_length, 1.408 + size_t desired_max_length) { 1.409 + assert(adaptive_young_list_length(), "pre-condition"); 1.410 + assert(full_young_gcs(), "only call this for fully-young GCs"); 1.411 + 1.412 + // In case some edge-condition makes the desired max length too small... 1.413 + if (desired_max_length <= desired_min_length) { 1.414 + return desired_min_length; 1.415 + } 1.416 + 1.417 + // We'll adjust min_young_length and max_young_length not to include 1.418 + // the already allocated young regions (i.e., so they reflect the 1.419 + // min and max eden regions we'll allocate). The base_min_length 1.420 + // will be reflected in the predictions by the 1.421 + // survivor_regions_evac_time prediction. 1.422 + assert(desired_min_length > base_min_length, "invariant"); 1.423 + size_t min_young_length = desired_min_length - base_min_length; 1.424 + assert(desired_max_length > base_min_length, "invariant"); 1.425 + size_t max_young_length = desired_max_length - base_min_length; 1.426 + 1.427 + double target_pause_time_ms = _mmu_tracker->max_gc_time() * 1000.0; 1.428 + double survivor_regions_evac_time = predict_survivor_regions_evac_time(); 1.429 + size_t pending_cards = (size_t) get_new_prediction(_pending_cards_seq); 1.430 + size_t adj_rs_lengths = rs_lengths + predict_rs_length_diff(); 1.431 + size_t scanned_cards = predict_young_card_num(adj_rs_lengths); 1.432 + double base_time_ms = 1.433 + predict_base_elapsed_time_ms(pending_cards, scanned_cards) + 1.434 + survivor_regions_evac_time; 1.435 + size_t available_free_regions = _free_regions_at_end_of_collection; 1.436 + size_t base_free_regions = 0; 1.437 + if (available_free_regions > _reserve_regions) { 1.438 + base_free_regions = available_free_regions - _reserve_regions; 1.439 + } 1.440 + 1.441 + // Here, we will make sure that the shortest young length that 1.442 + // makes sense fits within the target pause time. 1.443 + 1.444 + if (predict_will_fit(min_young_length, base_time_ms, 1.445 + base_free_regions, target_pause_time_ms)) { 1.446 + // The shortest young length will fit into the target pause time; 1.447 + // we'll now check whether the absolute maximum number of young 1.448 + // regions will fit in the target pause time. If not, we'll do 1.449 + // a binary search between min_young_length and max_young_length. 1.450 + if (predict_will_fit(max_young_length, base_time_ms, 1.451 + base_free_regions, target_pause_time_ms)) { 1.452 + // The maximum young length will fit into the target pause time. 1.453 + // We are done so set min young length to the maximum length (as 1.454 + // the result is assumed to be returned in min_young_length). 1.455 + min_young_length = max_young_length; 1.456 + } else { 1.457 + // The maximum possible number of young regions will not fit within 1.458 + // the target pause time so we'll search for the optimal 1.459 + // length. The loop invariants are: 1.460 + // 1.461 + // min_young_length < max_young_length 1.462 + // min_young_length is known to fit into the target pause time 1.463 + // max_young_length is known not to fit into the target pause time 1.464 + // 1.465 + // Going into the loop we know the above hold as we've just 1.466 + // checked them. Every time around the loop we check whether 1.467 + // the middle value between min_young_length and 1.468 + // max_young_length fits into the target pause time. If it 1.469 + // does, it becomes the new min. If it doesn't, it becomes 1.470 + // the new max. This way we maintain the loop invariants. 1.471 + 1.472 + assert(min_young_length < max_young_length, "invariant"); 1.473 + size_t diff = (max_young_length - min_young_length) / 2; 1.474 + while (diff > 0) { 1.475 + size_t young_length = min_young_length + diff; 1.476 + if (predict_will_fit(young_length, base_time_ms, 1.477 + base_free_regions, target_pause_time_ms)) { 1.478 + min_young_length = young_length; 1.479 + } else { 1.480 + max_young_length = young_length; 1.481 + } 1.482 + assert(min_young_length < max_young_length, "invariant"); 1.483 + diff = (max_young_length - min_young_length) / 2; 1.484 + } 1.485 + // The results is min_young_length which, according to the 1.486 + // loop invariants, should fit within the target pause time. 1.487 + 1.488 + // These are the post-conditions of the binary search above: 1.489 + assert(min_young_length < max_young_length, 1.490 + "otherwise we should have discovered that max_young_length " 1.491 + "fits into the pause target and not done the binary search"); 1.492 + assert(predict_will_fit(min_young_length, base_time_ms, 1.493 + base_free_regions, target_pause_time_ms), 1.494 + "min_young_length, the result of the binary search, should " 1.495 + "fit into the pause target"); 1.496 + assert(!predict_will_fit(min_young_length + 1, base_time_ms, 1.497 + base_free_regions, target_pause_time_ms), 1.498 + "min_young_length, the result of the binary search, should be " 1.499 + "optimal, so no larger length should fit into the pause target"); 1.500 + } 1.501 + } else { 1.502 + // Even the minimum length doesn't fit into the pause time 1.503 + // target, return it as the result nevertheless. 1.504 + } 1.505 + return base_min_length + min_young_length; 1.506 } 1.507 1.508 double G1CollectorPolicy::predict_survivor_regions_evac_time() { 1.509 @@ -738,17 +764,19 @@ 1.510 return survivor_regions_evac_time; 1.511 } 1.512 1.513 -void G1CollectorPolicy::check_prediction_validity() { 1.514 +void G1CollectorPolicy::revise_young_list_target_length_if_necessary() { 1.515 guarantee( adaptive_young_list_length(), "should not call this otherwise" ); 1.516 1.517 size_t rs_lengths = _g1->young_list()->sampled_rs_lengths(); 1.518 if (rs_lengths > _rs_lengths_prediction) { 1.519 // add 10% to avoid having to recalculate often 1.520 size_t rs_lengths_prediction = rs_lengths * 1100 / 1000; 1.521 - calculate_young_list_target_length(rs_lengths_prediction); 1.522 + update_young_list_target_length(rs_lengths_prediction); 1.523 } 1.524 } 1.525 1.526 + 1.527 + 1.528 HeapWord* G1CollectorPolicy::mem_allocate_work(size_t size, 1.529 bool is_tlab, 1.530 bool* gc_overhead_limit_was_exceeded) { 1.531 @@ -855,8 +883,7 @@ 1.532 _free_regions_at_end_of_collection = _g1->free_regions(); 1.533 // Reset survivors SurvRateGroup. 1.534 _survivor_surv_rate_group->reset(); 1.535 - calculate_young_list_min_length(); 1.536 - calculate_young_list_target_length(); 1.537 + update_young_list_target_length(); 1.538 } 1.539 1.540 void G1CollectorPolicy::record_stop_world_start() { 1.541 @@ -871,6 +898,11 @@ 1.542 gclog_or_tty->print(" (%s)", full_young_gcs() ? "young" : "partial"); 1.543 } 1.544 1.545 + // We only need to do this here as the policy will only be applied 1.546 + // to the GC we're about to start. so, no point is calculating this 1.547 + // every time we calculate / recalculate the target young length. 1.548 + update_survivors_policy(); 1.549 + 1.550 assert(_g1->used() == _g1->recalculate_used(), 1.551 err_msg("sanity, used: "SIZE_FORMAT" recalculate_used: "SIZE_FORMAT, 1.552 _g1->used(), _g1->recalculate_used())); 1.553 @@ -996,8 +1028,6 @@ 1.554 _should_revert_to_full_young_gcs = false; 1.555 _last_full_young_gc = true; 1.556 _in_marking_window = false; 1.557 - if (adaptive_young_list_length()) 1.558 - calculate_young_list_target_length(); 1.559 } 1.560 1.561 void G1CollectorPolicy::record_concurrent_pause() { 1.562 @@ -1648,8 +1678,7 @@ 1.563 _in_marking_window = new_in_marking_window; 1.564 _in_marking_window_im = new_in_marking_window_im; 1.565 _free_regions_at_end_of_collection = _g1->free_regions(); 1.566 - calculate_young_list_min_length(); 1.567 - calculate_young_list_target_length(); 1.568 + update_young_list_target_length(); 1.569 1.570 // Note that _mmu_tracker->max_gc_time() returns the time in seconds. 1.571 double update_rs_time_goal_ms = _mmu_tracker->max_gc_time() * MILLIUNITS * G1RSetUpdatingPauseTimePercent / 100.0; 1.572 @@ -2324,7 +2353,7 @@ 1.573 }; 1.574 } 1.575 1.576 -void G1CollectorPolicy::calculate_max_gc_locker_expansion() { 1.577 +void G1CollectorPolicy::update_max_gc_locker_expansion() { 1.578 size_t expansion_region_num = 0; 1.579 if (GCLockerEdenExpansionPercent > 0) { 1.580 double perc = (double) GCLockerEdenExpansionPercent / 100.0; 1.581 @@ -2340,9 +2369,13 @@ 1.582 } 1.583 1.584 // Calculates survivor space parameters. 1.585 -void G1CollectorPolicy::calculate_survivors_policy() 1.586 -{ 1.587 - _max_survivor_regions = _young_list_target_length / SurvivorRatio; 1.588 +void G1CollectorPolicy::update_survivors_policy() { 1.589 + double max_survivor_regions_d = 1.590 + (double) _young_list_target_length / (double) SurvivorRatio; 1.591 + // We use ceiling so that if max_survivor_regions_d is > 0.0 (but 1.592 + // smaller than 1.0) we'll get 1. 1.593 + _max_survivor_regions = (size_t) ceil(max_survivor_regions_d); 1.594 + 1.595 _tenuring_threshold = _survivors_age_table.compute_tenuring_threshold( 1.596 HeapRegion::GrainWords * _max_survivor_regions); 1.597 }