56 // get the continuation point from the BlockList instead of |
56 // get the continuation point from the BlockList instead of |
57 // fabricating it anew because Invokes would be considered to be |
57 // fabricating it anew because Invokes would be considered to be |
58 // BlockEnds. |
58 // BlockEnds. |
59 BlockBegin* _continuation; |
59 BlockBegin* _continuation; |
60 |
60 |
61 // Without return value of inlined method on stack |
|
62 ValueStack* _continuation_state; |
|
63 |
|
64 // Was this ScopeData created only for the parsing and inlining of |
61 // Was this ScopeData created only for the parsing and inlining of |
65 // a jsr? |
62 // a jsr? |
66 bool _parsing_jsr; |
63 bool _parsing_jsr; |
67 // We track the destination bci of the jsr only to determine |
64 // We track the destination bci of the jsr only to determine |
68 // bailout conditions, since we only handle a subset of all of the |
65 // bailout conditions, since we only handle a subset of all of the |
123 |
120 |
124 ciBytecodeStream* stream() { return _stream; } |
121 ciBytecodeStream* stream() { return _stream; } |
125 void set_stream(ciBytecodeStream* stream) { _stream = stream; } |
122 void set_stream(ciBytecodeStream* stream) { _stream = stream; } |
126 |
123 |
127 intx max_inline_size() const { return _max_inline_size; } |
124 intx max_inline_size() const { return _max_inline_size; } |
128 int caller_stack_size() const; |
|
129 |
125 |
130 BlockBegin* continuation() const { return _continuation; } |
126 BlockBegin* continuation() const { return _continuation; } |
131 void set_continuation(BlockBegin* cont) { _continuation = cont; } |
127 void set_continuation(BlockBegin* cont) { _continuation = cont; } |
132 |
|
133 ValueStack* continuation_state() const { return _continuation_state; } |
|
134 void set_continuation_state(ValueStack* s) { _continuation_state = s; } |
|
135 |
128 |
136 // Indicates whether this ScopeData was pushed only for the |
129 // Indicates whether this ScopeData was pushed only for the |
137 // parsing and inlining of a jsr |
130 // parsing and inlining of a jsr |
138 bool parsing_jsr() const { return _parsing_jsr; } |
131 bool parsing_jsr() const { return _parsing_jsr; } |
139 void set_parsing_jsr() { _parsing_jsr = true; } |
132 void set_parsing_jsr() { _parsing_jsr = true; } |
161 ValueStack* inline_cleanup_state() const { return _cleanup_state; } |
154 ValueStack* inline_cleanup_state() const { return _cleanup_state; } |
162 }; |
155 }; |
163 |
156 |
164 // for all GraphBuilders |
157 // for all GraphBuilders |
165 static bool _can_trap[Bytecodes::number_of_java_codes]; |
158 static bool _can_trap[Bytecodes::number_of_java_codes]; |
166 static bool _is_async[Bytecodes::number_of_java_codes]; |
|
167 |
159 |
168 // for each instance of GraphBuilder |
160 // for each instance of GraphBuilder |
169 ScopeData* _scope_data; // Per-scope data; used for inlining |
161 ScopeData* _scope_data; // Per-scope data; used for inlining |
170 Compilation* _compilation; // the current compilation |
162 Compilation* _compilation; // the current compilation |
171 ValueMap* _vmap; // the map of values encountered (for CSE) |
163 ValueMap* _vmap; // the map of values encountered (for CSE) |
177 ValueStack* _initial_state; // The state for the start block |
169 ValueStack* _initial_state; // The state for the start block |
178 |
170 |
179 // for each call to connect_to_end; can also be set by inliner |
171 // for each call to connect_to_end; can also be set by inliner |
180 BlockBegin* _block; // the current block |
172 BlockBegin* _block; // the current block |
181 ValueStack* _state; // the current execution state |
173 ValueStack* _state; // the current execution state |
182 ValueStack* _exception_state; // state that will be used by handle_exception |
|
183 Instruction* _last; // the last instruction added |
174 Instruction* _last; // the last instruction added |
184 bool _skip_block; // skip processing of the rest of this block |
175 bool _skip_block; // skip processing of the rest of this block |
185 |
176 |
186 // accessors |
177 // accessors |
187 ScopeData* scope_data() const { return _scope_data; } |
178 ScopeData* scope_data() const { return _scope_data; } |
192 |
183 |
193 BlockBegin* block() const { return _block; } |
184 BlockBegin* block() const { return _block; } |
194 ValueStack* state() const { return _state; } |
185 ValueStack* state() const { return _state; } |
195 void set_state(ValueStack* state) { _state = state; } |
186 void set_state(ValueStack* state) { _state = state; } |
196 IRScope* scope() const { return scope_data()->scope(); } |
187 IRScope* scope() const { return scope_data()->scope(); } |
197 ValueStack* exception_state() const { return _exception_state; } |
|
198 void set_exception_state(ValueStack* s) { _exception_state = s; } |
|
199 ciMethod* method() const { return scope()->method(); } |
188 ciMethod* method() const { return scope()->method(); } |
200 ciBytecodeStream* stream() const { return scope_data()->stream(); } |
189 ciBytecodeStream* stream() const { return scope_data()->stream(); } |
201 Instruction* last() const { return _last; } |
190 Instruction* last() const { return _last; } |
202 Bytecodes::Code code() const { return stream()->cur_bc(); } |
191 Bytecodes::Code code() const { return stream()->cur_bc(); } |
203 int bci() const { return stream()->cur_bci(); } |
192 int bci() const { return stream()->cur_bci(); } |
228 void store_local(ValueType* type, int index); |
217 void store_local(ValueType* type, int index); |
229 void store_local(ValueStack* state, Value value, ValueType* type, int index); |
218 void store_local(ValueStack* state, Value value, ValueType* type, int index); |
230 void load_indexed (BasicType type); |
219 void load_indexed (BasicType type); |
231 void store_indexed(BasicType type); |
220 void store_indexed(BasicType type); |
232 void stack_op(Bytecodes::Code code); |
221 void stack_op(Bytecodes::Code code); |
233 void arithmetic_op(ValueType* type, Bytecodes::Code code, ValueStack* lock_stack = NULL); |
222 void arithmetic_op(ValueType* type, Bytecodes::Code code, ValueStack* state_before = NULL); |
234 void negate_op(ValueType* type); |
223 void negate_op(ValueType* type); |
235 void shift_op(ValueType* type, Bytecodes::Code code); |
224 void shift_op(ValueType* type, Bytecodes::Code code); |
236 void logic_op(ValueType* type, Bytecodes::Code code); |
225 void logic_op(ValueType* type, Bytecodes::Code code); |
237 void compare_op(ValueType* type, Bytecodes::Code code); |
226 void compare_op(ValueType* type, Bytecodes::Code code); |
238 void convert(Bytecodes::Code op, BasicType from, BasicType to); |
227 void convert(Bytecodes::Code op, BasicType from, BasicType to); |
265 Instruction* append_with_bci(Instruction* instr, int bci); |
254 Instruction* append_with_bci(Instruction* instr, int bci); |
266 Instruction* append(Instruction* instr); |
255 Instruction* append(Instruction* instr); |
267 Instruction* append_split(StateSplit* instr); |
256 Instruction* append_split(StateSplit* instr); |
268 |
257 |
269 // other helpers |
258 // other helpers |
270 static bool is_async(Bytecodes::Code code) { |
|
271 assert(0 <= code && code < Bytecodes::number_of_java_codes, "illegal bytecode"); |
|
272 return _is_async[code]; |
|
273 } |
|
274 BlockBegin* block_at(int bci) { return scope_data()->block_at(bci); } |
259 BlockBegin* block_at(int bci) { return scope_data()->block_at(bci); } |
275 XHandlers* handle_exception(int bci); |
260 XHandlers* handle_exception(Instruction* instruction); |
276 void connect_to_end(BlockBegin* beg); |
261 void connect_to_end(BlockBegin* beg); |
277 void null_check(Value value); |
262 void null_check(Value value); |
278 void eliminate_redundant_phis(BlockBegin* start); |
263 void eliminate_redundant_phis(BlockBegin* start); |
279 BlockEnd* iterate_bytecodes_for_block(int bci); |
264 BlockEnd* iterate_bytecodes_for_block(int bci); |
280 void iterate_all_blocks(bool start_in_current_block_for_inlining = false); |
265 void iterate_all_blocks(bool start_in_current_block_for_inlining = false); |
281 Dependencies* dependency_recorder() const; // = compilation()->dependencies() |
266 Dependencies* dependency_recorder() const; // = compilation()->dependencies() |
282 bool direct_compare(ciKlass* k); |
267 bool direct_compare(ciKlass* k); |
283 |
268 |
284 void kill_all(); |
269 void kill_all(); |
285 |
270 |
286 ValueStack* lock_stack(); |
271 // use of state copy routines (try to minimize unnecessary state |
|
272 // object allocations): |
|
273 |
|
274 // - if the instruction unconditionally needs a full copy of the |
|
275 // state (for patching for example), then use copy_state_before* |
|
276 |
|
277 // - if the instruction needs a full copy of the state only for |
|
278 // handler generation (Instruction::needs_exception_state() returns |
|
279 // false) then use copy_state_exhandling* |
|
280 |
|
281 // - if the instruction needs either a full copy of the state for |
|
282 // handler generation and a least a minimal copy of the state (as |
|
283 // returned by Instruction::exception_state()) for debug info |
|
284 // generation (that is when Instruction::needs_exception_state() |
|
285 // returns true) then use copy_state_for_exception* |
|
286 |
|
287 ValueStack* copy_state_before_with_bci(int bci); |
|
288 ValueStack* copy_state_before(); |
|
289 ValueStack* copy_state_exhandling_with_bci(int bci); |
|
290 ValueStack* copy_state_exhandling(); |
|
291 ValueStack* copy_state_for_exception_with_bci(int bci); |
|
292 ValueStack* copy_state_for_exception(); |
287 |
293 |
288 // |
294 // |
289 // Inlining support |
295 // Inlining support |
290 // |
296 // |
291 |
297 |
292 // accessors |
298 // accessors |
293 bool parsing_jsr() const { return scope_data()->parsing_jsr(); } |
299 bool parsing_jsr() const { return scope_data()->parsing_jsr(); } |
294 BlockBegin* continuation() const { return scope_data()->continuation(); } |
300 BlockBegin* continuation() const { return scope_data()->continuation(); } |
295 ValueStack* continuation_state() const { return scope_data()->continuation_state(); } |
|
296 BlockBegin* jsr_continuation() const { return scope_data()->jsr_continuation(); } |
301 BlockBegin* jsr_continuation() const { return scope_data()->jsr_continuation(); } |
297 int caller_stack_size() const { return scope_data()->caller_stack_size(); } |
|
298 void set_continuation(BlockBegin* continuation) { scope_data()->set_continuation(continuation); } |
302 void set_continuation(BlockBegin* continuation) { scope_data()->set_continuation(continuation); } |
299 void set_inline_cleanup_info(BlockBegin* block, |
303 void set_inline_cleanup_info(BlockBegin* block, |
300 Instruction* return_prev, |
304 Instruction* return_prev, |
301 ValueStack* return_state) { scope_data()->set_inline_cleanup_info(block, |
305 ValueStack* return_state) { scope_data()->set_inline_cleanup_info(block, |
302 return_prev, |
306 return_prev, |