binee::
[sCTF 2016] pwn1 write up 본문
4박5일동안 진행하는 sCTF에서 pwnable 문제가 총 3개가 나왔다.
난이도는 상당히 쉬운 편이었고, 독창성이 있거나 기발한 문제는 없었다.
pwnable에 기본기만 가지고 있다면 시간을 투자하여 충분히 풀 수 있는 문제들이었다.
pwn1은 창의적이고 기발한 아이디어를 가진 문제는 아니었다.
가볍게 워밍업으로 푸는 문제로 풀이도 가볍게 쓰려고 한다.
Binary 분석
pwn1 바이너리를 확인 해보면
pwn1: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV), dynamically linked (uses shared libs), for GNU/Linux 2.6.24, BuildID[sha1]=4b1df4d30f1d6b75666c64bed078473a4ad8e799, not stripped
위와 같이 32bit elf 파일이고, stack canary가 없는 것을 확인 할 수 있다.
여기서부터 buffer overflow 느낌이 팍팍 온다.
Program Logic 분석
.
IDA로 확인해보면 main함수에는 vuln()함수를 호출하는 것 외에 아무것도 없다.
그리고 친절하게 get_flag라는 함수를 제공해준 것으로 보아 eip만 변조해서 get_flag함수만 호출하면 될 것 같다.
아래는 vuln함수의 hex-xay 결과다.
객체가 나오는 것으로 보아서 g++로 컴파일한 바이너리 같다.
처음에 분석 할 때 당황스러웠지만 계속해서 보니까 string 객체를 사용할때 어떤 식으로
함수들이 호출되는 알 수 있어서 좋았다.
내용은 간단하다. 32글자 입력 받고 해당 글자에서 I라는 문자열이 존재하면 you로 replace를 시킨다는 내용이다.
그림에 있는 Hex-Ray 결과에는 replace 인자값이 3개로 나와있지만,
어셈블리로 확인해보면 인자값이 4개가 넘어간다.
replace(&v4, &input, &v7, &v5) v5 변수가 누락되어서 해석되었다.
내 IDA만 그런건지 모르겠지만
나는 개인적으로 이런 경우가 많아서 IDA를 신뢰하지 않는 편이다.
그래서 매번 C코드를 보고 난 뒤 실제로 어셈블리 코드와 일치하는지 확인하는 과정을 거친다.
동적분석으로 확인해보겠다.
실제로 확인해보니 I -> you로 바꾸고
strcpy로 다시 s변수에 바뀐 문자열을 넣는 것을 확인할 수 있다.
프로그램 로직 분석은 끝났다!
Exploit
Exploit 방법은 설명 안해도 알 거라 믿는다...
그래도 writeup이니까
fgets로 입력 받을 수 있는 최대 문자수는 32글자이다.
스트링값을 입력 받는 s변수의 길이는 32byte이고
그외에 string 객체를 사용하면서 이용하는 변수들의 크기가 28byte를 차지한다.
s[32byt] + 변수들[28byte] + sfp[4byte]
위와 같은 stack구조를 가지므로, 총64바이트를 s값에 넣고
get_flag함수 주소 값으로 return address를 덮어버리면 된다.
그렇다면 fgets 입력 받을 수 있는 값은 32가 최대인데 어떻게 68byte를 덮을 것인지가 문제이다.
주어진 기능에서 한글자를 세글자로 늘려주는 기능이 있다.(I -> you)
I를 20번 입력하고 다른 문자열로 4개만 채워주면 24 글자만으로 64byte를 채울 수 있으므로 이를 통해서 stack overflow를 할 수 있다.
아래는 exploit 코드이다.
'CTF' 카테고리의 다른 글
[sCTF 2016] pwn3 write up (0) | 2016.04.21 |
---|---|
[sCTF 2016] pwn2 write up (0) | 2016.04.19 |
[Codegate 2016] oldschool write up (2) | 2016.04.19 |
[Codegate 2016] manager write up (0) | 2016.04.02 |
[Codegate 2016] watermelon write up (1) | 2016.03.27 |