1

我想覆盖 getdirentries(和其他,如 lstat)libc 系统调用。我可以覆盖 - 例如 - lstat 和 chmod,但我不能覆盖 getdirentries(以及其他 fstatfs)。

示例代码是:

    #include <errno.h>
    #include <dlfcn.h>
    #include <stdio.h>
    #include <strings.h>
    #include <string.h>
    #include <sys/_timespec.h>
    #include <sys/stat.h>
    #include <sys/mount.h>

    #ifndef RTLD_NEXT
    #define RTLD_NEXT   ((void *) -1l)
    #endif

    int (*getdirentries_orig)(int fd, char *buf, int nbytes, long *basep);
    int (*lstat_orig)(const char *path, struct stat *sb);
    int (*fstatfs_orig)(int fd, struct statfs *buf);
    int (*chmod_orig)(const char *path, mode_t mode);

    #define HOOK(func) func##_##orig = dlsym(RTLD_NEXT,#func)

    int getdirentries(int fd, char *buf, int nbytes, long *basep) {
        HOOK(getdirentries);
        printf("getdirentries\n");
        return getdirentries_orig(fd, buf, nbytes, basep);
    }

    int lstat(const char *path, struct stat *sb) {
        HOOK(lstat);
        printf("lstat\n");
        return (lstat_orig(path, sb));
    }

    int fstatfs(int fd, struct statfs *buf) {
        HOOK(fstatfs);
        printf("fstatfs\n");
        return fstatfs_orig(fd, buf);
    }

    int chmod(const char *path, mode_t mode) {
        HOOK(chmod);
        printf("chmod\n");
        return chmod_orig(path, mode);
    }

我在 FreeBSD 上编译它:

cc -Wall -g -O2 -fPIC -shared -o preload.so preload.c

(在 Linux 上,可能需要添加 -ldl)并将其与 LD​​_PRELOAD=./preload.so bash 一起使用。

如果我随后发出 ls -l,我会多次打印“lstat”,这很好。但是根据 ktrace,ls 也调用了多个 getdirentries,并且它的覆盖函数不会被调用。fstatfs 也不起作用。

如何覆盖 getdirentries、fstatfs 和可能的其他系统调用,以及为什么它们在这种情况下不起作用?

谢谢,

4

1 回答 1

0

事实证明,libc/readdir.c 中的 readdir()(readdir 是 ls 调用的,应该调用 getdirentries)调用 _getdirentries,而不是 getdirentries。如果我覆盖 _getdirentries,它会起作用。fstatfs 也是如此,所以这就是我的程序不起作用的原因。

于 2014-11-27T08:44:07.330 回答