]> git.tdb.fi Git - libs/gl.git/blob - source/glsl/preprocessor.cpp
Follow the GLSL syntax rules more closely
[libs/gl.git] / source / glsl / preprocessor.cpp
1 #include "glsl_error.h"
2 #include "preprocessor.h"
3 #include "tokenizer.h"
4
5 using namespace std;
6
7 namespace Msp {
8 namespace GL {
9 namespace SL {
10
11 Preprocessor::Preprocessor(Tokenizer &t):
12         tokenizer(t)
13 { }
14
15 void Preprocessor::preprocess()
16 {
17         string token = tokenizer.peek_token();
18         if(token=="pragma")
19                 preprocess_pragma();
20         else if(token=="version")
21                 preprocess_version();
22         else if(token=="define" || token=="undef" || token=="if" || token=="ifdef" || token=="ifndef" || token=="else" ||
23                 token=="elif" || token=="endif" || token=="error" || token=="extension" || token=="line")
24                 throw invalid_shader_source(tokenizer.get_location(), "Unsupported preprocessor directive '%s'", token);
25         else if(!token.empty())
26                 throw parse_error(tokenizer.get_location(), token, "a preprocessor directive");
27 }
28
29 void Preprocessor::preprocess_version()
30 {
31         tokenizer.expect("version");
32         string token = tokenizer.parse_token();
33         unsigned version = lexical_cast<unsigned>(token);
34         signal_version.emit(Version(version/100, version%100));
35
36         token = tokenizer.parse_token();
37         if(!token.empty())
38                 throw parse_error(tokenizer.get_location(), token, "end of line");
39 }
40
41 void Preprocessor::preprocess_pragma()
42 {
43         tokenizer.expect("pragma");
44         string token = tokenizer.parse_token();
45         if(token=="MSP")
46                 preprocess_pragma_msp();
47 }
48
49 void Preprocessor::preprocess_pragma_msp()
50 {
51         string token = tokenizer.peek_token();
52         if(token=="stage")
53                 preprocess_stage();
54         else
55                 throw invalid_shader_source(tokenizer.get_location(), "Unrecognized MSP pragma '%s'", token);
56
57         token = tokenizer.parse_token();
58         if(!token.empty())
59                 throw parse_error(tokenizer.get_location(), token, "end of line");
60 }
61
62 void Preprocessor::preprocess_stage()
63 {
64         tokenizer.expect("stage");
65         tokenizer.expect("(");
66         string token = tokenizer.parse_token();
67         StageType stage = SHARED;
68         if(token=="vertex")
69                 stage = VERTEX;
70         else if(token=="geometry")
71                 stage = GEOMETRY;
72         else if(token=="fragment")
73                 stage = FRAGMENT;
74         else
75                 throw parse_error(tokenizer.get_location(), token, "stage identifier");
76         tokenizer.expect(")");
77
78         signal_stage_change.emit(stage);
79 }
80
81 } // namespace SL
82 } // namespace GL
83 } // namespace Msp