基於ARM編譯器版本5的工程遷移與適配到ARM編譯器版本6.12的過程

By: Ailson Jack
Date: 2019.12.08
個人博客:http://www.only2fire.com/
本文在我博客的地址是:http://www.only2fire.com/archives/109.html,排版更好,便於學習,也可以去我博客逛逛,興許有你想要的內容呢。

爲了描述方便,將ARM Compiler 5簡稱爲AC5,將ARM Compiler 6.12簡稱AC6.12

       ARM官方的遷移文檔,下載地址:,密鑰:。(可到我的個人博客中進行下載)

1、爲什麼要進行ARM編譯器版本的更換

    目前,AC5基本處於停止更新狀態,如果想要使用AC5編譯器編譯新的ARM架構或者內核的代碼,基本是不可能了,因此自然要使用ARM Compiler 6來代替之前的ARM Compiler 5。

    其實,我自己覺得還有一個比較重要的原因,那就是AC6支持使用armclang編譯GNU語法格式的彙編代碼,這樣在以後的項目開發中,可以只編寫GNU語法格式的彙編代碼(不必像以前一樣還要再寫一份符合ARM語法格式的彙編代碼),這樣既可以使用ARM-GCC編譯工具鏈編譯這個項目,也可以使用ARM Compiler編譯這個項目,彙編代碼維護更加方便了。

2、AC6.12的組成

(1).armclang:armclang編譯器替代了AC5的armcc,並且具有如下優點:

    基於LLVM和Clang技術;

    支持編譯GNU語法的彙編代碼;

    高度兼容當初爲GCC編譯的源代碼;

    實現包括ANSI/ISO C和C++,用於Arm架構的ABI,用於64位Arm架構的ABI以及Arm C語言擴展(ACLE)等規範。

(2).armlink:功能豐富的專用嵌入式鏈接器,能夠將對象和庫組合在一起以生成可執行文件。

(3).fromelf:鏡像文件轉換和反彙編功能。

(4).armar:壓縮程序。

(5).armasm:ARM語法的彙編代碼編譯器。

(6).ARM C和C++庫:ARM C庫經過ARM公司的優化有很好的的性能和代碼密度;ARM C++庫基於LLVM libc++項目。

下圖展示了ARM Compiler 6.12編譯工具鏈的整體結構:

3、ARM Compiler 5和ARM Compiler 6編譯工具鏈的差異

    AC5和AC6的主要差異是AC6使用armclang代替了armcc,因此在AC6中就沒有armcc這個編譯工具了。並且armclang的編譯參數相對於之前的armcc的編譯參數也有許多不同。

    下表列出了ARM Compiler 5和ARM Compiler 6之間各個工具的功能:

4、編譯工具鏈升級過程

    其實將AC5更換爲AC6.12編譯工具鏈,無非就是找出這兩個工具鏈的編譯參數的差異進行修改即可。當然了,基本上編譯參數變化還是挺大的,這裏推薦大家參考如下手冊進行編譯工具鏈升級。

    參考手冊:《migration_and_compatibility_guide_100068_0612_00_en.pdf》。因爲AC5和AC6.12的差異主要體現在ARM Compiler 6使用armclang代替了armcc,因此這篇文章,可以重點關注Chapter 2和Chapter 3,當然了也可以通過搜索一些編譯參數來快速定位。

5、我在升級過程遇到的問題

    我在遷移一個項目使用AC6.12的過程中,主要還是參考《migration_and_compatibility_guide_100068_0612_00_en.pdf》文檔進行參數修改,起初還算比較順利,但是涉及到彙編代碼的編譯過程中死活編譯會有問題。這裏簡單的記錄下吧。我這裏仍然使用armasm來編譯之前的ARM語法格式的彙編代碼。

    修改彙編的編譯參數時,一定要注意編譯選項--cpreproc,該編譯選項在AC5的含義是命令armasm調用armcc預處理輸入的彙編源代碼;在AC6的含義是命令armasm調用armclang預處理輸入的彙編源代碼。

    我的工程,在使用AC5編譯工具鏈時,在彙編過程中,使用的編譯參數配置和armcc的編譯參數配置是一樣的,並且也添加了編譯選項--cpreproc

    升級到AC6.12之後,因爲armclang的編譯參數和armcc的差異比較大,自然的就不能夠直接用於armasm的配置,因此我按照AC5的armasm配置作爲AC6.12armasm的配置,此時能夠進行彙編,但是提示:armclang: fatal error: no target architecture given; use --target=arm-arm-none-eabi or --target=aarch64-arm-none-eabi

    當時我就在想,爲什麼我使用armasm編譯彙編代碼怎麼會調用armclang呢,還以爲編譯工程的腳本有問題,檢查了編譯腳本也沒發現問題,後來還是查看《migration_and_compatibility_guide_100068_0612_00_en.pdf》文檔纔有所收穫。

    原來在彙編過程中調用armclang是armasm的編譯選項--cpreproc在作怪,該編譯選項是命令armasm調用armclang預處理輸入的彙編源代碼。ARM Compile 6中armasm需要另一個編譯選項--cpreproc_opts,用於填寫armclang預處理彙編代碼時的一些配置參數。由於先前沒有配置--cpreproc_opts,當然的在使用armclang進行預處理時會提示armclang: fatal error: no target architecture given; use --target=arm-arm-none-eabi or --target=aarch64-arm-none-eabi

    問題解決辦法:對armasm新增編譯選項--cpreproc_opts,並且填寫上armclang預處理彙編代碼需要用到的一些配置信息。例如:

armasm --cpu=cortex-a9 --cpreproc --cpreproc_opts=--target=arm-arm-none-eabi,-mcpu=cortexa9,-D,DEF1,-D,DEF2 -I /path/to/includes1 -I /path/to/includes2 input.S

    對於--cpreproc--cpreproc_opts編譯選項,可參考《migration_and_compatibility_guide_100068_0612_00_en.pdf》文檔的 3.3 Command-line options for preprocessing assembly source code

6、下面簡單列舉一些編譯參數的差異

(1).對於armcc和armclang之間,編譯參數存在的差異如下:

AC5 Option

AC6 Option

描述

--cpu=Cortex-M4

--target=arm-arm-none-eabi -mcpu=cortex-m4

Cortex-M4處理器的修改,其他處理器可能不一樣,請參考我這裏提供的官方手冊.

--thumb

-mthumb

支持thumb指令集

--fpu=fpv5_sp_d16

-mfloat-abi=hard -mfpu=fpv5_sp_d16

支持硬件浮點

--fpu=softvfp

-mfloat-abi=soft -mfpu=none

軟件浮點

--unaligned_access

-munaligned-access

設定處理器可以生成地址非對齊的數據

--apcs=interwork

沒有對應的編譯選項

在AC6中總是允許ARM指令和Thumb指令一起使用,因此沒有對應的編譯選項.

--split_sections

-ffunction-sections

生成的函數在自己的段中

--debug/-g

-g

生成調試信息

--c99  --gnu

-xc -std=gnu99

允許編譯器編譯帶有GNU擴展的C99代碼

--cpp  --gnu

-xc++ -std=gnu++03

允許編譯器編譯帶有GNU擴展的C++03代碼

--no_exceptions

-fno-exceptions

禁止生成需要支持C++異常的代碼

--no_rtti

-fno-rtti [ALPHA]

禁止生成需要支持C++ Run Time Type Information(RTTI)特徵的代碼

-Otime

默認支持

減少執行時間的優化,代價就是執行文件的大小會增加

-O3 -Otime

-Omax

Highest optimization for performance

-O3 -Ospace

-Oz

Highest optimization for code size

(2).對於AC6使用armasm需要注意的事項:

    使用AC6編譯彙編代碼時,編譯選項和AC5基本差不多,這裏再強調一下編譯選項:--cpreproc。在AC6中如果使用了編譯選項--cpreproc,那麼就必須附帶的使用編譯選項--cpreproc_opts,並且填寫上armclang預處理彙編代碼需要用到的一些配置信息,例如:

armasm --cpu=cortex-a9 --cpreproc --cpreproc_opts=--target=arm-arm-none-eabi,-mcpu=cortexa9,-D,DEF1,-D,DEF2 -I /path/to/includes1 -I /path/to/includes2 input.S

    好了,我在這裏簡單的記錄了下ARM Compiler 5升級到ARM Compiler 6.12的過程,給以後有需要的朋友留作參考吧。

如果覺得文章寫的不錯,對你有幫助,歡迎點贊,關注博主喲!

排版更好的內容見我博客的地址:http://www.only2fire.com/archives/109.html
注:轉載請註明出處,謝謝!^_^

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章