1.Binder系统_C程序示例_框架分析

来源:互联网 发布:人民日报图文数据库 编辑:程序博客网 时间:2024/06/06 03:57

1>. Android Framework框架 之 Binder系统

1<. Binder系统核心

1<. IPC 过程间通信

假设有两个进程 A: Client , B: Server;  1<. 源      :A 进程  2<. 目的    :    1<. B 向 ServiceManager 注册 led 服务    2<. A 向 ServiceManager 查询 led 服务,得到一个Handle(指向进程B)    3<. 数据本身: 属于双方约定好的数据格式, eg: char buf[50]

2<. RPC 远程过程调用

  RPC 是基于 IPC 的一些封装  1<. 问题:    调用哪一个函数:Server 的函数编号    传给它什么参数 & 返回值:通过 IPC 的 buf 参数。

2<. 分析参考代码

/* 参考代码 : android_system_code\frameworks\native\cmds\servicemanager */

  • binder.h :
  • binder.c :封装好的 C 函数1<. binder_call /* 实现远程调用 */  1<. 函数定义:    int binder_call(struct binder_state *bs,        struct binder_io *msg, struct binder_io *reply,        uint32_t target, uint32_t code)  2<. 函数功能:    1<. 向谁发数据 : taget    2<. 调用那个函数 : code    3<. 提供什么参数 : msg    4<. 返回值 : reply  3<. binder_call 内部实现    1<. 构造数据 : 用 binder_io 来描述数据    [中间过程] : binder_io => binder_write_read 过程:    2<. 调用 ioctl 发送数据       res = ioctl(bs->fd, BINDER_WRITE_READ, &bwr);      1<. 解析 bwr : struct binder_write_read bwr;        1<. 结构体定义:                      struct binder_write_read {            signed long write_size; /* bytes to write */            signed long write_consumed; /* bytes consumed by driver */            unsigned long   write_buffer;            signed long read_size;  /* bytes to read */            signed long read_consumed;  /* bytes consumed by driver */            unsigned long   read_buffer;          };    3<. ioctl 也会接受数据,收到一个 binder_write_read 结构体        同时需要转换为 binder_io。
  • bctest.c : 注册服务的过程:1<. bs = binder_open(128*1024);2<. svcmgr_publish(bs, svcmgr, argv[1], &token);  1<. binder_call(bs, &msg, &reply, target, SVC_MGR_ADD_SERVICE)    1<. 函数定义:      int binder_call(struct binder_state *bs,            struct binder_io *msg, struct binder_io *reply,            uint32_t target, uint32_t code)    2<. 参数解析:      target : BINDER_SERVICE_MANAGER  0U      code   : 表示要调用 servicemanager 中的 "addservice" 函数      msg    : 含有服务的名字      reply  : 它会收到 servicemanager 回复的数据      bs     : 被打开的驱动的fd;获取服务的过程:1<. bs = binder_open(128*1024);2<. handle = svcmgr_lookup(bs, svcmgr, "alt_svc_mgr");  1<. binder_call(bs, &msg, &reply, target, SVC_MGR_CHECK_SERVICE)    1<. 函数定义:      int binder_call(struct binder_state *bs,            struct binder_io *msg, struct binder_io *reply,            uint32_t target, uint32_t code)    2<. 参数解析:      target : BINDER_SERVICE_MANAGER  0U      code   : 表示要调用 servicemanager 中的 "getservice" 函数      msg    : 含有服务的名字      reply  : 它会收到 servicemanager 回复的数据      bs     : 被打开的驱动的fd;
  • service_manager.c :1<. bs = binder_open(128*1024);2<. binder_become_context_manager(bs);3<. binder_loop(bs, svcmgr_handler);    1<. res = ioctl(bs->fd, BINDER_WRITE_READ, &bwr);    /* 解析并且处理数据 */    2<. binder_parse(bs, 0, (uintptr_t) readbuf, bwr.read_consumed, func);      /* 解析 */      1<. res = func(bs, txn, &msg, &reply);      /* 处理 */      2<. svcmgr_handler        /* 根据传入的命令 */        switch(txn->code) {        /* 获取服务 */        1<. SVC_MGR_GET_SERVICE / SVC_MGR_CHECK_SERVICE        /* 注册服务 */        2<. SVC_MGR_ADD_SERVICE     }    /* 回复 */    3<. binder_send_reply(bs, &reply, txn->data.ptr.buffer, res);
  • 图片


3<. 如何写应用程序

 1<. client    1<. binder_open   2<. 获得服务:handle   3<. 构造参数: binder_io   4<. 调用binder_call(hande, code, ...), 并且传入一些必要的参数   5<. 分析返回binder_io, 取出返回值 2<. server   1<. binder_open   2<. 注册服务   3<. ioctl(BINDER_WRITE_READ);   4<. 解析数据:解析 binder_write_read.readbuf->binder_transationdata这个结构体   5<. 根据第四步解析出来的 code 决定调用那个函数,并且从 binder_io 中取出参数,传入   6<. 将返回值转换为 binder_io 发送给 client

阅读全文
0 0
原创粉丝点击