aboutsummaryrefslogtreecommitdiff
path: root/include/llvm/TableGen
diff options
context:
space:
mode:
authorDimitry Andric <dim@FreeBSD.org>2016-07-23 20:41:05 +0000
committerDimitry Andric <dim@FreeBSD.org>2016-07-23 20:41:05 +0000
commit01095a5d43bbfde13731688ddcf6048ebb8b7721 (patch)
tree4def12e759965de927d963ac65840d663ef9d1ea /include/llvm/TableGen
parentf0f4822ed4b66e3579e92a89f368f8fb860e218e (diff)
Vendor import of llvm release_39 branch r276489:vendor/llvm/llvm-release_39-r276489
Diffstat (limited to 'include/llvm/TableGen')
-rw-r--r--include/llvm/TableGen/Record.h319
-rw-r--r--include/llvm/TableGen/SearchableTable.td41
-rw-r--r--include/llvm/TableGen/StringToOffsetTable.h20
3 files changed, 260 insertions, 120 deletions
diff --git a/include/llvm/TableGen/Record.h b/include/llvm/TableGen/Record.h
index 4c1ef4013dda..393cafa7924a 100644
--- a/include/llvm/TableGen/Record.h
+++ b/include/llvm/TableGen/Record.h
@@ -22,6 +22,7 @@
#include "llvm/Support/DataTypes.h"
#include "llvm/Support/ErrorHandling.h"
#include "llvm/Support/SMLoc.h"
+#include "llvm/Support/TrailingObjects.h"
#include "llvm/Support/raw_ostream.h"
#include <map>
@@ -43,6 +44,7 @@ public:
enum RecTyKind {
BitRecTyKind,
BitsRecTyKind,
+ CodeRecTyKind,
IntRecTyKind,
StringRecTyKind,
ListRecTyKind,
@@ -64,11 +66,11 @@ public:
void print(raw_ostream &OS) const { OS << getAsString(); }
void dump() const;
- /// typeIsConvertibleTo - Return true if all values of 'this' type can be
- /// converted to the specified type.
+ /// Return true if all values of 'this' type can be converted to the specified
+ /// type.
virtual bool typeIsConvertibleTo(const RecTy *RHS) const;
- /// getListTy - Returns the type representing list<this>.
+ /// Returns the type representing list<this>.
ListRecTy *getListTy();
};
@@ -77,7 +79,7 @@ inline raw_ostream &operator<<(raw_ostream &OS, const RecTy &Ty) {
return OS;
}
-/// BitRecTy - 'bit' - Represent a single bit
+/// 'bit' - Represent a single bit
///
class BitRecTy : public RecTy {
static BitRecTy Shared;
@@ -95,7 +97,7 @@ public:
bool typeIsConvertibleTo(const RecTy *RHS) const override;
};
-/// BitsRecTy - 'bits<n>' - Represent a fixed number of bits
+/// 'bits<n>' - Represent a fixed number of bits
///
class BitsRecTy : public RecTy {
unsigned Size;
@@ -115,7 +117,23 @@ public:
bool typeIsConvertibleTo(const RecTy *RHS) const override;
};
-/// IntRecTy - 'int' - Represent an integer value of no particular size
+/// 'code' - Represent a code fragment
+///
+class CodeRecTy : public RecTy {
+ static CodeRecTy Shared;
+ CodeRecTy() : RecTy(CodeRecTyKind) {}
+
+public:
+ static bool classof(const RecTy *RT) {
+ return RT->getRecTyKind() == CodeRecTyKind;
+ }
+
+ static CodeRecTy *get() { return &Shared; }
+
+ std::string getAsString() const override { return "code"; }
+};
+
+/// 'int' - Represent an integer value of no particular size
///
class IntRecTy : public RecTy {
static IntRecTy Shared;
@@ -133,7 +151,7 @@ public:
bool typeIsConvertibleTo(const RecTy *RHS) const override;
};
-/// StringRecTy - 'string' - Represent an string value
+/// 'string' - Represent an string value
///
class StringRecTy : public RecTy {
static StringRecTy Shared;
@@ -141,7 +159,8 @@ class StringRecTy : public RecTy {
public:
static bool classof(const RecTy *RT) {
- return RT->getRecTyKind() == StringRecTyKind;
+ return RT->getRecTyKind() == StringRecTyKind ||
+ RT->getRecTyKind() == CodeRecTyKind;
}
static StringRecTy *get() { return &Shared; }
@@ -149,7 +168,7 @@ public:
std::string getAsString() const override;
};
-/// ListRecTy - 'list<Ty>' - Represent a list of values, all of which must be of
+/// 'list<Ty>' - Represent a list of values, all of which must be of
/// the specified type.
///
class ListRecTy : public RecTy {
@@ -170,7 +189,7 @@ public:
bool typeIsConvertibleTo(const RecTy *RHS) const override;
};
-/// DagRecTy - 'dag' - Represent a dag fragment
+/// 'dag' - Represent a dag fragment
///
class DagRecTy : public RecTy {
static DagRecTy Shared;
@@ -186,7 +205,7 @@ public:
std::string getAsString() const override;
};
-/// RecordRecTy - '[classname]' - Represent an instance of a class, such as:
+/// '[classname]' - Represent an instance of a class, such as:
/// (R32 X = EAX).
///
class RecordRecTy : public RecTy {
@@ -208,7 +227,7 @@ public:
bool typeIsConvertibleTo(const RecTy *RHS) const override;
};
-/// resolveTypes - Find a common type that T1 and T2 convert to.
+/// Find a common type that T1 and T2 convert to.
/// Return 0 if no such type exists.
///
RecTy *resolveTypes(RecTy *T1, RecTy *T2);
@@ -236,6 +255,7 @@ protected:
IK_BitInit,
IK_FirstTypedInit,
IK_BitsInit,
+ IK_CodeInit,
IK_DagInit,
IK_DefInit,
IK_FieldInit,
@@ -272,30 +292,30 @@ protected:
public:
virtual ~Init() {}
- /// isComplete - This virtual method should be overridden by values that may
+ /// This virtual method should be overridden by values that may
/// not be completely specified yet.
virtual bool isComplete() const { return true; }
- /// print - Print out this value.
+ /// Print out this value.
void print(raw_ostream &OS) const { OS << getAsString(); }
- /// getAsString - Convert this value to a string form.
+ /// Convert this value to a string form.
virtual std::string getAsString() const = 0;
- /// getAsUnquotedString - Convert this value to a string form,
+ /// Convert this value to a string form,
/// without adding quote markers. This primaruly affects
/// StringInits where we will not surround the string value with
/// quotes.
virtual std::string getAsUnquotedString() const { return getAsString(); }
- /// dump - Debugging method that may be called through a debugger, just
+ /// Debugging method that may be called through a debugger, just
/// invokes print on stderr.
void dump() const;
- /// convertInitializerTo - This virtual function converts to the appropriate
+ /// This virtual function converts to the appropriate
/// Init based on the passed in type.
virtual Init *convertInitializerTo(RecTy *Ty) const = 0;
- /// convertInitializerBitRange - This method is used to implement the bitrange
+ /// This method is used to implement the bitrange
/// selection operator. Given an initializer, it selects the specified bits
/// out, returning them as a new init of bits type. If it is not legal to use
/// the bit subscript operator on this initializer, return null.
@@ -305,7 +325,7 @@ public:
return nullptr;
}
- /// convertInitListSlice - This method is used to implement the list slice
+ /// This method is used to implement the list slice
/// selection operator. Given an initializer, it selects the specified list
/// elements, returning them as a new init of list type. If it is not legal
/// to take a slice of this, return null.
@@ -315,7 +335,7 @@ public:
return nullptr;
}
- /// getFieldType - This method is used to implement the FieldInit class.
+ /// This method is used to implement the FieldInit class.
/// Implementors of this method should return the type of the named field if
/// they are of record type.
///
@@ -323,7 +343,7 @@ public:
return nullptr;
}
- /// getFieldInit - This method complements getFieldType to return the
+ /// This method complements getFieldType to return the
/// initializer for the specified field. If getFieldType returns non-null
/// this method should return non-null, otherwise it returns null.
///
@@ -332,7 +352,7 @@ public:
return nullptr;
}
- /// resolveReferences - This method is used by classes that refer to other
+ /// This method is used by classes that refer to other
/// variables which may not be defined at the time the expression is formed.
/// If a value is set for the variable later, this method will be called on
/// users of the value to allow the value to propagate out.
@@ -341,15 +361,15 @@ public:
return const_cast<Init *>(this);
}
- /// getBit - This method is used to return the initializer for the specified
+ /// This method is used to return the initializer for the specified
/// bit.
virtual Init *getBit(unsigned Bit) const = 0;
- /// getBitVar - This method is used to retrieve the initializer for bit
+ /// This method is used to retrieve the initializer for bit
/// reference. For non-VarBitInit, it simply returns itself.
virtual Init *getBitVar() const { return const_cast<Init*>(this); }
- /// getBitNum - This method is used to retrieve the bit number of a bit
+ /// This method is used to retrieve the bit number of a bit
/// reference. For non-VarBitInit, it simply returns 0.
virtual unsigned getBitNum() const { return 0; }
};
@@ -358,7 +378,7 @@ inline raw_ostream &operator<<(raw_ostream &OS, const Init &I) {
I.print(OS); return OS;
}
-/// TypedInit - This is the common super-class of types that have a specific,
+/// This is the common super-class of types that have a specific,
/// explicit, type.
///
class TypedInit : public Init {
@@ -390,20 +410,20 @@ public:
Init *
convertInitListSlice(const std::vector<unsigned> &Elements) const override;
- /// getFieldType - This method is used to implement the FieldInit class.
+ /// This method is used to implement the FieldInit class.
/// Implementors of this method should return the type of the named field if
/// they are of record type.
///
RecTy *getFieldType(const std::string &FieldName) const override;
- /// resolveListElementReference - This method is used to implement
+ /// This method is used to implement
/// VarListElementInit::resolveReferences. If the list element is resolvable
/// now, we return the resolved value, otherwise we return null.
virtual Init *resolveListElementReference(Record &R, const RecordVal *RV,
unsigned Elt) const = 0;
};
-/// UnsetInit - ? - Represents an uninitialized value
+/// '?' - Represents an uninitialized value
///
class UnsetInit : public Init {
UnsetInit() : Init(IK_UnsetInit) {}
@@ -426,7 +446,7 @@ public:
std::string getAsString() const override { return "?"; }
};
-/// BitInit - true/false - Represent a concrete initializer for a bit.
+/// 'true'/'false' - Represent a concrete initializer for a bit.
///
class BitInit : public Init {
bool Value;
@@ -453,20 +473,23 @@ public:
std::string getAsString() const override { return Value ? "1" : "0"; }
};
-/// BitsInit - { a, b, c } - Represents an initializer for a BitsRecTy value.
+/// '{ a, b, c }' - Represents an initializer for a BitsRecTy value.
/// It contains a vector of bits, whose size is determined by the type.
///
-class BitsInit : public TypedInit, public FoldingSetNode {
- std::vector<Init*> Bits;
+class BitsInit final : public TypedInit, public FoldingSetNode,
+ public TrailingObjects<BitsInit, Init *> {
+ unsigned NumBits;
- BitsInit(ArrayRef<Init *> Range)
- : TypedInit(IK_BitsInit, BitsRecTy::get(Range.size())),
- Bits(Range.begin(), Range.end()) {}
+ BitsInit(unsigned N)
+ : TypedInit(IK_BitsInit, BitsRecTy::get(N)), NumBits(N) {}
BitsInit(const BitsInit &Other) = delete;
BitsInit &operator=(const BitsInit &Other) = delete;
public:
+ // Do not use sized deallocation due to trailing objects.
+ void operator delete(void *p) { ::operator delete(p); }
+
static bool classof(const Init *I) {
return I->getKind() == IK_BitsInit;
}
@@ -474,7 +497,7 @@ public:
void Profile(FoldingSetNodeID &ID) const;
- unsigned getNumBits() const { return Bits.size(); }
+ unsigned getNumBits() const { return NumBits; }
Init *convertInitializerTo(RecTy *Ty) const override;
Init *
@@ -492,7 +515,7 @@ public:
}
std::string getAsString() const override;
- /// resolveListElementReference - This method is used to implement
+ /// This method is used to implement
/// VarListElementInit::resolveReferences. If the list element is resolvable
/// now, we return the resolved value, otherwise we return null.
Init *resolveListElementReference(Record &R, const RecordVal *RV,
@@ -503,12 +526,12 @@ public:
Init *resolveReferences(Record &R, const RecordVal *RV) const override;
Init *getBit(unsigned Bit) const override {
- assert(Bit < Bits.size() && "Bit index out of range!");
- return Bits[Bit];
+ assert(Bit < NumBits && "Bit index out of range!");
+ return getTrailingObjects<Init *>()[Bit];
}
};
-/// IntInit - 7 - Represent an initialization by a literal integer value.
+/// '7' - Represent an initialization by a literal integer value.
///
class IntInit : public TypedInit {
int64_t Value;
@@ -533,7 +556,7 @@ public:
std::string getAsString() const override;
- /// resolveListElementReference - This method is used to implement
+ /// This method is used to implement
/// VarListElementInit::resolveReferences. If the list element is resolvable
/// now, we return the resolved value, otherwise we return null.
Init *resolveListElementReference(Record &R, const RecordVal *RV,
@@ -546,13 +569,13 @@ public:
}
};
-/// StringInit - "foo" - Represent an initialization by a string value.
+/// "foo" - Represent an initialization by a string value.
///
class StringInit : public TypedInit {
std::string Value;
explicit StringInit(StringRef V)
- : TypedInit(IK_StringInit, StringRecTy::get()), Value(V) {}
+ : TypedInit(IK_StringInit, StringRecTy::get()), Value(V) {}
StringInit(const StringInit &Other) = delete;
StringInit &operator=(const StringInit &Other) = delete;
@@ -568,6 +591,7 @@ public:
Init *convertInitializerTo(RecTy *Ty) const override;
std::string getAsString() const override { return "\"" + Value + "\""; }
+
std::string getAsUnquotedString() const override { return Value; }
/// resolveListElementReference - This method is used to implement
@@ -583,23 +607,65 @@ public:
}
};
-/// ListInit - [AL, AH, CL] - Represent a list of defs
+class CodeInit : public TypedInit {
+ std::string Value;
+
+ explicit CodeInit(StringRef V)
+ : TypedInit(IK_CodeInit, static_cast<RecTy *>(CodeRecTy::get())),
+ Value(V) {}
+
+ CodeInit(const StringInit &Other) = delete;
+ CodeInit &operator=(const StringInit &Other) = delete;
+
+public:
+ static bool classof(const Init *I) {
+ return I->getKind() == IK_CodeInit;
+ }
+ static CodeInit *get(StringRef);
+
+ const std::string &getValue() const { return Value; }
+
+ Init *convertInitializerTo(RecTy *Ty) const override;
+
+ std::string getAsString() const override {
+ return "[{" + Value + "}]";
+ }
+
+ std::string getAsUnquotedString() const override { return Value; }
+
+ /// This method is used to implement
+ /// VarListElementInit::resolveReferences. If the list element is resolvable
+ /// now, we return the resolved value, otherwise we return null.
+ Init *resolveListElementReference(Record &R, const RecordVal *RV,
+ unsigned Elt) const override {
+ llvm_unreachable("Illegal element reference off string");
+ }
+
+ Init *getBit(unsigned Bit) const override {
+ llvm_unreachable("Illegal bit reference off string");
+ }
+};
+
+/// [AL, AH, CL] - Represent a list of defs
///
-class ListInit : public TypedInit, public FoldingSetNode {
- std::vector<Init*> Values;
+class ListInit final : public TypedInit, public FoldingSetNode,
+ public TrailingObjects<BitsInit, Init *> {
+ unsigned NumValues;
public:
- typedef std::vector<Init*>::const_iterator const_iterator;
+ typedef Init *const *const_iterator;
private:
- explicit ListInit(ArrayRef<Init *> Range, RecTy *EltTy)
- : TypedInit(IK_ListInit, ListRecTy::get(EltTy)),
- Values(Range.begin(), Range.end()) {}
+ explicit ListInit(unsigned N, RecTy *EltTy)
+ : TypedInit(IK_ListInit, ListRecTy::get(EltTy)), NumValues(N) {}
ListInit(const ListInit &Other) = delete;
ListInit &operator=(const ListInit &Other) = delete;
public:
+ // Do not use sized deallocation due to trailing objects.
+ void operator delete(void *p) { ::operator delete(p); }
+
static bool classof(const Init *I) {
return I->getKind() == IK_ListInit;
}
@@ -608,8 +674,8 @@ public:
void Profile(FoldingSetNodeID &ID) const;
Init *getElement(unsigned i) const {
- assert(i < Values.size() && "List element index out of range!");
- return Values[i];
+ assert(i < NumValues && "List element index out of range!");
+ return getTrailingObjects<Init *>()[i];
}
Record *getElementAsRecord(unsigned i) const;
@@ -619,7 +685,7 @@ public:
Init *convertInitializerTo(RecTy *Ty) const override;
- /// resolveReferences - This method is used by classes that refer to other
+ /// This method is used by classes that refer to other
/// variables which may not be defined at the time they expression is formed.
/// If a value is set for the variable later, this method will be called on
/// users of the value to allow the value to propagate out.
@@ -628,15 +694,17 @@ public:
std::string getAsString() const override;
- ArrayRef<Init*> getValues() const { return Values; }
+ ArrayRef<Init*> getValues() const {
+ return makeArrayRef(getTrailingObjects<Init *>(), NumValues);
+ }
- const_iterator begin() const { return Values.begin(); }
- const_iterator end () const { return Values.end(); }
+ const_iterator begin() const { return getTrailingObjects<Init *>(); }
+ const_iterator end () const { return begin() + NumValues; }
- size_t size () const { return Values.size(); }
- bool empty() const { return Values.empty(); }
+ size_t size () const { return NumValues; }
+ bool empty() const { return NumValues == 0; }
- /// resolveListElementReference - This method is used to implement
+ /// This method is used to implement
/// VarListElementInit::resolveReferences. If the list element is resolvable
/// now, we return the resolved value, otherwise we return null.
Init *resolveListElementReference(Record &R, const RecordVal *RV,
@@ -647,7 +715,7 @@ public:
}
};
-/// OpInit - Base class for operators
+/// Base class for operators
///
class OpInit : public TypedInit {
OpInit(const OpInit &Other) = delete;
@@ -678,9 +746,9 @@ public:
Init *getBit(unsigned Bit) const override;
};
-/// UnOpInit - !op (X) - Transform an init.
+/// !op (X) - Transform an init.
///
-class UnOpInit : public OpInit {
+class UnOpInit : public OpInit, public FoldingSetNode {
public:
enum UnaryOp : uint8_t { CAST, HEAD, TAIL, EMPTY };
@@ -699,6 +767,8 @@ public:
}
static UnOpInit *get(UnaryOp opc, Init *lhs, RecTy *Type);
+ void Profile(FoldingSetNodeID &ID) const;
+
// Clone - Clone this operator, replacing arguments with the new list
OpInit *clone(std::vector<Init *> &Operands) const override {
assert(Operands.size() == 1 &&
@@ -724,9 +794,9 @@ public:
std::string getAsString() const override;
};
-/// BinOpInit - !op (X, Y) - Combine two inits.
+/// !op (X, Y) - Combine two inits.
///
-class BinOpInit : public OpInit {
+class BinOpInit : public OpInit, public FoldingSetNode {
public:
enum BinaryOp : uint8_t { ADD, AND, SHL, SRA, SRL, LISTCONCAT,
STRCONCAT, CONCAT, EQ };
@@ -747,6 +817,8 @@ public:
static BinOpInit *get(BinaryOp opc, Init *lhs, Init *rhs,
RecTy *Type);
+ void Profile(FoldingSetNodeID &ID) const;
+
// Clone - Clone this operator, replacing arguments with the new list
OpInit *clone(std::vector<Init *> &Operands) const override {
assert(Operands.size() == 2 &&
@@ -776,9 +848,9 @@ public:
std::string getAsString() const override;
};
-/// TernOpInit - !op (X, Y, Z) - Combine two inits.
+/// !op (X, Y, Z) - Combine two inits.
///
-class TernOpInit : public OpInit {
+class TernOpInit : public OpInit, public FoldingSetNode {
public:
enum TernaryOp : uint8_t { SUBST, FOREACH, IF };
@@ -800,6 +872,8 @@ public:
Init *mhs, Init *rhs,
RecTy *Type);
+ void Profile(FoldingSetNodeID &ID) const;
+
// Clone - Clone this operator, replacing arguments with the new list
OpInit *clone(std::vector<Init *> &Operands) const override {
assert(Operands.size() == 3 &&
@@ -834,7 +908,7 @@ public:
std::string getAsString() const override;
};
-/// VarInit - 'Opcode' - Represent a reference to an entire variable object.
+/// 'Opcode' - Represent a reference to an entire variable object.
///
class VarInit : public TypedInit {
Init *VarName;
@@ -865,7 +939,7 @@ public:
Init *getFieldInit(Record &R, const RecordVal *RV,
const std::string &FieldName) const override;
- /// resolveReferences - This method is used by classes that refer to other
+ /// This method is used by classes that refer to other
/// variables which may not be defined at the time they expression is formed.
/// If a value is set for the variable later, this method will be called on
/// users of the value to allow the value to propagate out.
@@ -877,7 +951,7 @@ public:
std::string getAsString() const override { return getName(); }
};
-/// VarBitInit - Opcode{0} - Represent access to one bit of a variable or field.
+/// Opcode{0} - Represent access to one bit of a variable or field.
///
class VarBitInit : public Init {
TypedInit *TI;
@@ -914,7 +988,7 @@ public:
}
};
-/// VarListElementInit - List[4] - Represent access to one element of a var or
+/// List[4] - Represent access to one element of a var or
/// field.
class VarListElementInit : public TypedInit {
TypedInit *TI;
@@ -940,7 +1014,7 @@ public:
TypedInit *getVariable() const { return TI; }
unsigned getElementNum() const { return Element; }
- /// resolveListElementReference - This method is used to implement
+ /// This method is used to implement
/// VarListElementInit::resolveReferences. If the list element is resolvable
/// now, we return the resolved value, otherwise we return null.
Init *resolveListElementReference(Record &R, const RecordVal *RV,
@@ -952,7 +1026,7 @@ public:
Init *getBit(unsigned Bit) const override;
};
-/// DefInit - AL - Represent a reference to a 'def' in the description
+/// AL - Represent a reference to a 'def' in the description
///
class DefInit : public TypedInit {
Record *Def;
@@ -985,7 +1059,7 @@ public:
llvm_unreachable("Illegal bit reference off def");
}
- /// resolveListElementReference - This method is used to implement
+ /// This method is used to implement
/// VarListElementInit::resolveReferences. If the list element is resolvable
/// now, we return the resolved value, otherwise we return null.
Init *resolveListElementReference(Record &R, const RecordVal *RV,
@@ -994,7 +1068,7 @@ public:
}
};
-/// FieldInit - X.Y - Represent a reference to a subfield of a variable
+/// X.Y - Represent a reference to a subfield of a variable
///
class FieldInit : public TypedInit {
Init *Rec; // Record we are referring to
@@ -1026,7 +1100,7 @@ public:
}
};
-/// DagInit - (v a, b) - Represent a DAG tree value. DAG inits are required
+/// (v a, b) - Represent a DAG tree value. DAG inits are required
/// to have at least one value then a (possibly empty) list of arguments. Each
/// argument can have a name associated with it.
///
@@ -1148,21 +1222,22 @@ inline raw_ostream &operator<<(raw_ostream &OS, const RecordVal &RV) {
class Record {
static unsigned LastID;
- // Unique record ID.
- unsigned ID;
Init *Name;
// Location where record was instantiated, followed by the location of
// multiclass prototypes used.
SmallVector<SMLoc, 4> Locs;
- std::vector<Init *> TemplateArgs;
- std::vector<RecordVal> Values;
- std::vector<Record *> SuperClasses;
- std::vector<SMRange> SuperClassRanges;
+ SmallVector<Init *, 0> TemplateArgs;
+ SmallVector<RecordVal, 0> Values;
+ SmallVector<std::pair<Record *, SMRange>, 0> SuperClasses;
// Tracks Record instances. Not owned by Record.
RecordKeeper &TrackedRecords;
std::unique_ptr<DefInit> TheInit;
+
+ // Unique record ID.
+ unsigned ID;
+
bool IsAnonymous;
// Class-instance values can be used by other defs. For example, Struct<i>
@@ -1184,8 +1259,8 @@ public:
// Constructs a record.
explicit Record(Init *N, ArrayRef<SMLoc> locs, RecordKeeper &records,
bool Anonymous = false) :
- ID(LastID++), Name(N), Locs(locs.begin(), locs.end()),
- TrackedRecords(records), IsAnonymous(Anonymous), ResolveFirst(false) {
+ Name(N), Locs(locs.begin(), locs.end()), TrackedRecords(records),
+ ID(LastID++), IsAnonymous(Anonymous), ResolveFirst(false) {
init();
}
explicit Record(const std::string &N, ArrayRef<SMLoc> locs,
@@ -1197,11 +1272,10 @@ public:
// ID number. Don't copy TheInit either since it's owned by the original
// record. All other fields can be copied normally.
Record(const Record &O) :
- ID(LastID++), Name(O.Name), Locs(O.Locs), TemplateArgs(O.TemplateArgs),
+ Name(O.Name), Locs(O.Locs), TemplateArgs(O.TemplateArgs),
Values(O.Values), SuperClasses(O.SuperClasses),
- SuperClassRanges(O.SuperClassRanges), TrackedRecords(O.TrackedRecords),
- IsAnonymous(O.IsAnonymous),
- ResolveFirst(O.ResolveFirst) { }
+ TrackedRecords(O.TrackedRecords), ID(LastID++),
+ IsAnonymous(O.IsAnonymous), ResolveFirst(O.ResolveFirst) { }
static unsigned getNewUID() { return LastID++; }
@@ -1227,8 +1301,9 @@ public:
return TemplateArgs;
}
ArrayRef<RecordVal> getValues() const { return Values; }
- ArrayRef<Record *> getSuperClasses() const { return SuperClasses; }
- ArrayRef<SMRange> getSuperClassRanges() const { return SuperClassRanges; }
+ ArrayRef<std::pair<Record *, SMRange>> getSuperClasses() const {
+ return SuperClasses;
+ }
bool isTemplateArg(Init *Name) const {
for (Init *TA : TemplateArgs)
@@ -1290,31 +1365,35 @@ public:
}
bool isSubClassOf(const Record *R) const {
- for (const Record *SC : SuperClasses)
- if (SC == R)
+ for (const auto &SCPair : SuperClasses)
+ if (SCPair.first == R)
return true;
return false;
}
bool isSubClassOf(StringRef Name) const {
- for (const Record *SC : SuperClasses)
- if (SC->getNameInitAsString() == Name)
+ for (const auto &SCPair : SuperClasses) {
+ if (const auto *SI = dyn_cast<StringInit>(SCPair.first->getNameInit())) {
+ if (SI->getValue() == Name)
+ return true;
+ } else if (SCPair.first->getNameInitAsString() == Name) {
return true;
+ }
+ }
return false;
}
void addSuperClass(Record *R, SMRange Range) {
assert(!isSubClassOf(R) && "Already subclassing record!");
- SuperClasses.push_back(R);
- SuperClassRanges.push_back(Range);
+ SuperClasses.push_back(std::make_pair(R, Range));
}
- /// resolveReferences - If there are any field references that refer to fields
+ /// If there are any field references that refer to fields
/// that have been filled in, we can propagate the values now.
///
void resolveReferences() { resolveReferencesTo(nullptr); }
- /// resolveReferencesTo - If anything in this record refers to RV, replace the
+ /// If anything in this record refers to RV, replace the
/// reference to RV with the RHS of RV. If RV is null, we resolve all
/// possible references.
void resolveReferencesTo(const RecordVal *RV);
@@ -1341,7 +1420,7 @@ public:
// High-level methods useful to tablegen back-ends
//
- /// getValueInit - Return the initializer for a value with the specified name,
+ /// Return the initializer for a value with the specified name,
/// or throw an exception if the field does not exist.
///
Init *getValueInit(StringRef FieldName) const;
@@ -1351,67 +1430,67 @@ public:
return isa<UnsetInit>(getValueInit(FieldName));
}
- /// getValueAsString - This method looks up the specified field and returns
+ /// This method looks up the specified field and returns
/// its value as a string, throwing an exception if the field does not exist
/// or if the value is not a string.
///
std::string getValueAsString(StringRef FieldName) const;
- /// getValueAsBitsInit - This method looks up the specified field and returns
+ /// This method looks up the specified field and returns
/// its value as a BitsInit, throwing an exception if the field does not exist
/// or if the value is not the right type.
///
BitsInit *getValueAsBitsInit(StringRef FieldName) const;
- /// getValueAsListInit - This method looks up the specified field and returns
+ /// This method looks up the specified field and returns
/// its value as a ListInit, throwing an exception if the field does not exist
/// or if the value is not the right type.
///
ListInit *getValueAsListInit(StringRef FieldName) const;
- /// getValueAsListOfDefs - This method looks up the specified field and
+ /// This method looks up the specified field and
/// returns its value as a vector of records, throwing an exception if the
/// field does not exist or if the value is not the right type.
///
std::vector<Record*> getValueAsListOfDefs(StringRef FieldName) const;
- /// getValueAsListOfInts - This method looks up the specified field and
+ /// This method looks up the specified field and
/// returns its value as a vector of integers, throwing an exception if the
/// field does not exist or if the value is not the right type.
///
std::vector<int64_t> getValueAsListOfInts(StringRef FieldName) const;
- /// getValueAsListOfStrings - This method looks up the specified field and
+ /// This method looks up the specified field and
/// returns its value as a vector of strings, throwing an exception if the
/// field does not exist or if the value is not the right type.
///
std::vector<std::string> getValueAsListOfStrings(StringRef FieldName) const;
- /// getValueAsDef - This method looks up the specified field and returns its
+ /// This method looks up the specified field and returns its
/// value as a Record, throwing an exception if the field does not exist or if
/// the value is not the right type.
///
Record *getValueAsDef(StringRef FieldName) const;
- /// getValueAsBit - This method looks up the specified field and returns its
+ /// This method looks up the specified field and returns its
/// value as a bit, throwing an exception if the field does not exist or if
/// the value is not the right type.
///
bool getValueAsBit(StringRef FieldName) const;
- /// getValueAsBitOrUnset - This method looks up the specified field and
+ /// This method looks up the specified field and
/// returns its value as a bit. If the field is unset, sets Unset to true and
/// returns false.
///
bool getValueAsBitOrUnset(StringRef FieldName, bool &Unset) const;
- /// getValueAsInt - This method looks up the specified field and returns its
+ /// This method looks up the specified field and returns its
/// value as an int64_t, throwing an exception if the field does not exist or
/// if the value is not the right type.
///
int64_t getValueAsInt(StringRef FieldName) const;
- /// getValueAsDag - This method looks up the specified field and returns its
+ /// This method looks up the specified field and returns its
/// value as an Dag, throwing an exception if the field does not exist or if
/// the value is not the right type.
///
@@ -1463,16 +1542,16 @@ public:
//===--------------------------------------------------------------------===//
// High-level helper methods, useful for tablegen backends...
- /// getAllDerivedDefinitions - This method returns all concrete definitions
- /// that derive from the specified class name. If a class with the specified
- /// name does not exist, an exception is thrown.
- std::vector<Record*>
+ /// This method returns all concrete definitions
+ /// that derive from the specified class name. A class with the specified
+ /// name must exist.
+ std::vector<Record *>
getAllDerivedDefinitions(const std::string &ClassName) const;
void dump() const;
};
-/// LessRecord - Sorting predicate to sort record pointers by name.
+/// Sorting predicate to sort record pointers by name.
///
struct LessRecord {
bool operator()(const Record *Rec1, const Record *Rec2) const {
@@ -1480,7 +1559,7 @@ struct LessRecord {
}
};
-/// LessRecordByID - Sorting predicate to sort record pointers by their
+/// Sorting predicate to sort record pointers by their
/// unique ID. If you just need a deterministic order, use this, since it
/// just compares two `unsigned`; the other sorting predicates require
/// string manipulation.
@@ -1490,7 +1569,7 @@ struct LessRecordByID {
}
};
-/// LessRecordFieldName - Sorting predicate to sort record pointers by their
+/// Sorting predicate to sort record pointers by their
/// name field.
///
struct LessRecordFieldName {
@@ -1580,12 +1659,12 @@ struct LessRecordRegister {
raw_ostream &operator<<(raw_ostream &OS, const RecordKeeper &RK);
-/// QualifyName - Return an Init with a qualifier prefix referring
+/// Return an Init with a qualifier prefix referring
/// to CurRec's name.
Init *QualifyName(Record &CurRec, MultiClass *CurMultiClass,
Init *Name, const std::string &Scoper);
-/// QualifyName - Return an Init with a qualifier prefix referring
+/// Return an Init with a qualifier prefix referring
/// to CurRec's name.
Init *QualifyName(Record &CurRec, MultiClass *CurMultiClass,
const std::string &Name, const std::string &Scoper);
diff --git a/include/llvm/TableGen/SearchableTable.td b/include/llvm/TableGen/SearchableTable.td
new file mode 100644
index 000000000000..12aaf6000c31
--- /dev/null
+++ b/include/llvm/TableGen/SearchableTable.td
@@ -0,0 +1,41 @@
+//===- SearchableTable.td ----------------------------------*- tablegen -*-===//
+//
+// The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// This file defines the key top-level classes needed to produce a reasonably
+// generic table that can be binary-searched via int and string entries.
+//
+// Each table must instantiate "Mappingkind", listing the fields that should be
+// included and fields that shoould be searchable. Only two kinds of fields are
+// searchable at the moment: "strings" (which are compared case-insensitively),
+// and "bits".
+//
+// For each "MappingKind" the generated header will create GET_MAPPINGKIND_DECL
+// and GET_MAPPINGKIND_IMPL guards.
+//
+// Inside the DECL guard will be a set of function declarations:
+// "lookup{InstanceClass}By{SearchableField}", returning "const {InstanceClass}
+// *" and accepting either a StringRef or a uintN_t. Additionally, if
+// EnumNameField is still defined, there will be an "enum {InstanceClass}Values"
+// allowing C++ code to reference either the primary data table's entries (if
+// EnumValueField is not defined) or some other field (e.g. encoding) if it is.
+//
+// Inside the IMPL guard will be a primary data table "{InstanceClass}sList" and
+// as many searchable indexes as requested
+// ("{InstanceClass}sBy{SearchableField}"). Additionally implementations of the
+// lookup function will be provided.
+//
+// See AArch64SystemOperands.td and its generated header for example uses.
+//
+//===----------------------------------------------------------------------===//
+
+class SearchableTable {
+ list<string> SearchableFields;
+ string EnumNameField = "Name";
+ string EnumValueField;
+}
diff --git a/include/llvm/TableGen/StringToOffsetTable.h b/include/llvm/TableGen/StringToOffsetTable.h
index e3277036dc76..e5b61ed1195e 100644
--- a/include/llvm/TableGen/StringToOffsetTable.h
+++ b/include/llvm/TableGen/StringToOffsetTable.h
@@ -76,6 +76,26 @@ public:
}
O << "\"";
}
+
+ /// Emit the string using character literals. MSVC has a limitation that
+ /// string literals cannot be longer than 64K.
+ void EmitCharArray(raw_ostream &O) {
+ assert(AggregateString.find(')') == std::string::npos &&
+ "can't emit raw string with closing parens");
+ int Count = 0;
+ O << ' ';
+ for (char C : AggregateString) {
+ O << " \'";
+ O.write_escaped(StringRef(&C, 1));
+ O << "\',";
+ Count++;
+ if (Count > 14) {
+ O << "\n ";
+ Count = 0;
+ }
+ }
+ O << '\n';
+ }
};
} // end namespace llvm