Thread: Linked Lists

  1. #16
    Registered User MutantJohn's Avatar
    Join Date
    Feb 2013
    Posts
    2,665
    I'm glad you're helping me with this. Apparently, my command doesn't work.

    I've typed "LD_PRELOAD=/usr/lib/libhoard.so" which is where the shared object is located.

    I have libc.so.6 loaded.

    What am I doing wrong?

    Edit: I've found typing "export LD_PRELOAD=/usr/lib/libhoard.so" helps but now I have both libraries loaded and the first program you gave me says it's still pulling malloc from libc.so.6 even though libhoard.so is loaded too.

    Edit edit: Ha ha ha, I figured it out. First, I think all I have to really type is LD_PRELOAD=libhoard.so

    With this, the output of ldd /bin/ls looks like this:
    Code:
    	linux-vdso.so.1 (0x00007fff6d9fe000)
    	libhoard.so => /usr/lib/libhoard.so (0x00007f7368cdf000)
    	libcap.so.2 => /usr/lib/libcap.so.2 (0x00007f7368adb000)
    	libacl.so.1 => /usr/lib/libacl.so.1 (0x00007f73688d2000)
    	libc.so.6 => /usr/lib/libc.so.6 (0x00007f7368525000)
    	libdl.so.2 => /usr/lib/libdl.so.2 (0x00007f7368321000)
    	libpthread.so.0 => /usr/lib/libpthread.so.0 (0x00007f7368105000)
    	libstdc++.so.6 => /usr/lib/libstdc++.so.6 (0x00007f7367e01000)
    	libm.so.6 => /usr/lib/libm.so.6 (0x00007f7367b03000)
    	libgcc_s.so.1 => /usr/lib/libgcc_s.so.1 (0x00007f73678ed000)
    	/lib64/ld-linux-x86-64.so.2 (0x00007f7368f16000)
    	libattr.so.1 => /usr/lib/libattr.so.1 (0x00007f73676e8000)
    And Nominal, modifying your code because it didn't seem like it was doing what I wanted it to so I used:
    Code:
            libhoard_handle = dlopen(LIBHOARD_NAME, RTLD_NOW | RTLD_NOLOAD | RTLD_GLOBAL);
            if (libhoard_handle) {
                
                current_malloc = dlsym(RTLD_DEFAULT, "malloc");
                libhoard_malloc = dlsym(libhoard_handle, "malloc");
                if (current_malloc == libhoard_malloc) {
     
                    fprintf(stderr, "malloc() is from Hoard library (%s)\n", LIBHOARD_NAME);
     
                } else {
     
                    fprintf(stderr, "malloc() is from an unknown library.\n");
                }
     
                dlclose(libhoard_handle);
     
            } else {
     
                fprintf(stderr, "%s: Hoard library not loaded.\n", LIBHOARD_NAME);
     
            }
    And got the following output:
    Code:
    malloc() is from Hoard library (libhoard.so)
    I knew it couldn't really be that simple! Or did I do this wrong?
    Last edited by MutantJohn; 07-01-2013 at 03:59 PM.

  2. #17
    Ticked and off
    Join Date
    Oct 2011
    Location
    La-la land
    Posts
    1,728
    Quote Originally Posted by MutantJohn View Post
    I've found typing "export LD_PRELOAD=/usr/lib/libhoard.so" helps but now I have both libraries loaded and the first program you gave me says it's still pulling malloc from libc.so.6 even though libhoard.so is loaded too.
    I downloaded the Hoard sources, and took a peek.

    On Linux (make linux-gcc-x86-64), it does not replace malloc(), it hooks into its internals. Thus, the malloc() function stays the same, Hoard just modifies its behaviour. (The LD_PRELOAD facility is such that you can easily replace any C library function with your own version. Let me know if you want an example, it's real easy.)

    The GNU C library malloc() has these __malloc_initialize_hook(), __malloc_hook(), __realloc_hook(), __free_hook(), etc. function pointers that allow your own program -- without even having to write a library -- to modify the behaviour or the memory allocator. (They are deprecated, so this approach will stop working some day in the future, and you will get deprecation warnings if compiling with new enough GNU tools.)

    In your case, there is good news.

    It is even easier to detect whether you are using the "normal" GNU C malloc(), or a modified one: check if __malloc_initialize_hook is non-NULL:
    Code:
    #include <stdio.h>
    #include <malloc.h>
    
    int main(void)
    {
        if ((void *)__malloc_initialize_hook)
            printf("Using modified malloc()\n");
        else
            printf("Using regular malloc()\n");
        return 0;
    }
    You do not need to add any specific libraries, the <malloc.h> header file is enough (to declare the __malloc_initialize_hook variable).

  3. #18
    Registered User MutantJohn's Avatar
    Join Date
    Feb 2013
    Posts
    2,665
    Sorry to have highjacked the topic but thank you, Nominal. It seems like everything is working as it should now :silh:

  4. #19
    Ticked and off
    Join Date
    Oct 2011
    Location
    La-la land
    Posts
    1,728
    Quote Originally Posted by MutantJohn View Post
    Edit edit: Ha ha ha, I figured it out. First, I think all I have to really type is LD_PRELOAD=libhoard.so
    If you have the library in one of the system library directories, then the library name is enough. Otherwise you have to type the full path.

    Here is an example "do-nothing" malloc-interposing library, libmymalloc.c:
    Code:
    #define  _GNU_SOURCE
    #include <stdlib.h>
    #include <stdio.h>
    #include <dlfcn.h>
    
    static void *(*original_malloc)(size_t size) = NULL;
    static int notified = 0;
    
    void *malloc(size_t size)
    {
        if (!notified) {
            notified = 1;
            fflush(stdout);
            fprintf(stderr, "Using custom malloc().\n");
            fflush(stderr);
        }
    
        if (!original_malloc)
            *((void **)&original_malloc) = dlsym(RTLD_NEXT, "malloc");
    
        return original_malloc(size);
    }
    
    static void libmymalloc_init(void) __attribute__((constructor));
    static void libmymalloc_init(void)
    {
        fflush(stdout);
        fprintf(stderr, "libmymalloc loaded.\n");
        fflush(stderr);
    }
    It just prints "libmymalloc loaded." before a program starts main(), and "Using custom malloc()" when malloc() is called for the first time.
    To compile libmymalloc.c into a libmymalloc.so library, use
    Code:
    gcc -W -Wall -O3 -shared -Wl,-soname,libmymalloc.so libmymalloc.o -ldl -o libmymalloc.so
    gcc -W -Wall -O3 -fpic -fPIC -c libmymalloc.c
    If you compare this and the hoard library, you see that hoard does not interpose malloc(), it just hooks into the malloc() internals.

    Here is another helper program that you might find useful. It is very simple: give it one or more symbol names as command-line parameters, and it tells you where they are from, if they are available in the loaded libraries. I call this symbol.c:
    Code:
    #define  _GNU_SOURCE
    #include <stdio.h>
    #include <string.h>
    #include <dlfcn.h>
    
    int main(int argc, char *argv[])
    {
        Dl_info info;
        void   *sym;
        int     arg;
    
        if (argc < 2 || !strcmp("-h", argv[1]) || !strcmp("--help", argv[1])) {
            fprintf(stderr, "\n");
            fprintf(stderr, "Usage: %s [ -h | --help ]\n", argv[0]);
            fprintf(stderr, "       %s SYMBOL-NAME ...\n", argv[0]);
            fprintf(stderr, "\n");
            return 1;
        }
    
        for (arg = 1; arg < argc; arg++) {
            sym = dlsym(RTLD_DEFAULT, argv[arg]);
            if (sym) {
                printf("%s: Found (%p)\n", argv[arg], sym);
                dladdr(sym, &info);
                if (info.dli_sname && info.dli_fname)
                    printf("\t%s from %s\n", info.dli_sname, info.dli_fname);
            } else
                printf("%s: Not found.\n", argv[arg]);
        }
    
        return 0;
    }
    Compile it using e.g.
    Code:
    gcc -W -Wall -O3 symbol.c -ldl -o symbol
    Now, if you have all binaries in the same directory, then you should get something like
    Code:
    ./symbol malloc
    malloc: Found (0x7fcbe88cdf50)
            __libc_malloc from /lib/x86_64-linux-gnu/libc.so.6
    
    env LD_PRELOAD=./libhoard.so ./symbol malloc
    malloc: Found (0x7fcbe88cdf50)
            __libc_malloc from /lib/x86_64-linux-gnu/libc.so.6
    
    env LD_PRELOAD=./libmymalloc.so ./symbol malloc
    malloc: Found (0x7f8517267740)
            malloc from ./libmymalloc.so
    Finally, for detecting Hoard, you can use the following simple program. It does not need any special libraries (no need to use -ldl, for example, when linking).
    Code:
    #define  _GNU_SOURCE
    #include <stdio.h>
    #include <string.h>
    #include <malloc.h>
    
    int using_hoard_malloc(void)
    {
        char   buffer[1024], *line;
        FILE  *maps;
    
        /* Hoard uses malloc hooks. */
        if (!__malloc_initialize_hook)
            return 0;
    
        /* Read memory maps to see if libhoard.so is loaded. */
        maps = fopen("/proc/self/maps", "rb");
        if (!maps)
            return 0;
    
        /* If we see /libhoard.so, it's likely enough it is loaded. */
        while ((line = fgets(buffer, sizeof buffer, maps)))
            if (strstr(line, "/libhoard.so")) {
                fclose(maps);
                return 1;
            }
    
        /* Nope. */
        fclose(maps);
        return 0;
    }
    
    int main(void)
    {
        if (using_hoard_malloc())
            printf("This program is using libhoard malloc().\n");
        else
            printf("This program is not using libhoard malloc().\n");
        return 0;
    }
    Instead of using the dynamic linker, this one checks if malloc() is hooked. If not, hoard is not in use because it always hooks malloc().

    If malloc() is hooked, this uses the Linux /proc/self/maps pseudofile, which contains the memory maps the current process is using. It includes libraries, too. If the listing includes the string /libhoard.so (the paths are absolute in the pseudofile), then the function is satisfied that Hoard is in use. It's not perfect, but it should be robust enough for casual use.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Double Linked Dynamic Lists Vs Unrolled Linked Lists
    By lantzvillian in forum C Programming
    Replies: 6
    Last Post: 02-14-2012, 01:07 PM
  2. Replies: 4
    Last Post: 05-01-2010, 10:19 PM
  3. Question about Linked lists of lists
    By hear_no_evil in forum C Programming
    Replies: 2
    Last Post: 11-08-2004, 02:49 AM
  4. question on linked lists(stack with linked lists)
    By dionys in forum C Programming
    Replies: 1
    Last Post: 06-02-2004, 11:08 AM
  5. Linked List of Linked lists Revisited.
    By Qui in forum C++ Programming
    Replies: 11
    Last Post: 04-11-2004, 09:45 PM

Tags for this Thread