xref: /csrg-svn/lib/libc/gen/exec.c (revision 17259)
1*17259Ssam /* @(#)exec.c	4.2 (Berkeley) 10/16/84 */
21965Swnj /*
31965Swnj  *	execlp(name, arg,...,0)	(like execl, but does path search)
41965Swnj  *	execvp(name, argv)	(like execv, but does path search)
51965Swnj  */
61965Swnj #include <errno.h>
71965Swnj #define	NULL	0
81965Swnj 
91965Swnj static	char shell[] =	"/bin/sh";
101965Swnj char	*execat(), *getenv();
111965Swnj extern	errno;
121965Swnj 
131965Swnj execlp(name, argv)
141965Swnj char *name, *argv;
151965Swnj {
161965Swnj 	return(execvp(name, &argv));
171965Swnj }
181965Swnj 
191965Swnj execvp(name, argv)
201965Swnj char *name, **argv;
211965Swnj {
221965Swnj 	char *pathstr;
231965Swnj 	register char *cp;
241965Swnj 	char fname[128];
251965Swnj 	char *newargs[256];
261965Swnj 	int i;
271965Swnj 	register unsigned etxtbsy = 1;
281965Swnj 	register eacces = 0;
291965Swnj 
301965Swnj 	if ((pathstr = getenv("PATH")) == NULL)
311965Swnj 		pathstr = ":/bin:/usr/bin";
321965Swnj 	cp = index(name, '/')? "": pathstr;
331965Swnj 
341965Swnj 	do {
351965Swnj 		cp = execat(cp, name, fname);
361965Swnj 	retry:
371965Swnj 		execv(fname, argv);
381965Swnj 		switch(errno) {
391965Swnj 		case ENOEXEC:
401965Swnj 			newargs[0] = "sh";
411965Swnj 			newargs[1] = fname;
421965Swnj 			for (i=1; newargs[i+1]=argv[i]; i++) {
431965Swnj 				if (i>=254) {
441965Swnj 					errno = E2BIG;
451965Swnj 					return(-1);
461965Swnj 				}
471965Swnj 			}
481965Swnj 			execv(shell, newargs);
491965Swnj 			return(-1);
501965Swnj 		case ETXTBSY:
511965Swnj 			if (++etxtbsy > 5)
521965Swnj 				return(-1);
531965Swnj 			sleep(etxtbsy);
541965Swnj 			goto retry;
551965Swnj 		case EACCES:
561965Swnj 			eacces++;
571965Swnj 			break;
581965Swnj 		case ENOMEM:
591965Swnj 		case E2BIG:
601965Swnj 			return(-1);
611965Swnj 		}
621965Swnj 	} while (cp);
631965Swnj 	if (eacces)
641965Swnj 		errno = EACCES;
651965Swnj 	return(-1);
661965Swnj }
671965Swnj 
681965Swnj static char *
691965Swnj execat(s1, s2, si)
701965Swnj register char *s1, *s2;
711965Swnj char *si;
721965Swnj {
731965Swnj 	register char *s;
741965Swnj 
751965Swnj 	s = si;
76*17259Ssam 	while (*s1 && *s1 != ':')
771965Swnj 		*s++ = *s1++;
781965Swnj 	if (si != s)
791965Swnj 		*s++ = '/';
801965Swnj 	while (*s2)
811965Swnj 		*s++ = *s2++;
821965Swnj 	*s = '\0';
831965Swnj 	return(*s1? ++s1: 0);
841965Swnj }
85