Subject: make dumps core when invoked on large Makefile
Index:	bin/make 2.11BSD

Description:
	When 'make' was invoked on the C-Kermit(5A) Makefile it would
	dump core due to the stack underflowing.

Repeat-By:
	Get C-Kermit(5A) and "make bsd210ov" (after setting up an
	overlay configuration,etc).  Observe the "Stop.  core dumped"
	error.

Fix:
	'make' being heavily recursive does not work well with
	large buffers being allocated on the stack.  

	There were several pathname buffers still allocated as BUFSIZ
	(1024) bytes long, these were reduced to MAXPATHLEN (256).
	A slight downsizing of the OUTMAX parameter (from 2500 to 2300)
	was also done (the docom() routine allocates 2 of these buffers
	on the stack!).  Even a 'make' of the kernel does not use
	more than about 1300 bytes in the docom() buffers so a slight
	downsizing is safe.

	Other small changes to reduce the amount of local data 
	on the stack involve placing variables in registers,
	reducing flag variables to 'char' instead of 'int', etc.

	The maximum number of arguments to execvp() was reduced from
	400 to 254 and the table made static to further reduce the
	stack requirements.  This reduction is possible because
	execvp() can only handle 254 (in the case of invoking a shell
	script) arguments anyhow.

	The vpath_exp buffer was reduced to the maximum pathlength
	size (from INMAX) and made static to further reduce the
	stack requirements.

	Finally the Makefile was reorganized to use 'xstr' to share
	strings and the silly sccs strings were commented out, this 
	reduces the overall data space growth to about 400 bytes.

	These fixes do not forever fix 'make', but they do allow
	it to handle the C-Kermit(5A) Makefile (about 1400 lines).

------------------------------------------------------------------------
*** Makefile.old	Wed Dec 19 13:25:25 1990
--- Makefile	Sat Aug 10 14:49:49 1991
***************
*** 4,27 ****
  OBJECTS=ident.o main.o doname.o misc.o files.o dosys.o gram.o 
  LIBES= 
  LINT=	lint -ps
  # 2.11BSD uses the newer ascii format archives, not the old binary format
  CFLAGS=	-O -DASCARCH -I.
  # CFLAGS=	-O -I.
  SEPFLAG= -i
  
  all:	make
  
! make:	${OBJECTS}
! 	${CC} -o make ${CFLAGS} ${SEPFLAG} ${OBJECTS} ${LIBES}
  
  ${OBJECTS}:  defs
  
  clean:
! 	-rm -f *.o gram.c make a.out errs
  
  install:
  	install -s make ${DESTDIR}/bin/make
  
  lint :  dosys.c doname.c files.c main.c misc.c ident.c gram.c
! 	${LINT} dosys.c doname.c files.c main.c misc.c ident.c gram.c
  	rm -f gram.c
--- 4,46 ----
  OBJECTS=ident.o main.o doname.o misc.o files.o dosys.o gram.o 
  LIBES= 
  LINT=	lint -ps
+ XSTR=   /usr/ucb/xstr
  # 2.11BSD uses the newer ascii format archives, not the old binary format
  CFLAGS=	-O -DASCARCH -I.
  # CFLAGS=	-O -I.
  SEPFLAG= -i
  
+ # Special massaging of C files for sharing of strings
+ .c.o:
+ 	${CC} -E ${CFLAGS} $*.c | ${XSTR} -c -
+ 	${CC} -c ${CFLAGS} x.c 
+ 	mv -f x.o $*.o
+ 	rm -f x.c
+ 
  all:	make
  
! make:	${OBJECTS} strings.o
! 	${CC} -o make ${CFLAGS} ${SEPFLAG} ${OBJECTS} strings.o ${LIBES}
  
  ${OBJECTS}:  defs
  
  clean:
! 	-rm -f *.o gram.c make a.out errs x.c xs.c strings
  
  install:
  	install -s make ${DESTDIR}/bin/make
  
  lint :  dosys.c doname.c files.c main.c misc.c ident.c gram.c
! 	${LINT} -DASCARCH dosys.c doname.c files.c main.c misc.c ident.c gram.c
  	rm -f gram.c
+ 
+ gram.c: gram.y
+ 	yacc gram.y
+ 	fgrep -v "static char yaccpar_sccsid" y.tab.c >gram.c
+ 	rm -f y.tab.c
+ 
+ strings.o: strings
+ 	${XSTR}
+ 	${CC} -c xs.c
+ 	mv -f xs.o strings.o
+ 	rm -f xs.c
*** defs.old	Sat Jul  8 19:46:48 1989
--- defs	Sun Aug 11 15:04:37 1991
***************
*** 27,34 ****
  #define NLEFTS 80
  #define NCHARS 500
  #define NINTS  250
! #define INMAX 1500
! #define OUTMAX 2500
  #define MAXDIR	10
  #else !BSD2_10
  #define HASHSIZE 1021
--- 27,34 ----
  #define NLEFTS 80
  #define NCHARS 500
  #define NINTS  250
! #define INMAX 1350
! #define OUTMAX 2300
  #define MAXDIR	10
  #else !BSD2_10
  #define HASHSIZE 1021
*** doname.c.old	Sat Jul  8 18:04:47 1989
--- doname.c	Wed Aug 14 08:32:46 1991
***************
*** 20,27 ****
  TIMETYPE *tval;
  {
  int errstat;
! int okdel1;
! int didwork;
  TIMETYPE td, td1, tdep, ptime, ptime1, prestime();
  register struct depblock *q;
  struct depblock *qtemp, *srchdir(), *suffp, *suffp1;
--- 20,27 ----
  TIMETYPE *tval;
  {
  int errstat;
! u_char okdel1;
! u_char didwork;
  TIMETYPE td, td1, tdep, ptime, ptime1, prestime();
  register struct depblock *q;
  struct depblock *qtemp, *srchdir(), *suffp, *suffp1;
***************
*** 30,36 ****
  register struct lineblock *lp;
  struct lineblock *lp1, *lp2;
  #ifdef BSD2_10
! char sourcename[256], prefix[256], temp[256], concsuff[20];
  #else
  char sourcename[BUFSIZ], prefix[BUFSIZ], temp[BUFSIZ], concsuff[20];
  #endif
--- 30,39 ----
  register struct lineblock *lp;
  struct lineblock *lp1, *lp2;
  #ifdef BSD2_10
! /* temp and sourcename are mutually exclusive - save 254 bytes of stack by
!  * reusing sourcename's buffer
! */
! char sourcename[256], prefix[256], *temp = sourcename, concsuff[20];
  #else
  char sourcename[BUFSIZ], prefix[BUFSIZ], temp[BUFSIZ], concsuff[20];
  #endif
***************
*** 47,65 ****
  	 * was that, while macro expansion got done, the .c files in the
  	 * non-local directories wouldn't be found.
  	 */
! 	struct varblock	*vpath_cp, *varptr();
! 	static int	vpath_first;
! 	char	vpath_exp[INMAX];
  
! 	if (!vpath_first) {
! 		vpath_first = 1;
  		vpath_cp = varptr("VPATH");
  		if (vpath_cp->varval) {
  			subst(vpath_cp->varval, vpath_exp);
! 			setvar("VPATH",vpath_exp);
  		}
  	}
  }
  if(p == 0)
  	{
  	*tval = 0;
--- 50,68 ----
  	 * was that, while macro expansion got done, the .c files in the
  	 * non-local directories wouldn't be found.
  	 */
! 	static struct varblock	*vpath_cp;
! 	struct varblock *varptr();
! 	static char vpath_exp[256];
  
! 	if (!vpath_cp) {
  		vpath_cp = varptr("VPATH");
  		if (vpath_cp->varval) {
  			subst(vpath_cp->varval, vpath_exp);
! 			setvar("VPATH", vpath_exp);
  		}
  	}
  }
+ 
  if(p == 0)
  	{
  	*tval = 0;
***************
*** 160,166 ****
  		if (savenamep)
  			pnamep = ".a";
  
! 		srchdir( concat(prefix,"*",temp) , NO, (struct depblock *) NULL);
  		for(lp1 = sufflist ; lp1 ; lp1 = lp1->nxtlineblock)
  		    for(suffp1=lp1->depp ; suffp1 ; suffp1 = suffp1->nxtdepblock)
  			{
--- 163,169 ----
  		if (savenamep)
  			pnamep = ".a";
  
! 		srchdir( concat(prefix,"*",temp), NO, (struct depblock *) NULL);
  		for(lp1 = sufflist ; lp1 ; lp1 = lp1->nxtlineblock)
  		    for(suffp1=lp1->depp ; suffp1 ; suffp1 = suffp1->nxtdepblock)
  			{
***************
*** 246,254 ****
  docom(q)
  struct shblock *q;
  {
! char *s;
  struct varblock *varptr();
! int ign, nopr;
  char string[OUTMAX];
  char string2[OUTMAX];
  
--- 249,257 ----
  docom(q)
  struct shblock *q;
  {
! register char *s;
  struct varblock *varptr();
! register int ign, nopr;
  char string[OUTMAX];
  char string2[OUTMAX];
  
*** dosys.c.old	Fri Aug  9 17:39:46 1991
--- dosys.c	Fri Aug  9 17:57:46 1991
***************
*** 92,104 ****
  
  
  
! #define MAXARGV	400
  
  doexec(str)
  register char *str;
  {
  register char *t;
! char *argv[MAXARGV];
  register char **p;
  
  while( *str==' ' || *str=='\t' )
--- 92,104 ----
  
  
  
! #define MAXARGV	254		/* execvp can only handle 254 anyhow */
  
  doexec(str)
  register char *str;
  {
  register char *t;
! static char *argv[MAXARGV];	/* docom() ate most of the stack already */
  register char **p;
  
  while( *str==' ' || *str=='\t' )
*** files.c.old	Sat Jul  8 18:07:59 1989
--- files.c	Wed Aug 14 08:40:03 1991
***************
*** 194,210 ****
  int mkchain;  /* nonzero if results to be remembered */
  struct depblock *nextdbl;  /* final value for chain */
  {
! DIR *dirf;
! register int i;
! int nread, cldir;
! char *dirname, *dirpref, *endir, *filepat, *p, temp[BUFSIZ];
! char fullname[BUFSIZ], *p1, *p2;
  struct nameblock *q;
  struct depblock *thisdbl;
  struct dirhdr *od;
  struct pattern *patp;
  struct varblock *cp, *varptr();
! char *path, pth[BUFSIZ], *strcpy();
  struct direct *dptr;
  
  
--- 194,209 ----
  int mkchain;  /* nonzero if results to be remembered */
  struct depblock *nextdbl;  /* final value for chain */
  {
! register DIR *dirf;
! int cldir;
! char *dirname, *dirpref, *endir, *filepat, *p, temp[MAXPATHLEN];
! char fullname[MAXPATHLEN], *p1, *p2;
  struct nameblock *q;
  struct depblock *thisdbl;
  struct dirhdr *od;
  struct pattern *patp;
  struct varblock *cp, *varptr();
! char *path, pth[MAXPATHLEN], *strcpy();
  struct direct *dptr;
  
  
***************
*** 606,612 ****
  	{
  	if (fread(&objentry, sizeof(objentry), 1, arfd) != 1)
  		return (0);
! 	if (objentry.n_type == N_EXT | N_TEXT &&
  		!strncmp(objentry.n_name, s, 8))
  			return (1);
  	}
--- 605,611 ----
  	{
  	if (fread(&objentry, sizeof(objentry), 1, arfd) != 1)
  		return (0);
! 	if ((objentry.n_type == (N_EXT | N_TEXT)) &&
  		!strncmp(objentry.n_name, s, 8))
  			return (1);
  	}
***************
*** 696,702 ****
  {
  	register char *r, *q;
  	struct nameblock *pn;
! 	char name[BUFSIZ];
  
  	while (*s) {
  		if (isspace(*s)) *d++ = *s++;
--- 695,701 ----
  {
  	register char *r, *q;
  	struct nameblock *pn;
! 	char name[MAXPATHLEN];
  
  	while (*s) {
  		if (isspace(*s)) *d++ = *s++;
*** gram.y.old	Sun Feb  8 17:24:38 1987
--- gram.y	Sun Aug 11 15:24:59 1991
***************
*** 1,5 ****
  %{#include "defs"
! static	char *sccsid = "@(#)gram.y	4.1 (Berkeley) 81/02/28";
  %}
  
  %term NAME SHELLINE START MACRODEF COLON DOUBLECOLON GREATER
--- 1,5 ----
  %{#include "defs"
! /* static	char *sccsid = "@(#)gram.y	4.1 (Berkeley) 81/02/28"; */
  %}
  
  %term NAME SHELLINE START MACRODEF COLON DOUBLECOLON GREATER
*** ident.c.old	Thu Aug  8 18:18:41 1991
--- ident.c	Thu Aug  8 18:19:03 1991
***************
*** 1,4 ****
! char *xxxvers =  "\n@(#) MAKE.  VERSION 2.61     13 AUGUST 1980\n" ;
  /* static	char *sccsid = "@(#)ident.c	4.1 (Berkeley) 81/02/28"; */
  
  /*
--- 1,4 ----
! /* char *xxxvers =  "\n@(#) MAKE.  VERSION 2.61     13 AUGUST 1980\n" ; */
  /* static	char *sccsid = "@(#)ident.c	4.1 (Berkeley) 81/02/28"; */
  
  /*
*** main.c.old	Sat Jul  8 18:09:16 1989
--- main.c	Sat Aug 10 19:05:36 1991
***************
*** 56,66 ****
  char *argv[];
  {
  register struct nameblock *p;
! int i, j;
  int descset, nfargs;
  TIMETYPE tjunk;
  char c, *s;
! static char onechar[2] = "X";
  #ifdef unix
  int intrupt();
  #endif
--- 56,66 ----
  char *argv[];
  {
  register struct nameblock *p;
! register int i, j;
  int descset, nfargs;
  TIMETYPE tjunk;
  char c, *s;
! static char onechar[2] = 'X';
  #ifdef unix
  int intrupt();
  #endif
