1 | #pragma once |
---|---|
2 | |
3 | #ifndef _TRITON_IR_BASIC_BLOCK_H_ |
4 | #define _TRITON_IR_BASIC_BLOCK_H_ |
5 | |
6 | #include <string> |
7 | #include <list> |
8 | #include "value.h" |
9 | #include "visitor.h" |
10 | |
11 | namespace triton{ |
12 | namespace ir{ |
13 | |
14 | class context; |
15 | class function; |
16 | class instruction; |
17 | |
18 | /* Basic Block */ |
19 | class basic_block: public value{ |
20 | public: |
21 | // instruction iterator types |
22 | typedef std::list<instruction*> inst_list_t; |
23 | typedef inst_list_t::iterator iterator; |
24 | typedef inst_list_t::const_iterator const_iterator; |
25 | typedef inst_list_t::reverse_iterator reverse_iterator; |
26 | typedef inst_list_t::const_reverse_iterator const_reverse_iterator; |
27 | |
28 | private: |
29 | // constructors |
30 | basic_block(context &ctx, const std::string &name, function *parent, basic_block *next); |
31 | |
32 | public: |
33 | // accessors |
34 | function* get_parent() { return parent_; } |
35 | context& get_context() { return ctx_; } |
36 | |
37 | // get iterator to first instruction that is not a phi |
38 | void replace_phi_uses_with(basic_block* before, basic_block* after); |
39 | iterator get_first_non_phi(); |
40 | |
41 | // get instruction list |
42 | inst_list_t &get_inst_list() { return inst_list_; } |
43 | const inst_list_t &get_inst_list() const { return inst_list_; } |
44 | void erase(instruction *i) { inst_list_.remove(i); } |
45 | |
46 | // instruction iterator functions |
47 | inline iterator begin() { return inst_list_.begin(); } |
48 | inline const_iterator begin() const { return inst_list_.begin(); } |
49 | inline iterator end () { return inst_list_.end(); } |
50 | inline const_iterator end () const { return inst_list_.end(); } |
51 | |
52 | inline reverse_iterator rbegin() { return inst_list_.rbegin(); } |
53 | inline const_reverse_iterator rbegin() const { return inst_list_.rbegin(); } |
54 | inline reverse_iterator rend () { return inst_list_.rend(); } |
55 | inline const_reverse_iterator rend () const { return inst_list_.rend(); } |
56 | |
57 | inline size_t size() const { return inst_list_.size(); } |
58 | inline bool empty() const { return inst_list_.empty(); } |
59 | inline const instruction &front() const { return *inst_list_.front(); } |
60 | inline instruction &front() { return *inst_list_.front(); } |
61 | inline const instruction &back() const { return *inst_list_.back(); } |
62 | inline instruction &back() { return *inst_list_.back(); } |
63 | |
64 | void append_instruction(ir::instruction* i); |
65 | // split |
66 | basic_block* split_before(ir::instruction* loc, const std::string& name); |
67 | |
68 | // predecessors |
69 | std::vector<basic_block*> get_predecessors() const; |
70 | std::vector<basic_block*> get_successors() const; |
71 | |
72 | // factory functions |
73 | static basic_block* create(context &ctx, const std::string &name, function *parent, basic_block *next = nullptr); |
74 | |
75 | void print(std::ostream &os); |
76 | |
77 | // visitor |
78 | void accept(visitor *v) { v->visit_basic_block(this); } |
79 | |
80 | private: |
81 | context &ctx_; |
82 | std::string name_; |
83 | function *parent_; |
84 | std::vector<basic_block*> preds_; |
85 | std::vector<basic_block*> succs_; |
86 | inst_list_t inst_list_; |
87 | }; |
88 | |
89 | } |
90 | } |
91 | |
92 | #endif |
93 |