From rbezuide@oskar.nanoteq.co.za Fri Aug  6 00:11:58 1999
Return-Path: <rbezuide@oskar.nanoteq.co.za>
Received: from oskar.nanoteq.co.za (oskar.nanoteq.co.za [196.37.91.10])
	by hub.freebsd.org (Postfix) with ESMTP id C48BE15319
	for <FreeBSD-gnats-submit@freebsd.org>; Fri,  6 Aug 1999 00:11:31 -0700 (PDT)
	(envelope-from rbezuide@oskar.nanoteq.co.za)
Received: (from rbezuide@localhost)
	by oskar.nanoteq.co.za (8.9.0/8.9.0) id JAA26749;
	Fri, 6 Aug 1999 09:13:30 +0200 (SAT)
Message-Id: <199908060713.JAA26749@oskar.nanoteq.co.za>
Date: Fri, 6 Aug 1999 09:13:30 +0200 (SAT)
From: Reinier Bezuidenhout <rbezuide@oskar.nanoteq.co.za>
Reply-To: rbezuide@oskar.nanoteq.co.za
To: FreeBSD-gnats-submit@freebsd.org
Subject: ifconf in sys/net/if.c returns larger buffer than filled
X-Send-Pr-Version: 3.2

>Number:         12996
>Category:       kern
>Synopsis:       ifconf in sys/net/if.c returns larger buffer than filled
>Confidential:   no
>Severity:       serious
>Priority:       medium
>Responsible:    freebsd-bugs
>State:          closed
>Quarter:        
>Keywords:       
>Date-Required:  
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Fri Aug  6 00:20:01 PDT 1999
>Closed-Date:    Mon Mar 12 17:45:33 PST 2001
>Last-Modified:  Mon Mar 12 17:46:12 PST 2001
>Originator:     Reinier Bezuidenhout
>Release:        FreeBSD 3.2-STABLE i386
>Organization:
Nanoteq Pty Ltd
>Environment:

	FreeBSD 3.2-STABLE July 1999 / PII400 
	256 tun devices, fxp0, sl0

>Description:

When a program calls the SIOCGIFCONF ioctl and the
function ifconf in sys/net/if.c is executed, the value
that is returned in ifc.ifc_len could be longer than 
what was filled in the buffer causing the calling process
to read more data an crash.

Example ...

The calling process sends 16384 (512 * 32) as the size of the buffer.

ifconf loops through the number of interfaces and sees that
there are more interfaces than can fit into this buffer.  It
then fills the buffer to 16344 bytes and the one of
the checks fail ... ifconf doesn't return 16344 but still
returns 16384.  This causes the calling process to think that
there is still one more interface is the buffer it received,
which there is not.
e.g. program sendmail Sendmail 8.9.3/8.8.5 (fixed in 8.10)

It could also happen to other programs.

>How-To-Repeat:

	Configure a 3.2-STABLE kernel with more than 256 devices. Boot.
	Delete all devices configured devices (not delete, just
	ifconfig fxp0 delete).
	run newaliases
	It generates a segmentation fault.

>Fix:
	
	Checking was added to sendmail 8.10 for this.
	in sys/net/if.c add code to only return the exact amount
	of data written into the buffer.
	Example patch - not the best way. Please check :)

*** if.c.orig   Thu Jul 29 14:30:11 1999
--- if.c        Thu Jul 29 14:34:45 1999
***************
*** 814,820 ****
        register struct ifnet *ifp = ifnet.tqh_first;
        register struct ifaddr *ifa;
        struct ifreq ifr, *ifrp;
!       int space = ifc->ifc_len, error = 0;

        ifrp = ifc->ifc_req;
        for (; space > sizeof (ifr) && ifp; ifp = ifp->if_link.tqe_next) {
--- 814,820 ----
        register struct ifnet *ifp = ifnet.tqh_first;
        register struct ifaddr *ifa;
        struct ifreq ifr, *ifrp;
!       int space = ifc->ifc_len, error = 0, unused = 0;

        ifrp = ifc->ifc_req;
        for (; space > sizeof (ifr) && ifp; ifp = ifp->if_link.tqe_next) {
***************
*** 857,862 ****
--- 857,864 ----
                                                sizeof (ifr));
                                ifrp++;
                        } else {
+                               /* keep the value of unused space so far */
+                               unused = space;
                                space -= sa->sa_len - sizeof(*sa);      
                                if (space < sizeof (ifr))
                                        break;
***************
*** 871,879 ****
                        if (error)   
                                break;
                        space -= sizeof (ifr);
                }
        }
!       ifc->ifc_len -= space;       
        return (error);
  }
  
--- 873,883 ----
                        if (error)   
                                break;
                        space -= sizeof (ifr);
+                       /* reset the unused space to zero */
+                       unused = 0;  
                }
        }
!       ifc->ifc_len -= space + unused;
        return (error);
  }
  


>Release-Note:
>Audit-Trail:

From: Patrick Bihan-Faou <patrick@mindstep.com>
To: freebsd-gnats-submit@FreeBSD.org, rbezuide@oskar.nanoteq.co.za
Cc:  
Subject: Re: kern/12996: ifconf in sys/net/if.c returns larger buffer than filled
Date: Sat, 11 Mar 2000 02:22:50 -0500

 This PR should be closed by the fix included in kern/17311.
 
 
 http://www.freebsd.org/cgi/query-pr.cgi?pr=17311
 
 
 
 -- 
 Patrick Bihan-Faou
 MindStep Corporation
 
 
State-Changed-From-To: open->feedback 
State-Changed-By: guido 
State-Changed-When: Fri Apr 21 19:50:43 MEST 2000 
State-Changed-Why:  
Please chck if rev. 1.86 of if.c (in 5.0-current) or rev 1.85.2.1 
(4.-stable) fixes it 
State-Changed-From-To: feedback->closed 
State-Changed-By: des 
State-Changed-When: Mon Mar 12 17:45:33 PST 2001 
State-Changed-Why:  
This problem was fixed a long time ago, but only onw of the two PRs 
reporting it was closed. 

http://www.freebsd.org/cgi/query-pr.cgi?pr=12996 
>Unformatted:
