8
8
*
9
9
*
10
10
* IDENTIFICATION
11
- * $Header: /cvsroot/pgsql/src/backend/parser/scan.l,v 1.14 1997/08/20 01:50:06 vadim Exp $
11
+ * $Header: /cvsroot/pgsql/src/backend/parser/scan.l,v 1.15 1997/09/01 05:51:52 thomas Exp $
12
12
*
13
13
*-------------------------------------------------------------------------
14
14
*/
@@ -59,7 +59,42 @@ void unput(char);
59
59
#endif /* FLEX_SCANNER*/
60
60
61
61
extern YYSTYPE yylval;
62
+
63
+ int llen;
64
+ char literal[MAX_PARSE_BUFFER];
65
+
62
66
%}
67
+ /* OK, here is a short description of lex/flex rules behavior.
68
+ * The longest pattern which matches an input string is always chosen.
69
+ * For equal-length patterns, the first occurring in the rules list is chosen.
70
+ * INITIAL is the starting condition, to which all non-conditional rules apply.
71
+ * <xc> is an exclusive condition to allow embedded C-style comments.
72
+ * When in an exclusive condition, only those rules defined for that condition apply.
73
+ * So, when in condition <xc>, only strings which would terminate the "extended comment"
74
+ * trigger any action other than "ignore".
75
+ * The "extended comment" syntax closely resembles allowable operator syntax.
76
+ * Therefore, be sure to match _any_ candidate comment, including those with appended
77
+ * operator-like symbols. - thomas 1997-07-14
78
+ */
79
+
80
+ /* define an exclusive condition to allow extended C-style comments - tgl 1997-07-12 */
81
+ %x xc
82
+ /* define an exclusive condition for quoted strings - tgl 1997-07-30 */
83
+ %x xq
84
+
85
+ /* We used to allow double-quoted strings, but SQL doesn't so we won't either */
86
+ quote '
87
+ xqstart {quote }
88
+ xqstop {quote }
89
+ xqdouble {quote }{quote }
90
+ xqinside [^ \' ]*
91
+ xqliteral [\\ ].
92
+
93
+ xcline [\/ ][\* ]. * [\* ][\/ ]{space }* \n *
94
+ xcstart [\/ ][\* ]{op_and_self }*
95
+ xcstop {op_and_self }* [\* ][\/ ]({space }* | \n )
96
+ xcinside [^ * ]*
97
+ xcstar [^ / ]
63
98
64
99
digit [0 -9 ]
65
100
letter [_A -Za -z ]
@@ -69,15 +104,15 @@ sysfuncSYS_{letter}{letter_or_digit}*
69
104
70
105
identifier {letter }{letter_or_digit }*
71
106
107
+ typecast " ::"
108
+
72
109
self [,() \[\] .;$ \:\+\-\*\/\<\>\=\| ]
110
+ selfm {self }[\- ][\. 0 -9 ]
111
+
73
112
op_and_self [\~\!\@\#\%\^\&\|\`\?\$\:\+\-\*\/\<\>\= ]
74
- op_and_self2 [\~\!\@\#\%\^\&\|\`\?\$\:\*\/\<\>\= ]
75
- op_only [\~\!\@\#\%\^\&\`\? ]
76
113
77
- operator ({op_and_self }{op_and_self2 }+ )| {op_only }+
78
- /* we used to allow double-quoted strings, but SQL doesn't */
79
- /* so we won't either*/
80
- quote '
114
+ operator {op_and_self }+
115
+ operatorm {op_and_self }+ [\- ][\. 0 -9 ]
81
116
82
117
integer -? {digit }+
83
118
real -? {digit }+ \. {digit }+ ([Ee ][-+ ]? {digit }+ )?
@@ -97,10 +132,57 @@ other.
97
132
98
133
{comment }{/* ignore */ }
99
134
100
- " ::" {return TYPECAST;}
135
+ /* allow extended comments using C-style delimiters - tgl 1997-07-12 */
136
+ {xcline }{/* ignore */ }
137
+
138
+ <xc >{xcstar }|
139
+ {xcstart }{BEGIN (xc); }
101
140
102
- { self }{ return (yytext[ 0 ]); }
141
+ < xc >{ xcstop }{ BEGIN (INITIAL); }
103
142
143
+ <xc >{xcinside }{/* ignore */ }
144
+
145
+ {xqstart }{
146
+ BEGIN (xq);
147
+ llen =0 ;
148
+ *literal =' \0 ' ;
149
+ }
150
+ <xq >{xqstop }{
151
+ BEGIN (INITIAL);
152
+ yylval.str =pstrdup (scanstr (literal));
153
+ return (SCONST);
154
+ }
155
+ <xq >{xqdouble }|
156
+ <xq >{xqinside }{
157
+ if ((llen+yyleng) > (MAX_PARSE_BUFFER -1 )) {
158
+ elog (WARN," quoted string parse buffer of %d chars exceeded" ,MAX_PARSE_BUFFER);
159
+ /* not reached */
160
+ }
161
+ memcpy (literal+llen, yytext, yyleng+1 );
162
+ llen += yyleng;
163
+ }
164
+ <xq >{xqliteral }{
165
+ if ((llen+yyleng-1 ) > (MAX_PARSE_BUFFER -1 )) {
166
+ elog (WARN," quoted string parse buffer of %d chars exceeded" ,MAX_PARSE_BUFFER);
167
+ /* not reached */
168
+ }
169
+ memcpy (literal+llen, yytext+1 , yyleng);
170
+ llen += yyleng-1 ;
171
+ }
172
+
173
+ {typecast }{return TYPECAST; }
174
+
175
+ {selfm }{
176
+ yyless (yyleng-2 );
177
+ return (yytext[0 ]);
178
+ }
179
+ {self }{return (yytext[0 ]); }
180
+
181
+ {operatorm }{
182
+ yyless (yyleng-2 );
183
+ yylval.str =pstrdup ((char *)yytext);
184
+ return (Op);
185
+ }
104
186
{operator }{
105
187
if (strcmp ((char *)yytext," !=" ) ==0 )
106
188
yylval.str =pstrdup (" <>" );/* compatability */
@@ -124,49 +206,6 @@ other.
124
206
CheckFloat8Val (yylval.dval );
125
207
return (FCONST);
126
208
}
127
- {quote } {
128
- char literal[MAX_PARSE_BUFFER];
129
- int i =0 ;
130
- int c =0 ;
131
- /* quote_seen can be either \ or ' because
132
- we handle both cases of \' and '' for
133
- quoting quotes*/
134
- int quote_seen =0 ;
135
-
136
- while (i < MAX_PARSE_BUFFER -1 ) {
137
- c =input ();
138
- if (quote_seen !=0 ) {
139
- if (quote_seen ==' \' ' &&
140
- c !=' \' ' ) {
141
- /* a non-quote follows a single quote */
142
- /* so we've hit the end of the literal */
143
- if (c !=' \0 ' && c != EOF)
144
- unput (c);/* put back the extra char we read*/
145
- i = i -1 ;
146
- break ;/* break out of the while loop */
147
- }
148
- /* if we reach here, we're still in */
149
- /* the string literal */
150
- literal[i++] = c;
151
- quote_seen =0 ;
152
- continue ;
153
- }
154
- if (c ==' \0 ' || c == EOF) {
155
- elog (WARN," unterminated quoted string literal" );
156
- /* not reached */
157
- }
158
- literal[i++] = c;
159
- if (c ==' \' ' || c ==' \\ ' )
160
- quote_seen = c;
161
- }
162
- if ( i == MAX_PARSE_BUFFER -1 ) {
163
- elog (WARN," unterminated quote string. parse buffer of %d chars exceeded" , MAX_PARSE_BUFFER);
164
- /* not reached */
165
- }
166
- literal[i] =' \0 ' ;
167
- yylval.str =pstrdup (scanstr (literal));
168
- return (SCONST);
169
- }
170
209
{identifier }{
171
210
int i;
172
211
ScanKeyword*keyword;
@@ -177,19 +216,25 @@ other.
177
216
178
217
keyword =ScanKeywordLookup ((char *)yytext);
179
218
if (keyword !=NULL ) {
180
- if ( keyword->value == DEFAULT )
219
+ if ( keyword->value == DEFAULT ) {
181
220
DefaultStartPosition =CurScanPosition () + yyleng +1 ;
182
- else if ( keyword->value == CHECK )
221
+ printf (" default offset is %d\n " , DefaultStartPosition);
222
+
223
+ }else if ( keyword->value == CHECK ) {
183
224
CheckStartPosition =CurScanPosition () + yyleng +1 ;
225
+ printf (" check offset is %d\n " , CheckStartPosition);
226
+
227
+ };
228
+
184
229
return (keyword->value );
185
230
}else {
186
231
yylval.str =pstrdup ((char *)yytext);
187
232
return (IDENT);
188
233
}
189
234
}
190
- {space }{/* ignore */ }
235
+ {space }{/* ignore */ }
191
236
192
- {other }{return (yytext[0 ]); }
237
+ {other }{return (yytext[0 ]); }
193
238
194
239
%%
195
240
@@ -282,7 +327,12 @@ myinput(char* buf, int max)
282
327
int
283
328
CurScanPosition (void )
284
329
{
330
+ printf (" current position is %d\n " , yy_c_buf_p - yy_current_buffer->yy_ch_buf - yyleng);
331
+
332
+ return (parseCh - parseString - yyleng -1 );
333
+ #if FALSE
285
334
return (yy_c_buf_p - yy_current_buffer->yy_ch_buf - yyleng);
335
+ #endif
286
336
}
287
337
288
338
#endif /* FLEX_SCANNER */