Search code examples
androidbluetoothandroid-ndkruntime-error

Unable to load native library which is present in the app


I am building a native application with Android NDK. It has a dependency on various shared objects (.so). I have added them to the application in CMakeLists as below:

add_library(bluetooth SHARED IMPORTED)
/home/stoic/fluoride/bt/output_dir/out/Default/lib/libbluetooth.so)
set_target_properties(bluetooth PROPERTIES IMPORTED_LOCATION /home/stoic/lib-bluetooth-x86-64/libbluetooth.so)
add_library(chrome SHARED IMPORTED)
set_target_properties(chrome PROPERTIES IMPORTED_LOCATION /home/stoic/lib-bluetooth-x86-64/libchrome.so)
add_library(grpc++ SHARED IMPORTED)
set_target_properties(grpc++ PROPERTIES IMPORTED_LOCATION /home/stoic/lib-bluetooth-x86-64/libgrpc++.so)
add_library(grpc_wrap SHARED IMPORTED)
set_target_properties(grpc_wrap PROPERTIES IMPORTED_LOCATION /home/stoic/lib-bluetooth-x86-64/libgrpc_wrap.so)


target_link_libraries(native-activity
    android
    native_app_glue
    EGL
    GLESv1_CM
    log
        bluetooth
        chrome
        grpc++
        grpc_wrap
        /home/stoic/lib-bluetooth-x86-64/libstatslog.so
        /home/stoic/lib-bluetooth-x86-64/android.hardware.bluetooth.a2dp@1.0.so
)

I am not writing the entire CMakeLists.txt because the application compiles fine and apk is built successfully.

All the .sos loads fine but Android runtime gives this error for android.hardware.bluetooth.a2dp@1.0.so:

E/AndroidRuntime: FATAL EXCEPTION: main
    Process: com.example.native_activity, PID: 4230
    java.lang.UnsatisfiedLinkError: Unable to load native library "/data/app/~~J6dVW4LGncsbvMxzwtgq7w==/com.example.native_activity-Je33LNoodZDV37TTvXSpEw==/lib/x86_64/libnative-activity.so": dlopen failed: library "android.hardware.bluetooth.a2dp@1.0.so" not found: needed by /data/app/~~J6dVW4LGncsbvMxzwtgq7w==/com.example.native_activity-Je33LNoodZDV37TTvXSpEw==/lib/x86_64/libnative-activity.so in namespace classloader-namespace

I have checked in the unpacked apk of the built application and I see the android.hardware.bluetooth.a2dp@1.0.so present in lib/x86_64 directory along with other .sos.

ls lib/x86_64/
android.hardware.bluetooth.a2dp@1.0.so  libbluetooth.so  libchrome.so  libgrpc++.so  libgrpc_wrap.so  libnative-activity.so  libstatslog.so

Does anyone have any idea what's wrong with what I am doing?


Solution

  • I was able to solve the issue with answer pointed by @Michael in the comments. Another thing I found out was Android doesn't support the character @ as well in the name of libraries, so I had to replace that with _ as well. There is no documentation from Android about this, I found that from trial and error.

    I used sed instead of rpl used in the original answer.

    sed -i "s/@\([0-9]\).\([0-9]\).so/_\1_\2.so/g" libbluetooth.so
    

    I did the same thing for all the libraries used in my app. To solve the issue with all the libraries - I copied all the libraries in one directory and used this script:

    echo "" > change.log
    for var in `ls -1`;do
        echo $var
        sed -i "s/@\([0-9]\).\([0-9]\).so/_\1_\2.so/g" $var
        new_file=`echo $var|sed "s/@\([0-9]\).\([0-9]\).so$/_\1_\2.so/g"`
        mv $var $new_file
        objdump -p $new_file | grep so >> change.log
    done