Мы испытываем java.lang.UnsatisfiedLinkError
на некоторых телефонах Android, которые используют наше приложение на рынке.
Описание проблемы:
static
{
System.loadLibrary("stlport_shared"); // C++ STL
System.loadLibrary("lib2");
System.loadLibrary("lib3");
}
Сбой приложения в строке System.loadLibrary()
с помощью java.lang.UnsatisfiedLinkError
.
java.lang.UnsatisfiedLinkError: Couldn't load stlport_shared from loader dalvik.system.PathClassLoader[dexPath=/data/app/app_id-2.apk,libraryPath=/data/app-lib/app_id-2]: findLibrary returned null
Подход к решению
Мы начали запускать некоторую собственную диагностику на всех наших установках, чтобы проверить, не распакован ли каждый каталог в папке /data/data/app_id/lib
.
PackageManager m = context.getPackageManager();
String s = context.getPackageName();
PackageInfo p;
p = m.getPackageInfo(s, 0);
s = p.applicationInfo.dataDir;
File appDir = new File(s);
long freeSpace = appDir.getFreeSpace();
File[] appDirList = appDir.listFiles();
int numberOfLibFiles = 0;
boolean subFilesLarger0 = true;
for (int i = 0; i < appDirList.length; i++) {
if(appDirList[i].getName().startsWith("lib")) {
File[] subFile = appDirList[i].listFiles(FileFilters.FilterDirs);
numberOfLibFiles = subFile.length;
for (int j = 0; j < subFile.length; j++) {
if(subFile[j].length() <= 0) {
subFilesLarger0 = false;
break;
}
}
}
}
На каждом тестовом телефоне есть numberOfLibFiles == 3
и subFilesLarger0 == true
. Мы хотели проверить, все ли библиотеки распакованы правильно и они больше, чем 0 байт. Кроме того, мы смотрим на freeSpace
, чтобы узнать, сколько места на диске доступно. freeSpace
соответствует объему памяти, который вы можете найти в настройках → Приложения в нижней части экрана. Мысль за этим подходом заключалась в том, что, когда на диске недостаточно места для установки, у установщика могут возникнуть проблемы с распаковкой APK.
Сценарий реального мира
Посмотрев на диагностику, некоторые из устройств там НЕ имеют все 3 библиотеки lib в папке /data/data/app_id/lib
, но имеют достаточно свободного места. Мне интересно, почему сообщение об ошибке ищет /data/app-lib/app_id-2
. Все наши телефоны хранят свои библиотеки в /data/data/app_id/lib
. Кроме того, System.loadLibrary()
должен использовать согласованный путь для установки и загрузки libs? Как я могу узнать, где ОС ищет библиотеки?
Вопрос
Кто-нибудь испытывает проблемы с установкой родных libs? Какая работа прошла успешно? Какой-либо опыт загрузки загруженных в интернет-потоках собственных интернет-библиотек, если они не существуют и хранятся вручную? Что может вызвать проблему в первую очередь?
ИЗМЕНИТЬ
Теперь у меня также есть пользователь, который сталкивается с этой проблемой после обновления приложения. Предыдущая версия отлично работала на его телефоне, после обновления, по-видимому, отсутствуют собственные библиотеки. Как правило, копирование libs также вызывает проблемы. Он находится на android 4.x с ненастроенным телефоном без пользовательского ПЗУ.
РЕДАКТИРОВАТЬ 2 - Решение
Через 2 года тратится время на эту проблему. Мы придумали решение, которое хорошо работает для нас сейчас. Мы открываем его: https://github.com/KeepSafe/ReLinker