彙編中的暫存器說明

2021-03-31 15:04:14 字數 2399 閱讀 1456

組合語言和cpu以及記憶體,埠等硬體知識是連在一起的. 這也是為什麼組合語言沒有通用性的原因. 下面簡單講講基本知識(針對intel x86及其相容機) *************************=== x86組合語言的指令,其操作物件是cpu上的暫存器,系統記憶體,或者立即數. 有些指令表面上沒有運算元, 或者看上去缺少運算元, 其實該指令有內定的操作物件, 比如push指令, 一定是對ss:esp指定的記憶體操作, 而cdq的操作物件一定是eax / edx. 在組合語言中,暫存器用名字來訪問. cpu 暫存器有好幾類, 分別有不同的用處: 1. 通用暫存器: eax,ebx,ecx,edx,esi,edi,ebp,esp(這個雖然通用,但很少被用做除了堆疊指標外的用途) 這些32位可以被用作多種用途,但每乙個都有"專長". eax 是"累加器"(accumulator), 它是很多加法乘法指令的預設暫存器. ebx 是"基位址"(base)暫存器, 在記憶體定址時存放基位址. ecx 是計數器(counter), 是重複(rep)字首指令和loop指令的內定計數器. edx是...(忘了..哈哈)但它總是被用來放整數除法產生的餘數. 這4個暫存器的低16位可以被單獨訪問,分別用ax,bx,cx和dx. ax又可以單獨訪問低8位(al)和高8位(ah), bx,cx,dx也類似. 函式的返回值經常被放在eax中. esi/edi分別叫做"源/目標索引暫存器"(source/destination index),因為在很多字串操作指令中, ds:esi指向源串,而es:edi指向目標串.ebp是"基址指標"(base pointer), 它最經常被用作高階語言函式呼叫的"框架指標"(frame pointer).

在破解的時候,經常可以看見乙個標準的函式起始**: push ebp ;儲存當前ebp mov ebp,esp ;ebp設為當前堆疊指標 sub esp, *** ;預留***位元組給函式臨時變數. ... 這樣一來,ebp 構成了該函式的乙個框架, 在ebp上方分別是原來的ebp, 返回位址和引數. ebp下方則是臨時變數. 函式返回時作 mov esp,ebp/pop ebp/ret 即可. esp 專門用作堆疊指標. 2. 段暫存器: cs(code segment,**段) 指定當前執行的**段. eip (instruction pointer, 指令指標)則指向該段中乙個具體的指令. cs:eip指向哪個指令, cpu 就執行它. 一般只能用jmp, ret, jnz, call 等指令來改變程式流程,而不能直接對它們賦值. ds(data segment, 資料段) 指定乙個資料段. 注意:在當前的計算機系統中, **和資料沒有本質差別, 都是一串二進位制數, 區別只在於你如何用它. 例如, cs 制定的段總是被用作**, 一般不能通過cs指定的位址去修改該段. 然而,你可以為同乙個段申請乙個資料段描述符"別名"而通過ds來訪問/修改. 自修改**的程式常如此做. es,fs,gs 是輔助的段暫存器, 指定附加的資料段. ss(stack segment)指定當前堆疊段. esp 則指出該段中當前的堆疊頂. 所有push/pop 系列指令都只對ss:esp指出的位址進行操作.

3. 標誌暫存器(eflags): 該暫存器有32位,組合了各個系統標誌. eflags一般不作為整體訪問, 而只對單一的標誌位感興趣. 常用的標誌有: 進製標誌c(carry), 在加法產生進製或減法有借位時置1, 否則為0. 零標誌z(zero), 若運算結果為0則置1, 否則為0 符號位s(sign), 若運算結果的最高位置1, 則該位也置1. 溢位標誌o(overflow), 若(帶符號)運算結果超出可表示範圍, 則置1. jxx 系列指令就是根據這些標誌來決定是否要跳轉, 從而實現條件分枝. 要注意,很多jxx 指令是等價的, 對應相同的機器碼. 例如, je 和jz 是一樣的,都是當z=1是跳轉. 只有jmp 是無條件跳轉. jxx 指令分為兩組, 分別用於無符號操作和帶符號操作. jxx 後面的"xx" 有如下字母: 無符號操作: 帶符號操作: a = "above", 表示"高於" g = "greater", 表示"大於" b = "below", 表示"低於" l = "less", 表示"小於" c = "carry", 表示"進製"或"借位" o = "overflow", 表示"溢位" s = "sign", 表示"負" 通用符號: e = "equal" 表示"等於", 等價於z (zero) n = "not" 表示"非", 即標誌沒有置位. 如jnz "如果z沒有置位則跳轉" z = "zero", 與e同. 如果仔細想一想,就會發現 ja = jnbe, jae = jnb, jbe = jna, jg = jnle, jge= jnl, jl= jnge, .... 4. 埠 埠是直接和外部裝置通訊的地方。外設接入系統後,系統就會把外設的資料介面對映到特定的埠位址空間,這樣,從該埠讀入資料就是從外設讀入資料,而向外設寫入資料就是向埠寫入資料。當然這一切都必須遵循外設的工作方式。埠的位址空間與記憶體位址空間無關,系統總共提供對64k個8位埠的訪問,編號0-65535. 相鄰的8位埠可以組成成乙個16位埠,相鄰的16位埠可以組成乙個32位埠。埠輸入輸出由指令in,out,ins和outs實現,具體可參考組合語言書籍。

暫存器說明

table ds 是資料開始的段位址 ss 堆疊段暫存器 sp 堆疊指標,與ss配合使用,可指向目前的堆疊位置 cs 段 ds 資料段 cx 迴圈次數計數器 bx 基址暫存器 si 跟bx相似的暫存器,不能夠分成兩個8位暫存器,源變址暫存器 di 跟bx相似的暫存器,不能夠分成兩個8位暫存器,目地變...

暫存器說明

table ds 是資料開始的段位址 ss 堆疊段暫存器 sp 堆疊指標,與ss配合使用,可指向目前的堆疊位置 cs 段 ds 資料段 cx 迴圈次數計數器 bx 基址暫存器 si 跟bx相似的暫存器,不能夠分成兩個8位暫存器,源變址暫存器 di 跟bx相似的暫存器,不能夠分成兩個8位暫存器,目地變...

暫存器說明

table ds 是資料開始的段位址 ss 堆疊段暫存器 sp 堆疊指標,與ss配合使用,可指向目前的堆疊位置 cs 段 ds 資料段 cx 迴圈次數計數器 bx 基址暫存器 si 跟bx相似的暫存器,不能夠分成兩個8位暫存器,源變址暫存器 di 跟bx相似的暫存器,不能夠分成兩個8位暫存器,目地變...