Mercurial > hg > graal-jvmci-8
annotate src/share/vm/runtime/vframe.cpp @ 1716:be3f9c242c9d
6948538: CMS: BOT walkers can fall into object allocation and initialization cracks
Summary: GC workers now recognize an intermediate transient state of blocks which are allocated but have not yet completed initialization. blk_start() calls do not attempt to determine the size of a block in the transient state, rather waiting for the block to become initialized so that it is safe to query its size. Audited and ensured the order of initialization of object fields (klass, free bit and size) to respect block state transition protocol. Also included some new assertion checking code enabled in debug mode.
Reviewed-by: chrisphi, johnc, poonam
author | ysr |
---|---|
date | Mon, 16 Aug 2010 15:58:42 -0700 |
parents | c18cbe5936b8 |
children | 1aa5b22a7716 f95d63e2154a |
rev | line source |
---|---|
0 | 1 /* |
1552
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
1547
diff
changeset
|
2 * Copyright (c) 1997, 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:
1547
diff
changeset
|
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA |
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
1547
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:
1547
diff
changeset
|
21 * questions. |
0 | 22 * |
23 */ | |
24 | |
25 # include "incls/_precompiled.incl" | |
26 # include "incls/_vframe.cpp.incl" | |
27 | |
28 vframe::vframe(const frame* fr, const RegisterMap* reg_map, JavaThread* thread) | |
29 : _reg_map(reg_map), _thread(thread) { | |
30 assert(fr != NULL, "must have frame"); | |
31 _fr = *fr; | |
32 } | |
33 | |
34 vframe::vframe(const frame* fr, JavaThread* thread) | |
35 : _reg_map(thread), _thread(thread) { | |
36 assert(fr != NULL, "must have frame"); | |
37 _fr = *fr; | |
38 } | |
39 | |
40 vframe* vframe::new_vframe(const frame* f, const RegisterMap* reg_map, JavaThread* thread) { | |
41 // Interpreter frame | |
42 if (f->is_interpreted_frame()) { | |
43 return new interpretedVFrame(f, reg_map, thread); | |
44 } | |
45 | |
46 // Compiled frame | |
47 CodeBlob* cb = f->cb(); | |
48 if (cb != NULL) { | |
49 if (cb->is_nmethod()) { | |
50 nmethod* nm = (nmethod*)cb; | |
51 return new compiledVFrame(f, reg_map, thread, nm); | |
52 } | |
53 | |
54 if (f->is_runtime_frame()) { | |
55 // Skip this frame and try again. | |
56 RegisterMap temp_map = *reg_map; | |
57 frame s = f->sender(&temp_map); | |
58 return new_vframe(&s, &temp_map, thread); | |
59 } | |
60 } | |
61 | |
62 // External frame | |
63 return new externalVFrame(f, reg_map, thread); | |
64 } | |
65 | |
66 vframe* vframe::sender() const { | |
67 RegisterMap temp_map = *register_map(); | |
68 assert(is_top(), "just checking"); | |
69 if (_fr.is_entry_frame() && _fr.is_first_frame()) return NULL; | |
70 frame s = _fr.real_sender(&temp_map); | |
71 if (s.is_first_frame()) return NULL; | |
72 return vframe::new_vframe(&s, &temp_map, thread()); | |
73 } | |
74 | |
75 vframe* vframe::top() const { | |
76 vframe* vf = (vframe*) this; | |
77 while (!vf->is_top()) vf = vf->sender(); | |
78 return vf; | |
79 } | |
80 | |
81 | |
82 javaVFrame* vframe::java_sender() const { | |
83 vframe* f = sender(); | |
84 while (f != NULL) { | |
85 if (f->is_java_frame()) return javaVFrame::cast(f); | |
86 f = f->sender(); | |
87 } | |
88 return NULL; | |
89 } | |
90 | |
91 // ------------- javaVFrame -------------- | |
92 | |
93 GrowableArray<MonitorInfo*>* javaVFrame::locked_monitors() { | |
94 assert(SafepointSynchronize::is_at_safepoint() || JavaThread::current() == thread(), | |
95 "must be at safepoint or it's a java frame of the current thread"); | |
96 | |
97 GrowableArray<MonitorInfo*>* mons = monitors(); | |
98 GrowableArray<MonitorInfo*>* result = new GrowableArray<MonitorInfo*>(mons->length()); | |
99 if (mons->is_empty()) return result; | |
100 | |
101 bool found_first_monitor = false; | |
102 ObjectMonitor *pending_monitor = thread()->current_pending_monitor(); | |
103 ObjectMonitor *waiting_monitor = thread()->current_waiting_monitor(); | |
1547
fb1a39993f69
6951319: enable solaris builds using Sun Studio 12 update 1
jcoomes
parents:
1506
diff
changeset
|
104 oop pending_obj = (pending_monitor != NULL ? (oop) pending_monitor->object() : (oop) NULL); |
fb1a39993f69
6951319: enable solaris builds using Sun Studio 12 update 1
jcoomes
parents:
1506
diff
changeset
|
105 oop waiting_obj = (waiting_monitor != NULL ? (oop) waiting_monitor->object() : (oop) NULL); |
0 | 106 |
107 for (int index = (mons->length()-1); index >= 0; index--) { | |
108 MonitorInfo* monitor = mons->at(index); | |
818
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
109 if (monitor->eliminated() && is_compiled_frame()) continue; // skip eliminated monitor |
0 | 110 oop obj = monitor->owner(); |
111 if (obj == NULL) continue; // skip unowned monitor | |
112 // | |
113 // Skip the monitor that the thread is blocked to enter or waiting on | |
114 // | |
115 if (!found_first_monitor && (obj == pending_obj || obj == waiting_obj)) { | |
116 continue; | |
117 } | |
118 found_first_monitor = true; | |
119 result->append(monitor); | |
120 } | |
121 return result; | |
122 } | |
123 | |
124 static void print_locked_object_class_name(outputStream* st, Handle obj, const char* lock_state) { | |
125 if (obj.not_null()) { | |
126 st->print("\t- %s <" INTPTR_FORMAT "> ", lock_state, (address)obj()); | |
1142 | 127 if (obj->klass() == SystemDictionary::Class_klass()) { |
0 | 128 klassOop target_klass = java_lang_Class::as_klassOop(obj()); |
129 st->print_cr("(a java.lang.Class for %s)", instanceKlass::cast(target_klass)->external_name()); | |
130 } else { | |
131 Klass* k = Klass::cast(obj->klass()); | |
132 st->print_cr("(a %s)", k->external_name()); | |
133 } | |
134 } | |
135 } | |
136 | |
137 void javaVFrame::print_lock_info_on(outputStream* st, int frame_count) { | |
138 ResourceMark rm; | |
139 | |
140 // If this is the first frame, and java.lang.Object.wait(...) then print out the receiver. | |
141 if (frame_count == 0) { | |
142 if (method()->name() == vmSymbols::wait_name() && | |
143 instanceKlass::cast(method()->method_holder())->name() == vmSymbols::java_lang_Object()) { | |
144 StackValueCollection* locs = locals(); | |
145 if (!locs->is_empty()) { | |
146 StackValue* sv = locs->at(0); | |
147 if (sv->type() == T_OBJECT) { | |
148 Handle o = locs->at(0)->get_obj(); | |
149 print_locked_object_class_name(st, o, "waiting on"); | |
150 } | |
151 } | |
152 } else if (thread()->current_park_blocker() != NULL) { | |
153 oop obj = thread()->current_park_blocker(); | |
154 Klass* k = Klass::cast(obj->klass()); | |
155 st->print_cr("\t- %s <" INTPTR_FORMAT "> (a %s)", "parking to wait for ", (address)obj, k->external_name()); | |
156 } | |
157 } | |
158 | |
159 | |
160 // Print out all monitors that we have locked or are trying to lock | |
161 GrowableArray<MonitorInfo*>* mons = monitors(); | |
162 if (!mons->is_empty()) { | |
163 bool found_first_monitor = false; | |
164 for (int index = (mons->length()-1); index >= 0; index--) { | |
165 MonitorInfo* monitor = mons->at(index); | |
818
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
166 if (monitor->eliminated() && is_compiled_frame()) { // Eliminated in compiled code |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
167 if (monitor->owner_is_scalar_replaced()) { |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
168 Klass* k = Klass::cast(monitor->owner_klass()); |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
169 st->print("\t- eliminated <owner is scalar replaced> (a %s)", k->external_name()); |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
170 } else { |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
171 oop obj = monitor->owner(); |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
172 if (obj != NULL) { |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
173 print_locked_object_class_name(st, obj, "eliminated"); |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
174 } |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
175 } |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
176 continue; |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
177 } |
0 | 178 if (monitor->owner() != NULL) { |
179 | |
180 // First, assume we have the monitor locked. If we haven't found an | |
181 // owned monitor before and this is the first frame, then we need to | |
182 // see if we have completed the lock or we are blocked trying to | |
183 // acquire it - we can only be blocked if the monitor is inflated | |
184 | |
185 const char *lock_state = "locked"; // assume we have the monitor locked | |
186 if (!found_first_monitor && frame_count == 0) { | |
818
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
187 markOop mark = monitor->owner()->mark(); |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
188 if (mark->has_monitor() && |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
189 mark->monitor() == thread()->current_pending_monitor()) { |
0 | 190 lock_state = "waiting to lock"; |
818
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
191 } |
0 | 192 } |
193 | |
194 found_first_monitor = true; | |
195 print_locked_object_class_name(st, monitor->owner(), lock_state); | |
196 } | |
197 } | |
198 } | |
199 } | |
200 | |
201 // ------------- interpretedVFrame -------------- | |
202 | |
203 u_char* interpretedVFrame::bcp() const { | |
204 return fr().interpreter_frame_bcp(); | |
205 } | |
206 | |
207 void interpretedVFrame::set_bcp(u_char* bcp) { | |
208 fr().interpreter_frame_set_bcp(bcp); | |
209 } | |
210 | |
211 intptr_t* interpretedVFrame::locals_addr_at(int offset) const { | |
212 assert(fr().is_interpreted_frame(), "frame should be an interpreted frame"); | |
213 return fr().interpreter_frame_local_at(offset); | |
214 } | |
215 | |
216 | |
217 GrowableArray<MonitorInfo*>* interpretedVFrame::monitors() const { | |
218 GrowableArray<MonitorInfo*>* result = new GrowableArray<MonitorInfo*>(5); | |
219 for (BasicObjectLock* current = (fr().previous_monitor_in_interpreter_frame(fr().interpreter_frame_monitor_begin())); | |
220 current >= fr().interpreter_frame_monitor_end(); | |
221 current = fr().previous_monitor_in_interpreter_frame(current)) { | |
818
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
222 result->push(new MonitorInfo(current->obj(), current->lock(), false, false)); |
0 | 223 } |
224 return result; | |
225 } | |
226 | |
227 int interpretedVFrame::bci() const { | |
228 return method()->bci_from(bcp()); | |
229 } | |
230 | |
231 methodOop interpretedVFrame::method() const { | |
232 return fr().interpreter_frame_method(); | |
233 } | |
234 | |
235 StackValueCollection* interpretedVFrame::locals() const { | |
236 int length = method()->max_locals(); | |
237 | |
238 if (method()->is_native()) { | |
239 // If the method is native, max_locals is not telling the truth. | |
240 // maxlocals then equals the size of parameters | |
241 length = method()->size_of_parameters(); | |
242 } | |
243 | |
244 StackValueCollection* result = new StackValueCollection(length); | |
245 | |
246 // Get oopmap describing oops and int for current bci | |
1506 | 247 InterpreterOopMap oop_mask; |
248 if (TraceDeoptimization && Verbose) { | |
249 methodHandle m_h(thread(), method()); | |
250 OopMapCache::compute_one_oop_map(m_h, bci(), &oop_mask); | |
0 | 251 } else { |
1506 | 252 method()->mask_for(bci(), &oop_mask); |
253 } | |
254 // handle locals | |
255 for(int i=0; i < length; i++) { | |
256 // Find stack location | |
257 intptr_t *addr = locals_addr_at(i); | |
0 | 258 |
1506 | 259 // Depending on oop/int put it in the right package |
260 StackValue *sv; | |
261 if (oop_mask.is_oop(i)) { | |
262 // oop value | |
263 Handle h(*(oop *)addr); | |
264 sv = new StackValue(h); | |
265 } else { | |
266 // integer | |
267 sv = new StackValue(*addr); | |
0 | 268 } |
1506 | 269 assert(sv != NULL, "sanity check"); |
270 result->add(sv); | |
0 | 271 } |
272 return result; | |
273 } | |
274 | |
275 void interpretedVFrame::set_locals(StackValueCollection* values) const { | |
276 if (values == NULL || values->size() == 0) return; | |
277 | |
278 int length = method()->max_locals(); | |
279 if (method()->is_native()) { | |
280 // If the method is native, max_locals is not telling the truth. | |
281 // maxlocals then equals the size of parameters | |
282 length = method()->size_of_parameters(); | |
283 } | |
284 | |
285 assert(length == values->size(), "Mismatch between actual stack format and supplied data"); | |
286 | |
287 // handle locals | |
288 for (int i = 0; i < length; i++) { | |
289 // Find stack location | |
290 intptr_t *addr = locals_addr_at(i); | |
291 | |
292 // Depending on oop/int put it in the right package | |
293 StackValue *sv = values->at(i); | |
294 assert(sv != NULL, "sanity check"); | |
295 if (sv->type() == T_OBJECT) { | |
296 *(oop *) addr = (sv->get_obj())(); | |
297 } else { // integer | |
298 *addr = sv->get_int(); | |
299 } | |
300 } | |
301 } | |
302 | |
303 StackValueCollection* interpretedVFrame::expressions() const { | |
304 int length = fr().interpreter_frame_expression_stack_size(); | |
305 if (method()->is_native()) { | |
306 // If the method is native, there is no expression stack | |
307 length = 0; | |
308 } | |
309 | |
310 int nof_locals = method()->max_locals(); | |
311 StackValueCollection* result = new StackValueCollection(length); | |
312 | |
1506 | 313 InterpreterOopMap oop_mask; |
314 // Get oopmap describing oops and int for current bci | |
315 if (TraceDeoptimization && Verbose) { | |
316 methodHandle m_h(method()); | |
317 OopMapCache::compute_one_oop_map(m_h, bci(), &oop_mask); | |
0 | 318 } else { |
1506 | 319 method()->mask_for(bci(), &oop_mask); |
320 } | |
321 // handle expressions | |
322 for(int i=0; i < length; i++) { | |
323 // Find stack location | |
324 intptr_t *addr = fr().interpreter_frame_expression_stack_at(i); | |
0 | 325 |
1506 | 326 // Depending on oop/int put it in the right package |
327 StackValue *sv; | |
328 if (oop_mask.is_oop(i + nof_locals)) { | |
329 // oop value | |
330 Handle h(*(oop *)addr); | |
331 sv = new StackValue(h); | |
332 } else { | |
333 // integer | |
334 sv = new StackValue(*addr); | |
0 | 335 } |
1506 | 336 assert(sv != NULL, "sanity check"); |
337 result->add(sv); | |
0 | 338 } |
339 return result; | |
340 } | |
341 | |
342 | |
343 // ------------- cChunk -------------- | |
344 | |
345 entryVFrame::entryVFrame(const frame* fr, const RegisterMap* reg_map, JavaThread* thread) | |
346 : externalVFrame(fr, reg_map, thread) {} | |
347 | |
348 | |
349 void vframeStreamCommon::found_bad_method_frame() { | |
350 // 6379830 Cut point for an assertion that occasionally fires when | |
351 // we are using the performance analyzer. | |
352 // Disable this assert when testing the analyzer with fastdebug. | |
353 // -XX:SuppressErrorAt=vframe.cpp:XXX (XXX=following line number) | |
354 assert(false, "invalid bci or invalid scope desc"); | |
355 } | |
356 | |
357 // top-frame will be skipped | |
358 vframeStream::vframeStream(JavaThread* thread, frame top_frame, | |
359 bool stop_at_java_call_stub) : vframeStreamCommon(thread) { | |
360 _stop_at_java_call_stub = stop_at_java_call_stub; | |
361 | |
362 // skip top frame, as it may not be at safepoint | |
363 _frame = top_frame.sender(&_reg_map); | |
364 while (!fill_from_frame()) { | |
365 _frame = _frame.sender(&_reg_map); | |
366 } | |
367 } | |
368 | |
369 | |
370 // Step back n frames, skip any pseudo frames in between. | |
371 // This function is used in Class.forName, Class.newInstance, Method.Invoke, | |
372 // AccessController.doPrivileged. | |
373 // | |
374 // NOTE that in JDK 1.4 this has been exposed to Java as | |
375 // sun.reflect.Reflection.getCallerClass(), which can be inlined. | |
376 // Inlined versions must match this routine's logic. | |
377 // Native method prefixing logic does not need to match since | |
378 // the method names don't match and inlining will not occur. | |
379 // See, for example, | |
380 // Parse::inline_native_Reflection_getCallerClass in | |
381 // opto/library_call.cpp. | |
382 void vframeStreamCommon::security_get_caller_frame(int depth) { | |
383 bool use_new_reflection = JDK_Version::is_gte_jdk14x_version() && UseNewReflection; | |
384 | |
385 while (!at_end()) { | |
386 if (Universe::reflect_invoke_cache()->is_same_method(method())) { | |
387 // This is Method.invoke() -- skip it | |
388 } else if (use_new_reflection && | |
389 Klass::cast(method()->method_holder()) | |
1142 | 390 ->is_subclass_of(SystemDictionary::reflect_MethodAccessorImpl_klass())) { |
0 | 391 // This is an auxilary frame -- skip it |
1152
cd37471eaecc
6914206: change way of permission checking for generated MethodHandle adapters
twisti
parents:
1142
diff
changeset
|
392 } else if (method()->is_method_handle_adapter()) { |
cd37471eaecc
6914206: change way of permission checking for generated MethodHandle adapters
twisti
parents:
1142
diff
changeset
|
393 // This is an internal adapter frame from the MethodHandleCompiler -- skip it |
0 | 394 } else { |
395 // This is non-excluded frame, we need to count it against the depth | |
396 if (depth-- <= 0) { | |
397 // we have reached the desired depth, we are done | |
398 break; | |
399 } | |
400 } | |
401 if (method()->is_prefixed_native()) { | |
402 skip_prefixed_method_and_wrappers(); | |
403 } else { | |
404 next(); | |
405 } | |
406 } | |
407 } | |
408 | |
409 | |
410 void vframeStreamCommon::skip_prefixed_method_and_wrappers() { | |
411 ResourceMark rm; | |
412 HandleMark hm; | |
413 | |
414 int method_prefix_count = 0; | |
415 char** method_prefixes = JvmtiExport::get_all_native_method_prefixes(&method_prefix_count); | |
416 KlassHandle prefixed_klass(method()->method_holder()); | |
417 const char* prefixed_name = method()->name()->as_C_string(); | |
418 size_t prefixed_name_len = strlen(prefixed_name); | |
419 int prefix_index = method_prefix_count-1; | |
420 | |
421 while (!at_end()) { | |
422 next(); | |
423 if (method()->method_holder() != prefixed_klass()) { | |
424 break; // classes don't match, can't be a wrapper | |
425 } | |
426 const char* name = method()->name()->as_C_string(); | |
427 size_t name_len = strlen(name); | |
428 size_t prefix_len = prefixed_name_len - name_len; | |
429 if (prefix_len <= 0 || strcmp(name, prefixed_name + prefix_len) != 0) { | |
430 break; // prefixed name isn't prefixed version of method name, can't be a wrapper | |
431 } | |
432 for (; prefix_index >= 0; --prefix_index) { | |
433 const char* possible_prefix = method_prefixes[prefix_index]; | |
434 size_t possible_prefix_len = strlen(possible_prefix); | |
435 if (possible_prefix_len == prefix_len && | |
436 strncmp(possible_prefix, prefixed_name, prefix_len) == 0) { | |
437 break; // matching prefix found | |
438 } | |
439 } | |
440 if (prefix_index < 0) { | |
441 break; // didn't find the prefix, can't be a wrapper | |
442 } | |
443 prefixed_name = name; | |
444 prefixed_name_len = name_len; | |
445 } | |
446 } | |
447 | |
448 | |
449 void vframeStreamCommon::skip_reflection_related_frames() { | |
450 while (!at_end() && | |
451 (JDK_Version::is_gte_jdk14x_version() && UseNewReflection && | |
1142 | 452 (Klass::cast(method()->method_holder())->is_subclass_of(SystemDictionary::reflect_MethodAccessorImpl_klass()) || |
453 Klass::cast(method()->method_holder())->is_subclass_of(SystemDictionary::reflect_ConstructorAccessorImpl_klass())))) { | |
0 | 454 next(); |
455 } | |
456 } | |
457 | |
458 | |
459 #ifndef PRODUCT | |
460 void vframe::print() { | |
461 if (WizardMode) _fr.print_value_on(tty,NULL); | |
462 } | |
463 | |
464 | |
465 void vframe::print_value() const { | |
466 ((vframe*)this)->print(); | |
467 } | |
468 | |
469 | |
470 void entryVFrame::print_value() const { | |
471 ((entryVFrame*)this)->print(); | |
472 } | |
473 | |
474 void entryVFrame::print() { | |
475 vframe::print(); | |
476 tty->print_cr("C Chunk inbetween Java"); | |
477 tty->print_cr("C link " INTPTR_FORMAT, _fr.link()); | |
478 } | |
479 | |
480 | |
481 // ------------- javaVFrame -------------- | |
482 | |
483 static void print_stack_values(const char* title, StackValueCollection* values) { | |
484 if (values->is_empty()) return; | |
485 tty->print_cr("\t%s:", title); | |
486 values->print(); | |
487 } | |
488 | |
489 | |
490 void javaVFrame::print() { | |
491 ResourceMark rm; | |
492 vframe::print(); | |
493 tty->print("\t"); | |
494 method()->print_value(); | |
495 tty->cr(); | |
496 tty->print_cr("\tbci: %d", bci()); | |
497 | |
498 print_stack_values("locals", locals()); | |
499 print_stack_values("expressions", expressions()); | |
500 | |
501 GrowableArray<MonitorInfo*>* list = monitors(); | |
502 if (list->is_empty()) return; | |
503 tty->print_cr("\tmonitor list:"); | |
504 for (int index = (list->length()-1); index >= 0; index--) { | |
505 MonitorInfo* monitor = list->at(index); | |
818
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
506 tty->print("\t obj\t"); |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
507 if (monitor->owner_is_scalar_replaced()) { |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
508 Klass* k = Klass::cast(monitor->owner_klass()); |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
509 tty->print("( is scalar replaced %s)", k->external_name()); |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
510 } else if (monitor->owner() == NULL) { |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
511 tty->print("( null )"); |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
512 } else { |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
513 monitor->owner()->print_value(); |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
514 tty->print("(" INTPTR_FORMAT ")", (address)monitor->owner()); |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
515 } |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
516 if (monitor->eliminated() && is_compiled_frame()) |
b109e761e927
6837472: com/sun/jdi/MonitorFrameInfo.java fails with AggressiveOpts in 6u14
kvn
parents:
793
diff
changeset
|
517 tty->print(" ( lock is eliminated )"); |
0 | 518 tty->cr(); |
519 tty->print("\t "); | |
520 monitor->lock()->print_on(tty); | |
521 tty->cr(); | |
522 } | |
523 } | |
524 | |
525 | |
526 void javaVFrame::print_value() const { | |
527 methodOop m = method(); | |
528 klassOop k = m->method_holder(); | |
529 tty->print_cr("frame( sp=" INTPTR_FORMAT ", unextended_sp=" INTPTR_FORMAT ", fp=" INTPTR_FORMAT ", pc=" INTPTR_FORMAT ")", | |
530 _fr.sp(), _fr.unextended_sp(), _fr.fp(), _fr.pc()); | |
531 tty->print("%s.%s", Klass::cast(k)->internal_name(), m->name()->as_C_string()); | |
532 | |
533 if (!m->is_native()) { | |
534 symbolOop source_name = instanceKlass::cast(k)->source_file_name(); | |
535 int line_number = m->line_number_from_bci(bci()); | |
536 if (source_name != NULL && (line_number != -1)) { | |
537 tty->print("(%s:%d)", source_name->as_C_string(), line_number); | |
538 } | |
539 } else { | |
540 tty->print("(Native Method)"); | |
541 } | |
542 // Check frame size and print warning if it looks suspiciously large | |
543 if (fr().sp() != NULL) { | |
793
eacd97c88873
6848466: frame::frame_size() assertion failure with -XX:+DebugDeoptimization
cfang
parents:
196
diff
changeset
|
544 RegisterMap map = *register_map(); |
eacd97c88873
6848466: frame::frame_size() assertion failure with -XX:+DebugDeoptimization
cfang
parents:
196
diff
changeset
|
545 uint size = fr().frame_size(&map); |
0 | 546 #ifdef _LP64 |
547 if (size > 8*K) warning("SUSPICIOUSLY LARGE FRAME (%d)", size); | |
548 #else | |
549 if (size > 4*K) warning("SUSPICIOUSLY LARGE FRAME (%d)", size); | |
550 #endif | |
551 } | |
552 } | |
553 | |
554 | |
555 bool javaVFrame::structural_compare(javaVFrame* other) { | |
556 // Check static part | |
557 if (method() != other->method()) return false; | |
558 if (bci() != other->bci()) return false; | |
559 | |
560 // Check locals | |
561 StackValueCollection *locs = locals(); | |
562 StackValueCollection *other_locs = other->locals(); | |
563 assert(locs->size() == other_locs->size(), "sanity check"); | |
564 int i; | |
565 for(i = 0; i < locs->size(); i++) { | |
566 // it might happen the compiler reports a conflict and | |
567 // the interpreter reports a bogus int. | |
568 if ( is_compiled_frame() && locs->at(i)->type() == T_CONFLICT) continue; | |
569 if (other->is_compiled_frame() && other_locs->at(i)->type() == T_CONFLICT) continue; | |
570 | |
571 if (!locs->at(i)->equal(other_locs->at(i))) | |
572 return false; | |
573 } | |
574 | |
575 // Check expressions | |
576 StackValueCollection* exprs = expressions(); | |
577 StackValueCollection* other_exprs = other->expressions(); | |
578 assert(exprs->size() == other_exprs->size(), "sanity check"); | |
579 for(i = 0; i < exprs->size(); i++) { | |
580 if (!exprs->at(i)->equal(other_exprs->at(i))) | |
581 return false; | |
582 } | |
583 | |
584 return true; | |
585 } | |
586 | |
587 | |
588 void javaVFrame::print_activation(int index) const { | |
589 // frame number and method | |
590 tty->print("%2d - ", index); | |
591 ((vframe*)this)->print_value(); | |
592 tty->cr(); | |
593 | |
594 if (WizardMode) { | |
595 ((vframe*)this)->print(); | |
596 tty->cr(); | |
597 } | |
598 } | |
599 | |
600 | |
601 void javaVFrame::verify() const { | |
602 } | |
603 | |
604 | |
605 void interpretedVFrame::verify() const { | |
606 } | |
607 | |
608 | |
609 // ------------- externalVFrame -------------- | |
610 | |
611 void externalVFrame::print() { | |
612 _fr.print_value_on(tty,NULL); | |
613 } | |
614 | |
615 | |
616 void externalVFrame::print_value() const { | |
617 ((vframe*)this)->print(); | |
618 } | |
619 #endif // PRODUCT |