automount.c revision 7c478bd95313f5f23a4c958a745db2134aa03244
/*
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
* Common Development and Distribution License, Version 1.0 only
* (the "License"). You may not use this file except in compliance
* with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* See the License for the specific language governing permissions
* and limitations under the License.
*
* When distributing Covered Code, include this CDDL HEADER in each
* file and include the License file at usr/src/OPENSOLARIS.LICENSE.
* If applicable, add the following below this CDDL HEADER, with the
* fields enclosed by brackets "[]" replaced with your own identifying
* information: Portions Copyright [yyyy] [name of copyright owner]
*
* CDDL HEADER END
*/
/*
*
* Copyright 2005 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
#pragma ident "%Z%%M% %I% %E% SMI"
#include <ctype.h>
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <locale.h>
#include <stdarg.h>
#include <errno.h>
#include <string.h>
#include <dirent.h>
#include <signal.h>
#include <syslog.h>
#include <rpcsvc/nfs_prot.h>
#include <nsswitch.h>
#include <deflt.h>
#include <rpcsvc/daemon_utils.h>
#include "automount.h"
static int mkdir_r(char *);
static struct extmnttab *find_mount();
int verbose = 0;
int trace = 0;
static void usage();
static int compare_opts(char *, char *);
static void do_unmounts();
static int mount_timeout = AUTOFS_MOUNT_TIMEOUT;
/*
* XXX
* The following are needed because they're used in auto_subr.c and
* we link with it. Should avoid this.
*/
int argc;
char *argv[];
{
int c;
struct autofs_args ai;
char autofs_addr[MAXADDRLEN];
char *master_map = "auto_master";
int null;
char mntopts[MAX_MNTOPT_STR];
int mntflgs;
int count = 0;
char **stkptr;
char *defval;
/*
* protect this command from session termination when run in background
* we test background by whether SIGINT is ignored
*/
(void) setsid();
}
/*
* Read in the values from config file first before we check
* commandline options so the options override the file.
*/
if ((defopen(AUTOFSADMIN)) == 0) {
errno = 0;
if (errno != 0)
}
else
}
/* close defaults file */
}
switch (c) {
case 'm':
pr_msg("Warning: -m option not supported");
break;
case 'M':
pr_msg("Warning: -M option not supported");
break;
case 'D':
pr_msg("Warning: -D option not supported");
break;
case 'f':
pr_msg("Error: -f option no longer supported");
usage();
break;
case 't':
pr_msg("Error: invalid value for -t");
usage();
}
break;
case 'v':
verbose++;
break;
default:
usage();
break;
}
}
pr_msg("%s: command line mountpoints/maps "
"no longer supported",
usage();
}
current_mounts = getmntlist();
if (current_mounts == NULL) {
pr_msg("Couldn't establish current mounts");
exit(1);
}
(void) umask(0);
/*
* automount maps found. enable services as needed.
*/
}
closelog();
pr_msg("uname: %m");
exit(1);
}
/*
* Mount the daemon at its mount points.
*/
/*
* Skip null entries
*/
continue;
/*
* Skip null'ed entries
*/
null = 0;
null = 1;
}
if (null)
continue;
/*
* Check whether there's already an entry
* in the mnttab for this mountpoint.
*/
/*
* If it's not an autofs mount - don't
* mount over it.
*/
pr_msg("%s: already mounted",
mntp->mnt_mountp);
continue;
}
/*
* Compare the mnttab entry with the master map
* entry. If the map or mount options are
* different, then update this information
* with a remount.
*/
mntp->mnt_mntopts) == 0) {
continue; /* no change */
}
/*
* Check for an overlaid direct autofs mount.
* Cannot remount since it's inaccessible.
*/
if (verbose)
pr_msg("%s: cannot remount",
continue;
}
}
}
/*
* Create a mount point if necessary
* If the path refers to an existing symbolic
* link, refuse to mount on it. This avoids
* future problems.
*/
continue;
}
} else {
continue;
}
}
if (dir->dir_direct)
else
}
MAX_MNTOPT_STR) < 0) {
continue;
}
count++;
if (verbose) {
if (dir->dir_remount)
else
}
}
pr_msg("no mounts");
/*
* that are not in the master map must be
* unmounted
*/
do_unmounts();
return (0);
}
/*
* Find a mount entry given
* the mountpoint path.
* Optionally return the first
* or last entry.
*/
static struct extmnttab *
char *mntpnt;
int first;
{
if (first)
break;
}
}
return (found);
}
/*
* Compare mount options
* ignoring "ignore", "direct", "indirect"
* and "dev=".
*/
static int
{
char optbuf2[MAX_MNTOPT_STR];
int j, i, notsame;
/*
* Parse the two option strings to split them both into
* lists of individual options.
*/
else
*s = '\0';
if (*s != '\0')
nopts1 = 1;
else
nopts1 = 0;
nopts1++;
s++;
}
if (nopts1)
return (1);
nopts1 = 0;
s = optbuf1;
}
}
s = optbuf2;
else
*s = '\0';
if (*s != '\0')
nopts2 = 1;
else
nopts2 = 0;
nopts2++;
s++;
}
if (nopts2)
notsame = 1;
goto done;
}
nopts2 = 0;
s = optbuf2;
}
}
notsame = 1;
goto done;
}
notsame = 0;
for (i = 0; i < nopts1; i++) {
notsame = 1;
for (j = 0; j < nopts2; j++) {
notsame = 0;
break;
}
}
if (notsame)
break;
}
done:
return (notsame);
}
static void
usage()
{
pr_msg("Usage: automount [ -v ] [ -t duration ]");
exit(1);
/* NOTREACHED */
}
/*
* Unmount any autofs mounts that
* aren't in the master map
*/
static void
{
int current;
int count = 0;
struct zone_summary *zsp;
zsp = fs_get_zone_summaries();
pr_msg("Couldn't establish active zones");
exit(1);
}
continue;
continue;
/*
* Don't unmount autofs mounts done
* from the autofs mount command.
* How do we tell them apart ?
* Autofs mounts not eligible for auto-unmount
* have the "nest" pseudo-option.
*/
continue;
current = 0;
break;
}
}
if (current)
continue;
if (verbose) {
pr_msg("%s unmounted",
mnt->mnt_mountp);
}
count++;
}
}
pr_msg("no unmounts");
}
static int
char *dir;
{
int err;
char *slash;
return (0);
return (-1);
return (-1);
*slash = '\0';
*slash++ = '/';
return (err);
}
/*
* Print an error.
* Works like printf (fmt string and variable args)
* except that it will subsititute an error message
* for a "%m" string (like syslog).
*/
/* VARARGS1 */
void
{
char *p1;
char *nfmt;
}
p1++;
} else {
}
}
*p2++ = '\n';
*p2 = '\0';
}