GCC Code Coverage Report
Directory: ./ Exec Total Coverage
File: usr.bin/yacc/output.c Lines: 598 716 83.5 %
Date: 2016-12-06 Branches: 363 520 69.8 %

Line Branch Exec Source
1
/*	$OpenBSD: output.c,v 1.25 2015/12/11 20:25:47 mmcc Exp $	*/
2
/*	$NetBSD: output.c,v 1.4 1996/03/19 03:21:41 jtc Exp $	*/
3
4
/*
5
 * Copyright (c) 1989 The Regents of the University of California.
6
 * All rights reserved.
7
 *
8
 * This code is derived from software contributed to Berkeley by
9
 * Robert Paul Corbett.
10
 *
11
 * Redistribution and use in source and binary forms, with or without
12
 * modification, are permitted provided that the following conditions
13
 * are met:
14
 * 1. Redistributions of source code must retain the above copyright
15
 *    notice, this list of conditions and the following disclaimer.
16
 * 2. Redistributions in binary form must reproduce the above copyright
17
 *    notice, this list of conditions and the following disclaimer in the
18
 *    documentation and/or other materials provided with the distribution.
19
 * 3. Neither the name of the University nor the names of its contributors
20
 *    may be used to endorse or promote products derived from this software
21
 *    without specific prior written permission.
22
 *
23
 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
24
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
25
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
26
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
27
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
28
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
29
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
30
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
31
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
32
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
33
 * SUCH DAMAGE.
34
 */
35
36
#include "defs.h"
37
38
static int nvectors;
39
static int nentries;
40
static short **froms;
41
static short **tos;
42
static short *tally;
43
static short *width;
44
static short *state_count;
45
static short *order;
46
static short *base;
47
static short *pos;
48
static int maxtable;
49
static short *table;
50
static short *check;
51
static int lowzero;
52
static int high;
53
54
void output_prefix(void);
55
void output_rule_data(void);
56
void output_yydefred(void);
57
void output_actions(void);
58
void token_actions(void);
59
void goto_actions(void);
60
int default_goto(int);
61
void save_column(int, int);
62
void sort_actions(void);
63
void pack_table(void);
64
int matching_vector(int);
65
int pack_vector(int);
66
void output_base(void);
67
void output_table(void);
68
void output_check(void);
69
int is_C_identifier(char *);
70
void output_defines(void);
71
void output_stored_text(void);
72
void output_debug(void);
73
void output_stype(void);
74
void output_trailing_text(void);
75
void output_semantic_actions(void);
76
void free_itemsets(void);
77
void free_shifts(void);
78
void free_reductions(void);
79
80
void
81
output(void)
82
21
{
83
21
	free_itemsets();
84
21
	free_shifts();
85
21
	free_reductions();
86
21
	output_prefix();
87
21
	output_stored_text();
88
21
	output_defines();
89
21
	output_rule_data();
90
21
	output_yydefred();
91
21
	output_actions();
92
21
	free_parser();
93
21
	output_debug();
94
21
	output_stype();
95
21
	if (rflag)
96
		write_section(tables);
97
21
	write_section(header);
98
21
	output_trailing_text();
99
21
	write_section(body);
100
21
	output_semantic_actions();
101
21
	write_section(trailer);
102
21
}
103
104
105
void
106
output_prefix(void)
107
21
{
108
21
	if (symbol_prefix == NULL)
109
21
		symbol_prefix = "yy";
110
	else {
111
		++outline;
112
		fprintf(code_file, "#define yyparse %sparse\n", symbol_prefix);
113
		++outline;
114
		fprintf(code_file, "#define yylex %slex\n", symbol_prefix);
115
		++outline;
116
		fprintf(code_file, "#define yyerror %serror\n", symbol_prefix);
117
		++outline;
118
		fprintf(code_file, "#define yychar %schar\n", symbol_prefix);
119
		++outline;
120
		fprintf(code_file, "#define yyval %sval\n", symbol_prefix);
121
		++outline;
122
		fprintf(code_file, "#define yylval %slval\n", symbol_prefix);
123
		++outline;
124
		fprintf(code_file, "#define yydebug %sdebug\n", symbol_prefix);
125
		++outline;
126
		fprintf(code_file, "#define yynerrs %snerrs\n", symbol_prefix);
127
		++outline;
128
		fprintf(code_file, "#define yyerrflag %serrflag\n", symbol_prefix);
129
		++outline;
130
		fprintf(code_file, "#define yyss %sss\n", symbol_prefix);
131
		++outline;
132
		fprintf(code_file, "#define yysslim %ssslim\n", symbol_prefix);
133
		++outline;
134
		fprintf(code_file, "#define yyssp %sssp\n", symbol_prefix);
135
		++outline;
136
		fprintf(code_file, "#define yyvs %svs\n", symbol_prefix);
137
		++outline;
138
		fprintf(code_file, "#define yyvsp %svsp\n", symbol_prefix);
139
		++outline;
140
		fprintf(code_file, "#define yystacksize %sstacksize\n", symbol_prefix);
141
		++outline;
142
		fprintf(code_file, "#define yylhs %slhs\n", symbol_prefix);
143
		++outline;
144
		fprintf(code_file, "#define yylen %slen\n", symbol_prefix);
145
		++outline;
146
		fprintf(code_file, "#define yydefred %sdefred\n", symbol_prefix);
147
		++outline;
148
		fprintf(code_file, "#define yydgoto %sdgoto\n", symbol_prefix);
149
		++outline;
150
		fprintf(code_file, "#define yysindex %ssindex\n", symbol_prefix);
151
		++outline;
152
		fprintf(code_file, "#define yyrindex %srindex\n", symbol_prefix);
153
		++outline;
154
		fprintf(code_file, "#define yygindex %sgindex\n", symbol_prefix);
155
		++outline;
156
		fprintf(code_file, "#define yytable %stable\n", symbol_prefix);
157
		++outline;
158
		fprintf(code_file, "#define yycheck %scheck\n", symbol_prefix);
159
		++outline;
160
		fprintf(code_file, "#define yyname %sname\n", symbol_prefix);
161
		++outline;
162
		fprintf(code_file, "#define yyrule %srule\n", symbol_prefix);
163
	}
164
21
	++outline;
165
21
	fprintf(code_file, "#define YYPREFIX \"%s\"\n", symbol_prefix);
166
21
}
167
168
169
void
170
output_rule_data(void)
171
21
{
172
	int i;
173
	int j;
174
175
21
	fprintf(output_file,
176
	    "const short %slhs[] =\n"
177
	    "\t{%42d,", symbol_prefix, symbol_value[start_symbol]);
178
179
21
	j = 10;
180
2263
	for (i = 3; i < nrules; i++) {
181
2242
		if (j >= 10) {
182
236
			if (!rflag)
183
236
				++outline;
184
236
			putc('\n', output_file);
185
236
			j = 1;
186
		} else
187
2006
			++j;
188
2242
		fprintf(output_file, "%5d,", symbol_value[rlhs[i]]);
189
	}
190
21
	if (!rflag)
191
21
		outline += 2;
192
21
	fprintf(output_file, "\n};\n");
193
194
21
	fprintf(output_file,
195
	    "const short %slen[] =\n"
196
	    "\t{%42d,", symbol_prefix, 2);
197
198
21
	j = 10;
199
2263
	for (i = 3; i < nrules; i++) {
200
2242
		if (j >= 10) {
201
236
			if (!rflag)
202
236
				++outline;
203
236
			putc('\n', output_file);
204
236
			j = 1;
205
		} else
206
2006
			j++;
207
2242
		fprintf(output_file, "%5d,", rrhs[i + 1] - rrhs[i] - 1);
208
	}
209
21
	if (!rflag)
210
21
		outline += 2;
211
21
	fprintf(output_file, "\n};\n");
212
21
}
213
214
215
void
216
output_yydefred(void)
217
21
{
218
	int i, j;
219
220
21
	fprintf(output_file,
221
	    "const short %sdefred[] =\n"
222
	    "\t{%39d,",
223
	    symbol_prefix, (defred[0] ? defred[0] - 2 : 0));
224
225
21
	j = 10;
226
4002
	for (i = 1; i < nstates; i++) {
227
3981
		if (j < 10)
228
3575
			++j;
229
		else {
230
406
			if (!rflag)
231
406
				++outline;
232
406
			putc('\n', output_file);
233
406
			j = 1;
234
		}
235
3981
		fprintf(output_file, "%5d,", (defred[i] ? defred[i] - 2 : 0));
236
	}
237
238
21
	if (!rflag)
239
21
		outline += 2;
240
21
	fprintf(output_file, "\n};\n");
241
21
}
242
243
244
void
245
output_actions(void)
246
21
{
247
21
	nvectors = 2 * nstates + nvars;
248
249
21
	froms = NEW2(nvectors, short *);
250
21
	tos = NEW2(nvectors, short *);
251
21
	tally = NEW2(nvectors, short);
252
21
	width = NEW2(nvectors, short);
253
254
21
	token_actions();
255
21
	free(lookaheads);
256
21
	free(LA);
257
21
	free(LAruleno);
258
21
	free(accessing_symbol);
259
260
21
	goto_actions();
261
21
	free(goto_map + ntokens);
262
21
	free(from_state);
263
21
	free(to_state);
264
265
21
	sort_actions();
266
21
	pack_table();
267
21
	output_base();
268
21
	output_table();
269
21
	output_check();
270
21
}
271
272
273
void
274
token_actions(void)
275
21
{
276
	int i, j;
277
	int shiftcount, reducecount;
278
	int max, min;
279
	short *actionrow, *r, *s;
280
	action *p;
281
282
21
	actionrow = NEW2(2*ntokens, short);
283
4023
	for (i = 0; i < nstates; ++i) {
284
4002
	if (parser[i]) {
285
627338
		for (j = 0; j < 2 * ntokens; ++j)
286
623338
			actionrow[j] = 0;
287
4000
			shiftcount = 0;
288
4000
			reducecount = 0;
289
39482
			for (p = parser[i]; p; p = p->next) {
290
35482
				if (p->suppressed == 0) {
291
35393
					if (p->action_code == SHIFT) {
292
4299
						++shiftcount;
293
4299
						actionrow[p->symbol] = p->number;
294

31094
					} else if (p->action_code == REDUCE &&
295
					    p->number != defred[i]) {
296
3952
						++reducecount;
297
3952
						actionrow[p->symbol + ntokens] = p->number;
298
					}
299
				}
300
			}
301
302
4000
			tally[i] = shiftcount;
303
4000
			tally[nstates+i] = reducecount;
304
4000
			width[i] = 0;
305
4000
			width[nstates+i] = 0;
306
4000
			if (shiftcount > 0) {
307
2004
				froms[i] = r = NEW2(shiftcount, short);
308
2004
				tos[i] = s = NEW2(shiftcount, short);
309
2004
				min = MAXSHORT;
310
2004
				max = 0;
311
160064
				for (j = 0; j < ntokens; ++j) {
312
158060
					if (actionrow[j]) {
313
4299
						if (min > symbol_value[j])
314
2234
							min = symbol_value[j];
315
4299
						if (max < symbol_value[j])
316
4019
							max = symbol_value[j];
317
4299
						*r++ = symbol_value[j];
318
4299
						*s++ = actionrow[j];
319
					}
320
				}
321
2004
				width[i] = max - min + 1;
322
			}
323
4000
			if (reducecount > 0) {
324
432
				froms[nstates+i] = r = NEW2(reducecount, short);
325
432
				tos[nstates+i] = s = NEW2(reducecount, short);
326
432
				min = MAXSHORT;
327
432
				max = 0;
328
34174
				for (j = 0; j < ntokens; ++j) {
329
33742
					if (actionrow[ntokens+j]) {
330
3952
						if (min > symbol_value[j])
331
651
							min = symbol_value[j];
332
3952
						if (max < symbol_value[j])
333
3624
							max = symbol_value[j];
334
3952
						*r++ = symbol_value[j];
335
3952
						*s++ = actionrow[ntokens+j] - 2;
336
					}
337
				}
338
432
				width[nstates+i] = max - min + 1;
339
			}
340
		}
341
	}
342
21
	free(actionrow);
343
21
}
344
345
void
346
goto_actions(void)
347
21
{
348
	int i, j, k;
349
350
21
	state_count = NEW2(nstates, short);
351
352
21
	k = default_goto(start_symbol + 1);
353
21
	fprintf(output_file, "const short %sdgoto[] =\n"
354
	    "\t{%40d,", symbol_prefix, k);
355
21
	save_column(start_symbol + 1, k);
356
357
21
	j = 10;
358
866
	for (i = start_symbol + 2; i < nsyms; i++) {
359
845
		if (j >= 10) {
360
93
			if (!rflag)
361
93
				++outline;
362
93
			putc('\n', output_file);
363
93
			j = 1;
364
		} else
365
752
			++j;
366
367
845
		k = default_goto(i);
368
845
		fprintf(output_file, "%5d,", k);
369
845
		save_column(i, k);
370
	}
371
372
21
	if (!rflag)
373
21
		outline += 2;
374
21
	fprintf(output_file, "\n};\n");
375
21
	free(state_count);
376
21
}
377
378
int
379
default_goto(int symbol)
380
866
{
381
	int i;
382
	int m;
383
	int n;
384
	int default_state;
385
	int max;
386
387
866
	m = goto_map[symbol];
388
866
	n = goto_map[symbol + 1];
389
390
866
	if (m == n)
391
		return (0);
392
393
866
	memset(state_count, 0, nstates * sizeof(short));
394
395
2997
	for (i = m; i < n; i++)
396
2131
		state_count[to_state[i]]++;
397
398
866
	max = 0;
399
866
	default_state = 0;
400
229781
	for (i = 0; i < nstates; i++) {
401
228915
		if (state_count[i] > max) {
402
913
			max = state_count[i];
403
913
			default_state = i;
404
		}
405
	}
406
407
866
	return (default_state);
408
}
409
410
411
412
void
413
save_column(int symbol, int default_state)
414
866
{
415
	int i;
416
	int m;
417
	int n;
418
	short *sp;
419
	short *sp1;
420
	short *sp2;
421
	int count;
422
	int symno;
423
424
866
	m = goto_map[symbol];
425
866
	n = goto_map[symbol + 1];
426
427
866
	count = 0;
428
2997
	for (i = m; i < n; i++) {
429
2131
		if (to_state[i] != default_state)
430
866
			++count;
431
	}
432
866
	if (count == 0)
433
607
		return;
434
435
259
	symno = symbol_value[symbol] + 2*nstates;
436
437
259
	froms[symno] = sp1 = sp = NEW2(count, short);
438
259
	tos[symno] = sp2 = NEW2(count, short);
439
440
1606
	for (i = m; i < n; i++) {
441
1347
		if (to_state[i] != default_state) {
442
866
			*sp1++ = from_state[i];
443
866
			*sp2++ = to_state[i];
444
		}
445
	}
446
447
259
	tally[symno] = count;
448
259
	width[symno] = sp1[-1] - sp[0] + 1;
449
}
450
451
void
452
sort_actions(void)
453
21
{
454
	int i;
455
	int j;
456
	int k;
457
	int t;
458
	int w;
459
460
21
	order = NEW2(nvectors, short);
461
21
	nentries = 0;
462
463
8912
	for (i = 0; i < nvectors; i++) {
464
8891
		if (tally[i] > 0) {
465
2695
			t = tally[i];
466
2695
			w = width[i];
467
2695
			j = nentries - 1;
468
469

115079
			while (j >= 0 && (width[order[j]] < w))
470
109689
				j--;
471
472

3081
			while (j >= 0 && (width[order[j]] == w) &&
473
			    (tally[order[j]] < t))
474
386
				j--;
475
476
112770
			for (k = nentries - 1; k > j; k--)
477
110075
				order[k + 1] = order[k];
478
479
2695
			order[j + 1] = i;
480
2695
			nentries++;
481
		}
482
	}
483
21
}
484
485
486
void
487
pack_table(void)
488
21
{
489
	int i;
490
	int place;
491
	int state;
492
493
21
	base = NEW2(nvectors, short);
494
21
	pos = NEW2(nentries, short);
495
496
21
	maxtable = 1000;
497
21
	table = NEW2(maxtable, short);
498
21
	check = NEW2(maxtable, short);
499
500
21
	lowzero = 0;
501
21
	high = 0;
502
503
21021
	for (i = 0; i < maxtable; i++)
504
21000
		check[i] = -1;
505
506
2716
	for (i = 0; i < nentries; i++) {
507
2695
		state = matching_vector(i);
508
509
2695
		if (state < 0)
510
2017
			place = pack_vector(i);
511
		else
512
678
			place = base[state];
513
514
2695
		pos[i] = place;
515
2695
		base[order[i]] = place;
516
	}
517
518
8912
	for (i = 0; i < nvectors; i++) {
519
8891
		free(froms[i]);
520
8891
		free(tos[i]);
521
	}
522
523
21
	free(froms);
524
21
	free(tos);
525
21
	free(pos);
526
21
}
527
528
529
/*  The function matching_vector determines if the vector specified by	*/
530
/*  the input parameter matches a previously considered	vector.  The	*/
531
/*  test at the start of the function checks if the vector represents	*/
532
/*  a row of shifts over terminal symbols or a row of reductions, or a	*/
533
/*  column of shifts over a nonterminal symbol.  Berkeley Yacc does not	*/
534
/*  check if a column of shifts over a nonterminal symbols matches a	*/
535
/*  previously considered vector.  Because of the nature of LR parsing	*/
536
/*  tables, no two columns can match.  Therefore, the only possible	*/
537
/*  match would be between a row and a column.  Such matches are	*/
538
/*  unlikely.  Therefore, to save time, no attempt is made to see if a	*/
539
/*  column matches a previously considered vector.			*/
540
/*									*/
541
/*  Matching_vector is poorly designed.  The test could easily be made	*/
542
/*  faster.  Also, it depends on the vectors being in a specific	*/
543
/*  order.								*/
544
545
int
546
matching_vector(int vector)
547
2695
{
548
	int i, j, k, t, w, match, prev;
549
550
2695
	i = order[vector];
551
2695
	if (i >= 2*nstates)
552
259
		return (-1);
553
554
2436
	t = tally[i];
555
2436
	w = width[i];
556
557
55972
	for (prev = vector - 1; prev >= 0; prev--) {
558
55947
		j = order[prev];
559

55947
		if (width[j] != w || tally[j] != t)
560
1733
			return (-1);
561
562
54214
		match = 1;
563
111623
		for (k = 0; match && k < t; k++) {
564

57409
			if (tos[j][k] != tos[i][k] ||
565
			    froms[j][k] != froms[i][k])
566
53536
				match = 0;
567
		}
568
569
54214
		if (match)
570
678
			return (j);
571
	}
572
573
25
	return (-1);
574
}
575
576
577
578
int
579
pack_vector(int vector)
580
2017
{
581
	int i, j, k, l;
582
	int t, loc, ok;
583
	short *from, *to;
584
	int newmax;
585
586
2017
	i = order[vector];
587
2017
	t = tally[i];
588
2017
	assert(t);
589
590
2017
	from = froms[i];
591
2017
	to = tos[i];
592
593
2017
	j = lowzero - from[0];
594
7199
	for (k = 1; k < t; ++k)
595
5182
		if (lowzero - from[k] > j)
596
327
			j = lowzero - from[k];
597
124595
	for (;; ++j) {
598
126612
		if (j == 0)
599
260
			continue;
600
126352
		ok = 1;
601
412751
		for (k = 0; ok && k < t; k++) {
602
286399
			loc = j + from[k];
603
286399
			if (loc >= maxtable) {
604
7
				if (loc >= MAXTABLE)
605
					fatal("maximum table size exceeded");
606
607
7
				newmax = maxtable;
608
				do {
609
7
					newmax += 200;
610
7
				} while (newmax <= loc);
611
7
				table = realloc(table, newmax * sizeof(short));
612
7
				if (table == NULL)
613
					no_space();
614
7
				check = realloc(check, newmax * sizeof(short));
615
7
				if (check == NULL)
616
					no_space();
617
1407
				for (l  = maxtable; l < newmax; ++l) {
618
1400
					table[l] = 0;
619
1400
					check[l] = -1;
620
				}
621
7
				maxtable = newmax;
622
			}
623
624
286399
			if (check[loc] != -1)
625
123316
				ok = 0;
626
		}
627
377345
		for (k = 0; ok && k < vector; k++) {
628
250993
			if (pos[k] == j)
629
1019
				ok = 0;
630
		}
631
126352
		if (ok) {
632
9216
			for (k = 0; k < t; k++) {
633
7199
				loc = j + from[k];
634
7199
				table[loc] = to[k];
635
7199
				check[loc] = from[k];
636
7199
				if (loc > high)
637
2472
					high = loc;
638
			}
639
640

5405
			while (lowzero < maxtable && check[lowzero] != -1)
641
3388
				++lowzero;
642
643
2017
			return (j);
644
		}
645
124595
	}
646
}
647
648
649
650
void
651
output_base(void)
652
21
{
653
	int i, j;
654
655
21
	fprintf(output_file, "const short %ssindex[] =\n"
656
	    "\t{%39d,", symbol_prefix, base[0]);
657
658
21
	j = 10;
659
4002
	for (i = 1; i < nstates; i++) {
660
3981
		if (j >= 10) {
661
406
			if (!rflag)
662
406
				++outline;
663
406
			putc('\n', output_file);
664
406
			j = 1;
665
		} else
666
3575
			++j;
667
3981
		fprintf(output_file, "%5d,", base[i]);
668
	}
669
670
21
	if (!rflag)
671
21
		outline += 2;
672
21
	fprintf(output_file, "};\n"
673
	    "const short %srindex[] =\n"
674
	    "\t{%39d,", symbol_prefix, base[nstates]);
675
676
21
	j = 10;
677
4002
	for (i = nstates + 1; i < 2*nstates; i++) {
678
3981
		if (j >= 10) {
679
406
			if (!rflag)
680
406
				++outline;
681
406
			putc('\n', output_file);
682
406
			j = 1;
683
		} else
684
3575
			++j;
685
3981
		fprintf(output_file, "%5d,", base[i]);
686
	}
687
688
21
	if (!rflag)
689
21
		outline += 2;
690
21
	fprintf(output_file, "};\n"
691
	    "const short %sgindex[] =\n"
692
	    "\t{%39d,", symbol_prefix, base[2*nstates]);
693
694
21
	j = 10;
695
866
	for (i = 2*nstates + 1; i < nvectors - 1; i++) {
696
845
		if (j >= 10) {
697
93
			if (!rflag)
698
93
				++outline;
699
93
			putc('\n', output_file);
700
93
			j = 1;
701
		} else
702
752
			++j;
703
845
		fprintf(output_file, "%5d,", base[i]);
704
	}
705
706
21
	if (!rflag)
707
21
		outline += 2;
708
21
	fprintf(output_file, "\n};\n");
709
21
	free(base);
710
21
}
711
712
713
void
714
output_table(void)
715
21
{
716
	int i, j;
717
718
21
	++outline;
719
21
	fprintf(code_file, "#define YYTABLESIZE %d\n", high);
720
21
	fprintf(output_file, "const short %stable[] =\n"
721
	    "\t{%40d,", symbol_prefix, table[0]);
722
723
21
	j = 10;
724
11261
	for (i = 1; i <= high; i++) {
725
11240
		if (j >= 10) {
726
1135
			if (!rflag)
727
1135
				++outline;
728
1135
			putc('\n', output_file);
729
1135
			j = 1;
730
		} else
731
10105
			++j;
732
11240
		fprintf(output_file, "%5d,", table[i]);
733
	}
734
735
21
	if (!rflag)
736
21
		outline += 2;
737
21
	fprintf(output_file, "\n};\n");
738
21
	free(table);
739
21
}
740
741
742
void
743
output_check(void)
744
21
{
745
	int i, j;
746
747
21
	fprintf(output_file, "const short %scheck[] =\n"
748
	    "\t{%40d,", symbol_prefix, check[0]);
749
750
21
	j = 10;
751
11261
	for (i = 1; i <= high; i++) {
752
11240
		if (j >= 10) {
753
1135
			if (!rflag)
754
1135
				++outline;
755
1135
			putc('\n', output_file);
756
1135
			j = 1;
757
		} else
758
10105
			++j;
759
11240
		fprintf(output_file, "%5d,", check[i]);
760
	}
761
762
21
	if (!rflag)
763
21
		outline += 2;
764
21
	fprintf(output_file, "\n};\n");
765
21
	free(check);
766
21
}
767
768
769
int
770
is_C_identifier(char *name)
771
1133
{
772
	char *s;
773
	int c;
774
775
1133
	s = name;
776
1133
	c = (unsigned char)*s;
777
1133
	if (c == '"') {
778
1
		c = (unsigned char)*++s;
779

1
		if (!isalpha(c) && c != '_' && c != '$')
780
1
			return (0);
781
		while ((c = (unsigned char)*++s) != '"') {
782
			if (!isalnum(c) && c != '_' && c != '$')
783
				return (0);
784
		}
785
		return (1);
786
	}
787
788

1132
	if (!isalpha(c) && c != '_' && c != '$')
789
110
		return (0);
790
7840
	while ((c = (unsigned char)*++s)) {
791

6818
		if (!isalnum(c) && c != '_' && c != '$')
792
			return (0);
793
	}
794
1022
	return (1);
795
}
796
797
798
void
799
output_defines(void)
800
21
{
801
	int c, i;
802
	char *s;
803
804
1154
	for (i = 2; i < ntokens; ++i) {
805
1133
		s = symbol_name[i];
806
1133
		if (is_C_identifier(s)) {
807
1022
			fprintf(code_file, "#define ");
808
1022
			if (dflag)
809
692
				fprintf(defines_file, "#define ");
810
1022
			c = (unsigned char)*s;
811
1022
			if (c == '"') {
812
				while ((c = (unsigned char)*++s) != '"') {
813
					putc(c, code_file);
814
					if (dflag)
815
						putc(c, defines_file);
816
				}
817
			} else {
818
				do {
819
7840
					putc(c, code_file);
820
7840
					if (dflag)
821
5417
						putc(c, defines_file);
822
7840
				} while ((c = (unsigned char)*++s));
823
			}
824
1022
			++outline;
825
1022
			fprintf(code_file, " %d\n", symbol_value[i]);
826
1022
			if (dflag)
827
692
				fprintf(defines_file, " %d\n", symbol_value[i]);
828
		}
829
	}
830
831
21
	++outline;
832
21
	fprintf(code_file, "#define YYERRCODE %d\n", symbol_value[1]);
833
834

21
	if (dflag && unionized) {
835
4
		fclose(union_file);
836
4
		union_file = fopen(union_file_name, "r");
837
4
		if (union_file == NULL)
838
			open_error(union_file_name);
839

604
		while ((c = getc(union_file)) != EOF)
840
600
			putc(c, defines_file);
841
4
		fprintf(defines_file, " YYSTYPE;\n");
842
4
		fprintf(defines_file, "#endif /* YYSTYPE_DEFINED */\n");
843
4
		fprintf(defines_file, "extern YYSTYPE %slval;\n",
844
		    symbol_prefix);
845
	}
846
21
}
847
848
849
void
850
output_stored_text(void)
851
21
{
852
	int c;
853
	FILE *in, *out;
854
855
21
	fclose(text_file);
856
21
	text_file = fopen(text_file_name, "r");
857
21
	if (text_file == NULL)
858
		open_error(text_file_name);
859
21
	in = text_file;
860

21
	if ((c = getc(in)) == EOF)
861
		return;
862
21
	out = code_file;
863
21
	if (c ==  '\n')
864
		++outline;
865
21
	putc(c, out);
866

46284
	while ((c = getc(in)) != EOF) {
867
46263
		if (c == '\n')
868
1903
			++outline;
869
46263
		putc(c, out);
870
	}
871
21
	if (!lflag)
872
21
		fprintf(out, line_format, ++outline + 1, code_file_name);
873
}
874
875
876
void
877
output_debug(void)
878
21
{
879
	int i, j, k, max;
880
	char **symnam, *s;
881
882
21
	++outline;
883
21
	fprintf(code_file, "#define YYFINAL %d\n", final_state);
884
21
	outline += 3;
885
21
	fprintf(code_file, "#ifndef YYDEBUG\n#define YYDEBUG %d\n#endif\n",
886
		tflag);
887
21
	if (rflag)
888
		fprintf(output_file, "#ifndef YYDEBUG\n#define YYDEBUG %d\n#endif\n",
889
		    tflag);
890
891
21
	max = 0;
892
1154
	for (i = 2; i < ntokens; ++i)
893
1133
		if (symbol_value[i] > max)
894
1023
			max = symbol_value[i];
895
21
	++outline;
896
21
	fprintf(code_file, "#define YYMAXTOKEN %d\n", max);
897
898
21
	symnam = calloc(max+1, sizeof(char *));
899
21
	if (symnam == NULL)
900
		no_space();
901
902
1154
	for (i = ntokens - 1; i >= 2; --i)
903
1133
		symnam[symbol_value[i]] = symbol_name[i];
904
21
	symnam[0] = "end-of-file";
905
906
21
	if (!rflag)
907
21
		++outline;
908
21
	fprintf(output_file,
909
	    "#if YYDEBUG\n"
910
	    "const char * const %sname[] =\n"
911
	    "\t{", symbol_prefix);
912
21
	j = 80;
913
6441
	for (i = 0; i <= max; ++i) {
914
6420
		if ((s = symnam[i]) != '\0') {
915
1154
			if (s[0] == '"') {
916
1
				k = 7;
917
4
				while (*++s != '"') {
918
2
					++k;
919
2
					if (*s == '\\') {
920
						k += 2;
921
						if (*++s == '\\')
922
							++k;
923
					}
924
				}
925
1
				j += k;
926
1
				if (j > 80) {
927
					if (!rflag)
928
						++outline;
929
					putc('\n', output_file);
930
					j = k;
931
				}
932
1
				fprintf(output_file, "\"\\\"");
933
1
				s = symnam[i];
934
4
				while (*++s != '"') {
935
2
					if (*s == '\\') {
936
						fprintf(output_file, "\\\\");
937
						if (*++s == '\\')
938
							fprintf(output_file, "\\\\");
939
						else
940
							putc(*s, output_file);
941
					} else
942
2
						putc(*s, output_file);
943
				}
944
1
				fprintf(output_file, "\\\"\",");
945
1153
			} else if (s[0] == '\'') {
946
110
				if (s[1] == '"') {
947
					j += 7;
948
					if (j > 80) {
949
						if (!rflag)
950
							++outline;
951
						putc('\n', output_file);
952
						j = 7;
953
					}
954
					fprintf(output_file, "\"'\\\"'\",");
955
				} else {
956
110
					k = 5;
957
330
					while (*++s != '\'') {
958
110
						++k;
959
110
						if (*s == '\\') {
960
18
							k += 2;
961
18
							if (*++s == '\\')
962
								++k;
963
						}
964
					}
965
110
					j += k;
966
110
					if (j > 80) {
967
6
						if (!rflag)
968
6
							++outline;
969
6
						putc('\n', output_file);
970
6
						j = k;
971
					}
972
110
					fprintf(output_file, "\"'");
973
110
					s = symnam[i];
974
330
					while (*++s != '\'') {
975
110
						if (*s == '\\') {
976
18
							fprintf(output_file, "\\\\");
977
18
							if (*++s == '\\')
978
								fprintf(output_file, "\\\\");
979
							else
980
18
								putc(*s, output_file);
981
						} else
982
92
							putc(*s, output_file);
983
					}
984
110
					fprintf(output_file, "'\",");
985
				}
986
			} else {
987
1043
				k = strlen(s) + 3;
988
1043
				j += k;
989
1043
				if (j > 80) {
990
172
					if (!rflag)
991
172
						++outline;
992
172
					putc('\n', output_file);
993
172
					j = k;
994
				}
995
1043
				putc('"', output_file);
996
				do {
997
8071
					putc(*s, output_file);
998
8071
				} while (*++s);
999
1043
				fprintf(output_file, "\",");
1000
			}
1001
		} else {
1002
5266
			j += 2;
1003
5266
			if (j > 80) {
1004
125
				if (!rflag)
1005
125
					++outline;
1006
125
				putc('\n', output_file);
1007
125
				j = 2;
1008
			}
1009
5266
			fprintf(output_file, "0,");
1010
		}
1011
	}
1012
21
	if (!rflag)
1013
21
		outline += 2;
1014
21
	fprintf(output_file, "\n};\n");
1015
21
	free(symnam);
1016
1017
21
	if (!rflag)
1018
21
		++outline;
1019
21
	fprintf(output_file,
1020
	    "const char * const %srule[] =\n"
1021
	    "\t{", symbol_prefix);
1022
2284
	for (i = 2; i < nrules; ++i) {
1023
2263
		fprintf(output_file, "\"%s :", symbol_name[rlhs[i]]);
1024
6865
		for (j = rrhs[i]; ritem[j] > 0; ++j) {
1025
4602
			s = symbol_name[ritem[j]];
1026
4602
			if (s[0] == '"') {
1027
1
				fprintf(output_file, " \\\"");
1028
4
				while (*++s != '"') {
1029
2
					if (*s == '\\') {
1030
						if (s[1] == '\\')
1031
							fprintf(output_file, "\\\\\\\\");
1032
						else
1033
							fprintf(output_file, "\\\\%c", s[1]);
1034
						++s;
1035
					} else
1036
2
						putc(*s, output_file);
1037
				}
1038
1
				fprintf(output_file, "\\\"");
1039
4601
			} else if (s[0] == '\'') {
1040
431
				if (s[1] == '"')
1041
					fprintf(output_file, " '\\\"'");
1042
431
				else if (s[1] == '\\') {
1043
162
					if (s[2] == '\\')
1044
						fprintf(output_file, " '\\\\\\\\");
1045
					else
1046
162
						fprintf(output_file, " '\\\\%c", s[2]);
1047
162
					s += 2;
1048
324
					while (*++s != '\'')
1049
						putc(*s, output_file);
1050
162
					putc('\'', output_file);
1051
				} else
1052
269
					fprintf(output_file, " '%c'", s[1]);
1053
			} else
1054
4170
				fprintf(output_file, " %s", s);
1055
		}
1056
2263
		if (!rflag)
1057
2263
			++outline;
1058
2263
		fprintf(output_file, "\",\n");
1059
	}
1060
1061
21
	if (!rflag)
1062
21
		outline += 2;
1063
21
	fprintf(output_file, "};\n#endif\n");
1064
21
}
1065
1066
1067
void
1068
output_stype(void)
1069
21
{
1070

21
	if (!unionized && ntags == 0) {
1071
		outline += 3;
1072
		fprintf(code_file, "#ifndef YYSTYPE\ntypedef int YYSTYPE;\n#endif\n");
1073
	}
1074
21
}
1075
1076
1077
void
1078
output_trailing_text(void)
1079
21
{
1080
	int c, last;
1081
	FILE *in, *out;
1082
1083
21
	if (line == 0)
1084
		return;
1085
1086
21
	in = input_file;
1087
21
	out = code_file;
1088
21
	c = (unsigned char)*cptr;
1089
21
	if (c == '\n') {
1090
21
		++lineno;
1091

21
		if ((c = getc(in)) == EOF)
1092
			return;
1093
21
		if (!lflag) {
1094
21
			++outline;
1095
21
			fprintf(out, line_format, lineno, input_file_name);
1096
		}
1097
21
		if (c == '\n')
1098
20
			++outline;
1099
21
		putc(c, out);
1100
21
		last = c;
1101
	} else {
1102
		if (!lflag) {
1103
			++outline;
1104
			fprintf(out, line_format, lineno, input_file_name);
1105
		}
1106
		do {
1107
			putc(c, out);
1108
		} while ((c = (unsigned char)*++cptr) != '\n');
1109
		++outline;
1110
		putc('\n', out);
1111
		last = '\n';
1112
	}
1113
1114

262263
	while ((c = getc(in)) != EOF) {
1115
262242
		if (c == '\n')
1116
12752
			++outline;
1117
262242
		putc(c, out);
1118
262242
		last = c;
1119
	}
1120
1121
21
	if (last != '\n') {
1122
		++outline;
1123
		putc('\n', out);
1124
	}
1125
21
	if (!lflag)
1126
21
		fprintf(out, line_format, ++outline + 1, code_file_name);
1127
}
1128
1129
1130
void
1131
output_semantic_actions(void)
1132
21
{
1133
	int c, last;
1134
	FILE *out;
1135
1136
21
	fclose(action_file);
1137
21
	action_file = fopen(action_file_name, "r");
1138
21
	if (action_file == NULL)
1139
		open_error(action_file_name);
1140
1141

21
	if ((c = getc(action_file)) == EOF)
1142
		return;
1143
1144
21
	out = code_file;
1145
21
	last = c;
1146
21
	if (c == '\n')
1147
		++outline;
1148
21
	putc(c, out);
1149

355370
	while ((c = getc(action_file)) != EOF) {
1150
355349
		if (c == '\n')
1151
15065
			++outline;
1152
355349
		putc(c, out);
1153
355349
		last = c;
1154
	}
1155
1156
21
	if (last != '\n') {
1157
		++outline;
1158
		putc('\n', out);
1159
	}
1160
1161
21
	if (!lflag)
1162
21
		fprintf(out, line_format, ++outline + 1, code_file_name);
1163
}
1164
1165
1166
void
1167
free_itemsets(void)
1168
21
{
1169
	core *cp, *next;
1170
1171
21
	free(state_table);
1172
4023
	for (cp = first_state; cp; cp = next) {
1173
4002
		next = cp->next;
1174
4002
		free(cp);
1175
	}
1176
21
}
1177
1178
1179
void
1180
free_shifts(void)
1181
21
{
1182
	shifts *sp, *next;
1183
1184
21
	free(shift_table);
1185
2118
	for (sp = first_shift; sp; sp = next) {
1186
2097
		next = sp->next;
1187
2097
		free(sp);
1188
	}
1189
21
}
1190
1191
1192
1193
void
1194
free_reductions(void)
1195
21
{
1196
	reductions *rp, *next;
1197
1198
21
	free(reduction_table);
1199
2440
	for (rp = first_reduction; rp; rp = next) {
1200
2419
		next = rp->next;
1201
2419
		free(rp);
1202
	}
1203
21
}