From d48b626da392b24385d401954444c9dbdd04ecc2 Mon Sep 17 00:00:00 2001 From: Mike Pritchard Date: Sun, 10 Mar 1996 00:20:28 +0000 Subject: [PATCH] Do not allow the caller to specify the same path for the special device file and the mount point. This prevents the "unexpected recursive lock" panic from happening. This is a temporary fix. A kernel fix would be much much more ugly than this, and still wouldn't be the "right" way to fix it. After some of Terry's file system rework is installed, it will be possible to properly fix this problem in a clean manner. Until then, this change should prevent use from getting a problem report on this every month or so (and I just noticed that someone in one of the freebsd news groups was complaining about this problem, too). --- sbin/mount/mount.c | 19 +++++++++++++++++++ sbin/mount_ifs/mount.c | 19 +++++++++++++++++++ 2 files changed, 38 insertions(+) diff --git a/sbin/mount/mount.c b/sbin/mount/mount.c index 1be00ec7d26c..075ffcf943d6 100644 --- a/sbin/mount/mount.c +++ b/sbin/mount/mount.c @@ -262,6 +262,7 @@ mountfs(vfstype, spec, name, flags, options, mntopts) pid_t pid; int argc, i, status; char *optbuf, execname[MAXPATHLEN + 1], mntpath[MAXPATHLEN]; + char specpath[MAXPATHLEN]; if (realpath(name, mntpath) != NULL && stat(mntpath, &sb) == 0) { if (!S_ISDIR(sb.st_mode)) { @@ -273,6 +274,24 @@ mountfs(vfstype, spec, name, flags, options, mntopts) return (1); } + /* + * The following check is a kludge to prevent the caller from + * accidently using the file as the special device file and + * the mount point. This will cause a panic due to a recursive + * vnode lock. After some of the planned reworking of the + * file system code is done, the kernel can be fixed properly + * and this stupid check can be removed. + */ + if (realpath(spec, specpath) == NULL) { + warn("%s", specpath); + return (1); + } + if (strcmp(mntpath, specpath) == 0) { + warnx("%s: Special device file and mount point may not be the same", + specpath); + return (1); + } + if (mntopts == NULL) mntopts = ""; diff --git a/sbin/mount_ifs/mount.c b/sbin/mount_ifs/mount.c index 1be00ec7d26c..075ffcf943d6 100644 --- a/sbin/mount_ifs/mount.c +++ b/sbin/mount_ifs/mount.c @@ -262,6 +262,7 @@ mountfs(vfstype, spec, name, flags, options, mntopts) pid_t pid; int argc, i, status; char *optbuf, execname[MAXPATHLEN + 1], mntpath[MAXPATHLEN]; + char specpath[MAXPATHLEN]; if (realpath(name, mntpath) != NULL && stat(mntpath, &sb) == 0) { if (!S_ISDIR(sb.st_mode)) { @@ -273,6 +274,24 @@ mountfs(vfstype, spec, name, flags, options, mntopts) return (1); } + /* + * The following check is a kludge to prevent the caller from + * accidently using the file as the special device file and + * the mount point. This will cause a panic due to a recursive + * vnode lock. After some of the planned reworking of the + * file system code is done, the kernel can be fixed properly + * and this stupid check can be removed. + */ + if (realpath(spec, specpath) == NULL) { + warn("%s", specpath); + return (1); + } + if (strcmp(mntpath, specpath) == 0) { + warnx("%s: Special device file and mount point may not be the same", + specpath); + return (1); + } + if (mntopts == NULL) mntopts = "";