version 1.48.2.11, 2005/11/10 14:12:31 |
version 1.49, 2003/08/07 16:34:27 |
|
|
* documentation and/or other materials provided with the distribution. |
* documentation and/or other materials provided with the distribution. |
* 3. All advertising materials mentioning features or use of this software |
* 3. All advertising materials mentioning features or use of this software |
* must display the following acknowledgement: |
* must display the following acknowledgement: |
* This product includes software developed by Manuel Bouyer. |
* This product includes software developed by the University of |
* 4. The name of the author may not be used to endorse or promote products |
* California, Berkeley and its contributors. |
* derived from this software without specific prior written permission. |
* 4. Neither the name of the University nor the names of its contributors |
|
* may be used to endorse or promote products derived from this software |
|
* without specific prior written permission. |
* |
* |
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR |
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND |
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES |
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE |
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. |
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE |
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, |
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE |
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT |
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL |
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, |
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS |
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) |
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT |
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF |
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY |
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF |
|
* SUCH DAMAGE. |
* |
* |
* @(#)ufs_vnops.c 8.14 (Berkeley) 10/26/94 |
* @(#)ufs_vnops.c 8.14 (Berkeley) 10/26/94 |
* Modified for ext2fs by Manuel Bouyer. |
* Modified for ext2fs by Manuel Bouyer. |
Line 102 __KERNEL_RCSID(0, "$NetBSD$"); |
|
Line 105 __KERNEL_RCSID(0, "$NetBSD$"); |
|
|
|
extern int prtactive; |
extern int prtactive; |
|
|
static int ext2fs_chmod(struct vnode *, int, struct ucred *, struct proc *); |
static int ext2fs_chmod |
static int ext2fs_chown(struct vnode *, uid_t, gid_t, struct ucred *, |
__P((struct vnode *, int, struct ucred *, struct proc *)); |
struct proc *); |
static int ext2fs_chown |
|
__P((struct vnode *, uid_t, gid_t, struct ucred *, struct proc *)); |
|
|
union _qcvt { |
union _qcvt { |
int64_t qcvt; |
int64_t qcvt; |
int32_t val[2]; |
int32_t val[2]; |
}; |
}; |
|
|
#define SETHIGH(q, h) { \ |
#define SETHIGH(q, h) { \ |
union _qcvt tmp; \ |
union _qcvt tmp; \ |
tmp.qcvt = (q); \ |
tmp.qcvt = (q); \ |
|
|
* Create a regular file |
* Create a regular file |
*/ |
*/ |
int |
int |
ext2fs_create(void *v) |
ext2fs_create(v) |
|
void *v; |
{ |
{ |
struct vop_create_args /* { |
struct vop_create_args /* { |
struct vnode *a_dvp; |
struct vnode *a_dvp; |
Line 153 ext2fs_create(void *v) |
|
Line 157 ext2fs_create(void *v) |
|
*/ |
*/ |
/* ARGSUSED */ |
/* ARGSUSED */ |
int |
int |
ext2fs_mknod(void *v) |
ext2fs_mknod(v) |
|
void *v; |
{ |
{ |
struct vop_mknod_args /* { |
struct vop_mknod_args /* { |
struct vnode *a_dvp; |
struct vnode *a_dvp; |
Line 165 ext2fs_mknod(void *v) |
|
Line 170 ext2fs_mknod(void *v) |
|
struct vnode **vpp = ap->a_vpp; |
struct vnode **vpp = ap->a_vpp; |
struct inode *ip; |
struct inode *ip; |
int error; |
int error; |
struct mount *mp; |
struct mount *mp; |
ino_t ino; |
ino_t ino; |
|
|
if ((error = ext2fs_makeinode(MAKEIMODE(vap->va_type, vap->va_mode), |
if ((error = ext2fs_makeinode(MAKEIMODE(vap->va_type, vap->va_mode), |
Line 206 ext2fs_mknod(void *v) |
|
Line 211 ext2fs_mknod(void *v) |
|
*/ |
*/ |
/* ARGSUSED */ |
/* ARGSUSED */ |
int |
int |
ext2fs_open(void *v) |
ext2fs_open(v) |
|
void *v; |
{ |
{ |
struct vop_open_args /* { |
struct vop_open_args /* { |
struct vnode *a_vp; |
struct vnode *a_vp; |
int a_mode; |
int a_mode; |
struct ucred *a_cred; |
struct ucred *a_cred; |
struct lwp *a_l; |
struct proc *a_p; |
} */ *ap = v; |
} */ *ap = v; |
|
|
/* |
/* |
Line 225 ext2fs_open(void *v) |
|
Line 231 ext2fs_open(void *v) |
|
} |
} |
|
|
int |
int |
ext2fs_access(void *v) |
ext2fs_access(v) |
|
void *v; |
{ |
{ |
struct vop_access_args /* { |
struct vop_access_args /* { |
struct vnode *a_vp; |
struct vnode *a_vp; |
int a_mode; |
int a_mode; |
struct ucred *a_cred; |
struct ucred *a_cred; |
struct lwp *a_l; |
struct proc *a_p; |
} */ *ap = v; |
} */ *ap = v; |
struct vnode *vp = ap->a_vp; |
struct vnode *vp = ap->a_vp; |
struct inode *ip = VTOI(vp); |
struct inode *ip = VTOI(vp); |
Line 265 ext2fs_access(void *v) |
|
Line 272 ext2fs_access(void *v) |
|
|
|
/* ARGSUSED */ |
/* ARGSUSED */ |
int |
int |
ext2fs_getattr(void *v) |
ext2fs_getattr(v) |
|
void *v; |
{ |
{ |
struct vop_getattr_args /* { |
struct vop_getattr_args /* { |
struct vnode *a_vp; |
struct vnode *a_vp; |
struct vattr *a_vap; |
struct vattr *a_vap; |
struct ucred *a_cred; |
struct ucred *a_cred; |
struct lwp *a_l; |
struct proc *a_p; |
} */ *ap = v; |
} */ *ap = v; |
struct vnode *vp = ap->a_vp; |
struct vnode *vp = ap->a_vp; |
struct inode *ip = VTOI(vp); |
struct inode *ip = VTOI(vp); |
struct vattr *vap = ap->a_vap; |
struct vattr *vap = ap->a_vap; |
|
struct timespec ts; |
|
|
EXT2FS_ITIMES(ip, NULL, NULL, NULL); |
TIMEVAL_TO_TIMESPEC(&time, &ts); |
|
EXT2FS_ITIMES(ip, &ts, &ts, &ts); |
/* |
/* |
* Copy from inode table |
* Copy from inode table |
*/ |
*/ |
Line 320 ext2fs_getattr(void *v) |
|
Line 330 ext2fs_getattr(void *v) |
|
* Set attribute vnode op. called from several syscalls |
* Set attribute vnode op. called from several syscalls |
*/ |
*/ |
int |
int |
ext2fs_setattr(void *v) |
ext2fs_setattr(v) |
|
void *v; |
{ |
{ |
struct vop_setattr_args /* { |
struct vop_setattr_args /* { |
struct vnode *a_vp; |
struct vnode *a_vp; |
struct vattr *a_vap; |
struct vattr *a_vap; |
struct ucred *a_cred; |
struct ucred *a_cred; |
struct lwp *a_l; |
struct proc *a_p; |
} */ *ap = v; |
} */ *ap = v; |
struct vattr *vap = ap->a_vap; |
struct vattr *vap = ap->a_vap; |
struct vnode *vp = ap->a_vp; |
struct vnode *vp = ap->a_vp; |
struct inode *ip = VTOI(vp); |
struct inode *ip = VTOI(vp); |
struct ucred *cred = ap->a_cred; |
struct ucred *cred = ap->a_cred; |
struct lwp *l = ap->a_l; |
struct proc *p = ap->a_p; |
int error; |
int error; |
|
|
/* |
/* |
Line 348 ext2fs_setattr(void *v) |
|
Line 359 ext2fs_setattr(void *v) |
|
if (vp->v_mount->mnt_flag & MNT_RDONLY) |
if (vp->v_mount->mnt_flag & MNT_RDONLY) |
return (EROFS); |
return (EROFS); |
if (cred->cr_uid != ip->i_e2fs_uid && |
if (cred->cr_uid != ip->i_e2fs_uid && |
(error = suser(cred, &l->l_proc->p_acflag))) |
(error = suser(cred, &p->p_acflag))) |
return (error); |
return (error); |
#ifdef EXT2FS_SYSTEM_FLAGS |
#ifdef EXT2FS_SYSTEM_FLAGS |
if (cred->cr_uid == 0) { |
if (cred->cr_uid == 0) { |
Line 379 ext2fs_setattr(void *v) |
|
Line 390 ext2fs_setattr(void *v) |
|
if (vap->va_uid != (uid_t)VNOVAL || vap->va_gid != (gid_t)VNOVAL) { |
if (vap->va_uid != (uid_t)VNOVAL || vap->va_gid != (gid_t)VNOVAL) { |
if (vp->v_mount->mnt_flag & MNT_RDONLY) |
if (vp->v_mount->mnt_flag & MNT_RDONLY) |
return (EROFS); |
return (EROFS); |
error = ext2fs_chown(vp, vap->va_uid, vap->va_gid, cred, l->l_proc); |
error = ext2fs_chown(vp, vap->va_uid, vap->va_gid, cred, p); |
if (error) |
if (error) |
return (error); |
return (error); |
} |
} |
Line 399 ext2fs_setattr(void *v) |
|
Line 410 ext2fs_setattr(void *v) |
|
default: |
default: |
break; |
break; |
} |
} |
error = ext2fs_truncate(vp, vap->va_size, 0, cred, l->l_proc); |
error = VOP_TRUNCATE(vp, vap->va_size, 0, cred, p); |
if (error) |
if (error) |
return (error); |
return (error); |
} |
} |
Line 408 ext2fs_setattr(void *v) |
|
Line 419 ext2fs_setattr(void *v) |
|
if (vp->v_mount->mnt_flag & MNT_RDONLY) |
if (vp->v_mount->mnt_flag & MNT_RDONLY) |
return (EROFS); |
return (EROFS); |
if (cred->cr_uid != ip->i_e2fs_uid && |
if (cred->cr_uid != ip->i_e2fs_uid && |
(error = suser(cred, &l->l_proc->p_acflag)) && |
(error = suser(cred, &p->p_acflag)) && |
((vap->va_vaflags & VA_UTIMES_NULL) == 0 || |
((vap->va_vaflags & VA_UTIMES_NULL) == 0 || |
(error = VOP_ACCESS(vp, VWRITE, cred, l)))) |
(error = VOP_ACCESS(vp, VWRITE, cred, p)))) |
return (error); |
return (error); |
if (vap->va_atime.tv_sec != VNOVAL) |
if (vap->va_atime.tv_sec != VNOVAL) |
if (!(vp->v_mount->mnt_flag & MNT_NOATIME)) |
if (!(vp->v_mount->mnt_flag & MNT_NOATIME)) |
ip->i_flag |= IN_ACCESS; |
ip->i_flag |= IN_ACCESS; |
if (vap->va_mtime.tv_sec != VNOVAL) |
if (vap->va_mtime.tv_sec != VNOVAL) |
ip->i_flag |= IN_CHANGE | IN_UPDATE; |
ip->i_flag |= IN_CHANGE | IN_UPDATE; |
error = ext2fs_update(vp, &vap->va_atime, &vap->va_mtime, |
error = VOP_UPDATE(vp, &vap->va_atime, &vap->va_mtime, |
UPDATE_WAIT); |
UPDATE_WAIT); |
if (error) |
if (error) |
return (error); |
return (error); |
Line 426 ext2fs_setattr(void *v) |
|
Line 437 ext2fs_setattr(void *v) |
|
if (vap->va_mode != (mode_t)VNOVAL) { |
if (vap->va_mode != (mode_t)VNOVAL) { |
if (vp->v_mount->mnt_flag & MNT_RDONLY) |
if (vp->v_mount->mnt_flag & MNT_RDONLY) |
return (EROFS); |
return (EROFS); |
error = ext2fs_chmod(vp, (int)vap->va_mode, cred, l->l_proc); |
error = ext2fs_chmod(vp, (int)vap->va_mode, cred, p); |
} |
} |
VN_KNOTE(vp, NOTE_ATTRIB); |
VN_KNOTE(vp, NOTE_ATTRIB); |
return (error); |
return (error); |
Line 437 ext2fs_setattr(void *v) |
|
Line 448 ext2fs_setattr(void *v) |
|
* Inode must be locked before calling. |
* Inode must be locked before calling. |
*/ |
*/ |
static int |
static int |
ext2fs_chmod(struct vnode *vp, int mode, struct ucred *cred, struct proc *p) |
ext2fs_chmod(vp, mode, cred, p) |
|
struct vnode *vp; |
|
int mode; |
|
struct ucred *cred; |
|
struct proc *p; |
{ |
{ |
struct inode *ip = VTOI(vp); |
struct inode *ip = VTOI(vp); |
int error; |
int error; |
Line 462 ext2fs_chmod(struct vnode *vp, int mode, |
|
Line 477 ext2fs_chmod(struct vnode *vp, int mode, |
|
* inode must be locked prior to call. |
* inode must be locked prior to call. |
*/ |
*/ |
static int |
static int |
ext2fs_chown(struct vnode *vp, uid_t uid, gid_t gid, struct ucred *cred, |
ext2fs_chown(vp, uid, gid, cred, p) |
struct proc *p) |
struct vnode *vp; |
|
uid_t uid; |
|
gid_t gid; |
|
struct ucred *cred; |
|
struct proc *p; |
{ |
{ |
struct inode *ip = VTOI(vp); |
struct inode *ip = VTOI(vp); |
uid_t ouid; |
uid_t ouid; |
Line 480 ext2fs_chown(struct vnode *vp, uid_t uid |
|
Line 499 ext2fs_chown(struct vnode *vp, uid_t uid |
|
* the caller must be superuser or the call fails. |
* the caller must be superuser or the call fails. |
*/ |
*/ |
if ((cred->cr_uid != ip->i_e2fs_uid || uid != ip->i_e2fs_uid || |
if ((cred->cr_uid != ip->i_e2fs_uid || uid != ip->i_e2fs_uid || |
(gid != ip->i_e2fs_gid && |
(gid != ip->i_e2fs_gid && !groupmember((gid_t)gid, cred))) && |
!(cred->cr_gid == gid || groupmember((gid_t)gid, cred)))) && |
|
(error = suser(cred, &p->p_acflag))) |
(error = suser(cred, &p->p_acflag))) |
return (error); |
return (error); |
ogid = ip->i_e2fs_gid; |
ogid = ip->i_e2fs_gid; |
Line 499 ext2fs_chown(struct vnode *vp, uid_t uid |
|
Line 517 ext2fs_chown(struct vnode *vp, uid_t uid |
|
} |
} |
|
|
int |
int |
ext2fs_remove(void *v) |
ext2fs_remove(v) |
|
void *v; |
{ |
{ |
struct vop_remove_args /* { |
struct vop_remove_args /* { |
struct vnode *a_dvp; |
struct vnode *a_dvp; |
Line 538 ext2fs_remove(void *v) |
|
Line 557 ext2fs_remove(void *v) |
|
* link vnode call |
* link vnode call |
*/ |
*/ |
int |
int |
ext2fs_link(void *v) |
ext2fs_link(v) |
|
void *v; |
{ |
{ |
struct vop_link_args /* { |
struct vop_link_args /* { |
struct vnode *a_dvp; |
struct vnode *a_dvp; |
Line 582 ext2fs_link(void *v) |
|
Line 602 ext2fs_link(void *v) |
|
} |
} |
ip->i_e2fs_nlink++; |
ip->i_e2fs_nlink++; |
ip->i_flag |= IN_CHANGE; |
ip->i_flag |= IN_CHANGE; |
error = ext2fs_update(vp, NULL, NULL, UPDATE_WAIT); |
error = VOP_UPDATE(vp, NULL, NULL, UPDATE_WAIT); |
if (!error) |
if (!error) |
error = ext2fs_direnter(ip, dvp, cnp); |
error = ext2fs_direnter(ip, dvp, cnp); |
if (error) { |
if (error) { |
|
|
* directory. |
* directory. |
*/ |
*/ |
int |
int |
ext2fs_rename(void *v) |
ext2fs_rename(v) |
|
void *v; |
{ |
{ |
struct vop_rename_args /* { |
struct vop_rename_args /* { |
struct vnode *a_fdvp; |
struct vnode *a_fdvp; |
|
|
goto abortit; |
goto abortit; |
} |
} |
if ((ip->i_e2fs_mode & IFMT) == IFDIR) { |
if ((ip->i_e2fs_mode & IFMT) == IFDIR) { |
error = VOP_ACCESS(fvp, VWRITE, tcnp->cn_cred, tcnp->cn_lwp); |
error = VOP_ACCESS(fvp, VWRITE, tcnp->cn_cred, tcnp->cn_proc); |
if (!error && tvp) |
if (!error && tvp) |
error = VOP_ACCESS(tvp, VWRITE, tcnp->cn_cred, |
error = VOP_ACCESS(tvp, VWRITE, tcnp->cn_cred, |
tcnp->cn_lwp); |
tcnp->cn_proc); |
if (error) { |
if (error) { |
VOP_UNLOCK(fvp, 0); |
VOP_UNLOCK(fvp, 0); |
error = EACCES; |
error = EACCES; |
|
|
*/ |
*/ |
ip->i_e2fs_nlink++; |
ip->i_e2fs_nlink++; |
ip->i_flag |= IN_CHANGE; |
ip->i_flag |= IN_CHANGE; |
if ((error = ext2fs_update(fvp, NULL, NULL, UPDATE_WAIT)) != 0) { |
if ((error = VOP_UPDATE(fvp, NULL, NULL, UPDATE_WAIT)) != 0) { |
VOP_UNLOCK(fvp, 0); |
VOP_UNLOCK(fvp, 0); |
goto bad; |
goto bad; |
} |
} |
|
|
* directory hierarchy above the target, as this would |
* directory hierarchy above the target, as this would |
* orphan everything below the source directory. Also |
* orphan everything below the source directory. Also |
* the user must have write permission in the source so |
* the user must have write permission in the source so |
* as to be able to change "..". We must repeat the call |
* as to be able to change "..". We must repeat the call |
* to namei, as the parent directory is unlocked by the |
* to namei, as the parent directory is unlocked by the |
* call to checkpath(). |
* call to checkpath(). |
*/ |
*/ |
error = VOP_ACCESS(fvp, VWRITE, tcnp->cn_cred, tcnp->cn_lwp); |
error = VOP_ACCESS(fvp, VWRITE, tcnp->cn_cred, tcnp->cn_proc); |
VOP_UNLOCK(fvp, 0); |
VOP_UNLOCK(fvp, 0); |
if (oldparent != dp->i_number) |
if (oldparent != dp->i_number) |
newparent = dp->i_number; |
newparent = dp->i_number; |
|
|
} |
} |
/* |
/* |
* 2) If target doesn't exist, link the target |
* 2) If target doesn't exist, link the target |
* to the source and unlink the source. |
* to the source and unlink the source. |
* Otherwise, rewrite the target directory |
* Otherwise, rewrite the target directory |
* entry to reference the source inode and |
* entry to reference the source inode and |
* expunge the original entry's existence. |
* expunge the original entry's existence. |
|
|
} |
} |
dp->i_e2fs_nlink++; |
dp->i_e2fs_nlink++; |
dp->i_flag |= IN_CHANGE; |
dp->i_flag |= IN_CHANGE; |
if ((error = ext2fs_update(tdvp, NULL, NULL, |
if ((error = VOP_UPDATE(tdvp, NULL, NULL, UPDATE_WAIT)) |
UPDATE_WAIT)) != 0) |
!= 0) |
goto bad; |
goto bad; |
} |
} |
error = ext2fs_direnter(ip, tdvp, tcnp); |
error = ext2fs_direnter(ip, tdvp, tcnp); |
|
|
if (doingdirectory && newparent) { |
if (doingdirectory && newparent) { |
dp->i_e2fs_nlink--; |
dp->i_e2fs_nlink--; |
dp->i_flag |= IN_CHANGE; |
dp->i_flag |= IN_CHANGE; |
(void)ext2fs_update(tdvp, NULL, NULL, |
(void)VOP_UPDATE(tdvp, NULL, NULL, UPDATE_WAIT); |
UPDATE_WAIT); |
|
} |
} |
goto bad; |
goto bad; |
} |
} |
|
|
if (doingdirectory) { |
if (doingdirectory) { |
if (--xp->i_e2fs_nlink != 0) |
if (--xp->i_e2fs_nlink != 0) |
panic("rename: linked directory"); |
panic("rename: linked directory"); |
error = ext2fs_truncate(tvp, (off_t)0, IO_SYNC, |
error = VOP_TRUNCATE(tvp, (off_t)0, IO_SYNC, |
tcnp->cn_cred, tcnp->cn_lwp->l_proc); |
tcnp->cn_cred, tcnp->cn_proc); |
} |
} |
xp->i_flag |= IN_CHANGE; |
xp->i_flag |= IN_CHANGE; |
VN_KNOTE(tvp, NOTE_DELETE); |
VN_KNOTE(tvp, NOTE_DELETE); |
|
|
dp->i_flag |= IN_CHANGE; |
dp->i_flag |= IN_CHANGE; |
error = vn_rdwr(UIO_READ, fvp, (caddr_t)&dirbuf, |
error = vn_rdwr(UIO_READ, fvp, (caddr_t)&dirbuf, |
sizeof (struct ext2fs_dirtemplate), (off_t)0, |
sizeof (struct ext2fs_dirtemplate), (off_t)0, |
UIO_SYSSPACE, IO_NODELOCKED, |
UIO_SYSSPACE, IO_NODELOCKED, |
tcnp->cn_cred, (size_t *)0, NULL); |
tcnp->cn_cred, (size_t *)0, (struct proc *)0); |
if (error == 0) { |
if (error == 0) { |
namlen = dirbuf.dotdot_namlen; |
namlen = dirbuf.dotdot_namlen; |
if (namlen != 2 || |
if (namlen != 2 || |
|
|
(off_t)0, UIO_SYSSPACE, |
(off_t)0, UIO_SYSSPACE, |
IO_NODELOCKED|IO_SYNC, |
IO_NODELOCKED|IO_SYNC, |
tcnp->cn_cred, (size_t *)0, |
tcnp->cn_cred, (size_t *)0, |
NULL); |
(struct proc *)0); |
cache_purge(fdvp); |
cache_purge(fdvp); |
} |
} |
} |
} |
|
|
* Mkdir system call |
* Mkdir system call |
*/ |
*/ |
int |
int |
ext2fs_mkdir(void *v) |
ext2fs_mkdir(v) |
|
void *v; |
{ |
{ |
struct vop_mkdir_args /* { |
struct vop_mkdir_args /* { |
struct vnode *a_dvp; |
struct vnode *a_dvp; |
Line 1025 ext2fs_mkdir(void *v) |
|
Line 1046 ext2fs_mkdir(void *v) |
|
struct componentname *a_cnp; |
struct componentname *a_cnp; |
struct vattr *a_vap; |
struct vattr *a_vap; |
} */ *ap = v; |
} */ *ap = v; |
struct vnode *dvp = ap->a_dvp; |
struct vnode *dvp = ap->a_dvp; |
struct vattr *vap = ap->a_vap; |
struct vattr *vap = ap->a_vap; |
struct componentname *cnp = ap->a_cnp; |
struct componentname *cnp = ap->a_cnp; |
struct inode *ip, *dp = VTOI(dvp); |
struct inode *ip, *dp; |
struct vnode *tvp; |
struct vnode *tvp; |
struct ext2fs_dirtemplate dirtemplate; |
struct ext2fs_dirtemplate dirtemplate; |
int error, dmode; |
int error, dmode; |
|
|
#ifdef DIAGNOSTIC |
#ifdef DIAGNOSTIC |
if ((cnp->cn_flags & HASBUF) == 0) |
if ((cnp->cn_flags & HASBUF) == 0) |
panic("ext2fs_mkdir: no name"); |
panic("ext2fs_mkdir: no name"); |
#endif |
#endif |
|
dp = VTOI(dvp); |
if ((nlink_t)dp->i_e2fs_nlink >= LINK_MAX) { |
if ((nlink_t)dp->i_e2fs_nlink >= LINK_MAX) { |
error = EMLINK; |
error = EMLINK; |
goto out; |
goto out; |
Line 1048 ext2fs_mkdir(void *v) |
|
Line 1070 ext2fs_mkdir(void *v) |
|
* but not have it entered in the parent directory. The entry is |
* but not have it entered in the parent directory. The entry is |
* made later after writing "." and ".." entries. |
* made later after writing "." and ".." entries. |
*/ |
*/ |
if ((error = ext2fs_valloc(dvp, dmode, cnp->cn_cred, &tvp)) != 0) |
if ((error = VOP_VALLOC(dvp, dmode, cnp->cn_cred, &tvp)) != 0) |
goto out; |
goto out; |
ip = VTOI(tvp); |
ip = VTOI(tvp); |
ip->i_e2fs_uid = cnp->cn_cred->cr_uid; |
ip->i_e2fs_uid = cnp->cn_cred->cr_uid; |
Line 1057 ext2fs_mkdir(void *v) |
|
Line 1079 ext2fs_mkdir(void *v) |
|
ip->i_e2fs_mode = dmode; |
ip->i_e2fs_mode = dmode; |
tvp->v_type = VDIR; /* Rest init'd in getnewvnode(). */ |
tvp->v_type = VDIR; /* Rest init'd in getnewvnode(). */ |
ip->i_e2fs_nlink = 2; |
ip->i_e2fs_nlink = 2; |
|
error = VOP_UPDATE(tvp, NULL, NULL, UPDATE_WAIT); |
|
|
/* |
/* |
* Bump link count in parent directory |
* Bump link count in parent directory |
Line 1066 ext2fs_mkdir(void *v) |
|
Line 1089 ext2fs_mkdir(void *v) |
|
*/ |
*/ |
dp->i_e2fs_nlink++; |
dp->i_e2fs_nlink++; |
dp->i_flag |= IN_CHANGE; |
dp->i_flag |= IN_CHANGE; |
if ((error = ext2fs_update(dvp, NULL, NULL, UPDATE_DIROP)) != 0) |
if ((error = VOP_UPDATE(dvp, NULL, NULL, UPDATE_WAIT)) != 0) |
goto bad; |
goto bad; |
|
|
/* Initialize directory with "." and ".." from static template. */ |
/* Initialize directory with "." and ".." from static template. */ |
Line 1089 ext2fs_mkdir(void *v) |
|
Line 1112 ext2fs_mkdir(void *v) |
|
dirtemplate.dotdot_name[0] = dirtemplate.dotdot_name[1] = '.'; |
dirtemplate.dotdot_name[0] = dirtemplate.dotdot_name[1] = '.'; |
error = vn_rdwr(UIO_WRITE, tvp, (caddr_t)&dirtemplate, |
error = vn_rdwr(UIO_WRITE, tvp, (caddr_t)&dirtemplate, |
sizeof (dirtemplate), (off_t)0, UIO_SYSSPACE, |
sizeof (dirtemplate), (off_t)0, UIO_SYSSPACE, |
IO_NODELOCKED|IO_SYNC, cnp->cn_cred, (size_t *)0, NULL); |
IO_NODELOCKED|IO_SYNC, cnp->cn_cred, (size_t *)0, (struct proc *)0); |
if (error) { |
if (error) { |
dp->i_e2fs_nlink--; |
dp->i_e2fs_nlink--; |
dp->i_flag |= IN_CHANGE; |
dp->i_flag |= IN_CHANGE; |
goto bad; |
goto bad; |
} |
} |
if (VTOI(dvp)->i_e2fs->e2fs_bsize > dvp->v_mount->mnt_stat.f_bsize) |
if (VTOI(dvp)->i_e2fs->e2fs_bsize > |
|
VFSTOUFS(dvp->v_mount)->um_mountp->mnt_stat.f_bsize) |
panic("ext2fs_mkdir: blksize"); /* XXX should grow with balloc() */ |
panic("ext2fs_mkdir: blksize"); /* XXX should grow with balloc() */ |
else { |
else { |
error = ext2fs_setsize(ip, VTOI(dvp)->i_e2fs->e2fs_bsize); |
ip->i_e2fs_size = VTOI(dvp)->i_e2fs->e2fs_bsize; |
if (error) { |
|
dp->i_e2fs_nlink--; |
|
dp->i_flag |= IN_CHANGE; |
|
goto bad; |
|
} |
|
ip->i_flag |= IN_CHANGE; |
ip->i_flag |= IN_CHANGE; |
uvm_vnp_setsize(tvp, ext2fs_size(ip)); |
|
} |
} |
|
|
/* Directory set up, now install it's entry in the parent directory. */ |
/* Directory set up, now install it's entry in the parent directory. */ |
Line 1116 ext2fs_mkdir(void *v) |
|
Line 1134 ext2fs_mkdir(void *v) |
|
} |
} |
bad: |
bad: |
/* |
/* |
* No need to do an explicit ext2fs_truncate here, vrele will do this |
* No need to do an explicit VOP_TRUNCATE here, vrele will do this |
* for us because we set the link count to 0. |
* for us because we set the link count to 0. |
*/ |
*/ |
if (error) { |
if (error) { |
|
|
* Rmdir system call. |
* Rmdir system call. |
*/ |
*/ |
int |
int |
ext2fs_rmdir(void *v) |
ext2fs_rmdir(v) |
|
void *v; |
{ |
{ |
struct vop_rmdir_args /* { |
struct vop_rmdir_args /* { |
struct vnode *a_dvp; |
struct vnode *a_dvp; |
Line 1204 ext2fs_rmdir(void *v) |
|
Line 1223 ext2fs_rmdir(void *v) |
|
* worry about them later. |
* worry about them later. |
*/ |
*/ |
ip->i_e2fs_nlink -= 2; |
ip->i_e2fs_nlink -= 2; |
error = ext2fs_truncate(vp, (off_t)0, IO_SYNC, cnp->cn_cred, |
error = VOP_TRUNCATE(vp, (off_t)0, IO_SYNC, cnp->cn_cred, |
cnp->cn_lwp->l_proc); |
cnp->cn_proc); |
cache_purge(ITOV(ip)); |
cache_purge(ITOV(ip)); |
out: |
out: |
VN_KNOTE(vp, NOTE_DELETE); |
VN_KNOTE(vp, NOTE_DELETE); |
|
|
* symlink -- make a symbolic link |
* symlink -- make a symbolic link |
*/ |
*/ |
int |
int |
ext2fs_symlink(void *v) |
ext2fs_symlink(v) |
|
void *v; |
{ |
{ |
struct vop_symlink_args /* { |
struct vop_symlink_args /* { |
struct vnode *a_dvp; |
struct vnode *a_dvp; |
Line 1228 ext2fs_symlink(void *v) |
|
Line 1248 ext2fs_symlink(void *v) |
|
struct vattr *a_vap; |
struct vattr *a_vap; |
char *a_target; |
char *a_target; |
} */ *ap = v; |
} */ *ap = v; |
struct vnode *vp, **vpp; |
struct vnode *vp, **vpp = ap->a_vpp; |
struct inode *ip; |
struct inode *ip; |
int len, error; |
int len, error; |
|
|
vpp = ap->a_vpp; |
|
error = ext2fs_makeinode(IFLNK | ap->a_vap->va_mode, ap->a_dvp, |
error = ext2fs_makeinode(IFLNK | ap->a_vap->va_mode, ap->a_dvp, |
vpp, ap->a_cnp); |
vpp, ap->a_cnp); |
if (error) |
if (error) |
Line 1240 ext2fs_symlink(void *v) |
|
Line 1259 ext2fs_symlink(void *v) |
|
VN_KNOTE(ap->a_dvp, NOTE_WRITE); |
VN_KNOTE(ap->a_dvp, NOTE_WRITE); |
vp = *vpp; |
vp = *vpp; |
len = strlen(ap->a_target); |
len = strlen(ap->a_target); |
ip = VTOI(vp); |
if (len < vp->v_mount->mnt_maxsymlinklen) { |
if (len < ip->i_ump->um_maxsymlinklen) { |
ip = VTOI(vp); |
memcpy((char *)ip->i_din.e2fs_din->e2di_shortlink, ap->a_target, len); |
memcpy((char *)ip->i_din.e2fs_din->e2di_shortlink, ap->a_target, len); |
error = ext2fs_setsize(ip, len); |
ip->i_e2fs_size = len; |
if (error) |
|
goto bad; |
|
ip->i_flag |= IN_CHANGE | IN_UPDATE; |
ip->i_flag |= IN_CHANGE | IN_UPDATE; |
uvm_vnp_setsize(vp, len); |
|
} else |
} else |
error = vn_rdwr(UIO_WRITE, vp, ap->a_target, len, (off_t)0, |
error = vn_rdwr(UIO_WRITE, vp, ap->a_target, len, (off_t)0, |
UIO_SYSSPACE, IO_NODELOCKED, ap->a_cnp->cn_cred, |
UIO_SYSSPACE, IO_NODELOCKED, ap->a_cnp->cn_cred, |
(size_t *)0, NULL); |
(size_t *)0, (struct proc *)0); |
bad: |
|
if (error) |
if (error) |
vput(vp); |
vput(vp); |
return (error); |
return (error); |
|
|
* Return target name of a symbolic link |
* Return target name of a symbolic link |
*/ |
*/ |
int |
int |
ext2fs_readlink(void *v) |
ext2fs_readlink(v) |
|
void *v; |
{ |
{ |
struct vop_readlink_args /* { |
struct vop_readlink_args /* { |
struct vnode *a_vp; |
struct vnode *a_vp; |
struct uio *a_uio; |
struct uio *a_uio; |
struct ucred *a_cred; |
struct ucred *a_cred; |
} */ *ap = v; |
} */ *ap = v; |
struct vnode *vp = ap->a_vp; |
struct vnode *vp = ap->a_vp; |
struct inode *ip = VTOI(vp); |
struct inode *ip = VTOI(vp); |
struct ufsmount *ump = ip->i_ump; |
int isize; |
int isize; |
|
|
isize = ip->i_e2fs_size; |
isize = ext2fs_size(ip); |
if (isize < vp->v_mount->mnt_maxsymlinklen || |
if (isize < ump->um_maxsymlinklen || |
(vp->v_mount->mnt_maxsymlinklen == 0 && ip->i_e2fs_nblock == 0)) { |
(ump->um_maxsymlinklen == 0 && ip->i_e2fs_nblock == 0)) { |
|
uiomove((char *)ip->i_din.e2fs_din->e2di_shortlink, isize, ap->a_uio); |
uiomove((char *)ip->i_din.e2fs_din->e2di_shortlink, isize, ap->a_uio); |
return (0); |
return (0); |
} |
} |
Line 1287 ext2fs_readlink(void *v) |
|
Line 1302 ext2fs_readlink(void *v) |
|
* Advisory record locking support |
* Advisory record locking support |
*/ |
*/ |
int |
int |
ext2fs_advlock(void *v) |
ext2fs_advlock(v) |
|
void *v; |
{ |
{ |
struct vop_advlock_args /* { |
struct vop_advlock_args /* { |
struct vnode *a_vp; |
struct vnode *a_vp; |
Line 1298 ext2fs_advlock(void *v) |
|
Line 1314 ext2fs_advlock(void *v) |
|
} */ *ap = v; |
} */ *ap = v; |
struct inode *ip = VTOI(ap->a_vp); |
struct inode *ip = VTOI(ap->a_vp); |
|
|
return lf_advlock(ap, &ip->i_lockf, ext2fs_size(ip)); |
return lf_advlock(ap, &ip->i_lockf, ip->i_e2fs_size); |
} |
|
|
|
int |
|
ext2fs_fsync(void *v) |
|
{ |
|
struct vop_fsync_args /* { |
|
struct vnode *a_vp; |
|
struct ucred *a_cred; |
|
int a_flags; |
|
off_t offlo; |
|
off_t offhi; |
|
struct proc *a_p; |
|
} */ *ap = v; |
|
struct vnode *vp = ap->a_vp; |
|
int wait; |
|
int error; |
|
|
|
wait = (ap->a_flags & FSYNC_WAIT) != 0; |
|
vflushbuf(vp, wait); |
|
if ((ap->a_flags & FSYNC_DATAONLY) != 0) |
|
error = 0; |
|
else |
|
error = ext2fs_update(vp, NULL, NULL, wait ? UPDATE_WAIT : 0); |
|
|
|
if (error == 0 && ap->a_flags & FSYNC_CACHE) { |
|
int l = 0; |
|
error = VOP_IOCTL(VTOI(vp)->i_devvp, DIOCCACHESYNC, &l, FWRITE, |
|
ap->a_l->l_proc->p_ucred, ap->a_l); |
|
} |
|
|
|
return error; |
|
} |
} |
|
|
/* |
/* |
Line 1337 ext2fs_fsync(void *v) |
|
Line 1322 ext2fs_fsync(void *v) |
|
* vnodes. |
* vnodes. |
*/ |
*/ |
int |
int |
ext2fs_vinit(struct mount *mntp, int (**specops)(void *), |
ext2fs_vinit(mntp, specops, fifoops, vpp) |
int (**fifoops)(void *), struct vnode **vpp) |
struct mount *mntp; |
|
int (**specops) __P((void *)); |
|
int (**fifoops) __P((void *)); |
|
struct vnode **vpp; |
{ |
{ |
struct inode *ip; |
struct inode *ip; |
struct vnode *vp, *nvp; |
struct vnode *vp, *nvp; |
Line 1358 ext2fs_vinit(struct mount *mntp, int (** |
|
Line 1346 ext2fs_vinit(struct mount *mntp, int (** |
|
vp->v_data = NULL; |
vp->v_data = NULL; |
VOP_UNLOCK(vp, 0); |
VOP_UNLOCK(vp, 0); |
vp->v_op = spec_vnodeop_p; |
vp->v_op = spec_vnodeop_p; |
vp->v_flag &= ~VLOCKSWORK; |
|
vrele(vp); |
vrele(vp); |
vgone(vp); |
vgone(vp); |
lockmgr(&nvp->v_lock, LK_EXCLUSIVE, &nvp->v_interlock); |
lockmgr(&nvp->v_lock, LK_EXCLUSIVE, &nvp->v_interlock); |
Line 1395 ext2fs_vinit(struct mount *mntp, int (** |
|
Line 1382 ext2fs_vinit(struct mount *mntp, int (** |
|
* Allocate a new inode. |
* Allocate a new inode. |
*/ |
*/ |
int |
int |
ext2fs_makeinode(int mode, struct vnode *dvp, struct vnode **vpp, |
ext2fs_makeinode(mode, dvp, vpp, cnp) |
struct componentname *cnp) |
int mode; |
|
struct vnode *dvp; |
|
struct vnode **vpp; |
|
struct componentname *cnp; |
{ |
{ |
struct inode *ip, *pdir; |
struct inode *ip, *pdir; |
struct vnode *tvp; |
struct vnode *tvp; |
Line 1411 ext2fs_makeinode(int mode, struct vnode |
|
Line 1401 ext2fs_makeinode(int mode, struct vnode |
|
if ((mode & IFMT) == 0) |
if ((mode & IFMT) == 0) |
mode |= IFREG; |
mode |= IFREG; |
|
|
if ((error = ext2fs_valloc(dvp, mode, cnp->cn_cred, &tvp)) != 0) { |
if ((error = VOP_VALLOC(dvp, mode, cnp->cn_cred, &tvp)) != 0) { |
PNBUF_PUT(cnp->cn_pnbuf); |
PNBUF_PUT(cnp->cn_pnbuf); |
vput(dvp); |
vput(dvp); |
return (error); |
return (error); |
Line 1431 ext2fs_makeinode(int mode, struct vnode |
|
Line 1421 ext2fs_makeinode(int mode, struct vnode |
|
/* |
/* |
* Make sure inode goes to disk before directory entry. |
* Make sure inode goes to disk before directory entry. |
*/ |
*/ |
if ((error = ext2fs_update(tvp, NULL, NULL, UPDATE_WAIT)) != 0) |
if ((error = VOP_UPDATE(tvp, NULL, NULL, UPDATE_WAIT)) != 0) |
goto bad; |
goto bad; |
error = ext2fs_direnter(ip, dvp, cnp); |
error = ext2fs_direnter(ip, dvp, cnp); |
if (error != 0) |
if (error != 0) |
|
|
* Write error occurred trying to update the inode |
* Write error occurred trying to update the inode |
* or the directory so must deallocate the inode. |
* or the directory so must deallocate the inode. |
*/ |
*/ |
tvp->v_type = VNON; /* Stop explosion if VBLK */ |
PNBUF_PUT(cnp->cn_pnbuf); |
|
vput(dvp); |
ip->i_e2fs_nlink = 0; |
ip->i_e2fs_nlink = 0; |
ip->i_flag |= IN_CHANGE; |
ip->i_flag |= IN_CHANGE; |
vput(tvp); |
vput(tvp); |
PNBUF_PUT(cnp->cn_pnbuf); |
|
vput(dvp); |
|
return (error); |
return (error); |
} |
} |
|
|
|
|
* Reclaim an inode so that it can be used for other purposes. |
* Reclaim an inode so that it can be used for other purposes. |
*/ |
*/ |
int |
int |
ext2fs_reclaim(void *v) |
ext2fs_reclaim(v) |
|
void *v; |
{ |
{ |
struct vop_reclaim_args /* { |
struct vop_reclaim_args /* { |
struct vnode *a_vp; |
struct vnode *a_vp; |
} */ *ap = v; |
} */ *ap = v; |
struct vnode *vp = ap->a_vp; |
struct vnode *vp = ap->a_vp; |
struct inode *ip = VTOI(vp); |
struct inode *ip; |
int error; |
|
|
if (prtactive && vp->v_usecount != 0) |
|
vprint("ext2fs_reclaim: pushing active", vp); |
|
/* |
|
* Remove the inode from its hash chain. |
|
*/ |
|
ip = VTOI(vp); |
|
ufs_ihashrem(ip); |
|
/* |
|
* Purge old data structures associated with the inode. |
|
*/ |
|
cache_purge(vp); |
|
if (ip->i_devvp) { |
|
vrele(ip->i_devvp); |
|
ip->i_devvp = 0; |
|
} |
|
|
if ((error = ufs_reclaim(vp, ap->a_l)) != 0) |
|
return (error); |
|
if (ip->i_din.e2fs_din != NULL) |
if (ip->i_din.e2fs_din != NULL) |
pool_put(&ext2fs_dinode_pool, ip->i_din.e2fs_din); |
pool_put(&ext2fs_dinode_pool, ip->i_din.e2fs_din); |
|
|
pool_put(&ext2fs_inode_pool, vp->v_data); |
pool_put(&ext2fs_inode_pool, vp->v_data); |
vp->v_data = NULL; |
vp->v_data = NULL; |
return (0); |
return (0); |
} |
} |
|
|
/* Global vfs data structures for ext2fs. */ |
/* Global vfs data structures for ext2fs. */ |
int (**ext2fs_vnodeop_p)(void *); |
int (**ext2fs_vnodeop_p) __P((void *)); |
const struct vnodeopv_entry_desc ext2fs_vnodeop_entries[] = { |
const struct vnodeopv_entry_desc ext2fs_vnodeop_entries[] = { |
{ &vop_default_desc, vn_default_error }, |
{ &vop_default_desc, vn_default_error }, |
{ &vop_lookup_desc, ext2fs_lookup }, /* lookup */ |
{ &vop_lookup_desc, ext2fs_lookup }, /* lookup */ |
Line 1520 const struct vnodeopv_entry_desc ext2fs_ |
|
Line 1524 const struct vnodeopv_entry_desc ext2fs_ |
|
{ &vop_islocked_desc, ufs_islocked }, /* islocked */ |
{ &vop_islocked_desc, ufs_islocked }, /* islocked */ |
{ &vop_pathconf_desc, ufs_pathconf }, /* pathconf */ |
{ &vop_pathconf_desc, ufs_pathconf }, /* pathconf */ |
{ &vop_advlock_desc, ext2fs_advlock }, /* advlock */ |
{ &vop_advlock_desc, ext2fs_advlock }, /* advlock */ |
|
{ &vop_blkatoff_desc, ext2fs_blkatoff }, /* blkatoff */ |
|
{ &vop_valloc_desc, ext2fs_valloc }, /* valloc */ |
|
{ &vop_vfree_desc, ext2fs_vfree }, /* vfree */ |
|
{ &vop_truncate_desc, ext2fs_truncate }, /* truncate */ |
|
{ &vop_update_desc, ext2fs_update }, /* update */ |
{ &vop_bwrite_desc, vn_bwrite }, /* bwrite */ |
{ &vop_bwrite_desc, vn_bwrite }, /* bwrite */ |
{ &vop_getpages_desc, genfs_getpages }, /* getpages */ |
{ &vop_getpages_desc, genfs_getpages }, /* getpages */ |
{ &vop_putpages_desc, genfs_putpages }, /* putpages */ |
{ &vop_putpages_desc, genfs_putpages }, /* putpages */ |
Line 1528 const struct vnodeopv_entry_desc ext2fs_ |
|
Line 1537 const struct vnodeopv_entry_desc ext2fs_ |
|
const struct vnodeopv_desc ext2fs_vnodeop_opv_desc = |
const struct vnodeopv_desc ext2fs_vnodeop_opv_desc = |
{ &ext2fs_vnodeop_p, ext2fs_vnodeop_entries }; |
{ &ext2fs_vnodeop_p, ext2fs_vnodeop_entries }; |
|
|
int (**ext2fs_specop_p)(void *); |
int (**ext2fs_specop_p) __P((void *)); |
const struct vnodeopv_entry_desc ext2fs_specop_entries[] = { |
const struct vnodeopv_entry_desc ext2fs_specop_entries[] = { |
{ &vop_default_desc, vn_default_error }, |
{ &vop_default_desc, vn_default_error }, |
{ &vop_lookup_desc, spec_lookup }, /* lookup */ |
{ &vop_lookup_desc, spec_lookup }, /* lookup */ |
Line 1569 const struct vnodeopv_entry_desc ext2fs_ |
|
Line 1578 const struct vnodeopv_entry_desc ext2fs_ |
|
{ &vop_islocked_desc, ufs_islocked }, /* islocked */ |
{ &vop_islocked_desc, ufs_islocked }, /* islocked */ |
{ &vop_pathconf_desc, spec_pathconf }, /* pathconf */ |
{ &vop_pathconf_desc, spec_pathconf }, /* pathconf */ |
{ &vop_advlock_desc, spec_advlock }, /* advlock */ |
{ &vop_advlock_desc, spec_advlock }, /* advlock */ |
|
{ &vop_blkatoff_desc, spec_blkatoff }, /* blkatoff */ |
|
{ &vop_valloc_desc, spec_valloc }, /* valloc */ |
|
{ &vop_vfree_desc, ext2fs_vfree }, /* vfree */ |
|
{ &vop_truncate_desc, spec_truncate }, /* truncate */ |
|
{ &vop_update_desc, ext2fs_update }, /* update */ |
{ &vop_bwrite_desc, vn_bwrite }, /* bwrite */ |
{ &vop_bwrite_desc, vn_bwrite }, /* bwrite */ |
{ &vop_getpages_desc, spec_getpages }, /* getpages */ |
{ &vop_getpages_desc, spec_getpages }, /* getpages */ |
{ &vop_putpages_desc, spec_putpages }, /* putpages */ |
{ &vop_putpages_desc, spec_putpages }, /* putpages */ |
Line 1577 const struct vnodeopv_entry_desc ext2fs_ |
|
Line 1591 const struct vnodeopv_entry_desc ext2fs_ |
|
const struct vnodeopv_desc ext2fs_specop_opv_desc = |
const struct vnodeopv_desc ext2fs_specop_opv_desc = |
{ &ext2fs_specop_p, ext2fs_specop_entries }; |
{ &ext2fs_specop_p, ext2fs_specop_entries }; |
|
|
int (**ext2fs_fifoop_p)(void *); |
int (**ext2fs_fifoop_p) __P((void *)); |
const struct vnodeopv_entry_desc ext2fs_fifoop_entries[] = { |
const struct vnodeopv_entry_desc ext2fs_fifoop_entries[] = { |
{ &vop_default_desc, vn_default_error }, |
{ &vop_default_desc, vn_default_error }, |
{ &vop_lookup_desc, fifo_lookup }, /* lookup */ |
{ &vop_lookup_desc, fifo_lookup }, /* lookup */ |
Line 1618 const struct vnodeopv_entry_desc ext2fs_ |
|
Line 1632 const struct vnodeopv_entry_desc ext2fs_ |
|
{ &vop_islocked_desc, ufs_islocked }, /* islocked */ |
{ &vop_islocked_desc, ufs_islocked }, /* islocked */ |
{ &vop_pathconf_desc, fifo_pathconf }, /* pathconf */ |
{ &vop_pathconf_desc, fifo_pathconf }, /* pathconf */ |
{ &vop_advlock_desc, fifo_advlock }, /* advlock */ |
{ &vop_advlock_desc, fifo_advlock }, /* advlock */ |
|
{ &vop_blkatoff_desc, fifo_blkatoff }, /* blkatoff */ |
|
{ &vop_valloc_desc, fifo_valloc }, /* valloc */ |
|
{ &vop_vfree_desc, ext2fs_vfree }, /* vfree */ |
|
{ &vop_truncate_desc, fifo_truncate }, /* truncate */ |
|
{ &vop_update_desc, ext2fs_update }, /* update */ |
{ &vop_bwrite_desc, vn_bwrite }, /* bwrite */ |
{ &vop_bwrite_desc, vn_bwrite }, /* bwrite */ |
{ &vop_putpages_desc, fifo_putpages }, /* putpages */ |
{ &vop_putpages_desc, fifo_putpages }, /* putpages */ |
{ NULL, NULL } |
{ NULL, NULL } |