xref: /csrg-svn/old/pcc/mip/common.c (revision 18385)
1 /*	common.c	4.1	85/03/19	*/
2 
3 #ifdef PASS1COMMON
4 #include "pass1.h"
5 #else
6 #ifdef PASS2COMMON
7 #include "pass2.h"
8 #endif
9 #endif
10 
11 #ifdef FORT
12 #undef BUFSTDERR
13 #endif
14 #ifndef ONEPASS
15 #undef BUFSTDERR
16 #endif
17 # ifndef EXIT
18 # define EXIT exit
19 # endif
20 
21 int nerrors = 0;  /* number of errors */
22 
23 extern unsigned int offsz;
24 
25 unsigned caloff(){
26 	register i;
27 	unsigned int temp;
28 	unsigned int off;
29 	temp = 1;
30 	i = 0;
31 	do {
32 		temp <<= 1;
33 		++i;
34 		} while( temp != 0 );
35 	off = 1 << (i-1);
36 	return (off);
37 	}
38 
39 NODE *lastfree;  /* pointer to last free node; (for allocator) */
40 
41 	/* VARARGS1 */
42 uerror( s, a ) char *s; { /* nonfatal error message */
43 	/* the routine where is different for pass 1 and pass 2;
44 	/*  it tells where the error took place */
45 
46 	++nerrors;
47 	where('u');
48 	fprintf( stderr, s, a );
49 	fprintf( stderr, "\n" );
50 #ifdef BUFSTDERR
51 	fflush(stderr);
52 #endif
53 	if( nerrors > 30 ) cerror( "too many errors");
54 	}
55 
56 	/* VARARGS1 */
57 cerror( s, a, b, c ) char *s; { /* compiler error: die */
58 	where('c');
59 	if( nerrors && nerrors <= 30 ){ /* give the compiler the benefit of the doubt */
60 		fprintf( stderr, "cannot recover from earlier errors: goodbye!\n" );
61 		}
62 	else {
63 		fprintf( stderr, "compiler error: " );
64 		fprintf( stderr, s, a, b, c );
65 		fprintf( stderr, "\n" );
66 		}
67 #ifdef BUFSTDERR
68 	fflush(stderr);
69 #endif
70 	EXIT(1);
71 	}
72 
73 int Wflag = 0; /* Non-zero means do not print warnings */
74 
75 	/* VARARGS1 */
76 werror( s, a, b ) char *s; {  /* warning */
77 	if(Wflag) return;
78 	where('w');
79 	fprintf( stderr, "warning: " );
80 	fprintf( stderr, s, a, b );
81 	fprintf( stderr, "\n" );
82 #ifdef BUFSTDERR
83 	fflush(stderr);
84 #endif
85 	}
86 
87 tinit(){ /* initialize expression tree search */
88 
89 	NODE *p;
90 
91 	for( p=node; p<= &node[TREESZ-1]; ++p ) p->in.op = FREE;
92 	lastfree = node;
93 
94 	}
95 
96 # define TNEXT(p) (p== &node[TREESZ-1]?node:p+1)
97 
98 NODE *
99 talloc(){
100 	NODE *p, *q;
101 
102 	q = lastfree;
103 	for( p = TNEXT(q); p!=q; p= TNEXT(p))
104 		if( p->in.op ==FREE ) return(lastfree=p);
105 
106 	cerror( "out of tree space; simplify expression");
107 	/* NOTREACHED */
108 	}
109 
110 tcheck(){ /* ensure that all nodes have been freed */
111 
112 	NODE *p;
113 
114 	if( !nerrors )
115 		for( p=node; p<= &node[TREESZ-1]; ++p )
116 			if( p->in.op != FREE ) cerror( "wasted space: %o", p );
117 	tinit();
118 #ifdef FLEXNAMES
119 	freetstr();
120 #endif
121 	}
122 tfree( p )  NODE *p; {
123 	/* free the tree p */
124 	extern tfree1();
125 
126 	if( p->in.op != FREE ) walkf( p, tfree1 );
127 
128 	}
129 
130 tfree1(p)  NODE *p; {
131 	if( p == 0 ) cerror( "freeing blank tree!");
132 	else p->in.op = FREE;
133 	}
134 
135 fwalk( t, f, down ) register NODE *t; int (*f)(); {
136 
137 	int down1, down2;
138 
139 	more:
140 	down1 = down2 = 0;
141 
142 	(*f)( t, down, &down1, &down2 );
143 
144 	switch( optype( t->in.op ) ){
145 
146 	case BITYPE:
147 		fwalk( t->in.left, f, down1 );
148 		t = t->in.right;
149 		down = down2;
150 		goto more;
151 
152 	case UTYPE:
153 		t = t->in.left;
154 		down = down1;
155 		goto more;
156 
157 		}
158 	}
159 
160 walkf( t, f ) register NODE *t;  int (*f)(); {
161 	register opty;
162 
163 	opty = optype(t->in.op);
164 
165 	if( opty != LTYPE ) walkf( t->in.left, f );
166 	if( opty == BITYPE ) walkf( t->in.right, f );
167 	(*f)( t );
168 	}
169 
170 
171 
172 int dope[ DSIZE ];
173 char *opst[DSIZE];
174 
175 struct dopest { int dopeop; char opst[8]; int dopeval; } indope[] = {
176 
177 	NAME, "NAME", LTYPE,
178 	STRING, "STRING", LTYPE,
179 	REG, "REG", LTYPE,
180 	OREG, "OREG", LTYPE,
181 	ICON, "ICON", LTYPE,
182 	FCON, "FCON", LTYPE,
183 	DCON, "DCON", LTYPE,
184 	CCODES, "CCODES", LTYPE,
185 	UNARY MINUS, "U-", UTYPE,
186 	UNARY MUL, "U*", UTYPE,
187 	UNARY AND, "U&", UTYPE,
188 	UNARY CALL, "UCALL", UTYPE|CALLFLG,
189 	UNARY FORTCALL, "UFCALL", UTYPE|CALLFLG,
190 	NOT, "!", UTYPE|LOGFLG,
191 	COMPL, "~", UTYPE,
192 	FORCE, "FORCE", UTYPE,
193 	INIT, "INIT", UTYPE,
194 	SCONV, "SCONV", UTYPE,
195 	PCONV, "PCONV", UTYPE,
196 	PLUS, "+", BITYPE|FLOFLG|SIMPFLG|COMMFLG,
197 	ASG PLUS, "+=", BITYPE|ASGFLG|ASGOPFLG|FLOFLG|SIMPFLG|COMMFLG,
198 	MINUS, "-", BITYPE|FLOFLG|SIMPFLG,
199 	ASG MINUS, "-=", BITYPE|FLOFLG|SIMPFLG|ASGFLG|ASGOPFLG,
200 	MUL, "*", BITYPE|FLOFLG|MULFLG,
201 	ASG MUL, "*=", BITYPE|FLOFLG|MULFLG|ASGFLG|ASGOPFLG,
202 	AND, "&", BITYPE|SIMPFLG|COMMFLG,
203 	ASG AND, "&=", BITYPE|SIMPFLG|COMMFLG|ASGFLG|ASGOPFLG,
204 	QUEST, "?", BITYPE,
205 	COLON, ":", BITYPE,
206 	ANDAND, "&&", BITYPE|LOGFLG,
207 	OROR, "||", BITYPE|LOGFLG,
208 	CM, ",", BITYPE,
209 	COMOP, ",OP", BITYPE,
210 	ASSIGN, "=", BITYPE|ASGFLG,
211 	DIV, "/", BITYPE|FLOFLG|MULFLG|DIVFLG,
212 	ASG DIV, "/=", BITYPE|FLOFLG|MULFLG|DIVFLG|ASGFLG|ASGOPFLG,
213 	MOD, "%", BITYPE|DIVFLG,
214 	ASG MOD, "%=", BITYPE|DIVFLG|ASGFLG|ASGOPFLG,
215 	LS, "<<", BITYPE|SHFFLG,
216 	ASG LS, "<<=", BITYPE|SHFFLG|ASGFLG|ASGOPFLG,
217 	RS, ">>", BITYPE|SHFFLG,
218 	ASG RS, ">>=", BITYPE|SHFFLG|ASGFLG|ASGOPFLG,
219 	OR, "|", BITYPE|COMMFLG|SIMPFLG,
220 	ASG OR, "|=", BITYPE|COMMFLG|SIMPFLG|ASGFLG|ASGOPFLG,
221 	ER, "^", BITYPE|COMMFLG|SIMPFLG,
222 	ASG ER, "^=", BITYPE|COMMFLG|SIMPFLG|ASGFLG|ASGOPFLG,
223 	INCR, "++", BITYPE|ASGFLG,
224 	DECR, "--", BITYPE|ASGFLG,
225 	STREF, "->", BITYPE,
226 	CALL, "CALL", BITYPE|CALLFLG,
227 	FORTCALL, "FCALL", BITYPE|CALLFLG,
228 	EQ, "==", BITYPE|LOGFLG,
229 	NE, "!=", BITYPE|LOGFLG,
230 	LE, "<=", BITYPE|LOGFLG,
231 	LT, "<", BITYPE|LOGFLG,
232 	GE, ">", BITYPE|LOGFLG,
233 	GT, ">", BITYPE|LOGFLG,
234 	UGT, "UGT", BITYPE|LOGFLG,
235 	UGE, "UGE", BITYPE|LOGFLG,
236 	ULT, "ULT", BITYPE|LOGFLG,
237 	ULE, "ULE", BITYPE|LOGFLG,
238 #ifdef ARS
239 	ARS, "A>>", BITYPE,
240 #endif
241 	TYPE, "TYPE", LTYPE,
242 	LB, "[", BITYPE,
243 	CBRANCH, "CBRANCH", BITYPE,
244 	FLD, "FLD", UTYPE,
245 	PMCONV, "PMCONV", BITYPE,
246 	PVCONV, "PVCONV", BITYPE,
247 	RETURN, "RETURN", BITYPE|ASGFLG|ASGOPFLG,
248 	CAST, "CAST", BITYPE|ASGFLG|ASGOPFLG,
249 	GOTO, "GOTO", UTYPE,
250 	STASG, "STASG", BITYPE|ASGFLG,
251 	STARG, "STARG", UTYPE,
252 	STCALL, "STCALL", BITYPE|CALLFLG,
253 	UNARY STCALL, "USTCALL", UTYPE|CALLFLG,
254 
255 	-1,	"",	0
256 };
257 
258 mkdope(){
259 	register struct dopest *q;
260 
261 	for( q = indope; q->dopeop >= 0; ++q ){
262 		dope[q->dopeop] = q->dopeval;
263 		opst[q->dopeop] = q->opst;
264 		}
265 	}
266 # ifndef BUG4
267 tprint( t )  TWORD t; { /* output a nice description of the type of t */
268 
269 	static char * tnames[] = {
270 		"undef",
271 		"farg",
272 		"char",
273 		"short",
274 		"int",
275 		"long",
276 		"float",
277 		"double",
278 		"strty",
279 		"unionty",
280 		"enumty",
281 		"moety",
282 		"uchar",
283 		"ushort",
284 		"unsigned",
285 		"ulong",
286 		"?", "?"
287 		};
288 
289 	for(;; t = DECREF(t) ){
290 
291 		if( ISPTR(t) ) printf( "PTR " );
292 		else if( ISFTN(t) ) printf( "FTN " );
293 		else if( ISARY(t) ) printf( "ARY " );
294 		else {
295 			printf( "%s", tnames[t] );
296 			return;
297 			}
298 		}
299 	}
300 # endif
301 
302 #ifdef FLEXNAMES
303 #define	NTSTRBUF	40
304 #define	TSTRSZ		2048
305 char	itstrbuf[TSTRSZ];
306 char	*tstrbuf[NTSTRBUF] = { itstrbuf };
307 char	**curtstr = tstrbuf;
308 int	tstrused;
309 
310 char *
311 tstr(cp)
312 	register char *cp;
313 {
314 	register int i = strlen(cp);
315 	register char *dp;
316 
317 	if (tstrused + i >= TSTRSZ) {
318 		if (++curtstr >= &tstrbuf[NTSTRBUF])
319 			cerror("out of temporary string space");
320 		tstrused = 0;
321 		if (*curtstr == 0) {
322 			dp = (char *)malloc(TSTRSZ);
323 			if (dp == 0)
324 				cerror("out of memory (tstr)");
325 			*curtstr = dp;
326 		}
327 	}
328 	strcpy(dp = *curtstr+tstrused, cp);
329 	tstrused += i + 1;
330 	return (dp);
331 }
332 #endif
333