|
Ian Kent |
62ad96 |
autofs-5.0.3 - fix multi mount race.
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
From: Ian Kent <raven@themaw.net>
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
When using multi-mounts it is possible for a path walk to walk into
|
|
Ian Kent |
62ad96 |
a mount tree before it is completely setup which leads to autofs
|
|
Ian Kent |
62ad96 |
incorrectly failing to perform mounts.
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
For example, for the multi-mount
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
mm1
|
|
Ian Kent |
62ad96 |
/om1 <server1>:/<path1>
|
|
Ian Kent |
62ad96 |
/om2 <server2>:/<path2>
|
|
Ian Kent |
62ad96 |
/om2/om21 <server3>:/<path3>
|
|
Ian Kent |
62ad96 |
/om2/om22 <server3>:/<path4>
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
when a path walk hits mm1/om2 <serverr2>:/<path2> is mounted on top of
|
|
Ian Kent |
62ad96 |
mm1/om2. If a path walk comes along before the multi-mount offsets for
|
|
Ian Kent |
62ad96 |
mm1/om2 are setup it doesn't see that mm1/om2 is pending. This happens
|
|
Ian Kent |
62ad96 |
because the lookup gets to mm1/om2, which is within the mm1 file system,
|
|
Ian Kent |
62ad96 |
and is covered by a mount trigger mounted at mm1/om2, and the the trigger
|
|
Ian Kent |
62ad96 |
itself is covered by the <server3>:/<path3> mount. So the walk follows
|
|
Ian Kent |
62ad96 |
the stack up to the mount at <server3>:/<path3>, never seeing that the
|
|
Ian Kent |
62ad96 |
trigger mm1/om2 is currently pending.
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
In the example above mm1/om2 could also be a submount.
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
To resolve this the mount tree needs to be created under a temporary
|
|
Ian Kent |
62ad96 |
directory and moved into place once setup in one operation.
|
|
Ian Kent |
62ad96 |
---
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
CHANGELOG | 1
|
|
Ian Kent |
62ad96 |
daemon/automount.c | 32 ++-
|
|
Ian Kent |
62ad96 |
daemon/direct.c | 40 ++--
|
|
Ian Kent |
62ad96 |
daemon/indirect.c | 55 +++---
|
|
Ian Kent |
62ad96 |
daemon/lookup.c | 6
|
|
Ian Kent |
62ad96 |
daemon/state.c | 2
|
|
Ian Kent |
62ad96 |
include/automount.h | 12 -
|
|
Ian Kent |
62ad96 |
include/master.h | 1
|
|
Ian Kent |
62ad96 |
include/mounts.h | 4
|
|
Ian Kent |
62ad96 |
lib/master.c | 20 +-
|
|
Ian Kent |
62ad96 |
lib/mounts.c | 21 +-
|
|
Ian Kent |
62ad96 |
modules/mount_autofs.c | 61 +++----
|
|
Ian Kent |
62ad96 |
modules/mount_bind.c | 43 +---
|
|
Ian Kent |
62ad96 |
modules/mount_changer.c | 34 +--
|
|
Ian Kent |
62ad96 |
modules/mount_ext2.c | 40 +---
|
|
Ian Kent |
62ad96 |
modules/mount_generic.c | 40 +---
|
|
Ian Kent |
62ad96 |
modules/mount_nfs.c | 41 +---
|
|
Ian Kent |
62ad96 |
modules/parse_sun.c | 414 ++++++++++++++++++++++++++++++++++++------------
|
|
Ian Kent |
62ad96 |
18 files changed, 520 insertions(+), 347 deletions(-)
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/CHANGELOG
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/CHANGELOG
|
|
Ian Kent |
62ad96 |
@@ -27,6 +27,7 @@
|
|
Ian Kent |
62ad96 |
- fix submount shutdown recovery handling.
|
|
Ian Kent |
62ad96 |
- avoid stat of possibly dead mount points and limit time to wait for
|
|
Ian Kent |
62ad96 |
umount during expire.
|
|
Ian Kent |
62ad96 |
+- make mount of multi-mounts wuth a root offset atomic.
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
14/01/2008 autofs-5.0.3
|
|
Ian Kent |
62ad96 |
-----------------------
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/daemon/automount.c
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/daemon/automount.c
|
|
Ian Kent |
62ad96 |
@@ -489,7 +489,7 @@ static int umount_subtree_mounts(struct
|
|
Ian Kent |
62ad96 |
pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &cur_state);
|
|
Ian Kent |
62ad96 |
/* Lock the closest parent nesting point for umount */
|
|
Ian Kent |
62ad96 |
cache_multi_lock(me->parent);
|
|
Ian Kent |
62ad96 |
- if (umount_multi_triggers(ap, root, me, base)) {
|
|
Ian Kent |
62ad96 |
+ if (umount_multi_triggers(ap, me, root, base)) {
|
|
Ian Kent |
62ad96 |
warn(ap->logopt,
|
|
Ian Kent |
62ad96 |
"some offset mounts still present under %s", path);
|
|
Ian Kent |
62ad96 |
left++;
|
|
Ian Kent |
62ad96 |
@@ -572,7 +572,7 @@ static int umount_all(struct autofs_poin
|
|
Ian Kent |
62ad96 |
return left;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
-int umount_autofs(struct autofs_point *ap, int force)
|
|
Ian Kent |
62ad96 |
+int umount_autofs(struct autofs_point *ap, const char *root, int force)
|
|
Ian Kent |
62ad96 |
{
|
|
Ian Kent |
62ad96 |
int ret = 0;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
@@ -589,7 +589,7 @@ int umount_autofs(struct autofs_point *a
|
|
Ian Kent |
62ad96 |
if (ap->type == LKP_INDIRECT) {
|
|
Ian Kent |
62ad96 |
if (umount_all(ap, force) && !force)
|
|
Ian Kent |
62ad96 |
return -1;
|
|
Ian Kent |
62ad96 |
- ret = umount_autofs_indirect(ap);
|
|
Ian Kent |
62ad96 |
+ ret = umount_autofs_indirect(ap, root);
|
|
Ian Kent |
62ad96 |
} else
|
|
Ian Kent |
62ad96 |
ret = umount_autofs_direct(ap);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
@@ -754,7 +754,7 @@ out_free:
|
|
Ian Kent |
62ad96 |
return ret;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
-static int destroy_logpri_fifo(struct autofs_point *ap)
|
|
Ian Kent |
62ad96 |
+int destroy_logpri_fifo(struct autofs_point *ap)
|
|
Ian Kent |
62ad96 |
{
|
|
Ian Kent |
62ad96 |
int ret = -1;
|
|
Ian Kent |
62ad96 |
int fd = ap->logpri_fifo;
|
|
Ian Kent |
62ad96 |
@@ -1056,7 +1056,7 @@ static int autofs_init_ap(struct autofs_
|
|
Ian Kent |
62ad96 |
return 0;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
-static int mount_autofs(struct autofs_point *ap)
|
|
Ian Kent |
62ad96 |
+static int mount_autofs(struct autofs_point *ap, const char *root)
|
|
Ian Kent |
62ad96 |
{
|
|
Ian Kent |
62ad96 |
int status = 0;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
@@ -1066,7 +1066,7 @@ static int mount_autofs(struct autofs_po
|
|
Ian Kent |
62ad96 |
if (ap->type == LKP_DIRECT)
|
|
Ian Kent |
62ad96 |
status = mount_autofs_direct(ap);
|
|
Ian Kent |
62ad96 |
else
|
|
Ian Kent |
62ad96 |
- status = mount_autofs_indirect(ap);
|
|
Ian Kent |
62ad96 |
+ status = mount_autofs_indirect(ap, root);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
if (status < 0)
|
|
Ian Kent |
62ad96 |
return -1;
|
|
Ian Kent |
62ad96 |
@@ -1531,10 +1531,12 @@ void *handle_mounts(void *arg)
|
|
Ian Kent |
62ad96 |
struct startup_cond *suc;
|
|
Ian Kent |
62ad96 |
struct autofs_point *ap;
|
|
Ian Kent |
62ad96 |
int cancel_state, status = 0;
|
|
Ian Kent |
62ad96 |
+ char *root;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
suc = (struct startup_cond *) arg;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
ap = suc->ap;
|
|
Ian Kent |
62ad96 |
+ root = strdup(suc->root);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
pthread_cleanup_push(return_start_status, suc);
|
|
Ian Kent |
62ad96 |
pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &cancel_state);
|
|
Ian Kent |
62ad96 |
@@ -1545,14 +1547,24 @@ void *handle_mounts(void *arg)
|
|
Ian Kent |
62ad96 |
fatal(status);
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- if (mount_autofs(ap) < 0) {
|
|
Ian Kent |
62ad96 |
+ if (!root) {
|
|
Ian Kent |
62ad96 |
+ crit(ap->logopt, "failed to alloc string root");
|
|
Ian Kent |
62ad96 |
+ suc->status = 1;
|
|
Ian Kent |
62ad96 |
+ pthread_setcancelstate(cancel_state, NULL);
|
|
Ian Kent |
62ad96 |
+ pthread_exit(NULL);
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ if (mount_autofs(ap, root) < 0) {
|
|
Ian Kent |
62ad96 |
crit(ap->logopt, "mount of %s failed!", ap->path);
|
|
Ian Kent |
62ad96 |
suc->status = 1;
|
|
Ian Kent |
62ad96 |
- umount_autofs(ap, 1);
|
|
Ian Kent |
62ad96 |
+ umount_autofs(ap, root, 1);
|
|
Ian Kent |
62ad96 |
+ free(root);
|
|
Ian Kent |
62ad96 |
pthread_setcancelstate(cancel_state, NULL);
|
|
Ian Kent |
62ad96 |
pthread_exit(NULL);
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
+ free(root);
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
if (ap->ghost && ap->type != LKP_DIRECT)
|
|
Ian Kent |
62ad96 |
info(ap->logopt, "ghosting enabled");
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
@@ -1615,7 +1627,7 @@ void *handle_mounts(void *arg)
|
|
Ian Kent |
62ad96 |
* to check for possible recovery.
|
|
Ian Kent |
62ad96 |
*/
|
|
Ian Kent |
62ad96 |
if (ap->type == LKP_DIRECT) {
|
|
Ian Kent |
62ad96 |
- umount_autofs(ap, 1);
|
|
Ian Kent |
62ad96 |
+ umount_autofs(ap, NULL, 1);
|
|
Ian Kent |
62ad96 |
break;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
@@ -1625,7 +1637,7 @@ void *handle_mounts(void *arg)
|
|
Ian Kent |
62ad96 |
* so we can continue. This can happen if a lookup
|
|
Ian Kent |
62ad96 |
* occurs while we're trying to umount.
|
|
Ian Kent |
62ad96 |
*/
|
|
Ian Kent |
62ad96 |
- ret = umount_autofs(ap, 1);
|
|
Ian Kent |
62ad96 |
+ ret = umount_autofs(ap, NULL, 1);
|
|
Ian Kent |
62ad96 |
if (!ret)
|
|
Ian Kent |
62ad96 |
break;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/daemon/direct.c
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/daemon/direct.c
|
|
Ian Kent |
62ad96 |
@@ -646,7 +646,7 @@ force_umount:
|
|
Ian Kent |
62ad96 |
return rv;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
-int mount_autofs_offset(struct autofs_point *ap, struct mapent *me)
|
|
Ian Kent |
62ad96 |
+int mount_autofs_offset(struct autofs_point *ap, struct mapent *me, const char *root, const char *offset)
|
|
Ian Kent |
62ad96 |
{
|
|
Ian Kent |
62ad96 |
char buf[MAX_ERR_BUF];
|
|
Ian Kent |
62ad96 |
struct mnt_params *mp;
|
|
Ian Kent |
62ad96 |
@@ -654,6 +654,7 @@ int mount_autofs_offset(struct autofs_po
|
|
Ian Kent |
62ad96 |
struct stat st;
|
|
Ian Kent |
62ad96 |
int ioctlfd, cl_flags, status, ret;
|
|
Ian Kent |
62ad96 |
const char *type, *map_name = NULL;
|
|
Ian Kent |
62ad96 |
+ char mountpoint[PATH_MAX];
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
if (is_mounted(_PROC_MOUNTS, me->key, MNTS_AUTOFS)) {
|
|
Ian Kent |
62ad96 |
if (ap->state != ST_READMAP)
|
|
Ian Kent |
62ad96 |
@@ -695,8 +696,11 @@ int mount_autofs_offset(struct autofs_po
|
|
Ian Kent |
62ad96 |
return MOUNT_OFFSET_OK;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
+ strcpy(mountpoint, root);
|
|
Ian Kent |
62ad96 |
+ strcat(mountpoint, offset);
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
/* In case the directory doesn't exist, try to mkdir it */
|
|
Ian Kent |
62ad96 |
- if (mkdir_path(me->key, 0555) < 0) {
|
|
Ian Kent |
62ad96 |
+ if (mkdir_path(mountpoint, 0555) < 0) {
|
|
Ian Kent |
62ad96 |
if (errno == EEXIST) {
|
|
Ian Kent |
62ad96 |
/*
|
|
Ian Kent |
62ad96 |
* If the mount point directory is a real mount
|
|
Ian Kent |
62ad96 |
@@ -705,7 +709,7 @@ int mount_autofs_offset(struct autofs_po
|
|
Ian Kent |
62ad96 |
* the kernel NFS client.
|
|
Ian Kent |
62ad96 |
*/
|
|
Ian Kent |
62ad96 |
if (me->multi != me &&
|
|
Ian Kent |
62ad96 |
- is_mounted(_PATH_MOUNTED, me->key, MNTS_REAL))
|
|
Ian Kent |
62ad96 |
+ is_mounted(_PATH_MOUNTED, mountpoint, MNTS_REAL))
|
|
Ian Kent |
62ad96 |
return MOUNT_OFFSET_IGNORE;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
/*
|
|
Ian Kent |
62ad96 |
@@ -725,13 +729,13 @@ int mount_autofs_offset(struct autofs_po
|
|
Ian Kent |
62ad96 |
char *estr = strerror_r(errno, buf, MAX_ERR_BUF);
|
|
Ian Kent |
62ad96 |
debug(ap->logopt,
|
|
Ian Kent |
62ad96 |
"can't create mount directory: %s, %s",
|
|
Ian Kent |
62ad96 |
- me->key, estr);
|
|
Ian Kent |
62ad96 |
+ mountpoint, estr);
|
|
Ian Kent |
62ad96 |
return MOUNT_OFFSET_FAIL;
|
|
Ian Kent |
62ad96 |
} else {
|
|
Ian Kent |
62ad96 |
char *estr = strerror_r(errno, buf, MAX_ERR_BUF);
|
|
Ian Kent |
62ad96 |
crit(ap->logopt,
|
|
Ian Kent |
62ad96 |
"failed to create mount directory: %s, %s",
|
|
Ian Kent |
62ad96 |
- me->key, estr);
|
|
Ian Kent |
62ad96 |
+ mountpoint, estr);
|
|
Ian Kent |
62ad96 |
return MOUNT_OFFSET_FAIL;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
} else {
|
|
Ian Kent |
62ad96 |
@@ -741,7 +745,7 @@ int mount_autofs_offset(struct autofs_po
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
debug(ap->logopt,
|
|
Ian Kent |
62ad96 |
"calling mount -t autofs " SLOPPY " -o %s automount %s",
|
|
Ian Kent |
62ad96 |
- mp->options, me->key);
|
|
Ian Kent |
62ad96 |
+ mp->options, mountpoint);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
type = ap->entry->maps->type;
|
|
Ian Kent |
62ad96 |
if (type && !strcmp(ap->entry->maps->type, "hosts")) {
|
|
Ian Kent |
62ad96 |
@@ -753,22 +757,18 @@ int mount_autofs_offset(struct autofs_po
|
|
Ian Kent |
62ad96 |
} else
|
|
Ian Kent |
62ad96 |
map_name = me->mc->map->argv[0];
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- ret = mount(map_name, me->key, "autofs", MS_MGC_VAL, mp->options);
|
|
Ian Kent |
62ad96 |
+ ret = mount(map_name, mountpoint, "autofs", MS_MGC_VAL, mp->options);
|
|
Ian Kent |
62ad96 |
if (ret) {
|
|
Ian Kent |
62ad96 |
- crit(ap->logopt, "failed to mount autofs path %s", me->key);
|
|
Ian Kent |
62ad96 |
- goto out_err;
|
|
Ian Kent |
62ad96 |
- }
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- if (ret != 0) {
|
|
Ian Kent |
62ad96 |
crit(ap->logopt,
|
|
Ian Kent |
62ad96 |
- "failed to mount autofs offset trigger %s", me->key);
|
|
Ian Kent |
62ad96 |
+ "failed to mount offset trigger %s at %s",
|
|
Ian Kent |
62ad96 |
+ me->key, mountpoint);
|
|
Ian Kent |
62ad96 |
goto out_err;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
/* Root directory for ioctl()'s */
|
|
Ian Kent |
62ad96 |
- ioctlfd = open(me->key, O_RDONLY);
|
|
Ian Kent |
62ad96 |
+ ioctlfd = open(mountpoint, O_RDONLY);
|
|
Ian Kent |
62ad96 |
if (ioctlfd < 0) {
|
|
Ian Kent |
62ad96 |
- crit(ap->logopt, "failed to create ioctl fd for %s", me->key);
|
|
Ian Kent |
62ad96 |
+ crit(ap->logopt, "failed to create ioctl fd for %s", mountpoint);
|
|
Ian Kent |
62ad96 |
goto out_umount;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
@@ -782,7 +782,7 @@ int mount_autofs_offset(struct autofs_po
|
|
Ian Kent |
62ad96 |
ret = fstat(ioctlfd, &st);
|
|
Ian Kent |
62ad96 |
if (ret == -1) {
|
|
Ian Kent |
62ad96 |
error(ap->logopt,
|
|
Ian Kent |
62ad96 |
- "failed to stat direct mount trigger %s", me->key);
|
|
Ian Kent |
62ad96 |
+ "failed to stat direct mount trigger %s", mountpoint);
|
|
Ian Kent |
62ad96 |
goto out_close;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
@@ -790,17 +790,17 @@ int mount_autofs_offset(struct autofs_po
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
close(ioctlfd);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- debug(ap->logopt, "mounted trigger %s", me->key);
|
|
Ian Kent |
62ad96 |
+ debug(ap->logopt, "mounted trigger %s at %s", me->key, mountpoint);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
return MOUNT_OFFSET_OK;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
out_close:
|
|
Ian Kent |
62ad96 |
close(ioctlfd);
|
|
Ian Kent |
62ad96 |
out_umount:
|
|
Ian Kent |
62ad96 |
- umount(me->key);
|
|
Ian Kent |
62ad96 |
+ umount(mountpoint);
|
|
Ian Kent |
62ad96 |
out_err:
|
|
Ian Kent |
62ad96 |
- if (stat(me->key, &st) == 0 && me->dir_created)
|
|
Ian Kent |
62ad96 |
- rmdir_path(ap, me->key, st.st_dev);
|
|
Ian Kent |
62ad96 |
+ if (stat(mountpoint, &st) == 0 && me->dir_created)
|
|
Ian Kent |
62ad96 |
+ rmdir_path(ap, mountpoint, st.st_dev);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
return MOUNT_OFFSET_FAIL;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/daemon/indirect.c
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/daemon/indirect.c
|
|
Ian Kent |
62ad96 |
@@ -83,7 +83,7 @@ static int unlink_mount_tree(struct auto
|
|
Ian Kent |
62ad96 |
return ret;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
-static int do_mount_autofs_indirect(struct autofs_point *ap)
|
|
Ian Kent |
62ad96 |
+static int do_mount_autofs_indirect(struct autofs_point *ap, const char *root)
|
|
Ian Kent |
62ad96 |
{
|
|
Ian Kent |
62ad96 |
time_t timeout = ap->exp_timeout;
|
|
Ian Kent |
62ad96 |
char *options = NULL;
|
|
Ian Kent |
62ad96 |
@@ -109,11 +109,11 @@ static int do_mount_autofs_indirect(stru
|
|
Ian Kent |
62ad96 |
goto out_err;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
/* In case the directory doesn't exist, try to mkdir it */
|
|
Ian Kent |
62ad96 |
- if (mkdir_path(ap->path, 0555) < 0) {
|
|
Ian Kent |
62ad96 |
+ if (mkdir_path(root, 0555) < 0) {
|
|
Ian Kent |
62ad96 |
if (errno != EEXIST && errno != EROFS) {
|
|
Ian Kent |
62ad96 |
crit(ap->logopt,
|
|
Ian Kent |
62ad96 |
"failed to create autofs directory %s",
|
|
Ian Kent |
62ad96 |
- ap->path);
|
|
Ian Kent |
62ad96 |
+ root);
|
|
Ian Kent |
62ad96 |
goto out_err;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
/* If we recieve an error, and it's EEXIST or EROFS we know
|
|
Ian Kent |
62ad96 |
@@ -134,9 +134,10 @@ static int do_mount_autofs_indirect(stru
|
|
Ian Kent |
62ad96 |
} else
|
|
Ian Kent |
62ad96 |
map_name = ap->entry->maps->argv[0];
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- ret = mount(map_name, ap->path, "autofs", MS_MGC_VAL, options);
|
|
Ian Kent |
62ad96 |
+ ret = mount(map_name, root, "autofs", MS_MGC_VAL, options);
|
|
Ian Kent |
62ad96 |
if (ret) {
|
|
Ian Kent |
62ad96 |
- crit(ap->logopt, "failed to mount autofs path %s", ap->path);
|
|
Ian Kent |
62ad96 |
+ crit(ap->logopt,
|
|
Ian Kent |
62ad96 |
+ "failed to mount autofs path %s at %s", ap->path, root);
|
|
Ian Kent |
62ad96 |
goto out_rmdir;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
@@ -145,7 +146,7 @@ static int do_mount_autofs_indirect(stru
|
|
Ian Kent |
62ad96 |
options = NULL;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
/* Root directory for ioctl()'s */
|
|
Ian Kent |
62ad96 |
- ap->ioctlfd = open(ap->path, O_RDONLY);
|
|
Ian Kent |
62ad96 |
+ ap->ioctlfd = open(root, O_RDONLY);
|
|
Ian Kent |
62ad96 |
if (ap->ioctlfd < 0) {
|
|
Ian Kent |
62ad96 |
crit(ap->logopt,
|
|
Ian Kent |
62ad96 |
"failed to create ioctl fd for autofs path %s", ap->path);
|
|
Ian Kent |
62ad96 |
@@ -163,13 +164,13 @@ static int do_mount_autofs_indirect(stru
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
if (ap->exp_timeout)
|
|
Ian Kent |
62ad96 |
info(ap->logopt,
|
|
Ian Kent |
62ad96 |
- "mounted indirect mount on %s "
|
|
Ian Kent |
62ad96 |
+ "mounted indirect mount for %s "
|
|
Ian Kent |
62ad96 |
"with timeout %u, freq %u seconds", ap->path,
|
|
Ian Kent |
62ad96 |
(unsigned int) ap->exp_timeout,
|
|
Ian Kent |
62ad96 |
(unsigned int) ap->exp_runfreq);
|
|
Ian Kent |
62ad96 |
else
|
|
Ian Kent |
62ad96 |
info(ap->logopt,
|
|
Ian Kent |
62ad96 |
- "mounted indirect mount on %s with timeouts disabled",
|
|
Ian Kent |
62ad96 |
+ "mounted indirect mount for %s with timeouts disabled",
|
|
Ian Kent |
62ad96 |
ap->path);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
fstat(ap->ioctlfd, &st);
|
|
Ian Kent |
62ad96 |
@@ -178,10 +179,10 @@ static int do_mount_autofs_indirect(stru
|
|
Ian Kent |
62ad96 |
return 0;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
out_umount:
|
|
Ian Kent |
62ad96 |
- umount(ap->path);
|
|
Ian Kent |
62ad96 |
+ umount(root);
|
|
Ian Kent |
62ad96 |
out_rmdir:
|
|
Ian Kent |
62ad96 |
if (ap->dir_created)
|
|
Ian Kent |
62ad96 |
- rmdir_path(ap, ap->path, ap->dev);
|
|
Ian Kent |
62ad96 |
+ rmdir(root);
|
|
Ian Kent |
62ad96 |
out_err:
|
|
Ian Kent |
62ad96 |
if (options)
|
|
Ian Kent |
62ad96 |
free(options);
|
|
Ian Kent |
62ad96 |
@@ -193,7 +194,7 @@ out_err:
|
|
Ian Kent |
62ad96 |
return -1;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
-int mount_autofs_indirect(struct autofs_point *ap)
|
|
Ian Kent |
62ad96 |
+int mount_autofs_indirect(struct autofs_point *ap, const char *root)
|
|
Ian Kent |
62ad96 |
{
|
|
Ian Kent |
62ad96 |
time_t now = time(NULL);
|
|
Ian Kent |
62ad96 |
int status;
|
|
Ian Kent |
62ad96 |
@@ -207,11 +208,11 @@ int mount_autofs_indirect(struct autofs_
|
|
Ian Kent |
62ad96 |
return -1;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- status = do_mount_autofs_indirect(ap);
|
|
Ian Kent |
62ad96 |
+ status = do_mount_autofs_indirect(ap, root);
|
|
Ian Kent |
62ad96 |
if (status < 0)
|
|
Ian Kent |
62ad96 |
return -1;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- map = lookup_ghost(ap);
|
|
Ian Kent |
62ad96 |
+ map = lookup_ghost(ap, root);
|
|
Ian Kent |
62ad96 |
if (map & LKP_FAIL) {
|
|
Ian Kent |
62ad96 |
if (map & LKP_DIRECT) {
|
|
Ian Kent |
62ad96 |
error(ap->logopt,
|
|
Ian Kent |
62ad96 |
@@ -230,7 +231,7 @@ int mount_autofs_indirect(struct autofs_
|
|
Ian Kent |
62ad96 |
return 0;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
-static void close_mount_fds(struct autofs_point *ap)
|
|
Ian Kent |
62ad96 |
+void close_mount_fds(struct autofs_point *ap)
|
|
Ian Kent |
62ad96 |
{
|
|
Ian Kent |
62ad96 |
/*
|
|
Ian Kent |
62ad96 |
* Since submounts look after themselves the parent never knows
|
|
Ian Kent |
62ad96 |
@@ -255,11 +256,17 @@ static void close_mount_fds(struct autof
|
|
Ian Kent |
62ad96 |
return;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
-int umount_autofs_indirect(struct autofs_point *ap)
|
|
Ian Kent |
62ad96 |
+int umount_autofs_indirect(struct autofs_point *ap, const char *root)
|
|
Ian Kent |
62ad96 |
{
|
|
Ian Kent |
62ad96 |
char buf[MAX_ERR_BUF];
|
|
Ian Kent |
62ad96 |
+ char mountpoint[PATH_MAX + 1];
|
|
Ian Kent |
62ad96 |
int ret, rv, retries;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
+ if (root)
|
|
Ian Kent |
62ad96 |
+ strcpy(mountpoint, root);
|
|
Ian Kent |
62ad96 |
+ else
|
|
Ian Kent |
62ad96 |
+ strcpy(mountpoint, ap->path);
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
/* If we are trying to shutdown make sure we can umount */
|
|
Ian Kent |
62ad96 |
rv = ioctl(ap->ioctlfd, AUTOFS_IOC_ASKUMOUNT, &ret;;
|
|
Ian Kent |
62ad96 |
if (rv == -1) {
|
|
Ian Kent |
62ad96 |
@@ -284,7 +291,7 @@ int umount_autofs_indirect(struct autofs
|
|
Ian Kent |
62ad96 |
sched_yield();
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
retries = UMOUNT_RETRIES;
|
|
Ian Kent |
62ad96 |
- while ((rv = umount(ap->path)) == -1 && retries--) {
|
|
Ian Kent |
62ad96 |
+ while ((rv = umount(mountpoint)) == -1 && retries--) {
|
|
Ian Kent |
62ad96 |
struct timespec tm = {0, 200000000};
|
|
Ian Kent |
62ad96 |
if (errno != EBUSY)
|
|
Ian Kent |
62ad96 |
break;
|
|
Ian Kent |
62ad96 |
@@ -296,13 +303,13 @@ int umount_autofs_indirect(struct autofs
|
|
Ian Kent |
62ad96 |
case ENOENT:
|
|
Ian Kent |
62ad96 |
case EINVAL:
|
|
Ian Kent |
62ad96 |
error(ap->logopt,
|
|
Ian Kent |
62ad96 |
- "mount point %s does not exist", ap->path);
|
|
Ian Kent |
62ad96 |
+ "mount point %s does not exist", mountpoint);
|
|
Ian Kent |
62ad96 |
close_mount_fds(ap);
|
|
Ian Kent |
62ad96 |
return 0;
|
|
Ian Kent |
62ad96 |
break;
|
|
Ian Kent |
62ad96 |
case EBUSY:
|
|
Ian Kent |
62ad96 |
debug(ap->logopt,
|
|
Ian Kent |
62ad96 |
- "mount point %s is in use", ap->path);
|
|
Ian Kent |
62ad96 |
+ "mount point %s is in use", mountpoint);
|
|
Ian Kent |
62ad96 |
if (ap->state == ST_SHUTDOWN_FORCE) {
|
|
Ian Kent |
62ad96 |
close_mount_fds(ap);
|
|
Ian Kent |
62ad96 |
goto force_umount;
|
|
Ian Kent |
62ad96 |
@@ -321,11 +328,11 @@ int umount_autofs_indirect(struct autofs
|
|
Ian Kent |
62ad96 |
return 0;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
#endif
|
|
Ian Kent |
62ad96 |
- ap->ioctlfd = open(ap->path, O_RDONLY);
|
|
Ian Kent |
62ad96 |
+ ap->ioctlfd = open(mountpoint, O_RDONLY);
|
|
Ian Kent |
62ad96 |
if (ap->ioctlfd < 0) {
|
|
Ian Kent |
62ad96 |
warn(ap->logopt,
|
|
Ian Kent |
62ad96 |
"could not recover autofs path %s",
|
|
Ian Kent |
62ad96 |
- ap->path);
|
|
Ian Kent |
62ad96 |
+ mountpoint);
|
|
Ian Kent |
62ad96 |
close_mount_fds(ap);
|
|
Ian Kent |
62ad96 |
return 0;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
@@ -355,12 +362,12 @@ int umount_autofs_indirect(struct autofs
|
|
Ian Kent |
62ad96 |
force_umount:
|
|
Ian Kent |
62ad96 |
if (rv != 0) {
|
|
Ian Kent |
62ad96 |
warn(ap->logopt,
|
|
Ian Kent |
62ad96 |
- "forcing umount of indirect mount %s", ap->path);
|
|
Ian Kent |
62ad96 |
- rv = umount2(ap->path, MNT_DETACH);
|
|
Ian Kent |
62ad96 |
+ "forcing umount of indirect mount %s", mountpoint);
|
|
Ian Kent |
62ad96 |
+ rv = umount2(mountpoint, MNT_DETACH);
|
|
Ian Kent |
62ad96 |
} else {
|
|
Ian Kent |
62ad96 |
- info(ap->logopt, "umounted indirect mount %s", ap->path);
|
|
Ian Kent |
62ad96 |
+ info(ap->logopt, "umounted indirect mount %s", mountpoint);
|
|
Ian Kent |
62ad96 |
if (ap->submount)
|
|
Ian Kent |
62ad96 |
- rm_unwanted(ap->logopt, ap->path, 1, ap->dev);
|
|
Ian Kent |
62ad96 |
+ rm_unwanted(ap->logopt, mountpoint, 1, ap->dev);
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
return rv;
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/daemon/lookup.c
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/daemon/lookup.c
|
|
Ian Kent |
62ad96 |
@@ -565,7 +565,7 @@ int lookup_nss_read_map(struct autofs_po
|
|
Ian Kent |
62ad96 |
return 0;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
-int lookup_ghost(struct autofs_point *ap)
|
|
Ian Kent |
62ad96 |
+int lookup_ghost(struct autofs_point *ap, const char *root)
|
|
Ian Kent |
62ad96 |
{
|
|
Ian Kent |
62ad96 |
struct master_mapent *entry = ap->entry;
|
|
Ian Kent |
62ad96 |
struct map_source *map;
|
|
Ian Kent |
62ad96 |
@@ -611,12 +611,12 @@ int lookup_ghost(struct autofs_point *ap
|
|
Ian Kent |
62ad96 |
goto next;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- fullpath = alloca(strlen(me->key) + strlen(ap->path) + 3);
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(strlen(me->key) + strlen(root) + 3);
|
|
Ian Kent |
62ad96 |
if (!fullpath) {
|
|
Ian Kent |
62ad96 |
warn(ap->logopt, "failed to allocate full path");
|
|
Ian Kent |
62ad96 |
goto next;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
- sprintf(fullpath, "%s/%s", ap->path, me->key);
|
|
Ian Kent |
62ad96 |
+ sprintf(fullpath, "%s/%s", root, me->key);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
ret = stat(fullpath, &st);
|
|
Ian Kent |
62ad96 |
if (ret == -1 && errno != ENOENT) {
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/daemon/state.c
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/daemon/state.c
|
|
Ian Kent |
62ad96 |
@@ -393,7 +393,7 @@ static void *do_readmap(void *arg)
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
if (ap->type == LKP_INDIRECT) {
|
|
Ian Kent |
62ad96 |
lookup_prune_cache(ap, now);
|
|
Ian Kent |
62ad96 |
- status = lookup_ghost(ap);
|
|
Ian Kent |
62ad96 |
+ status = lookup_ghost(ap, ap->path);
|
|
Ian Kent |
62ad96 |
} else {
|
|
Ian Kent |
62ad96 |
struct mapent *me, *ne, *nested;
|
|
Ian Kent |
62ad96 |
mnts = tree_make_mnt_tree(_PROC_MOUNTS, "/");
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/include/automount.h
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/include/automount.h
|
|
Ian Kent |
62ad96 |
@@ -230,7 +230,7 @@ int lookup_nss_read_master(struct master
|
|
Ian Kent |
62ad96 |
int lookup_nss_read_map(struct autofs_point *ap, struct map_source *source, time_t age);
|
|
Ian Kent |
62ad96 |
int lookup_enumerate(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
int (*fn)(struct autofs_point *,struct mapent *, int), time_t now);
|
|
Ian Kent |
62ad96 |
-int lookup_ghost(struct autofs_point *ap);
|
|
Ian Kent |
62ad96 |
+int lookup_ghost(struct autofs_point *ap, const char *root);
|
|
Ian Kent |
62ad96 |
int lookup_nss_mount(struct autofs_point *ap, struct map_source *source, const char *name, int name_len);
|
|
Ian Kent |
62ad96 |
void lookup_close_lookup(struct autofs_point *ap);
|
|
Ian Kent |
62ad96 |
int lookup_prune_cache(struct autofs_point *ap, time_t age);
|
|
Ian Kent |
62ad96 |
@@ -332,6 +332,7 @@ struct startup_cond {
|
|
Ian Kent |
62ad96 |
pthread_mutex_t mutex;
|
|
Ian Kent |
62ad96 |
pthread_cond_t cond;
|
|
Ian Kent |
62ad96 |
struct autofs_point *ap;
|
|
Ian Kent |
62ad96 |
+ char *root;
|
|
Ian Kent |
62ad96 |
unsigned int done;
|
|
Ian Kent |
62ad96 |
unsigned int status;
|
|
Ian Kent |
62ad96 |
};
|
|
Ian Kent |
62ad96 |
@@ -427,12 +428,13 @@ int do_expire(struct autofs_point *ap, c
|
|
Ian Kent |
62ad96 |
void *expire_proc_indirect(void *);
|
|
Ian Kent |
62ad96 |
void *expire_proc_direct(void *);
|
|
Ian Kent |
62ad96 |
int expire_offsets_direct(struct autofs_point *ap, struct mapent *me, int now);
|
|
Ian Kent |
62ad96 |
-int mount_autofs_indirect(struct autofs_point *ap);
|
|
Ian Kent |
62ad96 |
+int mount_autofs_indirect(struct autofs_point *ap, const char *root);
|
|
Ian Kent |
62ad96 |
int mount_autofs_direct(struct autofs_point *ap);
|
|
Ian Kent |
62ad96 |
-int mount_autofs_offset(struct autofs_point *ap, struct mapent *me);
|
|
Ian Kent |
62ad96 |
+int mount_autofs_offset(struct autofs_point *ap, struct mapent *me, const char *root, const char *offset);
|
|
Ian Kent |
62ad96 |
void submount_signal_parent(struct autofs_point *ap, unsigned int success);
|
|
Ian Kent |
62ad96 |
-int umount_autofs(struct autofs_point *ap, int force);
|
|
Ian Kent |
62ad96 |
-int umount_autofs_indirect(struct autofs_point *ap);
|
|
Ian Kent |
62ad96 |
+void close_mount_fds(struct autofs_point *ap);
|
|
Ian Kent |
62ad96 |
+int umount_autofs(struct autofs_point *ap, const char *root, int force);
|
|
Ian Kent |
62ad96 |
+int umount_autofs_indirect(struct autofs_point *ap, const char *root);
|
|
Ian Kent |
62ad96 |
int do_umount_autofs_direct(struct autofs_point *ap, struct mnt_list *mnts, struct mapent *me);
|
|
Ian Kent |
62ad96 |
int umount_autofs_direct(struct autofs_point *ap);
|
|
Ian Kent |
62ad96 |
int umount_autofs_offset(struct autofs_point *ap, struct mapent *me);
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/include/master.h
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/include/master.h
|
|
Ian Kent |
62ad96 |
@@ -91,6 +91,7 @@ void master_source_lock_cleanup(void *);
|
|
Ian Kent |
62ad96 |
void master_source_current_wait(struct master_mapent *);
|
|
Ian Kent |
62ad96 |
void master_source_current_signal(struct master_mapent *);
|
|
Ian Kent |
62ad96 |
struct master_mapent *master_find_mapent(struct master *, const char *);
|
|
Ian Kent |
62ad96 |
+struct autofs_point *__master_find_submount(struct autofs_point *, const char *);
|
|
Ian Kent |
62ad96 |
struct autofs_point *master_find_submount(struct autofs_point *, const char *);
|
|
Ian Kent |
62ad96 |
struct master_mapent *master_new_mapent(struct master *, const char *, time_t);
|
|
Ian Kent |
62ad96 |
void master_add_mapent(struct master *, struct master_mapent *);
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/include/mounts.h
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/include/mounts.h
|
|
Ian Kent |
62ad96 |
@@ -85,7 +85,7 @@ int tree_find_mnt_ents(struct mnt_list *
|
|
Ian Kent |
62ad96 |
int tree_is_mounted(struct mnt_list *mnts, const char *path, unsigned int type);
|
|
Ian Kent |
62ad96 |
void set_tsd_user_vars(unsigned int, uid_t, gid_t);
|
|
Ian Kent |
62ad96 |
int umount_ent(struct autofs_point *, const char *);
|
|
Ian Kent |
62ad96 |
-int mount_multi_triggers(struct autofs_point *, char *, struct mapent *, const char *);
|
|
Ian Kent |
62ad96 |
-int umount_multi_triggers(struct autofs_point *, char *, struct mapent *, const char *);
|
|
Ian Kent |
62ad96 |
+int mount_multi_triggers(struct autofs_point *, struct mapent *, const char *, unsigned int, const char *);
|
|
Ian Kent |
62ad96 |
+int umount_multi_triggers(struct autofs_point *, struct mapent *, char *, const char *);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
#endif
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/lib/master.c
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/lib/master.c
|
|
Ian Kent |
62ad96 |
@@ -602,27 +602,32 @@ struct master_mapent *master_find_mapent
|
|
Ian Kent |
62ad96 |
return NULL;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
-struct autofs_point *master_find_submount(struct autofs_point *ap, const char *path)
|
|
Ian Kent |
62ad96 |
+struct autofs_point *__master_find_submount(struct autofs_point *ap, const char *path)
|
|
Ian Kent |
62ad96 |
{
|
|
Ian Kent |
62ad96 |
struct list_head *head, *p;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- mounts_mutex_lock(ap);
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
head = &ap->submounts;
|
|
Ian Kent |
62ad96 |
list_for_each(p, head) {
|
|
Ian Kent |
62ad96 |
struct autofs_point *submount;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
submount = list_entry(p, struct autofs_point, mounts);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- if (!strcmp(submount->path, path)) {
|
|
Ian Kent |
62ad96 |
- mounts_mutex_unlock(ap);
|
|
Ian Kent |
62ad96 |
+ if (!strcmp(submount->path, path))
|
|
Ian Kent |
62ad96 |
return submount;
|
|
Ian Kent |
62ad96 |
- }
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
+ return NULL;
|
|
Ian Kent |
62ad96 |
+}
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+struct autofs_point *master_find_submount(struct autofs_point *ap, const char *path)
|
|
Ian Kent |
62ad96 |
+{
|
|
Ian Kent |
62ad96 |
+ struct autofs_point *submount;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ mounts_mutex_lock(ap);
|
|
Ian Kent |
62ad96 |
+ submount = __master_find_submount(ap, path);
|
|
Ian Kent |
62ad96 |
mounts_mutex_unlock(ap);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- return NULL;
|
|
Ian Kent |
62ad96 |
+ return submount;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
struct master_mapent *master_new_mapent(struct master *master, const char *path, time_t age)
|
|
Ian Kent |
62ad96 |
@@ -955,6 +960,7 @@ static int master_do_mount(struct master
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
suc.ap = ap;
|
|
Ian Kent |
62ad96 |
+ suc.root = ap->path;
|
|
Ian Kent |
62ad96 |
suc.done = 0;
|
|
Ian Kent |
62ad96 |
suc.status = 0;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/lib/mounts.c
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/lib/mounts.c
|
|
Ian Kent |
62ad96 |
@@ -1105,7 +1105,8 @@ int umount_ent(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
return rv;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
-int mount_multi_triggers(struct autofs_point *ap, char *root, struct mapent *me, const char *base)
|
|
Ian Kent |
62ad96 |
+int mount_multi_triggers(struct autofs_point *ap, struct mapent *me,
|
|
Ian Kent |
62ad96 |
+ const char *root, unsigned int start, const char *base)
|
|
Ian Kent |
62ad96 |
{
|
|
Ian Kent |
62ad96 |
char path[PATH_MAX + 1];
|
|
Ian Kent |
62ad96 |
char *offset = path;
|
|
Ian Kent |
62ad96 |
@@ -1113,17 +1114,13 @@ int mount_multi_triggers(struct autofs_p
|
|
Ian Kent |
62ad96 |
struct list_head *pos = NULL;
|
|
Ian Kent |
62ad96 |
unsigned int fs_path_len;
|
|
Ian Kent |
62ad96 |
unsigned int mounted;
|
|
Ian Kent |
62ad96 |
- int ret, start;
|
|
Ian Kent |
62ad96 |
+ int ret;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- fs_path_len = strlen(root) + strlen(base);
|
|
Ian Kent |
62ad96 |
+ fs_path_len = start + strlen(base);
|
|
Ian Kent |
62ad96 |
if (fs_path_len > PATH_MAX)
|
|
Ian Kent |
62ad96 |
return -1;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- strcpy(path, root);
|
|
Ian Kent |
62ad96 |
- strcat(path, base);
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
mounted = 0;
|
|
Ian Kent |
62ad96 |
- start = strlen(root);
|
|
Ian Kent |
62ad96 |
offset = cache_get_offset(base, offset, start, &me->multi_list, &pos;;
|
|
Ian Kent |
62ad96 |
while (offset) {
|
|
Ian Kent |
62ad96 |
int plen = fs_path_len + strlen(offset);
|
|
Ian Kent |
62ad96 |
@@ -1137,9 +1134,9 @@ int mount_multi_triggers(struct autofs_p
|
|
Ian Kent |
62ad96 |
if (!oe || !oe->mapent)
|
|
Ian Kent |
62ad96 |
goto cont;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- debug(ap->logopt, "mount offset %s", oe->key);
|
|
Ian Kent |
62ad96 |
+ debug(ap->logopt, "mount offset %s at %s", oe->key, root);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- ret = mount_autofs_offset(ap, oe);
|
|
Ian Kent |
62ad96 |
+ ret = mount_autofs_offset(ap, oe, root, offset);
|
|
Ian Kent |
62ad96 |
if (ret >= MOUNT_OFFSET_OK)
|
|
Ian Kent |
62ad96 |
mounted++;
|
|
Ian Kent |
62ad96 |
else {
|
|
Ian Kent |
62ad96 |
@@ -1161,7 +1158,7 @@ cont:
|
|
Ian Kent |
62ad96 |
return mounted;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
-int umount_multi_triggers(struct autofs_point *ap, char *root, struct mapent *me, const char *base)
|
|
Ian Kent |
62ad96 |
+int umount_multi_triggers(struct autofs_point *ap, struct mapent *me, char *root, const char *base)
|
|
Ian Kent |
62ad96 |
{
|
|
Ian Kent |
62ad96 |
char path[PATH_MAX + 1];
|
|
Ian Kent |
62ad96 |
char *offset;
|
|
Ian Kent |
62ad96 |
@@ -1198,7 +1195,7 @@ int umount_multi_triggers(struct autofs_
|
|
Ian Kent |
62ad96 |
* nonstrict mount fail.
|
|
Ian Kent |
62ad96 |
*/
|
|
Ian Kent |
62ad96 |
oe_base = oe->key + strlen(root);
|
|
Ian Kent |
62ad96 |
- left += umount_multi_triggers(ap, root, oe, oe_base);
|
|
Ian Kent |
62ad96 |
+ left += umount_multi_triggers(ap, oe, root, oe_base);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
if (oe->ioctlfd != -1)
|
|
Ian Kent |
62ad96 |
left++;
|
|
Ian Kent |
62ad96 |
@@ -1238,7 +1235,7 @@ int umount_multi_triggers(struct autofs_
|
|
Ian Kent |
62ad96 |
if (is_mounted(_PATH_MOUNTED, root, MNTS_REAL)) {
|
|
Ian Kent |
62ad96 |
info(ap->logopt, "unmounting dir = %s", root);
|
|
Ian Kent |
62ad96 |
if (umount_ent(ap, root)) {
|
|
Ian Kent |
62ad96 |
- if (mount_multi_triggers(ap, root, me, "/") < 0)
|
|
Ian Kent |
62ad96 |
+ if (mount_multi_triggers(ap, me, root, strlen(root), "/") < 0)
|
|
Ian Kent |
62ad96 |
warn(ap->logopt,
|
|
Ian Kent |
62ad96 |
"failed to remount offset triggers");
|
|
Ian Kent |
62ad96 |
return left++;
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/modules/mount_autofs.c
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/modules/mount_autofs.c
|
|
Ian Kent |
62ad96 |
@@ -48,7 +48,7 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
{
|
|
Ian Kent |
62ad96 |
struct startup_cond suc;
|
|
Ian Kent |
62ad96 |
pthread_t thid;
|
|
Ian Kent |
62ad96 |
- char *fullpath;
|
|
Ian Kent |
62ad96 |
+ char *realpath, *mountpoint;
|
|
Ian Kent |
62ad96 |
const char **argv;
|
|
Ian Kent |
62ad96 |
int argc, status, ghost = ap->ghost;
|
|
Ian Kent |
62ad96 |
time_t timeout = ap->exp_timeout;
|
|
Ian Kent |
62ad96 |
@@ -60,32 +60,32 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
struct autofs_point *nap;
|
|
Ian Kent |
62ad96 |
char buf[MAX_ERR_BUF];
|
|
Ian Kent |
62ad96 |
char *options, *p;
|
|
Ian Kent |
62ad96 |
- int ret;
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- fullpath = alloca(strlen(root) + name_len + 2);
|
|
Ian Kent |
62ad96 |
- if (!fullpath) {
|
|
Ian Kent |
62ad96 |
- char *estr = strerror_r(errno, buf, MAX_ERR_BUF);
|
|
Ian Kent |
62ad96 |
- logerr(MODPREFIX "alloca: %s", estr);
|
|
Ian Kent |
62ad96 |
- return 1;
|
|
Ian Kent |
62ad96 |
- }
|
|
Ian Kent |
62ad96 |
+ int len, ret;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
/* Root offset of multi-mount */
|
|
Ian Kent |
62ad96 |
- if (*name == '/' && name_len == 1)
|
|
Ian Kent |
62ad96 |
- strcpy(fullpath, root);
|
|
Ian Kent |
62ad96 |
- else if (*name == '/')
|
|
Ian Kent |
62ad96 |
- strcpy(fullpath, name);
|
|
Ian Kent |
62ad96 |
- else {
|
|
Ian Kent |
62ad96 |
- strcpy(fullpath, root);
|
|
Ian Kent |
62ad96 |
- strcat(fullpath, "/");
|
|
Ian Kent |
62ad96 |
- strcat(fullpath, name);
|
|
Ian Kent |
62ad96 |
- }
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- if (is_mounted(_PATH_MOUNTED, fullpath, MNTS_REAL)) {
|
|
Ian Kent |
62ad96 |
- error(ap->logopt,
|
|
Ian Kent |
62ad96 |
- MODPREFIX
|
|
Ian Kent |
62ad96 |
- "warning: about to mount over %s, continuing",
|
|
Ian Kent |
62ad96 |
- fullpath);
|
|
Ian Kent |
62ad96 |
- return 0;
|
|
Ian Kent |
62ad96 |
+ len = strlen(root);
|
|
Ian Kent |
62ad96 |
+ if (root[len - 1] == '/') {
|
|
Ian Kent |
62ad96 |
+ realpath = alloca(strlen(ap->path) + name_len + 2);
|
|
Ian Kent |
62ad96 |
+ mountpoint = alloca(len + 1);
|
|
Ian Kent |
62ad96 |
+ strcpy(realpath, ap->path);
|
|
Ian Kent |
62ad96 |
+ strcat(realpath, "/");
|
|
Ian Kent |
62ad96 |
+ strcat(realpath, name);
|
|
Ian Kent |
62ad96 |
+ len--;
|
|
Ian Kent |
62ad96 |
+ strncpy(mountpoint, root, len);
|
|
Ian Kent |
62ad96 |
+ mountpoint[len] = '\0';
|
|
Ian Kent |
62ad96 |
+ } else if (*name == '/') {
|
|
Ian Kent |
62ad96 |
+ realpath = alloca(name_len + 1);
|
|
Ian Kent |
62ad96 |
+ mountpoint = alloca(len + 1);
|
|
Ian Kent |
62ad96 |
+ strcpy(mountpoint, root);
|
|
Ian Kent |
62ad96 |
+ strcpy(realpath, name);
|
|
Ian Kent |
62ad96 |
+ } else {
|
|
Ian Kent |
62ad96 |
+ realpath = alloca(len + name_len + 2);
|
|
Ian Kent |
62ad96 |
+ mountpoint = alloca(len + name_len + 2);
|
|
Ian Kent |
62ad96 |
+ strcpy(mountpoint, root);
|
|
Ian Kent |
62ad96 |
+ strcat(mountpoint, "/");
|
|
Ian Kent |
62ad96 |
+ strcpy(realpath, mountpoint);
|
|
Ian Kent |
62ad96 |
+ strcat(mountpoint, name);
|
|
Ian Kent |
62ad96 |
+ strcat(realpath, name);
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
options = NULL;
|
|
Ian Kent |
62ad96 |
@@ -136,12 +136,12 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
debug(ap->logopt,
|
|
Ian Kent |
62ad96 |
- MODPREFIX "fullpath=%s what=%s options=%s",
|
|
Ian Kent |
62ad96 |
- fullpath, what, options);
|
|
Ian Kent |
62ad96 |
+ MODPREFIX "mountpoint=%s what=%s options=%s",
|
|
Ian Kent |
62ad96 |
+ mountpoint, what, options);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
master = ap->entry->master;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- entry = master_new_mapent(master, fullpath, ap->entry->age);
|
|
Ian Kent |
62ad96 |
+ entry = master_new_mapent(master, realpath, ap->entry->age);
|
|
Ian Kent |
62ad96 |
if (!entry) {
|
|
Ian Kent |
62ad96 |
error(ap->logopt,
|
|
Ian Kent |
62ad96 |
MODPREFIX "failed to malloc master_mapent struct");
|
|
Ian Kent |
62ad96 |
@@ -228,6 +228,7 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
suc.ap = nap;
|
|
Ian Kent |
62ad96 |
+ suc.root = mountpoint;
|
|
Ian Kent |
62ad96 |
suc.done = 0;
|
|
Ian Kent |
62ad96 |
suc.status = 0;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
@@ -235,7 +236,7 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
crit(ap->logopt,
|
|
Ian Kent |
62ad96 |
MODPREFIX
|
|
Ian Kent |
62ad96 |
"failed to create mount handler thread for %s",
|
|
Ian Kent |
62ad96 |
- fullpath);
|
|
Ian Kent |
62ad96 |
+ realpath);
|
|
Ian Kent |
62ad96 |
handle_mounts_startup_cond_destroy(&suc);
|
|
Ian Kent |
62ad96 |
mounts_mutex_unlock(ap);
|
|
Ian Kent |
62ad96 |
master_free_map_source(source, 1);
|
|
Ian Kent |
62ad96 |
@@ -256,7 +257,7 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
if (suc.status) {
|
|
Ian Kent |
62ad96 |
crit(ap->logopt,
|
|
Ian Kent |
62ad96 |
- MODPREFIX "failed to create submount for %s", fullpath);
|
|
Ian Kent |
62ad96 |
+ MODPREFIX "failed to create submount for %s", realpath);
|
|
Ian Kent |
62ad96 |
handle_mounts_startup_cond_destroy(&suc);
|
|
Ian Kent |
62ad96 |
mounts_mutex_unlock(ap);
|
|
Ian Kent |
62ad96 |
master_free_map_source(source, 1);
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/modules/mount_bind.c
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/modules/mount_bind.c
|
|
Ian Kent |
62ad96 |
@@ -74,34 +74,24 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
char *fullpath;
|
|
Ian Kent |
62ad96 |
char buf[MAX_ERR_BUF];
|
|
Ian Kent |
62ad96 |
int err;
|
|
Ian Kent |
62ad96 |
- int i, rlen;
|
|
Ian Kent |
62ad96 |
+ int i, len;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
/* Root offset of multi-mount */
|
|
Ian Kent |
62ad96 |
- if (*name == '/' && name_len == 1) {
|
|
Ian Kent |
62ad96 |
- rlen = strlen(root);
|
|
Ian Kent |
62ad96 |
- name_len = 0;
|
|
Ian Kent |
62ad96 |
+ len = strlen(root);
|
|
Ian Kent |
62ad96 |
+ if (root[len - 1] == '/') {
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(len);
|
|
Ian Kent |
62ad96 |
+ len = snprintf(fullpath, len, "%s", root);
|
|
Ian Kent |
62ad96 |
/* Direct mount name is absolute path so don't use root */
|
|
Ian Kent |
62ad96 |
- } else if (*name == '/')
|
|
Ian Kent |
62ad96 |
- rlen = 0;
|
|
Ian Kent |
62ad96 |
- else
|
|
Ian Kent |
62ad96 |
- rlen = strlen(root);
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- fullpath = alloca(rlen + name_len + 2);
|
|
Ian Kent |
62ad96 |
- if (!fullpath) {
|
|
Ian Kent |
62ad96 |
- char *estr = strerror_r(errno, buf, MAX_ERR_BUF);
|
|
Ian Kent |
62ad96 |
- logerr(MODPREFIX "alloca: %s", estr);
|
|
Ian Kent |
62ad96 |
- return 1;
|
|
Ian Kent |
62ad96 |
+ } else if (*name == '/') {
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(len + 1);
|
|
Ian Kent |
62ad96 |
+ len = sprintf(fullpath, "%s", root);
|
|
Ian Kent |
62ad96 |
+ } else {
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(len + name_len + 2);
|
|
Ian Kent |
62ad96 |
+ len = sprintf(fullpath, "%s/%s", root, name);
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
+ fullpath[len] = '\0';
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- if (name_len) {
|
|
Ian Kent |
62ad96 |
- if (rlen)
|
|
Ian Kent |
62ad96 |
- sprintf(fullpath, "%s/%s", root, name);
|
|
Ian Kent |
62ad96 |
- else
|
|
Ian Kent |
62ad96 |
- sprintf(fullpath, "%s", name);
|
|
Ian Kent |
62ad96 |
- } else
|
|
Ian Kent |
62ad96 |
- sprintf(fullpath, "%s", root);
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- i = strlen(fullpath);
|
|
Ian Kent |
62ad96 |
+ i = len;
|
|
Ian Kent |
62ad96 |
while (--i > 0 && fullpath[i] == '/')
|
|
Ian Kent |
62ad96 |
fullpath[i] = '\0';
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
@@ -125,13 +115,6 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
if (!status)
|
|
Ian Kent |
62ad96 |
existed = 0;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- if (is_mounted(_PATH_MOUNTED, fullpath, MNTS_REAL)) {
|
|
Ian Kent |
62ad96 |
- error(ap->logopt,
|
|
Ian Kent |
62ad96 |
- MODPREFIX "warning: %s is already mounted",
|
|
Ian Kent |
62ad96 |
- fullpath);
|
|
Ian Kent |
62ad96 |
- return 0;
|
|
Ian Kent |
62ad96 |
- }
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
debug(ap->logopt,
|
|
Ian Kent |
62ad96 |
MODPREFIX
|
|
Ian Kent |
62ad96 |
"calling mount --bind " SLOPPY " -o %s %s %s",
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/modules/mount_changer.c
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/modules/mount_changer.c
|
|
Ian Kent |
62ad96 |
@@ -49,34 +49,24 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
char *fullpath;
|
|
Ian Kent |
62ad96 |
char buf[MAX_ERR_BUF];
|
|
Ian Kent |
62ad96 |
int err;
|
|
Ian Kent |
62ad96 |
- int rlen, status, existed = 1;
|
|
Ian Kent |
62ad96 |
+ int len, status, existed = 1;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
fstype = "iso9660";
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
/* Root offset of multi-mount */
|
|
Ian Kent |
62ad96 |
- if (*name == '/' && name_len == 1) {
|
|
Ian Kent |
62ad96 |
- rlen = strlen(root);
|
|
Ian Kent |
62ad96 |
- name_len = 0;
|
|
Ian Kent |
62ad96 |
+ len = strlen(root);
|
|
Ian Kent |
62ad96 |
+ if (root[len - 1] == '/') {
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(len);
|
|
Ian Kent |
62ad96 |
+ len = snprintf(fullpath, len, "%s", root);
|
|
Ian Kent |
62ad96 |
/* Direct mount name is absolute path so don't use root */
|
|
Ian Kent |
62ad96 |
- } else if (*name == '/')
|
|
Ian Kent |
62ad96 |
- rlen = 0;
|
|
Ian Kent |
62ad96 |
- else
|
|
Ian Kent |
62ad96 |
- rlen = strlen(root);
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- fullpath = alloca(rlen + name_len + 2);
|
|
Ian Kent |
62ad96 |
- if (!fullpath) {
|
|
Ian Kent |
62ad96 |
- char *estr = strerror_r(errno, buf, MAX_ERR_BUF);
|
|
Ian Kent |
62ad96 |
- logerr(MODPREFIX "alloca: %s", estr);
|
|
Ian Kent |
62ad96 |
- return 1;
|
|
Ian Kent |
62ad96 |
+ } else if (*name == '/') {
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(len + 1);
|
|
Ian Kent |
62ad96 |
+ len = sprintf(fullpath, "%s", root);
|
|
Ian Kent |
62ad96 |
+ } else {
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(len + name_len + 2);
|
|
Ian Kent |
62ad96 |
+ len = sprintf(fullpath, "%s/%s", root, name);
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- if (name_len) {
|
|
Ian Kent |
62ad96 |
- if (rlen)
|
|
Ian Kent |
62ad96 |
- sprintf(fullpath, "%s/%s", root, name);
|
|
Ian Kent |
62ad96 |
- else
|
|
Ian Kent |
62ad96 |
- sprintf(fullpath, "%s", name);
|
|
Ian Kent |
62ad96 |
- } else
|
|
Ian Kent |
62ad96 |
- sprintf(fullpath, "%s", root);
|
|
Ian Kent |
62ad96 |
+ fullpath[len] = '\0';
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
debug(ap->logopt, MODPREFIX "calling umount %s", what);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/modules/mount_ext2.c
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/modules/mount_ext2.c
|
|
Ian Kent |
62ad96 |
@@ -43,32 +43,22 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
const char *p, *p1;
|
|
Ian Kent |
62ad96 |
int err, ro = 0;
|
|
Ian Kent |
62ad96 |
const char *fsck_prog;
|
|
Ian Kent |
62ad96 |
- int rlen, status, existed = 1;
|
|
Ian Kent |
62ad96 |
+ int len, status, existed = 1;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
/* Root offset of multi-mount */
|
|
Ian Kent |
62ad96 |
- if (*name == '/' && name_len == 1) {
|
|
Ian Kent |
62ad96 |
- rlen = strlen(root);
|
|
Ian Kent |
62ad96 |
- name_len = 0;
|
|
Ian Kent |
62ad96 |
+ len = strlen(root);
|
|
Ian Kent |
62ad96 |
+ if (root[len - 1] == '/') {
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(len);
|
|
Ian Kent |
62ad96 |
+ len = snprintf(fullpath, len, "%s", root);
|
|
Ian Kent |
62ad96 |
/* Direct mount name is absolute path so don't use root */
|
|
Ian Kent |
62ad96 |
- } else if (*name == '/')
|
|
Ian Kent |
62ad96 |
- rlen = 0;
|
|
Ian Kent |
62ad96 |
- else
|
|
Ian Kent |
62ad96 |
- rlen = strlen(root);
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- fullpath = alloca(rlen + name_len + 2);
|
|
Ian Kent |
62ad96 |
- if (!fullpath) {
|
|
Ian Kent |
62ad96 |
- char *estr = strerror_r(errno, buf, MAX_ERR_BUF);
|
|
Ian Kent |
62ad96 |
- logerr(MODPREFIX "alloca: %s", estr);
|
|
Ian Kent |
62ad96 |
- return 1;
|
|
Ian Kent |
62ad96 |
+ } else if (*name == '/') {
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(len + 1);
|
|
Ian Kent |
62ad96 |
+ len = sprintf(fullpath, "%s", root);
|
|
Ian Kent |
62ad96 |
+ } else {
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(len + name_len + 2);
|
|
Ian Kent |
62ad96 |
+ len = sprintf(fullpath, "%s/%s", root, name);
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- if (name_len) {
|
|
Ian Kent |
62ad96 |
- if (rlen)
|
|
Ian Kent |
62ad96 |
- sprintf(fullpath, "%s/%s", root, name);
|
|
Ian Kent |
62ad96 |
- else
|
|
Ian Kent |
62ad96 |
- sprintf(fullpath, "%s", name);
|
|
Ian Kent |
62ad96 |
- } else
|
|
Ian Kent |
62ad96 |
- sprintf(fullpath, "%s", root);
|
|
Ian Kent |
62ad96 |
+ fullpath[len] = '\0';
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
debug(ap->logopt, MODPREFIX "calling mkdir_path %s", fullpath);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
@@ -83,12 +73,6 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
if (!status)
|
|
Ian Kent |
62ad96 |
existed = 0;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- if (is_mounted(_PATH_MOUNTED, fullpath, MNTS_REAL)) {
|
|
Ian Kent |
62ad96 |
- error(ap->logopt,
|
|
Ian Kent |
62ad96 |
- MODPREFIX "warning: %s is already mounted", fullpath);
|
|
Ian Kent |
62ad96 |
- return 0;
|
|
Ian Kent |
62ad96 |
- }
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
if (options && options[0]) {
|
|
Ian Kent |
62ad96 |
for (p = options; (p1 = strchr(p, ',')); p = p1)
|
|
Ian Kent |
62ad96 |
if (!strncmp(p, "ro", p1 - p) && ++p1 - p == sizeof("ro"))
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/modules/mount_generic.c
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/modules/mount_generic.c
|
|
Ian Kent |
62ad96 |
@@ -42,32 +42,22 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
char *fullpath;
|
|
Ian Kent |
62ad96 |
char buf[MAX_ERR_BUF];
|
|
Ian Kent |
62ad96 |
int err;
|
|
Ian Kent |
62ad96 |
- int rlen, status, existed = 1;
|
|
Ian Kent |
62ad96 |
+ int len, status, existed = 1;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
/* Root offset of multi-mount */
|
|
Ian Kent |
62ad96 |
- if (*name == '/' && name_len == 1) {
|
|
Ian Kent |
62ad96 |
- rlen = strlen(root);
|
|
Ian Kent |
62ad96 |
- name_len = 0;
|
|
Ian Kent |
62ad96 |
+ len = strlen(root);
|
|
Ian Kent |
62ad96 |
+ if (root[len - 1] == '/') {
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(len);
|
|
Ian Kent |
62ad96 |
+ len = snprintf(fullpath, len, "%s", root);
|
|
Ian Kent |
62ad96 |
/* Direct mount name is absolute path so don't use root */
|
|
Ian Kent |
62ad96 |
- } else if (*name == '/')
|
|
Ian Kent |
62ad96 |
- rlen = 0;
|
|
Ian Kent |
62ad96 |
- else
|
|
Ian Kent |
62ad96 |
- rlen = strlen(root);
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- fullpath = alloca(rlen + name_len + 2);
|
|
Ian Kent |
62ad96 |
- if (!fullpath) {
|
|
Ian Kent |
62ad96 |
- char *estr = strerror_r(errno, buf, MAX_ERR_BUF);
|
|
Ian Kent |
62ad96 |
- logerr(MODPREFIX "alloca: %s", estr);
|
|
Ian Kent |
62ad96 |
- return 1;
|
|
Ian Kent |
62ad96 |
+ } else if (*name == '/') {
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(len + 1);
|
|
Ian Kent |
62ad96 |
+ len = sprintf(fullpath, "%s", root);
|
|
Ian Kent |
62ad96 |
+ } else {
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(len + name_len + 2);
|
|
Ian Kent |
62ad96 |
+ len = sprintf(fullpath, "%s/%s", root, name);
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- if (name_len) {
|
|
Ian Kent |
62ad96 |
- if (rlen)
|
|
Ian Kent |
62ad96 |
- sprintf(fullpath, "%s/%s", root, name);
|
|
Ian Kent |
62ad96 |
- else
|
|
Ian Kent |
62ad96 |
- sprintf(fullpath, "%s", name);
|
|
Ian Kent |
62ad96 |
- } else
|
|
Ian Kent |
62ad96 |
- sprintf(fullpath, "%s", root);
|
|
Ian Kent |
62ad96 |
+ fullpath[len] = '\0';
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
debug(ap->logopt, MODPREFIX "calling mkdir_path %s", fullpath);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
@@ -82,12 +72,6 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
if (!status)
|
|
Ian Kent |
62ad96 |
existed = 0;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- if (is_mounted(_PATH_MOUNTED, fullpath, MNTS_REAL)) {
|
|
Ian Kent |
62ad96 |
- error(ap->logopt,
|
|
Ian Kent |
62ad96 |
- MODPREFIX "warning: %s is already mounted", fullpath);
|
|
Ian Kent |
62ad96 |
- return 0;
|
|
Ian Kent |
62ad96 |
- }
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
if (options && options[0]) {
|
|
Ian Kent |
62ad96 |
debug(ap->logopt,
|
|
Ian Kent |
62ad96 |
MODPREFIX "calling mount -t %s " SLOPPY "-o %s %s %s",
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/modules/mount_nfs.c
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/modules/mount_nfs.c
|
|
Ian Kent |
62ad96 |
@@ -64,7 +64,7 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
struct host *this, *hosts = NULL;
|
|
Ian Kent |
62ad96 |
unsigned int vers;
|
|
Ian Kent |
62ad96 |
char *nfsoptions = NULL;
|
|
Ian Kent |
62ad96 |
- int len, rlen, status, err, existed = 1;
|
|
Ian Kent |
62ad96 |
+ int len, status, err, existed = 1;
|
|
Ian Kent |
62ad96 |
int nosymlink = 0;
|
|
Ian Kent |
62ad96 |
int ro = 0; /* Set if mount bind should be read-only */
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
@@ -146,30 +146,18 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
/* Construct and perhaps create mount point directory */
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
/* Root offset of multi-mount */
|
|
Ian Kent |
62ad96 |
- if (*name == '/' && name_len == 1) {
|
|
Ian Kent |
62ad96 |
- rlen = strlen(root);
|
|
Ian Kent |
62ad96 |
- name_len = 0;
|
|
Ian Kent |
62ad96 |
+ len = strlen(root);
|
|
Ian Kent |
62ad96 |
+ if (root[len - 1] == '/') {
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(len);
|
|
Ian Kent |
62ad96 |
+ len = snprintf(fullpath, len, "%s", root);
|
|
Ian Kent |
62ad96 |
/* Direct mount name is absolute path so don't use root */
|
|
Ian Kent |
62ad96 |
- } else if (*name == '/')
|
|
Ian Kent |
62ad96 |
- rlen = 0;
|
|
Ian Kent |
62ad96 |
- else
|
|
Ian Kent |
62ad96 |
- rlen = strlen(root);
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- fullpath = alloca(rlen + name_len + 2);
|
|
Ian Kent |
62ad96 |
- if (!fullpath) {
|
|
Ian Kent |
62ad96 |
- char *estr = strerror_r(errno, buf, MAX_ERR_BUF);
|
|
Ian Kent |
62ad96 |
- logerr(MODPREFIX "alloca: %s", estr);
|
|
Ian Kent |
62ad96 |
- free_host_list(&hosts);
|
|
Ian Kent |
62ad96 |
- return 1;
|
|
Ian Kent |
62ad96 |
- }
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- if (name_len) {
|
|
Ian Kent |
62ad96 |
- if (rlen)
|
|
Ian Kent |
62ad96 |
- len = sprintf(fullpath, "%s/%s", root, name);
|
|
Ian Kent |
62ad96 |
- else
|
|
Ian Kent |
62ad96 |
- len = sprintf(fullpath, "%s", name);
|
|
Ian Kent |
62ad96 |
- } else
|
|
Ian Kent |
62ad96 |
+ } else if (*name == '/') {
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(len + 1);
|
|
Ian Kent |
62ad96 |
len = sprintf(fullpath, "%s", root);
|
|
Ian Kent |
62ad96 |
+ } else {
|
|
Ian Kent |
62ad96 |
+ fullpath = alloca(len + name_len + 2);
|
|
Ian Kent |
62ad96 |
+ len = sprintf(fullpath, "%s/%s", root, name);
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
fullpath[len] = '\0';
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
debug(ap->logopt, MODPREFIX "calling mkdir_path %s", fullpath);
|
|
Ian Kent |
62ad96 |
@@ -189,13 +177,6 @@ int mount_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
while (this) {
|
|
Ian Kent |
62ad96 |
char *loc, *port_opt = NULL;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- if (is_mounted(_PATH_MOUNTED, fullpath, MNTS_REAL)) {
|
|
Ian Kent |
62ad96 |
- error(ap->logopt,
|
|
Ian Kent |
62ad96 |
- MODPREFIX
|
|
Ian Kent |
62ad96 |
- "warning: %s is already mounted", fullpath);
|
|
Ian Kent |
62ad96 |
- break;
|
|
Ian Kent |
62ad96 |
- }
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
/*
|
|
Ian Kent |
62ad96 |
* If the "port" option is specified, then we don't want
|
|
Ian Kent |
62ad96 |
* a bind mount. Use the "port" option if you want to
|
|
Ian Kent |
62ad96 |
--- autofs-5.0.3.orig/modules/parse_sun.c
|
|
Ian Kent |
62ad96 |
+++ autofs-5.0.3/modules/parse_sun.c
|
|
Ian Kent |
62ad96 |
@@ -31,12 +31,18 @@
|
|
Ian Kent |
62ad96 |
#include <sys/vfs.h>
|
|
Ian Kent |
62ad96 |
#include <sys/utsname.h>
|
|
Ian Kent |
62ad96 |
#include <netinet/in.h>
|
|
Ian Kent |
62ad96 |
+#include <sys/mount.h>
|
|
Ian Kent |
62ad96 |
+#include <linux/fs.h>
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
#define MODULE_PARSE
|
|
Ian Kent |
62ad96 |
#include "automount.h"
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
#define MODPREFIX "parse(sun): "
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
+#define MOUNT_MOVE_NONE 0x00
|
|
Ian Kent |
62ad96 |
+#define MOUNT_MOVE_AUTOFS 0x01
|
|
Ian Kent |
62ad96 |
+#define MOUNT_MOVE_OTHER 0x02
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
int parse_version = AUTOFS_PARSE_VERSION; /* Required by protocol */
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
static struct mount_mod *mount_nfs = NULL;
|
|
Ian Kent |
62ad96 |
@@ -67,6 +73,7 @@ static struct parse_context default_cont
|
|
Ian Kent |
62ad96 |
1 /* Do slashify_colons */
|
|
Ian Kent |
62ad96 |
};
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
+int destroy_logpri_fifo(struct autofs_point *ap);
|
|
Ian Kent |
62ad96 |
static char *concat_options(char *left, char *right);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
/* Free all storage associated with this context */
|
|
Ian Kent |
62ad96 |
@@ -756,8 +763,10 @@ add_offset_entry(struct autofs_point *ap
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
p_len = strlen(path);
|
|
Ian Kent |
62ad96 |
/* Trailing '/' causes us pain */
|
|
Ian Kent |
62ad96 |
- if (p_len > 1 && path[p_len - 1] == '/')
|
|
Ian Kent |
62ad96 |
- p_len--;
|
|
Ian Kent |
62ad96 |
+ if (p_len > 1) {
|
|
Ian Kent |
62ad96 |
+ while (p_len > 1 && path[p_len - 1] == '/')
|
|
Ian Kent |
62ad96 |
+ p_len--;
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
m_key_len = m_root_len + p_len;
|
|
Ian Kent |
62ad96 |
if (m_key_len > PATH_MAX) {
|
|
Ian Kent |
62ad96 |
error(ap->logopt, MODPREFIX "multi mount key too long");
|
|
Ian Kent |
62ad96 |
@@ -961,53 +970,318 @@ static int parse_mapent(const char *ent,
|
|
Ian Kent |
62ad96 |
return (p - ent);
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
-static int mount_subtree_offsets(struct autofs_point *ap, struct mapent_cache *mc, struct mapent *me)
|
|
Ian Kent |
62ad96 |
+static int move_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
+ const char *mm_tmp_root, const char *mm_root,
|
|
Ian Kent |
62ad96 |
+ unsigned int move)
|
|
Ian Kent |
62ad96 |
{
|
|
Ian Kent |
62ad96 |
- struct mapent *mm;
|
|
Ian Kent |
62ad96 |
- char *m_key;
|
|
Ian Kent |
62ad96 |
- int ret, start;
|
|
Ian Kent |
62ad96 |
- char *base, *m_root;
|
|
Ian Kent |
62ad96 |
char buf[MAX_ERR_BUF];
|
|
Ian Kent |
62ad96 |
+ int err;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- mm = me->multi;
|
|
Ian Kent |
62ad96 |
+ if (move == MOUNT_MOVE_NONE)
|
|
Ian Kent |
62ad96 |
+ return 1;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ err = mkdir_path(mm_root, 0555);
|
|
Ian Kent |
62ad96 |
+ if (err < 0 && errno != EEXIST) {
|
|
Ian Kent |
62ad96 |
+ error(ap->logopt,
|
|
Ian Kent |
62ad96 |
+ "failed to create move target mount point %s", mm_root);
|
|
Ian Kent |
62ad96 |
+ return 0;
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- if (!mm)
|
|
Ian Kent |
62ad96 |
+ if (move == MOUNT_MOVE_AUTOFS)
|
|
Ian Kent |
62ad96 |
+ err = mount(mm_tmp_root, mm_root, NULL, MS_MOVE, NULL);
|
|
Ian Kent |
62ad96 |
+ else
|
|
Ian Kent |
62ad96 |
+ err = spawn_mount(ap->logopt,
|
|
Ian Kent |
62ad96 |
+ "--move", mm_tmp_root, mm_root, NULL);
|
|
Ian Kent |
62ad96 |
+ if (err) {
|
|
Ian Kent |
62ad96 |
+ char *estr = strerror_r(errno, buf, MAX_ERR_BUF);
|
|
Ian Kent |
62ad96 |
+ error(ap->logopt,
|
|
Ian Kent |
62ad96 |
+ "failed to move mount from %s to %s: %s",
|
|
Ian Kent |
62ad96 |
+ mm_tmp_root, mm_root, estr);
|
|
Ian Kent |
62ad96 |
return 0;
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ debug(ap->logopt,
|
|
Ian Kent |
62ad96 |
+ "moved mount tree from %s to %s", mm_tmp_root, mm_root);
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ return 1;
|
|
Ian Kent |
62ad96 |
+}
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+static void cleanup_multi_root(struct autofs_point *ap, const char *root,
|
|
Ian Kent |
62ad96 |
+ const char *path, unsigned int move)
|
|
Ian Kent |
62ad96 |
+{
|
|
Ian Kent |
62ad96 |
+ if (move == MOUNT_MOVE_NONE)
|
|
Ian Kent |
62ad96 |
+ return;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ if (move == MOUNT_MOVE_OTHER)
|
|
Ian Kent |
62ad96 |
+ spawn_umount(ap->logopt, root, NULL);
|
|
Ian Kent |
62ad96 |
+ else {
|
|
Ian Kent |
62ad96 |
+ struct autofs_point *submount;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ mounts_mutex_lock(ap);
|
|
Ian Kent |
62ad96 |
+ submount = __master_find_submount(ap, path);
|
|
Ian Kent |
62ad96 |
+ if (!submount) {
|
|
Ian Kent |
62ad96 |
+ mounts_mutex_unlock(ap);
|
|
Ian Kent |
62ad96 |
+ return;
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ alarm_delete(submount);
|
|
Ian Kent |
62ad96 |
+ st_remove_tasks(submount);
|
|
Ian Kent |
62ad96 |
+ st_wait_state(submount, ST_READY);
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ submount->parent->submnt_count--;
|
|
Ian Kent |
62ad96 |
+ list_del_init(&submount->mounts);
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ ioctl(submount->ioctlfd, AUTOFS_IOC_CATATONIC, 0);
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ mounts_mutex_unlock(ap);
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ if (submount->thid) {
|
|
Ian Kent |
62ad96 |
+ pthread_cancel(submount->thid);
|
|
Ian Kent |
62ad96 |
+ close_mount_fds(submount);
|
|
Ian Kent |
62ad96 |
+ umount(root);
|
|
Ian Kent |
62ad96 |
+ destroy_logpri_fifo(submount);
|
|
Ian Kent |
62ad96 |
+ master_free_mapent_sources(submount->entry, 1);
|
|
Ian Kent |
62ad96 |
+ master_free_mapent(ap->entry);
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+ return;
|
|
Ian Kent |
62ad96 |
+}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- cache_multi_lock(me->parent);
|
|
Ian Kent |
62ad96 |
+static void cleanup_multi_triggers(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
+ struct mapent *me, const char *root, int start,
|
|
Ian Kent |
62ad96 |
+ const char *base)
|
|
Ian Kent |
62ad96 |
+{
|
|
Ian Kent |
62ad96 |
+ char path[PATH_MAX + 1];
|
|
Ian Kent |
62ad96 |
+ char offset[PATH_MAX + 1];
|
|
Ian Kent |
62ad96 |
+ char *poffset = offset;
|
|
Ian Kent |
62ad96 |
+ struct mapent *oe;
|
|
Ian Kent |
62ad96 |
+ struct list_head *mm_root, *pos;
|
|
Ian Kent |
62ad96 |
+ const char o_root[] = "/";
|
|
Ian Kent |
62ad96 |
+ const char *mm_base;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- m_key = mm->key;
|
|
Ian Kent |
62ad96 |
+ mm_root = &me->multi->multi_list;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- if (*m_key == '/') {
|
|
Ian Kent |
62ad96 |
- m_root = m_key;
|
|
Ian Kent |
62ad96 |
- start = strlen(m_key);
|
|
Ian Kent |
62ad96 |
+ if (!base)
|
|
Ian Kent |
62ad96 |
+ mm_base = o_root;
|
|
Ian Kent |
62ad96 |
+ else
|
|
Ian Kent |
62ad96 |
+ mm_base = base;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ pos = NULL;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ /* Make sure "none" of the offsets have an active mount. */
|
|
Ian Kent |
62ad96 |
+ while ((poffset = cache_get_offset(mm_base, poffset, start, mm_root, &pos))) {
|
|
Ian Kent |
62ad96 |
+ oe = cache_lookup_offset(mm_base, poffset, start, &me->multi_list);
|
|
Ian Kent |
62ad96 |
+ /* root offset is a special case */
|
|
Ian Kent |
62ad96 |
+ if (!oe || !oe->mapent || (strlen(oe->key) - start) == 1)
|
|
Ian Kent |
62ad96 |
+ continue;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ strcpy(path, root);
|
|
Ian Kent |
62ad96 |
+ strcat(path, poffset);
|
|
Ian Kent |
62ad96 |
+ if (umount(path)) {
|
|
Ian Kent |
62ad96 |
+ error(ap->logopt, "error recovering from mount fail");
|
|
Ian Kent |
62ad96 |
+ error(ap->logopt, "cannot umount offset %s", path);
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ return;
|
|
Ian Kent |
62ad96 |
+}
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+static int check_fstype_autofs_option(const char *options)
|
|
Ian Kent |
62ad96 |
+{
|
|
Ian Kent |
62ad96 |
+ char *tok, *tokbuf;
|
|
Ian Kent |
62ad96 |
+ int found;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ /*
|
|
Ian Kent |
62ad96 |
+ * Look for fstype= in options and return true if
|
|
Ian Kent |
62ad96 |
+ * the last occurrence is fstype=autofs.
|
|
Ian Kent |
62ad96 |
+ */
|
|
Ian Kent |
62ad96 |
+ found = 0;
|
|
Ian Kent |
62ad96 |
+ tokbuf = alloca(strlen(options) + 2);
|
|
Ian Kent |
62ad96 |
+ strcpy(tokbuf, options);
|
|
Ian Kent |
62ad96 |
+ tok = strtok_r(tokbuf, ",", &tokbuf);
|
|
Ian Kent |
62ad96 |
+ if (tok) {
|
|
Ian Kent |
62ad96 |
+ do {
|
|
Ian Kent |
62ad96 |
+ if (strstr(tok, "fstype=")) {
|
|
Ian Kent |
62ad96 |
+ if (strstr(tok, "autofs"))
|
|
Ian Kent |
62ad96 |
+ found = 1;
|
|
Ian Kent |
62ad96 |
+ else
|
|
Ian Kent |
62ad96 |
+ found = 0;
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+ } while ((tok = strtok_r(NULL, ",", &tokbuf)));
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ return found;
|
|
Ian Kent |
62ad96 |
+}
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+static int mount_subtree(struct autofs_point *ap, struct mapent *me,
|
|
Ian Kent |
62ad96 |
+ const char *name, char *loc, char *options, void *ctxt)
|
|
Ian Kent |
62ad96 |
+{
|
|
Ian Kent |
62ad96 |
+ struct mapent *mm;
|
|
Ian Kent |
62ad96 |
+ struct mapent *ro;
|
|
Ian Kent |
62ad96 |
+ char t_dir[] = "/tmp/autoXXXXXX";
|
|
Ian Kent |
62ad96 |
+ char *mm_root, *mm_base, *mm_key;
|
|
Ian Kent |
62ad96 |
+ const char *mm_tmp_root, *target;
|
|
Ian Kent |
62ad96 |
+ unsigned int mm_tmp_root_len;
|
|
Ian Kent |
62ad96 |
+ int start, ret = 0, rv;
|
|
Ian Kent |
62ad96 |
+ unsigned int move;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ rv = 0;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ if (!me || !me->multi) {
|
|
Ian Kent |
62ad96 |
+ int loclen = strlen(loc);
|
|
Ian Kent |
62ad96 |
+ int namelen = strlen(name);
|
|
Ian Kent |
62ad96 |
+ const char *root = ap->path;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ if (!strcmp(ap->path, "/-"))
|
|
Ian Kent |
62ad96 |
+ root = name;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ rv = sun_mount(ap, root, name, namelen, loc, loclen, options, ctxt);
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ goto done;
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ mm = me->multi;
|
|
Ian Kent |
62ad96 |
+ mm_key = mm->key;
|
|
Ian Kent |
62ad96 |
+ move = MOUNT_MOVE_NONE;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ if (*mm_key == '/') {
|
|
Ian Kent |
62ad96 |
+ mm_root = mm_key;
|
|
Ian Kent |
62ad96 |
+ start = strlen(mm_key);
|
|
Ian Kent |
62ad96 |
} else {
|
|
Ian Kent |
62ad96 |
- start = strlen(ap->path) + strlen(m_key) + 1;
|
|
Ian Kent |
62ad96 |
- m_root = alloca(start + 1);
|
|
Ian Kent |
62ad96 |
- if (!m_root) {
|
|
Ian Kent |
62ad96 |
- char *estr;
|
|
Ian Kent |
62ad96 |
- cache_multi_unlock(me->parent);
|
|
Ian Kent |
62ad96 |
- estr = strerror_r(errno, buf, MAX_ERR_BUF);
|
|
Ian Kent |
62ad96 |
- error(ap->logopt, MODPREFIX "alloca: %s", estr);
|
|
Ian Kent |
62ad96 |
- return -1;
|
|
Ian Kent |
62ad96 |
- }
|
|
Ian Kent |
62ad96 |
- strcpy(m_root, ap->path);
|
|
Ian Kent |
62ad96 |
- strcat(m_root, "/");
|
|
Ian Kent |
62ad96 |
- strcat(m_root, m_key);
|
|
Ian Kent |
62ad96 |
- }
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- base = &me->key[start];
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- ret = mount_multi_triggers(ap, m_root, me->multi, base);
|
|
Ian Kent |
62ad96 |
- if (ret == -1) {
|
|
Ian Kent |
62ad96 |
- cache_multi_unlock(me->parent);
|
|
Ian Kent |
62ad96 |
- error(ap->logopt, MODPREFIX "failed to mount offset triggers");
|
|
Ian Kent |
62ad96 |
- return -1;
|
|
Ian Kent |
62ad96 |
+ start = strlen(ap->path) + strlen(mm_key) + 1;
|
|
Ian Kent |
62ad96 |
+ mm_root = alloca(start + 3);
|
|
Ian Kent |
62ad96 |
+ strcpy(mm_root, ap->path);
|
|
Ian Kent |
62ad96 |
+ strcat(mm_root, "/");
|
|
Ian Kent |
62ad96 |
+ strcat(mm_root, mm_key);
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- cache_multi_unlock(me->parent);
|
|
Ian Kent |
62ad96 |
+ mm_tmp_root = mkdtemp(t_dir);
|
|
Ian Kent |
62ad96 |
+ if (!mm_tmp_root)
|
|
Ian Kent |
62ad96 |
+ return 1;
|
|
Ian Kent |
62ad96 |
+ mm_tmp_root_len = strlen(mm_tmp_root);
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ if (me == me->multi) {
|
|
Ian Kent |
62ad96 |
+ /* name = NULL */
|
|
Ian Kent |
62ad96 |
+ /* destination = mm_root */
|
|
Ian Kent |
62ad96 |
+ target = mm_root;
|
|
Ian Kent |
62ad96 |
+ mm_base = "/";
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- return ret;
|
|
Ian Kent |
62ad96 |
+ /* Mount root offset if it exists */
|
|
Ian Kent |
62ad96 |
+ ro = cache_lookup_offset(mm_base, mm_base, strlen(mm_root), &me->multi_list);
|
|
Ian Kent |
62ad96 |
+ if (ro) {
|
|
Ian Kent |
62ad96 |
+ char *myoptions, *ro_loc, *tmp;
|
|
Ian Kent |
62ad96 |
+ int namelen = name ? strlen(name) : 0;
|
|
Ian Kent |
62ad96 |
+ const char *root;
|
|
Ian Kent |
62ad96 |
+ int ro_len;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ rv = parse_mapent(ro->mapent,
|
|
Ian Kent |
62ad96 |
+ options, &myoptions, &ro_loc, ap->logopt);
|
|
Ian Kent |
62ad96 |
+ if (!rv) {
|
|
Ian Kent |
62ad96 |
+ warn(ap->logopt,
|
|
Ian Kent |
62ad96 |
+ MODPREFIX "failed to parse root offset");
|
|
Ian Kent |
62ad96 |
+ cache_delete_offset_list(me->mc, name);
|
|
Ian Kent |
62ad96 |
+ rmdir(mm_tmp_root);
|
|
Ian Kent |
62ad96 |
+ return 1;
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+ ro_len = strlen(ro_loc);
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ move = MOUNT_MOVE_OTHER;
|
|
Ian Kent |
62ad96 |
+ if (check_fstype_autofs_option(myoptions))
|
|
Ian Kent |
62ad96 |
+ move = MOUNT_MOVE_AUTOFS;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ root = mm_tmp_root;
|
|
Ian Kent |
62ad96 |
+ tmp = alloca(mm_tmp_root_len + 1);
|
|
Ian Kent |
62ad96 |
+ strcpy(tmp, mm_tmp_root);
|
|
Ian Kent |
62ad96 |
+ tmp[mm_tmp_root_len] = '/';
|
|
Ian Kent |
62ad96 |
+ tmp[mm_tmp_root_len + 1] = '\0';
|
|
Ian Kent |
62ad96 |
+ root = tmp;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ rv = sun_mount(ap, root, name, namelen, ro_loc, ro_len, myoptions, ctxt);
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ free(myoptions);
|
|
Ian Kent |
62ad96 |
+ free(ro_loc);
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ if (ro && rv == 0) {
|
|
Ian Kent |
62ad96 |
+ ret = mount_multi_triggers(ap, me, mm_tmp_root, start, mm_base);
|
|
Ian Kent |
62ad96 |
+ if (ret == -1) {
|
|
Ian Kent |
62ad96 |
+ error(ap->logopt, MODPREFIX
|
|
Ian Kent |
62ad96 |
+ "failed to mount offset triggers");
|
|
Ian Kent |
62ad96 |
+ cleanup_multi_triggers(ap, me, mm_tmp_root, start, mm_base);
|
|
Ian Kent |
62ad96 |
+ cleanup_multi_root(ap, mm_tmp_root, mm_root, move);
|
|
Ian Kent |
62ad96 |
+ rmdir(mm_tmp_root);
|
|
Ian Kent |
62ad96 |
+ return 1;
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+ } else if (rv <= 0) {
|
|
Ian Kent |
62ad96 |
+ move = MOUNT_MOVE_NONE;
|
|
Ian Kent |
62ad96 |
+ ret = mount_multi_triggers(ap, me, mm_root, start, mm_base);
|
|
Ian Kent |
62ad96 |
+ if (ret == -1) {
|
|
Ian Kent |
62ad96 |
+ error(ap->logopt, MODPREFIX
|
|
Ian Kent |
62ad96 |
+ "failed to mount offset triggers");
|
|
Ian Kent |
62ad96 |
+ cleanup_multi_triggers(ap, me, mm_tmp_root, start, mm_base);
|
|
Ian Kent |
62ad96 |
+ rmdir(mm_tmp_root);
|
|
Ian Kent |
62ad96 |
+ return 1;
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+ } else {
|
|
Ian Kent |
62ad96 |
+ int loclen = strlen(loc);
|
|
Ian Kent |
62ad96 |
+ int namelen = strlen(name);
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ move = MOUNT_MOVE_OTHER;
|
|
Ian Kent |
62ad96 |
+ if (check_fstype_autofs_option(options))
|
|
Ian Kent |
62ad96 |
+ move = MOUNT_MOVE_AUTOFS;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ /* name = mm_root + mm_base */
|
|
Ian Kent |
62ad96 |
+ /* destination = mm_root + mm_base = name */
|
|
Ian Kent |
62ad96 |
+ target = name;
|
|
Ian Kent |
62ad96 |
+ mm_base = &me->key[start];
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ rv = sun_mount(ap, mm_tmp_root, name, namelen, loc, loclen, options, ctxt);
|
|
Ian Kent |
62ad96 |
+ if (rv == 0) {
|
|
Ian Kent |
62ad96 |
+ ret = mount_multi_triggers(ap, me->multi, mm_tmp_root, start, mm_base);
|
|
Ian Kent |
62ad96 |
+ if (ret == -1) {
|
|
Ian Kent |
62ad96 |
+ error(ap->logopt, MODPREFIX
|
|
Ian Kent |
62ad96 |
+ "failed to mount offset triggers");
|
|
Ian Kent |
62ad96 |
+ cleanup_multi_triggers(ap, me, mm_tmp_root, start, mm_base);
|
|
Ian Kent |
62ad96 |
+ cleanup_multi_root(ap, mm_tmp_root, mm_root, move);
|
|
Ian Kent |
62ad96 |
+ rmdir(mm_tmp_root);
|
|
Ian Kent |
62ad96 |
+ return 1;
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+ } else if (rv < 0) {
|
|
Ian Kent |
62ad96 |
+ move = MOUNT_MOVE_NONE;
|
|
Ian Kent |
62ad96 |
+ ret = mount_multi_triggers(ap, me->multi, mm_root, start, mm_base);
|
|
Ian Kent |
62ad96 |
+ if (ret == -1) {
|
|
Ian Kent |
62ad96 |
+ error(ap->logopt, MODPREFIX
|
|
Ian Kent |
62ad96 |
+ "failed to mount offset triggers");
|
|
Ian Kent |
62ad96 |
+ cleanup_multi_triggers(ap, me, mm_tmp_root, start, mm_base);
|
|
Ian Kent |
62ad96 |
+ rmdir(mm_tmp_root);
|
|
Ian Kent |
62ad96 |
+ return 1;
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ if (!move_mount(ap, mm_tmp_root, target, move)) {
|
|
Ian Kent |
62ad96 |
+ cleanup_multi_triggers(ap, me, mm_tmp_root, start, mm_base);
|
|
Ian Kent |
62ad96 |
+ cleanup_multi_root(ap, mm_tmp_root, mm_root, move);
|
|
Ian Kent |
62ad96 |
+ rmdir(mm_tmp_root);
|
|
Ian Kent |
62ad96 |
+ return 1;
|
|
Ian Kent |
62ad96 |
+ }
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ rmdir(mm_tmp_root);
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ /* Mount for base of tree failed */
|
|
Ian Kent |
62ad96 |
+ if (rv > 0)
|
|
Ian Kent |
62ad96 |
+ return rv;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+done:
|
|
Ian Kent |
62ad96 |
+ /*
|
|
Ian Kent |
62ad96 |
+ * Convert fail on nonstrict, non-empty multi-mount
|
|
Ian Kent |
62ad96 |
+ * to success
|
|
Ian Kent |
62ad96 |
+ */
|
|
Ian Kent |
62ad96 |
+ if (rv < 0 && ret > 0)
|
|
Ian Kent |
62ad96 |
+ rv = 0;
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ return rv;
|
|
Ian Kent |
62ad96 |
}
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
/*
|
|
Ian Kent |
62ad96 |
@@ -1029,7 +1303,7 @@ int parse_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
char buf[MAX_ERR_BUF];
|
|
Ian Kent |
62ad96 |
struct map_source *source;
|
|
Ian Kent |
62ad96 |
struct mapent_cache *mc;
|
|
Ian Kent |
62ad96 |
- struct mapent *me, *ro;
|
|
Ian Kent |
62ad96 |
+ struct mapent *me = NULL;
|
|
Ian Kent |
62ad96 |
char *pmapent, *options;
|
|
Ian Kent |
62ad96 |
const char *p;
|
|
Ian Kent |
62ad96 |
int mapent_len, rv = 0;
|
|
Ian Kent |
62ad96 |
@@ -1154,7 +1428,7 @@ int parse_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
char *m_root = NULL;
|
|
Ian Kent |
62ad96 |
int m_root_len;
|
|
Ian Kent |
62ad96 |
time_t age = time(NULL);
|
|
Ian Kent |
62ad96 |
- int l, ret;
|
|
Ian Kent |
62ad96 |
+ int l;
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
/* If name starts with "/" it's a direct mount */
|
|
Ian Kent |
62ad96 |
if (*name == '/') {
|
|
Ian Kent |
62ad96 |
@@ -1302,48 +1576,7 @@ int parse_mount(struct autofs_point *ap,
|
|
Ian Kent |
62ad96 |
*/
|
|
Ian Kent |
62ad96 |
cache_set_parents(me);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- /* Mount root offset if it exists */
|
|
Ian Kent |
62ad96 |
- ro = cache_lookup_offset("/", "/", strlen(m_root), &me->multi_list);
|
|
Ian Kent |
62ad96 |
- if (ro) {
|
|
Ian Kent |
62ad96 |
- char *myoptions, *loc;
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- rv = parse_mapent(ro->mapent,
|
|
Ian Kent |
62ad96 |
- options, &myoptions, &loc, ap->logopt);
|
|
Ian Kent |
62ad96 |
- if (!rv) {
|
|
Ian Kent |
62ad96 |
- warn(ap->logopt,
|
|
Ian Kent |
62ad96 |
- MODPREFIX "failed to mount root offset");
|
|
Ian Kent |
62ad96 |
- cache_delete_offset_list(mc, name);
|
|
Ian Kent |
62ad96 |
- cache_multi_unlock(me);
|
|
Ian Kent |
62ad96 |
- cache_unlock(mc);
|
|
Ian Kent |
62ad96 |
- free(options);
|
|
Ian Kent |
62ad96 |
- pthread_setcancelstate(cur_state, NULL);
|
|
Ian Kent |
62ad96 |
- return 1;
|
|
Ian Kent |
62ad96 |
- }
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- rv = sun_mount(ap, m_root,
|
|
Ian Kent |
62ad96 |
- "/", 1, loc, strlen(loc), myoptions, ctxt);
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- free(myoptions);
|
|
Ian Kent |
62ad96 |
- free(loc);
|
|
Ian Kent |
62ad96 |
- }
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- ret = mount_multi_triggers(ap, m_root, me, "/");
|
|
Ian Kent |
62ad96 |
- if (ret == -1) {
|
|
Ian Kent |
62ad96 |
- warn(ap->logopt,
|
|
Ian Kent |
62ad96 |
- MODPREFIX "failed to mount offset triggers");
|
|
Ian Kent |
62ad96 |
- cache_multi_unlock(me);
|
|
Ian Kent |
62ad96 |
- cache_unlock(mc);
|
|
Ian Kent |
62ad96 |
- free(options);
|
|
Ian Kent |
62ad96 |
- pthread_setcancelstate(cur_state, NULL);
|
|
Ian Kent |
62ad96 |
- return 1;
|
|
Ian Kent |
62ad96 |
- }
|
|
Ian Kent |
62ad96 |
-
|
|
Ian Kent |
62ad96 |
- /*
|
|
Ian Kent |
62ad96 |
- * Convert fail on nonstrict, non-empty multi-mount
|
|
Ian Kent |
62ad96 |
- * to success
|
|
Ian Kent |
62ad96 |
- */
|
|
Ian Kent |
62ad96 |
- if (rv < 0 && ret > 0)
|
|
Ian Kent |
62ad96 |
- rv = 0;
|
|
Ian Kent |
62ad96 |
+ rv = mount_subtree(ap, me, name, NULL, options, ctxt);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
cache_multi_unlock(me);
|
|
Ian Kent |
62ad96 |
cache_unlock(mc);
|
|
Ian Kent |
62ad96 |
@@ -1461,24 +1694,15 @@ mount_it:
|
|
Ian Kent |
62ad96 |
MODPREFIX "core of entry: options=%s, loc=%.*s",
|
|
Ian Kent |
62ad96 |
options, loclen, loc);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- rv = sun_mount(ap, ap->path, name, name_len, loc, loclen, options, ctxt);
|
|
Ian Kent |
62ad96 |
+ cache_readlock(mc);
|
|
Ian Kent |
62ad96 |
+ cache_multi_lock(me);
|
|
Ian Kent |
62ad96 |
+
|
|
Ian Kent |
62ad96 |
+ rv = mount_subtree(ap, me, name, loc, options, ctxt);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
free(loc);
|
|
Ian Kent |
62ad96 |
free(options);
|
|
Ian Kent |
62ad96 |
|
|
Ian Kent |
62ad96 |
- /*
|
|
Ian Kent |
62ad96 |
- * If it's a multi-mount insert the triggers
|
|
Ian Kent |
62ad96 |
- * These are always direct mount triggers so root = ""
|
|
Ian Kent |
62ad96 |
- */
|
|
Ian Kent |
62ad96 |
- pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &cur_state);
|
|
Ian Kent |
62ad96 |
- cache_readlock(mc);
|
|
Ian Kent |
62ad96 |
- me = cache_lookup_distinct(mc, name);
|
|
Ian Kent |
62ad96 |
- if (me) {
|
|
Ian Kent |
62ad96 |
- int ret = mount_subtree_offsets(ap, mc, me);
|
|
Ian Kent |
62ad96 |
- /* Convert fail on nonstrict, non-empty multi-mount to success */
|
|
Ian Kent |
62ad96 |
- if (rv < 0 && ret > 0)
|
|
Ian Kent |
62ad96 |
- rv = 0;
|
|
Ian Kent |
62ad96 |
- }
|
|
Ian Kent |
62ad96 |
+ cache_multi_unlock(me);
|
|
Ian Kent |
62ad96 |
cache_unlock(mc);
|
|
Ian Kent |
62ad96 |
pthread_setcancelstate(cur_state, NULL);
|
|
Ian Kent |
62ad96 |
}
|