blob: 38b782461bd56ef12fc22e4011d0ae5b3e8fc763 [file] [log] [blame]
Chris Lattnerf4127dd2007-11-22 20:49:04 +00001//===- TGParser.h - Parser for TableGen Files -------------------*- C++ -*-===//
2//
Chandler Carruth2946cd72019-01-19 08:50:56 +00003// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
Chris Lattnerf4127dd2007-11-22 20:49:04 +00006//
7//===----------------------------------------------------------------------===//
8//
9// This class represents the Parser for tablegen files.
10//
11//===----------------------------------------------------------------------===//
12
Benjamin Kramera7c40ef2014-08-13 16:26:38 +000013#ifndef LLVM_LIB_TABLEGEN_TGPARSER_H
14#define LLVM_LIB_TABLEGEN_TGPARSER_H
Chris Lattnerf4127dd2007-11-22 20:49:04 +000015
16#include "TGLexer.h"
Benjamin Kramerc7583112010-09-27 17:42:11 +000017#include "llvm/ADT/Twine.h"
Chris Lattner1b30e1ac2009-06-21 03:36:54 +000018#include "llvm/Support/SourceMgr.h"
Chandler Carruth802d7552012-12-04 07:12:27 +000019#include "llvm/TableGen/Error.h"
20#include "llvm/TableGen/Record.h"
Chris Lattnerf4127dd2007-11-22 20:49:04 +000021#include <map>
22
23namespace llvm {
24 class Record;
25 class RecordVal;
Chris Lattner77d369c2010-12-13 00:23:57 +000026 class RecordKeeper;
Jakob Stoklund Olesenabcfdce2011-07-18 17:02:57 +000027 class RecTy;
David Greene9908c172011-07-13 22:25:51 +000028 class Init;
Nicolai Haehnle7d69e0f2018-06-21 13:35:44 +000029 struct ForeachLoop;
Chris Lattnerf4127dd2007-11-22 20:49:04 +000030 struct MultiClass;
Sebastian Redl8d5baa02009-03-19 23:26:52 +000031 struct SubClassReference;
David Greene753ed8f2009-04-22 16:42:54 +000032 struct SubMultiClassReference;
Sean Silva50f06aa2012-10-04 00:54:27 +000033
Chris Lattnerf4127dd2007-11-22 20:49:04 +000034 struct LetRecord {
Matthias Braun215ff842016-12-05 07:35:13 +000035 StringInit *Name;
Chris Lattnerf4127dd2007-11-22 20:49:04 +000036 std::vector<unsigned> Bits;
David Greeneaf8ee2c2011-07-29 22:43:06 +000037 Init *Value;
Chris Lattner526c8cb2009-06-21 03:39:35 +000038 SMLoc Loc;
Matthias Braun215ff842016-12-05 07:35:13 +000039 LetRecord(StringInit *N, ArrayRef<unsigned> B, Init *V, SMLoc L)
Chris Lattnerf4127dd2007-11-22 20:49:04 +000040 : Name(N), Bits(B), Value(V), Loc(L) {
41 }
42 };
Sean Silva50f06aa2012-10-04 00:54:27 +000043
Nicolai Haehnle7d69e0f2018-06-21 13:35:44 +000044 /// RecordsEntry - Can be either a record or a foreach loop.
45 struct RecordsEntry {
46 std::unique_ptr<Record> Rec;
47 std::unique_ptr<ForeachLoop> Loop;
48
49 void dump() const;
50
51 RecordsEntry() {}
52 RecordsEntry(std::unique_ptr<Record> Rec) : Rec(std::move(Rec)) {}
53 RecordsEntry(std::unique_ptr<ForeachLoop> Loop)
54 : Loop(std::move(Loop)) {}
55 };
56
David Greenefb927af2012-02-22 16:09:41 +000057 /// ForeachLoop - Record the iteration state associated with a for loop.
58 /// This is used to instantiate items in the loop body.
59 struct ForeachLoop {
Nicolai Haehnle7d69e0f2018-06-21 13:35:44 +000060 SMLoc Loc;
Jakob Stoklund Olesen8a120b12012-05-24 22:17:33 +000061 VarInit *IterVar;
Nicolai Haehnle7d69e0f2018-06-21 13:35:44 +000062 Init *ListValue;
63 std::vector<RecordsEntry> Entries;
David Greenefb927af2012-02-22 16:09:41 +000064
Nicolai Haehnle7d69e0f2018-06-21 13:35:44 +000065 void dump() const;
66
67 ForeachLoop(SMLoc Loc, VarInit *IVar, Init *LValue)
68 : Loc(Loc), IterVar(IVar), ListValue(LValue) {}
David Greenefb927af2012-02-22 16:09:41 +000069 };
70
Nicolai Haehnlefcd65252018-03-09 12:24:42 +000071 struct DefsetRecord {
72 SMLoc Loc;
73 RecTy *EltTy;
74 SmallVector<Init *, 16> Elements;
75 };
76
Nicolai Haehnle7d69e0f2018-06-21 13:35:44 +000077struct MultiClass {
78 Record Rec; // Placeholder for template args and Name.
79 std::vector<RecordsEntry> Entries;
80
81 void dump() const;
82
83 MultiClass(StringRef Name, SMLoc Loc, RecordKeeper &Records) :
84 Rec(Name, Loc, Records) {}
85};
86
Chris Lattnerf4127dd2007-11-22 20:49:04 +000087class TGParser {
88 TGLexer Lex;
Matthias Braunc66e7552016-12-05 06:41:54 +000089 std::vector<SmallVector<LetRecord, 4>> LetStack;
Craig Topper7adf2bf2014-12-11 05:25:30 +000090 std::map<std::string, std::unique_ptr<MultiClass>> MultiClasses;
Sean Silva50f06aa2012-10-04 00:54:27 +000091
David Greenefb927af2012-02-22 16:09:41 +000092 /// Loops - Keep track of any foreach loops we are within.
93 ///
Nicolai Haehnle7d69e0f2018-06-21 13:35:44 +000094 std::vector<std::unique_ptr<ForeachLoop>> Loops;
David Greenefb927af2012-02-22 16:09:41 +000095
Nicolai Haehnlefcd65252018-03-09 12:24:42 +000096 SmallVector<DefsetRecord *, 2> Defsets;
97
Sean Silva50f06aa2012-10-04 00:54:27 +000098 /// CurMultiClass - If we are parsing a 'multiclass' definition, this is the
Chris Lattnerf4127dd2007-11-22 20:49:04 +000099 /// current value.
100 MultiClass *CurMultiClass;
Chris Lattner77d369c2010-12-13 00:23:57 +0000101
102 // Record tracker
Chris Lattner89dcb682010-12-15 04:48:22 +0000103 RecordKeeper &Records;
David Greened4263a62011-10-19 13:04:20 +0000104
105 // A "named boolean" indicating how to parse identifiers. Usually
106 // identifiers map to some existing object but in special cases
107 // (e.g. parsing def names) no such object exists yet because we are
108 // in the middle of creating in. For those situations, allow the
109 // parser to ignore missing object errors.
110 enum IDParseMode {
David Greenefb927af2012-02-22 16:09:41 +0000111 ParseValueMode, // We are parsing a value we expect to look up.
112 ParseNameMode, // We are parsing a name of an object that does not yet
113 // exist.
David Greened4263a62011-10-19 13:04:20 +0000114 };
115
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000116public:
Vyacheslav Zakharinf7d079e2018-11-27 18:57:43 +0000117 TGParser(SourceMgr &SrcMgr, ArrayRef<std::string> Macros,
118 RecordKeeper &records)
119 : Lex(SrcMgr, Macros), CurMultiClass(nullptr), Records(records) {}
Sean Silva50f06aa2012-10-04 00:54:27 +0000120
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000121 /// ParseFile - Main entrypoint for parsing a tblgen file. These parser
122 /// routines return true on error, or false on success.
123 bool ParseFile();
Sean Silva50f06aa2012-10-04 00:54:27 +0000124
Benjamin Kramerc7583112010-09-27 17:42:11 +0000125 bool Error(SMLoc L, const Twine &Msg) const {
Jim Grosbach797cff02011-06-21 22:55:50 +0000126 PrintError(L, Msg);
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000127 return true;
128 }
Benjamin Kramerc7583112010-09-27 17:42:11 +0000129 bool TokError(const Twine &Msg) const {
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000130 return Error(Lex.getLoc(), Msg);
131 }
Sean Silva3b964242013-02-07 04:30:39 +0000132 const TGLexer::DependenciesMapTy &getDependencies() const {
Joerg Sonnenbergeraf5f23e2011-06-01 13:10:15 +0000133 return Lex.getDependencies();
134 }
David Greenefb927af2012-02-22 16:09:41 +0000135
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000136private: // Semantic analysis methods.
Chris Lattner526c8cb2009-06-21 03:39:35 +0000137 bool AddValue(Record *TheRec, SMLoc Loc, const RecordVal &RV);
Sean Silva50f06aa2012-10-04 00:54:27 +0000138 bool SetValue(Record *TheRec, SMLoc Loc, Init *ValName,
Craig Toppercfd81732016-01-04 03:15:08 +0000139 ArrayRef<unsigned> BitList, Init *V,
Craig Topper1e23ed92016-01-04 03:05:14 +0000140 bool AllowSelfAssignment = false);
Cedric Venetd1e179d2009-02-14 16:06:42 +0000141 bool AddSubClass(Record *Rec, SubClassReference &SubClass);
Nicolai Haehnle7d69e0f2018-06-21 13:35:44 +0000142 bool AddSubClass(RecordsEntry &Entry, SubClassReference &SubClass);
Bob Wilsonf71e6562009-04-30 18:26:19 +0000143 bool AddSubMultiClass(MultiClass *CurMC,
144 SubMultiClassReference &SubMultiClass);
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000145
Nicolai Haehnle7d69e0f2018-06-21 13:35:44 +0000146 using SubstStack = SmallVector<std::pair<Init *, Init *>, 8>;
David Greenefb927af2012-02-22 16:09:41 +0000147
Nicolai Haehnle7d69e0f2018-06-21 13:35:44 +0000148 bool addEntry(RecordsEntry E);
149 bool resolve(const ForeachLoop &Loop, SubstStack &Stack, bool Final,
150 std::vector<RecordsEntry> *Dest, SMLoc *Loc = nullptr);
151 bool resolve(const std::vector<RecordsEntry> &Source, SubstStack &Substs,
152 bool Final, std::vector<RecordsEntry> *Dest,
153 SMLoc *Loc = nullptr);
154 bool addDefOne(std::unique_ptr<Record> Rec);
Nicolai Haehnlefcd65252018-03-09 12:24:42 +0000155
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000156private: // Parser methods.
Craig Toppere73658d2014-04-28 04:05:08 +0000157 bool ParseObjectList(MultiClass *MC = nullptr);
Bruno Cardoso Lopes5f2adcc2010-06-10 02:42:59 +0000158 bool ParseObject(MultiClass *MC);
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000159 bool ParseClass();
160 bool ParseMultiClass();
Bruno Cardoso Lopes5f2adcc2010-06-10 02:42:59 +0000161 bool ParseDefm(MultiClass *CurMultiClass);
162 bool ParseDef(MultiClass *CurMultiClass);
Nicolai Haehnlefcd65252018-03-09 12:24:42 +0000163 bool ParseDefset();
David Greenefb927af2012-02-22 16:09:41 +0000164 bool ParseForeach(MultiClass *CurMultiClass);
Bruno Cardoso Lopes5f2adcc2010-06-10 02:42:59 +0000165 bool ParseTopLevelLet(MultiClass *CurMultiClass);
Matthias Braunc66e7552016-12-05 06:41:54 +0000166 void ParseLetList(SmallVectorImpl<LetRecord> &Result);
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000167
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000168 bool ParseObjectBody(Record *CurRec);
169 bool ParseBody(Record *CurRec);
170 bool ParseBodyItem(Record *CurRec);
171
172 bool ParseTemplateArgList(Record *CurRec);
David Greenedb10e692011-10-19 13:02:42 +0000173 Init *ParseDeclaration(Record *CurRec, bool ParsingTemplateArgs);
Nicolai Haehnle7d69e0f2018-06-21 13:35:44 +0000174 VarInit *ParseForeachDeclaration(Init *&ForeachListValue);
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000175
176 SubClassReference ParseSubClassReference(Record *CurRec, bool isDefm);
Bob Wilsonf71e6562009-04-30 18:26:19 +0000177 SubMultiClassReference ParseSubMultiClassReference(MultiClass *CurMC);
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000178
Matthias Braun215ff842016-12-05 07:35:13 +0000179 Init *ParseIDValue(Record *CurRec, StringInit *Name, SMLoc NameLoc,
David Greened4263a62011-10-19 13:04:20 +0000180 IDParseMode Mode = ParseValueMode);
Craig Toppere73658d2014-04-28 04:05:08 +0000181 Init *ParseSimpleValue(Record *CurRec, RecTy *ItemType = nullptr,
David Greened4263a62011-10-19 13:04:20 +0000182 IDParseMode Mode = ParseValueMode);
Craig Toppere73658d2014-04-28 04:05:08 +0000183 Init *ParseValue(Record *CurRec, RecTy *ItemType = nullptr,
David Greened4263a62011-10-19 13:04:20 +0000184 IDParseMode Mode = ParseValueMode);
Matthias Braunc66e7552016-12-05 06:41:54 +0000185 void ParseValueList(SmallVectorImpl<llvm::Init*> &Result, Record *CurRec,
186 Record *ArgsRec = nullptr, RecTy *EltTy = nullptr);
Matthias Braun1ddb78c2016-12-05 06:41:51 +0000187 void ParseDagArgList(
188 SmallVectorImpl<std::pair<llvm::Init*, StringInit*>> &Result,
189 Record *CurRec);
Matthias Braunc66e7552016-12-05 06:41:54 +0000190 bool ParseOptionalRangeList(SmallVectorImpl<unsigned> &Ranges);
191 bool ParseOptionalBitList(SmallVectorImpl<unsigned> &Ranges);
192 void ParseRangeList(SmallVectorImpl<unsigned> &Result);
193 bool ParseRangePiece(SmallVectorImpl<unsigned> &Ranges);
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000194 RecTy *ParseType();
Matt Arsenaulta73fd932014-06-10 20:10:08 +0000195 Init *ParseOperation(Record *CurRec, RecTy *ItemType);
Javed Absara3e3d852019-01-25 10:25:25 +0000196 Init *ParseOperationCond(Record *CurRec, RecTy *ItemType);
David Greene5d0c0512009-05-14 20:54:48 +0000197 RecTy *ParseOperatorType();
David Greene2affd672011-10-19 13:04:29 +0000198 Init *ParseObjectName(MultiClass *CurMultiClass);
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000199 Record *ParseClassID();
David Greene753ed8f2009-04-22 16:42:54 +0000200 MultiClass *ParseMultiClassID();
Sean Silvacb1a75e2013-01-09 04:49:14 +0000201 bool ApplyLetStack(Record *CurRec);
Nicolai Haehnle7d69e0f2018-06-21 13:35:44 +0000202 bool ApplyLetStack(RecordsEntry &Entry);
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000203};
Sean Silva50f06aa2012-10-04 00:54:27 +0000204
Chris Lattnerf4127dd2007-11-22 20:49:04 +0000205} // end namespace llvm
206
207#endif