Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 1ca213d6 authored by William Loh's avatar William Loh
Browse files

Extract ASL in system APKs to new dir

ASL cannot be extracted from preloaded APKs to their code paths because
they reside on read only paritions. ASL files will, instead, be extracted
to /data/app-metadata/[packagename].

Bug: 336618214
Test: manual
Test: atest InstallAppMetadataTest
Change-Id: Ie2fcbc2bcba6d40ee88778a95cbd9e5ff36eaa82
parent f1a7f5b2
Loading
Loading
Loading
Loading
+45 −20
Original line number Diff line number Diff line
@@ -89,6 +89,7 @@ import static com.android.server.pm.PackageManagerServiceUtils.comparePackageSig
import static com.android.server.pm.PackageManagerServiceUtils.compareSignatures;
import static com.android.server.pm.PackageManagerServiceUtils.compressedFileExists;
import static com.android.server.pm.PackageManagerServiceUtils.deriveAbiOverride;
import static com.android.server.pm.PackageManagerServiceUtils.extractAppMetadataFromApk;
import static com.android.server.pm.PackageManagerServiceUtils.isInstalledByAdb;
import static com.android.server.pm.PackageManagerServiceUtils.logCriticalInfo;
import static com.android.server.pm.PackageManagerServiceUtils.makeDirRecursive;
@@ -500,6 +501,36 @@ final class InstallPackageHelper {
            mPm.setUpCustomResolverActivity(pkg, pkgSetting);
        }

        // When upgrading a package, pkgSetting is copied from oldPkgSetting. Clear the app
        // metadata file path for the new package.
        if (oldPkgSetting != null) {
            pkgSetting.setAppMetadataFilePath(null);
        }
        // If the app metadata file path is not null then this is a system app with a preloaded app
        // metadata file on the system image. Do not reset the path and source if this is the
        // case.
        if (pkgSetting.getAppMetadataFilePath() == null) {
            File dir = new File(pkg.getPath());
            if (pkgSetting.isSystem()) {
                dir = new File(Environment.getDataDirectory(),
                        "app-metadata/" + pkg.getPackageName());
            }
            File appMetadataFile = new File(dir, APP_METADATA_FILE_NAME);
            if (appMetadataFile.exists()) {
                pkgSetting.setAppMetadataFilePath(appMetadataFile.getAbsolutePath());
                if (Flags.aslInApkAppMetadataSource()) {
                    pkgSetting.setAppMetadataSource(APP_METADATA_SOURCE_INSTALLER);
                }
            } else if (Flags.aslInApkAppMetadataSource()) {
                Map<String, PackageManager.Property> properties = pkg.getProperties();
                if (properties.containsKey(PROPERTY_ANDROID_SAFETY_LABEL_PATH)) {
                    // ASL file extraction is done in post-install
                    pkgSetting.setAppMetadataFilePath(appMetadataFile.getAbsolutePath());
                    pkgSetting.setAppMetadataSource(APP_METADATA_SOURCE_APK);
                }
            }
        }

        if (pkg.getPackageName().equals("android")) {
            mPm.setPlatformPackage(pkg, pkgSetting);
        }
@@ -2215,24 +2246,6 @@ final class InstallPackageHelper {
                installRequest.setNewUsers(
                        ps.queryInstalledUsers(allUsers, true));
                ps.setUpdateAvailable(false /*updateAvailable*/);

                File appMetadataFile = new File(ps.getPath(), APP_METADATA_FILE_NAME);
                if (appMetadataFile.exists()) {
                    ps.setAppMetadataFilePath(appMetadataFile.getAbsolutePath());
                    if (Flags.aslInApkAppMetadataSource()) {
                        ps.setAppMetadataSource(APP_METADATA_SOURCE_INSTALLER);
                    }
                } else {
                    Map<String, PackageManager.Property> properties = parsedPackage.getProperties();
                    if (Flags.aslInApkAppMetadataSource()
                            && properties.containsKey(PROPERTY_ANDROID_SAFETY_LABEL_PATH)) {
                        // ASL file extraction is done in post-install
                        ps.setAppMetadataFilePath(appMetadataFile.getAbsolutePath());
                        ps.setAppMetadataSource(APP_METADATA_SOURCE_APK);
                    } else {
                        ps.setAppMetadataFilePath(null);
                    }
                }
            }
            if (installRequest.getReturnCode() == PackageManager.INSTALL_SUCCEEDED) {
                // If this is an archival installation then we'll initialize the archive status,
@@ -2829,8 +2842,8 @@ final class InstallPackageHelper {
        if (succeeded) {
            if (Flags.aslInApkAppMetadataSource()
                    && pkgSetting.getAppMetadataSource() == APP_METADATA_SOURCE_APK) {
                if (!PackageManagerServiceUtils.extractAppMetadataFromApk(request.getPkg(),
                        pkgSetting.getAppMetadataFilePath())) {
                if (!extractAppMetadataFromApk(request.getPkg(),
                        pkgSetting.getAppMetadataFilePath(), pkgSetting.isSystem())) {
                    synchronized (mPm.mLock) {
                        PackageSetting setting = mPm.mSettings.getPackageLPr(packageName);
                        if (setting != null) {
@@ -3815,6 +3828,18 @@ final class InstallPackageHelper {
                        new IncrementalProgressListener(parsedPackage.getPackageName(), mPm));
            }
        }

        if (Flags.aslInApkAppMetadataSource()
                && scanResult.mPkgSetting.getAppMetadataSource() == APP_METADATA_SOURCE_APK) {
            if (!extractAppMetadataFromApk(parsedPackage,
                    scanResult.mPkgSetting.getAppMetadataFilePath(),
                    scanResult.mPkgSetting.isSystem())) {
                synchronized (mPm.mLock) {
                    scanResult.mPkgSetting.setAppMetadataFilePath(null)
                            .setAppMetadataSource(APP_METADATA_SOURCE_UNKNOWN);
                }
            }
        }
        return scanResult.mPkgSetting.getPkg();
    }

+15 −2
Original line number Diff line number Diff line
@@ -1571,11 +1571,23 @@ public class PackageManagerServiceUtils {
     * Extract the app.metadata file from apk.
     */
    public static boolean extractAppMetadataFromApk(AndroidPackage pkg,
            String appMetadataFilePath) {
            String appMetadataFilePath, boolean isSystem) {
        if (appMetadataFilePath == null) {
            return false;
        }
        File appMetadataFile = new File(appMetadataFilePath);
        if (appMetadataFile.exists()) {
            return true;
        }
        if (isSystem) {
            try {
                makeDirRecursive(new File(appMetadataFilePath).getParentFile(), 0700);
            } catch (Exception e) {
                Slog.e(TAG, "Failed to create app metadata dir for package "
                        + pkg.getPackageName() + ": " + e.getMessage());
                return false;
            }
        }
        Map<String, Property> properties = pkg.getProperties();
        if (!properties.containsKey(PROPERTY_ANDROID_SAFETY_LABEL_PATH)) {
            return false;
@@ -1589,7 +1601,8 @@ public class PackageManagerServiceUtils {
        for (int i = 0; i < splits.size(); i++) {
            try (ZipFile zipFile = new ZipFile(splits.get(i).getPath())) {
                ZipEntry zipEntry = zipFile.getEntry(fileInApkPath);
                if (zipEntry != null && zipEntry.getSize() <= getAppMetadataSizeLimit()) {
                if (zipEntry != null
                        && (isSystem || zipEntry.getSize() <= getAppMetadataSizeLimit())) {
                    try (InputStream in = zipFile.getInputStream(zipEntry)) {
                        try (FileOutputStream out = new FileOutputStream(appMetadataFile)) {
                            FileUtils.copy(in, out);