Android面试Android跨进程通信之Binder

Posted Rose J

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Android面试Android跨进程通信之Binder相关的知识,希望对你有一定的参考价值。

Binder是啥?

1.binder是一种进程间通信机制

2.binder是一种基于C/S架构,运行在内核空间的binder驱动程序,进程间通过dev/binder这个文件来建立通信通道

:在linux中因为进程间是隔离的,而用户空间,需要通过系统调用才能访问到内核空间,

(内存被操作系统分为两块,用户控件和内核空间,用户空间是用户程序代码运行的地方,内核空间是内核代码运行的地方,用户空间之间是隔离的,用户空间和内核空间也是隔离的)

img

所以我们就可以通过binder驱动来进行客户端和服务端的通信

img

Open函数用来打开一个文件,建立一个文件描述符到文件路径的映射,建立文件标识。

mmap是一种内存映射文件的方法,即将一个文件或者其它对象映射到进程的地址空间,实现文件磁盘地址和进程虚拟地址空间中一段虚拟地址的一一对映关系

ioctl
:是设备驱动程序中设备控制接口函数,一个字符设备驱动通常会实现设备打开、关闭、读、写等功能,在一些需要细分的情境下,如果需要扩展新的功能,通常以增设
ioctl() 命令的方式实现。
3.binder 是一个java类,实现了IBinder接口,具有跨进程通信的功能

Binder基础概念

android中的Binder机制中,主要涉及四部分系统组件,分别是ServiceManager、Binder驱动、Client、Server,其中Client、Server、ServiceManager运行在各自的用户空间中,Binder驱动运行在内核空间中。

ServiceManger(SM): 负责注册管理所有的系统Server,并为Client提供查询Server的功能,SM更像是Server和Client中间的一个中介。而SM、Server、Client这三个组件都是运行在各自独立的进程中的。所以这三者之间的通信也是进程间的通信,而且也是采用的Binder机制来进行进程间通信的。在这个通信的过程中,ServiceManger除了要管理各种Server,同时自己也充当着Server的角色。

Server: Server通过SM的远程接口,将自己的Binder服务注册到SM中,然后将服务启动起来,同时会启动Binder线程池,等待客户端请求。

Client: Client通过SM的远程接口,获取到在SM中相对应的远程Server代理对象进行通信。

Binder驱动: Binder驱动是整个Binder通信机制的核心,进程间的数据交换就是通过它来完成的。如果Client要将数据传递给Server,正常情况下,Client把数据从自己的进程空间拷贝到内核空间,然后在从内核空间拷贝到Server的进程空间,这样Server就拿到了Client传递的数据,但是这个过程进行了两次内存拷贝。而通过Binder驱动,同一个物理页面,一方面映射到Server进程虚拟地址空间,另一方面又映射到内核虚拟地址空间。这样,只需要Client把要传递的数据拷贝到内核空间中,然后将拷贝到内核空间的数据同时映射到Server进程虚拟地址空间和内核虚拟地址空间,这样Server和内核就可以共享该数据了,一次内存拷贝就可以了。

Binder优势

在Linux中,也有进程间通信机制

管道,文件共享,socket,信号量,消息队列

既然linux已经有进程间通信机制,为什么Android还要自己去创建一个binder去进行进程间通信?

socket和信号量,消息队列,管道原理都比较相像,所以就拿socket作比较啦

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-neD5S60r-1620116882270)(C:\\Users\\Lenovo\\AppData\\Roaming\\Typora\\typora-user-images\\1620044892798.png)]

1.性能,首先性能上,binder只需要拷贝一次,仅次于共享内存,

2.特点,binder是基于C/S架构的,易用性很高,而共享内存控制复杂,会存在进程数据同步的问题,所以易用性较差,socket虽然也基于C/S架构,但是作为一款通用的接口,他的传输效率低,开销大

3.安全性,1.传统的ipc机制,是依赖上层协议的,系统是无法追踪到的,比方说socket进行进程间通信,ip地址是可以随便填的,

而binder是会为每个app分配用户IDuid,通过用户ID,就可以追踪到每一个app,这样的话用户做了什么操作,系统都可以追踪到位

2.传统的ipc机制访问的的接入点是开放的,谁都可以去访问 ,就好像公交车,只要知道站点想上就上,binder是同时支持实名和匿名,实名的话就相当于公开的,想访问就访问,但是匿名就像是滴滴打车,通过平台来返回一个新司机,这个匿名也是一样,需要系统返回一个IBinder对象,然后才能去访问对应的服务

实名—>对应系统服务

匿名—>对应自己创建的服务 -->由系统返回IBinder对象然后才能去访问

Binder是如何做到一次拷贝的?

传统

传统的传输数据是通过系统调用copy_from_user将数据从用户空间copy到内存缓冲区,然后再通过系统调用copy_to_user从内核空间copy到用户空间,所以需要进行两次拷贝

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-RHsLKixG-1620116882272)(C:\\Users\\Lenovo\\AppData\\Roaming\\Typora\\typora-user-images\\1620109969865.png)]

Binder

但是binder一次拷贝的原理是,首先发送数据端copy_from_user将数据从用户空间拷贝到内存地址空间后,然后内核直接将数据放到一个物理内存,而这个物理内存和我们数据接收方是共享的,换句话说内核空间映射到一个物理内存,接收方的地址空间也映射到这同一块物理空间,所以接收方就可以直接拿到数据

(内核空间的虚拟内存 和 接收方的用户空间的虚拟内存 同时映射在同一块物理空间,如果内核往这块物理内存放进数据,那么接收方也能从这块物理内存拿到数据)

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-2ZMHhXbO-1620116882273)(C:\\Users\\Lenovo\\AppData\\Roaming\\Typora\\typora-user-images\\1620109938705.png)]

MMAP的原理

在Linux中,通过将一个虚拟内存区域与一个磁带的对象(相当于物理内存)关联起来,以初始化这个虚拟内存区域的内容,这个过程称为内存映射(memory mapping)

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-83tjd8ST-1620116882276)(C:\\Users\\Lenovo\\AppData\\Roaming\\Typora\\typora-user-images\\1620111928035.png)]

:用户空间不能直接对文件进行读写

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-n7zsV3DA-1620116882278)(C:\\Users\\Lenovo\\AppData\\Roaming\\Typora\\typora-user-images\\1620111890506.png)]

Binder机制是如何进行跨进程的?

简述:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-GkLauyXk-1620116882279)(C:\\Users\\Lenovo\\AppData\\Roaming\\Typora\\typora-user-images\\1620109938705.png)]

数据发送方通过copy_from_user,将数据拷贝到内核空间,然后binder驱动会创建一块物理内存,然后让内核空间和接收方的用户空间同时映射到这快物理内存里面去,这样的话,发送方通过copy_from_user把数据拷贝到内核空间后,这数据就相当于直接到了接收方的用户空间去了。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-w1EXJW7x-1620116882280)(C:\\Users\\Lenovo\\Documents\\2345截图\\QQ图片20210504160843.png)]

实现一个binder通信实例,需要经过以下步骤:
(1)获得ServiceManager的对象引用

(2)向ServiceManager注册新的Service

(3)在Client中通过ServiceManager获得Service对象引用

(3)在Client中发送请求,由Service返回结果。

Android中怎么使用Binder?

Binder是客户端和服务端进行通信的媒介,当bindService的时候,服务端会返回一个包含服务端业务调用的Binder对象,通过这个Binder对象,客户端就可以获取服务端提供的服务或者数据,这里的服务包括普通服务和基于AIDL的服务

img

以上是关于Android面试Android跨进程通信之Binder的主要内容,如果未能解决你的问题,请参考以下文章

Android Framework实战开发视频--跨进程通信之Unix Socket通信

Android Framework实战开发视频--跨进程通信之Socket通信

Android Framework实战开发视频--跨进程通信之Socket通信

朝花夕拾一篇文章搞懂Android跨进程通信

Android Framework实战开发视频--跨进程通信之课程介绍

Android Framework实战开发视频--跨进程通信之课程介绍