1

How do I figure out the path of a shared library that my program is using at run time?

I have glibc 2.12 as the primary glibc running on my CentOS 6.10 system, and have also installed glibc 2.14 in /opt/glibc-2.14.

When I inspect my executable file with

$ objdump -p ./myProgram

it gives this info

Dynamic Section:
NEEDED               libpthread.so.0
NEEDED               libcurl.so.4
NEEDED               libc.so.6

and my LD_LIBRARY_PATH has this value /opt/glibc-2.14/lib.

Is there away to see which libc.so.6 library (perhaps with the path to the library file) my program is actually using while it is running?

Accountant م
  • 6,975
  • 3
  • 41
  • 61
  • 3
    *"how to know the shared library that my program is actually using now at run time..."* - Lol... You don't (give or take). Compiling and linking against one library, and then loading the the wrong library at runtime, has plagued Linux for the last 20 or 30 years. Stack Overflow and other sites are full of the carnage. Other OSes, including AIX, BSDs, OS X, Solaris and even Windows solved it. Linux is the only major OS that has not managed to solve it. Instead, Linux continues to let users suffer the fallout. The dunces who made the decisions should get a Darwin award... – jww Apr 20 '19 at 00:51
  • The `ld` tag is not needed, this question isn't about the linker itself. And there's no reason to have the "actually" in there because a correct answer would have to show the "actual" library that the program is using. – S.S. Anne Apr 20 '19 at 15:44
  • @Accountantم Why are you rejecting my edits? – S.S. Anne Apr 20 '19 at 21:37
  • @JL2210 I approved the one that improved the post, but keep suggesting to remove the `ld` 4 times is a strange behavior ! my rejection has included the reason. – Accountant م Apr 20 '19 at 21:47
  • Your rejection comments about "adding" tags. I'm trying to remove one that doesn't add any benefit to the question. Along with that, see my comment about not needing "actually" because a correct answer would show the library that's "actually" used. If you give me a reason to believe that the `ld` tag belongs here, then I'll leave your question alone. – S.S. Anne Apr 20 '19 at 21:52

1 Answers1

4

On Linux: One possible approach is to look into the corresponding entry in the /proc/ filesystem. For example for a program with PID X you can find info in /proc/X/maps similar to:

...
7f34a73d6000-7f34a73f8000 r--p 00000000 08:03 18371015                   /nix/store/681354n3k44r8z90m35hm8945vsp95h1-glibc-2.27/lib/libc-2.27.so
7f34a73f8000-7f34a7535000 r-xp 00022000 08:03 18371015                   /nix/store/681354n3k44r8z90m35hm8945vsp95h1-glibc-2.27/lib/libc-2.27.so
...

It clearly shows where my libc (the one used by this program) is.


Example (missing some error handling!) to show where fopen is coming from:

#include <stdio.h>
#include <sys/types.h>
#include <unistd.h>
#include <string.h>
#include <stdint.h>

#define BSIZE 200

int main(void) {
    char buffer[BSIZE];
    int const pid = getpid();
    snprintf(buffer, BSIZE, "/proc/%d/maps", pid);
    FILE * const maps = fopen(buffer, "r");
    while (fgets(buffer, BSIZE, maps) != NULL) {
        unsigned long from, to;
        int const r = sscanf(buffer, "%lx-%lx", &from, &to);
        if (r != 2) {
            puts("!");
            continue;
        }
        if ((from <= (uintptr_t)&fopen) && ((uintptr_t)&fopen < to)) {
            char const * name = strchr(buffer, '/');
            if (name) {
                printf("%s", name);
            } else {
                puts("?");
            }
        }
    }
    fclose(maps);
}
Daniel Jour
  • 15,896
  • 2
  • 36
  • 63
  • 1
    Daniel Jour is correct: [/proc/PID#/maps](https://linux.die.net/man/5/proc) is probably your best bet. A couple of other useful commands for analyzing shared libraries: (1) [ldd](https://linux.die.net/man/1/ldd) and (2) [lsof](https://linux.die.net/man/8/lsof) – paulsm4 Apr 20 '19 at 00:16
  • You can use `/proc/self/maps` instead of using `getpid`. – S.S. Anne Apr 20 '19 at 03:32