bin/55078: [patch] mount_mfs crashes RELENG_4 for tyny mfs
Dmitry Morozovsky
marck at rinet.ru
Wed Jul 30 11:40:12 PDT 2003
>Number: 55078
>Category: bin
>Synopsis: [patch] mount_mfs crashes RELENG_4 for tyny mfs
>Confidential: no
>Severity: serious
>Priority: medium
>Responsible: freebsd-bugs
>State: open
>Quarter:
>Keywords:
>Date-Required:
>Class: sw-bug
>Submitter-Id: current-users
>Arrival-Date: Wed Jul 30 11:40:09 PDT 2003
>Closed-Date:
>Last-Modified:
>Originator: Dmitry Morozovsky
>Release: FreeBSD 4-STABLE i386
>Organization:
Cronyx Plus LLC (RiNet ISP)
>Environment:
System: FreeBSD 4-STABLE
>Description:
for restricted jail environment, it's useful to make jail filesystem nodev just
to be safe; the most useful way to make jail's /dev is mfs of minimal size.
It's possible to crash RELENG_4 system that way, as mount_mfs doesn't check it
can successfully allocate inodes for root directory, etc.
Problem is RELENG_4-specific.
---
#0 dumpsys () at /usr/src/sys/kern/kern_shutdown.c:487
487 if (dumping++) {
(kgdb) bt
#0 dumpsys () at /usr/src/sys/kern/kern_shutdown.c:487
#1 0xc013a148 in boot (howto=256) at /usr/src/sys/kern/kern_shutdown.c:316
#2 0xc013a57c in poweroff_wait (junk=0xc01f6847, howto=-1047158784) at /usr/src/sys/kern/kern_shutdown.c:595
#3 0xc01a01e2 in ufs_dirbad (ip=0xc1986400, offset=0, how=0xc01f67f0 "mangled entry") at /usr/src/sys/ufs/ufs/ufs_lookup.c:641
#4 0xc019f9eb in ufs_lookup (ap=0xc5778db8) at /usr/src/sys/ufs/ufs/ufs_lookup.c:291
#5 0xc01a4ad9 in ufs_vnoperate (ap=0xc5778db8) at /usr/src/sys/ufs/ufs/ufs_vnops.c:2376
#6 0xc016436a in vfs_cache_lookup (ap=0xc5778e10) at vnode_if.h:77
#7 0xc01a4ad9 in ufs_vnoperate (ap=0xc5778e10) at /usr/src/sys/ufs/ufs/ufs_vnops.c:2376
#8 0xc016735d in lookup (ndp=0xc5778e8c) at vnode_if.h:52
#9 0xc0166e48 in namei (ndp=0xc5778e8c) at /usr/src/sys/kern/vfs_lookup.c:153
#10 0xc016cb75 in stat (p=0xc4718c20, uap=0xc5778f80) at /usr/src/sys/kern/vfs_syscalls.c:1787
#11 0xc01d7749 in syscall2 (frame={tf_fs = 47, tf_es = 47, tf_ds = 47, tf_edi = -1077937536, tf_esi = -1077937344,
tf_ebp = -1077937440, tf_isp = -982020140, tf_ebx = 251860, tf_edx = -1077937348, tf_ecx = 1059584793, tf_eax = 188,
tf_trapno = 12, tf_err = 2, tf_eip = 671739816, tf_cs = 31, tf_eflags = 663, tf_esp = -1077937628, tf_ss = 47})
at /usr/src/sys/i386/i386/trap.c:1175
#12 0xc01cb775 in Xint0x80_syscall ()
#13 0x804891e in ?? ()
(kgdb)
>How-To-Repeat:
mount_mfs -s 128 -i 256 swap /mnt
[notice 'first cylinder group ran out of space']
touch /mnt/1
>Fix:
Add checks in mount_mfs:
Index: sbin/newfs/mkfs.c
===================================================================
RCS file: /home/ncvs/src/sbin/newfs/mkfs.c,v
retrieving revision 1.29.2.6
diff -u -r1.29.2.6 mkfs.c
--- mkfs.c 21 Sep 2001 19:15:21 -0000 1.29.2.6
+++ mkfs.c 30 Jul 2003 18:23:40 -0000
@@ -148,7 +148,7 @@
long calcipg();
static int charsperline();
void clrblock __P((struct fs *, unsigned char *, int));
-void fsinit __P((time_t));
+int fsinit __P((time_t));
void initcg __P((int, time_t));
int isblock __P((struct fs *, unsigned char *, int));
void iput __P((struct dinode *, ino_t));
@@ -728,7 +728,8 @@
* Now construct the initial file system,
* then write out the super-block.
*/
- fsinit(utime);
+ if (fsinit(utime) == -1)
+ exit(1);
sblock.fs_time = utime;
wtfs((int)SBOFF / sectorsize, sbsize, (char *)&sblock);
for (i = 0; i < sblock.fs_cssize; i += sblock.fs_bsize)
@@ -968,7 +969,7 @@
#endif
char buf[MAXBSIZE];
-void
+int
fsinit(utime)
time_t utime;
{
@@ -1001,6 +1002,8 @@
node.di_nlink = 2;
node.di_size = sblock.fs_bsize;
node.di_db[0] = alloc(node.di_size, node.di_mode);
+ if (node.di_db[0] == 0)
+ return -1;
node.di_blocks = btodb(fragroundup(&sblock, node.di_size));
wtfs(fsbtodb(&sblock, node.di_db[0]), node.di_size, buf);
iput(&node, LOSTFOUNDINO);
@@ -1018,9 +1021,12 @@
else
node.di_size = makedir(root_dir, PREDEFDIR);
node.di_db[0] = alloc(sblock.fs_fsize, node.di_mode);
+ if (node.di_db[0] == 0)
+ return -1;
node.di_blocks = btodb(fragroundup(&sblock, node.di_size));
wtfs(fsbtodb(&sblock, node.di_db[0]), sblock.fs_fsize, buf);
iput(&node, ROOTINO);
+ return 0;
}
/*
>Release-Note:
>Audit-Trail:
>Unformatted:
More information about the freebsd-bugs
mailing list