BNO080固件升级流程

由于BNO080片上的程序是由Hillcrest Labs提供,而且代码不开源,我们只能通过他们提供的demo进行BNO080升级程序的编写。

从本质上来说,BNO的升级程序其实就是通过STM32的SPI或者IIC对另外一款MCU进行固件程序的更改。既然BNO是“另外一款MCU”,他就和普通的MCU一样,要升级就需要bootloader程序和用户存储区,不过这些Hillcrest Labs都提供好了,我们需要做的只是遵循BNO080内置的bootloader程序里面的通讯协议,通过STM32的SPI或者IIC,把他们提供的最新固件送入到BNO080的芯片内。至于BNO080如何写入到他自己的用户存储区,这我们就不用管了。这种方式既有好处也有坏处,最直观的好处就是我们少写了一份代码(即BNO的片内bootloader程序),Hillcrest Labs也做到了技术的保密。但是坏处就是,通过STM32对BNO080升级的过程中一旦出现了什么问题,是很难定位到问题产生的原因的(因为我们看不到BNO080的bootloader程序,更别说对其逻辑仿真),只能通过联系原厂FAE,一起协同定位问题原因,费时费力。

不要把BNO080当成一种传感器,其实它就是一个自带MCU的IMU,他里面有自己的固件程序、运行逻辑和数字运算处理单元,他做的工作就是通过自身的敏感元件上获取到的陀螺仪数据通过IIC或者SPI发送给我们的单片机,来被我们利用。我们对它所进行的固件升级也不过是通过BNO080的IAP功能,把APP程序(最新固件)写入到存储区。BNO080上电的时候运行在BOOT区,如果有外部改写程序的条件满足,则对存储区的程序进行改写操作。如果外部改写程序的条件不满足,程序指针跳到存储区,开始执行放在存储区的程序,这样便实现了IAP功能。

 

STEP 1.进入DFU模式

既然我们要对BNO080进行固件升级,我们要把BNO080模式置为DFU状态,他们提供的demo里面sh2_hal_reset就实现里此功能。

 

前两行代码Cookie这个参数这里没用,可以不加。OnRX是注册的回调函数,有sensor事件时给应用层。

spiReset(dfuMode);这个函数必须要有,里面更改了SPI的配置。后面再进行spiReset函数的解释。

然后把RSTN引脚拉低,再把BOOT引脚拉低,延迟10ms,再把RSTN引脚拉高。再延迟200MS,BNO080进入DFU状态,时序逻辑图如下。

 

IntnAsserted是中断标志,这里初始化成false;

 

点开spiReset函数,里面可以看到正常SPI和升级模式的SPI是不一样的

 

DFU模式SPI是

        hspi->Init.CLKPolarity = SPI_POLARITY_LOW;

//串行同步时钟的空闲状态为低电平

        hspi->Init.CLKPhase = SPI_PHASE_1EDGE;

//串行同步时钟的第一个跳变沿数据被采样

        hspi->Init.BaudRatePrescaler = SPI_BAUDRATEPRESCALER_64; 

//定义波特率预分频的值:波特率预分频值为64

正常模式SPI则是

        hspi->Init.CLKPolarity = SPI_POLARITY_HIGH;

//串行同步时钟的空闲状态为高电平

        hspi->Init.CLKPhase = SPI_PHASE_2EDGE;

//串行同步时钟的第二个跳变沿数据被采样

        hspi->Init.BaudRatePrescaler = SPI_BAUDRATEPRESCALER_32; 

//定义波特率预分频的值:波特率预分频值为32

这块SPI的配置可以看出BNO080里面升级模式与普通模式SPI配置是不一样的,我们必须要把STM32也配置成相应模式才能完成数据通讯。

 

改完SPI配置后,我们再向BNO080发一个dummy byte,来保证reset前SPI clock的相位已经拉低。

 

STEP 2.发送固件包大小和发送帧数据长度

 

进入升级状态后,获取到固件包大小,把当前固件包的大小塞进一个Buffer里面,再调用appendCrc函数在buffer末尾加入校验位,供BNO080进行数据校验,保证数据可靠性。再然后通过dfuSend函数,把Buffer发送给BNO080.

 

当ACK获取得到字符“n”(0x6E)代表写入未成功,得到字符“s”(0x73)时代表操作成功,即可进行下个操作。

设置发送帧数据长度(我设置的是24字节),把发送帧数据长度塞进一个Buffer里面,再调用appendCrc函数在buffer末尾加入校验位。再然后通过dfuSend函数,把Buffer发送给BNO080. 得到字符“s”(0x73)时代表操作成功。

STEP 3.发送固件

 

根据所设置发送帧数据长度获取固定个数的固件包数据,把固件包数据(我设置的是24字节,所以先塞24字节数据)依次塞进一个Buffer里面,再调用appendCrc函数在buffer末尾加入校验位。再然后通过dfuSend函数,把Buffer发送给BNO080. 得到字符“s”(0x73)时代表操作成功,然后固件包再偏移帧数据长度个数据(我偏移24字节),再发送下一包数据,直到数据全部写入。

STEP 4.发送固件完成后,重新初始化

重启或者重新初始化SPI,升级完成~

  • 2
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值