牡丹雖好,仍需綠葉扶持;RT雖快,仍需優(yōu)化。本文將分享在i.MX RT飛行學(xué)習(xí)板中的軟件優(yōu)化辦法,讓C代碼在ARM Cortex-M7內(nèi)核上極速飛奔!01
概述
i.MX RT飛行學(xué)習(xí)板,是真的會(huì)飛的處理器學(xué)習(xí)板!它的核心是恩智浦公司的跨界處理器i.MX RT1052, 基于ARM Cortex-M7內(nèi)核,主頻達(dá)600 MHz!對(duì)于電機(jī)驅(qū)動(dòng),雖然速度驚人,但是這個(gè)學(xué)習(xí)板要同時(shí)運(yùn)行“4無刷電機(jī)FOC驅(qū)動(dòng) + 飛控算法”,所以依然不是輕易的事情。
牡丹雖好,仍需綠葉扶持,下面將分享多種優(yōu)化手段,讓C代碼在i.MX RT上極速飛奔,實(shí)現(xiàn)這個(gè)“單芯片無人機(jī)”。先上段熱身視頻。
視頻1 熱身視頻
02
加快代碼速度的秘訣
1、選擇硬件浮點(diǎn)
重要而簡單的第一步是:在編譯器中選擇“硬件雙精度浮點(diǎn)”,圖1是在KEIL中的選擇配置。
圖1 雙精度浮點(diǎn)
選擇“硬件雙精度浮點(diǎn)”的作用是,當(dāng)C代碼需要雙精度、單精度浮點(diǎn)運(yùn)算,編譯器就選擇最優(yōu)的浮點(diǎn)指令,速度最快!如果選擇“硬件單精度浮點(diǎn)”,單精度浮點(diǎn)運(yùn)算就用單精度浮點(diǎn)指令,但雙精度浮點(diǎn)運(yùn)算只能結(jié)合多條單精度指令完成,速度較慢。如果不選擇任何硬件浮點(diǎn),編譯器僅能用定點(diǎn)指令完成浮點(diǎn)運(yùn)算,速度非常慢。
但要注意,不是任意處理器都支持“硬件浮點(diǎn)”,即便同樣是ARM Cortex-M7內(nèi)核,有些半導(dǎo)體廠家為了降低成本,會(huì)裁掉“雙精度浮點(diǎn)”單元,只留下“單精度浮點(diǎn)”。而i.MX RT支持完整的單、雙精度浮點(diǎn)單元。得益于這個(gè)優(yōu)勢,飛行學(xué)習(xí)板中的ZLG-Soar飛控軟件,全部核心代碼都使用雙精度浮點(diǎn)指令,不單止精度高、而且速度超快,在相同主頻下,比定點(diǎn)指令的Cortex-M3快20倍以上!
2、關(guān)鍵代碼RAM中運(yùn)行
將代碼放在ITCM相連的RAM中運(yùn)行,速度最快!
Cortex-M7的中ITCM(Instruction-Tightly Coupled Memories)是專門的指令總線。我們?cè)趇.MX RT1052中分配了256Kbytes的內(nèi)部RAM在ITCM上,而且和Flash相比,內(nèi)部RAM沒有明顯的讀取延時(shí),所以代碼在這段RAM中運(yùn)行,速度是最快的,沒有更快!
程序清單1是飛行學(xué)習(xí)板在KEIL中的分散加載的配置,全部只讀RO數(shù)據(jù)(即代碼和CONST變量等)放在0x00000400地址開始的ITCM RAM里面。KEIL編譯后,其實(shí)全部原始數(shù)據(jù)都是存在Flash中,但 KEIL自動(dòng)在main函數(shù)前插入一段Flash函數(shù),該函數(shù)將相關(guān)的代碼從Flash復(fù)制到RAM,最后將PC指針改到RAM。這樣代碼就從RAM開始運(yùn)行。
程序清單1 ITCM RAM分散加載
如果代碼很大,無法全部復(fù)制到RAM中運(yùn)行,那么可以修改分散加載,僅將必要的代碼放在RAM中運(yùn)行,其他代碼在Flash中運(yùn)行。
3、關(guān)鍵算法寫成宏定義
在ZLG-FOC電機(jī)矢量控制庫中,全部核心算法都寫成宏定義的形式,如程序清單2的Clarke變換。
程序清單2 宏定義算法
如果寫成C函數(shù),那么上層代碼調(diào)用時(shí),一般先進(jìn)行入棧操作、保護(hù)現(xiàn)場,接著跳轉(zhuǎn)到該函數(shù)運(yùn)行,然后調(diào)用返回指令回到上層代碼,最后進(jìn)行出棧操作、恢復(fù)現(xiàn)場。這個(gè)過程必然會(huì)延長爭分奪秒的算法執(zhí)行時(shí)間。
可能有的人會(huì)說:在函數(shù)前面聲明inline,函數(shù)不就直接嵌入到上層代碼中,省去這些啰嗦過程嗎?其實(shí)不一定,編譯器也是很無奈的,KEIL和IAR的編譯手冊(cè)都說得很明白:根據(jù)代碼調(diào)用與被調(diào)用的復(fù)雜程度,能嵌進(jìn)去的,編譯器就幫忙嵌進(jìn)去,不能嵌進(jìn)去的,只能按普通函數(shù)那樣處理!
但如果將算法寫成宏定義,那么編譯會(huì)100%保證代碼會(huì)被直接嵌入到上層代碼中!只是對(duì)于過長的代碼,宏定義編寫不方便,這時(shí)候可以將代碼分拆成多個(gè)宏定義組合使用,或者僅把最必要的部分寫成宏定義。
4、盡量用C,少用匯編
盡量用C,少用匯編?晚上加班眼花,寫反了吧?沒寫錯(cuò),“匯編比C快”是好多年前、奔騰電腦時(shí)代的事情!現(xiàn)在是人工智能、大數(shù)據(jù)的時(shí)代,KEIL和IAR 的C編譯器經(jīng)過幾十年的發(fā)展,都變得非常聰明了(GCC筆者使用不多,不敢莽加評(píng)論)。首先,人腦能想到的最優(yōu)指令,C編譯器很多時(shí)候也能想到,可能比人腦想得更優(yōu)!再者,用匯編寫代碼,即便絞盡腦汁,頂多就單個(gè)函數(shù)速度最優(yōu),僅此而已!而C編譯器還會(huì)“綜合統(tǒng)籌”,例如,前后重復(fù)的代碼,它會(huì)合拼在一起;廢話、沒用的代碼,它會(huì)刪除;函數(shù)反復(fù)跳轉(zhuǎn)時(shí)的出入棧過程,它會(huì)想辦法減少……再配合上面提到的“算法寫成宏定義”,C代碼的運(yùn)行速度將更快!
就如我們敬愛的周工教導(dǎo)說:豬腦不如人腦、人腦不如電腦,i.MX RT在極速飛奔下就是很好的體現(xiàn)。
5、巧妙浮點(diǎn)出入棧
圖2顯示了Cortex-M7的浮點(diǎn)寄存器,S0-S31是浮點(diǎn)的通用寄存器,其他是控制或狀態(tài)等寄存器。如果軟件使能了浮點(diǎn)單元,那么在中斷發(fā)生后,M7默認(rèn)會(huì)將S0-S15、FPSCR等17個(gè)浮點(diǎn)寄存器硬件入棧,中斷完成后硬件出棧。雖然說是“硬件”,其實(shí)硬件也要花時(shí)間一個(gè)一個(gè)寄存器弄的,只不過比軟件處理,省了調(diào)用指令的時(shí)間。
圖2 Cortex-M7浮點(diǎn)寄存器
這里提出一個(gè)問題:假如有10個(gè)中斷程序輪流產(chǎn)生,處理器就自動(dòng)對(duì)17個(gè)浮點(diǎn)寄存器出入棧操作,但如果僅只有一個(gè)中斷使用了浮點(diǎn)指令,其他9個(gè)都不使用,那么大部分浮點(diǎn)出入棧的操作都是浪費(fèi)時(shí)間的!
如何解決這個(gè)問題呢?
ARM提出一種LAZY模式(其實(shí)一點(diǎn)都不懶),在中斷發(fā)生后,硬件只給17個(gè)浮點(diǎn)寄存器預(yù)留堆??臻g,但不入棧,只有中斷函數(shù)調(diào)用了第一條浮點(diǎn)指令前(例如浮點(diǎn)加、減、乘、除),硬件才補(bǔ)充入棧;中斷完成后,如果真的發(fā)生過硬件浮點(diǎn)入棧,才會(huì)相應(yīng)地出棧。這樣大大提高了浮點(diǎn)出入棧的效率!這種LAZY模式夠聰明吧,真不知ARM怎樣起名的,可能懶的極端就是聰明吧。
6、代碼清晰、聰明
圖3中的兩條蛇在樹上互相糾纏,分不清尾巴是誰的。寫代碼也同樣道理,如果習(xí)慣性地想到一點(diǎn)寫一點(diǎn)、寫前不規(guī)劃、寫后懶修改,就像圖3左邊的代碼,一堆if/else,邏輯模糊、難懂、難改,運(yùn)行速度沒保證。而右邊的代碼是經(jīng)過分析推理的聰明辦法,用switch case替代一堆if/else,邏輯清晰、易懂、易改,運(yùn)行速度有保證!
圖3 清晰聰明的代碼
前面介紹了很多在i.MX RT上加快代碼速度的方法,但都是輔助的,最核心的還是:花點(diǎn)心思規(guī)劃代碼要怎樣寫,代碼要清晰、聰明。
03
總結(jié)
牡丹雖好,仍需綠葉扶持,RT雖快,但仍需優(yōu)化才能發(fā)揮到極致的速度,將不可能的事情變?yōu)楝F(xiàn)實(shí)!就如我們ZLG的i.MX RT飛行學(xué)習(xí)板,是業(yè)界唯一的“4無刷電機(jī)FOC +飛控算法”的無人機(jī)方案。
11月初期的廣州還是茵茵綠草,我們踏青放飛去。
視頻2 踏青放飛
-
處理器
+關(guān)注
關(guān)注
68文章
19896瀏覽量
235336 -
編譯器
+關(guān)注
關(guān)注
1文章
1662瀏覽量
50232 -
C代碼
+關(guān)注
關(guān)注
1文章
90瀏覽量
14787
原文標(biāo)題:i.MX RT飛行學(xué)習(xí)板——如何讓C代碼在M7上極速飛奔?
文章出處:【微信號(hào):Zlgmcu7890,微信公眾號(hào):周立功單片機(jī)】歡迎添加關(guān)注!文章轉(zhuǎn)載請(qǐng)注明出處。
發(fā)布評(píng)論請(qǐng)先 登錄
初識(shí)Layerscape和I.MX系列處理器
【大聯(lián)大品佳 NXP i.MX RT1050試用體驗(yàn)】芯林至尊,寶刀RT1050,初識(shí)i.MX RT系列跨界處理器 (之一)
i.MX RT處理器系列
Cortex-M7 + M4內(nèi)核的MCU資料大合集
Cortex-M7 + M4內(nèi)核的MCU性能及特點(diǎn)是什么
ZLG攜手NXP舉行i.MX RT 跨界處理器全國巡回研討會(huì)
高達(dá)600MHz主頻的Cortex-M7 MCU

基于i.MX RT1061處理器的OK1061-S開發(fā)板介紹

支持高級(jí)語音命令和人臉識(shí)別應(yīng)用的NXP i.MX RT106L和RT106F處理器
恩智浦i.MX RT1170開創(chuàng)GHz MCU時(shí)代
恩智浦i.MX RT1170在將該系列帶上了更高的層面
恩智浦推出核跨界MCU的第二款產(chǎn)品i.MX RT1160
NXP推出基于i.MX RT117H的智能人機(jī)界面解決方案
基于 NXP i.MX RT1050 的 3D 打印機(jī)方案

評(píng)論