]> git.tdb.fi Git - libs/gl.git/blob - source/glsl/generate.h
Refactor the way of applying visitors to stages
[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 class DeclarationCombiner: public BlockModifier
15 {
16 private:
17         bool toplevel;
18         std::map<std::string, std::vector<FunctionDeclaration *> > functions;
19         std::map<std::string, VariableDeclaration *> variables;
20
21 public:
22         DeclarationCombiner();
23
24         void apply(Stage &s) { visit(s.content); }
25
26         using BlockModifier::visit;
27         virtual void visit(Block &);
28         virtual void visit(FunctionDeclaration &);
29         virtual void visit(VariableDeclaration &);
30 };
31
32 class VariableResolver: public TraversingVisitor
33 {
34 private:
35         std::vector<Block *> blocks;
36         StructDeclaration *type;
37         bool anonymous;
38         std::string block_interface;
39         bool record_target;
40         VariableDeclaration *assignment_target;
41         bool self_referencing;
42
43 public:
44         VariableResolver();
45
46         void apply(Stage &);
47
48         using TraversingVisitor::visit;
49         virtual void visit(Block &);
50         virtual void visit(VariableReference &);
51         virtual void visit(MemberAccess &);
52         virtual void visit(BinaryExpression &);
53         virtual void visit(Assignment &);
54         virtual void visit(StructDeclaration &);
55         virtual void visit(VariableDeclaration &);
56         virtual void visit(InterfaceBlock &);
57 };
58
59 class FunctionResolver: public TraversingVisitor
60 {
61 private:
62         std::map<std::string, std::vector<FunctionDeclaration *> > functions;
63
64 public:
65         void apply(Stage &s) { visit(s.content); }
66
67         using TraversingVisitor::visit;
68         virtual void visit(FunctionCall &);
69         virtual void visit(FunctionDeclaration &);
70 };
71
72 class InterfaceGenerator: public BlockModifier
73 {
74 private:
75         Stage *stage;
76         std::string in_prefix;
77         std::string out_prefix;
78         unsigned scope_level;
79         std::map<std::string, RefPtr<VariableDeclaration> > iface_declarations;
80
81 public:
82         InterfaceGenerator();
83
84         void apply(Stage &);
85
86         static std::string get_out_prefix(Stage::Type);
87         using BlockModifier::visit;
88         virtual void visit(Block &);
89         std::string change_prefix(const std::string &, const std::string &) const;
90         bool generate_interface(VariableDeclaration &, const std::string &, const std::string &);
91         ExpressionStatement &insert_assignment(const std::string &, Expression *);
92         virtual void visit(VariableReference &);
93         virtual void visit(VariableDeclaration &);
94         virtual void visit(Passthrough &);
95 };
96
97 class DeclarationReorderer: public TraversingVisitor
98 {
99 private:
100         enum DeclarationKind
101         {
102                 NO_DECLARATION,
103                 LAYOUT,
104                 STRUCT,
105                 VARIABLE,
106                 FUNCTION
107         };
108
109         unsigned scope_level;
110         DeclarationKind kind;
111         std::set<Node *> ordered_funcs;
112         std::set<Node *> needed_funcs;
113
114 public:
115         DeclarationReorderer();
116
117         void apply(Stage &s) { visit(s.content); }
118
119         using TraversingVisitor::visit;
120         virtual void visit(Block &);
121         virtual void visit(FunctionCall &);
122         virtual void visit(InterfaceLayout &) { kind = LAYOUT; }
123         virtual void visit(StructDeclaration &) { kind = STRUCT; }
124         virtual void visit(VariableDeclaration &);
125         virtual void visit(InterfaceBlock &) { kind = VARIABLE; }
126         virtual void visit(FunctionDeclaration &);
127 };
128
129 } // namespace SL
130 } // namespace GL
131 } // namespace Msp
132
133 #endif