source: icGREP/icgrep-devel/icgrep/pablo/pabloAST.h @ 4416

Last change on this file since 4416 was 4416, checked in by nmedfort, 5 years ago

Many use def info changes; removed dependency on boost system library. More work still needed on CSE.

File size: 11.4 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 PE_PabloAST_H
8#define PE_PabloAST_H
9
10#include <llvm/Support/Casting.h>
11#include <llvm/Support/Compiler.h>
12#include <llvm/ADT/SetVector.h>
13#include <slab_allocator.h>
14#include <iterator>
15#include <unordered_map>
16
17using namespace llvm;
18
19namespace pablo {
20
21class PabloBlock;
22
23class PMDNode;
24
25class PabloAST {
26    friend class PMDNode;
27    friend class Statement;
28    friend class Var;
29    friend class If;
30    friend class While;
31    friend class PabloBlock;
32    friend class SymbolGenerator;
33    typedef std::unordered_map<std::string, PMDNode *> PMDNodeMap;
34
35public:
36
37    using Users = SetVector<PabloAST *>;
38    using user_iterator = Users::iterator;
39
40    typedef SlabAllocator<4096> Allocator;
41    enum class ClassTypeId : unsigned {
42        Advance
43        , And
44        , Assign
45        , Call
46        , If
47        , Integer
48        , MatchStar
49        , Next
50        , Not
51        , Ones
52        , Or
53        , ScanThru
54        , Sel
55        , String
56        , Var
57        , While
58        , Xor
59        , Zeroes
60    };
61    inline ClassTypeId getClassTypeId() const {
62        return mClassTypeId;
63    }
64
65    void setMetadata(const std::string & name, PMDNode * node);
66
67    PMDNode * getMetadata(const std::string & name);
68
69    inline static void release_memory() {
70        mAllocator.release_memory();
71    }
72
73    inline user_iterator user_begin() const {
74        return mUsers.begin();
75    }
76
77    inline user_iterator user_end() const {
78        return mUsers.end();
79    }
80
81    inline Users & users() {
82        return mUsers;
83    }
84
85    inline const Users & users() const {
86        return mUsers;
87    }
88
89    void replaceAllUsesWith(PabloAST * expr);
90
91    inline Users::size_type getNumUses() const {
92        return mUsers.size();
93    }
94
95    void* operator new (std::size_t size) noexcept {
96        return mAllocator.allocate(size);
97    }
98protected:
99    inline PabloAST(const ClassTypeId id)
100    : mClassTypeId(id)
101    , mMetadataMap(nullptr)
102    {
103
104    }
105    inline void addUser(PabloAST * user) {       
106        mUsers.insert(user);
107    }
108    inline void removeUser(PabloAST * user) {
109        mUsers.remove(user);
110    }
111    static Allocator        mAllocator;
112private:
113    const ClassTypeId       mClassTypeId;
114    Users                   mUsers;
115    PMDNodeMap *            mMetadataMap;
116};
117
118bool equals(const PabloAST * expr1, const PabloAST *expr2);
119
120class StatementList;
121
122class String;
123
124class Statement : public PabloAST {
125    friend class StatementList;
126    friend class If;
127    friend class While;
128    friend class Simplifier;
129    friend class PabloBlock;
130public:
131    static inline bool classof(const PabloAST * e) {
132        switch (e->getClassTypeId()) {
133            case PabloAST::ClassTypeId::String:
134            case PabloAST::ClassTypeId::Integer:
135            case PabloAST::ClassTypeId::Zeroes:
136            case PabloAST::ClassTypeId::Ones:
137            case PabloAST::ClassTypeId::Var:
138                return false;
139            default:
140                return true;
141        }
142    }
143    static inline bool classof(const Statement *) {
144        return true;
145    }
146    static inline bool classof(const void *) {
147        return false;
148    }
149
150    inline void replaceUsesOfWith(PabloAST * from, PabloAST * to) {
151        for (unsigned i = 0; i != getNumOperands(); ++i) {
152            if (getOperand(i) == from) {
153                setOperand(i, to);
154            }
155        }
156    }
157
158    inline PabloAST * getOperand(const unsigned index) const {
159        assert (index < getNumOperands());
160        return mOperand[index];
161    }
162
163    void setOperand(const unsigned index, PabloAST * value);
164
165    inline unsigned getNumOperands() const {
166        return mOperand.size();
167    }
168
169    void insertBefore(Statement * const statement);
170    void insertAfter(Statement * const statement);
171    Statement * removeFromParent();
172    Statement * eraseFromParent(const bool recursively = false);
173    void replaceWith(PabloAST * const expr);
174
175    inline const String * getName() const {
176        return mName;
177    }
178    inline Statement * getNextNode() const {
179        return mNext;
180    }
181    inline Statement * getPrevNode() const {
182        return mPrev;
183    }
184    inline PabloBlock * getParent() const {
185        return mParent;
186    }
187protected:
188    Statement(const ClassTypeId id, std::vector<PabloAST *> && operands, const String * name, PabloBlock * parent)
189    : PabloAST(id)
190    , mName(name)
191    , mNext(nullptr)
192    , mPrev(nullptr)
193    , mParent(parent)
194    , mOperand(std::move(operands))
195    {
196        for (PabloAST * op : mOperand) {
197            op->addUser(this);
198        }
199    }
200    inline void setName(const String * name) {
201        mName = name;
202    }
203    virtual ~Statement() = 0;
204protected:
205    const String *              mName;
206    Statement *                 mNext;
207    Statement *                 mPrev;
208    PabloBlock *                mParent;
209    std::vector<PabloAST *>     mOperand;
210
211};
212
213class StatementList {
214    friend class Statement;
215public:
216    class iterator: public std::iterator<std::forward_iterator_tag, Statement> {
217    public:
218        iterator(): mCurrent(nullptr) {}
219
220        iterator(Statement* base): mCurrent(base) {}
221
222        iterator(const iterator& other): mCurrent(other.mCurrent) {}
223
224        const iterator& operator=(const iterator& other) {
225            mCurrent = other.mCurrent; return other;
226        }
227
228        inline iterator& operator++() {
229            assert (mCurrent);
230            mCurrent = mCurrent->mNext;
231            return *this;
232        }
233
234        iterator  operator++(int) {
235            iterator tmp(*this);
236            ++(*this);
237            return tmp;
238        }
239
240        bool operator==(const iterator& other) const {
241            return  mCurrent == other.mCurrent;
242        }
243
244        bool operator!=(const iterator& other) const {
245            return  mCurrent != other.mCurrent;
246        }
247
248        Statement* operator*() {return mCurrent;}
249        Statement* operator->(){return mCurrent;}
250
251    private:
252        Statement * mCurrent;
253        friend class const_iterator;
254    };
255
256    class const_iterator: public std::iterator<std::forward_iterator_tag, Statement> {
257    public:
258        const_iterator(): mCurrent(nullptr) {}
259        const_iterator(const Statement* base): mCurrent(base) {}
260        const_iterator(const const_iterator& other): mCurrent(other.mCurrent) {}
261        const const_iterator& operator=(const const_iterator& other) {mCurrent = other.mCurrent; return other;}
262
263        inline const_iterator& operator++() {
264            assert (mCurrent);
265            mCurrent = mCurrent->mNext;
266            return *this;
267        }
268
269        const_iterator  operator++(int) {
270            const_iterator tmp(*this);
271            ++(*this);
272            return tmp;
273        }
274
275        bool operator==(const const_iterator & other) const {
276            return  mCurrent == other.mCurrent;
277        }
278        bool operator!=(const const_iterator & other) const {
279            return  mCurrent != other.mCurrent;
280        }
281
282        const Statement* operator*() {return mCurrent;}
283        const Statement* operator->(){return mCurrent;}
284
285    private:
286        const Statement * mCurrent;
287        friend struct iterator;
288    };
289
290    class reverse_iterator: public std::iterator<std::forward_iterator_tag, Statement> {
291    public:
292        reverse_iterator(): mCurrent(nullptr) {}
293
294        reverse_iterator(Statement* base): mCurrent(base) {}
295
296        reverse_iterator(const reverse_iterator& other): mCurrent(other.mCurrent) {}
297
298        const reverse_iterator& operator=(const reverse_iterator& other) {
299            mCurrent = other.mCurrent; return other;
300        }
301
302        inline reverse_iterator& operator++() {
303            assert (mCurrent);
304            mCurrent = mCurrent->mPrev;
305            return *this;
306        }
307
308        reverse_iterator operator++(int) {
309            reverse_iterator tmp(*this);
310            ++(*this);
311            return tmp;
312        }
313
314        bool operator==(const reverse_iterator& other) const {
315            return  mCurrent == other.mCurrent;
316        }
317
318        bool operator!=(const reverse_iterator& other) const {
319            return  mCurrent != other.mCurrent;
320        }
321
322        Statement* operator*() {return mCurrent;}
323        Statement* operator->(){return mCurrent;}
324
325    private:
326        Statement * mCurrent;
327        friend class const_reverse_iterator;
328    };
329
330    class const_reverse_iterator: public std::iterator<std::forward_iterator_tag, Statement> {
331    public:
332        const_reverse_iterator(): mCurrent(nullptr) {}
333        const_reverse_iterator(const Statement* base): mCurrent(base) {}
334        const_reverse_iterator(const const_reverse_iterator& other): mCurrent(other.mCurrent) {}
335        const const_reverse_iterator& operator=(const const_reverse_iterator& other) {mCurrent = other.mCurrent; return other;}
336
337        inline const_reverse_iterator& operator++() {
338            assert (mCurrent);
339            mCurrent = mCurrent->mPrev;
340            return *this;
341        }
342
343        const_reverse_iterator  operator++(int) {
344            const_reverse_iterator tmp(*this);
345            ++(*this);
346            return tmp;
347        }
348
349        bool operator==(const const_reverse_iterator & other) const {
350            return  mCurrent == other.mCurrent;
351        }
352        bool operator!=(const const_reverse_iterator & other) const {
353            return  mCurrent != other.mCurrent;
354        }
355
356        const Statement* operator*() {return mCurrent;}
357        const Statement* operator->(){return mCurrent;}
358
359    private:
360        const Statement * mCurrent;
361        friend struct iterator;
362    };
363
364public:
365
366    StatementList()
367    : mInsertionPoint(nullptr)
368    , mFirst(nullptr)
369    , mLast(nullptr)
370    {
371
372    }
373
374    StatementList(StatementList && other)
375    : mFirst(other.mFirst)
376    , mLast(other.mLast)
377    {
378        other.mFirst = nullptr;
379        other.mLast = nullptr;
380    }
381
382    iterator begin() {
383        return iterator(mFirst);
384    }
385
386    iterator end() {
387        return iterator(nullptr);
388    }
389
390    reverse_iterator rbegin() {
391        return reverse_iterator(mLast);
392    }
393
394    reverse_iterator rend() {
395        return reverse_iterator(nullptr);
396    }
397
398    const_iterator begin() const {
399        return const_iterator(mFirst);
400    }
401
402    const_iterator end() const {
403        return const_iterator(nullptr);
404    }
405
406    const_reverse_iterator rbegin() const {
407        return const_reverse_iterator(mLast);
408    }
409
410    const_reverse_iterator rend() const {
411        return const_reverse_iterator(nullptr);
412    }
413
414    const_iterator cbegin() const {
415        return const_iterator(mFirst);
416    }
417
418    const_iterator cend() const {
419        return const_iterator(nullptr);
420    }
421
422    const_reverse_iterator crbegin() const {
423        return const_reverse_iterator(mLast);
424    }
425
426    const_reverse_iterator crend() const {
427        return const_reverse_iterator(nullptr);
428    }
429
430    inline Statement * front() const {
431        return mFirst;
432    }
433
434    inline Statement * back() const {
435        return mLast;
436    }
437
438    inline void setInsertPoint(Statement * const statement) {
439        mInsertionPoint = statement;
440    }
441
442    inline void setInsertPoint(StatementList * const list) {
443        mInsertionPoint = list->back();
444    }
445
446    inline Statement * getInsertPoint() const {
447        return mInsertionPoint;
448    }
449
450    void insert(Statement * const statement);
451
452private:
453
454    Statement   * mInsertionPoint;
455    Statement   * mFirst;
456    Statement   * mLast;   
457};
458
459}
460
461#endif // PE_PabloAST_H
462
463
464
Note: See TracBrowser for help on using the repository browser.