am 7cb13f8a: Merge "Scan for renderscript files before deciding ABIs."

* commit '7cb13f8a0a40f3d971a953b330f38bfcfb001c5e':
  Scan for renderscript files before deciding ABIs.
This commit is contained in:
Narayan Kamath
2014-06-03 13:24:50 +00:00
committed by Android Git Automerger
4 changed files with 103 additions and 16 deletions

View File

@@ -20,6 +20,7 @@ import android.content.pm.PackageManager;
import android.util.Slog;
import java.io.File;
import java.io.IOException;
/**
* Native libraries helper.
@@ -141,4 +142,18 @@ public class NativeLibraryHelper {
return deletedFiles;
}
// We don't care about the other return values for now.
private static final int BITCODE_PRESENT = 1;
public static boolean hasRenderscriptBitcode(ApkHandle handle) throws IOException {
final int returnVal = hasRenderscriptBitcode(handle.apkHandle);
if (returnVal < 0) {
throw new IOException("Error scanning APK, code: " + returnVal);
}
return (returnVal == BITCODE_PRESENT);
}
private static native int hasRenderscriptBitcode(long apkHandle);
}

View File

@@ -46,6 +46,9 @@
#define LIB_SUFFIX ".so"
#define LIB_SUFFIX_LEN (sizeof(LIB_SUFFIX) - 1)
#define RS_BITCODE_SUFFIX ".bc"
#define RS_BITCODE_SUFFIX_LEN (sizeof(RS_BITCODE_SUFFIX) -1)
#define GDBSERVER "gdbserver"
#define GDBSERVER_LEN (sizeof(GDBSERVER) - 1)
@@ -486,6 +489,42 @@ com_android_internal_content_NativeLibraryHelper_findSupportedAbi(JNIEnv *env, j
return (jint) findSupportedAbi(env, apkHandle, javaCpuAbisToSearch);
}
enum bitcode_scan_result_t {
APK_SCAN_ERROR = -1,
NO_BITCODE_PRESENT = 0,
BITCODE_PRESENT = 1,
};
static jint
com_android_internal_content_NativeLibraryHelper_hasRenderscriptBitcode(JNIEnv *env, jclass clazz,
jlong apkHandle) {
ZipFileRO* zipFile = reinterpret_cast<ZipFileRO*>(apkHandle);
void* cookie = NULL;
if (!zipFile->startIteration(&cookie)) {
return APK_SCAN_ERROR;
}
char fileName[PATH_MAX];
ZipEntryRO next = NULL;
while ((next = zipFile->nextEntry(cookie)) != NULL) {
if (zipFile->getEntryFileName(next, fileName, sizeof(fileName))) {
continue;
}
const size_t fileNameLen = strlen(fileName);
const char* lastSlash = strrchr(fileName, '/');
const char* baseName = (lastSlash == NULL) ? fileName : fileName + 1;
if (!strncmp(fileName + fileNameLen - RS_BITCODE_SUFFIX_LEN, RS_BITCODE_SUFFIX,
RS_BITCODE_SUFFIX_LEN) && isFilenameSafe(baseName)) {
zipFile->endIteration(cookie);
return BITCODE_PRESENT;
}
}
zipFile->endIteration(cookie);
return NO_BITCODE_PRESENT;
}
static jlong
com_android_internal_content_NativeLibraryHelper_openApk(JNIEnv *env, jclass, jstring apkPath)
{
@@ -517,6 +556,8 @@ static JNINativeMethod gMethods[] = {
{"nativeFindSupportedAbi",
"(J[Ljava/lang/String;)I",
(void *)com_android_internal_content_NativeLibraryHelper_findSupportedAbi},
{"hasRenderscriptBitcode", "(J)I",
(void *)com_android_internal_content_NativeLibraryHelper_hasRenderscriptBitcode},
};

View File

@@ -88,7 +88,7 @@ public class DefaultContainerService extends IntentService {
private IMediaContainerService.Stub mBinder = new IMediaContainerService.Stub() {
/**
* Creates a new container and copies resource there.
* @param paackageURI the uri of resource to be copied. Can be either
* @param packageURI the uri of resource to be copied. Can be either
* a content uri or a file uri
* @param cid the id of the secure container that should
* be used for creating a secure container into which the resource
@@ -342,9 +342,22 @@ public class DefaultContainerService extends IntentService {
// The .apk file
String codePath = packageURI.getPath();
File codeFile = new File(codePath);
String[] abiList = (abiOverride != null) ? new String[] { abiOverride }
: Build.SUPPORTED_ABIS;
NativeLibraryHelper.ApkHandle handle = new NativeLibraryHelper.ApkHandle(codePath);
String[] abiList = Build.SUPPORTED_ABIS;
if (abiOverride != null) {
abiList = new String[] { abiList };
} else {
try {
if (Build.SUPPORTED_64_BIT_ABIS.length > 0 &&
NativeLibraryHelper.hasRenderscriptBitcode(handle)) {
abiList = Build.SUPPORTED_32_BIT_ABIS;
}
} catch (IOException ioe) {
Slog.w(TAG, "Problem determining ABI for: " + codeFile.getPath());
return null;
}
}
final int abi = NativeLibraryHelper.findSupportedAbi(handle, abiList);
// Calculate size of container needed to hold base APK.

View File

@@ -5073,12 +5073,23 @@ public class PackageManagerService extends IPackageManager.Stub {
if (pkg.applicationInfo.nativeLibraryDir != null) {
final NativeLibraryHelper.ApkHandle handle = new NativeLibraryHelper.ApkHandle(scanFile);
try {
// Enable gross and lame hacks for apps that are built with old
// SDK tools. We must scan their APKs for renderscript bitcode and
// not launch them if it's present. Don't bother checking on devices
// that don't have 64 bit support.
String[] abiList = Build.SUPPORTED_ABIS;
boolean hasLegacyRenderscriptBitcode = false;
if (abiOverride != null) {
abiList = new String[] { abiOverride };
} else if (Build.SUPPORTED_64_BIT_ABIS.length > 0 &&
NativeLibraryHelper.hasRenderscriptBitcode(handle)) {
abiList = Build.SUPPORTED_32_BIT_ABIS;
hasLegacyRenderscriptBitcode = true;
}
File nativeLibraryDir = new File(pkg.applicationInfo.nativeLibraryDir);
final String dataPathString = dataPath.getCanonicalPath();
final String[] abiList = (abiOverride != null) ? new String[] { abiOverride } :
Build.SUPPORTED_ABIS;
if (isSystemApp(pkg) && !isUpdatedSystemApp(pkg)) {
/*
* Upgrading from a previous version of the OS sometimes
@@ -5091,17 +5102,18 @@ public class PackageManagerService extends IPackageManager.Stub {
Log.i(TAG, "removed obsolete native libraries for system package "
+ path);
}
if (abiOverride != null) {
pkg.applicationInfo.cpuAbi = abiOverride;
if (abiOverride != null || hasLegacyRenderscriptBitcode) {
pkg.applicationInfo.cpuAbi = abiList[0];
pkgSetting.cpuAbiString = abiList[0];
} else {
setInternalAppAbi(pkg, pkgSetting);
}
} else {
if (!isForwardLocked(pkg) && !isExternal(pkg)) {
/*
* Update native library dir if it starts with
* /data/data
*/
* Update native library dir if it starts with
* /data/data
*/
if (nativeLibraryDir.getPath().startsWith(dataPathString)) {
setInternalAppNativeLibraryPath(pkg, pkgSetting);
nativeLibraryDir = new File(pkg.applicationInfo.nativeLibraryDir);
@@ -5120,8 +5132,8 @@ public class PackageManagerService extends IPackageManager.Stub {
// note of what ABI we're using
if (copyRet != PackageManager.NO_NATIVE_LIBRARIES) {
pkg.applicationInfo.cpuAbi = abiList[copyRet];
} else if (abiOverride != null) {
pkg.applicationInfo.cpuAbi = abiOverride;
} else if (abiOverride != null || hasLegacyRenderscriptBitcode) {
pkg.applicationInfo.cpuAbi = abiList[0];
} else {
pkg.applicationInfo.cpuAbi = null;
}
@@ -5145,8 +5157,8 @@ public class PackageManagerService extends IPackageManager.Stub {
// Note that (non upgraded) system apps will not have any native
// libraries bundled in their APK, but we're guaranteed not to be
// such an app at this point.
if (abiOverride != null) {
pkg.applicationInfo.cpuAbi = abiOverride;
if (abiOverride != null || hasLegacyRenderscriptBitcode) {
pkg.applicationInfo.cpuAbi = abiList[0];
} else {
pkg.applicationInfo.cpuAbi = null;
}
@@ -8812,9 +8824,15 @@ public class PackageManagerService extends IPackageManager.Stub {
}
final NativeLibraryHelper.ApkHandle handle = new NativeLibraryHelper.ApkHandle(codeFile);
final String[] abiList = (abiOverride != null) ?
String[] abiList = (abiOverride != null) ?
new String[] { abiOverride } : Build.SUPPORTED_ABIS;
try {
if (Build.SUPPORTED_64_BIT_ABIS.length > 0 &&
abiOverride == null &&
NativeLibraryHelper.hasRenderscriptBitcode(handle)) {
abiList = Build.SUPPORTED_32_BIT_ABIS;
}
int copyRet = copyNativeLibrariesForInternalApp(handle, nativeLibraryFile, abiList);
if (copyRet < 0 && copyRet != PackageManager.NO_NATIVE_LIBRARIES) {
return copyRet;