joshuayingwhat IT Engineer

二:binder驱动情景分析—数据结构

2024-09-08

server端在binder中提供的服务会以一个binder_node的结构存储在binder驱动中。

……

server传入一个flag_binder_object给驱动在内核驱动里会为每个服务创建一个binder_node。binder_node中有一个proc,binder_node.proc = server. servicemanager在内核驱动创建binder_ref,引用binder_node.其中binder_ref.desc = 1,2,3,….在用户态创建服务链表其中服务的名字.name,还有服务的handle == 就等于desc中的描述 client程序向servicemanager查询服务,传一个服务的名称name。

servicemanager返回一个handle,是返回给内核态驱动程序

驱动程序在servicemanager的binder_ref中根据handle找到binder_ref,再根据binder_ref.node找到binder_node。最后给client创建新的binder_ref,其中desc从1开始,驱动返回desc给client,它即为handle

handle是进程A对进程B提供的服务s的引用,驱动程序会通过handle找到目的进程 client程序发送数据给handle:驱动里面根据handle找到binder_ref,再根据binder_ref找到binder_node,根据binder_node然后再通过binder_proc找到server进程。 注释:客户端想要访问到server中的服务需要在驱动中通过一个binder_ref的结构指向到binder_node这样才能知道具体服务,而client端会有一个handle(这个handle就是client端通过查询servicemanager获取到的,handle就是指向的server)通过handle找到binder_ref,在根据binder_ref找到binder_node,根据binder_node找到server进程。

数据传输过程

client——> server

1.client首先要构造数据,然后调用ioctl发数据

2.驱动里根据handle最终可以找到server进程

3.把数据放入进程的binder_proc.todo,然后唤醒server

4.休眠

5.被唤醒

6.从todo链表取出数据,返回用户空间

server端

1.先读,后休眠

  1. 被唤醒
  2. 从todo链表取出数据,返回用户空间
  3. 处理
  4. 把结果写给client,放入client的binder_proc.todo,顺便把client程序唤醒

数据如何复制

binder方法:

1.server mmap:server程序的用户态可以直接访问驱动中某块buffer。

2.client程序构造数据,驱动copy_from_user将数据从用户态拷贝到内核态。

3.server程序可以在用户态直接使用数据,因此只需要一次拷贝。

数据复制一次针对的是数据本身,对于数据头还是需要复制2次。





参考:
https://blog.csdn.net/freekiteyu/article/details/70082302

http://gityuan.com/2015/10/31/binder-prepare/

https://weishu.me/2016/01/12/binder-index-for-newer/


Similar Posts

Content