4

如何确定代表当前进程的可执行文件的文件?

问题是它argv[0]不可靠,就好像它被调用 via 一样execXp,满足非限定命令的路径条目可能会或可能不会被前置。此外,任何来电者都exec*可以用任何东西代替argv[0]

因此,如果您运行ps,则不能保证argv[0]会是"/usr/bin/ps"。事实上,您可能会得到 OPOSITE 的保证。

我需要以下之一:

  1. 完整路径名(自己不进行路径搜索,以免我使用的 envp 不是 shell 使用的那个)
  2. 与当前进程映像对应的文件的实时、预先打开的文件描述符
  3. 一些与当前内存中的代码段相对应的魔法描述符(虽然不太确定 BSS 段)

这样,在启动时,我可以快速打开一个 FD 到我自己的可执行文件(对于案例 1.,以防文件被删除并变得无法打开),然后在更晚的日期调用:

int fexecve(int fd, char *const argv[], char *const envp[]);

to fork/exec我自己(通常需要在 OS-X 上解决之后的全局和系统描述符状态的不可靠性fork() )。换句话说(这个例子当然很傻):

void magicallyReplicate(argc, argv)
{
  if (!fork()) {
    magicallyExecMyself(argc, argv);
  }
}

甚至只是:

void startOver(argc, argv)
{
  magicallyExecMyself(argc, argv);
}

当然,在我的示例中,我将使用不同argv的 ',以便我可以在不同的模式下运行。

(早期的“不”反驳:你不能使用clone(),因为它是fork()的血统)

4

1 回答 1

2

fork所以基本上,最简单的平台是 MacOS(因为 libc 完全损坏,如果在and之间调用 getaddrinfo segfault 等简单的东西exec) - 在达尔文上,内核在启动进程时将完整的二进制名称交给你. 使用 main 的第四个参数(http://web.archive.org/web/20170816030258/http://unixjunkie.blogspot.com/2006/02/char-apple-argument-vector.html)或使用 _NSGetExecutablePath检索它这是完全相同的——它只是一个知道内核放置文件名的相同特殊位置的函数。

对于所有平台,这是一个个案问题。此线程中的完整详细信息:Find current executable's path without /proc/self/exe

于 2013-11-14T08:45:40.710 回答