Binder简介,摘选自《Android系统源代码情景分析》
1. 整体关系
Linux内核的进程间通信机制:管道Pipe,信号Signal,消息队列Message,共享内存ShareMemory,插口Socket等。
Android独特的IPC,Binder,基于CS架构,优势:进程间传输数据时,只需要执行一次复制操作,提高效率,节省内存空间。
提供服务的是Server进程,访问服务的进程是Client进程,一个Server进程可以运行多个组件来(Service组件)给Client进程提供服务,一个Client进程可以运行多个组件(Client组件)来请求服务。Server进程和Client进程都维护了一个Binder线程池,用来处理进程间通信请求,可并发操作。
Server进程和Client进程间的通信依靠运行在内核空间的Binder驱动程序来进行。Binder驱动程序向用户空间暴露了一个设备文件/dev/binder,使得应用程序进程可以间接地通过它来建立通信通道。
Service组件在启动时,会将自己注册到一个ServiceManager组件中,已便Client组件可以该组件找到它。因此,我们将ServiceManager组件称为Binder进程间通信机制的上下文管理者,同时由于它也需要与普通的Server进程和Client进程通信,我们也将它看作是一个Service组件,只不过它是一个特殊的Service组件。
Client、Service和ServiceManager运行在用户空间,Binder驱动程序运行在内核空间,其中,ServiceManager和Binder驱动程序由系统负责提供,Client和Service组件由应用程序来实现。
Client、Service和ServiceManager均是通过系统调用open、mmap和ioctl来访问设备文件/dev/binder,从而实现与Binder驱动程序的交互,从而达到间接地执行进程间通信的目的。
每一个Service组件在Binder驱动程序中都有一个对应的Binder实体对象binder_node,用来描述它在内核中的状态。
2. Service Manager
Service Manager是Binder进程间通信机制的核心组件之一,它扮演着Binder进程间通信机制上下文管理者的角色,同时负责管理系统中的Service组件,并且向Client组件提供获取Service代理服务对象的服务。
Service Manager运行在一个独立的进程中,因此,Service组件和Client组件也需要通过进程间通信机制来和它交互,也就是Binder进程间通信机制,所以,Service Manager也是一个特殊的Service组件。
Service Manager是由init进程负责启动的,而init进程是在系统启动时启动的,因此,Service Manager也是在系统启动时启动的。启动过程由三个步骤组成:第一步是调用函数binder_open打开设备文件/dev/binder,以及将它映射到本进程的地址空间;第二步是调用函数binder_become_context_manager将自己注册为Binder进程间通信机制的上下文管理者;第三步是调用函数binder_loop来循环等待和处理Client进程的通信请求。
3. Service代理对象的获取过程
Service组件将自己注册到Service Manager中之后,它就在Server进程中等待Client进程将进程间通信请求发送过来。Client进程为了和运行在Server进程中的Service组件通信,首先要获得它的一个代理对象,这是通过Service Manager提供的Service组件查询服务来实现的