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

Commit 5f865b07 authored by Makoto Onuki's avatar Makoto Onuki Committed by Android (Google) Code Review
Browse files

Merge "Make sure always reuse ApplicationInfo when generating ProviderInfo" into rvc-dev

parents c11267f3 db91e180
Loading
Loading
Loading
Loading
+34 −26
Original line number Diff line number Diff line
@@ -57,6 +57,7 @@ import com.android.internal.annotations.GuardedBy;
import com.android.internal.util.ArrayUtils;
import com.android.server.IntentResolver;
import com.android.server.pm.parsing.PackageInfoUtils;
import com.android.server.pm.parsing.PackageInfoUtils.CachedApplicationInfoGenerator;
import com.android.server.pm.parsing.pkg.AndroidPackage;

import java.io.PrintWriter;
@@ -273,9 +274,7 @@ public class ComponentResolver {
            return null;
        }
        List<ProviderInfo> providerList = null;

        // Map from a package name to the corresponding app info.
        ArrayMap<String, ApplicationInfo> appInfos = null;
        CachedApplicationInfoGenerator appInfoGenerator = null;
        synchronized (mLock) {
            for (int i = mProviders.mProviders.size() - 1; i >= 0; --i) {
                final ParsedProvider p = mProviders.mProviders.valueAt(i);
@@ -304,26 +303,15 @@ public class ComponentResolver {
                        && (p.getMetaData() == null || !p.getMetaData().containsKey(metaDataKey))) {
                    continue;
                }

                // Make sure we have AppInfo for this provider.
                if (appInfoGenerator == null) {
                    appInfoGenerator = new CachedApplicationInfoGenerator();
                }
                final PackageUserState state = ps.readUserState(userId);
                ApplicationInfo appInfo =
                        (appInfos == null) ? null : appInfos.get(pkg.getPackageName());
                final ApplicationInfo appInfo =
                        appInfoGenerator.generate(pkg, flags, state, userId, ps);
                if (appInfo == null) {
                    appInfo = PackageInfoUtils.generateApplicationInfo(
                            pkg, flags, state, userId, ps);
                    if (appInfo == null) {
                        // In this case, we should avoid calling generateApplicationInfo() for
                        // the same package in subsequent iterations, but appInfo shouldn't be null
                        // here, so we don't bother.
                    continue;
                }
                    if (appInfos == null) {
                        appInfos = new ArrayMap<>(4);
                    }
                    appInfos.put(pkg.getPackageName(), appInfo);
                }
                // At this point, appInfo != null.

                final ProviderInfo info = PackageInfoUtils.generateProviderInfo(
                        pkg, p, flags, state, appInfo, userId, ps);
@@ -355,14 +343,20 @@ public class ComponentResolver {
            if (pkg == null) {
                return null;
            }
            return PackageInfoUtils.generateProviderInfo(pkg, p, flags,
                    ps.readUserState(userId), userId, ps);
            final PackageUserState state = ps.readUserState(userId);
            ApplicationInfo appInfo = PackageInfoUtils.generateApplicationInfo(
                    pkg, flags, state, userId, ps);
            if (appInfo == null) {
                return null;
            }
            return PackageInfoUtils.generateProviderInfo(pkg, p, flags, state, appInfo, userId, ps);
        }
    }

    void querySyncProviders(List<String> outNames, List<ProviderInfo> outInfo, boolean safeMode,
            int userId) {
        synchronized (mLock) {
            CachedApplicationInfoGenerator appInfoGenerator = null;
            for (int i = mProvidersByAuthority.size() - 1; i >= 0; --i) {
                final ParsedProvider p = mProvidersByAuthority.valueAt(i);
                if (!p.isSyncable()) {
@@ -384,9 +378,18 @@ public class ComponentResolver {
                if (safeMode && !pkg.isSystem()) {
                    continue;
                }
                final ProviderInfo info =
                        PackageInfoUtils.generateProviderInfo(pkg, p, 0,
                                ps.readUserState(userId), userId, ps);
                if (appInfoGenerator == null) {
                    appInfoGenerator = new CachedApplicationInfoGenerator();
                }
                final PackageUserState state = ps.readUserState(userId);
                final ApplicationInfo appInfo =
                        appInfoGenerator.generate(pkg, 0, state, userId, ps);
                if (appInfo == null) {
                    continue;
                }

                final ProviderInfo info = PackageInfoUtils.generateProviderInfo(
                        pkg, p, 0, state, appInfo, userId, ps);
                if (info == null) {
                    continue;
                }
@@ -1731,8 +1734,13 @@ public class ComponentResolver {
            if (userState.instantApp && ps.isUpdateAvailable()) {
                return null;
            }
            final ApplicationInfo appInfo = PackageInfoUtils.generateApplicationInfo(
                    pkg, mFlags, userState, userId, ps);
            if (appInfo == null) {
                return null;
            }
            ProviderInfo pi = PackageInfoUtils.generateProviderInfo(pkg, provider, mFlags,
                    userState, userId, ps);
                    userState, appInfo, userId, ps);
            if (pi == null) {
                return null;
            }
+7 −1
Original line number Diff line number Diff line
@@ -5459,7 +5459,13 @@ public class PackageManagerService extends IPackageManager.Stub
                    return null;
                }
                PackageUserState state = ps.readUserState(userId);
                return PackageInfoUtils.generateProviderInfo(pkg, p, flags, state, userId, ps);
                final ApplicationInfo appInfo = PackageInfoUtils.generateApplicationInfo(
                        pkg, flags, state, userId, ps);
                if (appInfo == null) {
                    return null;
                }
                return PackageInfoUtils.generateProviderInfo(
                        pkg, p, flags, state, appInfo, userId, ps);
            }
        }
        return null;
+35 −21
Original line number Diff line number Diff line
@@ -48,7 +48,7 @@ import android.content.pm.parsing.component.ParsedService;
import android.os.UserHandle;
import android.util.ArrayMap;
import android.util.ArraySet;
import android.util.Pair;
import android.util.Slog;

import com.android.internal.util.ArrayUtils;
import com.android.server.pm.PackageSetting;
@@ -61,6 +61,7 @@ import libcore.util.EmptyArray;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.Set;


@@ -72,6 +73,7 @@ import java.util.Set;
 * @hide
 **/
public class PackageInfoUtils {
    private static final String TAG = PackageParser2.TAG;

    /**
     * @param pkgSetting See {@link PackageInfoUtils} for description of pkgSetting usage.
@@ -310,37 +312,24 @@ public class PackageInfoUtils {
        return info;
    }

    /**
     * @param pkgSetting See {@link PackageInfoUtils} for description of pkgSetting usage.
     *
     * @deprecated use {@link #generateProviderInfo(
     * AndroidPackage, ParsedProvider, int, PackageUserState, ApplicationInfo, int, PackageSetting)}
     * instead and pass {@link ApplicationInfo} explicitly to avoid generating duplicate instances
     * of it.
     */
    @Nullable
    @Deprecated
    public static ProviderInfo generateProviderInfo(AndroidPackage pkg, ParsedProvider p,
            @PackageManager.ComponentInfoFlags int flags, PackageUserState state, int userId,
            @Nullable PackageSetting pkgSetting) {
        return generateProviderInfo(pkg, p, flags, state, null, userId, pkgSetting);
    }

    /**
     * @param pkgSetting See {@link PackageInfoUtils} for description of pkgSetting usage.
     */
    @Nullable
    public static ProviderInfo generateProviderInfo(AndroidPackage pkg, ParsedProvider p,
            @PackageManager.ComponentInfoFlags int flags, PackageUserState state,
            @Nullable ApplicationInfo applicationInfo, int userId,
            @NonNull ApplicationInfo applicationInfo, int userId,
            @Nullable PackageSetting pkgSetting) {
        if (p == null) return null;
        if (applicationInfo == null || !pkg.getPackageName().equals(applicationInfo.packageName)) {
            Slog.wtf(TAG, "AppInfo's package name is different. Expected=" + pkg.getPackageName()
                    + " actual=" + (applicationInfo == null ? "(null AppInfo)"
                    : applicationInfo.packageName));
            applicationInfo = generateApplicationInfo(pkg, flags, state, userId, pkgSetting);
        }
        if (!checkUseInstalledOrHidden(pkg, pkgSetting, state, flags)) {
            return null;
        }
        if (applicationInfo == null) {
            applicationInfo = generateApplicationInfo(pkg, flags, state, userId, pkgSetting);
        }
        ProviderInfo info = PackageInfoWithoutStateUtils.generateProviderInfo(pkg, p, flags, state,
                applicationInfo, userId);
        if (info == null) {
@@ -486,4 +475,29 @@ public class PackageInfoUtils {
                | flag(pkg.isSignedWithPlatformKey(), ApplicationInfo.PRIVATE_FLAG_SIGNED_WITH_PLATFORM_KEY);
        // @formatter:on
    }

    /**
     * Wraps {@link PackageInfoUtils#generateApplicationInfo} with a cache.
     */
    public static class CachedApplicationInfoGenerator {
        // Map from a package name to the corresponding app info.
        private ArrayMap<String, ApplicationInfo> mCache = new ArrayMap<>();

        /**
         * {@link PackageInfoUtils#generateApplicationInfo} with a cache.
         */
        @Nullable
        public ApplicationInfo generate(AndroidPackage pkg,
                @PackageManager.ApplicationInfoFlags int flags, PackageUserState state, int userId,
                @Nullable PackageSetting pkgSetting) {
            ApplicationInfo appInfo = mCache.get(pkg.getPackageName());
            if (appInfo != null) {
                return appInfo;
            }
            appInfo = PackageInfoUtils.generateApplicationInfo(
                    pkg, flags, state, userId, pkgSetting);
            mCache.put(pkg.getPackageName(), appInfo);
            return appInfo;
        }
    }
}
+1 −1
Original line number Diff line number Diff line
@@ -42,7 +42,7 @@ import java.io.File;
 */
public class PackageParser2 {

    private static final String TAG = "PackageParser2";
    static final String TAG = "PackageParser2";

    private static final boolean LOG_PARSE_TIMINGS = Build.IS_DEBUGGABLE;
    private static final int LOG_PARSE_TIMINGS_THRESHOLD_MS = 100;