glsl: add preprocessor support for #pragma

Two forms are supported:

Pragmas are silently ignored at this time.
This commit is contained in:
Brian Paul
2009-01-13 15:06:52 -07:00
parent 1f47388dfe
commit 01a0938776
3 changed files with 74 additions and 1 deletions
@@ -79,6 +79,12 @@
.emtcode BEHAVIOR_WARN 3
.emtcode BEHAVIOR_DISABLE 4
/*
* The PRAGMA_* symbols follow TOKEN_PRAGMA
*/
.emtcode PRAGMA_NO_PARAM 0
.emtcode PRAGMA_PARAM 1
source
optional_directive .and .loop source_element .and '\0' .emit ESCAPE_TOKEN .emit TOKEN_END;
@@ -153,6 +159,7 @@ directive
dir_elif .emit TOKEN_ELIF .or
dir_endif .emit TOKEN_ENDIF .or
dir_ext .emit TOKEN_EXTENSION .or
dir_pragma .emit TOKEN_PRAGMA .or
dir_line .emit TOKEN_LINE;
dir_define
@@ -187,6 +194,19 @@ dir_ext
dir_line
optional_space .and '#' .and optional_space .and "line" .and expression;
dir_pragma
optional_space .and '#' .and optional_space .and "pragma" .and symbol .and opt_pragma_param;
opt_pragma_param
pragma_param .or .true .emit PRAGMA_NO_PARAM;
pragma_param
optional_space .and '(' .emit PRAGMA_PARAM .and optional_space .and symbol_no_space .and optional_space .and ')';
symbol_no_space
symbol_character .emit * .and .loop symbol_character2 .emit * .and .true .emit '\0';
symbol
space .and symbol_character .emit * .and .loop symbol_character2 .emit * .and .true .emit '\0';
@@ -20,6 +20,8 @@
".emtcode BEHAVIOR_ENABLE 2\n"
".emtcode BEHAVIOR_WARN 3\n"
".emtcode BEHAVIOR_DISABLE 4\n"
".emtcode PRAGMA_NO_PARAM 0\n"
".emtcode PRAGMA_PARAM 1\n"
"source\n"
" optional_directive .and .loop source_element .and '\\0' .emit ESCAPE_TOKEN .emit TOKEN_END;\n"
"source_element\n"
@@ -76,6 +78,7 @@
" dir_elif .emit TOKEN_ELIF .or\n"
" dir_endif .emit TOKEN_ENDIF .or\n"
" dir_ext .emit TOKEN_EXTENSION .or\n"
" dir_pragma .emit TOKEN_PRAGMA .or\n"
" dir_line .emit TOKEN_LINE;\n"
"dir_define\n"
" optional_space .and '#' .and optional_space .and \"define\" .and symbol .and opt_parameters .and\n"
@@ -99,6 +102,14 @@
" optional_space .and ':' .and optional_space .and extension_behavior;\n"
"dir_line\n"
" optional_space .and '#' .and optional_space .and \"line\" .and expression;\n"
"dir_pragma\n"
" optional_space .and '#' .and optional_space .and \"pragma\" .and symbol .and opt_pragma_param;\n"
"opt_pragma_param\n"
" pragma_param .or .true .emit PRAGMA_NO_PARAM;\n"
"pragma_param\n"
" optional_space .and '(' .emit PRAGMA_PARAM .and optional_space .and symbol_no_space .and optional_space .and ')';\n"
"symbol_no_space\n"
" symbol_character .emit * .and .loop symbol_character2 .emit * .and .true .emit '\\0';\n"
"symbol\n"
" space .and symbol_character .emit * .and .loop symbol_character2 .emit * .and .true .emit '\\0';\n"
"opt_parameters\n"
+43 -1
View File
@@ -51,6 +51,9 @@ grammar_error_to_log (slang_info_log *log)
GLint pos;
grammar_get_last_error ((byte *) (buf), sizeof (buf), &pos);
if (buf[0] == 0) {
_mesa_snprintf(buf, sizeof(buf), "Preprocessor error");
}
slang_info_log_error (log, buf);
}
@@ -528,6 +531,20 @@ pp_ext_set(pp_ext *self, const char *name, GLboolean enable)
}
/**
* Called in response to #pragma. For example, "#pragma debug(on)" would
* call this function as pp_pragma("debug", "on").
* At this time, pragmas are silently ignored.
*/
static void
pp_pragma(const char *pragma, const char *param)
{
#if 0
printf("#pragma %s %s\n", pragma, param);
#endif
}
/**
* The state of preprocessor: current line, file and version number, list
* of all defined macros and the #if/#endif context.
@@ -862,6 +879,10 @@ parse_if (slang_string *output, const byte *prod, GLuint *pi, GLint *result, pp_
#define BEHAVIOR_WARN 3
#define BEHAVIOR_DISABLE 4
#define PRAGMA_NO_PARAM 0
#define PRAGMA_PARAM 1
static GLboolean
preprocess_source (slang_string *output, const char *source,
grammar pid, grammar eid,
@@ -940,9 +961,11 @@ preprocess_source (slang_string *output, const char *source,
else {
const char *id;
GLuint idlen;
GLubyte token;
i++;
switch (prod[i++]) {
token = prod[i++];
switch (token) {
case TOKEN_END:
/* End of source string.
@@ -1159,6 +1182,25 @@ preprocess_source (slang_string *output, const char *source,
}
break;
case TOKEN_PRAGMA:
{
GLint have_param;
const char *pragma, *param;
pragma = (const char *) (&prod[i]);
i += _mesa_strlen(pragma) + 1;
have_param = (prod[i++] == PRAGMA_PARAM);
if (have_param) {
param = (const char *) (&prod[i]);
i += _mesa_strlen(param) + 1;
}
else {
param = NULL;
}
pp_pragma(pragma, param);
}
break;
case TOKEN_LINE:
id = (const char *) (&prod[i]);
i += _mesa_strlen (id) + 1;