I'm trying to implement execvp () using execv (). I don't know if the code is the best implementation.
my code:
#include <string.h>
#include <unistd.h>
#include <stdlib.h>
#include <errno.h>
#include <stdio.h>
extern char **environ;
int my_execvp(char *file, char *argv[])
{
char *p, *colon, *pathseq = getenv("PATH");
size_t len;
if(strchr (file, '/'))
return execv(file, argv);
if (pathseq == NULL) {
len = confstr(_CS_PATH, (char *) NULL, 0);
pathseq = (char *) alloca(1 + len);
pathseq[0] = ':';
(void) confstr (_CS_PATH, pathseq + 1, len);
}
len = strlen(file) + strlen(pathseq) + 2;
for(p = pathseq; p && *p; p = colon)
{
char b[len];
colon = strchr(p, ':');
if(colon)
{
memcpy(b, p, (size_t) (colon - p));
b[colon++-p] = 0;
}
else
strcpy(b, p);
strcat (b, "/");
strcat (b, file);
if(!access(b, F_OK)) {
execv(b, argv);
fprintf(stderr, "an error occurred in execv\n");
abort();
}
}
errno = ENOENT;
return -1;
}
int main()
{
/* "ls / -l" */
char *arg[] = {"ls", "/", "-l", NULL};
my_execvp (arg[0], arg);
return 0;
}
And the question I have, is it a good implementation? How could it be improved or write a better implementation?
1 Answer 1
The implementation is non-conformant.
- No handling of undefined
PATH
. Quotingman execp
:
search path is the path specified in the environment by ``PATH'' variable. If this variable is not specified, the default path is set according to the
_PATH_DEFPATH
definition in <paths.h>
Once confstr
returns 0
, check errno
, and act accordingly.
Calling
abort
onexecv
failure is plain wrong. At least return whatexecv
returns.Calling
access
is also incorrect. If the file exists, but doesn't have correct permissions,execvp
shall continue searching.
As a side note, access
is very rarely useful. Consider calling execvp
blindly, and testing errno
upon return.
Final
errno = ENOENT;
is also non-compliant.execvp
setsENOENT
if the file does not exist in any path. If it was found at least once, and fails to execute, theerrno
shall beEACCES
.execvp
is not supposed tofprintf
anything.
Explore related questions
See similar questions with these tags.