[英]pathname vs arguments for execve parameters
我正在尝试实现一个运行用户输入命令的简单 shell 程序。 我希望用户输入“ls”或“dir”并让 shell 运行 /bin/ls 或 /bin/dir。 对于 execve 参数,什么是正确的:
char *args[] ={"/bin/", "ls", NULL};
//Fork, pid, etc...then
execve(args[0], args+1, NULL);
还是会有所不同?? 我看到有些人使用/bin/ls
作为路径名,然后没有 arguments 或ls
作为路径名和\bin
作为环境? 我尝试了上面的方法,但它没有用,所以我想知道它是否是我发送的 arguments,或者我是否应该在我的代码中的其他地方寻找问题。 请注意,我对 execve 的其他变体不感兴趣,例如 execvp。 我在 Linux 系统上。 谢谢
execve()
中的路径名必须是可执行文件的完整路径,例如/bin/ls
。 如果使用execvpe()
,您可以单独使用ls
作为路径名,但正如您已经指定的那样,您不想使用它。
arguments 应该是一个字符串数组,一个字符串对应命令行上指定的每个以空格分隔的参数。 最后一个应该是 NULL。第一个参数应该是路径名本身。 例如:
char* args[] = {"/bin/ls", "-la", "foo/bar", NULL};
使用execve()
时不能省略环境变量。 在某些实现中, NULL
可以作为最后一个参数传递给execve()
,但这不是标准的。 相反,您应该传递一个指向 null 指针的指针; 本质上是一个空的环境变量数组。
char *args[] ={"/bin/ls", "-foo", "bar", NULL};
//Fork, pid, etc...then
char* nullstr = NULL;
execve(args[0], args, &nullstr);
来自execve [强调添加] :
int execve(const char *pathname, char *const argv[], char *const envp[]);
execve() 执行路径名引用的程序。 这导致调用进程当前正在运行的程序被新程序替换,具有新初始化的堆栈、堆和(已初始化和未初始化的)数据段。
路径名必须是二进制可执行文件或以以下形式的行开头的脚本:
#!interpreter [optional-arg]
有关后一种情况的详细信息,请参阅下面的“解释器脚本”。
argv 是一个指针数组,指向作为命令行 arguments 传递给新程序的字符串。按照惯例,这些字符串中的第一个(即 argv[0])应该包含与正在执行的文件关联的文件名。 argv 数组必须以 NULL 指针结尾。 (因此,在新程序中,argv[argc] 将为 NULL。)
在您的情况下, pathname
应该是"/bin/ls"
而不是"/bin/"
。 如果你想通过命令传递任何命令行参数,你可以为第一个参数提供argv
向量索引1
,第二个参数索引2
等等,并用NULL
终止参数向量。
一个用/bin/ls
程序替换当前可执行映像并运行/bin/ls testfile
的示例程序:
#include <stdio.h>
#include <unistd.h>
int main (void) {
char *args[] = {"/bin/ls", "testfile", NULL};
// here you can call fork and then call execve in child process
execve(args[0], args, NULL);
return 0;
}
Output:
# ./a.out
testfile
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.