Flip default of extractNativeLibs if targets Q+
Test: Local in-progress CTS Test: CtsDynamicLinkerTestCases Bug: 112037137 Change-Id: I41289ec6bdfff13ef4aa551bf0a98bad73c9371e
This commit is contained in:
@@ -1621,7 +1621,7 @@ public class PackageParser {
|
||||
}
|
||||
|
||||
final AttributeSet attrs = parser;
|
||||
return parseApkLite(apkPath, parser, attrs, signingDetails);
|
||||
return parseApkLite(apkPath, parser, attrs, signingDetails, flags);
|
||||
|
||||
} catch (XmlPullParserException | IOException | RuntimeException e) {
|
||||
Slog.w(TAG, "Failed to parse " + apkPath, e);
|
||||
@@ -1708,7 +1708,7 @@ public class PackageParser {
|
||||
}
|
||||
|
||||
private static ApkLite parseApkLite(String codePath, XmlPullParser parser, AttributeSet attrs,
|
||||
SigningDetails signingDetails)
|
||||
SigningDetails signingDetails, int flags)
|
||||
throws IOException, XmlPullParserException, PackageParserException {
|
||||
final Pair<String, String> packageSplit = parsePackageSplitNames(parser, attrs);
|
||||
|
||||
@@ -1716,11 +1716,12 @@ public class PackageParser {
|
||||
int versionCode = 0;
|
||||
int versionCodeMajor = 0;
|
||||
int revisionCode = 0;
|
||||
int targetSdkVersion = 0;
|
||||
boolean coreApp = false;
|
||||
boolean debuggable = false;
|
||||
boolean multiArch = false;
|
||||
boolean use32bitAbi = false;
|
||||
boolean extractNativeLibs = true;
|
||||
Boolean extractNativeLibsProvided = null;
|
||||
boolean isolatedSplits = false;
|
||||
boolean isFeatureSplit = false;
|
||||
boolean isSplitRequired = false;
|
||||
@@ -1785,7 +1786,8 @@ public class PackageParser {
|
||||
use32bitAbi = attrs.getAttributeBooleanValue(i, false);
|
||||
}
|
||||
if ("extractNativeLibs".equals(attr)) {
|
||||
extractNativeLibs = attrs.getAttributeBooleanValue(i, true);
|
||||
extractNativeLibsProvided = Boolean.valueOf(
|
||||
attrs.getAttributeBooleanValue(i, true));
|
||||
}
|
||||
if ("preferCodeIntegrity".equals(attr)) {
|
||||
preferCodeIntegrity = attrs.getAttributeBooleanValue(i, false);
|
||||
@@ -1803,9 +1805,51 @@ public class PackageParser {
|
||||
PackageManager.INSTALL_PARSE_FAILED_MANIFEST_MALFORMED,
|
||||
"<uses-split> tag requires 'android:name' attribute");
|
||||
}
|
||||
} else if (TAG_USES_SDK.equals(parser.getName())) {
|
||||
final String[] errorMsg = new String[1];
|
||||
Pair<Integer, Integer> versions = deriveSdkVersions(new AbstractVersionsAccessor() {
|
||||
@Override public String getMinSdkVersionCode() {
|
||||
return getAttributeAsString("minSdkVersion");
|
||||
}
|
||||
|
||||
@Override public int getMinSdkVersion() {
|
||||
return getAttributeAsInt("minSdkVersion");
|
||||
}
|
||||
|
||||
@Override public String getTargetSdkVersionCode() {
|
||||
return getAttributeAsString("targetSdkVersion");
|
||||
}
|
||||
|
||||
@Override public int getTargetSdkVersion() {
|
||||
return getAttributeAsInt("targetSdkVersion");
|
||||
}
|
||||
|
||||
private String getAttributeAsString(String name) {
|
||||
return attrs.getAttributeValue(ANDROID_RESOURCES, name);
|
||||
}
|
||||
|
||||
private int getAttributeAsInt(String name) {
|
||||
try {
|
||||
return attrs.getAttributeIntValue(ANDROID_RESOURCES, name, -1);
|
||||
} catch (NumberFormatException e) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
}, flags, errorMsg);
|
||||
|
||||
if (versions == null) {
|
||||
throw new PackageParserException(
|
||||
PackageManager.INSTALL_PARSE_FAILED_MANIFEST_MALFORMED, errorMsg[0]);
|
||||
}
|
||||
|
||||
targetSdkVersion = versions.second;
|
||||
}
|
||||
}
|
||||
|
||||
final boolean extractNativeLibsDefault = targetSdkVersion < Build.VERSION_CODES.Q;
|
||||
final boolean extractNativeLibs = (extractNativeLibsProvided != null)
|
||||
? extractNativeLibsProvided : extractNativeLibsDefault;
|
||||
|
||||
if (preferCodeIntegrity && extractNativeLibs) {
|
||||
throw new PackageParserException(
|
||||
PackageManager.INSTALL_PARSE_FAILED_MANIFEST_MALFORMED,
|
||||
@@ -2215,65 +2259,60 @@ public class PackageParser {
|
||||
|
||||
} else if (tagName.equals(TAG_USES_SDK)) {
|
||||
if (SDK_VERSION > 0) {
|
||||
sa = res.obtainAttributes(parser,
|
||||
com.android.internal.R.styleable.AndroidManifestUsesSdk);
|
||||
sa = res.obtainAttributes(parser, R.styleable.AndroidManifestUsesSdk);
|
||||
final TypedArray saFinal = sa;
|
||||
Pair<Integer, Integer> versions = deriveSdkVersions(
|
||||
new AbstractVersionsAccessor() {
|
||||
@Override public String getMinSdkVersionCode() {
|
||||
return getAttributeAsString(
|
||||
R.styleable.AndroidManifestUsesSdk_minSdkVersion);
|
||||
}
|
||||
|
||||
int minVers = 1;
|
||||
String minCode = null;
|
||||
int targetVers = 0;
|
||||
String targetCode = null;
|
||||
@Override public int getMinSdkVersion() {
|
||||
return getAttributeAsInt(
|
||||
R.styleable.AndroidManifestUsesSdk_minSdkVersion);
|
||||
}
|
||||
|
||||
TypedValue val = sa.peekValue(
|
||||
com.android.internal.R.styleable.AndroidManifestUsesSdk_minSdkVersion);
|
||||
if (val != null) {
|
||||
if (val.type == TypedValue.TYPE_STRING && val.string != null) {
|
||||
minCode = val.string.toString();
|
||||
} else {
|
||||
// If it's not a string, it's an integer.
|
||||
minVers = val.data;
|
||||
}
|
||||
@Override public String getTargetSdkVersionCode() {
|
||||
return getAttributeAsString(
|
||||
R.styleable.AndroidManifestUsesSdk_targetSdkVersion);
|
||||
}
|
||||
|
||||
@Override public int getTargetSdkVersion() {
|
||||
return getAttributeAsInt(
|
||||
R.styleable.AndroidManifestUsesSdk_targetSdkVersion);
|
||||
}
|
||||
|
||||
private String getAttributeAsString(int index) {
|
||||
TypedValue val = saFinal.peekValue(index);
|
||||
if (val != null && val.type == TypedValue.TYPE_STRING
|
||||
&& val.string != null) {
|
||||
return val.string.toString();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
private int getAttributeAsInt(int index) {
|
||||
TypedValue val = saFinal.peekValue(index);
|
||||
if (val != null && val.type != TypedValue.TYPE_STRING) {
|
||||
// If it's not a string, it's an integer.
|
||||
return val.data;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
}, flags, outError);
|
||||
|
||||
if (versions == null) {
|
||||
mParseError = PackageManager.INSTALL_FAILED_OLDER_SDK;
|
||||
return null;
|
||||
}
|
||||
|
||||
val = sa.peekValue(
|
||||
com.android.internal.R.styleable.AndroidManifestUsesSdk_targetSdkVersion);
|
||||
if (val != null) {
|
||||
if (val.type == TypedValue.TYPE_STRING && val.string != null) {
|
||||
targetCode = val.string.toString();
|
||||
if (minCode == null) {
|
||||
minCode = targetCode;
|
||||
}
|
||||
} else {
|
||||
// If it's not a string, it's an integer.
|
||||
targetVers = val.data;
|
||||
}
|
||||
} else {
|
||||
targetVers = minVers;
|
||||
targetCode = minCode;
|
||||
}
|
||||
pkg.applicationInfo.minSdkVersion = versions.first;
|
||||
pkg.applicationInfo.targetSdkVersion = versions.second;
|
||||
|
||||
sa.recycle();
|
||||
|
||||
final int minSdkVersion = PackageParser.computeMinSdkVersion(minVers, minCode,
|
||||
SDK_VERSION, SDK_CODENAMES, outError);
|
||||
if (minSdkVersion < 0) {
|
||||
mParseError = PackageManager.INSTALL_FAILED_OLDER_SDK;
|
||||
return null;
|
||||
}
|
||||
|
||||
boolean defaultToCurrentDevBranch = (flags & PARSE_FORCE_SDK) != 0;
|
||||
final int targetSdkVersion = PackageParser.computeTargetSdkVersion(targetVers,
|
||||
targetCode, SDK_CODENAMES, outError, defaultToCurrentDevBranch);
|
||||
if (targetSdkVersion < 0) {
|
||||
mParseError = PackageManager.INSTALL_FAILED_OLDER_SDK;
|
||||
return null;
|
||||
}
|
||||
|
||||
pkg.applicationInfo.minSdkVersion = minSdkVersion;
|
||||
pkg.applicationInfo.targetSdkVersion = targetSdkVersion;
|
||||
}
|
||||
|
||||
XmlUtils.skipCurrentTag(parser);
|
||||
|
||||
} else if (tagName.equals(TAG_SUPPORT_SCREENS)) {
|
||||
sa = res.obtainAttributes(parser,
|
||||
com.android.internal.R.styleable.AndroidManifestSupportsScreens);
|
||||
@@ -2675,6 +2714,67 @@ public class PackageParser {
|
||||
return -1;
|
||||
}
|
||||
|
||||
private interface AbstractVersionsAccessor {
|
||||
/** Returns minimum SDK version code string, or null if absent. */
|
||||
String getMinSdkVersionCode();
|
||||
|
||||
/** Returns minimum SDK version code, or -1 if absent. */
|
||||
int getMinSdkVersion();
|
||||
|
||||
/** Returns target SDK version code string, or null if absent. */
|
||||
String getTargetSdkVersionCode();
|
||||
|
||||
/** Returns target SDK version code, or -1 if absent. */
|
||||
int getTargetSdkVersion();
|
||||
}
|
||||
|
||||
private static @Nullable Pair<Integer, Integer> deriveSdkVersions(
|
||||
@NonNull AbstractVersionsAccessor accessor, int flags, String[] outError) {
|
||||
int minVers = 1;
|
||||
String minCode = null;
|
||||
int targetVers = 0;
|
||||
String targetCode = null;
|
||||
|
||||
String code = accessor.getMinSdkVersionCode();
|
||||
int version = accessor.getMinSdkVersion();
|
||||
// Check integer first since code is almost never a null string (e.g. "28").
|
||||
if (version >= 0) {
|
||||
minVers = version;
|
||||
} else if (code != null) {
|
||||
minCode = code;
|
||||
}
|
||||
|
||||
code = accessor.getTargetSdkVersionCode();
|
||||
version = accessor.getTargetSdkVersion();
|
||||
// Check integer first since code is almost never a null string (e.g. "28").
|
||||
if (version >= 0) {
|
||||
targetVers = version;
|
||||
} else if (code != null) {
|
||||
targetCode = code;
|
||||
if (minCode == null) {
|
||||
minCode = targetCode;
|
||||
}
|
||||
} else {
|
||||
targetVers = minVers;
|
||||
targetCode = minCode;
|
||||
}
|
||||
|
||||
final int minSdkVersion = computeMinSdkVersion(minVers, minCode,
|
||||
SDK_VERSION, SDK_CODENAMES, outError);
|
||||
if (minSdkVersion < 0) {
|
||||
return null;
|
||||
}
|
||||
|
||||
boolean defaultToCurrentDevBranch = (flags & PARSE_FORCE_SDK) != 0;
|
||||
final int targetSdkVersion = computeTargetSdkVersion(targetVers,
|
||||
targetCode, SDK_CODENAMES, outError, defaultToCurrentDevBranch);
|
||||
if (targetSdkVersion < 0) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return Pair.create(minSdkVersion, targetSdkVersion);
|
||||
}
|
||||
|
||||
/**
|
||||
* Computes the minSdkVersion to use at runtime. If the package is not
|
||||
* compatible with this platform, populates {@code outError[0]} with an
|
||||
|
||||
Reference in New Issue
Block a user