summaryrefslogtreecommitdiff
path: root/src/bin/pgbench/exprscan.l
diff options
context:
space:
mode:
Diffstat (limited to 'src/bin/pgbench/exprscan.l')
-rw-r--r--src/bin/pgbench/exprscan.l83
1 files changed, 52 insertions, 31 deletions
diff --git a/src/bin/pgbench/exprscan.l b/src/bin/pgbench/exprscan.l
index fc7615f5585..00cb74d7dad 100644
--- a/src/bin/pgbench/exprscan.l
+++ b/src/bin/pgbench/exprscan.l
@@ -7,6 +7,8 @@
* Portions Copyright (c) 1996-2016, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
+ * src/bin/pgbench/exprscan.l
+ *
*-------------------------------------------------------------------------
*/
@@ -16,16 +18,27 @@ static int yyline = 0, yycol = 0;
/* Handles to the buffer that the lexer uses internally */
static YY_BUFFER_STATE scanbufhandle;
static char *scanbuf;
-static int scanbuflen;
/* context information for error reporting */
-static char *expr_source = NULL;
+static const char *expr_source = NULL;
static int expr_lineno = 0;
-static char *expr_full_line = NULL;
-static char *expr_command = NULL;
+static const char *expr_full_line = NULL;
+static const char *expr_command = NULL;
static int expr_col = 0;
+
+/*
+ * Work around a bug in flex 2.5.35: it emits a couple of functions that
+ * it forgets to emit declarations for. Since we use -Wmissing-prototypes,
+ * this would cause warnings. Providing our own declarations should be
+ * harmless even when the bug gets fixed.
+ */
+extern int expr_yyget_column(yyscan_t yyscanner);
+extern void expr_yyset_column(int column_no, yyscan_t yyscanner);
+
%}
+/* Except for the prefix, these options should match psqlscan.l */
+%option reentrant
%option 8bit
%option never-interactive
%option nodefault
@@ -42,6 +55,15 @@ space [ \t\r\f]
%%
+%{
+ /*
+ * Force flex into the appropriate start state ... which, for this
+ * case, is always INITIAL. This ensures that we can transition
+ * between different lexers sharing the same yyscan_t.
+ */
+ BEGIN(INITIAL);
+%}
+
"+" { yycol += yyleng; return '+'; }
"-" { yycol += yyleng; return '-'; }
"*" { yycol += yyleng; return '*'; }
@@ -69,77 +91,76 @@ space [ \t\r\f]
[\n] { yycol = 0; yyline++; }
-{space}+ { yycol += yyleng; /* ignore */ }
+{space}+ { yycol += yyleng; /* otherwise ignore */ }
. {
yycol += yyleng;
syntax_error(expr_source, expr_lineno, expr_full_line, expr_command,
"unexpected character", yytext, expr_col + yycol);
- /* dead code, exit is called from syntax_error */
- return CHAR_ERROR;
+ /* NOTREACHED, exit is called from syntax_error */
+ return 0;
}
%%
void
-expr_yyerror_more(const char *message, const char *more)
+expr_yyerror_more(yyscan_t yyscanner, const char *message, const char *more)
{
syntax_error(expr_source, expr_lineno, expr_full_line, expr_command,
message, more, expr_col + yycol);
}
void
-yyerror(const char *message)
+yyerror(yyscan_t yyscanner, const char *message)
{
- expr_yyerror_more(message, NULL);
+ expr_yyerror_more(yyscanner, message, NULL);
}
/*
* Called before any actual parsing is done
*/
-void
+yyscan_t
expr_scanner_init(const char *str, const char *source,
- const int lineno, const char *line,
- const char *cmd, const int ecol)
+ int lineno, const char *line,
+ const char *cmd, int ecol)
{
+ yyscan_t yyscanner;
Size slen = strlen(str);
- /* save context informations for error messages */
- expr_source = (char *) source;
- expr_lineno = (int) lineno;
- expr_full_line = (char *) line;
- expr_command = (char *) cmd;
- expr_col = (int) ecol;
+ /* Set up yyscan_t */
+ yylex_init(&yyscanner);
+
+ /* save context information for error messages */
+ expr_source = source;
+ expr_lineno = lineno;
+ expr_full_line = line;
+ expr_command = cmd;
+ expr_col = ecol;
/* reset error pointers for this scan */
yycol = yyline = 0;
/*
- * Might be left over after error
- */
- if (YY_CURRENT_BUFFER)
- yy_delete_buffer(YY_CURRENT_BUFFER);
-
- /*
* Make a scan buffer with special termination needed by flex.
*/
- scanbuflen = slen;
scanbuf = pg_malloc(slen + 2);
memcpy(scanbuf, str, slen);
scanbuf[slen] = scanbuf[slen + 1] = YY_END_OF_BUFFER_CHAR;
- scanbufhandle = yy_scan_buffer(scanbuf, slen + 2);
+ scanbufhandle = yy_scan_buffer(scanbuf, slen + 2, yyscanner);
- BEGIN(INITIAL);
+ return yyscanner;
}
/*
- * Called after parsing is done to clean up after seg_scanner_init()
+ * Called after parsing is done to clean up after expr_scanner_init()
*/
void
-expr_scanner_finish(void)
+expr_scanner_finish(yyscan_t yyscanner)
{
- yy_delete_buffer(scanbufhandle);
+ yy_delete_buffer(scanbufhandle, yyscanner);
pg_free(scanbuf);
+ yylex_destroy(yyscanner);
+
expr_source = NULL;
expr_lineno = 0;
expr_full_line = NULL;