2016-12-25 41 views
2

我想了解內存跟蹤器和檢漏儀是如何工作的,所以我想到了這個想法,我有一個可執行文件,我希望在執行時強制使用我自己的內存分配函數,而不是通常的系統函數(「malloc 「,」realloc「...)。可以強制一個可執行文件使用用戶定義的'malloc'?

我自己的函數存儲在庫(靜態或共享),或者只是一個目標文件(名爲「.o」),THIK類似的東西:

void *my_own_malloc(unsigned long size) { 
    printf("allocate: %lu\n", size); 
    return malloc(size); 
} 

PS:我沒有更改可執行文件的源代碼(我沒有源代碼)

PS2:我想要做的是,在所有不同的平臺(Windows,OS X & Linux的...)

+0

@Lolrapa這裏的問題是注入的函數必須有一個名稱爲'malloc',但在注入的函數內有一個調用到系統「malloc」,這可能會產生一個無限遞歸函數?! –

回答

3

我不知道其他平臺,但在GNU/Linux上,您可以預先加載一個小內存跟蹤庫y與LD_PRELOAD環境變量,其中定義了您自己的mallocfree

你自己的malloc可能想要使用真實的malloc函數分配內存,所以這裏有一個可能的遞歸問題。要解決此問題,dlsym函數可以使用RTLD_NEXT參數來獲取指向下一個(即「真實」)函數的指針。

一個非常小的這個測試可能看起來如下:

#define _GNU_SOURCE 
#include <dlfcn.h> 
#include <stdio.h> 

void *malloc(size_t size) 
{ 
    static void *(*real_malloc)(size_t size) = 0; 

    if (!real_malloc) 
     real_malloc = dlsym(RTLD_NEXT, "malloc"); 

    void *result = real_malloc(size); 
    fprintf(stderr, "malloc(%d) = %p\n", (int)size, result); 
    return result; 
} 

void free(void *ptr) 
{ 
    static void (*real_free)(void *ptr) = 0; 
    if (!real_free) 
     real_free = dlsym(RTLD_NEXT, "free"); 

    real_free(ptr); 
    fprintf(stderr, "free(%p)\n", ptr); 
} 

如果我們把這個文件fakemalloc.c,它可以被編譯成一個fakemalloc.so共享對象與命令

gcc -fPIC -shared -Wl,-soname,fakemalloc.so -o fakemalloc.so fakemalloc.c -ldl 

由於一個測試,看看哪個mallocfree調用發生在ls命令的調用中,您需要執行

LD_PRELOAD=/path/to/fakemalloc.so ls 

編輯:正如在評論中提到,在glibc的系統,你可以通過使用功能__libc_malloc__libc_free避免RTLD_NEXT方法。這將產生以下代碼:

+0

非常感謝你! 'LD_PRELOAD'是所有需要的,構建步驟也很有用。 'DYLD_INSERT_LIBRARIES'可能在OS X中是等效的。 –

+2

在基於glibc的系統上,您還可以通過在您的替換malloc例程中調用'__libc_malloc'來調用系統malloc(不需要'RTLD_NEXT'技巧) –

+0

可能會打印消息是一個可能未定義的行爲,如調用free()並刷新結果(如果它不在換行符中)(當stderr是真實文件時)? – 12431234123412341234123

相關問題