无线MCU调试技巧汇总

对于初次接触无线mcu产品的人来说,拿到恩智浦的sdk后肯定需要一段时间适应,其实无线mcu也是mcu,只是在mcu的基础上增加了一个稍显复杂的射频单元,另外围绕这个射频单元增加了一些辅助组件,比如framework,freertos等,当然因为射频部分具有最高的优先级,所以用户的应用必须附属在无线系统之上。
恩智浦旗下的无线mcu采用了与普通mcu相同的sdk架构,对于芯片间的切换其实是很方便的。
下面是我总结的一些开发无线mcu的经验,希望能帮到刚开始使用nxp无线mcu的同学们。
本文由如下几部分组成:
开发环境
如何开始
低功耗模式下的代码调试
空中包时序分析
controller enhanced notifications
timer、event及其它资源分配
发射功率调节
panic分析
本文所有实例基于kw38芯片讲解,但对于同一系列的其它kw3x芯片同样适用,对于使用同一sdk架构的其它无线芯片(如qn9080,qn9090)大多数适用。
开发环境
sdk版本:sdk_2_6_13_frdm-kw38
sdk下载地址:https://mcuxpresso.nxp.com
开发板:frdm-kw38
ide:iar embeddedworkbench for arm version 8.50
演示代码:https://github.com/n40e116/sdk_2_6_13_frdm-kw38.git
如何开始
如果是第一次使用nxp的无线mcu,请先浏览sdk中的如下两个文件:
bluetooth low energy quick start guide.pdf
bluetooth low energy demo applicationsuser's guide.pdf
本文中的所有演示操作基于项目temp_sens/freertos,之所以选择这个工程是因为它包含了低功耗和串口输出等功能,方便演示。
sdk中所有项目都包含bm和freertos两个版本,其中bm是不含rtos的版本,freertos是集成了rtos的版本。
注意sdk中并非所有项目默认都是使能低功耗的,只有如下工程包含低功耗处理:
adv_ext_central /adv_ext_peripheral
beacon
ble_fscibb
hrs
temp_coll / temp_sens
建议在程序中增加打印复位源的功能,方便异常时的检测,实例代码如下:
void bleapp_init(void){… (void)serial_print(gappsermgrif, rnreset source:, gnoblock_d); serial_printdec(gappsermgrif, pwr_getsystemresetstatus()); (void)serial_print(gappsermgrif, rn, gnoblock_d);}  
如果你已经足够熟悉sdk的框架,现在准备开始开发自己的产品,强烈建议你只修改项目所在工程目录下的文件,因为其它文件是所有项目公用的,修改后可能导致其它项目的编译或运行问题,另外这样做的好处是,后续如果需要升级sdk,只需对比这些文件,进行移植即可,可大大节省升级时间。
如下是演示项目的工程目录结构,可以在这里修改或增加文件:
sdk_2_6_13_frdm-kw38boardsfrdmkw38wireless_examplesbluetoothtemp_sens
低功耗模式下的代码调试
如果直接将未经修改的temp_sens工程下载kw38中并开启调试,很快你就会收到如下错误提示,这是因为kw38进入了低功耗模式, swd引脚失去调试功能,j-link和kw38失去了通讯,所以调试器断开了。
要在低功耗的模式下调试代码,我们需要定时唤醒kw38,让debugger认为被调试芯片是一直在线的,我们可以让kw38一直处于广播或连接状态,这样kw38为了处理蓝牙事件会定时唤醒,从而保持住swd连接。
另外kw38进入的低功耗模式也是有选择的,需要进入low power mode 1。如下是对应的代码修改:
#define gappstartafterreset_d 1#define gappdeepsleepmode_c 1static void advertisingtimercallback(void* pparam){ /* stop advertising */// if (madvstate.advon)// {// (void)gap_stopadvertising();// }}bleapp_connectioncallback() -> case gconnevtdisconnected_c:#if defined(cpwr_usepowerdownmode) (cpwr_usepowerdownmode) /* ui */ led1off(); /* go to sleep */ sleeptimeoutsequence(); /* restart advertising*/ bleapp_start();#else  
如果需要上电后或复位后马上开启广播,可使能如下宏定义:
#define gappstartafterreset_d 1  
对于各功耗模式的介绍可参考源码文件pwr_configuration.h。
为了快速扫描连接到设备,可以修改一下kw38的广播间隔,实例代码如下:
gapadvertisingparameters_t gadvparams = { /* mininterval */ ggapadvertisingintervalrangeminimum_c, //0x12c0, /* maxinterval */ ggapadvertisingintervalrangeminimum_c, //0x1900,…}  
如果向已经下载过使能低功耗程序的开发板再次下载代码,有时会无法识别到芯片,此时需要按住开发板的sw3键以唤醒kw38,再点击下载按钮。
如果你现在没有调试低功耗功能,为方便开发调试,建议先禁用低功耗模式,只需修改如下宏定义:
#define cpwr_usepowerdownmode 0  
如果你的产品最终选择的功耗模式是需要mcu进入vllsx模式的,比如low power mode:5/8/9,那么每次休眠唤醒后,需要重新初始化外设,因为从这些模式唤醒走的是reset流程,不过进入休眠后io引脚的输出电平状态是可以保持的。
空中包时序分析
使用ellisys的bluetooth tracker抓包工具,结合它的逻辑分析仪功能,我们可以抓取到蓝牙空中包和io的时序关系,以下是我们使用该功能分析kw38功耗状态的一个实例。进入低功耗模式前拉低led1引脚,退出低功耗模式后置高led1。
#define gledsupported_d 1#include led.hvoid board_enterlowpowercb(void){ led1off();…}void board_exitlowpowercb(void){ led1on(); …}  
抓取到的空中数据和led1引脚数据如下:
聚焦到一个连接事件,我们看到kw38在空中包到来之前大约3ms唤醒了mcu,在处理完蓝牙事件后大约304us进入低功耗模式。
controller enhanced notifications
该特性可以产生额外的如下图所示蓝牙事件,但是默认只有wireless_uart使能了该功能,如果需要这些额外的event,请参考工程wireless_uart。
timer、event及其它资源分配
强烈建议用户仔细浏览一遍app_preinclude.h文件,该文件中包含了大多数项目配置信息,如果用户有增加的配置项的话,也建议放到这个文件中统一管理。
如用户需要自己创建timer或event的话,则如下配置参数需要对应的增加。
/* defines number of os events used */#define osnumberofevents 5/* defines number of timers needed by the application */#define gtmrapplicationtimers_c (4 + grepeatedattemptstimers_d + gappallowdevicetosleeptimers_d)  
app_config.c文件中包含了蓝牙的配置信息,如广播内容,安全设置,如有需要可修改该文件。
gatt_db.h文件定义了蓝牙的service,可以参考该文件增加或修改用户自定义的service。
发射功率调节
kw36系列通过如下宏定义,配置蓝牙的发射功率,但是该值对应的实际发射功率是如何计算的呢?
#define madvertisingdefaulttxpower_c 20#define mconnectiondefaulttxpower_c 20#define mdefaulttxpowerusepabump_c 0  
在kw36的datasheet里有如下表格,有两种方法计算实际发射功率:
第一种,设置值直接对应下面表格里的行数(从行0开始),如设置txpower_c为3,则发射功率对应的pa_power[5:0]= 6,对应的25℃发射功率为-15.6。
第二种,设置值为0时,pa_power[5:0]=1, 设置值为其它值时,pa_power[5:0]为二倍的设置值,然后通过下表查询对应的发射功率,如设置值为5,则pa_power[5:0] = 5*2=10,查询下表对应的25℃发射功率为-11.2。
上表对应的是未使能最大+5dbm输出时的配置,如果使能了+5dbm输出,请参考如下表格,修改宏定义mdefaulttxpowerusepabump_c为1,可使能+5dbm输出。
对于kw38系列,使用如下api配置发射功率,因为输入参数即为发射功率值,所以不再需要任何转换。
bleresult_t controller_settxpowerleveldbm(int8_t level_dbm, txchanneltype_t channel);
panic分析
这里的演示会使用到segger的j-link commander,所以如果你的开发板的debugger固件呈现的不是j-link的话,你需要按照如下链接里的说明更新debugger为segger jlink。或者使用一个外部的j-link或j-trace作为debugger。
opensdaserial and debug adapter | nxp semiconductors
panic是framework下的一个十分有用的调试工具,在开发调试阶段用于捕捉各种错误,sdk中默认已经在很多异常处添加了panic处理,但是该功能默认是关闭的,需要定义如下宏打开:
#define gusepanic_c 1  
debugger在线调试分析
如果是连着debugger的在线调试,我们只需暂停代码即可看到panic的位置,通过panic_data中保存的数据,我们能进一步定位到出问题时的更多信息,如下是我伪造的一个panic场景。
void bleapp_start(void){… panic(0,(uint32_t)bleapp_start,1,2);}  
运行代码,程序卡死在panic里,暂停程序,并查看相关信息如下:
将location里的地址0x234b9输入到汇编窗口的搜索栏,可以看到出问题的函数是bleapp_start(),当然这个也可以通过call stack进行查看。另外我们可以看到出问题时的一些其它参数extra1和extra2。
离线分析
很多场景下,产品是在没有连接debugger的情况下出现了异常,此时我们就需要segger的j-link commander工具了,注意调试使用的debugger必须是j-link或j-trace等segger公司的产品。
刚才相同的代码,下载到开发板后,断开debugger让程序全速运行,此时程序应该也运行到了panic的位置,但是我们如何查看呢?
打开j-link commander,并连接到kw38芯片,输入命令‘h’,此时可看到程序pc指针为0x19160。
通过addr2line工具我们可以定位到出问题的代码文件为panic.c,行数为65,addr2line的安装十分简单,大家可自行搜索下载安装。
对于出问题时的其它数据,我们可以通过变量panic_data查看,通过.map文件定位到panic_data的地址为0x2000421c。
结构体panic_data的定义如下:
typedef struct{ panicid_t id; uint32_t location; uint32_t extra1; uint32_t extra2; uint32_t linkregister; uint32_t cpsr_contents; /* may not be used initially */ uint8_t stack_dump[4]; /* initially just contain the contents of the lr */} panicdata_t;  
使用j-link commander的‘mem32’命令可以读取到如下图所示的panic_data数据,通过这些数据,查找出出问题的函数地址为0x234b9, extra1为1,extra2为2。
通过addr2line命令查询到出问题的函数位于temperature_sensor.c文件的179行,即bleapp_start()函数,再结合当时保存的extra1和extra2参数,我们大概就能分析出问题的原因了。
该方法用于panic后的代码追踪,当然也适用于程序跳入死循环、hardfault及其它的一些debugger离线后的异常分析。
以上是我在使用无线mcu时总结的一点经验,希望能帮到刚刚入门无线产品的同学们。
来源:恩智浦mcu加油站
免责声明:本文为转载文章,转载此文目的在于传递更多信息,版权归原作者所有。本文所用视频、图片、文字如涉及作品版权问题,请联系小编进行处理


自动断路器的使用注意事项
VCS/XRUN如何创建一个非UVM的简单仿真环境?
诺顿运算放大器的典型应用电路
昕诺飞智能互连道路照明系统及LED路灯已突破两万套
音圈模组加持的阿尔法蛋AI词典笔X10
无线MCU调试技巧汇总
废弃电池再循环负极材料(RAM)的循环利用研究
红外技术解决音频无线传输难题
微机保护装置是什么及其在电力系统中的作用
VR,AR,MR目前无处不在,正在从休闲游戏世界进入商业企业世界
基于LTCR3589设计的带I2C八输出电源稳压方案
如何用指针式万用表测量103瓷片电容
中国石墨烯芯片最新新闻
现代Enduro全时四驱,搭载2.0升发动机,仅售10万,还买哈弗H6?
财付通扣钱人工客服电话
云算力崛起,抹茶交易所的“云玩家”们
光纤网络高清传输的优势_光纤网络高清传输的缺点
abb变频器常见故障
“游戏机”改变医疗:体感技术跨入医疗行业
直线电机模组加持的基因测序设备