How to check what shared libraries are loaded at run time for a given process?
C++CLinuxShared LibrariesC++ Problem Overview
Is there a way to check which libraries is a running process using?
To be more specific, if a program loads some shared libraries using dlopen, then readelf or ldd is not going to show it. Is it possible at all to get that information from a running process? If yes, how?
C++ Solutions
Solution 1 - C++
Other people are on the right track. Here are a couple ways.
cat /proc/NNNN/maps | awk '{print $6}' | grep '\.so' | sort | uniq
Or, with strace:
strace CMD.... 2>&1 | grep -E '^open(at)?\(.*\.so'
Both of these assume that shared libraries have ".so" somewhere in their paths, but you can modify that. The first one gives fairly pretty output as just a list of libraries, one per line. The second one will keep on listing libraries as they are opened, so that's nice.
And of course lsof
...
lsof -p NNNN | awk '{print $9}' | grep '\.so'
Solution 2 - C++
May be lsof
- the swiss army knife of linux will help?
edit: to run, lsof -p <pid>
, lists all sorts of useful information, for example, if the process is java, lists all the open jars - very cool...
Solution 3 - C++
Actually, you can do this in your code in the following way:
#include <link.h>
using UnknownStruct = struct unknown_struct {
void* pointers[3];
struct unknown_struct* ptr;
};
using LinkMap = struct link_map;
auto* handle = dlopen(NULL, RTLD_NOW);
auto* p = reinterpret_cast<UnknownStruct*>(handle)->ptr;
auto* map = reinterpret_cast<LinkMap*>(p->ptr);
while (map) {
std::cout << map->l_name << std::endl;
// do something with |map| like with handle, returned by |dlopen()|.
map = map->l_next;
}
The link_map
structure contains at least the base address and the absolute file name. It's the structure that is actually returned by dlopen()
with non-NULL first argument. For more details see here.
Solution 4 - C++
ltrace
seems to be your friend.
From ltrace
manual:
> ltrace is a program that simply
> runs the specified command until it
> exits. It intercepts and records the dynamic library calls
> which are
> called by the executed process and the signals which are
> received by
> that process. It can also intercept and print the system calls
> exe‐
> cuted by the program.
>
> Its use is very similar to strace(1).
Solution 5 - C++
On Linux, /proc/<processid>/maps
contains a list of all the files mapped into memory, which I believe should include any loaded by dlopen()
.
Solution 6 - C++
On solaris there is also the pldd command.
Solution 7 - C++
You can do so programmatically on Linux. You can use the function dl_iterate_phdr
.
Here is a small example taken from the man page :
#define _GNU_SOURCE
#include <link.h>
#include <stdlib.h>
#include <stdio.h>
static int
callback(struct dl_phdr_info *info, size_t size, void *data)
{
int j;
printf("name=%s (%d segments)\n", info->dlpi_name,
info->dlpi_phnum);
for (j = 0; j < info->dlpi_phnum; j++)
printf("\t\t header %2d: address=%10p\n", j,
(void *) (info->dlpi_addr + info->dlpi_phdr[j].p_vaddr));
return 0;
}
int
main(int argc, char *argv[])
{
dl_iterate_phdr(callback, NULL);
exit(EXIT_SUCCESS);
}
Solution 8 - C++
Would strace
trace the library file being opened?