Skip to main content
remove dlopen() if using gnu
Source Link
meuh
  • 54.7k
  • 2
  • 70
  • 138

LD_PRELOAD isn't too difficult, and you don't need to be root. Interpose your own C routine which is called instead of the real open() in the C library. Your routine checks if the file to open is "/tmp/adb.log" and calls the real open with a different filename. Here's your shim_open.c:

/*
 * capture calls to a routine and replace with your code
 * gcc -Wall -O2 -fpic -shared -ldl -o shim_open.so shim_open.c
 * LD_PRELOAD=/.../shim_open.so cat /tmp/adb.log
 */
#define _FCNTL_H 1 /* hack for open() prototype */
#define _GNU_SOURCE /* needed to get RTLD_NEXT defined in dlfcn.h */
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <dlfcn.h>
#define OLDNAME "/tmp/adb.log"
#define NEWNAME "/tmp/myadb.log"

int open(const char *pathname, int flags, mode_t mode){
    static int (*real_open)(const char *pathname, int flags, mode_t mode) = NULL;

    if (!real_open) {
        void *handle = dlopen("/lib64/libc.so.6",RTLD_LAZY);
        if (!handle) {
            fprintf(stderr, "%s\n", dlerror());
            exit(1);
        }
        real_open = dlsym(handleRTLD_NEXT, "open");
        char *error = dlerror();
        if (error != NULL) {
            fprintf(stderr, "%s\n", error);
            exit(1);
        }
    }
    if (strcmp(pathname,OLDNAME)==0) pathname = NEWNAME;
    fprintf(stderr, "opening: %s\n", pathname);
    return real_open(pathname, flags, mode);
}

Compile it with gcc -Wall -O2 -fpic -shared -ldl -o shim_open.so shim_open.c and test it by putting something in /tmp/myadb.log and running LD_PRELOAD=/.../shim_open.so cat /tmp/adb.log. Then try the LD_PRELOAD on adb. YMMV: replace /lib64/libc.so.6 by wherever your libc is.

LD_PRELOAD isn't too difficult, and you don't need to be root. Interpose your own C routine which is called instead of the real open() in the C library. Your routine checks if the file to open is "/tmp/adb.log" and calls the real open with a different filename. Here's your shim_open.c:

/*
 * capture calls to a routine and replace with your code
 * gcc -Wall -O2 -fpic -shared -ldl -o shim_open.so shim_open.c
 * LD_PRELOAD=/.../shim_open.so cat /tmp/adb.log
 */
#define _FCNTL_H 1 /* hack for open() prototype */
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <dlfcn.h>
#define OLDNAME "/tmp/adb.log"
#define NEWNAME "/tmp/myadb.log"

int open(const char *pathname, int flags, mode_t mode){
    static int (*real_open)(const char *pathname, int flags, mode_t mode) = NULL;

    if (!real_open) {
        void *handle = dlopen("/lib64/libc.so.6",RTLD_LAZY);
        if (!handle) {
            fprintf(stderr, "%s\n", dlerror());
            exit(1);
        }
        real_open = dlsym(handle, "open");
        char *error = dlerror();
        if (error != NULL) {
            fprintf(stderr, "%s\n", error);
            exit(1);
        }
    }
    if (strcmp(pathname,OLDNAME)==0) pathname = NEWNAME;
    fprintf(stderr, "opening: %s\n", pathname);
    return real_open(pathname, flags, mode);
}

Compile it with gcc -Wall -O2 -fpic -shared -ldl -o shim_open.so shim_open.c and test it by putting something in /tmp/myadb.log and running LD_PRELOAD=/.../shim_open.so cat /tmp/adb.log. Then try the LD_PRELOAD on adb. YMMV: replace /lib64/libc.so.6 by wherever your libc is.

LD_PRELOAD isn't too difficult, and you don't need to be root. Interpose your own C routine which is called instead of the real open() in the C library. Your routine checks if the file to open is "/tmp/adb.log" and calls the real open with a different filename. Here's your shim_open.c:

/*
 * capture calls to a routine and replace with your code
 * gcc -Wall -O2 -fpic -shared -ldl -o shim_open.so shim_open.c
 * LD_PRELOAD=/.../shim_open.so cat /tmp/adb.log
 */
#define _FCNTL_H 1 /* hack for open() prototype */
#define _GNU_SOURCE /* needed to get RTLD_NEXT defined in dlfcn.h */
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <dlfcn.h>
#define OLDNAME "/tmp/adb.log"
#define NEWNAME "/tmp/myadb.log"

int open(const char *pathname, int flags, mode_t mode){
    static int (*real_open)(const char *pathname, int flags, mode_t mode) = NULL;

    if (!real_open) {
        real_open = dlsym(RTLD_NEXT, "open");
        char *error = dlerror();
        if (error != NULL) {
            fprintf(stderr, "%s\n", error);
            exit(1);
        }
    }
    if (strcmp(pathname,OLDNAME)==0) pathname = NEWNAME;
    fprintf(stderr, "opening: %s\n", pathname);
    return real_open(pathname, flags, mode);
}

Compile it with gcc -Wall -O2 -fpic -shared -ldl -o shim_open.so shim_open.c and test it by putting something in /tmp/myadb.log and running LD_PRELOAD=/.../shim_open.so cat /tmp/adb.log. Then try the LD_PRELOAD on adb.

Source Link
meuh
  • 54.7k
  • 2
  • 70
  • 138

LD_PRELOAD isn't too difficult, and you don't need to be root. Interpose your own C routine which is called instead of the real open() in the C library. Your routine checks if the file to open is "/tmp/adb.log" and calls the real open with a different filename. Here's your shim_open.c:

/*
 * capture calls to a routine and replace with your code
 * gcc -Wall -O2 -fpic -shared -ldl -o shim_open.so shim_open.c
 * LD_PRELOAD=/.../shim_open.so cat /tmp/adb.log
 */
#define _FCNTL_H 1 /* hack for open() prototype */
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <dlfcn.h>
#define OLDNAME "/tmp/adb.log"
#define NEWNAME "/tmp/myadb.log"

int open(const char *pathname, int flags, mode_t mode){
    static int (*real_open)(const char *pathname, int flags, mode_t mode) = NULL;

    if (!real_open) {
        void *handle = dlopen("/lib64/libc.so.6",RTLD_LAZY);
        if (!handle) {
            fprintf(stderr, "%s\n", dlerror());
            exit(1);
        }
        real_open = dlsym(handle, "open");
        char *error = dlerror();
        if (error != NULL) {
            fprintf(stderr, "%s\n", error);
            exit(1);
        }
    }
    if (strcmp(pathname,OLDNAME)==0) pathname = NEWNAME;
    fprintf(stderr, "opening: %s\n", pathname);
    return real_open(pathname, flags, mode);
}

Compile it with gcc -Wall -O2 -fpic -shared -ldl -o shim_open.so shim_open.c and test it by putting something in /tmp/myadb.log and running LD_PRELOAD=/.../shim_open.so cat /tmp/adb.log. Then try the LD_PRELOAD on adb. YMMV: replace /lib64/libc.so.6 by wherever your libc is.