Loading core/java/android/content/pm/PackageManager.java +1 −1 Original line number Diff line number Diff line Loading @@ -4758,7 +4758,7 @@ public abstract class PackageManager { PackageParser.Package pkg = parser.parseMonolithicPackage(apkFile, 0); if ((flags & GET_SIGNATURES) != 0) { PackageParser.collectCertificates(pkg, 0); PackageParser.collectCertificates(pkg, false /* skipVerify */); } PackageUserState state = new PackageUserState(); return PackageParser.generatePackageInfo(pkg, null, flags, 0, 0, null, state); Loading core/java/android/content/pm/PackageParser.java +9 −8 Original line number Diff line number Diff line Loading @@ -1484,9 +1484,9 @@ public class PackageParser { * populating {@link Package#mSigningDetails}. Also asserts that all APK * contents are signed correctly and consistently. */ public static void collectCertificates(Package pkg, @ParseFlags int parseFlags) public static void collectCertificates(Package pkg, boolean skipVerify) throws PackageParserException { collectCertificatesInternal(pkg, parseFlags); collectCertificatesInternal(pkg, skipVerify); final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; for (int i = 0; i < childCount; i++) { Package childPkg = pkg.childPackages.get(i); Loading @@ -1494,17 +1494,17 @@ public class PackageParser { } } private static void collectCertificatesInternal(Package pkg, @ParseFlags int parseFlags) private static void collectCertificatesInternal(Package pkg, boolean skipVerify) throws PackageParserException { pkg.mSigningDetails = SigningDetails.UNKNOWN; Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "collectCertificates"); try { collectCertificates(pkg, new File(pkg.baseCodePath), parseFlags); collectCertificates(pkg, new File(pkg.baseCodePath), skipVerify); if (!ArrayUtils.isEmpty(pkg.splitCodePaths)) { for (int i = 0; i < pkg.splitCodePaths.length; i++) { collectCertificates(pkg, new File(pkg.splitCodePaths[i]), parseFlags); collectCertificates(pkg, new File(pkg.splitCodePaths[i]), skipVerify); } } } finally { Loading @@ -1512,7 +1512,7 @@ public class PackageParser { } } private static void collectCertificates(Package pkg, File apkFile, @ParseFlags int parseFlags) private static void collectCertificates(Package pkg, File apkFile, boolean skipVerify) throws PackageParserException { final String apkPath = apkFile.getAbsolutePath(); Loading @@ -1522,7 +1522,7 @@ public class PackageParser { minSignatureScheme = SigningDetails.SignatureSchemeVersion.SIGNING_BLOCK_V2; } SigningDetails verified; if ((parseFlags & PARSE_IS_SYSTEM_DIR) != 0) { if (skipVerify) { // systemDir APKs are already trusted, save time by not verifying verified = ApkSignatureVerifier.plsCertsNoVerifyOnlyCerts( apkPath, minSignatureScheme); Loading Loading @@ -1600,9 +1600,10 @@ public class PackageParser { if ((flags & PARSE_COLLECT_CERTIFICATES) != 0) { // TODO: factor signature related items out of Package object final Package tempPkg = new Package((String) null); final boolean skipVerify = (flags & PARSE_IS_SYSTEM_DIR) != 0; Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "collectCertificates"); try { collectCertificates(tempPkg, apkFile, flags); collectCertificates(tempPkg, apkFile, skipVerify); } finally { Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); } Loading core/java/android/util/apk/ApkSignatureSchemeV2Verifier.java +14 −0 Original line number Diff line number Diff line Loading @@ -412,6 +412,20 @@ public class ApkSignatureSchemeV2Verifier { } } static byte[] generateFsverityRootHash(String apkPath) throws IOException, SignatureNotFoundException, DigestException, NoSuchAlgorithmException { try (RandomAccessFile apk = new RandomAccessFile(apkPath, "r")) { SignatureInfo signatureInfo = findSignature(apk); VerifiedSigner vSigner = verify(apk, false); if (vSigner.verityRootHash == null) { return null; } return ApkVerityBuilder.generateFsverityRootHash( apk, ByteBuffer.wrap(vSigner.verityRootHash), signatureInfo); } } private static boolean isSupportedSignatureAlgorithm(int sigAlgorithm) { switch (sigAlgorithm) { case SIGNATURE_RSA_PSS_WITH_SHA256: Loading core/java/android/util/apk/ApkSignatureSchemeV3Verifier.java +14 −0 Original line number Diff line number Diff line Loading @@ -523,6 +523,20 @@ public class ApkSignatureSchemeV3Verifier { } } static byte[] generateFsverityRootHash(String apkPath) throws NoSuchAlgorithmException, DigestException, IOException, SignatureNotFoundException { try (RandomAccessFile apk = new RandomAccessFile(apkPath, "r")) { SignatureInfo signatureInfo = findSignature(apk); VerifiedSigner vSigner = verify(apk, false); if (vSigner.verityRootHash == null) { return null; } return ApkVerityBuilder.generateFsverityRootHash( apk, ByteBuffer.wrap(vSigner.verityRootHash), signatureInfo); } } private static boolean isSupportedSignatureAlgorithm(int sigAlgorithm) { switch (sigAlgorithm) { case SIGNATURE_RSA_PSS_WITH_SHA256: Loading core/java/android/util/apk/ApkSignatureVerifier.java +21 −0 Original line number Diff line number Diff line Loading @@ -426,6 +426,27 @@ public class ApkSignatureVerifier { return ApkSignatureSchemeV2Verifier.generateApkVerity(apkPath, bufferFactory); } /** * Generates the FSVerity root hash from FSVerity header, extensions and Merkle tree root hash * in Signing Block. * * @return FSverity root hash */ public static byte[] generateFsverityRootHash(String apkPath) throws NoSuchAlgorithmException, DigestException, IOException { // first try v3 try { return ApkSignatureSchemeV3Verifier.generateFsverityRootHash(apkPath); } catch (SignatureNotFoundException e) { // try older version } try { return ApkSignatureSchemeV2Verifier.generateFsverityRootHash(apkPath); } catch (SignatureNotFoundException e) { return null; } } /** * Result of a successful APK verification operation. */ Loading Loading
core/java/android/content/pm/PackageManager.java +1 −1 Original line number Diff line number Diff line Loading @@ -4758,7 +4758,7 @@ public abstract class PackageManager { PackageParser.Package pkg = parser.parseMonolithicPackage(apkFile, 0); if ((flags & GET_SIGNATURES) != 0) { PackageParser.collectCertificates(pkg, 0); PackageParser.collectCertificates(pkg, false /* skipVerify */); } PackageUserState state = new PackageUserState(); return PackageParser.generatePackageInfo(pkg, null, flags, 0, 0, null, state); Loading
core/java/android/content/pm/PackageParser.java +9 −8 Original line number Diff line number Diff line Loading @@ -1484,9 +1484,9 @@ public class PackageParser { * populating {@link Package#mSigningDetails}. Also asserts that all APK * contents are signed correctly and consistently. */ public static void collectCertificates(Package pkg, @ParseFlags int parseFlags) public static void collectCertificates(Package pkg, boolean skipVerify) throws PackageParserException { collectCertificatesInternal(pkg, parseFlags); collectCertificatesInternal(pkg, skipVerify); final int childCount = (pkg.childPackages != null) ? pkg.childPackages.size() : 0; for (int i = 0; i < childCount; i++) { Package childPkg = pkg.childPackages.get(i); Loading @@ -1494,17 +1494,17 @@ public class PackageParser { } } private static void collectCertificatesInternal(Package pkg, @ParseFlags int parseFlags) private static void collectCertificatesInternal(Package pkg, boolean skipVerify) throws PackageParserException { pkg.mSigningDetails = SigningDetails.UNKNOWN; Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "collectCertificates"); try { collectCertificates(pkg, new File(pkg.baseCodePath), parseFlags); collectCertificates(pkg, new File(pkg.baseCodePath), skipVerify); if (!ArrayUtils.isEmpty(pkg.splitCodePaths)) { for (int i = 0; i < pkg.splitCodePaths.length; i++) { collectCertificates(pkg, new File(pkg.splitCodePaths[i]), parseFlags); collectCertificates(pkg, new File(pkg.splitCodePaths[i]), skipVerify); } } } finally { Loading @@ -1512,7 +1512,7 @@ public class PackageParser { } } private static void collectCertificates(Package pkg, File apkFile, @ParseFlags int parseFlags) private static void collectCertificates(Package pkg, File apkFile, boolean skipVerify) throws PackageParserException { final String apkPath = apkFile.getAbsolutePath(); Loading @@ -1522,7 +1522,7 @@ public class PackageParser { minSignatureScheme = SigningDetails.SignatureSchemeVersion.SIGNING_BLOCK_V2; } SigningDetails verified; if ((parseFlags & PARSE_IS_SYSTEM_DIR) != 0) { if (skipVerify) { // systemDir APKs are already trusted, save time by not verifying verified = ApkSignatureVerifier.plsCertsNoVerifyOnlyCerts( apkPath, minSignatureScheme); Loading Loading @@ -1600,9 +1600,10 @@ public class PackageParser { if ((flags & PARSE_COLLECT_CERTIFICATES) != 0) { // TODO: factor signature related items out of Package object final Package tempPkg = new Package((String) null); final boolean skipVerify = (flags & PARSE_IS_SYSTEM_DIR) != 0; Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "collectCertificates"); try { collectCertificates(tempPkg, apkFile, flags); collectCertificates(tempPkg, apkFile, skipVerify); } finally { Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER); } Loading
core/java/android/util/apk/ApkSignatureSchemeV2Verifier.java +14 −0 Original line number Diff line number Diff line Loading @@ -412,6 +412,20 @@ public class ApkSignatureSchemeV2Verifier { } } static byte[] generateFsverityRootHash(String apkPath) throws IOException, SignatureNotFoundException, DigestException, NoSuchAlgorithmException { try (RandomAccessFile apk = new RandomAccessFile(apkPath, "r")) { SignatureInfo signatureInfo = findSignature(apk); VerifiedSigner vSigner = verify(apk, false); if (vSigner.verityRootHash == null) { return null; } return ApkVerityBuilder.generateFsverityRootHash( apk, ByteBuffer.wrap(vSigner.verityRootHash), signatureInfo); } } private static boolean isSupportedSignatureAlgorithm(int sigAlgorithm) { switch (sigAlgorithm) { case SIGNATURE_RSA_PSS_WITH_SHA256: Loading
core/java/android/util/apk/ApkSignatureSchemeV3Verifier.java +14 −0 Original line number Diff line number Diff line Loading @@ -523,6 +523,20 @@ public class ApkSignatureSchemeV3Verifier { } } static byte[] generateFsverityRootHash(String apkPath) throws NoSuchAlgorithmException, DigestException, IOException, SignatureNotFoundException { try (RandomAccessFile apk = new RandomAccessFile(apkPath, "r")) { SignatureInfo signatureInfo = findSignature(apk); VerifiedSigner vSigner = verify(apk, false); if (vSigner.verityRootHash == null) { return null; } return ApkVerityBuilder.generateFsverityRootHash( apk, ByteBuffer.wrap(vSigner.verityRootHash), signatureInfo); } } private static boolean isSupportedSignatureAlgorithm(int sigAlgorithm) { switch (sigAlgorithm) { case SIGNATURE_RSA_PSS_WITH_SHA256: Loading
core/java/android/util/apk/ApkSignatureVerifier.java +21 −0 Original line number Diff line number Diff line Loading @@ -426,6 +426,27 @@ public class ApkSignatureVerifier { return ApkSignatureSchemeV2Verifier.generateApkVerity(apkPath, bufferFactory); } /** * Generates the FSVerity root hash from FSVerity header, extensions and Merkle tree root hash * in Signing Block. * * @return FSverity root hash */ public static byte[] generateFsverityRootHash(String apkPath) throws NoSuchAlgorithmException, DigestException, IOException { // first try v3 try { return ApkSignatureSchemeV3Verifier.generateFsverityRootHash(apkPath); } catch (SignatureNotFoundException e) { // try older version } try { return ApkSignatureSchemeV2Verifier.generateFsverityRootHash(apkPath); } catch (SignatureNotFoundException e) { return null; } } /** * Result of a successful APK verification operation. */ Loading