263 //------------------------------CmpD3Node--------------------------------------
264 // Compare 2 double values, returning integer value (-1, 0 or 1).
265 // This implements the Java bytecode dcmpl, so unordered returns -1.
266 // Operands may not commute.
267 class CmpD3Node : public CmpDNode {
268 public:
269 CmpD3Node( Node *in1, Node *in2 ) : CmpDNode(in1,in2) {
270 // Since it is not consumed by Bools, it is not really a Cmp.
271 init_class_id(Class_Sub);
272 }
273 virtual int Opcode() const;
274 virtual uint ideal_reg() const { return Op_RegI; }
275 };
276
277
278 //------------------------------BoolTest---------------------------------------
279 // Convert condition codes to a boolean test value (0 or -1).
280 // We pick the values as 3 bits; the low order 2 bits we compare against the
281 // condition codes, the high bit flips the sense of the result.
282 struct BoolTest {
283 enum mask { eq = 0, ne = 4, le = 5, ge = 7, lt = 3, gt = 1, overflow = 2, no_overflow = 6, illegal = 8 };
284 mask _test;
285 BoolTest( mask btm ) : _test(btm) {}
286 const Type *cc2logical( const Type *CC ) const;
287 // Commute the test. I use a small table lookup. The table is created as
288 // a simple char array where each element is the ASCII version of a 'mask'
289 // enum from above.
290 mask commute( ) const { return mask("032147658"[_test]-'0'); }
291 mask negate( ) const { return mask(_test^4); }
292 bool is_canonical( ) const { return (_test == BoolTest::ne || _test == BoolTest::lt || _test == BoolTest::le || _test == BoolTest::overflow); }
293 bool is_less( ) const { return _test == BoolTest::lt || _test == BoolTest::le; }
294 bool is_greater( ) const { return _test == BoolTest::gt || _test == BoolTest::ge; }
295 void dump_on(outputStream *st) const;
296 };
297
298 //------------------------------BoolNode---------------------------------------
299 // A Node to convert a Condition Codes to a Logical result.
300 class BoolNode : public Node {
301 virtual uint hash() const;
302 virtual uint cmp( const Node &n ) const;
303 virtual uint size_of() const;
304
305 // Try to optimize signed integer comparison
306 Node* fold_cmpI(PhaseGVN* phase, SubNode* cmp, Node* cmp1, int cmp_op,
307 int cmp1_op, const TypeInt* cmp2_type);
308 public:
309 const BoolTest _test;
310 BoolNode( Node *cc, BoolTest::mask t): Node(0,cc), _test(t) {
311 init_class_id(Class_Bool);
312 }
313 // Convert an arbitrary int value to a Bool or other suitable predicate.
314 static Node* make_predicate(Node* test_value, PhaseGVN* phase);
315 // Convert self back to an integer value.
|
263 //------------------------------CmpD3Node--------------------------------------
264 // Compare 2 double values, returning integer value (-1, 0 or 1).
265 // This implements the Java bytecode dcmpl, so unordered returns -1.
266 // Operands may not commute.
267 class CmpD3Node : public CmpDNode {
268 public:
269 CmpD3Node( Node *in1, Node *in2 ) : CmpDNode(in1,in2) {
270 // Since it is not consumed by Bools, it is not really a Cmp.
271 init_class_id(Class_Sub);
272 }
273 virtual int Opcode() const;
274 virtual uint ideal_reg() const { return Op_RegI; }
275 };
276
277
278 //------------------------------BoolTest---------------------------------------
279 // Convert condition codes to a boolean test value (0 or -1).
280 // We pick the values as 3 bits; the low order 2 bits we compare against the
281 // condition codes, the high bit flips the sense of the result.
282 struct BoolTest {
283 enum mask { eq = 0, ne = 4, le = 5, ge = 7, lt = 3, gt = 1, overflow = 2, no_overflow = 6, never = 8, illegal = 9 };
284 mask _test;
285 BoolTest( mask btm ) : _test(btm) {}
286 const Type *cc2logical( const Type *CC ) const;
287 // Commute the test. I use a small table lookup. The table is created as
288 // a simple char array where each element is the ASCII version of a 'mask'
289 // enum from above.
290 mask commute( ) const { return mask("032147658"[_test]-'0'); }
291 mask negate( ) const { return mask(_test^4); }
292 bool is_canonical( ) const { return (_test == BoolTest::ne || _test == BoolTest::lt || _test == BoolTest::le || _test == BoolTest::overflow); }
293 bool is_less( ) const { return _test == BoolTest::lt || _test == BoolTest::le; }
294 bool is_greater( ) const { return _test == BoolTest::gt || _test == BoolTest::ge; }
295 void dump_on(outputStream *st) const;
296 mask merge(BoolTest other) const;
297 };
298
299 //------------------------------BoolNode---------------------------------------
300 // A Node to convert a Condition Codes to a Logical result.
301 class BoolNode : public Node {
302 virtual uint hash() const;
303 virtual uint cmp( const Node &n ) const;
304 virtual uint size_of() const;
305
306 // Try to optimize signed integer comparison
307 Node* fold_cmpI(PhaseGVN* phase, SubNode* cmp, Node* cmp1, int cmp_op,
308 int cmp1_op, const TypeInt* cmp2_type);
309 public:
310 const BoolTest _test;
311 BoolNode( Node *cc, BoolTest::mask t): Node(0,cc), _test(t) {
312 init_class_id(Class_Bool);
313 }
314 // Convert an arbitrary int value to a Bool or other suitable predicate.
315 static Node* make_predicate(Node* test_value, PhaseGVN* phase);
316 // Convert self back to an integer value.
|