ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • [FTZ]해커스쿨(HackerSchool) LEVEL11 풀이(Solution)
    미사용/##Security 2015. 8. 15. 01:17

    HackerSchool FTZ WARGAME Solution

     

    Start : 15.07.03

     

    LEVEL11

     

    [그림 1]

     

    hint 파일을 열어 attackme 프로그램의 소스를 확인 해 보면 main 함수에서 argv 값을 전달받아 str 배열에 복사하는 것을 확인할 수 있다.

     

    [그림 2]

     

    gdb를 이용해 attackme를 열어보면 sub esp, 0x108 즉 264byte 만큼 메모리 공간을 할당한다. 그리고 strcpy 함수 부분을 보면 [ebp-264]를 인자로 전달을 하는데 이게 곳 str 배열의 시작 주소라는 것을 확인할 수 있다.

     

     

    [그림 3]

     

    call strcpy를 하기 직전 stack을 간단하게 그려보면 [그림 3]과 같이 나타내지는데 strcpy 함수로 전달되는 인자값 중에 [ebp+12] + 4를 한 값을 push 하는데 [ebp+12]에는 main 함수의 argv 값인데 argv로 전달되는 문자열은 문자열이 복사되는게 아니라 문자열이 위치한 메모리의 주소값이 전달된다. 따라서 [ebp+12] 는 주소값이 있고 이 주소값에 4만큼 더한 값을 strcpy 로 전달한다. 그 이유에 대해서 생각해보면 c언어의 main 함수가 인자를 전달받을 때 프로그램 명도 하나의 인자값으로 받기 때문에 실제 프로그램에 전달되는 인자값은 argv[1]에 저장이 된다. 따라서 우리가 원하는 인자값을 strcpy에 전달하기 위해서는 [ebp+12]에서 4만큼 더한 곳의 값을 push 해야한다.

     

    여기서 우선 쉘 코드를 메모리에 저장하고, strcpy를 이용해 버퍼 오버플로우를 발생시켜서 RET 값을 쉘 코드가 저장된 곳의 주소값으로 덮어 쓰는 방식으로 공격을 진행하려 한다.

     

    [그림 4]

     

    우리가 공격에 사용하는 쉘 코드를 우선 환경 변수에 저장을 한다. [그림 4]를 보면 그 명령어와 과정이 나와있는데 우선 바이너리로 전달하기 위해 perl을 사용했다. 특이한점은 \x90 (NOP)를 쉘 코드 앞에 100개 만큼 넣은 다음, 쉘 코드를 이어서 저장하는데 이 이유는 환경 변수의 주소는 파일명이나 실행하는 경로 등에 의해 약간씩 변하게 된다. 그렇기 때문에 우리는 공격을 확실하게 성공하기 위해 쉘 코드 앞에 "\x90"x100을 입력해 주었다.

     

    [그림 5]

     

    export를 입력해 환경 변수가 정상적으로 입력이 되었는지 확인할 수 있다.

     

    [그림 6]

     

    그리고 간단하게 환경 변수의 주소를 출력하는 프로그램을 [그림 6]과 같이 작성을 하고, 컴파일러를 한다.

     

    [그림 7]

     

    그리고 만들어진 프로그램으로 우리가 추가한 한경 변수의 주소가 [그림 7]과 같이 출력이 된다.

     

    [그림 8]

     

    그리고 이어서 attackme 프로그램에 공격 코드를 전달하면 되는데 여기서도 마찬가지로 바이너리 값을 전달하기 위해 perl을 사용했다. 코드를 분석해 보면 A를 268개를 프로그램에 전달해서 EBP 값까지 다 덮은 다음, RET 값을 앞에서 봤던 shellcode 의 주소값으로 전달하면 공격에 성공한다.

     

    이 때 주의점은 cpu가 리틀엔디언 방식으로 데이터를 읽기 때문에 1byte 단위로 거꾸로 전달해야 한다.

     

     

    댓글

Designed by Tistory.