[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: <reductions>
From: |
Joel E. Denny |
Subject: |
Re: <reductions> |
Date: |
Sat, 17 Nov 2007 22:43:38 -0500 (EST) |
On Sat, 10 Nov 2007, Joel E. Denny wrote:
> > How about @usefulness?
>
> So, I'm thinking we should have this:
>
> <rule number="0" usefulness="useful">...</rule>
> <rule number="1" usefulness="useful">...</rule>
> <rule number="2" usefulness="useless-in-parser">...</rule>
> <rule number="3" usefulness="useful">...</rule>
> <rule number="4" usefulness="useless-in-grammar">...</rule>
>
> Similarly for nonterminals:
>
> <nonterminal symbol-number="6" name="e" usefulness="useful"/>
> <nonterminal symbol-number="7" name="a" usefulness="useless-in-grammar"/>
>
> Same for terminals but they would have values "useful" and
> "unused-in-grammar" since it's not possible for Bison to know that a
> terminal is truly "useless".
>
> Any objections? If not, I can work on the implementation.
Here it is, not yet committed.
Index: ChangeLog
===================================================================
RCS file: /sources/bison/bison/ChangeLog,v
retrieving revision 1.1756
diff -p -u -r1.1756 ChangeLog
--- ChangeLog 14 Nov 2007 13:18:44 -0000 1.1756
+++ ChangeLog 18 Nov 2007 03:17:25 -0000
@@ -1,3 +1,38 @@
+2007-11-17 Joel E. Denny <address@hidden>
+
+ In the Bison XML output, list useless and unused symbols and rules with
+ the useful ones and add a "usefulness" attribute. Discussed starting
+ at
+ <http://lists.gnu.org/archive/html/bison-patches/2007-09/msg00017.html>.
+ * src/gram.c (grammar_rules_partial_print_xml): Remove.
+ (grammar_rules_print_xml): Print all rules instead of just those
+ useful in the grammar, and add a "usefulness" attribute.
+ * src/gram.h (grammar_rules_partial_print_xml): Remove prototype.
+ * src/print-xml.c (print_rules_useless_in_parser): Remove.
+ (print_grammar): Print all nonterminals instead of just useful ones,
+ and add a "usefulness" attribute to nonterminals and terminals.
+ (print_xml): Don't print a separate "reductions" or
+ "rules-useless-in-parser" element.
+ * src/reduce.c (reduce_output): Use reduce_token_unused_in_grammar.
+ (reduce_xml): Remove.
+ (reduce_token_unused_in_grammar): New.
+ (reduce_nonterminal_useless_in_grammar): New.
+ * src/reduce.h (reduce_xml): Remove prototype.
+ (reduce_token_unused_in_grammar): Add prototype.
+ (reduce_nonterminal_useless_in_grammar): Add prototype.
+ * data/xslt/xml2text.xsl: Update for XML changes.
+ * data/xslt/xml2xhtml.xsl: Update for XML changes.
+ * tests/reduce.at (Useless Terminals): Update output.
+ (Useless Rules): Update output.
+ (Reduced Automaton): Update output.
+
+ Say "Terminals unused in grammar" instead of "Unused terminals".
+ * NEWS (2.3a+): Update.
+ * doc/bison.texinfo (Understanding): Update example output.
+ * src/reduce.c (reduce_output): Implement.
+ * data/xslt/xml2text.xsl: Implement.
+ * data/xslt/xml2xhtml.xsl: Implement.
+
2007-11-14 Akim Demaille <address@hidden>
* doc/yacc.1.in: New.
Index: NEWS
===================================================================
RCS file: /sources/bison/bison/NEWS,v
retrieving revision 1.181
diff -p -u -r1.181 NEWS
--- NEWS 10 Nov 2007 03:42:35 -0000 1.181
+++ NEWS 18 Nov 2007 03:17:25 -0000
@@ -41,9 +41,10 @@ Changes in version 2.3a+ (????-??-??):
%defines "parser.h"
-* When reporting useless rules and nonterminals, Bison now employs the term
- "useless in grammar" instead of "useless" and employs the term "useless in
- parser" instead of "never reduced".
+* When reporting useless rules, useless nonterminals, and unused terminals,
+ Bison now employs the terms "useless in grammar" instead of "useless",
+ "useless in parser" instead of "never reduced", and "unused in grammar"
+ instead of "unused".
* Unreachable State Removal
Index: data/xslt/xml2text.xsl
===================================================================
RCS file: /sources/bison/bison/data/xslt/xml2text.xsl,v
retrieving revision 1.7
diff -p -u -r1.7 xml2text.xsl
--- data/xslt/xml2text.xsl 10 Nov 2007 03:42:36 -0000 1.7
+++ data/xslt/xml2text.xsl 18 Nov 2007 03:17:25 -0000
@@ -36,73 +36,95 @@
</xsl:template>
<xsl:template match="bison-xml-report">
- <xsl:apply-templates select="reductions"/>
- <xsl:apply-templates select="rules-useless-in-parser"/>
+ <xsl:apply-templates select="grammar" mode="reductions"/>
+ <xsl:apply-templates select="grammar" mode="useless-in-parser"/>
<xsl:apply-templates select="automaton" mode="conflicts"/>
<xsl:apply-templates select="grammar"/>
<xsl:apply-templates select="automaton"/>
</xsl:template>
-<xsl:template match="rules-useless-in-parser">
- <xsl:if test="rule">
- <xsl:text>Rules useless in parser due to conflicts </xsl:text>
- <xsl:apply-templates select="rule">
- <xsl:with-param name="pad" select="'3'"/>
- </xsl:apply-templates>
- <xsl:text> </xsl:text>
- </xsl:if>
+<xsl:template match="grammar" mode="reductions">
+ <xsl:apply-templates select="nonterminals" mode="useless-in-grammar"/>
+ <xsl:apply-templates select="terminals" mode="unused-in-grammar"/>
+ <xsl:apply-templates select="rules" mode="useless-in-grammar"/>
</xsl:template>
-<xsl:template match="reductions">
- <xsl:apply-templates select="useless-in-grammar/nonterminals"/>
- <xsl:apply-templates select="unused/terminals"/>
- <xsl:apply-templates select="useless-in-grammar/rules"/>
+<xsl:template match="nonterminals" mode="useless-in-grammar">
+ <xsl:if test="address@hidden'useless-in-grammar']">
+ <xsl:text>Nonterminals useless in grammar </xsl:text>
+ <xsl:for-each select="address@hidden'useless-in-grammar']">
+ <xsl:text> </xsl:text>
+ <xsl:value-of select="@name"/>
+ <xsl:text> </xsl:text>
+ </xsl:for-each>
+ <xsl:text> </xsl:text>
+ </xsl:if>
</xsl:template>
-<xsl:template match="useless-in-grammar/nonterminals">
- <xsl:if test="nonterminal">
- <xsl:text>Nonterminals useless in grammar </xsl:text>
- <xsl:for-each select="nonterminal">
+<xsl:template match="terminals" mode="unused-in-grammar">
+ <xsl:if test="address@hidden'unused-in-grammar']">
+ <xsl:text>Terminals unused in grammar </xsl:text>
+ <xsl:for-each select="address@hidden'unused-in-grammar']">
+ <xsl:sort select="@symbol-number" data-type="number"/>
<xsl:text> </xsl:text>
- <xsl:value-of select="."/>
+ <xsl:value-of select="@name"/>
<xsl:text> </xsl:text>
</xsl:for-each>
<xsl:text> </xsl:text>
</xsl:if>
</xsl:template>
-<xsl:template match="useless-in-grammar/rules">
- <xsl:if test="rule">
+<xsl:template match="rules" mode="useless-in-grammar">
+ <xsl:variable name="set" select="address@hidden'useless-in-grammar']"/>
+ <xsl:if test="$set">
<xsl:text>Rules useless in grammar </xsl:text>
- <xsl:apply-templates select="rule">
- <xsl:with-param name="pad" select="'3'"/>
- </xsl:apply-templates>
+ <xsl:call-template name="style-rule-set">
+ <xsl:with-param name="rule-set" select="$set"/>
+ </xsl:call-template>
<xsl:text> </xsl:text>
</xsl:if>
</xsl:template>
-<xsl:template match="unused/terminals">
- <xsl:if test="terminal">
- <xsl:text>Terminals which are not used </xsl:text>
- <xsl:for-each select="terminal">
- <xsl:text> </xsl:text>
- <xsl:value-of select="."/>
- <xsl:text> </xsl:text>
- </xsl:for-each>
+<xsl:template match="grammar" mode="useless-in-parser">
+ <xsl:variable
+ name="set" select="rules/address@hidden'useless-in-parser']"
+ />
+ <xsl:if test="$set">
+ <xsl:text>Rules useless in parser due to conflicts </xsl:text>
+ <xsl:call-template name="style-rule-set">
+ <xsl:with-param name="rule-set" select="$set"/>
+ </xsl:call-template>
<xsl:text> </xsl:text>
</xsl:if>
</xsl:template>
<xsl:template match="grammar">
<xsl:text>Grammar </xsl:text>
- <xsl:apply-templates select="rules/rule">
- <xsl:with-param name="pad" select="'3'"/>
- </xsl:apply-templates>
+ <xsl:call-template name="style-rule-set">
+ <xsl:with-param
+ name="rule-set" select="rules/address@hidden'useless-in-grammar']"
+ />
+ </xsl:call-template>
<xsl:text> </xsl:text>
<xsl:apply-templates select="terminals"/>
<xsl:apply-templates select="nonterminals"/>
</xsl:template>
+<xsl:template name="style-rule-set">
+ <xsl:param name="rule-set"/>
+ <xsl:for-each select="$rule-set">
+ <xsl:apply-templates select=".">
+ <xsl:with-param name="pad" select="'3'"/>
+ <xsl:with-param name="prev-lhs">
+ <xsl:if test="position()>1">
+ <xsl:variable name="position" select="position()"/>
+ <xsl:value-of select="$rule-set[$position - 1]/lhs"/>
+ </xsl:if>
+ </xsl:with-param>
+ </xsl:apply-templates>
+ </xsl:for-each>
+</xsl:template>
+
<xsl:template match="grammar/terminals">
<xsl:text>Terminals, with rules where they appear </xsl:text>
<xsl:apply-templates select="terminal"/>
@@ -111,7 +133,7 @@
<xsl:template match="grammar/nonterminals">
<xsl:text>Nonterminals, with rules where they appear </xsl:text>
- <xsl:apply-templates select="nonterminal"/>
+ <xsl:apply-templates select="address@hidden'useless-in-grammar']"/>
</xsl:template>
<xsl:template match="terminal">
@@ -293,8 +315,7 @@
<xsl:param name="point"/>
<xsl:param name="lookaheads"/>
- <xsl:if test="$itemset != 'true'
- and not(preceding-sibling::rule[1]/lhs[text()] = lhs[text()])">
+ <xsl:if test="$itemset != 'true' and not($prev-lhs = lhs[text()])">
<xsl:text> </xsl:text>
</xsl:if>
@@ -307,8 +328,7 @@
<!-- LHS -->
<xsl:choose>
- <xsl:when test="$itemset != 'true'
- and preceding-sibling::rule[1]/lhs[text()] = lhs[text()]">
+ <xsl:when test="$itemset != 'true' and $prev-lhs = lhs[text()]">
<xsl:call-template name="lpad">
<xsl:with-param name="str" select="'|'"/>
<xsl:with-param name="pad" select="number(string-length(lhs[text()])) +
1"/>
Index: data/xslt/xml2xhtml.xsl
===================================================================
RCS file: /sources/bison/bison/data/xslt/xml2xhtml.xsl,v
retrieving revision 1.6
diff -p -u -r1.6 xml2xhtml.xsl
--- data/xslt/xml2xhtml.xsl 10 Nov 2007 03:42:36 -0000 1.6
+++ data/xslt/xml2xhtml.xsl 18 Nov 2007 03:17:25 -0000
@@ -109,9 +109,9 @@
<a href="#reductions">Reductions</a>
<ul class="lower-alpha">
<li><a href="#nonterminals_useless_in_grammar">Nonterminals useless in
grammar</a></li>
- <li><a href="#unused_terminals">Unused terminals</a></li>
+ <li><a href="#terminals_unused_in_grammar">Terminals unused in
grammar</a></li>
<li><a href="#rules_useless_in_grammar">Rules useless in
grammar</a></li>
- <xsl:if test="rules-useless-in-parser/rule">
+ <xsl:if test="grammar/rules/address@hidden'useless-in-parser']">
<li><a href="#rules_useless_in_parser">Rules useless in parser due to
conflicts</a></li>
</xsl:if>
</ul>
@@ -127,50 +127,34 @@
</li>
<li><a href="#automaton">Automaton</a></li>
</ul>
- <xsl:apply-templates select="reductions"/>
- <xsl:apply-templates select="rules-useless-in-parser"/>
+ <xsl:apply-templates select="grammar" mode="reductions"/>
+ <xsl:apply-templates select="grammar" mode="useless-in-parser"/>
<xsl:apply-templates select="automaton" mode="conflicts"/>
<xsl:apply-templates select="grammar"/>
<xsl:apply-templates select="automaton"/>
</xsl:template>
-<xsl:template match="rules-useless-in-parser">
- <xsl:if test="rule">
- <h2>
- <a name="rules_useless_in_parser"/>
- <xsl:text> Rules useless in parser due to conflicts</xsl:text>
- </h2>
- <xsl:text> </xsl:text>
- <p class="pre">
- <xsl:apply-templates select="rule">
- <xsl:with-param name="pad" select="'3'"/>
- </xsl:apply-templates>
- </p>
- <xsl:text> </xsl:text>
- </xsl:if>
-</xsl:template>
-
-<xsl:template match="reductions">
+<xsl:template match="grammar" mode="reductions">
<h2>
<a name="reductions"/>
<xsl:text> Reductions</xsl:text>
</h2>
- <xsl:apply-templates select="useless-in-grammar/nonterminals"/>
- <xsl:apply-templates select="unused/terminals"/>
- <xsl:apply-templates select="useless-in-grammar/rules"/>
+ <xsl:apply-templates select="nonterminals" mode="useless-in-grammar"/>
+ <xsl:apply-templates select="terminals" mode="unused-in-grammar"/>
+ <xsl:apply-templates select="rules" mode="useless-in-grammar"/>
</xsl:template>
-<xsl:template match="useless-in-grammar/nonterminals">
+<xsl:template match="nonterminals" mode="useless-in-grammar">
<h3>
<a name="nonterminals_useless_in_grammar"/>
<xsl:text> Nonterminals useless in grammar</xsl:text>
</h3>
<xsl:text> </xsl:text>
- <xsl:if test="nonterminal">
+ <xsl:if test="address@hidden'useless-in-grammar']">
<p class="pre">
- <xsl:for-each select="nonterminal">
+ <xsl:for-each select="address@hidden'useless-in-grammar']">
<xsl:text> </xsl:text>
- <xsl:value-of select="."/>
+ <xsl:value-of select="@name"/>
<xsl:text> </xsl:text>
</xsl:for-each>
<xsl:text> </xsl:text>
@@ -178,40 +162,94 @@
</xsl:if>
</xsl:template>
-<xsl:template match="useless-in-grammar/rules">
+<xsl:template match="terminals" mode="unused-in-grammar">
<h3>
- <a name="rules_useless_in_grammar"/>
- <xsl:text> Rules useless in grammar</xsl:text>
+ <a name="terminals_unused_in_grammar"/>
+ <xsl:text> Terminals unused in grammar</xsl:text>
</h3>
- <xsl:text> </xsl:text>
- <xsl:if test="rule">
+ <xsl:text> </xsl:text>
+ <xsl:if test="address@hidden'unused-in-grammar']">
<p class="pre">
- <xsl:apply-templates select="rule">
- <xsl:with-param name="pad" select="'3'"/>
- </xsl:apply-templates>
+ <xsl:for-each select="address@hidden'unused-in-grammar']">
+ <xsl:sort select="@symbol-number" data-type="number"/>
+ <xsl:text> </xsl:text>
+ <xsl:value-of select="@name"/>
+ <xsl:text> </xsl:text>
+ </xsl:for-each>
<xsl:text> </xsl:text>
</p>
</xsl:if>
</xsl:template>
-<xsl:template match="unused/terminals">
+<xsl:template match="rules" mode="useless-in-grammar">
<h3>
- <a name="unused_terminals"/>
- <xsl:text> Terminals which are not used</xsl:text>
+ <a name="rules_useless_in_grammar"/>
+ <xsl:text> Rules useless in grammar</xsl:text>
</h3>
- <xsl:text> </xsl:text>
- <xsl:if test="terminal">
+ <xsl:text> </xsl:text>
+ <xsl:variable name="set" select="address@hidden'useless-in-grammar']"/>
+ <xsl:if test="$set">
<p class="pre">
- <xsl:for-each select="terminal">
- <xsl:text> </xsl:text>
- <xsl:value-of select="."/>
- <xsl:text> </xsl:text>
- </xsl:for-each>
+ <xsl:call-template name="style-rule-set">
+ <xsl:with-param name="rule-set" select="$set"/>
+ </xsl:call-template>
<xsl:text> </xsl:text>
</p>
</xsl:if>
</xsl:template>
+<xsl:template match="grammar" mode="useless-in-parser">
+ <xsl:variable
+ name="set" select="rules/address@hidden'useless-in-parser']"
+ />
+ <xsl:if test="$set">
+ <h2>
+ <a name="rules_useless_in_parser"/>
+ <xsl:text> Rules useless in parser due to conflicts</xsl:text>
+ </h2>
+ <xsl:text> </xsl:text>
+ <p class="pre">
+ <xsl:call-template name="style-rule-set">
+ <xsl:with-param name="rule-set" select="$set"/>
+ </xsl:call-template>
+ </p>
+ <xsl:text> </xsl:text>
+ </xsl:if>
+</xsl:template>
+
+<xsl:template match="grammar">
+ <h2>
+ <a name="grammar"/>
+ <xsl:text> Grammar</xsl:text>
+ </h2>
+ <xsl:text> </xsl:text>
+ <p class="pre">
+ <xsl:call-template name="style-rule-set">
+ <xsl:with-param
+ name="rule-set" select="rules/address@hidden'useless-in-grammar']"
+ />
+ </xsl:call-template>
+ </p>
+ <xsl:text> </xsl:text>
+ <xsl:apply-templates select="terminals"/>
+ <xsl:apply-templates select="nonterminals"/>
+</xsl:template>
+
+<xsl:template name="style-rule-set">
+ <xsl:param name="rule-set"/>
+ <xsl:for-each select="$rule-set">
+ <xsl:apply-templates select=".">
+ <xsl:with-param name="pad" select="'3'"/>
+ <xsl:with-param name="prev-lhs">
+ <xsl:if test="position()>1">
+ <xsl:variable name="position" select="position()"/>
+ <xsl:value-of select="$rule-set[$position - 1]/lhs"/>
+ </xsl:if>
+ </xsl:with-param>
+ </xsl:apply-templates>
+ </xsl:for-each>
+</xsl:template>
+
<xsl:template match="automaton" mode="conflicts">
<h2>
<a name="conflicts"/>
@@ -260,22 +298,6 @@
</xsl:if>
</xsl:template>
-<xsl:template match="grammar">
- <h2>
- <a name="grammar"/>
- <xsl:text> Grammar</xsl:text>
- </h2>
- <xsl:text> </xsl:text>
- <p class="pre">
- <xsl:apply-templates select="rules/rule">
- <xsl:with-param name="pad" select="'3'"/>
- </xsl:apply-templates>
- </p>
- <xsl:text> </xsl:text>
- <xsl:apply-templates select="terminals"/>
- <xsl:apply-templates select="nonterminals"/>
-</xsl:template>
-
<xsl:template match="grammar/terminals">
<h3>
<a name="terminals"/>
@@ -295,7 +317,9 @@
</h3>
<xsl:text> </xsl:text>
<p class="pre">
- <xsl:apply-templates select="nonterminal"/>
+ <xsl:apply-templates
+ select="address@hidden'useless-in-grammar']"
+ />
</p>
</xsl:template>
@@ -446,8 +470,7 @@
<xsl:param name="point"/>
<xsl:param name="lookaheads"/>
- <xsl:if test="$itemset != 'true'
- and not(preceding-sibling::rule[1]/lhs[text()] = lhs[text()])">
+ <xsl:if test="$itemset != 'true' and not($prev-lhs = lhs[text()])">
<xsl:text> </xsl:text>
</xsl:if>
@@ -483,8 +506,7 @@
<!-- LHS -->
<xsl:choose>
- <xsl:when test="$itemset != 'true'
- and preceding-sibling::rule[1]/lhs[text()] = lhs[text()]">
+ <xsl:when test="$itemset != 'true' and $prev-lhs = lhs[text()]">
<xsl:call-template name="lpad">
<xsl:with-param name="str" select="'|'"/>
<xsl:with-param name="pad" select="number(string-length(lhs[text()])) +
2"/>
Index: doc/bison.texinfo
===================================================================
RCS file: /sources/bison/bison/doc/bison.texinfo,v
retrieving revision 1.245
diff -p -u -r1.245 bison.texinfo
--- doc/bison.texinfo 10 Nov 2007 03:42:36 -0000 1.245
+++ doc/bison.texinfo 18 Nov 2007 03:17:29 -0000
@@ -7197,14 +7197,14 @@ State 11 conflicts: 4 shift/reduce
The next section reports useless tokens, nonterminal and rules. Useless
nonterminals and rules are removed in order to produce a smaller parser,
but useless tokens are preserved, since they might be used by the
-scanner (note the difference between ``useless'' and ``not used''
+scanner (note the difference between ``useless'' and ``unused''
below):
@example
-Useless nonterminals:
+Nonterminals useless in grammar:
useless
-Terminals which are not used:
+Terminals unused in grammar:
STR
Rules useless in grammar:
Index: src/gram.c
===================================================================
RCS file: /sources/bison/bison/src/gram.c,v
retrieving revision 1.63
diff -p -u -r1.63 gram.c
--- src/gram.c 10 Nov 2007 03:42:36 -0000 1.63
+++ src/gram.c 18 Nov 2007 03:17:29 -0000
@@ -197,45 +197,41 @@ grammar_rules_partial_print (FILE *out,
}
void
-grammar_rules_partial_print_xml (FILE *out, int level, bool rtag,
- rule_filter filter)
+grammar_rules_print (FILE *out)
+{
+ grammar_rules_partial_print (out, _("Grammar"), rule_useful_in_grammar_p);
+}
+
+void
+grammar_rules_print_xml (FILE *out, int level)
{
rule_number r;
bool first = true;
for (r = 0; r < nrules + nuseless_productions; r++)
{
- if (filter && !filter (&rules[r]))
- continue;
- if (rtag && first)
+ if (first)
xml_puts (out, level + 1, "<rules>");
first = false;
-
- xml_printf (out, level + 2, "<rule number=\"%d\">",
- rules[r].number);
+ {
+ char const *usefulness;
+ if (rule_useless_in_grammar_p (&rules[r]))
+ usefulness = "useless-in-grammar";
+ else if (rule_useless_in_parser_p (&rules[r]))
+ usefulness = "useless-in-parser";
+ else
+ usefulness = "useful";
+ xml_printf (out, level + 2, "<rule number=\"%d\" usefulness=\"%s\">",
+ rules[r].number, usefulness);
+ }
rule_lhs_print_xml (&rules[r], out, level + 3);
rule_rhs_print_xml (&rules[r], out, level + 3);
xml_puts (out, level + 2, "</rule>");
}
- if (rtag)
- {
- if (!first)
- xml_puts (out, level + 1, "</rules>");
- else
- xml_puts (out, level + 1, "<rules/>");
- }
-}
-
-void
-grammar_rules_print (FILE *out)
-{
- grammar_rules_partial_print (out, _("Grammar"), rule_useful_in_grammar_p);
-}
-
-void
-grammar_rules_print_xml (FILE *out, int level)
-{
- grammar_rules_partial_print_xml (out, level, true, rule_useful_in_grammar_p);
+ if (!first)
+ xml_puts (out, level + 1, "</rules>");
+ else
+ xml_puts (out, level + 1, "<rules/>");
}
void
Index: src/gram.h
===================================================================
RCS file: /sources/bison/bison/src/gram.h,v
retrieving revision 1.62
diff -p -u -r1.62 gram.h
--- src/gram.h 10 Nov 2007 03:42:36 -0000 1.62
+++ src/gram.h 18 Nov 2007 03:17:29 -0000
@@ -254,11 +254,10 @@ size_t ritem_longest_rhs (void);
/* Print the grammar's rules that match FILTER on OUT under TITLE. */
void grammar_rules_partial_print (FILE *out, const char *title,
rule_filter filter);
-void grammar_rules_partial_print_xml (FILE *out, int level, bool rtag,
- rule_filter filter);
/* Print the grammar's useful rules on OUT. */
void grammar_rules_print (FILE *out);
+/* Print all of the grammar's rules with a "usefulness" attribute. */
void grammar_rules_print_xml (FILE *out, int level);
/* Dump the grammar. */
Index: src/print-xml.c
===================================================================
RCS file: /sources/bison/bison/src/print-xml.c,v
retrieving revision 1.10
diff -p -u -r1.10 print-xml.c
--- src/print-xml.c 10 Nov 2007 03:42:36 -0000 1.10
+++ src/print-xml.c 18 Nov 2007 03:17:29 -0000
@@ -52,35 +52,6 @@ static struct escape_buf escape_bufs[2];
/*--------------------------------.
-| Print rules useless in parser. |
-`--------------------------------*/
-
-static void
-print_rules_useless_in_parser (FILE *out, int level)
-{
- rule_number r;
- bool count = false;
-
- for (r = 0; r < nrules + nuseless_productions; r++)
- {
- if (rule_useless_in_parser_p (&rules[r]))
- {
- count = true;
- break;
- }
- }
-
- if (count) {
- xml_puts (out, level, "<rules-useless-in-parser>");
- grammar_rules_partial_print_xml (out, level - 1,
- false, rule_useless_in_parser_p);
- xml_puts (out, level, "</rules-useless-in-parser>");
- }
- else
- xml_puts (out, level, "<rules-useless-in-parser/>");
-}
-
-/*--------------------------------.
| Report information on a state. |
`--------------------------------*/
@@ -430,8 +401,10 @@ print_grammar (FILE *out, int level)
xml_printf (out, level + 2,
"<terminal symbol-number=\"%d\" token-number=\"%d\""
- " name=\"%s\">",
- token_translations[i], i, xml_escape (tag));
+ " name=\"%s\" usefulness=\"%s\">",
+ token_translations[i], i, xml_escape (tag),
+ reduce_token_unused_in_grammar (token_translations[i])
+ ? "unused-in-grammar" : "useful");
for (r = 0; r < nrules; r++)
for (rhsp = rules[r].rhs; *rhsp >= 0; rhsp++)
@@ -446,7 +419,7 @@ print_grammar (FILE *out, int level)
/* Nonterminals */
xml_puts (out, level + 1, "<nonterminals>");
- for (i = ntokens; i < nsyms; i++)
+ for (i = ntokens; i < nsyms + nuseless_nonterminals; i++)
{
int left_count = 0, right_count = 0;
rule_number r;
@@ -466,8 +439,11 @@ print_grammar (FILE *out, int level)
}
xml_printf (out, level + 2,
- "<nonterminal symbol-number=\"%d\" name=\"%s\">",
- i, xml_escape (tag));
+ "<nonterminal symbol-number=\"%d\" name=\"%s\""
+ " usefulness=\"%s\">",
+ i, xml_escape (tag),
+ reduce_nonterminal_useless_in_grammar (i)
+ ? "useless-in-grammar" : "useful");
if (left_count > 0)
{
@@ -584,12 +560,6 @@ print_xml (void)
xml_printf (out, level + 1, "<filename>%s</filename>",
xml_escape (grammar_file));
- /* print reductions */
- reduce_xml (out, level + 1);
-
- /* print rules useless in parser */
- print_rules_useless_in_parser (out, level + 1);
-
/* print grammar */
print_grammar (out, level + 1);
Index: src/reduce.c
===================================================================
RCS file: /sources/bison/bison/src/reduce.c,v
retrieving revision 1.93
diff -p -u -r1.93 reduce.c
--- src/reduce.c 10 Nov 2007 03:42:36 -0000 1.93
+++ src/reduce.c 18 Nov 2007 03:17:29 -0000
@@ -358,10 +358,10 @@ reduce_output (FILE *out)
bool b = false;
int i;
for (i = 0; i < ntokens; i++)
- if (!bitset_test (V, i) && !bitset_test (V1, i))
+ if (reduce_token_unused_in_grammar (i))
{
if (!b)
- fprintf (out, "%s\n\n", _("Terminals which are not used"));
+ fprintf (out, "%s\n\n", _("Terminals unused in grammar"));
b = true;
fprintf (out, " %s\n", symbols[i]->tag);
}
@@ -375,64 +375,6 @@ reduce_output (FILE *out)
}
-/*--------------------------------------------------------------.
-| Output the detailed results of the reductions. For FILE.xml. |
-`---------------------------------------------------------------*/
-
-void
-reduce_xml (FILE *out, int level)
-{
- fputc ('\n', out);
- xml_puts (out, level, "<reductions>");
- xml_puts (out, level + 1, "<useless-in-grammar>");
-
- if (nuseless_nonterminals > 0)
- {
- int i;
- xml_puts (out, level + 2, "<nonterminals>");
- for (i = 0; i < nuseless_nonterminals; ++i)
- xml_printf (out, level + 3,
- "<nonterminal>%s</nonterminal>",
- symbols[nsyms + i]->tag);
- xml_puts (out, level + 2, "</nonterminals>");
- }
- else
- xml_puts (out, level + 2, "<nonterminals/>");
-
- if (nuseless_productions > 0)
- grammar_rules_partial_print_xml (out, level + 1, true,
- rule_useless_in_grammar_p);
- else
- xml_puts (out, level + 2, "<rules/>");
-
- xml_puts (out, level + 1, "</useless-in-grammar>");
- xml_puts (out, level + 1, "<unused>");
-
- {
- bool b = false;
- int i;
- for (i = 0; i < ntokens; i++)
- if (!bitset_test (V, i) && !bitset_test (V1, i))
- {
- if (!b)
- xml_puts (out, level + 2, "<terminals>");
- b = true;
- xml_printf (out, level + 3,
- "<terminal>%s</terminal>",
- xml_escape (symbols[i]->tag));
- }
- if (b)
- xml_puts (out, level + 2, "</terminals>");
- else
- xml_puts (out, level + 2, "<terminals/>");
- }
-
- xml_puts (out, level + 1, "</unused>");
- xml_puts (out, level, "</reductions>");
- fputc ('\n', out);
-}
-
-
/*-------------------------------.
| Report the results to STDERR. |
`-------------------------------*/
@@ -506,6 +448,19 @@ reduce_grammar (void)
}
}
+bool
+reduce_token_unused_in_grammar (symbol_number i)
+{
+ aver (i < ntokens);
+ return !bitset_test (V, i) && !bitset_test (V1, i);
+}
+
+bool
+reduce_nonterminal_useless_in_grammar (symbol_number i)
+{
+ aver (ntokens <= i && i < nsyms + nuseless_nonterminals);
+ return nsyms <= i;
+}
/*-----------------------------------------------------------.
| Free the global sets used to compute the reduced grammar. |
Index: src/reduce.h
===================================================================
RCS file: /sources/bison/bison/src/reduce.h,v
retrieving revision 1.11
diff -p -u -r1.11 reduce.h
--- src/reduce.h 21 Sep 2007 22:53:57 -0000 1.11
+++ src/reduce.h 18 Nov 2007 03:17:29 -0000
@@ -22,7 +22,8 @@
void reduce_grammar (void);
void reduce_output (FILE *out);
-void reduce_xml (FILE *out, int level);
+bool reduce_token_unused_in_grammar (symbol_number i);
+bool reduce_nonterminal_useless_in_grammar (symbol_number i);
void reduce_free (void);
extern symbol_number nuseless_nonterminals;
Index: tests/reduce.at
===================================================================
RCS file: /sources/bison/bison/tests/reduce.at,v
retrieving revision 1.17
diff -p -u -r1.17 reduce.at
--- tests/reduce.at 10 Nov 2007 03:42:37 -0000 1.17
+++ tests/reduce.at 18 Nov 2007 03:17:29 -0000
@@ -45,7 +45,7 @@ exp: useful;
AT_CHECK([[bison input.y]])
AT_CHECK([[sed -n '/^Grammar/q;/^$/!p' input.output]], 0,
-[[Terminals which are not used
+[[Terminals unused in grammar
useless1
useless2
useless3
@@ -174,7 +174,7 @@ AT_CHECK([[sed -n '/^Grammar/q;/^$/!p' i
useless7
useless8
useless9
-Terminals which are not used
+Terminals unused in grammar
'1'
'2'
'3'
@@ -249,7 +249,7 @@ AT_CHECK([[sed -n '/^Grammar/q;/^$/!p' n
[[Nonterminals useless in grammar
not_reachable
non_productive
-Terminals which are not used
+Terminals unused in grammar
useless_token
Rules useless in grammar
2 exp: non_productive