svn commit: r342548 - in head/sys: fs/ext2fs kern ufs/ffs ufs/ufs
Kirk McKusick
mckusick at FreeBSD.org
Thu Dec 27 07:18:55 UTC 2018
Author: mckusick
Date: Thu Dec 27 07:18:53 2018
New Revision: 342548
URL: https://svnweb.freebsd.org/changeset/base/342548
Log:
When loading an inode from disk, verify that its mode is valid.
If invalid, return EINVAL. Note that inode check-hashes greatly
reduce the chance that these errors will go undetected.
Reported by: Christopher Krah <krah at protonmail.com>
Reported as: FS-5-UFS-2: Denial Of Service in nmount-3 (ffs_read)
Reviewed by: kib
MFC after: 1 week
Sponsored by: Netflix
M sys/fs/ext2fs/ext2_vnops.c
M sys/kern/vfs_subr.c
M sys/ufs/ffs/ffs_snapshot.c
M sys/ufs/ufs/ufs_vnops.c
Modified:
head/sys/fs/ext2fs/ext2_vnops.c
head/sys/kern/vfs_subr.c
head/sys/ufs/ffs/ffs_snapshot.c
head/sys/ufs/ufs/ufs_vnops.c
Modified: head/sys/fs/ext2fs/ext2_vnops.c
==============================================================================
--- head/sys/fs/ext2fs/ext2_vnops.c Thu Dec 27 04:53:53 2018 (r342547)
+++ head/sys/fs/ext2fs/ext2_vnops.c Thu Dec 27 07:18:53 2018 (r342548)
@@ -1920,6 +1920,11 @@ ext2_vinit(struct mount *mntp, struct vop_vector *fifo
vp = *vpp;
ip = VTOI(vp);
vp->v_type = IFTOVT(ip->i_mode);
+ /*
+ * Only unallocated inodes should be of type VNON.
+ */
+ if (ip->i_mode != 0 && vp->v_type == VNON)
+ return (EINVAL);
if (vp->v_type == VFIFO)
vp->v_op = fifoops;
Modified: head/sys/kern/vfs_subr.c
==============================================================================
--- head/sys/kern/vfs_subr.c Thu Dec 27 04:53:53 2018 (r342547)
+++ head/sys/kern/vfs_subr.c Thu Dec 27 07:18:53 2018 (r342548)
@@ -156,7 +156,7 @@ SYSCTL_ULONG(_vfs, OID_AUTO, mnt_free_list_batch, CTLF
*/
enum vtype iftovt_tab[16] = {
VNON, VFIFO, VCHR, VNON, VDIR, VNON, VBLK, VNON,
- VREG, VNON, VLNK, VNON, VSOCK, VNON, VNON, VBAD,
+ VREG, VNON, VLNK, VNON, VSOCK, VNON, VNON, VNON
};
int vttoif_tab[10] = {
0, S_IFREG, S_IFDIR, S_IFBLK, S_IFCHR, S_IFLNK,
Modified: head/sys/ufs/ffs/ffs_snapshot.c
==============================================================================
--- head/sys/ufs/ffs/ffs_snapshot.c Thu Dec 27 04:53:53 2018 (r342547)
+++ head/sys/ufs/ffs/ffs_snapshot.c Thu Dec 27 07:18:53 2018 (r342548)
@@ -2001,15 +2001,19 @@ ffs_snapshot_mount(mp)
continue;
}
ip = VTOI(vp);
- if (!IS_SNAPSHOT(ip) || ip->i_size ==
+ if (vp->v_type != VREG) {
+ reason = "non-file snapshot";
+ } else if (!IS_SNAPSHOT(ip)) {
+ reason = "non-snapshot";
+ } else if (ip->i_size ==
lblktosize(fs, howmany(fs->fs_size, fs->fs_frag))) {
- if (!IS_SNAPSHOT(ip)) {
- reason = "non-snapshot";
- } else {
- reason = "old format snapshot";
- (void)ffs_truncate(vp, (off_t)0, 0, NOCRED);
- (void)ffs_syncvnode(vp, MNT_WAIT, 0);
- }
+ reason = "old format snapshot";
+ (void)ffs_truncate(vp, (off_t)0, 0, NOCRED);
+ (void)ffs_syncvnode(vp, MNT_WAIT, 0);
+ } else {
+ reason = NULL;
+ }
+ if (reason != NULL) {
printf("ffs_snapshot_mount: %s inode %d\n",
reason, fs->fs_snapinum[snaploc]);
vput(vp);
Modified: head/sys/ufs/ufs/ufs_vnops.c
==============================================================================
--- head/sys/ufs/ufs/ufs_vnops.c Thu Dec 27 04:53:53 2018 (r342547)
+++ head/sys/ufs/ufs/ufs_vnops.c Thu Dec 27 07:18:53 2018 (r342548)
@@ -2517,6 +2517,11 @@ ufs_vinit(mntp, fifoops, vpp)
vp = *vpp;
ip = VTOI(vp);
vp->v_type = IFTOVT(ip->i_mode);
+ /*
+ * Only unallocated inodes should be of type VNON.
+ */
+ if (ip->i_mode != 0 && vp->v_type == VNON)
+ return (EINVAL);
if (vp->v_type == VFIFO)
vp->v_op = fifoops;
ASSERT_VOP_LOCKED(vp, "ufs_vinit");
More information about the svn-src-head
mailing list