我open()
在 Linux(在我的情况下为 Debian)上拦截时遇到了麻烦。这是一个内置到共享对象中的简约 C 源代码:
/* Defines are needed for dlfcn.h (RTLD_NEXT) */
#define __USE_GNU
#define _GNU_SOURCE
#include <stdarg.h>
#include <stdio.h>
#include <stdlib.h>
#include <dlfcn.h>
#include <unistd.h>
int open(char const *path, int oflag, ...) {
int (*real_open)(char const *, int, ...);
char *msg;
va_list args;
int mflag;
fprintf(stderr, ">>>>> in open <<<<<<\n");
real_open = dlsym(RTLD_NEXT, "open");
if ( (msg = dlerror()) ) {
fprintf(stderr, "dlsym error: %s\n", msg);
exit(1);
}
va_start(args, oflag);
mflag = va_arg(args, int);
return real_open(path, oflag, mflag);
}
ssize_t read(int fd, void *buf, size_t count) {
ssize_t (*real_read)(int, void*, size_t);
char *msg;
fprintf(stderr, ">>>>> in read <<<<<\n");
real_read = dlsym(RTLD_NEXT, "read");
if ( (msg = dlerror()) ) {
fprintf(stderr, "dlsym error: %s\n", msg);
exit(1);
}
return real_read(fd, buf, count);
}
共享对象是使用以下方法构建的:
cc -c -fPIC -Wall funcs.c
cc -shared -o libfuncs.so funcs.o -ldl -lc
现在当我尝试
export LD_PRELOAD=/path/to/libfuncs.so
cat somefile
然后我只在输出中看到它的踪迹read()
是>>>>> in read <<<<<
. 我从来没有看到过一丝open()
。我检查了cat Makefile
使用的内容strace
,果然 - 两者open()
都read()
被称为:
open("Makefile", O_RDONLY|O_LARGEFILE) = 3
fstat64(3, {st_mode=S_IFREG|0644, st_size=213, ...}) = 0
read(3, "testrun: libfuncs.so\n\tLD_PRELOAD"..., 32768) = 213
顺便说一句,我还检查了其他程序,例如od
or bash
,从来没有拦截过open()
。这里发生了什么?提前致谢...
`