mirror of
https://github.com/asmjit/asmjit.git
synced 2025-12-17 04:24:37 +03:00
[ABI] Renamed a64::Vec::ElementType to a64::VecElementType
This commit is contained in:
@@ -47,7 +47,6 @@ TODO
|
|||||||
|
|
||||||
* [ ] Ports:
|
* [ ] Ports:
|
||||||
* [ ] 32-bit ARM/Thumb port.
|
* [ ] 32-bit ARM/Thumb port.
|
||||||
* [ ] 64-bit ARM (AArch64) port.
|
|
||||||
* [ ] RISC-V port.
|
* [ ] RISC-V port.
|
||||||
|
|
||||||
Support
|
Support
|
||||||
|
|||||||
@@ -21,12 +21,16 @@
|
|||||||
|
|
||||||
ASMJIT_BEGIN_SUB_NAMESPACE(a64)
|
ASMJIT_BEGIN_SUB_NAMESPACE(a64)
|
||||||
|
|
||||||
|
// a64::Assembler - Utils
|
||||||
|
// ======================
|
||||||
|
|
||||||
|
static ASMJIT_FORCE_INLINE constexpr uint32_t diff(RegType a, RegType b) noexcept { return uint32_t(a) - uint32_t(b); }
|
||||||
|
static ASMJIT_FORCE_INLINE constexpr uint32_t diff(VecElementType elementType, VecElementType baseType) noexcept { return uint32_t(elementType) - uint32_t(baseType); }
|
||||||
|
|
||||||
// a64::Assembler - Cond
|
// a64::Assembler - Cond
|
||||||
// =====================
|
// =====================
|
||||||
|
|
||||||
static inline uint32_t condCodeToOpcodeCond(uint32_t cond) noexcept {
|
static inline uint32_t condCodeToOpcodeCond(uint32_t cond) noexcept { return (uint32_t(cond) - 2u) & 0xFu; }
|
||||||
return (uint32_t(cond) - 2u) & 0xFu;
|
|
||||||
}
|
|
||||||
|
|
||||||
// a64::Assembler - Bits
|
// a64::Assembler - Bits
|
||||||
// =====================
|
// =====================
|
||||||
@@ -49,10 +53,6 @@ static constexpr uint32_t kWX = InstDB::kWX;
|
|||||||
static const uint8_t armShiftOpToLdStOptMap[] = { ASMJIT_LOOKUP_TABLE_16(VALUE, 0) };
|
static const uint8_t armShiftOpToLdStOptMap[] = { ASMJIT_LOOKUP_TABLE_16(VALUE, 0) };
|
||||||
#undef VALUE
|
#undef VALUE
|
||||||
|
|
||||||
static inline constexpr uint32_t diff(RegType a, RegType b) noexcept {
|
|
||||||
return uint32_t(a) - uint32_t(b);
|
|
||||||
}
|
|
||||||
|
|
||||||
// asmjit::a64::Assembler - SizeOp
|
// asmjit::a64::Assembler - SizeOp
|
||||||
// ===============================
|
// ===============================
|
||||||
|
|
||||||
@@ -118,25 +118,25 @@ struct SizeOpTable {
|
|||||||
};
|
};
|
||||||
|
|
||||||
#define VALUE_BIN(x) { \
|
#define VALUE_BIN(x) { \
|
||||||
x == (((uint32_t(RegType::kARM_VecD) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeNone)) ? SizeOp::k00 : \
|
x == (((uint32_t(RegType::kARM_VecD) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kNone)) ? SizeOp::k00 : \
|
||||||
x == (((uint32_t(RegType::kARM_VecV) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeNone)) ? SizeOp::k00Q : \
|
x == (((uint32_t(RegType::kARM_VecV) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kNone)) ? SizeOp::k00Q : \
|
||||||
x == (((uint32_t(RegType::kARM_VecD) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeB )) ? SizeOp::k00 : \
|
x == (((uint32_t(RegType::kARM_VecD) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kB )) ? SizeOp::k00 : \
|
||||||
x == (((uint32_t(RegType::kARM_VecV) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeB )) ? SizeOp::k00Q : SizeOp::kInvalid \
|
x == (((uint32_t(RegType::kARM_VecV) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kB )) ? SizeOp::k00Q : SizeOp::kInvalid \
|
||||||
}
|
}
|
||||||
|
|
||||||
#define VALUE_ANY(x) { \
|
#define VALUE_ANY(x) { \
|
||||||
x == (((uint32_t(RegType::kARM_VecB) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeNone)) ? SizeOp::k00S : \
|
x == (((uint32_t(RegType::kARM_VecB) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kNone)) ? SizeOp::k00S : \
|
||||||
x == (((uint32_t(RegType::kARM_VecH) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeNone)) ? SizeOp::k01S : \
|
x == (((uint32_t(RegType::kARM_VecH) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kNone)) ? SizeOp::k01S : \
|
||||||
x == (((uint32_t(RegType::kARM_VecS) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeNone)) ? SizeOp::k10S : \
|
x == (((uint32_t(RegType::kARM_VecS) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kNone)) ? SizeOp::k10S : \
|
||||||
x == (((uint32_t(RegType::kARM_VecD) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeNone)) ? SizeOp::k11S : \
|
x == (((uint32_t(RegType::kARM_VecD) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kNone)) ? SizeOp::k11S : \
|
||||||
x == (((uint32_t(RegType::kARM_VecD) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeB )) ? SizeOp::k00 : \
|
x == (((uint32_t(RegType::kARM_VecD) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kB )) ? SizeOp::k00 : \
|
||||||
x == (((uint32_t(RegType::kARM_VecV) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeB )) ? SizeOp::k00Q : \
|
x == (((uint32_t(RegType::kARM_VecV) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kB )) ? SizeOp::k00Q : \
|
||||||
x == (((uint32_t(RegType::kARM_VecD) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeH )) ? SizeOp::k01 : \
|
x == (((uint32_t(RegType::kARM_VecD) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kH )) ? SizeOp::k01 : \
|
||||||
x == (((uint32_t(RegType::kARM_VecV) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeH )) ? SizeOp::k01Q : \
|
x == (((uint32_t(RegType::kARM_VecV) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kH )) ? SizeOp::k01Q : \
|
||||||
x == (((uint32_t(RegType::kARM_VecD) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeS )) ? SizeOp::k10 : \
|
x == (((uint32_t(RegType::kARM_VecD) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kS )) ? SizeOp::k10 : \
|
||||||
x == (((uint32_t(RegType::kARM_VecV) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeS )) ? SizeOp::k10Q : \
|
x == (((uint32_t(RegType::kARM_VecV) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kS )) ? SizeOp::k10Q : \
|
||||||
x == (((uint32_t(RegType::kARM_VecD) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeD )) ? SizeOp::k11S : \
|
x == (((uint32_t(RegType::kARM_VecD) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kD )) ? SizeOp::k11S : \
|
||||||
x == (((uint32_t(RegType::kARM_VecV) - uint32_t(RegType::kARM_VecB)) << 3) | (Vec::kElementTypeD )) ? SizeOp::k11Q : SizeOp::kInvalid \
|
x == (((uint32_t(RegType::kARM_VecV) - uint32_t(RegType::kARM_VecB)) << 3) | uint32_t(VecElementType::kD )) ? SizeOp::k11Q : SizeOp::kInvalid \
|
||||||
}
|
}
|
||||||
|
|
||||||
static const SizeOpTable sizeOpTable[SizeOpTable::kCount] = {
|
static const SizeOpTable sizeOpTable[SizeOpTable::kCount] = {
|
||||||
@@ -254,16 +254,16 @@ static const Operand_& significantSimdOp(const Operand_& o0, const Operand_& o1,
|
|||||||
return !(instFlags & InstDB::kInstFlagLong) ? o0 : o1;
|
return !(instFlags & InstDB::kInstFlagLong) ? o0 : o1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline SizeOp armElementTypeToSizeOp(uint32_t vecOpType, RegType regType, uint32_t elementType) noexcept {
|
static inline SizeOp armElementTypeToSizeOp(uint32_t vecOpType, RegType regType, VecElementType elementType) noexcept {
|
||||||
// Instruction data or Assembler is wrong if this triggers an assertion failure.
|
// Instruction data or Assembler is wrong if this triggers an assertion failure.
|
||||||
ASMJIT_ASSERT(vecOpType < InstDB::kVO_Count);
|
ASMJIT_ASSERT(vecOpType < InstDB::kVO_Count);
|
||||||
// ElementType uses 3 bits in the operand signature, it should never overflow.
|
// ElementType uses 3 bits in the operand signature, it should never overflow.
|
||||||
ASMJIT_ASSERT(elementType <= 0x7u);
|
ASMJIT_ASSERT(uint32_t(elementType) <= 0x7u);
|
||||||
|
|
||||||
const SizeOpMap& map = sizeOpMap[vecOpType];
|
const SizeOpMap& map = sizeOpMap[vecOpType];
|
||||||
const SizeOpTable& table = sizeOpTable[map.tableId];
|
const SizeOpTable& table = sizeOpTable[map.tableId];
|
||||||
|
|
||||||
size_t index = (Support::min<uint32_t>(diff(regType, RegType::kARM_VecB), diff(RegType::kARM_VecV, RegType::kARM_VecB) + 1) << 3) | elementType;
|
size_t index = (Support::min<uint32_t>(diff(regType, RegType::kARM_VecB), diff(RegType::kARM_VecV, RegType::kARM_VecB) + 1) << 3) | uint32_t(elementType);
|
||||||
SizeOp op = table.array[index];
|
SizeOp op = table.array[index];
|
||||||
SizeOp modifiedOp { uint8_t(op.value & map.sizeOpMask) };
|
SizeOp modifiedOp { uint8_t(op.value & map.sizeOpMask) };
|
||||||
|
|
||||||
@@ -537,7 +537,7 @@ static inline bool pickFpOpcode(const Vec& reg, uint32_t sOp, uint32_t sHf, uint
|
|||||||
else {
|
else {
|
||||||
// Vector operation [HSD].
|
// Vector operation [HSD].
|
||||||
uint32_t q = diff(reg.type(), RegType::kARM_VecD);
|
uint32_t q = diff(reg.type(), RegType::kARM_VecD);
|
||||||
uint32_t sz = reg.elementType() - Vec::kElementTypeH;
|
uint32_t sz = diff(reg.elementType(), VecElementType::kH);
|
||||||
|
|
||||||
if (q > 1u || sz > 2u || !Support::bitTest(szBits[vHf].sizeMask, sz))
|
if (q > 1u || sz > 2u || !Support::bitTest(szBits[vHf].sizeMask, sz))
|
||||||
return false;
|
return false;
|
||||||
@@ -2768,7 +2768,7 @@ Case_BaseLdurStur:
|
|||||||
// hD, vS.{4|8}h (16-bit)
|
// hD, vS.{4|8}h (16-bit)
|
||||||
// sD, vS.4s (32-bit)
|
// sD, vS.4s (32-bit)
|
||||||
uint32_t sz = diff(o0.as<Reg>().type(), RegType::kARM_VecH);
|
uint32_t sz = diff(o0.as<Reg>().type(), RegType::kARM_VecH);
|
||||||
uint32_t elementSz = o1.as<Vec>().elementType() - Vec::kElementTypeH;
|
uint32_t elementSz = diff(o1.as<Vec>().elementType(), VecElementType::kH);
|
||||||
|
|
||||||
// Size greater than 1 means 64-bit elements, not supported.
|
// Size greater than 1 means 64-bit elements, not supported.
|
||||||
if ((sz | elementSz) > 1 || sz != elementSz)
|
if ((sz | elementSz) > 1 || sz != elementSz)
|
||||||
@@ -2890,7 +2890,7 @@ Case_BaseLdurStur:
|
|||||||
if (q > 1)
|
if (q > 1)
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
uint32_t sz = o0.as<Vec>().elementType() - Vec::kElementTypeB;
|
uint32_t sz = diff(o0.as<Vec>().elementType(), VecElementType::kB);
|
||||||
if (sz == 0 || sz > 3)
|
if (sz == 0 || sz > 3)
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
@@ -2982,7 +2982,7 @@ Case_BaseLdurStur:
|
|||||||
if (q > 1)
|
if (q > 1)
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
uint32_t sz = o0.as<Vec>().elementType() - Vec::kElementTypeB;
|
uint32_t sz = diff(o0.as<Vec>().elementType(), VecElementType::kB);
|
||||||
if (sz == 0 || sz > 3)
|
if (sz == 0 || sz > 3)
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
@@ -3164,11 +3164,11 @@ Case_BaseLdurStur:
|
|||||||
if (uint32_t(opcode.hasQ()) != q)
|
if (uint32_t(opcode.hasQ()) != q)
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
if (rL.isVecS4() && rN.elementType() == Vec::kElementTypeH && !opData.isCvtxn()) {
|
if (rL.isVecS4() && rN.elementType() == VecElementType::kH && !opData.isCvtxn()) {
|
||||||
goto EmitOp_Rd0_Rn5;
|
goto EmitOp_Rd0_Rn5;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (rL.isVecD2() && rN.elementType() == Vec::kElementTypeS) {
|
if (rL.isVecD2() && rN.elementType() == VecElementType::kS) {
|
||||||
opcode |= B(22);
|
opcode |= B(22);
|
||||||
goto EmitOp_Rd0_Rn5;
|
goto EmitOp_Rd0_Rn5;
|
||||||
}
|
}
|
||||||
@@ -3279,8 +3279,8 @@ Case_BaseLdurStur:
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (uint32_t(o0.as<Reg>().type()) != uint32_t(o1.as<Reg>().type()) + qIsOptional ||
|
if (uint32_t(o0.as<Reg>().type()) != uint32_t(o1.as<Reg>().type()) + qIsOptional ||
|
||||||
o0.as<Vec>().elementType() != opData.tA ||
|
uint32_t(o0.as<Vec>().elementType()) != opData.tA ||
|
||||||
o1.as<Vec>().elementType() != opData.tB)
|
uint32_t(o1.as<Vec>().elementType()) != opData.tB)
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
if (!o2.as<Vec>().hasElementIndex()) {
|
if (!o2.as<Vec>().hasElementIndex()) {
|
||||||
@@ -3292,7 +3292,7 @@ Case_BaseLdurStur:
|
|||||||
goto EmitOp_Rd0_Rn5_Rm16;
|
goto EmitOp_Rd0_Rn5_Rm16;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
if (o2.as<Vec>().elementType() != opData.tElement)
|
if (uint32_t(o2.as<Vec>().elementType()) != opData.tElement)
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
if (o2.as<Reg>().id() > 15)
|
if (o2.as<Reg>().id() > 15)
|
||||||
@@ -3442,7 +3442,7 @@ Case_BaseLdurStur:
|
|||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
uint32_t q = diff(o0.as<Vec>().type(), RegType::kARM_VecD);
|
uint32_t q = diff(o0.as<Vec>().type(), RegType::kARM_VecD);
|
||||||
uint32_t sz = o0.as<Vec>().elementType() - Vec::kElementTypeH;
|
uint32_t sz = diff(o0.as<Vec>().elementType(), VecElementType::kH);
|
||||||
|
|
||||||
if (q > 1 || sz > 2)
|
if (q > 1 || sz > 2)
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
@@ -3496,7 +3496,7 @@ Case_BaseLdurStur:
|
|||||||
if (q > 1)
|
if (q > 1)
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
uint32_t sz = o0.as<Vec>().elementType() - Vec::kElementTypeH;
|
uint32_t sz = diff(o0.as<Vec>().elementType(), VecElementType::kH);
|
||||||
if (sz > 2)
|
if (sz > 2)
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
@@ -3520,7 +3520,7 @@ Case_BaseLdurStur:
|
|||||||
if (isign4 == ENC_OPS2(Reg, Reg)) {
|
if (isign4 == ENC_OPS2(Reg, Reg)) {
|
||||||
// The first destination operand is scalar, which matches element-type of source vectors.
|
// The first destination operand is scalar, which matches element-type of source vectors.
|
||||||
uint32_t L = (instFlags & InstDB::kInstFlagLong) != 0;
|
uint32_t L = (instFlags & InstDB::kInstFlagLong) != 0;
|
||||||
if (diff(o0.as<Vec>().type(), RegType::kARM_VecB) != o1.as<Vec>().elementType() - Vec::kElementTypeB + L)
|
if (diff(o0.as<Vec>().type(), RegType::kARM_VecB) != diff(o1.as<Vec>().elementType(), VecElementType::kB) + L)
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
SizeOp sizeOp = armElementTypeToSizeOp(opData.vecOpType, o1.as<Reg>().type(), o1.as<Vec>().elementType());
|
SizeOp sizeOp = armElementTypeToSizeOp(opData.vecOpType, o1.as<Reg>().type(), o1.as<Vec>().elementType());
|
||||||
@@ -3620,7 +3620,7 @@ Case_BaseLdurStur:
|
|||||||
if (!sizeOp.isValid())
|
if (!sizeOp.isValid())
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
if (!checkSignature(o0, o1) || !o0.as<Reg>().isVecV() || o0.as<Vec>().elementType() != o2.as<Vec>().elementType() + 1)
|
if (!checkSignature(o0, o1) || !o0.as<Reg>().isVecV() || uint32_t(o0.as<Vec>().elementType()) != uint32_t(o2.as<Vec>().elementType()) + 1u)
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
opcode.reset(opData.opcode());
|
opcode.reset(opData.opcode());
|
||||||
@@ -3905,9 +3905,9 @@ Case_BaseLdurStur:
|
|||||||
if (o0.as<Reg>().type() != o1.as<Reg>().type() || o1.as<Reg>().type() != o2.as<Reg>().type())
|
if (o0.as<Reg>().type() != o1.as<Reg>().type() || o1.as<Reg>().type() != o2.as<Reg>().type())
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
if (o0.as<Vec>().elementType() != opData.tA ||
|
if (uint32_t(o0.as<Vec>().elementType()) != opData.tA ||
|
||||||
o1.as<Vec>().elementType() != opData.tB ||
|
uint32_t(o1.as<Vec>().elementType()) != opData.tB ||
|
||||||
o2.as<Vec>().elementType() != opData.tB)
|
uint32_t(o2.as<Vec>().elementType()) != opData.tB)
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
opcode.reset(uint32_t(opData.vectorOp) << 10);
|
opcode.reset(uint32_t(opData.vectorOp) << 10);
|
||||||
@@ -3921,9 +3921,9 @@ Case_BaseLdurStur:
|
|||||||
if (o0.as<Reg>().type() != o1.as<Reg>().type() || !o2.as<Reg>().isVecV())
|
if (o0.as<Reg>().type() != o1.as<Reg>().type() || !o2.as<Reg>().isVecV())
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
if (o0.as<Vec>().elementType() != opData.tA ||
|
if (uint32_t(o0.as<Vec>().elementType()) != opData.tA ||
|
||||||
o1.as<Vec>().elementType() != opData.tB ||
|
uint32_t(o1.as<Vec>().elementType()) != opData.tB ||
|
||||||
o2.as<Vec>().elementType() != opData.tElement)
|
uint32_t(o2.as<Vec>().elementType()) != opData.tElement)
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
uint32_t elementIndex = o2.as<Vec>().elementIndex();
|
uint32_t elementIndex = o2.as<Vec>().elementIndex();
|
||||||
@@ -3949,13 +3949,13 @@ Case_BaseLdurStur:
|
|||||||
case InstDB::kEncodingSimdDup: SimdDup: {
|
case InstDB::kEncodingSimdDup: SimdDup: {
|
||||||
if (isign4 == ENC_OPS2(Reg, Reg)) {
|
if (isign4 == ENC_OPS2(Reg, Reg)) {
|
||||||
// Truth table of valid encodings of `Q:1|ElementType:3`
|
// Truth table of valid encodings of `Q:1|ElementType:3`
|
||||||
uint32_t kValidEncodings = B(Vec::kElementTypeB + 0) |
|
uint32_t kValidEncodings = B(uint32_t(VecElementType::kB) + 0) |
|
||||||
B(Vec::kElementTypeH + 0) |
|
B(uint32_t(VecElementType::kH) + 0) |
|
||||||
B(Vec::kElementTypeS + 0) |
|
B(uint32_t(VecElementType::kS) + 0) |
|
||||||
B(Vec::kElementTypeB + 8) |
|
B(uint32_t(VecElementType::kB) + 8) |
|
||||||
B(Vec::kElementTypeH + 8) |
|
B(uint32_t(VecElementType::kH) + 8) |
|
||||||
B(Vec::kElementTypeS + 8) |
|
B(uint32_t(VecElementType::kS) + 8) |
|
||||||
B(Vec::kElementTypeD + 8) ;
|
B(uint32_t(VecElementType::kD) + 8) ;
|
||||||
|
|
||||||
uint32_t q = diff(o0.as<Reg>().type(), RegType::kARM_VecD);
|
uint32_t q = diff(o0.as<Reg>().type(), RegType::kARM_VecD);
|
||||||
|
|
||||||
@@ -3964,7 +3964,7 @@ Case_BaseLdurStur:
|
|||||||
//
|
//
|
||||||
// NOTE: This is only scalar for `dup d, x` case, otherwise the value
|
// NOTE: This is only scalar for `dup d, x` case, otherwise the value
|
||||||
// would be duplicated across all vector elements (1, 2, 4, 8, or 16).
|
// would be duplicated across all vector elements (1, 2, 4, 8, or 16).
|
||||||
uint32_t elementType = o0.as<Vec>().elementType();
|
uint32_t elementType = uint32_t(o0.as<Vec>().elementType());
|
||||||
if (q > 1 || !Support::bitTest(kValidEncodings, (q << 3) | elementType))
|
if (q > 1 || !Support::bitTest(kValidEncodings, (q << 3) | elementType))
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
@@ -3985,7 +3985,7 @@ Case_BaseLdurStur:
|
|||||||
// DUP - Vec (scalar) <- Vec[N].
|
// DUP - Vec (scalar) <- Vec[N].
|
||||||
uint32_t lsbIndex = diff(o0.as<Reg>().type(), RegType::kARM_VecB);
|
uint32_t lsbIndex = diff(o0.as<Reg>().type(), RegType::kARM_VecB);
|
||||||
|
|
||||||
if (lsbIndex != o1.as<Vec>().elementType() - Vec::kElementTypeB || lsbIndex > 3)
|
if (lsbIndex != diff(o1.as<Vec>().elementType(), VecElementType::kB) || lsbIndex > 3)
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
uint32_t imm5 = ((dstIndex << 1) | 1u) << lsbIndex;
|
uint32_t imm5 = ((dstIndex << 1) | 1u) << lsbIndex;
|
||||||
@@ -3998,7 +3998,7 @@ Case_BaseLdurStur:
|
|||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
// DUP - Vec (all) <- Vec[N].
|
// DUP - Vec (all) <- Vec[N].
|
||||||
uint32_t elementType = o0.as<Vec>().elementType();
|
uint32_t elementType = uint32_t(o0.as<Vec>().elementType());
|
||||||
if (q > 1 || !Support::bitTest(kValidEncodings, (q << 3) | elementType))
|
if (q > 1 || !Support::bitTest(kValidEncodings, (q << 3) | elementType))
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
@@ -4023,7 +4023,7 @@ Case_BaseLdurStur:
|
|||||||
if (!o0.as<Vec>().hasElementIndex())
|
if (!o0.as<Vec>().hasElementIndex())
|
||||||
goto InvalidInstruction;
|
goto InvalidInstruction;
|
||||||
|
|
||||||
uint32_t elementType = o0.as<Vec>().elementType();
|
uint32_t elementType = uint32_t(o0.as<Vec>().elementType());
|
||||||
uint32_t dstIndex = o0.as<Vec>().elementIndex();
|
uint32_t dstIndex = o0.as<Vec>().elementIndex();
|
||||||
uint32_t lsbIndex = elementType - 1u;
|
uint32_t lsbIndex = elementType - 1u;
|
||||||
|
|
||||||
@@ -4735,7 +4735,7 @@ Case_SimdLdurStur:
|
|||||||
uint32_t q = 0;
|
uint32_t q = 0;
|
||||||
uint32_t rm = 0;
|
uint32_t rm = 0;
|
||||||
uint32_t rn = m.baseId();
|
uint32_t rn = m.baseId();
|
||||||
uint32_t sz = v.elementType() - Vec::kElementTypeB;
|
uint32_t sz = diff(v.elementType(), VecElementType::kB);
|
||||||
uint32_t opcSsize = sz;
|
uint32_t opcSsize = sz;
|
||||||
uint32_t offsetPossibility = 0;
|
uint32_t offsetPossibility = 0;
|
||||||
|
|
||||||
|
|||||||
@@ -31,14 +31,6 @@ public:
|
|||||||
|
|
||||||
//! \}
|
//! \}
|
||||||
|
|
||||||
//! \name Accessors
|
|
||||||
//! \{
|
|
||||||
|
|
||||||
//! Gets whether the current ARM mode is THUMB (alternative to 32-bit ARM encoding).
|
|
||||||
ASMJIT_INLINE_NODEBUG bool isInThumbMode() const noexcept { return _environment.isArchThumb(); }
|
|
||||||
|
|
||||||
//! \}
|
|
||||||
|
|
||||||
//! \name Emit
|
//! \name Emit
|
||||||
//! \{
|
//! \{
|
||||||
|
|
||||||
|
|||||||
@@ -174,10 +174,10 @@ Error queryRWInfo(const BaseInst& inst, const Operand_* operands, size_t opCount
|
|||||||
if (srcOp.isReg()) {
|
if (srcOp.isReg()) {
|
||||||
if (srcOp.as<Vec>().hasElementIndex()) {
|
if (srcOp.as<Vec>().hasElementIndex()) {
|
||||||
// Only part of the vector is accessed if element index [] is used.
|
// Only part of the vector is accessed if element index [] is used.
|
||||||
uint32_t elementType = srcOp.as<Vec>().elementType();
|
VecElementType elementType = srcOp.as<Vec>().elementType();
|
||||||
uint32_t elementIndex = srcOp.as<Vec>().elementIndex();
|
uint32_t elementIndex = srcOp.as<Vec>().elementIndex();
|
||||||
|
|
||||||
uint32_t elementSize = elementTypeSize[elementType];
|
uint32_t elementSize = elementTypeSize[size_t(elementType)];
|
||||||
uint64_t accessMask = uint64_t(Support::lsbMask<uint32_t>(elementSize)) << (elementIndex * elementSize);
|
uint64_t accessMask = uint64_t(Support::lsbMask<uint32_t>(elementSize)) << (elementIndex * elementSize);
|
||||||
|
|
||||||
op._readByteMask &= accessMask;
|
op._readByteMask &= accessMask;
|
||||||
|
|||||||
@@ -59,14 +59,14 @@ enum RWInfoType : uint32_t {
|
|||||||
// a64::InstDB - ElementType
|
// a64::InstDB - ElementType
|
||||||
// =========================
|
// =========================
|
||||||
|
|
||||||
enum ElementType : uint8_t {
|
enum InstElementType : uint8_t {
|
||||||
kET_None = Vec::kElementTypeNone,
|
kET_None = uint8_t(VecElementType::kNone),
|
||||||
kET_B = Vec::kElementTypeB,
|
kET_B = uint8_t(VecElementType::kB),
|
||||||
kET_H = Vec::kElementTypeH,
|
kET_H = uint8_t(VecElementType::kH),
|
||||||
kET_S = Vec::kElementTypeS,
|
kET_S = uint8_t(VecElementType::kS),
|
||||||
kET_D = Vec::kElementTypeD,
|
kET_D = uint8_t(VecElementType::kD),
|
||||||
kET_2H = Vec::kElementTypeH2,
|
kET_2H = uint8_t(VecElementType::kH2),
|
||||||
kET_4B = Vec::kElementTypeB4
|
kET_4B = uint8_t(VecElementType::kB4)
|
||||||
};
|
};
|
||||||
|
|
||||||
// a64::InstDB - GpType
|
// a64::InstDB - GpType
|
||||||
|
|||||||
@@ -56,7 +56,7 @@ UNIT(a64_operand) {
|
|||||||
EXPECT_EQ(vd_1.group(), RegGroup::kVec);
|
EXPECT_EQ(vd_1.group(), RegGroup::kVec);
|
||||||
EXPECT_EQ(vd_1.id(), 15u);
|
EXPECT_EQ(vd_1.id(), 15u);
|
||||||
EXPECT_TRUE(vd_1.isVecD2());
|
EXPECT_TRUE(vd_1.isVecD2());
|
||||||
EXPECT_EQ(vd_1.elementType(), Vec::kElementTypeD);
|
EXPECT_EQ(vd_1.elementType(), VecElementType::kD);
|
||||||
EXPECT_TRUE(vd_1.hasElementIndex());
|
EXPECT_TRUE(vd_1.hasElementIndex());
|
||||||
EXPECT_EQ(vd_1.elementIndex(), 1u);
|
EXPECT_EQ(vd_1.elementIndex(), 1u);
|
||||||
|
|
||||||
@@ -65,7 +65,7 @@ UNIT(a64_operand) {
|
|||||||
EXPECT_EQ(vs_3.group(), RegGroup::kVec);
|
EXPECT_EQ(vs_3.group(), RegGroup::kVec);
|
||||||
EXPECT_EQ(vs_3.id(), 15u);
|
EXPECT_EQ(vs_3.id(), 15u);
|
||||||
EXPECT_TRUE(vs_3.isVecS4());
|
EXPECT_TRUE(vs_3.isVecS4());
|
||||||
EXPECT_EQ(vs_3.elementType(), Vec::kElementTypeS);
|
EXPECT_EQ(vs_3.elementType(), VecElementType::kS);
|
||||||
EXPECT_TRUE(vs_3.hasElementIndex());
|
EXPECT_TRUE(vs_3.hasElementIndex());
|
||||||
EXPECT_EQ(vs_3.elementIndex(), 3u);
|
EXPECT_EQ(vs_3.elementIndex(), 3u);
|
||||||
|
|
||||||
@@ -74,7 +74,7 @@ UNIT(a64_operand) {
|
|||||||
EXPECT_EQ(vb_4.group(), RegGroup::kVec);
|
EXPECT_EQ(vb_4.group(), RegGroup::kVec);
|
||||||
EXPECT_EQ(vb_4.id(), 15u);
|
EXPECT_EQ(vb_4.id(), 15u);
|
||||||
EXPECT_TRUE(vb_4.isVecB4x4());
|
EXPECT_TRUE(vb_4.isVecB4x4());
|
||||||
EXPECT_EQ(vb_4.elementType(), Vec::kElementTypeB4);
|
EXPECT_EQ(vb_4.elementType(), VecElementType::kB4);
|
||||||
EXPECT_TRUE(vb_4.hasElementIndex());
|
EXPECT_TRUE(vb_4.hasElementIndex());
|
||||||
EXPECT_EQ(vb_4.elementIndex(), 3u);
|
EXPECT_EQ(vb_4.elementIndex(), 3u);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -69,74 +69,60 @@ ASMJIT_INLINE_NODEBUG GpW Gp::w() const noexcept { return GpW(id()); }
|
|||||||
ASMJIT_INLINE_NODEBUG GpX Gp::x() const noexcept { return GpX(id()); }
|
ASMJIT_INLINE_NODEBUG GpX Gp::x() const noexcept { return GpX(id()); }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
//! Vector element type (AArch64).
|
||||||
|
enum class VecElementType : uint32_t {
|
||||||
|
//! No element type specified.
|
||||||
|
kNone = 0,
|
||||||
|
//! Byte elements (B8 or B16).
|
||||||
|
kB,
|
||||||
|
//! Halfword elements (H4 or H8).
|
||||||
|
kH,
|
||||||
|
//! Singleword elements (S2 or S4).
|
||||||
|
kS,
|
||||||
|
//! Doubleword elements (D2).
|
||||||
|
kD,
|
||||||
|
//! Byte elements grouped by 4 bytes (B4).
|
||||||
|
//!
|
||||||
|
//! \note This element-type is only used by few instructions.
|
||||||
|
kB4,
|
||||||
|
//! Halfword elements grouped by 2 halfwords (H2).
|
||||||
|
//!
|
||||||
|
//! \note This element-type is only used by few instructions.
|
||||||
|
kH2,
|
||||||
|
|
||||||
|
//! Maximum value of \ref VecElementType
|
||||||
|
kMaxValue = kH2
|
||||||
|
};
|
||||||
|
|
||||||
//! Vector register (AArch64).
|
//! Vector register (AArch64).
|
||||||
class Vec : public BaseVec {
|
class Vec : public BaseVec {
|
||||||
public:
|
public:
|
||||||
ASMJIT_DEFINE_ABSTRACT_REG(Vec, BaseVec)
|
ASMJIT_DEFINE_ABSTRACT_REG(Vec, BaseVec)
|
||||||
|
|
||||||
//! Element type (AArch64 only).
|
|
||||||
enum ElementType : uint32_t {
|
|
||||||
//! No element type specified.
|
|
||||||
kElementTypeNone = 0,
|
|
||||||
//! Byte elements (B8 or B16).
|
|
||||||
kElementTypeB,
|
|
||||||
//! Halfword elements (H4 or H8).
|
|
||||||
kElementTypeH,
|
|
||||||
//! Singleword elements (S2 or S4).
|
|
||||||
kElementTypeS,
|
|
||||||
//! Doubleword elements (D2).
|
|
||||||
kElementTypeD,
|
|
||||||
//! Byte elements grouped by 4 bytes (B4).
|
|
||||||
//!
|
|
||||||
//! \note This element-type is only used by few instructions.
|
|
||||||
kElementTypeB4,
|
|
||||||
//! Halfword elements grouped by 2 halfwords (H2).
|
|
||||||
//!
|
|
||||||
//! \note This element-type is only used by few instructions.
|
|
||||||
kElementTypeH2,
|
|
||||||
|
|
||||||
//! Count of element types.
|
|
||||||
kElementTypeCount
|
|
||||||
};
|
|
||||||
|
|
||||||
//! \cond
|
//! \cond
|
||||||
//! Shortcuts.
|
//! Shortcuts.
|
||||||
enum SignatureReg : uint32_t {
|
enum SignatureReg : uint32_t {
|
||||||
kSignatureElementB = kElementTypeB << kSignatureRegElementTypeShift,
|
kSignatureElementB = uint32_t(VecElementType::kB) << kSignatureRegElementTypeShift,
|
||||||
kSignatureElementH = kElementTypeH << kSignatureRegElementTypeShift,
|
kSignatureElementH = uint32_t(VecElementType::kH) << kSignatureRegElementTypeShift,
|
||||||
kSignatureElementS = kElementTypeS << kSignatureRegElementTypeShift,
|
kSignatureElementS = uint32_t(VecElementType::kS) << kSignatureRegElementTypeShift,
|
||||||
kSignatureElementD = kElementTypeD << kSignatureRegElementTypeShift,
|
kSignatureElementD = uint32_t(VecElementType::kD) << kSignatureRegElementTypeShift,
|
||||||
kSignatureElementB4 = kElementTypeB4 << kSignatureRegElementTypeShift,
|
kSignatureElementB4 = uint32_t(VecElementType::kB4) << kSignatureRegElementTypeShift,
|
||||||
kSignatureElementH2 = kElementTypeH2 << kSignatureRegElementTypeShift
|
kSignatureElementH2 = uint32_t(VecElementType::kH2) << kSignatureRegElementTypeShift
|
||||||
};
|
};
|
||||||
//! \endcond
|
//! \endcond
|
||||||
|
|
||||||
//! Returns whether the register has associated an element type.
|
|
||||||
ASMJIT_INLINE_NODEBUG constexpr bool hasElementType() const noexcept { return _signature.hasField<kSignatureRegElementTypeMask>(); }
|
|
||||||
//! Returns whether the register has element index (it's an element index access).
|
|
||||||
ASMJIT_INLINE_NODEBUG constexpr bool hasElementIndex() const noexcept { return _signature.hasField<kSignatureRegElementFlagMask>(); }
|
|
||||||
//! Returns whether the register has element type or element index (or both).
|
//! Returns whether the register has element type or element index (or both).
|
||||||
ASMJIT_INLINE_NODEBUG constexpr bool hasElementTypeOrIndex() const noexcept { return _signature.hasField<kSignatureRegElementTypeMask | kSignatureRegElementFlagMask>(); }
|
ASMJIT_INLINE_NODEBUG constexpr bool hasElementTypeOrIndex() const noexcept { return _signature.hasField<kSignatureRegElementTypeMask | kSignatureRegElementFlagMask>(); }
|
||||||
|
|
||||||
//! Returns element type of the register.
|
//! Returns whether the vector register has associated a vector element type.
|
||||||
ASMJIT_INLINE_NODEBUG constexpr uint32_t elementType() const noexcept { return _signature.getField<kSignatureRegElementTypeMask>(); }
|
ASMJIT_INLINE_NODEBUG constexpr bool hasElementType() const noexcept { return _signature.hasField<kSignatureRegElementTypeMask>(); }
|
||||||
//! Sets element type of the register to `elementType`.
|
//! Returns vector element type of the register.
|
||||||
ASMJIT_INLINE_NODEBUG void setElementType(uint32_t elementType) noexcept { _signature.setField<kSignatureRegElementTypeMask>(elementType); }
|
ASMJIT_INLINE_NODEBUG constexpr VecElementType elementType() const noexcept { return VecElementType(_signature.getField<kSignatureRegElementTypeMask>()); }
|
||||||
//! Resets element type to none.
|
//! Sets vector element type of the register to `elementType`.
|
||||||
|
ASMJIT_INLINE_NODEBUG void setElementType(VecElementType elementType) noexcept { _signature.setField<kSignatureRegElementTypeMask>(uint32_t(elementType)); }
|
||||||
|
//! Resets vector element type to none.
|
||||||
ASMJIT_INLINE_NODEBUG void resetElementType() noexcept { _signature.setField<kSignatureRegElementTypeMask>(0); }
|
ASMJIT_INLINE_NODEBUG void resetElementType() noexcept { _signature.setField<kSignatureRegElementTypeMask>(0); }
|
||||||
|
|
||||||
//! Returns element index of the register.
|
|
||||||
ASMJIT_INLINE_NODEBUG constexpr uint32_t elementIndex() const noexcept { return _signature.getField<kSignatureRegElementIndexMask>(); }
|
|
||||||
//! Sets element index of the register to `elementType`.
|
|
||||||
ASMJIT_INLINE_NODEBUG void setElementIndex(uint32_t elementIndex) noexcept {
|
|
||||||
_signature |= kSignatureRegElementFlagMask;
|
|
||||||
_signature.setField<kSignatureRegElementIndexMask>(elementIndex);
|
|
||||||
}
|
|
||||||
//! Resets element index of the register.
|
|
||||||
ASMJIT_INLINE_NODEBUG void resetElementIndex() noexcept {
|
|
||||||
_signature &= ~(kSignatureRegElementFlagMask | kSignatureRegElementIndexMask);
|
|
||||||
}
|
|
||||||
|
|
||||||
ASMJIT_INLINE_NODEBUG constexpr bool isVecB8() const noexcept { return _signature.subset(kBaseSignatureMask | kSignatureRegElementTypeMask) == (RegTraits<RegType::kARM_VecD>::kSignature | kSignatureElementB); }
|
ASMJIT_INLINE_NODEBUG constexpr bool isVecB8() const noexcept { return _signature.subset(kBaseSignatureMask | kSignatureRegElementTypeMask) == (RegTraits<RegType::kARM_VecD>::kSignature | kSignatureElementB); }
|
||||||
ASMJIT_INLINE_NODEBUG constexpr bool isVecH4() const noexcept { return _signature.subset(kBaseSignatureMask | kSignatureRegElementTypeMask) == (RegTraits<RegType::kARM_VecD>::kSignature | kSignatureElementH); }
|
ASMJIT_INLINE_NODEBUG constexpr bool isVecH4() const noexcept { return _signature.subset(kBaseSignatureMask | kSignatureRegElementTypeMask) == (RegTraits<RegType::kARM_VecD>::kSignature | kSignatureElementH); }
|
||||||
ASMJIT_INLINE_NODEBUG constexpr bool isVecS2() const noexcept { return _signature.subset(kBaseSignatureMask | kSignatureRegElementTypeMask) == (RegTraits<RegType::kARM_VecD>::kSignature | kSignatureElementS); }
|
ASMJIT_INLINE_NODEBUG constexpr bool isVecS2() const noexcept { return _signature.subset(kBaseSignatureMask | kSignatureRegElementTypeMask) == (RegTraits<RegType::kARM_VecD>::kSignature | kSignatureElementS); }
|
||||||
@@ -197,12 +183,12 @@ public:
|
|||||||
//! Cast this register to V.2D.
|
//! Cast this register to V.2D.
|
||||||
ASMJIT_INLINE_NODEBUG VecV d2() const noexcept;
|
ASMJIT_INLINE_NODEBUG VecV d2() const noexcept;
|
||||||
|
|
||||||
static ASMJIT_INLINE_NODEBUG constexpr OperandSignature _makeElementAccessSignature(uint32_t elementType, uint32_t elementIndex) noexcept {
|
static ASMJIT_INLINE_NODEBUG constexpr OperandSignature _makeElementAccessSignature(VecElementType elementType, uint32_t elementIndex) noexcept {
|
||||||
return OperandSignature{
|
return OperandSignature{
|
||||||
uint32_t(RegTraits<RegType::kARM_VecV>::kSignature) |
|
uint32_t(RegTraits<RegType::kARM_VecV>::kSignature) |
|
||||||
uint32_t(kSignatureRegElementFlagMask) |
|
uint32_t(kSignatureRegElementFlagMask) |
|
||||||
uint32_t(elementType << kSignatureRegElementTypeShift) |
|
(uint32_t(elementType) << kSignatureRegElementTypeShift) |
|
||||||
uint32_t(elementIndex << kSignatureRegElementIndexShift)};
|
(uint32_t(elementIndex << kSignatureRegElementIndexShift))};
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -243,12 +229,12 @@ ASMJIT_INLINE_NODEBUG VecD Vec::d() const noexcept { return VecD(id()); }
|
|||||||
ASMJIT_INLINE_NODEBUG VecV Vec::q() const noexcept { return VecV(id()); }
|
ASMJIT_INLINE_NODEBUG VecV Vec::q() const noexcept { return VecV(id()); }
|
||||||
ASMJIT_INLINE_NODEBUG VecV Vec::v() const noexcept { return VecV(id()); }
|
ASMJIT_INLINE_NODEBUG VecV Vec::v() const noexcept { return VecV(id()); }
|
||||||
|
|
||||||
ASMJIT_INLINE_NODEBUG VecV Vec::b(uint32_t elementIndex) const noexcept { return VecV(_makeElementAccessSignature(kElementTypeB, elementIndex), id()); }
|
ASMJIT_INLINE_NODEBUG VecV Vec::b(uint32_t elementIndex) const noexcept { return VecV(_makeElementAccessSignature(VecElementType::kB, elementIndex), id()); }
|
||||||
ASMJIT_INLINE_NODEBUG VecV Vec::h(uint32_t elementIndex) const noexcept { return VecV(_makeElementAccessSignature(kElementTypeH, elementIndex), id()); }
|
ASMJIT_INLINE_NODEBUG VecV Vec::h(uint32_t elementIndex) const noexcept { return VecV(_makeElementAccessSignature(VecElementType::kH, elementIndex), id()); }
|
||||||
ASMJIT_INLINE_NODEBUG VecV Vec::s(uint32_t elementIndex) const noexcept { return VecV(_makeElementAccessSignature(kElementTypeS, elementIndex), id()); }
|
ASMJIT_INLINE_NODEBUG VecV Vec::s(uint32_t elementIndex) const noexcept { return VecV(_makeElementAccessSignature(VecElementType::kS, elementIndex), id()); }
|
||||||
ASMJIT_INLINE_NODEBUG VecV Vec::d(uint32_t elementIndex) const noexcept { return VecV(_makeElementAccessSignature(kElementTypeD, elementIndex), id()); }
|
ASMJIT_INLINE_NODEBUG VecV Vec::d(uint32_t elementIndex) const noexcept { return VecV(_makeElementAccessSignature(VecElementType::kD, elementIndex), id()); }
|
||||||
ASMJIT_INLINE_NODEBUG VecV Vec::h2(uint32_t elementIndex) const noexcept { return VecV(_makeElementAccessSignature(kElementTypeH2, elementIndex), id()); }
|
ASMJIT_INLINE_NODEBUG VecV Vec::h2(uint32_t elementIndex) const noexcept { return VecV(_makeElementAccessSignature(VecElementType::kH2, elementIndex), id()); }
|
||||||
ASMJIT_INLINE_NODEBUG VecV Vec::b4(uint32_t elementIndex) const noexcept { return VecV(_makeElementAccessSignature(kElementTypeB4, elementIndex), id()); }
|
ASMJIT_INLINE_NODEBUG VecV Vec::b4(uint32_t elementIndex) const noexcept { return VecV(_makeElementAccessSignature(VecElementType::kB4, elementIndex), id()); }
|
||||||
|
|
||||||
ASMJIT_INLINE_NODEBUG VecD Vec::b8() const noexcept { return VecD(OperandSignature{VecD::kSignature | kSignatureElementB}, id()); }
|
ASMJIT_INLINE_NODEBUG VecD Vec::b8() const noexcept { return VecD(OperandSignature{VecD::kSignature | kSignatureElementB}, id()); }
|
||||||
ASMJIT_INLINE_NODEBUG VecS Vec::h2() const noexcept { return VecS(OperandSignature{VecS::kSignature | kSignatureElementH}, id()); }
|
ASMJIT_INLINE_NODEBUG VecS Vec::h2() const noexcept { return VecS(OperandSignature{VecS::kSignature | kSignatureElementH}, id()); }
|
||||||
|
|||||||
@@ -230,7 +230,7 @@ Error RACFGBuilder::onInst(InstNode* inst, InstControlFlow& controlType, RAInstB
|
|||||||
if (reg.as<Vec>().hasElementIndex()) {
|
if (reg.as<Vec>().hasElementIndex()) {
|
||||||
// Only the first 0..15 registers can be used if the register uses
|
// Only the first 0..15 registers can be used if the register uses
|
||||||
// element accessor that accesses half-words (h[0..7] elements).
|
// element accessor that accesses half-words (h[0..7] elements).
|
||||||
if (instInfo.hasFlag(InstDB::kInstFlagVH0_15) && reg.as<Vec>().elementType() == Vec::kElementTypeH) {
|
if (instInfo.hasFlag(InstDB::kInstFlagVH0_15) && reg.as<Vec>().elementType() == VecElementType::kH) {
|
||||||
if (Support::test(flags, RATiedFlags::kUse))
|
if (Support::test(flags, RATiedFlags::kUse))
|
||||||
useId &= 0x0000FFFFu;
|
useId &= 0x0000FFFFu;
|
||||||
else
|
else
|
||||||
|
|||||||
@@ -318,9 +318,9 @@ ASMJIT_FAVOR_SIZE Error FormatterInternal::formatRegister(
|
|||||||
ASMJIT_PROPAGATE(sb.appendFormat("%c%u", letter, rId));
|
ASMJIT_PROPAGATE(sb.appendFormat("%c%u", letter, rId));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
constexpr uint32_t kElementTypeCount = uint32_t(a64::VecElementType::kMaxValue) + 1;
|
||||||
if (elementType) {
|
if (elementType) {
|
||||||
if (elementType > a64::Vec::kElementTypeCount)
|
elementType = Support::min(elementType, kElementTypeCount);
|
||||||
elementType = a64::Vec::kElementTypeCount;
|
|
||||||
|
|
||||||
FormatElementData elementData = formatElementDataTable[elementType];
|
FormatElementData elementData = formatElementDataTable[elementType];
|
||||||
uint32_t elementCount = elementData.elementCount;
|
uint32_t elementCount = elementData.elementCount;
|
||||||
|
|||||||
@@ -239,6 +239,13 @@ namespace asmjit {
|
|||||||
//! because some compilers would warn about that. If your project compiles fine with `ASMJIT_NO_DEPRECATED`
|
//! because some compilers would warn about that. If your project compiles fine with `ASMJIT_NO_DEPRECATED`
|
||||||
//! it's not using anything, which was deprecated.
|
//! it's not using anything, which was deprecated.
|
||||||
//!
|
//!
|
||||||
|
//! ### Changes committed at 2023-12-27
|
||||||
|
//!
|
||||||
|
//! Core changes:
|
||||||
|
//!
|
||||||
|
//! - Renamed `a64::Vec::ElementType` to `a64::VecElementType` and made it a typed enum. This enum was used mostly
|
||||||
|
//! internally, but there is a public API using it, so it's a breaking change.
|
||||||
|
//!
|
||||||
//! ### Changes committed at 2023-12-26
|
//! ### Changes committed at 2023-12-26
|
||||||
//!
|
//!
|
||||||
//! Core changes:
|
//! Core changes:
|
||||||
@@ -1045,7 +1052,7 @@ namespace asmjit {
|
|||||||
//!
|
//!
|
||||||
//! // Type-unsafe, but possible.
|
//! // Type-unsafe, but possible.
|
||||||
//! a.emit(x86::Inst::kIdMov, dst, m);
|
//! a.emit(x86::Inst::kIdMov, dst, m);
|
||||||
//! // Also possible, `emit()` is typeless and can be used with raw Operand.
|
//! // Also possible, `emit()` is type-less and can be used with raw Operand.
|
||||||
//! a.emit(x86::Inst::kIdMov, dst, op);
|
//! a.emit(x86::Inst::kIdMov, dst, op);
|
||||||
//! }
|
//! }
|
||||||
//! ```
|
//! ```
|
||||||
@@ -1139,7 +1146,7 @@ namespace asmjit {
|
|||||||
//! mem.size(); // 4.
|
//! mem.size(); // 4.
|
||||||
//! mem.offset(); // 12.
|
//! mem.offset(); // 12.
|
||||||
//!
|
//!
|
||||||
//! mem.setSize(0); // Sets the size to 0 (makes it sizeless).
|
//! mem.setSize(0); // Sets the size to 0 (makes it size-less).
|
||||||
//! mem.addOffset(-1); // Adds -1 to the offset and makes it 11.
|
//! mem.addOffset(-1); // Adds -1 to the offset and makes it 11.
|
||||||
//! mem.setOffset(0); // Sets the offset to 0.
|
//! mem.setOffset(0); // Sets the offset to 0.
|
||||||
//! mem.setBase(rcx); // Changes BASE to RCX.
|
//! mem.setBase(rcx); // Changes BASE to RCX.
|
||||||
|
|||||||
Reference in New Issue
Block a user