Go to the documentation of this file.
13 #ifndef LLVM_LIB_TARGET_AARCH64_MCTARGETDESC_AARCH64ADDRESSINGMODES_H
14 #define LLVM_LIB_TARGET_AARCH64_MCTARGETDESC_AARCH64ADDRESSINGMODES_H
27 namespace AArch64_AM {
75 switch ((
Imm >> 6) & 0x7) {
101 assert((
Imm & 0x3f) ==
Imm &&
"Illegal shifted immedate value!");
111 return (STEnc << 6) | (
Imm & 0x3f);
173 assert((
Imm & 0x7) ==
Imm &&
"Illegal shifted immedate value!");
180 return (
Imm & 0x1) != 0;
207 return ((elt & 1) << (
size-1)) | (elt >> 1);
216 if (
Imm == 0ULL ||
Imm == ~0ULL ||
241 assert(
I < 64 &&
"undefined behavior");
256 assert(Size >
I &&
"I should be smaller than element size");
257 unsigned Immr = (Size -
I) & (Size - 1);
268 unsigned N = ((NImms >> 6) & 1) ^ 1;
270 Encoding = (
N << 12) | (Immr << 6) | (NImms & 0x3f);
286 assert(res &&
"invalid logical immediate");
296 unsigned N = (
val >> 12) & 1;
297 unsigned immr = (
val >> 6) & 0x3f;
298 unsigned imms =
val & 0x3f;
300 assert((regSize == 64 ||
N == 0) &&
"undefined logical immediate encoding");
302 assert(len >= 0 &&
"undefined logical immediate encoding");
303 unsigned size = (1 << len);
304 unsigned R = immr & (
size - 1);
305 unsigned S = imms & (
size - 1);
306 assert(
S !=
size - 1 &&
"undefined logical immediate encoding");
307 uint64_t pattern = (1ULL << (
S + 1)) - 1;
308 for (
unsigned i = 0;
i < R; ++
i)
312 while (
size != regSize) {
313 pattern |= (pattern <<
size);
325 unsigned N = (
val >> 12) & 1;
326 unsigned imms =
val & 0x3f;
328 if (regSize == 32 &&
N != 0)
333 unsigned size = (1 << len);
334 unsigned S = imms & (
size - 1);
347 uint8_t Sign = (
Imm >> 7) & 0x1;
348 uint8_t Exp = (
Imm >> 4) & 0x7;
349 uint8_t Mantissa =
Imm & 0xf;
358 I |= ((Exp & 0x4) != 0 ? 0 : 1) << 30;
359 I |= ((Exp & 0x4) != 0 ? 0x1f : 0) << 25;
360 I |= (Exp & 0x3) << 23;
362 return bit_cast<float>(
I);
370 int32_t Exp = (
Imm.lshr(10).getSExtValue() & 0x1f) - 15;
371 int32_t Mantissa =
Imm.getZExtValue() & 0x3ff;
380 if (Exp < -3 || Exp > 4)
382 Exp = ((Exp+3) & 0x7) ^ 4;
384 return ((
int)Sign << 7) | (Exp << 4) | Mantissa;
396 int32_t Exp = (
Imm.lshr(23).getSExtValue() & 0xff) - 127;
397 int64_t Mantissa =
Imm.getZExtValue() & 0x7fffff;
401 if (Mantissa & 0x7ffff)
404 if ((Mantissa & 0xf) != Mantissa)
408 if (Exp < -3 || Exp > 4)
410 Exp = ((Exp+3) & 0x7) ^ 4;
412 return ((
int)Sign << 7) | (Exp << 4) | Mantissa;
424 int64_t Exp = (
Imm.lshr(52).getSExtValue() & 0x7ff) - 1023;
425 uint64_t Mantissa =
Imm.getZExtValue() & 0xfffffffffffffULL;
429 if (Mantissa & 0xffffffffffffULL)
432 if ((Mantissa & 0xf) != Mantissa)
436 if (Exp < -3 || Exp > 4)
438 Exp = ((Exp+3) & 0x7) ^ 4;
440 return ((
int)Sign << 7) | (Exp << 4) | Mantissa;
453 return ((
Imm >> 32) == (
Imm & 0xffffffffULL)) &&
454 ((
Imm & 0xffffff00ffffff00ULL) == 0);
458 return (
Imm & 0xffULL);
463 return (EncVal << 32) | EncVal;
468 return ((
Imm >> 32) == (
Imm & 0xffffffffULL)) &&
469 ((
Imm & 0xffff00ffffff00ffULL) == 0);
473 return (
Imm & 0xff00ULL) >> 8;
478 return (EncVal << 40) | (EncVal << 8);
483 return ((
Imm >> 32) == (
Imm & 0xffffffffULL)) &&
484 ((
Imm & 0xff00ffffff00ffffULL) == 0);
488 return (
Imm & 0xff0000ULL) >> 16;
493 return (EncVal << 48) | (EncVal << 16);
498 return ((
Imm >> 32) == (
Imm & 0xffffffffULL)) &&
499 ((
Imm & 0x00ffffff00ffffffULL) == 0);
503 return (
Imm & 0xff000000ULL) >> 24;
508 return (EncVal << 56) | (EncVal << 24);
513 return ((
Imm >> 32) == (
Imm & 0xffffffffULL)) &&
514 (((
Imm & 0x00ff0000ULL) >> 16) == (
Imm & 0x000000ffULL)) &&
515 ((
Imm & 0xff00ff00ff00ff00ULL) == 0);
519 return (
Imm & 0xffULL);
524 return (EncVal << 48) | (EncVal << 32) | (EncVal << 16) | EncVal;
529 return ((
Imm >> 32) == (
Imm & 0xffffffffULL)) &&
530 (((
Imm & 0xff000000ULL) >> 16) == (
Imm & 0x0000ff00ULL)) &&
531 ((
Imm & 0x00ff00ff00ff00ffULL) == 0);
535 return (
Imm & 0xff00ULL) >> 8;
540 return (EncVal << 56) | (EncVal << 40) | (EncVal << 24) | (EncVal << 8);
545 return ((
Imm >> 32) == (
Imm & 0xffffffffULL)) &&
546 ((
Imm & 0xffff00ffffff00ffULL) == 0x000000ff000000ffULL);
550 return (
Imm & 0xff00ULL) >> 8;
555 return (EncVal << 40) | (EncVal << 8) | 0x000000ff000000ffULL;
560 return ((
Imm >> 32) == (
Imm & 0xffffffffULL)) &&
561 ((
Imm & 0xff00ffffff00ffffULL) == 0x0000ffff0000ffffULL);
566 return (EncVal << 48) | (EncVal << 16) | 0x0000ffff0000ffffULL;
570 return (
Imm & 0x00ff0000ULL) >> 16;
575 return ((
Imm >> 32) == (
Imm & 0xffffffffULL)) &&
576 ((
Imm >> 48) == (
Imm & 0x0000ffffULL)) &&
577 ((
Imm >> 56) == (
Imm & 0x000000ffULL));
581 return (
Imm & 0xffULL);
586 EncVal |= (EncVal << 8);
587 EncVal |= (EncVal << 16);
588 EncVal |= (EncVal << 32);
604 return (ByteA == 0ULL || ByteA == 0xff00000000000000ULL) &&
605 (ByteB == 0ULL || ByteB == 0x00ff000000000000ULL) &&
606 (ByteC == 0ULL || ByteC == 0x0000ff0000000000ULL) &&
607 (ByteD == 0ULL || ByteD == 0x000000ff00000000ULL) &&
608 (ByteE == 0ULL || ByteE == 0x00000000ff000000ULL) &&
609 (ByteF == 0ULL || ByteF == 0x0000000000ff0000ULL) &&
610 (ByteG == 0ULL || ByteG == 0x000000000000ff00ULL) &&
611 (ByteH == 0ULL || ByteH == 0x00000000000000ffULL);
615 uint8_t BitA = (
Imm & 0xff00000000000000ULL) != 0;
616 uint8_t BitB = (
Imm & 0x00ff000000000000ULL) != 0;
617 uint8_t BitC = (
Imm & 0x0000ff0000000000ULL) != 0;
618 uint8_t BitD = (
Imm & 0x000000ff00000000ULL) != 0;
619 uint8_t BitE = (
Imm & 0x00000000ff000000ULL) != 0;
620 uint8_t BitF = (
Imm & 0x0000000000ff0000ULL) != 0;
621 uint8_t BitG = (
Imm & 0x000000000000ff00ULL) != 0;
622 uint8_t BitH = (
Imm & 0x00000000000000ffULL) != 0;
624 uint8_t EncVal = BitA;
644 if (
Imm & 0x80) EncVal |= 0xff00000000000000ULL;
645 if (
Imm & 0x40) EncVal |= 0x00ff000000000000ULL;
646 if (
Imm & 0x20) EncVal |= 0x0000ff0000000000ULL;
647 if (
Imm & 0x10) EncVal |= 0x000000ff00000000ULL;
648 if (
Imm & 0x08) EncVal |= 0x00000000ff000000ULL;
649 if (
Imm & 0x04) EncVal |= 0x0000000000ff0000ULL;
650 if (
Imm & 0x02) EncVal |= 0x000000000000ff00ULL;
651 if (
Imm & 0x01) EncVal |= 0x00000000000000ffULL;
658 return ((
Imm >> 32) == (
Imm & 0xffffffffULL)) &&
659 (BString == 0x1f || BString == 0x20) &&
660 ((
Imm & 0x0007ffff0007ffffULL) == 0);
664 uint8_t BitA = (
Imm & 0x80000000ULL) != 0;
665 uint8_t BitB = (
Imm & 0x20000000ULL) != 0;
666 uint8_t BitC = (
Imm & 0x01000000ULL) != 0;
667 uint8_t BitD = (
Imm & 0x00800000ULL) != 0;
668 uint8_t BitE = (
Imm & 0x00400000ULL) != 0;
669 uint8_t BitF = (
Imm & 0x00200000ULL) != 0;
670 uint8_t BitG = (
Imm & 0x00100000ULL) != 0;
671 uint8_t BitH = (
Imm & 0x00080000ULL) != 0;
673 uint8_t EncVal = BitA;
693 if (
Imm & 0x80) EncVal |= 0x80000000ULL;
694 if (
Imm & 0x40) EncVal |= 0x3e000000ULL;
695 else EncVal |= 0x40000000ULL;
696 if (
Imm & 0x20) EncVal |= 0x01000000ULL;
697 if (
Imm & 0x10) EncVal |= 0x00800000ULL;
698 if (
Imm & 0x08) EncVal |= 0x00400000ULL;
699 if (
Imm & 0x04) EncVal |= 0x00200000ULL;
700 if (
Imm & 0x02) EncVal |= 0x00100000ULL;
701 if (
Imm & 0x01) EncVal |= 0x00080000ULL;
702 return (EncVal << 32) | EncVal;
707 uint64_t BString = (
Imm & 0x7fc0000000000000ULL) >> 54;
708 return ((BString == 0xff || BString == 0x100) &&
709 ((
Imm & 0x0000ffffffffffffULL) == 0));
713 uint8_t BitA = (
Imm & 0x8000000000000000ULL) != 0;
714 uint8_t BitB = (
Imm & 0x0040000000000000ULL) != 0;
715 uint8_t BitC = (
Imm & 0x0020000000000000ULL) != 0;
716 uint8_t BitD = (
Imm & 0x0010000000000000ULL) != 0;
717 uint8_t BitE = (
Imm & 0x0008000000000000ULL) != 0;
718 uint8_t BitF = (
Imm & 0x0004000000000000ULL) != 0;
719 uint8_t BitG = (
Imm & 0x0002000000000000ULL) != 0;
720 uint8_t BitH = (
Imm & 0x0001000000000000ULL) != 0;
722 uint8_t EncVal = BitA;
742 if (
Imm & 0x80) EncVal |= 0x8000000000000000ULL;
743 if (
Imm & 0x40) EncVal |= 0x3fc0000000000000ULL;
744 else EncVal |= 0x4000000000000000ULL;
745 if (
Imm & 0x20) EncVal |= 0x0020000000000000ULL;
746 if (
Imm & 0x10) EncVal |= 0x0010000000000000ULL;
747 if (
Imm & 0x08) EncVal |= 0x0008000000000000ULL;
748 if (
Imm & 0x04) EncVal |= 0x0004000000000000ULL;
749 if (
Imm & 0x02) EncVal |= 0x0002000000000000ULL;
750 if (
Imm & 0x01) EncVal |= 0x0001000000000000ULL;
751 return (EncVal << 32) | EncVal;
755 template <
typename T>
757 auto Parts =
bit_cast<std::array<
T,
sizeof(int64_t) /
sizeof(
T)>>(
Imm);
762 template <
typename T>
767 int64_t
Mask = ~int64_t(std::numeric_limits<std::make_unsigned_t<T>>::
max());
785 template <
typename T>
787 bool IsInt8t = std::is_same<int8_t, std::make_signed_t<T>>::value ||
788 std::is_same<int8_t, T>::value;
794 if (isSVECpyImm<int64_t>(
Imm))
797 auto S = bit_cast<std::array<int32_t, 2>>(
Imm);
798 auto H = bit_cast<std::array<int16_t, 4>>(
Imm);
799 auto B = bit_cast<std::array<int8_t, 8>>(
Imm);
801 if (isSVEMaskOfIdenticalElements<int32_t>(
Imm) && isSVECpyImm<int32_t>(
S[0]))
803 if (isSVEMaskOfIdenticalElements<int16_t>(
Imm) && isSVECpyImm<int16_t>(
H[0]))
805 if (isSVEMaskOfIdenticalElements<int8_t>(
Imm) && isSVECpyImm<int8_t>(
B[0]))
820 Value &= 0xffffffffULL;
836 Value &= 0xffffffffULL;
848 Value &= 0xffffffffULL;
static uint8_t encodeAdvSIMDModImmType3(uint64_t Imm)
static unsigned getArithShiftValue(unsigned Imm)
getArithShiftValue - get the arithmetic shift value.
static bool isAdvSIMDModImmType6(uint64_t Imm)
This is an optimization pass for GlobalISel generic memory operations.
static float getFPImmFloat(unsigned Imm)
static bool isAdvSIMDModImmType12(uint64_t Imm)
static bool isSVEMaskOfIdenticalElements(int64_t Imm)
Returns true if Imm is the concatenation of a repeating pattern of type T.
static int getFP16Imm(const APInt &Imm)
getFP16Imm - Return an 8-bit floating-point version of the 16-bit floating-point value.
static uint8_t encodeAdvSIMDModImmType1(uint64_t Imm)
static bool isAdvSIMDModImmType4(uint64_t Imm)
static uint64_t decodeAdvSIMDModImmType3(uint8_t Imm)
static uint64_t decodeAdvSIMDModImmType12(uint8_t Imm)
static bool isMOVZMovAlias(uint64_t Value, int Shift, int RegWidth)
static bool processLogicalImmediate(uint64_t Imm, unsigned RegSize, uint64_t &Encoding)
processLogicalImmediate - Determine if an immediate value can be encoded as the immediate operand of ...
static bool isAdvSIMDModImmType3(uint64_t Imm)
static bool isAnyMOVZMovAlias(uint64_t Value, int RegWidth)
static bool getMemDoShift(unsigned Imm)
getMemDoShift - Extract the "do shift" flag value for load/store instructions.
static bool isAdvSIMDModImmType7(uint64_t Imm)
Expected< ExpressionValue > max(const ExpressionValue &Lhs, const ExpressionValue &Rhs)
static uint64_t decodeAdvSIMDModImmType5(uint8_t Imm)
static bool isSVEAddSubImm(int64_t Imm)
Returns true if Imm is valid for ADD/SUB.
constexpr std::underlying_type_t< E > Mask()
Get a bitmask with 1s in all places up to the high-order bit of E's largest value.
static bool isSVECpyImm(int64_t Imm)
Returns true if Imm is valid for CPY/DUP.
static uint8_t encodeAdvSIMDModImmType6(uint64_t Imm)
static bool isLogicalImmediate(uint64_t imm, unsigned regSize)
isLogicalImmediate - Return true if the immediate is valid for a logical immediate instruction of the...
static AArch64_AM::ShiftExtendType getMemExtendType(unsigned Imm)
getExtendType - Extract the extend type for the offset operand of loads/stores.
static bool isAdvSIMDModImmType5(uint64_t Imm)
constexpr bool isShiftedMask_64(uint64_t Value)
Return true if the argument contains a non-empty sequence of ones with the remainder zero (64 bit ver...
static bool isMOVNMovAlias(uint64_t Value, int Shift, int RegWidth)
static bool isAdvSIMDModImmType2(uint64_t Imm)
static bool isSVEMoveMaskPreferredLogicalImmediate(int64_t Imm)
Return true if Imm is valid for DUPM and has no single CPY/DUP equivalent.
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
static unsigned getShifterImm(AArch64_AM::ShiftExtendType ST, unsigned Imm)
getShifterImm - Encode the shift type and amount: imm: 6-bit shift amount shifter: 000 ==> lsl 001 ==...
static unsigned getShiftValue(unsigned Imm)
getShiftValue - Extract the shift value.
unsigned countTrailingZeros(T Val)
Count number of 0's from the least significant bit to the most stopping at the first 1.
APInt bitcastToAPInt() const
static int getFP32Imm(const APInt &Imm)
getFP32Imm - Return an 8-bit floating-point version of the 32-bit floating-point value.
static bool isAdvSIMDModImmType9(uint64_t Imm)
static AArch64_AM::ShiftExtendType getArithExtendType(unsigned Imm)
bool all_equal(std::initializer_list< T > Values)
Returns true if all Values in the initializer lists are equal or the list.
static uint64_t decodeLogicalImmediate(uint64_t val, unsigned regSize)
decodeLogicalImmediate - Decode a logical immediate value in the form "N:immr:imms" (where the immr a...
static unsigned getMemExtendImm(AArch64_AM::ShiftExtendType ET, bool DoShift)
getExtendImm - Encode the extend type and amount for a load/store inst: doshift: should the offset be...
static uint64_t decodeAdvSIMDModImmType6(uint8_t Imm)
The initial backend is deliberately restricted to z10 We should add support for later architectures at some point If an asm ties an i32 r result to an i64 the input will be treated as an leaving the upper bits uninitialised For i64 store i32 val
static bool isAdvSIMDModImmType1(uint64_t Imm)
static const char * getShiftExtendName(AArch64_AM::ShiftExtendType ST)
getShiftName - Get the string encoding for the shift type.
static bool isAdvSIMDModImmType8(uint64_t Imm)
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
static uint8_t encodeAdvSIMDModImmType2(uint64_t Imm)
static AArch64_AM::ShiftExtendType getExtendType(unsigned Imm)
getExtendType - Extract the extend type for operands of arithmetic ops.
static uint8_t encodeAdvSIMDModImmType12(uint64_t Imm)
unsigned getExtendEncoding(AArch64_AM::ShiftExtendType ET)
Mapping from extend bits to required operation: shifter: 000 ==> uxtb 001 ==> uxth 010 ==> uxtw 011 =...
Class for arbitrary precision integers.
auto size(R &&Range, std::enable_if_t< std::is_base_of< std::random_access_iterator_tag, typename std::iterator_traits< decltype(Range.begin())>::iterator_category >::value, void > *=nullptr)
Get the size of a range.
static uint64_t encodeLogicalImmediate(uint64_t imm, unsigned regSize)
encodeLogicalImmediate - Return the encoded immediate value for a logical immediate instruction of th...
static int getFP64Imm(const APInt &Imm)
getFP64Imm - Return an 8-bit floating-point version of the 64-bit floating-point value.
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
add sub stmia L5 ldr r0 bl L_printf $stub Instead of a and a wouldn t it be better to do three moves *Return an aggregate type is even return S
static uint64_t decodeAdvSIMDModImmType7(uint8_t Imm)
static uint64_t decodeAdvSIMDModImmType1(uint8_t Imm)
static unsigned getArithExtendImm(AArch64_AM::ShiftExtendType ET, unsigned Imm)
getArithExtendImm - Encode the extend type and shift amount for an arithmetic instruction: imm: 3-bit...
static uint8_t encodeAdvSIMDModImmType5(uint64_t Imm)
unsigned countLeadingOnes(T Value)
Count the number of ones from the most significant bit to the first zero bit.
static uint8_t encodeAdvSIMDModImmType10(uint64_t Imm)
static uint8_t encodeAdvSIMDModImmType4(uint64_t Imm)
static bool isAnyMOVWMovAlias(uint64_t Value, int RegWidth)
unsigned countTrailingOnes(T Value)
Count the number of ones from the least significant bit to the first zero bit.
static uint64_t decodeAdvSIMDModImmType8(uint8_t Imm)
static uint64_t decodeAdvSIMDModImmType10(uint8_t Imm)
static bool isAdvSIMDModImmType10(uint64_t Imm)
static uint8_t encodeAdvSIMDModImmType8(uint64_t Imm)
static AArch64_AM::ShiftExtendType getShiftType(unsigned Imm)
getShiftType - Extract the shift type.
To bit_cast(const From &from) noexcept
static uint8_t encodeAdvSIMDModImmType11(uint64_t Imm)
static uint64_t decodeAdvSIMDModImmType4(uint8_t Imm)
unsigned countLeadingZeros(T Val)
Count number of 0's from the most significant bit to the least stopping at the first 1.
static bool isValidDecodeLogicalImmediate(uint64_t val, unsigned regSize)
isValidDecodeLogicalImmediate - Check to see if the logical immediate value in the form "N:immr:imms"...
static uint64_t decodeAdvSIMDModImmType2(uint8_t Imm)
static uint64_t decodeAdvSIMDModImmType11(uint8_t Imm)
static uint64_t ror(uint64_t elt, unsigned size)
static uint8_t encodeAdvSIMDModImmType9(uint64_t Imm)
static bool isAdvSIMDModImmType11(uint64_t Imm)
LLVM Value Representation.
static uint64_t decodeAdvSIMDModImmType9(uint8_t Imm)
static uint8_t encodeAdvSIMDModImmType7(uint64_t Imm)