1 /*
  2  * Copyright (c) 2014, 2019, Oracle and/or its affiliates. All rights reserved.
  3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  4  *
  5  * This code is free software; you can redistribute it and/or modify it
  6  * under the terms of the GNU General Public License version 2 only, as
  7  * published by the Free Software Foundation.
  8  *
  9  * This code is distributed in the hope that it will be useful, but WITHOUT
 10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
 12  * version 2 for more details (a copy is included in the LICENSE file that
 13  * accompanied this code).
 14  *
 15  * You should have received a copy of the GNU General Public License version
 16  * 2 along with this work; if not, write to the Free Software Foundation,
 17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 18  *
 19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 20  * or visit www.oracle.com if you need additional information or have any
 21  * questions.
 22  *
 23  */
 24 
 25 #ifndef SHARE_OPTO_CONVERTNODE_HPP
 26 #define SHARE_OPTO_CONVERTNODE_HPP
 27 
 28 #include "opto/node.hpp"
 29 #include "opto/opcodes.hpp"
 30 
 31 
 32 //------------------------------Conv2BNode-------------------------------------
 33 // Convert int/pointer to a Boolean.  Map zero to zero, all else to 1.
 34 class Conv2BNode : public Node {
 35   public:
 36   Conv2BNode( Node *i ) : Node(0,i) {}
 37   virtual int Opcode() const;
 38   virtual const Type *bottom_type() const { return TypeInt::BOOL; }
 39   virtual Node* Identity(PhaseGVN* phase);
 40   virtual const Type* Value(PhaseGVN* phase) const;
 41   virtual uint  ideal_reg() const { return Op_RegI; }
 42 };
 43 
 44 // The conversions operations are all Alpha sorted.  Please keep it that way!
 45 //------------------------------ConvD2FNode------------------------------------
 46 // Convert double to float
 47 class ConvD2FNode : public Node {
 48   public:
 49   ConvD2FNode( Node *in1 ) : Node(0,in1) {}
 50   virtual int Opcode() const;
 51   virtual const Type *bottom_type() const { return Type::FLOAT; }
 52   virtual const Type* Value(PhaseGVN* phase) const;
 53   virtual Node* Identity(PhaseGVN* phase);
 54   virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
 55   virtual uint  ideal_reg() const { return Op_RegF; }
 56 };
 57 
 58 //------------------------------ConvD2INode------------------------------------
 59 // Convert Double to Integer
 60 class ConvD2INode : public Node {
 61   public:
 62   ConvD2INode( Node *in1 ) : Node(0,in1) {}
 63   virtual int Opcode() const;
 64   virtual const Type *bottom_type() const { return TypeInt::INT; }
 65   virtual const Type* Value(PhaseGVN* phase) const;
 66   virtual Node* Identity(PhaseGVN* phase);
 67   virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
 68   virtual uint  ideal_reg() const { return Op_RegI; }
 69 };
 70 
 71 //------------------------------ConvD2LNode------------------------------------
 72 // Convert Double to Long
 73 class ConvD2LNode : public Node {
 74   public:
 75   ConvD2LNode( Node *dbl ) : Node(0,dbl) {}
 76   virtual int Opcode() const;
 77   virtual const Type *bottom_type() const { return TypeLong::LONG; }
 78   virtual const Type* Value(PhaseGVN* phase) const;
 79   virtual Node* Identity(PhaseGVN* phase);
 80   virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
 81   virtual uint ideal_reg() const { return Op_RegL; }
 82 };
 83 
 84 //------------------------------ConvF2DNode------------------------------------
 85 // Convert Float to a Double.
 86 class ConvF2DNode : public Node {
 87   public:
 88   ConvF2DNode( Node *in1 ) : Node(0,in1) {}
 89   virtual int Opcode() const;
 90   virtual const Type *bottom_type() const { return Type::DOUBLE; }
 91   virtual const Type* Value(PhaseGVN* phase) const;
 92   virtual uint  ideal_reg() const { return Op_RegD; }
 93 };
 94 
 95 //------------------------------ConvF2INode------------------------------------
 96 // Convert float to integer
 97 class ConvF2INode : public Node {
 98   public:
 99   ConvF2INode( Node *in1 ) : Node(0,in1) {}
100   virtual int Opcode() const;
101   virtual const Type *bottom_type() const { return TypeInt::INT; }
102   virtual const Type* Value(PhaseGVN* phase) const;
103   virtual Node* Identity(PhaseGVN* phase);
104   virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
105   virtual uint  ideal_reg() const { return Op_RegI; }
106 };
107 
108 //------------------------------ConvF2LNode------------------------------------
109 // Convert float to long
110 class ConvF2LNode : public Node {
111   public:
112   ConvF2LNode( Node *in1 ) : Node(0,in1) {}
113   virtual int Opcode() const;
114   virtual const Type *bottom_type() const { return TypeLong::LONG; }
115   virtual const Type* Value(PhaseGVN* phase) const;
116   virtual Node* Identity(PhaseGVN* phase);
117   virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
118   virtual uint  ideal_reg() const { return Op_RegL; }
119 };
120 
121 //------------------------------ConvI2DNode------------------------------------
122 // Convert Integer to Double
123 class ConvI2DNode : public Node {
124   public:
125   ConvI2DNode( Node *in1 ) : Node(0,in1) {}
126   virtual int Opcode() const;
127   virtual const Type *bottom_type() const { return Type::DOUBLE; }
128   virtual const Type* Value(PhaseGVN* phase) const;
129   virtual uint  ideal_reg() const { return Op_RegD; }
130 };
131 
132 //------------------------------ConvI2FNode------------------------------------
133 // Convert Integer to Float
134 class ConvI2FNode : public Node {
135   public:
136   ConvI2FNode( Node *in1 ) : Node(0,in1) {}
137   virtual int Opcode() const;
138   virtual const Type *bottom_type() const { return Type::FLOAT; }
139   virtual const Type* Value(PhaseGVN* phase) const;
140   virtual Node* Identity(PhaseGVN* phase);
141   virtual uint  ideal_reg() const { return Op_RegF; }
142 };
143 
144 //------------------------------ConvI2LNode------------------------------------
145 // Convert integer to long
146 class ConvI2LNode : public TypeNode {
147   public:
148   ConvI2LNode(Node *in1, const TypeLong* t = TypeLong::INT)
149   : TypeNode(t, 2)
150   { init_req(1, in1); }
151   virtual int Opcode() const;
152   virtual const Type* Value(PhaseGVN* phase) const;
153   virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
154   virtual uint  ideal_reg() const { return Op_RegL; }
155 };
156 
157 //------------------------------ConvL2DNode------------------------------------
158 // Convert Long to Double
159 class ConvL2DNode : public Node {
160   public:
161   ConvL2DNode( Node *in1 ) : Node(0,in1) {}
162   virtual int Opcode() const;
163   virtual const Type *bottom_type() const { return Type::DOUBLE; }
164   virtual const Type* Value(PhaseGVN* phase) const;
165   virtual uint ideal_reg() const { return Op_RegD; }
166 };
167 
168 //------------------------------ConvL2FNode------------------------------------
169 // Convert Long to Float
170 class ConvL2FNode : public Node {
171   public:
172   ConvL2FNode( Node *in1 ) : Node(0,in1) {}
173   virtual int Opcode() const;
174   virtual const Type *bottom_type() const { return Type::FLOAT; }
175   virtual const Type* Value(PhaseGVN* phase) const;
176   virtual uint  ideal_reg() const { return Op_RegF; }
177 };
178 
179 //------------------------------ConvL2INode------------------------------------
180 // Convert long to integer
181 class ConvL2INode : public TypeNode {
182   public:
183   ConvL2INode(Node *in1, const TypeInt* t = TypeInt::INT)
184   : TypeNode(t, 2) {
185     init_req(1, in1);
186   }
187   virtual int Opcode() const;
188   virtual Node* Identity(PhaseGVN* phase);
189   virtual const Type* Value(PhaseGVN* phase) const;
190   virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
191   virtual uint  ideal_reg() const { return Op_RegI; }
192 };
193 
194 //-----------------------------RoundFloatNode----------------------------------
195 class RoundFloatNode: public Node {
196   public:
197   RoundFloatNode(Node* c, Node *in1): Node(c, in1) {}
198   virtual int   Opcode() const;
199   virtual const Type *bottom_type() const { return Type::FLOAT; }
200   virtual uint  ideal_reg() const { return Op_RegF; }
201   virtual Node* Identity(PhaseGVN* phase);
202   virtual const Type* Value(PhaseGVN* phase) const;
203 };
204 
205 
206 //-----------------------------RoundDoubleNode---------------------------------
207 class RoundDoubleNode: public Node {
208   public:
209   RoundDoubleNode(Node* c, Node *in1): Node(c, in1) {}
210   virtual int   Opcode() const;
211   virtual const Type *bottom_type() const { return Type::DOUBLE; }
212   virtual uint  ideal_reg() const { return Op_RegD; }
213   virtual Node* Identity(PhaseGVN* phase);
214   virtual const Type* Value(PhaseGVN* phase) const;
215 };
216 
217 //-----------------------------RoundDoubleModeNode-----------------------------
218 class RoundDoubleModeNode: public Node {
219   public:
220   enum RoundingMode {
221     rmode_rint  = 0,
222     rmode_floor = 1,
223     rmode_ceil  = 2
224   };
225   RoundDoubleModeNode(Node *in1, Node * rmode): Node(0, in1, rmode) {}
226   static RoundDoubleModeNode* make(PhaseGVN& gvn, Node* arg, RoundDoubleModeNode::RoundingMode rmode);
227   virtual int   Opcode() const;
228   virtual const Type *bottom_type() const { return Type::DOUBLE; }
229   virtual uint  ideal_reg() const { return Op_RegD; }
230   virtual Node* Identity(PhaseGVN* phase);
231   virtual const Type* Value(PhaseGVN* phase) const;
232 };
233 
234 
235 #endif // SHARE_OPTO_CONVERTNODE_HPP