xref: /csrg-svn/usr.bin/pascal/src/tmps.c (revision 30033)
122197Sdist /*
222197Sdist  * Copyright (c) 1980 Regents of the University of California.
322197Sdist  * All rights reserved.  The Berkeley software License Agreement
422197Sdist  * specifies the terms and conditions for redistribution.
522197Sdist  */
63219Smckusick 
715939Smckusick #ifndef lint
8*30033Smckusick static char sccsid[] = "@(#)tmps.c	5.2 (Berkeley) 11/12/86";
922197Sdist #endif not lint
103219Smckusick 
113219Smckusick #include "whoami.h"
123219Smckusick #include "0.h"
1310657Speter #include "objfmt.h"
143280Smckusic #ifdef PC
153280Smckusic #   include "pc.h"
163280Smckusic #endif PC
1711853Speter #include "align.h"
1811332Speter #include "tmps.h"
193219Smckusick 
203219Smckusick /*
213280Smckusic  * This routine defines the register allocation strategy
223280Smckusic  * All temporaries are allocated here, and this routines decides
233280Smckusic  * where they are to be put.
243280Smckusic  */
253281Smckusic #ifdef PC
2611332Speter     /*
2715940Smckusick      *	register temporaries
2815940Smckusick      *	- are allocated from highreg towards lowreg.
2915940Smckusick      *	- are of size regsize.
3015940Smckusick      *	- register numbers from the various register types are mapped to
3115940Smckusick      *	  integer register numbers using the offsets.  (cf. pcc/mac2defs)
3215940Smckusick      *
3315940Smckusick      *	stack temporaries
3415940Smckusick      *	- are allocated on a downward growing stack.
3511332Speter      */
3611332Speter 
3710657Speter #ifdef vax
3811332Speter     /*
3911332Speter      *	first pass register declaration constants
4011332Speter      */
4111332Speter struct	regtype {
4211332Speter     long	lowreg;
4311332Speter     long	highreg;
4411332Speter     long	regsize;
4511332Speter } regtypes[NUMREGTYPES] = {
4615940Smckusick 	{ 6, 11, 4 },		/* r6..r11 */
4711332Speter };
4810657Speter #endif vax
4911332Speter 
50*30033Smckusick #ifdef tahoe
51*30033Smckusick     /*
52*30033Smckusick      *	first pass register declaration constants
53*30033Smckusick      */
54*30033Smckusick struct	regtype {
55*30033Smckusick     long	lowreg;
56*30033Smckusick     long	highreg;
57*30033Smckusick     long	regsize;
58*30033Smckusick } regtypes[NUMREGTYPES] = {
59*30033Smckusick 	{ 6, 12, 4 },		/* r6..r12 */
60*30033Smckusick };
61*30033Smckusick #endif tahoe
62*30033Smckusick 
6311332Speter #ifdef mc68000
6411332Speter     /*
6511332Speter      *	first pass register declaration constants
6611332Speter      */
6711332Speter struct	regtype {
6811332Speter     long	lowreg;
6911332Speter     long	highreg;
7011332Speter     long	regsize;
7111332Speter } regtypes[NUMREGTYPES] = {
7215940Smckusick 	{ 2, 7, 4 },		/* d2..d7 */
7315940Smckusick 	{ 2, 5, 4 },		/* a2..a5 */
7411332Speter };
7511332Speter #endif mc68000
763281Smckusic #endif PC
773280Smckusic 
7811332Speter tmpinit(cbn)
7911332Speter 	int	cbn;
8011332Speter {
8111332Speter 	struct om	*sizesp = &sizes[cbn];
8215939Smckusick #	ifdef PC
8311332Speter 	int	i;
8415939Smckusick #	endif PC
8511332Speter 
8611332Speter 	sizesp->om_max = -DPOFF1;
8711332Speter 	sizesp->curtmps.om_off = -DPOFF1;
8811332Speter #	ifdef PC
8911332Speter 		for (i = 0; i < NUMREGTYPES; i++) {
9011332Speter 			sizesp->low_water[i] = regtypes[i].highreg + 1;
9111332Speter 			sizesp->curtmps.next_avail[i] = regtypes[i].highreg;
9211332Speter 		}
9311332Speter #	endif PC
9411332Speter }
9511332Speter 
963280Smckusic /*
973219Smckusick  * allocate runtime temporary variables
983219Smckusick  */
9915939Smckusick /*ARGSUSED*/
1003839Speter struct nl *
1013280Smckusic tmpalloc(size, type, mode)
1023219Smckusick 	long size;
1033219Smckusick 	struct nl *type;
1043280Smckusic 	int mode;
1053219Smckusick {
10611332Speter 	register struct om	*op = &sizes[ cbn ];
10711332Speter 	register int		offset;
1083839Speter 	register struct nl	*nlp;
10911853Speter 	long			alignment;
1103219Smckusick 
1113280Smckusic #	ifdef PC
112*30033Smckusick #	    if defined(vax) || defined(tahoe)
11311332Speter 		if (  mode == REGOK
11411332Speter 		   && size == regtypes[REG_GENERAL].regsize
11511332Speter 		   && op->curtmps.next_avail[REG_GENERAL]
11611332Speter 			    >= regtypes[REG_GENERAL].lowreg) {
11711332Speter 			offset = op->curtmps.next_avail[REG_GENERAL]--;
11811332Speter 			if (offset < op->low_water[REG_GENERAL]) {
11911332Speter 				op->low_water[REG_GENERAL] = offset;
12011332Speter 			}
12115939Smckusick 			nlp = defnl( (char *) 0 , VAR , type , offset );
12211332Speter 			nlp -> extra_flags = NLOCAL | NREGVAR;
12311332Speter 			putlbracket(ftnno, op);
12411332Speter 			return nlp;
12511332Speter 		}
126*30033Smckusick #	    endif vax || tahoe
12715940Smckusick #	    ifdef mc68000
12815940Smckusick 		if (  mode == REGOK
12915940Smckusick 		   && type != nl + TPTR
13015940Smckusick 		   && size == regtypes[REG_DATA].regsize
13115940Smckusick 		   && op->curtmps.next_avail[REG_DATA]
13215940Smckusick 			    >= regtypes[REG_DATA].lowreg) {
13315940Smckusick 			offset = op->curtmps.next_avail[REG_DATA]--;
13415940Smckusick 			if (offset < op->low_water[REG_DATA]) {
13515940Smckusick 				op->low_water[REG_DATA] = offset;
13615940Smckusick 			}
13715940Smckusick 			nlp = defnl(0, VAR, type, offset + DATA_REG_OFFSET );
13815940Smckusick 			nlp -> extra_flags = NLOCAL | NREGVAR;
13915940Smckusick 			putlbracket(ftnno, op);
14015940Smckusick 			return nlp;
14115940Smckusick 		}
14215940Smckusick 		if (  mode == REGOK
14315940Smckusick 		   && type == nl + TPTR
14415940Smckusick 		   && size == regtypes[REG_ADDR].regsize
14515940Smckusick 		   && op->curtmps.next_avail[REG_ADDR]
14615940Smckusick 			    >= regtypes[REG_ADDR].lowreg) {
14715940Smckusick 			offset = op->curtmps.next_avail[REG_ADDR]--;
14815940Smckusick 			if (offset < op->low_water[REG_ADDR]) {
14915940Smckusick 				op->low_water[REG_ADDR] = offset;
15015940Smckusick 			}
15115940Smckusick 			nlp = defnl(0, VAR, type, offset + ADDR_REG_OFFSET );
15215940Smckusick 			nlp -> extra_flags = NLOCAL | NREGVAR;
15315940Smckusick 			putlbracket(ftnno, op);
15415940Smckusick 			return nlp;
15515940Smckusick 		}
15615940Smckusick #	    endif mc68000
1573280Smckusic #	endif PC
15811853Speter 	if (type == NIL) {
15911853Speter 	    alignment = A_STACK;
16015940Smckusick 	} else if (type == nl+TPTR) {
16115940Smckusick 	    alignment = A_POINT;
16211853Speter 	} else {
16311853Speter 	    alignment = align(type);
16411853Speter 	}
16511332Speter         op->curtmps.om_off =
16611853Speter 	    roundup((int)(op->curtmps.om_off - size), alignment);
16711332Speter 	offset = op->curtmps.om_off;
1683280Smckusic 	if ( offset < op->om_max ) {
1693280Smckusic 	        op->om_max = offset;
1703219Smckusick 	}
17115939Smckusick 	nlp = defnl( (char *) 0 , VAR , type , offset );
1723219Smckusick #	ifdef PC
1733839Speter 	    nlp -> extra_flags = NLOCAL;
17411332Speter 	    putlbracket(ftnno, op);
1753219Smckusick #	endif PC
1763839Speter 	return nlp;
1773219Smckusick }
17811332Speter 
1793219Smckusick /*
1803219Smckusick  * deallocate runtime temporary variables
1813219Smckusick  */
18215939Smckusick /*ARGSUSED*/
1833219Smckusick tmpfree(restore)
18411332Speter     register struct tmps	*restore;
1853219Smckusick {
18615939Smckusick #   ifdef PC
18711332Speter     register struct om		*op = &sizes[ cbn ];
18811332Speter     bool			change = FALSE;
1893219Smckusick 
190*30033Smckusick #	if defined(vax) || defined(tahoe)
19111332Speter 	    if (restore->next_avail[REG_GENERAL]
19211332Speter 		> op->curtmps.next_avail[REG_GENERAL]) {
19311332Speter 		    op->curtmps.next_avail[REG_GENERAL]
19411332Speter 			= restore->next_avail[REG_GENERAL];
19511332Speter 		    change = TRUE;
1963280Smckusic 	    }
197*30033Smckusick #	endif vax || tahoe
19815940Smckusick #	ifdef mc68000
19915940Smckusick 	    if (restore->next_avail[REG_DATA]
20015940Smckusick 		> op->curtmps.next_avail[REG_DATA]) {
20115940Smckusick 		    op->curtmps.next_avail[REG_DATA]
20215940Smckusick 			= restore->next_avail[REG_DATA];
20315940Smckusick 		    change = TRUE;
20415940Smckusick 	    }
20515940Smckusick 	    if (restore->next_avail[REG_ADDR]
20615940Smckusick 		> op->curtmps.next_avail[REG_ADDR]) {
20715940Smckusick 		    op->curtmps.next_avail[REG_ADDR]
20815940Smckusick 			= restore->next_avail[REG_ADDR];
20915940Smckusick 		    change = TRUE;
21015940Smckusick 	    }
21115940Smckusick #	endif mc68000
21211332Speter     if (restore->om_off > op->curtmps.om_off) {
21311332Speter 	    op->curtmps.om_off = restore->om_off;
21411332Speter 	    change = TRUE;
21511332Speter     }
21611332Speter 	if (change) {
21711332Speter 	    putlbracket(ftnno, op);
2183219Smckusick 	}
21915939Smckusick #endif PC
2203219Smckusick }
22111332Speter 
2223281Smckusic #ifdef PC
223*30033Smckusick #if defined(vax) || defined(tahoe)
2243280Smckusic /*
2253280Smckusic  * create a save mask for registers which have been used
2263280Smckusic  * in this level
2273280Smckusic  */
2283280Smckusic savmask()
2293280Smckusic {
2303839Speter 	int mask;
2313280Smckusic 	int i;
2323280Smckusic 
2333280Smckusic 	mask = RSAVEMASK;
2343280Smckusic 	if (opt('t'))
2353280Smckusic 	        mask |= RUNCHECK;
23611332Speter 	for (i = 0; i <= regtypes[REG_GENERAL].highreg; i++) {
23711332Speter 	    if (i >= sizes[cbn].low_water[REG_GENERAL]) {
23811332Speter 		mask |= 1 << i;
23911332Speter 	    }
24011332Speter 	}
2413280Smckusic 	return mask;
2423280Smckusic }
243*30033Smckusick #endif vax || tahoe
2443281Smckusic #endif PC
245