当前位置:   article > 正文

rtthread 固件升级代码(1)_ymodem-update

ymodem-update

 历程中:使用Ymode 向flash 中"download"写入下载文件。

 rt_err_t rym_recv_on_device(
        struct rym_ctx *ctx,
        rt_device_t dev,
        rt_uint16_t oflag,
        rym_callback on_begin,
        rym_callback on_data,
        rym_callback on_end,
        int handshake_timeout)  
实现了文件的传输:

struct rym_ctx *ctx  :

ymodem_update.c  【struct rym_ctx rctx】  调用ymode.c  【 struct rym_ctx *ctx】 ,

rctx 去耦合,放在了顶层函数中,底层依靠指针调用该结构提。具体功能不深究。

dev:  

rt_console_get_device()获取的结果就是serial1设备 ,也可改为其他serial设备。

oflag :

RT_DEVICE_OFLAG_RDWR | RT_DEVICE_FLAG_INT_RX 权限。

on_begin:

              --》ymodem_on_begin

on_data:

              -》ymodem_on_data

on_end:

               -》NULL,

handshake_timeout:

           -》RT_TICK_PER_SECOND

  1. rt_err_t rym_recv_on_device(
  2. struct rym_ctx *ctx,
  3. rt_device_t dev,
  4. rt_uint16_t oflag,
  5. rym_callback on_begin,
  6. rym_callback on_data,
  7. rym_callback on_end,
  8. int handshake_timeout)
  9. {
  10. rt_err_t res;
  11. rt_err_t (*odev_rx_ind)(rt_device_t dev, rt_size_t size);
  12. rt_uint16_t odev_flag;
  13. int int_lvl;
  14. RT_ASSERT(_rym_the_ctx == 0);
  15. _rym_the_ctx = ctx;
  16. ctx->on_begin = on_begin;
  17. ctx->on_data = on_data;
  18. ctx->on_end = on_end;
  19. ctx->dev = dev;
  20. rt_sem_init(&ctx->sem, "rymsem", 0, RT_IPC_FLAG_FIFO);
  21. odev_rx_ind = dev->rx_indicate;
  22. /* no data should be received before the device has been fully setted up.
  23. */
  24. int_lvl = rt_hw_interrupt_disable();
  25. rt_device_set_rx_indicate(dev, _rym_rx_ind);
  26. odev_flag = dev->flag;
  27. /* make sure the device don't change the content. */
  28. dev->flag &= ~RT_DEVICE_FLAG_STREAM;
  29. rt_hw_interrupt_enable(int_lvl);
  30. res = rt_device_open(dev, oflag);
  31. if (res != RT_EOK)
  32. goto __exit;
  33. res = _rym_do_recv(ctx, handshake_timeout);
  34. rt_device_close(dev);
  35. __exit:
  36. /* no rx_ind should be called before the callback has been fully detached.
  37. */
  38. int_lvl = rt_hw_interrupt_disable();
  39. rt_sem_detach(&ctx->sem);
  40. dev->flag = odev_flag;
  41. rt_device_set_rx_indicate(dev, odev_rx_ind);
  42. rt_hw_interrupt_enable(int_lvl);
  43. rt_free(ctx->buf);
  44. _rym_the_ctx = RT_NULL;
  45. return res;
  46. }

如果像更改下载的磁盘:更改这里。增加下载工厂模式的文件。

    if ((dl_part = fal_partition_find("download")) == RT_NULL)

  1. #define DBG_ENABLE
  2. #define DBG_SECTION_NAME "ymodem"
  3. #ifdef YMODEM_DEBUG
  4. #define DBG_LEVEL DBG_LOG
  5. #else
  6. #define DBG_LEVEL DBG_INFO
  7. #endif
  8. #define DBG_COLOR
  9. #include <rtdbg.h>
  10. static size_t update_file_total_size, update_file_cur_size;
  11. static const struct fal_partition * dl_part = RT_NULL;
  12. static enum rym_code ymodem_on_begin(struct rym_ctx *ctx, rt_uint8_t *buf, rt_size_t len)
  13. {
  14. char *file_name, *file_size;
  15. /* calculate and store file size */
  16. file_name = (char *)&buf[0];
  17. file_size = (char *)&buf[rt_strlen(file_name) + 1];
  18. update_file_total_size = atol(file_size);
  19. update_file_cur_size = 0;
  20. /* Get download partition information and erase download partition data */
  21. if ((dl_part = fal_partition_find("download")) == RT_NULL)
  22. {
  23. LOG_E("Firmware download failed! Partition (%s) find error!", "download");
  24. return RYM_CODE_CAN;
  25. }
  26. if (update_file_total_size > dl_part->len)
  27. {
  28. LOG_E("Firmware is too large! File size (%d), '%s' partition size (%d)", update_file_total_size, "download", dl_part->len);
  29. return RYM_CODE_CAN;
  30. }
  31. LOG_I("Start erase. Size (%d)", update_file_total_size);
  32. /* erase DL section */
  33. if (fal_partition_erase(dl_part, 0, update_file_total_size) < 0)
  34. {
  35. LOG_E("Firmware download failed! Partition (%s) erase error!", dl_part->name);
  36. return RYM_CODE_CAN;
  37. }
  38. return RYM_CODE_ACK;
  39. }
  40. static enum rym_code ymodem_on_data(struct rym_ctx *ctx, rt_uint8_t *buf, rt_size_t len)
  41. {
  42. /* write data of application to DL partition */
  43. if (fal_partition_write(dl_part, update_file_cur_size, buf, len) < 0)
  44. {
  45. LOG_E("Firmware download failed! Partition (%s) write data error!", dl_part->name);
  46. return RYM_CODE_CAN;
  47. }
  48. update_file_cur_size += len;
  49. return RYM_CODE_ACK;
  50. }
  51. void update(uint8_t argc, char **argv)
  52. {
  53. struct rym_ctx rctx;
  54. rt_kprintf("Waring: Ymodem has started! This operator will not recovery.\n");
  55. rt_kprintf("Please select the ota firmware file and use Ymodem to send.\n");
  56. if (!rym_recv_on_device(&rctx, rt_console_get_device(), RT_DEVICE_OFLAG_RDWR | RT_DEVICE_FLAG_INT_RX,
  57. ymodem_on_begin, ymodem_on_data, NULL, RT_TICK_PER_SECOND))
  58. {
  59. rt_kprintf("Download firmware to flash success.\n");
  60. rt_kprintf("System now will restart...\r\n");
  61. /* wait some time for terminal response finish */
  62. rt_thread_delay(rt_tick_from_millisecond(200));
  63. /* Reset the device, Start new firmware */
  64. extern void rt_hw_cpu_reset(void);
  65. rt_hw_cpu_reset();
  66. /* wait some time for terminal response finish */
  67. rt_thread_delay(rt_tick_from_millisecond(200));
  68. }
  69. else
  70. {
  71. /* wait some time for terminal response finish */
  72. rt_thread_delay(RT_TICK_PER_SECOND);
  73. rt_kprintf("Update firmware fail.\n");
  74. }
  75. return;
  76. }
  77. MSH_CMD_EXPORT_ALIAS(update, ymodem_start, Update user application firmware);

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/我家自动化/article/detail/779930
推荐阅读
相关标签
  

闽ICP备14008679号