bison-patches
[Top][All Lists]
Advanced

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

[PATCH for Dlang support 2/2] d: change YYLocation's type from class to


From: Adela Vais
Subject: [PATCH for Dlang support 2/2] d: change YYLocation's type from class to struct
Date: Fri, 20 Nov 2020 16:40:55 +0200

This avoids heap allocation and gives minimal costs for the
creation and destruction of the YYParser.Symbol struct if
the location tracking is active.

Suggested by H. S. Teoh.

* data/skeletons/lalr1.d: Here.
* doc/bison.texi: Document it.
* examples/d/calc/calc.y: Adjust.
* tests/calc.at: Test it.
---
 data/skeletons/lalr1.d | 20 ++++++++------------
 doc/bison.texi         |  4 ++--
 examples/d/calc/calc.y | 18 +++++++++---------
 tests/calc.at          | 30 +++++++++++++++---------------
 4 files changed, 34 insertions(+), 38 deletions(-)

diff --git a/data/skeletons/lalr1.d b/data/skeletons/lalr1.d
index 9fee542e..d126d499 100644
--- a/data/skeletons/lalr1.d
+++ b/data/skeletons/lalr1.d
@@ -139,11 +139,11 @@ static assert(__traits(compiles, (new string[1])[0]=(new 
]b4_location_type[[1])[
 
 private immutable bool yy_location_is_class = !__traits(compiles, *(new 
]b4_location_type[((new ]b4_position_type[[1])[0])));]], [[
 /**
- * A class defining a pair of positions.  Positions, defined by the
- * <code>]b4_position_type[</code> class, denote a point in the input.
+ * A struct defining a pair of positions.  Positions, defined by the
+ * <code>]b4_position_type[</code> struct, denote a point in the input.
  * Locations represent a part of the input through the beginning
  * and ending positions.  */
-public class ]b4_location_type[
+public struct ]b4_location_type[
 {
   /** The first, inclusive, position in the range.  */
   public ]b4_position_type[ begin;
@@ -159,9 +159,6 @@ public class ]b4_location_type[
     this.begin = this.end = loc;
   }
 
-  public this () {
-  }
-
   /**
    * Create a <code>]b4_location_type[</code> from the endpoints of the range.
    * @@param begin The first position included in the range.
@@ -173,10 +170,9 @@ public class ]b4_location_type[
   }
 
   /**
-   * A representation of the location. For this to be correct,
-   * <code>]b4_position_type[</code> should override the <code>toString</code>
-   * method.  */
-  public override string toString () const {
+   * A representation of the location.
+   */
+  public string toString () const {
     auto end_col = 0 < end.column ? end.column - 1 : 0;
     auto res = begin.toString ();
     if (end.filename && begin.filename != end.filename)
@@ -189,7 +185,7 @@ public class ]b4_location_type[
   }
 }
 
-private immutable bool yy_location_is_class = true;
+private immutable bool yy_location_is_class = false;
 
 ]])])m4_ifdef([b4_user_union_members], [private union YYSemanticType
 {
@@ -438,7 +434,7 @@ b4_symbol_type_define
     /* Error handling.  */
     int yynerrs_ = 0;]b4_locations_if([[
     /// The location where the error started.
-    ]b4_location_type[ yyerrloc = null;
+    ]b4_location_type[ yyerrloc;
 
     /// ]b4_location_type[ of the lookahead.
     ]b4_location_type[ yylloc;
diff --git a/doc/bison.texi b/doc/bison.texi
index 18b5dd2e..959a4039 100644
--- a/doc/bison.texi
+++ b/doc/bison.texi
@@ -13844,8 +13844,8 @@ can be used to print the semantic values.  This however 
may change
 @c - class Location
 
 When the directive @code{%locations} is used, the D parser supports
-location tracking, see @ref{Tracking Locations}.  The position
-structure and the location class are provided.
+location tracking, see @ref{Tracking Locations}.  The position and
+the location structures are provided.
 
 @deftypeivar {YYLocation} {YYPosition} begin
 @deftypeivarx {YYLocation} {YYPosition} end
diff --git a/examples/d/calc/calc.y b/examples/d/calc/calc.y
index 3f41f048..24ec85d4 100644
--- a/examples/d/calc/calc.y
+++ b/examples/d/calc/calc.y
@@ -127,7 +127,7 @@ if (isInputRange!R && is(ElementType!R : dchar))
     }
 
     if (input.empty)
-      return Calc.Symbol(TokenKind.YYEOF, new YYLocation(startPos, endPos));
+      return Calc.Symbol(TokenKind.YYEOF, YYLocation(startPos, endPos));
 
     // Numbers.
     if (input.front.isNumber)
@@ -143,7 +143,7 @@ if (isInputRange!R && is(ElementType!R : dchar))
       }
       start = end;
       end.column += lenChars;
-      return Calc.Symbol(TokenKind.NUM, semanticVal_.ival, new 
YYLocation(startPos, endPos));
+      return Calc.Symbol(TokenKind.NUM, semanticVal_.ival, 
YYLocation(startPos, endPos));
     }
 
     // Individual characters
@@ -153,17 +153,17 @@ if (isInputRange!R && is(ElementType!R : dchar))
     end.column++;
     switch (ch)
     {
-      case '+':  return Calc.Symbol(TokenKind.PLUS, new YYLocation(startPos, 
endPos));
-      case '-':  return Calc.Symbol(TokenKind.MINUS, new YYLocation(startPos, 
endPos));
-      case '*':  return Calc.Symbol(TokenKind.STAR, new YYLocation(startPos, 
endPos));
-      case '/':  return Calc.Symbol(TokenKind.SLASH, new YYLocation(startPos, 
endPos));
-      case '(':  return Calc.Symbol(TokenKind.LPAR, new YYLocation(startPos, 
endPos));
-      case ')':  return Calc.Symbol(TokenKind.RPAR, new YYLocation(startPos, 
endPos));
+      case '+':  return Calc.Symbol(TokenKind.PLUS, YYLocation(startPos, 
endPos));
+      case '-':  return Calc.Symbol(TokenKind.MINUS, YYLocation(startPos, 
endPos));
+      case '*':  return Calc.Symbol(TokenKind.STAR, YYLocation(startPos, 
endPos));
+      case '/':  return Calc.Symbol(TokenKind.SLASH, YYLocation(startPos, 
endPos));
+      case '(':  return Calc.Symbol(TokenKind.LPAR, YYLocation(startPos, 
endPos));
+      case ')':  return Calc.Symbol(TokenKind.RPAR, YYLocation(startPos, 
endPos));
       case '\n':
       {
         end.line++;
         end.column = 1;
-        return Calc.Symbol(TokenKind.EOL, new YYLocation(startPos, endPos));
+        return Calc.Symbol(TokenKind.EOL, YYLocation(startPos, endPos));
       }
       default: assert(0);
     }
diff --git a/tests/calc.at b/tests/calc.at
index d1a9d030..ae8d29de 100644
--- a/tests/calc.at
+++ b/tests/calc.at
@@ -560,7 +560,7 @@ class CalcLexer(R) : Lexer
   ]AT_YYERROR_DEFINE[
 
   YYSemanticType semanticVal_;]AT_LOCATION_IF([[
-  YYLocation location = new YYLocation;
+  YYLocation location;
 
   public final @property YYPosition startPos()
   {
@@ -606,13 +606,13 @@ class CalcLexer(R) : Lexer
 
     // EOF.
     if (input.empty)
-      return YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[EOF]AT_LOCATION_IF([[, 
new YYLocation(startPos, endPos)]])[);
+      return YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[EOF]AT_LOCATION_IF([[, 
YYLocation(startPos, endPos)]])[);
 
     // Numbers.
     if (input.front.isNumber)
       {
         semanticVal_.ival = parseInt;
-        return YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[NUM, 
semanticVal_.ival]AT_LOCATION_IF([[, new YYLocation(startPos, endPos)]])[);
+        return YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[NUM, 
semanticVal_.ival]AT_LOCATION_IF([[, YYLocation(startPos, endPos)]])[);
       }
 
     // Individual characters
@@ -630,22 +630,22 @@ class CalcLexer(R) : Lexer
     if (c == '#')
       {
         stderr.writeln (]AT_LOCATION_IF([location, ": ", ])["syntax error: 
invalid character: '#'");
-        return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[YYerror]AT_LOCATION_IF([[, new 
YYLocation(startPos, endPos)]])[);
+        return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[YYerror]AT_LOCATION_IF([[, 
YYLocation(startPos, endPos)]])[);
       }
 
     switch (c)
     {
-      case '+':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[PLUS]AT_LOCATION_IF([[, new 
YYLocation(startPos, endPos)]])[);
-      case '-':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[MINUS]AT_LOCATION_IF([[, new 
YYLocation(startPos, endPos)]])[);
-      case '*':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[STAR]AT_LOCATION_IF([[, new 
YYLocation(startPos, endPos)]])[);
-      case '/':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[SLASH]AT_LOCATION_IF([[, new 
YYLocation(startPos, endPos)]])[);
-      case '(':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[LPAR]AT_LOCATION_IF([[, new 
YYLocation(startPos, endPos)]])[);
-      case ')':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[RPAR]AT_LOCATION_IF([[, new 
YYLocation(startPos, endPos)]])[);
-      case '\n': return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[EOL]AT_LOCATION_IF([[, new 
YYLocation(startPos, endPos)]])[);
-      case '=':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[EQUAL]AT_LOCATION_IF([[, new 
YYLocation(startPos, endPos)]])[);
-      case '^':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[POW]AT_LOCATION_IF([[, new 
YYLocation(startPos, endPos)]])[);
-      case '!':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[NOT]AT_LOCATION_IF([[, new 
YYLocation(startPos, endPos)]])[);
-      default:   return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[YYUNDEF]AT_LOCATION_IF([[, new 
YYLocation(startPos, endPos)]])[);
+      case '+':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[PLUS]AT_LOCATION_IF([[, 
YYLocation(startPos, endPos)]])[);
+      case '-':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[MINUS]AT_LOCATION_IF([[, 
YYLocation(startPos, endPos)]])[);
+      case '*':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[STAR]AT_LOCATION_IF([[, 
YYLocation(startPos, endPos)]])[);
+      case '/':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[SLASH]AT_LOCATION_IF([[, 
YYLocation(startPos, endPos)]])[);
+      case '(':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[LPAR]AT_LOCATION_IF([[, 
YYLocation(startPos, endPos)]])[);
+      case ')':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[RPAR]AT_LOCATION_IF([[, 
YYLocation(startPos, endPos)]])[);
+      case '\n': return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[EOL]AT_LOCATION_IF([[, 
YYLocation(startPos, endPos)]])[);
+      case '=':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[EQUAL]AT_LOCATION_IF([[, 
YYLocation(startPos, endPos)]])[);
+      case '^':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[POW]AT_LOCATION_IF([[, 
YYLocation(startPos, endPos)]])[);
+      case '!':  return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[NOT]AT_LOCATION_IF([[, 
YYLocation(startPos, endPos)]])[);
+      default:   return 
YYParser.Symbol(TokenKind.]AT_TOKEN_PREFIX[YYUNDEF]AT_LOCATION_IF([[, 
YYLocation(startPos, endPos)]])[);
     }
   }
 }
-- 
2.17.1




reply via email to

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