Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
PojavLauncherTeam
GitHub Repository: PojavLauncherTeam/jdk17u
Path: blob/master/src/hotspot/share/opto/addnode.hpp
64440 views
1
/*
2
* Copyright (c) 1997, 2021, 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_ADDNODE_HPP
26
#define SHARE_OPTO_ADDNODE_HPP
27
28
#include "opto/node.hpp"
29
#include "opto/opcodes.hpp"
30
#include "opto/type.hpp"
31
32
// Portions of code courtesy of Clifford Click
33
34
class PhaseTransform;
35
36
//------------------------------AddNode----------------------------------------
37
// Classic Add functionality. This covers all the usual 'add' behaviors for
38
// an algebraic ring. Add-integer, add-float, add-double, and binary-or are
39
// all inherited from this class. The various identity values are supplied
40
// by virtual functions.
41
class AddNode : public Node {
42
virtual uint hash() const;
43
public:
44
AddNode( Node *in1, Node *in2 ) : Node(0,in1,in2) {
45
init_class_id(Class_Add);
46
}
47
48
// Handle algebraic identities here. If we have an identity, return the Node
49
// we are equivalent to. We look for "add of zero" as an identity.
50
virtual Node* Identity(PhaseGVN* phase);
51
52
// We also canonicalize the Node, moving constants to the right input,
53
// and flatten expressions (so that 1+x+2 becomes x+3).
54
virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
55
56
// Compute a new Type for this node. Basically we just do the pre-check,
57
// then call the virtual add() to set the type.
58
virtual const Type* Value(PhaseGVN* phase) const;
59
60
// Check if this addition involves the additive identity
61
virtual const Type *add_of_identity( const Type *t1, const Type *t2 ) const;
62
63
// Supplied function returns the sum of the inputs.
64
// This also type-checks the inputs for sanity. Guaranteed never to
65
// be passed a TOP or BOTTOM type, these are filtered out by a pre-check.
66
virtual const Type *add_ring( const Type *, const Type * ) const = 0;
67
68
// Supplied function to return the additive identity type
69
virtual const Type *add_id() const = 0;
70
71
// Supplied function to return the additive opcode
72
virtual int max_opcode() const = 0;
73
74
// Supplied function to return the multiplicative opcode
75
virtual int min_opcode() const = 0;
76
77
virtual bool operates_on(BasicType bt, bool signed_int) const {
78
assert(bt == T_INT || bt == T_LONG, "unsupported");
79
return false;
80
}
81
static AddNode* make(Node* in1, Node* in2, BasicType bt);
82
};
83
84
//------------------------------AddINode---------------------------------------
85
// Add 2 integers
86
class AddINode : public AddNode {
87
public:
88
AddINode( Node *in1, Node *in2 ) : AddNode(in1,in2) {}
89
virtual int Opcode() const;
90
virtual const Type *add_ring( const Type *, const Type * ) const;
91
virtual const Type *add_id() const { return TypeInt::ZERO; }
92
virtual const Type *bottom_type() const { return TypeInt::INT; }
93
int max_opcode() const { return Op_MaxI; }
94
int min_opcode() const { return Op_MinI; }
95
virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
96
virtual Node* Identity(PhaseGVN* phase);
97
virtual bool operates_on(BasicType bt, bool signed_int) const {
98
assert(bt == T_INT || bt == T_LONG, "unsupported");
99
return bt == T_INT;
100
}
101
virtual uint ideal_reg() const { return Op_RegI; }
102
};
103
104
//------------------------------AddLNode---------------------------------------
105
// Add 2 longs
106
class AddLNode : public AddNode {
107
public:
108
AddLNode( Node *in1, Node *in2 ) : AddNode(in1,in2) {}
109
virtual int Opcode() const;
110
virtual const Type *add_ring( const Type *, const Type * ) const;
111
virtual const Type *add_id() const { return TypeLong::ZERO; }
112
virtual const Type *bottom_type() const { return TypeLong::LONG; }
113
int max_opcode() const { return Op_MaxL; }
114
int min_opcode() const { return Op_MinL; }
115
virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
116
virtual Node* Identity(PhaseGVN* phase);
117
virtual bool operates_on(BasicType bt, bool signed_int) const {
118
assert(bt == T_INT || bt == T_LONG, "unsupported");
119
return bt == T_LONG;
120
}
121
virtual uint ideal_reg() const { return Op_RegL; }
122
};
123
124
//------------------------------AddFNode---------------------------------------
125
// Add 2 floats
126
class AddFNode : public AddNode {
127
public:
128
AddFNode( Node *in1, Node *in2 ) : AddNode(in1,in2) {}
129
virtual int Opcode() const;
130
virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
131
virtual const Type *add_of_identity( const Type *t1, const Type *t2 ) const;
132
virtual const Type *add_ring( const Type *, const Type * ) const;
133
virtual const Type *add_id() const { return TypeF::ZERO; }
134
virtual const Type *bottom_type() const { return Type::FLOAT; }
135
int max_opcode() const { return Op_MaxF; }
136
int min_opcode() const { return Op_MinF; }
137
virtual Node* Identity(PhaseGVN* phase) { return this; }
138
virtual uint ideal_reg() const { return Op_RegF; }
139
};
140
141
//------------------------------AddDNode---------------------------------------
142
// Add 2 doubles
143
class AddDNode : public AddNode {
144
public:
145
AddDNode( Node *in1, Node *in2 ) : AddNode(in1,in2) {}
146
virtual int Opcode() const;
147
virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
148
virtual const Type *add_of_identity( const Type *t1, const Type *t2 ) const;
149
virtual const Type *add_ring( const Type *, const Type * ) const;
150
virtual const Type *add_id() const { return TypeD::ZERO; }
151
virtual const Type *bottom_type() const { return Type::DOUBLE; }
152
int max_opcode() const { return Op_MaxD; }
153
int min_opcode() const { return Op_MinD; }
154
virtual Node* Identity(PhaseGVN* phase) { return this; }
155
virtual uint ideal_reg() const { return Op_RegD; }
156
};
157
158
//------------------------------AddPNode---------------------------------------
159
// Add pointer plus integer to get pointer. NOT commutative, really.
160
// So not really an AddNode. Lives here, because people associate it with
161
// an add.
162
class AddPNode : public Node {
163
public:
164
enum { Control, // When is it safe to do this add?
165
Base, // Base oop, for GC purposes
166
Address, // Actually address, derived from base
167
Offset } ; // Offset added to address
168
AddPNode( Node *base, Node *ptr, Node *off ) : Node(0,base,ptr,off) {
169
init_class_id(Class_AddP);
170
}
171
virtual int Opcode() const;
172
virtual Node* Identity(PhaseGVN* phase);
173
virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
174
virtual const Type* Value(PhaseGVN* phase) const;
175
virtual const Type *bottom_type() const;
176
virtual uint ideal_reg() const { return Op_RegP; }
177
Node *base_node() { assert( req() > Base, "Missing base"); return in(Base); }
178
static Node* Ideal_base_and_offset(Node* ptr, PhaseTransform* phase,
179
// second return value:
180
intptr_t& offset);
181
182
// Collect the AddP offset values into the elements array, giving up
183
// if there are more than length.
184
int unpack_offsets(Node* elements[], int length);
185
186
// Do not match base-ptr edge
187
virtual uint match_edge(uint idx) const;
188
};
189
190
//------------------------------OrINode----------------------------------------
191
// Logically OR 2 integers. Included with the ADD nodes because it inherits
192
// all the behavior of addition on a ring.
193
class OrINode : public AddNode {
194
public:
195
OrINode( Node *in1, Node *in2 ) : AddNode(in1,in2) {}
196
virtual int Opcode() const;
197
virtual const Type *add_ring( const Type *, const Type * ) const;
198
virtual const Type *add_id() const { return TypeInt::ZERO; }
199
virtual const Type *bottom_type() const { return TypeInt::INT; }
200
int max_opcode() const { return Op_MaxI; }
201
int min_opcode() const { return Op_MinI; }
202
virtual Node* Identity(PhaseGVN* phase);
203
virtual uint ideal_reg() const { return Op_RegI; }
204
virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
205
};
206
207
//------------------------------OrLNode----------------------------------------
208
// Logically OR 2 longs. Included with the ADD nodes because it inherits
209
// all the behavior of addition on a ring.
210
class OrLNode : public AddNode {
211
public:
212
OrLNode( Node *in1, Node *in2 ) : AddNode(in1,in2) {}
213
virtual int Opcode() const;
214
virtual const Type *add_ring( const Type *, const Type * ) const;
215
virtual const Type *add_id() const { return TypeLong::ZERO; }
216
virtual const Type *bottom_type() const { return TypeLong::LONG; }
217
int max_opcode() const { return Op_MaxL; }
218
int min_opcode() const { return Op_MinL; }
219
virtual Node* Identity(PhaseGVN* phase);
220
virtual uint ideal_reg() const { return Op_RegL; }
221
virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
222
};
223
224
//------------------------------XorINode---------------------------------------
225
// XOR'ing 2 integers
226
class XorINode : public AddNode {
227
public:
228
XorINode( Node *in1, Node *in2 ) : AddNode(in1,in2) {}
229
virtual int Opcode() const;
230
virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
231
virtual const Type *add_ring( const Type *, const Type * ) const;
232
virtual const Type *add_id() const { return TypeInt::ZERO; }
233
virtual const Type *bottom_type() const { return TypeInt::INT; }
234
int max_opcode() const { return Op_MaxI; }
235
int min_opcode() const { return Op_MinI; }
236
virtual const Type *Value(PhaseGVN *phase) const;
237
virtual uint ideal_reg() const { return Op_RegI; }
238
};
239
240
//------------------------------XorINode---------------------------------------
241
// XOR'ing 2 longs
242
class XorLNode : public AddNode {
243
public:
244
XorLNode( Node *in1, Node *in2 ) : AddNode(in1,in2) {}
245
virtual int Opcode() const;
246
virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
247
virtual const Type *add_ring( const Type *, const Type * ) const;
248
virtual const Type *add_id() const { return TypeLong::ZERO; }
249
virtual const Type *bottom_type() const { return TypeLong::LONG; }
250
int max_opcode() const { return Op_MaxL; }
251
int min_opcode() const { return Op_MinL; }
252
virtual const Type *Value(PhaseGVN *phase) const;
253
virtual uint ideal_reg() const { return Op_RegL; }
254
};
255
256
//------------------------------MaxNode----------------------------------------
257
// Max (or min) of 2 values. Included with the ADD nodes because it inherits
258
// all the behavior of addition on a ring. Only new thing is that we allow
259
// 2 equal inputs to be equal.
260
class MaxNode : public AddNode {
261
private:
262
static Node* build_min_max(Node* a, Node* b, bool is_max, bool is_unsigned, const Type* t, PhaseGVN& gvn);
263
static Node* build_min_max_diff_with_zero(Node* a, Node* b, bool is_max, const Type* t, PhaseGVN& gvn);
264
265
public:
266
MaxNode( Node *in1, Node *in2 ) : AddNode(in1,in2) {}
267
virtual int Opcode() const = 0;
268
virtual int max_opcode() const = 0;
269
virtual int min_opcode() const = 0;
270
271
static Node* unsigned_max(Node* a, Node* b, const Type* t, PhaseGVN& gvn) {
272
return build_min_max(a, b, true, true, t, gvn);
273
}
274
275
static Node* unsigned_min(Node* a, Node* b, const Type* t, PhaseGVN& gvn) {
276
return build_min_max(a, b, false, true, t, gvn);
277
}
278
279
static Node* signed_max(Node* a, Node* b, const Type* t, PhaseGVN& gvn) {
280
return build_min_max(a, b, true, false, t, gvn);
281
}
282
283
static Node* signed_min(Node* a, Node* b, const Type* t, PhaseGVN& gvn) {
284
return build_min_max(a, b, false, false, t, gvn);
285
}
286
287
// max(a-b, 0)
288
static Node* max_diff_with_zero(Node* a, Node* b, const Type* t, PhaseGVN& gvn) {
289
return build_min_max_diff_with_zero(a, b, true, t, gvn);
290
}
291
292
// min(a-b, 0)
293
static Node* min_diff_with_zero(Node* a, Node* b, const Type* t, PhaseGVN& gvn) {
294
return build_min_max_diff_with_zero(a, b, false, t, gvn);
295
}
296
};
297
298
//------------------------------MaxINode---------------------------------------
299
// Maximum of 2 integers. Included with the ADD nodes because it inherits
300
// all the behavior of addition on a ring.
301
class MaxINode : public MaxNode {
302
public:
303
MaxINode( Node *in1, Node *in2 ) : MaxNode(in1,in2) {}
304
virtual int Opcode() const;
305
virtual const Type *add_ring( const Type *, const Type * ) const;
306
virtual const Type *add_id() const { return TypeInt::make(min_jint); }
307
virtual const Type *bottom_type() const { return TypeInt::INT; }
308
virtual uint ideal_reg() const { return Op_RegI; }
309
int max_opcode() const { return Op_MaxI; }
310
int min_opcode() const { return Op_MinI; }
311
};
312
313
//------------------------------MinINode---------------------------------------
314
// MINimum of 2 integers. Included with the ADD nodes because it inherits
315
// all the behavior of addition on a ring.
316
class MinINode : public MaxNode {
317
public:
318
MinINode( Node *in1, Node *in2 ) : MaxNode(in1,in2) {}
319
virtual int Opcode() const;
320
virtual const Type *add_ring( const Type *, const Type * ) const;
321
virtual const Type *add_id() const { return TypeInt::make(max_jint); }
322
virtual const Type *bottom_type() const { return TypeInt::INT; }
323
virtual uint ideal_reg() const { return Op_RegI; }
324
int max_opcode() const { return Op_MaxI; }
325
int min_opcode() const { return Op_MinI; }
326
virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
327
};
328
329
//------------------------------MaxLNode---------------------------------------
330
// MAXimum of 2 longs.
331
class MaxLNode : public MaxNode {
332
public:
333
MaxLNode(Node *in1, Node *in2) : MaxNode(in1, in2) {}
334
virtual int Opcode() const;
335
virtual const Type *add_ring(const Type*, const Type*) const { return TypeLong::LONG; }
336
virtual const Type *add_id() const { return TypeLong::make(min_jlong); }
337
virtual const Type *bottom_type() const { return TypeLong::LONG; }
338
virtual uint ideal_reg() const { return Op_RegL; }
339
int max_opcode() const { return Op_MaxL; }
340
int min_opcode() const { return Op_MinL; }
341
};
342
343
//------------------------------MinLNode---------------------------------------
344
// MINimum of 2 longs.
345
class MinLNode : public MaxNode {
346
public:
347
MinLNode(Node *in1, Node *in2) : MaxNode(in1, in2) {}
348
virtual int Opcode() const;
349
virtual const Type *add_ring(const Type*, const Type*) const { return TypeLong::LONG; }
350
virtual const Type *add_id() const { return TypeLong::make(max_jlong); }
351
virtual const Type *bottom_type() const { return TypeLong::LONG; }
352
virtual uint ideal_reg() const { return Op_RegL; }
353
int max_opcode() const { return Op_MaxL; }
354
int min_opcode() const { return Op_MinL; }
355
};
356
357
//------------------------------MaxFNode---------------------------------------
358
// Maximum of 2 floats.
359
class MaxFNode : public MaxNode {
360
public:
361
MaxFNode(Node *in1, Node *in2) : MaxNode(in1, in2) {}
362
virtual int Opcode() const;
363
virtual const Type *add_ring(const Type*, const Type*) const;
364
virtual const Type *add_id() const { return TypeF::NEG_INF; }
365
virtual const Type *bottom_type() const { return Type::FLOAT; }
366
virtual uint ideal_reg() const { return Op_RegF; }
367
int max_opcode() const { return Op_MaxF; }
368
int min_opcode() const { return Op_MinF; }
369
};
370
371
//------------------------------MinFNode---------------------------------------
372
// Minimum of 2 floats.
373
class MinFNode : public MaxNode {
374
public:
375
MinFNode(Node *in1, Node *in2) : MaxNode(in1, in2) {}
376
virtual int Opcode() const;
377
virtual const Type *add_ring(const Type*, const Type*) const;
378
virtual const Type *add_id() const { return TypeF::POS_INF; }
379
virtual const Type *bottom_type() const { return Type::FLOAT; }
380
virtual uint ideal_reg() const { return Op_RegF; }
381
int max_opcode() const { return Op_MaxF; }
382
int min_opcode() const { return Op_MinF; }
383
};
384
385
//------------------------------MaxDNode---------------------------------------
386
// Maximum of 2 doubles.
387
class MaxDNode : public MaxNode {
388
public:
389
MaxDNode(Node *in1, Node *in2) : MaxNode(in1, in2) {}
390
virtual int Opcode() const;
391
virtual const Type *add_ring(const Type*, const Type*) const;
392
virtual const Type *add_id() const { return TypeD::NEG_INF; }
393
virtual const Type *bottom_type() const { return Type::DOUBLE; }
394
virtual uint ideal_reg() const { return Op_RegD; }
395
int max_opcode() const { return Op_MaxD; }
396
int min_opcode() const { return Op_MinD; }
397
};
398
399
//------------------------------MinDNode---------------------------------------
400
// Minimum of 2 doubles.
401
class MinDNode : public MaxNode {
402
public:
403
MinDNode(Node *in1, Node *in2) : MaxNode(in1, in2) {}
404
virtual int Opcode() const;
405
virtual const Type *add_ring(const Type*, const Type*) const;
406
virtual const Type *add_id() const { return TypeD::POS_INF; }
407
virtual const Type *bottom_type() const { return Type::DOUBLE; }
408
virtual uint ideal_reg() const { return Op_RegD; }
409
int max_opcode() const { return Op_MaxD; }
410
int min_opcode() const { return Op_MinD; }
411
};
412
413
#endif // SHARE_OPTO_ADDNODE_HPP
414
415