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

Commit b02eb4bb authored by Adam Cohen's avatar Adam Cohen Committed by Android (Google) Code Review
Browse files

Merge "Pushing state persistence to a background thread" into jb-mr1.1-dev

parents 674a131c a1a2f967
Loading
Loading
Loading
Loading
+10 −2
Original line number Diff line number Diff line
@@ -26,6 +26,8 @@ import android.content.IntentFilter;
import android.content.pm.PackageManager;
import android.os.Binder;
import android.os.Bundle;
import android.os.Handler;
import android.os.HandlerThread;
import android.os.IBinder;
import android.os.RemoteException;
import android.os.UserHandle;
@@ -54,13 +56,19 @@ class AppWidgetService extends IAppWidgetService.Stub
    Locale mLocale;
    PackageManager mPackageManager;
    boolean mSafeMode;
    private final Handler mSaveStateHandler;

    private final SparseArray<AppWidgetServiceImpl> mAppWidgetServices;

    AppWidgetService(Context context) {
        mContext = context;

        HandlerThread handlerThread = new HandlerThread("AppWidgetService -- Save state");
        handlerThread.start();
        mSaveStateHandler = new Handler(handlerThread.getLooper());

        mAppWidgetServices = new SparseArray<AppWidgetServiceImpl>(5);
        AppWidgetServiceImpl primary = new AppWidgetServiceImpl(context, 0);
        AppWidgetServiceImpl primary = new AppWidgetServiceImpl(context, 0, mSaveStateHandler);
        mAppWidgetServices.append(0, primary);
    }

@@ -229,7 +237,7 @@ class AppWidgetService extends IAppWidgetService.Stub
            if (service == null) {
                Slog.i(TAG, "Unable to find AppWidgetServiceImpl for user " + userId + ", adding");
                // TODO: Verify that it's a valid user
                service = new AppWidgetServiceImpl(mContext, userId);
                service = new AppWidgetServiceImpl(mContext, userId, mSaveStateHandler);
                service.systemReady(mSafeMode);
                // Assume that BOOT_COMPLETED was received, as this is a non-primary user.
                mAppWidgetServices.append(userId, service);
+33 −13
Original line number Diff line number Diff line
@@ -41,7 +41,10 @@ import android.net.Uri;
import android.os.Binder;
import android.os.Bundle;
import android.os.Environment;
import android.os.Handler;
import android.os.HandlerThread;
import android.os.IBinder;
import android.os.Looper;
import android.os.Process;
import android.os.RemoteException;
import android.os.SystemClock;
@@ -180,15 +183,18 @@ class AppWidgetServiceImpl {
    boolean mStateLoaded;
    int mMaxWidgetBitmapMemory;

    private final Handler mSaveStateHandler;

    // These are for debugging only -- widgets are going missing in some rare instances
    ArrayList<Provider> mDeletedProviders = new ArrayList<Provider>();
    ArrayList<Host> mDeletedHosts = new ArrayList<Host>();

    AppWidgetServiceImpl(Context context, int userId) {
    AppWidgetServiceImpl(Context context, int userId, Handler saveStateHandler) {
        mContext = context;
        mPm = AppGlobals.getPackageManager();
        mAlarmManager = (AlarmManager) mContext.getSystemService(Context.ALARM_SERVICE);
        mUserId = userId;
        mSaveStateHandler = saveStateHandler;
        computeMaximumWidgetBitmapMemory();
    }

@@ -236,7 +242,7 @@ class AppWidgetServiceImpl {
                        updateProvidersForPackageLocked(cn.getPackageName(), removedProviders);
                    }
                }
                saveStateLocked();
                saveStateAsync();
            }
        }
    }
@@ -286,7 +292,7 @@ class AppWidgetServiceImpl {
                        providersModified |= addProvidersForPackageLocked(pkgName);
                    }
                }
                saveStateLocked();
                saveStateAsync();
            }
        } else {
            Bundle extras = intent.getExtras();
@@ -297,7 +303,7 @@ class AppWidgetServiceImpl {
                    ensureStateLoadedLocked();
                    for (String pkgName : pkgList) {
                        providersModified |= removeProvidersForPackageLocked(pkgName);
                        saveStateLocked();
                        saveStateAsync();
                    }
                }
            }
@@ -410,7 +416,7 @@ class AppWidgetServiceImpl {

    private void ensureStateLoadedLocked() {
        if (!mStateLoaded) {
            loadAppWidgetList();
            loadAppWidgetListLocked();
            loadStateLocked();
            mStateLoaded = true;
        }
@@ -431,7 +437,7 @@ class AppWidgetServiceImpl {
            host.instances.add(id);
            mAppWidgetIds.add(id);

            saveStateLocked();
            saveStateAsync();
            if (DBG) log("Allocating AppWidgetId for " + packageName + " host=" + hostId
                    + " id=" + appWidgetId);
            return appWidgetId;
@@ -444,7 +450,7 @@ class AppWidgetServiceImpl {
            AppWidgetId id = lookupAppWidgetIdLocked(appWidgetId);
            if (id != null) {
                deleteAppWidgetLocked(id);
                saveStateLocked();
                saveStateAsync();
            }
        }
    }
@@ -456,7 +462,7 @@ class AppWidgetServiceImpl {
            Host host = lookupHostLocked(callingUid, hostId);
            if (host != null) {
                deleteHostLocked(host);
                saveStateLocked();
                saveStateAsync();
            }
        }
    }
@@ -475,7 +481,7 @@ class AppWidgetServiceImpl {
                }
            }
            if (changed) {
                saveStateLocked();
                saveStateAsync();
            }
        }
    }
@@ -591,7 +597,7 @@ class AppWidgetServiceImpl {

                // schedule the future updates
                registerForBroadcastsLocked(p, getAppWidgetIds(p));
                saveStateLocked();
                saveStateAsync();
            }
        } finally {
            Binder.restoreCallingIdentity(ident);
@@ -655,8 +661,8 @@ class AppWidgetServiceImpl {
            } else {
                mPackagesWithBindWidgetPermission.remove(packageName);
            }
            saveStateAsync();
        }
        saveStateLocked();
    }

    // Binds to a specific RemoteViewsService
@@ -893,6 +899,20 @@ class AppWidgetServiceImpl {
        }
    }

    private void saveStateAsync() {
        mSaveStateHandler.post(mSaveStateRunnable);
    }

    private final Runnable mSaveStateRunnable = new Runnable() {
        @Override
        public void run() {
            synchronized (mAppWidgetIds) {
                ensureStateLoadedLocked();
                saveStateLocked();
            }
        }
    };

    public void updateAppWidgetOptions(int appWidgetId, Bundle options) {
        synchronized (mAppWidgetIds) {
            options = cloneIfLocalBinder(options);
@@ -913,7 +933,7 @@ class AppWidgetServiceImpl {
            intent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, id.appWidgetId);
            intent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_OPTIONS, id.options);
            mContext.sendBroadcastAsUser(intent, new UserHandle(mUserId));
            saveStateLocked();
            saveStateAsync();
        }
    }

@@ -1214,7 +1234,7 @@ class AppWidgetServiceImpl {
        }
    }

    void loadAppWidgetList() {
    void loadAppWidgetListLocked() {
        Intent intent = new Intent(AppWidgetManager.ACTION_APPWIDGET_UPDATE);
        try {
            List<ResolveInfo> broadcastReceivers = mPm.queryIntentReceivers(intent,