このプログラムをCで書くのは少しばかげているように見えますが、そうする正当な理由がある場合(たとえば、setuidが必要な場合)、それについてははるかに防御的である必要があります。私はこのようなことをします:
#define _XOPEN_SOURCE 700 /* getline */
#include <stdio.h>
#include <string.h>
#include <unistd.h>
int main(void)
{
char *jobdir = 0;
size_t asize = 0;
ssize_t len;
fputs("Enter job directory: ", stdout);
fflush(stdout);
len = getline(&jobdir, &asize, stdin);
if (len < 0) {
perror("getline");
return 1;
}
jobdir[--len] = '\0'; /* remove trailing \n */
if (len == 0 || !strcmp(jobdir, ".") || !strcmp(jobdir, "..")
|| strchr(jobdir, '/')) {
fputs("job directory name may not be empty, \".\", or \"..\", "
"nor contain a '/'\n", stderr);
return 1;
}
if (chdir("/home/jobs") || chdir(jobdir) || chdir("xxx")) {
perror(jobdir);
return 1;
}
execlp("ls", "ls", "-ltr", (char *)0);
perror("exec");
return 1;
}
この回答の編集履歴は、これを100%正しくすることがどれほど難しいかを示しています。私はそれに戻って、防御する必要のあるさらに別のケースを忘れていることに気づきます。