mirror of
https://git.savannah.gnu.org/git/bison.git
synced 2026-03-20 01:33:03 +00:00
* src/closure.h: New file.
* src/closure.c: Formatting changes, topological sort over the functions, use of closure.h. (initialize_closure, finalize_closure): Rename as... (new_closure, free_closure): these. Adjust dependencies. * src/LR0.c: Formatting changes, topological sort, use of cloture.h. (initialize_states): Rename as... (new_states): this. * src/Makefile.am (noinst_HEADERS): Adjust.
This commit is contained in:
13
ChangeLog
13
ChangeLog
@@ -1,3 +1,16 @@
|
|||||||
|
2000-09-20 Akim Demaille <akim@epita.fr>
|
||||||
|
|
||||||
|
* src/closure.h: New file.
|
||||||
|
* src/closure.c: Formatting changes, topological sort over the
|
||||||
|
functions, use of closure.h.
|
||||||
|
(initialize_closure, finalize_closure): Rename as...
|
||||||
|
(new_closure, free_closure): these. Adjust dependencies.
|
||||||
|
* src/LR0.c: Formatting changes, topological sort, use of
|
||||||
|
cloture.h.
|
||||||
|
(initialize_states): Rename as...
|
||||||
|
(new_states): this.
|
||||||
|
* src/Makefile.am (noinst_HEADERS): Adjust.
|
||||||
|
|
||||||
2000-09-20 Akim Demaille <akim@epita.fr>
|
2000-09-20 Akim Demaille <akim@epita.fr>
|
||||||
|
|
||||||
* src/acconfig.h: Don't protect config.h against multiple
|
* src/acconfig.h: Don't protect config.h against multiple
|
||||||
|
|||||||
4
po/de.po
4
po/de.po
@@ -5,7 +5,7 @@
|
|||||||
msgid ""
|
msgid ""
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: bison 1.25\n"
|
"Project-Id-Version: bison 1.25\n"
|
||||||
"POT-Creation-Date: 2000-09-20 14:50+0200\n"
|
"POT-Creation-Date: 2000-09-20 17:44+0200\n"
|
||||||
"PO-Revision-Date: 1996-10-10 17:54 MET DST\n"
|
"PO-Revision-Date: 1996-10-10 17:54 MET DST\n"
|
||||||
"Last-Translator: Ulrich Drepper <drepper@gnu.ai.mit.edu>\n"
|
"Last-Translator: Ulrich Drepper <drepper@gnu.ai.mit.edu>\n"
|
||||||
"Language-Team: German <de@li.org>\n"
|
"Language-Team: German <de@li.org>\n"
|
||||||
@@ -13,7 +13,7 @@ msgstr ""
|
|||||||
"Content-Type: text/plain; charset=ISO-8859-1\n"
|
"Content-Type: text/plain; charset=ISO-8859-1\n"
|
||||||
"Content-Transfer-Encoding: 8-bit\n"
|
"Content-Transfer-Encoding: 8-bit\n"
|
||||||
|
|
||||||
#: src/LR0.c:375
|
#: src/LR0.c:212
|
||||||
#, c-format
|
#, c-format
|
||||||
msgid "too many states (max %d)"
|
msgid "too many states (max %d)"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|||||||
4
po/es.po
4
po/es.po
@@ -30,7 +30,7 @@
|
|||||||
msgid ""
|
msgid ""
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: GNU bison 1.25\n"
|
"Project-Id-Version: GNU bison 1.25\n"
|
||||||
"POT-Creation-Date: 2000-09-20 14:50+0200\n"
|
"POT-Creation-Date: 2000-09-20 17:44+0200\n"
|
||||||
"PO-Revision-Date: 1998-09-21 10:19+0200\n"
|
"PO-Revision-Date: 1998-09-21 10:19+0200\n"
|
||||||
"Last-Translator: Nicolás García-Pedrajas <ngarcia-pedrajas@acm.org>\n"
|
"Last-Translator: Nicolás García-Pedrajas <ngarcia-pedrajas@acm.org>\n"
|
||||||
"Language-Team: Spanish <es@li.org>\n"
|
"Language-Team: Spanish <es@li.org>\n"
|
||||||
@@ -38,7 +38,7 @@ msgstr ""
|
|||||||
"Content-Type: text/plain; charset=ISO-8859-1\n"
|
"Content-Type: text/plain; charset=ISO-8859-1\n"
|
||||||
"Content-Transfer-Encoding: 8-bit\n"
|
"Content-Transfer-Encoding: 8-bit\n"
|
||||||
|
|
||||||
#: src/LR0.c:375
|
#: src/LR0.c:212
|
||||||
#, c-format
|
#, c-format
|
||||||
msgid "too many states (max %d)"
|
msgid "too many states (max %d)"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|||||||
4
po/et.po
4
po/et.po
@@ -5,7 +5,7 @@
|
|||||||
msgid ""
|
msgid ""
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: bison 1.25\n"
|
"Project-Id-Version: bison 1.25\n"
|
||||||
"POT-Creation-Date: 2000-09-20 14:50+0200\n"
|
"POT-Creation-Date: 2000-09-20 17:44+0200\n"
|
||||||
"PO-Revision-Date: 2000-04-11 22:19+02:00\n"
|
"PO-Revision-Date: 2000-04-11 22:19+02:00\n"
|
||||||
"Last-Translator: Toomas Soome <tsoome@ut.ee>\n"
|
"Last-Translator: Toomas Soome <tsoome@ut.ee>\n"
|
||||||
"Language-Team: Estonian <et@li.org>\n"
|
"Language-Team: Estonian <et@li.org>\n"
|
||||||
@@ -13,7 +13,7 @@ msgstr ""
|
|||||||
"Content-Type: text/plain; charset=ISO-8859-15\n"
|
"Content-Type: text/plain; charset=ISO-8859-15\n"
|
||||||
"Content-Transfer-Encoding: 8-bit\n"
|
"Content-Transfer-Encoding: 8-bit\n"
|
||||||
|
|
||||||
#: src/LR0.c:375
|
#: src/LR0.c:212
|
||||||
#, c-format
|
#, c-format
|
||||||
msgid "too many states (max %d)"
|
msgid "too many states (max %d)"
|
||||||
msgstr "liiga palju olekuid (maks %d)"
|
msgstr "liiga palju olekuid (maks %d)"
|
||||||
|
|||||||
4
po/fr.po
4
po/fr.po
@@ -5,7 +5,7 @@
|
|||||||
msgid ""
|
msgid ""
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: bison 1.25\n"
|
"Project-Id-Version: bison 1.25\n"
|
||||||
"POT-Creation-Date: 2000-09-20 14:50+0200\n"
|
"POT-Creation-Date: 2000-09-20 17:44+0200\n"
|
||||||
"PO-Revision-Date: 1996-03-19 20:05 EST\n"
|
"PO-Revision-Date: 1996-03-19 20:05 EST\n"
|
||||||
"Last-Translator: Dominique Boucher <boucherd@IRO.UMontreal.CA>\n"
|
"Last-Translator: Dominique Boucher <boucherd@IRO.UMontreal.CA>\n"
|
||||||
"Language-Team: French <fr@li.org>\n"
|
"Language-Team: French <fr@li.org>\n"
|
||||||
@@ -13,7 +13,7 @@ msgstr ""
|
|||||||
"Content-Type: text/plain; charset=ISO-8859-1\n"
|
"Content-Type: text/plain; charset=ISO-8859-1\n"
|
||||||
"Content-Transfer-Encoding: 8-bit\n"
|
"Content-Transfer-Encoding: 8-bit\n"
|
||||||
|
|
||||||
#: src/LR0.c:375
|
#: src/LR0.c:212
|
||||||
#, c-format
|
#, c-format
|
||||||
msgid "too many states (max %d)"
|
msgid "too many states (max %d)"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|||||||
4
po/ja.po
4
po/ja.po
@@ -5,7 +5,7 @@
|
|||||||
msgid ""
|
msgid ""
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: GNU bison 1.28\n"
|
"Project-Id-Version: GNU bison 1.28\n"
|
||||||
"POT-Creation-Date: 2000-09-20 14:50+0200\n"
|
"POT-Creation-Date: 2000-09-20 17:44+0200\n"
|
||||||
"PO-Revision-Date: 1999-09-28 21:10+0900\n"
|
"PO-Revision-Date: 1999-09-28 21:10+0900\n"
|
||||||
"Last-Translator: Daisuke Yamashita <yamad@mb.infoweb.ne.jp>\n"
|
"Last-Translator: Daisuke Yamashita <yamad@mb.infoweb.ne.jp>\n"
|
||||||
"Language-Team: Japanese <ja@li.org>\n"
|
"Language-Team: Japanese <ja@li.org>\n"
|
||||||
@@ -13,7 +13,7 @@ msgstr ""
|
|||||||
"Content-Type: text/plain; charset=EUC-JP\n"
|
"Content-Type: text/plain; charset=EUC-JP\n"
|
||||||
"Content-Transfer-Encoding: 8bit\n"
|
"Content-Transfer-Encoding: 8bit\n"
|
||||||
|
|
||||||
#: src/LR0.c:375
|
#: src/LR0.c:212
|
||||||
#, fuzzy, c-format
|
#, fuzzy, c-format
|
||||||
msgid "too many states (max %d)"
|
msgid "too many states (max %d)"
|
||||||
msgstr "%s の数が多すぎます (最大 %d)"
|
msgstr "%s の数が多すぎます (最大 %d)"
|
||||||
|
|||||||
4
po/nl.po
4
po/nl.po
@@ -5,7 +5,7 @@
|
|||||||
msgid ""
|
msgid ""
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: bison 1.25\n"
|
"Project-Id-Version: bison 1.25\n"
|
||||||
"POT-Creation-Date: 2000-09-20 14:50+0200\n"
|
"POT-Creation-Date: 2000-09-20 17:44+0200\n"
|
||||||
"PO-Revision-Date: 1996-08-27 15:34 MET DST\n"
|
"PO-Revision-Date: 1996-08-27 15:34 MET DST\n"
|
||||||
"Last-Translator: Erick Branderhorst <branderh@debian.org>\n"
|
"Last-Translator: Erick Branderhorst <branderh@debian.org>\n"
|
||||||
"Language-Team: Dutch <nl@li.org>\n"
|
"Language-Team: Dutch <nl@li.org>\n"
|
||||||
@@ -13,7 +13,7 @@ msgstr ""
|
|||||||
"Content-Type: text/plain; charset=ISO-8859-1\n"
|
"Content-Type: text/plain; charset=ISO-8859-1\n"
|
||||||
"Content-Transfer-Encoding: 8-bit\n"
|
"Content-Transfer-Encoding: 8-bit\n"
|
||||||
|
|
||||||
#: src/LR0.c:375
|
#: src/LR0.c:212
|
||||||
#, c-format
|
#, c-format
|
||||||
msgid "too many states (max %d)"
|
msgid "too many states (max %d)"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|||||||
4
po/ru.po
4
po/ru.po
@@ -5,7 +5,7 @@
|
|||||||
msgid ""
|
msgid ""
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: bison 1.28a\n"
|
"Project-Id-Version: bison 1.28a\n"
|
||||||
"POT-Creation-Date: 2000-09-20 14:50+0200\n"
|
"POT-Creation-Date: 2000-09-20 17:44+0200\n"
|
||||||
"PO-Revision-Date: 2000-04-12 13:16+04:00\n"
|
"PO-Revision-Date: 2000-04-12 13:16+04:00\n"
|
||||||
"Last-Translator: Dmitry S. Sivachenko <dima@Chg.RU>\n"
|
"Last-Translator: Dmitry S. Sivachenko <dima@Chg.RU>\n"
|
||||||
"Language-Team: Russian <ru@li.org>\n"
|
"Language-Team: Russian <ru@li.org>\n"
|
||||||
@@ -13,7 +13,7 @@ msgstr ""
|
|||||||
"Content-Type: text/plain; charset=koi8-r\n"
|
"Content-Type: text/plain; charset=koi8-r\n"
|
||||||
"Content-Transfer-Encoding: 8-bit\n"
|
"Content-Transfer-Encoding: 8-bit\n"
|
||||||
|
|
||||||
#: src/LR0.c:375
|
#: src/LR0.c:212
|
||||||
#, c-format
|
#, c-format
|
||||||
msgid "too many states (max %d)"
|
msgid "too many states (max %d)"
|
||||||
msgstr "ÓÌÉÛËÏÍ ÍÎÏÇÏ ÓÏÓÔÏÑÎÉÊ (ÍÁËÓÉÍÁÌØÎÏ %d)"
|
msgstr "ÓÌÉÛËÏÍ ÍÎÏÇÏ ÓÏÓÔÏÑÎÉÊ (ÍÁËÓÉÍÁÌØÎÏ %d)"
|
||||||
|
|||||||
600
src/LR0.c
600
src/LR0.c
@@ -1,22 +1,22 @@
|
|||||||
/* Generate the nondeterministic finite state machine for bison,
|
/* Generate the nondeterministic finite state machine for bison,
|
||||||
Copyright (C) 1984, 1986, 1989 Free Software Foundation, Inc.
|
Copyright (C) 1984, 1986, 1989 Free Software Foundation, Inc.
|
||||||
|
|
||||||
This file is part of Bison, the GNU Compiler Compiler.
|
This file is part of Bison, the GNU Compiler Compiler.
|
||||||
|
|
||||||
Bison is free software; you can redistribute it and/or modify
|
Bison is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
the Free Software Foundation; either version 2, or (at your option)
|
the Free Software Foundation; either version 2, or (at your option)
|
||||||
any later version.
|
any later version.
|
||||||
|
|
||||||
Bison is distributed in the hope that it will be useful,
|
Bison is distributed in the hope that it will be useful,
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
GNU General Public License for more details.
|
GNU General Public License for more details.
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
You should have received a copy of the GNU General Public License
|
||||||
along with Bison; see the file COPYING. If not, write to
|
along with Bison; see the file COPYING. If not, write to
|
||||||
the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
||||||
Boston, MA 02111-1307, USA. */
|
Boston, MA 02111-1307, USA. */
|
||||||
|
|
||||||
|
|
||||||
/* See comments in state.h for the data structures that represent it.
|
/* See comments in state.h for the data structures that represent it.
|
||||||
@@ -27,7 +27,7 @@ Boston, MA 02111-1307, USA. */
|
|||||||
#include "gram.h"
|
#include "gram.h"
|
||||||
#include "state.h"
|
#include "state.h"
|
||||||
#include "complain.h"
|
#include "complain.h"
|
||||||
|
#include "closure.h"
|
||||||
|
|
||||||
extern char *nullable;
|
extern char *nullable;
|
||||||
extern short *itemset;
|
extern short *itemset;
|
||||||
@@ -40,23 +40,7 @@ core *first_state;
|
|||||||
shifts *first_shift;
|
shifts *first_shift;
|
||||||
reductions *first_reduction;
|
reductions *first_reduction;
|
||||||
|
|
||||||
extern void generate_states PARAMS((void));
|
extern void generate_states PARAMS ((void));
|
||||||
|
|
||||||
static int get_state PARAMS((int));
|
|
||||||
static core *new_state PARAMS((int));
|
|
||||||
static void allocate_itemsets PARAMS((void));
|
|
||||||
static void allocate_storage PARAMS((void));
|
|
||||||
static void free_storage PARAMS((void));
|
|
||||||
static void new_itemsets PARAMS((void));
|
|
||||||
static void append_states PARAMS((void));
|
|
||||||
static void initialize_states PARAMS((void));
|
|
||||||
static void save_shifts PARAMS((void));
|
|
||||||
static void save_reductions PARAMS((void));
|
|
||||||
static void augment_automaton PARAMS((void));
|
|
||||||
static void insert_start_shift PARAMS((void));
|
|
||||||
extern void initialize_closure PARAMS((int));
|
|
||||||
extern void closure PARAMS((short *, int));
|
|
||||||
extern void finalize_closure PARAMS((void));
|
|
||||||
|
|
||||||
static core *this_state;
|
static core *this_state;
|
||||||
static core *last_state;
|
static core *last_state;
|
||||||
@@ -78,19 +62,18 @@ static short *kernel_items;
|
|||||||
#define STATE_TABLE_SIZE 1009
|
#define STATE_TABLE_SIZE 1009
|
||||||
static core **state_table;
|
static core **state_table;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
allocate_itemsets (void)
|
allocate_itemsets (void)
|
||||||
{
|
{
|
||||||
register short *itemp;
|
short *itemp;
|
||||||
register int symbol;
|
int symbol;
|
||||||
register int i;
|
int i;
|
||||||
register int count;
|
int count;
|
||||||
register short *symbol_count;
|
short *symbol_count;
|
||||||
|
|
||||||
count = 0;
|
count = 0;
|
||||||
symbol_count = NEW2(nsyms, short);
|
symbol_count = NEW2 (nsyms, short);
|
||||||
|
|
||||||
itemp = ritem;
|
itemp = ritem;
|
||||||
symbol = *itemp++;
|
symbol = *itemp++;
|
||||||
@@ -104,14 +87,14 @@ allocate_itemsets (void)
|
|||||||
symbol = *itemp++;
|
symbol = *itemp++;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* see comments before new_itemsets. All the vectors of items
|
/* See comments before new_itemsets. All the vectors of items
|
||||||
live inside kernel_items. The number of active items after
|
live inside KERNEL_ITEMS. The number of active items after
|
||||||
some symbol cannot be more than the number of times that symbol
|
some symbol cannot be more than the number of times that symbol
|
||||||
appears as an item, which is symbol_count[symbol].
|
appears as an item, which is symbol_count[symbol].
|
||||||
We allocate that much space for each symbol. */
|
We allocate that much space for each symbol. */
|
||||||
|
|
||||||
kernel_base = NEW2(nsyms, short *);
|
kernel_base = NEW2 (nsyms, short *);
|
||||||
kernel_items = NEW2(count, short);
|
kernel_items = NEW2 (count, short);
|
||||||
|
|
||||||
count = 0;
|
count = 0;
|
||||||
for (i = 0; i < nsyms; i++)
|
for (i = 0; i < nsyms; i++)
|
||||||
@@ -121,94 +104,59 @@ allocate_itemsets (void)
|
|||||||
}
|
}
|
||||||
|
|
||||||
shift_symbol = symbol_count;
|
shift_symbol = symbol_count;
|
||||||
kernel_end = NEW2(nsyms, short *);
|
kernel_end = NEW2 (nsyms, short *);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
allocate_storage (void)
|
allocate_storage (void)
|
||||||
{
|
{
|
||||||
allocate_itemsets();
|
allocate_itemsets ();
|
||||||
|
|
||||||
shiftset = NEW2(nsyms, short);
|
shiftset = NEW2 (nsyms, short);
|
||||||
redset = NEW2(nrules + 1, short);
|
redset = NEW2 (nrules + 1, short);
|
||||||
state_table = NEW2(STATE_TABLE_SIZE, core *);
|
state_table = NEW2 (STATE_TABLE_SIZE, core *);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
free_storage (void)
|
free_storage (void)
|
||||||
{
|
{
|
||||||
FREE(shift_symbol);
|
FREE (shift_symbol);
|
||||||
FREE(redset);
|
FREE (redset);
|
||||||
FREE(shiftset);
|
FREE (shiftset);
|
||||||
FREE(kernel_base);
|
FREE (kernel_base);
|
||||||
FREE(kernel_end);
|
FREE (kernel_end);
|
||||||
FREE(kernel_items);
|
FREE (kernel_items);
|
||||||
FREE(state_table);
|
FREE (state_table);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/* compute the nondeterministic finite state machine (see state.h for details)
|
|
||||||
from the grammar. */
|
|
||||||
void
|
|
||||||
generate_states (void)
|
|
||||||
{
|
|
||||||
allocate_storage();
|
|
||||||
initialize_closure(nitems);
|
|
||||||
initialize_states();
|
|
||||||
|
|
||||||
while (this_state)
|
/*----------------------------------------------------------------.
|
||||||
{
|
| Find which symbols can be shifted in the current state, and for |
|
||||||
/* Set up ruleset and itemset for the transitions out of this state.
|
| each one record which items would be active after that shift. |
|
||||||
ruleset gets a 1 bit for each rule that could reduce now.
|
| Uses the contents of itemset. |
|
||||||
itemset gets a vector of all the items that could be accepted next. */
|
| |
|
||||||
closure(this_state->items, this_state->nitems);
|
| shift_symbol is set to a vector of the symbols that can be |
|
||||||
/* record the reductions allowed out of this state */
|
| shifted. For each symbol in the grammar, kernel_base[symbol] |
|
||||||
save_reductions();
|
| points to a vector of item numbers activated if that symbol is |
|
||||||
/* find the itemsets of the states that shifts can reach */
|
| shifted, and kernel_end[symbol] points after the end of that |
|
||||||
new_itemsets();
|
| vector. |
|
||||||
/* find or create the core structures for those states */
|
`----------------------------------------------------------------*/
|
||||||
append_states();
|
|
||||||
|
|
||||||
/* create the shifts structures for the shifts to those states,
|
|
||||||
now that the state numbers transitioning to are known */
|
|
||||||
if (nshifts > 0)
|
|
||||||
save_shifts();
|
|
||||||
|
|
||||||
/* states are queued when they are created; process them all */
|
|
||||||
this_state = this_state->next;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* discard various storage */
|
|
||||||
finalize_closure();
|
|
||||||
free_storage();
|
|
||||||
|
|
||||||
/* set up initial and final states as parser wants them */
|
|
||||||
augment_automaton();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/* Find which symbols can be shifted in the current state,
|
|
||||||
and for each one record which items would be active after that shift.
|
|
||||||
Uses the contents of itemset.
|
|
||||||
shift_symbol is set to a vector of the symbols that can be shifted.
|
|
||||||
For each symbol in the grammar, kernel_base[symbol] points to
|
|
||||||
a vector of item numbers activated if that symbol is shifted,
|
|
||||||
and kernel_end[symbol] points after the end of that vector. */
|
|
||||||
static void
|
static void
|
||||||
new_itemsets (void)
|
new_itemsets (void)
|
||||||
{
|
{
|
||||||
register int i;
|
int i;
|
||||||
register int shiftcount;
|
int shiftcount;
|
||||||
register short *isp;
|
short *isp;
|
||||||
register short *ksp;
|
short *ksp;
|
||||||
register int symbol;
|
int symbol;
|
||||||
|
|
||||||
#ifdef TRACE
|
#if TRACE
|
||||||
fprintf(stderr, "Entering new_itemsets\n");
|
fprintf (stderr, "Entering new_itemsets\n");
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
for (i = 0; i < nsyms; i++)
|
for (i = 0; i < nsyms; i++)
|
||||||
@@ -224,16 +172,16 @@ new_itemsets (void)
|
|||||||
symbol = ritem[i];
|
symbol = ritem[i];
|
||||||
if (symbol > 0)
|
if (symbol > 0)
|
||||||
{
|
{
|
||||||
ksp = kernel_end[symbol];
|
ksp = kernel_end[symbol];
|
||||||
|
|
||||||
if (!ksp)
|
if (!ksp)
|
||||||
{
|
{
|
||||||
shift_symbol[shiftcount++] = symbol;
|
shift_symbol[shiftcount++] = symbol;
|
||||||
ksp = kernel_base[symbol];
|
ksp = kernel_base[symbol];
|
||||||
}
|
}
|
||||||
|
|
||||||
*ksp++ = i + 1;
|
*ksp++ = i + 1;
|
||||||
kernel_end[symbol] = ksp;
|
kernel_end[symbol] = ksp;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -242,63 +190,70 @@ new_itemsets (void)
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
/* Use the information computed by new_itemsets to find the state numbers
|
/*-----------------------------------------------------------------.
|
||||||
reached by each shift transition from the current state.
|
| Subroutine of get_state. Create a new state for those items, if |
|
||||||
|
| necessary. |
|
||||||
|
`-----------------------------------------------------------------*/
|
||||||
|
|
||||||
shiftset is set up as a vector of state numbers of those states. */
|
static core *
|
||||||
static void
|
new_state (int symbol)
|
||||||
append_states (void)
|
|
||||||
{
|
{
|
||||||
register int i;
|
int n;
|
||||||
register int j;
|
core *p;
|
||||||
register int symbol;
|
short *isp1;
|
||||||
|
short *isp2;
|
||||||
|
short *iend;
|
||||||
|
|
||||||
#ifdef TRACE
|
#if TRACE
|
||||||
fprintf(stderr, "Entering append_states\n");
|
fprintf (stderr, "Entering new_state, symbol = %d\n", symbol);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* first sort shift_symbol into increasing order */
|
if (nstates >= MAXSHORT)
|
||||||
|
fatal (_("too many states (max %d)"), MAXSHORT);
|
||||||
|
|
||||||
for (i = 1; i < nshifts; i++)
|
isp1 = kernel_base[symbol];
|
||||||
{
|
iend = kernel_end[symbol];
|
||||||
symbol = shift_symbol[i];
|
n = iend - isp1;
|
||||||
j = i;
|
|
||||||
while (j > 0 && shift_symbol[j - 1] > symbol)
|
|
||||||
{
|
|
||||||
shift_symbol[j] = shift_symbol[j - 1];
|
|
||||||
j--;
|
|
||||||
}
|
|
||||||
shift_symbol[j] = symbol;
|
|
||||||
}
|
|
||||||
|
|
||||||
for (i = 0; i < nshifts; i++)
|
p =
|
||||||
{
|
(core *) xmalloc ((unsigned) (sizeof (core) + (n - 1) * sizeof (short)));
|
||||||
symbol = shift_symbol[i];
|
p->accessing_symbol = symbol;
|
||||||
shiftset[i] = get_state(symbol);
|
p->number = nstates;
|
||||||
}
|
p->nitems = n;
|
||||||
|
|
||||||
|
isp2 = p->items;
|
||||||
|
while (isp1 < iend)
|
||||||
|
*isp2++ = *isp1++;
|
||||||
|
|
||||||
|
last_state->next = p;
|
||||||
|
last_state = p;
|
||||||
|
|
||||||
|
nstates++;
|
||||||
|
|
||||||
|
return p;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*--------------------------------------------------------------.
|
||||||
/* find the state number for the state we would get to
|
| Find the state number for the state we would get to (from the |
|
||||||
(from the current state) by shifting symbol.
|
| current state) by shifting symbol. Create a new state if no |
|
||||||
Create a new state if no equivalent one exists already.
|
| equivalent one exists already. Used by append_states. |
|
||||||
Used by append_states */
|
`--------------------------------------------------------------*/
|
||||||
|
|
||||||
static int
|
static int
|
||||||
get_state (int symbol)
|
get_state (int symbol)
|
||||||
{
|
{
|
||||||
register int key;
|
int key;
|
||||||
register short *isp1;
|
short *isp1;
|
||||||
register short *isp2;
|
short *isp2;
|
||||||
register short *iend;
|
short *iend;
|
||||||
register core *sp;
|
core *sp;
|
||||||
register int found;
|
int found;
|
||||||
|
|
||||||
int n;
|
int n;
|
||||||
|
|
||||||
#ifdef TRACE
|
#if TRACE
|
||||||
fprintf(stderr, "Entering get_state, symbol = %d\n", symbol);
|
fprintf (stderr, "Entering get_state, symbol = %d\n", symbol);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
isp1 = kernel_base[symbol];
|
isp1 = kernel_base[symbol];
|
||||||
@@ -338,73 +293,68 @@ get_state (int symbol)
|
|||||||
{
|
{
|
||||||
sp = sp->link;
|
sp = sp->link;
|
||||||
}
|
}
|
||||||
else /* bucket exhausted and no match */
|
else /* bucket exhausted and no match */
|
||||||
{
|
{
|
||||||
sp = sp->link = new_state(symbol);
|
sp = sp->link = new_state (symbol);
|
||||||
found = 1;
|
found = 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else /* bucket is empty */
|
else /* bucket is empty */
|
||||||
{
|
{
|
||||||
state_table[key] = sp = new_state(symbol);
|
state_table[key] = sp = new_state (symbol);
|
||||||
}
|
}
|
||||||
|
|
||||||
return sp->number;
|
return sp->number;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*------------------------------------------------------------------.
|
||||||
|
| Use the information computed by new_itemsets to find the state |
|
||||||
|
| numbers reached by each shift transition from the current state. |
|
||||||
|
| |
|
||||||
|
| shiftset is set up as a vector of state numbers of those states. |
|
||||||
|
`------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
static void
|
||||||
/* subroutine of get_state. create a new state for those items, if necessary. */
|
append_states (void)
|
||||||
|
|
||||||
static core *
|
|
||||||
new_state (int symbol)
|
|
||||||
{
|
{
|
||||||
register int n;
|
int i;
|
||||||
register core *p;
|
int j;
|
||||||
register short *isp1;
|
int symbol;
|
||||||
register short *isp2;
|
|
||||||
register short *iend;
|
|
||||||
|
|
||||||
#ifdef TRACE
|
#if TRACE
|
||||||
fprintf(stderr, "Entering new_state, symbol = %d\n", symbol);
|
fprintf (stderr, "Entering append_states\n");
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if (nstates >= MAXSHORT)
|
/* first sort shift_symbol into increasing order */
|
||||||
fatal (_("too many states (max %d)"), MAXSHORT);
|
|
||||||
|
|
||||||
isp1 = kernel_base[symbol];
|
for (i = 1; i < nshifts; i++)
|
||||||
iend = kernel_end[symbol];
|
{
|
||||||
n = iend - isp1;
|
symbol = shift_symbol[i];
|
||||||
|
j = i;
|
||||||
|
while (j > 0 && shift_symbol[j - 1] > symbol)
|
||||||
|
{
|
||||||
|
shift_symbol[j] = shift_symbol[j - 1];
|
||||||
|
j--;
|
||||||
|
}
|
||||||
|
shift_symbol[j] = symbol;
|
||||||
|
}
|
||||||
|
|
||||||
p = (core *) xmalloc((unsigned) (sizeof(core) + (n - 1) * sizeof(short)));
|
for (i = 0; i < nshifts; i++)
|
||||||
p->accessing_symbol = symbol;
|
{
|
||||||
p->number = nstates;
|
symbol = shift_symbol[i];
|
||||||
p->nitems = n;
|
shiftset[i] = get_state (symbol);
|
||||||
|
}
|
||||||
isp2 = p->items;
|
|
||||||
while (isp1 < iend)
|
|
||||||
*isp2++ = *isp1++;
|
|
||||||
|
|
||||||
last_state->next = p;
|
|
||||||
last_state = p;
|
|
||||||
|
|
||||||
nstates++;
|
|
||||||
|
|
||||||
return p;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
initialize_states (void)
|
new_states (void)
|
||||||
{
|
{
|
||||||
register core *p;
|
core *p;
|
||||||
/* register unsigned *rp1; JF unused */
|
|
||||||
/* register unsigned *rp2; JF unused */
|
|
||||||
/* register unsigned *rend; JF unused */
|
|
||||||
|
|
||||||
p = (core *) xmalloc((unsigned) (sizeof(core) - sizeof(short)));
|
p = (core *) xmalloc ((unsigned) (sizeof (core) - sizeof (short)));
|
||||||
first_state = last_state = this_state = p;
|
first_state = last_state = this_state = p;
|
||||||
nstates = 1;
|
nstates = 1;
|
||||||
}
|
}
|
||||||
@@ -413,13 +363,13 @@ initialize_states (void)
|
|||||||
static void
|
static void
|
||||||
save_shifts (void)
|
save_shifts (void)
|
||||||
{
|
{
|
||||||
register shifts *p;
|
shifts *p;
|
||||||
register short *sp1;
|
short *sp1;
|
||||||
register short *sp2;
|
short *sp2;
|
||||||
register short *send;
|
short *send;
|
||||||
|
|
||||||
p = (shifts *) xmalloc((unsigned) (sizeof(shifts) +
|
p = (shifts *) xmalloc ((unsigned) (sizeof (shifts) +
|
||||||
(nshifts - 1) * sizeof(short)));
|
(nshifts - 1) * sizeof (short)));
|
||||||
|
|
||||||
p->number = this_state->number;
|
p->number = this_state->number;
|
||||||
p->nshifts = nshifts;
|
p->nshifts = nshifts;
|
||||||
@@ -444,80 +394,52 @@ save_shifts (void)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*------------------------------------------------------------------.
|
||||||
|
| Subroutine of augment_automaton. Create the next-to-final state, |
|
||||||
|
| to which a shift has already been made in the initial state. |
|
||||||
|
`------------------------------------------------------------------*/
|
||||||
|
|
||||||
/* find which rules can be used for reduction transitions from the current state
|
|
||||||
and make a reductions structure for the state to record their rule numbers. */
|
|
||||||
static void
|
static void
|
||||||
save_reductions (void)
|
insert_start_shift (void)
|
||||||
{
|
{
|
||||||
register short *isp;
|
core *statep;
|
||||||
register short *rp1;
|
shifts *sp;
|
||||||
register short *rp2;
|
|
||||||
register int item;
|
|
||||||
register int count;
|
|
||||||
register reductions *p;
|
|
||||||
|
|
||||||
short *rend;
|
statep = (core *) xmalloc ((unsigned) (sizeof (core) - sizeof (short)));
|
||||||
|
statep->number = nstates;
|
||||||
|
statep->accessing_symbol = start_symbol;
|
||||||
|
|
||||||
/* find and count the active items that represent ends of rules */
|
last_state->next = statep;
|
||||||
|
last_state = statep;
|
||||||
|
|
||||||
count = 0;
|
/* Make a shift from this state to (what will be) the final state. */
|
||||||
for (isp = itemset; isp < itemsetend; isp++)
|
sp = NEW (shifts);
|
||||||
{
|
sp->number = nstates++;
|
||||||
item = ritem[*isp];
|
sp->nshifts = 1;
|
||||||
if (item < 0)
|
sp->shifts[0] = nstates;
|
||||||
{
|
|
||||||
redset[count++] = -item;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* make a reductions structure and copy the data into it. */
|
last_shift->next = sp;
|
||||||
|
last_shift = sp;
|
||||||
if (count)
|
|
||||||
{
|
|
||||||
p = (reductions *) xmalloc((unsigned) (sizeof(reductions) +
|
|
||||||
(count - 1) * sizeof(short)));
|
|
||||||
|
|
||||||
p->number = this_state->number;
|
|
||||||
p->nreds = count;
|
|
||||||
|
|
||||||
rp1 = redset;
|
|
||||||
rp2 = p->rules;
|
|
||||||
rend = rp1 + count;
|
|
||||||
|
|
||||||
while (rp1 < rend)
|
|
||||||
*rp2++ = *rp1++;
|
|
||||||
|
|
||||||
if (last_reduction)
|
|
||||||
{
|
|
||||||
last_reduction->next = p;
|
|
||||||
last_reduction = p;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
first_reduction = p;
|
|
||||||
last_reduction = p;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*------------------------------------------------------------------.
|
||||||
|
| Make sure that the initial state has a shift that accepts the |
|
||||||
|
| grammar's start symbol and goes to the next-to-final state, which |
|
||||||
|
| has a shift going to the final state, which has a shift to the |
|
||||||
|
| termination state. Create such states and shifts if they don't |
|
||||||
|
| happen to exist already. |
|
||||||
|
`------------------------------------------------------------------*/
|
||||||
|
|
||||||
/* Make sure that the initial state has a shift that accepts the
|
|
||||||
grammar's start symbol and goes to the next-to-final state,
|
|
||||||
which has a shift going to the final state, which has a shift
|
|
||||||
to the termination state.
|
|
||||||
Create such states and shifts if they don't happen to exist already. */
|
|
||||||
static void
|
static void
|
||||||
augment_automaton (void)
|
augment_automaton (void)
|
||||||
{
|
{
|
||||||
register int i;
|
int i;
|
||||||
register int k;
|
int k;
|
||||||
/* register int found; JF unused */
|
core *statep;
|
||||||
register core *statep;
|
shifts *sp;
|
||||||
register shifts *sp;
|
shifts *sp2;
|
||||||
register shifts *sp2;
|
shifts *sp1 = NULL;
|
||||||
register shifts *sp1 = NULL;
|
|
||||||
|
|
||||||
sp = first_shift;
|
sp = first_shift;
|
||||||
|
|
||||||
@@ -531,13 +453,13 @@ augment_automaton (void)
|
|||||||
/* The states reached by shifts from first_state are numbered 1...K.
|
/* The states reached by shifts from first_state are numbered 1...K.
|
||||||
Look for one reached by start_symbol. */
|
Look for one reached by start_symbol. */
|
||||||
while (statep->accessing_symbol < start_symbol
|
while (statep->accessing_symbol < start_symbol
|
||||||
&& statep->number < k)
|
&& statep->number < k)
|
||||||
statep = statep->next;
|
statep = statep->next;
|
||||||
|
|
||||||
if (statep->accessing_symbol == start_symbol)
|
if (statep->accessing_symbol == start_symbol)
|
||||||
{
|
{
|
||||||
/* We already have a next-to-final state.
|
/* We already have a next-to-final state.
|
||||||
Make sure it has a shift to what will be the final state. */
|
Make sure it has a shift to what will be the final state. */
|
||||||
k = statep->number;
|
k = statep->number;
|
||||||
|
|
||||||
while (sp && sp->number < k)
|
while (sp && sp->number < k)
|
||||||
@@ -548,8 +470,10 @@ augment_automaton (void)
|
|||||||
|
|
||||||
if (sp && sp->number == k)
|
if (sp && sp->number == k)
|
||||||
{
|
{
|
||||||
sp2 = (shifts *) xmalloc((unsigned) (sizeof(shifts)
|
sp2 = (shifts *) xmalloc ((unsigned) (sizeof (shifts)
|
||||||
+ sp->nshifts * sizeof(short)));
|
+
|
||||||
|
sp->nshifts *
|
||||||
|
sizeof (short)));
|
||||||
sp2->number = k;
|
sp2->number = k;
|
||||||
sp2->nshifts = sp->nshifts + 1;
|
sp2->nshifts = sp->nshifts + 1;
|
||||||
sp2->shifts[0] = nstates;
|
sp2->shifts[0] = nstates;
|
||||||
@@ -562,11 +486,11 @@ augment_automaton (void)
|
|||||||
sp1->next = sp2;
|
sp1->next = sp2;
|
||||||
if (sp == last_shift)
|
if (sp == last_shift)
|
||||||
last_shift = sp2;
|
last_shift = sp2;
|
||||||
FREE(sp);
|
FREE (sp);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
sp2 = NEW(shifts);
|
sp2 = NEW (shifts);
|
||||||
sp2->number = k;
|
sp2->number = k;
|
||||||
sp2->nshifts = 1;
|
sp2->nshifts = 1;
|
||||||
sp2->shifts[0] = nstates;
|
sp2->shifts[0] = nstates;
|
||||||
@@ -582,11 +506,11 @@ augment_automaton (void)
|
|||||||
{
|
{
|
||||||
/* There is no next-to-final state as yet. */
|
/* There is no next-to-final state as yet. */
|
||||||
/* Add one more shift in first_shift,
|
/* Add one more shift in first_shift,
|
||||||
going to the next-to-final state (yet to be made). */
|
going to the next-to-final state (yet to be made). */
|
||||||
sp = first_shift;
|
sp = first_shift;
|
||||||
|
|
||||||
sp2 = (shifts *) xmalloc(sizeof(shifts)
|
sp2 = (shifts *) xmalloc (sizeof (shifts)
|
||||||
+ sp->nshifts * sizeof(short));
|
+ sp->nshifts * sizeof (short));
|
||||||
sp2->nshifts = sp->nshifts + 1;
|
sp2->nshifts = sp->nshifts + 1;
|
||||||
|
|
||||||
/* Stick this shift into the vector at the proper place. */
|
/* Stick this shift into the vector at the proper place. */
|
||||||
@@ -602,24 +526,24 @@ augment_automaton (void)
|
|||||||
sp2->shifts[k++] = nstates;
|
sp2->shifts[k++] = nstates;
|
||||||
|
|
||||||
/* Patch sp2 into the chain of shifts
|
/* Patch sp2 into the chain of shifts
|
||||||
in place of sp, at the beginning. */
|
in place of sp, at the beginning. */
|
||||||
sp2->next = sp->next;
|
sp2->next = sp->next;
|
||||||
first_shift = sp2;
|
first_shift = sp2;
|
||||||
if (last_shift == sp)
|
if (last_shift == sp)
|
||||||
last_shift = sp2;
|
last_shift = sp2;
|
||||||
|
|
||||||
FREE(sp);
|
FREE (sp);
|
||||||
|
|
||||||
/* Create the next-to-final state, with shift to
|
/* Create the next-to-final state, with shift to
|
||||||
what will be the final state. */
|
what will be the final state. */
|
||||||
insert_start_shift();
|
insert_start_shift ();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
/* The initial state didn't even have any shifts.
|
/* The initial state didn't even have any shifts.
|
||||||
Give it one shift, to the next-to-final state. */
|
Give it one shift, to the next-to-final state. */
|
||||||
sp = NEW(shifts);
|
sp = NEW (shifts);
|
||||||
sp->nshifts = 1;
|
sp->nshifts = 1;
|
||||||
sp->shifts[0] = nstates;
|
sp->shifts[0] = nstates;
|
||||||
|
|
||||||
@@ -629,15 +553,15 @@ augment_automaton (void)
|
|||||||
|
|
||||||
/* Create the next-to-final state, with shift to
|
/* Create the next-to-final state, with shift to
|
||||||
what will be the final state. */
|
what will be the final state. */
|
||||||
insert_start_shift();
|
insert_start_shift ();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
/* There are no shifts for any state.
|
/* There are no shifts for any state.
|
||||||
Make one shift, from the initial state to the next-to-final state. */
|
Make one shift, from the initial state to the next-to-final state. */
|
||||||
|
|
||||||
sp = NEW(shifts);
|
sp = NEW (shifts);
|
||||||
sp->nshifts = 1;
|
sp->nshifts = 1;
|
||||||
sp->shifts[0] = nstates;
|
sp->shifts[0] = nstates;
|
||||||
|
|
||||||
@@ -646,20 +570,20 @@ augment_automaton (void)
|
|||||||
last_shift = sp;
|
last_shift = sp;
|
||||||
|
|
||||||
/* Create the next-to-final state, with shift to
|
/* Create the next-to-final state, with shift to
|
||||||
what will be the final state. */
|
what will be the final state. */
|
||||||
insert_start_shift();
|
insert_start_shift ();
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Make the final state--the one that follows a shift from the
|
/* Make the final state--the one that follows a shift from the
|
||||||
next-to-final state.
|
next-to-final state.
|
||||||
The symbol for that shift is 0 (end-of-file). */
|
The symbol for that shift is 0 (end-of-file). */
|
||||||
statep = (core *) xmalloc((unsigned) (sizeof(core) - sizeof(short)));
|
statep = (core *) xmalloc ((unsigned) (sizeof (core) - sizeof (short)));
|
||||||
statep->number = nstates;
|
statep->number = nstates;
|
||||||
last_state->next = statep;
|
last_state->next = statep;
|
||||||
last_state = statep;
|
last_state = statep;
|
||||||
|
|
||||||
/* Make the shift from the final state to the termination state. */
|
/* Make the shift from the final state to the termination state. */
|
||||||
sp = NEW(shifts);
|
sp = NEW (shifts);
|
||||||
sp->number = nstates++;
|
sp->number = nstates++;
|
||||||
sp->nshifts = 1;
|
sp->nshifts = 1;
|
||||||
sp->shifts[0] = nstates;
|
sp->shifts[0] = nstates;
|
||||||
@@ -671,35 +595,111 @@ augment_automaton (void)
|
|||||||
final_state = nstates;
|
final_state = nstates;
|
||||||
|
|
||||||
/* Make the termination state. */
|
/* Make the termination state. */
|
||||||
statep = (core *) xmalloc((unsigned) (sizeof(core) - sizeof(short)));
|
statep = (core *) xmalloc ((unsigned) (sizeof (core) - sizeof (short)));
|
||||||
statep->number = nstates++;
|
statep->number = nstates++;
|
||||||
last_state->next = statep;
|
last_state->next = statep;
|
||||||
last_state = statep;
|
last_state = statep;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/* subroutine of augment_automaton.
|
/*----------------------------------------------------------------.
|
||||||
Create the next-to-final state, to which a shift has already been made in
|
| Find which rules can be used for reduction transitions from the |
|
||||||
the initial state. */
|
| current state and make a reductions structure for the state to |
|
||||||
|
| record their rule numbers. |
|
||||||
|
`----------------------------------------------------------------*/
|
||||||
|
|
||||||
static void
|
static void
|
||||||
insert_start_shift (void)
|
save_reductions (void)
|
||||||
{
|
{
|
||||||
register core *statep;
|
short *isp;
|
||||||
register shifts *sp;
|
short *rp1;
|
||||||
|
short *rp2;
|
||||||
|
int item;
|
||||||
|
int count;
|
||||||
|
reductions *p;
|
||||||
|
|
||||||
statep = (core *) xmalloc((unsigned) (sizeof(core) - sizeof(short)));
|
short *rend;
|
||||||
statep->number = nstates;
|
|
||||||
statep->accessing_symbol = start_symbol;
|
|
||||||
|
|
||||||
last_state->next = statep;
|
/* Find and count the active items that represent ends of rules. */
|
||||||
last_state = statep;
|
|
||||||
|
|
||||||
/* Make a shift from this state to (what will be) the final state. */
|
count = 0;
|
||||||
sp = NEW(shifts);
|
for (isp = itemset; isp < itemsetend; isp++)
|
||||||
sp->number = nstates++;
|
{
|
||||||
sp->nshifts = 1;
|
item = ritem[*isp];
|
||||||
sp->shifts[0] = nstates;
|
if (item < 0)
|
||||||
|
redset[count++] = -item;
|
||||||
|
}
|
||||||
|
|
||||||
last_shift->next = sp;
|
/* Make a reductions structure and copy the data into it. */
|
||||||
last_shift = sp;
|
|
||||||
|
if (count)
|
||||||
|
{
|
||||||
|
p = (reductions *) xmalloc ((unsigned) (sizeof (reductions) +
|
||||||
|
(count - 1) * sizeof (short)));
|
||||||
|
|
||||||
|
p->number = this_state->number;
|
||||||
|
p->nreds = count;
|
||||||
|
|
||||||
|
rp1 = redset;
|
||||||
|
rp2 = p->rules;
|
||||||
|
rend = rp1 + count;
|
||||||
|
|
||||||
|
for (/* nothing */; rp1 < rend; ++rp1, ++rp2)
|
||||||
|
*rp2 = *rp1;
|
||||||
|
|
||||||
|
if (last_reduction)
|
||||||
|
{
|
||||||
|
last_reduction->next = p;
|
||||||
|
last_reduction = p;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
first_reduction = p;
|
||||||
|
last_reduction = p;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*-------------------------------------------------------------------.
|
||||||
|
| Compute the nondeterministic finite state machine (see state.h for |
|
||||||
|
| details) from the grammar. |
|
||||||
|
`-------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
void
|
||||||
|
generate_states (void)
|
||||||
|
{
|
||||||
|
allocate_storage ();
|
||||||
|
new_closure (nitems);
|
||||||
|
new_states ();
|
||||||
|
|
||||||
|
while (this_state)
|
||||||
|
{
|
||||||
|
/* Set up ruleset and itemset for the transitions out of this
|
||||||
|
state. ruleset gets a 1 bit for each rule that could reduce
|
||||||
|
now. itemset gets a vector of all the items that could be
|
||||||
|
accepted next. */
|
||||||
|
closure (this_state->items, this_state->nitems);
|
||||||
|
/* record the reductions allowed out of this state */
|
||||||
|
save_reductions ();
|
||||||
|
/* find the itemsets of the states that shifts can reach */
|
||||||
|
new_itemsets ();
|
||||||
|
/* find or create the core structures for those states */
|
||||||
|
append_states ();
|
||||||
|
|
||||||
|
/* create the shifts structures for the shifts to those states,
|
||||||
|
now that the state numbers transitioning to are known */
|
||||||
|
if (nshifts > 0)
|
||||||
|
save_shifts ();
|
||||||
|
|
||||||
|
/* states are queued when they are created; process them all */
|
||||||
|
this_state = this_state->next;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* discard various storage */
|
||||||
|
free_closure ();
|
||||||
|
free_storage ();
|
||||||
|
|
||||||
|
/* set up initial and final states as parser wants them */
|
||||||
|
augment_automaton ();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -18,8 +18,10 @@ bison_SOURCES = LR0.c allocate.c closure.c complain.c conflicts.c \
|
|||||||
|
|
||||||
EXTRA_bison_SOURCES = vmsgetargs.c
|
EXTRA_bison_SOURCES = vmsgetargs.c
|
||||||
|
|
||||||
noinst_HEADERS = alloc.h complain.h files.h getargs.h gram.h lex.h \
|
noinst_HEADERS = alloc.h closure.h complain.h \
|
||||||
derives.h state.h \
|
derives.h \
|
||||||
|
files.h getargs.h gram.h lex.h \
|
||||||
|
state.h \
|
||||||
symtab.h system.h types.h
|
symtab.h system.h types.h
|
||||||
|
|
||||||
data_DATA = bison.simple bison.hairy
|
data_DATA = bison.simple bison.hairy
|
||||||
|
|||||||
333
src/closure.c
333
src/closure.c
@@ -19,52 +19,15 @@
|
|||||||
02111-1307, USA. */
|
02111-1307, USA. */
|
||||||
|
|
||||||
|
|
||||||
/* Subroutines of file LR0.c.
|
|
||||||
|
|
||||||
Entry points:
|
|
||||||
|
|
||||||
closure (items, n)
|
|
||||||
|
|
||||||
Given a vector of item numbers items, of length n, set up ruleset and
|
|
||||||
itemset to indicate what rules could be run and which items could be
|
|
||||||
accepted when those items are the active ones.
|
|
||||||
|
|
||||||
ruleset contains a bit for each rule. closure sets the bits for all
|
|
||||||
rules which could potentially describe the next input to be read.
|
|
||||||
|
|
||||||
itemset is a vector of item numbers; itemsetend points to just beyond
|
|
||||||
the end of the part of it that is significant. closure places there
|
|
||||||
the indices of all items which represent units of input that could
|
|
||||||
arrive next.
|
|
||||||
|
|
||||||
initialize_closure (n)
|
|
||||||
|
|
||||||
Allocates the itemset and ruleset vectors, and precomputes useful data
|
|
||||||
so that closure can be called. n is the number of elements to
|
|
||||||
allocate for itemset.
|
|
||||||
|
|
||||||
finalize_closure ()
|
|
||||||
|
|
||||||
Frees itemset, ruleset and internal data.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "system.h"
|
#include "system.h"
|
||||||
#include "alloc.h"
|
#include "alloc.h"
|
||||||
#include "gram.h"
|
#include "gram.h"
|
||||||
|
#include "closure.h"
|
||||||
|
|
||||||
extern short **derives;
|
extern short **derives;
|
||||||
extern char **tags;
|
extern char **tags;
|
||||||
|
|
||||||
extern void initialize_closure PARAMS((int));
|
extern void RTC PARAMS ((unsigned *, int));
|
||||||
extern void closure PARAMS((short *, int));
|
|
||||||
extern void finalize_closure PARAMS((void));
|
|
||||||
|
|
||||||
static void set_fderives PARAMS((void));
|
|
||||||
static void set_firsts PARAMS((void));
|
|
||||||
|
|
||||||
extern void RTC PARAMS((unsigned *, int));
|
|
||||||
|
|
||||||
short *itemset;
|
short *itemset;
|
||||||
short *itemsetend;
|
short *itemsetend;
|
||||||
@@ -79,47 +42,143 @@ static int rulesetsize;
|
|||||||
|
|
||||||
/* number of words required to hold a bit for each variable */
|
/* number of words required to hold a bit for each variable */
|
||||||
static int varsetsize;
|
static int varsetsize;
|
||||||
|
|
||||||
|
#if DEBUG
|
||||||
|
|
||||||
#ifdef DEBUG
|
/*-----------------.
|
||||||
static void print_closure PARAMS((int));
|
| Debugging code. |
|
||||||
static void print_fderives PARAMS((void));
|
`-----------------*/
|
||||||
static void print_firsts PARAMS((void));
|
|
||||||
#endif
|
|
||||||
|
|
||||||
void
|
static void
|
||||||
initialize_closure (int n)
|
print_closure (int n)
|
||||||
{
|
{
|
||||||
itemset = NEW2(n, short);
|
short *isp;
|
||||||
|
|
||||||
rulesetsize = WORDSIZE(nrules + 1);
|
printf ("\n\nn = %d\n\n", n);
|
||||||
ruleset = NEW2(rulesetsize, unsigned);
|
for (isp = itemset; isp < itemsetend; isp++)
|
||||||
|
printf (" %d\n", *isp);
|
||||||
set_fderives();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static void
|
||||||
|
print_firsts (void)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
int j;
|
||||||
|
unsigned *rowp;
|
||||||
|
|
||||||
|
printf ("\n\n\nFIRSTS\n\n");
|
||||||
|
|
||||||
|
for (i = ntokens; i < nsyms; i++)
|
||||||
|
{
|
||||||
|
printf ("\n\n%s firsts\n\n", tags[i]);
|
||||||
|
|
||||||
|
rowp = firsts + ((i - ntokens) * varsetsize);
|
||||||
|
|
||||||
|
for (j = 0; j < nvars; j++)
|
||||||
|
if (BITISSET (rowp, j))
|
||||||
|
printf (" %s\n", tags[j + ntokens]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static void
|
||||||
|
print_fderives (void)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
int j;
|
||||||
|
unsigned *rp;
|
||||||
|
|
||||||
|
printf ("\n\n\nFDERIVES\n");
|
||||||
|
|
||||||
|
for (i = ntokens; i < nsyms; i++)
|
||||||
|
{
|
||||||
|
printf ("\n\n%s derives\n\n", tags[i]);
|
||||||
|
rp = fderives + i * rulesetsize;
|
||||||
|
|
||||||
|
for (j = 0; j <= nrules; j++)
|
||||||
|
if (BITISSET (rp, j))
|
||||||
|
printf (" %d\n", j);
|
||||||
|
}
|
||||||
|
|
||||||
|
fflush (stdout);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/*-------------------------------------------------------------------.
|
||||||
|
| Set FIRSTS to be an NVARS by NVARS bit matrix indicating which |
|
||||||
|
| items can represent the beginning of the input corresponding to |
|
||||||
|
| which other items. |
|
||||||
|
| |
|
||||||
|
| For example, if some rule expands symbol 5 into the sequence of |
|
||||||
|
| symbols 8 3 20, the symbol 8 can be the beginning of the data for |
|
||||||
|
| symbol 5, so the bit [8 - ntokens, 5 - ntokens] in firsts is set. |
|
||||||
|
`-------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
static void
|
||||||
|
set_firsts (void)
|
||||||
|
{
|
||||||
|
unsigned *row;
|
||||||
|
int symbol;
|
||||||
|
short *sp;
|
||||||
|
int rowsize;
|
||||||
|
|
||||||
|
int i;
|
||||||
|
|
||||||
|
varsetsize = rowsize = WORDSIZE (nvars);
|
||||||
|
|
||||||
|
firsts = NEW2 (nvars * rowsize, unsigned);
|
||||||
|
|
||||||
|
row = firsts;
|
||||||
|
for (i = ntokens; i < nsyms; i++)
|
||||||
|
{
|
||||||
|
sp = derives[i];
|
||||||
|
while (*sp >= 0)
|
||||||
|
{
|
||||||
|
symbol = ritem[rrhs[*sp++]];
|
||||||
|
if (ISVAR (symbol))
|
||||||
|
{
|
||||||
|
symbol -= ntokens;
|
||||||
|
SETBIT (row, symbol);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
row += rowsize;
|
||||||
|
}
|
||||||
|
|
||||||
|
RTC (firsts, nvars);
|
||||||
|
|
||||||
|
#ifdef DEBUG
|
||||||
|
print_firsts ();
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
/*-------------------------------------------------------------------.
|
||||||
|
| Set FDERIVES to an NVARS by NRULES matrix of bits indicating which |
|
||||||
|
| rules can help derive the beginning of the data for each |
|
||||||
|
| nonterminal. |
|
||||||
|
| |
|
||||||
|
| For example, if symbol 5 can be derived as the sequence of symbols |
|
||||||
|
| 8 3 20, and one of the rules for deriving symbol 8 is rule 4, then |
|
||||||
|
| the [5 - NTOKENS, 4] bit in FDERIVES is set. |
|
||||||
|
`-------------------------------------------------------------------*/
|
||||||
|
|
||||||
/* set fderives to an nvars by nrules matrix of bits
|
|
||||||
indicating which rules can help derive the beginning of the data
|
|
||||||
for each nonterminal. For example, if symbol 5 can be derived as
|
|
||||||
the sequence of symbols 8 3 20, and one of the rules for deriving
|
|
||||||
symbol 8 is rule 4, then the [5 - ntokens, 4] bit in fderives is set. */
|
|
||||||
static void
|
static void
|
||||||
set_fderives (void)
|
set_fderives (void)
|
||||||
{
|
{
|
||||||
register unsigned *rrow;
|
unsigned *rrow;
|
||||||
register unsigned *vrow;
|
unsigned *vrow;
|
||||||
register int j;
|
int j;
|
||||||
register unsigned cword;
|
unsigned cword;
|
||||||
register short *rp;
|
short *rp;
|
||||||
register int b;
|
int b;
|
||||||
|
|
||||||
int ruleno;
|
int ruleno;
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
fderives = NEW2(nvars * rulesetsize, unsigned) - ntokens * rulesetsize;
|
fderives = NEW2 (nvars * rulesetsize, unsigned) - ntokens * rulesetsize;
|
||||||
|
|
||||||
set_firsts();
|
set_firsts ();
|
||||||
|
|
||||||
rrow = fderives + ntokens * rulesetsize;
|
rrow = fderives + ntokens * rulesetsize;
|
||||||
|
|
||||||
@@ -135,7 +194,7 @@ set_fderives (void)
|
|||||||
rp = derives[j];
|
rp = derives[j];
|
||||||
while ((ruleno = *rp++) > 0)
|
while ((ruleno = *rp++) > 0)
|
||||||
{
|
{
|
||||||
SETBIT(rrow, ruleno);
|
SETBIT (rrow, ruleno);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -151,71 +210,34 @@ set_fderives (void)
|
|||||||
}
|
}
|
||||||
|
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
print_fderives();
|
print_fderives ();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
FREE(firsts);
|
FREE (firsts);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void
|
||||||
|
new_closure (int n)
|
||||||
/* set firsts to be an nvars by nvars bit matrix indicating which
|
|
||||||
items can represent the beginning of the input corresponding to
|
|
||||||
which other items.
|
|
||||||
|
|
||||||
For example, if some rule expands symbol 5 into the sequence of
|
|
||||||
symbols 8 3 20, the symbol 8 can be the beginning of the data for
|
|
||||||
symbol 5, so the bit [8 - ntokens, 5 - ntokens] in firsts is
|
|
||||||
set. */
|
|
||||||
|
|
||||||
static void
|
|
||||||
set_firsts (void)
|
|
||||||
{
|
{
|
||||||
register unsigned *row;
|
itemset = NEW2 (n, short);
|
||||||
/* register int done; JF unused */
|
|
||||||
register int symbol;
|
|
||||||
register short *sp;
|
|
||||||
register int rowsize;
|
|
||||||
|
|
||||||
int i;
|
rulesetsize = WORDSIZE (nrules + 1);
|
||||||
|
ruleset = NEW2 (rulesetsize, unsigned);
|
||||||
|
|
||||||
varsetsize = rowsize = WORDSIZE(nvars);
|
set_fderives ();
|
||||||
|
|
||||||
firsts = NEW2(nvars * rowsize, unsigned);
|
|
||||||
|
|
||||||
row = firsts;
|
|
||||||
for (i = ntokens; i < nsyms; i++)
|
|
||||||
{
|
|
||||||
sp = derives[i];
|
|
||||||
while (*sp >= 0)
|
|
||||||
{
|
|
||||||
symbol = ritem[rrhs[*sp++]];
|
|
||||||
if (ISVAR(symbol))
|
|
||||||
{
|
|
||||||
symbol -= ntokens;
|
|
||||||
SETBIT(row, symbol);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
row += rowsize;
|
|
||||||
}
|
|
||||||
|
|
||||||
RTC(firsts, nvars);
|
|
||||||
|
|
||||||
#ifdef DEBUG
|
|
||||||
print_firsts ();
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
closure (short *core, int n)
|
closure (short *core, int n)
|
||||||
{
|
{
|
||||||
register int ruleno;
|
int ruleno;
|
||||||
register unsigned word;
|
unsigned word;
|
||||||
register short *csp;
|
short *csp;
|
||||||
register unsigned *dsp;
|
unsigned *dsp;
|
||||||
register unsigned *rsp;
|
unsigned *rsp;
|
||||||
|
|
||||||
short *csend;
|
short *csend;
|
||||||
unsigned *rsend;
|
unsigned *rsend;
|
||||||
@@ -241,7 +263,7 @@ closure (short *core, int n)
|
|||||||
while (csp < csend)
|
while (csp < csend)
|
||||||
{
|
{
|
||||||
symbol = ritem[*csp++];
|
symbol = ritem[*csp++];
|
||||||
if (ISVAR(symbol))
|
if (ISVAR (symbol))
|
||||||
{
|
{
|
||||||
dsp = fderives + symbol * rulesetsize;
|
dsp = fderives + symbol * rulesetsize;
|
||||||
rsp = ruleset;
|
rsp = ruleset;
|
||||||
@@ -264,7 +286,7 @@ closure (short *core, int n)
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
register int b;
|
int b;
|
||||||
|
|
||||||
for (b = 0; b < BITS_PER_WORD; b++)
|
for (b = 0; b < BITS_PER_WORD; b++)
|
||||||
{
|
{
|
||||||
@@ -284,77 +306,16 @@ closure (short *core, int n)
|
|||||||
while (csp < csend)
|
while (csp < csend)
|
||||||
*itemsetend++ = *csp++;
|
*itemsetend++ = *csp++;
|
||||||
|
|
||||||
#ifdef DEBUG
|
#if DEBUG
|
||||||
print_closure(n);
|
print_closure (n);
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
finalize_closure (void)
|
free_closure (void)
|
||||||
{
|
{
|
||||||
FREE(itemset);
|
FREE (itemset);
|
||||||
FREE(ruleset);
|
FREE (ruleset);
|
||||||
FREE(fderives + ntokens * rulesetsize);
|
FREE (fderives + ntokens * rulesetsize);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
#ifdef DEBUG
|
|
||||||
|
|
||||||
static void
|
|
||||||
print_closure(int n)
|
|
||||||
{
|
|
||||||
register short *isp;
|
|
||||||
|
|
||||||
printf ("\n\nn = %d\n\n", n);
|
|
||||||
for (isp = itemset; isp < itemsetend; isp++)
|
|
||||||
printf (" %d\n", *isp);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
static void
|
|
||||||
print_firsts (void)
|
|
||||||
{
|
|
||||||
register int i;
|
|
||||||
register int j;
|
|
||||||
register unsigned *rowp;
|
|
||||||
|
|
||||||
printf ("\n\n\nFIRSTS\n\n");
|
|
||||||
|
|
||||||
for (i = ntokens; i < nsyms; i++)
|
|
||||||
{
|
|
||||||
printf ("\n\n%s firsts\n\n", tags[i]);
|
|
||||||
|
|
||||||
rowp = firsts + ((i - ntokens) * varsetsize);
|
|
||||||
|
|
||||||
for (j = 0; j < nvars; j++)
|
|
||||||
if (BITISSET (rowp, j))
|
|
||||||
printf (" %s\n", tags[j + ntokens]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
static void
|
|
||||||
print_fderives (void)
|
|
||||||
{
|
|
||||||
register int i;
|
|
||||||
register int j;
|
|
||||||
register unsigned *rp;
|
|
||||||
|
|
||||||
printf ("\n\n\nFDERIVES\n");
|
|
||||||
|
|
||||||
for (i = ntokens; i < nsyms; i++)
|
|
||||||
{
|
|
||||||
printf ("\n\n%s derives\n\n", tags[i]);
|
|
||||||
rp = fderives + i * rulesetsize;
|
|
||||||
|
|
||||||
for (j = 0; j <= nrules; j++)
|
|
||||||
if (BITISSET (rp, j))
|
|
||||||
printf (" %d\n", j);
|
|
||||||
}
|
|
||||||
|
|
||||||
fflush(stdout);
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|||||||
Reference in New Issue
Block a user