1.通用暫存器
共有四個,其名稱分別是 AX、BX、CX、DX,在組合語言程式中大致沒有太大的差別,但是其中只有 AX ( accumulator,也稱為累加器) 可作為除法或乘法中的被除數與被乘數,當 16 位元不夠大時,常常用 DX:AX 來表示 32 位元。此外這四個暫存器,只有 BX ( base register,也稱為基底暫存器) 可以被作為位址存取之用。CX 也稱為計數暫存器 ( count register),用於計算迴圈之次數或字串處理之次數。DX 也稱為資料暫存器 ( data register),可用來存取埠。
這四個暫存器也可以分成兩個 8 位元的暫存器來使用,例如 AX 可被分成較低的 8 位元稱為 AL,以及較高的 8 位元 AH 來使用。其餘 BX、CX、DX 也都類似。
2.指標與索引暫存器
有五個,其名稱分別是 SP、BP、IP、SI、DI。前面兩個 SP (stack pointer,稱為堆疊指標)與(base pointer,也稱為基底指標)是與堆疊(stack)有關的暫存器,以獲得詳細的堆疊資料。堆疊是一塊區域,用來暫時存放資料之用,在 8086/8088 中,堆疊是由最高位址中開始存放,每次都必須存入一個字組的長度,並用一組指標,來表示堆疊已經使用到那兒了,這組指標就是 SS:SP。也就是說,當成是要將資料存入堆疊時,該資料應該存放在 SS:SP 所指的位址再低 2 個位元組,然後 CPU 再使 SP 之內容減 2,使 SP 再指到下一個未使用的空間。
那什麼情形會要將資料存入堆疊內呢?有好幾種情形,例如呼叫副程式時,會預先把返回位址存入堆疊﹔呼叫中斷時也是如此。BP 通常用於呼叫副程式時,傳遞參數之用。
IP (instruction pointer,稱為指令指標) 配合 CS 變成 CS:IP,指向將要執行的 8086/8088 位址。當 CPU 要執行程式時,必須到記憶體去提取要執行的指令,而要到那一個記憶體位址去提取指令呢?這時 CPU 就會到 CS:IP 指到的位址去提取。在程式中,一般是沒有辦法改變 CS:IP 的值,除非是跳躍 (jmp、jz等) 指令或是呼叫 (call、ret等) 指令。
SI (source index,稱為來源索引暫存器) 和 DI (destination index,稱為目的索引暫存器) 通常是用來當作位址指標,也可用作加減法。這五個暫存器,每一個都不能分開來當作兩個 8 位元的暫存器使用。
3.區段暫存器
有 CS、DS、ES、SS 四個,分別表示程式碼(code segment register)、資料(data segment register)、額外(extra segment register)、堆疊(stack segment register)區段之用。在 DOS 系統中,每一個區段容量只有 64KBytes。
當資料區段不夠用時,就可以用額外區段來補足,例如想要將一個區段的某些內容複製到另一區段中,就可以同時指定 DS、ES 分別表示這兩個區段。
4.旗標暫存器
旗標暫存器 (flag register) 是一個 16 位元的暫存器,但只有其中九個位元有用到,它們分散在這十六個位元中,採用這種分散方式是為了與舊式的 8080 CPU 的旗標相同。這 9 個旗標可分為三類:狀態旗標 ( status flag )、控制旗標 ( control flag ) 與系統旗標 ( system flag )。狀態旗標包含 CF、PF、AF、ZF、SF 和 OF,它們會受到算術、比較或邏輯運算結果狀態的影響,而使旗標被設定 ( set,其值為 1 ),或被清除 ( clear,其值為零 )。第 10 位元的 DF 用來控制掃描、搬移、搜尋字串的方向,屬於控制旗標。至於 IF、TF 為設計作業系統、除錯時才需要用到,屬於系統旗標,一般應用程式很少使用。底下簡單介紹這些旗標:
名稱 |
位元 |
狀態 |
說明 |
進位旗標
|
0 | CF=1,CY
CF=0,NC |
當運算發生進位或借位時,ZF 被設為 1;反之設為 0。例如兩數相加: mov ax,8000h add ax,8000h 8000h+8000h 應為 10000h,發生進位,雖然 AX 為 0,但是會使 CF 設為一,表示進位。 |
同位旗標
|
2 | PF=1,PE
PF=0,PO |
運算的結果換成二進位後,最低的 8 個位元中,若有偶數個 1,則此位元設為 1,反之為 0。 |
輔助進位旗標
|
4 | AF=1,AC
AF=0,NA |
當運算過程中,第 3 位元與第 4 位元之間發生進位或借位時,AF 被設為 1,否則被設為 0,常用於 BCD 的運算。 |
零旗標
|
6 | ZF=1,ZR
ZF=0,NZ |
運算結果為零時,ZF 會被設定為 1。若比較相同兩數, ZF 也會被設為一,若比較不相同的兩數,ZF 會被清除為零。例如:
mov ax,8000h add ax,8000h 相加後,AX 為零,故 ZF 設為一。 |
符號旗標
|
7 | SF=1,NG
SF=0,PL |
運算結果的最高位元為 1 時,SF 會被設為 1 ( 表示負數 ),否則被清除。 |
陷阱旗標
|
8 | 用於單步追蹤除錯時,所以也稱為追蹤旗標 ( trace flag ),例如在 MS-DOS 的 DEBUG 中,就是利用 TF 達到單步追蹤的目的。當 TF 設為一時,每執行一個指令便會發生中斷,此中斷就將執行該指令後暫存器列出。 | |
中斷旗標
|
9 | IF=1,EI
IF=0,DI |
當 IF 被設定時,可遮罩的硬體中斷才能使 CPU 產生中斷效果;反之所有可遮罩的硬體中斷均會被抑制。但是不可遮罩中斷以及 CPU 產生的例外卻完全不受 IF 影響。 |
方向旗標
|
10 | DF=1,DN
DF=0,UP |
當 DF 被清除時 ( 即 DF=0 ),處理字串的索引暫存器會遞增,往高位址方向處理,反之則遞減。 |
溢位旗標
|
11 | OF=1,OV
OF=0,NV |
當運算結果無法容納於目的運算元中,此旗標會被設為一。大致可分三種情形:(1)兩同號數相加或兩異號數相減,(2)乘除運算時,所得的積或商超過運算元存放範圍,在移位或旋轉指令時,最高位元值受到更動 ( 0 變成 1 或 1 變成 0 )。 |
在此列出 DEBUG 中執行 r 指令後的意義:
-r [Enter] AX=0000 BX=0000 CX=0025 DX=0000 SP=FFFE BP=0000 SI=0000 DI=0000 DS=10F7 ES=10F7 SS=10F7 CS=10F7 IP=0100 NV UP EI PL NZ NA PO NC 10F7:0100 EB19 JMP 0119
英文字母NV UP EI PL等等就是旗標的狀態,請看下表:
旗標名稱 | 設定(1) | 清除(0) |
---|---|---|
CF,進位(是/否)
PF,同位(偶數/基數) AF,輔助進位(是/否) ZF,零(是/否) SF,符號(是/否) IF,中斷(允許/抑制) DF,方向(遞減/遞增) OF,溢位(是/否) |
CY
PE AC ZR NG EI DN OV |
NC
PO NA NZ PL DI UP NV |
沒有留言:
張貼留言