通过观察nRF52服务的回调,解释两种回调函数的区别,以及为什么看不到他们回调函数的调用

张开发
2026/4/16 22:51:30 15 分钟阅读

分享文章

通过观察nRF52服务的回调,解释两种回调函数的区别,以及为什么看不到他们回调函数的调用
一、nRF52的两种回调我们在服务初始化的时候会有回调函数的传入这个回调到底是干什么的简单来说 它是你告诉服务“当这个服务发生重要事情时请通知我调用我的这个函数”。具体作用对于 led_write_handlerLBS 服务当手机写入LED Characteristic 时服务会调用 led_write_handler并把写入的值开/关传给你。你可以在里面控制实际的 LED 灯。对于 on_bas_evtBattery Service当手机启用或禁用电池电量通知Notification时服务会调用 on_bas_evt并告诉你事件类型BLE_BAS_EVT_NOTIFICATION_ENABLED 或 DISABLED。你可以在里面启动/停止电池测量定时器。两种回调最根本的区别就是“事件产生的方式”不同二、通过bsp_event_handler和on_bas_evt分析蓝牙按键自动使能通知下的 bsp_event_handler 回调函数调用蓝牙电池公共服务下的 on_bas_evt 回调函数调用为什么搜索不到回调函数的调用1. on_bas_evt 和 led_write_handler为什么搜不到因为在事件观察者中中断回调函数是被函数指针evt_handler被调用的它的实际调用路径是这样的多层间接你在 services_init() 中注册回调当 BLE 事件发生时例如手机写 Characteristic 或启用通知SoftDevice 产生具体 BLE 事件如 BLE_GATTS_EVT_WRITEnrf_sdh_ble 把事件分发给所有注册的Observer包括服务注册的 Observer服务内部的处理函数被调用BAS 服务 → ble_bas_on_ble_evt()位于 ble_bas.cLBS 服务 → ble_lbs_on_ble_evt()位于 ble_lbs.c服务内部函数解析事件后通过函数指针间接调用你的回调关键点 on_bas_evt 和 led_write_handler 是通过函数指针evt_handler 或 led_write_handler被调用的而不是在代码中直接出现 on_bas_evt(...) 或 led_write_handler(...) 的形式。因此你在整个工程中全局搜索 on_bas_evt( 带括号的调用是搜不到的这属于正常现象。二、重要总结只要是 BLE 服务相关的回调led_write_handler、on_bas_evt、ble_evt_handler全部 ← 主循环上下文全部 ←SoftDevice产生事件事件在事件观察者中触发回调只有外设驱动ADC、定时器、UART、GPIO才 ←硬件产生中断中断产生事件事件在事件观察者中触发回调SoftDevice 会产生很多具体可见的事件你在代码里完全能看到不是“看不到的”。常见例子你在代码中已经处理过的BLE_GAP_EVT_CONNECTED → 设备连接成功BLE_GAP_EVT_DISCONNECTED → 设备断开连接BLE_GATTS_EVT_WRITE → 手机写了某个 Characteristic比如写 LED、写 CCCD 使能通知BLE_GATTS_EVT_TIMEOUT、BLE_GATTC_EVT_TIMEOUT → GATT 超时

更多文章