Add a libc function execvP that takes the search path as an arguement.

Change execvp to be a wrapper around execvP. This is necessary for some
of the /rescue pieces. It may also be more generally applicable as well.

Submitted by:	Tim Kientzle <kientzle@acm.org>
Approved by:	Silence on arch@
This commit is contained in:
Gordon Tetlow 2003-06-29 17:33:34 +00:00
parent 2e7c2f97aa
commit 09f49aab84
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=117030
3 changed files with 41 additions and 15 deletions

View File

@ -335,6 +335,7 @@ int execlp(const char *, const char *, ...);
int execv(const char *, char * const *);
int execve(const char *, char * const *, char * const *);
int execvp(const char *, char * const *);
int execvP(const char *, const char *, char * const *);
pid_t fork(void);
long fpathconf(int, int);
char *getcwd(char *, size_t);

View File

@ -41,7 +41,8 @@
.Nm execle ,
.Nm exect ,
.Nm execv ,
.Nm execvp
.Nm execvp ,
.Nm execvP
.Nd execute a file
.Sh LIBRARY
.Lb libc
@ -60,6 +61,8 @@
.Fn execv "const char *path" "char *const argv[]"
.Ft int
.Fn execvp "const char *file" "char *const argv[]"
.Ft int
.Fn execvP "const char *file" "const char *search_path" "char *const argv[]"
.Sh DESCRIPTION
The
.Nm exec
@ -99,8 +102,9 @@ pointer.
The
.Fn exect ,
.Fn execv ,
.Fn execvp ,
and
.Fn execvp
.Fn execvP
functions provide an array of pointers to null-terminated strings that
represent the argument list available to the new program.
The first argument, by convention, should point to the file name associated
@ -134,14 +138,19 @@ in the current process.
Some of these functions have special semantics.
.Pp
The functions
.Fn execlp
.Fn execlp ,
.Fn execvp ,
and
.Fn execvp
.Fn execvP
will duplicate the actions of the shell in searching for an executable file
if the specified file name does not contain a slash
.Dq Li /
character.
The search path is the path specified in the environment by
For
.Fn execlp
and
.Fn execvp ,
search path is the path specified in the environment by
.Dq Ev PATH
variable.
If this variable isn't specified,
@ -151,6 +160,9 @@ definition in
.Aq paths.h ,
which is set to
.Dq Ev /usr/bin:/bin .
For
.Fn execvP ,
the search path is specified as an argument to the function.
In addition, certain errors are treated specially.
.Pp
If an error is ambiguous (for simplicity, we shall consider all
@ -206,9 +218,10 @@ The shell.
The
.Fn execl ,
.Fn execle ,
.Fn execlp
and
.Fn execlp ,
.Fn execvp
and
.Fn execvP
functions
may fail and set
.Va errno
@ -300,3 +313,7 @@ and
functions
conform to
.St -p1003.1-88 .
The
.Fn execvP
function first appeared in
.Fx 5.2 .

View File

@ -142,15 +142,27 @@ execv(name, argv)
}
int
execvp(name, argv)
execvp(const char *name, char *const *argv)
{
const char *path;
/* Get the path we're searching. */
if (!(path = getenv("PATH")))
path = _PATH_DEFPATH;
return(execvP(name,path,argv));
}
int
execvP(name, path, argv)
const char *name;
const char *path;
char * const *argv;
{
char **memp;
int cnt, lp, ln;
char *p;
int eacces, save_errno;
char *bp, *cur, *path, buf[MAXPATHLEN];
char *bp, *cur, buf[MAXPATHLEN];
struct stat sb;
eacces = 0;
@ -158,7 +170,7 @@ execvp(name, argv)
/* If it's an absolute or relative path name, it's easy. */
if (index(name, '/')) {
bp = (char *)name;
cur = path = NULL;
cur = NULL;
goto retry;
}
bp = buf;
@ -169,16 +181,12 @@ execvp(name, argv)
return (-1);
}
/* Get the path we're searching. */
if (!(path = getenv("PATH")))
path = _PATH_DEFPATH;
cur = alloca(strlen(path) + 1);
if (cur == NULL) {
errno = ENOMEM;
return (-1);
}
strcpy(cur, path);
path = cur;
while ( (p = strsep(&cur, ":")) ) {
/*
* It's a SHELL path -- double, leading and trailing colons
@ -197,7 +205,7 @@ execvp(name, argv)
* the user may execute the wrong program.
*/
if (lp + ln + 2 > sizeof(buf)) {
(void)_write(STDERR_FILENO, "execvp: ", 8);
(void)_write(STDERR_FILENO, "execvP: ", 8);
(void)_write(STDERR_FILENO, p, lp);
(void)_write(STDERR_FILENO, ": path too long\n",
16);