STM32+IAP方案 實現網絡升級應用固件


關注了這個概念有些日子了,這段時間總算有機會實戰==網絡升級應用固件,這里記錄下遇到的問題,及解決方案。
原理與網上流傳的串口作為傳輸手段 一致;不同之處,無非我這里使用了網絡設備傳輸。==(lwip)TFTP客戶端的應用.
參考:
IAR環境下STM32+IAP方案的實現
STM32淺談之IAP.pdf
基於IAP和Keil MDK的遠程升級設計
keil MDK中如何生成*.bin格式的文件


概況:

  • 什么是IAP,為什么要IAP
  • 可實現的原理
  • 實現過程
  • 細節及實現
    以上基本都可以從【IAR環境下STM32+IAP方案的實現】中找到答案。這里只是貼圖,醒目:
    IAP框架布局:
    這里寫圖片描述
    STM32F103ZET6的啟動方式有三種:內置FLASH啟動、內置SRAM啟動、系統存儲器ROM啟動,通過BOOT0和BOOT1引腳的設置可以選擇從哪中方式啟動,這里選擇內置的FLASH啟動。其FLASH的地址為0x08000000—0x0807ffff,共512KB,這些都能從芯片數據手冊中直接得到。而這里首要的一個問題是中斷的問題。正常情況下發生中斷的過程為:發生中斷(中斷請求),到中斷向量表查找中斷函數入口地址,跳轉到中斷函數,執行中斷函數,中斷返回。也就是說在STM32的內置的Flash中有一個中斷向量表來存放各個中斷服務函數的入口地址,內置Flash的分配情況大致如下圖2-1。
    這里寫圖片描述
    這里寫圖片描述
    這里寫圖片描述
    這里寫圖片描述
    在內置的Flash里面添加一個BootLoader程序,BootLoader程序和user application各有一個中斷向量表,假設BootLoader程序占用的空間為N+M字節,則程序的走向應該如圖2-2所示(借用網友的原圖並做改動,其中虛線部分為原圖步驟④⑤的走向,本人改為指向灰色部分)。
    這里寫圖片描述
    上電初始程序依然從0x08000004處取出復位中斷向量地址,執行復位中斷函數后跳轉到IAP的main(標號①所示),在IAP的main函數執行完成后強制跳轉到0x08000004+N+M處(標號②所示),最后跳轉到新的main函數中來(標號③所示),當發生中斷請求后,程序跳轉到新的中斷向量表中取出新的中斷函數入口地址,再跳轉到新的中斷服務函數中執行(標號④⑤所示),執行完中斷函數后再返回到main函數中來(標號⑥所示)。
    對於步驟④⑤,網友認為是:“在main執行的過程中,如果CPU得到一個中斷請求,PC指針仍強制跳轉到地址0x08000004中斷向量表處,而不是新的中斷向量表,如圖標號④所示,程序再根據我們設置的中斷向量表偏移量,跳轉到對應中斷源新的中斷服務程序中,如圖標號⑤所示”。我對此的理解是:“當發生中斷后,程序從0x08000004(舊)處的中斷向量表中得到相應的中斷服務函數入口地址,繼而跳轉到相應的中斷服務程序”。但是舊的中斷向量列表里邊存放的是IAP程序中斷函數的入口地址,它是如何得到user程序中斷函數的入口地址呢?所以我覺得此種說法是錯誤的。“當發生中斷時PC指針強制會跳轉到0x08000004處”這種說法並沒有錯,只是忽略了后續的一些知識要點而導致這個說法出現矛盾。
    對於步驟④⑤我認為的是,在main函數的執行過程中,如果CPU得到一個中斷請求,PC指針本來應該跳轉到0x08000004處的中斷向量表,由於我們設置了中斷向量表偏移量為N+M,因此PC指針被強制跳轉到0x08000004+N+M處的中斷向量表中得到相應的中斷函數地址(待求證),再跳轉到相應新的中斷服務函數,執行結束后返回到main函數中來。

IAP流程描述:

1、IAP的bootloader引導程序

IAP在應用中編程,可以拓展成遠程網絡更新應用固件。
片內的flash,至少划分成2個分區,對應至少兩個完整的程序;
低地址分區端推薦放入IAP程序==bootloader引導程序(這里邊的手段可以是串口、網絡等不同的方式),高地址分區端推薦燒寫app固件。
關鍵點提及:
IAP程序中,當滿足跳轉條件(被觸發)時,執行跳轉代碼到app應用固件程序,跳轉代碼流程:
至少需要設定跳轉目的地的app應用固件 棧頂指針,:

/* Initialize user application's Stack Pointer */ __set_MSP(*(__IO uint32_t*) USER_FLASH_FIRST_PAGE_ADDRESS);
  • 1
  • 2

其中,app應用固件的分區地址:

#define USER_FLASH_FIRST_PAGE_ADDRESS 0x08009000
  • 1

2、app應用固件

需要兩處的更改,不然錯誤未知
IROM設置如圖:
這里寫圖片描述
中斷向量表偏移:
這里寫圖片描述

NVIC_SetVectorTable(NVIC_VectTab_FLASH,VectorTable_Offset);
  • 1

其中:

#define NVIC_VectTab_FLASH ((uint32_t)0x08000000) #define VectorTable_Offset 0x9000 
  • 1
  • 2

查錯:

如果做了上邊的工作,IAP依然無法順利執行跳轉至app應用程序,可以查看.map和.bin文件,確定是否如實的改變的中斷向量表的偏移和棧頂指針,如圖:
這里寫圖片描述
.bin文件:
這里寫圖片描述
可以看到,主棧頂MSP地址=0x2000C8C8、reset_handler地址=0x08009189
如此,才能生效,否則,可能原因:
修改后的向量表偏移,在之后的程序中,又再次被還原,通過如下的函數:

void NVIC_SetVectorTable(uint32_t NVIC_VectTab, uint32_t Offset); void SystemInit (void); SCB->VTOR = FLASH_BASE | VECT_TAB_OFFSET;
  • 1
  • 2
  • 3

附:

1、如需要.hex文件轉.bin,參見上邊的文章
當然,就算使用.hex文件,同樣可以升級,只是需要修改IAP中判定已經升級的文件是否有效,文件條件部分的代碼,

if(((*(__IO uint32_t*)USER_FLASH_FIRST_PAGE_ADDRESS) & 0x2FFE0000 ) == 0x20000000)
  • 1

2、地址偏移后的app應用程序,是否能夠獨立的運行?
不能,理由:
這里寫圖片描述
可知,開機上電並不能夠找到我們指定的偏移后的向量表。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM