bison-patches
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[PATCH 5/7] c++: add support for parse.error=custom


From: Akim Demaille
Subject: [PATCH 5/7] c++: add support for parse.error=custom
Date: Fri, 28 Feb 2020 06:32:17 +0100

From: Adrian Vogelsgesang <address@hidden>

* data/skeletons/lalr1.cc: added support here
* tests/calc.at: added test cases
* tests/local.at: added yyreport_syntax_error implementation
   for C++ test cases
---
 data/skeletons/lalr1.cc | 16 ++++++++++++----
 tests/calc.at           |  3 +++
 tests/local.at          | 29 +++++++++++++++++++++++++++--
 3 files changed, 42 insertions(+), 6 deletions(-)

diff --git a/data/skeletons/lalr1.cc b/data/skeletons/lalr1.cc
index 5928f72c..8896a95d 100644
--- a/data/skeletons/lalr1.cc
+++ b/data/skeletons/lalr1.cc
@@ -243,7 +243,7 @@ m4_define([b4_shared_declarations],
           , yyla (yyla)
           {}
 ]b4_locations_if([[
-        const location_type& get_location () const { return yyla.location; }
+        const location_type& location () const { return yyla.location; }
 ]])[
         /* Put in YYARG at most YYARGN of the expected tokens, and return the
            number of tokens stored in YYARG.  If YYARG is null, return the
@@ -279,6 +279,10 @@ m4_define([b4_shared_declarations],
     /// Generate an error message.
     /// \param yyctx     the context in which the error occurred.
     virtual std::string yysyntax_error_ (const context& yyctx) const;
+]])b4_parse_error_bmatch([custom], [[
+    /// Report a syntax error
+    /// \param yyctx     the context in which the error occurred.
+    void yyreport_syntax_error (const context& yyctx) const;
 ]])[
     /// Compute post-reduction state.
     /// \param yystate   the current state
@@ -1071,11 +1075,15 @@ b4_dollar_popdef])[]dnl
       {
         ++yynerrs_;]b4_parse_error_case(
                   [simple], [[
-        std::string msg = YY_("syntax error");]],
+        std::string msg = YY_("syntax error");
+        error (]b4_join(b4_locations_if([yyla.location]), [[YY_MOVE 
(msg)]])[);]],
+                  [custom], [[
+        context yyctx (*this, yyla);
+        yyreport_syntax_error (yyctx);]],
                   [[
         context yyctx (*this, yyla);
-        std::string msg = yysyntax_error_ (yyctx);]])[
-        error (]b4_join(b4_locations_if([yyla.location]), [[YY_MOVE (msg)]])[);
+        std::string msg = yysyntax_error_ (yyctx);
+        error (]b4_join(b4_locations_if([yyla.location]), [[YY_MOVE 
(msg)]])[);]])[
       }
 
 ]b4_locations_if([[
diff --git a/tests/calc.at b/tests/calc.at
index 8b215c5b..401c5ffa 100644
--- a/tests/calc.at
+++ b/tests/calc.at
@@ -1138,6 +1138,9 @@ AT_CHECK_CALC_LALR1_CC([%no-lines %defines %locations 
%define api.location.file
 AT_CHECK_CALC_LALR1_CC([%locations %define parse.lac full %define parse.error 
verbose])
 AT_CHECK_CALC_LALR1_CC([%locations %define parse.lac full %define parse.error 
detailed])
 
+AT_CHECK_CALC_LALR1_CC([%define parse.error custom])
+AT_CHECK_CALC_LALR1_CC([%define parse.error custom %locations %define 
api.prefix {calc} %parse-param {semantic_value *result}{int *count}{int 
*nerrs}])
+AT_CHECK_CALC_LALR1_CC([%define parse.error custom %locations %define 
api.prefix {calc} %parse-param {semantic_value *result}{int *count}{int *nerrs} 
%define parse.lac full])
 
 # -------------------- #
 # GLR C++ Calculator.  #
diff --git a/tests/local.at b/tests/local.at
index 0dffe4cc..d824e36c 100644
--- a/tests/local.at
+++ b/tests/local.at
@@ -733,10 +733,35 @@ void
   ++global_nerrs;
   ++*nerrs;]])[
   std::cerr << ]AT_LOCATION_IF([l << ": " << ])[m << '\n';
-}]])
+}]AT_ERROR_CUSTOM_IF([[
+void
+]AT_NAMESPACE[::parser::yyreport_syntax_error (const context& ctx) const
+{
+  /* Arguments of yyformat: reported tokens (one for the "unexpected",
+     one per "expected"). */
+  int arg[yyntokens_];
+  int n = ctx.yysyntax_error_arguments (arg, 
yyntokens_);]AT_PARAM_IF([m4_bpatsubst(m4_defn([AT_PARSE_PARAMS]),
+              [[^,]+[^A-Za-z_0-9]\([A-Za-z_][A-Za-z_0-9]*\),* *], [
+  YYUSE (\1);])])[]m4_bmatch(m4_defn([AT_PARSE_PARAMS]), [nerrs],[[
+  ++global_nerrs;
+  ++*nerrs;]])[
+  if (n)
+  {]AT_LOCATION_IF([[
+    std::cerr << ctx.location () << ": ";]])[
+    std::cerr << "syntax error on token [" << yysymbol_name (arg[0]) << ']';
+    if (1 < n)
+      {
+        std::cerr << " (expected:";
+        for (int i = 1; i < n; ++i)
+          std::cerr << " [" << yysymbol_name (arg[i]) << ']';
+        std::cerr << ')';
+      }
+    std::cerr << '\n';
+  }
+}]])])
 
 
-# AT_YYERROR_DEFINE(c++)([INPUT], [ACTION])
+# AT_YYLEX_DEFINE(c++)([INPUT], [ACTION])
 # -----------------------------------------
 # Same as in C.
 m4_copy([AT_YYLEX_DEFINE(c)], [AT_YYLEX_DEFINE(c++)])
-- 
2.25.1




reply via email to

[Prev in Thread] Current Thread [Next in Thread]