]> git.tdb.fi Git - libs/gl.git/blob - source/glsl/generate.h
Further refactor the resolving process in SL::Compiler
[libs/gl.git] / source / glsl / generate.h
1 #ifndef MSP_GL_SL_GENERATE_H_
2 #define MSP_GL_SL_GENERATE_H_
3
4 #include <map>
5 #include <set>
6 #include <string>
7 #include <vector>
8 #include "visitor.h"
9
10 namespace Msp {
11 namespace GL {
12 namespace SL {
13
14 /** Combines multiple declarations of the same identifier into one. */
15 class DeclarationCombiner: private TraversingVisitor
16 {
17 private:
18         std::map<std::string, std::vector<FunctionDeclaration *> > functions;
19         std::map<std::string, VariableDeclaration *> variables;
20         std::set<Node *> nodes_to_remove;
21
22 public:
23         void apply(Stage &);
24
25 private:
26         virtual void visit(Block &);
27         virtual void visit(VariableDeclaration &);
28         virtual void visit(FunctionDeclaration &) { }
29 };
30
31 /** Manipulates specialization constants.  If values are specified, turns
32 specialization constants into normal constants.  Without values assigns
33 automatic constant_ids to specialization constants. */
34 class ConstantSpecializer: private TraversingVisitor
35 {
36 private:
37         const std::map<std::string, int> *values;
38
39 public:
40         ConstantSpecializer();
41
42         void apply(Stage &, const std::map<std::string, int> *);
43
44 private:
45         virtual void visit(VariableDeclaration &);
46 };
47
48 /** Forms links between nested blocks in the syntax tree. */
49 class BlockHierarchyResolver: private TraversingVisitor
50 {
51 private:
52         bool r_any_resolved;
53
54 public:
55         BlockHierarchyResolver(): r_any_resolved(false) { }
56
57         bool apply(Stage &s) { r_any_resolved = false; s.content.visit(*this); return r_any_resolved; }
58
59 private:
60         virtual void enter(Block &);
61 };
62
63 /** Resolves types of variables and base types of other types. */
64 class TypeResolver: private TraversingVisitor
65 {
66 private:
67         Stage *stage;
68         std::map<TypeDeclaration *, TypeDeclaration *> alias_map;
69         std::map<TypeDeclaration *, TypeDeclaration *> array_types;
70         NodeList<Statement>::iterator type_insert_point;
71         bool r_any_resolved;
72
73 public:
74         TypeResolver();
75
76         bool apply(Stage &);
77
78 private:
79         TypeDeclaration *get_or_create_array_type(TypeDeclaration &);
80         void resolve_type(TypeDeclaration *&, const std::string &, bool);
81         virtual void visit(Block &);
82         virtual void visit(BasicTypeDeclaration &);
83         virtual void visit(ImageTypeDeclaration &);
84         virtual void visit(StructDeclaration &);
85         virtual void visit(VariableDeclaration &);
86         virtual void visit(FunctionDeclaration &);
87 };
88
89 /** Resolves variable references.  Variable references which match the name
90 of an interface block are turned into interface block references. */
91 class VariableResolver: private TraversingVisitor
92 {
93 private:
94         Stage *stage;
95         RefPtr<Expression> r_replacement_expr;
96         std::string block_interface;
97         bool r_any_resolved;
98         bool record_target;
99         bool r_self_referencing;
100         VariableDeclaration *r_assignment_target;
101
102 public:
103         VariableResolver();
104
105         bool apply(Stage &);
106
107 private:
108         virtual void enter(Block &);
109         void visit_and_replace(RefPtr<Expression> &);
110         virtual void visit(VariableReference &);
111         virtual void visit(InterfaceBlockReference &);
112         virtual void visit(MemberAccess &);
113         virtual void visit(UnaryExpression &);
114         virtual void visit(BinaryExpression &);
115         virtual void visit(Assignment &);
116         virtual void visit(FunctionCall &);
117         virtual void visit(VariableDeclaration &);
118         virtual void visit(InterfaceBlock &);
119 };
120
121 /** Resolves types and lvalueness of expressions. */
122 class ExpressionResolver: private TraversingVisitor
123 {
124 private:
125         enum Compatibility
126         {
127                 NOT_COMPATIBLE,
128                 LEFT_CONVERTIBLE,
129                 RIGHT_CONVERTIBLE,
130                 SAME_TYPE
131         };
132
133         Stage *stage;
134         std::vector<BasicTypeDeclaration *> basic_types;
135         bool r_any_resolved;
136
137 public:
138         ExpressionResolver();
139
140         bool apply(Stage &);
141
142 private:
143         static bool is_scalar(BasicTypeDeclaration &);
144         static bool is_vector_or_matrix(BasicTypeDeclaration &);
145         static BasicTypeDeclaration *get_element_type(BasicTypeDeclaration &);
146         static bool can_convert(BasicTypeDeclaration &, BasicTypeDeclaration &);
147         static Compatibility get_compatibility(BasicTypeDeclaration &, BasicTypeDeclaration &);
148         BasicTypeDeclaration *find_type(BasicTypeDeclaration::Kind, unsigned);
149         BasicTypeDeclaration *find_type(BasicTypeDeclaration &, BasicTypeDeclaration::Kind, unsigned);
150         void convert_to(RefPtr<Expression> &, BasicTypeDeclaration &);
151         bool convert_to_element(RefPtr<Expression> &, BasicTypeDeclaration &);
152         void resolve(Expression &, TypeDeclaration *, bool);
153
154         virtual void visit(Literal &);
155         virtual void visit(ParenthesizedExpression &);
156         virtual void visit(VariableReference &);
157         virtual void visit(InterfaceBlockReference &);
158         virtual void visit(MemberAccess &);
159         virtual void visit(UnaryExpression &);
160         void visit(BinaryExpression &, bool);
161         virtual void visit(BinaryExpression &);
162         virtual void visit(Assignment &);
163         virtual void visit(FunctionCall &);
164         virtual void visit(BasicTypeDeclaration &);
165         virtual void visit(VariableDeclaration &);
166 };
167
168 /** Resolves function declarations and calls. */
169 class FunctionResolver: private TraversingVisitor
170 {
171 private:
172         Stage *stage;
173         std::map<std::string, std::vector<FunctionDeclaration *> > declarations;
174         bool r_any_resolved;
175
176 public:
177         bool apply(Stage &);
178
179 private:
180         virtual void visit(FunctionCall &);
181         virtual void visit(FunctionDeclaration &);
182 };
183
184 /** Materializes implicitly declared interfaces.
185
186 Out variable declarations inside functions are moved to the global scope.
187
188 Passthrough statements are processed, generating out variables to match in
189 variables and copying values.
190
191 Unresolved variables are looked up in the previous stage's out variables. */
192 class InterfaceGenerator: private TraversingVisitor
193 {
194 private:
195         Stage *stage;
196         std::string in_prefix;
197         std::string out_prefix;
198         bool function_scope;
199         InterfaceBlock *iface_block;
200         bool copy_block;
201         Block *iface_target_block;
202         NodeList<Statement>::iterator iface_insert_point;
203         NodeList<Statement>::iterator assignment_insert_point;
204         std::set<Node *> nodes_to_remove;
205
206 public:
207         InterfaceGenerator();
208
209         void apply(Stage &);
210
211 private:
212         static std::string get_out_prefix(Stage::Type);
213         std::string change_prefix(const std::string &, const std::string &) const;
214         virtual void visit(Block &);
215         VariableDeclaration *generate_interface(VariableDeclaration &, const std::string &, const std::string &);
216         InterfaceBlock *generate_interface(InterfaceBlock &);
217         ExpressionStatement &insert_assignment(const std::string &, Expression *);
218         virtual void visit(VariableReference &);
219         virtual void visit(VariableDeclaration &);
220         virtual void visit(InterfaceBlock &);
221         virtual void visit(FunctionDeclaration &);
222         virtual void visit(Passthrough &);
223 };
224
225 } // namespace SL
226 } // namespace GL
227 } // namespace Msp
228
229 #endif