proc.c

来自「<B>Digital的Unix操作系统VAX 4.2源码</B>」· C语言 代码 · 共 1,806 行 · 第 1/3 页

C
1,806
字号
		q->vdcldone = YES;		if(q->vtype == TYCHAR)			{			if(q->vleng == NULL)	/* character*(*) */				q->vleng = (expptr)						mkarg(TYLENG, nextarg(TYLENG) );			else if(nentry == 1)				nextarg(TYLENG);			}		else if(q->vclass==CLPROC && nentry==1)			nextarg(TYLENG) ;#ifdef SDB		if(sdbflag) {			namestab(q);		}#endif		}if (optimflag)	optbuff (SKLABEL, 0, ep->entrylabel, 0);else	putlabel(ep->entrylabel);}LOCAL nextarg(type)int type;{int k;k = lastargslot;lastargslot += typesize[type];return(k);}/* generate variable references */LOCAL dobss(){register struct Hashentry *p;register Namep q;register int i;int align;ftnint leng, iarrl;char *memname();int qstg, qclass, qtype;pruse(asmfile, USEBSS);varsizes = NULL;for(p = hashtab ; p<lasthash ; ++p)    if(q = p->varp)	{	qstg = q->vstg;	qtype = q->vtype;	qclass = q->vclass;	if( (qclass==CLUNKNOWN && qstg!=STGARG) ||	    (qclass==CLVAR && qstg==STGUNKNOWN) )		warn1("local variable %s never used", varstr(VL,q->varname) );	else if(qclass==CLPROC && q->vprocclass==PEXTERNAL && qstg!=STGARG)		mkext(varunder(VL, q->varname)) ->extstg = STGEXT;	if (qclass == CLVAR && qstg == STGBSS)	  {	    if(qtype==TYCHAR && (q->vleng==NULL || !ISICON(q->vleng)))		    dclerr("adjustable leng on nonargument", q);	    if (SMALLVAR(q->varsize))	      {		enlist(q->varsize, q, NULL);		q->inlcomm = NO;	      }	    else	      {		if (q->init == NO)		  {		    preven(ALIDOUBLE);		    prlocvar(memname(qstg, q->vardesc.varno), q->varsize);		    q->inlcomm = YES;		  }		else		  prlocdata(memname(qstg, q->vardesc.varno), q->varsize,			    q->vtype, q->initoffset, &(q->inlcomm));	      }	  }	else if(qclass==CLVAR && qstg!=STGARG)		{		if(q->vdim && !ISICON(q->vdim->nelt) )			dclerr("adjustable dimension on non-argument", q);		if(qtype==TYCHAR && (q->vleng==NULL || !ISICON(q->vleng)))			dclerr("adjustable leng on nonargument", q);		}	chkdim(q);	}for (i = 0 ; i < nequiv ; ++i)  if ( (leng = eqvclass[i].eqvleng) != 0 )    {      if (SMALLVAR(leng))	enlist(leng, NULL, eqvclass + i);      else if (eqvclass[i].init == NO)	{	  preven(ALIDOUBLE);	  prlocvar(memname(STGEQUIV, i), leng);	  eqvclass[i].inlcomm = YES;	}      else	prlocdata(memname(STGEQUIV, i), leng, TYDREAL, 		  eqvclass[i].initoffset, &(eqvclass[i].inlcomm));    }  outlocvars();#ifdef SDB    if(sdbflag) {      for(p = hashtab ; p<lasthash ; ++p) if(q = p->varp) {	  qstg = q->vstg;	  qclass = q->vclass;          if( ONEOF(qclass, M(CLVAR))) {	     if (! ONEOF(qstg,M(STGCOMMON)|M(STGARG) ) ) namestab(q);	  }       }    }#endif  close(vdatafile);  close(vchkfile);  unlink(vdatafname);  unlink(vchkfname);  vdatahwm = 0;}donmlist(){register struct Hashentry *p;register Namep q;pruse(asmfile, USEINIT);for(p=hashtab; p<lasthash; ++p)	if( (q = p->varp) && q->vclass==CLNAMELIST)		namelist(q);}doext(){struct Extsym *p;for(p = extsymtab ; p<nextext ; ++p)	prext(p);}ftnint iarrlen(q)register Namep q;{ftnint leng;leng = typesize[q->vtype];if(leng <= 0)	return(-1);if(q->vdim)	if( ISICON(q->vdim->nelt) )		leng *= q->vdim->nelt->constblock.const.ci;	else	return(-1);if(q->vleng)	if( ISICON(q->vleng) )		leng *= q->vleng->constblock.const.ci;	else 	return(-1);return(leng);}/* This routine creates a static block representing the namelist.   An equivalent declaration of the structure produced is:	struct namelist		{		char namelistname[16];		struct namelistentry			{			char varname[16]; #  16 plus null padding -> 20			char *varaddr;			short int type;			short int len;	# length of type			struct dimensions *dimp; # null means scalar			} names[];		};	struct dimensions		{		int numberofdimensions;		int numberofelements		int baseoffset;		int span[numberofdimensions];		};   where the namelistentry list terminates with a null varname   If dimp is not null, then the corner element of the array is at   varaddr.  However,  the element with subscripts (i1,...,in) is at   varaddr - dimp->baseoffset + sizeoftype * (i1+span[0]*(i2+span[1]*...)*/namelist(np)Namep np;{register chainp q;register Namep v;register struct Dimblock *dp;char *memname();int type, dimno, dimoffset;flag bad;preven(ALILONG);fprintf(asmfile, LABELFMT, memname(STGINIT, np->vardesc.varno));putstr(asmfile, varstr(VL, np->varname), 16);dimno = ++lastvarno;dimoffset = 0;bad = NO;for(q = np->varxptr.namelist ; q ; q = q->nextp)	{	vardcl( v = (Namep) (q->datap) );	type = v->vtype;	if( ONEOF(v->vstg, MSKSTATIC) )		{		preven(ALILONG);		putstr(asmfile, varstr(VL,v->varname), 16);		praddr(asmfile, v->vstg, v->vardesc.varno, v->voffset);		prconi(asmfile, TYSHORT, type );		prconi(asmfile, TYSHORT,			type==TYCHAR ?			    (v->vleng->constblock.const.ci) :					(ftnint) typesize[type]);		if(v->vdim)			{			praddr(asmfile, STGINIT, dimno, (ftnint)dimoffset);			dimoffset += (3 + v->vdim->ndim) * SZINT;			}		else			praddr(asmfile, STGNULL,0,(ftnint) 0);		}	else		{		dclerr("may not appear in namelist", v);		bad = YES;		}	}if(bad)	return;putstr(asmfile, "", 16);if(dimoffset > 0)	{	fprintf(asmfile, LABELFMT, memname(STGINIT,dimno));	for(q = np->varxptr.namelist ; q ; q = q->nextp)		if(dp = q->datap->nameblock.vdim)			{			int i;			prconi(asmfile, TYINT, (ftnint) (dp->ndim) );			prconi(asmfile, TYINT,				(ftnint) (dp->nelt->constblock.const.ci) );			prconi(asmfile, TYINT,				(ftnint) (dp->baseoffset->constblock.const.ci));			for(i=0; i<dp->ndim ; ++i)				prconi(asmfile, TYINT,					dp->dims[i].dimsize->constblock.const.ci);			}	}}LOCAL docommon(){register struct Extsym *p;register chainp q;struct Dimblock *t;expptr neltp;register Namep v;ftnint size;int type;for(p = extsymtab ; p<nextext ; ++p)	if(p->extstg==STGCOMMON)		{#ifdef SDB		if(sdbflag)			prstab(varstr(XL,p->extname), N_BCOMM, 0, 0);#endif		for(q = p->extp ; q ; q = q->nextp)			{			v = (Namep) (q->datap);			if(v->vdcldone == NO)				vardcl(v);			type = v->vtype;			if(p->extleng % typealign[type] != 0)				{				dclerr("common alignment", v);				p->extleng = roundup(p->extleng, typealign[type]);				}			v->voffset = p->extleng;			v->vardesc.varno = p - extsymtab;			if(type == TYCHAR)				size = v->vleng->constblock.const.ci;			else	size = typesize[type];			if(t = v->vdim)				if( (neltp = t->nelt) && ISCONST(neltp) )					size *= neltp->constblock.const.ci;				else					dclerr("adjustable array in common", v);			p->extleng += size;#ifdef SDB			if(sdbflag)				{				namestab(v);				}#endif			}		frchain( &(p->extp) );#ifdef SDB		if(sdbflag)			prstab(varstr(XL,p->extname), N_ECOMM, 0, 0);#endif		}}LOCAL docomleng(){register struct Extsym *p;for(p = extsymtab ; p < nextext ; ++p)	if(p->extstg == STGCOMMON)		{		if(p->maxleng!=0 && p->extleng!=0 && p->maxleng!=p->extleng		    && !eqn(XL,"_BLNK__ ",p->extname) )			warn1("incompatible lengths for common block %s",				nounder(XL, p->extname) );		if(p->maxleng < p->extleng)			p->maxleng = p->extleng;		p->extleng = 0;	}}/* ROUTINES DEALING WITH AUTOMATIC AND TEMPORARY STORAGE *//*  frees a temporary block  */frtemp(p)Tempp p;{Addrp t;if (optimflag)	{	if (p->tag != TTEMP)		badtag ("frtemp",p->tag);	t = p->memalloc;	}else	t = (Addrp) p;/* restore clobbered character string lengths */if(t->vtype==TYCHAR && t->varleng!=0)	{	frexpr(t->vleng);	t->vleng = ICON(t->varleng);	}/* put block on chain of temps to be reclaimed */holdtemps = mkchain(t, holdtemps);}/* allocate an automatic variable slot */Addrp autovar(nelt, t, lengp)register int nelt, t;expptr lengp;{ftnint leng;register Addrp q;if(lengp)	if( ISICON(lengp) )		leng = lengp->constblock.const.ci;	else	{		fatal("automatic variable of nonconstant length");		}else	leng = typesize[t];autoleng = roundup( autoleng, typealign[t]);q = ALLOC(Addrblock);q->tag = TADDR;q->vtype = t;if(lengp)	{	q->vleng = ICON(leng);	q->varleng = leng;	}q->vstg = STGAUTO;q->memno = newlabel();q->ntempelt = nelt;#if TARGET==PDP11 || TARGET==VAX	/* stack grows downward */	autoleng += nelt*leng;	q->memoffset = ICON( - autoleng );#else	q->memoffset = ICON( autoleng );	autoleng += nelt*leng;#endifreturn(q);}/* *  create a temporary block (TTEMP) when optimizing, *  an ordinary TADDR block when not optimizing */Tempp mktmpn(nelt, type, lengp)int nelt;register int type;expptr lengp;{ftnint leng;chainp p, oldp;register Tempp q;Addrp altemp;if (! optimflag)	return ( (Tempp) mkaltmpn(nelt,type,lengp) );if(type==TYUNKNOWN || type==TYERROR)	badtype("mktmpn", type);if(type==TYCHAR)	if( ISICON(lengp) )		leng = lengp->constblock.const.ci;	else	{		err("adjustable length");		return( (Tempp) errnode() );		}else	leng = typesize[type];q = ALLOC(Tempblock);q->tag = TTEMP;q->vtype = type;if(type == TYCHAR)	{	q->vleng = ICON(leng);	q->varleng = leng;	}altemp = ALLOC(Addrblock);altemp->tag = TADDR;altemp->vstg = STGUNKNOWN;q->memalloc = altemp;q->ntempelt = nelt;q->istemp = YES;return(q);}Addrp mktemp(type, lengp)int type;expptr lengp;{return( (Addrp) mktmpn(1,type,lengp) );}/*  allocate a temporary location for the given temporary block;    if already allocated, return its location  */Addrp altmpn(tp)Tempp tp;{Addrp t, q;if (tp->tag != TTEMP)	badtag ("altmpn",tp->tag);t = tp->memalloc;if (t->vstg != STGUNKNOWN)	{	if (tp->vtype == TYCHAR)		{		/*		 * Unformatted I/O parameters are treated like character		 *	strings (sigh) -- propagate type and length.		 */		t = (Addrp) cpexpr(t);		t->vtype = tp->vtype;		t->vleng = tp->vleng;		t->varleng = tp->varleng;		}	return (t);	}q = mkaltmpn (tp->ntempelt, tp->vtype, tp->vleng);cpn (sizeof(struct Addrblock), (char*)q, (char*)t);free ( (charptr) q);return(t);}/*  create and allocate space immediately for a temporary  */Addrp mkaltemp(type,lengp)int type;expptr lengp;{return (mkaltmpn(1,type,lengp));}Addrp mkaltmpn(nelt,type,lengp)int nelt;register int type;expptr lengp;{ftnint leng;chainp p, oldp;register Addrp q;if(type==TYUNKNOWN || type==TYERROR)	badtype("mkaltmpn", type);if(type==TYCHAR)	if( ISICON(lengp) )		leng = lengp->constblock.const.ci;	else	{		err("adjustable length");		return( (Addrp) errnode() );		}/* * if a temporary of appropriate shape is on the templist, * remove it from the list and return it */#ifdef notdef/* * This code is broken until SKFRTEMP slots can be processed in putopt() *	instead of in optimize() -- all kinds of things in putpcc.c can *	bomb because of this.  Sigh. */for(oldp=CHNULL, p=templist  ;  p  ;  oldp=p, p=p->nextp)	{	q = (Addrp) (p->datap);	if(q->vtype==type && q->ntempelt==nelt &&	    (type!=TYCHAR || q->vleng->constblock.const.ci==leng) )		{		if(oldp)			oldp->nextp = p->nextp;		else			templist = p->nextp;		free( (charptr) p);		if (debugflag[14])			fprintf(diagfile,"mkaltmpn reusing offset %d\n",				q->memoffset->constblock.const.ci);		return(q);		}	}#endif notdefq = autovar(nelt, type, lengp);q->istemp = YES;if (debugflag[14])	fprintf(diagfile,"mkaltmpn new offset %d\n",		q->memoffset->constblock.const.ci);return(q);}/*  The following routine is a patch which is only needed because the	*//*  code for processing actual arguments for calls does not allocate	*/

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?