in java/com/facebook/soloader/SoLoader.java [1018:1118]
private static void doLoadLibraryBySoName(
String soName, int loadFlags, @Nullable StrictMode.ThreadPolicy oldPolicy)
throws UnsatisfiedLinkError {
int result = SoSource.LOAD_RESULT_NOT_FOUND;
sSoSourcesLock.readLock().lock();
try {
if (sSoSources == null) {
Log.e(TAG, "Could not load: " + soName + " because no SO source exists");
throw new UnsatisfiedLinkError("couldn't find DSO to load: " + soName);
}
} finally {
sSoSourcesLock.readLock().unlock();
}
// This way, we set the thread policy only one per loadLibrary no matter how many
// dependencies we load. Each call to StrictMode.allowThreadDiskWrites allocates.
boolean restoreOldPolicy = false;
if (oldPolicy == null) {
oldPolicy = StrictMode.allowThreadDiskReads();
restoreOldPolicy = true;
}
if (SYSTRACE_LIBRARY_LOADING) {
Api18TraceUtils.beginTraceSection("SoLoader.loadLibrary[", soName, "]");
}
Throwable error = null;
try {
sSoSourcesLock.readLock().lock();
try {
for (int i = 0; result == SoSource.LOAD_RESULT_NOT_FOUND && i < sSoSources.length; ++i) {
SoSource currentSource = sSoSources[i];
result = currentSource.loadLibrary(soName, loadFlags, oldPolicy);
if (result == SoSource.LOAD_RESULT_CORRUPTED_LIB_FILE && sBackupSoSources != null) {
// Let's try from the backup source
if (Log.isLoggable(TAG, Log.DEBUG)) {
Log.d(TAG, "Trying backup SoSource for " + soName);
}
for (UnpackingSoSource backupSoSource : sBackupSoSources) {
backupSoSource.prepare(soName);
int resultFromBackup = backupSoSource.loadLibrary(soName, loadFlags, oldPolicy);
if (resultFromBackup == SoSource.LOAD_RESULT_LOADED) {
result = resultFromBackup;
break;
}
}
break;
}
}
} finally {
sSoSourcesLock.readLock().unlock();
}
} catch (Throwable t) {
error = t;
} finally {
if (SYSTRACE_LIBRARY_LOADING) {
Api18TraceUtils.endSection();
}
if (restoreOldPolicy) {
StrictMode.setThreadPolicy(oldPolicy);
}
if (result == SoSource.LOAD_RESULT_NOT_FOUND
|| result == SoSource.LOAD_RESULT_CORRUPTED_LIB_FILE) {
StringBuilder sb = new StringBuilder().append("couldn't find DSO to load: ").append(soName);
if (error != null) {
String cause = error.getMessage();
if (cause == null) {
cause = error.toString();
}
sb.append(" caused by: ").append(cause);
error.printStackTrace();
} else {
// load failure wasn't caused by dependent libraries.
// Print the sources and current native library directory
sSoSourcesLock.readLock().lock();
for (int i = 0; i < sSoSources.length; ++i) {
sb.append("\n\tSoSource ").append(i).append(": ").append(sSoSources[i].toString());
}
if (sApplicationSoSource != null) {
Context updatedContext = sApplicationSoSource.getUpdatedContext();
File updatedNativeLibDir =
ApplicationSoSource.getNativeLibDirFromContext(updatedContext);
sb.append("\n\tNative lib dir: ")
.append(updatedNativeLibDir.getAbsolutePath())
.append("\n");
}
sSoSourcesLock.readLock().unlock();
}
sb.append(" result: ").append(result);
final String message = sb.toString();
Log.e(TAG, message);
UnsatisfiedLinkError err = new UnsatisfiedLinkError(message);
if (error != null) {
err.initCause(error);
}
throw err;
}
}
}