我正在通过第一次分叉然后执行execve()来执行一个来自另一个程序的程序。现在问题是我希望A使用我的库,我通常会使用LD_PRELOAD。我如何在execve()中完成。
由于
答案 0 :(得分:11)
你可以在envp execve的参数中传递LD_PRELOAD:
获得执行的程序,名为“run”:
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
int main(int argc, char **argv)
{
printf("%s\n",getenv("LD_PRELOAD"));
}
执行execve的程序,名为“ex”:
#include <stdio.h>
#include <unistd.h>
int main(int argc, char **argv)
{
char *const args[] = {"./run",NULL};
char *const envs[] = {"LD_PRELOAD=caca",NULL};
execve("./run",args,envs);
}
运行它:
root@pinkpony:~# ./ex
ERROR: ld.so: object 'caca' from LD_PRELOAD cannot be preloaded: ignored.
caca
编辑: 显示的错误被抛出,因为“caca”lib无法为运行预加载,因此它可以正常工作。 (为了清楚起见,我跳过了fork()部分,但用法是相同的)
编辑: 做类似的事情:
LD_PRELOAD=caca ./ex
如果你没有通过envp execve()的参数传递它,那么将不会在execve()运行时自动预加载caca lib
答案 1 :(得分:0)
<强>更新强>
在阅读问题中添加的信息后,我猜你可能需要指定一个完整的路径,或者设置LD_LIBRARY_PATH?由于加载程序 确认预订已订购。
否则,我可以想象存在安全限制(尽管它必须与从登录shell调用运行绑定,这似乎很难检测)。尽管如此,您可能希望尝试以root身份运行(使用sudo -E
来保持您的环境)
从this earlier question看来,这种行为是默认的
LD_PRELOAD affects new child even after unsetenv("LD_PRELOAD")
你测试过吗?
答案 2 :(得分:0)
如果你想只为程序A(而不是它的父程序)使用LD_PRELOAD,你可以通过shell加载它;将要执行的程序的名称传递给shell,并将LD_PRELOAD添加到环境中。