mirror of
https://git.savannah.gnu.org/git/bison.git
synced 2026-03-18 00:33:03 +00:00
Named symbol references.
Discussed in: http://lists.gnu.org/archive/html/bison-patches/2009-01/msg00000.html http://lists.gnu.org/archive/html/bison-patches/2009-02/msg00002.html http://lists.gnu.org/archive/html/bison-patches/2009-03/msg00009.html * src/parse-gram.y: Add new syntax (named_ref.opt). * src/reader.c: Store named refs in symbol lists. * src/reader.h: New argument for symbol_append and action_append functions. * src/scan-code.h: Add new field (named_ref) into code_props data structure. Keeps named ref of midrule actions. * src/scan-code.l: Support for named refs in semantic action code. New function 'parse_named_ref'. * src/scan-gram.l: Support bracketed id. * src/symlist.c: Store named refs in symbol lists. * src/symlist.h: New field in symbol list: named_ref. * src/named-ref.h: New file, a struct for named_ref. * src/named-ref.c: New file, named_ref_new function. * src/Makefile.am: Add two new files. * tests/testsuite.at: Include new test group: * tests/named-refs.at: this new file.
This commit is contained in:
103
src/scan-gram.l
103
src/scan-gram.l
@@ -55,9 +55,21 @@ static boundary scanner_cursor;
|
||||
static size_t no_cr_read (FILE *, char *, size_t);
|
||||
#define YY_INPUT(buf, result, size) ((result) = no_cr_read (yyin, buf, size))
|
||||
|
||||
#define ROLLBACK_CURRENT_TOKEN \
|
||||
do { \
|
||||
scanner_cursor.column -= mbsnwidth (yytext, yyleng, 0); \
|
||||
yyless (0); \
|
||||
} while (0)
|
||||
|
||||
/* A string representing the most recently saved token. */
|
||||
static char *last_string;
|
||||
|
||||
/* Bracketed identifier */
|
||||
static uniqstr bracketed_id_str = 0;
|
||||
static location bracketed_id_loc;
|
||||
static boundary bracketed_id_start;
|
||||
static int bracketed_id_context_state = 0;
|
||||
|
||||
void
|
||||
gram_scanner_last_string_free (void)
|
||||
{
|
||||
@@ -88,6 +100,8 @@ static void unexpected_newline (boundary, char const *);
|
||||
%x SC_COMMENT SC_LINE_COMMENT
|
||||
/* Strings and characters in code. */
|
||||
%x SC_STRING SC_CHARACTER
|
||||
/* Bracketed identifiers support */
|
||||
%x SC_BRACKETED_ID SC_RETURN_BRACKETED_ID
|
||||
|
||||
letter [-.abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ_]
|
||||
id {letter}({letter}|[0-9])*
|
||||
@@ -129,7 +143,7 @@ splice (\\[ \f\t\v]*\n)*
|
||||
| Scanning white space. |
|
||||
`-----------------------*/
|
||||
|
||||
<INITIAL,SC_AFTER_IDENTIFIER>
|
||||
<INITIAL,SC_AFTER_IDENTIFIER,SC_BRACKETED_ID,SC_RETURN_BRACKETED_ID>
|
||||
{
|
||||
/* Comments and white space. */
|
||||
"," warn_at (*loc, _("stray `,' treated as white space"));
|
||||
@@ -217,6 +231,7 @@ splice (\\[ \f\t\v]*\n)*
|
||||
{id} {
|
||||
val->uniqstr = uniqstr_new (yytext);
|
||||
id_loc = *loc;
|
||||
bracketed_id_str = NULL;
|
||||
BEGIN SC_AFTER_IDENTIFIER;
|
||||
}
|
||||
|
||||
@@ -268,6 +283,13 @@ splice (\\[ \f\t\v]*\n)*
|
||||
return PERCENT_PERCENT;
|
||||
}
|
||||
|
||||
"[" {
|
||||
bracketed_id_str = NULL;
|
||||
bracketed_id_start = loc->start;
|
||||
bracketed_id_context_state = YY_START;
|
||||
BEGIN SC_BRACKETED_ID;
|
||||
}
|
||||
|
||||
. {
|
||||
complain_at (*loc, _("invalid character: %s"), quote (yytext));
|
||||
}
|
||||
@@ -285,25 +307,94 @@ splice (\\[ \f\t\v]*\n)*
|
||||
|
||||
<SC_AFTER_IDENTIFIER>
|
||||
{
|
||||
"[" {
|
||||
if (!bracketed_id_str)
|
||||
{
|
||||
bracketed_id_start = loc->start;
|
||||
bracketed_id_context_state = YY_START;
|
||||
BEGIN SC_BRACKETED_ID;
|
||||
}
|
||||
else
|
||||
{
|
||||
ROLLBACK_CURRENT_TOKEN;
|
||||
BEGIN SC_RETURN_BRACKETED_ID;
|
||||
*loc = id_loc;
|
||||
return ID;
|
||||
}
|
||||
}
|
||||
":" {
|
||||
BEGIN (bracketed_id_str ? SC_RETURN_BRACKETED_ID : INITIAL);
|
||||
*loc = id_loc;
|
||||
BEGIN INITIAL;
|
||||
return ID_COLON;
|
||||
}
|
||||
. {
|
||||
scanner_cursor.column -= mbsnwidth (yytext, yyleng, 0);
|
||||
yyless (0);
|
||||
ROLLBACK_CURRENT_TOKEN;
|
||||
BEGIN (bracketed_id_str ? SC_RETURN_BRACKETED_ID : INITIAL);
|
||||
*loc = id_loc;
|
||||
BEGIN INITIAL;
|
||||
return ID;
|
||||
}
|
||||
<<EOF>> {
|
||||
BEGIN (bracketed_id_str ? SC_RETURN_BRACKETED_ID : INITIAL);
|
||||
*loc = id_loc;
|
||||
BEGIN INITIAL;
|
||||
return ID;
|
||||
}
|
||||
}
|
||||
|
||||
/*--------------------------------.
|
||||
| Scanning bracketed identifiers. |
|
||||
`--------------------------------*/
|
||||
|
||||
<SC_BRACKETED_ID>
|
||||
{
|
||||
{id} {
|
||||
if (!bracketed_id_str)
|
||||
{
|
||||
bracketed_id_str = uniqstr_new (yytext);
|
||||
bracketed_id_loc = *loc;
|
||||
}
|
||||
else
|
||||
{
|
||||
complain_at (*loc, _("redundant identifier in bracketed name: %s"),
|
||||
quote (yytext));
|
||||
}
|
||||
}
|
||||
"]" {
|
||||
BEGIN bracketed_id_context_state;
|
||||
if (bracketed_id_str)
|
||||
{
|
||||
if (INITIAL == bracketed_id_context_state)
|
||||
{
|
||||
val->uniqstr = bracketed_id_str;
|
||||
bracketed_id_str = 0;
|
||||
*loc = bracketed_id_loc;
|
||||
return BRACKETED_ID;
|
||||
}
|
||||
}
|
||||
else
|
||||
complain_at (*loc, _("a non empty identifier expected"));
|
||||
}
|
||||
. {
|
||||
complain_at (*loc, _("invalid character in bracketed name: %s"),
|
||||
quote (yytext));
|
||||
}
|
||||
<<EOF>> {
|
||||
BEGIN bracketed_id_context_state;
|
||||
unexpected_eof (bracketed_id_start, "]");
|
||||
}
|
||||
}
|
||||
|
||||
<SC_RETURN_BRACKETED_ID>
|
||||
{
|
||||
. {
|
||||
ROLLBACK_CURRENT_TOKEN;
|
||||
val->uniqstr = bracketed_id_str;
|
||||
bracketed_id_str = 0;
|
||||
*loc = bracketed_id_loc;
|
||||
BEGIN INITIAL;
|
||||
return BRACKETED_ID;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/*---------------------------------------------------------------.
|
||||
| Scanning a Yacc comment. The initial `/ *' is already eaten. |
|
||||
|
||||
Reference in New Issue
Block a user