Luc*_*caW 2 c arguments fork argc
我在课堂上得到了这个代码:
int main(int argc, char **argv)
{
if(argc)
{
return 1;
}
puts(argv[3]);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
现在,我应该编写第二个程序来执行它并使其打印“Hello World!”。所以我必须找到一种方法来传递参数(我假设使用 execv)同时让 argc 保持在 0。
这是我到目前为止:
int main(int argc, char **argv)
{
if(argc)
{
return 1;
}
puts(argv[3]);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
这将在 Linux 上运行。
我尝试了 mbj 最初的建议,在参数数组中传递一个 0,但遗憾的是没有奏效。但是,如果我将 0 作为第一个参数,argc 将变为 0,但是当我尝试打印参数时会得到输出“LC_MEASUREMENT=de_DE.UTF-8”。谷歌搜索这也没有真正帮助我。
我在这里完全不知所措,所以任何帮助表示赞赏。
好的,经过我自己的一些实验,我现在想通了。
由于传递以NULL( 0)开头的数组会execv导致程序打印出来LC_MEASUREMENT=de_DE.UTF-8,我意识到它一定意味着指的argv[3]是进程环境中的一个元素(LC_MEASUREMENT 是用于在 Linux 中配置语言环境设置的环境变量之一)。
execv由于execv会将当前环境复制到新程序中,因此我们只需要修改环境并将字符串"Hello World!"放在正确的位置,然后再调用execv. 事实证明,打印的字符串是环境的索引 2 指向的字符串。
要访问当前环境,我们需要在environ之外声明变量main:
external char **environ;
int main()
{
...
Run Code Online (Sandbox Code Playgroud)
然后在调用之前执行此操作execv:
char *argv[] = { NULL };
environ[2] = "Hello world!";
execv("filepath", argv);
Run Code Online (Sandbox Code Playgroud)
execve我们可以使用该函数,而不是external char **environ在调用之前声明和修改当前环境,它让我们传入一个新的字符串数组作为程序的环境:execvexecve
char *argv[] = { NULL };
char *envp[] = { "foo", "bar", "Hello World!", NULL };
execve("filepath", argv, envp);
Run Code Online (Sandbox Code Playgroud)
如上面的代码片段所示,无论我们使用哪种方法,都"Hello World!"需要2位于环境的索引处。
这样做的原因是,当程序执行时,命令行参数和环境在进程内存中的布局有一个标准:字符指针的环境数组放在命令行参数数组之后。
由于这些数组以 NULL 条目终止,因此它将如下所示:
+---------+---------------------------------------+
| Args | Environment |
+---------+---------+---------+---------+---------+
| NULL | envp[0] | envp[1] | envp[2] | NULL |
+---------+---------+---------+---------+---------+
^ ^ ^
| | |
argv[0] argv[1] ... argv[3]
Run Code Online (Sandbox Code Playgroud)
我希望 ASCII 艺术可以帮助您理解为什么argv[3]与environ[2]我们执行这样的程序时的含义相同。
| 归档时间: |
|
| 查看次数: |
1502 次 |
| 最近记录: |