I am working on a project that requires wrapping libc calls particularly file i/o calls like open, read, write, close etc. I have created a shared library (say, wrapper.so) and preload this wrapper.so. I could successful use this wrapper on Linux by setting the LD_PRELOAD variable. On MAC, I tried setting the DYLD_FORCE_FLAT_NAMESPACE to 1, DYLD_INSERT_LIBRARIES to /path/wrapper.so using 1) .bash_profile, 2)launchctl setenv, 3)LaunchAgent, 4)LaunchDeamon approaches but nothing work.
I tried even setting the DYLD_FORCE_FLAT_NAMESPACE, DYLD_INSERT_LIBRARIES environment variables at application level for specific applications via their Info.plist but this didn't work either.
Note: I could set some random new variable, say MYVAR, with all the above mentioned approaches. So, it is while setting the DYLD_* variables that I have problem setting. Can you please help me set the DYLD_FORCE_FLAT_NAMESPACE, DYLD_INSERT_LIBRARIES variables on MAC.
A shared library (.dylib) on OS X 'knows' where it expects to be installed to and this information is in turn embedded in any executable that links against it so that the executable knows where to find the library at runtime. Weird though it sounds, that's how it works. Apple call it the dylib's 'install name'.
You can see the install name of a dylib by using
otool
. For example:If there is only one consumer of your dylib then it's probably easiest to tell the dylib to use a relative path, rather than an absolute path, as its install name. You can do this when building the library like so:
Then just put the dylib in the same directory as your executable and it should be able to find it. This also works with clang. You can also set the dylib's install name with a utility called
install_name_tool
, but that's a bit more difficult.Here are some links you might find useful:
Apple's documentation
https://blogs.oracle.com/dipol/dynamic-libraries,-rpath,-and-mac-os http://log.zyxar.com/blog/2012/03/10/install-name-on-os-x/