상세 컨텐츠

본문 제목

[Exploit Tech] ROP (Return Oriented Programming) -x64

SYSTEM HACKING/Exploit Tech

by koharin 2019. 8. 17. 17:12

본문

728x90
반응형

1. Gadgets POP; POP; POP; RET

 

x64의 호출 규약은 System V AMD64 ABI (x86의 호출 규약은 Cdecl(C declaration))

- 따라서 x64의 호출 규약으로 pop 명령어의 피연산자가 중요하다.

- x64ROP에서 POP 명령어의 역할

-> ESP 레지스터의 값을 증가시켜 함수를 연속으로 호출

-> 호출할 함수에 전달될 인자 값을 레지스터에 저장 (인자 값은 Stack에 저장되어 있음)

 

Gadgets

- “pop rdi; ret” : 호출할 함수의 첫 번째 인자 값을 저장

- “pop rsi; ret” : 호출할 함수의 두 번째 인자 값을 저장

- “pop rdi; pop rdx; ret” : 호출할 함수의 첫 번째, 세 번째 인자값을 저장

 

● 여러 개의 함수 연속해서 실행하는 방법

- x64에서는 Gadgets을 이용해 인자 값을 레지스터에 저장한 후 함수를 호출한다.

- Ex. Read 함수 호출 후 system 함수 호출

 

 

2. Proof of concept

 

# example code

 

 

# build & permission

$ gcc -fno-stack-protector -o rop rop.c -ldl

 

 

$ sudo chown root:root ./rop

$ sudo chmod 4755 ./rop

 

 

uid, gid 권한 모두 root로 설정하고 SetUID를 설정했다.

 

# Overflow

1) breakpoint 설정

- bp 1 : vuln 함수 첫 번째 코드 부분

- bp 2 : read 함수 호출 전

 

 

Read(0, buf, 256) 이므로 read 함수 호출 전 인자 구성 시

“mov edx, 0x100” 가 세 번째 인자를,

“mov rsi, rax” 가 두 번째 인자인 buf,

“mov edi, 0x0” 이 첫 번째 인자인 0을 넣는 것일 것이다.

따라서 buf의 시작주소를 알려면 rax 레지스터의 값을 출력해보면 될 것 같다.

 

Bp 1 : return address 확인 : 0x7ffc408dfb58 return address 0x4007d0을 값으로 가진다.

Bp 2 : buf 시작 주소 확인 : 0x7ffc408dfb10

Return address buf 시작 주소 = buf에서 return address 까지 거리 = 72

rbp-0x40 이므로 buf의 크기는 64 바이트이다.

Buf(64) + dummy(4) + SFP(4) + return address(4) stack 구조이다.

 

 

(bp 1에서 return address 0x4007d0은 실제로 vuln 함수 종료 후 main으로 리턴 시 시행할 다음 코드 주소임을 알 수 있다.)

 

3. exploit method

# exploit 순서

1. setuid 함수를 이용해 권한을 root(0)으로 변경 : setresuid(0, 0, 0)

2. system 함수를 이용해 “/bin/sh” 실행 : system(“/bin/sh”)

 

# 공격을 위해 필요한 정보

- “/bin/sh” 문자열이 저장된 영역

- libc offset : printf, system, setresuid

- 가젯의 위치 : pop rdi; ret , pop rsi; ret , pop rdx; ret

 

# “/bin/sh” libc 주소

 

안 구해진다…?

(Gdb-peda 로는 find “/bin/sh” 명령어로 바로 찾을 수 있다. )

 

“/bin/sh”를 어떻게 구할까

 

$ strings -t x /lib/x86_64-linux-gnu/libc-2.23.so | grep “/bin/sh”

 

 

구글링 했더니 이런 방법이..!

“/bin/sh” libc offset = 0x18cd57

Libc 시작 주소에서 이 0x18cd57 offset을 더하면 “/bin/sh” 주소인 것인가!

 

 

 

# printf ,system, setresuid 함수 offset

 

 

 

# gadgets

 

 

pop_rdx_ret_offset = 0x001150c9

 

Pop rdi; ret : 0x400843

Pop rsi; pop r15; ret : 0x400841

 

# exploit

 

 

Pop_rdi_ret 가젯은 system 함수 인자 세팅 시 필요한 가젯

 

 

728x90
반응형

관련글 더보기