rt-thread 自有协议下载固件

1 使用rtt 自带的例程,测试下载固件

添加软件包 ota_downloader , 启动http_ota/ymodem_ota 例程后, 在控制台输入 ymodem_ota , 通过 x-shell 等 支持ymodem 工具, 点击发送, 就可以下载固件到设备上(设备开启 rtt bootloader fal 软件包, 并定义好分区信息).

但是如果我们需要使用自有协议下载固件, 就需要了解一下下载流程

2 下载流程

通过查看源代码, 我们会发现几个关键信息 , 1 接收分区 recv_partition, 2 开始传输回调函数, 3 传输回调函数 传输流程如下

值得注意的是, x-shell 是支持发送文件大小的, 部分终端软件不支持发送文件大小

3 模拟实现流程

根据上述流程, 我们只需要实现, 开始接收函数, 和数据传输函数即可 参考提供的源代码 定义如下几个参数变量 3.0 变量参数

static size_t update_file_total_size, update_file_cur_size; // 定义固件的大小, 和已传输的大小
static const struct fal_partition * dl_part = RT_NULL; // 需要传输到的分区句柄

, 开始 接收函数需要实现的内容如下 3.1 , 文件名, 指定文件分区 3.2 文件大小

eg : int start_tran(uint8_t *name, uint8_t len)
{
 1 获取固件名 // 非必须
 file_name = xxx; 
 2 获取固件大小 // 必须
 update_file_total_size = xxx; // 自有协议实现
 3 重置已传输的大小参数// 必须
 update_file_cur_size = 0; 
 4 开启传输标志位/ 信号量// 可选
 5 查找, 判断大小, 和擦除分区
     /* Get download partition information and erase download partition data */
    if ((dl_part = fal_partition_find(recv_partition)) == RT_NULL)
    {
        LOG_E("Firmware download failed! Partition (%s) find error!", recv_partition);
        return 0;
    }

    if (update_file_total_size > dl_part->len)
    {
        LOG_E("Firmware is too large! File size (%d), %s partition size (%d)", update_file_total_size, recv_partition, dl_part->len);
        return 0;
    }

    LOG_I("Start erase. Size (%d)", update_file_total_size);

    /* erase DL section */
    if (fal_partition_erase(dl_part, 0, update_file_total_size) < 0)
    {
        LOG_E("Firmware download failed! Partition (%s) erase error!", dl_part->name);
        return 0;
    }

数据传输函数内容如下 3.3 数据本体, 帧头,和校验, 帧头和校验按照自己的通信协议即可

eg: int data_write(uint8_t *buf,size_t len)
{
1 获取数据本体内容
    /* write data of application to DL partition  */
    if (fal_partition_write(dl_part, update_file_cur_size, buf, len) < 0)
    {
        LOG_E("Firmware download failed! Partition (%s) write data error!", dl_part->name);
        return RYM_CODE_CAN;
    }

    update_file_cur_size += len;
}

在完成上述操作后, 固件就可以按照自有协议传输, 传输完成后, 再自行定义一个传输完成的标志, 然后进入重启状态, boot 会根据下载分区的数据内容, 自行搬运固件到程序区

复位重启
        /* wait some time for terminal response finish */
        rt_thread_delay(rt_tick_from_millisecond(200));

        /* Reset the device, Start new firmware */
        extern void rt_hw_cpu_reset(void);
        rt_hw_cpu_reset();
        /* wait some time for terminal response finish */
        rt_thread_delay(rt_tick_from_millisecond(200));

以上参考的源代码, 均可在rtt 官网上提供的软件包可以找到

经验分享 程序员 微信小程序 职场和发展