Search code examples
androidandroid-ndkdlopen

How to substitute dlopen() in Android Nougat?


I have an NDK app which can be extended via plugins which are loaded via dlopen. This used to work fine but it no longer works with Android N. As stated in the developer documentation, dlopen is now officially abandoned:

Starting in Android 7.0, the system prevents apps from dynamically linking against non-NDK libraries, which may cause your app to crash. This change in behavior aims to create a consistent app experience across platform updates and different devices.
...
All apps generate a runtime error when they call an API that is neither public nor temporarily accessible. The result is that System.loadLibrary and dlopen(3) both return NULL, and may cause your app to crash.

I have seen that there is a hack that simply manually implements dlopen and dlsym for Android. This seems to work for Android N but of course nobody can tell how long this is still going to work.

That's why I am thinking about changing my plugin design into something that is officially supported and is future-proof. The most obvious choice would be the use Android's Service API and simply distribute my plugins as separate APKs that implement a Service.

However, I don't really like that idea since I'm using the NDK and I don't think that the Service API is available for the NDK. Of course, I could create a Service in Java and then use JNI to integrate it with my C code but this is of course not a very elegant solution.

That's why I'd like to ask what's the recommended way to support plugins which were previously dlopen-based in Android N? Is there an alternative route or am I forced to use the Service API now?


Solution

  • For the record; this was discussed in the android-ndk google group/mailing list, and it turned out that dlopen wasn't the culprit for the original poster at all:

    https://groups.google.com/d/msg/android-ndk/hhUv1mg3c_A/a5BbRtr-AwAJ

    Oops, sorry, actually, dlopen() is still working fine on Android 7.0. I was getting the following error message:

    Detected problems with app native libraries (please consult log for detail): 
    foobar.so: text relocations 
    

    The wording in the developer documentation was clarified further:

    https://groups.google.com/d/msg/android-ndk/hhUv1mg3c_A/eIKHZZcDBAAJ

    I guess the wording does technically make it sound like you're now [sic: read not] allowed to link to your own libraries. That definitely is not the case. The policy is that your cannot link to or dlopen private system libraries (anything in /system/lib that is not in the NDK).