Mercurial > hg > truffle
annotate src/share/vm/opto/subnode.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 | c59b7900a2bd |
children | c9ccd7b85f20 |
rev | line source |
---|---|
0 | 1 /* |
6842
b9a9ed0f8eeb
7197424: update copyright year to match last edit in jdk8 hotspot repository
mikael
parents:
6207
diff
changeset
|
2 * Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights reserved. |
0 | 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
4 * | |
5 * This code is free software; you can redistribute it and/or modify it | |
6 * under the terms of the GNU General Public License version 2 only, as | |
7 * published by the Free Software Foundation. | |
8 * | |
9 * This code is distributed in the hope that it will be useful, but WITHOUT | |
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | |
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | |
12 * version 2 for more details (a copy is included in the LICENSE file that | |
13 * accompanied this code). | |
14 * | |
15 * You should have received a copy of the GNU General Public License version | |
16 * 2 along with this work; if not, write to the Free Software Foundation, | |
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. | |
18 * | |
1552
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
1396
diff
changeset
|
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA |
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
1396
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:
1396
diff
changeset
|
21 * questions. |
0 | 22 * |
23 */ | |
24 | |
1972 | 25 #ifndef SHARE_VM_OPTO_SUBNODE_HPP |
26 #define SHARE_VM_OPTO_SUBNODE_HPP | |
27 | |
28 #include "opto/node.hpp" | |
29 #include "opto/opcodes.hpp" | |
30 #include "opto/type.hpp" | |
31 | |
0 | 32 // Portions of code courtesy of Clifford Click |
33 | |
34 //------------------------------SUBNode---------------------------------------- | |
35 // Class SUBTRACTION functionality. This covers all the usual 'subtract' | |
36 // behaviors. Subtract-integer, -float, -double, binary xor, compare-integer, | |
37 // -float, and -double are all inherited from this class. The compare | |
38 // functions behave like subtract functions, except that all negative answers | |
39 // are compressed into -1, and all positive answers compressed to 1. | |
40 class SubNode : public Node { | |
41 public: | |
42 SubNode( Node *in1, Node *in2 ) : Node(0,in1,in2) { | |
43 init_class_id(Class_Sub); | |
44 } | |
45 | |
46 // Handle algebraic identities here. If we have an identity, return the Node | |
47 // we are equivalent to. We look for "add of zero" as an identity. | |
48 virtual Node *Identity( PhaseTransform *phase ); | |
49 | |
50 // Compute a new Type for this node. Basically we just do the pre-check, | |
51 // then call the virtual add() to set the type. | |
52 virtual const Type *Value( PhaseTransform *phase ) const; | |
53 | |
54 // Supplied function returns the subtractend of the inputs. | |
55 // This also type-checks the inputs for sanity. Guaranteed never to | |
56 // be passed a TOP or BOTTOM type, these are filtered out by a pre-check. | |
57 virtual const Type *sub( const Type *, const Type * ) const = 0; | |
58 | |
59 // Supplied function to return the additive identity type. | |
60 // This is returned whenever the subtracts inputs are the same. | |
61 virtual const Type *add_id() const = 0; | |
62 | |
63 }; | |
64 | |
65 | |
66 // NOTE: SubINode should be taken away and replaced by add and negate | |
67 //------------------------------SubINode--------------------------------------- | |
68 // Subtract 2 integers | |
69 class SubINode : public SubNode { | |
70 public: | |
71 SubINode( Node *in1, Node *in2 ) : SubNode(in1,in2) {} | |
72 virtual int Opcode() const; | |
73 virtual Node *Ideal(PhaseGVN *phase, bool can_reshape); | |
74 virtual const Type *sub( const Type *, const Type * ) const; | |
75 const Type *add_id() const { return TypeInt::ZERO; } | |
76 const Type *bottom_type() const { return TypeInt::INT; } | |
77 virtual uint ideal_reg() const { return Op_RegI; } | |
78 }; | |
79 | |
80 //------------------------------SubLNode--------------------------------------- | |
81 // Subtract 2 integers | |
82 class SubLNode : public SubNode { | |
83 public: | |
84 SubLNode( Node *in1, Node *in2 ) : SubNode(in1,in2) {} | |
85 virtual int Opcode() const; | |
86 virtual Node *Ideal(PhaseGVN *phase, bool can_reshape); | |
87 virtual const Type *sub( const Type *, const Type * ) const; | |
88 const Type *add_id() const { return TypeLong::ZERO; } | |
89 const Type *bottom_type() const { return TypeLong::LONG; } | |
90 virtual uint ideal_reg() const { return Op_RegL; } | |
91 }; | |
92 | |
93 // NOTE: SubFPNode should be taken away and replaced by add and negate | |
94 //------------------------------SubFPNode-------------------------------------- | |
95 // Subtract 2 floats or doubles | |
96 class SubFPNode : public SubNode { | |
97 protected: | |
98 SubFPNode( Node *in1, Node *in2 ) : SubNode(in1,in2) {} | |
99 public: | |
100 const Type *Value( PhaseTransform *phase ) const; | |
101 }; | |
102 | |
103 // NOTE: SubFNode should be taken away and replaced by add and negate | |
104 //------------------------------SubFNode--------------------------------------- | |
105 // Subtract 2 doubles | |
106 class SubFNode : public SubFPNode { | |
107 public: | |
108 SubFNode( Node *in1, Node *in2 ) : SubFPNode(in1,in2) {} | |
109 virtual int Opcode() const; | |
110 virtual Node *Ideal(PhaseGVN *phase, bool can_reshape); | |
111 virtual const Type *sub( const Type *, const Type * ) const; | |
112 const Type *add_id() const { return TypeF::ZERO; } | |
113 const Type *bottom_type() const { return Type::FLOAT; } | |
114 virtual uint ideal_reg() const { return Op_RegF; } | |
115 }; | |
116 | |
117 // NOTE: SubDNode should be taken away and replaced by add and negate | |
118 //------------------------------SubDNode--------------------------------------- | |
119 // Subtract 2 doubles | |
120 class SubDNode : public SubFPNode { | |
121 public: | |
122 SubDNode( Node *in1, Node *in2 ) : SubFPNode(in1,in2) {} | |
123 virtual int Opcode() const; | |
124 virtual Node *Ideal(PhaseGVN *phase, bool can_reshape); | |
125 virtual const Type *sub( const Type *, const Type * ) const; | |
126 const Type *add_id() const { return TypeD::ZERO; } | |
127 const Type *bottom_type() const { return Type::DOUBLE; } | |
128 virtual uint ideal_reg() const { return Op_RegD; } | |
129 }; | |
130 | |
131 //------------------------------CmpNode--------------------------------------- | |
132 // Compare 2 values, returning condition codes (-1, 0 or 1). | |
133 class CmpNode : public SubNode { | |
134 public: | |
135 CmpNode( Node *in1, Node *in2 ) : SubNode(in1,in2) { | |
136 init_class_id(Class_Cmp); | |
137 } | |
138 virtual Node *Identity( PhaseTransform *phase ); | |
139 const Type *add_id() const { return TypeInt::ZERO; } | |
140 const Type *bottom_type() const { return TypeInt::CC; } | |
141 virtual uint ideal_reg() const { return Op_RegFlags; } | |
142 }; | |
143 | |
144 //------------------------------CmpINode--------------------------------------- | |
145 // Compare 2 signed values, returning condition codes (-1, 0 or 1). | |
146 class CmpINode : public CmpNode { | |
147 public: | |
148 CmpINode( Node *in1, Node *in2 ) : CmpNode(in1,in2) {} | |
149 virtual int Opcode() const; | |
150 virtual Node *Ideal(PhaseGVN *phase, bool can_reshape); | |
151 virtual const Type *sub( const Type *, const Type * ) const; | |
152 }; | |
153 | |
154 //------------------------------CmpUNode--------------------------------------- | |
155 // Compare 2 unsigned values (integer or pointer), returning condition codes (-1, 0 or 1). | |
156 class CmpUNode : public CmpNode { | |
157 public: | |
158 CmpUNode( Node *in1, Node *in2 ) : CmpNode(in1,in2) {} | |
159 virtual int Opcode() const; | |
160 virtual const Type *sub( const Type *, const Type * ) const; | |
6207
ae9241bbce4a
7181658: CTW: assert(t->meet(t0) == t) failed: Not monotonic
kvn
parents:
3338
diff
changeset
|
161 bool is_index_range_check() const; |
0 | 162 }; |
163 | |
164 //------------------------------CmpPNode--------------------------------------- | |
165 // Compare 2 pointer values, returning condition codes (-1, 0 or 1). | |
166 class CmpPNode : public CmpNode { | |
167 public: | |
168 CmpPNode( Node *in1, Node *in2 ) : CmpNode(in1,in2) {} | |
169 virtual int Opcode() const; | |
170 virtual Node *Ideal(PhaseGVN *phase, bool can_reshape); | |
171 virtual const Type *sub( const Type *, const Type * ) const; | |
172 }; | |
173 | |
113
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
174 //------------------------------CmpNNode-------------------------------------- |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
175 // Compare 2 narrow oop values, returning condition codes (-1, 0 or 1). |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
176 class CmpNNode : public CmpNode { |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
177 public: |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
178 CmpNNode( Node *in1, Node *in2 ) : CmpNode(in1,in2) {} |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
179 virtual int Opcode() const; |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
180 virtual Node *Ideal(PhaseGVN *phase, bool can_reshape); |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
181 virtual const Type *sub( const Type *, const Type * ) const; |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
182 }; |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
183 |
0 | 184 //------------------------------CmpLNode--------------------------------------- |
185 // Compare 2 long values, returning condition codes (-1, 0 or 1). | |
186 class CmpLNode : public CmpNode { | |
187 public: | |
188 CmpLNode( Node *in1, Node *in2 ) : CmpNode(in1,in2) {} | |
189 virtual int Opcode() const; | |
190 virtual const Type *sub( const Type *, const Type * ) const; | |
191 }; | |
192 | |
193 //------------------------------CmpL3Node-------------------------------------- | |
194 // Compare 2 long values, returning integer value (-1, 0 or 1). | |
195 class CmpL3Node : public CmpLNode { | |
196 public: | |
197 CmpL3Node( Node *in1, Node *in2 ) : CmpLNode(in1,in2) { | |
198 // Since it is not consumed by Bools, it is not really a Cmp. | |
199 init_class_id(Class_Sub); | |
200 } | |
201 virtual int Opcode() const; | |
202 virtual uint ideal_reg() const { return Op_RegI; } | |
203 }; | |
204 | |
205 //------------------------------CmpFNode--------------------------------------- | |
206 // Compare 2 float values, returning condition codes (-1, 0 or 1). | |
207 // This implements the Java bytecode fcmpl, so unordered returns -1. | |
208 // Operands may not commute. | |
209 class CmpFNode : public CmpNode { | |
210 public: | |
211 CmpFNode( Node *in1, Node *in2 ) : CmpNode(in1,in2) {} | |
212 virtual int Opcode() const; | |
213 virtual const Type *sub( const Type *, const Type * ) const { ShouldNotReachHere(); return NULL; } | |
214 const Type *Value( PhaseTransform *phase ) const; | |
215 }; | |
216 | |
217 //------------------------------CmpF3Node-------------------------------------- | |
218 // Compare 2 float values, returning integer value (-1, 0 or 1). | |
219 // This implements the Java bytecode fcmpl, so unordered returns -1. | |
220 // Operands may not commute. | |
221 class CmpF3Node : public CmpFNode { | |
222 public: | |
223 CmpF3Node( Node *in1, Node *in2 ) : CmpFNode(in1,in2) { | |
224 // Since it is not consumed by Bools, it is not really a Cmp. | |
225 init_class_id(Class_Sub); | |
226 } | |
227 virtual int Opcode() const; | |
228 // Since it is not consumed by Bools, it is not really a Cmp. | |
229 virtual uint ideal_reg() const { return Op_RegI; } | |
230 }; | |
231 | |
232 | |
233 //------------------------------CmpDNode--------------------------------------- | |
234 // Compare 2 double values, returning condition codes (-1, 0 or 1). | |
235 // This implements the Java bytecode dcmpl, so unordered returns -1. | |
236 // Operands may not commute. | |
237 class CmpDNode : public CmpNode { | |
238 public: | |
239 CmpDNode( Node *in1, Node *in2 ) : CmpNode(in1,in2) {} | |
240 virtual int Opcode() const; | |
241 virtual const Type *sub( const Type *, const Type * ) const { ShouldNotReachHere(); return NULL; } | |
242 const Type *Value( PhaseTransform *phase ) const; | |
243 virtual Node *Ideal(PhaseGVN *phase, bool can_reshape); | |
244 }; | |
245 | |
246 //------------------------------CmpD3Node-------------------------------------- | |
247 // Compare 2 double values, returning integer value (-1, 0 or 1). | |
248 // This implements the Java bytecode dcmpl, so unordered returns -1. | |
249 // Operands may not commute. | |
250 class CmpD3Node : public CmpDNode { | |
251 public: | |
252 CmpD3Node( Node *in1, Node *in2 ) : CmpDNode(in1,in2) { | |
253 // Since it is not consumed by Bools, it is not really a Cmp. | |
254 init_class_id(Class_Sub); | |
255 } | |
256 virtual int Opcode() const; | |
257 virtual uint ideal_reg() const { return Op_RegI; } | |
258 }; | |
259 | |
260 | |
261 //------------------------------BoolTest--------------------------------------- | |
262 // Convert condition codes to a boolean test value (0 or -1). | |
263 // We pick the values as 3 bits; the low order 2 bits we compare against the | |
264 // condition codes, the high bit flips the sense of the result. | |
265 struct BoolTest VALUE_OBJ_CLASS_SPEC { | |
266 enum mask { eq = 0, ne = 4, le = 5, ge = 7, lt = 3, gt = 1, illegal = 8 }; | |
267 mask _test; | |
268 BoolTest( mask btm ) : _test(btm) {} | |
269 const Type *cc2logical( const Type *CC ) const; | |
270 // Commute the test. I use a small table lookup. The table is created as | |
271 // a simple char array where each element is the ASCII version of a 'mask' | |
272 // enum from above. | |
273 mask commute( ) const { return mask("038147858"[_test]-'0'); } | |
274 mask negate( ) const { return mask(_test^4); } | |
275 bool is_canonical( ) const { return (_test == BoolTest::ne || _test == BoolTest::lt || _test == BoolTest::le); } | |
276 #ifndef PRODUCT | |
277 void dump_on(outputStream *st) const; | |
278 #endif | |
279 }; | |
280 | |
281 //------------------------------BoolNode--------------------------------------- | |
282 // A Node to convert a Condition Codes to a Logical result. | |
283 class BoolNode : public Node { | |
284 virtual uint hash() const; | |
285 virtual uint cmp( const Node &n ) const; | |
286 virtual uint size_of() const; | |
287 public: | |
288 const BoolTest _test; | |
289 BoolNode( Node *cc, BoolTest::mask t): _test(t), Node(0,cc) { | |
290 init_class_id(Class_Bool); | |
291 } | |
292 // Convert an arbitrary int value to a Bool or other suitable predicate. | |
293 static Node* make_predicate(Node* test_value, PhaseGVN* phase); | |
294 // Convert self back to an integer value. | |
295 Node* as_int_value(PhaseGVN* phase); | |
296 // Invert sense of self, returning new Bool. | |
297 BoolNode* negate(PhaseGVN* phase); | |
298 virtual int Opcode() const; | |
299 virtual Node *Ideal(PhaseGVN *phase, bool can_reshape); | |
300 virtual const Type *Value( PhaseTransform *phase ) const; | |
301 virtual const Type *bottom_type() const { return TypeInt::BOOL; } | |
302 uint match_edge(uint idx) const { return 0; } | |
303 virtual uint ideal_reg() const { return Op_RegI; } | |
304 | |
305 bool is_counted_loop_exit_test(); | |
306 #ifndef PRODUCT | |
307 virtual void dump_spec(outputStream *st) const; | |
308 #endif | |
309 }; | |
310 | |
311 //------------------------------AbsNode---------------------------------------- | |
312 // Abstract class for absolute value. Mostly used to get a handy wrapper | |
313 // for finding this pattern in the graph. | |
314 class AbsNode : public Node { | |
315 public: | |
316 AbsNode( Node *value ) : Node(0,value) {} | |
317 }; | |
318 | |
319 //------------------------------AbsINode--------------------------------------- | |
320 // Absolute value an integer. Since a naive graph involves control flow, we | |
321 // "match" it in the ideal world (so the control flow can be removed). | |
322 class AbsINode : public AbsNode { | |
323 public: | |
324 AbsINode( Node *in1 ) : AbsNode(in1) {} | |
325 virtual int Opcode() const; | |
326 const Type *bottom_type() const { return TypeInt::INT; } | |
327 virtual uint ideal_reg() const { return Op_RegI; } | |
328 }; | |
329 | |
330 //------------------------------AbsFNode--------------------------------------- | |
331 // Absolute value a float, a common float-point idiom with a cheap hardware | |
332 // implemention on most chips. Since a naive graph involves control flow, we | |
333 // "match" it in the ideal world (so the control flow can be removed). | |
334 class AbsFNode : public AbsNode { | |
335 public: | |
336 AbsFNode( Node *in1 ) : AbsNode(in1) {} | |
337 virtual int Opcode() const; | |
338 const Type *bottom_type() const { return Type::FLOAT; } | |
339 virtual uint ideal_reg() const { return Op_RegF; } | |
340 }; | |
341 | |
342 //------------------------------AbsDNode--------------------------------------- | |
343 // Absolute value a double, a common float-point idiom with a cheap hardware | |
344 // implemention on most chips. Since a naive graph involves control flow, we | |
345 // "match" it in the ideal world (so the control flow can be removed). | |
346 class AbsDNode : public AbsNode { | |
347 public: | |
348 AbsDNode( Node *in1 ) : AbsNode(in1) {} | |
349 virtual int Opcode() const; | |
350 const Type *bottom_type() const { return Type::DOUBLE; } | |
351 virtual uint ideal_reg() const { return Op_RegD; } | |
352 }; | |
353 | |
354 | |
355 //------------------------------CmpLTMaskNode---------------------------------- | |
356 // If p < q, return -1 else return 0. Nice for flow-free idioms. | |
357 class CmpLTMaskNode : public Node { | |
358 public: | |
359 CmpLTMaskNode( Node *p, Node *q ) : Node(0, p, q) {} | |
360 virtual int Opcode() const; | |
361 const Type *bottom_type() const { return TypeInt::INT; } | |
362 virtual uint ideal_reg() const { return Op_RegI; } | |
363 }; | |
364 | |
365 | |
366 //------------------------------NegNode---------------------------------------- | |
367 class NegNode : public Node { | |
368 public: | |
369 NegNode( Node *in1 ) : Node(0,in1) {} | |
370 }; | |
371 | |
372 //------------------------------NegFNode--------------------------------------- | |
373 // Negate value a float. Negating 0.0 returns -0.0, but subtracting from | |
374 // zero returns +0.0 (per JVM spec on 'fneg' bytecode). As subtraction | |
375 // cannot be used to replace negation we have to implement negation as ideal | |
376 // node; note that negation and addition can replace subtraction. | |
377 class NegFNode : public NegNode { | |
378 public: | |
379 NegFNode( Node *in1 ) : NegNode(in1) {} | |
380 virtual int Opcode() const; | |
381 const Type *bottom_type() const { return Type::FLOAT; } | |
382 virtual uint ideal_reg() const { return Op_RegF; } | |
383 }; | |
384 | |
385 //------------------------------NegDNode--------------------------------------- | |
386 // Negate value a double. Negating 0.0 returns -0.0, but subtracting from | |
387 // zero returns +0.0 (per JVM spec on 'dneg' bytecode). As subtraction | |
388 // cannot be used to replace negation we have to implement negation as ideal | |
389 // node; note that negation and addition can replace subtraction. | |
390 class NegDNode : public NegNode { | |
391 public: | |
392 NegDNode( Node *in1 ) : NegNode(in1) {} | |
393 virtual int Opcode() const; | |
394 const Type *bottom_type() const { return Type::DOUBLE; } | |
395 virtual uint ideal_reg() const { return Op_RegD; } | |
396 }; | |
397 | |
398 //------------------------------CosDNode--------------------------------------- | |
399 // Cosinus of a double | |
400 class CosDNode : public Node { | |
401 public: | |
8076
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
402 CosDNode(Compile* C, Node *c, Node *in1) : Node(c, in1) { |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
403 init_flags(Flag_is_expensive); |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
404 C->add_expensive_node(this); |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
405 } |
0 | 406 virtual int Opcode() const; |
407 const Type *bottom_type() const { return Type::DOUBLE; } | |
408 virtual uint ideal_reg() const { return Op_RegD; } | |
409 virtual const Type *Value( PhaseTransform *phase ) const; | |
410 }; | |
411 | |
412 //------------------------------CosDNode--------------------------------------- | |
413 // Sinus of a double | |
414 class SinDNode : public Node { | |
415 public: | |
8076
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
416 SinDNode(Compile* C, Node *c, Node *in1) : Node(c, in1) { |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
417 init_flags(Flag_is_expensive); |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
418 C->add_expensive_node(this); |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
419 } |
0 | 420 virtual int Opcode() const; |
421 const Type *bottom_type() const { return Type::DOUBLE; } | |
422 virtual uint ideal_reg() const { return Op_RegD; } | |
423 virtual const Type *Value( PhaseTransform *phase ) const; | |
424 }; | |
425 | |
426 | |
427 //------------------------------TanDNode--------------------------------------- | |
428 // tangens of a double | |
429 class TanDNode : public Node { | |
430 public: | |
8076
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
431 TanDNode(Compile* C, Node *c,Node *in1) : Node(c, in1) { |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
432 init_flags(Flag_is_expensive); |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
433 C->add_expensive_node(this); |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
434 } |
0 | 435 virtual int Opcode() const; |
436 const Type *bottom_type() const { return Type::DOUBLE; } | |
437 virtual uint ideal_reg() const { return Op_RegD; } | |
438 virtual const Type *Value( PhaseTransform *phase ) const; | |
439 }; | |
440 | |
441 | |
442 //------------------------------AtanDNode-------------------------------------- | |
443 // arcus tangens of a double | |
444 class AtanDNode : public Node { | |
445 public: | |
446 AtanDNode(Node *c, Node *in1, Node *in2 ) : Node(c, in1, in2) {} | |
447 virtual int Opcode() const; | |
448 const Type *bottom_type() const { return Type::DOUBLE; } | |
449 virtual uint ideal_reg() const { return Op_RegD; } | |
450 }; | |
451 | |
452 | |
453 //------------------------------SqrtDNode-------------------------------------- | |
454 // square root a double | |
455 class SqrtDNode : public Node { | |
456 public: | |
8076
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
457 SqrtDNode(Compile* C, Node *c, Node *in1) : Node(c, in1) { |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
458 init_flags(Flag_is_expensive); |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
459 C->add_expensive_node(this); |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
460 } |
0 | 461 virtual int Opcode() const; |
462 const Type *bottom_type() const { return Type::DOUBLE; } | |
463 virtual uint ideal_reg() const { return Op_RegD; } | |
464 virtual const Type *Value( PhaseTransform *phase ) const; | |
465 }; | |
466 | |
467 //------------------------------ExpDNode--------------------------------------- | |
468 // Exponentiate a double | |
469 class ExpDNode : public Node { | |
470 public: | |
8048
8b3da8d14c93
7197327: 40% regression on 8 b41 comp 8 b40 on specjvm2008.mpegaudio on oob
roland
parents:
6842
diff
changeset
|
471 ExpDNode(Compile* C, Node *c, Node *in1) : Node(c, in1) { |
8b3da8d14c93
7197327: 40% regression on 8 b41 comp 8 b40 on specjvm2008.mpegaudio on oob
roland
parents:
6842
diff
changeset
|
472 init_flags(Flag_is_expensive); |
8b3da8d14c93
7197327: 40% regression on 8 b41 comp 8 b40 on specjvm2008.mpegaudio on oob
roland
parents:
6842
diff
changeset
|
473 C->add_expensive_node(this); |
8b3da8d14c93
7197327: 40% regression on 8 b41 comp 8 b40 on specjvm2008.mpegaudio on oob
roland
parents:
6842
diff
changeset
|
474 } |
0 | 475 virtual int Opcode() const; |
476 const Type *bottom_type() const { return Type::DOUBLE; } | |
477 virtual uint ideal_reg() const { return Op_RegD; } | |
478 virtual const Type *Value( PhaseTransform *phase ) const; | |
479 }; | |
480 | |
481 //------------------------------LogDNode--------------------------------------- | |
482 // Log_e of a double | |
483 class LogDNode : public Node { | |
484 public: | |
8076
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
485 LogDNode(Compile* C, Node *c, Node *in1) : Node(c, in1) { |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
486 init_flags(Flag_is_expensive); |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
487 C->add_expensive_node(this); |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
488 } |
0 | 489 virtual int Opcode() const; |
490 const Type *bottom_type() const { return Type::DOUBLE; } | |
491 virtual uint ideal_reg() const { return Op_RegD; } | |
492 virtual const Type *Value( PhaseTransform *phase ) const; | |
493 }; | |
494 | |
495 //------------------------------Log10DNode--------------------------------------- | |
496 // Log_10 of a double | |
497 class Log10DNode : public Node { | |
498 public: | |
8076
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
499 Log10DNode(Compile* C, Node *c, Node *in1) : Node(c, in1) { |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
500 init_flags(Flag_is_expensive); |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
501 C->add_expensive_node(this); |
c59b7900a2bd
8007959: Use expensive node logic for more math nodes
roland
parents:
8048
diff
changeset
|
502 } |
0 | 503 virtual int Opcode() const; |
504 const Type *bottom_type() const { return Type::DOUBLE; } | |
505 virtual uint ideal_reg() const { return Op_RegD; } | |
506 virtual const Type *Value( PhaseTransform *phase ) const; | |
507 }; | |
508 | |
509 //------------------------------PowDNode--------------------------------------- | |
510 // Raise a double to a double power | |
511 class PowDNode : public Node { | |
512 public: | |
8048
8b3da8d14c93
7197327: 40% regression on 8 b41 comp 8 b40 on specjvm2008.mpegaudio on oob
roland
parents:
6842
diff
changeset
|
513 PowDNode(Compile* C, Node *c, Node *in1, Node *in2 ) : Node(c, in1, in2) { |
8b3da8d14c93
7197327: 40% regression on 8 b41 comp 8 b40 on specjvm2008.mpegaudio on oob
roland
parents:
6842
diff
changeset
|
514 init_flags(Flag_is_expensive); |
8b3da8d14c93
7197327: 40% regression on 8 b41 comp 8 b40 on specjvm2008.mpegaudio on oob
roland
parents:
6842
diff
changeset
|
515 C->add_expensive_node(this); |
8b3da8d14c93
7197327: 40% regression on 8 b41 comp 8 b40 on specjvm2008.mpegaudio on oob
roland
parents:
6842
diff
changeset
|
516 } |
0 | 517 virtual int Opcode() const; |
518 const Type *bottom_type() const { return Type::DOUBLE; } | |
519 virtual uint ideal_reg() const { return Op_RegD; } | |
520 virtual const Type *Value( PhaseTransform *phase ) const; | |
521 }; | |
522 | |
523 //-------------------------------ReverseBytesINode-------------------------------- | |
524 // reverse bytes of an integer | |
525 class ReverseBytesINode : public Node { | |
526 public: | |
527 ReverseBytesINode(Node *c, Node *in1) : Node(c, in1) {} | |
528 virtual int Opcode() const; | |
529 const Type *bottom_type() const { return TypeInt::INT; } | |
530 virtual uint ideal_reg() const { return Op_RegI; } | |
531 }; | |
532 | |
533 //-------------------------------ReverseBytesLNode-------------------------------- | |
534 // reverse bytes of a long | |
535 class ReverseBytesLNode : public Node { | |
536 public: | |
537 ReverseBytesLNode(Node *c, Node *in1) : Node(c, in1) {} | |
538 virtual int Opcode() const; | |
539 const Type *bottom_type() const { return TypeLong::LONG; } | |
540 virtual uint ideal_reg() const { return Op_RegL; } | |
541 }; | |
1396
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
542 |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
543 //-------------------------------ReverseBytesUSNode-------------------------------- |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
544 // reverse bytes of an unsigned short / char |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
545 class ReverseBytesUSNode : public Node { |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
546 public: |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
547 ReverseBytesUSNode(Node *c, Node *in1) : Node(c, in1) {} |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
548 virtual int Opcode() const; |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
549 const Type *bottom_type() const { return TypeInt::CHAR; } |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
550 virtual uint ideal_reg() const { return Op_RegI; } |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
551 }; |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
552 |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
553 //-------------------------------ReverseBytesSNode-------------------------------- |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
554 // reverse bytes of a short |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
555 class ReverseBytesSNode : public Node { |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
556 public: |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
557 ReverseBytesSNode(Node *c, Node *in1) : Node(c, in1) {} |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
558 virtual int Opcode() const; |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
559 const Type *bottom_type() const { return TypeInt::SHORT; } |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
560 virtual uint ideal_reg() const { return Op_RegI; } |
d7f654633cfe
6946040: add intrinsic for short and char reverseBytes
never
parents:
196
diff
changeset
|
561 }; |
1972 | 562 |
563 #endif // SHARE_VM_OPTO_SUBNODE_HPP |