diff options
author | Pedro Martelletto <pedro@cvs.openbsd.org> | 2005-12-11 20:46:30 +0000 |
---|---|---|
committer | Pedro Martelletto <pedro@cvs.openbsd.org> | 2005-12-11 20:46:30 +0000 |
commit | 20a582ff861e899b606c6ac1ede65faf0bb165bb (patch) | |
tree | e61231df2619a5cff0e49d22e9592a6240a5b118 /sys/ufs/ext2fs | |
parent | d8f1edf86776895b23ddcb38a2c139a1a8777401 (diff) |
inode/dinode separation for ext2fs
Diffstat (limited to 'sys/ufs/ext2fs')
-rw-r--r-- | sys/ufs/ext2fs/ext2fs_alloc.c | 4 | ||||
-rw-r--r-- | sys/ufs/ext2fs/ext2fs_extern.h | 5 | ||||
-rw-r--r-- | sys/ufs/ext2fs/ext2fs_inode.c | 6 | ||||
-rw-r--r-- | sys/ufs/ext2fs/ext2fs_subr.c | 92 | ||||
-rw-r--r-- | sys/ufs/ext2fs/ext2fs_vfsops.c | 22 | ||||
-rw-r--r-- | sys/ufs/ext2fs/ext2fs_vnops.c | 32 |
6 files changed, 124 insertions, 37 deletions
diff --git a/sys/ufs/ext2fs/ext2fs_alloc.c b/sys/ufs/ext2fs/ext2fs_alloc.c index fa2fcb611a7..7992ff86ca2 100644 --- a/sys/ufs/ext2fs/ext2fs_alloc.c +++ b/sys/ufs/ext2fs/ext2fs_alloc.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ext2fs_alloc.c,v 1.19 2005/07/03 20:14:01 drahn Exp $ */ +/* $OpenBSD: ext2fs_alloc.c,v 1.20 2005/12/11 20:46:28 pedro Exp $ */ /* $NetBSD: ext2fs_alloc.c,v 1.10 2001/07/05 08:38:27 toshii Exp $ */ /* @@ -170,7 +170,7 @@ ext2fs_inode_alloc(struct inode *pip, mode_t mode, struct ucred *cred, panic("ext2fs_valloc: dup alloc"); } - bzero(&(ip->i_e2din), sizeof(struct ext2fs_dinode)); + bzero(ip->i_e2din, sizeof(struct ext2fs_dinode)); /* * Set up a new generation number for this inode. diff --git a/sys/ufs/ext2fs/ext2fs_extern.h b/sys/ufs/ext2fs/ext2fs_extern.h index 411d4b3e6b9..42b8cdfbb81 100644 --- a/sys/ufs/ext2fs/ext2fs_extern.h +++ b/sys/ufs/ext2fs/ext2fs_extern.h @@ -1,4 +1,4 @@ -/* $OpenBSD: ext2fs_extern.h,v 1.22 2005/07/28 23:11:25 pedro Exp $ */ +/* $OpenBSD: ext2fs_extern.h,v 1.23 2005/12/11 20:46:28 pedro Exp $ */ /* $NetBSD: ext2fs_extern.h,v 1.1 1997/06/11 09:33:55 bouyer Exp $ */ /*- @@ -52,6 +52,7 @@ struct mbuf; struct componentname; /* extern struct pool ext2fs_inode_pool; */ /* memory pool for inodes */ +extern struct pool ext2fs_dinode_pool; /* memory pool for dinodes */ __BEGIN_DECLS @@ -96,6 +97,8 @@ int ext2fs_checkpath(struct inode *, struct inode *, struct ucred *); /* ext2fs_subr.c */ int ext2fs_bufatoff(struct inode *, off_t, char **, struct buf **); +int ext2fs_vinit(struct mount *, int (**)(void *), int (**)(void *), + struct vnode **); void ext2fs_fragacct(struct m_ext2fs *, int, int32_t[], int); #ifdef DIAGNOSTIC void ext2fs_checkoverlap(struct buf *, struct inode *); diff --git a/sys/ufs/ext2fs/ext2fs_inode.c b/sys/ufs/ext2fs/ext2fs_inode.c index c969759606b..859a2179c9b 100644 --- a/sys/ufs/ext2fs/ext2fs_inode.c +++ b/sys/ufs/ext2fs/ext2fs_inode.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ext2fs_inode.c,v 1.29 2005/10/06 17:43:14 pedro Exp $ */ +/* $OpenBSD: ext2fs_inode.c,v 1.30 2005/12/11 20:46:28 pedro Exp $ */ /* $NetBSD: ext2fs_inode.c,v 1.24 2001/06/19 12:59:18 wiz Exp $ */ /* @@ -200,7 +200,7 @@ ext2fs_update(struct inode *ip, struct timespec *atime, struct timespec *mtime, ip->i_e2fs_uid_high = ip->i_e2fs_uid >> 16; ip->i_e2fs_gid_high = ip->i_e2fs_gid >> 16; - e2fs_isave(&ip->i_e2din, (struct ext2fs_dinode *)cp); + e2fs_isave(ip->i_e2din, (struct ext2fs_dinode *)cp); if (waitfor) return (bwrite(bp)); else { @@ -247,7 +247,7 @@ ext2fs_truncate(struct inode *oip, off_t length, int flags, struct ucred *cred) if (length != 0) panic("ext2fs_truncate: partial truncate of symlink"); #endif - bzero((char *)&oip->i_e2din.e2di_shortlink, + bzero((char *)&oip->i_e2din->e2di_shortlink, (u_int)ext2fs_size(oip)); (void)ext2fs_setsize(oip, 0); oip->i_flag |= IN_CHANGE | IN_UPDATE; diff --git a/sys/ufs/ext2fs/ext2fs_subr.c b/sys/ufs/ext2fs/ext2fs_subr.c index 555b963e3f5..ec7f4f90c5d 100644 --- a/sys/ufs/ext2fs/ext2fs_subr.c +++ b/sys/ufs/ext2fs/ext2fs_subr.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ext2fs_subr.c,v 1.12 2005/07/03 20:14:01 drahn Exp $ */ +/* $OpenBSD: ext2fs_subr.c,v 1.13 2005/12/11 20:46:28 pedro Exp $ */ /* $NetBSD: ext2fs_subr.c,v 1.1 1997/06/11 09:34:03 bouyer Exp $ */ /* @@ -47,6 +47,28 @@ #include <ufs/ext2fs/ext2fs.h> #include <ufs/ext2fs/ext2fs_extern.h> +#include <miscfs/specfs/specdev.h> +#include <miscfs/fifofs/fifo.h> + +union _qcvt { + int64_t qcvt; + int32_t val[2]; +}; + +#define SETHIGH(q, h) { \ + union _qcvt tmp; \ + tmp.qcvt = (q); \ + tmp.val[_QUAD_HIGHWORD] = (h); \ + (q) = tmp.qcvt; \ +} + +#define SETLOW(q, l) { \ + union _qcvt tmp; \ + tmp.qcvt = (q); \ + tmp.val[_QUAD_LOWWORD] = (l); \ + (q) = tmp.qcvt; \ +} + #ifdef _KERNEL /* @@ -112,3 +134,71 @@ ext2fs_checkoverlap(bp, ip) } } #endif /* DIAGNOSTIC */ + +/* + * Initialize the vnode associated with a new inode, handle aliased vnodes. + */ +int +ext2fs_vinit(struct mount *mp, int (**specops)(void *), + int (**fifoops)(void *), struct vnode **vpp) +{ + struct inode *ip; + struct vnode *vp, *nvp; + struct timeval tv; + + vp = *vpp; + ip = VTOI(vp); + vp->v_type = IFTOVT(ip->i_e2fs_mode); + + switch(vp->v_type) { + case VCHR: + case VBLK: + vp->v_op = specops; + + nvp = checkalias(vp, ip->i_e2din->e2di_rdev, mp); + if (nvp != NULL) { + /* + * Discard unneeded vnode, but save its inode. Note + * that the lock is carried over in the inode to the + * replacement vnode. + */ + nvp->v_data = vp->v_data; + vp->v_data = NULL; + vp->v_op = spec_vnodeop_p; +#ifdef VFSDEBUG + vp->v_flag &= ~VLOCKSWORK; +#endif + vrele(vp); + vgone(vp); + /* Reinitialize aliased vnode. */ + vp = nvp; + ip->i_vnode = vp; + } + + break; + + case VFIFO: +#ifdef FIFO + vp->v_op = fifoops; + break; +#else + return (EOPNOTSUPP); +#endif /* FIFO */ + + default: + + break; + } + + if (ip->i_number == EXT2_ROOTINO) + vp->v_flag |= VROOT; + + /* Initialize modrev times */ + getmicrouptime(&tv); + SETHIGH(ip->i_modrev, tv.tv_sec); + SETLOW(ip->i_modrev, tv.tv_usec * 4294); + + *vpp = vp; + + return (0); +} diff --git a/sys/ufs/ext2fs/ext2fs_vfsops.c b/sys/ufs/ext2fs/ext2fs_vfsops.c index e279efcda54..52a8e53b363 100644 --- a/sys/ufs/ext2fs/ext2fs_vfsops.c +++ b/sys/ufs/ext2fs/ext2fs_vfsops.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ext2fs_vfsops.c,v 1.41 2005/11/30 10:35:08 pedro Exp $ */ +/* $OpenBSD: ext2fs_vfsops.c,v 1.42 2005/12/11 20:46:28 pedro Exp $ */ /* $NetBSD: ext2fs_vfsops.c,v 1.1 1997/06/11 09:34:07 bouyer Exp $ */ /* @@ -101,6 +101,7 @@ const struct vfsops ext2fs_vfsops = { }; /* struct pool ext2fs_inode_pool; */ +struct pool ext2fs_dinode_pool; extern u_long ext2gennumber; @@ -108,6 +109,9 @@ int ext2fs_init(vfsp) struct vfsconf *vfsp; { + pool_init(&ext2fs_dinode_pool, sizeof(struct ext2fs_dinode), 0, 0, 0, + "ext2dinopl", &pool_allocator_nointr); + return (ufs_init(vfsp)); } @@ -363,7 +367,7 @@ ext2fs_reload_vnode(struct vnode *vp, void *args) { } cp = (caddr_t)bp->b_data + (ino_to_fsbo(era->fs, ip->i_number) * EXT2_DINODE_SIZE); - e2fs_iload((struct ext2fs_dinode *)cp, &ip->i_e2din); + e2fs_iload((struct ext2fs_dinode *)cp, ip->i_e2din); brelse(bp); vput(vp); return (0); @@ -831,6 +835,7 @@ ext2fs_vget(mp, ino, vpp) { register struct m_ext2fs *fs; register struct inode *ip; + struct ext2fs_dinode *dp; struct ufsmount *ump; struct buf *bp; struct vnode *vp; @@ -893,8 +898,12 @@ ext2fs_vget(mp, ino, vpp) *vpp = NULL; return (error); } - bcopy(((struct ext2fs_dinode*)bp->b_data + ino_to_fsbo(fs, ino)), - &ip->i_e2din, sizeof(struct ext2fs_dinode)); + + dp = (struct ext2fs_dinode *) bp->b_data + ino_to_fsbo(fs, ino); + ip->i_e2din = pool_get(&ext2fs_dinode_pool, PR_WAITOK); + e2fs_iload(dp, ip->i_e2din); + brelse(bp); + ip->i_effnlink = ip->i_e2fs_nlink; /* @@ -908,8 +917,6 @@ ext2fs_vget(mp, ino, vpp) ip->i_e2fs_uid = ip->i_e2fs_uid_low | (ip->i_e2fs_uid_high << 16); ip->i_e2fs_gid = ip->i_e2fs_gid_low | (ip->i_e2fs_gid_high << 16); - brelse(bp); - /* If the inode was deleted, reset all fields */ if (ip->i_e2fs_dtime != 0) { ip->i_e2fs_mode = ip->i_e2fs_nblock = 0; @@ -920,12 +927,13 @@ ext2fs_vget(mp, ino, vpp) * Initialize the vnode from the inode, check for aliases. * Note that the underlying vnode may have changed. */ - error = ufs_vinit(mp, ext2fs_specop_p, EXT2FS_FIFOOPS, &vp); + error = ext2fs_vinit(mp, ext2fs_specop_p, EXT2FS_FIFOOPS, &vp); if (error) { vput(vp); *vpp = NULL; return (error); } + /* * Finish inode initialization now that aliasing has been resolved. */ diff --git a/sys/ufs/ext2fs/ext2fs_vnops.c b/sys/ufs/ext2fs/ext2fs_vnops.c index 818c56126b1..c4faaf63dec 100644 --- a/sys/ufs/ext2fs/ext2fs_vnops.c +++ b/sys/ufs/ext2fs/ext2fs_vnops.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ext2fs_vnops.c,v 1.41 2005/08/14 12:41:44 pedro Exp $ */ +/* $OpenBSD: ext2fs_vnops.c,v 1.42 2005/12/11 20:46:28 pedro Exp $ */ /* $NetBSD: ext2fs_vnops.c,v 1.1 1997/06/11 09:34:09 bouyer Exp $ */ /* @@ -70,27 +70,9 @@ #include <ufs/ext2fs/ext2fs_extern.h> #include <ufs/ext2fs/ext2fs_dir.h> - static int ext2fs_chmod(struct vnode *, mode_t, struct ucred *, struct proc *); static int ext2fs_chown(struct vnode *, uid_t, gid_t, struct ucred *, struct proc *); -union _qcvt { - int64_t qcvt; - int32_t val[2]; -}; -#define SETHIGH(q, h) { \ - union _qcvt tmp; \ - tmp.qcvt = (q); \ - tmp.val[_QUAD_HIGHWORD] = (h); \ - (q) = tmp.qcvt; \ -} -#define SETLOW(q, l) { \ - union _qcvt tmp; \ - tmp.qcvt = (q); \ - tmp.val[_QUAD_LOWWORD] = (l); \ - (q) = tmp.qcvt; \ -} - /* * Create a regular file */ @@ -139,7 +121,7 @@ ext2fs_mknod(v) * Want to be able to use this to make badblock * inodes, so don't truncate the dev number. */ - ip->i_e2din.e2di_rdev = h2fs32(vap->va_rdev); + ip->i_e2din->e2di_rdev = h2fs32(vap->va_rdev); } /* * Remove inode so that it will be reloaded by VFS_VGET and @@ -228,7 +210,7 @@ ext2fs_getattr(v) vap->va_nlink = ip->i_e2fs_nlink; vap->va_uid = ip->i_e2fs_uid; vap->va_gid = ip->i_e2fs_gid; - vap->va_rdev = (dev_t)fs2h32(ip->i_e2din.e2di_rdev); + vap->va_rdev = (dev_t)fs2h32(ip->i_e2din->e2di_rdev); vap->va_size = ext2fs_size(ip); vap->va_atime.tv_sec = ip->i_e2fs_atime; vap->va_atime.tv_nsec = 0; @@ -1184,7 +1166,7 @@ ext2fs_symlink(v) len = strlen(ap->a_target); if (len < vp->v_mount->mnt_maxsymlinklen) { ip = VTOI(vp); - bcopy(ap->a_target, (char *)ip->i_e2din.e2di_shortlink, len); + bcopy(ap->a_target, (char *)ip->i_e2din->e2di_shortlink, len); error = ext2fs_setsize(ip, len); if (error) goto bad; @@ -1217,7 +1199,7 @@ ext2fs_readlink(v) isize = ext2fs_size(ip); if (isize < vp->v_mount->mnt_maxsymlinklen || (vp->v_mount->mnt_maxsymlinklen == 0 && ip->i_e2fs_nblock == 0)) { - uiomove((char *)ip->i_e2din.e2di_shortlink, isize, ap->a_uio); + uiomove((char *)ip->i_e2din->e2di_shortlink, isize, ap->a_uio); return (0); } return (VOP_READ(vp, ap->a_uio, 0, ap->a_cred)); @@ -1363,7 +1345,11 @@ ext2fs_reclaim(v) if (ip->i_devvp) vrele(ip->i_devvp); + if (ip->i_e2din != NULL) + pool_put(&ext2fs_dinode_pool, ip->i_e2din); + FREE(vp->v_data, M_EXT2FSNODE); + vp->v_data = NULL; return (0); |