设为首页 加入收藏

TOP

Linux LD_PRELOAD
2014-11-24 12:09:33 来源: 作者: 【 】 浏览:0
Tags:Linux LD_PRELOAD

前些天为了排查我们程序中不知道是库里面还是我们自己调用了assert断言,导致我们程序死亡。想通过hook拦截到调用这个函数的调用者,偶然间想起proload(预加载),小试牛刀使用如下代码


#include
#include
#include
#include
void abort(void)
{
printf("****************my abort, getpid():%u\n", __FILE__, __LINE__, getpid());
int *a = NULL;
*a = 1;
while(1)
{
sleep(10000);
}
}



gcc --shared -fPIC preload.c -o libpreload.so 编译成so的形式



使用如下代码进行测试


#include
#include
int main ( int argc, char *argv[] )
{
printf("file:%s, line:%d, getpid():%u\n", __FILE__, __LINE__, getpid());
abort();
printf("file:%s, line:%d\n", __FILE__, __LINE__);
void *p = malloc(3);
return p == NULL;
return EXIT_SUCCESS;
}


gcc testpreload.c -o testpreload 编译可执行程序,默认链接到了glibc中的assert



启动方式,


将libpreload.so放到和可执行程序testpreload同级目录下


LD_LIBRARY_PATH=".:$LD_LIBRARY_PATH" LD_PRELOAD="libpreload.so" ./testpreload



加入LD_LIBRARY_PATH 对当前目录的搜索,使用LD_PRELOAD 设定预加载的so,启动后输出如下结果


file:testpreload.c, line:31, getpid():9960
****************my abort, getpid():3086001460
./run.sh: line 1: 9960 段错误 LD_LIBRARY_PATH=".:$LD_LIBRARY_PATH" LD_PRELOAD="libpreload.so" ./testpreload



我故意产生了一个SIGV错误,暂时弄不清楚为什么getpid()的系统调用返回值不对,printf却可以运行无误。


主要用途:


可以代替ptrace拦截系统调用,或者对函数的调用,可以用来分析一些比如内存泄露(malloc free是否成对调用)等等问题


】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
分享到: 
上一篇Java中的继承与对象的访问 下一篇Linux Kernel中的编码技巧:将运..

评论

帐  号: 密码: (新用户注册)
验 证 码:
表  情:
内  容:

·PostgreSQL 索引 - (2025-12-25 22:20:43)
·MySQL Node.js 连接 (2025-12-25 22:20:41)
·SQL 撤销索引、表以 (2025-12-25 22:20:38)
·Linux系统简介 (2025-12-25 21:55:25)
·Linux安装MySQL过程 (2025-12-25 21:55:22)