mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2025-05-13 01:15:32 +00:00
Add a new overloaded EVT::vAny type for use in TableGen to allow intrinsic
arguments that are vectors of any size and element type. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@78631 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
1c5cf1b378
commit
61fc4cf7aa
@ -83,26 +83,31 @@ namespace llvm {
|
|||||||
MAX_ALLOWED_VALUETYPE = 64,
|
MAX_ALLOWED_VALUETYPE = 64,
|
||||||
|
|
||||||
// Metadata - This is MDNode or MDString.
|
// Metadata - This is MDNode or MDString.
|
||||||
Metadata = 251,
|
Metadata = 250,
|
||||||
|
|
||||||
// iPTRAny - An int value the size of the pointer of the current
|
// iPTRAny - An int value the size of the pointer of the current
|
||||||
// target to any address space. This must only be used internal to
|
// target to any address space. This must only be used internal to
|
||||||
// tblgen. Other than for overloading, we treat iPTRAny the same as iPTR.
|
// tblgen. Other than for overloading, we treat iPTRAny the same as iPTR.
|
||||||
iPTRAny = 252,
|
iPTRAny = 251,
|
||||||
|
|
||||||
|
// vAny - A vector with any length and element size. This is used
|
||||||
|
// for intrinsics that have overloadings based on vector types.
|
||||||
|
// This is only for tblgen's consumption!
|
||||||
|
vAny = 252,
|
||||||
|
|
||||||
// fAny - Any floating-point or vector floating-point value. This is used
|
// fAny - Any floating-point or vector floating-point value. This is used
|
||||||
// for intrinsics that have overloadings based on floating-point types.
|
// for intrinsics that have overloadings based on floating-point types.
|
||||||
// This is only for tblgen's consumption!
|
// This is only for tblgen's consumption!
|
||||||
fAny = 253,
|
fAny = 253,
|
||||||
|
|
||||||
// iAny - An integer or vector integer value of any bit width. This is
|
// iAny - An integer or vector integer value of any bit width. This is
|
||||||
// used for intrinsics that have overloadings based on integer bit widths.
|
// used for intrinsics that have overloadings based on integer bit widths.
|
||||||
// This is only for tblgen's consumption!
|
// This is only for tblgen's consumption!
|
||||||
iAny = 254,
|
iAny = 254,
|
||||||
|
|
||||||
// iPTR - An int value the size of the pointer of the current
|
// iPTR - An int value the size of the pointer of the current
|
||||||
// target. This should only be used internal to tblgen!
|
// target. This should only be used internal to tblgen!
|
||||||
iPTR = 255,
|
iPTR = 255,
|
||||||
|
|
||||||
// LastSimpleValueType - The greatest valid SimpleValueType value.
|
// LastSimpleValueType - The greatest valid SimpleValueType value.
|
||||||
LastSimpleValueType = 255
|
LastSimpleValueType = 255
|
||||||
@ -284,6 +289,11 @@ namespace llvm {
|
|||||||
V==v4i64) : isExtended256BitVector();
|
V==v4i64) : isExtended256BitVector();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// isOverloaded - Return true if this is an overloaded type for TableGen.
|
||||||
|
bool isOverloaded() const {
|
||||||
|
return (V==iAny || V==fAny || V==vAny || V==iPTRAny);
|
||||||
|
}
|
||||||
|
|
||||||
/// isByteSized - Return true if the bit size is a multiple of 8.
|
/// isByteSized - Return true if the bit size is a multiple of 8.
|
||||||
bool isByteSized() const {
|
bool isByteSized() const {
|
||||||
return (getSizeInBits() & 7) == 0;
|
return (getSizeInBits() & 7) == 0;
|
||||||
@ -396,6 +406,7 @@ namespace llvm {
|
|||||||
case iPTRAny:
|
case iPTRAny:
|
||||||
case iAny:
|
case iAny:
|
||||||
case fAny:
|
case fAny:
|
||||||
|
case vAny:
|
||||||
assert(0 && "Value type is overloaded.");
|
assert(0 && "Value type is overloaded.");
|
||||||
default:
|
default:
|
||||||
return getExtendedSizeInBits();
|
return getExtendedSizeInBits();
|
||||||
|
@ -56,11 +56,14 @@ def v8f32 : ValueType<256, 31>; // 8 x f32 vector value
|
|||||||
def v2f64 : ValueType<128, 32>; // 2 x f64 vector value
|
def v2f64 : ValueType<128, 32>; // 2 x f64 vector value
|
||||||
def v4f64 : ValueType<256, 33>; // 4 x f64 vector value
|
def v4f64 : ValueType<256, 33>; // 4 x f64 vector value
|
||||||
|
|
||||||
def MetadataVT: ValueType<0, 251>; // Metadata
|
def MetadataVT: ValueType<0, 250>; // Metadata
|
||||||
|
|
||||||
// Pseudo valuetype mapped to the current pointer size to any address space.
|
// Pseudo valuetype mapped to the current pointer size to any address space.
|
||||||
// Should only be used in TableGen.
|
// Should only be used in TableGen.
|
||||||
def iPTRAny : ValueType<0, 252>;
|
def iPTRAny : ValueType<0, 251>;
|
||||||
|
|
||||||
|
// Pseudo valuetype to represent "vector of any size"
|
||||||
|
def vAny : ValueType<0 , 252>;
|
||||||
|
|
||||||
// Pseudo valuetype to represent "float of any format"
|
// Pseudo valuetype to represent "float of any format"
|
||||||
def fAny : ValueType<0 , 253>;
|
def fAny : ValueType<0 , 253>;
|
||||||
|
@ -63,7 +63,7 @@ namespace Intrinsic {
|
|||||||
/// declaration for an intrinsic, and return it.
|
/// declaration for an intrinsic, and return it.
|
||||||
///
|
///
|
||||||
/// The Tys and numTys parameters are for intrinsics with overloaded types
|
/// The Tys and numTys parameters are for intrinsics with overloaded types
|
||||||
/// (i.e., those using iAny or fAny). For a declaration for an overloaded
|
/// (e.g., those using iAny or fAny). For a declaration for an overloaded
|
||||||
/// intrinsic, Tys should point to an array of numTys pointers to Type,
|
/// intrinsic, Tys should point to an array of numTys pointers to Type,
|
||||||
/// and must provide exactly one type for each overloaded type in the
|
/// and must provide exactly one type for each overloaded type in the
|
||||||
/// intrinsic.
|
/// intrinsic.
|
||||||
|
@ -94,6 +94,7 @@ class LLVMTruncatedElementVectorType<int num> : LLVMMatchType<num>;
|
|||||||
def llvm_void_ty : LLVMType<isVoid>;
|
def llvm_void_ty : LLVMType<isVoid>;
|
||||||
def llvm_anyint_ty : LLVMType<iAny>;
|
def llvm_anyint_ty : LLVMType<iAny>;
|
||||||
def llvm_anyfloat_ty : LLVMType<fAny>;
|
def llvm_anyfloat_ty : LLVMType<fAny>;
|
||||||
|
def llvm_anyvector_ty : LLVMType<vAny>;
|
||||||
def llvm_i1_ty : LLVMType<i1>;
|
def llvm_i1_ty : LLVMType<i1>;
|
||||||
def llvm_i8_ty : LLVMType<i8>;
|
def llvm_i8_ty : LLVMType<i8>;
|
||||||
def llvm_i16_ty : LLVMType<i16>;
|
def llvm_i16_ty : LLVMType<i16>;
|
||||||
|
@ -1597,6 +1597,12 @@ bool Verifier::PerformTypeCheck(Intrinsic::ID ID, Function *F, const Type *Ty,
|
|||||||
Suffix += "v" + utostr(NumElts);
|
Suffix += "v" + utostr(NumElts);
|
||||||
|
|
||||||
Suffix += EVT::getEVT(EltTy).getEVTString();
|
Suffix += EVT::getEVT(EltTy).getEVTString();
|
||||||
|
} else if (VT == EVT::vAny) {
|
||||||
|
if (!VTy) {
|
||||||
|
CheckFailed(IntrinsicParam(ArgNo, NumRets) + " is not a vector type.", F);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
Suffix += ".v" + utostr(NumElts) + EVT::getEVT(EltTy).getEVTString();
|
||||||
} else if (VT == EVT::iPTR) {
|
} else if (VT == EVT::iPTR) {
|
||||||
if (!isa<PointerType>(Ty)) {
|
if (!isa<PointerType>(Ty)) {
|
||||||
CheckFailed(IntrinsicParam(ArgNo, NumRets) + " is not a "
|
CheckFailed(IntrinsicParam(ArgNo, NumRets) + " is not a "
|
||||||
|
@ -87,9 +87,16 @@ bool isExtIntegerInVTs(const std::vector<unsigned char> &EVTs) {
|
|||||||
/// isExtFloatingPointInVTs - Return true if the specified extended value type
|
/// isExtFloatingPointInVTs - Return true if the specified extended value type
|
||||||
/// vector contains isFP or a FP value type.
|
/// vector contains isFP or a FP value type.
|
||||||
bool isExtFloatingPointInVTs(const std::vector<unsigned char> &EVTs) {
|
bool isExtFloatingPointInVTs(const std::vector<unsigned char> &EVTs) {
|
||||||
assert(!EVTs.empty() && "Cannot check for integer in empty ExtVT list!");
|
assert(!EVTs.empty() && "Cannot check for FP in empty ExtVT list!");
|
||||||
return EVTs[0] == isFP || !(FilterEVTs(EVTs, isFloatingPoint).empty());
|
return EVTs[0] == isFP || !(FilterEVTs(EVTs, isFloatingPoint).empty());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// isExtVectorInVTs - Return true if the specified extended value type
|
||||||
|
/// vector contains a vector value type.
|
||||||
|
bool isExtVectorInVTs(const std::vector<unsigned char> &EVTs) {
|
||||||
|
assert(!EVTs.empty() && "Cannot check for vector in empty ExtVT list!");
|
||||||
|
return !(FilterEVTs(EVTs, isVector).empty());
|
||||||
|
}
|
||||||
} // end namespace EEVT.
|
} // end namespace EEVT.
|
||||||
} // end namespace llvm.
|
} // end namespace llvm.
|
||||||
|
|
||||||
@ -495,6 +502,14 @@ bool TreePatternNode::UpdateNodeType(const std::vector<unsigned char> &ExtVTs,
|
|||||||
setTypes(FVTs);
|
setTypes(FVTs);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
if (ExtVTs[0] == EVT::vAny && EEVT::isExtVectorInVTs(getExtTypes())) {
|
||||||
|
assert(hasTypeSet() && "should be handled above!");
|
||||||
|
std::vector<unsigned char> FVTs = FilterEVTs(getExtTypes(), isVector);
|
||||||
|
if (getExtTypes() == FVTs)
|
||||||
|
return false;
|
||||||
|
setTypes(FVTs);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
// If we know this is an int or fp type, and we are told it is a specific one,
|
// If we know this is an int or fp type, and we are told it is a specific one,
|
||||||
// take the advice.
|
// take the advice.
|
||||||
@ -504,7 +519,9 @@ bool TreePatternNode::UpdateNodeType(const std::vector<unsigned char> &ExtVTs,
|
|||||||
if (((getExtTypeNum(0) == EEVT::isInt || getExtTypeNum(0) == EVT::iAny) &&
|
if (((getExtTypeNum(0) == EEVT::isInt || getExtTypeNum(0) == EVT::iAny) &&
|
||||||
EEVT::isExtIntegerInVTs(ExtVTs)) ||
|
EEVT::isExtIntegerInVTs(ExtVTs)) ||
|
||||||
((getExtTypeNum(0) == EEVT::isFP || getExtTypeNum(0) == EVT::fAny) &&
|
((getExtTypeNum(0) == EEVT::isFP || getExtTypeNum(0) == EVT::fAny) &&
|
||||||
EEVT::isExtFloatingPointInVTs(ExtVTs))) {
|
EEVT::isExtFloatingPointInVTs(ExtVTs)) ||
|
||||||
|
(getExtTypeNum(0) == EVT::vAny &&
|
||||||
|
EEVT::isExtVectorInVTs(ExtVTs))) {
|
||||||
setTypes(ExtVTs);
|
setTypes(ExtVTs);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -56,6 +56,7 @@ std::string llvm::getEnumName(EVT::SimpleValueType T) {
|
|||||||
case EVT::i128: return "EVT::i128";
|
case EVT::i128: return "EVT::i128";
|
||||||
case EVT::iAny: return "EVT::iAny";
|
case EVT::iAny: return "EVT::iAny";
|
||||||
case EVT::fAny: return "EVT::fAny";
|
case EVT::fAny: return "EVT::fAny";
|
||||||
|
case EVT::vAny: return "EVT::vAny";
|
||||||
case EVT::f32: return "EVT::f32";
|
case EVT::f32: return "EVT::f32";
|
||||||
case EVT::f64: return "EVT::f64";
|
case EVT::f64: return "EVT::f64";
|
||||||
case EVT::f80: return "EVT::f80";
|
case EVT::f80: return "EVT::f80";
|
||||||
@ -496,7 +497,7 @@ CodeGenIntrinsic::CodeGenIntrinsic(Record *R) {
|
|||||||
} else {
|
} else {
|
||||||
VT = getValueType(TyEl->getValueAsDef("VT"));
|
VT = getValueType(TyEl->getValueAsDef("VT"));
|
||||||
}
|
}
|
||||||
if (VT == EVT::iAny || VT == EVT::fAny || VT == EVT::iPTRAny) {
|
if (EVT(VT).isOverloaded()) {
|
||||||
OverloadedVTs.push_back(VT);
|
OverloadedVTs.push_back(VT);
|
||||||
isOverloaded |= true;
|
isOverloaded |= true;
|
||||||
}
|
}
|
||||||
@ -526,7 +527,7 @@ CodeGenIntrinsic::CodeGenIntrinsic(Record *R) {
|
|||||||
VT == EVT::iAny) && "Expected iAny type");
|
VT == EVT::iAny) && "Expected iAny type");
|
||||||
} else
|
} else
|
||||||
VT = getValueType(TyEl->getValueAsDef("VT"));
|
VT = getValueType(TyEl->getValueAsDef("VT"));
|
||||||
if (VT == EVT::iAny || VT == EVT::fAny || VT == EVT::iPTRAny) {
|
if (EVT(VT).isOverloaded()) {
|
||||||
OverloadedVTs.push_back(VT);
|
OverloadedVTs.push_back(VT);
|
||||||
isOverloaded |= true;
|
isOverloaded |= true;
|
||||||
}
|
}
|
||||||
|
@ -203,7 +203,7 @@ static void EmitTypeGenerate(raw_ostream &OS, const Record *ArgType,
|
|||||||
<< "(dyn_cast<VectorType>(Tys[" << Number << "]))";
|
<< "(dyn_cast<VectorType>(Tys[" << Number << "]))";
|
||||||
else
|
else
|
||||||
OS << "Tys[" << Number << "]";
|
OS << "Tys[" << Number << "]";
|
||||||
} else if (VT == EVT::iAny || VT == EVT::fAny) {
|
} else if (VT == EVT::iAny || VT == EVT::fAny || VT == EVT::vAny) {
|
||||||
// NOTE: The ArgNo variable here is not the absolute argument number, it is
|
// NOTE: The ArgNo variable here is not the absolute argument number, it is
|
||||||
// the index of the "arbitrary" type in the Tys array passed to the
|
// the index of the "arbitrary" type in the Tys array passed to the
|
||||||
// Intrinsic::getDeclaration function. Consequently, we only want to
|
// Intrinsic::getDeclaration function. Consequently, we only want to
|
||||||
@ -329,7 +329,7 @@ void IntrinsicEmitter::EmitVerifier(const std::vector<CodeGenIntrinsic> &Ints,
|
|||||||
EVT::SimpleValueType VT = getValueType(ArgType->getValueAsDef("VT"));
|
EVT::SimpleValueType VT = getValueType(ArgType->getValueAsDef("VT"));
|
||||||
OS << getEnumName(VT);
|
OS << getEnumName(VT);
|
||||||
|
|
||||||
if (VT == EVT::iAny || VT == EVT::fAny || VT == EVT::iPTRAny)
|
if (EVT(VT).isOverloaded())
|
||||||
OverloadedTypeIndices.push_back(j);
|
OverloadedTypeIndices.push_back(j);
|
||||||
|
|
||||||
if (VT == EVT::isVoid && j != 0 && j != je - 1)
|
if (VT == EVT::isVoid && j != 0 && j != je - 1)
|
||||||
@ -357,7 +357,7 @@ void IntrinsicEmitter::EmitVerifier(const std::vector<CodeGenIntrinsic> &Ints,
|
|||||||
EVT::SimpleValueType VT = getValueType(ArgType->getValueAsDef("VT"));
|
EVT::SimpleValueType VT = getValueType(ArgType->getValueAsDef("VT"));
|
||||||
OS << getEnumName(VT);
|
OS << getEnumName(VT);
|
||||||
|
|
||||||
if (VT == EVT::iAny || VT == EVT::fAny || VT == EVT::iPTRAny)
|
if (EVT(VT).isOverloaded())
|
||||||
OverloadedTypeIndices.push_back(j + RetTys.size());
|
OverloadedTypeIndices.push_back(j + RetTys.size());
|
||||||
|
|
||||||
if (VT == EVT::isVoid && j != 0 && j != je - 1)
|
if (VT == EVT::isVoid && j != 0 && j != je - 1)
|
||||||
|
Loading…
x
Reference in New Issue
Block a user