当前位置:操作系统 > 安卓/Android >>

Android源码分析]hciops的初始化

凡是真正分析过bluez代码或者debug过相关bug的童鞋,一定对hciops非常熟悉吧,是的,它是各个event的处理中心,承接着controller到上层host的各个方面的交互,本文就来详细分析一下它的初始化过程。
 
2.3.5.2 add_plugin分析
 
add_plugin只是单纯地把plugin加入到系统里面,或者就是plugin的初始化,来看看吧
 
[cpp] 
static gboolean add_plugin(void *handle, struct bluetooth_plugin_desc *desc)  
{  
    struct bluetooth_plugin *plugin;  
    //检查是否有init函数,没有直接返回  
    if (desc->init == NULL)  
        return FALSE;  
    //检查一下version是不是匹配,那边初始化的时候就是用的VERSION,所以,没有问题  
    if (g_str_equal(desc->version, VERSION) == FALSE) {  
        error("Version mismatch for %s", desc->name);  
        return FALSE;  
    }  
  
    DBG("Loading %s plugin", desc->name);  
    //初始化bluetooth_plugin结构体  
    plugin = g_try_new0(struct bluetooth_plugin, 1);  
    if (plugin == NULL)  
        return FALSE;  
  
    plugin->handle = handle;  
    plugin->active = FALSE;  
    plugin->desc = desc;  
    //按照priority来加入到plugins list中  
    plugins = g_slist_insert_sorted(plugins, plugin, compare_priority);  
  
    return TRUE;  
}  
2.3.5.3  hciops的init函数分析
 
初略一看,hciops的init函数还是蛮简单的,就是一句话:
 
[cpp] 
static int hciops_init(void)  
{  
    DBG("");  
    //这个我们比较熟悉,就是把hci_ops注册进来呗  
    //这里我们详细分析一下,究竟做了些什么  
    return btd_register_adapter_ops(&hci_ops, FALSE);  
}  
[cpp] 
int btd_register_adapter_ops(struct btd_adapter_ops *ops, gboolean priority)  
{  
    //其实就是判断setup函数是否存在,具体的带用会在后面的adapter_ops_setup中  
    if (ops->setup == NULL)  
        return -EINVAL;  
    //根据priority,决定吧ops加入到ops_candidates的头还是尾中,这个还是蛮简单的吧  
    if (priority)  
        ops_candidates = g_slist_prepend(ops_candidates, ops);  
    else  
        ops_candidates = g_slist_append(ops_candidates, ops);  
  
    return 0;  
}  
2.3.6 adapter_ops_setup的分析
 
其实这个函数很简单,就是setuphciops,我们来分析一下
 
[cpp] 
int adapter_ops_setup(void)  
{  
    GSList *l;  
    int ret;  
    //ops_candidates是在hciops的init函数中加入的  
    if (!ops_candidates)  
        return -EINVAL;  
    //这里也没有别的,就只有hciops,调用他的setup即可  
    for (l = ops_candidates; l != NULL; l = g_slist_next(l)) {  
        struct btd_adapter_ops *ops = l->data;  
        //Setup见下面的分析  
        ret = ops->setup();  
        if (ret < 0)  
            continue;  
        //同时需要把这个ops和adapter_ops相关联  
        adapter_ops = ops;  
        break;  
    }  
  
    return ret;  
}  
hciops的setup函数也是在对应的ops中定义的,我们去看一下:
 
[cpp] 
static int hciops_setup(void)  
{  
    struct sockaddr_hci addr;  
    struct hci_filter flt;  
    GIOChannel *ctl_io, *child_io;  
    int sock, err;  
  
    DBG("");  
    //先判断一下有没有pipe过  
    if (child_pipe[0] != -1)  
        return -EALREADY;  
    //创建一个管道,child_pipe[0]为读入端,child_pipe[1]为写入端  
    if (pipe(child_pipe) < 0) {  
        err = -errno;  
        error("pipe(): %s (%d)", strerror(-err), -err);  
        return err;  
    }  
      
//一个io channel进行监听,若是有数据,就会去读了  
    child_io = g_io_channel_unix_new(child_pipe[0]);  
    g_io_channel_set_close_on_unref(child_io, TRUE);  
    child_io_id = g_io_add_watch(child_io,  
                G_IO_IN | G_IO_ERR | G_IO_HUP | G_IO_NVAL,  
                child_exit, NULL);  
    g_io_channel_unref(child_io);  
    //创建并且bind hci socket  
    /* Create and bind HCI socket */  
    sock = socket(AF_BLUETOOTH, SOCK_RAW, BTPROTO_HCI);  
    if (sock < 0) {  
        err = -errno;  
        error("Can't open HCI socket: %s (%d)", strerror(-err),  
                                -err);  
        return err;  
    }  
  
    /* Set filter */  
    //这里只关注bluez stack的internal的event,这个就是DEV_REG,DEV_UP之类的event的处理了  
    hci_filter_clear(&flt);  
    hci_filter_set_ptype(HCI_EVENT_PKT, &flt);  
    hci_filter_set_event(EVT_STACK_INTERNAL, &flt);  
    if (setsockopt(sock, SOL_HCI, HCI_FILTER, &flt, sizeof(flt)) < 0) {  
        err = -errno;  
        error("Can't set filter: %s (%d)", strerror(-err), -err);  
        return err;  
    }  
  
    memset(&addr, 0, sizeof(addr));  
    addr.hci_family = AF_BLUETOOTH;  
&n
补充:移动开发 , Android ,
CopyRight © 2012 站长网 编程知识问答 www.zzzyk.com All Rights Reserved
部份技术文章来自网络,