bug-bison
[Top][All Lists]
Advanced

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

PATCH: parser subclass


From: Anthony Heading
Subject: PATCH: parser subclass
Date: Sun, 03 Jul 2022 17:46:19 -0400
User-agent: Cyrus-JMAP/3.7.0-alpha0-713-g1f035dc716-fm-20220617.001-g1f035dc7

Another patch I've had for ages and use a lot,  this one possibly more 
contentious because I recall Akim having reservations on the concept,  but that 
was maybe 15 years ago and my memory could be wrong.

The idea anyway, is that in a C++ parser it is nice if users can make 
unqualified calls in their actions, e.g.

     secret-key: "top-secret" { set_lex_flag(ROT13); } key

and have these resolve to a method in the user's parser class.  

This isn't possible by default because all the semantic action code is inserted 
into the parse() function in the closed bison-generated parser class.

Attached patch invents the 'api.parser.subclass' parameter.  If this is 
defined, bison generates a parse() member function body for this existing user 
class instead.  The user's class should inherit the default class, then can 
create any additional functions they would like for direct use in actions.

Thoughts welcomed.

Anthony

commit c49947ff0a9ded3f97d19dda2738be18a9a94828
Author: Anthony Heading <anthony.heading@localhost>
Date:   Sun Apr 3 16:33:24 2022 -0400

    Change 'private' to 'protected' to enable inheritance from the parser
    class.  Define 'api.parser.subclass' variable to have the generated
    parse() function be defined in this class.

diff --git data/skeletons/c++.m4 data/skeletons/c++.m4
index 8b30524b..10ab80ef 100644
--- data/skeletons/c++.m4
+++ data/skeletons/c++.m4
@@ -28,6 +28,7 @@ m4_include(b4_skeletonsdir/[c.m4])
 
 b4_percent_define_check_kind([api.namespace], [code], [deprecated])
 b4_percent_define_check_kind([api.parser.class], [code], [deprecated])
+b4_percent_define_check_kind([api.parser.subclass], [code], [deprecated])
 
 
 ## ----- ##
@@ -113,6 +114,8 @@ b4_percent_define_default([[define_location_comparison]],
                           [m4_if(b4_percent_define_get([[filename_type]]),
                                  [std::string], [[true]], [[false]])])
 
+b4_percent_define_default([[api.parser.subclass]],
+                         
[b4_percent_define_get([[api.namespace]])[::]][b4_percent_define_get([[api.parser.class]])])
 
 
 ## ----------- ##
diff --git data/skeletons/lalr1.cc data/skeletons/lalr1.cc
index 7cb69d3d..dcbfc2e2 100644
--- data/skeletons/lalr1.cc
+++ data/skeletons/lalr1.cc
@@ -163,6 +163,8 @@ m4_pushdef([b4_copyright_years],
 
 m4_define([b4_parser_class],
           [b4_percent_define_get([[api.parser.class]])])
+m4_define([b4_parser_subclass],
+          [b4_percent_define_get([[api.parser.subclass]])])
 
 b4_bison_locations_if([# Backward compatibility.
    m4_define([b4_location_constructors])
@@ -284,13 +286,14 @@ m4_define([b4_shared_declarations],
       const symbol_type& yyla_;
     };
 ]])[
-  private:
 #if YY_CPLUSPLUS < 201103L
+  private:
     /// Non copyable.
     ]b4_parser_class[ (const ]b4_parser_class[&);
     /// Non copyable.
     ]b4_parser_class[& operator= (const ]b4_parser_class[&);
 #endif
+  protected:
 ]b4_lac_if([[
     /// Check the lookahead yytoken.
     /// \returns  true iff the token will be eventually shifted.
@@ -384,7 +387,6 @@ m4_define([b4_shared_declarations],
     template <typename Base>
     void yy_destroy_ (const char* yymsg, basic_symbol<Base>& yysym) const;
 
-  private:
     /// Type access provider for state based symbols.
     struct by_state
     {
@@ -833,14 +835,16 @@ m4_if(b4_prefix, [yy], [],
     return yyvalue == yytable_ninf_;
   }
 
+]b4_namespace_close[
+
   int
-  ]b4_parser_class[::operator() ()
+  ]b4_parser_subclass[::operator() ()
   {
     return parse ();
   }
 
   int
-  ]b4_parser_class[::parse ()
+  ]b4_parser_subclass[::parse ()
   {
     int yyn;
     /// Length of the RHS of the rule being reduced.
@@ -1198,6 +1202,8 @@ b4_dollar_popdef])[]dnl
 #endif // YY_EXCEPTIONS
   }
 
+]b4_namespace_open[
+
   void
   ]b4_parser_class[::error (const syntax_error& yyexc)
   {
diff --git src/muscle-tab.c src/muscle-tab.c
index 3d3baf13..4bfd4200 100644
--- src/muscle-tab.c
+++ src/muscle-tab.c
@@ -455,6 +455,7 @@ muscle_percent_variable_update (char const *variable,
     { "namespace",                  "api.namespace",             muscle_code },
     { "package",                    "api.package",               muscle_code },
     { "parser_class_name",          "api.parser.class",          muscle_code },
+    { "parser_subclass_name",       "api.parser.subclass",       muscle_code },
     { "public",                     "api.parser.public",         
muscle_keyword },
     { "strictfp",                   "api.parser.strictfp",       
muscle_keyword },
     { "stype",                      "api.value.type",            -1 },

Attachment: subclass.patch
Description: Text Data


reply via email to

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