Android N:unsatisfiedlinkerror can only access so libraries that are set up as public libraries

Source: Internet
Author: User

Java.lang.UnsatisfiedLinkError occurs when using. So as the third-party library of APK on Android N:

09-27 12:17:01.280 D/listensoundmodel (3635): Load libxxxjni
09-27 12:17:01.292 D/androidruntime (3635): Shutting down VM
——— beginning of crash
09-27 12:17:01.293 E/androidruntime (3635): FATAL exception:main
09-27 12:17:01.293 E/androidruntime (3635): Process:com.qualcomm.xxx, pid:3635
09-27 12:17:01.293 E/androidruntime (3635): java.lang.unsatisfiedlinkerror:dalvik.system.pathclassloader[ Dexpathlist[[zip file "/data/app/xxxapp.apk"],nativelibrarydirectories=[/data/app-lib/xxxapp,/system/lib64,/ VENDOR/LIB64]] couldn ' t find "libxxxjni.so"
09-27 12:17:01.293 E/androidruntime (3635): at Java.lang.Runtime.loadLibrary0 (runtime.java:972)
09-27 12:17:01.293 E/androidruntime (3635): at Java.lang.System.loadLibrary (system.java:1530)
...
09-27 12:17:01.293 E/androidruntime (3635): at Android.os.Handler.dispatchMessage (handler.java:102)
09-27 12:17:01.293 E/androidruntime (3635): at Android.os.Looper.loop (looper.java:154)

This is described in Google's change note https://developer.android.com/preview/behavior-changes.html#ndk,

What is the specific reason, how to solve this problem, Google has given an official solution (such as the link), here also gives another method.

First, the main reason is that Google has restricted the loading of. So libraries on N, limiting the so library to loading from a partially specified path, not the so hint in this path
Java.lang.UnsatisfiedLinkError:dlopen failed:library "xxx.so" not found or
Java.lang.UnsatisfiedLinkError:dlopen failed:library "/vendor/lib64/xxx.so" needed or dlopened by "/system/lib64/ Libnativeloader.so "isn't accessible for the namespace" Classloader-namespace "or other exception error prompt.

The search path for so library loading on n is ld_library_path, runtime path, permit path, which fails to load under this search path.

From the code level, it is mainly related to the class loader ClassLoader,
Code1: (Loadedapk.java getclassloader ()) Check SDK version
Do not ship:this are a workaround for apps loading native libraries
Provided by 3rd party apps using absolute path instead of corresponding
ClassLoader See http://b/26954419 for example.
if (mapplicationinfo.targetsdkversion <= 23) {
Librarypermittedpath + = File.pathseparator + "/data/app";
}

Code2: (Loadedapk.java getclassloader ()) N add a new Permittedpath
String Librarypermittedpath = Mdatadir;

Code3: (native_loader.cpp) Use the new namespace rule with search Path:ld_library_path, runtime path, permit path.

After understanding the reason,
The solution is to add your own so to the whitelist of allowed paths, specifically, if you do not change the code to implement, then export the device's/vendor/etc/public.libraries.txt or/etc/ Public.libraries.txt file, add so name, on push to device, reboot.

/////////////////////////////////////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////

/////////////////////////////////////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////

Android N version has a new feature, that is, ordinary applications can not directly reference the system of some so libraries, can only directly reference the Public.libraries.txt file filter so library. This site has a description of how to deal with.
Source.android.com/devices/tec ...
The situation is this: I have a system permissions apk, this apk will compile some so library under the System/lib directory, just brush machine This apk can be referenced to these so libraries, but I debug the time directly install this apk, run the time incredibly directly hanging!! I'm drunk, too. I didn't expect this new feature to actually affect my system permissions apk. Real egg hurts, I do not want to push this apk and then reboot to take effect, generally I am directly install, but now the good days seem to end.

First, look at the error message.

The information of the specific error is as follows:

01-0102:17:24.22274757475 E Linker:library"/system/lib64/libhaha_utils.so" ("/system/lib64/libhaha_utils.so") neededor dlopenedBy"/system/lib64/libnativeloader.so"IsNot accessibleForThe namespace: [Name="Classloader-namespace", ld_library_paths="", default_library_paths= "/system/fake-libs64:/data/app/com.example.haha-1/base.apk!/lib/arm64-v8a", permitted _paths= "/data:/mnt/expand:/data/data/com.example.haha"]01< Span class= "Hljs-number" >-01 02: 17: 24.223 7475 7475 E System: Java.lang.UnsatisfiedLinkError:dlopen failed:library  "/system/lib64/libhaha_utils.so" Needed or dlopened by /system/ Lib64/libnativeloader.so "is not accessible for the namespace " Classloader-namespace "  

Probably means that the application Nativeloader can not open libhaha_utils.so this so library, it collapsed!! So cruel. Libhaha_utils.so This library was compiled with ANDROID.MK and placed under system/lib64. But I can't open it now.
Why is it?
Because/SYSTEM/LIB64/does not have a legitimate path to the APK to find the so library Ah, what is the legal path?
There's a description on the log above. The following three paths did not find the libhaha_utils.so library, so it hung up.
Ld_library_paths= "",
Default_library_paths= "/system/fake-libs64:/data/app/com.example.haha-1/base.apk!/lib/arm64-v8a", Permitted_ Paths= "/data:/mnt/expand:/data/data/com.example.haha

Two. Then why is the apk available after the flash, install this apk can not use it?

This apk is a system authority yo, is the apk list androidmanifest in the following sentence
Android:shareduserid= "Android.uid.system"

Normally, this high-end apk permitted_paths is included system/lib64, from the source can know
/frameworks/base/core/java/android/app/loadedapk.java

1 //if it is a system apk and has not been upgraded2Final Boolean Isbundledapp =Mapplicationinfo.issystemapp ()3&&!Mapplicationinfo.isupdatedsystemapp ();4 5String Librarypermittedpath =Mdatadir;6         if(Isbundledapp) {//permitted_paths increases system/lib64 .7             //necessary to grant bundled apps access to8             //libraries located in subdirectories Of/system/lib9Librarypermittedpath + = File.pathseparator +TenSystem.getproperty ("Java.library.path"); One}

Look at the comments above to know, if it is the system apk and has not been upgraded, so library search path will add a system/lib64. I go, Google what to do, why also limit can not upgrade.
Because install-r to install APK is equivalent to upgrade, so the APK can be used when the Flash, install upgrade can not be used.

Three. How do you solve this problem?

I am purely for debugging convenience, so refer to Google's links
Source.android.com/devices/tec ...


Google.png


The application can call all the so libraries in/vendor/etc/public.libraries.txt and/system/etc/public.libraries.txt, so the brother writes to this file Libhaha_ utils.so, this library becomes common, any application can find this so library, and finally can happily use the install APK way to debug!! No more reboots!!
Here's a map of native Google


Paste_image.png


There is probably such a thousand so that the library is shared.
Libandroid.so
Libc.so
Libdl.so
Libegl.so
Libglesv1_cm.so
......
You can look at the original commit changes.
android-review.googlesource.com/#/c/209029/

Four. Look at the source code this public.libraries.txt file is played

This TXT file is used in this source code.
/system/core/libnativeloader/native_loader.cpp
In the Librarynamespaces class initialize () will read this file, the so library is set to public so library, so-called public so library, it is this so library who can use.

1 StaticconstexprConst Char* Kpublicnativelibrariessystemconfigpathfromroot ="/etc/public.libraries.txt";2 StaticconstexprConst Char* Kpublicnativelibrariesvendorconfig ="/vendor/etc/public.libraries.txt";3   voidInitialize () {4     ..................5STD::VECTOR&LT;STD::string>Sonames;6Readconfig (Public_native_libraries_system_config, &sonames, &error_msg),7Readconfig (Kpublicnativelibrariesvendorconfig, &sonames);8Public_libraries_ =Base:: Join (Sonames,':');9     .............Ten}

When was this method called? Probably over the next process Luo.
First, when creating a virtual machine, initialize the Nativeloader, this nativeloader, as the name implies, is used to load so library.
/art/runtime/java_vm_ext.cc

1 extern "C"Jint JNI_CREATEJAVAVM (javavm** p_vm, jnienv** p_env,void*Vm_args) {2   ................3   //Initialize native Loader. This step makes sure we have4   //everything set up before we start using JNI.5 Android::initializenativeloader ();6   ..............7}

Then go to Native_loader and initialize
/system/core/libnativeloader/native_loader.cpp

1 Static New librarynamespaces; 2 3 void Initializenativeloader () {4   g_namespaces->Initialize (); 5 }

Initialization is to call the Librarynamespaces class initialize to complete the assignment of the public so library, hahaha, done!!

1 voidInitialize () {2     ..................3STD::VECTOR&LT;STD::string>Sonames;4Readconfig (Public_native_libraries_system_config, &sonames, &error_msg),5Readconfig (Kpublicnativelibrariesvendorconfig, &sonames);6Public_libraries_ =Base:: Join (Sonames,':');7     .............8}

Summarize:
1.Android N can not directly call some of the system's private libraries, the common library is defined in Public.libraries.txt.
2. The system application just brush machine is able to call the library under SYSTEM/LIB64, but when the app is upgraded by install, the app opens to hang. Because the permitted_paths will no longer contain system/lib64 after the upgrade. So we can write the name of the library that the APK will use to Public.libraries.txt to solve the problem of quick debugging.

Android N:unsatisfiedlinkerror can only access so libraries that are set up as public libraries

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.