上一篇记录了串口IAP升级,其实不管通过什么介质进行IAP升级,其核心都是不变的,都是通过iap代码和App代码控制相互跳转,iap核心代码是没有区别的。
今天记录一下自己在原子的探索者上实现的通过USB实现的IAP升级,同时记录以下过程中所遇到的问题。

  1. 总思路
    沿用了串口IAP升级的思路,预留一个Flash的空间记录标志位,上电通过判断标志位决定当前要执行App区的代码或要进行的代码升级操作。在Iap代码区更新了App区代码后,对标志位更新再跳转,使设备下次启动时能直接跳转至App执行;App代码中可通过任何方便的途径,判断需要更新软件后,对标志位做修改使软件下次启动时执行Iap更新程序。

  2. 实现细节
    USB实现IAP升级时,最长的时间花在了从U盘读取文件写入到Flash,包括对文件系统的不了解导致走了很多弯路。
    读取USB的文件写入到FLash后直接跳转到App程序执行,.bin文件默认放在最外层才可被识别,步骤包括:

    1.U盘初始化
    2.进入U盘根目录
    3.遍历外层文件,获取.bin文件的绝对路径
    4.根据路径打开文件
    5.获取文件的Size
    6.读取文件内容
    7.文件写入到FLASH
    8.更新标志位
    9.程序跳转
    以下为代码 ,对文件系统提供的封装函数内容做了些许操作,最后直接复制了所有有效代码,对封装函数做一些简单操作也可直接调用,看起来会简洁得多

void USB_UpData(void)
{FRESULT res;u8 filename[30] = {0};u8 *USB_Rx_Buf;    //缓存USB读取的数据char*path = "2:";  //u盘盘符u16 i=0,t=0;u16 tlen=0;        //记录文件总长u32 filesize = 0 ;char *fn;   /* This function is assuming non-Unicode cfg. */
#if _USE_LFNfileinfo.lfsize = _MAX_LFN * 2 + 1;  //文件系统扇区缓存的最大值fileinfo.lfname = mymalloc(SRAMIN,fileinfo.lfsize);
#endif        res = f_opendir(&dir,path); //打开根目录if (res == FR_OK) { while(1)  //枚举文件 获取.bin文件{res = f_readdir(&dir, &fileinfo);                if (res != FR_OK || fileinfo.fname[0] == 0) break;  //错误或遍历完成
#if _USE_LFNfn = *fileinfo.lfname ? fileinfo.lfname : fileinfo.fname;
#else                              fn = fileinfo.fname;
#endif                                                /* It is a file. *///打印所有遍历的文件路径名,直到获得.bin或遍历完printf("%s/", path);printf("%s\r\n",  fn); if(strstr(fn,".bin"))  {strcat((char*)filename,(char*)path);strcat((char*)filename,"/");strcat((char*)filename,fn);break;  }} }//可读模式打开文件if(!mf_open(filename,FA_READ)){//获取文件大小filesize = mf_size();USB_Rx_Buf = (u8*)mymalloc(SRAMIN,120*1024);   //120K //分批获取USB文件数据for(i=0;i<filesize/512;i++){res=f_read(file,fatbuf,512,&br);if(res){printf("Read Error:%d\r\n",res);break;}else{tlen+=br;for(t=0;t<br;t++){USB_Rx_Buf[tlen] = fatbuf[t];  //转存数据}}}if(filesize%512){res=f_read(file,fatbuf,filesize%512,&br);if(res) {printf("\r\nRead Error:%d\r\n",res);   }else{tlen+=br;for(t=0;t<br;t++){USB_Rx_Buf[tlen] = fatbuf[t];}}  }if(tlen)  //文件非0{//更新Flash        iap_write_appbin(FLASH_APP1_ADDR,USB_Rx_Buf,filesize);      //更新标志位memset(state,0x0,SIZE);strcpy((char*)state,"App");STMFLASH_Write(FLASH_UPDATA_FLAG_ADDR,(u32*)state,SIZE);//跳转Appif(((*(vu32*)(FLASH_APP1_ADDR+4))&0xFF000000)==0x08000000){     /*关闭中断*/INTX_DISABLE(); /*清楚嘀嗒时钟标志*/SysTick->CTRL = 0;SysTick->LOAD = 0;SysTick->VAL = 0;RCC_DeInit();for (i = 0; i < 8; i++){NVIC->ICER[i]=0xFFFFFFFF;NVIC->ICPR[i]=0xFFFFFFFF;} iap_load_app(FLASH_APP1_ADDR);//}else {printf("非FLASH应用!\r\n");}                         }free(USB_Rx_Buf);                                  }else printf("文件打开失败\r\n");//释放内存池myfree(SRAMIN,fileinfo.lfname);
}
  1. 问题总结
    1.mf_read(path,len)获取文件长度有限,不可超过512个字节,通过USMART验证,最大一次获取511
    2.程序在IAP跳转执行Jump2app时进入HardFault_Handler,有可能是.bin文件获取除了问题。
    3.对USB文件获取时,分批次获取文件内容,一次性写入到FLASH

    简单记录一下,如有错误,请大家指出~

STM32 USB IAP升级相关推荐

  1. 基于STM32的IAP升级程序

    基于STM32的IAP升级程序 IAP介绍 功能设计 硬件设计 软件设计 软件设计流程如下 完整程序 具体实现 设计功能程序 IAP实现程序 主程序 后续 IAP介绍 IAP(In Applicati ...

  2. 关于STM32单片机IAP升级中if(((*(__IO uint32_t*)ulAddr_App) 0x2FFE0000) == 0x20000000)语句的理解

    没有标题 初见if(((*(__IO uint32_t*)ulAddr_App) & 0x2FFE0000) == 0x20000000) 语句理解 语句功能 为什么ulAddr_App里存的 ...

  3. STM32芯片IAP升级机制详解

    一.先了解ICP和ISP.IAP之间的区别: 1. ISP(In System Programing 在系统编程)的实现相对要简单一些,一般通用做法是内部的存储器可以由上位机的软件通过串口来进行改写. ...

  4. 基于STM32的IAP升级

    文章目录 IAP是什么? IAP的组成? 如何使用? IAP流程总结 补充 代码评论区获取,一起进步,有错误欢迎指正ovo IAP是什么? 通俗的说是程序自己烧程序,完成版本迭代 IAP的组成? 1. ...

  5. 24. GD32F103C8T6入门教程-IAP升级教程

    GD32f103C8T6 IAP 升级教程 参考stm32的IAP升级原理 IAP测试源码 GD32和stm32的内核都是一样的,又因为IAP升级主要涉及升级的路径之和内核先关,所以gd32和stm3 ...

  6. STM32 USB HID IAP升级

    找了网上大量的资料,最后发现这个东西人家还出售源码.又不是什么算法级的东西,实在理解不了. 至于为什么要用HID,不用官方的DFU,因为驱动呀,DFU识别USB的时候还是要装驱动,客户你永远理解不了他 ...

  7. STM32 IAP升级(bootLoader)

    STM32 IAP升级(bootLoader) 今天给大家做一个STM32F系列的IAP 升级, 网上有不少例子,我这里字数有点多如果看请耐心看完,如果嫌麻烦可以看其他的帖子 我这边以103为例子,用 ...

  8. STM32升级方法(一):IAP升级

    此博客主要用于记录学习过程中的心得以及防止遗忘,下面的一些图片来源于网上,如有侵犯请联系. STM32芯片的升级方式众多,这里简单介绍下,主要有ICP((In-Circuit Programming ...

  9. STM32 CUbeIDE 使用Ymodem协议进行串口IAP升级

    STM32 CUbeIDE 使用Ymodem协议进行串口IAP升级 1.Ymodem协议简介 2.Boodload程序 2.1 传输32K限制解决 3.APP程序 4.升级测试 5.工程文件下载    ...

最新文章

  1. Javascript中的深拷贝和浅拷贝
  2. 阿联酋宣布成立全球首所人工智能大学
  3. ESIM (Enhanced LSTM for Natural Language Inference)
  4. 关于写文章的一点经验
  5. 某网session覆盖导致重置密码漏洞
  6. 听说你趁我不在家,欺负我老婆?
  7. 键盘keydown值表
  8. php导入csv 进度条,php 导入导出怎么做成有进度条??
  9. 风变Python编程13类的学习2
  10. 隐藏nginx 版本号信息(转)
  11. SQL Server 2019基础
  12. 韦东山linux嵌入式学习之路
  13. zlog日志使用说明
  14. BLDC (无刷直流电机) 六步式控制方法
  15. linux安装nebula
  16. 计算机专硕292,计算机2年制专硕越来越少,生活终于对我下手了吗?
  17. android模拟器 vt,逍遥安卓模拟器VT模式如何设置?VT模式设置流程图文分享
  18. python爬虫实战之多线程爬取前程无忧简历
  19. 基于Keras版本YOLOV7模型的锂电池自燃预警烟雾检测实践
  20. 药品过5关价翻12倍 批发商抢走药品一半利润

热门文章

  1. SQL Server 2012导入Excel文件时 未在本地计算机上注册“Microsoft.ACE.OLEDB.12.0”提供程序
  2. arduino连接1602LCD方法
  3. lcd c语言编程,1602Lcd,根据时序图 c语言编程
  4. js实现多个小方格输入验证码,一格输入完成后自动聚焦到下一格
  5. SOLIDWORKS Electrical 3D的柜外布线操作方法,你知道吗?
  6. 零基础Matlab Note11--三维图像
  7. 攻防世界-PWN-Challenge-Wirteup
  8. Python3-抓取某翻译网页 获取js数据
  9. SpringBoot Bean加载顺序 Order无效
  10. torch.cat试验