blob: 1a0052d689a30dac4587af9e593bb32ca3a18413 [file] [log] [blame]
Carl Worth3a37b872010-05-10 11:44:09 -07001%{
2/*
3 * Copyright © 2010 Intel Corporation
4 *
5 * Permission is hereby granted, free of charge, to any person obtaining a
6 * copy of this software and associated documentation files (the "Software"),
7 * to deal in the Software without restriction, including without limitation
8 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
9 * and/or sell copies of the Software, and to permit persons to whom the
10 * Software is furnished to do so, subject to the following conditions:
11 *
12 * The above copyright notice and this permission notice (including the next
13 * paragraph) shall be included in all copies or substantial portions of the
14 * Software.
15 *
16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
19 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
22 * DEALINGS IN THE SOFTWARE.
23 */
24
25#include <stdio.h>
26#include <string.h>
Kenneth Graunke7e908a62010-07-02 15:31:26 -070027#include <ctype.h>
Carl Worth3a37b872010-05-10 11:44:09 -070028
Carl Wortha1e32bc2010-05-10 13:17:25 -070029#include "glcpp.h"
Carl Worth3a37b872010-05-10 11:44:09 -070030#include "glcpp-parse.h"
Kenneth Graunkedb938102010-06-16 17:41:12 -070031
Carl Wortha9bb4bc2010-07-20 15:03:20 -070032/* Flex annoyingly generates some functions without making them
33 * static. Let's declare them here. */
34int glcpp_get_column (yyscan_t yyscanner);
35void glcpp_set_column (int column_no , yyscan_t yyscanner);
36
Carl Worthfb905602010-07-20 15:53:14 -070037#define YY_NO_INPUT
38
Kenneth Graunkedb938102010-06-16 17:41:12 -070039#define YY_USER_ACTION \
40 do { \
41 yylloc->source = 0; \
42 yylloc->first_column = yycolumn + 1; \
Kenneth Graunke8f322212010-06-18 15:23:50 -070043 yylloc->first_line = yylineno; \
Kenneth Graunkedb938102010-06-16 17:41:12 -070044 yycolumn += yyleng; \
45 } while(0);
Kenneth Graunke388ab9f2010-07-07 11:40:51 -070046#define YY_USER_INIT yylineno = 0; yycolumn = 0;
Carl Worth3a37b872010-05-10 11:44:09 -070047%}
48
Kenneth Graunke465e03e2010-06-16 16:35:57 -070049%option bison-bridge bison-locations reentrant noyywrap
Carl Worth5070a202010-05-12 12:45:33 -070050%option extra-type="glcpp_parser_t *"
Kenneth Graunke254a4852010-06-16 11:51:43 -070051%option prefix="glcpp_"
Kenneth Graunkedb938102010-06-16 17:41:12 -070052%option stack
Carl Worth3a37b872010-05-10 11:44:09 -070053
Carl Worthfb905602010-07-20 15:53:14 -070054%x DONE COMMENT UNREACHABLE
Kenneth Graunkef82d6732010-06-16 12:53:19 -070055
Carl Worth0b27b5f2010-05-10 16:16:06 -070056SPACE [[:space:]]
57NONSPACE [^[:space:]]
Carl Worth33cc4002010-05-12 12:17:10 -070058NEWLINE [\n]
Carl Worth0b27b5f2010-05-10 16:16:06 -070059HSPACE [ \t]
Carl Worthe36a4d52010-05-14 17:29:24 -070060HASH ^{HSPACE}*#{HSPACE}*
Carl Worth0b27b5f2010-05-10 16:16:06 -070061IDENTIFIER [_a-zA-Z][_a-zA-Z0-9]*
Carl Worth63101692010-05-29 05:07:24 -070062PUNCTUATION [][(){}.&*~!/%<>^|;,=+-]
Carl Worth3ff81672010-05-25 13:09:03 -070063OTHER [^][(){}.&*~!/%<>^|;,=#[:space:]+-]+
Carl Worth33cc4002010-05-12 12:17:10 -070064
Carl Worth03f6d5d2010-05-24 11:29:02 -070065DECIMAL_INTEGER [1-9][0-9]*[uU]?
66OCTAL_INTEGER 0[0-7]*[uU]?
67HEXADECIMAL_INTEGER 0[xX][0-9a-fA-F]+[uU]?
68
Carl Worth3a37b872010-05-10 11:44:09 -070069%%
70
Carl Worth25714152010-06-01 12:18:43 -070071 /* Single-line comments */
Kenneth Graunkee6ae7af2010-06-21 15:11:01 -070072"//"[^\n]*\n {
Kenneth Graunkedb938102010-06-16 17:41:12 -070073 yylineno++;
74 yycolumn = 0;
Carl Worth25714152010-06-01 12:18:43 -070075 return NEWLINE;
76}
77
78 /* Multi-line comments */
Kenneth Graunkedb938102010-06-16 17:41:12 -070079"/*" { yy_push_state(COMMENT, yyscanner); }
80<COMMENT>[^*\n]*
81<COMMENT>[^*\n]*\n { yylineno++; yycolumn = 0; }
82<COMMENT>"*"+[^*/\n]*
83<COMMENT>"*"+[^*/\n]*\n { yylineno++; yycolumn = 0; }
84<COMMENT>"*"+"/" {
85 yy_pop_state(yyscanner);
Carl Worth25714152010-06-01 12:18:43 -070086 if (yyextra->space_tokens)
87 return SPACE;
88}
89
Eric Anholtd4a04f32010-07-28 16:58:39 -070090{HASH}(version) {
Kenneth Graunke1ffc1cd2010-08-03 20:21:52 -070091 yylval->str = talloc_strdup (yyextra, yytext);
Eric Anholtd4a04f32010-07-28 16:58:39 -070092 yylineno++;
93 yycolumn = 0;
94 yyextra->space_tokens = 0;
95 return HASH_VERSION;
96}
97
Kenneth Graunke3b73ea32010-06-16 12:21:17 -070098 /* glcpp doesn't handle #extension, #version, or #pragma directives.
99 * Simply pass them through to the main compiler's lexer/parser. */
Eric Anholtd4a04f32010-07-28 16:58:39 -0700100{HASH}(extension|pragma)[^\n]+ {
Kenneth Graunke1ffc1cd2010-08-03 20:21:52 -0700101 yylval->str = talloc_strdup (yyextra, yytext);
Kenneth Graunke8f322212010-06-18 15:23:50 -0700102 yylineno++;
103 yycolumn = 0;
Kenneth Graunke3b73ea32010-06-16 12:21:17 -0700104 return OTHER;
105}
106
Kenneth Graunke77260fc2010-06-17 14:36:34 -0700107{HASH}ifdef/.*\n {
Carl Worth1d7e03e2010-07-20 14:13:32 -0700108 yyextra->lexing_if = 1;
Kenneth Graunke77260fc2010-06-17 14:36:34 -0700109 yyextra->space_tokens = 0;
110 return HASH_IFDEF;
111}
112
113{HASH}ifndef/.*\n {
Carl Worth1d7e03e2010-07-20 14:13:32 -0700114 yyextra->lexing_if = 1;
Kenneth Graunke77260fc2010-06-17 14:36:34 -0700115 yyextra->space_tokens = 0;
116 return HASH_IFNDEF;
117}
118
Carl Worth1d7e03e2010-07-20 14:13:32 -0700119{HASH}if/[^_a-zA-Z0-9].*\n {
Carl Wortha771a402010-06-01 11:20:18 -0700120 yyextra->lexing_if = 1;
121 yyextra->space_tokens = 0;
122 return HASH_IF;
123}
124
125{HASH}elif/.*\n {
126 yyextra->lexing_if = 1;
127 yyextra->space_tokens = 0;
128 return HASH_ELIF;
129}
130
131{HASH}else/.*\n {
132 yyextra->space_tokens = 0;
133 return HASH_ELSE;
134}
135
136{HASH}endif/.*\n {
137 yyextra->space_tokens = 0;
138 return HASH_ENDIF;
139}
140
141 /* When skipping (due to an #if 0 or similar) consume anything
Carl Worth1d7e03e2010-07-20 14:13:32 -0700142 * up to a newline. We do this with less priority than any
Carl Wortha771a402010-06-01 11:20:18 -0700143 * #if-related directive (#if, #elif, #else, #endif), but with
144 * more priority than any other directive or token to avoid
145 * any side-effects from skipped content.
146 *
147 * We use the lexing_if flag to avoid skipping any part of an
148 * if conditional expression. */
149[^\n]+/\n {
Kenneth Graunke8f322212010-06-18 15:23:50 -0700150 /* Since this rule always matches, YY_USER_ACTION gets called for it,
151 * wrongly incrementing yycolumn. We undo that effect here. */
152 yycolumn -= yyleng;
Carl Wortha771a402010-06-01 11:20:18 -0700153 if (yyextra->lexing_if ||
154 yyextra->skip_stack == NULL ||
155 yyextra->skip_stack->type == SKIP_NO_SKIP)
156 {
157 REJECT;
158 }
159}
160
Kenneth Graunke7e908a62010-07-02 15:31:26 -0700161{HASH}error.* {
162 char *p;
163 for (p = yytext; !isalpha(p[0]); p++); /* skip " # " */
164 p += 5; /* skip "error" */
165 glcpp_error(yylloc, yyextra, "#error%s", p);
166}
167
Carl Worth3ff81672010-05-25 13:09:03 -0700168{HASH}define{HSPACE}+/{IDENTIFIER}"(" {
Carl Worthf34a0002010-05-25 16:59:02 -0700169 yyextra->space_tokens = 0;
Carl Worth3ff81672010-05-25 13:09:03 -0700170 return HASH_DEFINE_FUNC;
Carl Worthb20d33c2010-05-20 22:27:07 -0700171}
172
Carl Worth3ff81672010-05-25 13:09:03 -0700173{HASH}define {
Carl Worthf34a0002010-05-25 16:59:02 -0700174 yyextra->space_tokens = 0;
Carl Worth3ff81672010-05-25 13:09:03 -0700175 return HASH_DEFINE_OBJ;
Carl Worthb20d33c2010-05-20 22:27:07 -0700176}
177
Carl Worth3ff81672010-05-25 13:09:03 -0700178{HASH}undef {
Carl Worthf34a0002010-05-25 16:59:02 -0700179 yyextra->space_tokens = 0;
Carl Worth3ff81672010-05-25 13:09:03 -0700180 return HASH_UNDEF;
Carl Worth03f6d5d2010-05-24 11:29:02 -0700181}
182
Carl Worth3ff81672010-05-25 13:09:03 -0700183{HASH} {
Carl Worthf34a0002010-05-25 16:59:02 -0700184 yyextra->space_tokens = 0;
Carl Worth3ff81672010-05-25 13:09:03 -0700185 return HASH;
Carl Worth81f01432010-05-14 17:08:45 -0700186}
187
Carl Worth8fed1cd2010-05-26 09:32:12 -0700188{DECIMAL_INTEGER} {
Kenneth Graunke1ffc1cd2010-08-03 20:21:52 -0700189 yylval->str = talloc_strdup (yyextra, yytext);
Carl Worth050e3de2010-05-27 14:36:29 -0700190 return INTEGER_STRING;
Carl Worth8fed1cd2010-05-26 09:32:12 -0700191}
192
193{OCTAL_INTEGER} {
Kenneth Graunke1ffc1cd2010-08-03 20:21:52 -0700194 yylval->str = talloc_strdup (yyextra, yytext);
Carl Worth050e3de2010-05-27 14:36:29 -0700195 return INTEGER_STRING;
Carl Worth8fed1cd2010-05-26 09:32:12 -0700196}
197
198{HEXADECIMAL_INTEGER} {
Kenneth Graunke1ffc1cd2010-08-03 20:21:52 -0700199 yylval->str = talloc_strdup (yyextra, yytext);
Carl Worth050e3de2010-05-27 14:36:29 -0700200 return INTEGER_STRING;
Carl Worth8fed1cd2010-05-26 09:32:12 -0700201}
202
Carl Worthf34a0002010-05-25 16:59:02 -0700203"<<" {
204 return LEFT_SHIFT;
Carl Worthb1854fd2010-05-25 16:28:26 -0700205}
206
Carl Worthf34a0002010-05-25 16:59:02 -0700207">>" {
208 return RIGHT_SHIFT;
Carl Worthb1854fd2010-05-25 16:28:26 -0700209}
210
Carl Worthf34a0002010-05-25 16:59:02 -0700211"<=" {
212 return LESS_OR_EQUAL;
213}
214
215">=" {
216 return GREATER_OR_EQUAL;
217}
218
219"==" {
220 return EQUAL;
221}
222
223"!=" {
224 return NOT_EQUAL;
225}
226
227"&&" {
228 return AND;
229}
230
231"||" {
232 return OR;
233}
234
235"##" {
236 return PASTE;
237}
238
Carl Worth8fed1cd2010-05-26 09:32:12 -0700239"defined" {
240 return DEFINED;
241}
242
Carl Worth16c1e982010-05-26 09:35:34 -0700243{IDENTIFIER} {
Kenneth Graunke1ffc1cd2010-08-03 20:21:52 -0700244 yylval->str = talloc_strdup (yyextra, yytext);
Carl Worth16c1e982010-05-26 09:35:34 -0700245 return IDENTIFIER;
246}
247
Carl Worthf34a0002010-05-25 16:59:02 -0700248{PUNCTUATION} {
249 return yytext[0];
Carl Worthb1854fd2010-05-25 16:28:26 -0700250}
251
Carl Worth9fb8b7a2010-05-25 15:04:32 -0700252{OTHER}+ {
Kenneth Graunke1ffc1cd2010-08-03 20:21:52 -0700253 yylval->str = talloc_strdup (yyextra, yytext);
Carl Worth9fb8b7a2010-05-25 15:04:32 -0700254 return OTHER;
Carl Worth3ff81672010-05-25 13:09:03 -0700255}
256
Carl Worth9fb8b7a2010-05-25 15:04:32 -0700257{HSPACE}+ {
Carl Worthf34a0002010-05-25 16:59:02 -0700258 if (yyextra->space_tokens) {
Carl Worthf34a0002010-05-25 16:59:02 -0700259 return SPACE;
260 }
Carl Worth0a93cbb2010-05-13 10:29:07 -0700261}
Carl Worthfcbbb462010-05-13 09:36:23 -0700262
Carl Worth3ff81672010-05-25 13:09:03 -0700263\n {
Carl Wortha771a402010-06-01 11:20:18 -0700264 yyextra->lexing_if = 0;
Kenneth Graunkedb938102010-06-16 17:41:12 -0700265 yylineno++;
266 yycolumn = 0;
Carl Worth3ff81672010-05-25 13:09:03 -0700267 return NEWLINE;
Carl Worth33cc4002010-05-12 12:17:10 -0700268}
Carl Worth3a37b872010-05-10 11:44:09 -0700269
Kenneth Graunkef82d6732010-06-16 12:53:19 -0700270 /* Handle missing newline at EOF. */
271<INITIAL><<EOF>> {
272 BEGIN DONE; /* Don't keep matching this rule forever. */
273 yyextra->lexing_if = 0;
274 return NEWLINE;
275}
276
Carl Worthfb905602010-07-20 15:53:14 -0700277 /* We don't actually use the UNREACHABLE start condition. We
278 only have this action here so that we can pretend to call some
279 generated functions, (to avoid "defined but not used"
280 warnings. */
281<UNREACHABLE>. {
282 unput('.');
283 yy_top_state(yyextra);
284}
285
Carl Worth3a37b872010-05-10 11:44:09 -0700286%%
Kenneth Graunke1b1f43e2010-06-16 12:01:17 -0700287
288void
289glcpp_lex_set_source_string(glcpp_parser_t *parser, const char *shader)
290{
291 yy_scan_string(shader, parser->scanner);
292}