summaryrefslogtreecommitdiffstats
path: root/sys
diff options
context:
space:
mode:
authorphk <phk@FreeBSD.org>1994-09-27 20:33:41 +0000
committerphk <phk@FreeBSD.org>1994-09-27 20:33:41 +0000
commitd0ad392702499b8224444ab43914aab79cee2ee9 (patch)
treebe46fa73b436f39cb6b10330724d83523da890f5 /sys
parent9aaca324b5b8c5827e7d32e8c8c14834bb5288a5 (diff)
downloadFreeBSD-src-d0ad392702499b8224444ab43914aab79cee2ee9.zip
FreeBSD-src-d0ad392702499b8224444ab43914aab79cee2ee9.tar.gz
Moved the "relookup" routine into vfs_lookup.c from ufs/ufs/ufs_vnops.c.
Several FS's use this, so it doesn't belong in ufs. (unionfs, msdosfs and ufs)
Diffstat (limited to 'sys')
-rw-r--r--sys/kern/vfs_lookup.c165
-rw-r--r--sys/sys/namei.h4
-rw-r--r--sys/ufs/ufs/ufs_vnops.c156
3 files changed, 164 insertions, 161 deletions
diff --git a/sys/kern/vfs_lookup.c b/sys/kern/vfs_lookup.c
index a6e9469..d1b19ce 100644
--- a/sys/kern/vfs_lookup.c
+++ b/sys/kern/vfs_lookup.c
@@ -36,7 +36,7 @@
* SUCH DAMAGE.
*
* @(#)vfs_lookup.c 8.4 (Berkeley) 2/16/94
- * $Id: vfs_lookup.c,v 1.3 1994/08/18 22:35:08 wollman Exp $
+ * $Id: vfs_lookup.c,v 1.4 1994/08/20 03:48:49 davidg Exp $
*/
#include <sys/param.h>
@@ -144,7 +144,8 @@ namei(ndp)
VREF(dp);
}
ndp->ni_startdir = dp;
- if (error = lookup(ndp)) {
+ error = lookup(ndp);
+ if (error) {
FREE(cnp->cn_pnbuf, M_NAMEI);
return (error);
}
@@ -177,7 +178,8 @@ namei(ndp)
auio.uio_segflg = UIO_SYSSPACE;
auio.uio_procp = (struct proc *)0;
auio.uio_resid = MAXPATHLEN;
- if (error = VOP_READLINK(ndp->ni_vp, &auio, cnp->cn_cred)) {
+ error = VOP_READLINK(ndp->ni_vp, &auio, cnp->cn_cred);
+ if (error) {
if (ndp->ni_pathlen > 1)
free(cp, M_NAMEI);
break;
@@ -374,7 +376,8 @@ dirloop:
*/
unionlookup:
ndp->ni_dvp = dp;
- if (error = VOP_LOOKUP(dp, &ndp->ni_vp, cnp)) {
+ error = VOP_LOOKUP(dp, &ndp->ni_vp, cnp);
+ if (error) {
#ifdef DIAGNOSTIC
if (ndp->ni_vp != NULL)
panic("leaf should be empty");
@@ -450,7 +453,8 @@ unionlookup:
sleep((caddr_t)mp, PVFS);
continue;
}
- if (error = VFS_ROOT(dp->v_mountedhere, &tdp))
+ error = VFS_ROOT(dp->v_mountedhere, &tdp);
+ if (error)
goto bad2;
vput(dp);
ndp->ni_vp = dp = tdp;
@@ -505,4 +509,155 @@ bad:
return (error);
}
+/*
+ * relookup - lookup a path name component
+ * Used by lookup to re-aquire things.
+ */
+int
+relookup(dvp, vpp, cnp)
+ struct vnode *dvp, **vpp;
+ struct componentname *cnp;
+{
+ register struct vnode *dp = 0; /* the directory we are searching */
+ int docache; /* == 0 do not cache last component */
+ int wantparent; /* 1 => wantparent or lockparent flag */
+ int rdonly; /* lookup read-only flag bit */
+ int error = 0;
+#ifdef NAMEI_DIAGNOSTIC
+ int newhash; /* DEBUG: check name hash */
+ char *cp; /* DEBUG: check name ptr/len */
+#endif
+
+ /*
+ * Setup: break out flag bits into variables.
+ */
+ wantparent = cnp->cn_flags & (LOCKPARENT|WANTPARENT);
+ docache = (cnp->cn_flags & NOCACHE) ^ NOCACHE;
+ if (cnp->cn_nameiop == DELETE ||
+ (wantparent && cnp->cn_nameiop != CREATE))
+ docache = 0;
+ rdonly = cnp->cn_flags & RDONLY;
+ cnp->cn_flags &= ~ISSYMLINK;
+ dp = dvp;
+ VOP_LOCK(dp);
+
+/* dirloop: */
+ /*
+ * Search a new directory.
+ *
+ * The cn_hash value is for use by vfs_cache.
+ * The last component of the filename is left accessible via
+ * cnp->cn_nameptr for callers that need the name. Callers needing
+ * the name set the SAVENAME flag. When done, they assume
+ * responsibility for freeing the pathname buffer.
+ */
+#ifdef NAMEI_DIAGNOSTIC
+ for (newhash = 0, cp = cnp->cn_nameptr; *cp != 0 && *cp != '/'; cp++)
+ newhash += (unsigned char)*cp;
+ if (newhash != cnp->cn_hash)
+ panic("relookup: bad hash");
+ if (cnp->cn_namelen != cp - cnp->cn_nameptr)
+ panic ("relookup: bad len");
+ if (*cp != 0)
+ panic("relookup: not last component");
+ printf("{%s}: ", cnp->cn_nameptr);
+#endif
+
+ /*
+ * Check for degenerate name (e.g. / or "")
+ * which is a way of talking about a directory,
+ * e.g. like "/." or ".".
+ */
+ if (cnp->cn_nameptr[0] == '\0') {
+ if (cnp->cn_nameiop != LOOKUP || wantparent) {
+ error = EISDIR;
+ goto bad;
+ }
+ if (dp->v_type != VDIR) {
+ error = ENOTDIR;
+ goto bad;
+ }
+ if (!(cnp->cn_flags & LOCKLEAF))
+ VOP_UNLOCK(dp);
+ *vpp = dp;
+ if (cnp->cn_flags & SAVESTART)
+ panic("lookup: SAVESTART");
+ return (0);
+ }
+
+ if (cnp->cn_flags & ISDOTDOT)
+ panic ("relookup: lookup on dot-dot");
+ /*
+ * We now have a segment name to search for, and a directory to search.
+ */
+ error = VOP_LOOKUP(dp, vpp, cnp);
+ if (error) {
+#ifdef DIAGNOSTIC
+ if (*vpp != NULL)
+ panic("leaf should be empty");
+#endif
+ if (error != EJUSTRETURN)
+ goto bad;
+ /*
+ * If creating and at end of pathname, then can consider
+ * allowing file to be created.
+ */
+ if (rdonly || (dvp->v_mount->mnt_flag & MNT_RDONLY)) {
+ error = EROFS;
+ goto bad;
+ }
+ /* ASSERT(dvp == ndp->ni_startdir) */
+ if (cnp->cn_flags & SAVESTART)
+ VREF(dvp);
+ /*
+ * We return with ni_vp NULL to indicate that the entry
+ * doesn't currently exist, leaving a pointer to the
+ * (possibly locked) directory inode in ndp->ni_dvp.
+ */
+ return (0);
+ }
+ dp = *vpp;
+
+#ifdef DIAGNOSTIC
+ /*
+ * Check for symbolic link
+ */
+ if (dp->v_type == VLNK && (cnp->cn_flags & FOLLOW))
+ panic ("relookup: symlink found.\n");
+#endif
+
+ /*
+ * Check for read-only file systems.
+ */
+ if (cnp->cn_nameiop == DELETE || cnp->cn_nameiop == RENAME) {
+ /*
+ * Disallow directory write attempts on read-only
+ * file systems.
+ */
+ if (rdonly || (dp->v_mount->mnt_flag & MNT_RDONLY) ||
+ (wantparent &&
+ (dvp->v_mount->mnt_flag & MNT_RDONLY))) {
+ error = EROFS;
+ goto bad2;
+ }
+ }
+ /* ASSERT(dvp == ndp->ni_startdir) */
+ if (cnp->cn_flags & SAVESTART)
+ VREF(dvp);
+
+ if (!wantparent)
+ vrele(dvp);
+ if ((cnp->cn_flags & LOCKLEAF) == 0)
+ VOP_UNLOCK(dp);
+ return (0);
+
+bad2:
+ if ((cnp->cn_flags & LOCKPARENT) && (cnp->cn_flags & ISLASTCN))
+ VOP_UNLOCK(dvp);
+ vrele(dvp);
+bad:
+ vput(dp);
+ *vpp = NULL;
+ return (error);
+}
diff --git a/sys/sys/namei.h b/sys/sys/namei.h
index bb8f0a9..1088ede 100644
--- a/sys/sys/namei.h
+++ b/sys/sys/namei.h
@@ -31,7 +31,7 @@
* SUCH DAMAGE.
*
* @(#)namei.h 8.2 (Berkeley) 1/4/94
- * $Id$
+ * $Id: namei.h,v 1.2 1994/08/02 07:53:18 davidg Exp $
*/
#ifndef _SYS_NAMEI_H_
@@ -171,6 +171,8 @@ struct namecache {
u_long nextvnodeid;
int namei __P((struct nameidata *ndp));
int lookup __P((struct nameidata *ndp));
+int relookup __P((struct vnode *dvp, struct vnode **vpp,
+ struct componentname *cnp));
#endif
/*
diff --git a/sys/ufs/ufs/ufs_vnops.c b/sys/ufs/ufs/ufs_vnops.c
index 41e1bba..f7eeacf 100644
--- a/sys/ufs/ufs/ufs_vnops.c
+++ b/sys/ufs/ufs/ufs_vnops.c
@@ -36,7 +36,7 @@
* SUCH DAMAGE.
*
* @(#)ufs_vnops.c 8.10 (Berkeley) 4/1/94
- * $Id: ufs_vnops.c,v 1.4 1994/08/08 17:31:01 davidg Exp $
+ * $Id: ufs_vnops.c,v 1.5 1994/09/22 19:38:41 wollman Exp $
*/
#include <sys/param.h>
@@ -709,160 +709,6 @@ out2:
}
-
-/*
- * relookup - lookup a path name component
- * Used by lookup to re-aquire things.
- */
-int
-relookup(dvp, vpp, cnp)
- struct vnode *dvp, **vpp;
- struct componentname *cnp;
-{
- register struct vnode *dp = 0; /* the directory we are searching */
- int docache; /* == 0 do not cache last component */
- int wantparent; /* 1 => wantparent or lockparent flag */
- int rdonly; /* lookup read-only flag bit */
- int error = 0;
-#ifdef NAMEI_DIAGNOSTIC
- int newhash; /* DEBUG: check name hash */
- char *cp; /* DEBUG: check name ptr/len */
-#endif
-
- /*
- * Setup: break out flag bits into variables.
- */
- wantparent = cnp->cn_flags & (LOCKPARENT|WANTPARENT);
- docache = (cnp->cn_flags & NOCACHE) ^ NOCACHE;
- if (cnp->cn_nameiop == DELETE ||
- (wantparent && cnp->cn_nameiop != CREATE))
- docache = 0;
- rdonly = cnp->cn_flags & RDONLY;
- cnp->cn_flags &= ~ISSYMLINK;
- dp = dvp;
- VOP_LOCK(dp);
-
-/* dirloop: */
- /*
- * Search a new directory.
- *
- * The cn_hash value is for use by vfs_cache.
- * The last component of the filename is left accessible via
- * cnp->cn_nameptr for callers that need the name. Callers needing
- * the name set the SAVENAME flag. When done, they assume
- * responsibility for freeing the pathname buffer.
- */
-#ifdef NAMEI_DIAGNOSTIC
- for (newhash = 0, cp = cnp->cn_nameptr; *cp != 0 && *cp != '/'; cp++)
- newhash += (unsigned char)*cp;
- if (newhash != cnp->cn_hash)
- panic("relookup: bad hash");
- if (cnp->cn_namelen != cp - cnp->cn_nameptr)
- panic ("relookup: bad len");
- if (*cp != 0)
- panic("relookup: not last component");
- printf("{%s}: ", cnp->cn_nameptr);
-#endif
-
- /*
- * Check for degenerate name (e.g. / or "")
- * which is a way of talking about a directory,
- * e.g. like "/." or ".".
- */
- if (cnp->cn_nameptr[0] == '\0') {
- if (cnp->cn_nameiop != LOOKUP || wantparent) {
- error = EISDIR;
- goto bad;
- }
- if (dp->v_type != VDIR) {
- error = ENOTDIR;
- goto bad;
- }
- if (!(cnp->cn_flags & LOCKLEAF))
- VOP_UNLOCK(dp);
- *vpp = dp;
- if (cnp->cn_flags & SAVESTART)
- panic("lookup: SAVESTART");
- return (0);
- }
-
- if (cnp->cn_flags & ISDOTDOT)
- panic ("relookup: lookup on dot-dot");
-
- /*
- * We now have a segment name to search for, and a directory to search.
- */
- if (error = VOP_LOOKUP(dp, vpp, cnp)) {
-#ifdef DIAGNOSTIC
- if (*vpp != NULL)
- panic("leaf should be empty");
-#endif
- if (error != EJUSTRETURN)
- goto bad;
- /*
- * If creating and at end of pathname, then can consider
- * allowing file to be created.
- */
- if (rdonly || (dvp->v_mount->mnt_flag & MNT_RDONLY)) {
- error = EROFS;
- goto bad;
- }
- /* ASSERT(dvp == ndp->ni_startdir) */
- if (cnp->cn_flags & SAVESTART)
- VREF(dvp);
- /*
- * We return with ni_vp NULL to indicate that the entry
- * doesn't currently exist, leaving a pointer to the
- * (possibly locked) directory inode in ndp->ni_dvp.
- */
- return (0);
- }
- dp = *vpp;
-
-#ifdef DIAGNOSTIC
- /*
- * Check for symbolic link
- */
- if (dp->v_type == VLNK && (cnp->cn_flags & FOLLOW))
- panic ("relookup: symlink found.\n");
-#endif
-
- /*
- * Check for read-only file systems.
- */
- if (cnp->cn_nameiop == DELETE || cnp->cn_nameiop == RENAME) {
- /*
- * Disallow directory write attempts on read-only
- * file systems.
- */
- if (rdonly || (dp->v_mount->mnt_flag & MNT_RDONLY) ||
- (wantparent &&
- (dvp->v_mount->mnt_flag & MNT_RDONLY))) {
- error = EROFS;
- goto bad2;
- }
- }
- /* ASSERT(dvp == ndp->ni_startdir) */
- if (cnp->cn_flags & SAVESTART)
- VREF(dvp);
-
- if (!wantparent)
- vrele(dvp);
- if ((cnp->cn_flags & LOCKLEAF) == 0)
- VOP_UNLOCK(dp);
- return (0);
-
-bad2:
- if ((cnp->cn_flags & LOCKPARENT) && (cnp->cn_flags & ISLASTCN))
- VOP_UNLOCK(dvp);
- vrele(dvp);
-bad:
- vput(dp);
- *vpp = NULL;
- return (error);
-}
-
-
/*
* Rename system call.
* rename("foo", "bar");
OpenPOWER on IntegriCloud