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

Commit 623484d2 authored by Winson Chung's avatar Winson Chung Committed by Android (Google) Code Review
Browse files

Merge "Ensuring that user-specific Recent tasks are removed. (Bug 18036610)" into lmp-mr1-dev

parents 6697322a 04400672
Loading
Loading
Loading
Loading
+5 −4
Original line number Diff line number Diff line
@@ -21,15 +21,16 @@ import android.util.LruCache;
import java.util.HashMap;

/**
 * An LRU cache that support querying the keys as well as values. By using the Task's key, we can
 * prevent holding onto a reference to the Task resource data, while keeping the cache data in
 * memory where necessary.
 * An LRU cache that internally support querying the keys as well as values.  We use this to keep
 * track of the task metadata to determine when to invalidate the cache when tasks have been
 * updated. Generally, this cache will return the last known cache value for the requested task
 * key.
 */
public class KeyStoreLruCache<V> {
    // We keep a set of keys that are associated with the LRU cache, so that we can find out
    // information about the Task that was previously in the cache.
    HashMap<Integer, Task.TaskKey> mTaskKeys = new HashMap<Integer, Task.TaskKey>();
    // The cache implementation
    // The cache implementation, mapping task id -> value
    LruCache<Integer, V> mCache;

    public KeyStoreLruCache(int cacheSize) {
+33 −31
Original line number Diff line number Diff line
@@ -19,6 +19,7 @@ package com.android.systemui.recents.model;
import android.content.ComponentName;
import android.content.Context;
import android.os.Looper;
import android.os.UserHandle;
import com.android.internal.content.PackageMonitor;
import com.android.systemui.recents.misc.SystemServicesProxy;

@@ -26,16 +27,16 @@ import java.util.HashSet;
import java.util.List;

/**
 * The package monitor listens for changes from PackageManager to update the contents of the Recents
 * list.
 * The package monitor listens for changes from PackageManager to update the contents of the
 * Recents list.
 */
public class RecentsPackageMonitor extends PackageMonitor {
    public interface PackageCallbacks {
        public void onComponentRemoved(HashSet<ComponentName> cns);
        public void onPackagesChanged(RecentsPackageMonitor monitor, String packageName,
                                      int userId);
    }

    PackageCallbacks mCb;
    List<Task.TaskKey> mTasks;
    SystemServicesProxy mSystemServicesProxy;

    /** Registers the broadcast receivers with the specified callbacks. */
@@ -43,7 +44,9 @@ public class RecentsPackageMonitor extends PackageMonitor {
        mSystemServicesProxy = new SystemServicesProxy(context);
        mCb = cb;
        try {
            register(context, Looper.getMainLooper(), true);
            // We register for events from all users, but will cross-reference them with
            // packages for the current user and any profiles they have
            register(context, Looper.getMainLooper(), UserHandle.ALL, true);
        } catch (IllegalStateException e) {
            e.printStackTrace();
        }
@@ -59,29 +62,15 @@ public class RecentsPackageMonitor extends PackageMonitor {
        }
        mSystemServicesProxy = null;
        mCb = null;
        mTasks.clear();
    }

    /** Sets the list of tasks to match against package broadcast changes. */
    void setTasks(List<Task.TaskKey> tasks) {
        mTasks = tasks;
    }

    @Override
    public void onPackageRemoved(String packageName, int uid) {
        if (mCb == null) return;

        // Identify all the tasks that should be removed as a result of the package being removed.
        // Using a set to ensure that we callback once per unique component.
        HashSet<ComponentName> componentsToRemove = new HashSet<ComponentName>();
        for (Task.TaskKey t : mTasks) {
            ComponentName cn = t.baseIntent.getComponent();
            if (cn.getPackageName().equals(packageName)) {
                componentsToRemove.add(cn);
            }
        }
        // Notify our callbacks that the components no longer exist
        mCb.onComponentRemoved(componentsToRemove);
        // Notify callbacks that a package has changed
        final int eventUserId = getChangingUserId();
        mCb.onPackagesChanged(this, packageName, eventUserId);
    }

    @Override
@@ -94,25 +83,38 @@ public class RecentsPackageMonitor extends PackageMonitor {
    public void onPackageModified(String packageName) {
        if (mCb == null) return;

        // Notify callbacks that a package has changed
        final int eventUserId = getChangingUserId();
        mCb.onPackagesChanged(this, packageName, eventUserId);
    }

    /**
     * Computes the components that have been removed as a result of a change in the specified
     * package.
     */
    public HashSet<ComponentName> computeComponentsRemoved(List<Task.TaskKey> taskKeys,
            String packageName, int userId) {
        // Identify all the tasks that should be removed as a result of the package being removed.
        // Using a set to ensure that we callback once per unique component.
        HashSet<ComponentName> componentsKnownToExist = new HashSet<ComponentName>();
        HashSet<ComponentName> componentsToRemove = new HashSet<ComponentName>();
        for (Task.TaskKey t : mTasks) {
        HashSet<ComponentName> existingComponents = new HashSet<ComponentName>();
        HashSet<ComponentName> removedComponents = new HashSet<ComponentName>();
        for (Task.TaskKey t : taskKeys) {
            // Skip if this doesn't apply to the current user
            if (t.userId != userId) continue;

            ComponentName cn = t.baseIntent.getComponent();
            if (cn.getPackageName().equals(packageName)) {
                if (componentsKnownToExist.contains(cn)) {
                if (existingComponents.contains(cn)) {
                    // If we know that the component still exists in the package, then skip
                    continue;
                }
                if (mSystemServicesProxy.getActivityInfo(cn) != null) {
                    componentsKnownToExist.add(cn);
                if (mSystemServicesProxy.getActivityInfo(cn, userId) != null) {
                    existingComponents.add(cn);
                } else {
                    componentsToRemove.add(cn);
                    removedComponents.add(cn);
                }
            }
        }
        // Notify our callbacks that the components no longer exist
        mCb.onComponentRemoved(componentsToRemove);
        return removedComponents;
    }
}
+0 −4
Original line number Diff line number Diff line
@@ -420,10 +420,6 @@ public class RecentsTaskLoader {
        // Start the task loader and add all the tasks we need to load
        mLoader.start(context);
        mLoadQueue.addTasks(tasksToLoad);

        // Update the package monitor with the list of packages to listen for
        mPackageMonitor.setTasks(taskKeys);

        return root;
    }

+1 −1
Original line number Diff line number Diff line
@@ -129,7 +129,7 @@ public class Task {
    TaskCallbacks mCb;

    public Task() {
        // Only used by RecentsService for task rect calculations.
        // Do nothing
    }

    public Task(TaskKey key, boolean isActive, int taskAffiliation, int taskAffiliationColor,
+11 −0
Original line number Diff line number Diff line
@@ -255,6 +255,17 @@ public class TaskStack {
        return mTaskList.getTasks().get(mTaskList.size() - 1);
    }

    /** Gets the task keys */
    public ArrayList<Task.TaskKey> getTaskKeys() {
        ArrayList<Task.TaskKey> taskKeys = new ArrayList<Task.TaskKey>();
        ArrayList<Task> tasks = mTaskList.getTasks();
        int taskCount = tasks.size();
        for (int i = 0; i < taskCount; i++) {
            taskKeys.add(tasks.get(i).key);
        }
        return taskKeys;
    }

    /** Gets the tasks */
    public ArrayList<Task> getTasks() {
        return mTaskList.getTasks();
Loading