xref: /csrg-svn/old/pcc/mip/common.c (revision 32806)
1*32806Sdonn /*	common.c	4.4	87/12/09	*/
218385Sralph 
318385Sralph #ifdef PASS1COMMON
418385Sralph #include "pass1.h"
518385Sralph #else
618385Sralph #ifdef PASS2COMMON
718385Sralph #include "pass2.h"
818385Sralph #endif
918385Sralph #endif
1018385Sralph 
1118385Sralph #ifdef FORT
1218385Sralph #undef BUFSTDERR
1318385Sralph #endif
1418385Sralph #ifndef ONEPASS
1518385Sralph #undef BUFSTDERR
1618385Sralph #endif
1718385Sralph # ifndef EXIT
1818385Sralph # define EXIT exit
1918385Sralph # endif
2018385Sralph 
2118385Sralph int nerrors = 0;  /* number of errors */
2218385Sralph 
2318385Sralph extern unsigned int offsz;
2418385Sralph 
2518385Sralph unsigned caloff(){
2618385Sralph 	register i;
2718385Sralph 	unsigned int temp;
2818385Sralph 	unsigned int off;
2918385Sralph 	temp = 1;
3018385Sralph 	i = 0;
3118385Sralph 	do {
3218385Sralph 		temp <<= 1;
3318385Sralph 		++i;
3418385Sralph 		} while( temp != 0 );
3518385Sralph 	off = 1 << (i-1);
3618385Sralph 	return (off);
3718385Sralph 	}
3818385Sralph 
3918385Sralph NODE *lastfree;  /* pointer to last free node; (for allocator) */
4018385Sralph 
4118385Sralph 	/* VARARGS1 */
4218385Sralph uerror( s, a ) char *s; { /* nonfatal error message */
4318385Sralph 	/* the routine where is different for pass 1 and pass 2;
4418385Sralph 	/*  it tells where the error took place */
4518385Sralph 
4618385Sralph 	++nerrors;
4718385Sralph 	where('u');
4818385Sralph 	fprintf( stderr, s, a );
4918385Sralph 	fprintf( stderr, "\n" );
5018385Sralph #ifdef BUFSTDERR
5118385Sralph 	fflush(stderr);
5218385Sralph #endif
5318385Sralph 	if( nerrors > 30 ) cerror( "too many errors");
5418385Sralph 	}
5518385Sralph 
5618385Sralph 	/* VARARGS1 */
5718385Sralph cerror( s, a, b, c ) char *s; { /* compiler error: die */
5818385Sralph 	where('c');
5918385Sralph 	if( nerrors && nerrors <= 30 ){ /* give the compiler the benefit of the doubt */
6018385Sralph 		fprintf( stderr, "cannot recover from earlier errors: goodbye!\n" );
6118385Sralph 		}
6218385Sralph 	else {
6318385Sralph 		fprintf( stderr, "compiler error: " );
6418385Sralph 		fprintf( stderr, s, a, b, c );
6518385Sralph 		fprintf( stderr, "\n" );
6618385Sralph 		}
6718385Sralph #ifdef BUFSTDERR
6818385Sralph 	fflush(stderr);
6918385Sralph #endif
7018385Sralph 	EXIT(1);
7118385Sralph 	}
7218385Sralph 
7318385Sralph int Wflag = 0; /* Non-zero means do not print warnings */
7418385Sralph 
7518385Sralph 	/* VARARGS1 */
7618385Sralph werror( s, a, b ) char *s; {  /* warning */
7718385Sralph 	if(Wflag) return;
7818385Sralph 	where('w');
7918385Sralph 	fprintf( stderr, "warning: " );
8018385Sralph 	fprintf( stderr, s, a, b );
8118385Sralph 	fprintf( stderr, "\n" );
8218385Sralph #ifdef BUFSTDERR
8318385Sralph 	fflush(stderr);
8418385Sralph #endif
8518385Sralph 	}
8618385Sralph 
8718385Sralph tinit(){ /* initialize expression tree search */
8818385Sralph 
8924401Smckusick 	register NODE *p;
9018385Sralph 
9118385Sralph 	for( p=node; p<= &node[TREESZ-1]; ++p ) p->in.op = FREE;
9218385Sralph 	lastfree = node;
9318385Sralph 
9418385Sralph 	}
9518385Sralph 
9618385Sralph # define TNEXT(p) (p== &node[TREESZ-1]?node:p+1)
9718385Sralph 
9818385Sralph NODE *
9918385Sralph talloc(){
10024401Smckusick 	register NODE *p, *q;
10118385Sralph 
10218385Sralph 	q = lastfree;
10318385Sralph 	for( p = TNEXT(q); p!=q; p= TNEXT(p))
104*32806Sdonn 		if( p->in.op ==FREE )
105*32806Sdonn 			return(lastfree=p);
10618385Sralph 
10718385Sralph 	cerror( "out of tree space; simplify expression");
10818385Sralph 	/* NOTREACHED */
10918385Sralph 	}
11018385Sralph 
11118385Sralph tcheck(){ /* ensure that all nodes have been freed */
11218385Sralph 
11324401Smckusick 	register NODE *p;
11418385Sralph 
11518385Sralph 	if( !nerrors )
11618385Sralph 		for( p=node; p<= &node[TREESZ-1]; ++p )
117*32806Sdonn 			if( p->in.op != FREE )
118*32806Sdonn 				cerror( "wasted space: %o", p );
11918385Sralph 	tinit();
12018385Sralph #ifdef FLEXNAMES
12118385Sralph 	freetstr();
12218385Sralph #endif
12318385Sralph 	}
12418385Sralph tfree( p )  NODE *p; {
12518385Sralph 	/* free the tree p */
12618385Sralph 	extern tfree1();
12718385Sralph 
12818385Sralph 	if( p->in.op != FREE ) walkf( p, tfree1 );
12918385Sralph 
13018385Sralph 	}
13118385Sralph 
13218385Sralph tfree1(p)  NODE *p; {
13318385Sralph 	if( p == 0 ) cerror( "freeing blank tree!");
13418385Sralph 	else p->in.op = FREE;
13518385Sralph 	}
13618385Sralph 
13718385Sralph fwalk( t, f, down ) register NODE *t; int (*f)(); {
13818385Sralph 
13918385Sralph 	int down1, down2;
14018385Sralph 
14118385Sralph 	more:
14218385Sralph 	down1 = down2 = 0;
14318385Sralph 
14418385Sralph 	(*f)( t, down, &down1, &down2 );
14518385Sralph 
14618385Sralph 	switch( optype( t->in.op ) ){
14718385Sralph 
14818385Sralph 	case BITYPE:
14918385Sralph 		fwalk( t->in.left, f, down1 );
15018385Sralph 		t = t->in.right;
15118385Sralph 		down = down2;
15218385Sralph 		goto more;
15318385Sralph 
15418385Sralph 	case UTYPE:
15518385Sralph 		t = t->in.left;
15618385Sralph 		down = down1;
15718385Sralph 		goto more;
15818385Sralph 
15918385Sralph 		}
16018385Sralph 	}
16118385Sralph 
16224401Smckusick #ifndef vax
16318385Sralph walkf( t, f ) register NODE *t;  int (*f)(); {
16418385Sralph 	register opty;
16518385Sralph 
16618385Sralph 	opty = optype(t->in.op);
16718385Sralph 
16818385Sralph 	if( opty != LTYPE ) walkf( t->in.left, f );
16918385Sralph 	if( opty == BITYPE ) walkf( t->in.right, f );
17018385Sralph 	(*f)( t );
17118385Sralph 	}
17224401Smckusick #else
17324401Smckusick #define	NR	100
17418385Sralph 
17524401Smckusick /*
17624401Smckusick  * Deliberately avoids recursion -- use this version on machines with
17724401Smckusick  * expensive procedure calls.
17824401Smckusick  */
17924401Smckusick walkf(t, f)
18024401Smckusick 	register NODE *t;
18124401Smckusick 	register int (*f)();
18224401Smckusick {
18324401Smckusick 	register int i = 1;
18424401Smckusick 	register int opty = optype(t->in.op);
18524401Smckusick 	static NODE *at[NR];
18624401Smckusick 	static int ao[NR];
18718385Sralph 
18824401Smckusick #define	PUSH(dir, state) \
18924401Smckusick 	(ao[i] = state, at[i++] = t, t = t->in.dir, opty = optype(t->in.op))
19024401Smckusick #define	POP() \
19124401Smckusick 	(opty = ao[--i], t = at[i])
19218385Sralph 
19324401Smckusick 	do {
19424401Smckusick 		switch (opty) {
19524401Smckusick 		case LTYPE:	(*f)(t); POP(); break;
19624401Smckusick 		case UTYPE:	PUSH(left, LTYPE); break;
19724401Smckusick 		case BITYPE:	PUSH(left, BITYPE+1); break;
19824401Smckusick 		case BITYPE+1:	PUSH(right, LTYPE); break;
19924401Smckusick 		default:
20024401Smckusick 			cerror("bad op type in walkf");
20124401Smckusick 		}
20224401Smckusick 		if (i >= NR) {
20324401Smckusick 			walkf(t, f);
20424401Smckusick 			POP();
20524401Smckusick 		}
20624401Smckusick 	} while (i > 0);
20724401Smckusick }
20824401Smckusick #undef NR
20924401Smckusick #undef PUSH
21024401Smckusick #undef POP
21124401Smckusick #endif
21224401Smckusick 
21324401Smckusick 
21424401Smckusick 
21518385Sralph int dope[ DSIZE ];
21618385Sralph char *opst[DSIZE];
21718385Sralph 
21818385Sralph struct dopest { int dopeop; char opst[8]; int dopeval; } indope[] = {
21918385Sralph 
22018385Sralph 	NAME, "NAME", LTYPE,
22118385Sralph 	STRING, "STRING", LTYPE,
22218385Sralph 	REG, "REG", LTYPE,
22318385Sralph 	OREG, "OREG", LTYPE,
22418385Sralph 	ICON, "ICON", LTYPE,
22518385Sralph 	FCON, "FCON", LTYPE,
22618385Sralph 	DCON, "DCON", LTYPE,
22718385Sralph 	CCODES, "CCODES", LTYPE,
22818385Sralph 	UNARY MINUS, "U-", UTYPE,
22918385Sralph 	UNARY MUL, "U*", UTYPE,
23018385Sralph 	UNARY AND, "U&", UTYPE,
23118385Sralph 	UNARY CALL, "UCALL", UTYPE|CALLFLG,
23218385Sralph 	UNARY FORTCALL, "UFCALL", UTYPE|CALLFLG,
23318385Sralph 	NOT, "!", UTYPE|LOGFLG,
23418385Sralph 	COMPL, "~", UTYPE,
23518385Sralph 	FORCE, "FORCE", UTYPE,
23618385Sralph 	INIT, "INIT", UTYPE,
23718385Sralph 	SCONV, "SCONV", UTYPE,
23818385Sralph 	PCONV, "PCONV", UTYPE,
23918385Sralph 	PLUS, "+", BITYPE|FLOFLG|SIMPFLG|COMMFLG,
24018385Sralph 	ASG PLUS, "+=", BITYPE|ASGFLG|ASGOPFLG|FLOFLG|SIMPFLG|COMMFLG,
24118385Sralph 	MINUS, "-", BITYPE|FLOFLG|SIMPFLG,
24218385Sralph 	ASG MINUS, "-=", BITYPE|FLOFLG|SIMPFLG|ASGFLG|ASGOPFLG,
24318385Sralph 	MUL, "*", BITYPE|FLOFLG|MULFLG,
24418385Sralph 	ASG MUL, "*=", BITYPE|FLOFLG|MULFLG|ASGFLG|ASGOPFLG,
24518385Sralph 	AND, "&", BITYPE|SIMPFLG|COMMFLG,
24618385Sralph 	ASG AND, "&=", BITYPE|SIMPFLG|COMMFLG|ASGFLG|ASGOPFLG,
24718385Sralph 	QUEST, "?", BITYPE,
24818385Sralph 	COLON, ":", BITYPE,
24918385Sralph 	ANDAND, "&&", BITYPE|LOGFLG,
25018385Sralph 	OROR, "||", BITYPE|LOGFLG,
25118385Sralph 	CM, ",", BITYPE,
25218385Sralph 	COMOP, ",OP", BITYPE,
25318385Sralph 	ASSIGN, "=", BITYPE|ASGFLG,
25418385Sralph 	DIV, "/", BITYPE|FLOFLG|MULFLG|DIVFLG,
25518385Sralph 	ASG DIV, "/=", BITYPE|FLOFLG|MULFLG|DIVFLG|ASGFLG|ASGOPFLG,
25618385Sralph 	MOD, "%", BITYPE|DIVFLG,
25718385Sralph 	ASG MOD, "%=", BITYPE|DIVFLG|ASGFLG|ASGOPFLG,
25818385Sralph 	LS, "<<", BITYPE|SHFFLG,
25918385Sralph 	ASG LS, "<<=", BITYPE|SHFFLG|ASGFLG|ASGOPFLG,
26018385Sralph 	RS, ">>", BITYPE|SHFFLG,
26118385Sralph 	ASG RS, ">>=", BITYPE|SHFFLG|ASGFLG|ASGOPFLG,
26218385Sralph 	OR, "|", BITYPE|COMMFLG|SIMPFLG,
26318385Sralph 	ASG OR, "|=", BITYPE|COMMFLG|SIMPFLG|ASGFLG|ASGOPFLG,
26418385Sralph 	ER, "^", BITYPE|COMMFLG|SIMPFLG,
26518385Sralph 	ASG ER, "^=", BITYPE|COMMFLG|SIMPFLG|ASGFLG|ASGOPFLG,
26618385Sralph 	INCR, "++", BITYPE|ASGFLG,
26718385Sralph 	DECR, "--", BITYPE|ASGFLG,
26818385Sralph 	STREF, "->", BITYPE,
26918385Sralph 	CALL, "CALL", BITYPE|CALLFLG,
27018385Sralph 	FORTCALL, "FCALL", BITYPE|CALLFLG,
27118385Sralph 	EQ, "==", BITYPE|LOGFLG,
27218385Sralph 	NE, "!=", BITYPE|LOGFLG,
27318385Sralph 	LE, "<=", BITYPE|LOGFLG,
27418385Sralph 	LT, "<", BITYPE|LOGFLG,
27518385Sralph 	GE, ">", BITYPE|LOGFLG,
27618385Sralph 	GT, ">", BITYPE|LOGFLG,
27718385Sralph 	UGT, "UGT", BITYPE|LOGFLG,
27818385Sralph 	UGE, "UGE", BITYPE|LOGFLG,
27918385Sralph 	ULT, "ULT", BITYPE|LOGFLG,
28018385Sralph 	ULE, "ULE", BITYPE|LOGFLG,
28118385Sralph #ifdef ARS
28218385Sralph 	ARS, "A>>", BITYPE,
28318385Sralph #endif
28418385Sralph 	TYPE, "TYPE", LTYPE,
28518385Sralph 	LB, "[", BITYPE,
28618385Sralph 	CBRANCH, "CBRANCH", BITYPE,
28718385Sralph 	FLD, "FLD", UTYPE,
28818385Sralph 	PMCONV, "PMCONV", BITYPE,
28918385Sralph 	PVCONV, "PVCONV", BITYPE,
29018385Sralph 	RETURN, "RETURN", BITYPE|ASGFLG|ASGOPFLG,
29118385Sralph 	CAST, "CAST", BITYPE|ASGFLG|ASGOPFLG,
29218385Sralph 	GOTO, "GOTO", UTYPE,
29318385Sralph 	STASG, "STASG", BITYPE|ASGFLG,
29418385Sralph 	STARG, "STARG", UTYPE,
29518385Sralph 	STCALL, "STCALL", BITYPE|CALLFLG,
29618385Sralph 	UNARY STCALL, "USTCALL", UTYPE|CALLFLG,
29718385Sralph 
29818385Sralph 	-1,	"",	0
29918385Sralph };
30018385Sralph 
30118385Sralph mkdope(){
30218385Sralph 	register struct dopest *q;
30318385Sralph 
30418385Sralph 	for( q = indope; q->dopeop >= 0; ++q ){
30518385Sralph 		dope[q->dopeop] = q->dopeval;
30618385Sralph 		opst[q->dopeop] = q->opst;
30718385Sralph 		}
30818385Sralph 	}
30918385Sralph # ifndef BUG4
31018385Sralph tprint( t )  TWORD t; { /* output a nice description of the type of t */
31118385Sralph 
31218385Sralph 	static char * tnames[] = {
31318385Sralph 		"undef",
31418385Sralph 		"farg",
31518385Sralph 		"char",
31618385Sralph 		"short",
31718385Sralph 		"int",
31818385Sralph 		"long",
31918385Sralph 		"float",
32018385Sralph 		"double",
32118385Sralph 		"strty",
32218385Sralph 		"unionty",
32318385Sralph 		"enumty",
32418385Sralph 		"moety",
32518385Sralph 		"uchar",
32618385Sralph 		"ushort",
32718385Sralph 		"unsigned",
32818385Sralph 		"ulong",
32918385Sralph 		"?", "?"
33018385Sralph 		};
33118385Sralph 
33218385Sralph 	for(;; t = DECREF(t) ){
33318385Sralph 
33418385Sralph 		if( ISPTR(t) ) printf( "PTR " );
33518385Sralph 		else if( ISFTN(t) ) printf( "FTN " );
33618385Sralph 		else if( ISARY(t) ) printf( "ARY " );
33718385Sralph 		else {
33818385Sralph 			printf( "%s", tnames[t] );
33918385Sralph 			return;
34018385Sralph 			}
34118385Sralph 		}
34218385Sralph 	}
34318385Sralph # endif
34418385Sralph 
34518385Sralph #ifdef FLEXNAMES
34618385Sralph #define	NTSTRBUF	40
34718385Sralph #define	TSTRSZ		2048
34818385Sralph char	itstrbuf[TSTRSZ];
34918385Sralph char	*tstrbuf[NTSTRBUF] = { itstrbuf };
35018385Sralph char	**curtstr = tstrbuf;
35118385Sralph int	tstrused;
35232805Sdonn char	*malloc();
35332805Sdonn char	*strcpy();
35418385Sralph 
35518385Sralph char *
35618385Sralph tstr(cp)
35718385Sralph 	register char *cp;
35818385Sralph {
35918385Sralph 	register int i = strlen(cp);
36018385Sralph 	register char *dp;
36118385Sralph 
36218385Sralph 	if (tstrused + i >= TSTRSZ) {
36318385Sralph 		if (++curtstr >= &tstrbuf[NTSTRBUF])
36418385Sralph 			cerror("out of temporary string space");
36518385Sralph 		tstrused = 0;
36618385Sralph 		if (*curtstr == 0) {
36732805Sdonn 			dp = malloc(TSTRSZ);
36818385Sralph 			if (dp == 0)
36918385Sralph 				cerror("out of memory (tstr)");
37018385Sralph 			*curtstr = dp;
37118385Sralph 		}
37218385Sralph 	}
37332805Sdonn 	(void) strcpy(dp = *curtstr+tstrused, cp);
37418385Sralph 	tstrused += i + 1;
37518385Sralph 	return (dp);
37618385Sralph }
37718385Sralph #endif
378