NX 와 ASLR이 걸린 환경에서 brute-force 방식으로 return to libc 를 해야할때 우선적으로 타겟 system 함수의 libc 오프셋을 구해야 한다.
코딩이 가능한 환경이라면 아래와같이 구할수 있다. 만약 그렇지 않다면 /lib 밑의 libc.so 파일의 정확한 버전을 파악하고 인터넷에서 동일한 버전을 구해서 그것을 코딩 가능한 리눅스 환경으로 옮기고 테스트하면 될것이다... libc.so 의 정확한 버전도 알수없는 상황이라면... 방법이 없다
#define _GNU_SOURCE
#include <stdio.h>
#include <link.h>
// system 함수의 초반 머신코드 패턴. gdb 로 알아내면됨
char* pattern = "\x83\xec\x0c\x89\x74\x24\x04\x8b\x74\x24"; // system
unsigned int libc_start=0;
unsigned int offset=0;
static int print_callback(struct dl_phdr_info *info, size_t size, void *data){
if((strstr(info->dlpi_name, "libc"))){
printf("%08x %s\n", info->dlpi_addr, info->dlpi_name);
libc_start = info->dlpi_addr;
}
return 0;
}
int main(){
// dynamic 하게 로딩되는 library 들에 대한 정보를 받는 콜백함수 등록후 호출.
dl_iterate_phdr(print_callback, NULL);
// libc 가 없음.
if(libc_start==0) return 0;
// libc 의 시작에서부터 바이트패턴매칭으로 system 함수의 시작을 찾음
for(offset = libc_start ; offset < 0xb7ffffff ; offset++){
if(!strncmp((char *)offset, pattern, strlen(pattern))){
printf("pattern address : 0x%x\n", offset);
printf("offset : %0x\n", offset - libc_start);
break;
}
}
return 0;
}
'Programming' 카테고리의 다른 글
Kernel module symbol reference (0) | 2013.07.10 |
---|---|
Linux x86 system call table (0) | 2013.07.10 |
x86 CR3 register (0) | 2013.07.10 |
x86 assembly 16bit prefix (0) | 2013.07.10 |
FreeBSD system call table (0) | 2013.07.10 |