很多没有写博客了,最近一段时间一直忙着工作,另外一方面也在忙着学点更深层次的东西及一些新的东西,如 Android Framework、PHP 等等。经过那么长时间的努力学习,终于初步了解了 Android Framework 及相关的东西,还有 PHP、ThinkPHP 等等。现在工作也不是很忙了,终于有时间写点总结了。其实我这篇文章写的挺杂的,也算不上是 Android 体系结构,但是实在想不到更好的名字了。而且很多东西都是一笔代过,因为其中的很多知识点,要详细讨论的话不是一两篇文章就能写的完的。这里我就先从整体上做个总结,后面我会就其中的很多问题进行总结讨论,敬请期待。
一、TheBinder
Binder 是 Android 中最重要的进程间通信手段,即最重要的 RPC/IPC 机制。但是 Binder 并不是 Android 的创意,早在 BeOS 出现的时期,Palm 就发明了 OpenBinder,并在他逝世的前几周发布其源代码。后来 George Hoffman和 Dianne Hackborn继续发展这个项目。当然,Android 也没有直接复制 OpenBinder 的所有实现,而是基于它的思想设计了自己的一套实现,就是 Binder 。想要了解更多关于 OpenBinder 的东西,请前往 http://www.angryredplanet.com/~hackbod/openbinder。 Android 的 Binder 和 Rosette Stone类似,Apps 的进程可以通过它与系统服务(进程)进行通信,Apps 之间的通信也可以通过 Binder 来进行。但是开发者不必知道 Binder 底层实现的细节,因为 Binder 向外提供了简单易用的接口,开发者只需要按需调用就可以完成进程间通信的功能。下图描述了 Binder 在系统中的位置。

二、System Services
System Services 是所有服务中最重要的一个,为什么它那么重要呢?因为系统中几乎所有的其它服务都是由它来启动的,只有启动了这些服务,app 才能调用它们,才能为用户提供相关的功能 。所有服务间的通信协作都依赖于 Binder,用户也可以通过 Binder 来创建自己的服务。除了那些需要硬件加速或者对性能要求较高的服务通常用 C/C++ 来写之外(如 sensor service 和 surface flinger),其它的大多数的服务都是用 Java 来写的。 System Services 启动起来后,它会加载其它的核心服务,并把这些服务都添加到 Service Manager 上。每个服务的启动都是耗时的,所以开机的时候,不必要的服务就不要启动,这样可以加快开机速度。如下是 SystemServer.java 的片断代码:
class ServerThread extends Thread {    private static final String TAG = "SystemServer";    private static finalString ENCRYPTING_STATE = "trigger_restart_min_framework";    private static final String ENCRYPTED_STATE = "1";     ContentResolver mContentResolver;     void reportWtf(String msg, Throwable e) {        Slog.w(TAG, "***********************************************");        Log.wtf(TAG, "BOOT FAILURE "+ msg, e);    }     @Override    public void run() {        EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_SYSTEM_RUN,        SystemClock.uptimeMillis());         Looper.prepareMainLooper();         android.os.Process.setThreadPriority(        android.os.Process.THREAD_PRIORITY_FOREGROUND); ...         Slog.i(TAG, "Battery Service");        battery = newBatteryService(context, lights);        ServiceManager.addService("battery", battery);         Slog.i(TAG, "Vibrator Service");        vibrator = newVibratorService(context);        ServiceManager.addService("vibrator", vibrator); ...         Slog.i(TAG, "Window Manager");        wm = WindowManagerService.main(context, power, display, inputManager, uiHandler, wmHandler,                               factoryTest != SystemServer.FACTORY_TEST_LOW_LEVEL,                               !firstBoot, onlyCore);         ServiceManager.addService(Context.WINDOW_SERVICE, wm);        ServiceManager.addService(Context.INPUT_SERVICE, inputManager);         ActivityManagerService.self().setWindowManager(wm);         inputManager.setWindowManagerCallbacks(wm.getInputMonitor());        inputManager.start();         display.setWindowManager(wm);        display.setInputManager(inputManager); ...

Android 系统的核心服务如下图

三、Service Manager Service Manager 就像是一个向导一样,它记录和管理着系统中所有的服务,它和 Binder 的协作是很紧密的。Service Manager 是系统中第一个启动起来的服务,它是由 Init 进程启动的。系统启动之初,启动的一些服务如下
service servicemanager /system/bin/servicemanager class core user system group system criticalonrestart restart zygoteonrestart restart mediaonrestart restart surfaceflingeronrestart restart drm

Service Manager 源码如下
package android.os;import com.android.internal.os.BinderInternal;import android.util.Log;import java.util.HashMap;import java.util.Map;public final class ServiceManager {    private static final String TAG = "ServiceManager";    private static IServiceManager sServiceManager;    private static HashMap<String, IBinder> sCache = new HashMap<String, IBinder>();    private static IServiceManager getIServiceManager() {        if (sServiceManager != null) {            return sServiceManager;        }        // Find the service manager        sServiceManager = ServiceManagerNative.asInterface(BinderInternal.getContextObject());        return sServiceManager;    }    /**     * Returns a reference to a service with the given name.     *      * @param name the name of the service to get     * @return a reference to the service, or <code>null</code> if the service doesn't exist     */    public static IBinder getService(String name) {        try {            IBinder service = sCache.get(name);            if (service != null) {                return service;            } else {                return getIServiceManager().getService(name);            }        } catch (RemoteException e) {            Log.e(TAG, "error in getService", e);        }        return null;    }    /**     * Place a new @a service called @a name into the service     * manager.     *      * @param name the name of the new service     * @param service the service object     */    public static void addService(String name, IBinder service) {        try {            getIServiceManager().addService(name, service, false);        } catch (RemoteException e) {            Log.e(TAG, "error in addService", e);        }    }    /**     * Place a new @a service called @a name into the service     * manager.     *      * @param name the name of the new service     * @param service the service object     * @param allowIsolated set to true to allow isolated sandboxed processes     * to access this service     */    public static void addService(String name, IBinder service, boolean allowIsolated) {        try {            getIServiceManager().addService(name, service, allowIsolated);        } catch (RemoteException e) {            Log.e(TAG, "error in addService", e);        }    }    /**     * Retrieve an existing service called @a name from the     * service manager.  Non-blocking.     */    public static IBinder checkService(String name) {        try {            IBinder service = sCache.get(name);            if (service != null) {                return service;            } else {                return getIServiceManager().checkService(name);            }        } catch (RemoteException e) {            Log.e(TAG, "error in checkService", e);            return null;        }    }    /**     * Return a list of all currently running services.     */    public static String[] listServices() throws RemoteException {        try {            return getIServiceManager().listServices();        } catch (RemoteException e) {            Log.e(TAG, "error in listServices", e);            return null;        }    }    /**     * This is only intended to be called when the process is first being brought     * up and bound by the activity manager. There is only one thread in the process     * at that time, so no locking is done.     *      * @param cache the cache of service references     * @hide     */    public static void initServiceCache(Map<String, IBinder> cache) {        if (sCache.size() != 0) {            throw new IllegalStateException("setServiceCache may only be called once");        }        sCache.putAll(cache);    }}

从源码中可以看出,当需要调用 ServiceManager 的功能时,要通过它的静态方法 getIServiceManager() 来获取它的 IServiceManager( sServiceManager) 对象,实际上对系统中的 Services 操作(如 getService()、addService()、checkService())是通过这个对象来完成的。
IServiceManager 类的源码如下
public interface IServiceManager extends IInterface{/*** Retrieve an existing service called @a name from the* service manager.  Blocks for a few seconds waiting for it to be* published if it does not already exist.*/public IBinder getService(String name) throws RemoteException;/*** Retrieve an existing service called @a name from the* service manager.  Non-blocking.*/public IBinder checkService(String name) throws RemoteException;/*** Place a new @a service called @a name into the service* manager.*/public void addService(String name, IBinder service, boolean allowIsolated)throws RemoteException;/*** Return a list of all currently running services.*/public String[] listServices() throws RemoteException;/*** Assign a permission controller to the service manager.  After set, this* interface is checked before any services are added.*/public void setPermissionController(IPermissionController controller)throws RemoteException;static final String descriptor = "android.os.IServiceManager";int GET_SERVICE_TRANSACTION = IBinder.FIRST_CALL_TRANSACTION;int CHECK_SERVICE_TRANSACTION = IBinder.FIRST_CALL_TRANSACTION+1;int ADD_SERVICE_TRANSACTION = IBinder.FIRST_CALL_TRANSACTION+2;int LIST_SERVICES_TRANSACTION = IBinder.FIRST_CALL_TRANSACTION+3;int CHECK_SERVICES_TRANSACTION = IBinder.FIRST_CALL_TRANSACTION+4;int SET_PERMISSION_CONTROLLER_TRANSACTION = IBinder.FIRST_CALL_TRANSACTION+5;}

下图是 Android Framework 的整体结构图

四、Zygote
Zygote 进程是一个守护进程,它的任务是启动 Apps 进程。Init.rc 的启动项中就有 Zygote,在 Service Manager 启动后,系统就启动 Zygote 进程。实际上 Zygote 进程是由 app_process 进程来启动的。我们来看一下下面这个启动进程顺序列表就知道了
service zygote /system/bin/app_process -Xzygote /system/bin --zygote --start-system-serverclass mainsocket zygote stream 660 root systemonrestart write /sys/android_power/request_state wakeonrestart write /sys/power/state ononrestart restart mediaonrestart restart netd

因为所有的 Applications 进程都是由 Zygote 进程来启动的,所以 Zygote 进程是所有 App 进程的父进程。当 app_process 进程启动 Zygote 进程的时候,它就会为其创建第一个 Dalvik VM 并调用 Zygote 进程的 main() 方法。Zygote 进程启动后,它就会加载所有必要的 Java 类及资源,启动 System Server,然后打开 /dev/socket/zygote 监听启动 application 的请求。System Server 进程是完全脱离其父进程的,它启动后就会初始化 System Services,然后启动 Activity Manager。 当 Zygote 通过/dev/socket/zygote接到 launch App(即启动 App)的请求的时候,它就会执行 fork() 方法,这个方法会在另外的地址空间中克隆当前进程。复制出来的进程中当然会和 Zygote 进程一样,拥有 Dalvik VM 实例,预加载了所有必要的 Java classes 及资源文件,这些东西都是 App 运行需要的。这样生成一个新的进程来运行 App 的效率是非常高的,而实际上,系统在这个 fork() 的实现上比我们想象的更加高效。我们都知道 Android 是运行在 Linux 上的,而 Linux 内核实现Copy On Write机制(写时复制),即在 fork() 一个进程的时候,克隆出来的子进程并不会真的全部去复制父进程的内存,当父进程的内存空间的内容没有发生变化的时候,子进程就和父进程共享这段空间。当父进程的某区域的内存因被写入而发生改变的时候,子进程才复制这一区域的内存空间。对于 Android 来说,Zygote 进程所加载的 Java classess 和公共资源是不可写的,所以实际 fork() 出来的子进程和 Zygote 进程共享了这些 classess 和资源。这样一方面使得从 Zygote 进程 fork() 出新进程的速度非常快,另一方面还大大节省了内存空间,所以 Android 每次启动一个新的 App 所需要的内存开销是很小的。 在进程系统移植的早期,如果你还不想启动 Zygote 进程,那么你在 init.rc 的适当位置加上 disabled 就行了,如下
service zygote /system/bin/app_process -Xzygote /system/bin --zygote --start-system-serverclass mainsocket zygote stream 660 root systemonrestart write /sys/android_power/request_state wakeonrestart write /sys/power/state ononrestart restart mediaonrestart restart netddisabled

Zygote 的 main() 方法
public static void main(String argv[]) { try{     // Start profiling the zygote initialization.     SamplingProfilerIntegration.start();     registerZygoteSocket();    EventLog.writeEvent(LOG_BOOT_PROGRESS_PRELOAD_START,    SystemClock.uptimeMillis());    preload();    EventLog.writeEvent(LOG_BOOT_PROGRESS_PRELOAD_END,    SystemClock.uptimeMillis());     // Finish profiling the zygote initialization.    SamplingProfilerIntegration.writeZygoteSnapshot();     // Do an initial gc to clean up after startup    gc();     // Disable tracing so that forked processes do not inherit stale tracing tags from    // Zygote.    Trace.setTracingEnabled(false);     // If requested, start system server directly from Zygote    if(argv.length != 2) {        thrownewRuntimeException(argv[0] + USAGE_STRING);    }     if(argv[1].equals("start-system-server")) {        startSystemServer();    } elseif(!argv[1].equals("")) {        thrownewRuntimeException(argv[0] + USAGE_STRING);    }     Log.i(TAG, "Accepting command socket connections");     runSelectLoop();     closeServerSocket(); } catch(MethodAndArgsCaller caller) {     caller.run(); } catch(RuntimeException ex) {     Log.e(TAG, "Zygote died with exception", ex);     closeServerSocket();     throwex; }}

然后再来看一下 Zygote 是如何启动 System Server 的
/** * Prepare the arguments and fork for the system server process. */ privatestaticbooleanstartSystemServer() throwsMethodAndArgsCaller, RuntimeException { /* Hardcoded command line to start the system server */ String args[] = { "--setuid=1000", "--setgid=1000", "--setgroups=1001,1002,1003,1004,1005,1006,1007,1008,1009,1010,1018,3001,3002,3003,3006,3007", "--capabilities=130104352,130104352", "--runtime-init", "--nice-name=system_server", "com.android.server.SystemServer", }; ZygoteConnection.Arguments parsedArgs = null; intpid; try{ parsedArgs = newZygoteConnection.Arguments(args); ZygoteConnection.applyDebuggerSystemProperty(parsedArgs); ZygoteConnection.applyInvokeWithSystemProperty(parsedArgs); /* Request to fork the system server process */ pid = Zygote.forkSystemServer( parsedArgs.uid, parsedArgs.gid, parsedArgs.gids, parsedArgs.debugFlags, null, parsedArgs.permittedCapabilities, parsedArgs.effectiveCapabilities); } catch(IllegalArgumentException ex) { thrownewRuntimeException(ex); } /* For child process */ if(pid == 0) { handleSystemServerProcess(parsedArgs); }     returntrue; }

五、Activity Manager
实际上手机桌面也是一个 Activity(即LauncherActivity),当用户在屏幕上点击一个 App 的图标的时候,会触发LauncherActivity 的 onClick() 方法。LauncherActivity 在监听到 App icon 的点击事件后,它就会通过 Binder 来获取 ActivityManager 向外提供的 handler,然后通过 handler 调用 ActivityManager 的 startActivity() 方法,即请求 ActivityManager 启动新的 App。前面我们有说到过,一个进程要与远程的进程通信时,它必须先通过系统的 Binder 来获取到远程进程向外提供的 handler 对象,然后才能通过这个 handler 调用远程进程的相关方法。当 Activity Manager 收到 startActivity() 请求的时候,它就调用 startViaZygote() 方法(通过 Zygote socket(/dev/socket/zygote) 调用)请求 Zygote 进行 fork() 操作,然后在 fork 出来的进程中加载相应的 App。
到这里,我们就可以来看看上面所讨论的各系统模块的结构是怎样的了,下图是整个 Android 系统启动的顺序图

实际上 Activity Manager 的任务远远不止上面说到的那些,它负责的任务是非常多的。这里我只再简单介绍一下它的另外一些任务(1)broadcasting intents(即广播 intent)。大家都应该知道 ANR,当发生 ANR 的时候,系统会弹出一个提示框,这个任务就是由 Activity Manager 来负责的。(2)当 Activity Manager 启动完成后,它就会向系统发出相关信息,告诉系统它已启动完成的事件。



更多相关文章

  1. Nginx系列教程(六)| 手把手教你搭建 LNMP 架构并部署天空网络电影
  2. 一款霸榜 GitHub 的开源 Linux 资源监视器!
  3. 正确认识android内存管理原理
  4. android 系统调用大全
  5. Android中的4.0新布局控件:Space和GridLayout
  6. Android(安卓)即时通讯开发小结(一)
  7. 修改Android中hosts文件的步骤详解
  8. 学徒浅析Android——Android(安卓)8.0(O)后台服务的限制和变化
  9. 2016年Windows Phone将超越iPhone

随机推荐

  1. Android黑科技动态加载(二)之Android中的
  2. Android(安卓)TextView内容过长加省略号,
  3. Android(安卓)ListView重要美化属性
  4. Kotlin 写 Android(安卓)单元测试(三),Mocki
  5. Android】Android(安卓)apk默认安装位置
  6. Android(安卓)的Margin和Padding属性以及
  7. 深入理解 Android消息处理系统的原理
  8. Google Maps Android(安卓)API v2初体验
  9. Android中的Handler的机制与用法详解
  10. 【Unity3D】Unity3D与Android的交互通信(A