adr adrl ldr mov簡單科普

ADR是一條小範圍的地址讀取僞指令,它將基於PC的相對偏移的地址值讀到目標寄存器中。格式:ADR register,exper。

 
編譯源程序時,彙編器首先計算當前PC值(當前指令位置)到exper的距離,而後用一條ADD或者SUB指令替換這條僞指令,
例如:ADD register,PC,#offset_to_exper。
注意,標號exper與指令必須在同一代碼段。
好比:adr r0, _start ://將指定地址賦到r0中
    .........
_start:
    b _start
r0的值爲標號_start與此指令的距離差 + PC值。

 
ADRL:
這是一條中等範圍的地址讀取僞指令,它將基於PC的相對偏移的地址值讀到目標寄存器中。格式:ADRL register,exper。編譯源程序時,彙編器會用兩條合適的指令替換這條僞指令。
好比:
ADD register,PC,offset1
ADD register,register,offset2  

 
與ADR相比,它能讀取更大範圍的地址。
注意,標號exper與指令必須在同一代碼段。

 
接下來是LDR,首先要說兩個傢伙,他們都叫LDR。

 
一個是LDR僞指令,一個是LDR指令,名字相同卻不是一個東西。

 
區分的方法就是看第二個參數,若是有等號,就是僞指令

 
LDR指令:
例: ldr r0, 0x12345678
是把0x12345678這個地址中的值存放到r0中。而mov不能幹這個活,mov只能在寄存器之間移動數據,或者把當即數移動到寄存器中。

 
LDR僞指令:
例1(當即數): ldr r0, =0x12345678
這樣,就把0x12345678這個地址寫到r0中了。因此,ldr僞指令和mov是比較類似的。只不過mov指令限制了當即數的長度爲8位,也就是不能超過512。而ldr僞指令沒有這個限制。若是使用ldr僞指令,後面跟的當即數沒有超過8位,那麼在實際彙編的時候該ldr僞指令會被轉換爲mov指令。

 
例2(標號): ldr r0, =_start //將指定標號的值賦給r0
這裏取得的是標號_start的絕對地址,這個絕對地址(運行地址)是在連接的時候肯定的。它要佔用 2 個32bit的空間,一條是指令,另外一條是文字池中存放_start 的絕對地址。

 
對比adr r0, _start和 ldr r0, =_start
它們的目的同樣,都是把標籤的賦給r0,區別---左邊是相對地址,右邊絕對地址。目的同樣,但結果不必定相同。結果是否相同,要看PC值是否和連接地址相同。
相關文章
相關標籤/搜索