tests: style: reorder the calculator test macros

* tests/local.at (AT_TOKEN_TRANSLATE_IF): New, moved from...
* tests/calc.at: here.
Instead of sorting per feature (main, yylex, calc.y) and then by
language, do the converse, so that C bits are together, etc.
This commit is contained in:
Akim Demaille
2020-09-27 12:16:31 +02:00
parent 15cf0095d3
commit c19c1e7ec5
2 changed files with 410 additions and 395 deletions

View File

@@ -19,16 +19,42 @@
## Compile the grammar described in the documentation. ## ## Compile the grammar described in the documentation. ##
## ---------------------------------------------------- ## ## ---------------------------------------------------- ##
# -------------- #
# AT_CALC_MAIN. #
# -------------- #
m4_pushdef([AT_CALC_MAIN], [AT_LANG_DISPATCH([$0], $@)]) m4_pushdef([AT_CALC_MAIN], [AT_LANG_DISPATCH([$0], $@)])
m4_pushdef([AT_CALC_YYLEX], [AT_LANG_DISPATCH([$0], $@)])
# Whether token translation is supported. # -------------- #
m4_pushdef([AT_TOKEN_TRANSLATE_IF], # AT_DATA_CALC. #
[AT_ERROR_CUSTOM_IF([$1], [AT_ERROR_DETAILED_IF([$1], [$2])])]) # -------------- #
# _AT_DATA_CALC_Y($1, $2, $3, [BISON-DIRECTIVES])
# -----------------------------------------------
# Produce 'calc.y' and, if %header was specified, 'calc-lex.c' or
# 'calc-lex.cc'.
#
# Don't call this macro directly, because it contains some occurrences
# of '$1' etc. which will be interpreted by m4. So you should call it
# with $1, $2, and $3 as arguments, which is what AT_DATA_CALC_Y does.
#
# When %header is not passed, generate a single self-contained file.
# Otherwise, generate three: calc.y with the parser, calc-lex.c with
# the scanner, and calc-main.c with "main()". This is in order to
# stress the use of the generated parser header. To avoid code
# duplication, AT_CALC_YYLEX and AT_CALC_MAIN contain the body of these
# two later files.
m4_pushdef([_AT_DATA_CALC_Y],
[m4_if([$1$2$3], $[1]$[2]$[3], [],
[m4_fatal([$0: Invalid arguments: $@])])dnl
AT_LANG_DISPATCH([$0], $@)])
## ----------- ##
## Calc in C. ##
## ----------- ##
# AT_CALC_MAIN(c).
m4_define([AT_CALC_MAIN(c)], m4_define([AT_CALC_MAIN(c)],
[[#include <assert.h> [[#include <assert.h>
#include <unistd.h> #include <unistd.h>
@@ -95,44 +121,8 @@ main (int argc, const char **argv)
} }
]]) ]])
m4_copy([AT_CALC_MAIN(c)], [AT_CALC_MAIN(c++)])
m4_define([AT_CALC_MAIN(d)],
[[int main (string[] args)
{]AT_PARAM_IF([[
semantic_value result = 0;
int count = 0;]])[
File input = args.length == 2 ? File (args[1], "r") : stdin;
auto l = calcLexer (input);
auto p = new YYParser (l);]AT_DEBUG_IF([[
p.setDebugLevel (1);]])[
return !p.parse ();
}
]])
m4_define([AT_CALC_MAIN(java)],
[[public static void main (String[] args) throws IOException
{]AT_LEXPARAM_IF([[
Calc p = new Calc (System.in);]], [[
CalcLexer l = new CalcLexer (System.in);
Calc p = new Calc (l);]])AT_DEBUG_IF([[
p.setDebugLevel (1);]])[
boolean success = p.parse ();
if (!success)
System.exit (1);
}
]])
# --------------- #
# AT_CALC_YYLEX. #
# --------------- #
m4_pushdef([AT_CALC_YYLEX], [AT_LANG_DISPATCH([$0], $@)])
# AT_CALC_YYLEX(c).
m4_define([AT_CALC_YYLEX(c)], m4_define([AT_CALC_YYLEX(c)],
[[#include <ctype.h> [[#include <ctype.h>
@@ -234,7 +224,266 @@ read_integer (]AT_YYLEX_FORMALS[)
} }
]]) ]])
m4_define([_AT_DATA_CALC_Y(c)],
[AT_DATA_GRAMMAR([calc.y],
[[/* Infix notation calculator--calc */
]$4[
%code requires
{
]AT_LOCATION_TYPE_SPAN_IF([[
typedef struct
{
int l;
int c;
} Point;
typedef struct
{
Point first;
Point last;
} Span;
# define YYLLOC_DEFAULT(Current, Rhs, N) \
do \
if (N) \
{ \
(Current).first = YYRHSLOC (Rhs, 1).first; \
(Current).last = YYRHSLOC (Rhs, N).last; \
} \
else \
{ \
(Current).first = (Current).last = YYRHSLOC (Rhs, 0).last; \
} \
while (0)
]AT_C_IF(
[[#include <stdio.h>
void location_print (FILE *o, Span s);
#define LOCATION_PRINT location_print
]])[
]])[
/* Exercise pre-prologue dependency to %union. */
typedef int semantic_value;
}
/* Exercise %union. */
%union
{
semantic_value ival;
};
%printer { ]AT_CXX_IF([[yyo << $$]],
[[fprintf (yyo, "%d", $$)]])[; } <ival>;
%code provides
{
#include <stdio.h>
/* The input. */
extern FILE *input;
extern semantic_value global_result;
extern int global_count;
extern int global_nerrs;
}
%code
{
#include <assert.h>
#include <string.h>
#define USE(Var)
FILE *input;
static int power (int base, int exponent);
]AT_YYERROR_DECLARE[
]AT_YYLEX_DECLARE_EXTERN[
]AT_TOKEN_TRANSLATE_IF([[
#define N_
static
const char *
_ (const char *cp)
{
if (strcmp (cp, "end of input") == 0)
return "end of file";
else if (strcmp (cp, "number") == 0)
return "nombre";
else
return cp;
}
]])[
}
]AT_LOCATION_TYPE_SPAN_IF([[
%initial-action
{
@$.first.l = @$.first.c = 1;
@$.last = @$.first;
}]])[
/* Bison Declarations */
%token CALC_EOF 0 ]AT_TOKEN_TRANSLATE_IF([_("end of input")], ["end of input"])[
%token <ival> NUM "number"
%type <ival> exp
%nonassoc '=' /* comparison */
%left '-' '+'
%left '*' '/'
%precedence NEG /* negation--unary minus */
%right '^' /* exponentiation */
/* Grammar follows */
%%
input:
line
| input line { ]AT_PARAM_IF([++*count; ++global_count;])[ }
;
line:
'\n'
| exp '\n' { ]AT_PARAM_IF([*result = global_result = $1;], [USE ($1);])[ }
;
exp:
NUM
| exp '=' exp
{
if ($1 != $3)]AT_LANG_CASE(
[c], [[
{
char buf[1024];
snprintf (buf, sizeof buf, "error: %d != %d", $1, $3);]AT_YYERROR_ARG_LOC_IF([[
yyerror (&@$, ]AT_PARAM_IF([result, count, nerrs, ])[buf);]], [[
{
YYLTYPE old_yylloc = yylloc;
yylloc = @$;
yyerror (]AT_PARAM_IF([result, count, nerrs, ])[buf);
yylloc = old_yylloc;
}
]])[
}]],
[c++], [[
{
char buf[1024];
snprintf (buf, sizeof buf, "error: %d != %d", $1, $3);
]AT_GLR_IF([[yyparser.]])[error (]AT_LOCATION_IF([[@$, ]])[buf);
}]])[
$$ = $1;
}
| exp '+' exp { $$ = $1 + $3; }
| exp '-' exp { $$ = $1 - $3; }
| exp '*' exp { $$ = $1 * $3; }
| exp '/' exp
{
if ($3 == 0)]AT_LANG_CASE(
[c], [[
{]AT_YYERROR_ARG_LOC_IF([[
yyerror (&@3, ]AT_PARAM_IF([result, count, nerrs, ])["error: null divisor");]], [[
{
YYLTYPE old_yylloc = yylloc;
yylloc = @3;
yyerror (]AT_PARAM_IF([result, count, nerrs, ])["error: null divisor");
yylloc = old_yylloc;
}
]])[
}]],
[c++], [[
{
]AT_GLR_IF([[yyparser.]])[error (]AT_LOCATION_IF([[@3, ]])["error: null divisor");
}]])[
else
$$ = $1 / $3;
}
| '-' exp %prec NEG { $$ = -$2; }
| exp '^' exp { $$ = power ($1, $3); }
| '(' exp ')' { $$ = $2; }
| '(' error ')' { $$ = 1111; yyerrok; }
| '!' { $$ = 0; YYERROR; }
| '-' error { $$ = 0; YYERROR; }
;
%%
int
power (int base, int exponent)
{
int res = 1;
assert (0 <= exponent);
for (/* Niente */; exponent; --exponent)
res *= base;
return res;
}
]AT_LOCATION_TYPE_SPAN_IF([AT_CXX_IF([[
#include <iostream>
namespace
{
std::ostream&
operator<< (std::ostream& o, const Span& s)
{
o << s.first.l << '.' << s.first.c;
if (s.first.l != s.last.l)
o << '-' << s.last.l << '.' << s.last.c - 1;
else if (s.first.c != s.last.c - 1)
o << '-' << s.last.c - 1;
return o;
}
}
]], [[
void
location_print (FILE *o, Span s)
{
fprintf (o, "%d.%d", s.first.l, s.first.c);
if (s.first.l != s.last.l)
fprintf (o, "-%d.%d", s.last.l, s.last.c - 1);
else if (s.first.c != s.last.c - 1)
fprintf (o, "-%d", s.last.c - 1);
}
]])])[
]AT_YYERROR_DEFINE[
]AT_HEADER_IF([],
[AT_CALC_YYLEX
AT_CALC_MAIN])])
AT_HEADER_IF([AT_DATA_SOURCE([[calc-lex.]AT_LANG_EXT],
[[#include "calc.]AT_LANG_HDR["
]AT_CALC_YYLEX])
AT_DATA_SOURCE([[calc-main.]AT_LANG_EXT],
[[#include "calc.]AT_LANG_HDR["
]AT_CALC_MAIN])
])
])# _AT_DATA_CALC_Y(c)
## ------------- ##
## Calc in C++. ##
## ------------- ##
m4_copy([AT_CALC_MAIN(c)], [AT_CALC_MAIN(c++)])
m4_copy([AT_CALC_YYLEX(c)], [AT_CALC_YYLEX(c++)]) m4_copy([AT_CALC_YYLEX(c)], [AT_CALC_YYLEX(c++)])
m4_copy([_AT_DATA_CALC_Y(c)], [_AT_DATA_CALC_Y(c++)])
## ----------- ##
## Calc in D. ##
## ----------- ##
# AT_CALC_MAIN(d).
m4_define([AT_CALC_MAIN(d)],
[[int main (string[] args)
{]AT_PARAM_IF([[
semantic_value result = 0;
int count = 0;]])[
File input = args.length == 2 ? File (args[1], "r") : stdin;
auto l = calcLexer (input);
auto p = new YYParser (l);]AT_DEBUG_IF([[
p.setDebugLevel (1);]])[
return !p.parse ();
}
]])
m4_define([AT_CALC_YYLEX(d)], m4_define([AT_CALC_YYLEX(d)],
[[import std.range.primitives; [[import std.range.primitives;
@@ -360,6 +609,114 @@ class CalcLexer(R) : Lexer
} }
]]) ]])
m4_define([_AT_DATA_CALC_Y(d)],
[AT_DATA_GRAMMAR([calc.y],
[[/* Infix notation calculator--calc */
]$4[
%code imports {
alias semantic_value = int;
}
/* Exercise %union. */
%union
{
semantic_value ival;
};
%printer { fprintf (yyo, "%d", $$); } <ival>;
/* Bison Declarations */
%token CALC_EOF 0 ]AT_TOKEN_TRANSLATE_IF([_("end of input")], ["end of input"])[
%token <ival> NUM "number"
%type <ival> exp
%token PLUS "+"
MINUS "-"
STAR "*"
SLASH "/"
LPAR "("
RPAR ")"
EQUAL "="
POW "^"
NOT "!"
EOL "\n"
%nonassoc "=" /* comparison */
%left "-" "+"
%left "*" "/"
%precedence NEG /* negation--unary minus */
%right "^" /* exponentiation */
/* Grammar follows */
%%
input:
line
| input line { ]AT_PARAM_IF([++*count; ++global_count;])[ }
;
line:
EOL
| exp EOL { ]AT_PARAM_IF([*result = global_result = $1;], [USE ($1);])[ }
;
exp:
NUM
| exp "=" exp
{
if ($1 != $3)
yyerror (]AT_LOCATION_IF([[@$, ]])[format ("error: %d != %d", $1, $3));
$$ = $1;
}
| exp "+" exp { $$ = $1 + $3; }
| exp "-" exp { $$ = $1 - $3; }
| exp "*" exp { $$ = $1 * $3; }
| exp "/" exp
{
if ($3 == 0)
yyerror (]AT_LOCATION_IF([[@3, ]])["error: null divisor");
else
$$ = $1 / $3;
}
| "-" exp %prec NEG { $$ = -$2; }
| exp "^" exp { $$ = power ($1, $3); }
| "(" exp ")" { $$ = $2; }
| "(" error ")" { $$ = 1111; yyerrok; }
| "!" { $$ = 0; return YYERROR; }
| "-" error { $$ = 0; return YYERROR; }
;
%%
int
power (int base, int exponent)
{
int res = 1;
assert (0 <= exponent);
for (/* Niente */; exponent; --exponent)
res *= base;
return res;
}
]AT_YYERROR_DEFINE[
]AT_CALC_YYLEX
AT_CALC_MAIN])
])# _AT_DATA_CALC_Y(d)
## -------------- ##
## Calc in Java. ##
## -------------- ##
m4_define([AT_CALC_MAIN(java)],
[[public static void main (String[] args) throws IOException
{]AT_LEXPARAM_IF([[
Calc p = new Calc (System.in);]], [[
CalcLexer l = new CalcLexer (System.in);
Calc p = new Calc (l);]])AT_DEBUG_IF([[
p.setDebugLevel (1);]])[
boolean success = p.parse ();
if (!success)
System.exit (1);
}
]])
m4_define([AT_CALC_YYLEX(java)], m4_define([AT_CALC_YYLEX(java)],
[AT_LEXPARAM_IF([[%code lexer {]], [AT_LEXPARAM_IF([[%code lexer {]],
@@ -427,357 +784,6 @@ m4_define([AT_CALC_YYLEX(java)],
}; };
]]) ]])
# -------------- #
# AT_DATA_CALC. #
# -------------- #
# _AT_DATA_CALC_Y($1, $2, $3, [BISON-DIRECTIVES])
# -----------------------------------------------
# Produce 'calc.y' and, if %header was specified, 'calc-lex.c' or
# 'calc-lex.cc'.
#
# Don't call this macro directly, because it contains some occurrences
# of '$1' etc. which will be interpreted by m4. So you should call it
# with $1, $2, and $3 as arguments, which is what AT_DATA_CALC_Y does.
#
# When %header is not passed, generate a single self-contained file.
# Otherwise, generate three: calc.y with the parser, calc-lex.c with
# the scanner, and calc-main.c with "main()". This is in order to
# stress the use of the generated parser header. To avoid code
# duplication, AT_CALC_YYLEX and AT_CALC_MAIN contain the body of these
# two later files.
m4_pushdef([_AT_DATA_CALC_Y],
[m4_if([$1$2$3], $[1]$[2]$[3], [],
[m4_fatal([$0: Invalid arguments: $@])])dnl
AT_LANG_DISPATCH([$0], $@)])
m4_define([_AT_DATA_CALC_Y(c)],
[AT_DATA_GRAMMAR([calc.y],
[[/* Infix notation calculator--calc */
]$4[
%code requires
{
]AT_LOCATION_TYPE_SPAN_IF([[
typedef struct
{
int l;
int c;
} Point;
typedef struct
{
Point first;
Point last;
} Span;
# define YYLLOC_DEFAULT(Current, Rhs, N) \
do \
if (N) \
{ \
(Current).first = YYRHSLOC (Rhs, 1).first; \
(Current).last = YYRHSLOC (Rhs, N).last; \
} \
else \
{ \
(Current).first = (Current).last = YYRHSLOC (Rhs, 0).last; \
} \
while (0)
]AT_C_IF(
[[#include <stdio.h>
void location_print (FILE *o, Span s);
#define LOCATION_PRINT location_print
]])[
]])[
/* Exercise pre-prologue dependency to %union. */
typedef int semantic_value;
}
/* Exercise %union. */
%union
{
semantic_value ival;
};
%printer { ]AT_CXX_IF([[yyo << $$]],
[[fprintf (yyo, "%d", $$)]])[; } <ival>;
]AT_LANG_MATCH([c\|c++], [[
%code provides
{
#include <stdio.h>
/* The input. */
extern FILE *input;
extern semantic_value global_result;
extern int global_count;
extern int global_nerrs;
}
%code
{
#include <assert.h>
#include <string.h>
#define USE(Var)
FILE *input;
static int power (int base, int exponent);
]AT_YYERROR_DECLARE[
]AT_YYLEX_DECLARE_EXTERN[
]AT_TOKEN_TRANSLATE_IF([[
#define N_
static
const char *
_ (const char *cp)
{
if (strcmp (cp, "end of input") == 0)
return "end of file";
else if (strcmp (cp, "number") == 0)
return "nombre";
else
return cp;
}
]])[
}
]])[
]AT_LOCATION_TYPE_SPAN_IF([[
%initial-action
{
@$.first.l = @$.first.c = 1;
@$.last = @$.first;
}]])[
/* Bison Declarations */
%token CALC_EOF 0 ]AT_TOKEN_TRANSLATE_IF([_("end of input")], ["end of input"])[
%token <ival> NUM "number"
%type <ival> exp
%nonassoc '=' /* comparison */
%left '-' '+'
%left '*' '/'
%precedence NEG /* negation--unary minus */
%right '^' /* exponentiation */
/* Grammar follows */
%%
input:
line
| input line { ]AT_PARAM_IF([++*count; ++global_count;])[ }
;
line:
'\n'
| exp '\n' { ]AT_PARAM_IF([*result = global_result = $1;], [AT_D_IF([], [USE ($1);])])[ }
;
exp:
NUM
| exp '=' exp
{
if ($1 != $3)]AT_LANG_CASE(
[c], [[
{
char buf[1024];
snprintf (buf, sizeof buf, "error: %d != %d", $1, $3);]AT_YYERROR_ARG_LOC_IF([[
yyerror (&@$, ]AT_PARAM_IF([result, count, nerrs, ])[buf);]], [[
{
YYLTYPE old_yylloc = yylloc;
yylloc = @$;
yyerror (]AT_PARAM_IF([result, count, nerrs, ])[buf);
yylloc = old_yylloc;
}
]])[
}]],
[c++], [[
{
char buf[1024];
snprintf (buf, sizeof buf, "error: %d != %d", $1, $3);
]AT_GLR_IF([[yyparser.]])[error (]AT_LOCATION_IF([[@$, ]])[buf);
}]])[
$$ = $1;
}
| exp '+' exp { $$ = $1 + $3; }
| exp '-' exp { $$ = $1 - $3; }
| exp '*' exp { $$ = $1 * $3; }
| exp '/' exp
{
if ($3 == 0)]AT_LANG_CASE(
[c], [[
{]AT_YYERROR_ARG_LOC_IF([[
yyerror (&@3, ]AT_PARAM_IF([result, count, nerrs, ])["error: null divisor");]], [[
{
YYLTYPE old_yylloc = yylloc;
yylloc = @3;
yyerror (]AT_PARAM_IF([result, count, nerrs, ])["error: null divisor");
yylloc = old_yylloc;
}
]])[
}]],
[c++], [[
{
]AT_GLR_IF([[yyparser.]])[error (]AT_LOCATION_IF([[@3, ]])["error: null divisor");
}]])[
else
$$ = $1 / $3;
}
| '-' exp %prec NEG { $$ = -$2; }
| exp '^' exp { $$ = power ($1, $3); }
| '(' exp ')' { $$ = $2; }
| '(' error ')' { $$ = 1111; yyerrok; }
| '!' { $$ = 0; YYERROR; }
| '-' error { $$ = 0; YYERROR; }
;
%%
int
power (int base, int exponent)
{
int res = 1;
assert (0 <= exponent);
for (/* Niente */; exponent; --exponent)
res *= base;
return res;
}
]AT_LOCATION_TYPE_SPAN_IF([AT_CXX_IF([[
#include <iostream>
namespace
{
std::ostream&
operator<< (std::ostream& o, const Span& s)
{
o << s.first.l << '.' << s.first.c;
if (s.first.l != s.last.l)
o << '-' << s.last.l << '.' << s.last.c - 1;
else if (s.first.c != s.last.c - 1)
o << '-' << s.last.c - 1;
return o;
}
}
]], [[
void
location_print (FILE *o, Span s)
{
fprintf (o, "%d.%d", s.first.l, s.first.c);
if (s.first.l != s.last.l)
fprintf (o, "-%d.%d", s.last.l, s.last.c - 1);
else if (s.first.c != s.last.c - 1)
fprintf (o, "-%d", s.last.c - 1);
}
]])])[
]AT_YYERROR_DEFINE[
]AT_HEADER_IF([],
[AT_CALC_YYLEX
AT_CALC_MAIN])])
AT_HEADER_IF([AT_DATA_SOURCE([[calc-lex.]AT_LANG_EXT],
[[#include "calc.]AT_LANG_HDR["
]AT_CALC_YYLEX])
AT_DATA_SOURCE([[calc-main.]AT_LANG_EXT],
[[#include "calc.]AT_LANG_HDR["
]AT_CALC_MAIN])
])
])# _AT_DATA_CALC_Y(c)
m4_copy([_AT_DATA_CALC_Y(c)], [_AT_DATA_CALC_Y(c++)])
m4_define([_AT_DATA_CALC_Y(d)],
[AT_DATA_GRAMMAR([calc.y],
[[/* Infix notation calculator--calc */
]$4[
%code imports {
alias semantic_value = int;
}
/* Exercise %union. */
%union
{
semantic_value ival;
};
%printer { fprintf (yyo, "%d", $$); } <ival>;
/* Bison Declarations */
%token CALC_EOF 0 ]AT_TOKEN_TRANSLATE_IF([_("end of input")], ["end of input"])[
%token <ival> NUM "number"
%type <ival> exp
%token PLUS "+"
MINUS "-"
STAR "*"
SLASH "/"
LPAR "("
RPAR ")"
EQUAL "="
POW "^"
NOT "!"
EOL "\n"
%nonassoc "=" /* comparison */
%left "-" "+"
%left "*" "/"
%precedence NEG /* negation--unary minus */
%right "^" /* exponentiation */
/* Grammar follows */
%%
input:
line
| input line { ]AT_PARAM_IF([++*count; ++global_count;])[ }
;
line:
EOL
| exp EOL { ]AT_PARAM_IF([*result = global_result = $1;], [AT_D_IF([], [USE ($1);])])[ }
;
exp:
NUM
| exp "=" exp
{
if ($1 != $3)
yyerror (]AT_LOCATION_IF([[@$, ]])[format ("error: %d != %d", $1, $3));
$$ = $1;
}
| exp "+" exp { $$ = $1 + $3; }
| exp "-" exp { $$ = $1 - $3; }
| exp "*" exp { $$ = $1 * $3; }
| exp "/" exp
{
if ($3 == 0)
yyerror (]AT_LOCATION_IF([[@3, ]])["error: null divisor");
else
$$ = $1 / $3;
}
| "-" exp %prec NEG { $$ = -$2; }
| exp "^" exp { $$ = power ($1, $3); }
| "(" exp ")" { $$ = $2; }
| "(" error ")" { $$ = 1111; ]AT_D_IF([], [yyerrok;])[ }
| "!" { $$ = 0; return YYERROR; }
| "-" error { $$ = 0; return YYERROR; }
;
%%
int
power (int base, int exponent)
{
int res = 1;
assert (0 <= exponent);
for (/* Niente */; exponent; --exponent)
res *= base;
return res;
}
]AT_YYERROR_DEFINE[
]AT_CALC_YYLEX
AT_CALC_MAIN])
])# _AT_DATA_CALC_Y(d)
m4_define([_AT_DATA_CALC_Y(java)], m4_define([_AT_DATA_CALC_Y(java)],
[AT_DATA_GRAMMAR([Calc.y], [AT_DATA_GRAMMAR([Calc.y],
[[/* Infix notation calculator--calc */ [[/* Infix notation calculator--calc */
@@ -868,6 +874,12 @@ exp:
## ------------------ ##
## Calculator tests. ##
## ------------------ ##
# AT_DATA_CALC_Y([BISON-OPTIONS]) # AT_DATA_CALC_Y([BISON-OPTIONS])
# ------------------------------- # -------------------------------
# Produce 'calc.y' and, if %header was specified, 'calc-lex.c' or # Produce 'calc.y' and, if %header was specified, 'calc-lex.c' or
@@ -877,7 +889,6 @@ m4_define([AT_DATA_CALC_Y],
]) ])
# _AT_CHECK_CALC(BISON-OPTIONS, INPUT, [STDOUT], [NUM-STDERR-LINES]) # _AT_CHECK_CALC(BISON-OPTIONS, INPUT, [STDOUT], [NUM-STDERR-LINES])
# ------------------------------------------------------------------ # ------------------------------------------------------------------
# Run 'calc' on INPUT and expect no STDOUT nor STDERR. # Run 'calc' on INPUT and expect no STDOUT nor STDERR.
@@ -1404,6 +1415,5 @@ AT_CHECK_CALC_LALR1_JAVA([%define parse.trace %define parse.error custom %locati
AT_CHECK_CALC_LALR1_JAVA([%define parse.trace %define parse.error verbose %locations %lex-param {InputStream is} %define api.push-pull both]) AT_CHECK_CALC_LALR1_JAVA([%define parse.trace %define parse.error verbose %locations %lex-param {InputStream is} %define api.push-pull both])
m4_popdef([AT_TOKEN_TRANSLATE_IF])
m4_popdef([AT_CALC_MAIN]) m4_popdef([AT_CALC_MAIN])
m4_popdef([AT_CALC_YYLEX]) m4_popdef([AT_CALC_YYLEX])

View File

@@ -340,6 +340,10 @@ m4_pushdef([AT_PURE_LEX_IF],
[AT_PURE_IF([$1], [AT_PURE_IF([$1],
[AT_CXX_IF([$1], [$2])])]) [AT_CXX_IF([$1], [$2])])])
# Whether token translation is supported.
m4_pushdef([AT_TOKEN_TRANSLATE_IF],
[AT_ERROR_CUSTOM_IF([$1], [AT_ERROR_DETAILED_IF([$1], [$2])])])
m4_pushdef([AT_YYSTYPE], m4_pushdef([AT_YYSTYPE],
[AT_CXX_IF([AT_NAMESPACE[::parser::semantic_type]], [AT_CXX_IF([AT_NAMESPACE[::parser::semantic_type]],
[AT_API_PREFIX[STYPE]])]) [AT_API_PREFIX[STYPE]])])
@@ -409,6 +413,7 @@ m4_popdef([AT_YYLTYPE])
m4_popdef([AT_YYSTYPE]) m4_popdef([AT_YYSTYPE])
m4_popdef([AT_VAL]) m4_popdef([AT_VAL])
m4_popdef([AT_LOC]) m4_popdef([AT_LOC])
m4_popdef([AT_TOKEN_TRANSLATE_IF])
m4_popdef([AT_PURE_LEX_IF]) m4_popdef([AT_PURE_LEX_IF])
m4_popdef([AT_YYERROR_SEES_LOC_IF]) m4_popdef([AT_YYERROR_SEES_LOC_IF])
m4_popdef([AT_YYERROR_ARG_LOC_IF]) m4_popdef([AT_YYERROR_ARG_LOC_IF])