|
|
1.1 root 1: /* Copyright (c) 1979 Regents of the University of California */
2: #
3: /*
4: * pi - Pascal interpreter code translator
5: *
6: * Charles Haley, Bill Joy UCB
7: * Version 1.1 February 1978
8: *
9: *
10: * pxp - Pascal execution profiler
11: *
12: * Bill Joy UCB
13: * Version 1.1 February 1978
14: */
15:
16: #include "0.h"
17: #include "yy.h"
18:
19: /*
20: * Symbol costs for Pascal.
21: *
22: * Cost strategy of August 14, 1977.
23: *
24: * The costs determined by the routines in this file are used by
25: * the recovery in choosing appropriate corrections.
26: * The cost vectors and the error productions in the grammar
27: * work together to define the corrective capacity of the grammar.
28: *
29: * The costs here largely derive from those given in Steve Rhode's
30: * thesis for the Pascal-I error correcting parser which he implemented.
31: * Some minor changes have been made to adjust for the fact that
32: * the current error recovery is not as "smart", both because of the
33: * limited forward move and because of the lack of any type information
34: * about identifiers.
35: *
36: * These adjustments largely take the form of increased costs for certain
37: * tokens, noticeably keywords which are major brackets such as "begin"
38: * "label", "procedure", etc.
39: *
40: * The overall weighting strategy is still similar to Rhodes' strategy.
41: * The costs can be considered:
42: *
43: * LOW <= 3
44: * MEDIUM 4 or 5
45: * HIGH >= 6
46: */
47:
48: /*
49: * Insertion costs
50: *
51: * In addition to the normal symbol insertion costs,
52: * there are zero cost insertions here.
53: * The current error recovery system treats symbols
54: * which have zero insertion cost in a special way,
55: * inserting them but suppressing diagnostics.
56: * This allows the system to hold of on bracketing
57: * error diagnostics about missing end's until the
58: * reduction occurs which knows the line number of the
59: * corresponding "begin", "repeat", etc.
60: * A more intelligent and useful diagnostic can then
61: * be printed.
62: *
63: * Although this routine never allows the insertion
64: * of the keyword begin, it can be inserted after a
65: * procedure or function body starts, if it was omitted
66: * by a special case in the panic routine, which notices
67: * the keywords in the statement body of the procedure
68: * and inserts the begin to recover.
69: *
70: * Similarly, we do not insert end-of-file, but
71: * the fact that end-of-file is the unique input
72: * is noticed by the recovery routines as a special
73: * case and handled there.
74: */
75: inscost(sy, before)
76: register int sy, before;
77: {
78:
79: switch (before) {
80: case YEND:
81: if (sy == YEND)
82: break;
83: case YPROCEDURE:
84: case YFUNCTION:
85: if (sy == YUNTIL || sy == YEND)
86: return (0);
87: }
88: switch (sy) {
89: case ';':
90: return (1);
91: case ',':
92: case ':':
93: case YOF:
94: case YDO:
95: return (2);
96: case YARRAY:
97: case '+':
98: case '*':
99: return (3);
100: default:
101: return (4);
102: case '^':
103: case YNOT:
104: case YLABEL:
105: case YCONST:
106: case YTYPE:
107: case YVAR:
108: case YUNTIL:
109: case '(':
110: case '[':
111: case YWHILE:
112: case YWITH:
113: case YASSERT:
114: return (5);
115: case YPROCEDURE:
116: case YFUNCTION:
117: case YCASE:
118: return (6);
119: case YEND:
120: return (8);
121: case YBEGIN:
122: case YEOF:
123: case YREPEAT:
124: case YRECORD:
125: return (INFINITY);
126: }
127: }
128:
129: /*
130: * Replacement costs
131: *
132: * Most replacement costs are the same as an insertion
133: * plus a deletion cost. One special case is the replacement
134: * of a large number of keywords by an identifier.
135: * These are given lower costs, especially the keyword "to".
136: */
137: repcost(what, with)
138: register int what, with;
139: {
140: register int c;
141:
142: if (with == what)
143: return (INFINITY);
144: if (with == YID && what > ERROR)
145: switch (what) {
146: case YID:
147: case YDOTDOT:
148: case YINT:
149: case YBINT:
150: case YSTRING:
151: case YNUMB:
152: break;
153: case YTO:
154: return (3);
155: default:
156: return (5);
157: case YRECORD:
158: case YTHEN:
159: return (6);
160: case YBEGIN:
161: break;
162: }
163: if (what == ';' && (with == ',' || with == '.'))
164: return (CLIMIT - 1);
165: c = delcost(what) + inscost(with);
166: /*
167: * It costs extra to replace something which has
168: * semantics by something which doesn't.
169: */
170: if (nullsem(what) == NIL && nullsem(with) != NIL)
171: c =+ 4;
172: return (c);
173: }
174:
175: /*
176: * Deletion costs
177: */
178: delcost(what)
179: int what;
180: {
181:
182: switch (what) {
183: case '.':
184: case ':':
185: case ',':
186: case '=':
187: case '(':
188: return (3);
189: case YELSE:
190: case YTHEN:
191: return (4);
192: default:
193: return (5);
194: case YLABEL:
195: case YCONST:
196: case YTYPE:
197: case YVAR:
198: return (10);
199: case YPROCEDURE:
200: case YFUNCTION:
201: case YBEGIN:
202: case YEND:
203: return ((CLIMIT * 3) / 4);
204: case ';':
205: case YEOF:
206: return (INFINITY);
207: }
208: }
209: #ifdef DEBUG
210:
211: /*
212: * Routine to print out costs with "-C" option.
213: */
214: char yysyms[] ";,:=*+/-|&()[]<>~^";
215:
216:
217: yycosts()
218: {
219: register int c;
220: register char *cp;
221:
222: printf("Insert\tDelete\tRep(ID)\tSymbol\n");
223: for (cp = yysyms; *cp; cp++)
224: yydocost(*cp);
225: for (c = ERROR + 1; c < YLAST; c++)
226: yydocost(c);
227: #ifdef PXP
228: flush();
229: #endif
230: }
231:
232: yydocost(c)
233: int c;
234: {
235:
236: printf("%4d\t", inscost(c, -1));
237: printf("%4d\t", delcost(c));
238: if (repcost(c, YID) != inscost(YID) + delcost(c))
239: printf("%4d", repcost(c, YID));
240: printf("\t%s%s\n", charname(c));
241: }
242: #endif
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.