System分區應用自帶庫與原生庫同名問題分析
問題背景
某系統應用發生必現崩潰問題。崩潰log如下
0*-** **:**:**.** 66666 66666 E ***** aar error:: java.lang.UnsatisfiedLinkError: dlopen failed: cannot
locate symbol "_TTT_TTT_TTT"
referenced by "/system/app/LINDUO/lib/arm64/liblinduo.so"...
0*-** **:**:**.** 66666 66666 E offline_da aar error:: at java.lang.Runtime.loadLibrary0(Runtime.java)
- 根據Log提示,動態庫依賴時找不到_TTT_TTT_TTT這個符號。檢索liblinduo.so依賴的動態庫。發現,_TTT_TTT_TTT這個符號,在應用自帶的libA.so這個庫中。
nm -D linA.so | grep _TTT_TTT_TTT
- 檢查進程對應的map文件,/proc/66666/maps,發現加載了系統中的libA.so(/system/lib64/libA.so)。
相關知識點
動態庫加載優先級
- 應用私有目錄
- 自定義注入路徑
- 系統目錄
- Android 7.0+強制/system分區的應用使用AOSP原生庫,即使應用自帶同名庫也會被忽略。可以理解為,Aosp的原生庫比如libA.so是Aosp自身依賴的。如果系統應用自帶了libA.so,那么system分區的應用,就會忽略這個庫。因為,不能讓應用自帶的庫把系統的原生庫替換了。
解決System分區應用自帶庫與原生庫同名問題
- 把應用挪到/vendor分區,或者作為后裝應用(可以的話),利用Android命名空間機制隔離(參考Asop官網原生庫的命名空間)
- 重命名應用自帶的動態庫,把動態庫改成其他名字。
- 使用和系統版本統一的動態庫。
- 應用使用靜態庫,靜態依賴。