|
FireBlue QN9021 QN902x Proximity Reportor profile(防丢器) 之源码分析 (三)广播
发表于 2015-4-3 11:38:53
浏览:11040
|
回复:1
打印
只看该作者
[复制链接]
楼主
本帖最后由 dezhi 于 2015-4-3 14:41 编辑
每一对蓝牙设备的的通信都有一个连接的过程,而蓝牙4.0 与传统蓝牙的连接过程又有些不一样的,BLE4.0 的连接过程的先由从机(这里自然就是防丢器)先通过广播通道广播数据(advertising),主机(手机)监听广播通道,如果监听到有广播数据,则向其发送扫描请求(scan request),广播者接受到扫描请求后回复扫描响应(scan response)。流程如下图:
从机的广播关键有3点
1.广播的数据
2.扫描响应的数据
3.广播的时间间隙
回想一下FireBlue 开发板 烧录防丢器方案程序 上电后,需要向上拨动 joystick 才会开始广播,我们就从这里入手,找到按键处理函数,得到关键代码如下:- app_gap_adv_start_req(GAP_GEN_DISCOVERABLE|GAP_UND_CONNECTABLE,
- app_env.adv_data, app_set_adv_data(GAP_GEN_DISCOVERABLE),
- app_env.scanrsp_data,
- app_set_scan_rsp_data(app_get_local_service_flag()),
- GAP_ADV_FAST_INTV1, GAP_ADV_FAST_INTV2);
复制代码
F12 得到函数原型与参数注释如下
- ****************************************************************************************
- * @brief Start the device to advertising process. *//**
- *
- * @param[in] mode Device mode to set, possible values are:
- * - GAP_NON_DISCOVERABLE
- * - GAP_GEN_DISCOVERABLE
- * - GAP_LIM_DISCOVERABLE
- * - GAP_NON_CONNECTABLE
- * - GAP_UND_CONNECTABLE
- * - GAP_DIR_CONNECTABLE
- * @param[in] adv_data Pointer to advertising data used in the advertising packets
- * @param[in] adv_data_len The length of advertising data
- * @param[in] scan_rsp_data Pointer to Scan Response data used in the advertising packets
- * @param[in] scan_rsp_data_len The length of Scan Response data
- * @param[in] adv_intv_min Minimum interval for advertising
- * @param[in] adv_intv_max Maximum interval for advertising
- * @response GAP_SET_MODE_REQ_CMP_EVT
- * @description
- *
- * This function is used to set the device to advertising.
- *
- * @note
- * The stack will keep advertising with new parameters if calling this function in advertising state.
- * The adv_intv_min and adv_intv_max shall not be set to less than 0x00A0(100 ms) if the mode
- * is GAP_NON_DISCOVERABLE.
- ****************************************************************************************
- */
- void app_gap_adv_start_req(uint16_t mode, uint8_t *adv_data, uint8_t adv_data_len,
- uint8_t *scan_rsp_data, uint8_t scan_rsp_data_len,
- uint16_t adv_intv_min, uint16_t adv_intv_max);
复制代码
第一个参数为广播的模式,
第二、第三为广播的数据的指针和长度。
第四、第五为扫描响应的数据指针和长度。
第六、第七为广播间隙的最小和最大值。
跟进app_gap_adv_start_req 得知,实质是TASK_APP 向 TASK_GAP 发送了一个GAP_SET_MODE_REQ 消息,消息携带了的参数为广播的内容。
- struct gap_set_mode_req *msg = KE_MSG_ALLOC(GAP_SET_MODE_REQ, TASK_GAP, TASK_APP,
- gap_set_mode_req);
复制代码
应用层与协议栈的交互是通过消息投递系统实现的,当TASK_GAP层完成设置广播参数的设定后会向TASK_APP,发送GAP_SET_MODE_REQ_CMP_EVT 消息,该消息的处理函数为:
- {GAP_SET_MODE_REQ_CMP_EVT, (ke_msg_func_t) app_gap_set_mode_req_cmp_evt_handler}
复制代码
跟进该函数,函数根据任务当前状态做出相应的处理。
跟进app_set_adv_data(GAP_GEN_DISCOVERABLE)
从源码解析出来的函数功能为设置app_env.adv_data 即广播数据为发现模式和名字
跟进app_set_scan_rsp_data(app_get_local_service_flag())从源码解析出来的函数功能为设置app_env.scanrsp_data 即扫描响应数据为Profiles 的UUID
前面提到的 2个函数所组织的返回数据类型参考蓝牙标准规范v4.0,以下为从规格书截图,
所提供截图为广播、扫描响应数据格式 ,可以广播数据的内容,这里还得读者自己去查阅,理解得更为通透。
在两个广播事件之间有一个间隔,如下图
计算公式为:T_advEvent = advInterval + advDelay
其中:
advInterval 应为0.625ms 的整倍数,并且在20ms~10.24s 之间
advDelay 是一个随机值 ,在 0~10ms 之间
这里的广播间隙会影响BLE 的功耗,如果时间间隙过小,会频繁广播,加大功耗,间隙过大,被发现的过程就会增大,这里还得按照需求适当调整。
最后我们用Light Blue 探测 广播的内容,均为所设置的 内容,包括了发现模式,设备名称,Profiles UUID。
欢迎关注小弟博客http://blog.csdn.net/q562359345
|
|