zoukankan      html  css  js  c++  java
  • [Android5.1]ActivityManagerService启动过程分析

    ActivityManagerService(简称AMS)是Android系统的关键服务之中的一个。它的主要作用例如以下:

    • 管理系统中全部应用进程的整个生命周期
    • 管理应用进程中的Activity、Service、Broadcast和ContentProvider
    • 内存管理,低内存释放等

    AMS是一个服务端,定义了IBinder接口。其它的进程能够通过Binder机制与AMS进行通信。


    AMS由system_server进程启动的,并作为一个独立线程执行在system_server进程中。
    以下就简略分析一下AMS的启动过程

    system_server启动AMS

    PATH:frameworks/base/services/java/com/android/server/SystemServer.java
    启动过程大致例如以下:
    SystemServer.main()–>SystemServer.run()。

    private void run() {
        ......
        startBootstrapServices();
        startOtherServices();
        ......
    }
    
    private void startBootstrapServices() {
        ......
        // 启动AMS服务
        mActivityManagerService = mSystemServiceManager.startService(
                ActivityManagerService.Lifecycle.class).getService();
    
        // 初始化AMS的成员变量mSystemServiceManager        
        mActivityManagerService.setSystemServiceManager(mSystemServiceManager);
        // 初始化AMS的成员变量mInstaller
        mActivityManagerService.setInstaller(installer);     
        ......
        // 主要是创建system_server相应的ProcessRecord,并初始化 
        mActivityManagerService.setSystemProcess();
        ......
    }
    
    private void startOtherServices() {
        ......
        // 主要是创建并注冊SettingsProvider
        mActivityManagerService.installSystemProviders();
        ......
        // 系统启动前的准备工作,启动SystemUI和Home界面等
        mActivityManagerService.systemReady(new Runnable() {...});
    }

    重点看一下mSystemServiceManager.startService():

    public SystemService startService(String className) {
        final Class<SystemService> serviceClass;
        try {
            serviceClass = (Class<SystemService>)Class.forName(className);
        } catch (ClassNotFoundException ex) {
            ......
        }
        return startService(serviceClass);
    }
    
    public <T extends SystemService> T startService(Class<T> serviceClass) {
        final String name = serviceClass.getName();
        Slog.i(TAG, "Starting " + name);
    
        // Create the service.
        if (!SystemService.class.isAssignableFrom(serviceClass)) {
            throw new RuntimeException("Failed to create " + name
                    + ": service must extend " + SystemService.class.getName());
        }
        final T service;
        try {
            Constructor<T> constructor = serviceClass.getConstructor(Context.class);
            //创建ActivityManagerService.Lifecycle对象
            service = constructor.newInstance(mContext);
        } catch (InstantiationException ex) {
            ......
        }
    
        // 加入到成员变量mServices中
        mServices.add(service);
    
        // Start it.
        try {
            // 执行ActivityManagerService.Lifecycle.onStart()
            service.onStart();
        } catch (RuntimeException ex) {
            throw new RuntimeException("Failed to start service " + name
                    + ": onStart threw an exception", ex);
        }
        return service;
    }

    ActivityManagerService.Lifecycle

    PATH:frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java

    public static final class Lifecycle extends SystemService {
        private final ActivityManagerService mService;
    
        public Lifecycle(Context context) {
            super(context);
            // 创建ActivityManagerServiceEx对象
            mService = new ActivityManagerServiceEx(context);
        }
    
        @Override
        public void onStart() {
            mService.start(); //执行ActivityManagerServiceEx.start()
        }
    
        public ActivityManagerService getService() {
            return mService;
        }
    }

    当中,ActivityManagerServiceEx是ActivityManagerService的子类,定义例如以下:

    public final class ActivityManagerServiceEx extends ActivityManagerService {
        ......
        public ActivityManagerServiceEx(Context systemContext) {
           super(systemContext);
           mIsInHome = true;
        }
        ......
    }

    这样,在new ActivityManagerServiceEx()时候。会调用到其父类ActivityManagerService的构造函数。

    ActivityManagerService构造函数

    PATH:frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java

    public ActivityManagerService(Context systemContext) {
        mContext = systemContext;
        mFactoryTest = FactoryTest.getMode();
        mSystemThread = ActivityThread.currentActivityThread();
    
        Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass());
    
        //创建名称为“ActivityManager”的消息循环线程。
        mHandlerThread = new ServiceThread(TAG,
                android.os.Process.THREAD_PRIORITY_FOREGROUND, false /*allowIo*/);
        mHandlerThread.start();
    
        //将该线程绑定到MainHandler,由MainHandler完毕消息的处理
        mHandler = new MainHandler(mHandlerThread.getLooper());
    
        //创建前台广播接收器,执行超时为10s
        mFgBroadcastQueue = new BroadcastQueue(this, mHandler,
                "foreground", BROADCAST_FG_TIMEOUT, false);
        //创建后台广播接收器。执行超时为60s
        mBgBroadcastQueue = new BroadcastQueue(this, mHandler,
                "background", BROADCAST_BG_TIMEOUT, true);
        mBroadcastQueues[0] = mFgBroadcastQueue;
        mBroadcastQueues[1] = mBgBroadcastQueue;
    
        mServices = new ActiveServicesEx(this);
        mProviderMap = new ProviderMap(this);
    
        //新建/data/system文件夹
        File dataDir = Environment.getDataDirectory();
        File systemDir = new File(dataDir, "system");
        systemDir.mkdirs();
    
        //创建BatteryStatsService服务
        mBatteryStatsService = new BatteryStatsService(systemDir, mHandler);
        mBatteryStatsService.getActiveStatistics().readLocked();
        mBatteryStatsService.getActiveStatistics().writeAsyncLocked();
        mOnBattery = DEBUG_POWER ?

    true : mBatteryStatsService.getActiveStatistics().getIsOnBattery(); mBatteryStatsService.getActiveStatistics().setCallback(this); //创建ProcessStatsService服务 mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats")); //创建AppOpsService服务 mAppOpsService = new AppOpsService(new File(systemDir, "appops.xml"), mHandler); //创建AtomicFile文件 mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml")); // User 0 is the first and only user that runs at boot. mStartedUsers.put(0, new UserStartedState(new UserHandle(0), true)); mUserLru.add(Integer.valueOf(0)); updateStartedUserArrayLocked(); GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", ConfigurationInfo.GL_ES_VERSION_UNDEFINED); mTrackingAssociations = "1".equals(SystemProperties.get("debug.track-associations")); mConfiguration.setToDefaults(); mConfiguration.locale = Locale.getDefault(); mConfigurationSeq = mConfiguration.seq = 1; mProcessCpuTracker.init(); mCompatModePackages = new CompatModePackages(this, systemDir, mHandler); mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler); mStackSupervisor = new ActivityStackSupervisor(this); mTaskPersister = new TaskPersister(systemDir, mStackSupervisor); mProcessCpuThread = new Thread("CpuTracker") { @Override public void run() { while (true) { try { try { synchronized(this) { final long now = SystemClock.uptimeMillis(); long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now; long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now; //Slog.i(TAG, "Cpu delay=" + nextCpuDelay // + ", write delay=" + nextWriteDelay); if (nextWriteDelay < nextCpuDelay) { nextCpuDelay = nextWriteDelay; } if (nextCpuDelay > 0) { mProcessCpuMutexFree.set(true); this.wait(nextCpuDelay); } } } catch (InterruptedException e) { } updateCpuStatsNow(); } catch (Exception e) { Slog.e(TAG, "Unexpected exception collecting process stats", e); } } } }; Watchdog.getInstance().addMonitor(this); Watchdog.getInstance().addThread(mHandler); }

    首先,创建了一个名为“ActivityManager”的消息循环线程,不断地接收其它进程发给AMS的消息;并把该消息循环线程与MainHandler绑定,这样,由MainHandler完毕消息的详细处理。


    然后,创建了一些服务,并在/data/system文件夹下创建该服务须要的文件或文件夹,详细例如以下:

    服务 服务说明 文件 文件说明
    BatteryStatsService 电池状态管理 /data/system/batterystats.bin 记录包含电压在内的各种电池信息
    ProcessStatsService 进程状态管理 /data/system/procstats 记录各个进程的状态信息
    AppOpsService 应用操作权限管理 /data/system/appops.xml 存储各个app的权限设置和操作信息

    另外,还创建了一个AtomicFile类型的文件mGrantFile ,文件路径为/data/system/urigrants.xml。
    AtomicFile文件是通过创建一个备份文件来执行原子性操作的帮助类,保证文件读写的完整。
    这样。system_server就完毕AMS的构造和启动。
    回到system_server中,我们看到又调用了AMS的setSystemProcess方法。以下就分析一下该方法。

    ActivityManagerService.setSystemProcess

    public void setSystemProcess() {
        try {
            ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true);
            ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats);
            ServiceManager.addService("meminfo", new MemBinder(this));
            ServiceManager.addService("gfxinfo", new GraphicsBinder(this));
            ServiceManager.addService("dbinfo", new DbBinder(this));
            if (MONITOR_CPU_USAGE) {
                ServiceManager.addService("cpuinfo", new CpuBinder(this));
            }
            ServiceManager.addService("permission", new PermissionController(this));
    
            ApplicationInfo info = mContext.getPackageManager().getApplicationInfo(
                    "android", STOCK_PM_FLAGS);
            mSystemThread.installSystemApplicationInfo(info, getClass().getClassLoader());
    
            synchronized (this) {
                ProcessRecord app = newProcessRecordLocked(info, info.processName, false, 0);
                app.persistent = true;
                app.pid = MY_PID;
                app.maxAdj = ProcessList.SYSTEM_ADJ;
                app.makeActive(mSystemThread.getApplicationThread(), mProcessStats);
                mProcessNames.put(app.processName, app.uid, app);
                synchronized (mPidsSelfLocked) {
                    mPidsSelfLocked.put(app.pid, app);
                }
                updateLruProcessLocked(app, false, null);
                updateOomAdjLocked();
            }
        } catch (PackageManager.NameNotFoundException e) {
            throw new RuntimeException(
                    "Unable to find android system package", e);
        }
    }

    首先,向SystemServiceManager中加入了若干个服务:

    服务 服务说明
    activity AMS服务本身
    procstats 进程状态管理
    meminfo 获取内存信息
    gfxinfo 监控分析GPU profiling信息
    dbinfo 数据库相关服务
    cpuinfo 获取cpu相关信息
    permission 权限控制相关服务

    然后。调用PMS的getApplicationInfo接口,获取名为”android”的应用程序信息。包名为”android”的apk即/system/framework/framework-res.apk。里面保存着系统GUI美化的相关文件,包含图标,弹出对话框的样式,动作特效,界面布局等。调用installSystemApplicationInfo载入framework-res.apk文件。
    接着,调用newProcessRecordLocked新建一个ProcessRecord 对象app。ProcessRecord用来描写叙述一个进程的全部信息,包含该进程的全部activity和service等。在这里就是system_server(AMS就是在system_server进程中执行的)。

    创建后,对app的一些成员变量进行初始化。包含设置为常驻内存执行;设置system_server的pid等。
    最后。调用mProcessNames.put()将创建的ProcessRecord 对象app加入到ProcessMap< ProcessRecord >类型的成员变量mProcessNames中。

    这里。app.processName=“system”。

    这样,AMS就得到了system_server的ProcessRecord,以后AMS也能够管理system_server了。


    继续回到system_server中。我们看到又调用了AMS的installSystemProviders方法,以下就分析一下该方法。

    ActivityManagerService.installSystemProviders

    public final void installSystemProviders() {
        List<ProviderInfo> providers;
        synchronized (this) {
            ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID);
            providers = generateApplicationProvidersLocked(app);
            if (providers != null) {
                for (int i=providers.size()-1; i>=0; i--) {
                    ProviderInfo pi = (ProviderInfo)providers.get(i);
                    if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) {
                        Slog.w(TAG, "Not installing system proc provider " + pi.name
                                + ": not system .apk");
                        providers.remove(i);
                    }
                }
            }
        }
        if (providers != null) {
            mSystemThread.installSystemProviders(providers);
        }
    
        mCoreSettingsObserver = new CoreSettingsObserver(this);
    
        //mUsageStatsService.monitorPackages();
    }

    首先,取出在setSystemProcess()中put到mProcessNames中的ProcessRecord对象app,即system_server的进程信息。


    然后,调用generateApplicationProvidersLocked:

    private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) {
        List<ProviderInfo> providers = null;
        try {
            providers = AppGlobals.getPackageManager().
                queryContentProviders(app.processName, app.uid,
                        STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS);
        } catch (RemoteException ex) {
        }
        if (DEBUG_MU)
            Slog.v(TAG_MU, "generateApplicationProvidersLocked, app.info.uid = " + app.uid);
        int userId = app.userId;
        if (providers != null) {
            int N = providers.size();
            app.pubProviders.ensureCapacity(N + app.pubProviders.size());
            for (int i=0; i<N; i++) {
                ProviderInfo cpi =
                    (ProviderInfo)providers.get(i);
                boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo,
                        cpi.name, cpi.flags);
                if (singleton && UserHandle.getUserId(app.uid) != 0) {
                    providers.remove(i);
                    N--;
                    i--;
                    continue;
                }
    
                ComponentName comp = new ComponentName(cpi.packageName, cpi.name);
                ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId);
                if (cpr == null) {
                    cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton);
                    mProviderMap.putProviderByClass(comp, cpr);
                }
                if (DEBUG_MU)
                    Slog.v(TAG_MU, "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid);
                app.pubProviders.put(cpi.name, cpr);
                if (!cpi.multiprocess || !"android".equals(cpi.packageName)) {
                    app.addPackage(cpi.applicationInfo.packageName, cpi.applicationInfo.versionCode,
                            mProcessStats);
                }
                ensurePackageDexOpt(cpi.applicationInfo.packageName);
            }
        }
        return providers;
    }

    首先,调用PMS的queryContentProviders查找processName=“system”和uid=SYSTEM_UID的provider。即SettingsProvider。并获取其ProviderInfo 。
    然后新建一个ContentProviderRecord(描写叙述一个ContentProvider,这里为SettingsProvider),并加入到AMS的成员变量mProviderMap和ProcessRecord对象的pubProviders中。


    最后将SettingsProvider所在的package加入到ProcessRecord对象的pkglist中。

    继续回到installSystemProviders()。调用installSystemProviders,先创建后注冊SettingsProvider。这样,其它进程就能够调用SettingsProvider。查询或改动一些系统设置了。

    在installSystemProviders()的最后,注冊一个ContentObserver来监听SettingsProvider中的状态变化。


    继续回到system_server中。我们看到又调用了AMS的systemReady方法。以下就分析一下该方法。

    ActivityManagerService.systemReady

    该函数主要完毕了以下几件事:

    • 在当前执行的进程中,查找在systemReady之前不同意启动的进程。然后调用removeProcessLocked()终止该进程并释放资源。推断条件例如以下:
    boolean isAllowedWhileBooting(ApplicationInfo ai) {
        return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0;
    }
    • 载入若干配置信息和资源信息,代码例如以下:
    retrieveSettings();
    loadResourcesOnSystemReady();
    
    private void retrieveSettings() {
        final ContentResolver resolver = mContext.getContentResolver();
        String debugApp = Settings.Global.getString(
            resolver, Settings.Global.DEBUG_APP);
        boolean waitForDebugger = Settings.Global.getInt(
            resolver, Settings.Global.WAIT_FOR_DEBUGGER, 0) != 0;
        boolean alwaysFinishActivities = Settings.Global.getInt(
            resolver, Settings.Global.ALWAYS_FINISH_ACTIVITIES, 0) != 0;
        boolean forceRtl = Settings.Global.getInt(
                resolver, Settings.Global.DEVELOPMENT_FORCE_RTL, 0) != 0;
        ......
    }
    
    private void loadResourcesOnSystemReady() {
        final Resources res = mContext.getResources();
        mHasRecents = res.getBoolean(com.android.internal.R.bool.config_hasRecents);
        mThumbnailWidth = res.getDimensionPixelSize(com.android.internal.R.dimen.thumbnail_width);
        mThumbnailHeight = res.getDimensionPixelSize(com.android.internal.R.dimen.thumbnail_height);
    }
    
    • 调用回调函数goingCallback.run()。主要完毕两件事:执行其它系统服务的systemready()或systemRunning();启动SystemUI。


      goingCallback.run()的实如今systemserver.java中:

    mActivityManagerService.systemReady(new Runnable() {
        @Override
        public void run() {
            Slog.i(TAG, "Making services ready");
            mSystemServiceManager.startBootPhase(
                    SystemService.PHASE_ACTIVITY_MANAGER_READY);
    
            try {
                mActivityManagerService.startObservingNativeCrashes();
            } catch (Throwable e) {
                reportWtf("observing native crashes", e);
            }
    
            Slog.i(TAG, "WebViewFactory preparation");
            WebViewFactory.prepareWebViewInSystemServer();
    
            try {
                startSystemUi(context); //启动SystemUI
            } catch (Throwable e) {
                reportWtf("starting System UI", e);
            }
            try {
                if (mountServiceF != null) mountServiceF.systemReady();
            } catch (Throwable e) {
                reportWtf("making Mount Service ready", e);
            }
            try {
                if (networkScoreF != null) networkScoreF.systemReady();
            } catch (Throwable e) {
                reportWtf("making Network Score Service ready", e);
            }
            try {
                if (networkManagementF != null) networkManagementF.systemReady();
            } catch (Throwable e) {
                reportWtf("making Network Managment Service ready", e);
            }
            try {
                if (networkStatsF != null) networkStatsF.systemReady();
            } catch (Throwable e) {
                reportWtf("making Network Stats Service ready", e);
            }
            try {
                if (networkPolicyF != null) networkPolicyF.systemReady();
            } catch (Throwable e) {
                reportWtf("making Network Policy Service ready", e);
            }
            try {
                if (connectivityF != null) connectivityF.systemReady();
            } catch (Throwable e) {
                reportWtf("making Connectivity Service ready", e);
            }
            try {
                if (audioServiceF != null) audioServiceF.systemReady();
            } catch (Throwable e) {
                reportWtf("Notifying AudioService running", e);
            }
            Watchdog.getInstance().start();
    
            // 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 (wallpaperF != null) wallpaperF.systemRunning();
            } catch (Throwable e) {
                reportWtf("Notifying WallpaperService running", e);
            }
            try {
                if (immF != null) immF.systemRunning(statusBarF);
            } catch (Throwable e) {
                reportWtf("Notifying InputMethodService running", e);
            }
            try {
                if (locationF != null) locationF.systemRunning();
            } catch (Throwable e) {
                reportWtf("Notifying Location Service running", e);
            }
            try {
                if (countryDetectorF != null) countryDetectorF.systemRunning();
            } catch (Throwable e) {
                reportWtf("Notifying CountryDetectorService running", e);
            }
            try {
                if (networkTimeUpdaterF != null) networkTimeUpdaterF.systemRunning();
            } catch (Throwable e) {
                reportWtf("Notifying NetworkTimeService running", e);
            }
            try {
                if (commonTimeMgmtServiceF != null) {
                    commonTimeMgmtServiceF.systemRunning();
                }
            } catch (Throwable e) {
                reportWtf("Notifying CommonTimeManagementService running", e);
            }
            try {
                if (textServiceManagerServiceF != null)
                    textServiceManagerServiceF.systemRunning();
            } catch (Throwable e) {
                reportWtf("Notifying TextServicesManagerService running", e);
            }
            try {
                if (atlasF != null) atlasF.systemRunning();
            } catch (Throwable e) {
                reportWtf("Notifying AssetAtlasService running", e);
            }
            try {
                // TODO(BT) Pass parameter to input manager
                if (inputManagerF != null) inputManagerF.systemRunning();
            } catch (Throwable e) {
                reportWtf("Notifying InputManagerService running", e);
            }
            try {
                if (telephonyRegistryF != null) telephonyRegistryF.systemRunning();
            } catch (Throwable e) {
                reportWtf("Notifying TelephonyRegistry running", e);
            }
    
            try {
                if (mediaRouterF != null) mediaRouterF.systemRunning();
            } catch (Throwable e) {
                reportWtf("Notifying MediaRouterService running", e);
            }
    
            if (SystemProperties.get("persist.support.securetest").equals("1")) {
                if (securityF != null) {
                    try {
                        securityF.systemReady(context);
                    } catch (Throwable e) {
                        reportWtf("Security Service ready", e);
                    }
                }
            }
        }
    });
    • 调用addAppLocked启动那些声明为“FLAG_SYSTEM|FLAG_PERSISTENT”的应用程序:
    final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated,
                String abiOverride) {
        ProcessRecord app;
        if (!isolated) {
            app = getProcessRecordLocked(info.processName, info.uid, true);
        } else {
            ......
        }
        ......
        // This package really, really can not be stopped.
        try {
            AppGlobals.getPackageManager().setPackageStoppedState(
                    info.packageName, false, UserHandle.getUserId(app.uid));
        } catch (RemoteException e) {
        } catch (IllegalArgumentException e) {
            Slog.w(TAG, "Failed trying to unstop package "
                    + info.packageName + ": " + e);
        }
        //推断条件
        if ((info.flags&(ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT))
                == (ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) {
            app.persistent = true;
            app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ;
        }
        //假设该app的IApplicationThread等于null,而且没有在ArrayList<ProcessRecord>类型
        //的成员变量mPersistentStartingProcesses中,
        //启动该app,并把它加入到mPersistentStartingProcesses中。
        if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) {
            mPersistentStartingProcesses.add(app);
            startProcessLocked(app, "added application", app.processName, abiOverride,
                    null /* entryPoint */, null /* entryPointArgs */);
        }
    
        return app;
    }
    • 广播两个消息:ACTION_USER_STARTED和ACTION_USER_STARTING。标识用户已经started
    Intent intent = new Intent(Intent.ACTION_USER_STARTED);
    intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY
            | Intent.FLAG_RECEIVER_FOREGROUND);
    intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId);
    broadcastIntentLocked(null, null, intent,
            null, null, 0, null, null, null, AppOpsManager.OP_NONE,
            false, false, MY_PID, Process.SYSTEM_UID, mCurrentUserId);
    intent = new Intent(Intent.ACTION_USER_STARTING);
    intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY);
    intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId);
    broadcastIntentLocked(null, null, intent,
        null, new IIntentReceiver.Stub() {
           @Override
            public void performReceive(Intent intent, int resultCode, String data,
                    Bundle extras, boolean ordered, boolean sticky, int sendingUser)
                    throws RemoteException {
            }
            }, 0, null, null,
        INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE,
        true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL);
    } catch (Throwable t) {
    ......
    • 调用startHomeActivityLocked()启动HOME界面。

    这样,ActivityManagerService的启动和初始化就完毕了。

  • 相关阅读:
    《架构师》反思:系统可靠性
    表现力(转)
    4月反思
    30天敏捷结果(10) 强化你的一周
    认真对待学习(2月反思)
    Sort By Double
    12月反思 组内设计评审会议
    WPF框架的内存泄漏BUG
    OpenExpressApp 框架结构(2)
    绑定子类的泛型基类,反模式?
  • 原文地址:https://www.cnblogs.com/zhchoutai/p/8365063.html
Copyright © 2011-2022 走看看