annotate src/share/vm/opto/superword.hpp @ 9126:bc26f978b0ce

HotSpotResolvedObjectType: implement hasFinalizeSubclass() correctly don't use the (wrong) cached value, but ask the runtime on each request. Fixes regression on xml.* benchmarks @ specjvm2008. The problem was: After the constructor of Object was deoptimized due to an assumption violation, it was recompiled again after some time. However, on recompilation, the value of hasFinalizeSubclass for the class was not updated and it was compiled again with a, now wrong, assumption, which then triggers deoptimization again. This was repeated until it hit the recompilation limit (defined by PerMethodRecompilationCutoff), and therefore only executed by the interpreter from now on, causing the performance regression.
author Bernhard Urban <bernhard.urban@jku.at>
date Mon, 15 Apr 2013 19:54:58 +0200
parents ad736b4683b4
children de6a9e811145
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
a61af66fc99e Initial load
duke
parents:
diff changeset
1 /*
6179
8c92982cbbc4 7119644: Increase superword's vector size up to 256 bits
kvn
parents: 3842
diff changeset
2 * Copyright (c) 2007, 2012, Oracle and/or its affiliates. All rights reserved.
0
a61af66fc99e Initial load
duke
parents:
diff changeset
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
a61af66fc99e Initial load
duke
parents:
diff changeset
4 *
a61af66fc99e Initial load
duke
parents:
diff changeset
5 * This code is free software; you can redistribute it and/or modify it
a61af66fc99e Initial load
duke
parents:
diff changeset
6 * under the terms of the GNU General Public License version 2 only, as
a61af66fc99e Initial load
duke
parents:
diff changeset
7 * published by the Free Software Foundation.
a61af66fc99e Initial load
duke
parents:
diff changeset
8 *
a61af66fc99e Initial load
duke
parents:
diff changeset
9 * This code is distributed in the hope that it will be useful, but WITHOUT
a61af66fc99e Initial load
duke
parents:
diff changeset
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
a61af66fc99e Initial load
duke
parents:
diff changeset
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
a61af66fc99e Initial load
duke
parents:
diff changeset
12 * version 2 for more details (a copy is included in the LICENSE file that
a61af66fc99e Initial load
duke
parents:
diff changeset
13 * accompanied this code).
a61af66fc99e Initial load
duke
parents:
diff changeset
14 *
a61af66fc99e Initial load
duke
parents:
diff changeset
15 * You should have received a copy of the GNU General Public License version
a61af66fc99e Initial load
duke
parents:
diff changeset
16 * 2 along with this work; if not, write to the Free Software Foundation,
a61af66fc99e Initial load
duke
parents:
diff changeset
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
a61af66fc99e Initial load
duke
parents:
diff changeset
18 *
1552
c18cbe5936b8 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 844
diff changeset
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
c18cbe5936b8 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 844
diff changeset
20 * or visit www.oracle.com if you need additional information or have any
c18cbe5936b8 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 844
diff changeset
21 * questions.
0
a61af66fc99e Initial load
duke
parents:
diff changeset
22 */
a61af66fc99e Initial load
duke
parents:
diff changeset
23
1972
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
24 #ifndef SHARE_VM_OPTO_SUPERWORD_HPP
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
25 #define SHARE_VM_OPTO_SUPERWORD_HPP
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
26
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
27 #include "opto/connode.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
28 #include "opto/loopnode.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
29 #include "opto/node.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
30 #include "opto/phaseX.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
31 #include "opto/vectornode.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
32 #include "utilities/growableArray.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
33
0
a61af66fc99e Initial load
duke
parents:
diff changeset
34 //
a61af66fc99e Initial load
duke
parents:
diff changeset
35 // S U P E R W O R D T R A N S F O R M
a61af66fc99e Initial load
duke
parents:
diff changeset
36 //
a61af66fc99e Initial load
duke
parents:
diff changeset
37 // SuperWords are short, fixed length vectors.
a61af66fc99e Initial load
duke
parents:
diff changeset
38 //
a61af66fc99e Initial load
duke
parents:
diff changeset
39 // Algorithm from:
a61af66fc99e Initial load
duke
parents:
diff changeset
40 //
a61af66fc99e Initial load
duke
parents:
diff changeset
41 // Exploiting SuperWord Level Parallelism with
a61af66fc99e Initial load
duke
parents:
diff changeset
42 // Multimedia Instruction Sets
a61af66fc99e Initial load
duke
parents:
diff changeset
43 // by
a61af66fc99e Initial load
duke
parents:
diff changeset
44 // Samuel Larsen and Saman Amarasighe
a61af66fc99e Initial load
duke
parents:
diff changeset
45 // MIT Laboratory for Computer Science
a61af66fc99e Initial load
duke
parents:
diff changeset
46 // date
a61af66fc99e Initial load
duke
parents:
diff changeset
47 // May 2000
a61af66fc99e Initial load
duke
parents:
diff changeset
48 // published in
a61af66fc99e Initial load
duke
parents:
diff changeset
49 // ACM SIGPLAN Notices
a61af66fc99e Initial load
duke
parents:
diff changeset
50 // Proceedings of ACM PLDI '00, Volume 35 Issue 5
a61af66fc99e Initial load
duke
parents:
diff changeset
51 //
a61af66fc99e Initial load
duke
parents:
diff changeset
52 // Definition 3.1 A Pack is an n-tuple, <s1, ...,sn>, where
a61af66fc99e Initial load
duke
parents:
diff changeset
53 // s1,...,sn are independent isomorphic statements in a basic
a61af66fc99e Initial load
duke
parents:
diff changeset
54 // block.
a61af66fc99e Initial load
duke
parents:
diff changeset
55 //
a61af66fc99e Initial load
duke
parents:
diff changeset
56 // Definition 3.2 A PackSet is a set of Packs.
a61af66fc99e Initial load
duke
parents:
diff changeset
57 //
a61af66fc99e Initial load
duke
parents:
diff changeset
58 // Definition 3.3 A Pair is a Pack of size two, where the
a61af66fc99e Initial load
duke
parents:
diff changeset
59 // first statement is considered the left element, and the
a61af66fc99e Initial load
duke
parents:
diff changeset
60 // second statement is considered the right element.
a61af66fc99e Initial load
duke
parents:
diff changeset
61
a61af66fc99e Initial load
duke
parents:
diff changeset
62 class SWPointer;
a61af66fc99e Initial load
duke
parents:
diff changeset
63 class OrderedPair;
a61af66fc99e Initial load
duke
parents:
diff changeset
64
a61af66fc99e Initial load
duke
parents:
diff changeset
65 // ========================= Dependence Graph =====================
a61af66fc99e Initial load
duke
parents:
diff changeset
66
a61af66fc99e Initial load
duke
parents:
diff changeset
67 class DepMem;
a61af66fc99e Initial load
duke
parents:
diff changeset
68
a61af66fc99e Initial load
duke
parents:
diff changeset
69 //------------------------------DepEdge---------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
70 // An edge in the dependence graph. The edges incident to a dependence
a61af66fc99e Initial load
duke
parents:
diff changeset
71 // node are threaded through _next_in for incoming edges and _next_out
a61af66fc99e Initial load
duke
parents:
diff changeset
72 // for outgoing edges.
a61af66fc99e Initial load
duke
parents:
diff changeset
73 class DepEdge : public ResourceObj {
a61af66fc99e Initial load
duke
parents:
diff changeset
74 protected:
a61af66fc99e Initial load
duke
parents:
diff changeset
75 DepMem* _pred;
a61af66fc99e Initial load
duke
parents:
diff changeset
76 DepMem* _succ;
a61af66fc99e Initial load
duke
parents:
diff changeset
77 DepEdge* _next_in; // list of in edges, null terminated
a61af66fc99e Initial load
duke
parents:
diff changeset
78 DepEdge* _next_out; // list of out edges, null terminated
a61af66fc99e Initial load
duke
parents:
diff changeset
79
a61af66fc99e Initial load
duke
parents:
diff changeset
80 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
81 DepEdge(DepMem* pred, DepMem* succ, DepEdge* next_in, DepEdge* next_out) :
a61af66fc99e Initial load
duke
parents:
diff changeset
82 _pred(pred), _succ(succ), _next_in(next_in), _next_out(next_out) {}
a61af66fc99e Initial load
duke
parents:
diff changeset
83
a61af66fc99e Initial load
duke
parents:
diff changeset
84 DepEdge* next_in() { return _next_in; }
a61af66fc99e Initial load
duke
parents:
diff changeset
85 DepEdge* next_out() { return _next_out; }
a61af66fc99e Initial load
duke
parents:
diff changeset
86 DepMem* pred() { return _pred; }
a61af66fc99e Initial load
duke
parents:
diff changeset
87 DepMem* succ() { return _succ; }
a61af66fc99e Initial load
duke
parents:
diff changeset
88
a61af66fc99e Initial load
duke
parents:
diff changeset
89 void print();
a61af66fc99e Initial load
duke
parents:
diff changeset
90 };
a61af66fc99e Initial load
duke
parents:
diff changeset
91
a61af66fc99e Initial load
duke
parents:
diff changeset
92 //------------------------------DepMem---------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
93 // A node in the dependence graph. _in_head starts the threaded list of
a61af66fc99e Initial load
duke
parents:
diff changeset
94 // incoming edges, and _out_head starts the list of outgoing edges.
a61af66fc99e Initial load
duke
parents:
diff changeset
95 class DepMem : public ResourceObj {
a61af66fc99e Initial load
duke
parents:
diff changeset
96 protected:
a61af66fc99e Initial load
duke
parents:
diff changeset
97 Node* _node; // Corresponding ideal node
a61af66fc99e Initial load
duke
parents:
diff changeset
98 DepEdge* _in_head; // Head of list of in edges, null terminated
a61af66fc99e Initial load
duke
parents:
diff changeset
99 DepEdge* _out_head; // Head of list of out edges, null terminated
a61af66fc99e Initial load
duke
parents:
diff changeset
100
a61af66fc99e Initial load
duke
parents:
diff changeset
101 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
102 DepMem(Node* node) : _node(node), _in_head(NULL), _out_head(NULL) {}
a61af66fc99e Initial load
duke
parents:
diff changeset
103
a61af66fc99e Initial load
duke
parents:
diff changeset
104 Node* node() { return _node; }
a61af66fc99e Initial load
duke
parents:
diff changeset
105 DepEdge* in_head() { return _in_head; }
a61af66fc99e Initial load
duke
parents:
diff changeset
106 DepEdge* out_head() { return _out_head; }
a61af66fc99e Initial load
duke
parents:
diff changeset
107 void set_in_head(DepEdge* hd) { _in_head = hd; }
a61af66fc99e Initial load
duke
parents:
diff changeset
108 void set_out_head(DepEdge* hd) { _out_head = hd; }
a61af66fc99e Initial load
duke
parents:
diff changeset
109
a61af66fc99e Initial load
duke
parents:
diff changeset
110 int in_cnt(); // Incoming edge count
a61af66fc99e Initial load
duke
parents:
diff changeset
111 int out_cnt(); // Outgoing edge count
a61af66fc99e Initial load
duke
parents:
diff changeset
112
a61af66fc99e Initial load
duke
parents:
diff changeset
113 void print();
a61af66fc99e Initial load
duke
parents:
diff changeset
114 };
a61af66fc99e Initial load
duke
parents:
diff changeset
115
a61af66fc99e Initial load
duke
parents:
diff changeset
116 //------------------------------DepGraph---------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
117 class DepGraph VALUE_OBJ_CLASS_SPEC {
a61af66fc99e Initial load
duke
parents:
diff changeset
118 protected:
a61af66fc99e Initial load
duke
parents:
diff changeset
119 Arena* _arena;
a61af66fc99e Initial load
duke
parents:
diff changeset
120 GrowableArray<DepMem*> _map;
a61af66fc99e Initial load
duke
parents:
diff changeset
121 DepMem* _root;
a61af66fc99e Initial load
duke
parents:
diff changeset
122 DepMem* _tail;
a61af66fc99e Initial load
duke
parents:
diff changeset
123
a61af66fc99e Initial load
duke
parents:
diff changeset
124 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
125 DepGraph(Arena* a) : _arena(a), _map(a, 8, 0, NULL) {
a61af66fc99e Initial load
duke
parents:
diff changeset
126 _root = new (_arena) DepMem(NULL);
a61af66fc99e Initial load
duke
parents:
diff changeset
127 _tail = new (_arena) DepMem(NULL);
a61af66fc99e Initial load
duke
parents:
diff changeset
128 }
a61af66fc99e Initial load
duke
parents:
diff changeset
129
a61af66fc99e Initial load
duke
parents:
diff changeset
130 DepMem* root() { return _root; }
a61af66fc99e Initial load
duke
parents:
diff changeset
131 DepMem* tail() { return _tail; }
a61af66fc99e Initial load
duke
parents:
diff changeset
132
a61af66fc99e Initial load
duke
parents:
diff changeset
133 // Return dependence node corresponding to an ideal node
a61af66fc99e Initial load
duke
parents:
diff changeset
134 DepMem* dep(Node* node) { return _map.at(node->_idx); }
a61af66fc99e Initial load
duke
parents:
diff changeset
135
a61af66fc99e Initial load
duke
parents:
diff changeset
136 // Make a new dependence graph node for an ideal node.
a61af66fc99e Initial load
duke
parents:
diff changeset
137 DepMem* make_node(Node* node);
a61af66fc99e Initial load
duke
parents:
diff changeset
138
a61af66fc99e Initial load
duke
parents:
diff changeset
139 // Make a new dependence graph edge dprec->dsucc
a61af66fc99e Initial load
duke
parents:
diff changeset
140 DepEdge* make_edge(DepMem* dpred, DepMem* dsucc);
a61af66fc99e Initial load
duke
parents:
diff changeset
141
a61af66fc99e Initial load
duke
parents:
diff changeset
142 DepEdge* make_edge(Node* pred, Node* succ) { return make_edge(dep(pred), dep(succ)); }
a61af66fc99e Initial load
duke
parents:
diff changeset
143 DepEdge* make_edge(DepMem* pred, Node* succ) { return make_edge(pred, dep(succ)); }
a61af66fc99e Initial load
duke
parents:
diff changeset
144 DepEdge* make_edge(Node* pred, DepMem* succ) { return make_edge(dep(pred), succ); }
a61af66fc99e Initial load
duke
parents:
diff changeset
145
a61af66fc99e Initial load
duke
parents:
diff changeset
146 void init() { _map.clear(); } // initialize
a61af66fc99e Initial load
duke
parents:
diff changeset
147
a61af66fc99e Initial load
duke
parents:
diff changeset
148 void print(Node* n) { dep(n)->print(); }
a61af66fc99e Initial load
duke
parents:
diff changeset
149 void print(DepMem* d) { d->print(); }
a61af66fc99e Initial load
duke
parents:
diff changeset
150 };
a61af66fc99e Initial load
duke
parents:
diff changeset
151
a61af66fc99e Initial load
duke
parents:
diff changeset
152 //------------------------------DepPreds---------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
153 // Iterator over predecessors in the dependence graph and
a61af66fc99e Initial load
duke
parents:
diff changeset
154 // non-memory-graph inputs of ideal nodes.
a61af66fc99e Initial load
duke
parents:
diff changeset
155 class DepPreds : public StackObj {
a61af66fc99e Initial load
duke
parents:
diff changeset
156 private:
a61af66fc99e Initial load
duke
parents:
diff changeset
157 Node* _n;
a61af66fc99e Initial load
duke
parents:
diff changeset
158 int _next_idx, _end_idx;
a61af66fc99e Initial load
duke
parents:
diff changeset
159 DepEdge* _dep_next;
a61af66fc99e Initial load
duke
parents:
diff changeset
160 Node* _current;
a61af66fc99e Initial load
duke
parents:
diff changeset
161 bool _done;
a61af66fc99e Initial load
duke
parents:
diff changeset
162
a61af66fc99e Initial load
duke
parents:
diff changeset
163 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
164 DepPreds(Node* n, DepGraph& dg);
a61af66fc99e Initial load
duke
parents:
diff changeset
165 Node* current() { return _current; }
a61af66fc99e Initial load
duke
parents:
diff changeset
166 bool done() { return _done; }
a61af66fc99e Initial load
duke
parents:
diff changeset
167 void next();
a61af66fc99e Initial load
duke
parents:
diff changeset
168 };
a61af66fc99e Initial load
duke
parents:
diff changeset
169
a61af66fc99e Initial load
duke
parents:
diff changeset
170 //------------------------------DepSuccs---------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
171 // Iterator over successors in the dependence graph and
a61af66fc99e Initial load
duke
parents:
diff changeset
172 // non-memory-graph outputs of ideal nodes.
a61af66fc99e Initial load
duke
parents:
diff changeset
173 class DepSuccs : public StackObj {
a61af66fc99e Initial load
duke
parents:
diff changeset
174 private:
a61af66fc99e Initial load
duke
parents:
diff changeset
175 Node* _n;
a61af66fc99e Initial load
duke
parents:
diff changeset
176 int _next_idx, _end_idx;
a61af66fc99e Initial load
duke
parents:
diff changeset
177 DepEdge* _dep_next;
a61af66fc99e Initial load
duke
parents:
diff changeset
178 Node* _current;
a61af66fc99e Initial load
duke
parents:
diff changeset
179 bool _done;
a61af66fc99e Initial load
duke
parents:
diff changeset
180
a61af66fc99e Initial load
duke
parents:
diff changeset
181 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
182 DepSuccs(Node* n, DepGraph& dg);
a61af66fc99e Initial load
duke
parents:
diff changeset
183 Node* current() { return _current; }
a61af66fc99e Initial load
duke
parents:
diff changeset
184 bool done() { return _done; }
a61af66fc99e Initial load
duke
parents:
diff changeset
185 void next();
a61af66fc99e Initial load
duke
parents:
diff changeset
186 };
a61af66fc99e Initial load
duke
parents:
diff changeset
187
a61af66fc99e Initial load
duke
parents:
diff changeset
188
a61af66fc99e Initial load
duke
parents:
diff changeset
189 // ========================= SuperWord =====================
a61af66fc99e Initial load
duke
parents:
diff changeset
190
a61af66fc99e Initial load
duke
parents:
diff changeset
191 // -----------------------------SWNodeInfo---------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
192 // Per node info needed by SuperWord
a61af66fc99e Initial load
duke
parents:
diff changeset
193 class SWNodeInfo VALUE_OBJ_CLASS_SPEC {
a61af66fc99e Initial load
duke
parents:
diff changeset
194 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
195 int _alignment; // memory alignment for a node
a61af66fc99e Initial load
duke
parents:
diff changeset
196 int _depth; // Max expression (DAG) depth from block start
a61af66fc99e Initial load
duke
parents:
diff changeset
197 const Type* _velt_type; // vector element type
a61af66fc99e Initial load
duke
parents:
diff changeset
198 Node_List* _my_pack; // pack containing this node
a61af66fc99e Initial load
duke
parents:
diff changeset
199
a61af66fc99e Initial load
duke
parents:
diff changeset
200 SWNodeInfo() : _alignment(-1), _depth(0), _velt_type(NULL), _my_pack(NULL) {}
a61af66fc99e Initial load
duke
parents:
diff changeset
201 static const SWNodeInfo initial;
a61af66fc99e Initial load
duke
parents:
diff changeset
202 };
a61af66fc99e Initial load
duke
parents:
diff changeset
203
a61af66fc99e Initial load
duke
parents:
diff changeset
204 // -----------------------------SuperWord---------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
205 // Transforms scalar operations into packed (superword) operations.
a61af66fc99e Initial load
duke
parents:
diff changeset
206 class SuperWord : public ResourceObj {
a61af66fc99e Initial load
duke
parents:
diff changeset
207 private:
a61af66fc99e Initial load
duke
parents:
diff changeset
208 PhaseIdealLoop* _phase;
a61af66fc99e Initial load
duke
parents:
diff changeset
209 Arena* _arena;
a61af66fc99e Initial load
duke
parents:
diff changeset
210 PhaseIterGVN &_igvn;
a61af66fc99e Initial load
duke
parents:
diff changeset
211
a61af66fc99e Initial load
duke
parents:
diff changeset
212 enum consts { top_align = -1, bottom_align = -666 };
a61af66fc99e Initial load
duke
parents:
diff changeset
213
a61af66fc99e Initial load
duke
parents:
diff changeset
214 GrowableArray<Node_List*> _packset; // Packs for the current block
a61af66fc99e Initial load
duke
parents:
diff changeset
215
a61af66fc99e Initial load
duke
parents:
diff changeset
216 GrowableArray<int> _bb_idx; // Map from Node _idx to index within block
a61af66fc99e Initial load
duke
parents:
diff changeset
217
a61af66fc99e Initial load
duke
parents:
diff changeset
218 GrowableArray<Node*> _block; // Nodes in current block
a61af66fc99e Initial load
duke
parents:
diff changeset
219 GrowableArray<Node*> _data_entry; // Nodes with all inputs from outside
a61af66fc99e Initial load
duke
parents:
diff changeset
220 GrowableArray<Node*> _mem_slice_head; // Memory slice head nodes
a61af66fc99e Initial load
duke
parents:
diff changeset
221 GrowableArray<Node*> _mem_slice_tail; // Memory slice tail nodes
a61af66fc99e Initial load
duke
parents:
diff changeset
222
a61af66fc99e Initial load
duke
parents:
diff changeset
223 GrowableArray<SWNodeInfo> _node_info; // Info needed per node
a61af66fc99e Initial load
duke
parents:
diff changeset
224
a61af66fc99e Initial load
duke
parents:
diff changeset
225 MemNode* _align_to_ref; // Memory reference that pre-loop will align to
a61af66fc99e Initial load
duke
parents:
diff changeset
226
a61af66fc99e Initial load
duke
parents:
diff changeset
227 GrowableArray<OrderedPair> _disjoint_ptrs; // runtime disambiguated pointer pairs
a61af66fc99e Initial load
duke
parents:
diff changeset
228
a61af66fc99e Initial load
duke
parents:
diff changeset
229 DepGraph _dg; // Dependence graph
a61af66fc99e Initial load
duke
parents:
diff changeset
230
a61af66fc99e Initial load
duke
parents:
diff changeset
231 // Scratch pads
a61af66fc99e Initial load
duke
parents:
diff changeset
232 VectorSet _visited; // Visited set
a61af66fc99e Initial load
duke
parents:
diff changeset
233 VectorSet _post_visited; // Post-visited set
a61af66fc99e Initial load
duke
parents:
diff changeset
234 Node_Stack _n_idx_list; // List of (node,index) pairs
a61af66fc99e Initial load
duke
parents:
diff changeset
235 GrowableArray<Node*> _nlist; // List of nodes
a61af66fc99e Initial load
duke
parents:
diff changeset
236 GrowableArray<Node*> _stk; // Stack of nodes
a61af66fc99e Initial load
duke
parents:
diff changeset
237
a61af66fc99e Initial load
duke
parents:
diff changeset
238 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
239 SuperWord(PhaseIdealLoop* phase);
a61af66fc99e Initial load
duke
parents:
diff changeset
240
a61af66fc99e Initial load
duke
parents:
diff changeset
241 void transform_loop(IdealLoopTree* lpt);
a61af66fc99e Initial load
duke
parents:
diff changeset
242
a61af66fc99e Initial load
duke
parents:
diff changeset
243 // Accessors for SWPointer
a61af66fc99e Initial load
duke
parents:
diff changeset
244 PhaseIdealLoop* phase() { return _phase; }
a61af66fc99e Initial load
duke
parents:
diff changeset
245 IdealLoopTree* lpt() { return _lpt; }
a61af66fc99e Initial load
duke
parents:
diff changeset
246 PhiNode* iv() { return _iv; }
a61af66fc99e Initial load
duke
parents:
diff changeset
247
a61af66fc99e Initial load
duke
parents:
diff changeset
248 private:
a61af66fc99e Initial load
duke
parents:
diff changeset
249 IdealLoopTree* _lpt; // Current loop tree node
a61af66fc99e Initial load
duke
parents:
diff changeset
250 LoopNode* _lp; // Current LoopNode
a61af66fc99e Initial load
duke
parents:
diff changeset
251 Node* _bb; // Current basic block
a61af66fc99e Initial load
duke
parents:
diff changeset
252 PhiNode* _iv; // Induction var
a61af66fc99e Initial load
duke
parents:
diff changeset
253
a61af66fc99e Initial load
duke
parents:
diff changeset
254 // Accessors
a61af66fc99e Initial load
duke
parents:
diff changeset
255 Arena* arena() { return _arena; }
a61af66fc99e Initial load
duke
parents:
diff changeset
256
a61af66fc99e Initial load
duke
parents:
diff changeset
257 Node* bb() { return _bb; }
a61af66fc99e Initial load
duke
parents:
diff changeset
258 void set_bb(Node* bb) { _bb = bb; }
a61af66fc99e Initial load
duke
parents:
diff changeset
259
a61af66fc99e Initial load
duke
parents:
diff changeset
260 void set_lpt(IdealLoopTree* lpt) { _lpt = lpt; }
a61af66fc99e Initial load
duke
parents:
diff changeset
261
a61af66fc99e Initial load
duke
parents:
diff changeset
262 LoopNode* lp() { return _lp; }
a61af66fc99e Initial load
duke
parents:
diff changeset
263 void set_lp(LoopNode* lp) { _lp = lp;
a61af66fc99e Initial load
duke
parents:
diff changeset
264 _iv = lp->as_CountedLoop()->phi()->as_Phi(); }
a61af66fc99e Initial load
duke
parents:
diff changeset
265 int iv_stride() { return lp()->as_CountedLoop()->stride_con(); }
a61af66fc99e Initial load
duke
parents:
diff changeset
266
6183
6f8f439e247d 7177923: SIGBUS on sparc in compiled code for java.util.Calendar.clear()
kvn
parents: 6179
diff changeset
267 int vector_width(Node* n) {
6f8f439e247d 7177923: SIGBUS on sparc in compiled code for java.util.Calendar.clear()
kvn
parents: 6179
diff changeset
268 BasicType bt = velt_basic_type(n);
6f8f439e247d 7177923: SIGBUS on sparc in compiled code for java.util.Calendar.clear()
kvn
parents: 6179
diff changeset
269 return MIN2(ABS(iv_stride()), Matcher::max_vector_size(bt));
6179
8c92982cbbc4 7119644: Increase superword's vector size up to 256 bits
kvn
parents: 3842
diff changeset
270 }
6183
6f8f439e247d 7177923: SIGBUS on sparc in compiled code for java.util.Calendar.clear()
kvn
parents: 6179
diff changeset
271 int vector_width_in_bytes(Node* n) {
6f8f439e247d 7177923: SIGBUS on sparc in compiled code for java.util.Calendar.clear()
kvn
parents: 6179
diff changeset
272 BasicType bt = velt_basic_type(n);
6f8f439e247d 7177923: SIGBUS on sparc in compiled code for java.util.Calendar.clear()
kvn
parents: 6179
diff changeset
273 return vector_width(n)*type2aelembytes(bt);
6f8f439e247d 7177923: SIGBUS on sparc in compiled code for java.util.Calendar.clear()
kvn
parents: 6179
diff changeset
274 }
0
a61af66fc99e Initial load
duke
parents:
diff changeset
275 MemNode* align_to_ref() { return _align_to_ref; }
a61af66fc99e Initial load
duke
parents:
diff changeset
276 void set_align_to_ref(MemNode* m) { _align_to_ref = m; }
a61af66fc99e Initial load
duke
parents:
diff changeset
277
a61af66fc99e Initial load
duke
parents:
diff changeset
278 Node* ctrl(Node* n) const { return _phase->has_ctrl(n) ? _phase->get_ctrl(n) : n; }
a61af66fc99e Initial load
duke
parents:
diff changeset
279
a61af66fc99e Initial load
duke
parents:
diff changeset
280 // block accessors
a61af66fc99e Initial load
duke
parents:
diff changeset
281 bool in_bb(Node* n) { return n != NULL && n->outcnt() > 0 && ctrl(n) == _bb; }
a61af66fc99e Initial load
duke
parents:
diff changeset
282 int bb_idx(Node* n) { assert(in_bb(n), "must be"); return _bb_idx.at(n->_idx); }
a61af66fc99e Initial load
duke
parents:
diff changeset
283 void set_bb_idx(Node* n, int i) { _bb_idx.at_put_grow(n->_idx, i); }
a61af66fc99e Initial load
duke
parents:
diff changeset
284
a61af66fc99e Initial load
duke
parents:
diff changeset
285 // visited set accessors
a61af66fc99e Initial load
duke
parents:
diff changeset
286 void visited_clear() { _visited.Clear(); }
a61af66fc99e Initial load
duke
parents:
diff changeset
287 void visited_set(Node* n) { return _visited.set(bb_idx(n)); }
a61af66fc99e Initial load
duke
parents:
diff changeset
288 int visited_test(Node* n) { return _visited.test(bb_idx(n)); }
a61af66fc99e Initial load
duke
parents:
diff changeset
289 int visited_test_set(Node* n) { return _visited.test_set(bb_idx(n)); }
a61af66fc99e Initial load
duke
parents:
diff changeset
290 void post_visited_clear() { _post_visited.Clear(); }
a61af66fc99e Initial load
duke
parents:
diff changeset
291 void post_visited_set(Node* n) { return _post_visited.set(bb_idx(n)); }
a61af66fc99e Initial load
duke
parents:
diff changeset
292 int post_visited_test(Node* n) { return _post_visited.test(bb_idx(n)); }
a61af66fc99e Initial load
duke
parents:
diff changeset
293
a61af66fc99e Initial load
duke
parents:
diff changeset
294 // Ensure node_info contains element "i"
a61af66fc99e Initial load
duke
parents:
diff changeset
295 void grow_node_info(int i) { if (i >= _node_info.length()) _node_info.at_put_grow(i, SWNodeInfo::initial); }
a61af66fc99e Initial load
duke
parents:
diff changeset
296
a61af66fc99e Initial load
duke
parents:
diff changeset
297 // memory alignment for a node
a61af66fc99e Initial load
duke
parents:
diff changeset
298 int alignment(Node* n) { return _node_info.adr_at(bb_idx(n))->_alignment; }
a61af66fc99e Initial load
duke
parents:
diff changeset
299 void set_alignment(Node* n, int a) { int i = bb_idx(n); grow_node_info(i); _node_info.adr_at(i)->_alignment = a; }
a61af66fc99e Initial load
duke
parents:
diff changeset
300
a61af66fc99e Initial load
duke
parents:
diff changeset
301 // Max expression (DAG) depth from beginning of the block for each node
a61af66fc99e Initial load
duke
parents:
diff changeset
302 int depth(Node* n) { return _node_info.adr_at(bb_idx(n))->_depth; }
a61af66fc99e Initial load
duke
parents:
diff changeset
303 void set_depth(Node* n, int d) { int i = bb_idx(n); grow_node_info(i); _node_info.adr_at(i)->_depth = d; }
a61af66fc99e Initial load
duke
parents:
diff changeset
304
a61af66fc99e Initial load
duke
parents:
diff changeset
305 // vector element type
a61af66fc99e Initial load
duke
parents:
diff changeset
306 const Type* velt_type(Node* n) { return _node_info.adr_at(bb_idx(n))->_velt_type; }
6179
8c92982cbbc4 7119644: Increase superword's vector size up to 256 bits
kvn
parents: 3842
diff changeset
307 BasicType velt_basic_type(Node* n) { return velt_type(n)->array_element_basic_type(); }
0
a61af66fc99e Initial load
duke
parents:
diff changeset
308 void set_velt_type(Node* n, const Type* t) { int i = bb_idx(n); grow_node_info(i); _node_info.adr_at(i)->_velt_type = t; }
6179
8c92982cbbc4 7119644: Increase superword's vector size up to 256 bits
kvn
parents: 3842
diff changeset
309 bool same_velt_type(Node* n1, Node* n2);
0
a61af66fc99e Initial load
duke
parents:
diff changeset
310
a61af66fc99e Initial load
duke
parents:
diff changeset
311 // my_pack
a61af66fc99e Initial load
duke
parents:
diff changeset
312 Node_List* my_pack(Node* n) { return !in_bb(n) ? NULL : _node_info.adr_at(bb_idx(n))->_my_pack; }
a61af66fc99e Initial load
duke
parents:
diff changeset
313 void set_my_pack(Node* n, Node_List* p) { int i = bb_idx(n); grow_node_info(i); _node_info.adr_at(i)->_my_pack = p; }
a61af66fc99e Initial load
duke
parents:
diff changeset
314
a61af66fc99e Initial load
duke
parents:
diff changeset
315 // methods
a61af66fc99e Initial load
duke
parents:
diff changeset
316
a61af66fc99e Initial load
duke
parents:
diff changeset
317 // Extract the superword level parallelism
a61af66fc99e Initial load
duke
parents:
diff changeset
318 void SLP_extract();
a61af66fc99e Initial load
duke
parents:
diff changeset
319 // Find the adjacent memory references and create pack pairs for them.
a61af66fc99e Initial load
duke
parents:
diff changeset
320 void find_adjacent_refs();
a61af66fc99e Initial load
duke
parents:
diff changeset
321 // Find a memory reference to align the loop induction variable to.
6179
8c92982cbbc4 7119644: Increase superword's vector size up to 256 bits
kvn
parents: 3842
diff changeset
322 MemNode* find_align_to_ref(Node_List &memops);
8c92982cbbc4 7119644: Increase superword's vector size up to 256 bits
kvn
parents: 3842
diff changeset
323 // Calculate loop's iv adjustment for this memory ops.
8c92982cbbc4 7119644: Increase superword's vector size up to 256 bits
kvn
parents: 3842
diff changeset
324 int get_iv_adjustment(MemNode* mem);
0
a61af66fc99e Initial load
duke
parents:
diff changeset
325 // Can the preloop align the reference to position zero in the vector?
a61af66fc99e Initial load
duke
parents:
diff changeset
326 bool ref_is_alignable(SWPointer& p);
a61af66fc99e Initial load
duke
parents:
diff changeset
327 // Construct dependency graph.
a61af66fc99e Initial load
duke
parents:
diff changeset
328 void dependence_graph();
a61af66fc99e Initial load
duke
parents:
diff changeset
329 // Return a memory slice (node list) in predecessor order starting at "start"
a61af66fc99e Initial load
duke
parents:
diff changeset
330 void mem_slice_preds(Node* start, Node* stop, GrowableArray<Node*> &preds);
605
98cb887364d3 6810672: Comment typos
twisti
parents: 0
diff changeset
331 // Can s1 and s2 be in a pack with s1 immediately preceding s2 and s1 aligned at "align"
0
a61af66fc99e Initial load
duke
parents:
diff changeset
332 bool stmts_can_pack(Node* s1, Node* s2, int align);
a61af66fc99e Initial load
duke
parents:
diff changeset
333 // Does s exist in a pack at position pos?
a61af66fc99e Initial load
duke
parents:
diff changeset
334 bool exists_at(Node* s, uint pos);
a61af66fc99e Initial load
duke
parents:
diff changeset
335 // Is s1 immediately before s2 in memory?
a61af66fc99e Initial load
duke
parents:
diff changeset
336 bool are_adjacent_refs(Node* s1, Node* s2);
a61af66fc99e Initial load
duke
parents:
diff changeset
337 // Are s1 and s2 similar?
a61af66fc99e Initial load
duke
parents:
diff changeset
338 bool isomorphic(Node* s1, Node* s2);
a61af66fc99e Initial load
duke
parents:
diff changeset
339 // Is there no data path from s1 to s2 or s2 to s1?
a61af66fc99e Initial load
duke
parents:
diff changeset
340 bool independent(Node* s1, Node* s2);
a61af66fc99e Initial load
duke
parents:
diff changeset
341 // Helper for independent
a61af66fc99e Initial load
duke
parents:
diff changeset
342 bool independent_path(Node* shallow, Node* deep, uint dp=0);
a61af66fc99e Initial load
duke
parents:
diff changeset
343 void set_alignment(Node* s1, Node* s2, int align);
a61af66fc99e Initial load
duke
parents:
diff changeset
344 int data_size(Node* s);
a61af66fc99e Initial load
duke
parents:
diff changeset
345 // Extend packset by following use->def and def->use links from pack members.
a61af66fc99e Initial load
duke
parents:
diff changeset
346 void extend_packlist();
a61af66fc99e Initial load
duke
parents:
diff changeset
347 // Extend the packset by visiting operand definitions of nodes in pack p
a61af66fc99e Initial load
duke
parents:
diff changeset
348 bool follow_use_defs(Node_List* p);
a61af66fc99e Initial load
duke
parents:
diff changeset
349 // Extend the packset by visiting uses of nodes in pack p
a61af66fc99e Initial load
duke
parents:
diff changeset
350 bool follow_def_uses(Node_List* p);
a61af66fc99e Initial load
duke
parents:
diff changeset
351 // Estimate the savings from executing s1 and s2 as a pack
a61af66fc99e Initial load
duke
parents:
diff changeset
352 int est_savings(Node* s1, Node* s2);
a61af66fc99e Initial load
duke
parents:
diff changeset
353 int adjacent_profit(Node* s1, Node* s2);
a61af66fc99e Initial load
duke
parents:
diff changeset
354 int pack_cost(int ct);
a61af66fc99e Initial load
duke
parents:
diff changeset
355 int unpack_cost(int ct);
a61af66fc99e Initial load
duke
parents:
diff changeset
356 // Combine packs A and B with A.last == B.first into A.first..,A.last,B.second,..B.last
a61af66fc99e Initial load
duke
parents:
diff changeset
357 void combine_packs();
a61af66fc99e Initial load
duke
parents:
diff changeset
358 // Construct the map from nodes to packs.
a61af66fc99e Initial load
duke
parents:
diff changeset
359 void construct_my_pack_map();
a61af66fc99e Initial load
duke
parents:
diff changeset
360 // Remove packs that are not implemented or not profitable.
a61af66fc99e Initial load
duke
parents:
diff changeset
361 void filter_packs();
a61af66fc99e Initial load
duke
parents:
diff changeset
362 // Adjust the memory graph for the packed operations
a61af66fc99e Initial load
duke
parents:
diff changeset
363 void schedule();
667
78af5ae8e731 6636138: UseSuperWord enabled failure
cfang
parents: 605
diff changeset
364 // Remove "current" from its current position in the memory graph and insert
78af5ae8e731 6636138: UseSuperWord enabled failure
cfang
parents: 605
diff changeset
365 // it after the appropriate insert points (lip or uip);
78af5ae8e731 6636138: UseSuperWord enabled failure
cfang
parents: 605
diff changeset
366 void remove_and_insert(MemNode *current, MemNode *prev, MemNode *lip, Node *uip, Unique_Node_List &schd_before);
78af5ae8e731 6636138: UseSuperWord enabled failure
cfang
parents: 605
diff changeset
367 // Within a store pack, schedule stores together by moving out the sandwiched memory ops according
78af5ae8e731 6636138: UseSuperWord enabled failure
cfang
parents: 605
diff changeset
368 // to dependence info; and within a load pack, move loads down to the last executed load.
0
a61af66fc99e Initial load
duke
parents:
diff changeset
369 void co_locate_pack(Node_List* p);
a61af66fc99e Initial load
duke
parents:
diff changeset
370 // Convert packs into vector node operations
a61af66fc99e Initial load
duke
parents:
diff changeset
371 void output();
a61af66fc99e Initial load
duke
parents:
diff changeset
372 // Create a vector operand for the nodes in pack p for operand: in(opd_idx)
3842
c7b60b601eb4 7069452: Cleanup NodeFlags
kvn
parents: 1972
diff changeset
373 Node* vector_opd(Node_List* p, int opd_idx);
0
a61af66fc99e Initial load
duke
parents:
diff changeset
374 // Can code be generated for pack p?
a61af66fc99e Initial load
duke
parents:
diff changeset
375 bool implemented(Node_List* p);
a61af66fc99e Initial load
duke
parents:
diff changeset
376 // For pack p, are all operands and all uses (with in the block) vector?
a61af66fc99e Initial load
duke
parents:
diff changeset
377 bool profitable(Node_List* p);
a61af66fc99e Initial load
duke
parents:
diff changeset
378 // If a use of pack p is not a vector use, then replace the use with an extract operation.
a61af66fc99e Initial load
duke
parents:
diff changeset
379 void insert_extracts(Node_List* p);
a61af66fc99e Initial load
duke
parents:
diff changeset
380 // Is use->in(u_idx) a vector use?
a61af66fc99e Initial load
duke
parents:
diff changeset
381 bool is_vector_use(Node* use, int u_idx);
a61af66fc99e Initial load
duke
parents:
diff changeset
382 // Construct reverse postorder list of block members
8079
ad736b4683b4 8004867: VM crashing with assert "share/vm/opto/node.hpp:357 - assert(i < _max) failed: oob"
kvn
parents: 6794
diff changeset
383 bool construct_bb();
0
a61af66fc99e Initial load
duke
parents:
diff changeset
384 // Initialize per node info
a61af66fc99e Initial load
duke
parents:
diff changeset
385 void initialize_bb();
a61af66fc99e Initial load
duke
parents:
diff changeset
386 // Insert n into block after pos
a61af66fc99e Initial load
duke
parents:
diff changeset
387 void bb_insert_after(Node* n, int pos);
a61af66fc99e Initial load
duke
parents:
diff changeset
388 // Compute max depth for expressions from beginning of block
a61af66fc99e Initial load
duke
parents:
diff changeset
389 void compute_max_depth();
a61af66fc99e Initial load
duke
parents:
diff changeset
390 // Compute necessary vector element type for expressions
a61af66fc99e Initial load
duke
parents:
diff changeset
391 void compute_vector_element_type();
a61af66fc99e Initial load
duke
parents:
diff changeset
392 // Are s1 and s2 in a pack pair and ordered as s1,s2?
a61af66fc99e Initial load
duke
parents:
diff changeset
393 bool in_packset(Node* s1, Node* s2);
a61af66fc99e Initial load
duke
parents:
diff changeset
394 // Is s in pack p?
a61af66fc99e Initial load
duke
parents:
diff changeset
395 Node_List* in_pack(Node* s, Node_List* p);
a61af66fc99e Initial load
duke
parents:
diff changeset
396 // Remove the pack at position pos in the packset
a61af66fc99e Initial load
duke
parents:
diff changeset
397 void remove_pack_at(int pos);
a61af66fc99e Initial load
duke
parents:
diff changeset
398 // Return the node executed first in pack p.
a61af66fc99e Initial load
duke
parents:
diff changeset
399 Node* executed_first(Node_List* p);
a61af66fc99e Initial load
duke
parents:
diff changeset
400 // Return the node executed last in pack p.
a61af66fc99e Initial load
duke
parents:
diff changeset
401 Node* executed_last(Node_List* p);
a61af66fc99e Initial load
duke
parents:
diff changeset
402 // Alignment within a vector memory reference
6794
8ae8f9dd7099 7199010: incorrect vector alignment
kvn
parents: 6183
diff changeset
403 int memory_alignment(MemNode* s, int iv_adjust);
0
a61af66fc99e Initial load
duke
parents:
diff changeset
404 // (Start, end] half-open range defining which operands are vector
a61af66fc99e Initial load
duke
parents:
diff changeset
405 void vector_opd_range(Node* n, uint* start, uint* end);
a61af66fc99e Initial load
duke
parents:
diff changeset
406 // Smallest type containing range of values
6179
8c92982cbbc4 7119644: Increase superword's vector size up to 256 bits
kvn
parents: 3842
diff changeset
407 const Type* container_type(Node* n);
0
a61af66fc99e Initial load
duke
parents:
diff changeset
408 // Adjust pre-loop limit so that in main loop, a load/store reference
a61af66fc99e Initial load
duke
parents:
diff changeset
409 // to align_to_ref will be a position zero in the vector.
a61af66fc99e Initial load
duke
parents:
diff changeset
410 void align_initial_loop_index(MemNode* align_to_ref);
a61af66fc99e Initial load
duke
parents:
diff changeset
411 // Find pre loop end from main loop. Returns null if none.
a61af66fc99e Initial load
duke
parents:
diff changeset
412 CountedLoopEndNode* get_pre_loop_end(CountedLoopNode *cl);
a61af66fc99e Initial load
duke
parents:
diff changeset
413 // Is the use of d1 in u1 at the same operand position as d2 in u2?
a61af66fc99e Initial load
duke
parents:
diff changeset
414 bool opnd_positions_match(Node* d1, Node* u1, Node* d2, Node* u2);
a61af66fc99e Initial load
duke
parents:
diff changeset
415 void init();
a61af66fc99e Initial load
duke
parents:
diff changeset
416
a61af66fc99e Initial load
duke
parents:
diff changeset
417 // print methods
a61af66fc99e Initial load
duke
parents:
diff changeset
418 void print_packset();
a61af66fc99e Initial load
duke
parents:
diff changeset
419 void print_pack(Node_List* p);
a61af66fc99e Initial load
duke
parents:
diff changeset
420 void print_bb();
a61af66fc99e Initial load
duke
parents:
diff changeset
421 void print_stmt(Node* s);
a61af66fc99e Initial load
duke
parents:
diff changeset
422 char* blank(uint depth);
a61af66fc99e Initial load
duke
parents:
diff changeset
423 };
a61af66fc99e Initial load
duke
parents:
diff changeset
424
a61af66fc99e Initial load
duke
parents:
diff changeset
425
a61af66fc99e Initial load
duke
parents:
diff changeset
426 //------------------------------SWPointer---------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
427 // Information about an address for dependence checking and vector alignment
a61af66fc99e Initial load
duke
parents:
diff changeset
428 class SWPointer VALUE_OBJ_CLASS_SPEC {
a61af66fc99e Initial load
duke
parents:
diff changeset
429 protected:
a61af66fc99e Initial load
duke
parents:
diff changeset
430 MemNode* _mem; // My memory reference node
a61af66fc99e Initial load
duke
parents:
diff changeset
431 SuperWord* _slp; // SuperWord class
a61af66fc99e Initial load
duke
parents:
diff changeset
432
a61af66fc99e Initial load
duke
parents:
diff changeset
433 Node* _base; // NULL if unsafe nonheap reference
a61af66fc99e Initial load
duke
parents:
diff changeset
434 Node* _adr; // address pointer
a61af66fc99e Initial load
duke
parents:
diff changeset
435 jint _scale; // multipler for iv (in bytes), 0 if no loop iv
a61af66fc99e Initial load
duke
parents:
diff changeset
436 jint _offset; // constant offset (in bytes)
a61af66fc99e Initial load
duke
parents:
diff changeset
437 Node* _invar; // invariant offset (in bytes), NULL if none
a61af66fc99e Initial load
duke
parents:
diff changeset
438 bool _negate_invar; // if true then use: (0 - _invar)
a61af66fc99e Initial load
duke
parents:
diff changeset
439
a61af66fc99e Initial load
duke
parents:
diff changeset
440 PhaseIdealLoop* phase() { return _slp->phase(); }
a61af66fc99e Initial load
duke
parents:
diff changeset
441 IdealLoopTree* lpt() { return _slp->lpt(); }
a61af66fc99e Initial load
duke
parents:
diff changeset
442 PhiNode* iv() { return _slp->iv(); } // Induction var
a61af66fc99e Initial load
duke
parents:
diff changeset
443
a61af66fc99e Initial load
duke
parents:
diff changeset
444 bool invariant(Node* n) {
a61af66fc99e Initial load
duke
parents:
diff changeset
445 Node *n_c = phase()->get_ctrl(n);
a61af66fc99e Initial load
duke
parents:
diff changeset
446 return !lpt()->is_member(phase()->get_loop(n_c));
a61af66fc99e Initial load
duke
parents:
diff changeset
447 }
a61af66fc99e Initial load
duke
parents:
diff changeset
448
a61af66fc99e Initial load
duke
parents:
diff changeset
449 // Match: k*iv + offset
a61af66fc99e Initial load
duke
parents:
diff changeset
450 bool scaled_iv_plus_offset(Node* n);
a61af66fc99e Initial load
duke
parents:
diff changeset
451 // Match: k*iv where k is a constant that's not zero
a61af66fc99e Initial load
duke
parents:
diff changeset
452 bool scaled_iv(Node* n);
a61af66fc99e Initial load
duke
parents:
diff changeset
453 // Match: offset is (k [+/- invariant])
a61af66fc99e Initial load
duke
parents:
diff changeset
454 bool offset_plus_k(Node* n, bool negate = false);
a61af66fc99e Initial load
duke
parents:
diff changeset
455
a61af66fc99e Initial load
duke
parents:
diff changeset
456 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
457 enum CMP {
a61af66fc99e Initial load
duke
parents:
diff changeset
458 Less = 1,
a61af66fc99e Initial load
duke
parents:
diff changeset
459 Greater = 2,
a61af66fc99e Initial load
duke
parents:
diff changeset
460 Equal = 4,
a61af66fc99e Initial load
duke
parents:
diff changeset
461 NotEqual = (Less | Greater),
a61af66fc99e Initial load
duke
parents:
diff changeset
462 NotComparable = (Less | Greater | Equal)
a61af66fc99e Initial load
duke
parents:
diff changeset
463 };
a61af66fc99e Initial load
duke
parents:
diff changeset
464
a61af66fc99e Initial load
duke
parents:
diff changeset
465 SWPointer(MemNode* mem, SuperWord* slp);
a61af66fc99e Initial load
duke
parents:
diff changeset
466 // Following is used to create a temporary object during
a61af66fc99e Initial load
duke
parents:
diff changeset
467 // the pattern match of an address expression.
a61af66fc99e Initial load
duke
parents:
diff changeset
468 SWPointer(SWPointer* p);
a61af66fc99e Initial load
duke
parents:
diff changeset
469
a61af66fc99e Initial load
duke
parents:
diff changeset
470 bool valid() { return _adr != NULL; }
a61af66fc99e Initial load
duke
parents:
diff changeset
471 bool has_iv() { return _scale != 0; }
a61af66fc99e Initial load
duke
parents:
diff changeset
472
a61af66fc99e Initial load
duke
parents:
diff changeset
473 Node* base() { return _base; }
a61af66fc99e Initial load
duke
parents:
diff changeset
474 Node* adr() { return _adr; }
6179
8c92982cbbc4 7119644: Increase superword's vector size up to 256 bits
kvn
parents: 3842
diff changeset
475 MemNode* mem() { return _mem; }
0
a61af66fc99e Initial load
duke
parents:
diff changeset
476 int scale_in_bytes() { return _scale; }
a61af66fc99e Initial load
duke
parents:
diff changeset
477 Node* invar() { return _invar; }
a61af66fc99e Initial load
duke
parents:
diff changeset
478 bool negate_invar() { return _negate_invar; }
a61af66fc99e Initial load
duke
parents:
diff changeset
479 int offset_in_bytes() { return _offset; }
a61af66fc99e Initial load
duke
parents:
diff changeset
480 int memory_size() { return _mem->memory_size(); }
a61af66fc99e Initial load
duke
parents:
diff changeset
481
a61af66fc99e Initial load
duke
parents:
diff changeset
482 // Comparable?
a61af66fc99e Initial load
duke
parents:
diff changeset
483 int cmp(SWPointer& q) {
a61af66fc99e Initial load
duke
parents:
diff changeset
484 if (valid() && q.valid() &&
a61af66fc99e Initial load
duke
parents:
diff changeset
485 (_adr == q._adr || _base == _adr && q._base == q._adr) &&
a61af66fc99e Initial load
duke
parents:
diff changeset
486 _scale == q._scale &&
a61af66fc99e Initial load
duke
parents:
diff changeset
487 _invar == q._invar &&
a61af66fc99e Initial load
duke
parents:
diff changeset
488 _negate_invar == q._negate_invar) {
a61af66fc99e Initial load
duke
parents:
diff changeset
489 bool overlap = q._offset < _offset + memory_size() &&
a61af66fc99e Initial load
duke
parents:
diff changeset
490 _offset < q._offset + q.memory_size();
a61af66fc99e Initial load
duke
parents:
diff changeset
491 return overlap ? Equal : (_offset < q._offset ? Less : Greater);
a61af66fc99e Initial load
duke
parents:
diff changeset
492 } else {
a61af66fc99e Initial load
duke
parents:
diff changeset
493 return NotComparable;
a61af66fc99e Initial load
duke
parents:
diff changeset
494 }
a61af66fc99e Initial load
duke
parents:
diff changeset
495 }
a61af66fc99e Initial load
duke
parents:
diff changeset
496
a61af66fc99e Initial load
duke
parents:
diff changeset
497 bool not_equal(SWPointer& q) { return not_equal(cmp(q)); }
a61af66fc99e Initial load
duke
parents:
diff changeset
498 bool equal(SWPointer& q) { return equal(cmp(q)); }
a61af66fc99e Initial load
duke
parents:
diff changeset
499 bool comparable(SWPointer& q) { return comparable(cmp(q)); }
a61af66fc99e Initial load
duke
parents:
diff changeset
500 static bool not_equal(int cmp) { return cmp <= NotEqual; }
a61af66fc99e Initial load
duke
parents:
diff changeset
501 static bool equal(int cmp) { return cmp == Equal; }
a61af66fc99e Initial load
duke
parents:
diff changeset
502 static bool comparable(int cmp) { return cmp < NotComparable; }
a61af66fc99e Initial load
duke
parents:
diff changeset
503
a61af66fc99e Initial load
duke
parents:
diff changeset
504 void print();
a61af66fc99e Initial load
duke
parents:
diff changeset
505 };
a61af66fc99e Initial load
duke
parents:
diff changeset
506
a61af66fc99e Initial load
duke
parents:
diff changeset
507
a61af66fc99e Initial load
duke
parents:
diff changeset
508 //------------------------------OrderedPair---------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
509 // Ordered pair of Node*.
a61af66fc99e Initial load
duke
parents:
diff changeset
510 class OrderedPair VALUE_OBJ_CLASS_SPEC {
a61af66fc99e Initial load
duke
parents:
diff changeset
511 protected:
a61af66fc99e Initial load
duke
parents:
diff changeset
512 Node* _p1;
a61af66fc99e Initial load
duke
parents:
diff changeset
513 Node* _p2;
a61af66fc99e Initial load
duke
parents:
diff changeset
514 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
515 OrderedPair() : _p1(NULL), _p2(NULL) {}
a61af66fc99e Initial load
duke
parents:
diff changeset
516 OrderedPair(Node* p1, Node* p2) {
a61af66fc99e Initial load
duke
parents:
diff changeset
517 if (p1->_idx < p2->_idx) {
a61af66fc99e Initial load
duke
parents:
diff changeset
518 _p1 = p1; _p2 = p2;
a61af66fc99e Initial load
duke
parents:
diff changeset
519 } else {
a61af66fc99e Initial load
duke
parents:
diff changeset
520 _p1 = p2; _p2 = p1;
a61af66fc99e Initial load
duke
parents:
diff changeset
521 }
a61af66fc99e Initial load
duke
parents:
diff changeset
522 }
a61af66fc99e Initial load
duke
parents:
diff changeset
523
a61af66fc99e Initial load
duke
parents:
diff changeset
524 bool operator==(const OrderedPair &rhs) {
a61af66fc99e Initial load
duke
parents:
diff changeset
525 return _p1 == rhs._p1 && _p2 == rhs._p2;
a61af66fc99e Initial load
duke
parents:
diff changeset
526 }
a61af66fc99e Initial load
duke
parents:
diff changeset
527 void print() { tty->print(" (%d, %d)", _p1->_idx, _p2->_idx); }
a61af66fc99e Initial load
duke
parents:
diff changeset
528
a61af66fc99e Initial load
duke
parents:
diff changeset
529 static const OrderedPair initial;
a61af66fc99e Initial load
duke
parents:
diff changeset
530 };
1972
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
531
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
532 #endif // SHARE_VM_OPTO_SUPERWORD_HPP