芯片啟動時很多設備沒有初始化,需要匯編語言進行准備。
簡單的GNU匯編語法:
1 label: instruction @ comment
label :標號,類似於外號,為所在位置做標號,可以通過這個標號訪問這里的內容 所有的以“:”結尾的都被認為是標號
instruction : 指令,包含匯編指令和偽指令
comment : 注釋部分 ,在“@”后面的被認為是注釋,也可以用類似於C語言的 “/*” 和“*/”
ARM 中的指令、偽指令、偽操作、寄存器名等可以全部使用大寫,也可以全部使用小寫,但是不能大小寫混用。
用戶可以使用.section 偽操作來定義一個段,匯編系統預定義了一些段名:
.text 代碼段
.data 數據段(初始化的)
.bss 數據段(未初始化的)
.rodata 只讀數據
我們可以自己使用.section 來定義一個段,每個段以段名開始,以下一段名或者文件結尾結束,比如:
1 .section .testsection @定義一個 testsetcion 段(text/data/bss/rodata)
匯編程序的默認入口標號是_start,不過我們也可以在鏈接腳本中使用 ENTRY 來指明其它的入口點
下面的代碼就是使用_start 作為入口標號:
1 global _start 2 3 _start: 4 ldr r0, =0x12 @r0=0x12
上面代碼中.global 是偽操作,表示_start 是一個全局標號,類似 C 語言里面的全局變量一樣
常見的偽操作有:
GNU 匯編同樣也支持函數,函數格式如下:
1 函數名: 2 函數體 3 返回語句 @非必須
代碼類似於:
1 /* 未定義中斷 */ 2 Undefined_Handler: 3 ldr r0, =Undefined_Handler 4 bx r0 5 6 7 /* SVC 中斷 */ 8 SVC_Handler: 9 ldr r0, =SVC_Handler 10 bx r0 11 12 13 /* 預取終止中斷 */ 14 PrefAbort_Handler: 15 ldr r0, =PrefAbort_Handler 16 bx r0
Cortex-A7常用匯編指令
1、處理器內部數據傳輸指令
2、存儲器訪問指令
3、壓棧出棧指令
例如:
1 PUSH {R0~R3, R12} @將 R0~R3 和 R12 壓棧
PUSH 和 POP 的另外一種寫法是“STMFD SP!”和“LDMFD SP!”
1 STMFD SP!,{R0~R3, R12} @R0~R3,R12 入棧 2 STMFD SP!,{LR} @LR 入棧 3 4 LDMFD SP!, {LR} @先恢復 LR 5 LDMFD SP!, {R0~R3, R12} @再恢復 R0~R3, R12
4、跳轉指令
5、算術運算符
6、邏輯運算指令