I have a program that links against a shared library libfoo
. I want to override one of the functions from libfoo
inside my program, such that internal calls to that function from within libfoo
resolve to the definition in my program. (For context, my intention is to mock out the library function for testing.)
This question is kind of related to this one: symbol lookup in shared libraries. This is the example from that question:
// foo.c
void dispatch_write_hello(void) {
fprintf(stderr, "hello\n");
}
void print_hello(void) {
dispatch_write_hello();
}
// main.c
extern void print_hello(void);
void dispatch_write_hello(void) {
fprintf(stderr, "overridden\n");
}
int main(int argc, char **argv) {
print_hello();
return 0;
}
Here's what it does on linux:
$ clang -shared -fPIC foo.c -o libfoo.so
$ clang main.c -L. -lfoo
$ LD_LIBRARY_PATH=. ./a.out
overridden
This is the behavior I want, but on macOS I get this:
$ clang -dynamiclib -fPIC foo.c -o libfoo.dylib
$ clang main.c -L. -lfoo
$ ./a.out
hello
How can I achieve the behavior of the linux example on macOS? Preferably I'd like one approach that works on both linux and macOS, but I guess it's okay if I need to use macOS-specific build flags and/or environment variables.
I was able to achieve this by adding
-Wl,-flat_namespace
when building the library.(I also tried some other folklore from the internet including
-Wl,-force_flat_namespace
when linking the program, or running the program withDYLD_FORCE_FLAT_NAMESPACE=1
, but neither seemed to work.)