Mercurial > hg > truffle
annotate src/share/vm/services/memTracker.hpp @ 21231:0bb06deee33b
Check for null in LabelOp#setIncomingValues and JumpOp#setOutgoingValues.
author | Josef Eisl <josef.eisl@jku.at> |
---|---|
date | Tue, 05 May 2015 12:12:33 +0200 |
parents | 417e3b8d04c5 |
children |
rev | line source |
---|---|
6197 | 1 /* |
20360 | 2 * Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved. |
6197 | 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
4 * | |
5 * This code is free software; you can redistribute it and/or modify it | |
6 * under the terms of the GNU General Public License version 2 only, as | |
7 * published by the Free Software Foundation. | |
8 * | |
9 * This code is distributed in the hope that it will be useful, but WITHOUT | |
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | |
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | |
12 * version 2 for more details (a copy is included in the LICENSE file that | |
13 * accompanied this code). | |
14 * | |
15 * You should have received a copy of the GNU General Public License version | |
16 * 2 along with this work; if not, write to the Free Software Foundation, | |
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. | |
18 * | |
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA | |
20 * or visit www.oracle.com if you need additional information or have any | |
21 * questions. | |
22 * | |
23 */ | |
24 | |
25 #ifndef SHARE_VM_SERVICES_MEM_TRACKER_HPP | |
26 #define SHARE_VM_SERVICES_MEM_TRACKER_HPP | |
27 | |
20360 | 28 #include "services/nmtCommon.hpp" |
20364 | 29 #include "utilities/nativeCallStack.hpp" |
20360 | 30 |
6854
fb19af007ffc
7189254: Change makefiles for more flexibility to override defaults
jprovino
parents:
6770
diff
changeset
|
31 |
fb19af007ffc
7189254: Change makefiles for more flexibility to override defaults
jprovino
parents:
6770
diff
changeset
|
32 #if !INCLUDE_NMT |
fb19af007ffc
7189254: Change makefiles for more flexibility to override defaults
jprovino
parents:
6770
diff
changeset
|
33 |
20364 | 34 #define CURRENT_PC NativeCallStack::EMPTY_STACK |
35 #define CALLER_PC NativeCallStack::EMPTY_STACK | |
6854
fb19af007ffc
7189254: Change makefiles for more flexibility to override defaults
jprovino
parents:
6770
diff
changeset
|
36 |
20360 | 37 class Tracker : public StackObj { |
38 public: | |
39 Tracker() { } | |
40 void record(address addr, size_t size) { } | |
6854
fb19af007ffc
7189254: Change makefiles for more flexibility to override defaults
jprovino
parents:
6770
diff
changeset
|
41 }; |
fb19af007ffc
7189254: Change makefiles for more flexibility to override defaults
jprovino
parents:
6770
diff
changeset
|
42 |
20360 | 43 class MemTracker : AllStatic { |
44 public: | |
45 static inline NMT_TrackingLevel tracking_level() { return NMT_off; } | |
46 static inline void shutdown() { } | |
47 static inline void init() { } | |
48 static bool check_launcher_nmt_support(const char* value) { return true; } | |
49 static bool verify_nmt_option() { return true; } | |
50 | |
51 static inline void* record_malloc(void* mem_base, size_t size, MEMFLAGS flag, | |
52 const NativeCallStack& stack, NMT_TrackingLevel level) { return mem_base; } | |
53 static inline size_t malloc_header_size(NMT_TrackingLevel level) { return 0; } | |
54 static inline size_t malloc_header_size(void* memblock) { return 0; } | |
55 static inline void* malloc_base(void* memblock) { return memblock; } | |
56 static inline void* record_free(void* memblock) { return memblock; } | |
57 | |
58 static inline void record_new_arena(MEMFLAGS flag) { } | |
59 static inline void record_arena_free(MEMFLAGS flag) { } | |
60 static inline void record_arena_size_change(int diff, MEMFLAGS flag) { } | |
61 static inline void record_virtual_memory_reserve(void* addr, size_t size, const NativeCallStack& stack, | |
62 MEMFLAGS flag = mtNone) { } | |
63 static inline void record_virtual_memory_reserve_and_commit(void* addr, size_t size, | |
64 const NativeCallStack& stack, MEMFLAGS flag = mtNone) { } | |
65 static inline void record_virtual_memory_commit(void* addr, size_t size, const NativeCallStack& stack) { } | |
66 static inline Tracker get_virtual_memory_uncommit_tracker() { return Tracker(); } | |
67 static inline Tracker get_virtual_memory_release_tracker() { } | |
68 static inline void record_virtual_memory_type(void* addr, MEMFLAGS flag) { } | |
69 static inline void record_thread_stack(void* addr, size_t size) { } | |
70 static inline void release_thread_stack(void* addr, size_t size) { } | |
71 | |
72 static void final_report(outputStream*) { } | |
20553
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
73 static void error_report(outputStream*) { } |
20360 | 74 }; |
75 | |
76 #else | |
77 | |
78 #include "runtime/atomic.hpp" | |
79 #include "runtime/threadCritical.hpp" | |
80 #include "services/mallocTracker.hpp" | |
81 #include "services/virtualMemoryTracker.hpp" | |
82 | |
83 extern volatile bool NMT_stack_walkable; | |
84 | |
85 #define CURRENT_PC ((MemTracker::tracking_level() == NMT_detail && NMT_stack_walkable) ? \ | |
20364 | 86 NativeCallStack(0, true) : NativeCallStack::EMPTY_STACK) |
20360 | 87 #define CALLER_PC ((MemTracker::tracking_level() == NMT_detail && NMT_stack_walkable) ? \ |
20364 | 88 NativeCallStack(1, true) : NativeCallStack::EMPTY_STACK) |
20360 | 89 |
90 class MemBaseline; | |
91 class Mutex; | |
92 | |
93 // Tracker is used for guarding 'release' semantics of virtual memory operation, to avoid | |
94 // the other thread obtains and records the same region that is just 'released' by current | |
95 // thread but before it can record the operation. | |
96 class Tracker : public StackObj { | |
97 public: | |
98 enum TrackerType { | |
99 uncommit, | |
100 release | |
101 }; | |
102 | |
103 public: | |
104 Tracker(enum TrackerType type) : _type(type) { } | |
105 void record(address addr, size_t size); | |
106 private: | |
107 enum TrackerType _type; | |
108 // Virtual memory tracking data structures are protected by ThreadCritical lock. | |
109 ThreadCritical _tc; | |
6854
fb19af007ffc
7189254: Change makefiles for more flexibility to override defaults
jprovino
parents:
6770
diff
changeset
|
110 }; |
fb19af007ffc
7189254: Change makefiles for more flexibility to override defaults
jprovino
parents:
6770
diff
changeset
|
111 |
fb19af007ffc
7189254: Change makefiles for more flexibility to override defaults
jprovino
parents:
6770
diff
changeset
|
112 class MemTracker : AllStatic { |
6197 | 113 public: |
20360 | 114 static inline NMT_TrackingLevel tracking_level() { |
115 if (_tracking_level == NMT_unknown) { | |
116 // No fencing is needed here, since JVM is in single-threaded | |
117 // mode. | |
118 _tracking_level = init_tracking_level(); | |
119 _cmdline_tracking_level = _tracking_level; | |
120 } | |
6770
9a86ddfc6c8f
7188594: Print statistic collected by NMT with VM flag
zgu
parents:
6768
diff
changeset
|
121 return _tracking_level; |
9a86ddfc6c8f
7188594: Print statistic collected by NMT with VM flag
zgu
parents:
6768
diff
changeset
|
122 } |
9a86ddfc6c8f
7188594: Print statistic collected by NMT with VM flag
zgu
parents:
6768
diff
changeset
|
123 |
20360 | 124 // A late initialization, for the stuff(s) can not be |
125 // done in init_tracking_level(), which can NOT malloc | |
126 // any memory. | |
127 static void init(); | |
128 | |
129 // Shutdown native memory tracking | |
130 static void shutdown(); | |
131 | |
132 // Verify native memory tracking command line option. | |
133 // This check allows JVM to detect if compatible launcher | |
134 // is used. | |
135 // If an incompatible launcher is used, NMT may not be | |
136 // able to start, even it is enabled by command line option. | |
137 // A warning message should be given if it is encountered. | |
138 static bool check_launcher_nmt_support(const char* value); | |
139 | |
140 // This method checks native memory tracking environment | |
141 // variable value passed by launcher. | |
142 // Launcher only obligates to pass native memory tracking | |
143 // option value, but not obligates to validate the value, | |
144 // and launcher has option to discard native memory tracking | |
145 // option from the command line once it sets up the environment | |
146 // variable, so NMT has to catch the bad value here. | |
147 static bool verify_nmt_option(); | |
148 | |
149 // Transition the tracking level to specified level | |
150 static bool transition_to(NMT_TrackingLevel level); | |
151 | |
152 static inline void* record_malloc(void* mem_base, size_t size, MEMFLAGS flag, | |
153 const NativeCallStack& stack, NMT_TrackingLevel level) { | |
154 return MallocTracker::record_malloc(mem_base, size, flag, stack, level); | |
155 } | |
156 | |
157 static inline size_t malloc_header_size(NMT_TrackingLevel level) { | |
158 return MallocTracker::malloc_header_size(level); | |
6197 | 159 } |
160 | |
20360 | 161 static size_t malloc_header_size(void* memblock) { |
162 if (tracking_level() != NMT_off) { | |
163 return MallocTracker::get_header_size(memblock); | |
164 } | |
165 return 0; | |
166 } | |
167 | |
168 // To malloc base address, which is the starting address | |
169 // of malloc tracking header if tracking is enabled. | |
170 // Otherwise, it returns the same address. | |
171 static void* malloc_base(void* memblock); | |
172 | |
173 // Record malloc free and return malloc base address | |
174 static inline void* record_free(void* memblock) { | |
175 return MallocTracker::record_free(memblock); | |
6197 | 176 } |
177 | |
20360 | 178 |
179 // Record creation of an arena | |
180 static inline void record_new_arena(MEMFLAGS flag) { | |
181 if (tracking_level() < NMT_summary) return; | |
182 MallocTracker::record_new_arena(flag); | |
183 } | |
184 | |
185 // Record destruction of an arena | |
186 static inline void record_arena_free(MEMFLAGS flag) { | |
187 if (tracking_level() < NMT_summary) return; | |
188 MallocTracker::record_arena_free(flag); | |
189 } | |
6197 | 190 |
20360 | 191 // Record arena size change. Arena size is the size of all arena |
192 // chuncks that backing up the arena. | |
193 static inline void record_arena_size_change(int diff, MEMFLAGS flag) { | |
194 if (tracking_level() < NMT_summary) return; | |
195 MallocTracker::record_arena_size_change(diff, flag); | |
196 } | |
197 | |
198 static inline void record_virtual_memory_reserve(void* addr, size_t size, const NativeCallStack& stack, | |
199 MEMFLAGS flag = mtNone) { | |
200 if (tracking_level() < NMT_summary) return; | |
201 if (addr != NULL) { | |
202 ThreadCritical tc; | |
203 // Recheck to avoid potential racing during NMT shutdown | |
204 if (tracking_level() < NMT_summary) return; | |
205 VirtualMemoryTracker::add_reserved_region((address)addr, size, stack, flag); | |
8810
06db4c0afbf3
8009298: NMT: Special version of class loading/unloading with runThese stresses out NMT
zgu
parents:
7971
diff
changeset
|
206 } |
06db4c0afbf3
8009298: NMT: Special version of class loading/unloading with runThese stresses out NMT
zgu
parents:
7971
diff
changeset
|
207 } |
06db4c0afbf3
8009298: NMT: Special version of class loading/unloading with runThese stresses out NMT
zgu
parents:
7971
diff
changeset
|
208 |
20360 | 209 static inline void record_virtual_memory_reserve_and_commit(void* addr, size_t size, |
210 const NativeCallStack& stack, MEMFLAGS flag = mtNone) { | |
211 if (tracking_level() < NMT_summary) return; | |
212 if (addr != NULL) { | |
213 ThreadCritical tc; | |
214 if (tracking_level() < NMT_summary) return; | |
215 VirtualMemoryTracker::add_reserved_region((address)addr, size, | |
216 stack, flag, true); | |
12110
4c84d351cca9
8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents:
11090
diff
changeset
|
217 } |
4c84d351cca9
8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents:
11090
diff
changeset
|
218 } |
6197 | 219 |
20360 | 220 static inline void record_virtual_memory_commit(void* addr, size_t size, |
221 const NativeCallStack& stack) { | |
222 if (tracking_level() < NMT_summary) return; | |
223 if (addr != NULL) { | |
224 ThreadCritical tc; | |
225 if (tracking_level() < NMT_summary) return; | |
226 VirtualMemoryTracker::add_committed_region((address)addr, size, stack); | |
227 } | |
10986
1f4355cee9a2
8013651: NMT: reserve/release sequence id's in incorrect order due to race
zgu
parents:
10096
diff
changeset
|
228 } |
1f4355cee9a2
8013651: NMT: reserve/release sequence id's in incorrect order due to race
zgu
parents:
10096
diff
changeset
|
229 |
1f4355cee9a2
8013651: NMT: reserve/release sequence id's in incorrect order due to race
zgu
parents:
10096
diff
changeset
|
230 static inline Tracker get_virtual_memory_uncommit_tracker() { |
20360 | 231 assert(tracking_level() >= NMT_summary, "Check by caller"); |
232 return Tracker(Tracker::uncommit); | |
10986
1f4355cee9a2
8013651: NMT: reserve/release sequence id's in incorrect order due to race
zgu
parents:
10096
diff
changeset
|
233 } |
1f4355cee9a2
8013651: NMT: reserve/release sequence id's in incorrect order due to race
zgu
parents:
10096
diff
changeset
|
234 |
1f4355cee9a2
8013651: NMT: reserve/release sequence id's in incorrect order due to race
zgu
parents:
10096
diff
changeset
|
235 static inline Tracker get_virtual_memory_release_tracker() { |
20360 | 236 assert(tracking_level() >= NMT_summary, "Check by caller"); |
237 return Tracker(Tracker::release); | |
6197 | 238 } |
239 | |
20360 | 240 static inline void record_virtual_memory_type(void* addr, MEMFLAGS flag) { |
241 if (tracking_level() < NMT_summary) return; | |
242 if (addr != NULL) { | |
243 ThreadCritical tc; | |
244 if (tracking_level() < NMT_summary) return; | |
245 VirtualMemoryTracker::set_reserved_region_type((address)addr, flag); | |
6197 | 246 } |
247 } | |
248 | |
20360 | 249 static inline void record_thread_stack(void* addr, size_t size) { |
250 if (tracking_level() < NMT_summary) return; | |
251 if (addr != NULL) { | |
252 // uses thread stack malloc slot for book keeping number of threads | |
253 MallocMemorySummary::record_malloc(0, mtThreadStack); | |
254 record_virtual_memory_reserve_and_commit(addr, size, CALLER_PC, mtThreadStack); | |
255 } | |
10986
1f4355cee9a2
8013651: NMT: reserve/release sequence id's in incorrect order due to race
zgu
parents:
10096
diff
changeset
|
256 } |
1f4355cee9a2
8013651: NMT: reserve/release sequence id's in incorrect order due to race
zgu
parents:
10096
diff
changeset
|
257 |
20360 | 258 static inline void release_thread_stack(void* addr, size_t size) { |
259 if (tracking_level() < NMT_summary) return; | |
260 if (addr != NULL) { | |
261 // uses thread stack malloc slot for book keeping number of threads | |
262 MallocMemorySummary::record_free(0, mtThreadStack); | |
263 ThreadCritical tc; | |
264 if (tracking_level() < NMT_summary) return; | |
265 VirtualMemoryTracker::remove_released_region((address)addr, size); | |
10986
1f4355cee9a2
8013651: NMT: reserve/release sequence id's in incorrect order due to race
zgu
parents:
10096
diff
changeset
|
266 } |
1f4355cee9a2
8013651: NMT: reserve/release sequence id's in incorrect order due to race
zgu
parents:
10096
diff
changeset
|
267 } |
1f4355cee9a2
8013651: NMT: reserve/release sequence id's in incorrect order due to race
zgu
parents:
10096
diff
changeset
|
268 |
20360 | 269 // Query lock is used to synchronize the access to tracking data. |
270 // So far, it is only used by JCmd query, but it may be used by | |
271 // other tools. | |
272 static inline Mutex* query_lock() { return _query_lock; } | |
10986
1f4355cee9a2
8013651: NMT: reserve/release sequence id's in incorrect order due to race
zgu
parents:
10096
diff
changeset
|
273 |
20553
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
274 // Make a final report or report for hs_err file. |
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
275 static void error_report(outputStream* output) { |
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
276 if (tracking_level() >= NMT_summary) { |
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
277 report(true, output); // just print summary for error case. |
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
278 } |
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
279 } |
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
280 |
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
281 static void final_report(outputStream* output) { |
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
282 NMT_TrackingLevel level = tracking_level(); |
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
283 if (level >= NMT_summary) { |
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
284 report(level == NMT_summary, output); |
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
285 } |
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
286 } |
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
287 |
20360 | 288 |
289 // Stored baseline | |
290 static inline MemBaseline& get_baseline() { | |
291 return _baseline; | |
10986
1f4355cee9a2
8013651: NMT: reserve/release sequence id's in incorrect order due to race
zgu
parents:
10096
diff
changeset
|
292 } |
1f4355cee9a2
8013651: NMT: reserve/release sequence id's in incorrect order due to race
zgu
parents:
10096
diff
changeset
|
293 |
20360 | 294 static NMT_TrackingLevel cmdline_tracking_level() { |
295 return _cmdline_tracking_level; | |
7971
4102b59539ce
8005012: Add WB APIs to better support NMT testing
ctornqvi
parents:
7464
diff
changeset
|
296 } |
4102b59539ce
8005012: Add WB APIs to better support NMT testing
ctornqvi
parents:
7464
diff
changeset
|
297 |
20360 | 298 static void tuning_statistics(outputStream* out); |
7971
4102b59539ce
8005012: Add WB APIs to better support NMT testing
ctornqvi
parents:
7464
diff
changeset
|
299 |
6197 | 300 private: |
20360 | 301 static NMT_TrackingLevel init_tracking_level(); |
20553
417e3b8d04c5
8059100: SIGSEGV VirtualMemoryTracker::remove_released_region
coleenp
parents:
20364
diff
changeset
|
302 static void report(bool summary_only, outputStream* output); |
6197 | 303 |
20360 | 304 private: |
305 // Tracking level | |
306 static volatile NMT_TrackingLevel _tracking_level; | |
307 // If NMT option value passed by launcher through environment | |
308 // variable is valid | |
309 static bool _is_nmt_env_valid; | |
310 // command line tracking level | |
311 static NMT_TrackingLevel _cmdline_tracking_level; | |
312 // Stored baseline | |
313 static MemBaseline _baseline; | |
314 // Query lock | |
315 static Mutex* _query_lock; | |
6197 | 316 }; |
317 | |
20360 | 318 #endif // INCLUDE_NMT |
6854
fb19af007ffc
7189254: Change makefiles for more flexibility to override defaults
jprovino
parents:
6770
diff
changeset
|
319 |
6197 | 320 #endif // SHARE_VM_SERVICES_MEM_TRACKER_HPP |
20360 | 321 |