1%{
2 #include "emp_ematch.yacc.h"
3 #include "m_ematch.h"
4
5 extern int ematch_argc;
6 extern char **ematch_argv;
7
8 #define yylval ematch_lval
9
10 #define NEXT_EM_ARG() do { ematch_argc--; ematch_argv++; } while(0);
11
12 #define YY_INPUT(buf, result, max_size)				\
13 {									\
14 next:									\
15 	if (ematch_argc <= 0)						\
16		result = YY_NULL;					\
17	else if (**ematch_argv == '\0') {				\
18		NEXT_EM_ARG();						\
19		goto next;						\
20	} else {							\
21		if (max_size <= strlen(*ematch_argv) + 1) {		\
22			fprintf(stderr, "match argument too long.\n");	\
23			result = YY_NULL;				\
24		} else {						\
25			strcpy(buf, *ematch_argv);			\
26			result = strlen(*ematch_argv) + 1;		\
27			buf[result-1] = ' ';				\
28			buf[result] = '\0';				\
29			NEXT_EM_ARG();					\
30		}							\
31	}								\
32 }
33
34 static void __attribute__ ((unused)) yyunput (int c,char *buf_ptr  );
35 static void __attribute__ ((unused)) yy_push_state (int  new_state );
36 static void __attribute__ ((unused)) yy_pop_state  (void);
37 static int  __attribute__ ((unused)) yy_top_state (void );
38
39 static char *strbuf;
40 static unsigned int strbuf_size;
41 static unsigned int strbuf_index;
42
43 static void strbuf_enlarge(void)
44 {
45 	strbuf_size += 512;
46 	strbuf = realloc(strbuf, strbuf_size);
47 }
48
49 static void strbuf_append_char(char c)
50 {
51 	while (strbuf_index >= strbuf_size)
52 		strbuf_enlarge();
53 	strbuf[strbuf_index++] = c;
54 }
55
56 static void strbuf_append_charp(char *s)
57 {
58 	while (strbuf_index >= strbuf_size)
59 		strbuf_enlarge();
60 	memcpy(strbuf + strbuf_index, s, strlen(s));
61 	strbuf_index += strlen(s);
62 }
63
64%}
65
66%x str
67
68%option 8bit stack warn noyywrap prefix="ematch_"
69%%
70[ \t\r\n]+
71
72\"					{
73						if (strbuf == NULL) {
74							strbuf_size = 512;
75							strbuf = calloc(1, strbuf_size);
76							if (strbuf == NULL)
77								return ERROR;
78						}
79						strbuf_index = 0;
80
81						BEGIN(str);
82					}
83
84<str>\"					{
85						BEGIN(INITIAL);
86						yylval.b = bstr_new(strbuf, strbuf_index);
87						yylval.b->quoted = 1;
88						return ATTRIBUTE;
89					}
90
91<str>\\[0-7]{1,3}			{ /* octal escape sequence */
92						int res;
93
94						sscanf(yytext + 1, "%o", &res);
95						if (res > 0xFF) {
96							fprintf(stderr, "error: octal escape sequence" \
97							" out of range\n");
98							return ERROR;
99						}
100						strbuf_append_char((unsigned char) res);
101					}
102
103<str>\\[0-9]+				{ /* catch wrong octal escape seq. */
104						fprintf(stderr, "error: invalid octale escape sequence\n");
105						return ERROR;
106					}
107
108<str>\\x[0-9a-fA-F]{1,2}		{
109						int res;
110
111						sscanf(yytext + 2, "%x", &res);
112
113						if (res > 0xFF) {
114							fprintf(stderr, "error: hexadecimal escape " \
115							"sequence out of range\n");
116							return ERROR;
117						}
118						strbuf_append_char((unsigned char) res);
119					}
120
121<str>\\n				strbuf_append_char('\n');
122<str>\\r				strbuf_append_char('\r');
123<str>\\t				strbuf_append_char('\t');
124<str>\\v				strbuf_append_char('\v');
125<str>\\b				strbuf_append_char('\b');
126<str>\\f				strbuf_append_char('\f');
127<str>\\a				strbuf_append_char('\a');
128
129<str>\\(.|\n)				strbuf_append_char(yytext[1]);
130<str>[^\\\n\"]+				strbuf_append_charp(yytext);
131
132[aA][nN][dD]				return AND;
133[oO][rR]				return OR;
134[nN][oO][tT]				return NOT;
135"("					|
136")"					{
137						return yylval.i = *yytext;
138					}
139[^ \t\r\n()]+				{
140						yylval.b = bstr_alloc(yytext);
141						if (yylval.b == NULL)
142							return ERROR;
143						return ATTRIBUTE;
144					}
145%%
146