|
1 /* |
|
2 * Copyright (c) 2005, 2013, 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 #ifndef SHARE_VM_OPTO_MACRO_HPP |
|
26 #define SHARE_VM_OPTO_MACRO_HPP |
|
27 |
|
28 #include "opto/phase.hpp" |
|
29 |
|
30 class AllocateNode; |
|
31 class AllocateArrayNode; |
|
32 class CallNode; |
|
33 class Node; |
|
34 class PhaseIterGVN; |
|
35 |
|
36 class PhaseMacroExpand : public Phase { |
|
37 private: |
|
38 PhaseIterGVN &_igvn; |
|
39 |
|
40 // Helper methods roughly modelled after GraphKit: |
|
41 Node* top() const { return C->top(); } |
|
42 Node* intcon(jint con) const { return _igvn.intcon(con); } |
|
43 Node* longcon(jlong con) const { return _igvn.longcon(con); } |
|
44 Node* makecon(const Type *t) const { return _igvn.makecon(t); } |
|
45 Node* basic_plus_adr(Node* base, int offset) { |
|
46 return (offset == 0)? base: basic_plus_adr(base, MakeConX(offset)); |
|
47 } |
|
48 Node* basic_plus_adr(Node* base, Node* ptr, int offset) { |
|
49 return (offset == 0)? ptr: basic_plus_adr(base, ptr, MakeConX(offset)); |
|
50 } |
|
51 Node* basic_plus_adr(Node* base, Node* offset) { |
|
52 return basic_plus_adr(base, base, offset); |
|
53 } |
|
54 Node* basic_plus_adr(Node* base, Node* ptr, Node* offset) { |
|
55 Node* adr = new (C) AddPNode(base, ptr, offset); |
|
56 return transform_later(adr); |
|
57 } |
|
58 Node* transform_later(Node* n) { |
|
59 // equivalent to _gvn.transform in GraphKit, Ideal, etc. |
|
60 _igvn.register_new_node_with_optimizer(n); |
|
61 return n; |
|
62 } |
|
63 void set_eden_pointers(Node* &eden_top_adr, Node* &eden_end_adr); |
|
64 Node* make_load( Node* ctl, Node* mem, Node* base, int offset, |
|
65 const Type* value_type, BasicType bt); |
|
66 Node* make_store(Node* ctl, Node* mem, Node* base, int offset, |
|
67 Node* value, BasicType bt); |
|
68 |
|
69 // projections extracted from a call node |
|
70 ProjNode *_fallthroughproj; |
|
71 ProjNode *_fallthroughcatchproj; |
|
72 ProjNode *_ioproj_fallthrough; |
|
73 ProjNode *_ioproj_catchall; |
|
74 ProjNode *_catchallcatchproj; |
|
75 ProjNode *_memproj_fallthrough; |
|
76 ProjNode *_memproj_catchall; |
|
77 ProjNode *_resproj; |
|
78 |
|
79 // Additional data collected during macro expansion |
|
80 bool _has_locks; |
|
81 |
|
82 void expand_allocate(AllocateNode *alloc); |
|
83 void expand_allocate_array(AllocateArrayNode *alloc); |
|
84 void expand_allocate_common(AllocateNode* alloc, |
|
85 Node* length, |
|
86 const TypeFunc* slow_call_type, |
|
87 address slow_call_address); |
|
88 Node *value_from_mem(Node *mem, BasicType ft, const Type *ftype, const TypeOopPtr *adr_t, Node *alloc); |
|
89 Node *value_from_mem_phi(Node *mem, BasicType ft, const Type *ftype, const TypeOopPtr *adr_t, Node *alloc, Node_Stack *value_phis, int level); |
|
90 |
|
91 bool eliminate_boxing_node(CallStaticJavaNode *boxing); |
|
92 bool eliminate_allocate_node(AllocateNode *alloc); |
|
93 bool can_eliminate_allocation(AllocateNode *alloc, GrowableArray <SafePointNode *>& safepoints); |
|
94 bool scalar_replacement(AllocateNode *alloc, GrowableArray <SafePointNode *>& safepoints_done); |
|
95 void process_users_of_allocation(CallNode *alloc); |
|
96 |
|
97 void eliminate_card_mark(Node *cm); |
|
98 void mark_eliminated_box(Node* box, Node* obj); |
|
99 void mark_eliminated_locking_nodes(AbstractLockNode *alock); |
|
100 bool eliminate_locking_node(AbstractLockNode *alock); |
|
101 void expand_lock_node(LockNode *lock); |
|
102 void expand_unlock_node(UnlockNode *unlock); |
|
103 |
|
104 int replace_input(Node *use, Node *oldref, Node *newref); |
|
105 void copy_call_debug_info(CallNode *oldcall, CallNode * newcall); |
|
106 Node* opt_bits_test(Node* ctrl, Node* region, int edge, Node* word, int mask, int bits, bool return_fast_path = false); |
|
107 void copy_predefined_input_for_runtime_call(Node * ctrl, CallNode* oldcall, CallNode* call); |
|
108 CallNode* make_slow_call(CallNode *oldcall, const TypeFunc* slow_call_type, address slow_call, |
|
109 const char* leaf_name, Node* slow_path, Node* parm0, Node* parm1); |
|
110 void extract_call_projections(CallNode *call); |
|
111 |
|
112 Node* initialize_object(AllocateNode* alloc, |
|
113 Node* control, Node* rawmem, Node* object, |
|
114 Node* klass_node, Node* length, |
|
115 Node* size_in_bytes); |
|
116 |
|
117 Node* prefetch_allocation(Node* i_o, |
|
118 Node*& needgc_false, Node*& contended_phi_rawmem, |
|
119 Node* old_eden_top, Node* new_eden_top, |
|
120 Node* length); |
|
121 |
|
122 public: |
|
123 PhaseMacroExpand(PhaseIterGVN &igvn) : Phase(Macro_Expand), _igvn(igvn), _has_locks(false) { |
|
124 _igvn.set_delay_transform(true); |
|
125 } |
|
126 void eliminate_macro_nodes(); |
|
127 bool expand_macro_nodes(); |
|
128 |
|
129 }; |
|
130 |
|
131 #endif // SHARE_VM_OPTO_MACRO_HPP |