X-Git-Url: https://git.saurik.com/bison.git/blobdiff_plain/f16b08196c780556cbf50691e2944960aebc46f6..f64e406b80ddaadf25c5b64bbe1d65097568db09:/src/conflicts.c?ds=sidebyside diff --git a/src/conflicts.c b/src/conflicts.c index b50922e0..f11d8e3a 100644 --- a/src/conflicts.c +++ b/src/conflicts.c @@ -1,7 +1,7 @@ /* Find and resolve or report lookahead conflicts for bison, - Copyright (C) 1984, 1989, 1992, 2000, 2001, 2002, 2003, 2004, 2005, 2006, - 2007 Free Software Foundation, Inc. + Copyright (C) 1984, 1989, 1992, 2000, 2001, 2002, 2003, 2004, 2005, + 2006, 2007, 2008-2009 Free Software Foundation, Inc. This file is part of Bison, the GNU Compiler Compiler. @@ -30,6 +30,7 @@ #include "getargs.h" #include "gram.h" #include "lalr.h" +#include "print-xml.h" #include "reader.h" #include "state.h" #include "symtab.h" @@ -39,6 +40,7 @@ int expected_sr_conflicts = -1; int expected_rr_conflicts = -1; static char *conflicts; static struct obstack solved_conflicts_obstack; +static struct obstack solved_conflicts_xml_obstack; static bitset shift_set; static bitset lookahead_set; @@ -72,23 +74,25 @@ log_resolution (rule *r, symbol_number token, case shift_resolution: case right_resolution: obstack_fgrow2 (&solved_conflicts_obstack, - _("\ - Conflict between rule %d and token %s resolved as shift"), + _(" Conflict between rule %d and token %s" + " resolved as shift"), r->number, symbols[token]->tag); break; + case reduce_resolution: case left_resolution: obstack_fgrow2 (&solved_conflicts_obstack, - _("\ - Conflict between rule %d and token %s resolved as reduce"), + _(" Conflict between rule %d and token %s" + " resolved as reduce"), r->number, symbols[token]->tag); break; + case nonassoc_resolution: obstack_fgrow2 (&solved_conflicts_obstack, - _("\ - Conflict between rule %d and token %s resolved as an error"), + _(" Conflict between rule %d and token %s" + " resolved as an error"), r->number, symbols[token]->tag); break; @@ -122,14 +126,88 @@ log_resolution (rule *r, symbol_number token, " (%%right %s)", symbols[token]->tag); break; + case nonassoc_resolution: obstack_fgrow1 (&solved_conflicts_obstack, " (%%nonassoc %s)", symbols[token]->tag); break; } + obstack_sgrow (&solved_conflicts_obstack, ".\n"); } + + /* XML report */ + if (xml_flag) + { + /* The description of the resolution. */ + switch (resolution) + { + case shift_resolution: + case right_resolution: + obstack_fgrow2 (&solved_conflicts_xml_obstack, + " ", + r->number, + xml_escape (symbols[token]->tag)); + break; + + case reduce_resolution: + case left_resolution: + obstack_fgrow2 (&solved_conflicts_xml_obstack, + " ", + r->number, + xml_escape (symbols[token]->tag)); + break; + + case nonassoc_resolution: + obstack_fgrow2 (&solved_conflicts_xml_obstack, + " ", + r->number, + xml_escape (symbols[token]->tag)); + break; + } + + /* The reason. */ + switch (resolution) + { + case shift_resolution: + obstack_fgrow2 (&solved_conflicts_xml_obstack, + "%s < %s", + xml_escape_n (0, r->prec->tag), + xml_escape_n (1, symbols[token]->tag)); + break; + + case reduce_resolution: + obstack_fgrow2 (&solved_conflicts_xml_obstack, + "%s < %s", + xml_escape_n (0, symbols[token]->tag), + xml_escape_n (1, r->prec->tag)); + break; + + case left_resolution: + obstack_fgrow1 (&solved_conflicts_xml_obstack, + "%%left %s", + xml_escape (symbols[token]->tag)); + break; + + case right_resolution: + obstack_fgrow1 (&solved_conflicts_xml_obstack, + "%%right %s", + xml_escape (symbols[token]->tag)); + break; + + case nonassoc_resolution: + obstack_fgrow1 (&solved_conflicts_xml_obstack, + "%%nonassoc %s", + xml_escape (symbols[token]->tag)); + break; + } + + obstack_sgrow (&solved_conflicts_xml_obstack, "\n"); + } } @@ -207,16 +285,21 @@ resolve_sr_conflict (state *s, int ruleno, symbol **errors, int *nerrs) flush_reduce (lookahead_tokens, i); } else - /* Matching precedence levels. - For left association, keep only the reduction. - For right association, keep only the shift. - For nonassociation, keep neither. */ + /* Matching precedence levels. + For non-defined associativity, keep both: unexpected + associativity conflict. + For left associativity, keep only the reduction. + For right associativity, keep only the shift. + For nonassociativity, keep neither. */ switch (symbols[i]->assoc) { - default: + case undef_assoc: abort (); + case precedence_assoc: + break; + case right_assoc: log_resolution (redrule, i, right_resolution); flush_reduce (lookahead_tokens, i); @@ -281,6 +364,11 @@ set_conflicts (state *s, symbol **errors) obstack_1grow (&solved_conflicts_obstack, '\0'); s->solved_conflicts = obstack_finish (&solved_conflicts_obstack); } + if (obstack_object_size (&solved_conflicts_xml_obstack)) + { + obstack_1grow (&solved_conflicts_xml_obstack, '\0'); + s->solved_conflicts_xml = obstack_finish (&solved_conflicts_xml_obstack); + } /* Loop over all rules which require lookahead in this state. Check for conflicts not resolved above. */ @@ -309,6 +397,7 @@ conflicts_solve (void) shift_set = bitset_create (ntokens, BITSET_FIXED); lookahead_set = bitset_create (ntokens, BITSET_FIXED); obstack_init (&solved_conflicts_obstack); + obstack_init (&solved_conflicts_xml_obstack); for (i = 0; i < nstates; i++) { @@ -540,4 +629,5 @@ conflicts_free (void) bitset_free (shift_set); bitset_free (lookahead_set); obstack_free (&solved_conflicts_obstack, NULL); + obstack_free (&solved_conflicts_xml_obstack, NULL); }