]> git.tdb.fi Git - libs/gl.git/blobdiff - source/glsl/tokenizer.cpp
Recognize the #line directive in the GLSL parser
[libs/gl.git] / source / glsl / tokenizer.cpp
index e73afd5273add2dec2f907f223b2b1e5421b9f9d..b7efb8f8f9414d759c3cce3843593e14ae2a72e5 100644 (file)
@@ -11,12 +11,12 @@ namespace GL {
 namespace SL {
 
 Tokenizer::Tokenizer():
-       allow_preprocess(true)
+       allow_preprocess(true),
+       suppress_line_advance(false)
 {
        static string empty;
        iter = empty.begin();
        source_end = empty.end();
-       location.line = 0;
 }
 
 void Tokenizer::begin(const string &name, const string &src)
@@ -56,6 +56,11 @@ void Tokenizer::expect(const string &token)
                throw parse_error(location, parsed, format("'%s'", token));
 }
 
+void Tokenizer::set_location(const Location &loc)
+{
+       location = loc;
+}
+
 string Tokenizer::parse_token_()
 {
        while(1)
@@ -74,7 +79,9 @@ string Tokenizer::parse_token_()
                        return parse_identifier();
                else if(isdigit(*iter))
                        return parse_number();
-               else if(*iter=='"' || *iter=='#' || *iter=='$' || *iter=='\'' || *iter=='@' || *iter=='\\' || *iter=='`')
+               else if(*iter=='"')
+                       return parse_string();
+               else if(*iter=='#' || *iter=='$' || *iter=='\'' || *iter=='@' || *iter=='\\' || *iter=='`')
                        throw syntax_error(location, string(1, *iter), "Invalid character in source");
                else
                        return parse_other();
@@ -152,6 +159,25 @@ string Tokenizer::parse_number()
        return number;
 }
 
+string Tokenizer::parse_string()
+{
+       string str(1, *iter++);
+       bool escape = false;
+       while(iter!=source_end)
+       {
+               char c = *iter++;
+               str += c;
+               if(c=='\\')
+                       escape = true;
+               else if(c=='"' && !escape)
+                       break;
+               else
+                       escape = false;
+       }
+
+       return str;
+}
+
 string Tokenizer::parse_other()
 {
        if(iter==source_end)
@@ -219,12 +245,15 @@ void Tokenizer::skip_comment_and_whitespace()
 
                if(*iter=='\n')
                {
-                       ++location.line;
+                       if(!suppress_line_advance)
+                               ++location.line;
                        allow_preprocess = (comment<3);
                }
 
                ++iter;
        }
+
+       suppress_line_advance = false;
 }
 
 } // namespace SL