xref: /dflybsd-src/sbin/mount_devfs/mount_devfs.c (revision e0b1d537f9cbe376acec34421ad8b0f7da996ea0)
1710b4c75SMatthew Dillon /*
2710b4c75SMatthew Dillon  * Copyright (c) 2009 The DragonFly Project.  All rights reserved.
3710b4c75SMatthew Dillon  *
4710b4c75SMatthew Dillon  * This code is derived from software contributed to The DragonFly Project
5710b4c75SMatthew Dillon  * by Alex Hornung <ahornung@gmail.com>
6710b4c75SMatthew Dillon  *
7710b4c75SMatthew Dillon  * Redistribution and use in source and binary forms, with or without
8710b4c75SMatthew Dillon  * modification, are permitted provided that the following conditions
9710b4c75SMatthew Dillon  * are met:
10710b4c75SMatthew Dillon  *
11710b4c75SMatthew Dillon  * 1. Redistributions of source code must retain the above copyright
12710b4c75SMatthew Dillon  *    notice, this list of conditions and the following disclaimer.
13710b4c75SMatthew Dillon  * 2. Redistributions in binary form must reproduce the above copyright
14710b4c75SMatthew Dillon  *    notice, this list of conditions and the following disclaimer in
15710b4c75SMatthew Dillon  *    the documentation and/or other materials provided with the
16710b4c75SMatthew Dillon  *    distribution.
17710b4c75SMatthew Dillon  * 3. Neither the name of The DragonFly Project nor the names of its
18710b4c75SMatthew Dillon  *    contributors may be used to endorse or promote products derived
19710b4c75SMatthew Dillon  *    from this software without specific, prior written permission.
20710b4c75SMatthew Dillon  *
21710b4c75SMatthew Dillon  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22710b4c75SMatthew Dillon  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23710b4c75SMatthew Dillon  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
24710b4c75SMatthew Dillon  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE
25710b4c75SMatthew Dillon  * COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
26710b4c75SMatthew Dillon  * INCIDENTAL, SPECIAL, EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING,
27710b4c75SMatthew Dillon  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
28710b4c75SMatthew Dillon  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
29710b4c75SMatthew Dillon  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
30710b4c75SMatthew Dillon  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
31710b4c75SMatthew Dillon  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
32710b4c75SMatthew Dillon  * SUCH DAMAGE.
33710b4c75SMatthew Dillon  */
342dc55a02SSascha Wildner 
35710b4c75SMatthew Dillon #include <sys/param.h>
36710b4c75SMatthew Dillon #include <sys/mount.h>
372c1e28ddSAlex Hornung #include <sys/devfs.h>
38710b4c75SMatthew Dillon 
39710b4c75SMatthew Dillon #include <err.h>
402dc55a02SSascha Wildner #include <mntopts.h>
41710b4c75SMatthew Dillon #include <stdio.h>
42710b4c75SMatthew Dillon #include <stdlib.h>
43710b4c75SMatthew Dillon #include <string.h>
44710b4c75SMatthew Dillon #include <sysexits.h>
45710b4c75SMatthew Dillon #include <unistd.h>
46710b4c75SMatthew Dillon 
4785819c59SAlex Hornung #if 0
4885819c59SAlex Hornung #define MOPT_UPDATE         { "update",     0, MNT_UPDATE, 0 }
4985819c59SAlex Hornung #endif
5085819c59SAlex Hornung #define MOPT_DEVFSOPTS		\
5185819c59SAlex Hornung 	{ "ruleset=", 0, DEVFS_MNT_RULESET, 1 },	\
5285819c59SAlex Hornung 	{ "jail", 0, DEVFS_MNT_JAIL, 1 }
5385819c59SAlex Hornung 
5485819c59SAlex Hornung 
55710b4c75SMatthew Dillon struct mntopt mopts[] = {
56710b4c75SMatthew Dillon 	MOPT_STDOPTS,
5785819c59SAlex Hornung 	MOPT_DEVFSOPTS,
5885819c59SAlex Hornung #if 0
5985819c59SAlex Hornung 	MOPT_UPDATE,
6085819c59SAlex Hornung #endif
61710b4c75SMatthew Dillon 	MOPT_NULL
62710b4c75SMatthew Dillon };
63710b4c75SMatthew Dillon 
64710b4c75SMatthew Dillon static void	usage(void);
65710b4c75SMatthew Dillon 
66710b4c75SMatthew Dillon int
main(int argc,char ** argv)67710b4c75SMatthew Dillon main(int argc, char **argv)
68710b4c75SMatthew Dillon {
6985819c59SAlex Hornung 	struct statfs sfb;
7085819c59SAlex Hornung 	struct devfs_mount_info info;
71710b4c75SMatthew Dillon 	int ch, mntflags;
72ecbd263aSAlex Hornung 	char *ptr, *mntto;
73710b4c75SMatthew Dillon 	char mntpoint[MAXPATHLEN];
7485819c59SAlex Hornung 	char rule_file[MAXPATHLEN];
75710b4c75SMatthew Dillon 	struct vfsconf vfc;
76710b4c75SMatthew Dillon 	int error;
7785819c59SAlex Hornung 	info.flags = 0;
7885819c59SAlex Hornung 	int i,k;
7985819c59SAlex Hornung 	int mounted = 0;
80710b4c75SMatthew Dillon 
81710b4c75SMatthew Dillon 	mntflags = 0;
82710b4c75SMatthew Dillon 
83710b4c75SMatthew Dillon 	while ((ch = getopt(argc, argv, "o:")) != -1)
84710b4c75SMatthew Dillon 		switch(ch) {
85710b4c75SMatthew Dillon 		case 'o':
8685819c59SAlex Hornung 			getmntopts(optarg, mopts, &mntflags, &info.flags);
8785819c59SAlex Hornung 			ptr = strstr(optarg, "ruleset=");
8885819c59SAlex Hornung 			if (ptr) {
8985819c59SAlex Hornung 				ptr += 8;
9085819c59SAlex Hornung 				for (i = 0, k = 0;
91*e0b1d537SSascha Wildner 				    (i < MAXPATHLEN) && (ptr[i] != '\0') && (ptr[i] != ',');
9285819c59SAlex Hornung 				    i++) {
9385819c59SAlex Hornung 					rule_file[k++] = ptr[i];
9485819c59SAlex Hornung 
9585819c59SAlex Hornung 				}
9685819c59SAlex Hornung 				rule_file[k] = '\0';
9785819c59SAlex Hornung 			}
98710b4c75SMatthew Dillon 			break;
99710b4c75SMatthew Dillon 		case '?':
100710b4c75SMatthew Dillon 		default:
101710b4c75SMatthew Dillon 			usage();
102710b4c75SMatthew Dillon 		}
103710b4c75SMatthew Dillon 	argc -= optind;
104710b4c75SMatthew Dillon 	argv += optind;
105710b4c75SMatthew Dillon 
106710b4c75SMatthew Dillon 	if (argc < 1)
107710b4c75SMatthew Dillon 		usage();
108710b4c75SMatthew Dillon 
109710b4c75SMatthew Dillon 	/* resolve mount point with realpath(3) */
110ecbd263aSAlex Hornung 	switch(argc) {
111ecbd263aSAlex Hornung 	case 1:
112ecbd263aSAlex Hornung 		mntto = argv[0];
113ecbd263aSAlex Hornung 		break;
114ecbd263aSAlex Hornung 	case 2:
115ecbd263aSAlex Hornung 		mntto = argv[1];
116ecbd263aSAlex Hornung 		break;
117ecbd263aSAlex Hornung 	default:
118ecbd263aSAlex Hornung 		mntto = NULL;
119ecbd263aSAlex Hornung 		usage();
120ecbd263aSAlex Hornung 		/* NOTREACHED */
121ecbd263aSAlex Hornung 	}
122710b4c75SMatthew Dillon 
123ecbd263aSAlex Hornung 	checkpath(mntto, mntpoint);
124710b4c75SMatthew Dillon 
125710b4c75SMatthew Dillon 	error = getvfsbyname("devfs", &vfc);
126710b4c75SMatthew Dillon 	if (error && vfsisloadable("devfs")) {
127710b4c75SMatthew Dillon 		if(vfsload("devfs"))
128710b4c75SMatthew Dillon 			err(EX_OSERR, "vfsload(devfs)");
129710b4c75SMatthew Dillon 		endvfsent();
130710b4c75SMatthew Dillon 		error = getvfsbyname("devfs", &vfc);
131710b4c75SMatthew Dillon 	}
132710b4c75SMatthew Dillon 	if (error)
133710b4c75SMatthew Dillon 		errx(EX_OSERR, "devfs filesystem is not available");
134710b4c75SMatthew Dillon 
13585819c59SAlex Hornung 	error = statfs(mntpoint, &sfb);
13685819c59SAlex Hornung 
13785819c59SAlex Hornung 	if (error)
13885819c59SAlex Hornung 		err(EX_OSERR, "could not statfs() the mount point");
13985819c59SAlex Hornung 
14085819c59SAlex Hornung 	if ((!strcmp(sfb.f_fstypename, "devfs")) &&
14185819c59SAlex Hornung 	    (!strcmp(sfb.f_mntfromname, "devfs"))) {
14285819c59SAlex Hornung 		mounted = 1;
14385819c59SAlex Hornung 	}
14485819c59SAlex Hornung 
14585819c59SAlex Hornung 	if (!mounted) {
14685819c59SAlex Hornung 		if (mount(vfc.vfc_name, mntpoint, mntflags, &info))
147710b4c75SMatthew Dillon 			err(1, NULL);
14884dcbb75SAlex Hornung 	} else {
14985819c59SAlex Hornung 		if (fork() == 0) {
15085819c59SAlex Hornung 			execlp("devfsctl", "devfsctl",
15185819c59SAlex Hornung 			    "-m", mntpoint,
15285819c59SAlex Hornung 				"-c",
15385819c59SAlex Hornung 				"-r",
15485819c59SAlex Hornung 				NULL);
15585819c59SAlex Hornung 		}
15684dcbb75SAlex Hornung 	}
15785819c59SAlex Hornung 
15885819c59SAlex Hornung 	if (info.flags & DEVFS_MNT_RULESET) {
15985819c59SAlex Hornung 		if (fork() == 0) {
16085819c59SAlex Hornung 			execlp("devfsctl", "devfsctl",
16185819c59SAlex Hornung 			    "-m", mntpoint,
16285819c59SAlex Hornung 				"-a",
16385819c59SAlex Hornung 				"-f", rule_file,
16485819c59SAlex Hornung 			    NULL);
16585819c59SAlex Hornung 		}
16685819c59SAlex Hornung 	}
167710b4c75SMatthew Dillon 	exit(0);
168710b4c75SMatthew Dillon }
169710b4c75SMatthew Dillon 
170710b4c75SMatthew Dillon static void
usage(void)171710b4c75SMatthew Dillon usage(void)
172710b4c75SMatthew Dillon {
173710b4c75SMatthew Dillon 	fprintf(stderr,
174ecbd263aSAlex Hornung 	    "usage: mount_devfs [-o options] [mount_from] mount_point\n");
175710b4c75SMatthew Dillon 	exit(1);
176710b4c75SMatthew Dillon }
177