annotate src/share/vm/gc_implementation/concurrentMarkSweep/concurrentMarkSweepThread.hpp @ 3285:49a67202bc67

7011855: G1: non-product flag to artificially grow the heap Summary: It introduces non-product cmd line parameter G1DummyRegionsPerGC which indicates how many "dummy" regions to allocate at the end of each GC. This allows the G1 heap to grow artificially and makes concurrent marking cycles more frequent irrespective of what the application that is running is doing. The dummy regions will be found totally empty during cleanup so this parameter can also be used to stress the concurrent cleanup operation. Reviewed-by: brutisso, johnc
author tonyp
date Tue, 19 Apr 2011 15:46:59 -0400
parents a181f3a124dd
children f08d439fab8c
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
a61af66fc99e Initial load
duke
parents:
diff changeset
1 /*
2365
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
2 * Copyright (c) 2001, 2011, Oracle and/or its affiliates. All rights reserved.
0
a61af66fc99e Initial load
duke
parents:
diff changeset
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
a61af66fc99e Initial load
duke
parents:
diff changeset
4 *
a61af66fc99e Initial load
duke
parents:
diff changeset
5 * This code is free software; you can redistribute it and/or modify it
a61af66fc99e Initial load
duke
parents:
diff changeset
6 * under the terms of the GNU General Public License version 2 only, as
a61af66fc99e Initial load
duke
parents:
diff changeset
7 * published by the Free Software Foundation.
a61af66fc99e Initial load
duke
parents:
diff changeset
8 *
a61af66fc99e Initial load
duke
parents:
diff changeset
9 * This code is distributed in the hope that it will be useful, but WITHOUT
a61af66fc99e Initial load
duke
parents:
diff changeset
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
a61af66fc99e Initial load
duke
parents:
diff changeset
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
a61af66fc99e Initial load
duke
parents:
diff changeset
12 * version 2 for more details (a copy is included in the LICENSE file that
a61af66fc99e Initial load
duke
parents:
diff changeset
13 * accompanied this code).
a61af66fc99e Initial load
duke
parents:
diff changeset
14 *
a61af66fc99e Initial load
duke
parents:
diff changeset
15 * You should have received a copy of the GNU General Public License version
a61af66fc99e Initial load
duke
parents:
diff changeset
16 * 2 along with this work; if not, write to the Free Software Foundation,
a61af66fc99e Initial load
duke
parents:
diff changeset
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
a61af66fc99e Initial load
duke
parents:
diff changeset
18 *
1552
c18cbe5936b8 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 0
diff changeset
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
c18cbe5936b8 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 0
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: 0
diff changeset
21 * questions.
0
a61af66fc99e Initial load
duke
parents:
diff changeset
22 *
a61af66fc99e Initial load
duke
parents:
diff changeset
23 */
a61af66fc99e Initial load
duke
parents:
diff changeset
24
1972
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
25 #ifndef SHARE_VM_GC_IMPLEMENTATION_CONCURRENTMARKSWEEP_CONCURRENTMARKSWEEPTHREAD_HPP
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
26 #define SHARE_VM_GC_IMPLEMENTATION_CONCURRENTMARKSWEEP_CONCURRENTMARKSWEEPTHREAD_HPP
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
27
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
28 #include "gc_implementation/concurrentMarkSweep/concurrentMarkSweepGeneration.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
29 #include "gc_implementation/shared/concurrentGCThread.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
30 #ifdef TARGET_OS_FAMILY_linux
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
31 # include "thread_linux.inline.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
32 #endif
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
33 #ifdef TARGET_OS_FAMILY_solaris
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
34 # include "thread_solaris.inline.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
35 #endif
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
36 #ifdef TARGET_OS_FAMILY_windows
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
37 # include "thread_windows.inline.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
38 #endif
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
39
0
a61af66fc99e Initial load
duke
parents:
diff changeset
40 class ConcurrentMarkSweepGeneration;
a61af66fc99e Initial load
duke
parents:
diff changeset
41 class CMSCollector;
a61af66fc99e Initial load
duke
parents:
diff changeset
42
2365
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
43 // The Concurrent Mark Sweep GC Thread
0
a61af66fc99e Initial load
duke
parents:
diff changeset
44 class ConcurrentMarkSweepThread: public ConcurrentGCThread {
a61af66fc99e Initial load
duke
parents:
diff changeset
45 friend class VMStructs;
a61af66fc99e Initial load
duke
parents:
diff changeset
46 friend class ConcurrentMarkSweepGeneration; // XXX should remove friendship
a61af66fc99e Initial load
duke
parents:
diff changeset
47 friend class CMSCollector;
a61af66fc99e Initial load
duke
parents:
diff changeset
48 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
49 virtual void run();
a61af66fc99e Initial load
duke
parents:
diff changeset
50
a61af66fc99e Initial load
duke
parents:
diff changeset
51 private:
a61af66fc99e Initial load
duke
parents:
diff changeset
52 static ConcurrentMarkSweepThread* _cmst;
a61af66fc99e Initial load
duke
parents:
diff changeset
53 static CMSCollector* _collector;
a61af66fc99e Initial load
duke
parents:
diff changeset
54 static SurrogateLockerThread* _slt;
a61af66fc99e Initial load
duke
parents:
diff changeset
55 static SurrogateLockerThread::SLT_msg_type _sltBuffer;
a61af66fc99e Initial load
duke
parents:
diff changeset
56 static Monitor* _sltMonitor;
a61af66fc99e Initial load
duke
parents:
diff changeset
57
a61af66fc99e Initial load
duke
parents:
diff changeset
58 static bool _should_terminate;
a61af66fc99e Initial load
duke
parents:
diff changeset
59
a61af66fc99e Initial load
duke
parents:
diff changeset
60 enum CMS_flag_type {
a61af66fc99e Initial load
duke
parents:
diff changeset
61 CMS_nil = NoBits,
a61af66fc99e Initial load
duke
parents:
diff changeset
62 CMS_cms_wants_token = nth_bit(0),
a61af66fc99e Initial load
duke
parents:
diff changeset
63 CMS_cms_has_token = nth_bit(1),
a61af66fc99e Initial load
duke
parents:
diff changeset
64 CMS_vm_wants_token = nth_bit(2),
a61af66fc99e Initial load
duke
parents:
diff changeset
65 CMS_vm_has_token = nth_bit(3)
a61af66fc99e Initial load
duke
parents:
diff changeset
66 };
a61af66fc99e Initial load
duke
parents:
diff changeset
67
a61af66fc99e Initial load
duke
parents:
diff changeset
68 static int _CMS_flag;
a61af66fc99e Initial load
duke
parents:
diff changeset
69
a61af66fc99e Initial load
duke
parents:
diff changeset
70 static bool CMS_flag_is_set(int b) { return (_CMS_flag & b) != 0; }
a61af66fc99e Initial load
duke
parents:
diff changeset
71 static bool set_CMS_flag(int b) { return (_CMS_flag |= b) != 0; }
a61af66fc99e Initial load
duke
parents:
diff changeset
72 static bool clear_CMS_flag(int b) { return (_CMS_flag &= ~b) != 0; }
a61af66fc99e Initial load
duke
parents:
diff changeset
73 void sleepBeforeNextCycle();
a61af66fc99e Initial load
duke
parents:
diff changeset
74
a61af66fc99e Initial load
duke
parents:
diff changeset
75 // CMS thread should yield for a young gen collection, direct allocation,
a61af66fc99e Initial load
duke
parents:
diff changeset
76 // and iCMS activity.
a61af66fc99e Initial load
duke
parents:
diff changeset
77 static char _pad_1[64 - sizeof(jint)]; // prevent cache-line sharing
a61af66fc99e Initial load
duke
parents:
diff changeset
78 static volatile jint _pending_yields;
a61af66fc99e Initial load
duke
parents:
diff changeset
79 static volatile jint _pending_decrements; // decrements to _pending_yields
a61af66fc99e Initial load
duke
parents:
diff changeset
80 static char _pad_2[64 - sizeof(jint)]; // prevent cache-line sharing
a61af66fc99e Initial load
duke
parents:
diff changeset
81
a61af66fc99e Initial load
duke
parents:
diff changeset
82 // Tracing messages, enabled by CMSTraceThreadState.
a61af66fc99e Initial load
duke
parents:
diff changeset
83 static inline void trace_state(const char* desc);
a61af66fc99e Initial load
duke
parents:
diff changeset
84
2365
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
85 static volatile int _icms_disabled; // a counter to track #iCMS disable & enable
0
a61af66fc99e Initial load
duke
parents:
diff changeset
86 static volatile bool _should_run; // iCMS may run
a61af66fc99e Initial load
duke
parents:
diff changeset
87 static volatile bool _should_stop; // iCMS should stop
a61af66fc99e Initial load
duke
parents:
diff changeset
88
a61af66fc99e Initial load
duke
parents:
diff changeset
89 // debugging
a61af66fc99e Initial load
duke
parents:
diff changeset
90 void verify_ok_to_terminate() const PRODUCT_RETURN;
a61af66fc99e Initial load
duke
parents:
diff changeset
91
a61af66fc99e Initial load
duke
parents:
diff changeset
92 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
93 // Constructor
a61af66fc99e Initial load
duke
parents:
diff changeset
94 ConcurrentMarkSweepThread(CMSCollector* collector);
a61af66fc99e Initial load
duke
parents:
diff changeset
95
a61af66fc99e Initial load
duke
parents:
diff changeset
96 static void makeSurrogateLockerThread(TRAPS);
a61af66fc99e Initial load
duke
parents:
diff changeset
97 static SurrogateLockerThread* slt() { return _slt; }
a61af66fc99e Initial load
duke
parents:
diff changeset
98
a61af66fc99e Initial load
duke
parents:
diff changeset
99 // Tester
a61af66fc99e Initial load
duke
parents:
diff changeset
100 bool is_ConcurrentGC_thread() const { return true; }
a61af66fc99e Initial load
duke
parents:
diff changeset
101
a61af66fc99e Initial load
duke
parents:
diff changeset
102 static void threads_do(ThreadClosure* tc);
a61af66fc99e Initial load
duke
parents:
diff changeset
103
a61af66fc99e Initial load
duke
parents:
diff changeset
104 // Printing
a61af66fc99e Initial load
duke
parents:
diff changeset
105 void print_on(outputStream* st) const;
a61af66fc99e Initial load
duke
parents:
diff changeset
106 void print() const { print_on(tty); }
a61af66fc99e Initial load
duke
parents:
diff changeset
107 static void print_all_on(outputStream* st);
a61af66fc99e Initial load
duke
parents:
diff changeset
108 static void print_all() { print_all_on(tty); }
a61af66fc99e Initial load
duke
parents:
diff changeset
109
a61af66fc99e Initial load
duke
parents:
diff changeset
110 // Returns the CMS Thread
a61af66fc99e Initial load
duke
parents:
diff changeset
111 static ConcurrentMarkSweepThread* cmst() { return _cmst; }
a61af66fc99e Initial load
duke
parents:
diff changeset
112 static CMSCollector* collector() { return _collector; }
a61af66fc99e Initial load
duke
parents:
diff changeset
113
a61af66fc99e Initial load
duke
parents:
diff changeset
114 // Create and start the CMS Thread, or stop it on shutdown
a61af66fc99e Initial load
duke
parents:
diff changeset
115 static ConcurrentMarkSweepThread* start(CMSCollector* collector);
a61af66fc99e Initial load
duke
parents:
diff changeset
116 static void stop();
a61af66fc99e Initial load
duke
parents:
diff changeset
117 static bool should_terminate() { return _should_terminate; }
a61af66fc99e Initial load
duke
parents:
diff changeset
118
a61af66fc99e Initial load
duke
parents:
diff changeset
119 // Synchronization using CMS token
a61af66fc99e Initial load
duke
parents:
diff changeset
120 static void synchronize(bool is_cms_thread);
a61af66fc99e Initial load
duke
parents:
diff changeset
121 static void desynchronize(bool is_cms_thread);
a61af66fc99e Initial load
duke
parents:
diff changeset
122 static bool vm_thread_has_cms_token() {
a61af66fc99e Initial load
duke
parents:
diff changeset
123 return CMS_flag_is_set(CMS_vm_has_token);
a61af66fc99e Initial load
duke
parents:
diff changeset
124 }
a61af66fc99e Initial load
duke
parents:
diff changeset
125 static bool cms_thread_has_cms_token() {
a61af66fc99e Initial load
duke
parents:
diff changeset
126 return CMS_flag_is_set(CMS_cms_has_token);
a61af66fc99e Initial load
duke
parents:
diff changeset
127 }
a61af66fc99e Initial load
duke
parents:
diff changeset
128 static bool vm_thread_wants_cms_token() {
a61af66fc99e Initial load
duke
parents:
diff changeset
129 return CMS_flag_is_set(CMS_vm_wants_token);
a61af66fc99e Initial load
duke
parents:
diff changeset
130 }
a61af66fc99e Initial load
duke
parents:
diff changeset
131 static bool cms_thread_wants_cms_token() {
a61af66fc99e Initial load
duke
parents:
diff changeset
132 return CMS_flag_is_set(CMS_cms_wants_token);
a61af66fc99e Initial load
duke
parents:
diff changeset
133 }
a61af66fc99e Initial load
duke
parents:
diff changeset
134
a61af66fc99e Initial load
duke
parents:
diff changeset
135 // Wait on CMS lock until the next synchronous GC
1887
cd3ef3fd20dd 6992998: CMSWaitDuration=0 causes hangs with +ExplicitGCInvokesConcurrent
ysr
parents: 1837
diff changeset
136 // or given timeout, whichever is earlier. A timeout value
cd3ef3fd20dd 6992998: CMSWaitDuration=0 causes hangs with +ExplicitGCInvokesConcurrent
ysr
parents: 1837
diff changeset
137 // of 0 indicates that there is no upper bound on the wait time.
cd3ef3fd20dd 6992998: CMSWaitDuration=0 causes hangs with +ExplicitGCInvokesConcurrent
ysr
parents: 1837
diff changeset
138 // A concurrent full gc request terminates the wait.
cd3ef3fd20dd 6992998: CMSWaitDuration=0 causes hangs with +ExplicitGCInvokesConcurrent
ysr
parents: 1837
diff changeset
139 void wait_on_cms_lock(long t_millis);
0
a61af66fc99e Initial load
duke
parents:
diff changeset
140
1837
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
141 // The CMS thread will yield during the work portion of its cycle
0
a61af66fc99e Initial load
duke
parents:
diff changeset
142 // only when requested to. Both synchronous and asychronous requests
1837
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
143 // are provided:
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
144 // (1) A synchronous request is used for young gen collections and
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
145 // for direct allocations. The requesting thread increments
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
146 // _pending_yields at the beginning of an operation, and decrements
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
147 // _pending_yields when that operation is completed.
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
148 // In turn, the CMS thread yields when _pending_yields is positive,
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
149 // and continues to yield until the value reverts to 0.
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
150 // (2) An asynchronous request, on the other hand, is used by iCMS
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
151 // for the stop_icms() operation. A single yield satisfies all of
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
152 // the outstanding asynch yield requests, of which there may
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
153 // occasionally be several in close succession. To accomplish
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
154 // this, an asynch-requesting thread atomically increments both
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
155 // _pending_yields and _pending_decrements. An asynchr requesting
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
156 // thread does not wait and "acknowledge" completion of an operation
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
157 // and deregister the request, like the synchronous version described
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
158 // above does. In turn, after yielding, the CMS thread decrements both
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
159 // _pending_yields and _pending_decrements by the value seen in
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
160 // _pending_decrements before the decrement.
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
161 // NOTE: The above scheme is isomorphic to having two request counters,
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
162 // one for async requests and one for sync requests, and for the CMS thread
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
163 // to check the sum of the two counters to decide whether it should yield
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
164 // and to clear only the async counter when it yields. However, it turns out
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
165 // to be more efficient for CMS code to just check a single counter
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
166 // _pending_yields that holds the sum (of both sync and async requests), and
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
167 // a second counter _pending_decrements that only holds the async requests,
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
168 // for greater efficiency, since in a typical CMS run, there are many more
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
169 // pontential (i.e. static) yield points than there are actual
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
170 // (i.e. dynamic) yields because of requests, which are few and far between.
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
171 //
0
a61af66fc99e Initial load
duke
parents:
diff changeset
172 // Note that, while "_pending_yields >= _pending_decrements" is an invariant,
a61af66fc99e Initial load
duke
parents:
diff changeset
173 // we cannot easily test that invariant, since the counters are manipulated via
a61af66fc99e Initial load
duke
parents:
diff changeset
174 // atomic instructions without explicit locking and we cannot read
a61af66fc99e Initial load
duke
parents:
diff changeset
175 // the two counters atomically together: one suggestion is to
a61af66fc99e Initial load
duke
parents:
diff changeset
176 // use (for example) 16-bit counters so as to be able to read the
a61af66fc99e Initial load
duke
parents:
diff changeset
177 // two counters atomically even on 32-bit platforms. Notice that
1837
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
178 // the second assert in acknowledge_yield_request() below does indeed
0
a61af66fc99e Initial load
duke
parents:
diff changeset
179 // check a form of the above invariant, albeit indirectly.
a61af66fc99e Initial load
duke
parents:
diff changeset
180
a61af66fc99e Initial load
duke
parents:
diff changeset
181 static void increment_pending_yields() {
a61af66fc99e Initial load
duke
parents:
diff changeset
182 Atomic::inc(&_pending_yields);
a61af66fc99e Initial load
duke
parents:
diff changeset
183 assert(_pending_yields >= 0, "can't be negative");
a61af66fc99e Initial load
duke
parents:
diff changeset
184 }
a61af66fc99e Initial load
duke
parents:
diff changeset
185 static void decrement_pending_yields() {
a61af66fc99e Initial load
duke
parents:
diff changeset
186 Atomic::dec(&_pending_yields);
a61af66fc99e Initial load
duke
parents:
diff changeset
187 assert(_pending_yields >= 0, "can't be negative");
a61af66fc99e Initial load
duke
parents:
diff changeset
188 }
a61af66fc99e Initial load
duke
parents:
diff changeset
189 static void asynchronous_yield_request() {
1837
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
190 assert(CMSIncrementalMode, "Currently only used w/iCMS");
0
a61af66fc99e Initial load
duke
parents:
diff changeset
191 increment_pending_yields();
a61af66fc99e Initial load
duke
parents:
diff changeset
192 Atomic::inc(&_pending_decrements);
a61af66fc99e Initial load
duke
parents:
diff changeset
193 assert(_pending_decrements >= 0, "can't be negative");
a61af66fc99e Initial load
duke
parents:
diff changeset
194 }
a61af66fc99e Initial load
duke
parents:
diff changeset
195 static void acknowledge_yield_request() {
a61af66fc99e Initial load
duke
parents:
diff changeset
196 jint decrement = _pending_decrements;
a61af66fc99e Initial load
duke
parents:
diff changeset
197 if (decrement > 0) {
1837
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
198 assert(CMSIncrementalMode, "Currently only used w/iCMS");
0
a61af66fc99e Initial load
duke
parents:
diff changeset
199 // Order important to preserve: _pending_yields >= _pending_decrements
a61af66fc99e Initial load
duke
parents:
diff changeset
200 Atomic::add(-decrement, &_pending_decrements);
a61af66fc99e Initial load
duke
parents:
diff changeset
201 Atomic::add(-decrement, &_pending_yields);
a61af66fc99e Initial load
duke
parents:
diff changeset
202 assert(_pending_decrements >= 0, "can't be negative");
a61af66fc99e Initial load
duke
parents:
diff changeset
203 assert(_pending_yields >= 0, "can't be negative");
a61af66fc99e Initial load
duke
parents:
diff changeset
204 }
a61af66fc99e Initial load
duke
parents:
diff changeset
205 }
a61af66fc99e Initial load
duke
parents:
diff changeset
206 static bool should_yield() { return _pending_yields > 0; }
a61af66fc99e Initial load
duke
parents:
diff changeset
207
a61af66fc99e Initial load
duke
parents:
diff changeset
208 // CMS incremental mode.
a61af66fc99e Initial load
duke
parents:
diff changeset
209 static void start_icms(); // notify thread to start a quantum of work
a61af66fc99e Initial load
duke
parents:
diff changeset
210 static void stop_icms(); // request thread to stop working
a61af66fc99e Initial load
duke
parents:
diff changeset
211 void icms_wait(); // if asked to stop, wait until notified to start
a61af66fc99e Initial load
duke
parents:
diff changeset
212
a61af66fc99e Initial load
duke
parents:
diff changeset
213 // Incremental mode is enabled globally by the flag CMSIncrementalMode. It
a61af66fc99e Initial load
duke
parents:
diff changeset
214 // must also be enabled/disabled dynamically to allow foreground collections.
2365
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
215 #define ICMS_ENABLING_ASSERT \
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
216 assert((CMSIncrementalMode && _icms_disabled >= 0) || \
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
217 (!CMSIncrementalMode && _icms_disabled <= 0), "Error")
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
218
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
219 static inline void enable_icms() {
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
220 ICMS_ENABLING_ASSERT;
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
221 Atomic::dec(&_icms_disabled);
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
222 }
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
223 static inline void disable_icms() {
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
224 ICMS_ENABLING_ASSERT;
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
225 Atomic::inc(&_icms_disabled);
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
226 }
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
227 static inline bool icms_is_disabled() {
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
228 ICMS_ENABLING_ASSERT;
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
229 return _icms_disabled > 0;
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
230 }
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
231 static inline bool icms_is_enabled() {
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
232 return !icms_is_disabled();
a181f3a124dd 6987703: iCMS: Intermittent hang with gc/gctests/CallGC/CallGC01 and +ExplicitGCInvokesConcurrent
ysr
parents: 1972
diff changeset
233 }
0
a61af66fc99e Initial load
duke
parents:
diff changeset
234 };
a61af66fc99e Initial load
duke
parents:
diff changeset
235
a61af66fc99e Initial load
duke
parents:
diff changeset
236 inline void ConcurrentMarkSweepThread::trace_state(const char* desc) {
a61af66fc99e Initial load
duke
parents:
diff changeset
237 if (CMSTraceThreadState) {
a61af66fc99e Initial load
duke
parents:
diff changeset
238 char buf[128];
a61af66fc99e Initial load
duke
parents:
diff changeset
239 TimeStamp& ts = gclog_or_tty->time_stamp();
a61af66fc99e Initial load
duke
parents:
diff changeset
240 if (!ts.is_updated()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
241 ts.update();
a61af66fc99e Initial load
duke
parents:
diff changeset
242 }
a61af66fc99e Initial load
duke
parents:
diff changeset
243 jio_snprintf(buf, sizeof(buf), " [%.3f: CMSThread %s] ",
a61af66fc99e Initial load
duke
parents:
diff changeset
244 ts.seconds(), desc);
a61af66fc99e Initial load
duke
parents:
diff changeset
245 buf[sizeof(buf) - 1] = '\0';
a61af66fc99e Initial load
duke
parents:
diff changeset
246 gclog_or_tty->print(buf);
a61af66fc99e Initial load
duke
parents:
diff changeset
247 }
a61af66fc99e Initial load
duke
parents:
diff changeset
248 }
a61af66fc99e Initial load
duke
parents:
diff changeset
249
1837
c99c53f07c14 6692906: CMS: parallel concurrent marking may be prone to hanging or stalling mutators for periods of time
ysr
parents: 1552
diff changeset
250 // For scoped increment/decrement of (synchronous) yield requests
0
a61af66fc99e Initial load
duke
parents:
diff changeset
251 class CMSSynchronousYieldRequest: public StackObj {
a61af66fc99e Initial load
duke
parents:
diff changeset
252 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
253 CMSSynchronousYieldRequest() {
a61af66fc99e Initial load
duke
parents:
diff changeset
254 ConcurrentMarkSweepThread::increment_pending_yields();
a61af66fc99e Initial load
duke
parents:
diff changeset
255 }
a61af66fc99e Initial load
duke
parents:
diff changeset
256 ~CMSSynchronousYieldRequest() {
a61af66fc99e Initial load
duke
parents:
diff changeset
257 ConcurrentMarkSweepThread::decrement_pending_yields();
a61af66fc99e Initial load
duke
parents:
diff changeset
258 }
a61af66fc99e Initial load
duke
parents:
diff changeset
259 };
a61af66fc99e Initial load
duke
parents:
diff changeset
260
a61af66fc99e Initial load
duke
parents:
diff changeset
261 // Used to emit a warning in case of unexpectedly excessive
a61af66fc99e Initial load
duke
parents:
diff changeset
262 // looping (in "apparently endless loops") in CMS code.
a61af66fc99e Initial load
duke
parents:
diff changeset
263 class CMSLoopCountWarn: public StackObj {
a61af66fc99e Initial load
duke
parents:
diff changeset
264 private:
a61af66fc99e Initial load
duke
parents:
diff changeset
265 const char* _src;
a61af66fc99e Initial load
duke
parents:
diff changeset
266 const char* _msg;
a61af66fc99e Initial load
duke
parents:
diff changeset
267 const intx _threshold;
a61af66fc99e Initial load
duke
parents:
diff changeset
268 intx _ticks;
a61af66fc99e Initial load
duke
parents:
diff changeset
269
a61af66fc99e Initial load
duke
parents:
diff changeset
270 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
271 inline CMSLoopCountWarn(const char* src, const char* msg,
a61af66fc99e Initial load
duke
parents:
diff changeset
272 const intx threshold) :
a61af66fc99e Initial load
duke
parents:
diff changeset
273 _src(src), _msg(msg), _threshold(threshold), _ticks(0) { }
a61af66fc99e Initial load
duke
parents:
diff changeset
274
a61af66fc99e Initial load
duke
parents:
diff changeset
275 inline void tick() {
a61af66fc99e Initial load
duke
parents:
diff changeset
276 _ticks++;
a61af66fc99e Initial load
duke
parents:
diff changeset
277 if (CMSLoopWarn && _ticks % _threshold == 0) {
a61af66fc99e Initial load
duke
parents:
diff changeset
278 warning("%s has looped %d times %s", _src, _ticks, _msg);
a61af66fc99e Initial load
duke
parents:
diff changeset
279 }
a61af66fc99e Initial load
duke
parents:
diff changeset
280 }
a61af66fc99e Initial load
duke
parents:
diff changeset
281 };
1972
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
282
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1887
diff changeset
283 #endif // SHARE_VM_GC_IMPLEMENTATION_CONCURRENTMARKSWEEP_CONCURRENTMARKSWEEPTHREAD_HPP