source: icGREP/icgrep-devel/icgrep/pablo/codegenstate.h @ 5202

Last change on this file since 5202 was 5202, checked in by nmedfort, 2 years ago

Initial work on adding types to PabloAST and mutable Var objects.

File size: 10.1 KB
Line 
1/*
2 *  Copyright (c) 2014 International Characters.
3 *  This software is licensed to the public under the Open Software License 3.0.
4 *  icgrep is a trademark of International Characters.
5 */
6
7#ifndef PS_PABLOS_H
8#define PS_PABLOS_H
9
10#include <pablo/pabloAST.h>
11#include <pablo/symbol_generator.h>
12#include <pablo/pe_advance.h>
13#include <pablo/pe_lookahead.h>
14#include <pablo/pe_and.h>
15#include <pablo/pe_call.h>
16#include <pablo/pe_matchstar.h>
17#include <pablo/pe_not.h>
18#include <pablo/pe_ones.h>
19#include <pablo/pe_or.h>
20#include <pablo/pe_scanthru.h>
21#include <pablo/pe_sel.h>
22#include <pablo/pe_infile.h>
23#include <pablo/pe_integer.h>
24#include <pablo/pe_string.h>
25#include <pablo/pe_var.h>
26#include <pablo/pe_xor.h>
27#include <pablo/pe_zeroes.h>
28#include <pablo/pe_count.h>
29#include <pablo/ps_assign.h>
30#include <pablo/branch.h>
31#include <pablo/function.h>
32#include <llvm/ADT/ArrayRef.h>
33#include <stdexcept>
34
35namespace pablo {
36
37class PabloBlock : public PabloAST, public StatementList {
38    friend class PabloAST;
39    friend class Branch;
40    friend class PabloBuilder;
41public:
42
43    static inline bool classof(const PabloBlock *) {
44        return true;
45    }
46    static inline bool classof(const Statement *) {
47        return false;
48    }
49    static inline bool classof(const PabloAST * e) {
50        return e->getClassTypeId() == ClassTypeId::Block;
51    }
52    static inline bool classof(const void *) {
53        return false;
54    }
55
56    inline static PabloBlock * Create(PabloFunction & parent) noexcept {
57        return new PabloBlock(&parent);
58    }
59
60    inline static PabloBlock * Create(PabloBlock * const predecessor) noexcept {
61        return new PabloBlock(predecessor->mParent);
62    }
63
64    Advance * createAdvance(PabloAST * expr, PabloAST * shiftAmount) {
65        return createAdvance(expr, shiftAmount, nullptr);
66    }
67
68    Advance * createAdvance(PabloAST * expr, PabloAST * shiftAmount, const std::string & prefix) {
69        return createAdvance(expr, shiftAmount, makeName(prefix));
70    }
71
72    Advance * createAdvance(PabloAST * expr, PabloAST * shiftAmount, String * const name);
73
74    Lookahead * createLookahead(PabloAST * expr, PabloAST * shiftAmount) {
75        return createLookahead(expr, shiftAmount, nullptr);
76    }
77
78    Lookahead * createLookahead(PabloAST * expr, PabloAST * shiftAmount, const std::string & prefix) {
79        return createLookahead(expr, shiftAmount, makeName(prefix));
80    }
81
82    Lookahead * createLookahead(PabloAST * expr, PabloAST * shiftAmount, String * const name);
83
84    inline Zeroes * createZeroes(Type * const type = nullptr) {
85        return mParent->getNullValue(type);
86    }
87
88    inline Ones * createOnes(Type * const type = nullptr) {
89        return mParent->getAllOnesValue(type);
90    }
91
92    inline Call * createCall(Prototype * prototype, const std::vector<Var *> & args) {
93        return createCall(prototype, reinterpret_cast<const std::vector<PabloAST *> &>(args));
94    }
95
96    inline Call * createCall(Prototype * prototype, const std::vector<PabloAST *> & args) {
97        if (prototype == nullptr) {
98            throw std::runtime_error("Call object cannot be created with a Null prototype!");
99        }
100        if (args.size() != cast<Prototype>(prototype)->getNumOfParameters()) {
101            throw std::runtime_error("Invalid number of arguments passed into Call object!");
102        }
103        return createCall(static_cast<PabloAST *>(prototype), args);
104    }
105
106    Not * createNot(PabloAST * expr) {
107        return createNot(expr, nullptr);
108    }
109
110    Not * createNot(PabloAST * expr, const std::string & prefix) {
111        return createNot(expr, makeName(prefix));
112    }
113
114    Not * createNot(PabloAST * expr, String * const name);
115
116    inline Var * createVar(const std::string & name, Type * const type = nullptr) {
117        return createVar(makeName(name), type);
118    }
119
120    inline Var * createVar(String * name, Type * const type = nullptr) {
121        return createVar(cast<PabloAST>(name), type);
122    }
123
124    Count * createCount(PabloAST * expr);
125
126    Count * createCount(PabloAST * expr, const std::string & prefix);
127
128    InFile * createInFile(PabloAST * expr) {
129        return createInFile(expr, nullptr);
130    }
131
132    InFile * createInFile(PabloAST * expr, const std::string & prefix) {
133        return createInFile(expr, makeName(prefix));
134    }
135
136    InFile * createInFile(PabloAST * expr, String * const name);
137
138    AtEOF * createAtEOF(PabloAST * expr) {
139        return createAtEOF(expr, nullptr);
140    }
141
142    AtEOF * createAtEOF(PabloAST * expr, const std::string & prefix) {
143        return createAtEOF(expr, makeName(prefix));
144    }
145
146    AtEOF * createAtEOF(PabloAST * expr, String * const name);
147
148    Extract * createExtract(PabloAST * array, const Integer::Type index) {
149        return createExtract(array, getInteger(index), nullptr);
150    }
151
152    inline Extract * createExtract(PabloAST * array, PabloAST * index) {
153        return createExtract(array, index, nullptr);
154    }
155
156    Extract * createExtract(PabloAST * array, PabloAST * index, const std::string & prefix) {
157        return createExtract(array, index, makeName(prefix));
158    }
159
160    Extract * createExtract(PabloAST * array, const Integer::Type index, const std::string & prefix) {
161        return createExtract(array, getInteger(index), makeName(prefix));
162    }
163
164    Extract * createExtract(PabloAST * array, PabloAST * index, String * const name);
165
166    Assign * createAssign(PabloAST * const var, PabloAST * const value);
167
168    And * createAnd(PabloAST * expr1, PabloAST * expr2) {
169        return createAnd(expr1, expr2, nullptr);
170    }
171
172    And * createAnd(PabloAST * expr1, PabloAST * expr2, const std::string & prefix) {
173        return createAnd(expr1, expr2, nullptr);
174    }
175
176    And * createAnd(PabloAST * expr1, PabloAST * expr2, String * const name);
177
178    And * createAnd(Type * const type, const unsigned reserved) {
179        return createAnd(type, reserved, nullptr);
180    }
181
182    And * createAnd(Type * const type, const unsigned reserved, String * const name);
183
184    Or * createOr(PabloAST * expr1, PabloAST * expr2) {
185        return createOr(expr1, expr2, nullptr);
186    }
187
188    Or * createOr(PabloAST * expr1, PabloAST * expr2, const std::string & prefix) {
189        return createOr(expr1, expr2, makeName(prefix));
190    }
191
192    Or * createOr(PabloAST * expr1, PabloAST * expr2, String * const name);
193
194    Or * createOr(Type * const type, const unsigned reserved) {
195        return createOr(type, reserved, nullptr);
196    }
197
198    Or * createOr(Type * const type, const unsigned reserved, String * const name);
199
200    Xor * createXor(PabloAST * expr1, PabloAST * expr2) {
201        return createXor(expr1, expr2, nullptr);
202    }
203
204    Xor * createXor(PabloAST * expr1, PabloAST * expr2, const std::string & prefix) {
205        return createXor(expr1, expr2, makeName(prefix));
206    }
207
208    Xor * createXor(PabloAST * expr1, PabloAST * expr2, String * const name);
209
210    Xor * createXor(Type * const type, const unsigned reserved) {
211        return createXor(type, reserved, nullptr);
212    }
213
214    Xor * createXor(Type * const type, const unsigned reserved, String * const name);
215
216    MatchStar * createMatchStar(PabloAST * marker, PabloAST * charclass) {
217        return createMatchStar(marker, charclass, nullptr);
218    }
219
220    MatchStar * createMatchStar(PabloAST * marker, PabloAST * charclass, const std::string & prefix) {
221        return createMatchStar(marker, charclass, makeName(prefix));
222    }
223
224    MatchStar * createMatchStar(PabloAST * marker, PabloAST * charclass, String * const name);
225
226    ScanThru * createScanThru(PabloAST * from, PabloAST * thru) {
227        return createScanThru(from, thru, nullptr);
228    }
229
230    ScanThru * createScanThru(PabloAST * from, PabloAST * thru, const std::string & prefix) {
231        return createScanThru(from, thru, makeName(prefix));
232    }
233
234    ScanThru * createScanThru(PabloAST * from, PabloAST * thru, String * const name);
235
236    Sel * createSel(PabloAST * condition, PabloAST * trueExpr, PabloAST * falseExpr) {
237        return createSel(condition, trueExpr, falseExpr, nullptr);
238    }
239
240    Sel * createSel(PabloAST * condition, PabloAST * trueExpr, PabloAST * falseExpr, const std::string & prefix) {
241        return createSel(condition, trueExpr, falseExpr, makeName(prefix));
242    }
243
244    Sel * createSel(PabloAST * condition, PabloAST * trueExpr, PabloAST * falseExpr, String * const name);
245   
246    If * createIf(PabloAST * condition, PabloBlock * body);
247
248    While * createWhile(PabloAST * condition, PabloBlock * body);
249
250    inline PabloBlock * getPredecessor() const {
251        return getBranch() ? getBranch()->getParent() : nullptr;
252    }
253
254    inline PabloFunction * getParent() const {
255        return mParent;
256    }
257
258    void setParent(PabloFunction * const parent) {
259        mParent = parent;
260    }
261
262    void insert(Statement * const statement);
263
264    unsigned enumerateScopes(unsigned baseScopeIndex);
265   
266    inline unsigned getScopeIndex() const {
267        return mScopeIndex;
268    }
269   
270    void eraseFromParent(const bool recursively = false);
271
272    inline Branch * getBranch() const {
273        return mBranch;
274    }
275
276    inline void setBranch(Branch * const branch) {
277        mBranch = branch;
278    }
279
280    inline String * getName(const std::string name) const {
281        return getSymbolTable()->get(name);
282    }
283
284    inline String * makeName(const std::string & prefix) const {
285        return getSymbolTable()->make(prefix);
286    }
287
288    inline Integer * getInteger(Integer::Type value) const {
289        return getSymbolTable()->getInteger(value);
290    }
291
292    SymbolGenerator * getSymbolTable() const {
293        return mParent->getSymbolTable();
294    }
295
296    virtual ~PabloBlock();
297
298protected:
299
300    explicit PabloBlock(PabloFunction * parent) noexcept;
301
302    template<typename Type>
303    inline Type * insertAtInsertionPoint(Type * expr) {
304        if (isa<Statement>(expr)) {
305            insert(cast<Statement>(expr));
306        }
307        return expr;
308    }
309
310    Call * createCall(PabloAST * prototype, const std::vector<PabloAST *> &);
311
312    Var * createVar(PabloAST * name, Type * const type);
313
314private:       
315    PabloFunction *                                     mParent;
316    Branch *                                            mBranch;
317    unsigned                                            mScopeIndex;
318};
319
320}
321
322#endif // PS_PABLOS_H
Note: See TracBrowser for help on using the repository browser.