android开发 加载so库的解析和出现的各种错误分析
来源:互联网 发布:九博人才网软件下载 编辑:程序博客网 时间:2024/05/13 05:21
一.android目前有几种cpu架构?
早期的Android系统几乎只支持ARMv5的CPU架构,你知道现在它支持多少种吗?7种!
Android系统目前支持以下七种不同的CPU架构:ARMv5,ARMv7 (从2010年起),x86 (从2011年起),MIPS (从2012年起),ARMv8,MIPS64和x86_64 (从2014年起),每一种都关联着一个相应的ABI。
二.每种cpu架构对应的文件夹名称是什么?
在Android系统上,每一个CPU架构对应一个ABI:armeabi,armeabi-v7a,x86,mips,arm64-v8a,mips64,x86_64也就是说我们要想支持全部系统的手机需要放全所有不同版本的so库。
三.我们需要每种版本的so库都放全吗?
1.看你的so库的来源,是第三方提供的,还是自己开发的。倘若你是集成了某些第三方的sdk,然后他们提供了多少 ,你最好将它提供的都拷贝到项目中。(但是基本很少有能提供全面的so库支持的)
2.倘若是自己开发的 ,那就根据自己的情况,开发出对应版本的so库支持。
四.每种机型就只能加载一种适合自己版本的so库吗?
很多设备都支持多于一种的ABI。例如ARM64和x86设备也可以同时运行armeabi-v7a和armeabi的二进制包。但最好是针对特定平台提供相应平台的二进制包,这种情况下运行时就少了一个模拟层(例如x86设备上模拟arm的虚拟层),从而得到更好的性能(归功于最近的架构更新,例如硬件fpu,更多的寄存器,更好的向量化等)。
五.如何查看当前设备支持那些版本的so库?
我们可以通过Build.SUPPORTED_ABIS得到根据偏好排序的设备支持的ABI列表。但你不应该从你的应用程序中读取它,因为Android包管理器安装APK时,如果在对应的lib/ABI目录中存在.so文件的话,会自动选择APK包中为对应系统ABI预编译好的.so文件。
六.不同的开发环境so库应该放在哪里?
Android Studio工程放在jniLibs/ABI目录中(当然也可以通过在build.gradle文件中的设置jniLibs.srcDir属性自己指定)
Eclipse工程放在libs/ABI目录中(这也是ndk-build命令默认生成.so文件的目录)
AAR压缩包中位于jni/ABI目录中(.so文件会自动包含到引用AAR压缩包的APK中)
最终APK文件中的lib/ABI目录中
通过PackageManager安装后,在小于Android 5.0的系统中,.so文件位于app的nativeLibraryPath目录中;在大于等于Android 5.0的系统中,.so文件位于app的nativeLibraryRootDir/CPU_ARCH目录中。
七.为什么一般的项目中只看到armeabi文件夹?
因为所有的x86/x86_64/armeabi-v7a/arm64-v8a设备都支持armeabi架构的.so文件。
八.那我们是不是只放一种armeabi就够了?
事实上并不是:这不只影响到函数库的性能和兼容性。x86设备能够很好的运行ARM类型函数库,但并不保证100%不发生crash,特别是对旧设备。64位设备(arm64-v8a, x86_64, mips64)能够运行32位的函数库,但是以32位模式运行,在64位平台上运行32位版本的ART和Android组件,将丢失专为64位优化过的性能(ART,webview,media等等)。
八.so库开发过程中的一些错误汇总!(后续补充)
基本上大部分关于so库的错误 都是 java.lang.UnsatisfiedLinkError
官方解释 Throw if the java Virtural Machine cannot find an appropriate native-language definition of method declared native意思就是JVM找不到native method的native实现!所以看到这个错误,一般常见的几种情况分析。
1、低级错误——根本木有SO,你加载个球啊!
code System.loadLibrary(Bugly);libs 空
运行设备 Android ARM设备
运行结果 Crash!java.lang.UnsatisfiedLinkError: dalvik.system.PathClassLoader[DexPathList[[zip file “/data/app/com.tencent.bugly.demo-1/base.apk”],nativeLibraryDirectories=[/vendor/lib, /systemb]]] couldn’t find “libBugly.so”
原因分析 apk安装时,系统会把apk中libs目录下armeabi的SO拷贝到应用的私有目录下。所以libs里没有放入SO,运行时肯定找不到SO。
修复方式 添加SO:libs\armeabi\libBugly.so或加载代码注释掉://System.loadLibrary(Bugly) ;
2、进阶错误——根本木有X86的SO,在X86的设备上你加载个球啊!
code System.loadLibrary(Bugly);libs libs\armeabi\libBugly.so
运行设备 Android X86设备
运行结果 Crash!java.lang.UnsatisfiedLinkError: dalvik.system.PathClassLoader[DexPathList[[zip file “/data/app/com.tencent.bugly.demo-1/base.apk”],nativeLibraryDirectories=[/vendor/lib, /systemb]]] couldn’t find “libBugly.so”
原因分析 apk安装时,x86设备上系统会把apk中libs目录下x86的SO,拷贝到应用的私有目录下。虽然libs下有armeabi的SO,但没有放入x86的SO,运行时还是找不到libbugly.so。
修复方式 添加SO:libs\x86\libBugly.so或加载代码注释掉://System.loadLibrary(Bugly) ;
3、大坑——尼玛,好难发现!
libs libs\armeabi\libBugly.solibs\armeabi\libBugly2.solibs\armeabi-v7a\libBugly.so运行设备 Android ARMv7设备
运行结果 Crash!java.lang.UnsatisfiedLinkError: dalvik.system.PathClassLoader[DexPathList[[zip file “/data/app/com.tencent.bugly.demo-1/base.apk”],nativeLibraryDirectories=[/vendor/lib, /systemb]]] couldn’t find “libBugly2.so”
原因分析 apk安装时,系统会把apk中libs目录下armeabi-v7a整个目录下的SO拷贝到应用的私有目录下。因为armeabi-v7a下没有放入libBugly2.so,运行时找不到libBugly2.so。不同的工具兼容的CPU架构不一致,就容易出这个错误了!例如:
libBugly.so提供armeabi、armeabi-v7a、x86三种。
但其它产品可能只提供了armeabi。
如果把这些so都直接拷贝进apk,就会因为上述的原因直接crash,会误以为该Crash是因为不同产品的so不能兼容导致的!
修复方式 添加SO:libs\armeabi-v7a\libBugly2.so或直接删除armeabi-v7a目录,arm设备上系统会自动选择armeabi
4、天坑——尼玛,巨难发现!
java.lang.UnsatisfiedLinkError中couldn’t find “XX.so”的占比非常高,上面提的三个场景都是这种错误!但你见过下面这种错误吗?
java.lang.UnsatisfiedLinkError:dlopen failed: “**/*/arm/*.so” has unexpected e_machine: 3
code if(getArch().contain(“arm”)){//只在arm下加载System.loadLibrary(Bugly) ;}
libs libs\armeabi\libBugly.so 坑爹实习生放入了x86编译的libBugly.so(同名很容易出错)
运行设备 Android ARM设备
运行结果 Crash!java.lang.UnsatisfiedLinkError: dlopen failed: “/data/app/com.tencent.bugly.crashreport.demo-2/lib/arm/libBugly.so” has unexpected e_machine: 3
原因分析 apk安装时,系统把armeabi下的libBugly.so放入应用的私有目录中了!但这个libBugly.so不是arm的,而是x86编译的libBugly.so运行时,系统检察ELF文件中的e_machine字段的值,跟arm的不匹配,就会抛出这个异常了!
5 java.lang.UnsatisfiedLinkError:No implementation found for XXX
这种错误也是醉了,说是要建立跟c/cpp写的代码一样的包名和java文件
以上错误汇总来自于 http://blog.csdn.net/u013278099/article/details/50414438这篇文章
这个so库的错误是我这几天在做腾讯云视频直播的时候出现的一些问题,他们的sdk(1.8.2版本)里面的问题是:sdk里面提供的so库不全,导致出现各种问题。基本上面都介绍到了。
先写到这里,希望能让大家都so库有一些基本的了解。肯定还有很多我没有介绍到的,希望大家多多交流。
大家可以加入我的qq群:Android开发经验交流群454430053
- android开发 加载so库的解析和出现的各种错误分析
- android开发 加载so库的解析和出现的各种错误分析
- Android中so使用知识和问题总结以及插件开发过程中加载so的方案解析
- Android中so使用知识和问题总结以及插件开发过程中加载so的方案解析
- Android开发过程中so调用出现的常见问题分析
- Android 加载 SO 库 UnsatisfiedLinkError 错误的原因及解决方案
- Android中出现的各种错误
- android开发遇到make is not found in path 或者是报加载不到so库的错误
- android so文件的加载过程以及常规错误处理
- Android Studio 导入.so文件出现的错误
- Android动态加载so库的实现
- Android Studio 加载 .so库出现couldn't find "*.so"
- Android Studio 加载 .so库出现couldn't find "*.so"
- android Studio so的加载
- Android开发中遇到加载有相同函数的so库时的问题
- android studio 如何加载第三方的jar和so
- Myeclipse的各种错误解析
- Android开发中出现的错误集
- POJ3278-Catch That Cow
- 使用 FireDAC的 TFDConnection, TFDQuery 最初只能显示50条记录,TDateSet.RecordCount总是获得50的解决方法。
- widnows:The signal HUP is in use by the JVM and will not work correctly on this platform
- Ubuntu修改时间
- 编程练习:动态规划0-1背包问题
- android开发 加载so库的解析和出现的各种错误分析
- iOS开发中集成友盟6.0.0发现的问题
- excel导出和导入。
- Java技术文章收集汇总【不定期更新】
- Excel 正则表达式 VB 提取字符串
- 关于java线程的一些东西
- Android 摄像头开发
- 使用sublime+PlantUML画图
- 脑筋急转弯的歧义性