System.Loadlibrary(...) Couldn't Find Native Library in My Case

System.loadLibrary(...) couldn't find native library in my case

To root cause (and maybe solve your issue in the same time), here is what you can do:

  1. Remove the jni folder and all the .mk files. You don't need these nor the NDK if you aren't compiling anything.

  2. Copy your libcalculate.so file inside <project>/libs/(armeabi|armeabi-v7a|x86|...) . When using Android Studio, it's <project>/app/src/main/jniLibs/(armeabi|armeabi-v7a|x86|...), but I see you're using eclipse.

  3. Build your APK and open it as a zip file, to check that your libcalculate.so file is inside lib/(armeabi|armeabi-v7a|x86|...).

  4. Remove and install your application

  5. Run dumpsys package packages | grep yourpackagename to get the nativeLibraryPath or legacyNativeLibraryDir of your application.

  6. Run ls on the nativeLibraryPath you had or on legacyNativeLibraryDir/armeabi, to check if your libcalculate.so is indeed there.

  7. If it's there, check if it hasn't been altered from your original libcalculate.so file: is it compiled against the right architecture, does it contain the expected symbols, are there any missing dependencies. You can analyze libcalculate.so using readelf.

In order to check step 5-7, you can use my application instead of command lines and readelf: Native Libs Monitor

PS: It's easy to get confused on where .so files should be put or generated by default, here is a summary:

  • libs/CPU_ABI inside an eclipse project

  • jniLibs/CPU_ABI inside an Android Studio project

  • jni/CPU_ABI inside an AAR

  • lib/CPU_ABI inside the final APK

  • inside the app's nativeLibraryPath on a <5.0 device, and inside the app's legacyNativeLibraryDir/CPU_ARCH on a >=5.0 device.

Where CPU_ABI is any of: armeabi, armeabi-v7a, arm64-v8a, x86, x86_64, mips, mips64. Depending on which architectures you're targeting and your libs have been compiled for.

Note also that libs aren't mixed between CPU_ABI directories: you need the full set of what you're using, a lib that is inside the armeabi folder will not be installed on a armeabi-v7a device if there are any libs inside the armeabi-v7a folder from the APK.

couldn't find libmynative.so even though its copied to libs folder(Android NDK)

If you are using Android studio, the default jni libraries directory is not libs, you have to specify it under gradle build script explicitly.

sourceSets.main {
jniLibs.srcDir 'src/main/libs'
jni.srcDirs = []
}

Also, after build finish, you can check if the native libraries are built into your apk.

$ unzip -l app-debug.apk |grep mynative

android loadLibrary fails when native method is used

As you see, the cardrecognizer library is built for 32-bit ARM (armeabi-v7a). In the short run, you can build you native library for the same ABI. This is usually controlled by abiFilters in the build.gradle script.

But if you intend to distribute your app on Play Store, you should learn to build the third-party library for arm64, too. Google announced this requirement for August 2019.

Why won't my native library load in my Android App?

I was able to load them using...

System.load("/data/data/com.imtroymiller.myapp/lib/libmylib.so");

It looks like System.load takes the path name and System.loadLibrary takes the library name. But both will load the library.

Nexus7 can't load native library

As Michael wrote, I have to set the right DANDROID_NATIVE_API_LEVEL. To get it running on Android 6.0.1 I have to use API level 23 or below. So the cmake command should look like this:

~/development/sdks/android-sdk/cmake/3.10.2.4988404/bin/cmake \
-DANDROID_NDK=~/development/sdks/android-sdk/ndk/21.0.6113669 \
-DCMAKE_TOOLCHAIN_FILE=~/development/sdks/android-sdk/ndk/21.0.6113669/build/cmake/android.toolchain.cmake \
-DCMAKE_LIBRARY_OUTPUT_DIRECTORY=armeabi-v7a \
-DANDROID_TOOLCHAIN=clang \
-DANDROID_ABI=armeabi-v7a \
-DANDROID_NATIVE_API_LEVEL=19

System.loadLibrary() gives error on loading on a suse machine

You cannot use the NDK to build libraries for use on a normal Linux, for a number of reasons, including that the C libraries and their associated dynamic linker are different and the library naming conventions differ. Typically you would also have a different processor (though the NDK now supports most that might be in your development machine), and perhaps a subtly different ABI even when the processor matches.

You can still accomplish your goal of testing your jni code on the desktop, you will just need to build it with a toolchain targeting your desktop Linux environment (with appropriate settings for jni usage there), then re-build it with the NDK for your android target.



Related Topics



Leave a reply



Submit