From 26ff6626fc4ee0ae46f01ad309b366921da589fe Mon Sep 17 00:00:00 2001 From: Kenny Root Date: Mon, 30 Jul 2012 12:58:03 -0700 Subject: [PATCH] Delay AccountManagerService initialization Since applications can have Account providers, they need to be delayed until after PackageManagerService says everything is mounted. Otherwise the accounts associated with that provider will be removed immediately when startup happens. Bug: 6820670 Change-Id: Iba81765260421649f706624d0605a40ebc1347b1 --- .../accounts/AccountManagerService.java | 7 ++++-- .../accounts/IAccountAuthenticatorCache.java | 5 +++++ core/java/android/content/ContentService.java | 5 ++++- .../content/pm/RegisteredServicesCache.java | 2 +- .../java/com/android/server/SystemServer.java | 22 ++++++++++++++++--- 5 files changed, 34 insertions(+), 7 deletions(-) diff --git a/core/java/android/accounts/AccountManagerService.java b/core/java/android/accounts/AccountManagerService.java index 079b9bd284768..22e454f9dc2fd 100644 --- a/core/java/android/accounts/AccountManagerService.java +++ b/core/java/android/accounts/AccountManagerService.java @@ -220,8 +220,6 @@ public class AccountManagerService sThis.set(this); - UserAccounts accounts = initUser(0); - IntentFilter intentFilter = new IntentFilter(); intentFilter.addAction(Intent.ACTION_PACKAGE_REMOVED); intentFilter.addDataScheme("package"); @@ -242,6 +240,11 @@ public class AccountManagerService }, userFilter); } + public void systemReady() { + mAuthenticatorCache.generateServicesMap(); + initUser(0); + } + private UserAccounts initUser(int userId) { synchronized (mUsers) { UserAccounts accounts = mUsers.get(userId); diff --git a/core/java/android/accounts/IAccountAuthenticatorCache.java b/core/java/android/accounts/IAccountAuthenticatorCache.java index 618771f354150..20dd585a45a22 100644 --- a/core/java/android/accounts/IAccountAuthenticatorCache.java +++ b/core/java/android/accounts/IAccountAuthenticatorCache.java @@ -60,4 +60,9 @@ public interface IAccountAuthenticatorCache { */ void setListener(RegisteredServicesCacheListener listener, Handler handler); + + /** + * Refreshes the authenticator cache. + */ + void generateServicesMap(); } \ No newline at end of file diff --git a/core/java/android/content/ContentService.java b/core/java/android/content/ContentService.java index f827c3de43c34..1a07504f2fbe7 100644 --- a/core/java/android/content/ContentService.java +++ b/core/java/android/content/ContentService.java @@ -132,6 +132,9 @@ public final class ContentService extends IContentService.Stub { /*package*/ ContentService(Context context, boolean factoryTest) { mContext = context; mFactoryTest = factoryTest; + } + + public void systemReady() { getSyncManager(); } @@ -524,7 +527,7 @@ public final class ContentService extends IContentService.Stub { } } - public static IContentService main(Context context, boolean factoryTest) { + public static ContentService main(Context context, boolean factoryTest) { ContentService service = new ContentService(context, factoryTest); ServiceManager.addService(ContentResolver.CONTENT_SERVICE_NAME, service); return service; diff --git a/core/java/android/content/pm/RegisteredServicesCache.java b/core/java/android/content/pm/RegisteredServicesCache.java index b1fc788c16a8f..d8f920478aa66 100644 --- a/core/java/android/content/pm/RegisteredServicesCache.java +++ b/core/java/android/content/pm/RegisteredServicesCache.java @@ -251,7 +251,7 @@ public abstract class RegisteredServicesCache { return false; } - void generateServicesMap() { + public void generateServicesMap() { PackageManager pm = mContext.getPackageManager(); ArrayList> serviceInfos = new ArrayList>(); List resolveInfos = pm.queryIntentServices(new Intent(mInterfaceName), diff --git a/services/java/com/android/server/SystemServer.java b/services/java/com/android/server/SystemServer.java index 9dd4a91f119a9..6d0b26fb11dbe 100644 --- a/services/java/com/android/server/SystemServer.java +++ b/services/java/com/android/server/SystemServer.java @@ -114,6 +114,8 @@ class ServerThread extends Thread { : Integer.parseInt(factoryTestStr); final boolean headless = "1".equals(SystemProperties.get("ro.config.headless", "0")); + AccountManagerService accountManager = null; + ContentService contentService = null; LightsService lights = null; PowerManagerService power = null; BatteryService battery = null; @@ -190,14 +192,14 @@ class ServerThread extends Thread { // The AccountManager must come before the ContentService try { Slog.i(TAG, "Account Manager"); - ServiceManager.addService(Context.ACCOUNT_SERVICE, - new AccountManagerService(context)); + accountManager = new AccountManagerService(context); + ServiceManager.addService(Context.ACCOUNT_SERVICE, accountManager); } catch (Throwable e) { Slog.e(TAG, "Failure starting Account Manager", e); } Slog.i(TAG, "Content Manager"); - ContentService.main(context, + contentService = ContentService.main(context, factoryTest == SystemServer.FACTORY_TEST_LOW_LEVEL); Slog.i(TAG, "System Content Providers"); @@ -465,6 +467,20 @@ class ServerThread extends Thread { mountService.waitForAsecScan(); } + try { + if (accountManager != null) + accountManager.systemReady(); + } catch (Throwable e) { + reportWtf("making Account Manager Service ready", e); + } + + try { + if (contentService != null) + contentService.systemReady(); + } catch (Throwable e) { + reportWtf("making Content Service ready", e); + } + try { Slog.i(TAG, "Notification Manager"); notification = new NotificationManagerService(context, statusBar, lights);