bin/86135: Fwd: Latent buffer overflow in getcwd

Trevor Blackwell tlb at tlb.org
Wed Sep 14 13:20:23 PDT 2005


>Number:         86135
>Category:       bin
>Synopsis:       Latent buffer overflow in getcwd
>Confidential:   no
>Severity:       non-critical
>Priority:       low
>Responsible:    freebsd-bugs
>State:          open
>Quarter:        
>Keywords:       
>Date-Required:
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Wed Sep 14 20:20:21 GMT 2005
>Closed-Date:
>Last-Modified:
>Originator:     Trevor Blackwell
>Release:        FreeBSD 5.4-RELEASE-p6 i386
>Organization:
Anybots Inc
>Environment:
System: FreeBSD tlb.anybots.com 5.4-RELEASE-p6 FreeBSD 5.4-RELEASE-p6 #0: Mon Sep 12 17:14:32 PDT 2005 root at tlb.anybots.com:/usr/obj/usr/src/sys/TLB i386


>Description:

The libc getcwd has a latent bug, where it allocates a buffer of 1020 bytes and assumes 
it to have MAXPATHLEN (=1024) bytes. Normal modern mallocs will allocate 1024 bytes
anyway, but a different malloc could cause an overrun, and changing MAXPATHLEN could cause
trouble, and it'll cause trouble with debugging mallocs.

Allocating 1024-4 was an optimization assuming the existence of a malloc header, which
isn't the case nowadays. The most important think is that eup = up + upsize, but the most
robust plan is to allocate MAXPATHLEN bytes in case that changes.

>How-To-Repeat:
       It wouldn't be easy to cause an actual corruption

>Fix:

Index: getcwd.c
===================================================================
RCS file: /home/ncvs/src/lib/libc/gen/getcwd.c,v
retrieving revision 1.25
diff -c -r1.25 getcwd.c
*** getcwd.c    29 Oct 2003 10:45:01 -0000      1.25
--- getcwd.c    14 Sep 2005 18:25:48 -0000
***************
*** 115,123 ****
         * Should always be enough (it's 340 levels).  If it's not, allocate
         * as necessary.  Special case the first stat, it's ".", not "..".
         */
!       if ((up = malloc(upsize = 1024 - 4)) == NULL)
                goto err;
!       eup = up + MAXPATHLEN;
        bup = up;
        up[0] = '.';
        up[1] = '\0';
--- 115,123 ----
         * Should always be enough (it's 340 levels).  If it's not, allocate
         * as necessary.  Special case the first stat, it's ".", not "..".
         */
!       if ((up = malloc(upsize = MAXPATHLEN)) == NULL)
                goto err;
!       eup = up + upsize;
        bup = up;
        up[0] = '.';
        up[1] = '\0';



>Release-Note:
>Audit-Trail:
>Unformatted:


More information about the freebsd-bugs mailing list