Mercurial > hg > graal-compiler
annotate src/share/vm/gc_implementation/concurrentMarkSweep/cmsAdaptiveSizePolicy.hpp @ 10185:d50cc62e94ff
8012715: G1: GraphKit accesses PtrQueue::_index as int but is size_t
Summary: In graphKit INT operations were generated to access PtrQueue::_index which has type size_t. This is 64 bit on 64-bit machines. No problems occur on little endian machines as long as the index fits into 32 bit, but on big endian machines the upper part is read, which is zero. This leads to unnecessary branches to the slow path in the runtime.
Reviewed-by: twisti, johnc
Contributed-by: Martin Doerr <martin.doerr@sap.com>
author | johnc |
---|---|
date | Wed, 24 Apr 2013 14:48:43 -0700 |
parents | 22b8d3d181d9 |
children | 14d3f71f831d |
rev | line source |
---|---|
0 | 1 /* |
1972 | 2 * Copyright (c) 2004, 2010, Oracle and/or its affiliates. All rights reserved. |
0 | 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 * | |
1552
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
605
diff
changeset
|
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA |
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
605
diff
changeset
|
20 * or visit www.oracle.com if you need additional information or have any |
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
605
diff
changeset
|
21 * questions. |
0 | 22 * |
23 */ | |
24 | |
1972 | 25 #ifndef SHARE_VM_GC_IMPLEMENTATION_CONCURRENTMARKSWEEP_CMSADAPTIVESIZEPOLICY_HPP |
26 #define SHARE_VM_GC_IMPLEMENTATION_CONCURRENTMARKSWEEP_CMSADAPTIVESIZEPOLICY_HPP | |
27 | |
28 #include "gc_implementation/shared/adaptiveSizePolicy.hpp" | |
29 #include "runtime/timer.hpp" | |
30 | |
0 | 31 // This class keeps statistical information and computes the |
32 // size of the heap for the concurrent mark sweep collector. | |
33 // | |
34 // Cost for garbage collector include cost for | |
35 // minor collection | |
36 // concurrent collection | |
37 // stop-the-world component | |
38 // concurrent component | |
39 // major compacting collection | |
40 // uses decaying cost | |
41 | |
42 // Forward decls | |
43 class elapsedTimer; | |
44 | |
45 class CMSAdaptiveSizePolicy : public AdaptiveSizePolicy { | |
46 friend class CMSGCAdaptivePolicyCounters; | |
47 friend class CMSCollector; | |
48 private: | |
49 | |
50 // Total number of processors available | |
51 int _processor_count; | |
52 // Number of processors used by the concurrent phases of GC | |
53 // This number is assumed to be the same for all concurrent | |
54 // phases. | |
55 int _concurrent_processor_count; | |
56 | |
57 // Time that the mutators run exclusive of a particular | |
58 // phase. For example, the time the mutators run excluding | |
59 // the time during which the cms collector runs concurrently | |
60 // with the mutators. | |
61 // Between end of most recent cms reset and start of initial mark | |
62 // This may be redundant | |
63 double _latest_cms_reset_end_to_initial_mark_start_secs; | |
64 // Between end of the most recent initial mark and start of remark | |
65 double _latest_cms_initial_mark_end_to_remark_start_secs; | |
66 // Between end of most recent collection and start of | |
67 // a concurrent collection | |
68 double _latest_cms_collection_end_to_collection_start_secs; | |
69 // Times of the concurrent phases of the most recent | |
70 // concurrent collection | |
71 double _latest_cms_concurrent_marking_time_secs; | |
72 double _latest_cms_concurrent_precleaning_time_secs; | |
73 double _latest_cms_concurrent_sweeping_time_secs; | |
74 // Between end of most recent STW MSC and start of next STW MSC | |
75 double _latest_cms_msc_end_to_msc_start_time_secs; | |
76 // Between end of most recent MS and start of next MS | |
77 // This does not include any time spent during a concurrent | |
78 // collection. | |
79 double _latest_cms_ms_end_to_ms_start; | |
80 // Between start and end of the initial mark of the most recent | |
81 // concurrent collection. | |
82 double _latest_cms_initial_mark_start_to_end_time_secs; | |
83 // Between start and end of the remark phase of the most recent | |
84 // concurrent collection | |
85 double _latest_cms_remark_start_to_end_time_secs; | |
86 // Between start and end of the most recent MS STW marking phase | |
87 double _latest_cms_ms_marking_start_to_end_time_secs; | |
88 | |
89 // Pause time timers | |
90 static elapsedTimer _STW_timer; | |
91 // Concurrent collection timer. Used for total of all concurrent phases | |
92 // during 1 collection cycle. | |
93 static elapsedTimer _concurrent_timer; | |
94 | |
95 // When the size of the generation is changed, the size | |
96 // of the change will rounded up or down (depending on the | |
97 // type of change) by this value. | |
98 size_t _generation_alignment; | |
99 | |
100 // If this variable is true, the size of the young generation | |
101 // may be changed in order to reduce the pause(s) of the | |
102 // collection of the tenured generation in order to meet the | |
103 // pause time goal. It is common to change the size of the | |
104 // tenured generation in order to meet the pause time goal | |
105 // for the tenured generation. With the CMS collector for | |
106 // the tenured generation, the size of the young generation | |
107 // can have an significant affect on the pause times for collecting the | |
108 // tenured generation. | |
109 // This is a duplicate of a variable in PSAdaptiveSizePolicy. It | |
110 // is duplicated because it is not clear that it is general enough | |
111 // to go into AdaptiveSizePolicy. | |
112 int _change_young_gen_for_maj_pauses; | |
113 | |
114 // Variable that is set to true after a collection. | |
115 bool _first_after_collection; | |
116 | |
117 // Fraction of collections that are of each type | |
118 double concurrent_fraction() const; | |
119 double STW_msc_fraction() const; | |
120 double STW_ms_fraction() const; | |
121 | |
122 // This call cannot be put into the epilogue as long as some | |
123 // of the counters can be set during concurrent phases. | |
124 virtual void clear_generation_free_space_flags(); | |
125 | |
126 void set_first_after_collection() { _first_after_collection = true; } | |
127 | |
128 protected: | |
129 // Average of the sum of the concurrent times for | |
130 // one collection in seconds. | |
131 AdaptiveWeightedAverage* _avg_concurrent_time; | |
132 // Average time between concurrent collections in seconds. | |
133 AdaptiveWeightedAverage* _avg_concurrent_interval; | |
134 // Average cost of the concurrent part of a collection | |
135 // in seconds. | |
136 AdaptiveWeightedAverage* _avg_concurrent_gc_cost; | |
137 | |
138 // Average of the initial pause of a concurrent collection in seconds. | |
139 AdaptivePaddedAverage* _avg_initial_pause; | |
140 // Average of the remark pause of a concurrent collection in seconds. | |
141 AdaptivePaddedAverage* _avg_remark_pause; | |
142 | |
143 // Average of the stop-the-world (STW) (initial mark + remark) | |
144 // times in seconds for concurrent collections. | |
145 AdaptiveWeightedAverage* _avg_cms_STW_time; | |
146 // Average of the STW collection cost for concurrent collections. | |
147 AdaptiveWeightedAverage* _avg_cms_STW_gc_cost; | |
148 | |
149 // Average of the bytes free at the start of the sweep. | |
150 AdaptiveWeightedAverage* _avg_cms_free_at_sweep; | |
151 // Average of the bytes free at the end of the collection. | |
152 AdaptiveWeightedAverage* _avg_cms_free; | |
153 // Average of the bytes promoted between cms collections. | |
154 AdaptiveWeightedAverage* _avg_cms_promo; | |
155 | |
156 // stop-the-world (STW) mark-sweep-compact | |
157 // Average of the pause time in seconds for STW mark-sweep-compact | |
158 // collections. | |
159 AdaptiveWeightedAverage* _avg_msc_pause; | |
160 // Average of the interval in seconds between STW mark-sweep-compact | |
161 // collections. | |
162 AdaptiveWeightedAverage* _avg_msc_interval; | |
163 // Average of the collection costs for STW mark-sweep-compact | |
164 // collections. | |
165 AdaptiveWeightedAverage* _avg_msc_gc_cost; | |
166 | |
167 // Averages for mark-sweep collections. | |
168 // The collection may have started as a background collection | |
169 // that completes in a stop-the-world (STW) collection. | |
170 // Average of the pause time in seconds for mark-sweep | |
171 // collections. | |
172 AdaptiveWeightedAverage* _avg_ms_pause; | |
173 // Average of the interval in seconds between mark-sweep | |
174 // collections. | |
175 AdaptiveWeightedAverage* _avg_ms_interval; | |
176 // Average of the collection costs for mark-sweep | |
177 // collections. | |
178 AdaptiveWeightedAverage* _avg_ms_gc_cost; | |
179 | |
180 // These variables contain a linear fit of | |
181 // a generation size as the independent variable | |
182 // and a pause time as the dependent variable. | |
183 // For example _remark_pause_old_estimator | |
184 // is a fit of the old generation size as the | |
185 // independent variable and the remark pause | |
186 // as the dependent variable. | |
187 // remark pause time vs. cms gen size | |
188 LinearLeastSquareFit* _remark_pause_old_estimator; | |
189 // initial pause time vs. cms gen size | |
190 LinearLeastSquareFit* _initial_pause_old_estimator; | |
191 // remark pause time vs. young gen size | |
192 LinearLeastSquareFit* _remark_pause_young_estimator; | |
193 // initial pause time vs. young gen size | |
194 LinearLeastSquareFit* _initial_pause_young_estimator; | |
195 | |
196 // Accessors | |
197 int processor_count() const { return _processor_count; } | |
198 int concurrent_processor_count() const { return _concurrent_processor_count; } | |
199 | |
200 AdaptiveWeightedAverage* avg_concurrent_time() const { | |
201 return _avg_concurrent_time; | |
202 } | |
203 | |
204 AdaptiveWeightedAverage* avg_concurrent_interval() const { | |
205 return _avg_concurrent_interval; | |
206 } | |
207 | |
208 AdaptiveWeightedAverage* avg_concurrent_gc_cost() const { | |
209 return _avg_concurrent_gc_cost; | |
210 } | |
211 | |
212 AdaptiveWeightedAverage* avg_cms_STW_time() const { | |
213 return _avg_cms_STW_time; | |
214 } | |
215 | |
216 AdaptiveWeightedAverage* avg_cms_STW_gc_cost() const { | |
217 return _avg_cms_STW_gc_cost; | |
218 } | |
219 | |
220 AdaptivePaddedAverage* avg_initial_pause() const { | |
221 return _avg_initial_pause; | |
222 } | |
223 | |
224 AdaptivePaddedAverage* avg_remark_pause() const { | |
225 return _avg_remark_pause; | |
226 } | |
227 | |
228 AdaptiveWeightedAverage* avg_cms_free() const { | |
229 return _avg_cms_free; | |
230 } | |
231 | |
232 AdaptiveWeightedAverage* avg_cms_free_at_sweep() const { | |
233 return _avg_cms_free_at_sweep; | |
234 } | |
235 | |
236 AdaptiveWeightedAverage* avg_msc_pause() const { | |
237 return _avg_msc_pause; | |
238 } | |
239 | |
240 AdaptiveWeightedAverage* avg_msc_interval() const { | |
241 return _avg_msc_interval; | |
242 } | |
243 | |
244 AdaptiveWeightedAverage* avg_msc_gc_cost() const { | |
245 return _avg_msc_gc_cost; | |
246 } | |
247 | |
248 AdaptiveWeightedAverage* avg_ms_pause() const { | |
249 return _avg_ms_pause; | |
250 } | |
251 | |
252 AdaptiveWeightedAverage* avg_ms_interval() const { | |
253 return _avg_ms_interval; | |
254 } | |
255 | |
256 AdaptiveWeightedAverage* avg_ms_gc_cost() const { | |
257 return _avg_ms_gc_cost; | |
258 } | |
259 | |
260 LinearLeastSquareFit* remark_pause_old_estimator() { | |
261 return _remark_pause_old_estimator; | |
262 } | |
263 LinearLeastSquareFit* initial_pause_old_estimator() { | |
264 return _initial_pause_old_estimator; | |
265 } | |
266 LinearLeastSquareFit* remark_pause_young_estimator() { | |
267 return _remark_pause_young_estimator; | |
268 } | |
269 LinearLeastSquareFit* initial_pause_young_estimator() { | |
270 return _initial_pause_young_estimator; | |
271 } | |
272 | |
273 // These *slope() methods return the slope | |
274 // m for the linear fit of an independent | |
275 // variable vs. a dependent variable. For | |
276 // example | |
277 // remark_pause = m * old_generation_size + c | |
278 // These may be used to determine if an | |
279 // adjustment should be made to achieve a goal. | |
280 // For example, if remark_pause_old_slope() is | |
281 // positive, a reduction of the old generation | |
282 // size has on average resulted in the reduction | |
283 // of the remark pause. | |
284 float remark_pause_old_slope() { | |
285 return _remark_pause_old_estimator->slope(); | |
286 } | |
287 | |
288 float initial_pause_old_slope() { | |
289 return _initial_pause_old_estimator->slope(); | |
290 } | |
291 | |
292 float remark_pause_young_slope() { | |
293 return _remark_pause_young_estimator->slope(); | |
294 } | |
295 | |
296 float initial_pause_young_slope() { | |
297 return _initial_pause_young_estimator->slope(); | |
298 } | |
299 | |
300 // Update estimators | |
301 void update_minor_pause_old_estimator(double minor_pause_in_ms); | |
302 | |
303 // Fraction of processors used by the concurrent phases. | |
304 double concurrent_processor_fraction(); | |
305 | |
306 // Returns the total times for the concurrent part of the | |
307 // latest collection in seconds. | |
308 double concurrent_collection_time(); | |
309 | |
310 // Return the total times for the concurrent part of the | |
311 // latest collection in seconds where the times of the various | |
312 // concurrent phases are scaled by the processor fraction used | |
313 // during the phase. | |
314 double scaled_concurrent_collection_time(); | |
315 | |
316 // Dimensionless concurrent GC cost for all the concurrent phases. | |
317 double concurrent_collection_cost(double interval_in_seconds); | |
318 | |
319 // Dimensionless GC cost | |
320 double collection_cost(double pause_in_seconds, double interval_in_seconds); | |
321 | |
322 virtual GCPolicyKind kind() const { return _gc_cms_adaptive_size_policy; } | |
323 | |
324 virtual double time_since_major_gc() const; | |
325 | |
326 // This returns the maximum average for the concurrent, ms, and | |
327 // msc collections. This is meant to be used for the calculation | |
328 // of the decayed major gc cost and is not in general the | |
329 // average of all the different types of major collections. | |
330 virtual double major_gc_interval_average_for_decay() const; | |
331 | |
332 public: | |
333 CMSAdaptiveSizePolicy(size_t init_eden_size, | |
334 size_t init_promo_size, | |
335 size_t init_survivor_size, | |
336 double max_gc_minor_pause_sec, | |
337 double max_gc_pause_sec, | |
338 uint gc_cost_ratio); | |
339 | |
340 // The timers for the stop-the-world phases measure a total | |
341 // stop-the-world time. The timer is started and stopped | |
342 // for each phase but is only reset after the final checkpoint. | |
343 void checkpoint_roots_initial_begin(); | |
344 void checkpoint_roots_initial_end(GCCause::Cause gc_cause); | |
345 void checkpoint_roots_final_begin(); | |
346 void checkpoint_roots_final_end(GCCause::Cause gc_cause); | |
347 | |
348 // Methods for gathering information about the | |
349 // concurrent marking phase of the collection. | |
350 // Records the mutator times and | |
351 // resets the concurrent timer. | |
352 void concurrent_marking_begin(); | |
353 // Resets concurrent phase timer in the begin methods and | |
354 // saves the time for a phase in the end methods. | |
355 void concurrent_marking_end(); | |
356 void concurrent_sweeping_begin(); | |
357 void concurrent_sweeping_end(); | |
358 // Similar to the above (e.g., concurrent_marking_end()) and | |
359 // is used for both the precleaning an abortable precleaing | |
360 // phases. | |
361 void concurrent_precleaning_begin(); | |
362 void concurrent_precleaning_end(); | |
363 // Stops the concurrent phases time. Gathers | |
364 // information and resets the timer. | |
365 void concurrent_phases_end(GCCause::Cause gc_cause, | |
366 size_t cur_eden, | |
367 size_t cur_promo); | |
368 | |
369 // Methods for gather information about STW Mark-Sweep-Compact | |
370 void msc_collection_begin(); | |
371 void msc_collection_end(GCCause::Cause gc_cause); | |
372 | |
373 // Methods for gather information about Mark-Sweep done | |
374 // in the foreground. | |
375 void ms_collection_begin(); | |
376 void ms_collection_end(GCCause::Cause gc_cause); | |
377 | |
378 // Cost for a mark-sweep tenured gen collection done in the foreground | |
379 double ms_gc_cost() const { | |
380 return MAX2(0.0F, _avg_ms_gc_cost->average()); | |
381 } | |
382 | |
383 // Cost of collecting the tenured generation. Includes | |
384 // concurrent collection and STW collection costs | |
385 double cms_gc_cost() const; | |
386 | |
387 // Cost of STW mark-sweep-compact tenured gen collection. | |
388 double msc_gc_cost() const { | |
389 return MAX2(0.0F, _avg_msc_gc_cost->average()); | |
390 } | |
391 | |
392 // | |
393 double compacting_gc_cost() const { | |
394 double result = MIN2(1.0, minor_gc_cost() + msc_gc_cost()); | |
395 assert(result >= 0.0, "Both minor and major costs are non-negative"); | |
396 return result; | |
397 } | |
398 | |
399 // Restarts the concurrent phases timer. | |
400 void concurrent_phases_resume(); | |
401 | |
605 | 402 // Time beginning and end of the marking phase for |
0 | 403 // a synchronous MS collection. A MS collection |
404 // that finishes in the foreground can have started | |
405 // in the background. These methods capture the | |
406 // completion of the marking (after the initial | |
407 // marking) that is done in the foreground. | |
408 void ms_collection_marking_begin(); | |
409 void ms_collection_marking_end(GCCause::Cause gc_cause); | |
410 | |
411 static elapsedTimer* concurrent_timer_ptr() { | |
412 return &_concurrent_timer; | |
413 } | |
414 | |
415 AdaptiveWeightedAverage* avg_cms_promo() const { | |
416 return _avg_cms_promo; | |
417 } | |
418 | |
419 int change_young_gen_for_maj_pauses() { | |
420 return _change_young_gen_for_maj_pauses; | |
421 } | |
422 void set_change_young_gen_for_maj_pauses(int v) { | |
423 _change_young_gen_for_maj_pauses = v; | |
424 } | |
425 | |
426 void clear_internal_time_intervals(); | |
427 | |
428 | |
429 // Either calculated_promo_size_in_bytes() or promo_size() | |
430 // should be deleted. | |
431 size_t promo_size() { return _promo_size; } | |
432 void set_promo_size(size_t v) { _promo_size = v; } | |
433 | |
434 // Cost of GC for all types of collections. | |
435 virtual double gc_cost() const; | |
436 | |
437 size_t generation_alignment() { return _generation_alignment; } | |
438 | |
439 virtual void compute_young_generation_free_space(size_t cur_eden, | |
440 size_t max_eden_size); | |
441 // Calculates new survivor space size; returns a new tenuring threshold | |
442 // value. Stores new survivor size in _survivor_size. | |
6818 | 443 virtual uint compute_survivor_space_size_and_threshold( |
0 | 444 bool is_survivor_overflow, |
6818 | 445 uint tenuring_threshold, |
0 | 446 size_t survivor_limit); |
447 | |
448 virtual void compute_tenured_generation_free_space(size_t cur_tenured_free, | |
449 size_t max_tenured_available, | |
450 size_t cur_eden); | |
451 | |
452 size_t eden_decrement_aligned_down(size_t cur_eden); | |
453 size_t eden_increment_aligned_up(size_t cur_eden); | |
454 | |
455 size_t adjust_eden_for_pause_time(size_t cur_eden); | |
456 size_t adjust_eden_for_throughput(size_t cur_eden); | |
457 size_t adjust_eden_for_footprint(size_t cur_eden); | |
458 | |
459 size_t promo_decrement_aligned_down(size_t cur_promo); | |
460 size_t promo_increment_aligned_up(size_t cur_promo); | |
461 | |
462 size_t adjust_promo_for_pause_time(size_t cur_promo); | |
463 size_t adjust_promo_for_throughput(size_t cur_promo); | |
464 size_t adjust_promo_for_footprint(size_t cur_promo, size_t cur_eden); | |
465 | |
466 // Scale down the input size by the ratio of the cost to collect the | |
467 // generation to the total GC cost. | |
468 size_t scale_by_gen_gc_cost(size_t base_change, double gen_gc_cost); | |
469 | |
470 // Return the value and clear it. | |
471 bool get_and_clear_first_after_collection(); | |
472 | |
473 // Printing support | |
474 virtual bool print_adaptive_size_policy_on(outputStream* st) const; | |
475 }; | |
1972 | 476 |
477 #endif // SHARE_VM_GC_IMPLEMENTATION_CONCURRENTMARKSWEEP_CMSADAPTIVESIZEPOLICY_HPP |