aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/llvm/CodeGen/ValueTypes.h150
-rw-r--r--lib/VMCore/ValueTypes.cpp54
-rw-r--r--test/CodeGen/X86/i2k.ll9
-rw-r--r--utils/TableGen/CMakeLists.txt1
-rw-r--r--utils/TableGen/TGValueTypes.cpp123
5 files changed, 255 insertions, 82 deletions
diff --git a/include/llvm/CodeGen/ValueTypes.h b/include/llvm/CodeGen/ValueTypes.h
index 561616b..a6fa57d 100644
--- a/include/llvm/CodeGen/ValueTypes.h
+++ b/include/llvm/CodeGen/ValueTypes.h
@@ -26,7 +26,6 @@ namespace llvm {
struct MVT { // MVT = Machine Value Type
public:
-
enum SimpleValueType {
// If you change this numbering, you must change the values in
// ValueTypes.td as well!
@@ -87,10 +86,14 @@ namespace llvm {
// iPTR - An int value the size of the pointer of the current
// target. This should only be used internal to tblgen!
- iPTR = 255
+ iPTR = 255,
+
+ // LastSimpleValueType - The greatest valid SimpleValueType value.
+ LastSimpleValueType = 255
};
- /// MVT - This type holds low-level value types. Valid values include any of
+ private:
+ /// This union holds low-level value types. Valid values include any of
/// the values in the SimpleValueType enum, or any value returned from one
/// of the MVT methods. Any value type equal to one of the SimpleValueType
/// enum values is a "simple" value type. All others are "extended".
@@ -99,48 +102,22 @@ namespace llvm {
/// All legal value types must be simple, but often there are some simple
/// value types that are not legal.
///
- /// @internal
- /// Extended types are either vector types or arbitrary precision integers.
- /// Arbitrary precision integers have iAny in the first SimpleTypeBits bits,
- /// and the bit-width in the next PrecisionBits bits, offset by minus one.
- /// Vector types are encoded by having the first
- /// SimpleTypeBits+PrecisionBits bits encode the vector element type
- /// (which must be a scalar type, possibly an arbitrary precision integer)
- /// and the remaining VectorBits upper bits encode the vector length, offset
- /// by one.
- ///
- /// 32--------------16-----------8-------------0
- /// | Vector length | Precision | Simple type |
- /// | | Vector element |
- ///
-
- private:
-
- static const int SimpleTypeBits = 8;
- static const int PrecisionBits = 8;
- static const int VectorBits = 32 - SimpleTypeBits - PrecisionBits;
-
- static const uint32_t SimpleTypeMask =
- (~uint32_t(0) << (32 - SimpleTypeBits)) >> (32 - SimpleTypeBits);
-
- static const uint32_t PrecisionMask =
- ((~uint32_t(0) << VectorBits) >> (32 - PrecisionBits)) << SimpleTypeBits;
-
- static const uint32_t VectorMask =
- (~uint32_t(0) >> (32 - VectorBits)) << (32 - VectorBits);
-
- static const uint32_t ElementMask =
- (~uint32_t(0) << VectorBits) >> VectorBits;
-
- uint32_t V;
+ union {
+ uintptr_t V;
+ SimpleValueType SimpleTy;
+ const Type *LLVMTy;
+ };
public:
-
MVT() {}
MVT(SimpleValueType S) : V(S) {}
- bool operator== (const MVT VT) const { return V == VT.V; }
- bool operator!= (const MVT VT) const { return V != VT.V; }
+ bool operator==(const MVT VT) const {
+ return getRawBits() == VT.getRawBits();
+ }
+ bool operator!=(const MVT VT) const {
+ return getRawBits() != VT.getRawBits();
+ }
/// getFloatingPointVT - Returns the MVT that represents a floating point
/// type with the given number of bits. There are two floating point types
@@ -179,10 +156,7 @@ namespace llvm {
case 128:
return i128;
}
- MVT VT;
- VT.V = iAny | (((BitWidth - 1) << SimpleTypeBits) & PrecisionMask);
- assert(VT.getSizeInBits() == BitWidth && "Bad bit width!");
- return VT;
+ return getExtendedIntegerVT(BitWidth);
}
/// getVectorVT - Returns the MVT that represents a vector NumElements in
@@ -217,13 +191,7 @@ namespace llvm {
if (NumElements == 2) return v2f64;
break;
}
- MVT Result;
- Result.V = VT.V | ((NumElements + 1) << (32 - VectorBits));
- assert(Result.getVectorElementType() == VT &&
- "Bad vector element type!");
- assert(Result.getVectorNumElements() == NumElements &&
- "Bad vector length!");
- return Result;
+ return getExtendedVectorVT(VT, NumElements);
}
/// getIntVectorWithNumElements - Return any integer vector type that has
@@ -240,11 +208,10 @@ namespace llvm {
}
}
-
/// isSimple - Test if the given MVT is simple (as opposed to being
/// extended).
bool isSimple() const {
- return V <= SimpleTypeMask;
+ return V <= LastSimpleValueType;
}
/// isExtended - Test if the given MVT is extended (as opposed to
@@ -255,34 +222,43 @@ namespace llvm {
/// isFloatingPoint - Return true if this is a FP, or a vector FP type.
bool isFloatingPoint() const {
- uint32_t SVT = V & SimpleTypeMask;
- return (SVT >= f32 && SVT <= ppcf128) || (SVT >= v2f32 && SVT <= v2f64);
+ return isSimple() ?
+ ((SimpleTy >= f32 && SimpleTy <= ppcf128) ||
+ (SimpleTy >= v2f32 && SimpleTy <= v2f64)) :
+ isExtendedFloatingPoint();
}
/// isInteger - Return true if this is an integer, or a vector integer type.
bool isInteger() const {
- uint32_t SVT = V & SimpleTypeMask;
- return (SVT >= FIRST_INTEGER_VALUETYPE && SVT <= LAST_INTEGER_VALUETYPE) ||
- (SVT >= v8i8 && SVT <= v2i64) || (SVT == iAny && (V & PrecisionMask));
+ return isSimple() ?
+ ((SimpleTy >= FIRST_INTEGER_VALUETYPE &&
+ SimpleTy <= LAST_INTEGER_VALUETYPE) ||
+ (SimpleTy >= v8i8 && SimpleTy <= v2i64)) :
+ isExtendedInteger();
}
/// isVector - Return true if this is a vector value type.
bool isVector() const {
- return (V >= FIRST_VECTOR_VALUETYPE && V <= LAST_VECTOR_VALUETYPE) ||
- (V & VectorMask);
+ return isSimple() ?
+ (SimpleTy >= FIRST_VECTOR_VALUETYPE &&
+ SimpleTy <= LAST_VECTOR_VALUETYPE) :
+ isExtendedVector();
}
/// is64BitVector - Return true if this is a 64-bit vector type.
bool is64BitVector() const {
- return (V==v8i8 || V==v4i16 || V==v2i32 || V==v1i64 || V==v2f32 ||
- (isExtended() && isVector() && getSizeInBits()==64));
+ return isSimple() ?
+ (SimpleTy==v8i8 || SimpleTy==v4i16 || SimpleTy==v2i32 ||
+ SimpleTy==v1i64 || SimpleTy==v2f32) :
+ isExtended64BitVector();
}
/// is128BitVector - Return true if this is a 128-bit vector type.
bool is128BitVector() const {
- return (V==v16i8 || V==v8i16 || V==v4i32 || V==v2i64 ||
- V==v4f32 || V==v2f64 ||
- (isExtended() && isVector() && getSizeInBits()==128));
+ return isSimple() ?
+ (SimpleTy==v16i8 || SimpleTy==v8i16 || SimpleTy==v4i32 ||
+ SimpleTy==v2i64 || SimpleTy==v4f32 || SimpleTy==v2f64) :
+ isExtended128BitVector();
}
/// isByteSized - Return true if the bit size is a multiple of 8.
@@ -321,7 +297,7 @@ namespace llvm {
/// simple MVT.
SimpleValueType getSimpleVT() const {
assert(isSimple() && "Expected a SimpleValueType!");
- return (SimpleValueType)V;
+ return SimpleTy;
}
/// getVectorElementType - Given a vector type, return the type of
@@ -329,12 +305,8 @@ namespace llvm {
MVT getVectorElementType() const {
assert(isVector() && "Invalid vector type!");
switch (V) {
- default: {
- assert(isExtended() && "Unknown simple vector type!");
- MVT VT;
- VT.V = V & ElementMask;
- return VT;
- }
+ default:
+ return getExtendedVectorElementType();
case v8i8 :
case v16i8: return i8;
case v4i16:
@@ -357,8 +329,7 @@ namespace llvm {
assert(isVector() && "Invalid vector type!");
switch (V) {
default:
- assert(isExtended() && "Unknown simple vector type!");
- return ((V & VectorMask) >> (32 - VectorBits)) - 1;
+ return getExtendedVectorNumElements();
case v16i8: return 16;
case v8i8 :
case v8i16: return 8;
@@ -379,13 +350,7 @@ namespace llvm {
unsigned getSizeInBits() const {
switch (V) {
default:
- assert(isExtended() && "MVT has no known size!");
- if (isVector())
- return getVectorElementType().getSizeInBits()*getVectorNumElements();
- if (isInteger())
- return ((V & PrecisionMask) >> SimpleTypeBits) + 1;
- assert(false && "Unknown value type!");
- return 0;
+ return getExtendedSizeInBits();
case i1 : return 1;
case i8 : return 8;
case i16 : return 16;
@@ -410,6 +375,12 @@ namespace llvm {
case v2i64:
case v4f32:
case v2f64: return 128;
+ case iPTR:
+ assert(false && "Value type size is target-dependent. Ask TLI.");
+ case iPTRAny:
+ case iAny:
+ case fAny:
+ assert(false && "Value type is overloaded.");
}
}
@@ -461,7 +432,7 @@ namespace llvm {
static MVT getMVT(const Type *Ty, bool HandleUnknown = false);
/// getRawBits - Represent the type as a bunch of bits.
- uint32_t getRawBits() const { return V; }
+ uintptr_t getRawBits() const { return V; }
/// compareRawBits - A meaningless but well-behaved order, useful for
/// constructing containers.
@@ -470,6 +441,21 @@ namespace llvm {
return L.getRawBits() < R.getRawBits();
}
};
+
+ private:
+ // Methods for handling the Extended-type case in functions above.
+ // These are all out-of-line to prevent users of this header file
+ // from having a dependency on Type.h.
+ static MVT getExtendedIntegerVT(unsigned BitWidth);
+ static MVT getExtendedVectorVT(MVT VT, unsigned NumElements);
+ bool isExtendedFloatingPoint() const;
+ bool isExtendedInteger() const;
+ bool isExtendedVector() const;
+ bool isExtended64BitVector() const;
+ bool isExtended128BitVector() const;
+ MVT getExtendedVectorElementType() const;
+ unsigned getExtendedVectorNumElements() const;
+ unsigned getExtendedSizeInBits() const;
};
} // End llvm namespace
diff --git a/lib/VMCore/ValueTypes.cpp b/lib/VMCore/ValueTypes.cpp
index ca23284..99dc1de 100644
--- a/lib/VMCore/ValueTypes.cpp
+++ b/lib/VMCore/ValueTypes.cpp
@@ -17,6 +17,60 @@
#include "llvm/DerivedTypes.h"
using namespace llvm;
+MVT MVT::getExtendedIntegerVT(unsigned BitWidth) {
+ MVT VT;
+ VT.LLVMTy = IntegerType::get(BitWidth);
+ return VT;
+}
+
+MVT MVT::getExtendedVectorVT(MVT VT, unsigned NumElements) {
+ MVT ResultVT;
+ ResultVT.LLVMTy = VectorType::get(VT.getTypeForMVT(), NumElements);
+ return ResultVT;
+}
+
+bool MVT::isExtendedFloatingPoint() const {
+ assert(isExtended() && "Type is not extended!");
+ return LLVMTy->isFPOrFPVector();
+}
+
+bool MVT::isExtendedInteger() const {
+ assert(isExtended() && "Type is not extended!");
+ return LLVMTy->isIntOrIntVector();
+}
+
+bool MVT::isExtendedVector() const {
+ assert(isExtended() && "Type is not extended!");
+ return isa<VectorType>(LLVMTy);
+}
+
+bool MVT::isExtended64BitVector() const {
+ return isExtendedVector() && getSizeInBits() == 64;
+}
+
+bool MVT::isExtended128BitVector() const {
+ return isExtendedVector() && getSizeInBits() == 128;
+}
+
+MVT MVT::getExtendedVectorElementType() const {
+ assert(isExtended() && "Type is not extended!");
+ return MVT::getMVT(cast<VectorType>(LLVMTy)->getElementType());
+}
+
+unsigned MVT::getExtendedVectorNumElements() const {
+ assert(isExtended() && "Type is not extended!");
+ return cast<VectorType>(LLVMTy)->getNumElements();
+}
+
+unsigned MVT::getExtendedSizeInBits() const {
+ assert(isExtended() && "Type is not extended!");
+ if (const IntegerType *ITy = dyn_cast<IntegerType>(LLVMTy))
+ return ITy->getBitWidth();
+ if (const VectorType *VTy = dyn_cast<VectorType>(LLVMTy))
+ return VTy->getBitWidth();
+ assert(false && "Unrecognized extended type!");
+}
+
/// getMVTString - This function returns value type as a string, e.g. "i32".
std::string MVT::getMVTString() const {
switch (V) {
diff --git a/test/CodeGen/X86/i2k.ll b/test/CodeGen/X86/i2k.ll
new file mode 100644
index 0000000..712302d
--- /dev/null
+++ b/test/CodeGen/X86/i2k.ll
@@ -0,0 +1,9 @@
+; RUN: llvm-as < %s | llc -march=x86
+
+define void @foo(i2011* %x, i2011* %y, i2011* %p) nounwind {
+ %a = load i2011* %x
+ %b = load i2011* %y
+ %c = add i2011 %a, %b
+ store i2011 %c, i2011* %p
+ ret void
+}
diff --git a/utils/TableGen/CMakeLists.txt b/utils/TableGen/CMakeLists.txt
index 8141d76..8e6a3e1 100644
--- a/utils/TableGen/CMakeLists.txt
+++ b/utils/TableGen/CMakeLists.txt
@@ -15,6 +15,7 @@ add_executable(tblgen
SubtargetEmitter.cpp
TGLexer.cpp
TGParser.cpp
+ TGValueTypes.cpp
TableGen.cpp
TableGenBackend.cpp
FastISelEmitter.cpp
diff --git a/utils/TableGen/TGValueTypes.cpp b/utils/TableGen/TGValueTypes.cpp
new file mode 100644
index 0000000..209e7c9
--- /dev/null
+++ b/utils/TableGen/TGValueTypes.cpp
@@ -0,0 +1,123 @@
+//===- ValueTypes.cpp - Tablegen extended ValueType implementation --------===//
+//
+// The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// The MVT type is used by tablegen as well as in LLVM. In order to handle
+// extended types, the MVT type uses support functions that call into
+// LLVM's type system code. These aren't accessible in tablegen, so this
+// file provides simple replacements.
+//
+//===----------------------------------------------------------------------===//
+
+#include "llvm/CodeGen/ValueTypes.h"
+#include "llvm/Support/Streams.h"
+#include <map>
+#include <vector>
+using namespace llvm;
+
+namespace llvm {
+
+class Type {
+public:
+ virtual unsigned getSizeInBits() const = 0;
+};
+
+}
+
+class ExtendedIntegerType : public Type {
+ unsigned BitWidth;
+public:
+ explicit ExtendedIntegerType(unsigned bits)
+ : BitWidth(bits) {}
+ unsigned getSizeInBits() const {
+ return getBitWidth();
+ }
+ unsigned getBitWidth() const {
+ return BitWidth;
+ }
+};
+
+class ExtendedVectorType : public Type {
+ MVT ElementType;
+ unsigned NumElements;
+public:
+ ExtendedVectorType(MVT elty, unsigned num)
+ : ElementType(elty), NumElements(num) {}
+ unsigned getSizeInBits() const {
+ return getNumElements() * getElementType().getSizeInBits();
+ }
+ MVT getElementType() const {
+ return ElementType;
+ }
+ unsigned getNumElements() const {
+ return NumElements;
+ }
+};
+
+static std::map<unsigned, const Type *>
+ ExtendedIntegerTypeMap;
+static std::map<std::pair<uintptr_t, uintptr_t>, const Type *>
+ ExtendedVectorTypeMap;
+
+MVT MVT::getExtendedIntegerVT(unsigned BitWidth) {
+ const Type *&ET = ExtendedIntegerTypeMap[BitWidth];
+ if (!ET) ET = new ExtendedIntegerType(BitWidth);
+ MVT VT;
+ VT.LLVMTy = ET;
+ return VT;
+}
+
+MVT MVT::getExtendedVectorVT(MVT VT, unsigned NumElements) {
+ const Type *&ET = ExtendedVectorTypeMap[std::make_pair(VT.getRawBits(),
+ NumElements)];
+ if (!ET) ET = new ExtendedVectorType(VT, NumElements);
+ MVT ResultVT;
+ ResultVT.LLVMTy = ET;
+ return ResultVT;
+}
+
+bool MVT::isExtendedFloatingPoint() const {
+ assert(isExtended() && "Type is not extended!");
+ // Extended floating-point types are not supported yet.
+ return false;
+}
+
+bool MVT::isExtendedInteger() const {
+ assert(isExtended() && "Type is not extended!");
+ return dynamic_cast<const ExtendedIntegerType *>(LLVMTy) != 0;
+}
+
+bool MVT::isExtendedVector() const {
+ assert(isExtended() && "Type is not extended!");
+ return dynamic_cast<const ExtendedVectorType *>(LLVMTy) != 0;
+}
+
+bool MVT::isExtended64BitVector() const {
+ assert(isExtended() && "Type is not extended!");
+ return isExtendedVector() && getSizeInBits() == 64;
+}
+
+bool MVT::isExtended128BitVector() const {
+ assert(isExtended() && "Type is not extended!");
+ return isExtendedVector() && getSizeInBits() == 128;
+}
+
+MVT MVT::getExtendedVectorElementType() const {
+ assert(isExtendedVector() && "Type is not an extended vector!");
+ return static_cast<const ExtendedVectorType *>(LLVMTy)->getElementType();
+}
+
+unsigned MVT::getExtendedVectorNumElements() const {
+ assert(isExtendedVector() && "Type is not an extended vector!");
+ return static_cast<const ExtendedVectorType *>(LLVMTy)->getNumElements();
+}
+
+unsigned MVT::getExtendedSizeInBits() const {
+ assert(isExtended() && "Type is not extended!");
+ return LLVMTy->getSizeInBits();
+}