Mercurial > hg > truffle
annotate src/share/vm/opto/doCall.cpp @ 4710:41406797186b
7113012: G1: rename not-fully-young GCs as "mixed"
Summary: Renamed partially-young GCs as mixed and fully-young GCs as young. Change all external output that includes those terms (GC log and GC ergo log) as well as any comments, fields, methods, etc. The changeset also includes very minor code tidying up (added some curly brackets).
Reviewed-by: johnc, brutisso
author | tonyp |
---|---|
date | Fri, 16 Dec 2011 02:14:27 -0500 |
parents | a04a201f0f5a |
children | b40ac3579043 |
rev | line source |
---|---|
0 | 1 /* |
2405
3d58a4983660
7022998: JSR 292 recursive method handle calls inline themselves infinitely
twisti
parents:
1972
diff
changeset
|
2 * Copyright (c) 1998, 2011, 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:
1344
diff
changeset
|
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA |
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
1344
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:
1344
diff
changeset
|
21 * questions. |
0 | 22 * |
23 */ | |
24 | |
1972 | 25 #include "precompiled.hpp" |
26 #include "ci/ciCPCache.hpp" | |
27 #include "ci/ciCallSite.hpp" | |
28 #include "ci/ciMethodHandle.hpp" | |
29 #include "classfile/vmSymbols.hpp" | |
2405
3d58a4983660
7022998: JSR 292 recursive method handle calls inline themselves infinitely
twisti
parents:
1972
diff
changeset
|
30 #include "compiler/compileBroker.hpp" |
1972 | 31 #include "compiler/compileLog.hpp" |
32 #include "interpreter/linkResolver.hpp" | |
33 #include "opto/addnode.hpp" | |
34 #include "opto/callGenerator.hpp" | |
35 #include "opto/cfgnode.hpp" | |
36 #include "opto/mulnode.hpp" | |
37 #include "opto/parse.hpp" | |
38 #include "opto/rootnode.hpp" | |
39 #include "opto/runtime.hpp" | |
40 #include "opto/subnode.hpp" | |
41 #include "prims/nativeLookup.hpp" | |
42 #include "runtime/sharedRuntime.hpp" | |
0 | 43 |
44 #ifndef PRODUCT | |
45 void trace_type_profile(ciMethod *method, int depth, int bci, ciMethod *prof_method, ciKlass *prof_klass, int site_count, int receiver_count) { | |
46 if (TraceTypeProfile || PrintInlining || PrintOptoInlining) { | |
2405
3d58a4983660
7022998: JSR 292 recursive method handle calls inline themselves infinitely
twisti
parents:
1972
diff
changeset
|
47 if (!PrintInlining) { |
3d58a4983660
7022998: JSR 292 recursive method handle calls inline themselves infinitely
twisti
parents:
1972
diff
changeset
|
48 if (!PrintOpto && !PrintCompilation) { |
3d58a4983660
7022998: JSR 292 recursive method handle calls inline themselves infinitely
twisti
parents:
1972
diff
changeset
|
49 method->print_short_name(); |
3d58a4983660
7022998: JSR 292 recursive method handle calls inline themselves infinitely
twisti
parents:
1972
diff
changeset
|
50 tty->cr(); |
3d58a4983660
7022998: JSR 292 recursive method handle calls inline themselves infinitely
twisti
parents:
1972
diff
changeset
|
51 } |
3d58a4983660
7022998: JSR 292 recursive method handle calls inline themselves infinitely
twisti
parents:
1972
diff
changeset
|
52 CompileTask::print_inlining(prof_method, depth, bci); |
0 | 53 } |
2405
3d58a4983660
7022998: JSR 292 recursive method handle calls inline themselves infinitely
twisti
parents:
1972
diff
changeset
|
54 CompileTask::print_inline_indent(depth); |
3d58a4983660
7022998: JSR 292 recursive method handle calls inline themselves infinitely
twisti
parents:
1972
diff
changeset
|
55 tty->print(" \\-> TypeProfile (%d/%d counts) = ", receiver_count, site_count); |
0 | 56 prof_klass->name()->print_symbol(); |
2405
3d58a4983660
7022998: JSR 292 recursive method handle calls inline themselves infinitely
twisti
parents:
1972
diff
changeset
|
57 tty->cr(); |
0 | 58 } |
59 } | |
60 #endif | |
61 | |
1157
c3b315a0d58a
6912063: inlining parameters need to be adjusted for some uses of the JVM
jrose
parents:
1138
diff
changeset
|
62 CallGenerator* Compile::call_generator(ciMethod* call_method, int vtable_index, bool call_is_virtual, |
c3b315a0d58a
6912063: inlining parameters need to be adjusted for some uses of the JVM
jrose
parents:
1138
diff
changeset
|
63 JVMState* jvms, bool allow_inline, |
c3b315a0d58a
6912063: inlining parameters need to be adjusted for some uses of the JVM
jrose
parents:
1138
diff
changeset
|
64 float prof_factor) { |
3371
fabcf26ee72f
6998541: JSR 292 implement missing return-type conversion for OP_RETYPE_RAW
twisti
parents:
3366
diff
changeset
|
65 ciMethod* caller = jvms->method(); |
fabcf26ee72f
6998541: JSR 292 implement missing return-type conversion for OP_RETYPE_RAW
twisti
parents:
3366
diff
changeset
|
66 int bci = jvms->bci(); |
fabcf26ee72f
6998541: JSR 292 implement missing return-type conversion for OP_RETYPE_RAW
twisti
parents:
3366
diff
changeset
|
67 Bytecodes::Code bytecode = caller->java_code_at_bci(bci); |
2462
4124a5a27707
7009600: JSR 292 Server compiler crashes in Compile::find_intrinsic(ciMethod*, bool)
jrose
parents:
2405
diff
changeset
|
68 guarantee(call_method != NULL, "failed method resolution"); |
0 | 69 |
70 // Dtrace currently doesn't work unless all calls are vanilla | |
780
c96bf21b756f
6788527: Server vm intermittently fails with assertion "live value must not be garbage" with fastdebug bits
kvn
parents:
726
diff
changeset
|
71 if (env()->dtrace_method_probes()) { |
0 | 72 allow_inline = false; |
73 } | |
74 | |
75 // Note: When we get profiling during stage-1 compiles, we want to pull | |
76 // from more specific profile data which pertains to this inlining. | |
77 // Right now, ignore the information in jvms->caller(), and do method[bci]. | |
3371
fabcf26ee72f
6998541: JSR 292 implement missing return-type conversion for OP_RETYPE_RAW
twisti
parents:
3366
diff
changeset
|
78 ciCallProfile profile = caller->call_profile_at_bci(bci); |
0 | 79 |
80 // See how many times this site has been invoked. | |
81 int site_count = profile.count(); | |
82 int receiver_count = -1; | |
83 if (call_is_virtual && UseTypeProfile && profile.has_receiver(0)) { | |
84 // Receivers in the profile structure are ordered by call counts | |
85 // so that the most called (major) receiver is profile.receiver(0). | |
86 receiver_count = profile.receiver_count(0); | |
87 } | |
88 | |
89 CompileLog* log = this->log(); | |
90 if (log != NULL) { | |
91 int rid = (receiver_count >= 0)? log->identify(profile.receiver(0)): -1; | |
1251
576e77447e3c
6923002: assert(false,"this call site should not be polymorphic")
kvn
parents:
1206
diff
changeset
|
92 int r2id = (rid != -1 && profile.has_receiver(1))? log->identify(profile.receiver(1)):-1; |
0 | 93 log->begin_elem("call method='%d' count='%d' prof_factor='%g'", |
94 log->identify(call_method), site_count, prof_factor); | |
95 if (call_is_virtual) log->print(" virtual='1'"); | |
96 if (allow_inline) log->print(" inline='1'"); | |
97 if (receiver_count >= 0) { | |
98 log->print(" receiver='%d' receiver_count='%d'", rid, receiver_count); | |
99 if (profile.has_receiver(1)) { | |
100 log->print(" receiver2='%d' receiver2_count='%d'", r2id, profile.receiver_count(1)); | |
101 } | |
102 } | |
103 log->end_elem(); | |
104 } | |
105 | |
106 // Special case the handling of certain common, profitable library | |
107 // methods. If these methods are replaced with specialized code, | |
108 // then we return it as the inlined version of the call. | |
109 // We do this before the strict f.p. check below because the | |
110 // intrinsics handle strict f.p. correctly. | |
111 if (allow_inline) { | |
4117
a04a201f0f5a
7108383: JSR 292: JRuby bench_define_method_methods.rb: assert(slow_jvms != NULL) failed: miss path must not
twisti
parents:
3901
diff
changeset
|
112 CallGenerator* cg = find_intrinsic(call_method, call_is_virtual); |
0 | 113 if (cg != NULL) return cg; |
114 } | |
115 | |
3852
fdb992d83a87
7071653: JSR 292: call site change notification should be pushed not pulled
twisti
parents:
3784
diff
changeset
|
116 // Do method handle calls. |
1823
8aa5fd5d2046
6987634: JSR 292 assert(start_bci() >= 0 && start_bci() < code_size()) failed: correct osr_bci argument
twisti
parents:
1645
diff
changeset
|
117 // NOTE: This must happen before normal inlining logic below since |
8aa5fd5d2046
6987634: JSR 292 assert(start_bci() >= 0 && start_bci() < code_size()) failed: correct osr_bci argument
twisti
parents:
1645
diff
changeset
|
118 // MethodHandle.invoke* are native methods which obviously don't |
8aa5fd5d2046
6987634: JSR 292 assert(start_bci() >= 0 && start_bci() < code_size()) failed: correct osr_bci argument
twisti
parents:
1645
diff
changeset
|
119 // have bytecodes and so normal inlining fails. |
8aa5fd5d2046
6987634: JSR 292 assert(start_bci() >= 0 && start_bci() < code_size()) failed: correct osr_bci argument
twisti
parents:
1645
diff
changeset
|
120 if (call_method->is_method_handle_invoke()) { |
3366
e2a92dd0d3d2
7042122: JSR 292: adjust various inline thresholds for JSR 292 API methods and method handle adapters
twisti
parents:
2462
diff
changeset
|
121 if (bytecode != Bytecodes::_invokedynamic) { |
1823
8aa5fd5d2046
6987634: JSR 292 assert(start_bci() >= 0 && start_bci() < code_size()) failed: correct osr_bci argument
twisti
parents:
1645
diff
changeset
|
122 GraphKit kit(jvms); |
4117
a04a201f0f5a
7108383: JSR 292: JRuby bench_define_method_methods.rb: assert(slow_jvms != NULL) failed: miss path must not
twisti
parents:
3901
diff
changeset
|
123 Node* method_handle = kit.argument(0); |
a04a201f0f5a
7108383: JSR 292: JRuby bench_define_method_methods.rb: assert(slow_jvms != NULL) failed: miss path must not
twisti
parents:
3901
diff
changeset
|
124 return CallGenerator::for_method_handle_call(method_handle, jvms, caller, call_method, profile); |
1823
8aa5fd5d2046
6987634: JSR 292 assert(start_bci() >= 0 && start_bci() < code_size()) failed: correct osr_bci argument
twisti
parents:
1645
diff
changeset
|
125 } |
8aa5fd5d2046
6987634: JSR 292 assert(start_bci() >= 0 && start_bci() < code_size()) failed: correct osr_bci argument
twisti
parents:
1645
diff
changeset
|
126 else { |
4117
a04a201f0f5a
7108383: JSR 292: JRuby bench_define_method_methods.rb: assert(slow_jvms != NULL) failed: miss path must not
twisti
parents:
3901
diff
changeset
|
127 return CallGenerator::for_invokedynamic_call(jvms, caller, call_method, profile); |
1823
8aa5fd5d2046
6987634: JSR 292 assert(start_bci() >= 0 && start_bci() < code_size()) failed: correct osr_bci argument
twisti
parents:
1645
diff
changeset
|
128 } |
8aa5fd5d2046
6987634: JSR 292 assert(start_bci() >= 0 && start_bci() < code_size()) failed: correct osr_bci argument
twisti
parents:
1645
diff
changeset
|
129 } |
8aa5fd5d2046
6987634: JSR 292 assert(start_bci() >= 0 && start_bci() < code_size()) failed: correct osr_bci argument
twisti
parents:
1645
diff
changeset
|
130 |
0 | 131 // Do not inline strict fp into non-strict code, or the reverse |
4117
a04a201f0f5a
7108383: JSR 292: JRuby bench_define_method_methods.rb: assert(slow_jvms != NULL) failed: miss path must not
twisti
parents:
3901
diff
changeset
|
132 if (caller->is_strict() ^ call_method->is_strict()) { |
0 | 133 allow_inline = false; |
134 } | |
135 | |
136 // Attempt to inline... | |
137 if (allow_inline) { | |
138 // The profile data is only partly attributable to this caller, | |
139 // scale back the call site information. | |
140 float past_uses = jvms->method()->scale_count(site_count, prof_factor); | |
141 // This is the number of times we expect the call code to be used. | |
142 float expected_uses = past_uses; | |
143 | |
144 // Try inlining a bytecoded method: | |
145 if (!call_is_virtual) { | |
146 InlineTree* ilt; | |
147 if (UseOldInlining) { | |
148 ilt = InlineTree::find_subtree_from_root(this->ilt(), jvms->caller(), jvms->method()); | |
149 } else { | |
150 // Make a disembodied, stateless ILT. | |
151 // TO DO: When UseOldInlining is removed, copy the ILT code elsewhere. | |
152 float site_invoke_ratio = prof_factor; | |
153 // Note: ilt is for the root of this parse, not the present call site. | |
3784
aabf25fa3f05
7057587: JSR 292 - crash with jruby in test/test_respond_to.rb
never
parents:
3752
diff
changeset
|
154 ilt = new InlineTree(this, jvms->method(), jvms->caller(), site_invoke_ratio, MaxInlineLevel); |
0 | 155 } |
156 WarmCallInfo scratch_ci; | |
157 if (!UseOldInlining) | |
158 scratch_ci.init(jvms, call_method, profile, prof_factor); | |
159 WarmCallInfo* ci = ilt->ok_to_inline(call_method, jvms, profile, &scratch_ci); | |
160 assert(ci != &scratch_ci, "do not let this pointer escape"); | |
161 bool allow_inline = (ci != NULL && !ci->is_cold()); | |
162 bool require_inline = (allow_inline && ci->is_hot()); | |
163 | |
164 if (allow_inline) { | |
165 CallGenerator* cg = CallGenerator::for_inline(call_method, expected_uses); | |
1080
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
166 if (require_inline && cg != NULL && should_delay_inlining(call_method, jvms)) { |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
167 // Delay the inlining of this method to give us the |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
168 // opportunity to perform some high level optimizations |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
169 // first. |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
170 return CallGenerator::for_late_inline(call_method, cg); |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
171 } |
0 | 172 if (cg == NULL) { |
173 // Fall through. | |
174 } else if (require_inline || !InlineWarmCalls) { | |
175 return cg; | |
176 } else { | |
177 CallGenerator* cold_cg = call_generator(call_method, vtable_index, call_is_virtual, jvms, false, prof_factor); | |
178 return CallGenerator::for_warm_call(ci, cold_cg, cg); | |
179 } | |
180 } | |
181 } | |
182 | |
183 // Try using the type profile. | |
184 if (call_is_virtual && site_count > 0 && receiver_count > 0) { | |
185 // The major receiver's count >= TypeProfileMajorReceiverPercent of site_count. | |
186 bool have_major_receiver = (100.*profile.receiver_prob(0) >= (float)TypeProfileMajorReceiverPercent); | |
187 ciMethod* receiver_method = NULL; | |
188 if (have_major_receiver || profile.morphism() == 1 || | |
189 (profile.morphism() == 2 && UseBimorphicInlining)) { | |
190 // receiver_method = profile.method(); | |
191 // Profiles do not suggest methods now. Look it up in the major receiver. | |
192 receiver_method = call_method->resolve_invoke(jvms->method()->holder(), | |
193 profile.receiver(0)); | |
194 } | |
195 if (receiver_method != NULL) { | |
196 // The single majority receiver sufficiently outweighs the minority. | |
197 CallGenerator* hit_cg = this->call_generator(receiver_method, | |
198 vtable_index, !call_is_virtual, jvms, allow_inline, prof_factor); | |
199 if (hit_cg != NULL) { | |
200 // Look up second receiver. | |
201 CallGenerator* next_hit_cg = NULL; | |
202 ciMethod* next_receiver_method = NULL; | |
203 if (profile.morphism() == 2 && UseBimorphicInlining) { | |
204 next_receiver_method = call_method->resolve_invoke(jvms->method()->holder(), | |
205 profile.receiver(1)); | |
206 if (next_receiver_method != NULL) { | |
207 next_hit_cg = this->call_generator(next_receiver_method, | |
208 vtable_index, !call_is_virtual, jvms, | |
209 allow_inline, prof_factor); | |
210 if (next_hit_cg != NULL && !next_hit_cg->is_inline() && | |
211 have_major_receiver && UseOnlyInlinedBimorphic) { | |
212 // Skip if we can't inline second receiver's method | |
213 next_hit_cg = NULL; | |
214 } | |
215 } | |
216 } | |
217 CallGenerator* miss_cg; | |
1206
87684f1a88b5
6614597: Performance variability in jvm2008 xml.validation
kvn
parents:
1157
diff
changeset
|
218 Deoptimization::DeoptReason reason = (profile.morphism() == 2) ? |
87684f1a88b5
6614597: Performance variability in jvm2008 xml.validation
kvn
parents:
1157
diff
changeset
|
219 Deoptimization::Reason_bimorphic : |
87684f1a88b5
6614597: Performance variability in jvm2008 xml.validation
kvn
parents:
1157
diff
changeset
|
220 Deoptimization::Reason_class_check; |
0 | 221 if (( profile.morphism() == 1 || |
222 (profile.morphism() == 2 && next_hit_cg != NULL) ) && | |
1206
87684f1a88b5
6614597: Performance variability in jvm2008 xml.validation
kvn
parents:
1157
diff
changeset
|
223 !too_many_traps(jvms->method(), jvms->bci(), reason) |
0 | 224 ) { |
225 // Generate uncommon trap for class check failure path | |
226 // in case of monomorphic or bimorphic virtual call site. | |
1206
87684f1a88b5
6614597: Performance variability in jvm2008 xml.validation
kvn
parents:
1157
diff
changeset
|
227 miss_cg = CallGenerator::for_uncommon_trap(call_method, reason, |
0 | 228 Deoptimization::Action_maybe_recompile); |
229 } else { | |
230 // Generate virtual call for class check failure path | |
231 // in case of polymorphic virtual call site. | |
232 miss_cg = CallGenerator::for_virtual_call(call_method, vtable_index); | |
233 } | |
234 if (miss_cg != NULL) { | |
235 if (next_hit_cg != NULL) { | |
2405
3d58a4983660
7022998: JSR 292 recursive method handle calls inline themselves infinitely
twisti
parents:
1972
diff
changeset
|
236 NOT_PRODUCT(trace_type_profile(jvms->method(), jvms->depth() - 1, jvms->bci(), next_receiver_method, profile.receiver(1), site_count, profile.receiver_count(1))); |
0 | 237 // We don't need to record dependency on a receiver here and below. |
238 // Whenever we inline, the dependency is added by Parse::Parse(). | |
239 miss_cg = CallGenerator::for_predicted_call(profile.receiver(1), miss_cg, next_hit_cg, PROB_MAX); | |
240 } | |
241 if (miss_cg != NULL) { | |
2405
3d58a4983660
7022998: JSR 292 recursive method handle calls inline themselves infinitely
twisti
parents:
1972
diff
changeset
|
242 NOT_PRODUCT(trace_type_profile(jvms->method(), jvms->depth() - 1, jvms->bci(), receiver_method, profile.receiver(0), site_count, receiver_count)); |
4117
a04a201f0f5a
7108383: JSR 292: JRuby bench_define_method_methods.rb: assert(slow_jvms != NULL) failed: miss path must not
twisti
parents:
3901
diff
changeset
|
243 CallGenerator* cg = CallGenerator::for_predicted_call(profile.receiver(0), miss_cg, hit_cg, profile.receiver_prob(0)); |
0 | 244 if (cg != NULL) return cg; |
245 } | |
246 } | |
247 } | |
248 } | |
249 } | |
250 } | |
251 | |
252 // There was no special inlining tactic, or it bailed out. | |
253 // Use a more generic tactic, like a simple call. | |
254 if (call_is_virtual) { | |
255 return CallGenerator::for_virtual_call(call_method, vtable_index); | |
256 } else { | |
257 // Class Hierarchy Analysis or Type Profile reveals a unique target, | |
258 // or it is a static or special call. | |
1080
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
259 return CallGenerator::for_direct_call(call_method, should_delay_inlining(call_method, jvms)); |
0 | 260 } |
261 } | |
262 | |
1080
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
263 // Return true for methods that shouldn't be inlined early so that |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
264 // they are easier to analyze and optimize as intrinsics. |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
265 bool Compile::should_delay_inlining(ciMethod* call_method, JVMState* jvms) { |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
266 if (has_stringbuilder()) { |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
267 |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
268 if ((call_method->holder() == C->env()->StringBuilder_klass() || |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
269 call_method->holder() == C->env()->StringBuffer_klass()) && |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
270 (jvms->method()->holder() == C->env()->StringBuilder_klass() || |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
271 jvms->method()->holder() == C->env()->StringBuffer_klass())) { |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
272 // Delay SB calls only when called from non-SB code |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
273 return false; |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
274 } |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
275 |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
276 switch (call_method->intrinsic_id()) { |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
277 case vmIntrinsics::_StringBuilder_void: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
278 case vmIntrinsics::_StringBuilder_int: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
279 case vmIntrinsics::_StringBuilder_String: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
280 case vmIntrinsics::_StringBuilder_append_char: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
281 case vmIntrinsics::_StringBuilder_append_int: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
282 case vmIntrinsics::_StringBuilder_append_String: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
283 case vmIntrinsics::_StringBuilder_toString: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
284 case vmIntrinsics::_StringBuffer_void: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
285 case vmIntrinsics::_StringBuffer_int: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
286 case vmIntrinsics::_StringBuffer_String: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
287 case vmIntrinsics::_StringBuffer_append_char: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
288 case vmIntrinsics::_StringBuffer_append_int: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
289 case vmIntrinsics::_StringBuffer_append_String: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
290 case vmIntrinsics::_StringBuffer_toString: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
291 case vmIntrinsics::_Integer_toString: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
292 return true; |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
293 |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
294 case vmIntrinsics::_String_String: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
295 { |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
296 Node* receiver = jvms->map()->in(jvms->argoff() + 1); |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
297 if (receiver->is_Proj() && receiver->in(0)->is_CallStaticJava()) { |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
298 CallStaticJavaNode* csj = receiver->in(0)->as_CallStaticJava(); |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
299 ciMethod* m = csj->method(); |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
300 if (m != NULL && |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
301 (m->intrinsic_id() == vmIntrinsics::_StringBuffer_toString || |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
302 m->intrinsic_id() == vmIntrinsics::_StringBuilder_toString)) |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
303 // Delay String.<init>(new SB()) |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
304 return true; |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
305 } |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
306 return false; |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
307 } |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
308 |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
309 default: |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
310 return false; |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
311 } |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
312 } |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
313 return false; |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
314 } |
7c57aead6d3e
6892658: C2 should optimize some stringbuilder patterns
never
parents:
844
diff
changeset
|
315 |
0 | 316 |
317 // uncommon-trap call-sites where callee is unloaded, uninitialized or will not link | |
318 bool Parse::can_not_compile_call_site(ciMethod *dest_method, ciInstanceKlass* klass) { | |
319 // Additional inputs to consider... | |
320 // bc = bc() | |
321 // caller = method() | |
322 // iter().get_method_holder_index() | |
323 assert( dest_method->is_loaded(), "ciTypeFlow should not let us get here" ); | |
324 // Interface classes can be loaded & linked and never get around to | |
325 // being initialized. Uncommon-trap for not-initialized static or | |
326 // v-calls. Let interface calls happen. | |
1137
97125851f396
6829187: compiler optimizations required for JSR 292
twisti
parents:
1135
diff
changeset
|
327 ciInstanceKlass* holder_klass = dest_method->holder(); |
1645
3941674cc7fa
6958668: repeated uncommon trapping for new of klass which is being initialized
never
parents:
1552
diff
changeset
|
328 if (!holder_klass->is_being_initialized() && |
3941674cc7fa
6958668: repeated uncommon trapping for new of klass which is being initialized
never
parents:
1552
diff
changeset
|
329 !holder_klass->is_initialized() && |
0 | 330 !holder_klass->is_interface()) { |
331 uncommon_trap(Deoptimization::Reason_uninitialized, | |
332 Deoptimization::Action_reinterpret, | |
333 holder_klass); | |
334 return true; | |
335 } | |
336 | |
337 assert(dest_method->will_link(method()->holder(), klass, bc()), "dest_method: typeflow responsibility"); | |
338 return false; | |
339 } | |
340 | |
341 | |
342 //------------------------------do_call---------------------------------------- | |
343 // Handle your basic call. Inline if we can & want to, else just setup call. | |
344 void Parse::do_call() { | |
345 // It's likely we are going to add debug info soon. | |
346 // Also, if we inline a guy who eventually needs debug info for this JVMS, | |
347 // our contribution to it is cleaned up right here. | |
348 kill_dead_locals(); | |
349 | |
350 // Set frequently used booleans | |
351 bool is_virtual = bc() == Bytecodes::_invokevirtual; | |
352 bool is_virtual_or_interface = is_virtual || bc() == Bytecodes::_invokeinterface; | |
353 bool has_receiver = is_virtual_or_interface || bc() == Bytecodes::_invokespecial; | |
1137
97125851f396
6829187: compiler optimizations required for JSR 292
twisti
parents:
1135
diff
changeset
|
354 bool is_invokedynamic = bc() == Bytecodes::_invokedynamic; |
0 | 355 |
356 // Find target being called | |
357 bool will_link; | |
358 ciMethod* dest_method = iter().get_method(will_link); | |
359 ciInstanceKlass* holder_klass = dest_method->holder(); | |
360 ciKlass* holder = iter().get_declared_method_holder(); | |
361 ciInstanceKlass* klass = ciEnv::get_instance_klass_for_declared_method_holder(holder); | |
362 | |
1137
97125851f396
6829187: compiler optimizations required for JSR 292
twisti
parents:
1135
diff
changeset
|
363 int nargs = dest_method->arg_size(); |
97125851f396
6829187: compiler optimizations required for JSR 292
twisti
parents:
1135
diff
changeset
|
364 if (is_invokedynamic) nargs -= 1; |
0 | 365 |
366 // uncommon-trap when callee is unloaded, uninitialized or will not link | |
367 // bailout when too many arguments for register representation | |
368 if (!will_link || can_not_compile_call_site(dest_method, klass)) { | |
369 #ifndef PRODUCT | |
370 if (PrintOpto && (Verbose || WizardMode)) { | |
371 method()->print_name(); tty->print_cr(" can not compile call at bci %d to:", bci()); | |
372 dest_method->print_name(); tty->cr(); | |
373 } | |
374 #endif | |
375 return; | |
376 } | |
377 assert(holder_klass->is_loaded(), ""); | |
1137
97125851f396
6829187: compiler optimizations required for JSR 292
twisti
parents:
1135
diff
changeset
|
378 assert((dest_method->is_static() || is_invokedynamic) == !has_receiver , "must match bc"); |
0 | 379 // Note: this takes into account invokeinterface of methods declared in java/lang/Object, |
380 // which should be invokevirtuals but according to the VM spec may be invokeinterfaces | |
381 assert(holder_klass->is_interface() || holder_klass->super() == NULL || (bc() != Bytecodes::_invokeinterface), "must match bc"); | |
382 // Note: In the absence of miranda methods, an abstract class K can perform | |
383 // an invokevirtual directly on an interface method I.m if K implements I. | |
384 | |
385 // --------------------- | |
386 // Does Class Hierarchy Analysis reveal only a single target of a v-call? | |
387 // Then we may inline or make a static call, but become dependent on there being only 1 target. | |
388 // Does the call-site type profile reveal only one receiver? | |
389 // Then we may introduce a run-time check and inline on the path where it succeeds. | |
390 // The other path may uncommon_trap, check for another receiver, or do a v-call. | |
391 | |
392 // Choose call strategy. | |
393 bool call_is_virtual = is_virtual_or_interface; | |
394 int vtable_index = methodOopDesc::invalid_vtable_index; | |
395 ciMethod* call_method = dest_method; | |
396 | |
397 // Try to get the most accurate receiver type | |
398 if (is_virtual_or_interface) { | |
399 Node* receiver_node = stack(sp() - nargs); | |
400 const TypeOopPtr* receiver_type = _gvn.type(receiver_node)->isa_oopptr(); | |
401 ciMethod* optimized_virtual_method = optimize_inlining(method(), bci(), klass, dest_method, receiver_type); | |
402 | |
403 // Have the call been sufficiently improved such that it is no longer a virtual? | |
404 if (optimized_virtual_method != NULL) { | |
405 call_method = optimized_virtual_method; | |
406 call_is_virtual = false; | |
407 } else if (!UseInlineCaches && is_virtual && call_method->is_loaded()) { | |
408 // We can make a vtable call at this site | |
409 vtable_index = call_method->resolve_vtable_index(method()->holder(), klass); | |
410 } | |
411 } | |
412 | |
413 // Note: It's OK to try to inline a virtual call. | |
414 // The call generator will not attempt to inline a polymorphic call | |
415 // unless it knows how to optimize the receiver dispatch. | |
416 bool try_inline = (C->do_inlining() || InlineAccessors); | |
417 | |
418 // --------------------- | |
419 inc_sp(- nargs); // Temporarily pop args for JVM state of call | |
420 JVMState* jvms = sync_jvms(); | |
421 | |
422 // --------------------- | |
423 // Decide call tactic. | |
424 // This call checks with CHA, the interpreter profile, intrinsics table, etc. | |
425 // It decides whether inlining is desirable or not. | |
426 CallGenerator* cg = C->call_generator(call_method, vtable_index, call_is_virtual, jvms, try_inline, prof_factor()); | |
427 | |
428 // --------------------- | |
429 // Round double arguments before call | |
430 round_double_arguments(dest_method); | |
431 | |
432 #ifndef PRODUCT | |
433 // bump global counters for calls | |
434 count_compiled_calls(false/*at_method_entry*/, cg->is_inline()); | |
435 | |
436 // Record first part of parsing work for this call | |
437 parse_histogram()->record_change(); | |
438 #endif // not PRODUCT | |
439 | |
440 assert(jvms == this->jvms(), "still operating on the right JVMS"); | |
441 assert(jvms_in_sync(), "jvms must carry full info into CG"); | |
442 | |
443 // save across call, for a subsequent cast_not_null. | |
444 Node* receiver = has_receiver ? argument(0) : NULL; | |
445 | |
446 // Bump method data counters (We profile *before* the call is made | |
447 // because exceptions don't return to the call site.) | |
448 profile_call(receiver); | |
449 | |
450 JVMState* new_jvms; | |
451 if ((new_jvms = cg->generate(jvms)) == NULL) { | |
452 // When inlining attempt fails (e.g., too many arguments), | |
453 // it may contaminate the current compile state, making it | |
454 // impossible to pull back and try again. Once we call | |
455 // cg->generate(), we are committed. If it fails, the whole | |
456 // compilation task is compromised. | |
457 if (failing()) return; | |
458 #ifndef PRODUCT | |
459 if (PrintOpto || PrintOptoInlining || PrintInlining) { | |
460 // Only one fall-back, so if an intrinsic fails, ignore any bytecodes. | |
461 if (cg->is_intrinsic() && call_method->code_size() > 0) { | |
462 tty->print("Bailed out of intrinsic, will not inline: "); | |
463 call_method->print_name(); tty->cr(); | |
464 } | |
465 } | |
466 #endif | |
467 // This can happen if a library intrinsic is available, but refuses | |
468 // the call site, perhaps because it did not match a pattern the | |
469 // intrinsic was expecting to optimize. The fallback position is | |
470 // to call out-of-line. | |
471 try_inline = false; // Inline tactic bailed out. | |
472 cg = C->call_generator(call_method, vtable_index, call_is_virtual, jvms, try_inline, prof_factor()); | |
473 if ((new_jvms = cg->generate(jvms)) == NULL) { | |
474 guarantee(failing(), "call failed to generate: calls should work"); | |
475 return; | |
476 } | |
477 } | |
478 | |
479 if (cg->is_inline()) { | |
67 | 480 // Accumulate has_loops estimate |
481 C->set_has_loops(C->has_loops() || call_method->has_loops()); | |
0 | 482 C->env()->notice_inlined_method(call_method); |
483 } | |
484 | |
485 // Reset parser state from [new_]jvms, which now carries results of the call. | |
486 // Return value (if any) is already pushed on the stack by the cg. | |
487 add_exception_states_from(new_jvms); | |
488 if (new_jvms->map()->control() == top()) { | |
489 stop_and_kill_map(); | |
490 } else { | |
491 assert(new_jvms->same_calls_as(jvms), "method/bci left unchanged"); | |
492 set_jvms(new_jvms); | |
493 } | |
494 | |
495 if (!stopped()) { | |
496 // This was some sort of virtual call, which did a null check for us. | |
497 // Now we can assert receiver-not-null, on the normal return path. | |
498 if (receiver != NULL && cg->is_virtual()) { | |
499 Node* cast = cast_not_null(receiver); | |
500 // %%% assert(receiver == cast, "should already have cast the receiver"); | |
501 } | |
502 | |
503 // Round double result after a call from strict to non-strict code | |
504 round_double_result(dest_method); | |
505 | |
506 // If the return type of the method is not loaded, assert that the | |
507 // value we got is a null. Otherwise, we need to recompile. | |
508 if (!dest_method->return_type()->is_loaded()) { | |
509 #ifndef PRODUCT | |
510 if (PrintOpto && (Verbose || WizardMode)) { | |
511 method()->print_name(); tty->print_cr(" asserting nullness of result at bci: %d", bci()); | |
512 dest_method->print_name(); tty->cr(); | |
513 } | |
514 #endif | |
515 if (C->log() != NULL) { | |
516 C->log()->elem("assert_null reason='return' klass='%d'", | |
517 C->log()->identify(dest_method->return_type())); | |
518 } | |
519 // If there is going to be a trap, put it at the next bytecode: | |
520 set_bci(iter().next_bci()); | |
521 do_null_assert(peek(), T_OBJECT); | |
522 set_bci(iter().cur_bci()); // put it back | |
523 } | |
524 } | |
525 | |
526 // Restart record of parsing work after possible inlining of call | |
527 #ifndef PRODUCT | |
528 parse_histogram()->set_initial_state(bc()); | |
529 #endif | |
530 } | |
531 | |
532 //---------------------------catch_call_exceptions----------------------------- | |
533 // Put a Catch and CatchProj nodes behind a just-created call. | |
534 // Send their caught exceptions to the proper handler. | |
535 // This may be used after a call to the rethrow VM stub, | |
536 // when it is needed to process unloaded exception classes. | |
537 void Parse::catch_call_exceptions(ciExceptionHandlerStream& handlers) { | |
538 // Exceptions are delivered through this channel: | |
539 Node* i_o = this->i_o(); | |
540 | |
541 // Add a CatchNode. | |
542 GrowableArray<int>* bcis = new (C->node_arena()) GrowableArray<int>(C->node_arena(), 8, 0, -1); | |
543 GrowableArray<const Type*>* extypes = new (C->node_arena()) GrowableArray<const Type*>(C->node_arena(), 8, 0, NULL); | |
544 GrowableArray<int>* saw_unloaded = new (C->node_arena()) GrowableArray<int>(C->node_arena(), 8, 0, 0); | |
545 | |
546 for (; !handlers.is_done(); handlers.next()) { | |
547 ciExceptionHandler* h = handlers.handler(); | |
548 int h_bci = h->handler_bci(); | |
549 ciInstanceKlass* h_klass = h->is_catch_all() ? env()->Throwable_klass() : h->catch_klass(); | |
550 // Do not introduce unloaded exception types into the graph: | |
551 if (!h_klass->is_loaded()) { | |
552 if (saw_unloaded->contains(h_bci)) { | |
553 /* We've already seen an unloaded exception with h_bci, | |
554 so don't duplicate. Duplication will cause the CatchNode to be | |
555 unnecessarily large. See 4713716. */ | |
556 continue; | |
557 } else { | |
558 saw_unloaded->append(h_bci); | |
559 } | |
560 } | |
561 const Type* h_extype = TypeOopPtr::make_from_klass(h_klass); | |
562 // (We use make_from_klass because it respects UseUniqueSubclasses.) | |
563 h_extype = h_extype->join(TypeInstPtr::NOTNULL); | |
564 assert(!h_extype->empty(), "sanity"); | |
565 // Note: It's OK if the BCIs repeat themselves. | |
566 bcis->append(h_bci); | |
567 extypes->append(h_extype); | |
568 } | |
569 | |
570 int len = bcis->length(); | |
571 CatchNode *cn = new (C, 2) CatchNode(control(), i_o, len+1); | |
572 Node *catch_ = _gvn.transform(cn); | |
573 | |
574 // now branch with the exception state to each of the (potential) | |
575 // handlers | |
576 for(int i=0; i < len; i++) { | |
577 // Setup JVM state to enter the handler. | |
578 PreserveJVMState pjvms(this); | |
579 // Locals are just copied from before the call. | |
580 // Get control from the CatchNode. | |
581 int handler_bci = bcis->at(i); | |
582 Node* ctrl = _gvn.transform( new (C, 1) CatchProjNode(catch_, i+1,handler_bci)); | |
583 // This handler cannot happen? | |
584 if (ctrl == top()) continue; | |
585 set_control(ctrl); | |
586 | |
587 // Create exception oop | |
588 const TypeInstPtr* extype = extypes->at(i)->is_instptr(); | |
589 Node *ex_oop = _gvn.transform(new (C, 2) CreateExNode(extypes->at(i), ctrl, i_o)); | |
590 | |
591 // Handle unloaded exception classes. | |
592 if (saw_unloaded->contains(handler_bci)) { | |
593 // An unloaded exception type is coming here. Do an uncommon trap. | |
594 #ifndef PRODUCT | |
595 // We do not expect the same handler bci to take both cold unloaded | |
596 // and hot loaded exceptions. But, watch for it. | |
597 if (extype->is_loaded()) { | |
598 tty->print_cr("Warning: Handler @%d takes mixed loaded/unloaded exceptions in "); | |
599 method()->print_name(); tty->cr(); | |
600 } else if (PrintOpto && (Verbose || WizardMode)) { | |
601 tty->print("Bailing out on unloaded exception type "); | |
602 extype->klass()->print_name(); | |
603 tty->print(" at bci:%d in ", bci()); | |
604 method()->print_name(); tty->cr(); | |
605 } | |
606 #endif | |
607 // Emit an uncommon trap instead of processing the block. | |
608 set_bci(handler_bci); | |
609 push_ex_oop(ex_oop); | |
610 uncommon_trap(Deoptimization::Reason_unloaded, | |
611 Deoptimization::Action_reinterpret, | |
612 extype->klass(), "!loaded exception"); | |
613 set_bci(iter().cur_bci()); // put it back | |
614 continue; | |
615 } | |
616 | |
617 // go to the exception handler | |
618 if (handler_bci < 0) { // merge with corresponding rethrow node | |
619 throw_to_exit(make_exception_state(ex_oop)); | |
620 } else { // Else jump to corresponding handle | |
621 push_ex_oop(ex_oop); // Clear stack and push just the oop. | |
622 merge_exception(handler_bci); | |
623 } | |
624 } | |
625 | |
626 // The first CatchProj is for the normal return. | |
627 // (Note: If this is a call to rethrow_Java, this node goes dead.) | |
628 set_control(_gvn.transform( new (C, 1) CatchProjNode(catch_, CatchProjNode::fall_through_index, CatchProjNode::no_handler_bci))); | |
629 } | |
630 | |
631 | |
632 //----------------------------catch_inline_exceptions-------------------------- | |
633 // Handle all exceptions thrown by an inlined method or individual bytecode. | |
634 // Common case 1: we have no handler, so all exceptions merge right into | |
635 // the rethrow case. | |
636 // Case 2: we have some handlers, with loaded exception klasses that have | |
637 // no subklasses. We do a Deutsch-Shiffman style type-check on the incoming | |
638 // exception oop and branch to the handler directly. | |
639 // Case 3: We have some handlers with subklasses or are not loaded at | |
640 // compile-time. We have to call the runtime to resolve the exception. | |
641 // So we insert a RethrowCall and all the logic that goes with it. | |
642 void Parse::catch_inline_exceptions(SafePointNode* ex_map) { | |
643 // Caller is responsible for saving away the map for normal control flow! | |
644 assert(stopped(), "call set_map(NULL) first"); | |
645 assert(method()->has_exception_handlers(), "don't come here w/o work to do"); | |
646 | |
647 Node* ex_node = saved_ex_oop(ex_map); | |
648 if (ex_node == top()) { | |
649 // No action needed. | |
650 return; | |
651 } | |
652 const TypeInstPtr* ex_type = _gvn.type(ex_node)->isa_instptr(); | |
653 NOT_PRODUCT(if (ex_type==NULL) tty->print_cr("*** Exception not InstPtr")); | |
654 if (ex_type == NULL) | |
655 ex_type = TypeOopPtr::make_from_klass(env()->Throwable_klass())->is_instptr(); | |
656 | |
657 // determine potential exception handlers | |
658 ciExceptionHandlerStream handlers(method(), bci(), | |
659 ex_type->klass()->as_instance_klass(), | |
660 ex_type->klass_is_exact()); | |
661 | |
662 // Start executing from the given throw state. (Keep its stack, for now.) | |
663 // Get the exception oop as known at compile time. | |
664 ex_node = use_exception_state(ex_map); | |
665 | |
666 // Get the exception oop klass from its header | |
667 Node* ex_klass_node = NULL; | |
668 if (has_ex_handler() && !ex_type->klass_is_exact()) { | |
669 Node* p = basic_plus_adr( ex_node, ex_node, oopDesc::klass_offset_in_bytes()); | |
164
c436414a719e
6703890: Compressed Oops: add LoadNKlass node to generate narrow oops (32-bits) compare instructions
kvn
parents:
67
diff
changeset
|
670 ex_klass_node = _gvn.transform( LoadKlassNode::make(_gvn, immutable_memory(), p, TypeInstPtr::KLASS, TypeKlassPtr::OBJECT) ); |
0 | 671 |
672 // Compute the exception klass a little more cleverly. | |
673 // Obvious solution is to simple do a LoadKlass from the 'ex_node'. | |
674 // However, if the ex_node is a PhiNode, I'm going to do a LoadKlass for | |
675 // each arm of the Phi. If I know something clever about the exceptions | |
676 // I'm loading the class from, I can replace the LoadKlass with the | |
677 // klass constant for the exception oop. | |
678 if( ex_node->is_Phi() ) { | |
679 ex_klass_node = new (C, ex_node->req()) PhiNode( ex_node->in(0), TypeKlassPtr::OBJECT ); | |
680 for( uint i = 1; i < ex_node->req(); i++ ) { | |
681 Node* p = basic_plus_adr( ex_node->in(i), ex_node->in(i), oopDesc::klass_offset_in_bytes() ); | |
164
c436414a719e
6703890: Compressed Oops: add LoadNKlass node to generate narrow oops (32-bits) compare instructions
kvn
parents:
67
diff
changeset
|
682 Node* k = _gvn.transform( LoadKlassNode::make(_gvn, immutable_memory(), p, TypeInstPtr::KLASS, TypeKlassPtr::OBJECT) ); |
0 | 683 ex_klass_node->init_req( i, k ); |
684 } | |
685 _gvn.set_type(ex_klass_node, TypeKlassPtr::OBJECT); | |
686 | |
687 } | |
688 } | |
689 | |
690 // Scan the exception table for applicable handlers. | |
691 // If none, we can call rethrow() and be done! | |
692 // If precise (loaded with no subklasses), insert a D.S. style | |
693 // pointer compare to the correct handler and loop back. | |
694 // If imprecise, switch to the Rethrow VM-call style handling. | |
695 | |
696 int remaining = handlers.count_remaining(); | |
697 | |
698 // iterate through all entries sequentially | |
699 for (;!handlers.is_done(); handlers.next()) { | |
700 ciExceptionHandler* handler = handlers.handler(); | |
701 | |
702 if (handler->is_rethrow()) { | |
703 // If we fell off the end of the table without finding an imprecise | |
704 // exception klass (and without finding a generic handler) then we | |
705 // know this exception is not handled in this method. We just rethrow | |
706 // the exception into the caller. | |
707 throw_to_exit(make_exception_state(ex_node)); | |
708 return; | |
709 } | |
710 | |
711 // exception handler bci range covers throw_bci => investigate further | |
712 int handler_bci = handler->handler_bci(); | |
713 | |
714 if (remaining == 1) { | |
715 push_ex_oop(ex_node); // Push exception oop for handler | |
716 #ifndef PRODUCT | |
717 if (PrintOpto && WizardMode) { | |
718 tty->print_cr(" Catching every inline exception bci:%d -> handler_bci:%d", bci(), handler_bci); | |
719 } | |
720 #endif | |
721 merge_exception(handler_bci); // jump to handler | |
722 return; // No more handling to be done here! | |
723 } | |
724 | |
1344 | 725 // Get the handler's klass |
0 | 726 ciInstanceKlass* klass = handler->catch_klass(); |
1344 | 727 |
728 if (!klass->is_loaded()) { // klass is not loaded? | |
729 // fall through into catch_call_exceptions which will emit a | |
730 // handler with an uncommon trap. | |
731 break; | |
0 | 732 } |
733 | |
734 if (klass->is_interface()) // should not happen, but... | |
735 break; // bail out | |
736 | |
1344 | 737 // Check the type of the exception against the catch type |
0 | 738 const TypeKlassPtr *tk = TypeKlassPtr::make(klass); |
739 Node* con = _gvn.makecon(tk); | |
1344 | 740 Node* not_subtype_ctrl = gen_subtype_check(ex_klass_node, con); |
741 if (!stopped()) { | |
742 PreserveJVMState pjvms(this); | |
743 const TypeInstPtr* tinst = TypeOopPtr::make_from_klass_unique(klass)->cast_to_ptr_type(TypePtr::NotNull)->is_instptr(); | |
744 assert(klass->has_subklass() || tinst->klass_is_exact(), "lost exactness"); | |
0 | 745 Node* ex_oop = _gvn.transform(new (C, 2) CheckCastPPNode(control(), ex_node, tinst)); |
746 push_ex_oop(ex_oop); // Push exception oop for handler | |
747 #ifndef PRODUCT | |
748 if (PrintOpto && WizardMode) { | |
749 tty->print(" Catching inline exception bci:%d -> handler_bci:%d -- ", bci(), handler_bci); | |
750 klass->print_name(); | |
751 tty->cr(); | |
752 } | |
753 #endif | |
754 merge_exception(handler_bci); | |
755 } | |
1344 | 756 set_control(not_subtype_ctrl); |
0 | 757 |
758 // Come here if exception does not match handler. | |
759 // Carry on with more handler checks. | |
760 --remaining; | |
761 } | |
762 | |
763 assert(!stopped(), "you should return if you finish the chain"); | |
764 | |
765 // Oops, need to call into the VM to resolve the klasses at runtime. | |
766 // Note: This call must not deoptimize, since it is not a real at this bci! | |
767 kill_dead_locals(); | |
768 | |
769 make_runtime_call(RC_NO_LEAF | RC_MUST_THROW, | |
770 OptoRuntime::rethrow_Type(), | |
771 OptoRuntime::rethrow_stub(), | |
772 NULL, NULL, | |
773 ex_node); | |
774 | |
775 // Rethrow is a pure call, no side effects, only a result. | |
776 // The result cannot be allocated, so we use I_O | |
777 | |
778 // Catch exceptions from the rethrow | |
779 catch_call_exceptions(handlers); | |
780 } | |
781 | |
782 | |
783 // (Note: Moved add_debug_info into GraphKit::add_safepoint_edges.) | |
784 | |
785 | |
786 #ifndef PRODUCT | |
787 void Parse::count_compiled_calls(bool at_method_entry, bool is_inline) { | |
788 if( CountCompiledCalls ) { | |
789 if( at_method_entry ) { | |
790 // bump invocation counter if top method (for statistics) | |
791 if (CountCompiledCalls && depth() == 1) { | |
792 const TypeInstPtr* addr_type = TypeInstPtr::make(method()); | |
793 Node* adr1 = makecon(addr_type); | |
794 Node* adr2 = basic_plus_adr(adr1, adr1, in_bytes(methodOopDesc::compiled_invocation_counter_offset())); | |
795 increment_counter(adr2); | |
796 } | |
797 } else if (is_inline) { | |
798 switch (bc()) { | |
799 case Bytecodes::_invokevirtual: increment_counter(SharedRuntime::nof_inlined_calls_addr()); break; | |
800 case Bytecodes::_invokeinterface: increment_counter(SharedRuntime::nof_inlined_interface_calls_addr()); break; | |
801 case Bytecodes::_invokestatic: | |
726
be93aad57795
6655646: dynamic languages need dynamically linked call sites
jrose
parents:
367
diff
changeset
|
802 case Bytecodes::_invokedynamic: |
0 | 803 case Bytecodes::_invokespecial: increment_counter(SharedRuntime::nof_inlined_static_calls_addr()); break; |
804 default: fatal("unexpected call bytecode"); | |
805 } | |
806 } else { | |
807 switch (bc()) { | |
808 case Bytecodes::_invokevirtual: increment_counter(SharedRuntime::nof_normal_calls_addr()); break; | |
809 case Bytecodes::_invokeinterface: increment_counter(SharedRuntime::nof_interface_calls_addr()); break; | |
810 case Bytecodes::_invokestatic: | |
726
be93aad57795
6655646: dynamic languages need dynamically linked call sites
jrose
parents:
367
diff
changeset
|
811 case Bytecodes::_invokedynamic: |
0 | 812 case Bytecodes::_invokespecial: increment_counter(SharedRuntime::nof_static_calls_addr()); break; |
813 default: fatal("unexpected call bytecode"); | |
814 } | |
815 } | |
816 } | |
817 } | |
818 #endif //PRODUCT | |
819 | |
820 | |
821 // Identify possible target method and inlining style | |
822 ciMethod* Parse::optimize_inlining(ciMethod* caller, int bci, ciInstanceKlass* klass, | |
823 ciMethod *dest_method, const TypeOopPtr* receiver_type) { | |
824 // only use for virtual or interface calls | |
825 | |
826 // If it is obviously final, do not bother to call find_monomorphic_target, | |
827 // because the class hierarchy checks are not needed, and may fail due to | |
828 // incompletely loaded classes. Since we do our own class loading checks | |
829 // in this module, we may confidently bind to any method. | |
830 if (dest_method->can_be_statically_bound()) { | |
831 return dest_method; | |
832 } | |
833 | |
834 // Attempt to improve the receiver | |
835 bool actual_receiver_is_exact = false; | |
836 ciInstanceKlass* actual_receiver = klass; | |
837 if (receiver_type != NULL) { | |
838 // Array methods are all inherited from Object, and are monomorphic. | |
839 if (receiver_type->isa_aryptr() && | |
840 dest_method->holder() == env()->Object_klass()) { | |
841 return dest_method; | |
842 } | |
843 | |
844 // All other interesting cases are instance klasses. | |
845 if (!receiver_type->isa_instptr()) { | |
846 return NULL; | |
847 } | |
848 | |
849 ciInstanceKlass *ikl = receiver_type->klass()->as_instance_klass(); | |
850 if (ikl->is_loaded() && ikl->is_initialized() && !ikl->is_interface() && | |
367
194b8e3a2fc4
6384206: Phis which are later unneeded are impairing our ability to inline based on static types
never
parents:
196
diff
changeset
|
851 (ikl == actual_receiver || ikl->is_subtype_of(actual_receiver))) { |
0 | 852 // ikl is a same or better type than the original actual_receiver, |
853 // e.g. static receiver from bytecodes. | |
854 actual_receiver = ikl; | |
855 // Is the actual_receiver exact? | |
856 actual_receiver_is_exact = receiver_type->klass_is_exact(); | |
857 } | |
858 } | |
859 | |
860 ciInstanceKlass* calling_klass = caller->holder(); | |
861 ciMethod* cha_monomorphic_target = dest_method->find_monomorphic_target(calling_klass, klass, actual_receiver); | |
862 if (cha_monomorphic_target != NULL) { | |
863 assert(!cha_monomorphic_target->is_abstract(), ""); | |
864 // Look at the method-receiver type. Does it add "too much information"? | |
865 ciKlass* mr_klass = cha_monomorphic_target->holder(); | |
866 const Type* mr_type = TypeInstPtr::make(TypePtr::BotPTR, mr_klass); | |
867 if (receiver_type == NULL || !receiver_type->higher_equal(mr_type)) { | |
868 // Calling this method would include an implicit cast to its holder. | |
869 // %%% Not yet implemented. Would throw minor asserts at present. | |
870 // %%% The most common wins are already gained by +UseUniqueSubclasses. | |
871 // To fix, put the higher_equal check at the call of this routine, | |
872 // and add a CheckCastPP to the receiver. | |
873 if (TraceDependencies) { | |
874 tty->print_cr("found unique CHA method, but could not cast up"); | |
875 tty->print(" method = "); | |
876 cha_monomorphic_target->print(); | |
877 tty->cr(); | |
878 } | |
879 if (C->log() != NULL) { | |
880 C->log()->elem("missed_CHA_opportunity klass='%d' method='%d'", | |
881 C->log()->identify(klass), | |
882 C->log()->identify(cha_monomorphic_target)); | |
883 } | |
884 cha_monomorphic_target = NULL; | |
885 } | |
886 } | |
887 if (cha_monomorphic_target != NULL) { | |
888 // Hardwiring a virtual. | |
889 // If we inlined because CHA revealed only a single target method, | |
890 // then we are dependent on that target method not getting overridden | |
891 // by dynamic class loading. Be sure to test the "static" receiver | |
892 // dest_method here, as opposed to the actual receiver, which may | |
893 // falsely lead us to believe that the receiver is final or private. | |
894 C->dependencies()->assert_unique_concrete_method(actual_receiver, cha_monomorphic_target); | |
895 return cha_monomorphic_target; | |
896 } | |
897 | |
898 // If the type is exact, we can still bind the method w/o a vcall. | |
899 // (This case comes after CHA so we can see how much extra work it does.) | |
900 if (actual_receiver_is_exact) { | |
901 // In case of evolution, there is a dependence on every inlined method, since each | |
902 // such method can be changed when its class is redefined. | |
903 ciMethod* exact_method = dest_method->resolve_invoke(calling_klass, actual_receiver); | |
904 if (exact_method != NULL) { | |
905 #ifndef PRODUCT | |
906 if (PrintOpto) { | |
907 tty->print(" Calling method via exact type @%d --- ", bci); | |
908 exact_method->print_name(); | |
909 tty->cr(); | |
910 } | |
911 #endif | |
912 return exact_method; | |
913 } | |
914 } | |
915 | |
916 return NULL; | |
917 } |