20222318 2024-2025-1 《網路與系統攻防技術》實驗一實驗報告

追风是菜鸟發表於2024-10-11

一.實驗內容

(一)本週學習內容

本週學習了緩衝區溢位的相關原理,包括簡單的彙編程式碼、緩衝區溢位本質、堆疊的工作原理、Shellcode的編寫等等。

(二)實驗涉及知識點

(1)Linux基本操作:

①熟悉Linux環境:能夠在Linux系統中進行基本的檔案操作、目錄導航,如cd等。
②常用指令理解:如管道(|)、輸入、輸出重定向(>)、提升命令許可權(sudo)等。

(2)緩衝區溢位原理:

①緩衝區溢位原理:本質是陣列的生長方向與棧的生長方向相反,且陣列呼叫沒有進行越界檢查。
②返回地址覆蓋:掌握如何透過緩衝區溢位覆蓋棧上的返回地址,以控制程式的執行路徑。
③堆疊原理:理解堆疊的工作原理,包括資料的壓棧和出棧過程。
④返回地址位置:明確在函式呼叫過程中,返回地址是如何被儲存在堆疊上的。

(3)程式彙編與反彙編:

①組合語言基礎:能看懂簡單的彙編程式碼,如指令呼叫call、資料移動mov等。
②EIP與指令地址:理解EIP(指令指標暫存器)的作用,以及EIP如何操作才能變成call需要的地址。
③objdump工具:會使用objdump工具對程式進行反彙編,以檢視其彙編程式碼。

(4)程式編輯與除錯:

①gdb偵錯程式:會使用gdb進行程式的除錯,如設定斷點、檢視暫存器值、記憶體地址等。
②vi編輯器:掌握vi文字編輯器的使用方法,用於修改程式碼或編寫指令碼。

(5)Shellcode相關知識:

①Shellcode編寫:瞭解如何編寫或獲取一段用於執行特定操作的機器碼Shellcode。
②Shellcode注入:掌握將Shellcode注入到目標程式中的方法,以實現特定的攻擊效果。
③堆疊可執行設定:瞭解如何設定堆疊為可執行狀態,以便注入的Shellcode能夠執行。
④地址隨機化關閉:掌握如何關閉地址隨機化技術,以穩定地找到目標程式的地址空間。

二.實驗過程

(一)任務一:手工修改可執行檔案,改變程式執行流程,直接跳轉到getShell函式。

(1)下載並解壓縮pwn1檔案,透過Xftp傳輸到Kali虛擬機器上

(2)修改主機名(檔名也全程要注意有學號痕跡!)

在命令列頁面使用sudo hostnamectl set-hostname 新的主機名命令將主機名修改為自己的姓名拼音
再重啟即可(可手動可用命令sudo reboot

(3)反彙編檢視pwn1檔案的彙編程式碼,瞭解這一部分彙編程式碼的意義以及做的事情(非必須)

反彙編需要進入檔案所在資料夾,在該資料夾下進入命令列終端,命令為objdump -d 可執行檔案 | more

·~往下查詢目標函式,看到main函式第四行“e8 d7ffffff call 804891 ”,瞭解到彙編程式碼中call後面跟的地址即為foo函式的首地址,這點在圖中函式左側也有體現。再看機器碼e8 d7ffffff,結合圖上其他call的機器碼,猜測e8是對EIP進行操作的意思。而後面跟的是一個運算元,EIP與該運算元進行補碼加運算得到真實的需要跳轉的函式的地址。
·~具體原理:當main函式執行到call一行時,EIP此時已指向下一行即80484ba,此時將EIP壓棧,這個值在foo函式執行完畢後,會被用來恢復EIP,從而使程式能夠繼續執行foo之後的指令。然後處理器才會計算目標地址,再將EIP設定為計算出的目標函式的地址,從而跳轉到foo函式執行。
·~所以此處若需直接改動跳轉地址,需計算EIP相對於函式的偏移量,804847d-80484ba得到是c3ffffff,故將“e8 d7ffffff”改為“e8 c3ffffff”即可。

(4)備份pwn檔案並修改備份檔案

所需命令如下:
cp pwn1 複製後的檔名 //cp是複製檔案命令
vi pwn20222318 //vi+檔名進行修改
//開啟檔案後顯示亂碼
:%!xxd //將檔案顯示模式切換為16進位制模式
/e8 d7 //‘/’為檢索命令。此處可換成/d7ff

i進入插入模式,修改“d7”為“c3”,按Esc退出插入模式
再用:%!xxd -r命令轉換回原格式,最後:wq儲存並退出(如果沒用root賬號登入需要在後面加一個!,如:wq!表示強制執行)

再用反彙編命令objdump -d pwn20222318 | more檢視,修改成功

(5)執行pwn檔案,檢驗是否成功

此時直接執行檔案可以直接跳轉ShellCode.
其中chmod +x ./可執行檔案是提升檔案許可權的指令,因為我註冊的是普通使用者,做什麼操作都要提升許可權(比如還要用sudo命令)
./pwn就能執行pwn了

可以看到出現Shell提示符$,任務一完成。

(二)任務二:利用foo函式的Bof漏洞,構造一個攻擊輸入字串,覆蓋返回地址,觸發getShell函式。

(1)反彙編瞭解程式結構

由上圖可見foo函式只預留了56位元組的緩衝區(0x38=3*16+8=56)【自己的理解:其中sub是不借位減法指令,在上一行將棧底指標的值賦給棧頂指標,進行整個棧幀的清空、初始化,下一行就對棧頂指標進行操作,為棧中的區域性變數預留空間。】,而只要我們輸入足夠長的字串,超出部分就會溢位,從而覆蓋到返回地址。棧的結構參考如下:

故接下來我們需要看輸入字元才能覆蓋到返回地址RET(在除錯過程中體現為EIP的值),以及具體是哪幾個字元的位置可以覆蓋到RET

(2)確認輸入字串哪幾個字元會覆蓋到返回地址

此處需要用到編譯、斷點功能,顧需要下載編譯器gdb。使用sudo apt-get update && sudo apt-get upgrade升級下載服務包,再用sudo apt-get install gdb下載gdb。

下載完之後用gdb --version檢視是否下載完成,如上圖。

複製一份pwn檔案,之後進行編譯。使用字串“8個1,8個2,8個3,8個4,8個5”作為輸入,使用如圖命令檢視各暫存器的值。

可以看到EBP=0x34343434,0x34是ASCII碼中的4,又EIP=0x35353535,是ASCII碼中的5,可以確定最終覆蓋在RET上的數字為5555(前四個)

(3)確認存放順序是小端還是大端,從而確認如何輸入才能將Shell的地址正確覆蓋在返回地址上

這次使用字串“8個1,8個2,8個3,8個4,12345678”作為輸入。

可以看到,EIP=0x34333231,即4321,確認為倒序。故等下輸入返回地址的時候也需要是倒序。

再用斷點驗證一下猜想(指導裡這麼寫的,但是我沒太看懂這一步有什麼用?)

結合反彙編檔案中的getshell地址0804847d,故最終應輸入“8個1,8個2,8個3,8個4,\x7d\x84\x04\x08......”

(4)構造輸入字串

因為我們沒法透過鍵盤輸入\x7d\x84\x04\x08這樣的16進位制值,所以先生成包括這樣字串的一個檔案。\x0a表示回車,如果沒有的話,在程式執行時就需要手工按一下Enter鍵。

xxd是使用十六進位制檢視input檔案的命令,驗證輸入無誤之後可將input檔案作為pwn的輸入。

可以看見執行pwn檔案後出現了命令列,輸入指令,可以正常執行,任務二完成。

(三)任務三:注入一個自己製作的shellcode並執行這段shellcode。

(1)做準備工作,為pwn檔案放行

下載execstack:在自己的物理機上下載。網址:
下載完之後用Xftp傳到虛擬機器上,用sudo dpkg -i execstack_0.0.20131005-1+b10_amd64.deb命令解壓縮即可

接著就是輸入下圖指令(-s設定堆疊可執行,-q查詢檔案的堆疊是否可執行,echo “0” 關閉地址隨機化)

(2)構造要注入的Payload

注:本環節需要開啟兩個終端,一個用於監聽程序執行,一個用於執行程序
開啟終端後點選檔案一欄內的“新建標籤頁”即可

在參考資料內找到一段用於攻擊的Shellcode:\x90\x90\x90\x90\x90\x90\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x50\x53\x89\xe1\x31\xd2\xb0\x0b\xcd\x80\x90\x4\x3\x2\x1\x00

開啟一個終端注入這個攻擊buf

再開啟另一個終端,先用ps -ef | grep pwn20222318-3檢視程序號

可以看見./pwn20222318-3的程序號為47056(因人而異)
再使用gdb除錯該程序

透過設定斷點,來檢視注入buf的記憶體地址

ret完,就跳到我們覆蓋的retaddr那個地方了,在另外一個終端中按下回車,繼續執行。

然後完善Shellcode,將分析所得結果填入,以input_shellcode檔案作為輸出執行。

Shellcode成功執行了,任務三結束。
另:有一個有趣的現象,此時另一個終端也出現了Shellcode的神秘命令列。

三.問題及解決方案

  • 問題1:Xftp無法連線上Kali虛擬機器,無法傳輸pwn檔案

  • 問題1解決方案:使用sudo vi /etc/ssh/sshd_config命令修改ssh配置檔案,將#TcpForwarding yes這一行以及以下四行的“#”都刪去,然後將Gateway改成yes,再用sudo systemctl restart sshd重啟ssh服務,再與Xftp建立連線即可。

  • 問題2:用/e8d7命令找對應機器碼的時候沒找到

  • 問題2解決方案:在檔案內e8 d7不是連著的,中間有空格,故檢索命令中間加個空格就行了。

  • 問題3:執行./pwn檔案時許可權不夠

  • 問題3解決方案:使用chmod +x ./pwn提升許可權

  • 問題4:關閉地址隨機化的時候許可權不夠,sudo語句不能解決問題

  • 問題4解決方案:使用 sudo echo "0" > /proc/sys/kernel/randomize_va_space 命令時,實際上 sudo 只提升了 echo 命令的許可權,而沒有提升重定向運算子 > 的許可權。因此,這個命令會因為許可權不足而失敗,故使用sudo sh -c '需要提升許可權的命令'命令進行操作

  • 問題5:任務三不知道怎麼分析出的堆疊地址

  • 問題5解決方案:待解決

四.學習感悟、思考等

這次實驗真的很考驗實踐能力了,很多知識都不僅僅是從課堂上學的,要自己去查每一行程式碼什麼意思,從而去從底層理解緩衝區溢位的原理。這是以前從來沒有過的視角,理解起來確實有一點挑戰。計算機底層的世界有些晦澀,但也歡迎求知者去探索。我從這次實驗學到了很多,也改進了我的學習方法。從以前的只會運用課堂知識去做實驗,到現在的主動去網上找大量資料去補全自己的知識網路,我在慢慢習慣大三的學習節奏。希望我能繼續克服萬難,學好網路攻防!

相關文章