controller层任务
接上一篇中说的controller层通过任务线程来实现一个事件的大循环。该循环以任务
的形式来处理event:host层发来的、controller层本身的一些事件。nimble遵循
host-controller interface transport协议,因此来自host层的event就不足为奇了,
至于controller层本身的事件,通过断点调试与Log打印发现的,但是对其还没有更
具体的分析。
controller层任务循环处打断点分析
总的来说,使用keil断点调试用着还挺舒服的,可以随时断点分析程序流程,就是
中断处理的时候有点难受,一旦调试就很难就行连接了。断点调试后肯定影响radio等
外设了,会造成无法连接的。
ble_ll.c文件,然后点击调试就可以啦,使用单步跳入和单步跳过进行分析。断点处是
从队列中获取到事件,而ble_npl_event_run(ev)则是运行对应回调的。
controller层任务循环Log输出ev中一些数据
Log输出,其实就是串口输出一些信息,便于调试以掌握程序运行流程。通过查看
ev结构体变量,可以发现其有三个变量,其中fn和arg很重要(回调函数与参数)。通过
Log打印处其中参数,来分析其意义。
**************现在觉的应该是信道切换的**********************,在此处打个断点看看,
最后一张图片应该可以说明这个吧,ble_ll_adv_event_done就是controller层的一个、
事件
struct ble_npl_event *ev;
struct ble_npl_event
{
bool queued;
ble_npl_event_fn *fn;
void *arg;
};
void
ble_ll_task(void *arg)
{
struct ble_npl_event *ev;
#ifdef RIOT_VERSION
ble_npl_eventq_init(&g_ble_ll_data.ll_evq);
#endif
/* Init ble phy */
ble_phy_init();
/* Set output power to 1mW (0 dBm) */
ble_phy_txpwr_set(MYNEWT_VAL(BLE_LL_TX_PWR_DBM));
/* Tell the host that we are ready to receive packets */
ble_ll_hci_send_noop();
ble_ll_rand_start();
while (1) {
ev = ble_npl_eventq_get(&g_ble_ll_data.ll_evq, BLE_NPL_TIME_FOREVER);
assert(ev);
ble_npl_event_run(ev);
if(ev->arg) rt_kprintf("%x %x\r\n",(*(int*)ev->arg),(*(int*)(ev->arg+4)));
}
}
总结
controller层的任务循环,就是不断地接受来自host层和controller层本身
的event。host层不用多说,规范中定义了,而controller层呢,这里猜测可
能是一个广播周期结束或者信道切换等。
这就是我平时用的两种分析方法。哈哈