1
0
mirror of https://github.com/postgres/postgres.git synced 2025-09-03 15:22:11 +03:00

Tweak the core scanner so that it can be used by plpgsql too.

Changes:

Pass in the keyword lookup array instead of having it be hardwired.
(This incidentally allows elimination of some duplicate coding in ecpg.)

Re-order the token declarations in gram.y so that non-keyword tokens have
numbers that won't change when keywords are added or removed.

Add ".." and ":=" to the set of tokens recognized by scan.l.  (Since these
combinations are nowhere legal in core SQL, this does not change anything
except the precise wording of the error you get when you write this.)
This commit is contained in:
Tom Lane
2009-07-14 20:24:10 +00:00
parent 0d4899e448
commit 1aa58d3a83
15 changed files with 139 additions and 116 deletions

View File

@@ -24,7 +24,7 @@
* Portions Copyright (c) 1994, Regents of the University of California
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/parser/scan.l,v 1.156 2009/07/13 03:11:12 tgl Exp $
* $PostgreSQL: pgsql/src/backend/parser/scan.l,v 1.157 2009/07/14 20:24:10 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -304,6 +304,10 @@ identifier {ident_start}{ident_cont}*
typecast "::"
/* these two token types are used by PL/pgsql, though not in core SQL */
dot_dot \.\.
colon_equals ":="
/*
* "self" is the set of chars that should be returned as single-character
* tokens. "op_chars" is the set of chars that can make up "Op" tokens,
@@ -450,11 +454,21 @@ other .
SET_YYLLOC();
yyless(1); /* eat only 'n' this time */
/* nchar had better be a keyword! */
keyword = ScanKeywordLookup("nchar");
Assert(keyword != NULL);
yylval->keyword = keyword->name;
return keyword->value;
keyword = ScanKeywordLookup("nchar",
yyextra->keywords,
yyextra->num_keywords);
if (keyword != NULL)
{
yylval->keyword = keyword->name;
return keyword->value;
}
else
{
/* If NCHAR isn't a keyword, just return "n" */
yylval->str = pstrdup("n");
return IDENT;
}
}
{xqstart} {
@@ -680,6 +694,16 @@ other .
return TYPECAST;
}
{dot_dot} {
SET_YYLLOC();
return DOT_DOT;
}
{colon_equals} {
SET_YYLLOC();
return COLON_EQUALS;
}
{self} {
SET_YYLLOC();
return yytext[0];
@@ -830,7 +854,9 @@ other .
SET_YYLLOC();
/* Is it a keyword? */
keyword = ScanKeywordLookup(yytext);
keyword = ScanKeywordLookup(yytext,
yyextra->keywords,
yyextra->num_keywords);
if (keyword != NULL)
{
yylval->keyword = keyword->name;
@@ -939,7 +965,10 @@ scanner_yyerror(const char *message, base_yyscan_t yyscanner)
* Called before any actual parsing is done
*/
base_yyscan_t
scanner_init(const char *str, base_yy_extra_type *yyext)
scanner_init(const char *str,
base_yy_extra_type *yyext,
const ScanKeyword *keywords,
int num_keywords)
{
Size slen = strlen(str);
yyscan_t scanner;
@@ -949,6 +978,9 @@ scanner_init(const char *str, base_yy_extra_type *yyext)
base_yyset_extra(yyext, scanner);
yyext->keywords = keywords;
yyext->num_keywords = num_keywords;
/*
* Make a scan buffer with special termination needed by flex.
*/