I am trying to build a program in C which has a lot of optional features that depend on various shared libraries.
In our heterogeneous computing cluster not all of those libraries are available (or up to date) on all systems.
Examples are symbols from newer glibc (sched_getcpu@@GLIBC_2.6
, __sched_cpucount@@GLIBC_2.6
) or whole shared libraries which may or may not be available (libnuma
, libR
, libpbs
).
I know that I can use libdl
to load the symbols with dlopen
and dlsym
, but doing this for an ever growing number of symbols (around 30 at the moment) is tedious at best.
As far as I understand shared libraries in Linux are lazy-loaded by default, so a symbol should not be needed until it is actually used.
But if I try to check for that in advance then it fails at execution start:
#define _GNU_SOURCE
#include <stdlib.h>
#include <stdio.h>
#include <stdint.h>
#include <dlfcn.h>
#include <sched.h>
int main() {
void *lib_handle;
int (*fn)(void);
int x;
char *error;
lib_handle = dlopen("libc.so.6", RTLD_LAZY);
if (!lib_handle)
{
fprintf(stderr, "%s\n", dlerror());
exit(1);
}
fn = dlsym(lib_handle, "sched_getcpu");
if ((error = dlerror()) != NULL)
{
fprintf(stderr, "%s\n", error);
exit(1);
}
printf("%d\n", sched_getcpu());
return 0;
}
On compile system which has all libraries:
$ icc test.c
$ ./a.out
10
On another system which has a less recent version of GLIBC:
$ ./a.out
./a.out: /lib64/libc.so.6: version `GLIBC_2.6' not found (required by ./a.out)
If I comment out the line that actually calls sched_getcpu
then I get instead on the lesser system:
$ ./a.out
/lib64/libc.so.6: undefined symbol: sched_getcpu
So, is there a way to force libraries only to be loaded on use and have checks like these before blocks that use them?
The C runtime library is a collection of subroutines that are needed to build a program in C. The subroutines can basically be put into 2 categories: C standard library. Compiler-specific auxiliary functions.
A library function is accessed by simply writing the function name, followed by a list of arguments, which represent the information being passed to the function. The arguments must be enclosed in parentheses, and separated by commas: they can be constants, variables, or more complex expressions.
Open Source, Embedded Linux, and Android The compiler support library is called libgcc and is provided by the compiler itself to supply low-level compiler support routines such as software floating-point emulation and support for exception-handling. This library is used by virtually all programs compiled with GCC.
C Standard library functions or simply C Library functions are inbuilt functions in C programming. The prototype and data definitions of these functions are present in their respective header files. To use these functions we need to include the header file in our program.
Not with glibc. This is a fail-safe and it's in place so that you won't shoot yourself in the foot. If the GLIBC_2.6
symbol wasn't defined and looked up, even if there were no other missing symbols, you could get garbage results from glibc (data corruption and crashes,) since it's not forwards compatible.
If you need compatibility on the glibc level, you need to build against the lowest common version.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With