1//===- CodeGen/ValueTypes.h - Low-Level Target independ. types --*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This file defines the set of low-level target independent types which various
10// values in the code generator are. This allows the target specific behavior
11// of instructions to be described to target independent passes.
12//
13//===----------------------------------------------------------------------===//
14
15#ifndef LLVM_CODEGEN_VALUETYPES_H
16#define LLVM_CODEGEN_VALUETYPES_H
17
18#include "llvm/CodeGenTypes/MachineValueType.h"
19#include "llvm/Support/Compiler.h"
20#include "llvm/Support/MathExtras.h"
21#include "llvm/Support/TypeSize.h"
22#include <cassert>
23#include <cstdint>
24#include <string>
25
26namespace llvm {
27
28 class LLVMContext;
29 class Type;
30
31 /// Extended Value Type. Capable of holding value types which are not native
32 /// for any processor (such as the i12345 type), as well as the types an MVT
33 /// can represent.
34 struct EVT {
35 private:
36 MVT V = MVT::INVALID_SIMPLE_VALUE_TYPE;
37 Type *LLVMTy = nullptr;
38
39 public:
40 constexpr EVT() = default;
41 constexpr EVT(MVT::SimpleValueType SVT) : V(SVT) {}
42 constexpr EVT(MVT S) : V(S) {}
43
44 bool operator==(EVT VT) const {
45 return !(*this != VT);
46 }
47 bool operator!=(EVT VT) const {
48 if (V.SimpleTy != VT.V.SimpleTy)
49 return true;
50 if (V.SimpleTy == MVT::INVALID_SIMPLE_VALUE_TYPE)
51 return LLVMTy != VT.LLVMTy;
52 return false;
53 }
54
55 /// Returns the EVT that represents a floating-point type with the given
56 /// number of bits. There are two floating-point types with 128 bits - this
57 /// returns f128 rather than ppcf128.
58 static EVT getFloatingPointVT(unsigned BitWidth) {
59 return MVT::getFloatingPointVT(BitWidth);
60 }
61
62 /// Returns the EVT that represents an integer with the given number of
63 /// bits.
64 static EVT getIntegerVT(LLVMContext &Context, unsigned BitWidth) {
65 MVT M = MVT::getIntegerVT(BitWidth);
66 if (M.SimpleTy != MVT::INVALID_SIMPLE_VALUE_TYPE)
67 return M;
68 return getExtendedIntegerVT(C&: Context, BitWidth);
69 }
70
71 /// Returns the EVT that represents a vector NumElements in length, where
72 /// each element is of type VT.
73 static EVT getVectorVT(LLVMContext &Context, EVT VT, unsigned NumElements,
74 bool IsScalable = false) {
75 MVT M = MVT::getVectorVT(VT: VT.V, NumElements, IsScalable);
76 if (M.SimpleTy != MVT::INVALID_SIMPLE_VALUE_TYPE)
77 return M;
78 return getExtendedVectorVT(C&: Context, VT, NumElements, IsScalable);
79 }
80
81 /// Returns the EVT that represents a vector EC.Min elements in length,
82 /// where each element is of type VT.
83 static EVT getVectorVT(LLVMContext &Context, EVT VT, ElementCount EC) {
84 MVT M = MVT::getVectorVT(VT: VT.V, EC);
85 if (M.SimpleTy != MVT::INVALID_SIMPLE_VALUE_TYPE)
86 return M;
87 return getExtendedVectorVT(Context, VT, EC);
88 }
89
90 /// Return a vector with the same number of elements as this vector, but
91 /// with the element type converted to an integer type with the same
92 /// bitwidth.
93 EVT changeVectorElementTypeToInteger() const {
94 if (isSimple())
95 return getSimpleVT().changeVectorElementTypeToInteger();
96 return changeExtendedVectorElementTypeToInteger();
97 }
98
99 /// Return a VT for a vector type whose attributes match ourselves
100 /// with the exception of the element type that is chosen by the caller.
101 EVT changeVectorElementType(EVT EltVT) const {
102 if (isSimple()) {
103 assert(EltVT.isSimple() &&
104 "Can't change simple vector VT to have extended element VT");
105 return getSimpleVT().changeVectorElementType(EltVT: EltVT.getSimpleVT());
106 }
107 return changeExtendedVectorElementType(EltVT);
108 }
109
110 /// Return a VT for a type whose attributes match ourselves with the
111 /// exception of the element type that is chosen by the caller.
112 EVT changeElementType(EVT EltVT) const {
113 EltVT = EltVT.getScalarType();
114 return isVector() ? changeVectorElementType(EltVT) : EltVT;
115 }
116
117 /// Return the type converted to an equivalently sized integer or vector
118 /// with integer element type. Similar to changeVectorElementTypeToInteger,
119 /// but also handles scalars.
120 EVT changeTypeToInteger() const {
121 if (isVector())
122 return changeVectorElementTypeToInteger();
123
124 if (isSimple())
125 return getSimpleVT().changeTypeToInteger();
126 return changeExtendedTypeToInteger();
127 }
128
129 /// Test if the given EVT has zero size, this will fail if called on a
130 /// scalable type
131 bool isZeroSized() const {
132 return getSizeInBits().isZero();
133 }
134
135 /// Test if the given EVT is simple (as opposed to being extended).
136 bool isSimple() const {
137 return V.SimpleTy != MVT::INVALID_SIMPLE_VALUE_TYPE;
138 }
139
140 /// Test if the given EVT is extended (as opposed to being simple).
141 bool isExtended() const {
142 return !isSimple();
143 }
144
145 /// Return true if this is a FP or a vector FP type.
146 bool isFloatingPoint() const {
147 return isSimple() ? V.isFloatingPoint() : isExtendedFloatingPoint();
148 }
149
150 /// Return true if this is an integer or a vector integer type.
151 bool isInteger() const {
152 return isSimple() ? V.isInteger() : isExtendedInteger();
153 }
154
155 /// Return true if this is an integer, but not a vector.
156 bool isScalarInteger() const {
157 return isSimple() ? V.isScalarInteger() : isExtendedScalarInteger();
158 }
159
160 /// Return true if this is a vector type where the runtime
161 /// length is machine dependent
162 bool isScalableTargetExtVT() const {
163 return isSimple() && V.isScalableTargetExtVT();
164 }
165
166 /// Return true if this is a vector value type.
167 bool isVector() const {
168 return isSimple() ? V.isVector() : isExtendedVector();
169 }
170
171 /// Return true if this is a vector type where the runtime
172 /// length is machine dependent
173 bool isScalableVector() const {
174 return isSimple() ? V.isScalableVector() : isExtendedScalableVector();
175 }
176
177 bool isFixedLengthVector() const {
178 return isSimple() ? V.isFixedLengthVector()
179 : isExtendedFixedLengthVector();
180 }
181
182 /// Return true if the type is a scalable type.
183 bool isScalableVT() const {
184 return isScalableVector() || isScalableTargetExtVT();
185 }
186
187 /// Return true if this is a 16-bit vector type.
188 bool is16BitVector() const {
189 return isSimple() ? V.is16BitVector() : isExtended16BitVector();
190 }
191
192 /// Return true if this is a 32-bit vector type.
193 bool is32BitVector() const {
194 return isSimple() ? V.is32BitVector() : isExtended32BitVector();
195 }
196
197 /// Return true if this is a 64-bit vector type.
198 bool is64BitVector() const {
199 return isSimple() ? V.is64BitVector() : isExtended64BitVector();
200 }
201
202 /// Return true if this is a 128-bit vector type.
203 bool is128BitVector() const {
204 return isSimple() ? V.is128BitVector() : isExtended128BitVector();
205 }
206
207 /// Return true if this is a 256-bit vector type.
208 bool is256BitVector() const {
209 return isSimple() ? V.is256BitVector() : isExtended256BitVector();
210 }
211
212 /// Return true if this is a 512-bit vector type.
213 bool is512BitVector() const {
214 return isSimple() ? V.is512BitVector() : isExtended512BitVector();
215 }
216
217 /// Return true if this is a 1024-bit vector type.
218 bool is1024BitVector() const {
219 return isSimple() ? V.is1024BitVector() : isExtended1024BitVector();
220 }
221
222 /// Return true if this is a 2048-bit vector type.
223 bool is2048BitVector() const {
224 return isSimple() ? V.is2048BitVector() : isExtended2048BitVector();
225 }
226
227 /// Return true if this is an overloaded type for TableGen.
228 bool isOverloaded() const {
229 return (V==MVT::iAny || V==MVT::fAny || V==MVT::vAny || V==MVT::iPTRAny);
230 }
231
232 /// Return true if the bit size is a multiple of 8.
233 bool isByteSized() const {
234 return !isZeroSized() && getSizeInBits().isKnownMultipleOf(RHS: 8);
235 }
236
237 /// Return true if the size is a power-of-two number of bytes.
238 bool isRound() const {
239 if (isScalableVector())
240 return false;
241 unsigned BitSize = getSizeInBits();
242 return BitSize >= 8 && !(BitSize & (BitSize - 1));
243 }
244
245 /// Return true if this has the same number of bits as VT.
246 bool bitsEq(EVT VT) const {
247 if (EVT::operator==(VT)) return true;
248 return getSizeInBits() == VT.getSizeInBits();
249 }
250
251 /// Return true if we know at compile time this has more bits than VT.
252 bool knownBitsGT(EVT VT) const {
253 return TypeSize::isKnownGT(LHS: getSizeInBits(), RHS: VT.getSizeInBits());
254 }
255
256 /// Return true if we know at compile time this has more than or the same
257 /// bits as VT.
258 bool knownBitsGE(EVT VT) const {
259 return TypeSize::isKnownGE(LHS: getSizeInBits(), RHS: VT.getSizeInBits());
260 }
261
262 /// Return true if we know at compile time this has fewer bits than VT.
263 bool knownBitsLT(EVT VT) const {
264 return TypeSize::isKnownLT(LHS: getSizeInBits(), RHS: VT.getSizeInBits());
265 }
266
267 /// Return true if we know at compile time this has fewer than or the same
268 /// bits as VT.
269 bool knownBitsLE(EVT VT) const {
270 return TypeSize::isKnownLE(LHS: getSizeInBits(), RHS: VT.getSizeInBits());
271 }
272
273 /// Return true if this has more bits than VT.
274 bool bitsGT(EVT VT) const {
275 if (EVT::operator==(VT)) return false;
276 assert(isScalableVector() == VT.isScalableVector() &&
277 "Comparison between scalable and fixed types");
278 return knownBitsGT(VT);
279 }
280
281 /// Return true if this has no less bits than VT.
282 bool bitsGE(EVT VT) const {
283 if (EVT::operator==(VT)) return true;
284 assert(isScalableVector() == VT.isScalableVector() &&
285 "Comparison between scalable and fixed types");
286 return knownBitsGE(VT);
287 }
288
289 /// Return true if this has less bits than VT.
290 bool bitsLT(EVT VT) const {
291 if (EVT::operator==(VT)) return false;
292 assert(isScalableVector() == VT.isScalableVector() &&
293 "Comparison between scalable and fixed types");
294 return knownBitsLT(VT);
295 }
296
297 /// Return true if this has no more bits than VT.
298 bool bitsLE(EVT VT) const {
299 if (EVT::operator==(VT)) return true;
300 assert(isScalableVector() == VT.isScalableVector() &&
301 "Comparison between scalable and fixed types");
302 return knownBitsLE(VT);
303 }
304
305 /// Return the SimpleValueType held in the specified simple EVT.
306 MVT getSimpleVT() const {
307 assert(isSimple() && "Expected a SimpleValueType!");
308 return V;
309 }
310
311 /// If this is a vector type, return the element type, otherwise return
312 /// this.
313 EVT getScalarType() const {
314 return isVector() ? getVectorElementType() : *this;
315 }
316
317 /// Given a vector type, return the type of each element.
318 EVT getVectorElementType() const {
319 assert(isVector() && "Invalid vector type!");
320 if (isSimple())
321 return V.getVectorElementType();
322 return getExtendedVectorElementType();
323 }
324
325 /// Given a vector type, return the number of elements it contains.
326 unsigned getVectorNumElements() const {
327 assert(isVector() && "Invalid vector type!");
328
329 if (isScalableVector())
330 llvm::reportInvalidSizeRequest(
331 Msg: "Possible incorrect use of EVT::getVectorNumElements() for "
332 "scalable vector. Scalable flag may be dropped, use "
333 "EVT::getVectorElementCount() instead");
334
335 return isSimple() ? V.getVectorNumElements()
336 : getExtendedVectorNumElements();
337 }
338
339 // Given a (possibly scalable) vector type, return the ElementCount
340 ElementCount getVectorElementCount() const {
341 assert((isVector()) && "Invalid vector type!");
342 if (isSimple())
343 return V.getVectorElementCount();
344
345 return getExtendedVectorElementCount();
346 }
347
348 /// Given a vector type, return the minimum number of elements it contains.
349 unsigned getVectorMinNumElements() const {
350 return getVectorElementCount().getKnownMinValue();
351 }
352
353 /// Return the size of the specified value type in bits.
354 ///
355 /// If the value type is a scalable vector type, the scalable property will
356 /// be set and the runtime size will be a positive integer multiple of the
357 /// base size.
358 TypeSize getSizeInBits() const {
359 if (isSimple())
360 return V.getSizeInBits();
361 return getExtendedSizeInBits();
362 }
363
364 /// Return the size of the specified fixed width value type in bits. The
365 /// function will assert if the type is scalable.
366 uint64_t getFixedSizeInBits() const {
367 return getSizeInBits().getFixedValue();
368 }
369
370 uint64_t getScalarSizeInBits() const {
371 return getScalarType().getSizeInBits().getFixedValue();
372 }
373
374 /// Return the number of bytes overwritten by a store of the specified value
375 /// type.
376 ///
377 /// If the value type is a scalable vector type, the scalable property will
378 /// be set and the runtime size will be a positive integer multiple of the
379 /// base size.
380 TypeSize getStoreSize() const {
381 TypeSize BaseSize = getSizeInBits();
382 return {(BaseSize.getKnownMinValue() + 7) / 8, BaseSize.isScalable()};
383 }
384
385 // Return the number of bytes overwritten by a store of this value type or
386 // this value type's element type in the case of a vector.
387 uint64_t getScalarStoreSize() const {
388 return getScalarType().getStoreSize().getFixedValue();
389 }
390
391 /// Return the number of bits overwritten by a store of the specified value
392 /// type.
393 ///
394 /// If the value type is a scalable vector type, the scalable property will
395 /// be set and the runtime size will be a positive integer multiple of the
396 /// base size.
397 TypeSize getStoreSizeInBits() const {
398 return getStoreSize() * 8;
399 }
400
401 /// Rounds the bit-width of the given integer EVT up to the nearest power of
402 /// two (and at least to eight), and returns the integer EVT with that
403 /// number of bits.
404 EVT getRoundIntegerType(LLVMContext &Context) const {
405 assert(isInteger() && !isVector() && "Invalid integer type!");
406 unsigned BitWidth = getSizeInBits();
407 if (BitWidth <= 8)
408 return EVT(MVT::i8);
409 return getIntegerVT(Context, BitWidth: llvm::bit_ceil(Value: BitWidth));
410 }
411
412 /// Finds the smallest simple value type that is greater than or equal to
413 /// half the width of this EVT. If no simple value type can be found, an
414 /// extended integer value type of half the size (rounded up) is returned.
415 EVT getHalfSizedIntegerVT(LLVMContext &Context) const {
416 assert(isInteger() && !isVector() && "Invalid integer type!");
417 unsigned EVTSize = getSizeInBits();
418 for (unsigned IntVT = MVT::FIRST_INTEGER_VALUETYPE;
419 IntVT <= MVT::LAST_INTEGER_VALUETYPE; ++IntVT) {
420 EVT HalfVT = EVT((MVT::SimpleValueType)IntVT);
421 if (HalfVT.getSizeInBits() * 2 >= EVTSize)
422 return HalfVT;
423 }
424 return getIntegerVT(Context, BitWidth: (EVTSize + 1) / 2);
425 }
426
427 /// Return a VT for an integer vector type with the size of the
428 /// elements doubled. The typed returned may be an extended type.
429 EVT widenIntegerVectorElementType(LLVMContext &Context) const {
430 EVT EltVT = getVectorElementType();
431 EltVT = EVT::getIntegerVT(Context, BitWidth: 2 * EltVT.getSizeInBits());
432 return EVT::getVectorVT(Context, VT: EltVT, EC: getVectorElementCount());
433 }
434
435 // Return a VT for a vector type with the same element type but
436 // half the number of elements. The type returned may be an
437 // extended type.
438 EVT getHalfNumVectorElementsVT(LLVMContext &Context) const {
439 EVT EltVT = getVectorElementType();
440 auto EltCnt = getVectorElementCount();
441 assert(EltCnt.isKnownEven() && "Splitting vector, but not in half!");
442 return EVT::getVectorVT(Context, VT: EltVT, EC: EltCnt.divideCoefficientBy(RHS: 2));
443 }
444
445 // Return a VT for a vector type with the same element type but
446 // double the number of elements. The type returned may be an
447 // extended type.
448 EVT getDoubleNumVectorElementsVT(LLVMContext &Context) const {
449 EVT EltVT = getVectorElementType();
450 auto EltCnt = getVectorElementCount();
451 return EVT::getVectorVT(Context, VT: EltVT, EC: EltCnt * 2);
452 }
453
454 /// Returns true if the given vector is a power of 2.
455 bool isPow2VectorType() const {
456 unsigned NElts = getVectorMinNumElements();
457 return !(NElts & (NElts - 1));
458 }
459
460 /// Widens the length of the given vector EVT up to the nearest power of 2
461 /// and returns that type.
462 EVT getPow2VectorType(LLVMContext &Context) const {
463 if (!isPow2VectorType()) {
464 ElementCount NElts = getVectorElementCount();
465 unsigned NewMinCount = 1 << Log2_32_Ceil(Value: NElts.getKnownMinValue());
466 NElts = ElementCount::get(MinVal: NewMinCount, Scalable: NElts.isScalable());
467 return EVT::getVectorVT(Context, VT: getVectorElementType(), EC: NElts);
468 }
469 else {
470 return *this;
471 }
472 }
473
474 /// This function returns value type as a string, e.g. "i32".
475 std::string getEVTString() const;
476
477 /// Support for debugging, callable in GDB: VT.dump()
478 void dump() const;
479
480 /// Implement operator<<.
481 void print(raw_ostream &OS) const {
482 OS << getEVTString();
483 }
484
485 /// This method returns an LLVM type corresponding to the specified EVT.
486 /// For integer types, this returns an unsigned type. Note that this will
487 /// abort for types that cannot be represented.
488 Type *getTypeForEVT(LLVMContext &Context) const;
489
490 /// Return the value type corresponding to the specified type.
491 /// This returns all pointers as iPTR. If HandleUnknown is true, unknown
492 /// types are returned as Other, otherwise they are invalid.
493 static EVT getEVT(Type *Ty, bool HandleUnknown = false);
494
495 intptr_t getRawBits() const {
496 if (isSimple())
497 return V.SimpleTy;
498 else
499 return (intptr_t)(LLVMTy);
500 }
501
502 /// A meaningless but well-behaved order, useful for constructing
503 /// containers.
504 struct compareRawBits {
505 bool operator()(EVT L, EVT R) const {
506 if (L.V.SimpleTy == R.V.SimpleTy)
507 return L.LLVMTy < R.LLVMTy;
508 else
509 return L.V.SimpleTy < R.V.SimpleTy;
510 }
511 };
512
513 private:
514 // Methods for handling the Extended-type case in functions above.
515 // These are all out-of-line to prevent users of this header file
516 // from having a dependency on Type.h.
517 EVT changeExtendedTypeToInteger() const;
518 EVT changeExtendedVectorElementType(EVT EltVT) const;
519 EVT changeExtendedVectorElementTypeToInteger() const;
520 static EVT getExtendedIntegerVT(LLVMContext &C, unsigned BitWidth);
521 static EVT getExtendedVectorVT(LLVMContext &C, EVT VT, unsigned NumElements,
522 bool IsScalable);
523 static EVT getExtendedVectorVT(LLVMContext &Context, EVT VT,
524 ElementCount EC);
525 bool isExtendedFloatingPoint() const LLVM_READONLY;
526 bool isExtendedInteger() const LLVM_READONLY;
527 bool isExtendedScalarInteger() const LLVM_READONLY;
528 bool isExtendedVector() const LLVM_READONLY;
529 bool isExtended16BitVector() const LLVM_READONLY;
530 bool isExtended32BitVector() const LLVM_READONLY;
531 bool isExtended64BitVector() const LLVM_READONLY;
532 bool isExtended128BitVector() const LLVM_READONLY;
533 bool isExtended256BitVector() const LLVM_READONLY;
534 bool isExtended512BitVector() const LLVM_READONLY;
535 bool isExtended1024BitVector() const LLVM_READONLY;
536 bool isExtended2048BitVector() const LLVM_READONLY;
537 bool isExtendedFixedLengthVector() const LLVM_READONLY;
538 bool isExtendedScalableVector() const LLVM_READONLY;
539 EVT getExtendedVectorElementType() const;
540 unsigned getExtendedVectorNumElements() const LLVM_READONLY;
541 ElementCount getExtendedVectorElementCount() const LLVM_READONLY;
542 TypeSize getExtendedSizeInBits() const LLVM_READONLY;
543 };
544
545 inline raw_ostream &operator<<(raw_ostream &OS, const EVT &V) {
546 V.print(OS);
547 return OS;
548 }
549} // end namespace llvm
550
551#endif // LLVM_CODEGEN_VALUETYPES_H
552

source code of llvm/include/llvm/CodeGen/ValueTypes.h