| Guido van Rossum | f70e43a | 1991-02-19 12:39:46 +0000 | [diff] [blame] | 1 | /*********************************************************** | 
| Guido van Rossum | b9f8d6e | 1995-01-04 19:08:09 +0000 | [diff] [blame] | 2 | Copyright 1991-1995 by Stichting Mathematisch Centrum, Amsterdam, | 
|  | 3 | The Netherlands. | 
| Guido van Rossum | f70e43a | 1991-02-19 12:39:46 +0000 | [diff] [blame] | 4 |  | 
|  | 5 | All Rights Reserved | 
|  | 6 |  | 
| Guido van Rossum | d266eb4 | 1996-10-25 14:44:06 +0000 | [diff] [blame] | 7 | Permission to use, copy, modify, and distribute this software and its | 
|  | 8 | documentation for any purpose and without fee is hereby granted, | 
| Guido van Rossum | f70e43a | 1991-02-19 12:39:46 +0000 | [diff] [blame] | 9 | provided that the above copyright notice appear in all copies and that | 
| Guido van Rossum | d266eb4 | 1996-10-25 14:44:06 +0000 | [diff] [blame] | 10 | both that copyright notice and this permission notice appear in | 
| Guido van Rossum | f70e43a | 1991-02-19 12:39:46 +0000 | [diff] [blame] | 11 | supporting documentation, and that the names of Stichting Mathematisch | 
| Guido van Rossum | d266eb4 | 1996-10-25 14:44:06 +0000 | [diff] [blame] | 12 | Centrum or CWI or Corporation for National Research Initiatives or | 
|  | 13 | CNRI not be used in advertising or publicity pertaining to | 
|  | 14 | distribution of the software without specific, written prior | 
|  | 15 | permission. | 
| Guido van Rossum | f70e43a | 1991-02-19 12:39:46 +0000 | [diff] [blame] | 16 |  | 
| Guido van Rossum | d266eb4 | 1996-10-25 14:44:06 +0000 | [diff] [blame] | 17 | While CWI is the initial source for this software, a modified version | 
|  | 18 | is made available by the Corporation for National Research Initiatives | 
|  | 19 | (CNRI) at the Internet address ftp://ftp.python.org. | 
|  | 20 |  | 
|  | 21 | STICHTING MATHEMATISCH CENTRUM AND CNRI DISCLAIM ALL WARRANTIES WITH | 
|  | 22 | REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF | 
|  | 23 | MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL STICHTING MATHEMATISCH | 
|  | 24 | CENTRUM OR CNRI BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL | 
|  | 25 | DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR | 
|  | 26 | PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER | 
|  | 27 | TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR | 
|  | 28 | PERFORMANCE OF THIS SOFTWARE. | 
| Guido van Rossum | f70e43a | 1991-02-19 12:39:46 +0000 | [diff] [blame] | 29 |  | 
|  | 30 | ******************************************************************/ | 
|  | 31 |  | 
| Guido van Rossum | 85a5fbb | 1990-10-14 12:07:46 +0000 | [diff] [blame] | 32 | /* Computation of FIRST stets */ | 
|  | 33 |  | 
| Guido van Rossum | 3f5da24 | 1990-12-20 15:06:42 +0000 | [diff] [blame] | 34 | #include "pgenheaders.h" | 
| Guido van Rossum | 85a5fbb | 1990-10-14 12:07:46 +0000 | [diff] [blame] | 35 | #include "grammar.h" | 
|  | 36 | #include "token.h" | 
|  | 37 |  | 
| Guido van Rossum | 86bea46 | 1997-04-29 21:03:06 +0000 | [diff] [blame] | 38 | extern int Py_DebugFlag; | 
| Guido van Rossum | 85a5fbb | 1990-10-14 12:07:46 +0000 | [diff] [blame] | 39 |  | 
| Guido van Rossum | 3f5da24 | 1990-12-20 15:06:42 +0000 | [diff] [blame] | 40 | /* Forward */ | 
| Guido van Rossum | 86bea46 | 1997-04-29 21:03:06 +0000 | [diff] [blame] | 41 | static void calcfirstset Py_PROTO((grammar *, dfa *)); | 
| Guido van Rossum | 3f5da24 | 1990-12-20 15:06:42 +0000 | [diff] [blame] | 42 |  | 
|  | 43 | void | 
|  | 44 | addfirstsets(g) | 
|  | 45 | grammar *g; | 
|  | 46 | { | 
|  | 47 | int i; | 
|  | 48 | dfa *d; | 
|  | 49 |  | 
|  | 50 | printf("Adding FIRST sets ...\n"); | 
|  | 51 | for (i = 0; i < g->g_ndfas; i++) { | 
|  | 52 | d = &g->g_dfa[i]; | 
|  | 53 | if (d->d_first == NULL) | 
|  | 54 | calcfirstset(g, d); | 
|  | 55 | } | 
|  | 56 | } | 
|  | 57 |  | 
| Guido van Rossum | 85a5fbb | 1990-10-14 12:07:46 +0000 | [diff] [blame] | 58 | static void | 
|  | 59 | calcfirstset(g, d) | 
|  | 60 | grammar *g; | 
|  | 61 | dfa *d; | 
|  | 62 | { | 
|  | 63 | int i, j; | 
|  | 64 | state *s; | 
|  | 65 | arc *a; | 
|  | 66 | int nsyms; | 
|  | 67 | int *sym; | 
|  | 68 | int nbits; | 
|  | 69 | static bitset dummy; | 
|  | 70 | bitset result; | 
|  | 71 | int type; | 
|  | 72 | dfa *d1; | 
|  | 73 | label *l0; | 
|  | 74 |  | 
| Guido van Rossum | 86bea46 | 1997-04-29 21:03:06 +0000 | [diff] [blame] | 75 | if (Py_DebugFlag) | 
| Guido van Rossum | 85a5fbb | 1990-10-14 12:07:46 +0000 | [diff] [blame] | 76 | printf("Calculate FIRST set for '%s'\n", d->d_name); | 
|  | 77 |  | 
|  | 78 | if (dummy == NULL) | 
|  | 79 | dummy = newbitset(1); | 
|  | 80 | if (d->d_first == dummy) { | 
|  | 81 | fprintf(stderr, "Left-recursion for '%s'\n", d->d_name); | 
|  | 82 | return; | 
|  | 83 | } | 
|  | 84 | if (d->d_first != NULL) { | 
|  | 85 | fprintf(stderr, "Re-calculating FIRST set for '%s' ???\n", | 
|  | 86 | d->d_name); | 
|  | 87 | } | 
|  | 88 | d->d_first = dummy; | 
|  | 89 |  | 
|  | 90 | l0 = g->g_ll.ll_label; | 
|  | 91 | nbits = g->g_ll.ll_nlabels; | 
|  | 92 | result = newbitset(nbits); | 
|  | 93 |  | 
| Guido van Rossum | 86bea46 | 1997-04-29 21:03:06 +0000 | [diff] [blame] | 94 | sym = PyMem_NEW(int, 1); | 
| Guido van Rossum | 85a5fbb | 1990-10-14 12:07:46 +0000 | [diff] [blame] | 95 | if (sym == NULL) | 
| Guido van Rossum | 86bea46 | 1997-04-29 21:03:06 +0000 | [diff] [blame] | 96 | Py_FatalError("no mem for new sym in calcfirstset"); | 
| Guido van Rossum | 85a5fbb | 1990-10-14 12:07:46 +0000 | [diff] [blame] | 97 | nsyms = 1; | 
|  | 98 | sym[0] = findlabel(&g->g_ll, d->d_type, (char *)NULL); | 
|  | 99 |  | 
|  | 100 | s = &d->d_state[d->d_initial]; | 
|  | 101 | for (i = 0; i < s->s_narcs; i++) { | 
|  | 102 | a = &s->s_arc[i]; | 
|  | 103 | for (j = 0; j < nsyms; j++) { | 
|  | 104 | if (sym[j] == a->a_lbl) | 
|  | 105 | break; | 
|  | 106 | } | 
|  | 107 | if (j >= nsyms) { /* New label */ | 
| Guido van Rossum | 86bea46 | 1997-04-29 21:03:06 +0000 | [diff] [blame] | 108 | PyMem_RESIZE(sym, int, nsyms + 1); | 
| Guido van Rossum | 85a5fbb | 1990-10-14 12:07:46 +0000 | [diff] [blame] | 109 | if (sym == NULL) | 
| Guido van Rossum | 86bea46 | 1997-04-29 21:03:06 +0000 | [diff] [blame] | 110 | Py_FatalError( | 
|  | 111 | "no mem to resize sym in calcfirstset"); | 
| Guido van Rossum | 85a5fbb | 1990-10-14 12:07:46 +0000 | [diff] [blame] | 112 | sym[nsyms++] = a->a_lbl; | 
|  | 113 | type = l0[a->a_lbl].lb_type; | 
|  | 114 | if (ISNONTERMINAL(type)) { | 
| Guido van Rossum | 86bea46 | 1997-04-29 21:03:06 +0000 | [diff] [blame] | 115 | d1 = PyGrammar_FindDFA(g, type); | 
| Guido van Rossum | 85a5fbb | 1990-10-14 12:07:46 +0000 | [diff] [blame] | 116 | if (d1->d_first == dummy) { | 
|  | 117 | fprintf(stderr, | 
|  | 118 | "Left-recursion below '%s'\n", | 
|  | 119 | d->d_name); | 
|  | 120 | } | 
|  | 121 | else { | 
|  | 122 | if (d1->d_first == NULL) | 
|  | 123 | calcfirstset(g, d1); | 
| Guido van Rossum | 86bea46 | 1997-04-29 21:03:06 +0000 | [diff] [blame] | 124 | mergebitset(result, | 
|  | 125 | d1->d_first, nbits); | 
| Guido van Rossum | 85a5fbb | 1990-10-14 12:07:46 +0000 | [diff] [blame] | 126 | } | 
|  | 127 | } | 
|  | 128 | else if (ISTERMINAL(type)) { | 
|  | 129 | addbit(result, a->a_lbl); | 
|  | 130 | } | 
|  | 131 | } | 
|  | 132 | } | 
|  | 133 | d->d_first = result; | 
| Guido van Rossum | 86bea46 | 1997-04-29 21:03:06 +0000 | [diff] [blame] | 134 | if (Py_DebugFlag) { | 
| Guido van Rossum | 85a5fbb | 1990-10-14 12:07:46 +0000 | [diff] [blame] | 135 | printf("FIRST set for '%s': {", d->d_name); | 
|  | 136 | for (i = 0; i < nbits; i++) { | 
|  | 137 | if (testbit(result, i)) | 
| Guido van Rossum | 86bea46 | 1997-04-29 21:03:06 +0000 | [diff] [blame] | 138 | printf(" %s", PyGrammar_LabelRepr(&l0[i])); | 
| Guido van Rossum | 85a5fbb | 1990-10-14 12:07:46 +0000 | [diff] [blame] | 139 | } | 
|  | 140 | printf(" }\n"); | 
|  | 141 | } | 
|  | 142 | } |