1 | /* |
2 | * Copyright (c) 2000, 2019, Oracle and/or its affiliates. All rights reserved. |
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 | #include "precompiled.hpp" |
26 | #include "ci/ciConstant.hpp" |
27 | #include "ci/ciField.hpp" |
28 | #include "ci/ciMethod.hpp" |
29 | #include "ci/ciMethodData.hpp" |
30 | #include "ci/ciObjArrayKlass.hpp" |
31 | #include "ci/ciStreams.hpp" |
32 | #include "ci/ciTypeArrayKlass.hpp" |
33 | #include "ci/ciTypeFlow.hpp" |
34 | #include "compiler/compileLog.hpp" |
35 | #include "interpreter/bytecode.hpp" |
36 | #include "interpreter/bytecodes.hpp" |
37 | #include "memory/allocation.inline.hpp" |
38 | #include "memory/resourceArea.hpp" |
39 | #include "oops/oop.inline.hpp" |
40 | #include "opto/compile.hpp" |
41 | #include "opto/node.hpp" |
42 | #include "runtime/deoptimization.hpp" |
43 | #include "utilities/growableArray.hpp" |
44 | |
45 | // ciTypeFlow::JsrSet |
46 | // |
47 | // A JsrSet represents some set of JsrRecords. This class |
48 | // is used to record a set of all jsr routines which we permit |
49 | // execution to return (ret) from. |
50 | // |
51 | // During abstract interpretation, JsrSets are used to determine |
52 | // whether two paths which reach a given block are unique, and |
53 | // should be cloned apart, or are compatible, and should merge |
54 | // together. |
55 | |
56 | // ------------------------------------------------------------------ |
57 | // ciTypeFlow::JsrSet::JsrSet |
58 | ciTypeFlow::JsrSet::JsrSet(Arena* arena, int default_len) { |
59 | if (arena != NULL) { |
60 | // Allocate growable array in Arena. |
61 | _set = new (arena) GrowableArray<JsrRecord*>(arena, default_len, 0, NULL); |
62 | } else { |
63 | // Allocate growable array in current ResourceArea. |
64 | _set = new GrowableArray<JsrRecord*>(4, 0, NULL, false); |
65 | } |
66 | } |
67 | |
68 | // ------------------------------------------------------------------ |
69 | // ciTypeFlow::JsrSet::copy_into |
70 | void ciTypeFlow::JsrSet::copy_into(JsrSet* jsrs) { |
71 | int len = size(); |
72 | jsrs->_set->clear(); |
73 | for (int i = 0; i < len; i++) { |
74 | jsrs->_set->append(_set->at(i)); |
75 | } |
76 | } |
77 | |
78 | // ------------------------------------------------------------------ |
79 | // ciTypeFlow::JsrSet::is_compatible_with |
80 | // |
81 | // !!!! MISGIVINGS ABOUT THIS... disregard |
82 | // |
83 | // Is this JsrSet compatible with some other JsrSet? |
84 | // |
85 | // In set-theoretic terms, a JsrSet can be viewed as a partial function |
86 | // from entry addresses to return addresses. Two JsrSets A and B are |
87 | // compatible iff |
88 | // |
89 | // For any x, |
90 | // A(x) defined and B(x) defined implies A(x) == B(x) |
91 | // |
92 | // Less formally, two JsrSets are compatible when they have identical |
93 | // return addresses for any entry addresses they share in common. |
94 | bool ciTypeFlow::JsrSet::is_compatible_with(JsrSet* other) { |
95 | // Walk through both sets in parallel. If the same entry address |
96 | // appears in both sets, then the return address must match for |
97 | // the sets to be compatible. |
98 | int size1 = size(); |
99 | int size2 = other->size(); |
100 | |
101 | // Special case. If nothing is on the jsr stack, then there can |
102 | // be no ret. |
103 | if (size2 == 0) { |
104 | return true; |
105 | } else if (size1 != size2) { |
106 | return false; |
107 | } else { |
108 | for (int i = 0; i < size1; i++) { |
109 | JsrRecord* record1 = record_at(i); |
110 | JsrRecord* record2 = other->record_at(i); |
111 | if (record1->entry_address() != record2->entry_address() || |
112 | record1->return_address() != record2->return_address()) { |
113 | return false; |
114 | } |
115 | } |
116 | return true; |
117 | } |
118 | |
119 | #if 0 |
120 | int pos1 = 0; |
121 | int pos2 = 0; |
122 | int size1 = size(); |
123 | int size2 = other->size(); |
124 | while (pos1 < size1 && pos2 < size2) { |
125 | JsrRecord* record1 = record_at(pos1); |
126 | JsrRecord* record2 = other->record_at(pos2); |
127 | int entry1 = record1->entry_address(); |
128 | int entry2 = record2->entry_address(); |
129 | if (entry1 < entry2) { |
130 | pos1++; |
131 | } else if (entry1 > entry2) { |
132 | pos2++; |
133 | } else { |
134 | if (record1->return_address() == record2->return_address()) { |
135 | pos1++; |
136 | pos2++; |
137 | } else { |
138 | // These two JsrSets are incompatible. |
139 | return false; |
140 | } |
141 | } |
142 | } |
143 | // The two JsrSets agree. |
144 | return true; |
145 | #endif |
146 | } |
147 | |
148 | // ------------------------------------------------------------------ |
149 | // ciTypeFlow::JsrSet::insert_jsr_record |
150 | // |
151 | // Insert the given JsrRecord into the JsrSet, maintaining the order |
152 | // of the set and replacing any element with the same entry address. |
153 | void ciTypeFlow::JsrSet::insert_jsr_record(JsrRecord* record) { |
154 | int len = size(); |
155 | int entry = record->entry_address(); |
156 | int pos = 0; |
157 | for ( ; pos < len; pos++) { |
158 | JsrRecord* current = record_at(pos); |
159 | if (entry == current->entry_address()) { |
160 | // Stomp over this entry. |
161 | _set->at_put(pos, record); |
162 | assert(size() == len, "must be same size" ); |
163 | return; |
164 | } else if (entry < current->entry_address()) { |
165 | break; |
166 | } |
167 | } |
168 | |
169 | // Insert the record into the list. |
170 | JsrRecord* swap = record; |
171 | JsrRecord* temp = NULL; |
172 | for ( ; pos < len; pos++) { |
173 | temp = _set->at(pos); |
174 | _set->at_put(pos, swap); |
175 | swap = temp; |
176 | } |
177 | _set->append(swap); |
178 | assert(size() == len+1, "must be larger" ); |
179 | } |
180 | |
181 | // ------------------------------------------------------------------ |
182 | // ciTypeFlow::JsrSet::remove_jsr_record |
183 | // |
184 | // Remove the JsrRecord with the given return address from the JsrSet. |
185 | void ciTypeFlow::JsrSet::remove_jsr_record(int return_address) { |
186 | int len = size(); |
187 | for (int i = 0; i < len; i++) { |
188 | if (record_at(i)->return_address() == return_address) { |
189 | // We have found the proper entry. Remove it from the |
190 | // JsrSet and exit. |
191 | for (int j = i+1; j < len ; j++) { |
192 | _set->at_put(j-1, _set->at(j)); |
193 | } |
194 | _set->trunc_to(len-1); |
195 | assert(size() == len-1, "must be smaller" ); |
196 | return; |
197 | } |
198 | } |
199 | assert(false, "verify: returning from invalid subroutine" ); |
200 | } |
201 | |
202 | // ------------------------------------------------------------------ |
203 | // ciTypeFlow::JsrSet::apply_control |
204 | // |
205 | // Apply the effect of a control-flow bytecode on the JsrSet. The |
206 | // only bytecodes that modify the JsrSet are jsr and ret. |
207 | void ciTypeFlow::JsrSet::apply_control(ciTypeFlow* analyzer, |
208 | ciBytecodeStream* str, |
209 | ciTypeFlow::StateVector* state) { |
210 | Bytecodes::Code code = str->cur_bc(); |
211 | if (code == Bytecodes::_jsr) { |
212 | JsrRecord* record = |
213 | analyzer->make_jsr_record(str->get_dest(), str->next_bci()); |
214 | insert_jsr_record(record); |
215 | } else if (code == Bytecodes::_jsr_w) { |
216 | JsrRecord* record = |
217 | analyzer->make_jsr_record(str->get_far_dest(), str->next_bci()); |
218 | insert_jsr_record(record); |
219 | } else if (code == Bytecodes::_ret) { |
220 | Cell local = state->local(str->get_index()); |
221 | ciType* return_address = state->type_at(local); |
222 | assert(return_address->is_return_address(), "verify: wrong type" ); |
223 | if (size() == 0) { |
224 | // Ret-state underflow: Hit a ret w/o any previous jsrs. Bail out. |
225 | // This can happen when a loop is inside a finally clause (4614060). |
226 | analyzer->record_failure("OSR in finally clause" ); |
227 | return; |
228 | } |
229 | remove_jsr_record(return_address->as_return_address()->bci()); |
230 | } |
231 | } |
232 | |
233 | #ifndef PRODUCT |
234 | // ------------------------------------------------------------------ |
235 | // ciTypeFlow::JsrSet::print_on |
236 | void ciTypeFlow::JsrSet::print_on(outputStream* st) const { |
237 | st->print("{ " ); |
238 | int num_elements = size(); |
239 | if (num_elements > 0) { |
240 | int i = 0; |
241 | for( ; i < num_elements - 1; i++) { |
242 | _set->at(i)->print_on(st); |
243 | st->print(", " ); |
244 | } |
245 | _set->at(i)->print_on(st); |
246 | st->print(" " ); |
247 | } |
248 | st->print("}" ); |
249 | } |
250 | #endif |
251 | |
252 | // ciTypeFlow::StateVector |
253 | // |
254 | // A StateVector summarizes the type information at some point in |
255 | // the program. |
256 | |
257 | // ------------------------------------------------------------------ |
258 | // ciTypeFlow::StateVector::type_meet |
259 | // |
260 | // Meet two types. |
261 | // |
262 | // The semi-lattice of types use by this analysis are modeled on those |
263 | // of the verifier. The lattice is as follows: |
264 | // |
265 | // top_type() >= all non-extremal types >= bottom_type |
266 | // and |
267 | // Every primitive type is comparable only with itself. The meet of |
268 | // reference types is determined by their kind: instance class, |
269 | // interface, or array class. The meet of two types of the same |
270 | // kind is their least common ancestor. The meet of two types of |
271 | // different kinds is always java.lang.Object. |
272 | ciType* ciTypeFlow::StateVector::type_meet_internal(ciType* t1, ciType* t2, ciTypeFlow* analyzer) { |
273 | assert(t1 != t2, "checked in caller" ); |
274 | if (t1->equals(top_type())) { |
275 | return t2; |
276 | } else if (t2->equals(top_type())) { |
277 | return t1; |
278 | } else if (t1->is_primitive_type() || t2->is_primitive_type()) { |
279 | // Special case null_type. null_type meet any reference type T |
280 | // is T. null_type meet null_type is null_type. |
281 | if (t1->equals(null_type())) { |
282 | if (!t2->is_primitive_type() || t2->equals(null_type())) { |
283 | return t2; |
284 | } |
285 | } else if (t2->equals(null_type())) { |
286 | if (!t1->is_primitive_type()) { |
287 | return t1; |
288 | } |
289 | } |
290 | |
291 | // At least one of the two types is a non-top primitive type. |
292 | // The other type is not equal to it. Fall to bottom. |
293 | return bottom_type(); |
294 | } else { |
295 | // Both types are non-top non-primitive types. That is, |
296 | // both types are either instanceKlasses or arrayKlasses. |
297 | ciKlass* object_klass = analyzer->env()->Object_klass(); |
298 | ciKlass* k1 = t1->as_klass(); |
299 | ciKlass* k2 = t2->as_klass(); |
300 | if (k1->equals(object_klass) || k2->equals(object_klass)) { |
301 | return object_klass; |
302 | } else if (!k1->is_loaded() || !k2->is_loaded()) { |
303 | // Unloaded classes fall to java.lang.Object at a merge. |
304 | return object_klass; |
305 | } else if (k1->is_interface() != k2->is_interface()) { |
306 | // When an interface meets a non-interface, we get Object; |
307 | // This is what the verifier does. |
308 | return object_klass; |
309 | } else if (k1->is_array_klass() || k2->is_array_klass()) { |
310 | // When an array meets a non-array, we get Object. |
311 | // When objArray meets typeArray, we also get Object. |
312 | // And when typeArray meets different typeArray, we again get Object. |
313 | // But when objArray meets objArray, we look carefully at element types. |
314 | if (k1->is_obj_array_klass() && k2->is_obj_array_klass()) { |
315 | // Meet the element types, then construct the corresponding array type. |
316 | ciKlass* elem1 = k1->as_obj_array_klass()->element_klass(); |
317 | ciKlass* elem2 = k2->as_obj_array_klass()->element_klass(); |
318 | ciKlass* elem = type_meet_internal(elem1, elem2, analyzer)->as_klass(); |
319 | // Do an easy shortcut if one type is a super of the other. |
320 | if (elem == elem1) { |
321 | assert(k1 == ciObjArrayKlass::make(elem), "shortcut is OK" ); |
322 | return k1; |
323 | } else if (elem == elem2) { |
324 | assert(k2 == ciObjArrayKlass::make(elem), "shortcut is OK" ); |
325 | return k2; |
326 | } else { |
327 | return ciObjArrayKlass::make(elem); |
328 | } |
329 | } else { |
330 | return object_klass; |
331 | } |
332 | } else { |
333 | // Must be two plain old instance klasses. |
334 | assert(k1->is_instance_klass(), "previous cases handle non-instances" ); |
335 | assert(k2->is_instance_klass(), "previous cases handle non-instances" ); |
336 | return k1->least_common_ancestor(k2); |
337 | } |
338 | } |
339 | } |
340 | |
341 | |
342 | // ------------------------------------------------------------------ |
343 | // ciTypeFlow::StateVector::StateVector |
344 | // |
345 | // Build a new state vector |
346 | ciTypeFlow::StateVector::StateVector(ciTypeFlow* analyzer) { |
347 | _outer = analyzer; |
348 | _stack_size = -1; |
349 | _monitor_count = -1; |
350 | // Allocate the _types array |
351 | int max_cells = analyzer->max_cells(); |
352 | _types = (ciType**)analyzer->arena()->Amalloc(sizeof(ciType*) * max_cells); |
353 | for (int i=0; i<max_cells; i++) { |
354 | _types[i] = top_type(); |
355 | } |
356 | _trap_bci = -1; |
357 | _trap_index = 0; |
358 | _def_locals.clear(); |
359 | } |
360 | |
361 | |
362 | // ------------------------------------------------------------------ |
363 | // ciTypeFlow::get_start_state |
364 | // |
365 | // Set this vector to the method entry state. |
366 | const ciTypeFlow::StateVector* ciTypeFlow::get_start_state() { |
367 | StateVector* state = new StateVector(this); |
368 | if (is_osr_flow()) { |
369 | ciTypeFlow* non_osr_flow = method()->get_flow_analysis(); |
370 | if (non_osr_flow->failing()) { |
371 | record_failure(non_osr_flow->failure_reason()); |
372 | return NULL; |
373 | } |
374 | JsrSet* jsrs = new JsrSet(NULL, 16); |
375 | Block* non_osr_block = non_osr_flow->existing_block_at(start_bci(), jsrs); |
376 | if (non_osr_block == NULL) { |
377 | record_failure("cannot reach OSR point" ); |
378 | return NULL; |
379 | } |
380 | // load up the non-OSR state at this point |
381 | non_osr_block->copy_state_into(state); |
382 | int non_osr_start = non_osr_block->start(); |
383 | if (non_osr_start != start_bci()) { |
384 | // must flow forward from it |
385 | if (CITraceTypeFlow) { |
386 | tty->print_cr(">> Interpreting pre-OSR block %d:" , non_osr_start); |
387 | } |
388 | Block* block = block_at(non_osr_start, jsrs); |
389 | assert(block->limit() == start_bci(), "must flow forward to start" ); |
390 | flow_block(block, state, jsrs); |
391 | } |
392 | return state; |
393 | // Note: The code below would be an incorrect for an OSR flow, |
394 | // even if it were possible for an OSR entry point to be at bci zero. |
395 | } |
396 | // "Push" the method signature into the first few locals. |
397 | state->set_stack_size(-max_locals()); |
398 | if (!method()->is_static()) { |
399 | state->push(method()->holder()); |
400 | assert(state->tos() == state->local(0), "" ); |
401 | } |
402 | for (ciSignatureStream str(method()->signature()); |
403 | !str.at_return_type(); |
404 | str.next()) { |
405 | state->push_translate(str.type()); |
406 | } |
407 | // Set the rest of the locals to bottom. |
408 | Cell cell = state->next_cell(state->tos()); |
409 | state->set_stack_size(0); |
410 | int limit = state->limit_cell(); |
411 | for (; cell < limit; cell = state->next_cell(cell)) { |
412 | state->set_type_at(cell, state->bottom_type()); |
413 | } |
414 | // Lock an object, if necessary. |
415 | state->set_monitor_count(method()->is_synchronized() ? 1 : 0); |
416 | return state; |
417 | } |
418 | |
419 | // ------------------------------------------------------------------ |
420 | // ciTypeFlow::StateVector::copy_into |
421 | // |
422 | // Copy our value into some other StateVector |
423 | void ciTypeFlow::StateVector::copy_into(ciTypeFlow::StateVector* copy) |
424 | const { |
425 | copy->set_stack_size(stack_size()); |
426 | copy->set_monitor_count(monitor_count()); |
427 | Cell limit = limit_cell(); |
428 | for (Cell c = start_cell(); c < limit; c = next_cell(c)) { |
429 | copy->set_type_at(c, type_at(c)); |
430 | } |
431 | } |
432 | |
433 | // ------------------------------------------------------------------ |
434 | // ciTypeFlow::StateVector::meet |
435 | // |
436 | // Meets this StateVector with another, destructively modifying this |
437 | // one. Returns true if any modification takes place. |
438 | bool ciTypeFlow::StateVector::meet(const ciTypeFlow::StateVector* incoming) { |
439 | if (monitor_count() == -1) { |
440 | set_monitor_count(incoming->monitor_count()); |
441 | } |
442 | assert(monitor_count() == incoming->monitor_count(), "monitors must match" ); |
443 | |
444 | if (stack_size() == -1) { |
445 | set_stack_size(incoming->stack_size()); |
446 | Cell limit = limit_cell(); |
447 | #ifdef ASSERT |
448 | { for (Cell c = start_cell(); c < limit; c = next_cell(c)) { |
449 | assert(type_at(c) == top_type(), "" ); |
450 | } } |
451 | #endif |
452 | // Make a simple copy of the incoming state. |
453 | for (Cell c = start_cell(); c < limit; c = next_cell(c)) { |
454 | set_type_at(c, incoming->type_at(c)); |
455 | } |
456 | return true; // it is always different the first time |
457 | } |
458 | #ifdef ASSERT |
459 | if (stack_size() != incoming->stack_size()) { |
460 | _outer->method()->print_codes(); |
461 | tty->print_cr("!!!! Stack size conflict" ); |
462 | tty->print_cr("Current state:" ); |
463 | print_on(tty); |
464 | tty->print_cr("Incoming state:" ); |
465 | ((StateVector*)incoming)->print_on(tty); |
466 | } |
467 | #endif |
468 | assert(stack_size() == incoming->stack_size(), "sanity" ); |
469 | |
470 | bool different = false; |
471 | Cell limit = limit_cell(); |
472 | for (Cell c = start_cell(); c < limit; c = next_cell(c)) { |
473 | ciType* t1 = type_at(c); |
474 | ciType* t2 = incoming->type_at(c); |
475 | if (!t1->equals(t2)) { |
476 | ciType* new_type = type_meet(t1, t2); |
477 | if (!t1->equals(new_type)) { |
478 | set_type_at(c, new_type); |
479 | different = true; |
480 | } |
481 | } |
482 | } |
483 | return different; |
484 | } |
485 | |
486 | // ------------------------------------------------------------------ |
487 | // ciTypeFlow::StateVector::meet_exception |
488 | // |
489 | // Meets this StateVector with another, destructively modifying this |
490 | // one. The incoming state is coming via an exception. Returns true |
491 | // if any modification takes place. |
492 | bool ciTypeFlow::StateVector::meet_exception(ciInstanceKlass* exc, |
493 | const ciTypeFlow::StateVector* incoming) { |
494 | if (monitor_count() == -1) { |
495 | set_monitor_count(incoming->monitor_count()); |
496 | } |
497 | assert(monitor_count() == incoming->monitor_count(), "monitors must match" ); |
498 | |
499 | if (stack_size() == -1) { |
500 | set_stack_size(1); |
501 | } |
502 | |
503 | assert(stack_size() == 1, "must have one-element stack" ); |
504 | |
505 | bool different = false; |
506 | |
507 | // Meet locals from incoming array. |
508 | Cell limit = local(_outer->max_locals()-1); |
509 | for (Cell c = start_cell(); c <= limit; c = next_cell(c)) { |
510 | ciType* t1 = type_at(c); |
511 | ciType* t2 = incoming->type_at(c); |
512 | if (!t1->equals(t2)) { |
513 | ciType* new_type = type_meet(t1, t2); |
514 | if (!t1->equals(new_type)) { |
515 | set_type_at(c, new_type); |
516 | different = true; |
517 | } |
518 | } |
519 | } |
520 | |
521 | // Handle stack separately. When an exception occurs, the |
522 | // only stack entry is the exception instance. |
523 | ciType* tos_type = type_at_tos(); |
524 | if (!tos_type->equals(exc)) { |
525 | ciType* new_type = type_meet(tos_type, exc); |
526 | if (!tos_type->equals(new_type)) { |
527 | set_type_at_tos(new_type); |
528 | different = true; |
529 | } |
530 | } |
531 | |
532 | return different; |
533 | } |
534 | |
535 | // ------------------------------------------------------------------ |
536 | // ciTypeFlow::StateVector::push_translate |
537 | void ciTypeFlow::StateVector::push_translate(ciType* type) { |
538 | BasicType basic_type = type->basic_type(); |
539 | if (basic_type == T_BOOLEAN || basic_type == T_CHAR || |
540 | basic_type == T_BYTE || basic_type == T_SHORT) { |
541 | push_int(); |
542 | } else { |
543 | push(type); |
544 | if (type->is_two_word()) { |
545 | push(half_type(type)); |
546 | } |
547 | } |
548 | } |
549 | |
550 | // ------------------------------------------------------------------ |
551 | // ciTypeFlow::StateVector::do_aaload |
552 | void ciTypeFlow::StateVector::do_aaload(ciBytecodeStream* str) { |
553 | pop_int(); |
554 | ciObjArrayKlass* array_klass = pop_objArray(); |
555 | if (array_klass == NULL) { |
556 | // Did aaload on a null reference; push a null and ignore the exception. |
557 | // This instruction will never continue normally. All we have to do |
558 | // is report a value that will meet correctly with any downstream |
559 | // reference types on paths that will truly be executed. This null type |
560 | // meets with any reference type to yield that same reference type. |
561 | // (The compiler will generate an unconditional exception here.) |
562 | push(null_type()); |
563 | return; |
564 | } |
565 | if (!array_klass->is_loaded()) { |
566 | // Only fails for some -Xcomp runs |
567 | trap(str, array_klass, |
568 | Deoptimization::make_trap_request |
569 | (Deoptimization::Reason_unloaded, |
570 | Deoptimization::Action_reinterpret)); |
571 | return; |
572 | } |
573 | ciKlass* element_klass = array_klass->element_klass(); |
574 | if (!element_klass->is_loaded() && element_klass->is_instance_klass()) { |
575 | Untested("unloaded array element class in ciTypeFlow" ); |
576 | trap(str, element_klass, |
577 | Deoptimization::make_trap_request |
578 | (Deoptimization::Reason_unloaded, |
579 | Deoptimization::Action_reinterpret)); |
580 | } else { |
581 | push_object(element_klass); |
582 | } |
583 | } |
584 | |
585 | |
586 | // ------------------------------------------------------------------ |
587 | // ciTypeFlow::StateVector::do_checkcast |
588 | void ciTypeFlow::StateVector::do_checkcast(ciBytecodeStream* str) { |
589 | bool will_link; |
590 | ciKlass* klass = str->get_klass(will_link); |
591 | if (!will_link) { |
592 | // VM's interpreter will not load 'klass' if object is NULL. |
593 | // Type flow after this block may still be needed in two situations: |
594 | // 1) C2 uses do_null_assert() and continues compilation for later blocks |
595 | // 2) C2 does an OSR compile in a later block (see bug 4778368). |
596 | pop_object(); |
597 | do_null_assert(klass); |
598 | } else { |
599 | pop_object(); |
600 | push_object(klass); |
601 | } |
602 | } |
603 | |
604 | // ------------------------------------------------------------------ |
605 | // ciTypeFlow::StateVector::do_getfield |
606 | void ciTypeFlow::StateVector::do_getfield(ciBytecodeStream* str) { |
607 | // could add assert here for type of object. |
608 | pop_object(); |
609 | do_getstatic(str); |
610 | } |
611 | |
612 | // ------------------------------------------------------------------ |
613 | // ciTypeFlow::StateVector::do_getstatic |
614 | void ciTypeFlow::StateVector::do_getstatic(ciBytecodeStream* str) { |
615 | bool will_link; |
616 | ciField* field = str->get_field(will_link); |
617 | if (!will_link) { |
618 | trap(str, field->holder(), str->get_field_holder_index()); |
619 | } else { |
620 | ciType* field_type = field->type(); |
621 | if (!field_type->is_loaded()) { |
622 | // Normally, we need the field's type to be loaded if we are to |
623 | // do anything interesting with its value. |
624 | // We used to do this: trap(str, str->get_field_signature_index()); |
625 | // |
626 | // There is one good reason not to trap here. Execution can |
627 | // get past this "getfield" or "getstatic" if the value of |
628 | // the field is null. As long as the value is null, the class |
629 | // does not need to be loaded! The compiler must assume that |
630 | // the value of the unloaded class reference is null; if the code |
631 | // ever sees a non-null value, loading has occurred. |
632 | // |
633 | // This actually happens often enough to be annoying. If the |
634 | // compiler throws an uncommon trap at this bytecode, you can |
635 | // get an endless loop of recompilations, when all the code |
636 | // needs to do is load a series of null values. Also, a trap |
637 | // here can make an OSR entry point unreachable, triggering the |
638 | // assert on non_osr_block in ciTypeFlow::get_start_state. |
639 | // (See bug 4379915.) |
640 | do_null_assert(field_type->as_klass()); |
641 | } else { |
642 | push_translate(field_type); |
643 | } |
644 | } |
645 | } |
646 | |
647 | // ------------------------------------------------------------------ |
648 | // ciTypeFlow::StateVector::do_invoke |
649 | void ciTypeFlow::StateVector::do_invoke(ciBytecodeStream* str, |
650 | bool has_receiver) { |
651 | bool will_link; |
652 | ciSignature* declared_signature = NULL; |
653 | ciMethod* callee = str->get_method(will_link, &declared_signature); |
654 | assert(declared_signature != NULL, "cannot be null" ); |
655 | if (!will_link) { |
656 | // We weren't able to find the method. |
657 | if (str->cur_bc() == Bytecodes::_invokedynamic) { |
658 | trap(str, NULL, |
659 | Deoptimization::make_trap_request |
660 | (Deoptimization::Reason_uninitialized, |
661 | Deoptimization::Action_reinterpret)); |
662 | } else { |
663 | ciKlass* unloaded_holder = callee->holder(); |
664 | trap(str, unloaded_holder, str->get_method_holder_index()); |
665 | } |
666 | } else { |
667 | // We are using the declared signature here because it might be |
668 | // different from the callee signature (Cf. invokedynamic and |
669 | // invokehandle). |
670 | ciSignatureStream sigstr(declared_signature); |
671 | const int arg_size = declared_signature->size(); |
672 | const int stack_base = stack_size() - arg_size; |
673 | int i = 0; |
674 | for( ; !sigstr.at_return_type(); sigstr.next()) { |
675 | ciType* type = sigstr.type(); |
676 | ciType* stack_type = type_at(stack(stack_base + i++)); |
677 | // Do I want to check this type? |
678 | // assert(stack_type->is_subtype_of(type), "bad type for field value"); |
679 | if (type->is_two_word()) { |
680 | ciType* stack_type2 = type_at(stack(stack_base + i++)); |
681 | assert(stack_type2->equals(half_type(type)), "must be 2nd half" ); |
682 | } |
683 | } |
684 | assert(arg_size == i, "must match" ); |
685 | for (int j = 0; j < arg_size; j++) { |
686 | pop(); |
687 | } |
688 | if (has_receiver) { |
689 | // Check this? |
690 | pop_object(); |
691 | } |
692 | assert(!sigstr.is_done(), "must have return type" ); |
693 | ciType* return_type = sigstr.type(); |
694 | if (!return_type->is_void()) { |
695 | if (!return_type->is_loaded()) { |
696 | // As in do_getstatic(), generally speaking, we need the return type to |
697 | // be loaded if we are to do anything interesting with its value. |
698 | // We used to do this: trap(str, str->get_method_signature_index()); |
699 | // |
700 | // We do not trap here since execution can get past this invoke if |
701 | // the return value is null. As long as the value is null, the class |
702 | // does not need to be loaded! The compiler must assume that |
703 | // the value of the unloaded class reference is null; if the code |
704 | // ever sees a non-null value, loading has occurred. |
705 | // |
706 | // See do_getstatic() for similar explanation, as well as bug 4684993. |
707 | do_null_assert(return_type->as_klass()); |
708 | } else { |
709 | push_translate(return_type); |
710 | } |
711 | } |
712 | } |
713 | } |
714 | |
715 | // ------------------------------------------------------------------ |
716 | // ciTypeFlow::StateVector::do_jsr |
717 | void ciTypeFlow::StateVector::do_jsr(ciBytecodeStream* str) { |
718 | push(ciReturnAddress::make(str->next_bci())); |
719 | } |
720 | |
721 | // ------------------------------------------------------------------ |
722 | // ciTypeFlow::StateVector::do_ldc |
723 | void ciTypeFlow::StateVector::do_ldc(ciBytecodeStream* str) { |
724 | ciConstant con = str->get_constant(); |
725 | BasicType basic_type = con.basic_type(); |
726 | if (basic_type == T_ILLEGAL) { |
727 | // OutOfMemoryError in the CI while loading constant |
728 | push_null(); |
729 | outer()->record_failure("ldc did not link" ); |
730 | return; |
731 | } |
732 | if (basic_type == T_OBJECT || basic_type == T_ARRAY) { |
733 | ciObject* obj = con.as_object(); |
734 | if (obj->is_null_object()) { |
735 | push_null(); |
736 | } else { |
737 | assert(obj->is_instance() || obj->is_array(), "must be java_mirror of klass" ); |
738 | push_object(obj->klass()); |
739 | } |
740 | } else { |
741 | push_translate(ciType::make(basic_type)); |
742 | } |
743 | } |
744 | |
745 | // ------------------------------------------------------------------ |
746 | // ciTypeFlow::StateVector::do_multianewarray |
747 | void ciTypeFlow::StateVector::do_multianewarray(ciBytecodeStream* str) { |
748 | int dimensions = str->get_dimensions(); |
749 | bool will_link; |
750 | ciArrayKlass* array_klass = str->get_klass(will_link)->as_array_klass(); |
751 | if (!will_link) { |
752 | trap(str, array_klass, str->get_klass_index()); |
753 | } else { |
754 | for (int i = 0; i < dimensions; i++) { |
755 | pop_int(); |
756 | } |
757 | push_object(array_klass); |
758 | } |
759 | } |
760 | |
761 | // ------------------------------------------------------------------ |
762 | // ciTypeFlow::StateVector::do_new |
763 | void ciTypeFlow::StateVector::do_new(ciBytecodeStream* str) { |
764 | bool will_link; |
765 | ciKlass* klass = str->get_klass(will_link); |
766 | if (!will_link || str->is_unresolved_klass()) { |
767 | trap(str, klass, str->get_klass_index()); |
768 | } else { |
769 | push_object(klass); |
770 | } |
771 | } |
772 | |
773 | // ------------------------------------------------------------------ |
774 | // ciTypeFlow::StateVector::do_newarray |
775 | void ciTypeFlow::StateVector::do_newarray(ciBytecodeStream* str) { |
776 | pop_int(); |
777 | ciKlass* klass = ciTypeArrayKlass::make((BasicType)str->get_index()); |
778 | push_object(klass); |
779 | } |
780 | |
781 | // ------------------------------------------------------------------ |
782 | // ciTypeFlow::StateVector::do_putfield |
783 | void ciTypeFlow::StateVector::do_putfield(ciBytecodeStream* str) { |
784 | do_putstatic(str); |
785 | if (_trap_bci != -1) return; // unloaded field holder, etc. |
786 | // could add assert here for type of object. |
787 | pop_object(); |
788 | } |
789 | |
790 | // ------------------------------------------------------------------ |
791 | // ciTypeFlow::StateVector::do_putstatic |
792 | void ciTypeFlow::StateVector::do_putstatic(ciBytecodeStream* str) { |
793 | bool will_link; |
794 | ciField* field = str->get_field(will_link); |
795 | if (!will_link) { |
796 | trap(str, field->holder(), str->get_field_holder_index()); |
797 | } else { |
798 | ciType* field_type = field->type(); |
799 | ciType* type = pop_value(); |
800 | // Do I want to check this type? |
801 | // assert(type->is_subtype_of(field_type), "bad type for field value"); |
802 | if (field_type->is_two_word()) { |
803 | ciType* type2 = pop_value(); |
804 | assert(type2->is_two_word(), "must be 2nd half" ); |
805 | assert(type == half_type(type2), "must be 2nd half" ); |
806 | } |
807 | } |
808 | } |
809 | |
810 | // ------------------------------------------------------------------ |
811 | // ciTypeFlow::StateVector::do_ret |
812 | void ciTypeFlow::StateVector::do_ret(ciBytecodeStream* str) { |
813 | Cell index = local(str->get_index()); |
814 | |
815 | ciType* address = type_at(index); |
816 | assert(address->is_return_address(), "bad return address" ); |
817 | set_type_at(index, bottom_type()); |
818 | } |
819 | |
820 | // ------------------------------------------------------------------ |
821 | // ciTypeFlow::StateVector::trap |
822 | // |
823 | // Stop interpretation of this path with a trap. |
824 | void ciTypeFlow::StateVector::trap(ciBytecodeStream* str, ciKlass* klass, int index) { |
825 | _trap_bci = str->cur_bci(); |
826 | _trap_index = index; |
827 | |
828 | // Log information about this trap: |
829 | CompileLog* log = outer()->env()->log(); |
830 | if (log != NULL) { |
831 | int mid = log->identify(outer()->method()); |
832 | int kid = (klass == NULL)? -1: log->identify(klass); |
833 | log->begin_elem("uncommon_trap method='%d' bci='%d'" , mid, str->cur_bci()); |
834 | char buf[100]; |
835 | log->print(" %s" , Deoptimization::format_trap_request(buf, sizeof(buf), |
836 | index)); |
837 | if (kid >= 0) |
838 | log->print(" klass='%d'" , kid); |
839 | log->end_elem(); |
840 | } |
841 | } |
842 | |
843 | // ------------------------------------------------------------------ |
844 | // ciTypeFlow::StateVector::do_null_assert |
845 | // Corresponds to graphKit::do_null_assert. |
846 | void ciTypeFlow::StateVector::do_null_assert(ciKlass* unloaded_klass) { |
847 | if (unloaded_klass->is_loaded()) { |
848 | // We failed to link, but we can still compute with this class, |
849 | // since it is loaded somewhere. The compiler will uncommon_trap |
850 | // if the object is not null, but the typeflow pass can not assume |
851 | // that the object will be null, otherwise it may incorrectly tell |
852 | // the parser that an object is known to be null. 4761344, 4807707 |
853 | push_object(unloaded_klass); |
854 | } else { |
855 | // The class is not loaded anywhere. It is safe to model the |
856 | // null in the typestates, because we can compile in a null check |
857 | // which will deoptimize us if someone manages to load the |
858 | // class later. |
859 | push_null(); |
860 | } |
861 | } |
862 | |
863 | |
864 | // ------------------------------------------------------------------ |
865 | // ciTypeFlow::StateVector::apply_one_bytecode |
866 | // |
867 | // Apply the effect of one bytecode to this StateVector |
868 | bool ciTypeFlow::StateVector::apply_one_bytecode(ciBytecodeStream* str) { |
869 | _trap_bci = -1; |
870 | _trap_index = 0; |
871 | |
872 | if (CITraceTypeFlow) { |
873 | tty->print_cr(">> Interpreting bytecode %d:%s" , str->cur_bci(), |
874 | Bytecodes::name(str->cur_bc())); |
875 | } |
876 | |
877 | switch(str->cur_bc()) { |
878 | case Bytecodes::_aaload: do_aaload(str); break; |
879 | |
880 | case Bytecodes::_aastore: |
881 | { |
882 | pop_object(); |
883 | pop_int(); |
884 | pop_objArray(); |
885 | break; |
886 | } |
887 | case Bytecodes::_aconst_null: |
888 | { |
889 | push_null(); |
890 | break; |
891 | } |
892 | case Bytecodes::_aload: load_local_object(str->get_index()); break; |
893 | case Bytecodes::_aload_0: load_local_object(0); break; |
894 | case Bytecodes::_aload_1: load_local_object(1); break; |
895 | case Bytecodes::_aload_2: load_local_object(2); break; |
896 | case Bytecodes::_aload_3: load_local_object(3); break; |
897 | |
898 | case Bytecodes::_anewarray: |
899 | { |
900 | pop_int(); |
901 | bool will_link; |
902 | ciKlass* element_klass = str->get_klass(will_link); |
903 | if (!will_link) { |
904 | trap(str, element_klass, str->get_klass_index()); |
905 | } else { |
906 | push_object(ciObjArrayKlass::make(element_klass)); |
907 | } |
908 | break; |
909 | } |
910 | case Bytecodes::_areturn: |
911 | case Bytecodes::_ifnonnull: |
912 | case Bytecodes::_ifnull: |
913 | { |
914 | pop_object(); |
915 | break; |
916 | } |
917 | case Bytecodes::_monitorenter: |
918 | { |
919 | pop_object(); |
920 | set_monitor_count(monitor_count() + 1); |
921 | break; |
922 | } |
923 | case Bytecodes::_monitorexit: |
924 | { |
925 | pop_object(); |
926 | assert(monitor_count() > 0, "must be a monitor to exit from" ); |
927 | set_monitor_count(monitor_count() - 1); |
928 | break; |
929 | } |
930 | case Bytecodes::_arraylength: |
931 | { |
932 | pop_array(); |
933 | push_int(); |
934 | break; |
935 | } |
936 | case Bytecodes::_astore: store_local_object(str->get_index()); break; |
937 | case Bytecodes::_astore_0: store_local_object(0); break; |
938 | case Bytecodes::_astore_1: store_local_object(1); break; |
939 | case Bytecodes::_astore_2: store_local_object(2); break; |
940 | case Bytecodes::_astore_3: store_local_object(3); break; |
941 | |
942 | case Bytecodes::_athrow: |
943 | { |
944 | NEEDS_CLEANUP; |
945 | pop_object(); |
946 | break; |
947 | } |
948 | case Bytecodes::_baload: |
949 | case Bytecodes::_caload: |
950 | case Bytecodes::_iaload: |
951 | case Bytecodes::_saload: |
952 | { |
953 | pop_int(); |
954 | ciTypeArrayKlass* array_klass = pop_typeArray(); |
955 | // Put assert here for right type? |
956 | push_int(); |
957 | break; |
958 | } |
959 | case Bytecodes::_bastore: |
960 | case Bytecodes::_castore: |
961 | case Bytecodes::_iastore: |
962 | case Bytecodes::_sastore: |
963 | { |
964 | pop_int(); |
965 | pop_int(); |
966 | pop_typeArray(); |
967 | // assert here? |
968 | break; |
969 | } |
970 | case Bytecodes::_bipush: |
971 | case Bytecodes::_iconst_m1: |
972 | case Bytecodes::_iconst_0: |
973 | case Bytecodes::_iconst_1: |
974 | case Bytecodes::_iconst_2: |
975 | case Bytecodes::_iconst_3: |
976 | case Bytecodes::_iconst_4: |
977 | case Bytecodes::_iconst_5: |
978 | case Bytecodes::_sipush: |
979 | { |
980 | push_int(); |
981 | break; |
982 | } |
983 | case Bytecodes::_checkcast: do_checkcast(str); break; |
984 | |
985 | case Bytecodes::_d2f: |
986 | { |
987 | pop_double(); |
988 | push_float(); |
989 | break; |
990 | } |
991 | case Bytecodes::_d2i: |
992 | { |
993 | pop_double(); |
994 | push_int(); |
995 | break; |
996 | } |
997 | case Bytecodes::_d2l: |
998 | { |
999 | pop_double(); |
1000 | push_long(); |
1001 | break; |
1002 | } |
1003 | case Bytecodes::_dadd: |
1004 | case Bytecodes::_ddiv: |
1005 | case Bytecodes::_dmul: |
1006 | case Bytecodes::_drem: |
1007 | case Bytecodes::_dsub: |
1008 | { |
1009 | pop_double(); |
1010 | pop_double(); |
1011 | push_double(); |
1012 | break; |
1013 | } |
1014 | case Bytecodes::_daload: |
1015 | { |
1016 | pop_int(); |
1017 | ciTypeArrayKlass* array_klass = pop_typeArray(); |
1018 | // Put assert here for right type? |
1019 | push_double(); |
1020 | break; |
1021 | } |
1022 | case Bytecodes::_dastore: |
1023 | { |
1024 | pop_double(); |
1025 | pop_int(); |
1026 | pop_typeArray(); |
1027 | // assert here? |
1028 | break; |
1029 | } |
1030 | case Bytecodes::_dcmpg: |
1031 | case Bytecodes::_dcmpl: |
1032 | { |
1033 | pop_double(); |
1034 | pop_double(); |
1035 | push_int(); |
1036 | break; |
1037 | } |
1038 | case Bytecodes::_dconst_0: |
1039 | case Bytecodes::_dconst_1: |
1040 | { |
1041 | push_double(); |
1042 | break; |
1043 | } |
1044 | case Bytecodes::_dload: load_local_double(str->get_index()); break; |
1045 | case Bytecodes::_dload_0: load_local_double(0); break; |
1046 | case Bytecodes::_dload_1: load_local_double(1); break; |
1047 | case Bytecodes::_dload_2: load_local_double(2); break; |
1048 | case Bytecodes::_dload_3: load_local_double(3); break; |
1049 | |
1050 | case Bytecodes::_dneg: |
1051 | { |
1052 | pop_double(); |
1053 | push_double(); |
1054 | break; |
1055 | } |
1056 | case Bytecodes::_dreturn: |
1057 | { |
1058 | pop_double(); |
1059 | break; |
1060 | } |
1061 | case Bytecodes::_dstore: store_local_double(str->get_index()); break; |
1062 | case Bytecodes::_dstore_0: store_local_double(0); break; |
1063 | case Bytecodes::_dstore_1: store_local_double(1); break; |
1064 | case Bytecodes::_dstore_2: store_local_double(2); break; |
1065 | case Bytecodes::_dstore_3: store_local_double(3); break; |
1066 | |
1067 | case Bytecodes::_dup: |
1068 | { |
1069 | push(type_at_tos()); |
1070 | break; |
1071 | } |
1072 | case Bytecodes::_dup_x1: |
1073 | { |
1074 | ciType* value1 = pop_value(); |
1075 | ciType* value2 = pop_value(); |
1076 | push(value1); |
1077 | push(value2); |
1078 | push(value1); |
1079 | break; |
1080 | } |
1081 | case Bytecodes::_dup_x2: |
1082 | { |
1083 | ciType* value1 = pop_value(); |
1084 | ciType* value2 = pop_value(); |
1085 | ciType* value3 = pop_value(); |
1086 | push(value1); |
1087 | push(value3); |
1088 | push(value2); |
1089 | push(value1); |
1090 | break; |
1091 | } |
1092 | case Bytecodes::_dup2: |
1093 | { |
1094 | ciType* value1 = pop_value(); |
1095 | ciType* value2 = pop_value(); |
1096 | push(value2); |
1097 | push(value1); |
1098 | push(value2); |
1099 | push(value1); |
1100 | break; |
1101 | } |
1102 | case Bytecodes::_dup2_x1: |
1103 | { |
1104 | ciType* value1 = pop_value(); |
1105 | ciType* value2 = pop_value(); |
1106 | ciType* value3 = pop_value(); |
1107 | push(value2); |
1108 | push(value1); |
1109 | push(value3); |
1110 | push(value2); |
1111 | push(value1); |
1112 | break; |
1113 | } |
1114 | case Bytecodes::_dup2_x2: |
1115 | { |
1116 | ciType* value1 = pop_value(); |
1117 | ciType* value2 = pop_value(); |
1118 | ciType* value3 = pop_value(); |
1119 | ciType* value4 = pop_value(); |
1120 | push(value2); |
1121 | push(value1); |
1122 | push(value4); |
1123 | push(value3); |
1124 | push(value2); |
1125 | push(value1); |
1126 | break; |
1127 | } |
1128 | case Bytecodes::_f2d: |
1129 | { |
1130 | pop_float(); |
1131 | push_double(); |
1132 | break; |
1133 | } |
1134 | case Bytecodes::_f2i: |
1135 | { |
1136 | pop_float(); |
1137 | push_int(); |
1138 | break; |
1139 | } |
1140 | case Bytecodes::_f2l: |
1141 | { |
1142 | pop_float(); |
1143 | push_long(); |
1144 | break; |
1145 | } |
1146 | case Bytecodes::_fadd: |
1147 | case Bytecodes::_fdiv: |
1148 | case Bytecodes::_fmul: |
1149 | case Bytecodes::_frem: |
1150 | case Bytecodes::_fsub: |
1151 | { |
1152 | pop_float(); |
1153 | pop_float(); |
1154 | push_float(); |
1155 | break; |
1156 | } |
1157 | case Bytecodes::_faload: |
1158 | { |
1159 | pop_int(); |
1160 | ciTypeArrayKlass* array_klass = pop_typeArray(); |
1161 | // Put assert here. |
1162 | push_float(); |
1163 | break; |
1164 | } |
1165 | case Bytecodes::_fastore: |
1166 | { |
1167 | pop_float(); |
1168 | pop_int(); |
1169 | ciTypeArrayKlass* array_klass = pop_typeArray(); |
1170 | // Put assert here. |
1171 | break; |
1172 | } |
1173 | case Bytecodes::_fcmpg: |
1174 | case Bytecodes::_fcmpl: |
1175 | { |
1176 | pop_float(); |
1177 | pop_float(); |
1178 | push_int(); |
1179 | break; |
1180 | } |
1181 | case Bytecodes::_fconst_0: |
1182 | case Bytecodes::_fconst_1: |
1183 | case Bytecodes::_fconst_2: |
1184 | { |
1185 | push_float(); |
1186 | break; |
1187 | } |
1188 | case Bytecodes::_fload: load_local_float(str->get_index()); break; |
1189 | case Bytecodes::_fload_0: load_local_float(0); break; |
1190 | case Bytecodes::_fload_1: load_local_float(1); break; |
1191 | case Bytecodes::_fload_2: load_local_float(2); break; |
1192 | case Bytecodes::_fload_3: load_local_float(3); break; |
1193 | |
1194 | case Bytecodes::_fneg: |
1195 | { |
1196 | pop_float(); |
1197 | push_float(); |
1198 | break; |
1199 | } |
1200 | case Bytecodes::_freturn: |
1201 | { |
1202 | pop_float(); |
1203 | break; |
1204 | } |
1205 | case Bytecodes::_fstore: store_local_float(str->get_index()); break; |
1206 | case Bytecodes::_fstore_0: store_local_float(0); break; |
1207 | case Bytecodes::_fstore_1: store_local_float(1); break; |
1208 | case Bytecodes::_fstore_2: store_local_float(2); break; |
1209 | case Bytecodes::_fstore_3: store_local_float(3); break; |
1210 | |
1211 | case Bytecodes::_getfield: do_getfield(str); break; |
1212 | case Bytecodes::_getstatic: do_getstatic(str); break; |
1213 | |
1214 | case Bytecodes::_goto: |
1215 | case Bytecodes::_goto_w: |
1216 | case Bytecodes::_nop: |
1217 | case Bytecodes::_return: |
1218 | { |
1219 | // do nothing. |
1220 | break; |
1221 | } |
1222 | case Bytecodes::_i2b: |
1223 | case Bytecodes::_i2c: |
1224 | case Bytecodes::_i2s: |
1225 | case Bytecodes::_ineg: |
1226 | { |
1227 | pop_int(); |
1228 | push_int(); |
1229 | break; |
1230 | } |
1231 | case Bytecodes::_i2d: |
1232 | { |
1233 | pop_int(); |
1234 | push_double(); |
1235 | break; |
1236 | } |
1237 | case Bytecodes::_i2f: |
1238 | { |
1239 | pop_int(); |
1240 | push_float(); |
1241 | break; |
1242 | } |
1243 | case Bytecodes::_i2l: |
1244 | { |
1245 | pop_int(); |
1246 | push_long(); |
1247 | break; |
1248 | } |
1249 | case Bytecodes::_iadd: |
1250 | case Bytecodes::_iand: |
1251 | case Bytecodes::_idiv: |
1252 | case Bytecodes::_imul: |
1253 | case Bytecodes::_ior: |
1254 | case Bytecodes::_irem: |
1255 | case Bytecodes::_ishl: |
1256 | case Bytecodes::_ishr: |
1257 | case Bytecodes::_isub: |
1258 | case Bytecodes::_iushr: |
1259 | case Bytecodes::_ixor: |
1260 | { |
1261 | pop_int(); |
1262 | pop_int(); |
1263 | push_int(); |
1264 | break; |
1265 | } |
1266 | case Bytecodes::_if_acmpeq: |
1267 | case Bytecodes::_if_acmpne: |
1268 | { |
1269 | pop_object(); |
1270 | pop_object(); |
1271 | break; |
1272 | } |
1273 | case Bytecodes::_if_icmpeq: |
1274 | case Bytecodes::_if_icmpge: |
1275 | case Bytecodes::_if_icmpgt: |
1276 | case Bytecodes::_if_icmple: |
1277 | case Bytecodes::_if_icmplt: |
1278 | case Bytecodes::_if_icmpne: |
1279 | { |
1280 | pop_int(); |
1281 | pop_int(); |
1282 | break; |
1283 | } |
1284 | case Bytecodes::_ifeq: |
1285 | case Bytecodes::_ifle: |
1286 | case Bytecodes::_iflt: |
1287 | case Bytecodes::_ifge: |
1288 | case Bytecodes::_ifgt: |
1289 | case Bytecodes::_ifne: |
1290 | case Bytecodes::_ireturn: |
1291 | case Bytecodes::_lookupswitch: |
1292 | case Bytecodes::_tableswitch: |
1293 | { |
1294 | pop_int(); |
1295 | break; |
1296 | } |
1297 | case Bytecodes::_iinc: |
1298 | { |
1299 | int lnum = str->get_index(); |
1300 | check_int(local(lnum)); |
1301 | store_to_local(lnum); |
1302 | break; |
1303 | } |
1304 | case Bytecodes::_iload: load_local_int(str->get_index()); break; |
1305 | case Bytecodes::_iload_0: load_local_int(0); break; |
1306 | case Bytecodes::_iload_1: load_local_int(1); break; |
1307 | case Bytecodes::_iload_2: load_local_int(2); break; |
1308 | case Bytecodes::_iload_3: load_local_int(3); break; |
1309 | |
1310 | case Bytecodes::_instanceof: |
1311 | { |
1312 | // Check for uncommon trap: |
1313 | do_checkcast(str); |
1314 | pop_object(); |
1315 | push_int(); |
1316 | break; |
1317 | } |
1318 | case Bytecodes::_invokeinterface: do_invoke(str, true); break; |
1319 | case Bytecodes::_invokespecial: do_invoke(str, true); break; |
1320 | case Bytecodes::_invokestatic: do_invoke(str, false); break; |
1321 | case Bytecodes::_invokevirtual: do_invoke(str, true); break; |
1322 | case Bytecodes::_invokedynamic: do_invoke(str, false); break; |
1323 | |
1324 | case Bytecodes::_istore: store_local_int(str->get_index()); break; |
1325 | case Bytecodes::_istore_0: store_local_int(0); break; |
1326 | case Bytecodes::_istore_1: store_local_int(1); break; |
1327 | case Bytecodes::_istore_2: store_local_int(2); break; |
1328 | case Bytecodes::_istore_3: store_local_int(3); break; |
1329 | |
1330 | case Bytecodes::_jsr: |
1331 | case Bytecodes::_jsr_w: do_jsr(str); break; |
1332 | |
1333 | case Bytecodes::_l2d: |
1334 | { |
1335 | pop_long(); |
1336 | push_double(); |
1337 | break; |
1338 | } |
1339 | case Bytecodes::_l2f: |
1340 | { |
1341 | pop_long(); |
1342 | push_float(); |
1343 | break; |
1344 | } |
1345 | case Bytecodes::_l2i: |
1346 | { |
1347 | pop_long(); |
1348 | push_int(); |
1349 | break; |
1350 | } |
1351 | case Bytecodes::_ladd: |
1352 | case Bytecodes::_land: |
1353 | case Bytecodes::_ldiv: |
1354 | case Bytecodes::_lmul: |
1355 | case Bytecodes::_lor: |
1356 | case Bytecodes::_lrem: |
1357 | case Bytecodes::_lsub: |
1358 | case Bytecodes::_lxor: |
1359 | { |
1360 | pop_long(); |
1361 | pop_long(); |
1362 | push_long(); |
1363 | break; |
1364 | } |
1365 | case Bytecodes::_laload: |
1366 | { |
1367 | pop_int(); |
1368 | ciTypeArrayKlass* array_klass = pop_typeArray(); |
1369 | // Put assert here for right type? |
1370 | push_long(); |
1371 | break; |
1372 | } |
1373 | case Bytecodes::_lastore: |
1374 | { |
1375 | pop_long(); |
1376 | pop_int(); |
1377 | pop_typeArray(); |
1378 | // assert here? |
1379 | break; |
1380 | } |
1381 | case Bytecodes::_lcmp: |
1382 | { |
1383 | pop_long(); |
1384 | pop_long(); |
1385 | push_int(); |
1386 | break; |
1387 | } |
1388 | case Bytecodes::_lconst_0: |
1389 | case Bytecodes::_lconst_1: |
1390 | { |
1391 | push_long(); |
1392 | break; |
1393 | } |
1394 | case Bytecodes::_ldc: |
1395 | case Bytecodes::_ldc_w: |
1396 | case Bytecodes::_ldc2_w: |
1397 | { |
1398 | do_ldc(str); |
1399 | break; |
1400 | } |
1401 | |
1402 | case Bytecodes::_lload: load_local_long(str->get_index()); break; |
1403 | case Bytecodes::_lload_0: load_local_long(0); break; |
1404 | case Bytecodes::_lload_1: load_local_long(1); break; |
1405 | case Bytecodes::_lload_2: load_local_long(2); break; |
1406 | case Bytecodes::_lload_3: load_local_long(3); break; |
1407 | |
1408 | case Bytecodes::_lneg: |
1409 | { |
1410 | pop_long(); |
1411 | push_long(); |
1412 | break; |
1413 | } |
1414 | case Bytecodes::_lreturn: |
1415 | { |
1416 | pop_long(); |
1417 | break; |
1418 | } |
1419 | case Bytecodes::_lshl: |
1420 | case Bytecodes::_lshr: |
1421 | case Bytecodes::_lushr: |
1422 | { |
1423 | pop_int(); |
1424 | pop_long(); |
1425 | push_long(); |
1426 | break; |
1427 | } |
1428 | case Bytecodes::_lstore: store_local_long(str->get_index()); break; |
1429 | case Bytecodes::_lstore_0: store_local_long(0); break; |
1430 | case Bytecodes::_lstore_1: store_local_long(1); break; |
1431 | case Bytecodes::_lstore_2: store_local_long(2); break; |
1432 | case Bytecodes::_lstore_3: store_local_long(3); break; |
1433 | |
1434 | case Bytecodes::_multianewarray: do_multianewarray(str); break; |
1435 | |
1436 | case Bytecodes::_new: do_new(str); break; |
1437 | |
1438 | case Bytecodes::_newarray: do_newarray(str); break; |
1439 | |
1440 | case Bytecodes::_pop: |
1441 | { |
1442 | pop(); |
1443 | break; |
1444 | } |
1445 | case Bytecodes::_pop2: |
1446 | { |
1447 | pop(); |
1448 | pop(); |
1449 | break; |
1450 | } |
1451 | |
1452 | case Bytecodes::_putfield: do_putfield(str); break; |
1453 | case Bytecodes::_putstatic: do_putstatic(str); break; |
1454 | |
1455 | case Bytecodes::_ret: do_ret(str); break; |
1456 | |
1457 | case Bytecodes::_swap: |
1458 | { |
1459 | ciType* value1 = pop_value(); |
1460 | ciType* value2 = pop_value(); |
1461 | push(value1); |
1462 | push(value2); |
1463 | break; |
1464 | } |
1465 | case Bytecodes::_wide: |
1466 | default: |
1467 | { |
1468 | // The iterator should skip this. |
1469 | ShouldNotReachHere(); |
1470 | break; |
1471 | } |
1472 | } |
1473 | |
1474 | if (CITraceTypeFlow) { |
1475 | print_on(tty); |
1476 | } |
1477 | |
1478 | return (_trap_bci != -1); |
1479 | } |
1480 | |
1481 | #ifndef PRODUCT |
1482 | // ------------------------------------------------------------------ |
1483 | // ciTypeFlow::StateVector::print_cell_on |
1484 | void ciTypeFlow::StateVector::print_cell_on(outputStream* st, Cell c) const { |
1485 | ciType* type = type_at(c); |
1486 | if (type == top_type()) { |
1487 | st->print("top" ); |
1488 | } else if (type == bottom_type()) { |
1489 | st->print("bottom" ); |
1490 | } else if (type == null_type()) { |
1491 | st->print("null" ); |
1492 | } else if (type == long2_type()) { |
1493 | st->print("long2" ); |
1494 | } else if (type == double2_type()) { |
1495 | st->print("double2" ); |
1496 | } else if (is_int(type)) { |
1497 | st->print("int" ); |
1498 | } else if (is_long(type)) { |
1499 | st->print("long" ); |
1500 | } else if (is_float(type)) { |
1501 | st->print("float" ); |
1502 | } else if (is_double(type)) { |
1503 | st->print("double" ); |
1504 | } else if (type->is_return_address()) { |
1505 | st->print("address(%d)" , type->as_return_address()->bci()); |
1506 | } else { |
1507 | if (type->is_klass()) { |
1508 | type->as_klass()->name()->print_symbol_on(st); |
1509 | } else { |
1510 | st->print("UNEXPECTED TYPE" ); |
1511 | type->print(); |
1512 | } |
1513 | } |
1514 | } |
1515 | |
1516 | // ------------------------------------------------------------------ |
1517 | // ciTypeFlow::StateVector::print_on |
1518 | void ciTypeFlow::StateVector::print_on(outputStream* st) const { |
1519 | int num_locals = _outer->max_locals(); |
1520 | int num_stack = stack_size(); |
1521 | int num_monitors = monitor_count(); |
1522 | st->print_cr(" State : locals %d, stack %d, monitors %d" , num_locals, num_stack, num_monitors); |
1523 | if (num_stack >= 0) { |
1524 | int i; |
1525 | for (i = 0; i < num_locals; i++) { |
1526 | st->print(" local %2d : " , i); |
1527 | print_cell_on(st, local(i)); |
1528 | st->cr(); |
1529 | } |
1530 | for (i = 0; i < num_stack; i++) { |
1531 | st->print(" stack %2d : " , i); |
1532 | print_cell_on(st, stack(i)); |
1533 | st->cr(); |
1534 | } |
1535 | } |
1536 | } |
1537 | #endif |
1538 | |
1539 | |
1540 | // ------------------------------------------------------------------ |
1541 | // ciTypeFlow::SuccIter::next |
1542 | // |
1543 | void ciTypeFlow::SuccIter::next() { |
1544 | int succ_ct = _pred->successors()->length(); |
1545 | int next = _index + 1; |
1546 | if (next < succ_ct) { |
1547 | _index = next; |
1548 | _succ = _pred->successors()->at(next); |
1549 | return; |
1550 | } |
1551 | for (int i = next - succ_ct; i < _pred->exceptions()->length(); i++) { |
1552 | // Do not compile any code for unloaded exception types. |
1553 | // Following compiler passes are responsible for doing this also. |
1554 | ciInstanceKlass* exception_klass = _pred->exc_klasses()->at(i); |
1555 | if (exception_klass->is_loaded()) { |
1556 | _index = next; |
1557 | _succ = _pred->exceptions()->at(i); |
1558 | return; |
1559 | } |
1560 | next++; |
1561 | } |
1562 | _index = -1; |
1563 | _succ = NULL; |
1564 | } |
1565 | |
1566 | // ------------------------------------------------------------------ |
1567 | // ciTypeFlow::SuccIter::set_succ |
1568 | // |
1569 | void ciTypeFlow::SuccIter::set_succ(Block* succ) { |
1570 | int succ_ct = _pred->successors()->length(); |
1571 | if (_index < succ_ct) { |
1572 | _pred->successors()->at_put(_index, succ); |
1573 | } else { |
1574 | int idx = _index - succ_ct; |
1575 | _pred->exceptions()->at_put(idx, succ); |
1576 | } |
1577 | } |
1578 | |
1579 | // ciTypeFlow::Block |
1580 | // |
1581 | // A basic block. |
1582 | |
1583 | // ------------------------------------------------------------------ |
1584 | // ciTypeFlow::Block::Block |
1585 | ciTypeFlow::Block::Block(ciTypeFlow* outer, |
1586 | ciBlock *ciblk, |
1587 | ciTypeFlow::JsrSet* jsrs) { |
1588 | _ciblock = ciblk; |
1589 | _exceptions = NULL; |
1590 | _exc_klasses = NULL; |
1591 | _successors = NULL; |
1592 | _predecessors = new (outer->arena()) GrowableArray<Block*>(outer->arena(), 1, 0, NULL); |
1593 | _state = new (outer->arena()) StateVector(outer); |
1594 | JsrSet* new_jsrs = |
1595 | new (outer->arena()) JsrSet(outer->arena(), jsrs->size()); |
1596 | jsrs->copy_into(new_jsrs); |
1597 | _jsrs = new_jsrs; |
1598 | _next = NULL; |
1599 | _on_work_list = false; |
1600 | _backedge_copy = false; |
1601 | _has_monitorenter = false; |
1602 | _trap_bci = -1; |
1603 | _trap_index = 0; |
1604 | df_init(); |
1605 | |
1606 | if (CITraceTypeFlow) { |
1607 | tty->print_cr(">> Created new block" ); |
1608 | print_on(tty); |
1609 | } |
1610 | |
1611 | assert(this->outer() == outer, "outer link set up" ); |
1612 | assert(!outer->have_block_count(), "must not have mapped blocks yet" ); |
1613 | } |
1614 | |
1615 | // ------------------------------------------------------------------ |
1616 | // ciTypeFlow::Block::df_init |
1617 | void ciTypeFlow::Block::df_init() { |
1618 | _pre_order = -1; assert(!has_pre_order(), "" ); |
1619 | _post_order = -1; assert(!has_post_order(), "" ); |
1620 | _loop = NULL; |
1621 | _irreducible_entry = false; |
1622 | _rpo_next = NULL; |
1623 | } |
1624 | |
1625 | // ------------------------------------------------------------------ |
1626 | // ciTypeFlow::Block::successors |
1627 | // |
1628 | // Get the successors for this Block. |
1629 | GrowableArray<ciTypeFlow::Block*>* |
1630 | ciTypeFlow::Block::successors(ciBytecodeStream* str, |
1631 | ciTypeFlow::StateVector* state, |
1632 | ciTypeFlow::JsrSet* jsrs) { |
1633 | if (_successors == NULL) { |
1634 | if (CITraceTypeFlow) { |
1635 | tty->print(">> Computing successors for block " ); |
1636 | print_value_on(tty); |
1637 | tty->cr(); |
1638 | } |
1639 | |
1640 | ciTypeFlow* analyzer = outer(); |
1641 | Arena* arena = analyzer->arena(); |
1642 | Block* block = NULL; |
1643 | bool has_successor = !has_trap() && |
1644 | (control() != ciBlock::fall_through_bci || limit() < analyzer->code_size()); |
1645 | if (!has_successor) { |
1646 | _successors = |
1647 | new (arena) GrowableArray<Block*>(arena, 1, 0, NULL); |
1648 | // No successors |
1649 | } else if (control() == ciBlock::fall_through_bci) { |
1650 | assert(str->cur_bci() == limit(), "bad block end" ); |
1651 | // This block simply falls through to the next. |
1652 | _successors = |
1653 | new (arena) GrowableArray<Block*>(arena, 1, 0, NULL); |
1654 | |
1655 | Block* block = analyzer->block_at(limit(), _jsrs); |
1656 | assert(_successors->length() == FALL_THROUGH, "" ); |
1657 | _successors->append(block); |
1658 | } else { |
1659 | int current_bci = str->cur_bci(); |
1660 | int next_bci = str->next_bci(); |
1661 | int branch_bci = -1; |
1662 | Block* target = NULL; |
1663 | assert(str->next_bci() == limit(), "bad block end" ); |
1664 | // This block is not a simple fall-though. Interpret |
1665 | // the current bytecode to find our successors. |
1666 | switch (str->cur_bc()) { |
1667 | case Bytecodes::_ifeq: case Bytecodes::_ifne: |
1668 | case Bytecodes::_iflt: case Bytecodes::_ifge: |
1669 | case Bytecodes::_ifgt: case Bytecodes::_ifle: |
1670 | case Bytecodes::_if_icmpeq: case Bytecodes::_if_icmpne: |
1671 | case Bytecodes::_if_icmplt: case Bytecodes::_if_icmpge: |
1672 | case Bytecodes::_if_icmpgt: case Bytecodes::_if_icmple: |
1673 | case Bytecodes::_if_acmpeq: case Bytecodes::_if_acmpne: |
1674 | case Bytecodes::_ifnull: case Bytecodes::_ifnonnull: |
1675 | // Our successors are the branch target and the next bci. |
1676 | branch_bci = str->get_dest(); |
1677 | _successors = |
1678 | new (arena) GrowableArray<Block*>(arena, 2, 0, NULL); |
1679 | assert(_successors->length() == IF_NOT_TAKEN, "" ); |
1680 | _successors->append(analyzer->block_at(next_bci, jsrs)); |
1681 | assert(_successors->length() == IF_TAKEN, "" ); |
1682 | _successors->append(analyzer->block_at(branch_bci, jsrs)); |
1683 | break; |
1684 | |
1685 | case Bytecodes::_goto: |
1686 | branch_bci = str->get_dest(); |
1687 | _successors = |
1688 | new (arena) GrowableArray<Block*>(arena, 1, 0, NULL); |
1689 | assert(_successors->length() == GOTO_TARGET, "" ); |
1690 | _successors->append(analyzer->block_at(branch_bci, jsrs)); |
1691 | break; |
1692 | |
1693 | case Bytecodes::_jsr: |
1694 | branch_bci = str->get_dest(); |
1695 | _successors = |
1696 | new (arena) GrowableArray<Block*>(arena, 1, 0, NULL); |
1697 | assert(_successors->length() == GOTO_TARGET, "" ); |
1698 | _successors->append(analyzer->block_at(branch_bci, jsrs)); |
1699 | break; |
1700 | |
1701 | case Bytecodes::_goto_w: |
1702 | case Bytecodes::_jsr_w: |
1703 | _successors = |
1704 | new (arena) GrowableArray<Block*>(arena, 1, 0, NULL); |
1705 | assert(_successors->length() == GOTO_TARGET, "" ); |
1706 | _successors->append(analyzer->block_at(str->get_far_dest(), jsrs)); |
1707 | break; |
1708 | |
1709 | case Bytecodes::_tableswitch: { |
1710 | Bytecode_tableswitch tableswitch(str); |
1711 | |
1712 | int len = tableswitch.length(); |
1713 | _successors = |
1714 | new (arena) GrowableArray<Block*>(arena, len+1, 0, NULL); |
1715 | int bci = current_bci + tableswitch.default_offset(); |
1716 | Block* block = analyzer->block_at(bci, jsrs); |
1717 | assert(_successors->length() == SWITCH_DEFAULT, "" ); |
1718 | _successors->append(block); |
1719 | while (--len >= 0) { |
1720 | int bci = current_bci + tableswitch.dest_offset_at(len); |
1721 | block = analyzer->block_at(bci, jsrs); |
1722 | assert(_successors->length() >= SWITCH_CASES, "" ); |
1723 | _successors->append_if_missing(block); |
1724 | } |
1725 | break; |
1726 | } |
1727 | |
1728 | case Bytecodes::_lookupswitch: { |
1729 | Bytecode_lookupswitch lookupswitch(str); |
1730 | |
1731 | int npairs = lookupswitch.number_of_pairs(); |
1732 | _successors = |
1733 | new (arena) GrowableArray<Block*>(arena, npairs+1, 0, NULL); |
1734 | int bci = current_bci + lookupswitch.default_offset(); |
1735 | Block* block = analyzer->block_at(bci, jsrs); |
1736 | assert(_successors->length() == SWITCH_DEFAULT, "" ); |
1737 | _successors->append(block); |
1738 | while(--npairs >= 0) { |
1739 | LookupswitchPair pair = lookupswitch.pair_at(npairs); |
1740 | int bci = current_bci + pair.offset(); |
1741 | Block* block = analyzer->block_at(bci, jsrs); |
1742 | assert(_successors->length() >= SWITCH_CASES, "" ); |
1743 | _successors->append_if_missing(block); |
1744 | } |
1745 | break; |
1746 | } |
1747 | |
1748 | case Bytecodes::_athrow: case Bytecodes::_ireturn: |
1749 | case Bytecodes::_lreturn: case Bytecodes::_freturn: |
1750 | case Bytecodes::_dreturn: case Bytecodes::_areturn: |
1751 | case Bytecodes::_return: |
1752 | _successors = |
1753 | new (arena) GrowableArray<Block*>(arena, 1, 0, NULL); |
1754 | // No successors |
1755 | break; |
1756 | |
1757 | case Bytecodes::_ret: { |
1758 | _successors = |
1759 | new (arena) GrowableArray<Block*>(arena, 1, 0, NULL); |
1760 | |
1761 | Cell local = state->local(str->get_index()); |
1762 | ciType* return_address = state->type_at(local); |
1763 | assert(return_address->is_return_address(), "verify: wrong type" ); |
1764 | int bci = return_address->as_return_address()->bci(); |
1765 | assert(_successors->length() == GOTO_TARGET, "" ); |
1766 | _successors->append(analyzer->block_at(bci, jsrs)); |
1767 | break; |
1768 | } |
1769 | |
1770 | case Bytecodes::_wide: |
1771 | default: |
1772 | ShouldNotReachHere(); |
1773 | break; |
1774 | } |
1775 | } |
1776 | |
1777 | // Set predecessor information |
1778 | for (int i = 0; i < _successors->length(); i++) { |
1779 | Block* block = _successors->at(i); |
1780 | block->predecessors()->append(this); |
1781 | } |
1782 | } |
1783 | return _successors; |
1784 | } |
1785 | |
1786 | // ------------------------------------------------------------------ |
1787 | // ciTypeFlow::Block:compute_exceptions |
1788 | // |
1789 | // Compute the exceptional successors and types for this Block. |
1790 | void ciTypeFlow::Block::compute_exceptions() { |
1791 | assert(_exceptions == NULL && _exc_klasses == NULL, "repeat" ); |
1792 | |
1793 | if (CITraceTypeFlow) { |
1794 | tty->print(">> Computing exceptions for block " ); |
1795 | print_value_on(tty); |
1796 | tty->cr(); |
1797 | } |
1798 | |
1799 | ciTypeFlow* analyzer = outer(); |
1800 | Arena* arena = analyzer->arena(); |
1801 | |
1802 | // Any bci in the block will do. |
1803 | ciExceptionHandlerStream str(analyzer->method(), start()); |
1804 | |
1805 | // Allocate our growable arrays. |
1806 | int exc_count = str.count(); |
1807 | _exceptions = new (arena) GrowableArray<Block*>(arena, exc_count, 0, NULL); |
1808 | _exc_klasses = new (arena) GrowableArray<ciInstanceKlass*>(arena, exc_count, |
1809 | 0, NULL); |
1810 | |
1811 | for ( ; !str.is_done(); str.next()) { |
1812 | ciExceptionHandler* handler = str.handler(); |
1813 | int bci = handler->handler_bci(); |
1814 | ciInstanceKlass* klass = NULL; |
1815 | if (bci == -1) { |
1816 | // There is no catch all. It is possible to exit the method. |
1817 | break; |
1818 | } |
1819 | if (handler->is_catch_all()) { |
1820 | klass = analyzer->env()->Throwable_klass(); |
1821 | } else { |
1822 | klass = handler->catch_klass(); |
1823 | } |
1824 | Block* block = analyzer->block_at(bci, _jsrs); |
1825 | _exceptions->append(block); |
1826 | block->predecessors()->append(this); |
1827 | _exc_klasses->append(klass); |
1828 | } |
1829 | } |
1830 | |
1831 | // ------------------------------------------------------------------ |
1832 | // ciTypeFlow::Block::set_backedge_copy |
1833 | // Use this only to make a pre-existing public block into a backedge copy. |
1834 | void ciTypeFlow::Block::set_backedge_copy(bool z) { |
1835 | assert(z || (z == is_backedge_copy()), "cannot make a backedge copy public" ); |
1836 | _backedge_copy = z; |
1837 | } |
1838 | |
1839 | // ------------------------------------------------------------------ |
1840 | // ciTypeFlow::Block::is_clonable_exit |
1841 | // |
1842 | // At most 2 normal successors, one of which continues looping, |
1843 | // and all exceptional successors must exit. |
1844 | bool ciTypeFlow::Block::is_clonable_exit(ciTypeFlow::Loop* lp) { |
1845 | int normal_cnt = 0; |
1846 | int in_loop_cnt = 0; |
1847 | for (SuccIter iter(this); !iter.done(); iter.next()) { |
1848 | Block* succ = iter.succ(); |
1849 | if (iter.is_normal_ctrl()) { |
1850 | if (++normal_cnt > 2) return false; |
1851 | if (lp->contains(succ->loop())) { |
1852 | if (++in_loop_cnt > 1) return false; |
1853 | } |
1854 | } else { |
1855 | if (lp->contains(succ->loop())) return false; |
1856 | } |
1857 | } |
1858 | return in_loop_cnt == 1; |
1859 | } |
1860 | |
1861 | // ------------------------------------------------------------------ |
1862 | // ciTypeFlow::Block::looping_succ |
1863 | // |
1864 | ciTypeFlow::Block* ciTypeFlow::Block::looping_succ(ciTypeFlow::Loop* lp) { |
1865 | assert(successors()->length() <= 2, "at most 2 normal successors" ); |
1866 | for (SuccIter iter(this); !iter.done(); iter.next()) { |
1867 | Block* succ = iter.succ(); |
1868 | if (lp->contains(succ->loop())) { |
1869 | return succ; |
1870 | } |
1871 | } |
1872 | return NULL; |
1873 | } |
1874 | |
1875 | #ifndef PRODUCT |
1876 | // ------------------------------------------------------------------ |
1877 | // ciTypeFlow::Block::print_value_on |
1878 | void ciTypeFlow::Block::print_value_on(outputStream* st) const { |
1879 | if (has_pre_order()) st->print("#%-2d " , pre_order()); |
1880 | if (has_rpo()) st->print("rpo#%-2d " , rpo()); |
1881 | st->print("[%d - %d)" , start(), limit()); |
1882 | if (is_loop_head()) st->print(" lphd" ); |
1883 | if (is_irreducible_entry()) st->print(" irred" ); |
1884 | if (_jsrs->size() > 0) { st->print("/" ); _jsrs->print_on(st); } |
1885 | if (is_backedge_copy()) st->print("/backedge_copy" ); |
1886 | } |
1887 | |
1888 | // ------------------------------------------------------------------ |
1889 | // ciTypeFlow::Block::print_on |
1890 | void ciTypeFlow::Block::print_on(outputStream* st) const { |
1891 | if ((Verbose || WizardMode) && (limit() >= 0)) { |
1892 | // Don't print 'dummy' blocks (i.e. blocks with limit() '-1') |
1893 | outer()->method()->print_codes_on(start(), limit(), st); |
1894 | } |
1895 | st->print_cr(" ==================================================== " ); |
1896 | st->print (" " ); |
1897 | print_value_on(st); |
1898 | st->print(" Stored locals: " ); def_locals()->print_on(st, outer()->method()->max_locals()); tty->cr(); |
1899 | if (loop() && loop()->parent() != NULL) { |
1900 | st->print(" loops:" ); |
1901 | Loop* lp = loop(); |
1902 | do { |
1903 | st->print(" %d<-%d" , lp->head()->pre_order(),lp->tail()->pre_order()); |
1904 | if (lp->is_irreducible()) st->print("(ir)" ); |
1905 | lp = lp->parent(); |
1906 | } while (lp->parent() != NULL); |
1907 | } |
1908 | st->cr(); |
1909 | _state->print_on(st); |
1910 | if (_successors == NULL) { |
1911 | st->print_cr(" No successor information" ); |
1912 | } else { |
1913 | int num_successors = _successors->length(); |
1914 | st->print_cr(" Successors : %d" , num_successors); |
1915 | for (int i = 0; i < num_successors; i++) { |
1916 | Block* successor = _successors->at(i); |
1917 | st->print(" " ); |
1918 | successor->print_value_on(st); |
1919 | st->cr(); |
1920 | } |
1921 | } |
1922 | if (_predecessors == NULL) { |
1923 | st->print_cr(" No predecessor information" ); |
1924 | } else { |
1925 | int num_predecessors = _predecessors->length(); |
1926 | st->print_cr(" Predecessors : %d" , num_predecessors); |
1927 | for (int i = 0; i < num_predecessors; i++) { |
1928 | Block* predecessor = _predecessors->at(i); |
1929 | st->print(" " ); |
1930 | predecessor->print_value_on(st); |
1931 | st->cr(); |
1932 | } |
1933 | } |
1934 | if (_exceptions == NULL) { |
1935 | st->print_cr(" No exception information" ); |
1936 | } else { |
1937 | int num_exceptions = _exceptions->length(); |
1938 | st->print_cr(" Exceptions : %d" , num_exceptions); |
1939 | for (int i = 0; i < num_exceptions; i++) { |
1940 | Block* exc_succ = _exceptions->at(i); |
1941 | ciInstanceKlass* exc_klass = _exc_klasses->at(i); |
1942 | st->print(" " ); |
1943 | exc_succ->print_value_on(st); |
1944 | st->print(" -- " ); |
1945 | exc_klass->name()->print_symbol_on(st); |
1946 | st->cr(); |
1947 | } |
1948 | } |
1949 | if (has_trap()) { |
1950 | st->print_cr(" Traps on %d with trap index %d" , trap_bci(), trap_index()); |
1951 | } |
1952 | st->print_cr(" ==================================================== " ); |
1953 | } |
1954 | #endif |
1955 | |
1956 | #ifndef PRODUCT |
1957 | // ------------------------------------------------------------------ |
1958 | // ciTypeFlow::LocalSet::print_on |
1959 | void ciTypeFlow::LocalSet::print_on(outputStream* st, int limit) const { |
1960 | st->print("{" ); |
1961 | for (int i = 0; i < max; i++) { |
1962 | if (test(i)) st->print(" %d" , i); |
1963 | } |
1964 | if (limit > max) { |
1965 | st->print(" %d..%d " , max, limit); |
1966 | } |
1967 | st->print(" }" ); |
1968 | } |
1969 | #endif |
1970 | |
1971 | // ciTypeFlow |
1972 | // |
1973 | // This is a pass over the bytecodes which computes the following: |
1974 | // basic block structure |
1975 | // interpreter type-states (a la the verifier) |
1976 | |
1977 | // ------------------------------------------------------------------ |
1978 | // ciTypeFlow::ciTypeFlow |
1979 | ciTypeFlow::ciTypeFlow(ciEnv* env, ciMethod* method, int osr_bci) { |
1980 | _env = env; |
1981 | _method = method; |
1982 | _methodBlocks = method->get_method_blocks(); |
1983 | _max_locals = method->max_locals(); |
1984 | _max_stack = method->max_stack(); |
1985 | _code_size = method->code_size(); |
1986 | _has_irreducible_entry = false; |
1987 | _osr_bci = osr_bci; |
1988 | _failure_reason = NULL; |
1989 | assert(0 <= start_bci() && start_bci() < code_size() , "correct osr_bci argument: 0 <= %d < %d" , start_bci(), code_size()); |
1990 | _work_list = NULL; |
1991 | |
1992 | _ciblock_count = _methodBlocks->num_blocks(); |
1993 | _idx_to_blocklist = NEW_ARENA_ARRAY(arena(), GrowableArray<Block*>*, _ciblock_count); |
1994 | for (int i = 0; i < _ciblock_count; i++) { |
1995 | _idx_to_blocklist[i] = NULL; |
1996 | } |
1997 | _block_map = NULL; // until all blocks are seen |
1998 | _jsr_count = 0; |
1999 | _jsr_records = NULL; |
2000 | } |
2001 | |
2002 | // ------------------------------------------------------------------ |
2003 | // ciTypeFlow::work_list_next |
2004 | // |
2005 | // Get the next basic block from our work list. |
2006 | ciTypeFlow::Block* ciTypeFlow::work_list_next() { |
2007 | assert(!work_list_empty(), "work list must not be empty" ); |
2008 | Block* next_block = _work_list; |
2009 | _work_list = next_block->next(); |
2010 | next_block->set_next(NULL); |
2011 | next_block->set_on_work_list(false); |
2012 | return next_block; |
2013 | } |
2014 | |
2015 | // ------------------------------------------------------------------ |
2016 | // ciTypeFlow::add_to_work_list |
2017 | // |
2018 | // Add a basic block to our work list. |
2019 | // List is sorted by decreasing postorder sort (same as increasing RPO) |
2020 | void ciTypeFlow::add_to_work_list(ciTypeFlow::Block* block) { |
2021 | assert(!block->is_on_work_list(), "must not already be on work list" ); |
2022 | |
2023 | if (CITraceTypeFlow) { |
2024 | tty->print(">> Adding block " ); |
2025 | block->print_value_on(tty); |
2026 | tty->print_cr(" to the work list : " ); |
2027 | } |
2028 | |
2029 | block->set_on_work_list(true); |
2030 | |
2031 | // decreasing post order sort |
2032 | |
2033 | Block* prev = NULL; |
2034 | Block* current = _work_list; |
2035 | int po = block->post_order(); |
2036 | while (current != NULL) { |
2037 | if (!current->has_post_order() || po > current->post_order()) |
2038 | break; |
2039 | prev = current; |
2040 | current = current->next(); |
2041 | } |
2042 | if (prev == NULL) { |
2043 | block->set_next(_work_list); |
2044 | _work_list = block; |
2045 | } else { |
2046 | block->set_next(current); |
2047 | prev->set_next(block); |
2048 | } |
2049 | |
2050 | if (CITraceTypeFlow) { |
2051 | tty->cr(); |
2052 | } |
2053 | } |
2054 | |
2055 | // ------------------------------------------------------------------ |
2056 | // ciTypeFlow::block_at |
2057 | // |
2058 | // Return the block beginning at bci which has a JsrSet compatible |
2059 | // with jsrs. |
2060 | ciTypeFlow::Block* ciTypeFlow::block_at(int bci, ciTypeFlow::JsrSet* jsrs, CreateOption option) { |
2061 | // First find the right ciBlock. |
2062 | if (CITraceTypeFlow) { |
2063 | tty->print(">> Requesting block for %d/" , bci); |
2064 | jsrs->print_on(tty); |
2065 | tty->cr(); |
2066 | } |
2067 | |
2068 | ciBlock* ciblk = _methodBlocks->block_containing(bci); |
2069 | assert(ciblk->start_bci() == bci, "bad ciBlock boundaries" ); |
2070 | Block* block = get_block_for(ciblk->index(), jsrs, option); |
2071 | |
2072 | assert(block == NULL? (option == no_create): block->is_backedge_copy() == (option == create_backedge_copy), "create option consistent with result" ); |
2073 | |
2074 | if (CITraceTypeFlow) { |
2075 | if (block != NULL) { |
2076 | tty->print(">> Found block " ); |
2077 | block->print_value_on(tty); |
2078 | tty->cr(); |
2079 | } else { |
2080 | tty->print_cr(">> No such block." ); |
2081 | } |
2082 | } |
2083 | |
2084 | return block; |
2085 | } |
2086 | |
2087 | // ------------------------------------------------------------------ |
2088 | // ciTypeFlow::make_jsr_record |
2089 | // |
2090 | // Make a JsrRecord for a given (entry, return) pair, if such a record |
2091 | // does not already exist. |
2092 | ciTypeFlow::JsrRecord* ciTypeFlow::make_jsr_record(int entry_address, |
2093 | int return_address) { |
2094 | if (_jsr_records == NULL) { |
2095 | _jsr_records = new (arena()) GrowableArray<JsrRecord*>(arena(), |
2096 | _jsr_count, |
2097 | 0, |
2098 | NULL); |
2099 | } |
2100 | JsrRecord* record = NULL; |
2101 | int len = _jsr_records->length(); |
2102 | for (int i = 0; i < len; i++) { |
2103 | JsrRecord* record = _jsr_records->at(i); |
2104 | if (record->entry_address() == entry_address && |
2105 | record->return_address() == return_address) { |
2106 | return record; |
2107 | } |
2108 | } |
2109 | |
2110 | record = new (arena()) JsrRecord(entry_address, return_address); |
2111 | _jsr_records->append(record); |
2112 | return record; |
2113 | } |
2114 | |
2115 | // ------------------------------------------------------------------ |
2116 | // ciTypeFlow::flow_exceptions |
2117 | // |
2118 | // Merge the current state into all exceptional successors at the |
2119 | // current point in the code. |
2120 | void ciTypeFlow::flow_exceptions(GrowableArray<ciTypeFlow::Block*>* exceptions, |
2121 | GrowableArray<ciInstanceKlass*>* exc_klasses, |
2122 | ciTypeFlow::StateVector* state) { |
2123 | int len = exceptions->length(); |
2124 | assert(exc_klasses->length() == len, "must have same length" ); |
2125 | for (int i = 0; i < len; i++) { |
2126 | Block* block = exceptions->at(i); |
2127 | ciInstanceKlass* exception_klass = exc_klasses->at(i); |
2128 | |
2129 | if (!exception_klass->is_loaded()) { |
2130 | // Do not compile any code for unloaded exception types. |
2131 | // Following compiler passes are responsible for doing this also. |
2132 | continue; |
2133 | } |
2134 | |
2135 | if (block->meet_exception(exception_klass, state)) { |
2136 | // Block was modified and has PO. Add it to the work list. |
2137 | if (block->has_post_order() && |
2138 | !block->is_on_work_list()) { |
2139 | add_to_work_list(block); |
2140 | } |
2141 | } |
2142 | } |
2143 | } |
2144 | |
2145 | // ------------------------------------------------------------------ |
2146 | // ciTypeFlow::flow_successors |
2147 | // |
2148 | // Merge the current state into all successors at the current point |
2149 | // in the code. |
2150 | void ciTypeFlow::flow_successors(GrowableArray<ciTypeFlow::Block*>* successors, |
2151 | ciTypeFlow::StateVector* state) { |
2152 | int len = successors->length(); |
2153 | for (int i = 0; i < len; i++) { |
2154 | Block* block = successors->at(i); |
2155 | if (block->meet(state)) { |
2156 | // Block was modified and has PO. Add it to the work list. |
2157 | if (block->has_post_order() && |
2158 | !block->is_on_work_list()) { |
2159 | add_to_work_list(block); |
2160 | } |
2161 | } |
2162 | } |
2163 | } |
2164 | |
2165 | // ------------------------------------------------------------------ |
2166 | // ciTypeFlow::can_trap |
2167 | // |
2168 | // Tells if a given instruction is able to generate an exception edge. |
2169 | bool ciTypeFlow::can_trap(ciBytecodeStream& str) { |
2170 | // Cf. GenerateOopMap::do_exception_edge. |
2171 | if (!Bytecodes::can_trap(str.cur_bc())) return false; |
2172 | |
2173 | switch (str.cur_bc()) { |
2174 | // %%% FIXME: ldc of Class can generate an exception |
2175 | case Bytecodes::_ldc: |
2176 | case Bytecodes::_ldc_w: |
2177 | case Bytecodes::_ldc2_w: |
2178 | case Bytecodes::_aload_0: |
2179 | // These bytecodes can trap for rewriting. We need to assume that |
2180 | // they do not throw exceptions to make the monitor analysis work. |
2181 | return false; |
2182 | |
2183 | case Bytecodes::_ireturn: |
2184 | case Bytecodes::_lreturn: |
2185 | case Bytecodes::_freturn: |
2186 | case Bytecodes::_dreturn: |
2187 | case Bytecodes::_areturn: |
2188 | case Bytecodes::_return: |
2189 | // We can assume the monitor stack is empty in this analysis. |
2190 | return false; |
2191 | |
2192 | case Bytecodes::_monitorexit: |
2193 | // We can assume monitors are matched in this analysis. |
2194 | return false; |
2195 | |
2196 | default: |
2197 | return true; |
2198 | } |
2199 | } |
2200 | |
2201 | // ------------------------------------------------------------------ |
2202 | // ciTypeFlow::clone_loop_heads |
2203 | // |
2204 | // Clone the loop heads |
2205 | bool ciTypeFlow::clone_loop_heads(Loop* lp, StateVector* temp_vector, JsrSet* temp_set) { |
2206 | bool rslt = false; |
2207 | for (PreorderLoops iter(loop_tree_root()); !iter.done(); iter.next()) { |
2208 | lp = iter.current(); |
2209 | Block* head = lp->head(); |
2210 | if (lp == loop_tree_root() || |
2211 | lp->is_irreducible() || |
2212 | !head->is_clonable_exit(lp)) |
2213 | continue; |
2214 | |
2215 | // Avoid BoxLock merge. |
2216 | if (EliminateNestedLocks && head->has_monitorenter()) |
2217 | continue; |
2218 | |
2219 | // check not already cloned |
2220 | if (head->backedge_copy_count() != 0) |
2221 | continue; |
2222 | |
2223 | // Don't clone head of OSR loop to get correct types in start block. |
2224 | if (is_osr_flow() && head->start() == start_bci()) |
2225 | continue; |
2226 | |
2227 | // check _no_ shared head below us |
2228 | Loop* ch; |
2229 | for (ch = lp->child(); ch != NULL && ch->head() != head; ch = ch->sibling()); |
2230 | if (ch != NULL) |
2231 | continue; |
2232 | |
2233 | // Clone head |
2234 | Block* new_head = head->looping_succ(lp); |
2235 | Block* clone = clone_loop_head(lp, temp_vector, temp_set); |
2236 | // Update lp's info |
2237 | clone->set_loop(lp); |
2238 | lp->set_head(new_head); |
2239 | lp->set_tail(clone); |
2240 | // And move original head into outer loop |
2241 | head->set_loop(lp->parent()); |
2242 | |
2243 | rslt = true; |
2244 | } |
2245 | return rslt; |
2246 | } |
2247 | |
2248 | // ------------------------------------------------------------------ |
2249 | // ciTypeFlow::clone_loop_head |
2250 | // |
2251 | // Clone lp's head and replace tail's successors with clone. |
2252 | // |
2253 | // | |
2254 | // v |
2255 | // head <-> body |
2256 | // | |
2257 | // v |
2258 | // exit |
2259 | // |
2260 | // new_head |
2261 | // |
2262 | // | |
2263 | // v |
2264 | // head ----------\ |
2265 | // | | |
2266 | // | v |
2267 | // | clone <-> body |
2268 | // | | |
2269 | // | /--/ |
2270 | // | | |
2271 | // v v |
2272 | // exit |
2273 | // |
2274 | ciTypeFlow::Block* ciTypeFlow::clone_loop_head(Loop* lp, StateVector* temp_vector, JsrSet* temp_set) { |
2275 | Block* head = lp->head(); |
2276 | Block* tail = lp->tail(); |
2277 | if (CITraceTypeFlow) { |
2278 | tty->print(">> Requesting clone of loop head " ); head->print_value_on(tty); |
2279 | tty->print(" for predecessor " ); tail->print_value_on(tty); |
2280 | tty->cr(); |
2281 | } |
2282 | Block* clone = block_at(head->start(), head->jsrs(), create_backedge_copy); |
2283 | assert(clone->backedge_copy_count() == 1, "one backedge copy for all back edges" ); |
2284 | |
2285 | assert(!clone->has_pre_order(), "just created" ); |
2286 | clone->set_next_pre_order(); |
2287 | |
2288 | // Insert clone after (orig) tail in reverse post order |
2289 | clone->set_rpo_next(tail->rpo_next()); |
2290 | tail->set_rpo_next(clone); |
2291 | |
2292 | // tail->head becomes tail->clone |
2293 | for (SuccIter iter(tail); !iter.done(); iter.next()) { |
2294 | if (iter.succ() == head) { |
2295 | iter.set_succ(clone); |
2296 | // Update predecessor information |
2297 | head->predecessors()->remove(tail); |
2298 | clone->predecessors()->append(tail); |
2299 | } |
2300 | } |
2301 | flow_block(tail, temp_vector, temp_set); |
2302 | if (head == tail) { |
2303 | // For self-loops, clone->head becomes clone->clone |
2304 | flow_block(clone, temp_vector, temp_set); |
2305 | for (SuccIter iter(clone); !iter.done(); iter.next()) { |
2306 | if (iter.succ() == head) { |
2307 | iter.set_succ(clone); |
2308 | // Update predecessor information |
2309 | head->predecessors()->remove(clone); |
2310 | clone->predecessors()->append(clone); |
2311 | break; |
2312 | } |
2313 | } |
2314 | } |
2315 | flow_block(clone, temp_vector, temp_set); |
2316 | |
2317 | return clone; |
2318 | } |
2319 | |
2320 | // ------------------------------------------------------------------ |
2321 | // ciTypeFlow::flow_block |
2322 | // |
2323 | // Interpret the effects of the bytecodes on the incoming state |
2324 | // vector of a basic block. Push the changed state to succeeding |
2325 | // basic blocks. |
2326 | void ciTypeFlow::flow_block(ciTypeFlow::Block* block, |
2327 | ciTypeFlow::StateVector* state, |
2328 | ciTypeFlow::JsrSet* jsrs) { |
2329 | if (CITraceTypeFlow) { |
2330 | tty->print("\n>> ANALYZING BLOCK : " ); |
2331 | tty->cr(); |
2332 | block->print_on(tty); |
2333 | } |
2334 | assert(block->has_pre_order(), "pre-order is assigned before 1st flow" ); |
2335 | |
2336 | int start = block->start(); |
2337 | int limit = block->limit(); |
2338 | int control = block->control(); |
2339 | if (control != ciBlock::fall_through_bci) { |
2340 | limit = control; |
2341 | } |
2342 | |
2343 | // Grab the state from the current block. |
2344 | block->copy_state_into(state); |
2345 | state->def_locals()->clear(); |
2346 | |
2347 | GrowableArray<Block*>* exceptions = block->exceptions(); |
2348 | GrowableArray<ciInstanceKlass*>* exc_klasses = block->exc_klasses(); |
2349 | bool has_exceptions = exceptions->length() > 0; |
2350 | |
2351 | bool exceptions_used = false; |
2352 | |
2353 | ciBytecodeStream str(method()); |
2354 | str.reset_to_bci(start); |
2355 | Bytecodes::Code code; |
2356 | while ((code = str.next()) != ciBytecodeStream::EOBC() && |
2357 | str.cur_bci() < limit) { |
2358 | // Check for exceptional control flow from this point. |
2359 | if (has_exceptions && can_trap(str)) { |
2360 | flow_exceptions(exceptions, exc_klasses, state); |
2361 | exceptions_used = true; |
2362 | } |
2363 | // Apply the effects of the current bytecode to our state. |
2364 | bool res = state->apply_one_bytecode(&str); |
2365 | |
2366 | // Watch for bailouts. |
2367 | if (failing()) return; |
2368 | |
2369 | if (str.cur_bc() == Bytecodes::_monitorenter) { |
2370 | block->set_has_monitorenter(); |
2371 | } |
2372 | |
2373 | if (res) { |
2374 | |
2375 | // We have encountered a trap. Record it in this block. |
2376 | block->set_trap(state->trap_bci(), state->trap_index()); |
2377 | |
2378 | if (CITraceTypeFlow) { |
2379 | tty->print_cr(">> Found trap" ); |
2380 | block->print_on(tty); |
2381 | } |
2382 | |
2383 | // Save set of locals defined in this block |
2384 | block->def_locals()->add(state->def_locals()); |
2385 | |
2386 | // Record (no) successors. |
2387 | block->successors(&str, state, jsrs); |
2388 | |
2389 | assert(!has_exceptions || exceptions_used, "Not removing exceptions" ); |
2390 | |
2391 | // Discontinue interpretation of this Block. |
2392 | return; |
2393 | } |
2394 | } |
2395 | |
2396 | GrowableArray<Block*>* successors = NULL; |
2397 | if (control != ciBlock::fall_through_bci) { |
2398 | // Check for exceptional control flow from this point. |
2399 | if (has_exceptions && can_trap(str)) { |
2400 | flow_exceptions(exceptions, exc_klasses, state); |
2401 | exceptions_used = true; |
2402 | } |
2403 | |
2404 | // Fix the JsrSet to reflect effect of the bytecode. |
2405 | block->copy_jsrs_into(jsrs); |
2406 | jsrs->apply_control(this, &str, state); |
2407 | |
2408 | // Find successor edges based on old state and new JsrSet. |
2409 | successors = block->successors(&str, state, jsrs); |
2410 | |
2411 | // Apply the control changes to the state. |
2412 | state->apply_one_bytecode(&str); |
2413 | } else { |
2414 | // Fall through control |
2415 | successors = block->successors(&str, NULL, NULL); |
2416 | } |
2417 | |
2418 | // Save set of locals defined in this block |
2419 | block->def_locals()->add(state->def_locals()); |
2420 | |
2421 | // Remove untaken exception paths |
2422 | if (!exceptions_used) |
2423 | exceptions->clear(); |
2424 | |
2425 | // Pass our state to successors. |
2426 | flow_successors(successors, state); |
2427 | } |
2428 | |
2429 | // ------------------------------------------------------------------ |
2430 | // ciTypeFlow::PreOrderLoops::next |
2431 | // |
2432 | // Advance to next loop tree using a preorder, left-to-right traversal. |
2433 | void ciTypeFlow::PreorderLoops::next() { |
2434 | assert(!done(), "must not be done." ); |
2435 | if (_current->child() != NULL) { |
2436 | _current = _current->child(); |
2437 | } else if (_current->sibling() != NULL) { |
2438 | _current = _current->sibling(); |
2439 | } else { |
2440 | while (_current != _root && _current->sibling() == NULL) { |
2441 | _current = _current->parent(); |
2442 | } |
2443 | if (_current == _root) { |
2444 | _current = NULL; |
2445 | assert(done(), "must be done." ); |
2446 | } else { |
2447 | assert(_current->sibling() != NULL, "must be more to do" ); |
2448 | _current = _current->sibling(); |
2449 | } |
2450 | } |
2451 | } |
2452 | |
2453 | // ------------------------------------------------------------------ |
2454 | // ciTypeFlow::Loop::sorted_merge |
2455 | // |
2456 | // Merge the branch lp into this branch, sorting on the loop head |
2457 | // pre_orders. Returns the leaf of the merged branch. |
2458 | // Child and sibling pointers will be setup later. |
2459 | // Sort is (looking from leaf towards the root) |
2460 | // descending on primary key: loop head's pre_order, and |
2461 | // ascending on secondary key: loop tail's pre_order. |
2462 | ciTypeFlow::Loop* ciTypeFlow::Loop::sorted_merge(Loop* lp) { |
2463 | Loop* leaf = this; |
2464 | Loop* prev = NULL; |
2465 | Loop* current = leaf; |
2466 | while (lp != NULL) { |
2467 | int lp_pre_order = lp->head()->pre_order(); |
2468 | // Find insertion point for "lp" |
2469 | while (current != NULL) { |
2470 | if (current == lp) |
2471 | return leaf; // Already in list |
2472 | if (current->head()->pre_order() < lp_pre_order) |
2473 | break; |
2474 | if (current->head()->pre_order() == lp_pre_order && |
2475 | current->tail()->pre_order() > lp->tail()->pre_order()) { |
2476 | break; |
2477 | } |
2478 | prev = current; |
2479 | current = current->parent(); |
2480 | } |
2481 | Loop* next_lp = lp->parent(); // Save future list of items to insert |
2482 | // Insert lp before current |
2483 | lp->set_parent(current); |
2484 | if (prev != NULL) { |
2485 | prev->set_parent(lp); |
2486 | } else { |
2487 | leaf = lp; |
2488 | } |
2489 | prev = lp; // Inserted item is new prev[ious] |
2490 | lp = next_lp; // Next item to insert |
2491 | } |
2492 | return leaf; |
2493 | } |
2494 | |
2495 | // ------------------------------------------------------------------ |
2496 | // ciTypeFlow::build_loop_tree |
2497 | // |
2498 | // Incrementally build loop tree. |
2499 | void ciTypeFlow::build_loop_tree(Block* blk) { |
2500 | assert(!blk->is_post_visited(), "precondition" ); |
2501 | Loop* innermost = NULL; // merge of loop tree branches over all successors |
2502 | |
2503 | for (SuccIter iter(blk); !iter.done(); iter.next()) { |
2504 | Loop* lp = NULL; |
2505 | Block* succ = iter.succ(); |
2506 | if (!succ->is_post_visited()) { |
2507 | // Found backedge since predecessor post visited, but successor is not |
2508 | assert(succ->pre_order() <= blk->pre_order(), "should be backedge" ); |
2509 | |
2510 | // Create a LoopNode to mark this loop. |
2511 | lp = new (arena()) Loop(succ, blk); |
2512 | if (succ->loop() == NULL) |
2513 | succ->set_loop(lp); |
2514 | // succ->loop will be updated to innermost loop on a later call, when blk==succ |
2515 | |
2516 | } else { // Nested loop |
2517 | lp = succ->loop(); |
2518 | |
2519 | // If succ is loop head, find outer loop. |
2520 | while (lp != NULL && lp->head() == succ) { |
2521 | lp = lp->parent(); |
2522 | } |
2523 | if (lp == NULL) { |
2524 | // Infinite loop, it's parent is the root |
2525 | lp = loop_tree_root(); |
2526 | } |
2527 | } |
2528 | |
2529 | // Check for irreducible loop. |
2530 | // Successor has already been visited. If the successor's loop head |
2531 | // has already been post-visited, then this is another entry into the loop. |
2532 | while (lp->head()->is_post_visited() && lp != loop_tree_root()) { |
2533 | _has_irreducible_entry = true; |
2534 | lp->set_irreducible(succ); |
2535 | if (!succ->is_on_work_list()) { |
2536 | // Assume irreducible entries need more data flow |
2537 | add_to_work_list(succ); |
2538 | } |
2539 | Loop* plp = lp->parent(); |
2540 | if (plp == NULL) { |
2541 | // This only happens for some irreducible cases. The parent |
2542 | // will be updated during a later pass. |
2543 | break; |
2544 | } |
2545 | lp = plp; |
2546 | } |
2547 | |
2548 | // Merge loop tree branch for all successors. |
2549 | innermost = innermost == NULL ? lp : innermost->sorted_merge(lp); |
2550 | |
2551 | } // end loop |
2552 | |
2553 | if (innermost == NULL) { |
2554 | assert(blk->successors()->length() == 0, "CFG exit" ); |
2555 | blk->set_loop(loop_tree_root()); |
2556 | } else if (innermost->head() == blk) { |
2557 | // If loop header, complete the tree pointers |
2558 | if (blk->loop() != innermost) { |
2559 | #ifdef ASSERT |
2560 | assert(blk->loop()->head() == innermost->head(), "same head" ); |
2561 | Loop* dl; |
2562 | for (dl = innermost; dl != NULL && dl != blk->loop(); dl = dl->parent()); |
2563 | assert(dl == blk->loop(), "blk->loop() already in innermost list" ); |
2564 | #endif |
2565 | blk->set_loop(innermost); |
2566 | } |
2567 | innermost->def_locals()->add(blk->def_locals()); |
2568 | Loop* l = innermost; |
2569 | Loop* p = l->parent(); |
2570 | while (p && l->head() == blk) { |
2571 | l->set_sibling(p->child()); // Put self on parents 'next child' |
2572 | p->set_child(l); // Make self the first child of parent |
2573 | p->def_locals()->add(l->def_locals()); |
2574 | l = p; // Walk up the parent chain |
2575 | p = l->parent(); |
2576 | } |
2577 | } else { |
2578 | blk->set_loop(innermost); |
2579 | innermost->def_locals()->add(blk->def_locals()); |
2580 | } |
2581 | } |
2582 | |
2583 | // ------------------------------------------------------------------ |
2584 | // ciTypeFlow::Loop::contains |
2585 | // |
2586 | // Returns true if lp is nested loop. |
2587 | bool ciTypeFlow::Loop::contains(ciTypeFlow::Loop* lp) const { |
2588 | assert(lp != NULL, "" ); |
2589 | if (this == lp || head() == lp->head()) return true; |
2590 | int depth1 = depth(); |
2591 | int depth2 = lp->depth(); |
2592 | if (depth1 > depth2) |
2593 | return false; |
2594 | while (depth1 < depth2) { |
2595 | depth2--; |
2596 | lp = lp->parent(); |
2597 | } |
2598 | return this == lp; |
2599 | } |
2600 | |
2601 | // ------------------------------------------------------------------ |
2602 | // ciTypeFlow::Loop::depth |
2603 | // |
2604 | // Loop depth |
2605 | int ciTypeFlow::Loop::depth() const { |
2606 | int dp = 0; |
2607 | for (Loop* lp = this->parent(); lp != NULL; lp = lp->parent()) |
2608 | dp++; |
2609 | return dp; |
2610 | } |
2611 | |
2612 | #ifndef PRODUCT |
2613 | // ------------------------------------------------------------------ |
2614 | // ciTypeFlow::Loop::print |
2615 | void ciTypeFlow::Loop::print(outputStream* st, int indent) const { |
2616 | for (int i = 0; i < indent; i++) st->print(" " ); |
2617 | st->print("%d<-%d %s" , |
2618 | is_root() ? 0 : this->head()->pre_order(), |
2619 | is_root() ? 0 : this->tail()->pre_order(), |
2620 | is_irreducible()?" irr" :"" ); |
2621 | st->print(" defs: " ); |
2622 | def_locals()->print_on(st, _head->outer()->method()->max_locals()); |
2623 | st->cr(); |
2624 | for (Loop* ch = child(); ch != NULL; ch = ch->sibling()) |
2625 | ch->print(st, indent+2); |
2626 | } |
2627 | #endif |
2628 | |
2629 | // ------------------------------------------------------------------ |
2630 | // ciTypeFlow::df_flow_types |
2631 | // |
2632 | // Perform the depth first type flow analysis. Helper for flow_types. |
2633 | void ciTypeFlow::df_flow_types(Block* start, |
2634 | bool do_flow, |
2635 | StateVector* temp_vector, |
2636 | JsrSet* temp_set) { |
2637 | int dft_len = 100; |
2638 | GrowableArray<Block*> stk(dft_len); |
2639 | |
2640 | ciBlock* dummy = _methodBlocks->make_dummy_block(); |
2641 | JsrSet* root_set = new JsrSet(NULL, 0); |
2642 | Block* root_head = new (arena()) Block(this, dummy, root_set); |
2643 | Block* root_tail = new (arena()) Block(this, dummy, root_set); |
2644 | root_head->set_pre_order(0); |
2645 | root_head->set_post_order(0); |
2646 | root_tail->set_pre_order(max_jint); |
2647 | root_tail->set_post_order(max_jint); |
2648 | set_loop_tree_root(new (arena()) Loop(root_head, root_tail)); |
2649 | |
2650 | stk.push(start); |
2651 | |
2652 | _next_pre_order = 0; // initialize pre_order counter |
2653 | _rpo_list = NULL; |
2654 | int next_po = 0; // initialize post_order counter |
2655 | |
2656 | // Compute RPO and the control flow graph |
2657 | int size; |
2658 | while ((size = stk.length()) > 0) { |
2659 | Block* blk = stk.top(); // Leave node on stack |
2660 | if (!blk->is_visited()) { |
2661 | // forward arc in graph |
2662 | assert (!blk->has_pre_order(), "" ); |
2663 | blk->set_next_pre_order(); |
2664 | |
2665 | if (_next_pre_order >= (int)Compile::current()->max_node_limit() / 2) { |
2666 | // Too many basic blocks. Bail out. |
2667 | // This can happen when try/finally constructs are nested to depth N, |
2668 | // and there is O(2**N) cloning of jsr bodies. See bug 4697245! |
2669 | // "MaxNodeLimit / 2" is used because probably the parser will |
2670 | // generate at least twice that many nodes and bail out. |
2671 | record_failure("too many basic blocks" ); |
2672 | return; |
2673 | } |
2674 | if (do_flow) { |
2675 | flow_block(blk, temp_vector, temp_set); |
2676 | if (failing()) return; // Watch for bailouts. |
2677 | } |
2678 | } else if (!blk->is_post_visited()) { |
2679 | // cross or back arc |
2680 | for (SuccIter iter(blk); !iter.done(); iter.next()) { |
2681 | Block* succ = iter.succ(); |
2682 | if (!succ->is_visited()) { |
2683 | stk.push(succ); |
2684 | } |
2685 | } |
2686 | if (stk.length() == size) { |
2687 | // There were no additional children, post visit node now |
2688 | stk.pop(); // Remove node from stack |
2689 | |
2690 | build_loop_tree(blk); |
2691 | blk->set_post_order(next_po++); // Assign post order |
2692 | prepend_to_rpo_list(blk); |
2693 | assert(blk->is_post_visited(), "" ); |
2694 | |
2695 | if (blk->is_loop_head() && !blk->is_on_work_list()) { |
2696 | // Assume loop heads need more data flow |
2697 | add_to_work_list(blk); |
2698 | } |
2699 | } |
2700 | } else { |
2701 | stk.pop(); // Remove post-visited node from stack |
2702 | } |
2703 | } |
2704 | } |
2705 | |
2706 | // ------------------------------------------------------------------ |
2707 | // ciTypeFlow::flow_types |
2708 | // |
2709 | // Perform the type flow analysis, creating and cloning Blocks as |
2710 | // necessary. |
2711 | void ciTypeFlow::flow_types() { |
2712 | ResourceMark rm; |
2713 | StateVector* temp_vector = new StateVector(this); |
2714 | JsrSet* temp_set = new JsrSet(NULL, 16); |
2715 | |
2716 | // Create the method entry block. |
2717 | Block* start = block_at(start_bci(), temp_set); |
2718 | |
2719 | // Load the initial state into it. |
2720 | const StateVector* start_state = get_start_state(); |
2721 | if (failing()) return; |
2722 | start->meet(start_state); |
2723 | |
2724 | // Depth first visit |
2725 | df_flow_types(start, true /*do flow*/, temp_vector, temp_set); |
2726 | |
2727 | if (failing()) return; |
2728 | assert(_rpo_list == start, "must be start" ); |
2729 | |
2730 | // Any loops found? |
2731 | if (loop_tree_root()->child() != NULL && |
2732 | env()->comp_level() >= CompLevel_full_optimization) { |
2733 | // Loop optimizations are not performed on Tier1 compiles. |
2734 | |
2735 | bool changed = clone_loop_heads(loop_tree_root(), temp_vector, temp_set); |
2736 | |
2737 | // If some loop heads were cloned, recompute postorder and loop tree |
2738 | if (changed) { |
2739 | loop_tree_root()->set_child(NULL); |
2740 | for (Block* blk = _rpo_list; blk != NULL;) { |
2741 | Block* next = blk->rpo_next(); |
2742 | blk->df_init(); |
2743 | blk = next; |
2744 | } |
2745 | df_flow_types(start, false /*no flow*/, temp_vector, temp_set); |
2746 | } |
2747 | } |
2748 | |
2749 | if (CITraceTypeFlow) { |
2750 | tty->print_cr("\nLoop tree" ); |
2751 | loop_tree_root()->print(); |
2752 | } |
2753 | |
2754 | // Continue flow analysis until fixed point reached |
2755 | |
2756 | debug_only(int max_block = _next_pre_order;) |
2757 | |
2758 | while (!work_list_empty()) { |
2759 | Block* blk = work_list_next(); |
2760 | assert (blk->has_post_order(), "post order assigned above" ); |
2761 | |
2762 | flow_block(blk, temp_vector, temp_set); |
2763 | |
2764 | assert (max_block == _next_pre_order, "no new blocks" ); |
2765 | assert (!failing(), "no more bailouts" ); |
2766 | } |
2767 | } |
2768 | |
2769 | // ------------------------------------------------------------------ |
2770 | // ciTypeFlow::map_blocks |
2771 | // |
2772 | // Create the block map, which indexes blocks in reverse post-order. |
2773 | void ciTypeFlow::map_blocks() { |
2774 | assert(_block_map == NULL, "single initialization" ); |
2775 | int block_ct = _next_pre_order; |
2776 | _block_map = NEW_ARENA_ARRAY(arena(), Block*, block_ct); |
2777 | assert(block_ct == block_count(), "" ); |
2778 | |
2779 | Block* blk = _rpo_list; |
2780 | for (int m = 0; m < block_ct; m++) { |
2781 | int rpo = blk->rpo(); |
2782 | assert(rpo == m, "should be sequential" ); |
2783 | _block_map[rpo] = blk; |
2784 | blk = blk->rpo_next(); |
2785 | } |
2786 | assert(blk == NULL, "should be done" ); |
2787 | |
2788 | for (int j = 0; j < block_ct; j++) { |
2789 | assert(_block_map[j] != NULL, "must not drop any blocks" ); |
2790 | Block* block = _block_map[j]; |
2791 | // Remove dead blocks from successor lists: |
2792 | for (int e = 0; e <= 1; e++) { |
2793 | GrowableArray<Block*>* l = e? block->exceptions(): block->successors(); |
2794 | for (int k = 0; k < l->length(); k++) { |
2795 | Block* s = l->at(k); |
2796 | if (!s->has_post_order()) { |
2797 | if (CITraceTypeFlow) { |
2798 | tty->print("Removing dead %s successor of #%d: " , (e? "exceptional" : "normal" ), block->pre_order()); |
2799 | s->print_value_on(tty); |
2800 | tty->cr(); |
2801 | } |
2802 | l->remove(s); |
2803 | --k; |
2804 | } |
2805 | } |
2806 | } |
2807 | } |
2808 | } |
2809 | |
2810 | // ------------------------------------------------------------------ |
2811 | // ciTypeFlow::get_block_for |
2812 | // |
2813 | // Find a block with this ciBlock which has a compatible JsrSet. |
2814 | // If no such block exists, create it, unless the option is no_create. |
2815 | // If the option is create_backedge_copy, always create a fresh backedge copy. |
2816 | ciTypeFlow::Block* ciTypeFlow::get_block_for(int ciBlockIndex, ciTypeFlow::JsrSet* jsrs, CreateOption option) { |
2817 | Arena* a = arena(); |
2818 | GrowableArray<Block*>* blocks = _idx_to_blocklist[ciBlockIndex]; |
2819 | if (blocks == NULL) { |
2820 | // Query only? |
2821 | if (option == no_create) return NULL; |
2822 | |
2823 | // Allocate the growable array. |
2824 | blocks = new (a) GrowableArray<Block*>(a, 4, 0, NULL); |
2825 | _idx_to_blocklist[ciBlockIndex] = blocks; |
2826 | } |
2827 | |
2828 | if (option != create_backedge_copy) { |
2829 | int len = blocks->length(); |
2830 | for (int i = 0; i < len; i++) { |
2831 | Block* block = blocks->at(i); |
2832 | if (!block->is_backedge_copy() && block->is_compatible_with(jsrs)) { |
2833 | return block; |
2834 | } |
2835 | } |
2836 | } |
2837 | |
2838 | // Query only? |
2839 | if (option == no_create) return NULL; |
2840 | |
2841 | // We did not find a compatible block. Create one. |
2842 | Block* new_block = new (a) Block(this, _methodBlocks->block(ciBlockIndex), jsrs); |
2843 | if (option == create_backedge_copy) new_block->set_backedge_copy(true); |
2844 | blocks->append(new_block); |
2845 | return new_block; |
2846 | } |
2847 | |
2848 | // ------------------------------------------------------------------ |
2849 | // ciTypeFlow::backedge_copy_count |
2850 | // |
2851 | int ciTypeFlow::backedge_copy_count(int ciBlockIndex, ciTypeFlow::JsrSet* jsrs) const { |
2852 | GrowableArray<Block*>* blocks = _idx_to_blocklist[ciBlockIndex]; |
2853 | |
2854 | if (blocks == NULL) { |
2855 | return 0; |
2856 | } |
2857 | |
2858 | int count = 0; |
2859 | int len = blocks->length(); |
2860 | for (int i = 0; i < len; i++) { |
2861 | Block* block = blocks->at(i); |
2862 | if (block->is_backedge_copy() && block->is_compatible_with(jsrs)) { |
2863 | count++; |
2864 | } |
2865 | } |
2866 | |
2867 | return count; |
2868 | } |
2869 | |
2870 | // ------------------------------------------------------------------ |
2871 | // ciTypeFlow::do_flow |
2872 | // |
2873 | // Perform type inference flow analysis. |
2874 | void ciTypeFlow::do_flow() { |
2875 | if (CITraceTypeFlow) { |
2876 | tty->print_cr("\nPerforming flow analysis on method" ); |
2877 | method()->print(); |
2878 | if (is_osr_flow()) tty->print(" at OSR bci %d" , start_bci()); |
2879 | tty->cr(); |
2880 | method()->print_codes(); |
2881 | } |
2882 | if (CITraceTypeFlow) { |
2883 | tty->print_cr("Initial CI Blocks" ); |
2884 | print_on(tty); |
2885 | } |
2886 | flow_types(); |
2887 | // Watch for bailouts. |
2888 | if (failing()) { |
2889 | return; |
2890 | } |
2891 | |
2892 | map_blocks(); |
2893 | |
2894 | if (CIPrintTypeFlow || CITraceTypeFlow) { |
2895 | rpo_print_on(tty); |
2896 | } |
2897 | } |
2898 | |
2899 | // ------------------------------------------------------------------ |
2900 | // ciTypeFlow::is_dominated_by |
2901 | // |
2902 | // Determine if the instruction at bci is dominated by the instruction at dom_bci. |
2903 | bool ciTypeFlow::is_dominated_by(int bci, int dom_bci) { |
2904 | assert(!method()->has_jsrs(), "jsrs are not supported" ); |
2905 | |
2906 | ResourceMark rm; |
2907 | JsrSet* jsrs = new ciTypeFlow::JsrSet(NULL); |
2908 | int index = _methodBlocks->block_containing(bci)->index(); |
2909 | int dom_index = _methodBlocks->block_containing(dom_bci)->index(); |
2910 | Block* block = get_block_for(index, jsrs, ciTypeFlow::no_create); |
2911 | Block* dom_block = get_block_for(dom_index, jsrs, ciTypeFlow::no_create); |
2912 | |
2913 | // Start block dominates all other blocks |
2914 | if (start_block()->rpo() == dom_block->rpo()) { |
2915 | return true; |
2916 | } |
2917 | |
2918 | // Dominated[i] is true if block i is dominated by dom_block |
2919 | int num_blocks = block_count(); |
2920 | bool* dominated = NEW_RESOURCE_ARRAY(bool, num_blocks); |
2921 | for (int i = 0; i < num_blocks; ++i) { |
2922 | dominated[i] = true; |
2923 | } |
2924 | dominated[start_block()->rpo()] = false; |
2925 | |
2926 | // Iterative dominator algorithm |
2927 | bool changed = true; |
2928 | while (changed) { |
2929 | changed = false; |
2930 | // Use reverse postorder iteration |
2931 | for (Block* blk = _rpo_list; blk != NULL; blk = blk->rpo_next()) { |
2932 | if (blk->is_start()) { |
2933 | // Ignore start block |
2934 | continue; |
2935 | } |
2936 | // The block is dominated if it is the dominating block |
2937 | // itself or if all predecessors are dominated. |
2938 | int index = blk->rpo(); |
2939 | bool dom = (index == dom_block->rpo()); |
2940 | if (!dom) { |
2941 | // Check if all predecessors are dominated |
2942 | dom = true; |
2943 | for (int i = 0; i < blk->predecessors()->length(); ++i) { |
2944 | Block* pred = blk->predecessors()->at(i); |
2945 | if (!dominated[pred->rpo()]) { |
2946 | dom = false; |
2947 | break; |
2948 | } |
2949 | } |
2950 | } |
2951 | // Update dominator information |
2952 | if (dominated[index] != dom) { |
2953 | changed = true; |
2954 | dominated[index] = dom; |
2955 | } |
2956 | } |
2957 | } |
2958 | // block dominated by dom_block? |
2959 | return dominated[block->rpo()]; |
2960 | } |
2961 | |
2962 | // ------------------------------------------------------------------ |
2963 | // ciTypeFlow::record_failure() |
2964 | // The ciTypeFlow object keeps track of failure reasons separately from the ciEnv. |
2965 | // This is required because there is not a 1-1 relation between the ciEnv and |
2966 | // the TypeFlow passes within a compilation task. For example, if the compiler |
2967 | // is considering inlining a method, it will request a TypeFlow. If that fails, |
2968 | // the compilation as a whole may continue without the inlining. Some TypeFlow |
2969 | // requests are not optional; if they fail the requestor is responsible for |
2970 | // copying the failure reason up to the ciEnv. (See Parse::Parse.) |
2971 | void ciTypeFlow::record_failure(const char* reason) { |
2972 | if (env()->log() != NULL) { |
2973 | env()->log()->elem("failure reason='%s' phase='typeflow'" , reason); |
2974 | } |
2975 | if (_failure_reason == NULL) { |
2976 | // Record the first failure reason. |
2977 | _failure_reason = reason; |
2978 | } |
2979 | } |
2980 | |
2981 | #ifndef PRODUCT |
2982 | // ------------------------------------------------------------------ |
2983 | // ciTypeFlow::print_on |
2984 | void ciTypeFlow::print_on(outputStream* st) const { |
2985 | // Walk through CI blocks |
2986 | st->print_cr("********************************************************" ); |
2987 | st->print ("TypeFlow for " ); |
2988 | method()->name()->print_symbol_on(st); |
2989 | int limit_bci = code_size(); |
2990 | st->print_cr(" %d bytes" , limit_bci); |
2991 | ciMethodBlocks *mblks = _methodBlocks; |
2992 | ciBlock* current = NULL; |
2993 | for (int bci = 0; bci < limit_bci; bci++) { |
2994 | ciBlock* blk = mblks->block_containing(bci); |
2995 | if (blk != NULL && blk != current) { |
2996 | current = blk; |
2997 | current->print_on(st); |
2998 | |
2999 | GrowableArray<Block*>* blocks = _idx_to_blocklist[blk->index()]; |
3000 | int num_blocks = (blocks == NULL) ? 0 : blocks->length(); |
3001 | |
3002 | if (num_blocks == 0) { |
3003 | st->print_cr(" No Blocks" ); |
3004 | } else { |
3005 | for (int i = 0; i < num_blocks; i++) { |
3006 | Block* block = blocks->at(i); |
3007 | block->print_on(st); |
3008 | } |
3009 | } |
3010 | st->print_cr("--------------------------------------------------------" ); |
3011 | st->cr(); |
3012 | } |
3013 | } |
3014 | st->print_cr("********************************************************" ); |
3015 | st->cr(); |
3016 | } |
3017 | |
3018 | void ciTypeFlow::rpo_print_on(outputStream* st) const { |
3019 | st->print_cr("********************************************************" ); |
3020 | st->print ("TypeFlow for " ); |
3021 | method()->name()->print_symbol_on(st); |
3022 | int limit_bci = code_size(); |
3023 | st->print_cr(" %d bytes" , limit_bci); |
3024 | for (Block* blk = _rpo_list; blk != NULL; blk = blk->rpo_next()) { |
3025 | blk->print_on(st); |
3026 | st->print_cr("--------------------------------------------------------" ); |
3027 | st->cr(); |
3028 | } |
3029 | st->print_cr("********************************************************" ); |
3030 | st->cr(); |
3031 | } |
3032 | #endif |
3033 | |