diff options
Diffstat (limited to 'services/java/com/android/server/SystemServer.java')
| -rw-r--r-- | services/java/com/android/server/SystemServer.java | 620 |
1 files changed, 293 insertions, 327 deletions
diff --git a/services/java/com/android/server/SystemServer.java b/services/java/com/android/server/SystemServer.java index a42cbcf..d5e49a0 100644 --- a/services/java/com/android/server/SystemServer.java +++ b/services/java/com/android/server/SystemServer.java @@ -17,6 +17,9 @@ package com.android.server; import android.app.ActivityManagerNative; +import android.app.ActivityThread; +import android.app.IAlarmManager; +import android.app.INotificationManager; import android.bluetooth.BluetoothAdapter; import android.content.ComponentName; import android.content.ContentResolver; @@ -28,8 +31,10 @@ import android.content.res.Configuration; import android.media.AudioService; import android.net.wifi.p2p.WifiP2pService; import android.os.Environment; +import android.os.FactoryTest; import android.os.Handler; -import android.os.HandlerThread; +import android.os.IBinder; +import android.os.IPowerManager; import android.os.Looper; import android.os.RemoteException; import android.os.ServiceManager; @@ -51,22 +56,29 @@ import com.android.server.accessibility.AccessibilityManagerService; import com.android.server.accounts.AccountManagerService; import com.android.server.am.ActivityManagerService; import com.android.server.am.BatteryStatsService; +import com.android.server.clipboard.ClipboardService; import com.android.server.content.ContentService; import com.android.server.display.DisplayManagerService; import com.android.server.dreams.DreamManagerService; import com.android.server.input.InputManagerService; +import com.android.server.lights.LightsManager; +import com.android.server.lights.LightsService; import com.android.server.media.MediaRouterService; import com.android.server.net.NetworkPolicyManagerService; import com.android.server.net.NetworkStatsService; +import com.android.server.notification.NotificationManagerService; import com.android.server.os.SchedulingPolicyService; import com.android.server.pm.Installer; import com.android.server.pm.PackageManagerService; import com.android.server.pm.UserManagerService; import com.android.server.power.PowerManagerService; import com.android.server.power.ShutdownThread; -import com.android.server.print.PrintManagerService; import com.android.server.search.SearchManagerService; +import com.android.server.statusbar.StatusBarManagerService; +import com.android.server.storage.DeviceStorageMonitorService; +import com.android.server.twilight.TwilightService; import com.android.server.usb.UsbService; +import com.android.server.wallpaper.WallpaperManagerService; import com.android.server.wifi.WifiService; import com.android.server.wm.WindowManagerService; @@ -77,62 +89,214 @@ import java.io.File; import java.util.Timer; import java.util.TimerTask; -class ServerThread { +public final class SystemServer { private static final String TAG = "SystemServer"; + private static final String ENCRYPTING_STATE = "trigger_restart_min_framework"; private static final String ENCRYPTED_STATE = "1"; - ContentResolver mContentResolver; + private static final long SNAPSHOT_INTERVAL = 60 * 60 * 1000; // 1hr - void reportWtf(String msg, Throwable e) { - Slog.w(TAG, "***********************************************"); - Log.wtf(TAG, "BOOT FAILURE " + msg, e); + // The earliest supported time. We pick one day into 1970, to + // give any timezone code room without going into negative time. + private static final long EARLIEST_SUPPORTED_TIME = 86400 * 1000; + + /* + * Implementation class names. TODO: Move them to a codegen class or load + * them from the build system somehow. + */ + private static final String BACKUP_MANAGER_SERVICE_CLASS = + "com.android.server.backup.BackupManagerService$Lifecycle"; + private static final String DEVICE_POLICY_MANAGER_SERVICE_CLASS = + "com.android.server.devicepolicy.DevicePolicyManagerService$Lifecycle"; + private static final String APPWIDGET_SERVICE_CLASS = + "com.android.server.appwidget.AppWidgetService"; + private static final String PRINT_MANAGER_SERVICE_CLASS = + "com.android.server.print.PrintManagerService"; + private static final String USB_SERVICE_CLASS = + "com.android.server.usb.UsbService$Lifecycle"; + private static final String HDMI_CEC_SERVICE_CLASS = + "com.android.server.hdmi.HdmiCecService"; + + private final int mFactoryTestMode; + private Timer mProfilerSnapshotTimer; + + private Context mSystemContext; + private SystemServiceManager mSystemServiceManager; + + // TODO: remove all of these references by improving dependency resolution and boot phases + private Installer mInstaller; + private PowerManagerService mPowerManagerService; + private ActivityManagerService mActivityManagerService; + private DisplayManagerService mDisplayManagerService; + private ContentResolver mContentResolver; + + /** + * Called to initialize native system services. + */ + private static native void nativeInit(); + + /** + * The main entry point from zygote. + */ + public static void main(String[] args) { + new SystemServer().run(); } - public void initAndLoop() { - EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_SYSTEM_RUN, - SystemClock.uptimeMillis()); + public SystemServer() { + mFactoryTestMode = FactoryTest.getMode(); + } - Looper.prepareMainLooper(); + private void run() { + // If a device's clock is before 1970 (before 0), a lot of + // APIs crash dealing with negative numbers, notably + // java.io.File#setLastModified, so instead we fake it and + // hope that time from cell towers or NTP fixes it shortly. + if (System.currentTimeMillis() < EARLIEST_SUPPORTED_TIME) { + Slog.w(TAG, "System clock is before 1970; setting to 1970."); + SystemClock.setCurrentTimeMillis(EARLIEST_SUPPORTED_TIME); + } - android.os.Process.setThreadPriority( - android.os.Process.THREAD_PRIORITY_FOREGROUND); + // Here we go! + Slog.i(TAG, "Entered the Android system server!"); + EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_SYSTEM_RUN, SystemClock.uptimeMillis()); + + // In case the runtime switched since last boot (such as when + // the old runtime was removed in an OTA), set the system + // property so that it is in sync. We can't do this in + // libnativehelper's JniInvocation::Init code where we already + // had to fallback to a different runtime because it is + // running as root and we need to be the system user to set + // the property. http://b/11463182 + SystemProperties.set("persist.sys.dalvik.vm.lib", VMRuntime.getRuntime().vmLibrary()); + + // Enable the sampling profiler. + if (SamplingProfilerIntegration.isEnabled()) { + SamplingProfilerIntegration.start(); + mProfilerSnapshotTimer = new Timer(); + mProfilerSnapshotTimer.schedule(new TimerTask() { + @Override + public void run() { + SamplingProfilerIntegration.writeSnapshot("system_server", null); + } + }, SNAPSHOT_INTERVAL, SNAPSHOT_INTERVAL); + } + // Mmmmmm... more memory! + VMRuntime.getRuntime().clearGrowthLimit(); + + // The system server has to run all of the time, so it needs to be + // as efficient as possible with its memory usage. + VMRuntime.getRuntime().setTargetHeapUtilization(0.8f); + + // Within the system server, it is an error to access Environment paths without + // explicitly specifying a user. + Environment.setUserRequired(true); + + // Ensure binder calls into the system always run at foreground priority. BinderInternal.disableBackgroundScheduling(true); + + // Prepare the main looper thread (this thread). + android.os.Process.setThreadPriority( + android.os.Process.THREAD_PRIORITY_FOREGROUND); android.os.Process.setCanSelfBackground(false); + Looper.prepareMainLooper(); + + // Initialize native services. + System.loadLibrary("android_servers"); + nativeInit(); // Check whether we failed to shut down last time we tried. - { - final String shutdownAction = SystemProperties.get( - ShutdownThread.SHUTDOWN_ACTION_PROPERTY, ""); - if (shutdownAction != null && shutdownAction.length() > 0) { - boolean reboot = (shutdownAction.charAt(0) == '1'); - - final String reason; - if (shutdownAction.length() > 1) { - reason = shutdownAction.substring(1, shutdownAction.length()); - } else { - reason = null; - } + // This call may not return. + performPendingShutdown(); - ShutdownThread.rebootOrShutdown(reboot, reason); + // Initialize the system context. + createSystemContext(); + + // Create the system service manager. + mSystemServiceManager = new SystemServiceManager(mSystemContext); + LocalServices.addService(SystemServiceManager.class, mSystemServiceManager); + + // Start services. + try { + startBootstrapServices(); + startCoreServices(); + startOtherServices(); + } catch (RuntimeException ex) { + Slog.e("System", "******************************************"); + Slog.e("System", "************ Failure starting system services", ex); + throw ex; + } + + // For debug builds, log event loop stalls to dropbox for analysis. + if (StrictMode.conditionallyEnableDebugLogging()) { + Slog.i(TAG, "Enabled StrictMode for system server main thread."); + } + + // Loop forever. + Looper.loop(); + throw new RuntimeException("Main thread loop unexpectedly exited"); + } + + private void reportWtf(String msg, Throwable e) { + Slog.w(TAG, "***********************************************"); + Log.wtf(TAG, "BOOT FAILURE " + msg, e); + } + + private void performPendingShutdown() { + final String shutdownAction = SystemProperties.get( + ShutdownThread.SHUTDOWN_ACTION_PROPERTY, ""); + if (shutdownAction != null && shutdownAction.length() > 0) { + boolean reboot = (shutdownAction.charAt(0) == '1'); + + final String reason; + if (shutdownAction.length() > 1) { + reason = shutdownAction.substring(1, shutdownAction.length()); + } else { + reason = null; } + + ShutdownThread.rebootOrShutdown(reboot, reason); } + } - String factoryTestStr = SystemProperties.get("ro.factorytest"); - int factoryTest = "".equals(factoryTestStr) ? SystemServer.FACTORY_TEST_OFF - : Integer.parseInt(factoryTestStr); - final boolean headless = "1".equals(SystemProperties.get("ro.config.headless", "0")); + private void createSystemContext() { + ActivityThread activityThread = ActivityThread.systemMain(); + mSystemContext = activityThread.getSystemContext(); + mSystemContext.setTheme(android.R.style.Theme_Holo); + } - Installer installer = null; + private void startBootstrapServices() { + // Wait for installd to finish starting up so that it has a chance to + // create critical directories such as /data/user with the appropriate + // permissions. We need this to complete before we initialize other services. + mInstaller = mSystemServiceManager.startService(Installer.class); + + // Power manager needs to be started early because other services need it. + // TODO: The conversion to the new pattern is incomplete. We need to switch + // the power manager's dependencies over then we can use boot phases to arrange + // initialization order and remove the mPowerManagerService field. + mPowerManagerService = mSystemServiceManager.startService(PowerManagerService.class); + + // Activity manager runs the show. + mActivityManagerService = mSystemServiceManager.startService( + ActivityManagerService.Lifecycle.class).getService(); + } + + private void startCoreServices() { + // Display manager is needed to provide display metrics before package manager + // starts up. + mDisplayManagerService = mSystemServiceManager.startService(DisplayManagerService.class); + } + + private void startOtherServices() { + final Context context = mSystemContext; AccountManagerService accountManager = null; ContentService contentService = null; - LightsService lights = null; - PowerManagerService power = null; - DisplayManagerService display = null; + LightsManager lights = null; BatteryService battery = null; VibratorService vibrator = null; - AlarmManagerService alarm = null; + IAlarmManager alarm = null; MountService mountService = null; NetworkManagementService networkManagement = null; NetworkStatsService networkStats = null; @@ -142,14 +306,11 @@ class ServerThread { WifiService wifi = null; NsdService serviceDiscovery= null; IPackageManager pm = null; - Context context = null; WindowManagerService wm = null; BluetoothManagerService bluetooth = null; DockObserver dock = null; UsbService usb = null; SerialService serial = null; - TwilightService twilight = null; - UiModeManagerService uiMode = null; RecognitionManagerService recognition = null; NetworkTimeUpdateService networkTimeUpdater = null; CommonTimeManagementService commonTimeMgmtService = null; @@ -157,48 +318,8 @@ class ServerThread { TelephonyRegistry telephonyRegistry = null; ConsumerIrService consumerIr = null; - // Create a handler thread just for the window manager to enjoy. - HandlerThread wmHandlerThread = new HandlerThread("WindowManager"); - wmHandlerThread.start(); - Handler wmHandler = new Handler(wmHandlerThread.getLooper()); - wmHandler.post(new Runnable() { - @Override - public void run() { - //Looper.myLooper().setMessageLogging(new LogPrinter( - // android.util.Log.DEBUG, TAG, android.util.Log.LOG_ID_SYSTEM)); - android.os.Process.setThreadPriority( - android.os.Process.THREAD_PRIORITY_DISPLAY); - android.os.Process.setCanSelfBackground(false); - - // For debug builds, log event loop stalls to dropbox for analysis. - if (StrictMode.conditionallyEnableDebugLogging()) { - Slog.i(TAG, "Enabled StrictMode logging for WM Looper"); - } - } - }); - - // bootstrap services boolean onlyCore = false; boolean firstBoot = false; - try { - // Wait for installd to finished starting up so that it has a chance to - // create critical directories such as /data/user with the appropriate - // permissions. We need this to complete before we initialize other services. - Slog.i(TAG, "Waiting for installd to be ready."); - installer = new Installer(); - installer.ping(); - - Slog.i(TAG, "Power Manager"); - power = new PowerManagerService(); - ServiceManager.addService(Context.POWER_SERVICE, power); - - Slog.i(TAG, "Activity Manager"); - context = ActivityManagerService.main(factoryTest); - } catch (RuntimeException e) { - Slog.e("System", "******************************************"); - Slog.e("System", "************ Failure starting bootstrap service", e); - } - boolean disableStorage = SystemProperties.getBoolean("config.disable_storage", false); boolean disableMedia = SystemProperties.getBoolean("config.disable_media", false); boolean disableBluetooth = SystemProperties.getBoolean("config.disable_bluetooth", false); @@ -209,10 +330,6 @@ class ServerThread { boolean disableNetwork = SystemProperties.getBoolean("config.disable_network", false); try { - Slog.i(TAG, "Display Manager"); - display = new DisplayManagerService(context, wmHandler); - ServiceManager.addService(Context.DISPLAY_SERVICE, display, true); - Slog.i(TAG, "Telephony Registry"); telephonyRegistry = new TelephonyRegistry(context); ServiceManager.addService("telephony.registry", telephonyRegistry); @@ -222,10 +339,8 @@ class ServerThread { AttributeCache.init(context); - if (!display.waitForDefaultDisplay()) { - reportWtf("Timeout waiting for default display to be initialized.", - new Throwable()); - } + // We need the default display before we can initialize the package manager. + mSystemServiceManager.startBootPhase(SystemService.PHASE_WAIT_FOR_DEFAULT_DISPLAY); Slog.i(TAG, "Package Manager"); // Only run "core" apps if we're encrypting the device. @@ -238,15 +353,15 @@ class ServerThread { onlyCore = true; } - pm = PackageManagerService.main(context, installer, - factoryTest != SystemServer.FACTORY_TEST_OFF, + pm = PackageManagerService.main(context, mInstaller, + mFactoryTestMode != FactoryTest.FACTORY_TEST_OFF, onlyCore); try { firstBoot = pm.isFirstBoot(); } catch (RemoteException e) { } - ActivityManagerService.setSystemProcess(); + mActivityManagerService.setSystemProcess(); Slog.i(TAG, "Entropy Mixer"); ServiceManager.addService("entropy", new EntropyMixer(context)); @@ -269,13 +384,13 @@ class ServerThread { Slog.i(TAG, "Content Manager"); contentService = ContentService.main(context, - factoryTest == SystemServer.FACTORY_TEST_LOW_LEVEL); + mFactoryTestMode == FactoryTest.FACTORY_TEST_LOW_LEVEL); Slog.i(TAG, "System Content Providers"); - ActivityManagerService.installSystemProviders(); + mActivityManagerService.installSystemProviders(); - Slog.i(TAG, "Lights Service"); - lights = new LightsService(context); + mSystemServiceManager.startService(LightsService.class); + lights = LocalServices.getService(LightsManager.class); Slog.i(TAG, "Battery Service"); battery = new BatteryService(context, lights); @@ -285,49 +400,49 @@ class ServerThread { vibrator = new VibratorService(context); ServiceManager.addService("vibrator", vibrator); - Slog.i(TAG, "Consumer IR Service"); - consumerIr = new ConsumerIrService(context); - ServiceManager.addService(Context.CONSUMER_IR_SERVICE, consumerIr); - + // TODO: use boot phase // only initialize the power service after we have started the // lights service, content providers and the battery service. - power.init(context, lights, ActivityManagerService.self(), battery, + mPowerManagerService.init(lights, battery, BatteryStatsService.getService(), - ActivityManagerService.self().getAppOpsService(), display); + mActivityManagerService.getAppOpsService()); - Slog.i(TAG, "Alarm Manager"); - alarm = new AlarmManagerService(context); - ServiceManager.addService(Context.ALARM_SERVICE, alarm); + Slog.i(TAG, "Consumer IR Service"); + consumerIr = new ConsumerIrService(context); + ServiceManager.addService(Context.CONSUMER_IR_SERVICE, consumerIr); + + mSystemServiceManager.startService(AlarmManagerService.class); + alarm = IAlarmManager.Stub.asInterface( + ServiceManager.getService(Context.ALARM_SERVICE)); Slog.i(TAG, "Init Watchdog"); - Watchdog.getInstance().init(context, battery, power, alarm, - ActivityManagerService.self()); - Watchdog.getInstance().addThread(wmHandler, "WindowManager thread"); + final Watchdog watchdog = Watchdog.getInstance(); + watchdog.init(context, mActivityManagerService); Slog.i(TAG, "Input Manager"); - inputManager = new InputManagerService(context, wmHandler); + inputManager = new InputManagerService(context); Slog.i(TAG, "Window Manager"); - wm = WindowManagerService.main(context, power, display, inputManager, - wmHandler, factoryTest != SystemServer.FACTORY_TEST_LOW_LEVEL, + wm = WindowManagerService.main(context, inputManager, + mFactoryTestMode != FactoryTest.FACTORY_TEST_LOW_LEVEL, !firstBoot, onlyCore); ServiceManager.addService(Context.WINDOW_SERVICE, wm); ServiceManager.addService(Context.INPUT_SERVICE, inputManager); - ActivityManagerService.self().setWindowManager(wm); + mActivityManagerService.setWindowManager(wm); inputManager.setWindowManagerCallbacks(wm.getInputMonitor()); inputManager.start(); - display.setWindowManager(wm); - display.setInputManager(inputManager); + // TODO: Use service dependencies instead. + mDisplayManagerService.windowManagerAndInputReady(); // Skip Bluetooth if we have an emulator kernel // TODO: Use a more reliable check to see if this product should // support Bluetooth - see bug 988521 if (SystemProperties.get("ro.kernel.qemu").equals("1")) { Slog.i(TAG, "No Bluetooh Service (emulator)"); - } else if (factoryTest == SystemServer.FACTORY_TEST_LOW_LEVEL) { + } else if (mFactoryTestMode == FactoryTest.FACTORY_TEST_LOW_LEVEL) { Slog.i(TAG, "No Bluetooth Service (factory test)"); } else if (!context.getPackageManager().hasSystemFeature (PackageManager.FEATURE_BLUETOOTH)) { @@ -344,23 +459,19 @@ class ServerThread { Slog.e("System", "************ Failure starting core service", e); } - DevicePolicyManagerService devicePolicy = null; StatusBarManagerService statusBar = null; + INotificationManager notification = null; InputMethodManagerService imm = null; - AppWidgetService appWidget = null; - NotificationManagerService notification = null; WallpaperManagerService wallpaper = null; LocationManagerService location = null; CountryDetectorService countryDetector = null; TextServicesManagerService tsms = null; LockSettingsService lockSettings = null; - DreamManagerService dreamy = null; AssetAtlasService atlas = null; - PrintManagerService printManager = null; MediaRouterService mediaRouter = null; // Bring up services needed for UI. - if (factoryTest != SystemServer.FACTORY_TEST_LOW_LEVEL) { + if (mFactoryTestMode != FactoryTest.FACTORY_TEST_LOW_LEVEL) { //if (!disableNonCoreServices) { // TODO: View depends on these; mock them? if (true) { try { @@ -397,11 +508,11 @@ class ServerThread { ActivityManagerNative.getDefault().showBootMessage( context.getResources().getText( com.android.internal.R.string.android_upgrading_starting_apps), - false); + false); } catch (RemoteException e) { } - if (factoryTest != SystemServer.FACTORY_TEST_LOW_LEVEL) { + if (mFactoryTestMode != FactoryTest.FACTORY_TEST_LOW_LEVEL) { if (!disableStorage && !"0".equals(SystemProperties.get("system_init.startmountservice"))) { try { @@ -427,9 +538,9 @@ class ServerThread { } try { - Slog.i(TAG, "Device Policy"); - devicePolicy = new DevicePolicyManagerService(context); - ServiceManager.addService(Context.DEVICE_POLICY_SERVICE, devicePolicy); + if (pm.hasSystemFeature(PackageManager.FEATURE_DEVICE_ADMIN)) { + mSystemServiceManager.startService(DEVICE_POLICY_MANAGER_SERVICE_CLASS); + } } catch (Throwable e) { reportWtf("starting DevicePolicyService", e); } @@ -487,7 +598,8 @@ class ServerThread { try { Slog.i(TAG, "NetworkPolicy Service"); networkPolicy = new NetworkPolicyManagerService( - context, ActivityManagerService.self(), power, + context, mActivityManagerService, + (IPowerManager)ServiceManager.getService(Context.POWER_SERVICE), networkStats, networkManagement); ServiceManager.addService(Context.NETWORK_POLICY_SERVICE, networkPolicy); } catch (Throwable e) { @@ -567,22 +679,12 @@ class ServerThread { reportWtf("making Content Service ready", e); } - try { - Slog.i(TAG, "Notification Manager"); - notification = new NotificationManagerService(context, statusBar, lights); - ServiceManager.addService(Context.NOTIFICATION_SERVICE, notification); - networkPolicy.bindNotificationManager(notification); - } catch (Throwable e) { - reportWtf("starting Notification Manager", e); - } + mSystemServiceManager.startService(NotificationManagerService.class); + notification = INotificationManager.Stub.asInterface( + ServiceManager.getService(Context.NOTIFICATION_SERVICE)); + networkPolicy.bindNotificationManager(notification); - try { - Slog.i(TAG, "Device Storage Monitor"); - ServiceManager.addService(DeviceStorageMonitorService.SERVICE, - new DeviceStorageMonitorService(context)); - } catch (Throwable e) { - reportWtf("starting DeviceStorageMonitor service", e); - } + mSystemServiceManager.startService(DeviceStorageMonitorService.class); if (!disableLocation) { try { @@ -624,10 +726,8 @@ class ServerThread { R.bool.config_enableWallpaperService)) { try { Slog.i(TAG, "Wallpaper Service"); - if (!headless) { - wallpaper = new WallpaperManagerService(context); - ServiceManager.addService(Context.WALLPAPER_SERVICE, wallpaper); - } + wallpaper = new WallpaperManagerService(context); + ServiceManager.addService(Context.WALLPAPER_SERVICE, wallpaper); } catch (Throwable e) { reportWtf("starting Wallpaper Service", e); } @@ -665,10 +765,11 @@ class ServerThread { if (!disableNonCoreServices) { try { - Slog.i(TAG, "USB Service"); - // Manage USB host and device support - usb = new UsbService(context); - ServiceManager.addService(Context.USB_SERVICE, usb); + if (pm.hasSystemFeature(PackageManager.FEATURE_USB_HOST) || + pm.hasSystemFeature(PackageManager.FEATURE_USB_ACCESSORY)) { + // Manage USB host and device support + mSystemServiceManager.startService(USB_SERVICE_CLASS); + } } catch (Throwable e) { reportWtf("starting UsbService", e); } @@ -683,34 +784,23 @@ class ServerThread { } } - try { - Slog.i(TAG, "Twilight Service"); - twilight = new TwilightService(context); - } catch (Throwable e) { - reportWtf("starting TwilightService", e); - } + mSystemServiceManager.startService(TwilightService.class); - try { - Slog.i(TAG, "UI Mode Manager Service"); - // Listen for UI mode changes - uiMode = new UiModeManagerService(context, twilight); - } catch (Throwable e) { - reportWtf("starting UiModeManagerService", e); - } + mSystemServiceManager.startService(UiModeManagerService.class); if (!disableNonCoreServices) { try { - Slog.i(TAG, "Backup Service"); - ServiceManager.addService(Context.BACKUP_SERVICE, - new BackupManagerService(context)); + if (pm.hasSystemFeature(PackageManager.FEATURE_BACKUP)) { + mSystemServiceManager.startService(BACKUP_MANAGER_SERVICE_CLASS); + } } catch (Throwable e) { Slog.e(TAG, "Failure starting Backup Service", e); } try { - Slog.i(TAG, "AppWidget Service"); - appWidget = new AppWidgetService(context); - ServiceManager.addService(Context.APPWIDGET_SERVICE, appWidget); + if (pm.hasSystemFeature(PackageManager.FEATURE_APP_WIDGETS)) { + mSystemServiceManager.startService(APPWIDGET_SERVICE_CLASS); + } } catch (Throwable e) { reportWtf("starting AppWidget Service", e); } @@ -770,16 +860,9 @@ class ServerThread { } } - if (!disableNonCoreServices && - context.getResources().getBoolean(R.bool.config_dreamsSupported)) { - try { - Slog.i(TAG, "Dreams Service"); - // Dreams (interactive idle-time views, a/k/a screen savers) - dreamy = new DreamManagerService(context, wmHandler); - ServiceManager.addService(DreamService.DREAM_SERVICE, dreamy); - } catch (Throwable e) { - reportWtf("starting DreamManagerService", e); - } + if (!disableNonCoreServices) { + // Dreams (interactive idle-time views, a/k/a screen savers, and doze mode) + mSystemServiceManager.startService(DreamManagerService.class); } if (!disableNonCoreServices) { @@ -800,13 +883,19 @@ class ServerThread { } try { - Slog.i(TAG, "Print Service"); - printManager = new PrintManagerService(context); - ServiceManager.addService(Context.PRINT_SERVICE, printManager); + if (pm.hasSystemFeature(PackageManager.FEATURE_PRINTING)) { + mSystemServiceManager.startService(PRINT_MANAGER_SERVICE_CLASS); + } } catch (Throwable e) { reportWtf("starting Print Service", e); } + try { + mSystemServiceManager.startService(HDMI_CEC_SERVICE_CLASS); + } catch (Throwable e) { + reportWtf("starting HdmiCec Service", e); + } + if (!disableNonCoreServices) { try { Slog.i(TAG, "Media Router Service"); @@ -822,7 +911,7 @@ class ServerThread { // we are in safe mode. final boolean safeMode = wm.detectSafeMode(); if (safeMode) { - ActivityManagerService.self().enterSafeMode(); + mActivityManagerService.enterSafeMode(); // Post the safe mode state in the Zygote class Zygote.systemInSafeMode = true; // Disable the JIT for the system_server process @@ -848,21 +937,10 @@ class ServerThread { } } - if (devicePolicy != null) { - try { - devicePolicy.systemReady(); - } catch (Throwable e) { - reportWtf("making Device Policy Service ready", e); - } - } + // Needed by DevicePolicyManager for initialization + mSystemServiceManager.startBootPhase(SystemService.PHASE_LOCK_SETTINGS_READY); - if (notification != null) { - try { - notification.systemReady(); - } catch (Throwable e) { - reportWtf("making Notification Service ready", e); - } - } + mSystemServiceManager.startBootPhase(SystemService.PHASE_SYSTEM_SERVICES_READY); try { wm.systemReady(); @@ -871,7 +949,7 @@ class ServerThread { } if (safeMode) { - ActivityManagerService.self().showSafeModeOverlay(); + mActivityManagerService.showSafeModeOverlay(); } // Update the configuration for this context by hand, because we're going @@ -884,7 +962,8 @@ class ServerThread { context.getResources().updateConfiguration(config, metrics); try { - power.systemReady(twilight, dreamy); + // TODO: use boot phase + mPowerManagerService.systemReady(); } catch (Throwable e) { reportWtf("making Power Manager Service ready", e); } @@ -896,13 +975,13 @@ class ServerThread { } try { - display.systemReady(safeMode, onlyCore); + // TODO: use boot phase and communicate these flags some other way + mDisplayManagerService.systemReady(safeMode, onlyCore); } catch (Throwable e) { reportWtf("making Display Manager Service ready", e); } // These are needed to propagate to the runnable below. - final Context contextF = context; final MountService mountServiceF = mountService; final BatteryService batteryF = battery; final NetworkManagementService networkManagementF = networkManagement; @@ -910,10 +989,6 @@ class ServerThread { final NetworkPolicyManagerService networkPolicyF = networkPolicy; final ConnectivityService connectivityF = connectivity; final DockObserver dockF = dock; - final UsbService usbF = usb; - final TwilightService twilightF = twilight; - final UiModeManagerService uiModeF = uiMode; - final AppWidgetService appWidgetF = appWidget; final WallpaperManagerService wallpaperF = wallpaper; final InputMethodManagerService immF = imm; final RecognitionManagerService recognitionF = recognition; @@ -923,11 +998,9 @@ class ServerThread { final CommonTimeManagementService commonTimeMgmtServiceF = commonTimeMgmtService; final TextServicesManagerService textServiceManagerServiceF = tsms; final StatusBarManagerService statusBarF = statusBar; - final DreamManagerService dreamyF = dreamy; final AssetAtlasService atlasF = atlas; final InputManagerService inputManagerF = inputManager; final TelephonyRegistry telephonyRegistryF = telephonyRegistry; - final PrintManagerService printManagerF = printManager; final MediaRouterService mediaRouterF = mediaRouter; // We now tell the activity manager it is okay to run third party @@ -935,17 +1008,22 @@ class ServerThread { // where third party code can really run (but before it has actually // started launching the initial applications), for us to complete our // initialization. - ActivityManagerService.self().systemReady(new Runnable() { + mActivityManagerService.systemReady(new Runnable() { + @Override public void run() { Slog.i(TAG, "Making services ready"); + mSystemServiceManager.startBootPhase( + SystemService.PHASE_ACTIVITY_MANAGER_READY); try { - ActivityManagerService.self().startObservingNativeCrashes(); + mActivityManagerService.startObservingNativeCrashes(); } catch (Throwable e) { reportWtf("observing native crashes", e); } - if (!headless) { - startSystemUi(contextF); + try { + startSystemUi(context); + } catch (Throwable e) { + reportWtf("starting System UI", e); } try { if (mountServiceF != null) mountServiceF.systemReady(); @@ -983,21 +1061,6 @@ class ServerThread { reportWtf("making Dock Service ready", e); } try { - if (usbF != null) usbF.systemReady(); - } catch (Throwable e) { - reportWtf("making USB Service ready", e); - } - try { - if (twilightF != null) twilightF.systemReady(); - } catch (Throwable e) { - reportWtf("makin Twilight Service ready", e); - } - try { - if (uiModeF != null) uiModeF.systemReady(); - } catch (Throwable e) { - reportWtf("making UI Mode Service ready", e); - } - try { if (recognitionF != null) recognitionF.systemReady(); } catch (Throwable e) { reportWtf("making Recognition Service ready", e); @@ -1006,13 +1069,10 @@ class ServerThread { // It is now okay to let the various system services start their // third party code... + mSystemServiceManager.startBootPhase( + SystemService.PHASE_THIRD_PARTY_APPS_CAN_START); try { - if (appWidgetF != null) appWidgetF.systemRunning(safeMode); - } catch (Throwable e) { - reportWtf("Notifying AppWidgetService running", e); - } - try { if (wallpaperF != null) wallpaperF.systemRunning(); } catch (Throwable e) { reportWtf("Notifying WallpaperService running", e); @@ -1038,7 +1098,9 @@ class ServerThread { reportWtf("Notifying NetworkTimeService running", e); } try { - if (commonTimeMgmtServiceF != null) commonTimeMgmtServiceF.systemRunning(); + if (commonTimeMgmtServiceF != null) { + commonTimeMgmtServiceF.systemRunning(); + } } catch (Throwable e) { reportWtf("Notifying CommonTimeManagementService running", e); } @@ -1049,11 +1111,6 @@ class ServerThread { reportWtf("Notifying TextServicesManagerService running", e); } try { - if (dreamyF != null) dreamyF.systemRunning(); - } catch (Throwable e) { - reportWtf("Notifying DreamManagerService running", e); - } - try { if (atlasF != null) atlasF.systemRunning(); } catch (Throwable e) { reportWtf("Notifying AssetAtlasService running", e); @@ -1064,34 +1121,20 @@ class ServerThread { } catch (Throwable e) { reportWtf("Notifying InputManagerService running", e); } - try { if (telephonyRegistryF != null) telephonyRegistryF.systemRunning(); } catch (Throwable e) { reportWtf("Notifying TelephonyRegistry running", e); } - - try { - if (printManagerF != null) printManagerF.systemRuning(); - } catch (Throwable e) { - reportWtf("Notifying PrintManagerService running", e); - } - try { if (mediaRouterF != null) mediaRouterF.systemRunning(); } catch (Throwable e) { reportWtf("Notifying MediaRouterService running", e); } + + mSystemServiceManager.startBootPhase(SystemService.PHASE_BOOT_COMPLETE); } }); - - // For debug builds, log event loop stalls to dropbox for analysis. - if (StrictMode.conditionallyEnableDebugLogging()) { - Slog.i(TAG, "Enabled StrictMode for system server main thread."); - } - - Looper.loop(); - Slog.d(TAG, "System ServerThread is exiting!"); } static final void startSystemUi(Context context) { @@ -1102,80 +1145,3 @@ class ServerThread { context.startServiceAsUser(intent, UserHandle.OWNER); } } - -public class SystemServer { - private static final String TAG = "SystemServer"; - - public static final int FACTORY_TEST_OFF = 0; - public static final int FACTORY_TEST_LOW_LEVEL = 1; - public static final int FACTORY_TEST_HIGH_LEVEL = 2; - - static Timer timer; - static final long SNAPSHOT_INTERVAL = 60 * 60 * 1000; // 1hr - - // The earliest supported time. We pick one day into 1970, to - // give any timezone code room without going into negative time. - private static final long EARLIEST_SUPPORTED_TIME = 86400 * 1000; - - /** - * Called to initialize native system services. - */ - private static native void nativeInit(); - - public static void main(String[] args) { - - /* - * In case the runtime switched since last boot (such as when - * the old runtime was removed in an OTA), set the system - * property so that it is in sync. We can't do this in - * libnativehelper's JniInvocation::Init code where we already - * had to fallback to a different runtime because it is - * running as root and we need to be the system user to set - * the property. http://b/11463182 - */ - SystemProperties.set("persist.sys.dalvik.vm.lib", - VMRuntime.getRuntime().vmLibrary()); - - if (System.currentTimeMillis() < EARLIEST_SUPPORTED_TIME) { - // If a device's clock is before 1970 (before 0), a lot of - // APIs crash dealing with negative numbers, notably - // java.io.File#setLastModified, so instead we fake it and - // hope that time from cell towers or NTP fixes it - // shortly. - Slog.w(TAG, "System clock is before 1970; setting to 1970."); - SystemClock.setCurrentTimeMillis(EARLIEST_SUPPORTED_TIME); - } - - if (SamplingProfilerIntegration.isEnabled()) { - SamplingProfilerIntegration.start(); - timer = new Timer(); - timer.schedule(new TimerTask() { - @Override - public void run() { - SamplingProfilerIntegration.writeSnapshot("system_server", null); - } - }, SNAPSHOT_INTERVAL, SNAPSHOT_INTERVAL); - } - - // Mmmmmm... more memory! - dalvik.system.VMRuntime.getRuntime().clearGrowthLimit(); - - // The system server has to run all of the time, so it needs to be - // as efficient as possible with its memory usage. - VMRuntime.getRuntime().setTargetHeapUtilization(0.8f); - - Environment.setUserRequired(true); - - System.loadLibrary("android_servers"); - - Slog.i(TAG, "Entered the Android system server!"); - - // Initialize native services. - nativeInit(); - - // This used to be its own separate thread, but now it is - // just the loop we run on the main thread. - ServerThread thr = new ServerThread(); - thr.initAndLoop(); - } -} |
