diff --git a/AndroidManifest.xml b/AndroidManifest.xml
index e3a7e96..d1b09cb 100644
--- a/AndroidManifest.xml
+++ b/AndroidManifest.xml
@@ -4,6 +4,9 @@
         coreApp="true"
         android:sharedUserId="android.uid.system">
 
+    <uses-sdk
+        android:minSdkVersion="21" />
+
     <original-package android:name="com.android.settings" />
 
     <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
diff --git a/src/com/android/settings/Utils.java b/src/com/android/settings/Utils.java
index b7f62a3..21a5019 100644
--- a/src/com/android/settings/Utils.java
+++ b/src/com/android/settings/Utils.java
@@ -16,8 +16,6 @@
 
 package com.android.settings;
 
-import static android.content.Intent.EXTRA_USER;
-
 import android.annotation.Nullable;
 import android.app.ActivityManager;
 import android.app.ActivityManagerNative;
@@ -70,8 +68,6 @@
 import android.provider.ContactsContract.Profile;
 import android.provider.ContactsContract.RawContacts;
 import android.service.persistentdata.PersistentDataBlockManager;
-import android.telephony.SubscriptionInfo;
-import android.telephony.SubscriptionManager;
 import android.telephony.TelephonyManager;
 import android.text.TextUtils;
 import android.util.Log;
@@ -87,20 +83,21 @@
 
 import com.android.internal.util.UserIcons;
 import com.android.settings.UserAdapter.UserDetails;
-import com.android.settings.applications.ApplicationsState;
 import com.android.settings.dashboard.DashboardTile;
 import com.android.settings.drawable.CircleFramedDrawable;
+import com.android.settingslib.applications.ApplicationsState;
 
 import java.io.IOException;
 import java.io.InputStream;
 import java.net.InetAddress;
 import java.text.NumberFormat;
 import java.util.ArrayList;
-import java.util.Collections;
 import java.util.Iterator;
 import java.util.List;
 import java.util.Locale;
 
+import static android.content.Intent.EXTRA_USER;
+
 public final class Utils {
     private static final String TAG = "Settings";
 
diff --git a/src/com/android/settings/applications/AdvancedAppSettings.java b/src/com/android/settings/applications/AdvancedAppSettings.java
index f407cb1..c2966fe 100644
--- a/src/com/android/settings/applications/AdvancedAppSettings.java
+++ b/src/com/android/settings/applications/AdvancedAppSettings.java
@@ -23,10 +23,11 @@
 import com.android.internal.logging.MetricsLogger;
 import com.android.settings.R;
 import com.android.settings.SettingsPreferenceFragment;
-import com.android.settings.applications.ApplicationsState.AppEntry;
-import com.android.settings.applications.ApplicationsState.Session;
 import com.android.settings.applications.PermissionsSummaryHelper.PermissionsResultCallback;
 import com.android.settings.fuelgauge.PowerWhitelistBackend;
+import com.android.settingslib.applications.ApplicationsState;
+import com.android.settingslib.applications.ApplicationsState.AppEntry;
+import com.android.settingslib.applications.ApplicationsState.Session;
 
 import java.util.ArrayList;
 
diff --git a/src/com/android/settings/applications/AppInfoBase.java b/src/com/android/settings/applications/AppInfoBase.java
index 6dbeefd..ff618c2 100644
--- a/src/com/android/settings/applications/AppInfoBase.java
+++ b/src/com/android/settings/applications/AppInfoBase.java
@@ -38,7 +38,8 @@
 import com.android.settings.SettingsActivity;
 import com.android.settings.SettingsPreferenceFragment;
 import com.android.settings.Utils;
-import com.android.settings.applications.ApplicationsState.AppEntry;
+import com.android.settingslib.applications.ApplicationsState;
+import com.android.settingslib.applications.ApplicationsState.AppEntry;
 
 import java.util.ArrayList;
 
diff --git a/src/com/android/settings/applications/AppPermissionSettings.java b/src/com/android/settings/applications/AppPermissionSettings.java
deleted file mode 100644
index 16757d9..0000000
--- a/src/com/android/settings/applications/AppPermissionSettings.java
+++ /dev/null
@@ -1,236 +0,0 @@
-/*
- * Copyright (C) 2015 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.settings.applications;
-
-import android.app.AlertDialog;
-import android.content.Context;
-import android.content.pm.ApplicationInfo;
-import android.content.pm.PackageManager;
-import android.content.res.Resources;
-import android.os.Build;
-import android.os.Bundle;
-import android.os.RemoteException;
-import android.os.ServiceManager;
-import android.util.Log;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.AdapterView;
-import android.widget.AppSecurityPermissions;
-import android.widget.ArrayAdapter;
-import android.widget.LinearLayout;
-import android.widget.Spinner;
-import android.widget.TextView;
-
-import com.android.internal.logging.MetricsLogger;
-import com.android.internal.telephony.ISms;
-import com.android.internal.telephony.SmsUsageMonitor;
-import com.android.settings.R;
-import com.android.settings.Utils;
-import com.android.settings.applications.ApplicationsState.AppEntry;
-
-import java.util.ArrayList;
-
-public class AppPermissionSettings extends AppInfoWithHeader {
-
-    private ISms mSmsManager;
-    private View mRootView;
-
-    @Override
-    public void onCreate(Bundle savedInstanceState) {
-        super.onCreate(savedInstanceState);
-        mSmsManager = ISms.Stub.asInterface(ServiceManager.getService("isms"));
-    }
-
-    @Override
-    public View onCreateView(LayoutInflater inflater, ViewGroup container,
-            Bundle savedInstanceState) {
-        final View view = inflater.inflate(R.layout.permission_settings, container, false);
-
-        final ViewGroup allDetails = (ViewGroup) view.findViewById(R.id.all_details);
-        Utils.forceCustomPadding(allDetails, true /* additive padding */);
-
-        mRootView = view;
-        return view;
-    }
-
-    @Override
-    protected boolean refreshUi() {
-        retrieveAppEntry();
-        // Security permissions section
-        LinearLayout permsView = (LinearLayout) mRootView.findViewById(R.id.permissions_section);
-        AppSecurityPermissions asp = new AppSecurityPermissions(getActivity(), mPackageName);
-        int premiumSmsPermission = getPremiumSmsPermission(mPackageName);
-        // Premium SMS permission implies the app also has SEND_SMS permission, so the original
-        // application permissions list doesn't have to be shown/hidden separately. The premium
-        // SMS subsection should only be visible if the app has tried to send to a premium SMS.
-        if (asp.getPermissionCount() > 0
-                || premiumSmsPermission != SmsUsageMonitor.PREMIUM_SMS_PERMISSION_UNKNOWN) {
-            permsView.setVisibility(View.VISIBLE);
-        } else {
-            permsView.setVisibility(View.GONE);
-        }
-        // Premium SMS permission subsection
-        TextView securityBillingDesc = (TextView) permsView.findViewById(
-                R.id.security_settings_billing_desc);
-        LinearLayout securityBillingList = (LinearLayout) permsView.findViewById(
-                R.id.security_settings_billing_list);
-        if (premiumSmsPermission != SmsUsageMonitor.PREMIUM_SMS_PERMISSION_UNKNOWN) {
-            // Show the premium SMS permission selector
-            securityBillingDesc.setVisibility(View.VISIBLE);
-            securityBillingList.setVisibility(View.VISIBLE);
-            Spinner spinner = (Spinner) permsView.findViewById(
-                    R.id.security_settings_premium_sms_list);
-            ArrayAdapter<CharSequence> adapter = ArrayAdapter.createFromResource(getActivity(),
-                    R.array.security_settings_premium_sms_values,
-                    android.R.layout.simple_spinner_item);
-            adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
-            spinner.setAdapter(adapter);
-            // List items are in the same order as SmsUsageMonitor constants, offset by 1.
-            spinner.setSelection(premiumSmsPermission - 1);
-            spinner.setOnItemSelectedListener(new PremiumSmsSelectionListener(
-                    mPackageName, mSmsManager));
-        } else {
-            // Hide the premium SMS permission selector
-            securityBillingDesc.setVisibility(View.GONE);
-            securityBillingList.setVisibility(View.GONE);
-        }
-        // App permissions subsection
-        if (asp.getPermissionCount() > 0) {
-            // Make the security sections header visible
-            LinearLayout securityList = (LinearLayout) permsView.findViewById(
-                    R.id.security_settings_list);
-            securityList.removeAllViews();
-            securityList.addView(asp.getPermissionsViewWithRevokeButtons());
-            // If this app is running under a shared user ID with other apps,
-            // update the description to explain this.
-            String[] packages = mPm.getPackagesForUid(mPackageInfo.applicationInfo.uid);
-            if (packages != null && packages.length > 1) {
-                ArrayList<CharSequence> pnames = new ArrayList<CharSequence>();
-                for (int i=0; i<packages.length; i++) {
-                    String pkg = packages[i];
-                    if (mPackageInfo.packageName.equals(pkg)) {
-                        continue;
-                    }
-                    try {
-                        ApplicationInfo ainfo = mPm.getApplicationInfo(pkg, 0);
-                        pnames.add(ainfo.loadLabel(mPm));
-                    } catch (PackageManager.NameNotFoundException e) {
-                    }
-                }
-                final int N = pnames.size();
-                if (N > 0) {
-                    final Resources res = getActivity().getResources();
-                    String appListStr;
-                    if (N == 1) {
-                        appListStr = pnames.get(0).toString();
-                    } else if (N == 2) {
-                        appListStr = res.getString(R.string.join_two_items, pnames.get(0),
-                                pnames.get(1));
-                    } else {
-                        appListStr = pnames.get(N-2).toString();
-                        for (int i=N-3; i>=0; i--) {
-                            appListStr = res.getString(i == 0 ? R.string.join_many_items_first
-                                    : R.string.join_many_items_middle, pnames.get(i), appListStr);
-                        }
-                        appListStr = res.getString(R.string.join_many_items_last,
-                                appListStr, pnames.get(N-1));
-                    }
-                    TextView descr = (TextView) mRootView.findViewById(
-                            R.id.security_settings_desc);
-                    descr.setText(res.getString(R.string.security_settings_desc_multi,
-                            mPackageInfo.applicationInfo.loadLabel(mPm), appListStr));
-                }
-            }
-        }
-        return true;
-    }
-
-    private int getPremiumSmsPermission(String packageName) {
-        try {
-            if (mSmsManager != null) {
-                return mSmsManager.getPremiumSmsPermission(packageName);
-            }
-        } catch (RemoteException ex) {
-            // ignored
-        }
-        return SmsUsageMonitor.PREMIUM_SMS_PERMISSION_UNKNOWN;
-    }
-
-    @Override
-    protected AlertDialog createDialog(int id, int errorCode) {
-        // No dialogs for Permissions screen.
-        return null;
-    }
-
-    public static CharSequence getSummary(AppEntry appEntry, Context context) {
-        if (appEntry.info.targetSdkVersion > Build.VERSION_CODES.LOLLIPOP_MR1) {
-            AppPermissions appPerms = new AppPermissions(context, appEntry.info.packageName);
-            int count = appPerms.getPermissionCount();
-            int grantedCount = appPerms.getGrantedPermissionsCount();
-            return context.getResources().getQuantityString(R.plurals.runtime_permissions_summary,
-                    count, grantedCount, count);
-        }
-        AppSecurityPermissions asp = new AppSecurityPermissions(context,
-                appEntry.info.packageName);
-        int count = asp.getPermissionCount();
-        return context.getResources().getQuantityString(R.plurals.permissions_summary,
-                count, count);
-    }
-
-    @Override
-    protected int getMetricsCategory() {
-        return MetricsLogger.APPLICATIONS_APP_PERMISSION;
-    }
-
-    private static class PremiumSmsSelectionListener implements AdapterView.OnItemSelectedListener {
-        private final String mPackageName;
-        private final ISms mSmsManager;
-
-        PremiumSmsSelectionListener(String packageName, ISms smsManager) {
-            mPackageName = packageName;
-            mSmsManager = smsManager;
-        }
-
-        @Override
-        public void onItemSelected(AdapterView<?> parent, View view, int position,
-                long id) {
-            if (position >= 0 && position < 3) {
-                if (localLOGV) Log.d(TAG, "Selected premium SMS policy " + position);
-                setPremiumSmsPermission(mPackageName, (position + 1));
-            } else {
-                Log.e(TAG, "Error: unknown premium SMS policy " + position);
-            }
-        }
-
-        @Override
-        public void onNothingSelected(AdapterView<?> parent) {
-            // Ignored
-        }
-
-        private void setPremiumSmsPermission(String packageName, int permission) {
-            try {
-                if (mSmsManager != null) {
-                    mSmsManager.setPremiumSmsPermission(packageName, permission);
-                }
-            } catch (RemoteException ex) {
-                // ignored
-            }
-        }
-    }
-
-}
\ No newline at end of file
diff --git a/src/com/android/settings/applications/AppStateBaseBridge.java b/src/com/android/settings/applications/AppStateBaseBridge.java
index 04eb77b..1e04e13 100644
--- a/src/com/android/settings/applications/AppStateBaseBridge.java
+++ b/src/com/android/settings/applications/AppStateBaseBridge.java
@@ -19,8 +19,9 @@
 import android.os.Looper;
 import android.os.Message;
 
-import com.android.settings.applications.ApplicationsState.AppEntry;
-import com.android.settings.applications.ApplicationsState.Session;
+import com.android.settingslib.applications.ApplicationsState;
+import com.android.settingslib.applications.ApplicationsState.AppEntry;
+import com.android.settingslib.applications.ApplicationsState.Session;
 
 import java.util.ArrayList;
 
diff --git a/src/com/android/settings/applications/AppStateNotificationBridge.java b/src/com/android/settings/applications/AppStateNotificationBridge.java
index 4ac8650..5a8e811 100644
--- a/src/com/android/settings/applications/AppStateNotificationBridge.java
+++ b/src/com/android/settings/applications/AppStateNotificationBridge.java
@@ -17,10 +17,11 @@
 
 import android.content.pm.PackageManager;
 
-import com.android.settings.applications.ApplicationsState.AppEntry;
-import com.android.settings.applications.ApplicationsState.AppFilter;
 import com.android.settings.notification.NotificationBackend;
 import com.android.settings.notification.NotificationBackend.AppRow;
+import com.android.settingslib.applications.ApplicationsState;
+import com.android.settingslib.applications.ApplicationsState.AppEntry;
+import com.android.settingslib.applications.ApplicationsState.AppFilter;
 
 import java.util.ArrayList;
 
diff --git a/src/com/android/settings/applications/AppStatePowerBridge.java b/src/com/android/settings/applications/AppStatePowerBridge.java
index 40163cb..3b1707f 100644
--- a/src/com/android/settings/applications/AppStatePowerBridge.java
+++ b/src/com/android/settings/applications/AppStatePowerBridge.java
@@ -15,9 +15,10 @@
  */
 package com.android.settings.applications;
 
-import com.android.settings.applications.ApplicationsState.AppEntry;
-import com.android.settings.applications.ApplicationsState.AppFilter;
 import com.android.settings.fuelgauge.PowerWhitelistBackend;
+import com.android.settingslib.applications.ApplicationsState;
+import com.android.settingslib.applications.ApplicationsState.AppEntry;
+import com.android.settingslib.applications.ApplicationsState.AppFilter;
 
 import java.util.ArrayList;
 
diff --git a/src/com/android/settings/applications/AppStateUsageBridge.java b/src/com/android/settings/applications/AppStateUsageBridge.java
index 22f19b2..c06492c 100644
--- a/src/com/android/settings/applications/AppStateUsageBridge.java
+++ b/src/com/android/settings/applications/AppStateUsageBridge.java
@@ -30,8 +30,9 @@
 import android.util.Log;
 import android.util.SparseArray;
 
-import com.android.settings.applications.ApplicationsState.AppEntry;
-import com.android.settings.applications.ApplicationsState.AppFilter;
+import com.android.settingslib.applications.ApplicationsState;
+import com.android.settingslib.applications.ApplicationsState.AppEntry;
+import com.android.settingslib.applications.ApplicationsState.AppFilter;
 
 import java.util.List;
 
diff --git a/src/com/android/settings/applications/AppStorageSettings.java b/src/com/android/settings/applications/AppStorageSettings.java
index fe68cbc4..808f738 100644
--- a/src/com/android/settings/applications/AppStorageSettings.java
+++ b/src/com/android/settings/applications/AppStorageSettings.java
@@ -36,15 +36,15 @@
 import android.view.View;
 import android.view.View.OnClickListener;
 import android.widget.Button;
-import android.widget.TextView;
 
 import com.android.internal.logging.MetricsLogger;
 import com.android.settings.DropDownPreference;
 import com.android.settings.R;
 import com.android.settings.Utils;
-import com.android.settings.applications.ApplicationsState.AppEntry;
-import com.android.settings.applications.ApplicationsState.Callbacks;
 import com.android.settings.deviceinfo.StorageWizardMoveConfirm;
+import com.android.settingslib.applications.ApplicationsState;
+import com.android.settingslib.applications.ApplicationsState.AppEntry;
+import com.android.settingslib.applications.ApplicationsState.Callbacks;
 
 import java.util.Collections;
 import java.util.List;
diff --git a/src/com/android/settings/applications/AppViewHolder.java b/src/com/android/settings/applications/AppViewHolder.java
index 34c9952..f58cf06 100644
--- a/src/com/android/settings/applications/AppViewHolder.java
+++ b/src/com/android/settings/applications/AppViewHolder.java
@@ -16,8 +16,6 @@
 
 package com.android.settings.applications;
 
-import com.android.settings.R;
-
 import android.util.Log;
 import android.view.LayoutInflater;
 import android.view.View;
@@ -25,6 +23,9 @@
 import android.widget.ImageView;
 import android.widget.TextView;
 
+import com.android.settings.R;
+import com.android.settingslib.applications.ApplicationsState;
+
 // View Holder used when displaying views
 public class AppViewHolder {
     public ApplicationsState.AppEntry entry;
diff --git a/src/com/android/settings/applications/ApplicationsState.java b/src/com/android/settings/applications/ApplicationsState.java
deleted file mode 100644
index 055e415..0000000
--- a/src/com/android/settings/applications/ApplicationsState.java
+++ /dev/null
@@ -1,1341 +0,0 @@
-/*
- * Copyright (C) 2015 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.settings.applications;
-
-import android.app.ActivityManager;
-import android.app.AppGlobals;
-import android.app.Application;
-import android.content.BroadcastReceiver;
-import android.content.Context;
-import android.content.Intent;
-import android.content.IntentFilter;
-import android.content.pm.ApplicationInfo;
-import android.content.pm.IPackageManager;
-import android.content.pm.IPackageStatsObserver;
-import android.content.pm.PackageManager;
-import android.content.pm.PackageStats;
-import android.content.pm.ParceledListSlice;
-import android.content.pm.ResolveInfo;
-import android.graphics.drawable.Drawable;
-import android.net.Uri;
-import android.os.Handler;
-import android.os.HandlerThread;
-import android.os.Looper;
-import android.os.Message;
-import android.os.Process;
-import android.os.RemoteException;
-import android.os.SystemClock;
-import android.os.UserHandle;
-import android.os.UserManager;
-import android.text.format.Formatter;
-import android.util.Log;
-import android.util.SparseArray;
-
-import java.io.File;
-import java.text.Collator;
-import java.text.Normalizer;
-import java.text.Normalizer.Form;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.Comparator;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Objects;
-import java.util.regex.Pattern;
-
-/**
- * Keeps track of information about all installed applications, lazy-loading
- * as needed.
- */
-public class ApplicationsState {
-    static final String TAG = "ApplicationsState";
-    static final boolean DEBUG = false;
-    static final boolean DEBUG_LOCKING = false;
-
-    public static interface Callbacks {
-        public void onRunningStateChanged(boolean running);
-        public void onPackageListChanged();
-        public void onRebuildComplete(ArrayList<AppEntry> apps);
-        public void onPackageIconChanged();
-        public void onPackageSizeChanged(String packageName);
-        public void onAllSizesComputed();
-        public void onLauncherInfoChanged();
-        public void onLoadEntriesCompleted();
-    }
-
-    public static interface AppFilter {
-        public void init();
-        public boolean filterApp(AppEntry info);
-    }
-
-    static final int SIZE_UNKNOWN = -1;
-    static final int SIZE_INVALID = -2;
-
-    static final Pattern REMOVE_DIACRITICALS_PATTERN
-            = Pattern.compile("\\p{InCombiningDiacriticalMarks}+");
-
-    public static String normalize(String str) {
-        String tmp = Normalizer.normalize(str, Form.NFD);
-        return REMOVE_DIACRITICALS_PATTERN.matcher(tmp)
-                .replaceAll("").toLowerCase();
-    }
-
-    public static class SizeInfo {
-        long cacheSize;
-        long codeSize;
-        long dataSize;
-        long externalCodeSize;
-        long externalDataSize;
-
-        // This is the part of externalDataSize that is in the cache
-        // section of external storage.  Note that we don't just combine
-        // this with cacheSize because currently the platform can't
-        // automatically trim this data when needed, so it is something
-        // the user may need to manage.  The externalDataSize also includes
-        // this value, since what this is here is really the part of
-        // externalDataSize that we can just consider to be "cache" files
-        // for purposes of cleaning them up in the app details UI.
-        long externalCacheSize;
-    }
-
-    public static class AppEntry extends SizeInfo {
-        final File apkFile;
-        final long id;
-        String label;
-        long size;
-        long internalSize;
-        long externalSize;
-
-        boolean mounted;
-
-        boolean hasLauncherEntry;
-
-        String getNormalizedLabel() {
-            if (normalizedLabel != null) {
-                return normalizedLabel;
-            }
-            normalizedLabel = normalize(label);
-            return normalizedLabel;
-        }
-
-        // Need to synchronize on 'this' for the following.
-        public ApplicationInfo info;
-        Drawable icon;
-        String sizeStr;
-        String internalSizeStr;
-        String externalSizeStr;
-        boolean sizeStale;
-        long sizeLoadStart;
-
-        String normalizedLabel;
-
-        // A location where extra info can be placed to be used by custom filters.
-        Object extraInfo;
-
-        AppEntry(Context context, ApplicationInfo info, long id) {
-            apkFile = new File(info.sourceDir);
-            this.id = id;
-            this.info = info;
-            this.size = SIZE_UNKNOWN;
-            this.sizeStale = true;
-            ensureLabel(context);
-        }
-
-        void ensureLabel(Context context) {
-            if (this.label == null || !this.mounted) {
-                if (!this.apkFile.exists()) {
-                    this.mounted = false;
-                    this.label = info.packageName;
-                } else {
-                    this.mounted = true;
-                    CharSequence label = info.loadLabel(context.getPackageManager());
-                    this.label = label != null ? label.toString() : info.packageName;
-                }
-            }
-        }
-
-        boolean ensureIconLocked(Context context, PackageManager pm) {
-            if (this.icon == null) {
-                if (this.apkFile.exists()) {
-                    this.icon = getBadgedIcon(pm);
-                    return true;
-                } else {
-                    this.mounted = false;
-                    this.icon = context.getDrawable(
-                            com.android.internal.R.drawable.sym_app_on_sd_unavailable_icon);
-                }
-            } else if (!this.mounted) {
-                // If the app wasn't mounted but is now mounted, reload
-                // its icon.
-                if (this.apkFile.exists()) {
-                    this.mounted = true;
-                    this.icon = getBadgedIcon(pm);
-                    return true;
-                }
-            }
-            return false;
-        }
-
-        private Drawable getBadgedIcon(PackageManager pm) {
-            // Do badging ourself so that it comes from the user of the app not the current user.
-            return pm.getUserBadgedIcon(pm.loadUnbadgedItemIcon(info, info),
-                    new UserHandle(UserHandle.getUserId(info.uid)));
-        }
-    }
-
-    public static final Comparator<AppEntry> ALPHA_COMPARATOR = new Comparator<AppEntry>() {
-        private final Collator sCollator = Collator.getInstance();
-        @Override
-        public int compare(AppEntry object1, AppEntry object2) {
-            return sCollator.compare(object1.label, object2.label);
-        }
-    };
-
-    public static final Comparator<AppEntry> SIZE_COMPARATOR
-            = new Comparator<AppEntry>() {
-        private final Collator sCollator = Collator.getInstance();
-        @Override
-        public int compare(AppEntry object1, AppEntry object2) {
-            if (object1.size < object2.size) return 1;
-            if (object1.size > object2.size) return -1;
-            return sCollator.compare(object1.label, object2.label);
-        }
-    };
-
-    public static final Comparator<AppEntry> INTERNAL_SIZE_COMPARATOR
-            = new Comparator<AppEntry>() {
-        private final Collator sCollator = Collator.getInstance();
-        @Override
-        public int compare(AppEntry object1, AppEntry object2) {
-            if (object1.internalSize < object2.internalSize) return 1;
-            if (object1.internalSize > object2.internalSize) return -1;
-            return sCollator.compare(object1.label, object2.label);
-        }
-    };
-
-    public static final Comparator<AppEntry> EXTERNAL_SIZE_COMPARATOR
-            = new Comparator<AppEntry>() {
-        private final Collator sCollator = Collator.getInstance();
-        @Override
-        public int compare(AppEntry object1, AppEntry object2) {
-            if (object1.externalSize < object2.externalSize) return 1;
-            if (object1.externalSize > object2.externalSize) return -1;
-            return sCollator.compare(object1.label, object2.label);
-        }
-    };
-
-    public static final AppFilter FILTER_PERSONAL = new AppFilter() {
-        private int mCurrentUser;
-
-        public void init() {
-            mCurrentUser = ActivityManager.getCurrentUser();
-        }
-
-        @Override
-        public boolean filterApp(AppEntry entry) {
-            return UserHandle.getUserId(entry.info.uid) == mCurrentUser;
-        }
-    };
-
-    public static final AppFilter FILTER_WORK = new AppFilter() {
-        private int mCurrentUser;
-
-        public void init() {
-            mCurrentUser = ActivityManager.getCurrentUser();
-        }
-
-        @Override
-        public boolean filterApp(AppEntry entry) {
-            return UserHandle.getUserId(entry.info.uid) != mCurrentUser;
-        }
-    };
-
-    public static final AppFilter FILTER_DOWNLOADED_AND_LAUNCHER = new AppFilter() {
-        public void init() {
-        }
-
-        @Override
-        public boolean filterApp(AppEntry entry) {
-            if ((entry.info.flags & ApplicationInfo.FLAG_UPDATED_SYSTEM_APP) != 0) {
-                return true;
-            } else if ((entry.info.flags & ApplicationInfo.FLAG_SYSTEM) == 0) {
-                return true;
-            } else if (entry.hasLauncherEntry) {
-                return true;
-            }
-            return false;
-        }
-    };
-
-    public static final AppFilter FILTER_THIRD_PARTY = new AppFilter() {
-        public void init() {
-        }
-
-        @Override
-        public boolean filterApp(AppEntry entry) {
-            if ((entry.info.flags & ApplicationInfo.FLAG_UPDATED_SYSTEM_APP) != 0) {
-                return true;
-            } else if ((entry.info.flags & ApplicationInfo.FLAG_SYSTEM) == 0) {
-                return true;
-            }
-            return false;
-        }
-    };
-
-    public static final AppFilter FILTER_DISABLED = new AppFilter() {
-        public void init() {
-        }
-
-        @Override
-        public boolean filterApp(AppEntry entry) {
-            return !entry.info.enabled;
-        }
-    };
-
-    public static final AppFilter FILTER_ALL_ENABLED = new AppFilter() {
-        public void init() {
-        }
-
-        @Override
-        public boolean filterApp(AppEntry entry) {
-            return entry.info.enabled;
-        }
-    };
-
-    public static final AppFilter FILTER_EVERYTHING = new AppFilter() {
-        public void init() {
-        }
-
-        @Override
-        public boolean filterApp(AppEntry entry) {
-            return true;
-        }
-    };
-
-    public static final AppFilter FILTER_WITH_DOMAIN_URLS = new AppFilter() {
-        public void init() {
-        }
-
-        @Override
-        public boolean filterApp(AppEntry entry) {
-            return (entry.info.privateFlags & ApplicationInfo.PRIVATE_FLAG_HAS_DOMAIN_URLS) != 0;
-        }
-    };
-
-    public static class VolumeFilter implements AppFilter {
-        private final String mVolumeUuid;
-
-        public VolumeFilter(String volumeUuid) {
-            mVolumeUuid = volumeUuid;
-        }
-
-        @Override
-        public void init() {
-        }
-
-        @Override
-        public boolean filterApp(AppEntry info) {
-            return Objects.equals(info.info.volumeUuid, mVolumeUuid);
-        }
-    }
-
-    public static class CompoundFilter implements AppFilter {
-        private final AppFilter mFirstFilter;
-        private final AppFilter mSecondFilter;
-
-        public CompoundFilter(AppFilter first, AppFilter second) {
-            mFirstFilter = first;
-            mSecondFilter = second;
-        }
-
-        @Override
-        public void init() {
-            mFirstFilter.init();
-            mSecondFilter.init();
-        }
-
-        @Override
-        public boolean filterApp(AppEntry info) {
-            return mFirstFilter.filterApp(info) && mSecondFilter.filterApp(info);
-        }
-    }
-
-    final Context mContext;
-    final PackageManager mPm;
-    final IPackageManager mIpm;
-    final UserManager mUm;
-    final int mOwnerRetrieveFlags;
-    final int mRetrieveFlags;
-    PackageIntentReceiver mPackageIntentReceiver;
-
-    boolean mResumed;
-    boolean mHaveDisabledApps;
-
-    // Information about all applications.  Synchronize on mEntriesMap
-    // to protect access to these.
-    final ArrayList<Session> mSessions = new ArrayList<Session>();
-    final ArrayList<Session> mRebuildingSessions = new ArrayList<Session>();
-    final InterestingConfigChanges mInterestingConfigChanges = new InterestingConfigChanges();
-    // Map: userid => (Map: package name => AppEntry)
-    final SparseArray<HashMap<String, AppEntry>> mEntriesMap =
-            new SparseArray<HashMap<String, AppEntry>>();
-    final ArrayList<AppEntry> mAppEntries = new ArrayList<AppEntry>();
-    List<ApplicationInfo> mApplications = new ArrayList<ApplicationInfo>();
-    long mCurId = 1;
-    String mCurComputingSizePkg;
-    int mCurComputingSizeUserId;
-    boolean mSessionsChanged;
-
-    // Temporary for dispatching session callbacks.  Only touched by main thread.
-    final ArrayList<Session> mActiveSessions = new ArrayList<Session>();
-
-    /**
-     * Receives notifications when applications are added/removed.
-     */
-    private class PackageIntentReceiver extends BroadcastReceiver {
-         void registerReceiver() {
-             IntentFilter filter = new IntentFilter(Intent.ACTION_PACKAGE_ADDED);
-             filter.addAction(Intent.ACTION_PACKAGE_REMOVED);
-             filter.addAction(Intent.ACTION_PACKAGE_CHANGED);
-             filter.addDataScheme("package");
-             mContext.registerReceiver(this, filter);
-             // Register for events related to sdcard installation.
-             IntentFilter sdFilter = new IntentFilter();
-             sdFilter.addAction(Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE);
-             sdFilter.addAction(Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE);
-             mContext.registerReceiver(this, sdFilter);
-             // Register for events related to user creation/deletion.
-             IntentFilter userFilter = new IntentFilter();
-             userFilter.addAction(Intent.ACTION_USER_ADDED);
-             userFilter.addAction(Intent.ACTION_USER_REMOVED);
-             mContext.registerReceiver(this, userFilter);
-         }
-         void unregisterReceiver() {
-             mContext.unregisterReceiver(this);
-         }
-         @Override
-         public void onReceive(Context context, Intent intent) {
-             String actionStr = intent.getAction();
-             if (Intent.ACTION_PACKAGE_ADDED.equals(actionStr)) {
-                 Uri data = intent.getData();
-                 String pkgName = data.getEncodedSchemeSpecificPart();
-                 for (int i = 0; i < mEntriesMap.size(); i++) {
-                     addPackage(pkgName, mEntriesMap.keyAt(i));
-                 }
-             } else if (Intent.ACTION_PACKAGE_REMOVED.equals(actionStr)) {
-                 Uri data = intent.getData();
-                 String pkgName = data.getEncodedSchemeSpecificPart();
-                 for (int i = 0; i < mEntriesMap.size(); i++) {
-                     removePackage(pkgName, mEntriesMap.keyAt(i));
-                 }
-             } else if (Intent.ACTION_PACKAGE_CHANGED.equals(actionStr)) {
-                 Uri data = intent.getData();
-                 String pkgName = data.getEncodedSchemeSpecificPart();
-                 for (int i = 0; i < mEntriesMap.size(); i++) {
-                     invalidatePackage(pkgName, mEntriesMap.keyAt(i));
-                 }
-             } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(actionStr) ||
-                     Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(actionStr)) {
-                 // When applications become available or unavailable (perhaps because
-                 // the SD card was inserted or ejected) we need to refresh the
-                 // AppInfo with new label, icon and size information as appropriate
-                 // given the newfound (un)availability of the application.
-                 // A simple way to do that is to treat the refresh as a package
-                 // removal followed by a package addition.
-                 String pkgList[] = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST);
-                 if (pkgList == null || pkgList.length == 0) {
-                     // Ignore
-                     return;
-                 }
-                 boolean avail = Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(actionStr);
-                 if (avail) {
-                     for (String pkgName : pkgList) {
-                         for (int i = 0; i < mEntriesMap.size(); i++) {
-                             invalidatePackage(pkgName, mEntriesMap.keyAt(i));
-                         }
-                     }
-                 }
-             } else if (Intent.ACTION_USER_ADDED.equals(actionStr)) {
-                 addUser(intent.getIntExtra(Intent.EXTRA_USER_HANDLE, UserHandle.USER_NULL));
-             } else if (Intent.ACTION_USER_REMOVED.equals(actionStr)) {
-                 removeUser(intent.getIntExtra(Intent.EXTRA_USER_HANDLE, UserHandle.USER_NULL));
-             }
-         }
-    }
-
-    void rebuildActiveSessions() {
-        synchronized (mEntriesMap) {
-            if (!mSessionsChanged) {
-                return;
-            }
-            mActiveSessions.clear();
-            for (int i=0; i<mSessions.size(); i++) {
-                Session s = mSessions.get(i);
-                if (s.mResumed) {
-                    mActiveSessions.add(s);
-                }
-            }
-        }
-    }
-
-    class MainHandler extends Handler {
-        static final int MSG_REBUILD_COMPLETE = 1;
-        static final int MSG_PACKAGE_LIST_CHANGED = 2;
-        static final int MSG_PACKAGE_ICON_CHANGED = 3;
-        static final int MSG_PACKAGE_SIZE_CHANGED = 4;
-        static final int MSG_ALL_SIZES_COMPUTED = 5;
-        static final int MSG_RUNNING_STATE_CHANGED = 6;
-        static final int MSG_LAUNCHER_INFO_CHANGED = 7;
-        static final int MSG_LOAD_ENTRIES_COMPLETE = 8;
-
-        @Override
-        public void handleMessage(Message msg) {
-            rebuildActiveSessions();
-            switch (msg.what) {
-                case MSG_REBUILD_COMPLETE: {
-                    Session s = (Session)msg.obj;
-                    if (mActiveSessions.contains(s)) {
-                        s.mCallbacks.onRebuildComplete(s.mLastAppList);
-                    }
-                } break;
-                case MSG_PACKAGE_LIST_CHANGED: {
-                    for (int i=0; i<mActiveSessions.size(); i++) {
-                        mActiveSessions.get(i).mCallbacks.onPackageListChanged();
-                    }
-                } break;
-                case MSG_PACKAGE_ICON_CHANGED: {
-                    for (int i=0; i<mActiveSessions.size(); i++) {
-                        mActiveSessions.get(i).mCallbacks.onPackageIconChanged();
-                    }
-                } break;
-                case MSG_PACKAGE_SIZE_CHANGED: {
-                    for (int i=0; i<mActiveSessions.size(); i++) {
-                        mActiveSessions.get(i).mCallbacks.onPackageSizeChanged(
-                                (String)msg.obj);
-                    }
-                } break;
-                case MSG_ALL_SIZES_COMPUTED: {
-                    for (int i=0; i<mActiveSessions.size(); i++) {
-                        mActiveSessions.get(i).mCallbacks.onAllSizesComputed();
-                    }
-                } break;
-                case MSG_RUNNING_STATE_CHANGED: {
-                    for (int i=0; i<mActiveSessions.size(); i++) {
-                        mActiveSessions.get(i).mCallbacks.onRunningStateChanged(
-                                msg.arg1 != 0);
-                    }
-                } break;
-                case MSG_LAUNCHER_INFO_CHANGED: {
-                    for (int i=0; i<mActiveSessions.size(); i++) {
-                        mActiveSessions.get(i).mCallbacks.onLauncherInfoChanged();
-                    }
-                } break;
-                case MSG_LOAD_ENTRIES_COMPLETE: {
-                    for (int i=0; i<mActiveSessions.size(); i++) {
-                        mActiveSessions.get(i).mCallbacks.onLoadEntriesCompleted();
-                    }
-                } break;
-            }
-        }
-    }
-
-    final MainHandler mMainHandler = new MainHandler();
-
-    // --------------------------------------------------------------
-
-    static final Object sLock = new Object();
-    static ApplicationsState sInstance;
-
-    static ApplicationsState getInstance(Application app) {
-        synchronized (sLock) {
-            if (sInstance == null) {
-                sInstance = new ApplicationsState(app);
-            }
-            return sInstance;
-        }
-    }
-
-    private ApplicationsState(Application app) {
-        mContext = app;
-        mPm = mContext.getPackageManager();
-        mIpm = AppGlobals.getPackageManager();
-        mUm = (UserManager) app.getSystemService(Context.USER_SERVICE);
-        for (UserHandle user : mUm.getUserProfiles()) {
-            mEntriesMap.put(user.getIdentifier(), new HashMap<String, AppEntry>());
-        }
-        mThread = new HandlerThread("ApplicationsState.Loader",
-                Process.THREAD_PRIORITY_BACKGROUND);
-        mThread.start();
-        mBackgroundHandler = new BackgroundHandler(mThread.getLooper());
-
-        // Only the owner can see all apps.
-        mOwnerRetrieveFlags = PackageManager.GET_UNINSTALLED_PACKAGES |
-                PackageManager.GET_DISABLED_COMPONENTS |
-                PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS;
-        mRetrieveFlags = PackageManager.GET_DISABLED_COMPONENTS |
-                PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS;
-
-        /**
-         * This is a trick to prevent the foreground thread from being delayed.
-         * The problem is that Dalvik monitors are initially spin locks, to keep
-         * them lightweight.  This leads to unfair contention -- Even though the
-         * background thread only holds the lock for a short amount of time, if
-         * it keeps running and locking again it can prevent the main thread from
-         * acquiring its lock for a long time...  sometimes even > 5 seconds
-         * (leading to an ANR).
-         *
-         * Dalvik will promote a monitor to a "real" lock if it detects enough
-         * contention on it.  It doesn't figure this out fast enough for us
-         * here, though, so this little trick will force it to turn into a real
-         * lock immediately.
-         */
-        synchronized (mEntriesMap) {
-            try {
-                mEntriesMap.wait(1);
-            } catch (InterruptedException e) {
-            }
-        }
-    }
-
-    Looper getBackgroundLooper() {
-        return mThread.getLooper();
-    }
-
-    public class Session {
-        final Callbacks mCallbacks;
-        boolean mResumed;
-
-        // Rebuilding of app list.  Synchronized on mRebuildSync.
-        final Object mRebuildSync = new Object();
-        boolean mRebuildRequested;
-        boolean mRebuildAsync;
-        AppFilter mRebuildFilter;
-        Comparator<AppEntry> mRebuildComparator;
-        ArrayList<AppEntry> mRebuildResult;
-        ArrayList<AppEntry> mLastAppList;
-
-        Session(Callbacks callbacks) {
-            mCallbacks = callbacks;
-        }
-
-        public void resume() {
-            if (DEBUG_LOCKING) Log.v(TAG, "resume about to acquire lock...");
-            synchronized (mEntriesMap) {
-                if (!mResumed) {
-                    mResumed = true;
-                    mSessionsChanged = true;
-                    doResumeIfNeededLocked();
-                }
-            }
-            if (DEBUG_LOCKING) Log.v(TAG, "...resume releasing lock");
-        }
-
-        public void pause() {
-            if (DEBUG_LOCKING) Log.v(TAG, "pause about to acquire lock...");
-            synchronized (mEntriesMap) {
-                if (mResumed) {
-                    mResumed = false;
-                    mSessionsChanged = true;
-                    mBackgroundHandler.removeMessages(BackgroundHandler.MSG_REBUILD_LIST, this);
-                    doPauseIfNeededLocked();
-                }
-                if (DEBUG_LOCKING) Log.v(TAG, "...pause releasing lock");
-            }
-        }
-
-        ArrayList<AppEntry> getAllApps() {
-            synchronized (mEntriesMap) {
-                return new ArrayList<>(mAppEntries);
-            }
-        }
-
-        // Creates a new list of app entries with the given filter and comparator.
-        ArrayList<AppEntry> rebuild(AppFilter filter, Comparator<AppEntry> comparator) {
-            synchronized (mRebuildSync) {
-                synchronized (mEntriesMap) {
-                    mRebuildingSessions.add(this);
-                    mRebuildRequested = true;
-                    mRebuildAsync = false;
-                    mRebuildFilter = filter;
-                    mRebuildComparator = comparator;
-                    mRebuildResult = null;
-                    if (!mBackgroundHandler.hasMessages(BackgroundHandler.MSG_REBUILD_LIST)) {
-                        Message msg = mBackgroundHandler.obtainMessage(
-                                BackgroundHandler.MSG_REBUILD_LIST);
-                        mBackgroundHandler.sendMessage(msg);
-                    }
-                }
-
-                // We will wait for .25s for the list to be built.
-                long waitend = SystemClock.uptimeMillis()+250;
-
-                while (mRebuildResult == null) {
-                    long now = SystemClock.uptimeMillis();
-                    if (now >= waitend) {
-                        break;
-                    }
-                    try {
-                        mRebuildSync.wait(waitend - now);
-                    } catch (InterruptedException e) {
-                    }
-                }
-
-                mRebuildAsync = true;
-
-                return mRebuildResult;
-            }
-        }
-
-        void handleRebuildList() {
-            AppFilter filter;
-            Comparator<AppEntry> comparator;
-            synchronized (mRebuildSync) {
-                if (!mRebuildRequested) {
-                    return;
-                }
-
-                filter = mRebuildFilter;
-                comparator = mRebuildComparator;
-                mRebuildRequested = false;
-                mRebuildFilter = null;
-                mRebuildComparator = null;
-            }
-
-            Process.setThreadPriority(Process.THREAD_PRIORITY_FOREGROUND);
-
-            if (filter != null) {
-                filter.init();
-            }
-
-            List<AppEntry> apps;
-            synchronized (mEntriesMap) {
-                apps = new ArrayList<>(mAppEntries);
-            }
-
-            ArrayList<AppEntry> filteredApps = new ArrayList<AppEntry>();
-            if (DEBUG) Log.i(TAG, "Rebuilding...");
-            for (int i=0; i<apps.size(); i++) {
-                AppEntry entry = apps.get(i);
-                if (filter == null || filter.filterApp(entry)) {
-                    synchronized (mEntriesMap) {
-                        if (DEBUG_LOCKING) Log.v(TAG, "rebuild acquired lock");
-                        entry.ensureLabel(mContext);
-                        if (DEBUG) Log.i(TAG, "Using " + entry.info.packageName + ": " + entry);
-                        filteredApps.add(entry);
-                        if (DEBUG_LOCKING) Log.v(TAG, "rebuild releasing lock");
-                    }
-                }
-            }
-
-            Collections.sort(filteredApps, comparator);
-
-            synchronized (mRebuildSync) {
-                if (!mRebuildRequested) {
-                    mLastAppList = filteredApps;
-                    if (!mRebuildAsync) {
-                        mRebuildResult = filteredApps;
-                        mRebuildSync.notifyAll();
-                    } else {
-                        if (!mMainHandler.hasMessages(MainHandler.MSG_REBUILD_COMPLETE, this)) {
-                            Message msg = mMainHandler.obtainMessage(
-                                    MainHandler.MSG_REBUILD_COMPLETE, this);
-                            mMainHandler.sendMessage(msg);
-                        }
-                    }
-                }
-            }
-
-            Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
-        }
-
-        public void release() {
-            pause();
-            synchronized (mEntriesMap) {
-                mSessions.remove(this);
-            }
-        }
-    }
-
-    public Session newSession(Callbacks callbacks) {
-        Session s = new Session(callbacks);
-        synchronized (mEntriesMap) {
-            mSessions.add(s);
-        }
-        return s;
-    }
-
-    void doResumeIfNeededLocked() {
-        if (mResumed) {
-            return;
-        }
-        mResumed = true;
-        if (mPackageIntentReceiver == null) {
-            mPackageIntentReceiver = new PackageIntentReceiver();
-            mPackageIntentReceiver.registerReceiver();
-        }
-        mApplications = new ArrayList<ApplicationInfo>();
-        for (UserHandle user : mUm.getUserProfiles()) {
-            try {
-                // If this user is new, it needs a map created.
-                if (mEntriesMap.indexOfKey(user.getIdentifier()) < 0) {
-                    mEntriesMap.put(user.getIdentifier(), new HashMap<String, AppEntry>());
-                }
-                ParceledListSlice<ApplicationInfo> list =
-                        mIpm.getInstalledApplications(
-                                user.isOwner() ? mOwnerRetrieveFlags : mRetrieveFlags,
-                                user.getIdentifier());
-                mApplications.addAll(list.getList());
-            } catch (RemoteException e) {
-            }
-        }
-
-        if (mInterestingConfigChanges.applyNewConfig(mContext.getResources())) {
-            // If an interesting part of the configuration has changed, we
-            // should completely reload the app entries.
-            clearEntries();
-        } else {
-            for (int i=0; i<mAppEntries.size(); i++) {
-                mAppEntries.get(i).sizeStale = true;
-            }
-        }
-
-        mHaveDisabledApps = false;
-        for (int i=0; i<mApplications.size(); i++) {
-            final ApplicationInfo info = mApplications.get(i);
-            // Need to trim out any applications that are disabled by
-            // something different than the user.
-            if (!info.enabled) {
-                if (info.enabledSetting != PackageManager.COMPONENT_ENABLED_STATE_DISABLED_USER) {
-                    mApplications.remove(i);
-                    i--;
-                    continue;
-                }
-                mHaveDisabledApps = true;
-            }
-            int userId = UserHandle.getUserId(info.uid);
-            final AppEntry entry = mEntriesMap.get(userId).get(info.packageName);
-            if (entry != null) {
-                entry.info = info;
-            }
-        }
-        if (mAppEntries.size() > mApplications.size()) {
-            // There are less apps now, some must have been uninstalled.
-            clearEntries();
-        }
-        mCurComputingSizePkg = null;
-        if (!mBackgroundHandler.hasMessages(BackgroundHandler.MSG_LOAD_ENTRIES)) {
-            mBackgroundHandler.sendEmptyMessage(BackgroundHandler.MSG_LOAD_ENTRIES);
-        }
-    }
-
-    private void clearEntries() {
-        for (int i = 0; i < mEntriesMap.size(); i++) {
-            mEntriesMap.valueAt(i).clear();
-        }
-        mAppEntries.clear();
-    }
-
-    public boolean haveDisabledApps() {
-        return mHaveDisabledApps;
-    }
-
-    void doPauseIfNeededLocked() {
-        if (!mResumed) {
-            return;
-        }
-        for (int i=0; i<mSessions.size(); i++) {
-            if (mSessions.get(i).mResumed) {
-                return;
-            }
-        }
-        doPauseLocked();
-    }
-
-    void doPauseLocked() {
-        mResumed = false;
-        if (mPackageIntentReceiver != null) {
-            mPackageIntentReceiver.unregisterReceiver();
-            mPackageIntentReceiver = null;
-        }
-    }
-
-    AppEntry getEntry(String packageName, int userId) {
-        if (DEBUG_LOCKING) Log.v(TAG, "getEntry about to acquire lock...");
-        synchronized (mEntriesMap) {
-            AppEntry entry = mEntriesMap.get(userId).get(packageName);
-            if (entry == null) {
-                ApplicationInfo info = getAppInfoLocked(packageName, userId);
-                if (info == null) {
-                    try {
-                        info = mIpm.getApplicationInfo(packageName, 0, userId);
-                    } catch (RemoteException e) {
-                        Log.w(TAG, "getEntry couldn't reach PackageManager", e);
-                        return null;
-                    }
-                }
-                entry = getEntryLocked(info);
-            }
-            if (DEBUG_LOCKING) Log.v(TAG, "...getEntry releasing lock");
-            return entry;
-        }
-    }
-
-    private ApplicationInfo getAppInfoLocked(String pkg, int userId) {
-        for (int i = 0; i < mApplications.size(); i++) {
-            ApplicationInfo info = mApplications.get(i);
-            if (pkg.equals(info.packageName)
-                    && userId == UserHandle.getUserId(info.uid)) {
-                return info;
-            }
-        }
-        return null;
-    }
-
-    void ensureIcon(AppEntry entry) {
-        if (entry.icon != null) {
-            return;
-        }
-        synchronized (entry) {
-            entry.ensureIconLocked(mContext, mPm);
-        }
-    }
-
-    void requestSize(String packageName, int userId) {
-        if (DEBUG_LOCKING) Log.v(TAG, "requestSize about to acquire lock...");
-        synchronized (mEntriesMap) {
-            AppEntry entry = mEntriesMap.get(userId).get(packageName);
-            if (entry != null) {
-                mPm.getPackageSizeInfo(packageName, userId, mBackgroundHandler.mStatsObserver);
-            }
-            if (DEBUG_LOCKING) Log.v(TAG, "...requestSize releasing lock");
-        }
-    }
-
-    long sumCacheSizes() {
-        long sum = 0;
-        if (DEBUG_LOCKING) Log.v(TAG, "sumCacheSizes about to acquire lock...");
-        synchronized (mEntriesMap) {
-            if (DEBUG_LOCKING) Log.v(TAG, "-> sumCacheSizes now has lock");
-            for (int i=mAppEntries.size()-1; i>=0; i--) {
-                sum += mAppEntries.get(i).cacheSize;
-            }
-            if (DEBUG_LOCKING) Log.v(TAG, "...sumCacheSizes releasing lock");
-        }
-        return sum;
-    }
-
-    int indexOfApplicationInfoLocked(String pkgName, int userId) {
-        for (int i=mApplications.size()-1; i>=0; i--) {
-            ApplicationInfo appInfo = mApplications.get(i);
-            if (appInfo.packageName.equals(pkgName)
-                    && UserHandle.getUserId(appInfo.uid) == userId) {
-                return i;
-            }
-        }
-        return -1;
-    }
-
-    void addPackage(String pkgName, int userId) {
-        try {
-            synchronized (mEntriesMap) {
-                if (DEBUG_LOCKING) Log.v(TAG, "addPackage acquired lock");
-                if (DEBUG) Log.i(TAG, "Adding package " + pkgName);
-                if (!mResumed) {
-                    // If we are not resumed, we will do a full query the
-                    // next time we resume, so there is no reason to do work
-                    // here.
-                    if (DEBUG_LOCKING) Log.v(TAG, "addPackage release lock: not resumed");
-                    return;
-                }
-                if (indexOfApplicationInfoLocked(pkgName, userId) >= 0) {
-                    if (DEBUG) Log.i(TAG, "Package already exists!");
-                    if (DEBUG_LOCKING) Log.v(TAG, "addPackage release lock: already exists");
-                    return;
-                }
-                ApplicationInfo info = mIpm.getApplicationInfo(pkgName,
-                        userId == UserHandle.USER_OWNER ? mOwnerRetrieveFlags : mRetrieveFlags,
-                                userId);
-                if (info == null) {
-                    return;
-                }
-                if (!info.enabled) {
-                    if (info.enabledSetting
-                            != PackageManager.COMPONENT_ENABLED_STATE_DISABLED_USER) {
-                        return;
-                    }
-                    mHaveDisabledApps = true;
-                }
-                mApplications.add(info);
-                if (!mBackgroundHandler.hasMessages(BackgroundHandler.MSG_LOAD_ENTRIES)) {
-                    mBackgroundHandler.sendEmptyMessage(BackgroundHandler.MSG_LOAD_ENTRIES);
-                }
-                if (!mMainHandler.hasMessages(MainHandler.MSG_PACKAGE_LIST_CHANGED)) {
-                    mMainHandler.sendEmptyMessage(MainHandler.MSG_PACKAGE_LIST_CHANGED);
-                }
-                if (DEBUG_LOCKING) Log.v(TAG, "addPackage releasing lock");
-            }
-        } catch (RemoteException e) {
-        }
-    }
-
-    void removePackage(String pkgName, int userId) {
-        synchronized (mEntriesMap) {
-            if (DEBUG_LOCKING) Log.v(TAG, "removePackage acquired lock");
-            int idx = indexOfApplicationInfoLocked(pkgName, userId);
-            if (DEBUG) Log.i(TAG, "removePackage: " + pkgName + " @ " + idx);
-            if (idx >= 0) {
-                AppEntry entry = mEntriesMap.get(userId).get(pkgName);
-                if (DEBUG) Log.i(TAG, "removePackage: " + entry);
-                if (entry != null) {
-                    mEntriesMap.get(userId).remove(pkgName);
-                    mAppEntries.remove(entry);
-                }
-                ApplicationInfo info = mApplications.get(idx);
-                mApplications.remove(idx);
-                if (!info.enabled) {
-                    mHaveDisabledApps = false;
-                    for (int i=0; i<mApplications.size(); i++) {
-                        if (!mApplications.get(i).enabled) {
-                            mHaveDisabledApps = true;
-                            break;
-                        }
-                    }
-                }
-                if (!mMainHandler.hasMessages(MainHandler.MSG_PACKAGE_LIST_CHANGED)) {
-                    mMainHandler.sendEmptyMessage(MainHandler.MSG_PACKAGE_LIST_CHANGED);
-                }
-            }
-            if (DEBUG_LOCKING) Log.v(TAG, "removePackage releasing lock");
-        }
-    }
-
-    void invalidatePackage(String pkgName, int userId) {
-        removePackage(pkgName, userId);
-        addPackage(pkgName, userId);
-    }
-
-    void addUser(int userId) {
-        if (mUm.getUserProfiles().contains(new UserHandle(userId))) {
-            synchronized (mEntriesMap) {
-                mEntriesMap.put(userId, new HashMap<String, AppEntry>());
-                if (mResumed) {
-                    // If resumed, Manually pause, then cause a resume to repopulate the app list.
-                    // This is the simplest way to reload the packages so that the new user
-                    // is included.  Otherwise the list will be repopulated on next resume.
-                    doPauseLocked();
-                    doResumeIfNeededLocked();
-                }
-                if (!mMainHandler.hasMessages(MainHandler.MSG_PACKAGE_LIST_CHANGED)) {
-                    mMainHandler.sendEmptyMessage(MainHandler.MSG_PACKAGE_LIST_CHANGED);
-                }
-            }
-        }
-    }
-
-    void removeUser(int userId) {
-        synchronized (mEntriesMap) {
-            HashMap<String, AppEntry> userMap = mEntriesMap.get(userId);
-            if (userMap != null) {
-                for (AppEntry appEntry : userMap.values()) {
-                    mAppEntries.remove(appEntry);
-                    mApplications.remove(appEntry.info);
-                }
-                mEntriesMap.remove(userId);
-                if (!mMainHandler.hasMessages(MainHandler.MSG_PACKAGE_LIST_CHANGED)) {
-                    mMainHandler.sendEmptyMessage(MainHandler.MSG_PACKAGE_LIST_CHANGED);
-                }
-            }
-        }
-    }
-
-    AppEntry getEntryLocked(ApplicationInfo info) {
-        int userId = UserHandle.getUserId(info.uid);
-        AppEntry entry = mEntriesMap.get(userId).get(info.packageName);
-        if (DEBUG) Log.i(TAG, "Looking up entry of pkg " + info.packageName + ": " + entry);
-        if (entry == null) {
-            if (DEBUG) Log.i(TAG, "Creating AppEntry for " + info.packageName);
-            entry = new AppEntry(mContext, info, mCurId++);
-            mEntriesMap.get(userId).put(info.packageName, entry);
-            mAppEntries.add(entry);
-        } else if (entry.info != info) {
-            entry.info = info;
-        }
-        return entry;
-    }
-
-    // --------------------------------------------------------------
-
-    private long getTotalInternalSize(PackageStats ps) {
-        if (ps != null) {
-            return ps.codeSize + ps.dataSize;
-        }
-        return SIZE_INVALID;
-    }
-
-    private long getTotalExternalSize(PackageStats ps) {
-        if (ps != null) {
-            // We also include the cache size here because for non-emulated
-            // we don't automtically clean cache files.
-            return ps.externalCodeSize + ps.externalDataSize
-                    + ps.externalCacheSize
-                    + ps.externalMediaSize + ps.externalObbSize;
-        }
-        return SIZE_INVALID;
-    }
-
-    private String getSizeStr(long size) {
-        if (size >= 0) {
-            return Formatter.formatFileSize(mContext, size);
-        }
-        return null;
-    }
-
-    final HandlerThread mThread;
-    final BackgroundHandler mBackgroundHandler;
-    class BackgroundHandler extends Handler {
-        static final int MSG_REBUILD_LIST = 1;
-        static final int MSG_LOAD_ENTRIES = 2;
-        static final int MSG_LOAD_ICONS = 3;
-        static final int MSG_LOAD_SIZES = 4;
-        static final int MSG_LOAD_LAUNCHER = 5;
-
-        boolean mRunning;
-
-        final IPackageStatsObserver.Stub mStatsObserver = new IPackageStatsObserver.Stub() {
-            public void onGetStatsCompleted(PackageStats stats, boolean succeeded) {
-                boolean sizeChanged = false;
-                synchronized (mEntriesMap) {
-                    if (DEBUG_LOCKING) Log.v(TAG, "onGetStatsCompleted acquired lock");
-                    HashMap<String, AppEntry> userMap = mEntriesMap.get(stats.userHandle);
-                    if (userMap == null) {
-                        // The user must have been removed.
-                        return;
-                    }
-                    AppEntry entry = userMap.get(stats.packageName);
-                    if (entry != null) {
-                        synchronized (entry) {
-                            entry.sizeStale = false;
-                            entry.sizeLoadStart = 0;
-                            long externalCodeSize = stats.externalCodeSize
-                                    + stats.externalObbSize;
-                            long externalDataSize = stats.externalDataSize
-                                    + stats.externalMediaSize;
-                            long newSize = externalCodeSize + externalDataSize
-                                    + getTotalInternalSize(stats);
-                            if (entry.size != newSize ||
-                                    entry.cacheSize != stats.cacheSize ||
-                                    entry.codeSize != stats.codeSize ||
-                                    entry.dataSize != stats.dataSize ||
-                                    entry.externalCodeSize != externalCodeSize ||
-                                    entry.externalDataSize != externalDataSize ||
-                                    entry.externalCacheSize != stats.externalCacheSize) {
-                                entry.size = newSize;
-                                entry.cacheSize = stats.cacheSize;
-                                entry.codeSize = stats.codeSize;
-                                entry.dataSize = stats.dataSize;
-                                entry.externalCodeSize = externalCodeSize;
-                                entry.externalDataSize = externalDataSize;
-                                entry.externalCacheSize = stats.externalCacheSize;
-                                entry.sizeStr = getSizeStr(entry.size);
-                                entry.internalSize = getTotalInternalSize(stats);
-                                entry.internalSizeStr = getSizeStr(entry.internalSize);
-                                entry.externalSize = getTotalExternalSize(stats);
-                                entry.externalSizeStr = getSizeStr(entry.externalSize);
-                                if (DEBUG) Log.i(TAG, "Set size of " + entry.label + " " + entry
-                                        + ": " + entry.sizeStr);
-                                sizeChanged = true;
-                            }
-                        }
-                        if (sizeChanged) {
-                            Message msg = mMainHandler.obtainMessage(
-                                    MainHandler.MSG_PACKAGE_SIZE_CHANGED, stats.packageName);
-                            mMainHandler.sendMessage(msg);
-                        }
-                    }
-                    if (mCurComputingSizePkg != null
-                            && (mCurComputingSizePkg.equals(stats.packageName)
-                                    && mCurComputingSizeUserId == stats.userHandle)) {
-                        mCurComputingSizePkg = null;
-                        sendEmptyMessage(MSG_LOAD_SIZES);
-                    }
-                    if (DEBUG_LOCKING) Log.v(TAG, "onGetStatsCompleted releasing lock");
-                }
-            }
-        };
-
-        BackgroundHandler(Looper looper) {
-            super(looper);
-        }
-
-        @Override
-        public void handleMessage(Message msg) {
-            // Always try rebuilding list first thing, if needed.
-            ArrayList<Session> rebuildingSessions = null;
-            synchronized (mEntriesMap) {
-                if (mRebuildingSessions.size() > 0) {
-                    rebuildingSessions = new ArrayList<Session>(mRebuildingSessions);
-                    mRebuildingSessions.clear();
-                }
-            }
-            if (rebuildingSessions != null) {
-                for (int i=0; i<rebuildingSessions.size(); i++) {
-                    rebuildingSessions.get(i).handleRebuildList();
-                }
-            }
-
-            switch (msg.what) {
-                case MSG_REBUILD_LIST: {
-                } break;
-                case MSG_LOAD_ENTRIES: {
-                    int numDone = 0;
-                    synchronized (mEntriesMap) {
-                        if (DEBUG_LOCKING) Log.v(TAG, "MSG_LOAD_ENTRIES acquired lock");
-                        for (int i = 0; i < mApplications.size() && numDone < 6; i++) {
-                            if (!mRunning) {
-                                mRunning = true;
-                                Message m = mMainHandler.obtainMessage(
-                                        MainHandler.MSG_RUNNING_STATE_CHANGED, 1);
-                                mMainHandler.sendMessage(m);
-                            }
-                            ApplicationInfo info = mApplications.get(i);
-                            int userId = UserHandle.getUserId(info.uid);
-                            if (mEntriesMap.get(userId).get(info.packageName) == null) {
-                                numDone++;
-                                getEntryLocked(info);
-                            }
-                        }
-                        if (DEBUG_LOCKING) Log.v(TAG, "MSG_LOAD_ENTRIES releasing lock");
-                    }
-
-                    if (numDone >= 6) {
-                        sendEmptyMessage(MSG_LOAD_ENTRIES);
-                    } else {
-                        if (!mMainHandler.hasMessages(MainHandler.MSG_LOAD_ENTRIES_COMPLETE)) {
-                            mMainHandler.sendEmptyMessage(MainHandler.MSG_LOAD_ENTRIES_COMPLETE);
-                        }
-                        sendEmptyMessage(MSG_LOAD_LAUNCHER);
-                    }
-                } break;
-                case MSG_LOAD_LAUNCHER: {
-                    Intent launchIntent = new Intent(Intent.ACTION_MAIN, null)
-                            .addCategory(Intent.CATEGORY_LAUNCHER);
-
-                    for (int i = 0; i < mEntriesMap.size(); i++) {
-                        int userId = mEntriesMap.keyAt(i);
-                        List<ResolveInfo> intents = mPm.queryIntentActivitiesAsUser(launchIntent,
-                                PackageManager.GET_DISABLED_COMPONENTS, userId);
-                        synchronized (mEntriesMap) {
-                            if (DEBUG_LOCKING) Log.v(TAG, "MSG_LOAD_LAUNCHER acquired lock");
-                            HashMap<String, AppEntry> userEntries = mEntriesMap.valueAt(i);
-                            final int N = intents.size();
-                            for (int j = 0; j < N; j++) {
-                                String packageName = intents.get(j).activityInfo.packageName;
-                                AppEntry entry = userEntries.get(packageName);
-                                if (entry != null) {
-                                    entry.hasLauncherEntry = true;
-                                } else {
-                                    Log.w(TAG, "Cannot find pkg: " + packageName
-                                            + " on user " + userId);
-                                }
-                            }
-                            if (DEBUG_LOCKING) Log.v(TAG, "MSG_LOAD_LAUNCHER releasing lock");
-                        }
-                    }
-
-                    if (!mMainHandler.hasMessages(MainHandler.MSG_LAUNCHER_INFO_CHANGED)) {
-                        mMainHandler.sendEmptyMessage(MainHandler.MSG_LAUNCHER_INFO_CHANGED);
-                    }
-                    sendEmptyMessage(MSG_LOAD_ICONS);
-                } break;
-                case MSG_LOAD_ICONS: {
-                    int numDone = 0;
-                    synchronized (mEntriesMap) {
-                        if (DEBUG_LOCKING) Log.v(TAG, "MSG_LOAD_ICONS acquired lock");
-                        for (int i=0; i<mAppEntries.size() && numDone<2; i++) {
-                            AppEntry entry = mAppEntries.get(i);
-                            if (entry.icon == null || !entry.mounted) {
-                                synchronized (entry) {
-                                    if (entry.ensureIconLocked(mContext, mPm)) {
-                                        if (!mRunning) {
-                                            mRunning = true;
-                                            Message m = mMainHandler.obtainMessage(
-                                                    MainHandler.MSG_RUNNING_STATE_CHANGED, 1);
-                                            mMainHandler.sendMessage(m);
-                                        }
-                                        numDone++;
-                                    }
-                                }
-                            }
-                        }
-                        if (DEBUG_LOCKING) Log.v(TAG, "MSG_LOAD_ICONS releasing lock");
-                    }
-                    if (numDone > 0) {
-                        if (!mMainHandler.hasMessages(MainHandler.MSG_PACKAGE_ICON_CHANGED)) {
-                            mMainHandler.sendEmptyMessage(MainHandler.MSG_PACKAGE_ICON_CHANGED);
-                        }
-                    }
-                    if (numDone >= 2) {
-                        sendEmptyMessage(MSG_LOAD_ICONS);
-                    } else {
-                        sendEmptyMessage(MSG_LOAD_SIZES);
-                    }
-                } break;
-                case MSG_LOAD_SIZES: {
-                    synchronized (mEntriesMap) {
-                        if (DEBUG_LOCKING) Log.v(TAG, "MSG_LOAD_SIZES acquired lock");
-                        if (mCurComputingSizePkg != null) {
-                            if (DEBUG_LOCKING) Log.v(TAG, "MSG_LOAD_SIZES releasing: currently computing");
-                            return;
-                        }
-
-                        long now = SystemClock.uptimeMillis();
-                        for (int i=0; i<mAppEntries.size(); i++) {
-                            AppEntry entry = mAppEntries.get(i);
-                            if (entry.size == SIZE_UNKNOWN || entry.sizeStale) {
-                                if (entry.sizeLoadStart == 0 ||
-                                        (entry.sizeLoadStart < (now-20*1000))) {
-                                    if (!mRunning) {
-                                        mRunning = true;
-                                        Message m = mMainHandler.obtainMessage(
-                                                MainHandler.MSG_RUNNING_STATE_CHANGED, 1);
-                                        mMainHandler.sendMessage(m);
-                                    }
-                                    entry.sizeLoadStart = now;
-                                    mCurComputingSizePkg = entry.info.packageName;
-                                    mCurComputingSizeUserId = UserHandle.getUserId(entry.info.uid);
-                                    mPm.getPackageSizeInfo(mCurComputingSizePkg,
-                                            mCurComputingSizeUserId, mStatsObserver);
-                                }
-                                if (DEBUG_LOCKING) Log.v(TAG, "MSG_LOAD_SIZES releasing: now computing");
-                                return;
-                            }
-                        }
-                        if (!mMainHandler.hasMessages(MainHandler.MSG_ALL_SIZES_COMPUTED)) {
-                            mMainHandler.sendEmptyMessage(MainHandler.MSG_ALL_SIZES_COMPUTED);
-                            mRunning = false;
-                            Message m = mMainHandler.obtainMessage(
-                                    MainHandler.MSG_RUNNING_STATE_CHANGED, 0);
-                            mMainHandler.sendMessage(m);
-                        }
-                        if (DEBUG_LOCKING) Log.v(TAG, "MSG_LOAD_SIZES releasing lock");
-                    }
-                } break;
-            }
-        }
-
-    }
-}
diff --git a/src/com/android/settings/applications/ClearDefaultsPreference.java b/src/com/android/settings/applications/ClearDefaultsPreference.java
index 1799cad..8be4be0 100644
--- a/src/com/android/settings/applications/ClearDefaultsPreference.java
+++ b/src/com/android/settings/applications/ClearDefaultsPreference.java
@@ -37,6 +37,7 @@
 
 import com.android.settings.R;
 import com.android.settings.Utils;
+import com.android.settingslib.applications.ApplicationsState;
 
 public class ClearDefaultsPreference extends Preference {
 
diff --git a/src/com/android/settings/applications/InstalledAppDetails.java b/src/com/android/settings/applications/InstalledAppDetails.java
index 26e3d49..6e96f6a 100755
--- a/src/com/android/settings/applications/InstalledAppDetails.java
+++ b/src/com/android/settings/applications/InstalledAppDetails.java
@@ -16,11 +16,11 @@
 
 package com.android.settings.applications;
 
-import android.app.admin.DevicePolicyManager;
 import android.app.Activity;
 import android.app.ActivityManager;
 import android.app.AlertDialog;
 import android.app.LoaderManager.LoaderCallbacks;
+import android.app.admin.DevicePolicyManager;
 import android.content.ActivityNotFoundException;
 import android.content.BroadcastReceiver;
 import android.content.ComponentName;
@@ -66,7 +66,6 @@
 import com.android.settings.R;
 import com.android.settings.SettingsActivity;
 import com.android.settings.Utils;
-import com.android.settings.applications.ApplicationsState.AppEntry;
 import com.android.settings.applications.PermissionsSummaryHelper.PermissionsResultCallback;
 import com.android.settings.fuelgauge.BatteryEntry;
 import com.android.settings.fuelgauge.PowerUsageDetail;
@@ -75,6 +74,8 @@
 import com.android.settings.notification.AppNotificationSettings;
 import com.android.settings.notification.NotificationBackend;
 import com.android.settings.notification.NotificationBackend.AppRow;
+import com.android.settingslib.applications.ApplicationsState;
+import com.android.settingslib.applications.ApplicationsState.AppEntry;
 
 import java.lang.ref.WeakReference;
 import java.util.ArrayList;
diff --git a/src/com/android/settings/applications/InterestingConfigChanges.java b/src/com/android/settings/applications/InterestingConfigChanges.java
deleted file mode 100644
index 816d169..0000000
--- a/src/com/android/settings/applications/InterestingConfigChanges.java
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.settings.applications;
-
-import android.content.pm.ActivityInfo;
-import android.content.res.Configuration;
-import android.content.res.Resources;
-
-class InterestingConfigChanges {
-    final Configuration mLastConfiguration = new Configuration();
-    int mLastDensity;
-
-    boolean applyNewConfig(Resources res) {
-        int configChanges = mLastConfiguration.updateFrom(res.getConfiguration());
-        boolean densityChanged = mLastDensity != res.getDisplayMetrics().densityDpi;
-        if (densityChanged || (configChanges&(ActivityInfo.CONFIG_LOCALE
-                |ActivityInfo.CONFIG_UI_MODE|ActivityInfo.CONFIG_SCREEN_LAYOUT)) != 0) {
-            mLastDensity = res.getDisplayMetrics().densityDpi;
-            return true;
-        }
-        return false;
-    }
-}
diff --git a/src/com/android/settings/applications/ManageApplications.java b/src/com/android/settings/applications/ManageApplications.java
index 18a3f11..e18e9b6 100644
--- a/src/com/android/settings/applications/ManageApplications.java
+++ b/src/com/android/settings/applications/ManageApplications.java
@@ -62,14 +62,15 @@
 import com.android.settings.SettingsActivity;
 import com.android.settings.Utils;
 import com.android.settings.applications.AppStateUsageBridge.UsageState;
-import com.android.settings.applications.ApplicationsState.AppEntry;
-import com.android.settings.applications.ApplicationsState.AppFilter;
-import com.android.settings.applications.ApplicationsState.CompoundFilter;
-import com.android.settings.applications.ApplicationsState.VolumeFilter;
 import com.android.settings.fuelgauge.HighPowerDetail;
 import com.android.settings.notification.AppNotificationSettings;
 import com.android.settings.notification.NotificationBackend;
 import com.android.settings.notification.NotificationBackend.AppRow;
+import com.android.settingslib.applications.ApplicationsState;
+import com.android.settingslib.applications.ApplicationsState.AppEntry;
+import com.android.settingslib.applications.ApplicationsState.AppFilter;
+import com.android.settingslib.applications.ApplicationsState.CompoundFilter;
+import com.android.settingslib.applications.ApplicationsState.VolumeFilter;
 
 import java.util.ArrayList;
 import java.util.Collections;
diff --git a/src/com/android/settings/applications/RunningState.java b/src/com/android/settings/applications/RunningState.java
index f0c33dd..2286a24 100644
--- a/src/com/android/settings/applications/RunningState.java
+++ b/src/com/android/settings/applications/RunningState.java
@@ -46,6 +46,7 @@
 
 import com.android.settings.R;
 import com.android.settings.Utils;
+import com.android.settingslib.applications.InterestingConfigChanges;
 
 import java.util.ArrayList;
 import java.util.Collections;
diff --git a/src/com/android/settings/fuelgauge/HighPowerDetail.java b/src/com/android/settings/fuelgauge/HighPowerDetail.java
index bd18671..e399a34 100644
--- a/src/com/android/settings/fuelgauge/HighPowerDetail.java
+++ b/src/com/android/settings/fuelgauge/HighPowerDetail.java
@@ -24,10 +24,9 @@
 import android.preference.SwitchPreference;
 
 import com.android.internal.logging.MetricsLogger;
-import com.android.settings.InstrumentedFragment;
 import com.android.settings.R;
 import com.android.settings.applications.AppInfoWithHeader;
-import com.android.settings.applications.ApplicationsState.AppEntry;
+import com.android.settingslib.applications.ApplicationsState.AppEntry;
 
 public class HighPowerDetail extends AppInfoWithHeader implements OnPreferenceChangeListener {
 
