annotate src/share/vm/opto/subnode.cpp @ 1994:6cd6d394f280

7001033: assert(gch->gc_cause() == GCCause::_scavenge_alot || !gch->incremental_collection_failed()) 7002546: regression on SpecJbb2005 on 7b118 comparing to 7b117 on small heaps Summary: Relaxed assertion checking related to incremental_collection_failed flag to allow for ExplicitGCInvokesConcurrent behaviour where we do not want a failing scavenge to bail to a stop-world collection. Parameterized incremental_collection_will_fail() so we can selectively use, or not use, as appropriate, the statistical prediction at specific use sites. This essentially reverts the scavenge bail-out logic to what it was prior to some recent changes that had inadvertently started using the statistical prediction which can be noisy in the presence of bursty loads. Added some associated verbose non-product debugging messages. Reviewed-by: johnc, tonyp
author ysr
date Tue, 07 Dec 2010 21:55:53 -0800
parents f95d63e2154a
children f1d6640088a1
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
a61af66fc99e Initial load
duke
parents:
diff changeset
1 /*
1552
c18cbe5936b8 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 1174
diff changeset
2 * Copyright (c) 1997, 2010, 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: 1174
diff changeset
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
c18cbe5936b8 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 1174
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: 1174
diff changeset
21 * questions.
0
a61af66fc99e Initial load
duke
parents:
diff changeset
22 *
a61af66fc99e Initial load
duke
parents:
diff changeset
23 */
a61af66fc99e Initial load
duke
parents:
diff changeset
24
1972
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
25 #include "precompiled.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
26 #include "compiler/compileLog.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
27 #include "memory/allocation.inline.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
28 #include "opto/addnode.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
29 #include "opto/callnode.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
30 #include "opto/cfgnode.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
31 #include "opto/connode.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
32 #include "opto/loopnode.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
33 #include "opto/matcher.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
34 #include "opto/mulnode.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
35 #include "opto/opcodes.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
36 #include "opto/phaseX.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
37 #include "opto/subnode.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
38 #include "runtime/sharedRuntime.hpp"
f95d63e2154a 6989984: Use standard include model for Hospot
stefank
parents: 1552
diff changeset
39
0
a61af66fc99e Initial load
duke
parents:
diff changeset
40 // Portions of code courtesy of Clifford Click
a61af66fc99e Initial load
duke
parents:
diff changeset
41
a61af66fc99e Initial load
duke
parents:
diff changeset
42 // Optimization - Graph Style
a61af66fc99e Initial load
duke
parents:
diff changeset
43
a61af66fc99e Initial load
duke
parents:
diff changeset
44 #include "math.h"
a61af66fc99e Initial load
duke
parents:
diff changeset
45
a61af66fc99e Initial load
duke
parents:
diff changeset
46 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
47 //------------------------------Identity---------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
48 // If right input is a constant 0, return the left input.
a61af66fc99e Initial load
duke
parents:
diff changeset
49 Node *SubNode::Identity( PhaseTransform *phase ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
50 assert(in(1) != this, "Must already have called Value");
a61af66fc99e Initial load
duke
parents:
diff changeset
51 assert(in(2) != this, "Must already have called Value");
a61af66fc99e Initial load
duke
parents:
diff changeset
52
a61af66fc99e Initial load
duke
parents:
diff changeset
53 // Remove double negation
a61af66fc99e Initial load
duke
parents:
diff changeset
54 const Type *zero = add_id();
a61af66fc99e Initial load
duke
parents:
diff changeset
55 if( phase->type( in(1) )->higher_equal( zero ) &&
a61af66fc99e Initial load
duke
parents:
diff changeset
56 in(2)->Opcode() == Opcode() &&
a61af66fc99e Initial load
duke
parents:
diff changeset
57 phase->type( in(2)->in(1) )->higher_equal( zero ) ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
58 return in(2)->in(2);
a61af66fc99e Initial load
duke
parents:
diff changeset
59 }
a61af66fc99e Initial load
duke
parents:
diff changeset
60
212
99bf1609e2a5 6697236: missing Identity for "(X+Y) - X" into Y
never
parents: 113
diff changeset
61 // Convert "(X+Y) - Y" into X and "(X+Y) - X" into Y
0
a61af66fc99e Initial load
duke
parents:
diff changeset
62 if( in(1)->Opcode() == Op_AddI ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
63 if( phase->eqv(in(1)->in(2),in(2)) )
a61af66fc99e Initial load
duke
parents:
diff changeset
64 return in(1)->in(1);
212
99bf1609e2a5 6697236: missing Identity for "(X+Y) - X" into Y
never
parents: 113
diff changeset
65 if (phase->eqv(in(1)->in(1),in(2)))
99bf1609e2a5 6697236: missing Identity for "(X+Y) - X" into Y
never
parents: 113
diff changeset
66 return in(1)->in(2);
99bf1609e2a5 6697236: missing Identity for "(X+Y) - X" into Y
never
parents: 113
diff changeset
67
0
a61af66fc99e Initial load
duke
parents:
diff changeset
68 // Also catch: "(X + Opaque2(Y)) - Y". In this case, 'Y' is a loop-varying
a61af66fc99e Initial load
duke
parents:
diff changeset
69 // trip counter and X is likely to be loop-invariant (that's how O2 Nodes
a61af66fc99e Initial load
duke
parents:
diff changeset
70 // are originally used, although the optimizer sometimes jiggers things).
a61af66fc99e Initial load
duke
parents:
diff changeset
71 // This folding through an O2 removes a loop-exit use of a loop-varying
a61af66fc99e Initial load
duke
parents:
diff changeset
72 // value and generally lowers register pressure in and around the loop.
a61af66fc99e Initial load
duke
parents:
diff changeset
73 if( in(1)->in(2)->Opcode() == Op_Opaque2 &&
a61af66fc99e Initial load
duke
parents:
diff changeset
74 phase->eqv(in(1)->in(2)->in(1),in(2)) )
a61af66fc99e Initial load
duke
parents:
diff changeset
75 return in(1)->in(1);
a61af66fc99e Initial load
duke
parents:
diff changeset
76 }
a61af66fc99e Initial load
duke
parents:
diff changeset
77
a61af66fc99e Initial load
duke
parents:
diff changeset
78 return ( phase->type( in(2) )->higher_equal( zero ) ) ? in(1) : this;
a61af66fc99e Initial load
duke
parents:
diff changeset
79 }
a61af66fc99e Initial load
duke
parents:
diff changeset
80
a61af66fc99e Initial load
duke
parents:
diff changeset
81 //------------------------------Value------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
82 // A subtract node differences it's two inputs.
a61af66fc99e Initial load
duke
parents:
diff changeset
83 const Type *SubNode::Value( PhaseTransform *phase ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
84 const Node* in1 = in(1);
a61af66fc99e Initial load
duke
parents:
diff changeset
85 const Node* in2 = in(2);
a61af66fc99e Initial load
duke
parents:
diff changeset
86 // Either input is TOP ==> the result is TOP
a61af66fc99e Initial load
duke
parents:
diff changeset
87 const Type* t1 = (in1 == this) ? Type::TOP : phase->type(in1);
a61af66fc99e Initial load
duke
parents:
diff changeset
88 if( t1 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
89 const Type* t2 = (in2 == this) ? Type::TOP : phase->type(in2);
a61af66fc99e Initial load
duke
parents:
diff changeset
90 if( t2 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
91
a61af66fc99e Initial load
duke
parents:
diff changeset
92 // Not correct for SubFnode and AddFNode (must check for infinity)
a61af66fc99e Initial load
duke
parents:
diff changeset
93 // Equal? Subtract is zero
a61af66fc99e Initial load
duke
parents:
diff changeset
94 if (phase->eqv_uncast(in1, in2)) return add_id();
a61af66fc99e Initial load
duke
parents:
diff changeset
95
a61af66fc99e Initial load
duke
parents:
diff changeset
96 // Either input is BOTTOM ==> the result is the local BOTTOM
a61af66fc99e Initial load
duke
parents:
diff changeset
97 if( t1 == Type::BOTTOM || t2 == Type::BOTTOM )
a61af66fc99e Initial load
duke
parents:
diff changeset
98 return bottom_type();
a61af66fc99e Initial load
duke
parents:
diff changeset
99
a61af66fc99e Initial load
duke
parents:
diff changeset
100 return sub(t1,t2); // Local flavor of type subtraction
a61af66fc99e Initial load
duke
parents:
diff changeset
101
a61af66fc99e Initial load
duke
parents:
diff changeset
102 }
a61af66fc99e Initial load
duke
parents:
diff changeset
103
a61af66fc99e Initial load
duke
parents:
diff changeset
104 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
105
a61af66fc99e Initial load
duke
parents:
diff changeset
106 //------------------------------Helper function--------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
107 static bool ok_to_convert(Node* inc, Node* iv) {
a61af66fc99e Initial load
duke
parents:
diff changeset
108 // Do not collapse (x+c0)-y if "+" is a loop increment, because the
a61af66fc99e Initial load
duke
parents:
diff changeset
109 // "-" is loop invariant and collapsing extends the live-range of "x"
a61af66fc99e Initial load
duke
parents:
diff changeset
110 // to overlap with the "+", forcing another register to be used in
a61af66fc99e Initial load
duke
parents:
diff changeset
111 // the loop.
a61af66fc99e Initial load
duke
parents:
diff changeset
112 // This test will be clearer with '&&' (apply DeMorgan's rule)
a61af66fc99e Initial load
duke
parents:
diff changeset
113 // but I like the early cutouts that happen here.
a61af66fc99e Initial load
duke
parents:
diff changeset
114 const PhiNode *phi;
a61af66fc99e Initial load
duke
parents:
diff changeset
115 if( ( !inc->in(1)->is_Phi() ||
a61af66fc99e Initial load
duke
parents:
diff changeset
116 !(phi=inc->in(1)->as_Phi()) ||
a61af66fc99e Initial load
duke
parents:
diff changeset
117 phi->is_copy() ||
a61af66fc99e Initial load
duke
parents:
diff changeset
118 !phi->region()->is_CountedLoop() ||
a61af66fc99e Initial load
duke
parents:
diff changeset
119 inc != phi->region()->as_CountedLoop()->incr() )
a61af66fc99e Initial load
duke
parents:
diff changeset
120 &&
a61af66fc99e Initial load
duke
parents:
diff changeset
121 // Do not collapse (x+c0)-iv if "iv" is a loop induction variable,
a61af66fc99e Initial load
duke
parents:
diff changeset
122 // because "x" maybe invariant.
a61af66fc99e Initial load
duke
parents:
diff changeset
123 ( !iv->is_loop_iv() )
a61af66fc99e Initial load
duke
parents:
diff changeset
124 ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
125 return true;
a61af66fc99e Initial load
duke
parents:
diff changeset
126 } else {
a61af66fc99e Initial load
duke
parents:
diff changeset
127 return false;
a61af66fc99e Initial load
duke
parents:
diff changeset
128 }
a61af66fc99e Initial load
duke
parents:
diff changeset
129 }
a61af66fc99e Initial load
duke
parents:
diff changeset
130 //------------------------------Ideal------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
131 Node *SubINode::Ideal(PhaseGVN *phase, bool can_reshape){
a61af66fc99e Initial load
duke
parents:
diff changeset
132 Node *in1 = in(1);
a61af66fc99e Initial load
duke
parents:
diff changeset
133 Node *in2 = in(2);
a61af66fc99e Initial load
duke
parents:
diff changeset
134 uint op1 = in1->Opcode();
a61af66fc99e Initial load
duke
parents:
diff changeset
135 uint op2 = in2->Opcode();
a61af66fc99e Initial load
duke
parents:
diff changeset
136
a61af66fc99e Initial load
duke
parents:
diff changeset
137 #ifdef ASSERT
a61af66fc99e Initial load
duke
parents:
diff changeset
138 // Check for dead loop
a61af66fc99e Initial load
duke
parents:
diff changeset
139 if( phase->eqv( in1, this ) || phase->eqv( in2, this ) ||
a61af66fc99e Initial load
duke
parents:
diff changeset
140 ( op1 == Op_AddI || op1 == Op_SubI ) &&
a61af66fc99e Initial load
duke
parents:
diff changeset
141 ( phase->eqv( in1->in(1), this ) || phase->eqv( in1->in(2), this ) ||
a61af66fc99e Initial load
duke
parents:
diff changeset
142 phase->eqv( in1->in(1), in1 ) || phase->eqv( in1->in(2), in1 ) ) )
a61af66fc99e Initial load
duke
parents:
diff changeset
143 assert(false, "dead loop in SubINode::Ideal");
a61af66fc99e Initial load
duke
parents:
diff changeset
144 #endif
a61af66fc99e Initial load
duke
parents:
diff changeset
145
a61af66fc99e Initial load
duke
parents:
diff changeset
146 const Type *t2 = phase->type( in2 );
a61af66fc99e Initial load
duke
parents:
diff changeset
147 if( t2 == Type::TOP ) return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
148 // Convert "x-c0" into "x+ -c0".
a61af66fc99e Initial load
duke
parents:
diff changeset
149 if( t2->base() == Type::Int ){ // Might be bottom or top...
a61af66fc99e Initial load
duke
parents:
diff changeset
150 const TypeInt *i = t2->is_int();
a61af66fc99e Initial load
duke
parents:
diff changeset
151 if( i->is_con() )
a61af66fc99e Initial load
duke
parents:
diff changeset
152 return new (phase->C, 3) AddINode(in1, phase->intcon(-i->get_con()));
a61af66fc99e Initial load
duke
parents:
diff changeset
153 }
a61af66fc99e Initial load
duke
parents:
diff changeset
154
a61af66fc99e Initial load
duke
parents:
diff changeset
155 // Convert "(x+c0) - y" into (x-y) + c0"
a61af66fc99e Initial load
duke
parents:
diff changeset
156 // Do not collapse (x+c0)-y if "+" is a loop increment or
a61af66fc99e Initial load
duke
parents:
diff changeset
157 // if "y" is a loop induction variable.
a61af66fc99e Initial load
duke
parents:
diff changeset
158 if( op1 == Op_AddI && ok_to_convert(in1, in2) ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
159 const Type *tadd = phase->type( in1->in(2) );
a61af66fc99e Initial load
duke
parents:
diff changeset
160 if( tadd->singleton() && tadd != Type::TOP ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
161 Node *sub2 = phase->transform( new (phase->C, 3) SubINode( in1->in(1), in2 ));
a61af66fc99e Initial load
duke
parents:
diff changeset
162 return new (phase->C, 3) AddINode( sub2, in1->in(2) );
a61af66fc99e Initial load
duke
parents:
diff changeset
163 }
a61af66fc99e Initial load
duke
parents:
diff changeset
164 }
a61af66fc99e Initial load
duke
parents:
diff changeset
165
a61af66fc99e Initial load
duke
parents:
diff changeset
166
a61af66fc99e Initial load
duke
parents:
diff changeset
167 // Convert "x - (y+c0)" into "(x-y) - c0"
a61af66fc99e Initial load
duke
parents:
diff changeset
168 // Need the same check as in above optimization but reversed.
a61af66fc99e Initial load
duke
parents:
diff changeset
169 if (op2 == Op_AddI && ok_to_convert(in2, in1)) {
a61af66fc99e Initial load
duke
parents:
diff changeset
170 Node* in21 = in2->in(1);
a61af66fc99e Initial load
duke
parents:
diff changeset
171 Node* in22 = in2->in(2);
a61af66fc99e Initial load
duke
parents:
diff changeset
172 const TypeInt* tcon = phase->type(in22)->isa_int();
a61af66fc99e Initial load
duke
parents:
diff changeset
173 if (tcon != NULL && tcon->is_con()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
174 Node* sub2 = phase->transform( new (phase->C, 3) SubINode(in1, in21) );
a61af66fc99e Initial load
duke
parents:
diff changeset
175 Node* neg_c0 = phase->intcon(- tcon->get_con());
a61af66fc99e Initial load
duke
parents:
diff changeset
176 return new (phase->C, 3) AddINode(sub2, neg_c0);
a61af66fc99e Initial load
duke
parents:
diff changeset
177 }
a61af66fc99e Initial load
duke
parents:
diff changeset
178 }
a61af66fc99e Initial load
duke
parents:
diff changeset
179
a61af66fc99e Initial load
duke
parents:
diff changeset
180 const Type *t1 = phase->type( in1 );
a61af66fc99e Initial load
duke
parents:
diff changeset
181 if( t1 == Type::TOP ) return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
182
a61af66fc99e Initial load
duke
parents:
diff changeset
183 #ifdef ASSERT
a61af66fc99e Initial load
duke
parents:
diff changeset
184 // Check for dead loop
a61af66fc99e Initial load
duke
parents:
diff changeset
185 if( ( op2 == Op_AddI || op2 == Op_SubI ) &&
a61af66fc99e Initial load
duke
parents:
diff changeset
186 ( phase->eqv( in2->in(1), this ) || phase->eqv( in2->in(2), this ) ||
a61af66fc99e Initial load
duke
parents:
diff changeset
187 phase->eqv( in2->in(1), in2 ) || phase->eqv( in2->in(2), in2 ) ) )
a61af66fc99e Initial load
duke
parents:
diff changeset
188 assert(false, "dead loop in SubINode::Ideal");
a61af66fc99e Initial load
duke
parents:
diff changeset
189 #endif
a61af66fc99e Initial load
duke
parents:
diff changeset
190
a61af66fc99e Initial load
duke
parents:
diff changeset
191 // Convert "x - (x+y)" into "-y"
a61af66fc99e Initial load
duke
parents:
diff changeset
192 if( op2 == Op_AddI &&
a61af66fc99e Initial load
duke
parents:
diff changeset
193 phase->eqv( in1, in2->in(1) ) )
a61af66fc99e Initial load
duke
parents:
diff changeset
194 return new (phase->C, 3) SubINode( phase->intcon(0),in2->in(2));
a61af66fc99e Initial load
duke
parents:
diff changeset
195 // Convert "(x-y) - x" into "-y"
a61af66fc99e Initial load
duke
parents:
diff changeset
196 if( op1 == Op_SubI &&
a61af66fc99e Initial load
duke
parents:
diff changeset
197 phase->eqv( in1->in(1), in2 ) )
a61af66fc99e Initial load
duke
parents:
diff changeset
198 return new (phase->C, 3) SubINode( phase->intcon(0),in1->in(2));
a61af66fc99e Initial load
duke
parents:
diff changeset
199 // Convert "x - (y+x)" into "-y"
a61af66fc99e Initial load
duke
parents:
diff changeset
200 if( op2 == Op_AddI &&
a61af66fc99e Initial load
duke
parents:
diff changeset
201 phase->eqv( in1, in2->in(2) ) )
a61af66fc99e Initial load
duke
parents:
diff changeset
202 return new (phase->C, 3) SubINode( phase->intcon(0),in2->in(1));
a61af66fc99e Initial load
duke
parents:
diff changeset
203
a61af66fc99e Initial load
duke
parents:
diff changeset
204 // Convert "0 - (x-y)" into "y-x"
a61af66fc99e Initial load
duke
parents:
diff changeset
205 if( t1 == TypeInt::ZERO && op2 == Op_SubI )
a61af66fc99e Initial load
duke
parents:
diff changeset
206 return new (phase->C, 3) SubINode( in2->in(2), in2->in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
207
a61af66fc99e Initial load
duke
parents:
diff changeset
208 // Convert "0 - (x+con)" into "-con-x"
a61af66fc99e Initial load
duke
parents:
diff changeset
209 jint con;
a61af66fc99e Initial load
duke
parents:
diff changeset
210 if( t1 == TypeInt::ZERO && op2 == Op_AddI &&
a61af66fc99e Initial load
duke
parents:
diff changeset
211 (con = in2->in(2)->find_int_con(0)) != 0 )
a61af66fc99e Initial load
duke
parents:
diff changeset
212 return new (phase->C, 3) SubINode( phase->intcon(-con), in2->in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
213
a61af66fc99e Initial load
duke
parents:
diff changeset
214 // Convert "(X+A) - (X+B)" into "A - B"
a61af66fc99e Initial load
duke
parents:
diff changeset
215 if( op1 == Op_AddI && op2 == Op_AddI && in1->in(1) == in2->in(1) )
a61af66fc99e Initial load
duke
parents:
diff changeset
216 return new (phase->C, 3) SubINode( in1->in(2), in2->in(2) );
a61af66fc99e Initial load
duke
parents:
diff changeset
217
a61af66fc99e Initial load
duke
parents:
diff changeset
218 // Convert "(A+X) - (B+X)" into "A - B"
a61af66fc99e Initial load
duke
parents:
diff changeset
219 if( op1 == Op_AddI && op2 == Op_AddI && in1->in(2) == in2->in(2) )
a61af66fc99e Initial load
duke
parents:
diff changeset
220 return new (phase->C, 3) SubINode( in1->in(1), in2->in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
221
400
cc80376deb0c 6667595: Set probability FAIR for pre-, post- loops and ALWAYS for main loop
kvn
parents: 296
diff changeset
222 // Convert "(A+X) - (X+B)" into "A - B"
cc80376deb0c 6667595: Set probability FAIR for pre-, post- loops and ALWAYS for main loop
kvn
parents: 296
diff changeset
223 if( op1 == Op_AddI && op2 == Op_AddI && in1->in(2) == in2->in(1) )
cc80376deb0c 6667595: Set probability FAIR for pre-, post- loops and ALWAYS for main loop
kvn
parents: 296
diff changeset
224 return new (phase->C, 3) SubINode( in1->in(1), in2->in(2) );
cc80376deb0c 6667595: Set probability FAIR for pre-, post- loops and ALWAYS for main loop
kvn
parents: 296
diff changeset
225
cc80376deb0c 6667595: Set probability FAIR for pre-, post- loops and ALWAYS for main loop
kvn
parents: 296
diff changeset
226 // Convert "(X+A) - (B+X)" into "A - B"
cc80376deb0c 6667595: Set probability FAIR for pre-, post- loops and ALWAYS for main loop
kvn
parents: 296
diff changeset
227 if( op1 == Op_AddI && op2 == Op_AddI && in1->in(1) == in2->in(2) )
cc80376deb0c 6667595: Set probability FAIR for pre-, post- loops and ALWAYS for main loop
kvn
parents: 296
diff changeset
228 return new (phase->C, 3) SubINode( in1->in(2), in2->in(1) );
cc80376deb0c 6667595: Set probability FAIR for pre-, post- loops and ALWAYS for main loop
kvn
parents: 296
diff changeset
229
0
a61af66fc99e Initial load
duke
parents:
diff changeset
230 // Convert "A-(B-C)" into (A+C)-B", since add is commutative and generally
a61af66fc99e Initial load
duke
parents:
diff changeset
231 // nicer to optimize than subtract.
a61af66fc99e Initial load
duke
parents:
diff changeset
232 if( op2 == Op_SubI && in2->outcnt() == 1) {
a61af66fc99e Initial load
duke
parents:
diff changeset
233 Node *add1 = phase->transform( new (phase->C, 3) AddINode( in1, in2->in(2) ) );
a61af66fc99e Initial load
duke
parents:
diff changeset
234 return new (phase->C, 3) SubINode( add1, in2->in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
235 }
a61af66fc99e Initial load
duke
parents:
diff changeset
236
a61af66fc99e Initial load
duke
parents:
diff changeset
237 return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
238 }
a61af66fc99e Initial load
duke
parents:
diff changeset
239
a61af66fc99e Initial load
duke
parents:
diff changeset
240 //------------------------------sub--------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
241 // A subtract node differences it's two inputs.
a61af66fc99e Initial load
duke
parents:
diff changeset
242 const Type *SubINode::sub( const Type *t1, const Type *t2 ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
243 const TypeInt *r0 = t1->is_int(); // Handy access
a61af66fc99e Initial load
duke
parents:
diff changeset
244 const TypeInt *r1 = t2->is_int();
a61af66fc99e Initial load
duke
parents:
diff changeset
245 int32 lo = r0->_lo - r1->_hi;
a61af66fc99e Initial load
duke
parents:
diff changeset
246 int32 hi = r0->_hi - r1->_lo;
a61af66fc99e Initial load
duke
parents:
diff changeset
247
a61af66fc99e Initial load
duke
parents:
diff changeset
248 // We next check for 32-bit overflow.
a61af66fc99e Initial load
duke
parents:
diff changeset
249 // If that happens, we just assume all integers are possible.
a61af66fc99e Initial load
duke
parents:
diff changeset
250 if( (((r0->_lo ^ r1->_hi) >= 0) || // lo ends have same signs OR
a61af66fc99e Initial load
duke
parents:
diff changeset
251 ((r0->_lo ^ lo) >= 0)) && // lo results have same signs AND
a61af66fc99e Initial load
duke
parents:
diff changeset
252 (((r0->_hi ^ r1->_lo) >= 0) || // hi ends have same signs OR
a61af66fc99e Initial load
duke
parents:
diff changeset
253 ((r0->_hi ^ hi) >= 0)) ) // hi results have same signs
a61af66fc99e Initial load
duke
parents:
diff changeset
254 return TypeInt::make(lo,hi,MAX2(r0->_widen,r1->_widen));
a61af66fc99e Initial load
duke
parents:
diff changeset
255 else // Overflow; assume all integers
a61af66fc99e Initial load
duke
parents:
diff changeset
256 return TypeInt::INT;
a61af66fc99e Initial load
duke
parents:
diff changeset
257 }
a61af66fc99e Initial load
duke
parents:
diff changeset
258
a61af66fc99e Initial load
duke
parents:
diff changeset
259 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
260 //------------------------------Ideal------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
261 Node *SubLNode::Ideal(PhaseGVN *phase, bool can_reshape) {
a61af66fc99e Initial load
duke
parents:
diff changeset
262 Node *in1 = in(1);
a61af66fc99e Initial load
duke
parents:
diff changeset
263 Node *in2 = in(2);
a61af66fc99e Initial load
duke
parents:
diff changeset
264 uint op1 = in1->Opcode();
a61af66fc99e Initial load
duke
parents:
diff changeset
265 uint op2 = in2->Opcode();
a61af66fc99e Initial load
duke
parents:
diff changeset
266
a61af66fc99e Initial load
duke
parents:
diff changeset
267 #ifdef ASSERT
a61af66fc99e Initial load
duke
parents:
diff changeset
268 // Check for dead loop
a61af66fc99e Initial load
duke
parents:
diff changeset
269 if( phase->eqv( in1, this ) || phase->eqv( in2, this ) ||
a61af66fc99e Initial load
duke
parents:
diff changeset
270 ( op1 == Op_AddL || op1 == Op_SubL ) &&
a61af66fc99e Initial load
duke
parents:
diff changeset
271 ( phase->eqv( in1->in(1), this ) || phase->eqv( in1->in(2), this ) ||
a61af66fc99e Initial load
duke
parents:
diff changeset
272 phase->eqv( in1->in(1), in1 ) || phase->eqv( in1->in(2), in1 ) ) )
a61af66fc99e Initial load
duke
parents:
diff changeset
273 assert(false, "dead loop in SubLNode::Ideal");
a61af66fc99e Initial load
duke
parents:
diff changeset
274 #endif
a61af66fc99e Initial load
duke
parents:
diff changeset
275
a61af66fc99e Initial load
duke
parents:
diff changeset
276 if( phase->type( in2 ) == Type::TOP ) return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
277 const TypeLong *i = phase->type( in2 )->isa_long();
a61af66fc99e Initial load
duke
parents:
diff changeset
278 // Convert "x-c0" into "x+ -c0".
a61af66fc99e Initial load
duke
parents:
diff changeset
279 if( i && // Might be bottom or top...
a61af66fc99e Initial load
duke
parents:
diff changeset
280 i->is_con() )
a61af66fc99e Initial load
duke
parents:
diff changeset
281 return new (phase->C, 3) AddLNode(in1, phase->longcon(-i->get_con()));
a61af66fc99e Initial load
duke
parents:
diff changeset
282
a61af66fc99e Initial load
duke
parents:
diff changeset
283 // Convert "(x+c0) - y" into (x-y) + c0"
a61af66fc99e Initial load
duke
parents:
diff changeset
284 // Do not collapse (x+c0)-y if "+" is a loop increment or
a61af66fc99e Initial load
duke
parents:
diff changeset
285 // if "y" is a loop induction variable.
a61af66fc99e Initial load
duke
parents:
diff changeset
286 if( op1 == Op_AddL && ok_to_convert(in1, in2) ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
287 Node *in11 = in1->in(1);
a61af66fc99e Initial load
duke
parents:
diff changeset
288 const Type *tadd = phase->type( in1->in(2) );
a61af66fc99e Initial load
duke
parents:
diff changeset
289 if( tadd->singleton() && tadd != Type::TOP ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
290 Node *sub2 = phase->transform( new (phase->C, 3) SubLNode( in11, in2 ));
a61af66fc99e Initial load
duke
parents:
diff changeset
291 return new (phase->C, 3) AddLNode( sub2, in1->in(2) );
a61af66fc99e Initial load
duke
parents:
diff changeset
292 }
a61af66fc99e Initial load
duke
parents:
diff changeset
293 }
a61af66fc99e Initial load
duke
parents:
diff changeset
294
a61af66fc99e Initial load
duke
parents:
diff changeset
295 // Convert "x - (y+c0)" into "(x-y) - c0"
a61af66fc99e Initial load
duke
parents:
diff changeset
296 // Need the same check as in above optimization but reversed.
a61af66fc99e Initial load
duke
parents:
diff changeset
297 if (op2 == Op_AddL && ok_to_convert(in2, in1)) {
a61af66fc99e Initial load
duke
parents:
diff changeset
298 Node* in21 = in2->in(1);
a61af66fc99e Initial load
duke
parents:
diff changeset
299 Node* in22 = in2->in(2);
a61af66fc99e Initial load
duke
parents:
diff changeset
300 const TypeLong* tcon = phase->type(in22)->isa_long();
a61af66fc99e Initial load
duke
parents:
diff changeset
301 if (tcon != NULL && tcon->is_con()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
302 Node* sub2 = phase->transform( new (phase->C, 3) SubLNode(in1, in21) );
a61af66fc99e Initial load
duke
parents:
diff changeset
303 Node* neg_c0 = phase->longcon(- tcon->get_con());
a61af66fc99e Initial load
duke
parents:
diff changeset
304 return new (phase->C, 3) AddLNode(sub2, neg_c0);
a61af66fc99e Initial load
duke
parents:
diff changeset
305 }
a61af66fc99e Initial load
duke
parents:
diff changeset
306 }
a61af66fc99e Initial load
duke
parents:
diff changeset
307
a61af66fc99e Initial load
duke
parents:
diff changeset
308 const Type *t1 = phase->type( in1 );
a61af66fc99e Initial load
duke
parents:
diff changeset
309 if( t1 == Type::TOP ) return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
310
a61af66fc99e Initial load
duke
parents:
diff changeset
311 #ifdef ASSERT
a61af66fc99e Initial load
duke
parents:
diff changeset
312 // Check for dead loop
a61af66fc99e Initial load
duke
parents:
diff changeset
313 if( ( op2 == Op_AddL || op2 == Op_SubL ) &&
a61af66fc99e Initial load
duke
parents:
diff changeset
314 ( phase->eqv( in2->in(1), this ) || phase->eqv( in2->in(2), this ) ||
a61af66fc99e Initial load
duke
parents:
diff changeset
315 phase->eqv( in2->in(1), in2 ) || phase->eqv( in2->in(2), in2 ) ) )
a61af66fc99e Initial load
duke
parents:
diff changeset
316 assert(false, "dead loop in SubLNode::Ideal");
a61af66fc99e Initial load
duke
parents:
diff changeset
317 #endif
a61af66fc99e Initial load
duke
parents:
diff changeset
318
a61af66fc99e Initial load
duke
parents:
diff changeset
319 // Convert "x - (x+y)" into "-y"
a61af66fc99e Initial load
duke
parents:
diff changeset
320 if( op2 == Op_AddL &&
a61af66fc99e Initial load
duke
parents:
diff changeset
321 phase->eqv( in1, in2->in(1) ) )
a61af66fc99e Initial load
duke
parents:
diff changeset
322 return new (phase->C, 3) SubLNode( phase->makecon(TypeLong::ZERO), in2->in(2));
a61af66fc99e Initial load
duke
parents:
diff changeset
323 // Convert "x - (y+x)" into "-y"
a61af66fc99e Initial load
duke
parents:
diff changeset
324 if( op2 == Op_AddL &&
a61af66fc99e Initial load
duke
parents:
diff changeset
325 phase->eqv( in1, in2->in(2) ) )
a61af66fc99e Initial load
duke
parents:
diff changeset
326 return new (phase->C, 3) SubLNode( phase->makecon(TypeLong::ZERO),in2->in(1));
a61af66fc99e Initial load
duke
parents:
diff changeset
327
a61af66fc99e Initial load
duke
parents:
diff changeset
328 // Convert "0 - (x-y)" into "y-x"
a61af66fc99e Initial load
duke
parents:
diff changeset
329 if( phase->type( in1 ) == TypeLong::ZERO && op2 == Op_SubL )
a61af66fc99e Initial load
duke
parents:
diff changeset
330 return new (phase->C, 3) SubLNode( in2->in(2), in2->in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
331
a61af66fc99e Initial load
duke
parents:
diff changeset
332 // Convert "(X+A) - (X+B)" into "A - B"
a61af66fc99e Initial load
duke
parents:
diff changeset
333 if( op1 == Op_AddL && op2 == Op_AddL && in1->in(1) == in2->in(1) )
a61af66fc99e Initial load
duke
parents:
diff changeset
334 return new (phase->C, 3) SubLNode( in1->in(2), in2->in(2) );
a61af66fc99e Initial load
duke
parents:
diff changeset
335
a61af66fc99e Initial load
duke
parents:
diff changeset
336 // Convert "(A+X) - (B+X)" into "A - B"
a61af66fc99e Initial load
duke
parents:
diff changeset
337 if( op1 == Op_AddL && op2 == Op_AddL && in1->in(2) == in2->in(2) )
a61af66fc99e Initial load
duke
parents:
diff changeset
338 return new (phase->C, 3) SubLNode( in1->in(1), in2->in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
339
a61af66fc99e Initial load
duke
parents:
diff changeset
340 // Convert "A-(B-C)" into (A+C)-B"
a61af66fc99e Initial load
duke
parents:
diff changeset
341 if( op2 == Op_SubL && in2->outcnt() == 1) {
a61af66fc99e Initial load
duke
parents:
diff changeset
342 Node *add1 = phase->transform( new (phase->C, 3) AddLNode( in1, in2->in(2) ) );
a61af66fc99e Initial load
duke
parents:
diff changeset
343 return new (phase->C, 3) SubLNode( add1, in2->in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
344 }
a61af66fc99e Initial load
duke
parents:
diff changeset
345
a61af66fc99e Initial load
duke
parents:
diff changeset
346 return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
347 }
a61af66fc99e Initial load
duke
parents:
diff changeset
348
a61af66fc99e Initial load
duke
parents:
diff changeset
349 //------------------------------sub--------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
350 // A subtract node differences it's two inputs.
a61af66fc99e Initial load
duke
parents:
diff changeset
351 const Type *SubLNode::sub( const Type *t1, const Type *t2 ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
352 const TypeLong *r0 = t1->is_long(); // Handy access
a61af66fc99e Initial load
duke
parents:
diff changeset
353 const TypeLong *r1 = t2->is_long();
a61af66fc99e Initial load
duke
parents:
diff changeset
354 jlong lo = r0->_lo - r1->_hi;
a61af66fc99e Initial load
duke
parents:
diff changeset
355 jlong hi = r0->_hi - r1->_lo;
a61af66fc99e Initial load
duke
parents:
diff changeset
356
a61af66fc99e Initial load
duke
parents:
diff changeset
357 // We next check for 32-bit overflow.
a61af66fc99e Initial load
duke
parents:
diff changeset
358 // If that happens, we just assume all integers are possible.
a61af66fc99e Initial load
duke
parents:
diff changeset
359 if( (((r0->_lo ^ r1->_hi) >= 0) || // lo ends have same signs OR
a61af66fc99e Initial load
duke
parents:
diff changeset
360 ((r0->_lo ^ lo) >= 0)) && // lo results have same signs AND
a61af66fc99e Initial load
duke
parents:
diff changeset
361 (((r0->_hi ^ r1->_lo) >= 0) || // hi ends have same signs OR
a61af66fc99e Initial load
duke
parents:
diff changeset
362 ((r0->_hi ^ hi) >= 0)) ) // hi results have same signs
a61af66fc99e Initial load
duke
parents:
diff changeset
363 return TypeLong::make(lo,hi,MAX2(r0->_widen,r1->_widen));
a61af66fc99e Initial load
duke
parents:
diff changeset
364 else // Overflow; assume all integers
a61af66fc99e Initial load
duke
parents:
diff changeset
365 return TypeLong::LONG;
a61af66fc99e Initial load
duke
parents:
diff changeset
366 }
a61af66fc99e Initial load
duke
parents:
diff changeset
367
a61af66fc99e Initial load
duke
parents:
diff changeset
368 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
369 //------------------------------Value------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
370 // A subtract node differences its two inputs.
a61af66fc99e Initial load
duke
parents:
diff changeset
371 const Type *SubFPNode::Value( PhaseTransform *phase ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
372 const Node* in1 = in(1);
a61af66fc99e Initial load
duke
parents:
diff changeset
373 const Node* in2 = in(2);
a61af66fc99e Initial load
duke
parents:
diff changeset
374 // Either input is TOP ==> the result is TOP
a61af66fc99e Initial load
duke
parents:
diff changeset
375 const Type* t1 = (in1 == this) ? Type::TOP : phase->type(in1);
a61af66fc99e Initial load
duke
parents:
diff changeset
376 if( t1 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
377 const Type* t2 = (in2 == this) ? Type::TOP : phase->type(in2);
a61af66fc99e Initial load
duke
parents:
diff changeset
378 if( t2 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
379
a61af66fc99e Initial load
duke
parents:
diff changeset
380 // if both operands are infinity of same sign, the result is NaN; do
a61af66fc99e Initial load
duke
parents:
diff changeset
381 // not replace with zero
a61af66fc99e Initial load
duke
parents:
diff changeset
382 if( (t1->is_finite() && t2->is_finite()) ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
383 if( phase->eqv(in1, in2) ) return add_id();
a61af66fc99e Initial load
duke
parents:
diff changeset
384 }
a61af66fc99e Initial load
duke
parents:
diff changeset
385
a61af66fc99e Initial load
duke
parents:
diff changeset
386 // Either input is BOTTOM ==> the result is the local BOTTOM
a61af66fc99e Initial load
duke
parents:
diff changeset
387 const Type *bot = bottom_type();
a61af66fc99e Initial load
duke
parents:
diff changeset
388 if( (t1 == bot) || (t2 == bot) ||
a61af66fc99e Initial load
duke
parents:
diff changeset
389 (t1 == Type::BOTTOM) || (t2 == Type::BOTTOM) )
a61af66fc99e Initial load
duke
parents:
diff changeset
390 return bot;
a61af66fc99e Initial load
duke
parents:
diff changeset
391
a61af66fc99e Initial load
duke
parents:
diff changeset
392 return sub(t1,t2); // Local flavor of type subtraction
a61af66fc99e Initial load
duke
parents:
diff changeset
393 }
a61af66fc99e Initial load
duke
parents:
diff changeset
394
a61af66fc99e Initial load
duke
parents:
diff changeset
395
a61af66fc99e Initial load
duke
parents:
diff changeset
396 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
397 //------------------------------Ideal------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
398 Node *SubFNode::Ideal(PhaseGVN *phase, bool can_reshape) {
a61af66fc99e Initial load
duke
parents:
diff changeset
399 const Type *t2 = phase->type( in(2) );
a61af66fc99e Initial load
duke
parents:
diff changeset
400 // Convert "x-c0" into "x+ -c0".
a61af66fc99e Initial load
duke
parents:
diff changeset
401 if( t2->base() == Type::FloatCon ) { // Might be bottom or top...
a61af66fc99e Initial load
duke
parents:
diff changeset
402 // return new (phase->C, 3) AddFNode(in(1), phase->makecon( TypeF::make(-t2->getf()) ) );
a61af66fc99e Initial load
duke
parents:
diff changeset
403 }
a61af66fc99e Initial load
duke
parents:
diff changeset
404
a61af66fc99e Initial load
duke
parents:
diff changeset
405 // Not associative because of boundary conditions (infinity)
a61af66fc99e Initial load
duke
parents:
diff changeset
406 if( IdealizedNumerics && !phase->C->method()->is_strict() ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
407 // Convert "x - (x+y)" into "-y"
a61af66fc99e Initial load
duke
parents:
diff changeset
408 if( in(2)->is_Add() &&
a61af66fc99e Initial load
duke
parents:
diff changeset
409 phase->eqv(in(1),in(2)->in(1) ) )
a61af66fc99e Initial load
duke
parents:
diff changeset
410 return new (phase->C, 3) SubFNode( phase->makecon(TypeF::ZERO),in(2)->in(2));
a61af66fc99e Initial load
duke
parents:
diff changeset
411 }
a61af66fc99e Initial load
duke
parents:
diff changeset
412
a61af66fc99e Initial load
duke
parents:
diff changeset
413 // Cannot replace 0.0-X with -X because a 'fsub' bytecode computes
a61af66fc99e Initial load
duke
parents:
diff changeset
414 // 0.0-0.0 as +0.0, while a 'fneg' bytecode computes -0.0.
a61af66fc99e Initial load
duke
parents:
diff changeset
415 //if( phase->type(in(1)) == TypeF::ZERO )
a61af66fc99e Initial load
duke
parents:
diff changeset
416 //return new (phase->C, 2) NegFNode(in(2));
a61af66fc99e Initial load
duke
parents:
diff changeset
417
a61af66fc99e Initial load
duke
parents:
diff changeset
418 return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
419 }
a61af66fc99e Initial load
duke
parents:
diff changeset
420
a61af66fc99e Initial load
duke
parents:
diff changeset
421 //------------------------------sub--------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
422 // A subtract node differences its two inputs.
a61af66fc99e Initial load
duke
parents:
diff changeset
423 const Type *SubFNode::sub( const Type *t1, const Type *t2 ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
424 // no folding if one of operands is infinity or NaN, do not do constant folding
a61af66fc99e Initial load
duke
parents:
diff changeset
425 if( g_isfinite(t1->getf()) && g_isfinite(t2->getf()) ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
426 return TypeF::make( t1->getf() - t2->getf() );
a61af66fc99e Initial load
duke
parents:
diff changeset
427 }
a61af66fc99e Initial load
duke
parents:
diff changeset
428 else if( g_isnan(t1->getf()) ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
429 return t1;
a61af66fc99e Initial load
duke
parents:
diff changeset
430 }
a61af66fc99e Initial load
duke
parents:
diff changeset
431 else if( g_isnan(t2->getf()) ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
432 return t2;
a61af66fc99e Initial load
duke
parents:
diff changeset
433 }
a61af66fc99e Initial load
duke
parents:
diff changeset
434 else {
a61af66fc99e Initial load
duke
parents:
diff changeset
435 return Type::FLOAT;
a61af66fc99e Initial load
duke
parents:
diff changeset
436 }
a61af66fc99e Initial load
duke
parents:
diff changeset
437 }
a61af66fc99e Initial load
duke
parents:
diff changeset
438
a61af66fc99e Initial load
duke
parents:
diff changeset
439 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
440 //------------------------------Ideal------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
441 Node *SubDNode::Ideal(PhaseGVN *phase, bool can_reshape){
a61af66fc99e Initial load
duke
parents:
diff changeset
442 const Type *t2 = phase->type( in(2) );
a61af66fc99e Initial load
duke
parents:
diff changeset
443 // Convert "x-c0" into "x+ -c0".
a61af66fc99e Initial load
duke
parents:
diff changeset
444 if( t2->base() == Type::DoubleCon ) { // Might be bottom or top...
a61af66fc99e Initial load
duke
parents:
diff changeset
445 // return new (phase->C, 3) AddDNode(in(1), phase->makecon( TypeD::make(-t2->getd()) ) );
a61af66fc99e Initial load
duke
parents:
diff changeset
446 }
a61af66fc99e Initial load
duke
parents:
diff changeset
447
a61af66fc99e Initial load
duke
parents:
diff changeset
448 // Not associative because of boundary conditions (infinity)
a61af66fc99e Initial load
duke
parents:
diff changeset
449 if( IdealizedNumerics && !phase->C->method()->is_strict() ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
450 // Convert "x - (x+y)" into "-y"
a61af66fc99e Initial load
duke
parents:
diff changeset
451 if( in(2)->is_Add() &&
a61af66fc99e Initial load
duke
parents:
diff changeset
452 phase->eqv(in(1),in(2)->in(1) ) )
a61af66fc99e Initial load
duke
parents:
diff changeset
453 return new (phase->C, 3) SubDNode( phase->makecon(TypeD::ZERO),in(2)->in(2));
a61af66fc99e Initial load
duke
parents:
diff changeset
454 }
a61af66fc99e Initial load
duke
parents:
diff changeset
455
a61af66fc99e Initial load
duke
parents:
diff changeset
456 // Cannot replace 0.0-X with -X because a 'dsub' bytecode computes
a61af66fc99e Initial load
duke
parents:
diff changeset
457 // 0.0-0.0 as +0.0, while a 'dneg' bytecode computes -0.0.
a61af66fc99e Initial load
duke
parents:
diff changeset
458 //if( phase->type(in(1)) == TypeD::ZERO )
a61af66fc99e Initial load
duke
parents:
diff changeset
459 //return new (phase->C, 2) NegDNode(in(2));
a61af66fc99e Initial load
duke
parents:
diff changeset
460
a61af66fc99e Initial load
duke
parents:
diff changeset
461 return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
462 }
a61af66fc99e Initial load
duke
parents:
diff changeset
463
a61af66fc99e Initial load
duke
parents:
diff changeset
464 //------------------------------sub--------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
465 // A subtract node differences its two inputs.
a61af66fc99e Initial load
duke
parents:
diff changeset
466 const Type *SubDNode::sub( const Type *t1, const Type *t2 ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
467 // no folding if one of operands is infinity or NaN, do not do constant folding
a61af66fc99e Initial load
duke
parents:
diff changeset
468 if( g_isfinite(t1->getd()) && g_isfinite(t2->getd()) ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
469 return TypeD::make( t1->getd() - t2->getd() );
a61af66fc99e Initial load
duke
parents:
diff changeset
470 }
a61af66fc99e Initial load
duke
parents:
diff changeset
471 else if( g_isnan(t1->getd()) ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
472 return t1;
a61af66fc99e Initial load
duke
parents:
diff changeset
473 }
a61af66fc99e Initial load
duke
parents:
diff changeset
474 else if( g_isnan(t2->getd()) ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
475 return t2;
a61af66fc99e Initial load
duke
parents:
diff changeset
476 }
a61af66fc99e Initial load
duke
parents:
diff changeset
477 else {
a61af66fc99e Initial load
duke
parents:
diff changeset
478 return Type::DOUBLE;
a61af66fc99e Initial load
duke
parents:
diff changeset
479 }
a61af66fc99e Initial load
duke
parents:
diff changeset
480 }
a61af66fc99e Initial load
duke
parents:
diff changeset
481
a61af66fc99e Initial load
duke
parents:
diff changeset
482 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
483 //------------------------------Idealize---------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
484 // Unlike SubNodes, compare must still flatten return value to the
a61af66fc99e Initial load
duke
parents:
diff changeset
485 // range -1, 0, 1.
a61af66fc99e Initial load
duke
parents:
diff changeset
486 // And optimizations like those for (X + Y) - X fail if overflow happens.
a61af66fc99e Initial load
duke
parents:
diff changeset
487 Node *CmpNode::Identity( PhaseTransform *phase ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
488 return this;
a61af66fc99e Initial load
duke
parents:
diff changeset
489 }
a61af66fc99e Initial load
duke
parents:
diff changeset
490
a61af66fc99e Initial load
duke
parents:
diff changeset
491 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
492 //------------------------------cmp--------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
493 // Simplify a CmpI (compare 2 integers) node, based on local information.
a61af66fc99e Initial load
duke
parents:
diff changeset
494 // If both inputs are constants, compare them.
a61af66fc99e Initial load
duke
parents:
diff changeset
495 const Type *CmpINode::sub( const Type *t1, const Type *t2 ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
496 const TypeInt *r0 = t1->is_int(); // Handy access
a61af66fc99e Initial load
duke
parents:
diff changeset
497 const TypeInt *r1 = t2->is_int();
a61af66fc99e Initial load
duke
parents:
diff changeset
498
a61af66fc99e Initial load
duke
parents:
diff changeset
499 if( r0->_hi < r1->_lo ) // Range is always low?
a61af66fc99e Initial load
duke
parents:
diff changeset
500 return TypeInt::CC_LT;
a61af66fc99e Initial load
duke
parents:
diff changeset
501 else if( r0->_lo > r1->_hi ) // Range is always high?
a61af66fc99e Initial load
duke
parents:
diff changeset
502 return TypeInt::CC_GT;
a61af66fc99e Initial load
duke
parents:
diff changeset
503
a61af66fc99e Initial load
duke
parents:
diff changeset
504 else if( r0->is_con() && r1->is_con() ) { // comparing constants?
a61af66fc99e Initial load
duke
parents:
diff changeset
505 assert(r0->get_con() == r1->get_con(), "must be equal");
a61af66fc99e Initial load
duke
parents:
diff changeset
506 return TypeInt::CC_EQ; // Equal results.
a61af66fc99e Initial load
duke
parents:
diff changeset
507 } else if( r0->_hi == r1->_lo ) // Range is never high?
a61af66fc99e Initial load
duke
parents:
diff changeset
508 return TypeInt::CC_LE;
a61af66fc99e Initial load
duke
parents:
diff changeset
509 else if( r0->_lo == r1->_hi ) // Range is never low?
a61af66fc99e Initial load
duke
parents:
diff changeset
510 return TypeInt::CC_GE;
a61af66fc99e Initial load
duke
parents:
diff changeset
511 return TypeInt::CC; // else use worst case results
a61af66fc99e Initial load
duke
parents:
diff changeset
512 }
a61af66fc99e Initial load
duke
parents:
diff changeset
513
a61af66fc99e Initial load
duke
parents:
diff changeset
514 // Simplify a CmpU (compare 2 integers) node, based on local information.
a61af66fc99e Initial load
duke
parents:
diff changeset
515 // If both inputs are constants, compare them.
a61af66fc99e Initial load
duke
parents:
diff changeset
516 const Type *CmpUNode::sub( const Type *t1, const Type *t2 ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
517 assert(!t1->isa_ptr(), "obsolete usage of CmpU");
a61af66fc99e Initial load
duke
parents:
diff changeset
518
a61af66fc99e Initial load
duke
parents:
diff changeset
519 // comparing two unsigned ints
a61af66fc99e Initial load
duke
parents:
diff changeset
520 const TypeInt *r0 = t1->is_int(); // Handy access
a61af66fc99e Initial load
duke
parents:
diff changeset
521 const TypeInt *r1 = t2->is_int();
a61af66fc99e Initial load
duke
parents:
diff changeset
522
a61af66fc99e Initial load
duke
parents:
diff changeset
523 // Current installed version
a61af66fc99e Initial load
duke
parents:
diff changeset
524 // Compare ranges for non-overlap
a61af66fc99e Initial load
duke
parents:
diff changeset
525 juint lo0 = r0->_lo;
a61af66fc99e Initial load
duke
parents:
diff changeset
526 juint hi0 = r0->_hi;
a61af66fc99e Initial load
duke
parents:
diff changeset
527 juint lo1 = r1->_lo;
a61af66fc99e Initial load
duke
parents:
diff changeset
528 juint hi1 = r1->_hi;
a61af66fc99e Initial load
duke
parents:
diff changeset
529
a61af66fc99e Initial load
duke
parents:
diff changeset
530 // If either one has both negative and positive values,
a61af66fc99e Initial load
duke
parents:
diff changeset
531 // it therefore contains both 0 and -1, and since [0..-1] is the
a61af66fc99e Initial load
duke
parents:
diff changeset
532 // full unsigned range, the type must act as an unsigned bottom.
a61af66fc99e Initial load
duke
parents:
diff changeset
533 bool bot0 = ((jint)(lo0 ^ hi0) < 0);
a61af66fc99e Initial load
duke
parents:
diff changeset
534 bool bot1 = ((jint)(lo1 ^ hi1) < 0);
a61af66fc99e Initial load
duke
parents:
diff changeset
535
a61af66fc99e Initial load
duke
parents:
diff changeset
536 if (bot0 || bot1) {
a61af66fc99e Initial load
duke
parents:
diff changeset
537 // All unsigned values are LE -1 and GE 0.
a61af66fc99e Initial load
duke
parents:
diff changeset
538 if (lo0 == 0 && hi0 == 0) {
a61af66fc99e Initial load
duke
parents:
diff changeset
539 return TypeInt::CC_LE; // 0 <= bot
a61af66fc99e Initial load
duke
parents:
diff changeset
540 } else if (lo1 == 0 && hi1 == 0) {
a61af66fc99e Initial load
duke
parents:
diff changeset
541 return TypeInt::CC_GE; // bot >= 0
a61af66fc99e Initial load
duke
parents:
diff changeset
542 }
a61af66fc99e Initial load
duke
parents:
diff changeset
543 } else {
a61af66fc99e Initial load
duke
parents:
diff changeset
544 // We can use ranges of the form [lo..hi] if signs are the same.
a61af66fc99e Initial load
duke
parents:
diff changeset
545 assert(lo0 <= hi0 && lo1 <= hi1, "unsigned ranges are valid");
a61af66fc99e Initial load
duke
parents:
diff changeset
546 // results are reversed, '-' > '+' for unsigned compare
a61af66fc99e Initial load
duke
parents:
diff changeset
547 if (hi0 < lo1) {
a61af66fc99e Initial load
duke
parents:
diff changeset
548 return TypeInt::CC_LT; // smaller
a61af66fc99e Initial load
duke
parents:
diff changeset
549 } else if (lo0 > hi1) {
a61af66fc99e Initial load
duke
parents:
diff changeset
550 return TypeInt::CC_GT; // greater
a61af66fc99e Initial load
duke
parents:
diff changeset
551 } else if (hi0 == lo1 && lo0 == hi1) {
a61af66fc99e Initial load
duke
parents:
diff changeset
552 return TypeInt::CC_EQ; // Equal results
a61af66fc99e Initial load
duke
parents:
diff changeset
553 } else if (lo0 >= hi1) {
a61af66fc99e Initial load
duke
parents:
diff changeset
554 return TypeInt::CC_GE;
a61af66fc99e Initial load
duke
parents:
diff changeset
555 } else if (hi0 <= lo1) {
a61af66fc99e Initial load
duke
parents:
diff changeset
556 // Check for special case in Hashtable::get. (See below.)
a61af66fc99e Initial load
duke
parents:
diff changeset
557 if ((jint)lo0 >= 0 && (jint)lo1 >= 0 &&
a61af66fc99e Initial load
duke
parents:
diff changeset
558 in(1)->Opcode() == Op_ModI &&
a61af66fc99e Initial load
duke
parents:
diff changeset
559 in(1)->in(2) == in(2) )
a61af66fc99e Initial load
duke
parents:
diff changeset
560 return TypeInt::CC_LT;
a61af66fc99e Initial load
duke
parents:
diff changeset
561 return TypeInt::CC_LE;
a61af66fc99e Initial load
duke
parents:
diff changeset
562 }
a61af66fc99e Initial load
duke
parents:
diff changeset
563 }
a61af66fc99e Initial load
duke
parents:
diff changeset
564 // Check for special case in Hashtable::get - the hash index is
a61af66fc99e Initial load
duke
parents:
diff changeset
565 // mod'ed to the table size so the following range check is useless.
a61af66fc99e Initial load
duke
parents:
diff changeset
566 // Check for: (X Mod Y) CmpU Y, where the mod result and Y both have
a61af66fc99e Initial load
duke
parents:
diff changeset
567 // to be positive.
a61af66fc99e Initial load
duke
parents:
diff changeset
568 // (This is a gross hack, since the sub method never
a61af66fc99e Initial load
duke
parents:
diff changeset
569 // looks at the structure of the node in any other case.)
a61af66fc99e Initial load
duke
parents:
diff changeset
570 if ((jint)lo0 >= 0 && (jint)lo1 >= 0 &&
a61af66fc99e Initial load
duke
parents:
diff changeset
571 in(1)->Opcode() == Op_ModI &&
a61af66fc99e Initial load
duke
parents:
diff changeset
572 in(1)->in(2)->uncast() == in(2)->uncast())
a61af66fc99e Initial load
duke
parents:
diff changeset
573 return TypeInt::CC_LT;
a61af66fc99e Initial load
duke
parents:
diff changeset
574 return TypeInt::CC; // else use worst case results
a61af66fc99e Initial load
duke
parents:
diff changeset
575 }
a61af66fc99e Initial load
duke
parents:
diff changeset
576
a61af66fc99e Initial load
duke
parents:
diff changeset
577 //------------------------------Idealize---------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
578 Node *CmpINode::Ideal( PhaseGVN *phase, bool can_reshape ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
579 if (phase->type(in(2))->higher_equal(TypeInt::ZERO)) {
a61af66fc99e Initial load
duke
parents:
diff changeset
580 switch (in(1)->Opcode()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
581 case Op_CmpL3: // Collapse a CmpL3/CmpI into a CmpL
a61af66fc99e Initial load
duke
parents:
diff changeset
582 return new (phase->C, 3) CmpLNode(in(1)->in(1),in(1)->in(2));
a61af66fc99e Initial load
duke
parents:
diff changeset
583 case Op_CmpF3: // Collapse a CmpF3/CmpI into a CmpF
a61af66fc99e Initial load
duke
parents:
diff changeset
584 return new (phase->C, 3) CmpFNode(in(1)->in(1),in(1)->in(2));
a61af66fc99e Initial load
duke
parents:
diff changeset
585 case Op_CmpD3: // Collapse a CmpD3/CmpI into a CmpD
a61af66fc99e Initial load
duke
parents:
diff changeset
586 return new (phase->C, 3) CmpDNode(in(1)->in(1),in(1)->in(2));
a61af66fc99e Initial load
duke
parents:
diff changeset
587 //case Op_SubI:
a61af66fc99e Initial load
duke
parents:
diff changeset
588 // If (x - y) cannot overflow, then ((x - y) <?> 0)
a61af66fc99e Initial load
duke
parents:
diff changeset
589 // can be turned into (x <?> y).
a61af66fc99e Initial load
duke
parents:
diff changeset
590 // This is handled (with more general cases) by Ideal_sub_algebra.
a61af66fc99e Initial load
duke
parents:
diff changeset
591 }
a61af66fc99e Initial load
duke
parents:
diff changeset
592 }
a61af66fc99e Initial load
duke
parents:
diff changeset
593 return NULL; // No change
a61af66fc99e Initial load
duke
parents:
diff changeset
594 }
a61af66fc99e Initial load
duke
parents:
diff changeset
595
a61af66fc99e Initial load
duke
parents:
diff changeset
596
a61af66fc99e Initial load
duke
parents:
diff changeset
597 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
598 // Simplify a CmpL (compare 2 longs ) node, based on local information.
a61af66fc99e Initial load
duke
parents:
diff changeset
599 // If both inputs are constants, compare them.
a61af66fc99e Initial load
duke
parents:
diff changeset
600 const Type *CmpLNode::sub( const Type *t1, const Type *t2 ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
601 const TypeLong *r0 = t1->is_long(); // Handy access
a61af66fc99e Initial load
duke
parents:
diff changeset
602 const TypeLong *r1 = t2->is_long();
a61af66fc99e Initial load
duke
parents:
diff changeset
603
a61af66fc99e Initial load
duke
parents:
diff changeset
604 if( r0->_hi < r1->_lo ) // Range is always low?
a61af66fc99e Initial load
duke
parents:
diff changeset
605 return TypeInt::CC_LT;
a61af66fc99e Initial load
duke
parents:
diff changeset
606 else if( r0->_lo > r1->_hi ) // Range is always high?
a61af66fc99e Initial load
duke
parents:
diff changeset
607 return TypeInt::CC_GT;
a61af66fc99e Initial load
duke
parents:
diff changeset
608
a61af66fc99e Initial load
duke
parents:
diff changeset
609 else if( r0->is_con() && r1->is_con() ) { // comparing constants?
a61af66fc99e Initial load
duke
parents:
diff changeset
610 assert(r0->get_con() == r1->get_con(), "must be equal");
a61af66fc99e Initial load
duke
parents:
diff changeset
611 return TypeInt::CC_EQ; // Equal results.
a61af66fc99e Initial load
duke
parents:
diff changeset
612 } else if( r0->_hi == r1->_lo ) // Range is never high?
a61af66fc99e Initial load
duke
parents:
diff changeset
613 return TypeInt::CC_LE;
a61af66fc99e Initial load
duke
parents:
diff changeset
614 else if( r0->_lo == r1->_hi ) // Range is never low?
a61af66fc99e Initial load
duke
parents:
diff changeset
615 return TypeInt::CC_GE;
a61af66fc99e Initial load
duke
parents:
diff changeset
616 return TypeInt::CC; // else use worst case results
a61af66fc99e Initial load
duke
parents:
diff changeset
617 }
a61af66fc99e Initial load
duke
parents:
diff changeset
618
a61af66fc99e Initial load
duke
parents:
diff changeset
619 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
620 //------------------------------sub--------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
621 // Simplify an CmpP (compare 2 pointers) node, based on local information.
a61af66fc99e Initial load
duke
parents:
diff changeset
622 // If both inputs are constants, compare them.
a61af66fc99e Initial load
duke
parents:
diff changeset
623 const Type *CmpPNode::sub( const Type *t1, const Type *t2 ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
624 const TypePtr *r0 = t1->is_ptr(); // Handy access
a61af66fc99e Initial load
duke
parents:
diff changeset
625 const TypePtr *r1 = t2->is_ptr();
a61af66fc99e Initial load
duke
parents:
diff changeset
626
a61af66fc99e Initial load
duke
parents:
diff changeset
627 // Undefined inputs makes for an undefined result
a61af66fc99e Initial load
duke
parents:
diff changeset
628 if( TypePtr::above_centerline(r0->_ptr) ||
a61af66fc99e Initial load
duke
parents:
diff changeset
629 TypePtr::above_centerline(r1->_ptr) )
a61af66fc99e Initial load
duke
parents:
diff changeset
630 return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
631
a61af66fc99e Initial load
duke
parents:
diff changeset
632 if (r0 == r1 && r0->singleton()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
633 // Equal pointer constants (klasses, nulls, etc.)
a61af66fc99e Initial load
duke
parents:
diff changeset
634 return TypeInt::CC_EQ;
a61af66fc99e Initial load
duke
parents:
diff changeset
635 }
a61af66fc99e Initial load
duke
parents:
diff changeset
636
a61af66fc99e Initial load
duke
parents:
diff changeset
637 // See if it is 2 unrelated classes.
a61af66fc99e Initial load
duke
parents:
diff changeset
638 const TypeOopPtr* p0 = r0->isa_oopptr();
a61af66fc99e Initial load
duke
parents:
diff changeset
639 const TypeOopPtr* p1 = r1->isa_oopptr();
a61af66fc99e Initial load
duke
parents:
diff changeset
640 if (p0 && p1) {
33
3288958bf319 6667580: Optimize CmpP for allocations
kvn
parents: 0
diff changeset
641 Node* in1 = in(1)->uncast();
3288958bf319 6667580: Optimize CmpP for allocations
kvn
parents: 0
diff changeset
642 Node* in2 = in(2)->uncast();
3288958bf319 6667580: Optimize CmpP for allocations
kvn
parents: 0
diff changeset
643 AllocateNode* alloc1 = AllocateNode::Ideal_allocation(in1, NULL);
3288958bf319 6667580: Optimize CmpP for allocations
kvn
parents: 0
diff changeset
644 AllocateNode* alloc2 = AllocateNode::Ideal_allocation(in2, NULL);
3288958bf319 6667580: Optimize CmpP for allocations
kvn
parents: 0
diff changeset
645 if (MemNode::detect_ptr_independence(in1, alloc1, in2, alloc2, NULL)) {
3288958bf319 6667580: Optimize CmpP for allocations
kvn
parents: 0
diff changeset
646 return TypeInt::CC_GT; // different pointers
3288958bf319 6667580: Optimize CmpP for allocations
kvn
parents: 0
diff changeset
647 }
0
a61af66fc99e Initial load
duke
parents:
diff changeset
648 ciKlass* klass0 = p0->klass();
a61af66fc99e Initial load
duke
parents:
diff changeset
649 bool xklass0 = p0->klass_is_exact();
a61af66fc99e Initial load
duke
parents:
diff changeset
650 ciKlass* klass1 = p1->klass();
a61af66fc99e Initial load
duke
parents:
diff changeset
651 bool xklass1 = p1->klass_is_exact();
a61af66fc99e Initial load
duke
parents:
diff changeset
652 int kps = (p0->isa_klassptr()?1:0) + (p1->isa_klassptr()?1:0);
a61af66fc99e Initial load
duke
parents:
diff changeset
653 if (klass0 && klass1 &&
a61af66fc99e Initial load
duke
parents:
diff changeset
654 kps != 1 && // both or neither are klass pointers
668
90a66aa50514 6820510: assertion failure with unloaded class in subnode.cpp
never
parents: 400
diff changeset
655 klass0->is_loaded() && !klass0->is_interface() && // do not trust interfaces
783
a9e116455022 6832293: JIT compiler got wrong result in type checking with -server
kvn
parents: 668
diff changeset
656 klass1->is_loaded() && !klass1->is_interface() &&
a9e116455022 6832293: JIT compiler got wrong result in type checking with -server
kvn
parents: 668
diff changeset
657 (!klass0->is_obj_array_klass() ||
a9e116455022 6832293: JIT compiler got wrong result in type checking with -server
kvn
parents: 668
diff changeset
658 !klass0->as_obj_array_klass()->base_element_klass()->is_interface()) &&
a9e116455022 6832293: JIT compiler got wrong result in type checking with -server
kvn
parents: 668
diff changeset
659 (!klass1->is_obj_array_klass() ||
a9e116455022 6832293: JIT compiler got wrong result in type checking with -server
kvn
parents: 668
diff changeset
660 !klass1->as_obj_array_klass()->base_element_klass()->is_interface())) {
296
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
661 bool unrelated_classes = false;
0
a61af66fc99e Initial load
duke
parents:
diff changeset
662 // See if neither subclasses the other, or if the class on top
296
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
663 // is precise. In either of these cases, the compare is known
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
664 // to fail if at least one of the pointers is provably not null.
0
a61af66fc99e Initial load
duke
parents:
diff changeset
665 if (klass0->equals(klass1) || // if types are unequal but klasses are
a61af66fc99e Initial load
duke
parents:
diff changeset
666 !klass0->is_java_klass() || // types not part of Java language?
a61af66fc99e Initial load
duke
parents:
diff changeset
667 !klass1->is_java_klass()) { // types not part of Java language?
a61af66fc99e Initial load
duke
parents:
diff changeset
668 // Do nothing; we know nothing for imprecise types
a61af66fc99e Initial load
duke
parents:
diff changeset
669 } else if (klass0->is_subtype_of(klass1)) {
296
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
670 // If klass1's type is PRECISE, then classes are unrelated.
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
671 unrelated_classes = xklass1;
0
a61af66fc99e Initial load
duke
parents:
diff changeset
672 } else if (klass1->is_subtype_of(klass0)) {
296
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
673 // If klass0's type is PRECISE, then classes are unrelated.
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
674 unrelated_classes = xklass0;
0
a61af66fc99e Initial load
duke
parents:
diff changeset
675 } else { // Neither subtypes the other
296
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
676 unrelated_classes = true;
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
677 }
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
678 if (unrelated_classes) {
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
679 // The oops classes are known to be unrelated. If the joined PTRs of
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
680 // two oops is not Null and not Bottom, then we are sure that one
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
681 // of the two oops is non-null, and the comparison will always fail.
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
682 TypePtr::PTR jp = r0->join_ptr(r1->_ptr);
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
683 if (jp != TypePtr::Null && jp != TypePtr::BotPTR) {
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
684 return TypeInt::CC_GT;
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
685 }
0
a61af66fc99e Initial load
duke
parents:
diff changeset
686 }
a61af66fc99e Initial load
duke
parents:
diff changeset
687 }
a61af66fc99e Initial load
duke
parents:
diff changeset
688 }
a61af66fc99e Initial load
duke
parents:
diff changeset
689
a61af66fc99e Initial load
duke
parents:
diff changeset
690 // Known constants can be compared exactly
a61af66fc99e Initial load
duke
parents:
diff changeset
691 // Null can be distinguished from any NotNull pointers
a61af66fc99e Initial load
duke
parents:
diff changeset
692 // Unknown inputs makes an unknown result
a61af66fc99e Initial load
duke
parents:
diff changeset
693 if( r0->singleton() ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
694 intptr_t bits0 = r0->get_con();
a61af66fc99e Initial load
duke
parents:
diff changeset
695 if( r1->singleton() )
a61af66fc99e Initial load
duke
parents:
diff changeset
696 return bits0 == r1->get_con() ? TypeInt::CC_EQ : TypeInt::CC_GT;
a61af66fc99e Initial load
duke
parents:
diff changeset
697 return ( r1->_ptr == TypePtr::NotNull && bits0==0 ) ? TypeInt::CC_GT : TypeInt::CC;
a61af66fc99e Initial load
duke
parents:
diff changeset
698 } else if( r1->singleton() ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
699 intptr_t bits1 = r1->get_con();
a61af66fc99e Initial load
duke
parents:
diff changeset
700 return ( r0->_ptr == TypePtr::NotNull && bits1==0 ) ? TypeInt::CC_GT : TypeInt::CC;
a61af66fc99e Initial load
duke
parents:
diff changeset
701 } else
a61af66fc99e Initial load
duke
parents:
diff changeset
702 return TypeInt::CC;
a61af66fc99e Initial load
duke
parents:
diff changeset
703 }
a61af66fc99e Initial load
duke
parents:
diff changeset
704
a61af66fc99e Initial load
duke
parents:
diff changeset
705 //------------------------------Ideal------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
706 // Check for the case of comparing an unknown klass loaded from the primary
a61af66fc99e Initial load
duke
parents:
diff changeset
707 // super-type array vs a known klass with no subtypes. This amounts to
a61af66fc99e Initial load
duke
parents:
diff changeset
708 // checking to see an unknown klass subtypes a known klass with no subtypes;
a61af66fc99e Initial load
duke
parents:
diff changeset
709 // this only happens on an exact match. We can shorten this test by 1 load.
a61af66fc99e Initial load
duke
parents:
diff changeset
710 Node *CmpPNode::Ideal( PhaseGVN *phase, bool can_reshape ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
711 // Constant pointer on right?
a61af66fc99e Initial load
duke
parents:
diff changeset
712 const TypeKlassPtr* t2 = phase->type(in(2))->isa_klassptr();
a61af66fc99e Initial load
duke
parents:
diff changeset
713 if (t2 == NULL || !t2->klass_is_exact())
a61af66fc99e Initial load
duke
parents:
diff changeset
714 return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
715 // Get the constant klass we are comparing to.
a61af66fc99e Initial load
duke
parents:
diff changeset
716 ciKlass* superklass = t2->klass();
a61af66fc99e Initial load
duke
parents:
diff changeset
717
a61af66fc99e Initial load
duke
parents:
diff changeset
718 // Now check for LoadKlass on left.
a61af66fc99e Initial load
duke
parents:
diff changeset
719 Node* ldk1 = in(1);
293
c3e045194476 6731641: assert(m->adr_type() == mach->adr_type(),"matcher should not change adr type")
kvn
parents: 235
diff changeset
720 if (ldk1->is_DecodeN()) {
c3e045194476 6731641: assert(m->adr_type() == mach->adr_type(),"matcher should not change adr type")
kvn
parents: 235
diff changeset
721 ldk1 = ldk1->in(1);
c3e045194476 6731641: assert(m->adr_type() == mach->adr_type(),"matcher should not change adr type")
kvn
parents: 235
diff changeset
722 if (ldk1->Opcode() != Op_LoadNKlass )
c3e045194476 6731641: assert(m->adr_type() == mach->adr_type(),"matcher should not change adr type")
kvn
parents: 235
diff changeset
723 return NULL;
c3e045194476 6731641: assert(m->adr_type() == mach->adr_type(),"matcher should not change adr type")
kvn
parents: 235
diff changeset
724 } else if (ldk1->Opcode() != Op_LoadKlass )
0
a61af66fc99e Initial load
duke
parents:
diff changeset
725 return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
726 // Take apart the address of the LoadKlass:
a61af66fc99e Initial load
duke
parents:
diff changeset
727 Node* adr1 = ldk1->in(MemNode::Address);
a61af66fc99e Initial load
duke
parents:
diff changeset
728 intptr_t con2 = 0;
a61af66fc99e Initial load
duke
parents:
diff changeset
729 Node* ldk2 = AddPNode::Ideal_base_and_offset(adr1, phase, con2);
a61af66fc99e Initial load
duke
parents:
diff changeset
730 if (ldk2 == NULL)
a61af66fc99e Initial load
duke
parents:
diff changeset
731 return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
732 if (con2 == oopDesc::klass_offset_in_bytes()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
733 // We are inspecting an object's concrete class.
a61af66fc99e Initial load
duke
parents:
diff changeset
734 // Short-circuit the check if the query is abstract.
a61af66fc99e Initial load
duke
parents:
diff changeset
735 if (superklass->is_interface() ||
a61af66fc99e Initial load
duke
parents:
diff changeset
736 superklass->is_abstract()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
737 // Make it come out always false:
a61af66fc99e Initial load
duke
parents:
diff changeset
738 this->set_req(2, phase->makecon(TypePtr::NULL_PTR));
a61af66fc99e Initial load
duke
parents:
diff changeset
739 return this;
a61af66fc99e Initial load
duke
parents:
diff changeset
740 }
a61af66fc99e Initial load
duke
parents:
diff changeset
741 }
a61af66fc99e Initial load
duke
parents:
diff changeset
742
a61af66fc99e Initial load
duke
parents:
diff changeset
743 // Check for a LoadKlass from primary supertype array.
a61af66fc99e Initial load
duke
parents:
diff changeset
744 // Any nested loadklass from loadklass+con must be from the p.s. array.
293
c3e045194476 6731641: assert(m->adr_type() == mach->adr_type(),"matcher should not change adr type")
kvn
parents: 235
diff changeset
745 if (ldk2->is_DecodeN()) {
c3e045194476 6731641: assert(m->adr_type() == mach->adr_type(),"matcher should not change adr type")
kvn
parents: 235
diff changeset
746 // Keep ldk2 as DecodeN since it could be used in CmpP below.
c3e045194476 6731641: assert(m->adr_type() == mach->adr_type(),"matcher should not change adr type")
kvn
parents: 235
diff changeset
747 if (ldk2->in(1)->Opcode() != Op_LoadNKlass )
c3e045194476 6731641: assert(m->adr_type() == mach->adr_type(),"matcher should not change adr type")
kvn
parents: 235
diff changeset
748 return NULL;
c3e045194476 6731641: assert(m->adr_type() == mach->adr_type(),"matcher should not change adr type")
kvn
parents: 235
diff changeset
749 } else if (ldk2->Opcode() != Op_LoadKlass)
0
a61af66fc99e Initial load
duke
parents:
diff changeset
750 return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
751
a61af66fc99e Initial load
duke
parents:
diff changeset
752 // Verify that we understand the situation
a61af66fc99e Initial load
duke
parents:
diff changeset
753 if (con2 != (intptr_t) superklass->super_check_offset())
a61af66fc99e Initial load
duke
parents:
diff changeset
754 return NULL; // Might be element-klass loading from array klass
a61af66fc99e Initial load
duke
parents:
diff changeset
755
a61af66fc99e Initial load
duke
parents:
diff changeset
756 // If 'superklass' has no subklasses and is not an interface, then we are
a61af66fc99e Initial load
duke
parents:
diff changeset
757 // assured that the only input which will pass the type check is
a61af66fc99e Initial load
duke
parents:
diff changeset
758 // 'superklass' itself.
a61af66fc99e Initial load
duke
parents:
diff changeset
759 //
a61af66fc99e Initial load
duke
parents:
diff changeset
760 // We could be more liberal here, and allow the optimization on interfaces
a61af66fc99e Initial load
duke
parents:
diff changeset
761 // which have a single implementor. This would require us to increase the
a61af66fc99e Initial load
duke
parents:
diff changeset
762 // expressiveness of the add_dependency() mechanism.
a61af66fc99e Initial load
duke
parents:
diff changeset
763 // %%% Do this after we fix TypeOopPtr: Deps are expressive enough now.
a61af66fc99e Initial load
duke
parents:
diff changeset
764
a61af66fc99e Initial load
duke
parents:
diff changeset
765 // Object arrays must have their base element have no subtypes
a61af66fc99e Initial load
duke
parents:
diff changeset
766 while (superklass->is_obj_array_klass()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
767 ciType* elem = superklass->as_obj_array_klass()->element_type();
a61af66fc99e Initial load
duke
parents:
diff changeset
768 superklass = elem->as_klass();
a61af66fc99e Initial load
duke
parents:
diff changeset
769 }
a61af66fc99e Initial load
duke
parents:
diff changeset
770 if (superklass->is_instance_klass()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
771 ciInstanceKlass* ik = superklass->as_instance_klass();
a61af66fc99e Initial load
duke
parents:
diff changeset
772 if (ik->has_subklass() || ik->is_interface()) return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
773 // Add a dependency if there is a chance that a subclass will be added later.
a61af66fc99e Initial load
duke
parents:
diff changeset
774 if (!ik->is_final()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
775 phase->C->dependencies()->assert_leaf_type(ik);
a61af66fc99e Initial load
duke
parents:
diff changeset
776 }
a61af66fc99e Initial load
duke
parents:
diff changeset
777 }
a61af66fc99e Initial load
duke
parents:
diff changeset
778
a61af66fc99e Initial load
duke
parents:
diff changeset
779 // Bypass the dependent load, and compare directly
a61af66fc99e Initial load
duke
parents:
diff changeset
780 this->set_req(1,ldk2);
a61af66fc99e Initial load
duke
parents:
diff changeset
781
a61af66fc99e Initial load
duke
parents:
diff changeset
782 return this;
a61af66fc99e Initial load
duke
parents:
diff changeset
783 }
a61af66fc99e Initial load
duke
parents:
diff changeset
784
a61af66fc99e Initial load
duke
parents:
diff changeset
785 //=============================================================================
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
786 //------------------------------sub--------------------------------------------
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
787 // Simplify an CmpN (compare 2 pointers) node, based on local information.
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
788 // If both inputs are constants, compare them.
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
789 const Type *CmpNNode::sub( const Type *t1, const Type *t2 ) const {
221
1e026f8da827 6710487: More than half of JDI Regression tests hang with COOPs in -Xcomp mode
kvn
parents: 212
diff changeset
790 const TypePtr *r0 = t1->make_ptr(); // Handy access
1e026f8da827 6710487: More than half of JDI Regression tests hang with COOPs in -Xcomp mode
kvn
parents: 212
diff changeset
791 const TypePtr *r1 = t2->make_ptr();
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
792
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
793 // Undefined inputs makes for an undefined result
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
794 if( TypePtr::above_centerline(r0->_ptr) ||
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
795 TypePtr::above_centerline(r1->_ptr) )
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
796 return Type::TOP;
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
797
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
798 if (r0 == r1 && r0->singleton()) {
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
799 // Equal pointer constants (klasses, nulls, etc.)
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
800 return TypeInt::CC_EQ;
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
801 }
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
802
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
803 // See if it is 2 unrelated classes.
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
804 const TypeOopPtr* p0 = r0->isa_oopptr();
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
805 const TypeOopPtr* p1 = r1->isa_oopptr();
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
806 if (p0 && p1) {
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
807 ciKlass* klass0 = p0->klass();
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
808 bool xklass0 = p0->klass_is_exact();
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
809 ciKlass* klass1 = p1->klass();
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
810 bool xklass1 = p1->klass_is_exact();
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
811 int kps = (p0->isa_klassptr()?1:0) + (p1->isa_klassptr()?1:0);
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
812 if (klass0 && klass1 &&
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
813 kps != 1 && // both or neither are klass pointers
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
814 !klass0->is_interface() && // do not trust interfaces
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
815 !klass1->is_interface()) {
296
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
816 bool unrelated_classes = false;
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
817 // See if neither subclasses the other, or if the class on top
296
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
818 // is precise. In either of these cases, the compare is known
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
819 // to fail if at least one of the pointers is provably not null.
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
820 if (klass0->equals(klass1) || // if types are unequal but klasses are
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
821 !klass0->is_java_klass() || // types not part of Java language?
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
822 !klass1->is_java_klass()) { // types not part of Java language?
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
823 // Do nothing; we know nothing for imprecise types
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
824 } else if (klass0->is_subtype_of(klass1)) {
296
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
825 // If klass1's type is PRECISE, then classes are unrelated.
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
826 unrelated_classes = xklass1;
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
827 } else if (klass1->is_subtype_of(klass0)) {
296
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
828 // If klass0's type is PRECISE, then classes are unrelated.
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
829 unrelated_classes = xklass0;
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
830 } else { // Neither subtypes the other
296
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
831 unrelated_classes = true;
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
832 }
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
833 if (unrelated_classes) {
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
834 // The oops classes are known to be unrelated. If the joined PTRs of
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
835 // two oops is not Null and not Bottom, then we are sure that one
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
836 // of the two oops is non-null, and the comparison will always fail.
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
837 TypePtr::PTR jp = r0->join_ptr(r1->_ptr);
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
838 if (jp != TypePtr::Null && jp != TypePtr::BotPTR) {
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
839 return TypeInt::CC_GT;
ce93a51457ae 6730716: nulls from two unrelated classes compare not equal
rasbold
parents: 293
diff changeset
840 }
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
841 }
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
842 }
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
843 }
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
844
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
845 // Known constants can be compared exactly
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
846 // Null can be distinguished from any NotNull pointers
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
847 // Unknown inputs makes an unknown result
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
848 if( r0->singleton() ) {
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
849 intptr_t bits0 = r0->get_con();
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
850 if( r1->singleton() )
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
851 return bits0 == r1->get_con() ? TypeInt::CC_EQ : TypeInt::CC_GT;
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
852 return ( r1->_ptr == TypePtr::NotNull && bits0==0 ) ? TypeInt::CC_GT : TypeInt::CC;
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
853 } else if( r1->singleton() ) {
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
854 intptr_t bits1 = r1->get_con();
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
855 return ( r0->_ptr == TypePtr::NotNull && bits1==0 ) ? TypeInt::CC_GT : TypeInt::CC;
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
856 } else
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
857 return TypeInt::CC;
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
858 }
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
859
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
860 //------------------------------Ideal------------------------------------------
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
861 Node *CmpNNode::Ideal( PhaseGVN *phase, bool can_reshape ) {
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
862 return NULL;
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
863 }
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
864
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 33
diff changeset
865 //=============================================================================
0
a61af66fc99e Initial load
duke
parents:
diff changeset
866 //------------------------------Value------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
867 // Simplify an CmpF (compare 2 floats ) node, based on local information.
a61af66fc99e Initial load
duke
parents:
diff changeset
868 // If both inputs are constants, compare them.
a61af66fc99e Initial load
duke
parents:
diff changeset
869 const Type *CmpFNode::Value( PhaseTransform *phase ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
870 const Node* in1 = in(1);
a61af66fc99e Initial load
duke
parents:
diff changeset
871 const Node* in2 = in(2);
a61af66fc99e Initial load
duke
parents:
diff changeset
872 // Either input is TOP ==> the result is TOP
a61af66fc99e Initial load
duke
parents:
diff changeset
873 const Type* t1 = (in1 == this) ? Type::TOP : phase->type(in1);
a61af66fc99e Initial load
duke
parents:
diff changeset
874 if( t1 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
875 const Type* t2 = (in2 == this) ? Type::TOP : phase->type(in2);
a61af66fc99e Initial load
duke
parents:
diff changeset
876 if( t2 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
877
a61af66fc99e Initial load
duke
parents:
diff changeset
878 // Not constants? Don't know squat - even if they are the same
a61af66fc99e Initial load
duke
parents:
diff changeset
879 // value! If they are NaN's they compare to LT instead of EQ.
a61af66fc99e Initial load
duke
parents:
diff changeset
880 const TypeF *tf1 = t1->isa_float_constant();
a61af66fc99e Initial load
duke
parents:
diff changeset
881 const TypeF *tf2 = t2->isa_float_constant();
a61af66fc99e Initial load
duke
parents:
diff changeset
882 if( !tf1 || !tf2 ) return TypeInt::CC;
a61af66fc99e Initial load
duke
parents:
diff changeset
883
a61af66fc99e Initial load
duke
parents:
diff changeset
884 // This implements the Java bytecode fcmpl, so unordered returns -1.
a61af66fc99e Initial load
duke
parents:
diff changeset
885 if( tf1->is_nan() || tf2->is_nan() )
a61af66fc99e Initial load
duke
parents:
diff changeset
886 return TypeInt::CC_LT;
a61af66fc99e Initial load
duke
parents:
diff changeset
887
a61af66fc99e Initial load
duke
parents:
diff changeset
888 if( tf1->_f < tf2->_f ) return TypeInt::CC_LT;
a61af66fc99e Initial load
duke
parents:
diff changeset
889 if( tf1->_f > tf2->_f ) return TypeInt::CC_GT;
a61af66fc99e Initial load
duke
parents:
diff changeset
890 assert( tf1->_f == tf2->_f, "do not understand FP behavior" );
a61af66fc99e Initial load
duke
parents:
diff changeset
891 return TypeInt::CC_EQ;
a61af66fc99e Initial load
duke
parents:
diff changeset
892 }
a61af66fc99e Initial load
duke
parents:
diff changeset
893
a61af66fc99e Initial load
duke
parents:
diff changeset
894
a61af66fc99e Initial load
duke
parents:
diff changeset
895 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
896 //------------------------------Value------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
897 // Simplify an CmpD (compare 2 doubles ) node, based on local information.
a61af66fc99e Initial load
duke
parents:
diff changeset
898 // If both inputs are constants, compare them.
a61af66fc99e Initial load
duke
parents:
diff changeset
899 const Type *CmpDNode::Value( PhaseTransform *phase ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
900 const Node* in1 = in(1);
a61af66fc99e Initial load
duke
parents:
diff changeset
901 const Node* in2 = in(2);
a61af66fc99e Initial load
duke
parents:
diff changeset
902 // Either input is TOP ==> the result is TOP
a61af66fc99e Initial load
duke
parents:
diff changeset
903 const Type* t1 = (in1 == this) ? Type::TOP : phase->type(in1);
a61af66fc99e Initial load
duke
parents:
diff changeset
904 if( t1 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
905 const Type* t2 = (in2 == this) ? Type::TOP : phase->type(in2);
a61af66fc99e Initial load
duke
parents:
diff changeset
906 if( t2 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
907
a61af66fc99e Initial load
duke
parents:
diff changeset
908 // Not constants? Don't know squat - even if they are the same
a61af66fc99e Initial load
duke
parents:
diff changeset
909 // value! If they are NaN's they compare to LT instead of EQ.
a61af66fc99e Initial load
duke
parents:
diff changeset
910 const TypeD *td1 = t1->isa_double_constant();
a61af66fc99e Initial load
duke
parents:
diff changeset
911 const TypeD *td2 = t2->isa_double_constant();
a61af66fc99e Initial load
duke
parents:
diff changeset
912 if( !td1 || !td2 ) return TypeInt::CC;
a61af66fc99e Initial load
duke
parents:
diff changeset
913
a61af66fc99e Initial load
duke
parents:
diff changeset
914 // This implements the Java bytecode dcmpl, so unordered returns -1.
a61af66fc99e Initial load
duke
parents:
diff changeset
915 if( td1->is_nan() || td2->is_nan() )
a61af66fc99e Initial load
duke
parents:
diff changeset
916 return TypeInt::CC_LT;
a61af66fc99e Initial load
duke
parents:
diff changeset
917
a61af66fc99e Initial load
duke
parents:
diff changeset
918 if( td1->_d < td2->_d ) return TypeInt::CC_LT;
a61af66fc99e Initial load
duke
parents:
diff changeset
919 if( td1->_d > td2->_d ) return TypeInt::CC_GT;
a61af66fc99e Initial load
duke
parents:
diff changeset
920 assert( td1->_d == td2->_d, "do not understand FP behavior" );
a61af66fc99e Initial load
duke
parents:
diff changeset
921 return TypeInt::CC_EQ;
a61af66fc99e Initial load
duke
parents:
diff changeset
922 }
a61af66fc99e Initial load
duke
parents:
diff changeset
923
a61af66fc99e Initial load
duke
parents:
diff changeset
924 //------------------------------Ideal------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
925 Node *CmpDNode::Ideal(PhaseGVN *phase, bool can_reshape){
a61af66fc99e Initial load
duke
parents:
diff changeset
926 // Check if we can change this to a CmpF and remove a ConvD2F operation.
a61af66fc99e Initial load
duke
parents:
diff changeset
927 // Change (CMPD (F2D (float)) (ConD value))
a61af66fc99e Initial load
duke
parents:
diff changeset
928 // To (CMPF (float) (ConF value))
a61af66fc99e Initial load
duke
parents:
diff changeset
929 // Valid when 'value' does not lose precision as a float.
a61af66fc99e Initial load
duke
parents:
diff changeset
930 // Benefits: eliminates conversion, does not require 24-bit mode
a61af66fc99e Initial load
duke
parents:
diff changeset
931
a61af66fc99e Initial load
duke
parents:
diff changeset
932 // NaNs prevent commuting operands. This transform works regardless of the
a61af66fc99e Initial load
duke
parents:
diff changeset
933 // order of ConD and ConvF2D inputs by preserving the original order.
a61af66fc99e Initial load
duke
parents:
diff changeset
934 int idx_f2d = 1; // ConvF2D on left side?
a61af66fc99e Initial load
duke
parents:
diff changeset
935 if( in(idx_f2d)->Opcode() != Op_ConvF2D )
a61af66fc99e Initial load
duke
parents:
diff changeset
936 idx_f2d = 2; // No, swap to check for reversed args
a61af66fc99e Initial load
duke
parents:
diff changeset
937 int idx_con = 3-idx_f2d; // Check for the constant on other input
a61af66fc99e Initial load
duke
parents:
diff changeset
938
a61af66fc99e Initial load
duke
parents:
diff changeset
939 if( ConvertCmpD2CmpF &&
a61af66fc99e Initial load
duke
parents:
diff changeset
940 in(idx_f2d)->Opcode() == Op_ConvF2D &&
a61af66fc99e Initial load
duke
parents:
diff changeset
941 in(idx_con)->Opcode() == Op_ConD ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
942 const TypeD *t2 = in(idx_con)->bottom_type()->is_double_constant();
a61af66fc99e Initial load
duke
parents:
diff changeset
943 double t2_value_as_double = t2->_d;
a61af66fc99e Initial load
duke
parents:
diff changeset
944 float t2_value_as_float = (float)t2_value_as_double;
a61af66fc99e Initial load
duke
parents:
diff changeset
945 if( t2_value_as_double == (double)t2_value_as_float ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
946 // Test value can be represented as a float
a61af66fc99e Initial load
duke
parents:
diff changeset
947 // Eliminate the conversion to double and create new comparison
a61af66fc99e Initial load
duke
parents:
diff changeset
948 Node *new_in1 = in(idx_f2d)->in(1);
a61af66fc99e Initial load
duke
parents:
diff changeset
949 Node *new_in2 = phase->makecon( TypeF::make(t2_value_as_float) );
a61af66fc99e Initial load
duke
parents:
diff changeset
950 if( idx_f2d != 1 ) { // Must flip args to match original order
a61af66fc99e Initial load
duke
parents:
diff changeset
951 Node *tmp = new_in1;
a61af66fc99e Initial load
duke
parents:
diff changeset
952 new_in1 = new_in2;
a61af66fc99e Initial load
duke
parents:
diff changeset
953 new_in2 = tmp;
a61af66fc99e Initial load
duke
parents:
diff changeset
954 }
a61af66fc99e Initial load
duke
parents:
diff changeset
955 CmpFNode *new_cmp = (Opcode() == Op_CmpD3)
a61af66fc99e Initial load
duke
parents:
diff changeset
956 ? new (phase->C, 3) CmpF3Node( new_in1, new_in2 )
a61af66fc99e Initial load
duke
parents:
diff changeset
957 : new (phase->C, 3) CmpFNode ( new_in1, new_in2 ) ;
a61af66fc99e Initial load
duke
parents:
diff changeset
958 return new_cmp; // Changed to CmpFNode
a61af66fc99e Initial load
duke
parents:
diff changeset
959 }
a61af66fc99e Initial load
duke
parents:
diff changeset
960 // Testing value required the precision of a double
a61af66fc99e Initial load
duke
parents:
diff changeset
961 }
a61af66fc99e Initial load
duke
parents:
diff changeset
962 return NULL; // No change
a61af66fc99e Initial load
duke
parents:
diff changeset
963 }
a61af66fc99e Initial load
duke
parents:
diff changeset
964
a61af66fc99e Initial load
duke
parents:
diff changeset
965
a61af66fc99e Initial load
duke
parents:
diff changeset
966 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
967 //------------------------------cc2logical-------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
968 // Convert a condition code type to a logical type
a61af66fc99e Initial load
duke
parents:
diff changeset
969 const Type *BoolTest::cc2logical( const Type *CC ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
970 if( CC == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
971 if( CC->base() != Type::Int ) return TypeInt::BOOL; // Bottom or worse
a61af66fc99e Initial load
duke
parents:
diff changeset
972 const TypeInt *ti = CC->is_int();
a61af66fc99e Initial load
duke
parents:
diff changeset
973 if( ti->is_con() ) { // Only 1 kind of condition codes set?
a61af66fc99e Initial load
duke
parents:
diff changeset
974 // Match low order 2 bits
a61af66fc99e Initial load
duke
parents:
diff changeset
975 int tmp = ((ti->get_con()&3) == (_test&3)) ? 1 : 0;
a61af66fc99e Initial load
duke
parents:
diff changeset
976 if( _test & 4 ) tmp = 1-tmp; // Optionally complement result
a61af66fc99e Initial load
duke
parents:
diff changeset
977 return TypeInt::make(tmp); // Boolean result
a61af66fc99e Initial load
duke
parents:
diff changeset
978 }
a61af66fc99e Initial load
duke
parents:
diff changeset
979
a61af66fc99e Initial load
duke
parents:
diff changeset
980 if( CC == TypeInt::CC_GE ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
981 if( _test == ge ) return TypeInt::ONE;
a61af66fc99e Initial load
duke
parents:
diff changeset
982 if( _test == lt ) return TypeInt::ZERO;
a61af66fc99e Initial load
duke
parents:
diff changeset
983 }
a61af66fc99e Initial load
duke
parents:
diff changeset
984 if( CC == TypeInt::CC_LE ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
985 if( _test == le ) return TypeInt::ONE;
a61af66fc99e Initial load
duke
parents:
diff changeset
986 if( _test == gt ) return TypeInt::ZERO;
a61af66fc99e Initial load
duke
parents:
diff changeset
987 }
a61af66fc99e Initial load
duke
parents:
diff changeset
988
a61af66fc99e Initial load
duke
parents:
diff changeset
989 return TypeInt::BOOL;
a61af66fc99e Initial load
duke
parents:
diff changeset
990 }
a61af66fc99e Initial load
duke
parents:
diff changeset
991
a61af66fc99e Initial load
duke
parents:
diff changeset
992 //------------------------------dump_spec-------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
993 // Print special per-node info
a61af66fc99e Initial load
duke
parents:
diff changeset
994 #ifndef PRODUCT
a61af66fc99e Initial load
duke
parents:
diff changeset
995 void BoolTest::dump_on(outputStream *st) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
996 const char *msg[] = {"eq","gt","??","lt","ne","le","??","ge"};
a61af66fc99e Initial load
duke
parents:
diff changeset
997 st->print(msg[_test]);
a61af66fc99e Initial load
duke
parents:
diff changeset
998 }
a61af66fc99e Initial load
duke
parents:
diff changeset
999 #endif
a61af66fc99e Initial load
duke
parents:
diff changeset
1000
a61af66fc99e Initial load
duke
parents:
diff changeset
1001 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
1002 uint BoolNode::hash() const { return (Node::hash() << 3)|(_test._test+1); }
a61af66fc99e Initial load
duke
parents:
diff changeset
1003 uint BoolNode::size_of() const { return sizeof(BoolNode); }
a61af66fc99e Initial load
duke
parents:
diff changeset
1004
a61af66fc99e Initial load
duke
parents:
diff changeset
1005 //------------------------------operator==-------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1006 uint BoolNode::cmp( const Node &n ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
1007 const BoolNode *b = (const BoolNode *)&n; // Cast up
a61af66fc99e Initial load
duke
parents:
diff changeset
1008 return (_test._test == b->_test._test);
a61af66fc99e Initial load
duke
parents:
diff changeset
1009 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1010
a61af66fc99e Initial load
duke
parents:
diff changeset
1011 //------------------------------clone_cmp--------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1012 // Clone a compare/bool tree
a61af66fc99e Initial load
duke
parents:
diff changeset
1013 static Node *clone_cmp( Node *cmp, Node *cmp1, Node *cmp2, PhaseGVN *gvn, BoolTest::mask test ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1014 Node *ncmp = cmp->clone();
a61af66fc99e Initial load
duke
parents:
diff changeset
1015 ncmp->set_req(1,cmp1);
a61af66fc99e Initial load
duke
parents:
diff changeset
1016 ncmp->set_req(2,cmp2);
a61af66fc99e Initial load
duke
parents:
diff changeset
1017 ncmp = gvn->transform( ncmp );
a61af66fc99e Initial load
duke
parents:
diff changeset
1018 return new (gvn->C, 2) BoolNode( ncmp, test );
a61af66fc99e Initial load
duke
parents:
diff changeset
1019 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1020
a61af66fc99e Initial load
duke
parents:
diff changeset
1021 //-------------------------------make_predicate--------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1022 Node* BoolNode::make_predicate(Node* test_value, PhaseGVN* phase) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1023 if (test_value->is_Con()) return test_value;
a61af66fc99e Initial load
duke
parents:
diff changeset
1024 if (test_value->is_Bool()) return test_value;
a61af66fc99e Initial load
duke
parents:
diff changeset
1025 Compile* C = phase->C;
a61af66fc99e Initial load
duke
parents:
diff changeset
1026 if (test_value->is_CMove() &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1027 test_value->in(CMoveNode::Condition)->is_Bool()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1028 BoolNode* bol = test_value->in(CMoveNode::Condition)->as_Bool();
a61af66fc99e Initial load
duke
parents:
diff changeset
1029 const Type* ftype = phase->type(test_value->in(CMoveNode::IfFalse));
a61af66fc99e Initial load
duke
parents:
diff changeset
1030 const Type* ttype = phase->type(test_value->in(CMoveNode::IfTrue));
a61af66fc99e Initial load
duke
parents:
diff changeset
1031 if (ftype == TypeInt::ZERO && !TypeInt::ZERO->higher_equal(ttype)) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1032 return bol;
a61af66fc99e Initial load
duke
parents:
diff changeset
1033 } else if (ttype == TypeInt::ZERO && !TypeInt::ZERO->higher_equal(ftype)) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1034 return phase->transform( bol->negate(phase) );
a61af66fc99e Initial load
duke
parents:
diff changeset
1035 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1036 // Else fall through. The CMove gets in the way of the test.
a61af66fc99e Initial load
duke
parents:
diff changeset
1037 // It should be the case that make_predicate(bol->as_int_value()) == bol.
a61af66fc99e Initial load
duke
parents:
diff changeset
1038 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1039 Node* cmp = new (C, 3) CmpINode(test_value, phase->intcon(0));
a61af66fc99e Initial load
duke
parents:
diff changeset
1040 cmp = phase->transform(cmp);
a61af66fc99e Initial load
duke
parents:
diff changeset
1041 Node* bol = new (C, 2) BoolNode(cmp, BoolTest::ne);
a61af66fc99e Initial load
duke
parents:
diff changeset
1042 return phase->transform(bol);
a61af66fc99e Initial load
duke
parents:
diff changeset
1043 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1044
a61af66fc99e Initial load
duke
parents:
diff changeset
1045 //--------------------------------as_int_value---------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1046 Node* BoolNode::as_int_value(PhaseGVN* phase) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1047 // Inverse to make_predicate. The CMove probably boils down to a Conv2B.
a61af66fc99e Initial load
duke
parents:
diff changeset
1048 Node* cmov = CMoveNode::make(phase->C, NULL, this,
a61af66fc99e Initial load
duke
parents:
diff changeset
1049 phase->intcon(0), phase->intcon(1),
a61af66fc99e Initial load
duke
parents:
diff changeset
1050 TypeInt::BOOL);
a61af66fc99e Initial load
duke
parents:
diff changeset
1051 return phase->transform(cmov);
a61af66fc99e Initial load
duke
parents:
diff changeset
1052 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1053
a61af66fc99e Initial load
duke
parents:
diff changeset
1054 //----------------------------------negate-------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1055 BoolNode* BoolNode::negate(PhaseGVN* phase) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1056 Compile* C = phase->C;
a61af66fc99e Initial load
duke
parents:
diff changeset
1057 return new (C, 2) BoolNode(in(1), _test.negate());
a61af66fc99e Initial load
duke
parents:
diff changeset
1058 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1059
a61af66fc99e Initial load
duke
parents:
diff changeset
1060
a61af66fc99e Initial load
duke
parents:
diff changeset
1061 //------------------------------Ideal------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1062 Node *BoolNode::Ideal(PhaseGVN *phase, bool can_reshape) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1063 // Change "bool tst (cmp con x)" into "bool ~tst (cmp x con)".
a61af66fc99e Initial load
duke
parents:
diff changeset
1064 // This moves the constant to the right. Helps value-numbering.
a61af66fc99e Initial load
duke
parents:
diff changeset
1065 Node *cmp = in(1);
a61af66fc99e Initial load
duke
parents:
diff changeset
1066 if( !cmp->is_Sub() ) return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
1067 int cop = cmp->Opcode();
a61af66fc99e Initial load
duke
parents:
diff changeset
1068 if( cop == Op_FastLock || cop == Op_FastUnlock ) return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
1069 Node *cmp1 = cmp->in(1);
a61af66fc99e Initial load
duke
parents:
diff changeset
1070 Node *cmp2 = cmp->in(2);
a61af66fc99e Initial load
duke
parents:
diff changeset
1071 if( !cmp1 ) return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
1072
a61af66fc99e Initial load
duke
parents:
diff changeset
1073 // Constant on left?
a61af66fc99e Initial load
duke
parents:
diff changeset
1074 Node *con = cmp1;
a61af66fc99e Initial load
duke
parents:
diff changeset
1075 uint op2 = cmp2->Opcode();
a61af66fc99e Initial load
duke
parents:
diff changeset
1076 // Move constants to the right of compare's to canonicalize.
a61af66fc99e Initial load
duke
parents:
diff changeset
1077 // Do not muck with Opaque1 nodes, as this indicates a loop
a61af66fc99e Initial load
duke
parents:
diff changeset
1078 // guard that cannot change shape.
a61af66fc99e Initial load
duke
parents:
diff changeset
1079 if( con->is_Con() && !cmp2->is_Con() && op2 != Op_Opaque1 &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1080 // Because of NaN's, CmpD and CmpF are not commutative
a61af66fc99e Initial load
duke
parents:
diff changeset
1081 cop != Op_CmpD && cop != Op_CmpF &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1082 // Protect against swapping inputs to a compare when it is used by a
a61af66fc99e Initial load
duke
parents:
diff changeset
1083 // counted loop exit, which requires maintaining the loop-limit as in(2)
a61af66fc99e Initial load
duke
parents:
diff changeset
1084 !is_counted_loop_exit_test() ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1085 // Ok, commute the constant to the right of the cmp node.
a61af66fc99e Initial load
duke
parents:
diff changeset
1086 // Clone the Node, getting a new Node of the same class
a61af66fc99e Initial load
duke
parents:
diff changeset
1087 cmp = cmp->clone();
a61af66fc99e Initial load
duke
parents:
diff changeset
1088 // Swap inputs to the clone
a61af66fc99e Initial load
duke
parents:
diff changeset
1089 cmp->swap_edges(1, 2);
a61af66fc99e Initial load
duke
parents:
diff changeset
1090 cmp = phase->transform( cmp );
a61af66fc99e Initial load
duke
parents:
diff changeset
1091 return new (phase->C, 2) BoolNode( cmp, _test.commute() );
a61af66fc99e Initial load
duke
parents:
diff changeset
1092 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1093
a61af66fc99e Initial load
duke
parents:
diff changeset
1094 // Change "bool eq/ne (cmp (xor X 1) 0)" into "bool ne/eq (cmp X 0)".
a61af66fc99e Initial load
duke
parents:
diff changeset
1095 // The XOR-1 is an idiom used to flip the sense of a bool. We flip the
a61af66fc99e Initial load
duke
parents:
diff changeset
1096 // test instead.
a61af66fc99e Initial load
duke
parents:
diff changeset
1097 int cmp1_op = cmp1->Opcode();
a61af66fc99e Initial load
duke
parents:
diff changeset
1098 const TypeInt* cmp2_type = phase->type(cmp2)->isa_int();
a61af66fc99e Initial load
duke
parents:
diff changeset
1099 if (cmp2_type == NULL) return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
1100 Node* j_xor = cmp1;
a61af66fc99e Initial load
duke
parents:
diff changeset
1101 if( cmp2_type == TypeInt::ZERO &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1102 cmp1_op == Op_XorI &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1103 j_xor->in(1) != j_xor && // An xor of itself is dead
a61af66fc99e Initial load
duke
parents:
diff changeset
1104 phase->type( j_xor->in(2) ) == TypeInt::ONE &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1105 (_test._test == BoolTest::eq ||
a61af66fc99e Initial load
duke
parents:
diff changeset
1106 _test._test == BoolTest::ne) ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1107 Node *ncmp = phase->transform(new (phase->C, 3) CmpINode(j_xor->in(1),cmp2));
a61af66fc99e Initial load
duke
parents:
diff changeset
1108 return new (phase->C, 2) BoolNode( ncmp, _test.negate() );
a61af66fc99e Initial load
duke
parents:
diff changeset
1109 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1110
a61af66fc99e Initial load
duke
parents:
diff changeset
1111 // Change "bool eq/ne (cmp (Conv2B X) 0)" into "bool eq/ne (cmp X 0)".
a61af66fc99e Initial load
duke
parents:
diff changeset
1112 // This is a standard idiom for branching on a boolean value.
a61af66fc99e Initial load
duke
parents:
diff changeset
1113 Node *c2b = cmp1;
a61af66fc99e Initial load
duke
parents:
diff changeset
1114 if( cmp2_type == TypeInt::ZERO &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1115 cmp1_op == Op_Conv2B &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1116 (_test._test == BoolTest::eq ||
a61af66fc99e Initial load
duke
parents:
diff changeset
1117 _test._test == BoolTest::ne) ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1118 Node *ncmp = phase->transform(phase->type(c2b->in(1))->isa_int()
a61af66fc99e Initial load
duke
parents:
diff changeset
1119 ? (Node*)new (phase->C, 3) CmpINode(c2b->in(1),cmp2)
a61af66fc99e Initial load
duke
parents:
diff changeset
1120 : (Node*)new (phase->C, 3) CmpPNode(c2b->in(1),phase->makecon(TypePtr::NULL_PTR))
a61af66fc99e Initial load
duke
parents:
diff changeset
1121 );
a61af66fc99e Initial load
duke
parents:
diff changeset
1122 return new (phase->C, 2) BoolNode( ncmp, _test._test );
a61af66fc99e Initial load
duke
parents:
diff changeset
1123 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1124
a61af66fc99e Initial load
duke
parents:
diff changeset
1125 // Comparing a SubI against a zero is equal to comparing the SubI
a61af66fc99e Initial load
duke
parents:
diff changeset
1126 // arguments directly. This only works for eq and ne comparisons
a61af66fc99e Initial load
duke
parents:
diff changeset
1127 // due to possible integer overflow.
a61af66fc99e Initial load
duke
parents:
diff changeset
1128 if ((_test._test == BoolTest::eq || _test._test == BoolTest::ne) &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1129 (cop == Op_CmpI) &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1130 (cmp1->Opcode() == Op_SubI) &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1131 ( cmp2_type == TypeInt::ZERO ) ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1132 Node *ncmp = phase->transform( new (phase->C, 3) CmpINode(cmp1->in(1),cmp1->in(2)));
a61af66fc99e Initial load
duke
parents:
diff changeset
1133 return new (phase->C, 2) BoolNode( ncmp, _test._test );
a61af66fc99e Initial load
duke
parents:
diff changeset
1134 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1135
a61af66fc99e Initial load
duke
parents:
diff changeset
1136 // Change (-A vs 0) into (A vs 0) by commuting the test. Disallow in the
a61af66fc99e Initial load
duke
parents:
diff changeset
1137 // most general case because negating 0x80000000 does nothing. Needed for
a61af66fc99e Initial load
duke
parents:
diff changeset
1138 // the CmpF3/SubI/CmpI idiom.
a61af66fc99e Initial load
duke
parents:
diff changeset
1139 if( cop == Op_CmpI &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1140 cmp1->Opcode() == Op_SubI &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1141 cmp2_type == TypeInt::ZERO &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1142 phase->type( cmp1->in(1) ) == TypeInt::ZERO &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1143 phase->type( cmp1->in(2) )->higher_equal(TypeInt::SYMINT) ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1144 Node *ncmp = phase->transform( new (phase->C, 3) CmpINode(cmp1->in(2),cmp2));
a61af66fc99e Initial load
duke
parents:
diff changeset
1145 return new (phase->C, 2) BoolNode( ncmp, _test.commute() );
a61af66fc99e Initial load
duke
parents:
diff changeset
1146 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1147
a61af66fc99e Initial load
duke
parents:
diff changeset
1148 // The transformation below is not valid for either signed or unsigned
a61af66fc99e Initial load
duke
parents:
diff changeset
1149 // comparisons due to wraparound concerns at MAX_VALUE and MIN_VALUE.
a61af66fc99e Initial load
duke
parents:
diff changeset
1150 // This transformation can be resurrected when we are able to
a61af66fc99e Initial load
duke
parents:
diff changeset
1151 // make inferences about the range of values being subtracted from
a61af66fc99e Initial load
duke
parents:
diff changeset
1152 // (or added to) relative to the wraparound point.
a61af66fc99e Initial load
duke
parents:
diff changeset
1153 //
a61af66fc99e Initial load
duke
parents:
diff changeset
1154 // // Remove +/-1's if possible.
a61af66fc99e Initial load
duke
parents:
diff changeset
1155 // // "X <= Y-1" becomes "X < Y"
a61af66fc99e Initial load
duke
parents:
diff changeset
1156 // // "X+1 <= Y" becomes "X < Y"
a61af66fc99e Initial load
duke
parents:
diff changeset
1157 // // "X < Y+1" becomes "X <= Y"
a61af66fc99e Initial load
duke
parents:
diff changeset
1158 // // "X-1 < Y" becomes "X <= Y"
a61af66fc99e Initial load
duke
parents:
diff changeset
1159 // // Do not this to compares off of the counted-loop-end. These guys are
a61af66fc99e Initial load
duke
parents:
diff changeset
1160 // // checking the trip counter and they want to use the post-incremented
a61af66fc99e Initial load
duke
parents:
diff changeset
1161 // // counter. If they use the PRE-incremented counter, then the counter has
a61af66fc99e Initial load
duke
parents:
diff changeset
1162 // // to be incremented in a private block on a loop backedge.
a61af66fc99e Initial load
duke
parents:
diff changeset
1163 // if( du && du->cnt(this) && du->out(this)[0]->Opcode() == Op_CountedLoopEnd )
a61af66fc99e Initial load
duke
parents:
diff changeset
1164 // return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
1165 // #ifndef PRODUCT
a61af66fc99e Initial load
duke
parents:
diff changeset
1166 // // Do not do this in a wash GVN pass during verification.
a61af66fc99e Initial load
duke
parents:
diff changeset
1167 // // Gets triggered by too many simple optimizations to be bothered with
a61af66fc99e Initial load
duke
parents:
diff changeset
1168 // // re-trying it again and again.
a61af66fc99e Initial load
duke
parents:
diff changeset
1169 // if( !phase->allow_progress() ) return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
1170 // #endif
a61af66fc99e Initial load
duke
parents:
diff changeset
1171 // // Not valid for unsigned compare because of corner cases in involving zero.
a61af66fc99e Initial load
duke
parents:
diff changeset
1172 // // For example, replacing "X-1 <u Y" with "X <=u Y" fails to throw an
a61af66fc99e Initial load
duke
parents:
diff changeset
1173 // // exception in case X is 0 (because 0-1 turns into 4billion unsigned but
a61af66fc99e Initial load
duke
parents:
diff changeset
1174 // // "0 <=u Y" is always true).
a61af66fc99e Initial load
duke
parents:
diff changeset
1175 // if( cmp->Opcode() == Op_CmpU ) return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
1176 // int cmp2_op = cmp2->Opcode();
a61af66fc99e Initial load
duke
parents:
diff changeset
1177 // if( _test._test == BoolTest::le ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1178 // if( cmp1_op == Op_AddI &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1179 // phase->type( cmp1->in(2) ) == TypeInt::ONE )
a61af66fc99e Initial load
duke
parents:
diff changeset
1180 // return clone_cmp( cmp, cmp1->in(1), cmp2, phase, BoolTest::lt );
a61af66fc99e Initial load
duke
parents:
diff changeset
1181 // else if( cmp2_op == Op_AddI &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1182 // phase->type( cmp2->in(2) ) == TypeInt::MINUS_1 )
a61af66fc99e Initial load
duke
parents:
diff changeset
1183 // return clone_cmp( cmp, cmp1, cmp2->in(1), phase, BoolTest::lt );
a61af66fc99e Initial load
duke
parents:
diff changeset
1184 // } else if( _test._test == BoolTest::lt ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1185 // if( cmp1_op == Op_AddI &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1186 // phase->type( cmp1->in(2) ) == TypeInt::MINUS_1 )
a61af66fc99e Initial load
duke
parents:
diff changeset
1187 // return clone_cmp( cmp, cmp1->in(1), cmp2, phase, BoolTest::le );
a61af66fc99e Initial load
duke
parents:
diff changeset
1188 // else if( cmp2_op == Op_AddI &&
a61af66fc99e Initial load
duke
parents:
diff changeset
1189 // phase->type( cmp2->in(2) ) == TypeInt::ONE )
a61af66fc99e Initial load
duke
parents:
diff changeset
1190 // return clone_cmp( cmp, cmp1, cmp2->in(1), phase, BoolTest::le );
a61af66fc99e Initial load
duke
parents:
diff changeset
1191 // }
a61af66fc99e Initial load
duke
parents:
diff changeset
1192
a61af66fc99e Initial load
duke
parents:
diff changeset
1193 return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
1194 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1195
a61af66fc99e Initial load
duke
parents:
diff changeset
1196 //------------------------------Value------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1197 // Simplify a Bool (convert condition codes to boolean (1 or 0)) node,
a61af66fc99e Initial load
duke
parents:
diff changeset
1198 // based on local information. If the input is constant, do it.
a61af66fc99e Initial load
duke
parents:
diff changeset
1199 const Type *BoolNode::Value( PhaseTransform *phase ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
1200 return _test.cc2logical( phase->type( in(1) ) );
a61af66fc99e Initial load
duke
parents:
diff changeset
1201 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1202
a61af66fc99e Initial load
duke
parents:
diff changeset
1203 //------------------------------dump_spec--------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1204 // Dump special per-node info
a61af66fc99e Initial load
duke
parents:
diff changeset
1205 #ifndef PRODUCT
a61af66fc99e Initial load
duke
parents:
diff changeset
1206 void BoolNode::dump_spec(outputStream *st) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
1207 st->print("[");
a61af66fc99e Initial load
duke
parents:
diff changeset
1208 _test.dump_on(st);
a61af66fc99e Initial load
duke
parents:
diff changeset
1209 st->print("]");
a61af66fc99e Initial load
duke
parents:
diff changeset
1210 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1211 #endif
a61af66fc99e Initial load
duke
parents:
diff changeset
1212
a61af66fc99e Initial load
duke
parents:
diff changeset
1213 //------------------------------is_counted_loop_exit_test--------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1214 // Returns true if node is used by a counted loop node.
a61af66fc99e Initial load
duke
parents:
diff changeset
1215 bool BoolNode::is_counted_loop_exit_test() {
a61af66fc99e Initial load
duke
parents:
diff changeset
1216 for( DUIterator_Fast imax, i = fast_outs(imax); i < imax; i++ ) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1217 Node* use = fast_out(i);
a61af66fc99e Initial load
duke
parents:
diff changeset
1218 if (use->is_CountedLoopEnd()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1219 return true;
a61af66fc99e Initial load
duke
parents:
diff changeset
1220 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1221 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1222 return false;
a61af66fc99e Initial load
duke
parents:
diff changeset
1223 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1224
a61af66fc99e Initial load
duke
parents:
diff changeset
1225 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
1226 //------------------------------NegNode----------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1227 Node *NegFNode::Ideal(PhaseGVN *phase, bool can_reshape) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1228 if( in(1)->Opcode() == Op_SubF )
a61af66fc99e Initial load
duke
parents:
diff changeset
1229 return new (phase->C, 3) SubFNode( in(1)->in(2), in(1)->in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
1230 return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
1231 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1232
a61af66fc99e Initial load
duke
parents:
diff changeset
1233 Node *NegDNode::Ideal(PhaseGVN *phase, bool can_reshape) {
a61af66fc99e Initial load
duke
parents:
diff changeset
1234 if( in(1)->Opcode() == Op_SubD )
a61af66fc99e Initial load
duke
parents:
diff changeset
1235 return new (phase->C, 3) SubDNode( in(1)->in(2), in(1)->in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
1236 return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
1237 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1238
a61af66fc99e Initial load
duke
parents:
diff changeset
1239
a61af66fc99e Initial load
duke
parents:
diff changeset
1240 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
1241 //------------------------------Value------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1242 // Compute sqrt
a61af66fc99e Initial load
duke
parents:
diff changeset
1243 const Type *SqrtDNode::Value( PhaseTransform *phase ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
1244 const Type *t1 = phase->type( in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
1245 if( t1 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
1246 if( t1->base() != Type::DoubleCon ) return Type::DOUBLE;
a61af66fc99e Initial load
duke
parents:
diff changeset
1247 double d = t1->getd();
a61af66fc99e Initial load
duke
parents:
diff changeset
1248 if( d < 0.0 ) return Type::DOUBLE;
a61af66fc99e Initial load
duke
parents:
diff changeset
1249 return TypeD::make( sqrt( d ) );
a61af66fc99e Initial load
duke
parents:
diff changeset
1250 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1251
a61af66fc99e Initial load
duke
parents:
diff changeset
1252 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
1253 //------------------------------Value------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1254 // Compute cos
a61af66fc99e Initial load
duke
parents:
diff changeset
1255 const Type *CosDNode::Value( PhaseTransform *phase ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
1256 const Type *t1 = phase->type( in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
1257 if( t1 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
1258 if( t1->base() != Type::DoubleCon ) return Type::DOUBLE;
a61af66fc99e Initial load
duke
parents:
diff changeset
1259 double d = t1->getd();
1174
ddb7834449d0 6849984: Value methods for platform dependent math functions constant fold incorrectly
never
parents: 844
diff changeset
1260 return TypeD::make( StubRoutines::intrinsic_cos( d ) );
0
a61af66fc99e Initial load
duke
parents:
diff changeset
1261 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1262
a61af66fc99e Initial load
duke
parents:
diff changeset
1263 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
1264 //------------------------------Value------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1265 // Compute sin
a61af66fc99e Initial load
duke
parents:
diff changeset
1266 const Type *SinDNode::Value( PhaseTransform *phase ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
1267 const Type *t1 = phase->type( in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
1268 if( t1 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
1269 if( t1->base() != Type::DoubleCon ) return Type::DOUBLE;
a61af66fc99e Initial load
duke
parents:
diff changeset
1270 double d = t1->getd();
1174
ddb7834449d0 6849984: Value methods for platform dependent math functions constant fold incorrectly
never
parents: 844
diff changeset
1271 return TypeD::make( StubRoutines::intrinsic_sin( d ) );
0
a61af66fc99e Initial load
duke
parents:
diff changeset
1272 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1273
a61af66fc99e Initial load
duke
parents:
diff changeset
1274 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
1275 //------------------------------Value------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1276 // Compute tan
a61af66fc99e Initial load
duke
parents:
diff changeset
1277 const Type *TanDNode::Value( PhaseTransform *phase ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
1278 const Type *t1 = phase->type( in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
1279 if( t1 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
1280 if( t1->base() != Type::DoubleCon ) return Type::DOUBLE;
a61af66fc99e Initial load
duke
parents:
diff changeset
1281 double d = t1->getd();
1174
ddb7834449d0 6849984: Value methods for platform dependent math functions constant fold incorrectly
never
parents: 844
diff changeset
1282 return TypeD::make( StubRoutines::intrinsic_tan( d ) );
0
a61af66fc99e Initial load
duke
parents:
diff changeset
1283 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1284
a61af66fc99e Initial load
duke
parents:
diff changeset
1285 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
1286 //------------------------------Value------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1287 // Compute log
a61af66fc99e Initial load
duke
parents:
diff changeset
1288 const Type *LogDNode::Value( PhaseTransform *phase ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
1289 const Type *t1 = phase->type( in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
1290 if( t1 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
1291 if( t1->base() != Type::DoubleCon ) return Type::DOUBLE;
a61af66fc99e Initial load
duke
parents:
diff changeset
1292 double d = t1->getd();
1174
ddb7834449d0 6849984: Value methods for platform dependent math functions constant fold incorrectly
never
parents: 844
diff changeset
1293 return TypeD::make( StubRoutines::intrinsic_log( d ) );
0
a61af66fc99e Initial load
duke
parents:
diff changeset
1294 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1295
a61af66fc99e Initial load
duke
parents:
diff changeset
1296 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
1297 //------------------------------Value------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1298 // Compute log10
a61af66fc99e Initial load
duke
parents:
diff changeset
1299 const Type *Log10DNode::Value( PhaseTransform *phase ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
1300 const Type *t1 = phase->type( in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
1301 if( t1 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
1302 if( t1->base() != Type::DoubleCon ) return Type::DOUBLE;
a61af66fc99e Initial load
duke
parents:
diff changeset
1303 double d = t1->getd();
1174
ddb7834449d0 6849984: Value methods for platform dependent math functions constant fold incorrectly
never
parents: 844
diff changeset
1304 return TypeD::make( StubRoutines::intrinsic_log10( d ) );
0
a61af66fc99e Initial load
duke
parents:
diff changeset
1305 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1306
a61af66fc99e Initial load
duke
parents:
diff changeset
1307 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
1308 //------------------------------Value------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1309 // Compute exp
a61af66fc99e Initial load
duke
parents:
diff changeset
1310 const Type *ExpDNode::Value( PhaseTransform *phase ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
1311 const Type *t1 = phase->type( in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
1312 if( t1 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
1313 if( t1->base() != Type::DoubleCon ) return Type::DOUBLE;
a61af66fc99e Initial load
duke
parents:
diff changeset
1314 double d = t1->getd();
1174
ddb7834449d0 6849984: Value methods for platform dependent math functions constant fold incorrectly
never
parents: 844
diff changeset
1315 return TypeD::make( StubRoutines::intrinsic_exp( d ) );
0
a61af66fc99e Initial load
duke
parents:
diff changeset
1316 }
a61af66fc99e Initial load
duke
parents:
diff changeset
1317
a61af66fc99e Initial load
duke
parents:
diff changeset
1318
a61af66fc99e Initial load
duke
parents:
diff changeset
1319 //=============================================================================
a61af66fc99e Initial load
duke
parents:
diff changeset
1320 //------------------------------Value------------------------------------------
a61af66fc99e Initial load
duke
parents:
diff changeset
1321 // Compute pow
a61af66fc99e Initial load
duke
parents:
diff changeset
1322 const Type *PowDNode::Value( PhaseTransform *phase ) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
1323 const Type *t1 = phase->type( in(1) );
a61af66fc99e Initial load
duke
parents:
diff changeset
1324 if( t1 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
1325 if( t1->base() != Type::DoubleCon ) return Type::DOUBLE;
a61af66fc99e Initial load
duke
parents:
diff changeset
1326 const Type *t2 = phase->type( in(2) );
a61af66fc99e Initial load
duke
parents:
diff changeset
1327 if( t2 == Type::TOP ) return Type::TOP;
a61af66fc99e Initial load
duke
parents:
diff changeset
1328 if( t2->base() != Type::DoubleCon ) return Type::DOUBLE;
a61af66fc99e Initial load
duke
parents:
diff changeset
1329 double d1 = t1->getd();
a61af66fc99e Initial load
duke
parents:
diff changeset
1330 double d2 = t2->getd();
a61af66fc99e Initial load
duke
parents:
diff changeset
1331 if( d1 < 0.0 ) return Type::DOUBLE;
a61af66fc99e Initial load
duke
parents:
diff changeset
1332 if( d2 < 0.0 ) return Type::DOUBLE;
1174
ddb7834449d0 6849984: Value methods for platform dependent math functions constant fold incorrectly
never
parents: 844
diff changeset
1333 return TypeD::make( StubRoutines::intrinsic_pow( d1, d2 ) );
0
a61af66fc99e Initial load
duke
parents:
diff changeset
1334 }