1/*
2 * CDDL HEADER START
3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
7 *
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
12 *
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 *
19 * CDDL HEADER END
20 */
21/*
22 * Copyright (c) 1992, 2010, Oracle and/or its affiliates. All rights reserved.
23 */
24
25#ifndef	_SYS_FS_AUTOFS_H
26#define	_SYS_FS_AUTOFS_H
27
28#include <rpc/clnt.h>
29#include <gssapi/gssapi.h>
30#include <sys/vfs.h>
31#include <sys/dirent.h>
32#include <sys/types.h>
33#include <sys/types32.h>
34#include <sys/note.h>
35#include <sys/time_impl.h>
36#include <sys/mntent.h>
37#include <nfs/mount.h>
38#include <rpc/rpcsec_gss.h>
39#include <sys/zone.h>
40#include <sys/door.h>
41#include <rpcsvc/autofs_prot.h>
42
43#ifdef _KERNEL
44#include <sys/vfs_opreg.h>
45#endif
46
47#ifdef	__cplusplus
48extern "C" {
49#endif
50
51
52#ifdef	_KERNEL
53
54
55/*
56 * Tracing macro; expands to nothing for non-debug kernels.
57 */
58#ifndef DEBUG
59#define	AUTOFS_DPRINT(x)
60#else
61#define	AUTOFS_DPRINT(x)	auto_dprint x
62#endif
63
64/*
65 * Per AUTOFS mountpoint information.
66 */
67typedef struct fninfo {
68	struct vfs	*fi_mountvfs;		/* mounted-here VFS */
69	struct vnode	*fi_rootvp;		/* root vnode */
70	struct knetconfig fi_knconf;		/* netconfig */
71	struct netbuf	fi_addr;		/* daemon address */
72	char		*fi_path;		/* autofs mountpoint */
73	char 		*fi_map;		/* context/map-name */
74	char		*fi_subdir;		/* subdir within map */
75	char		*fi_key;		/* key to use on direct maps */
76	char		*fi_opts;		/* default mount options */
77	int		fi_pathlen;		/* autofs mountpoint len */
78	int		fi_maplen;		/* size of context */
79	int		fi_subdirlen;
80	int		fi_keylen;
81	int		fi_optslen;		/* default mount options len */
82	int		fi_refcnt;		/* reference count */
83	int		fi_flags;
84	int		fi_mount_to;
85	int		fi_rpc_to;
86	zoneid_t	fi_zoneid;		/* zone mounted in */
87} fninfo_t;
88
89/*
90 * The AUTOFS locking scheme:
91 *
92 * The locks:
93 * 	fn_lock: protects the fn_node. It must be grabbed to change any
94 *		 field on the fn_node, except for those protected by
95 *		 fn_rwlock.
96 *
97 * 	fn_rwlock: readers/writers lock to protect the subdirectory and
98 *		   top level list traversal.
99 *		   Protects: fn_dirents
100 *			     fn_next
101 *		             fn_size
102 *		             fn_linkcnt
103 *                 - Grab readers when checking if certain fn_node exists
104 *                   under fn_dirents.
105 *		   - Grab readers when attempting to reference a node
106 *                   pointed to by fn_dirents, fn_next, and fn_parent.
107 *                 - Grab writers to add a new fnnode under fn_dirents and
108 *		     to remove a node pointed to by fn_dirents or fn_next.
109 *
110 *	Lock ordering:
111 *		fn_rwlock > fn_lock
112 *
113 * The flags:
114 *	MF_INPROG:
115 *		- Indicates a mount request has been sent to the daemon.
116 *		- If this flag is set, the thread sets MF_WAITING on the
117 *                fnnode and sleeps.
118 *
119 *	MF_WAITING:
120 *		- Set by a thread when it puts itself to sleep waiting for
121 *		  the ongoing operation on this fnnode to be done.
122 *
123 * 	MF_LOOKUP:
124 * 		- Indicates a lookup request has been sent to the daemon.
125 *		- If this flag is set, the thread sets MF_WAITING on the
126 *                fnnode and sleeps.
127 *
128 *	MF_IK_MOUNT:
129 *		- This flag is set to indicate the mount was done in the
130 *		  kernel, and so should the unmount.
131 *
132 *	MF_DIRECT:
133 *		- Direct mountpoint if set, indirect otherwise.
134 *
135 *	MF_TRIGGER:
136 *		- This is a trigger node.
137 *
138 *	MF_THISUID_MATCH_RQD:
139 *		- User-relative context binding kind of node.
140 *		- Node with this flag set requires a name match as well
141 *		  as a cred match in order to be returned from the directory
142 *		  hierarchy.
143 *
144 * 	MF_MOUNTPOINT:
145 * 		- At some point automountd mounted a filesystem on this node.
146 * 		If fn_trigger is non-NULL, v_vfsmountedhere is NULL and this
147 * 		flag is set then the filesystem must have been forcibly
148 * 		unmounted.
149 */
150
151/*
152 * The inode of AUTOFS
153 */
154typedef struct fnnode {
155	char		*fn_name;
156	char		*fn_symlink;		/* if VLNK, this is what it */
157						/* points to */
158	int		fn_namelen;
159	int		fn_symlinklen;
160	uint_t		fn_linkcnt;		/* link count */
161	mode_t		fn_mode;		/* file mode bits */
162	uid_t		fn_uid;			/* owner's uid */
163	gid_t		fn_gid;			/* group's uid */
164	int		fn_error;		/* mount/lookup error */
165	ino_t		fn_nodeid;
166	off_t		fn_offset;		/* offset into directory */
167	int		fn_flags;
168	uint_t		fn_size;		/* size of directory */
169	struct vnode	*fn_vnode;
170	struct fnnode	*fn_parent;
171	struct fnnode	*fn_next;		/* sibling */
172	struct fnnode	*fn_dirents;		/* children */
173	struct fnnode	*fn_trigger; 		/* pointer to next level */
174						/* AUTOFS trigger nodes */
175	struct action_list *fn_alp;		/* Pointer to mount info */
176						/* used for remounting */
177						/* trigger nodes */
178	cred_t		*fn_cred;		/* pointer to cred, used for */
179						/* "thisuser" processing */
180	krwlock_t	fn_rwlock;		/* protects list traversal */
181	kmutex_t	fn_lock;		/* protects the fnnode */
182	timestruc_t	fn_atime;
183	timestruc_t	fn_mtime;
184	timestruc_t	fn_ctime;
185	time_t		fn_ref_time;		/* time last referenced */
186	time_t		fn_unmount_ref_time;	/* last time unmount was done */
187	kcondvar_t	fn_cv_mount;		/* mount blocking variable */
188	struct vnode	*fn_seen;		/* vnode already traversed */
189	kthread_t	*fn_thread;		/* thread that has currently */
190						/* modified fn_seen */
191	struct autofs_globals *fn_globals;	/* global variables */
192} fnnode_t;
193
194
195#define	vntofn(vp)	((struct fnnode *)((vp)->v_data))
196#define	fntovn(fnp)	(((fnp)->fn_vnode))
197#define	vfstofni(vfsp)	((struct fninfo *)((vfsp)->vfs_data))
198
199#define	MF_DIRECT	0x001
200#define	MF_INPROG	0x002		/* Mount in progress */
201#define	MF_WAITING	0x004
202#define	MF_LOOKUP	0x008		/* Lookup in progress */
203#define	MF_ATTR_WAIT	0x010
204#define	MF_IK_MOUNT	0x040
205#define	MF_TRIGGER	0x080
206#define	MF_THISUID_MATCH_RQD	0x100	/* UID match required for this node */
207					/* required for thisuser kind of */
208					/* nodes */
209#define	MF_MOUNTPOINT	0x200		/* Node is/was a mount point */
210
211#define	AUTOFS_MODE		0555
212#define	AUTOFS_BLOCKSIZE	1024
213
214struct autofs_callargs {
215	fnnode_t	*fnc_fnp;	/* fnnode */
216	char		*fnc_name;	/* path to lookup/mount */
217	kthread_t	*fnc_origin;	/* thread that fired up this thread */
218					/* used for debugging purposes */
219	cred_t		*fnc_cred;
220};
221
222struct autofs_globals {
223	fnnode_t		*fng_rootfnnodep;
224	int			fng_fnnode_count;
225	int			fng_printed_not_running_msg;
226	kmutex_t		fng_unmount_threads_lock;
227	int			fng_unmount_threads;
228	int			fng_verbose;
229	zoneid_t		fng_zoneid;
230	pid_t			fng_autofs_pid;
231	kmutex_t		fng_autofs_daemon_lock;
232	/*
233	 * autofs_daemon_lock protects fng_autofs_daemon_dh
234	 */
235	door_handle_t		fng_autofs_daemon_dh;
236};
237
238extern kmutex_t autofs_minor_lock;
239extern zone_key_t autofs_key;
240
241/*
242 * Sets the MF_INPROG flag on this fnnode.
243 * fnp->fn_lock should be held before this macro is called,
244 * operation is either MF_INPROG or MF_LOOKUP.
245 */
246#define	AUTOFS_BLOCK_OTHERS(fnp, operation)	{ \
247	ASSERT(MUTEX_HELD(&(fnp)->fn_lock)); \
248	ASSERT(!((fnp)->fn_flags & operation)); \
249	(fnp)->fn_flags |= (operation); \
250}
251
252#define	AUTOFS_UNBLOCK_OTHERS(fnp, operation)	{ \
253	auto_unblock_others((fnp), (operation)); \
254}
255
256extern struct vnodeops *auto_vnodeops;
257extern const struct fs_operation_def auto_vnodeops_template[];
258
259/*
260 * Utility routines
261 */
262extern int auto_search(fnnode_t *, char *, fnnode_t **, cred_t *);
263extern int auto_enter(fnnode_t *, char *, fnnode_t **, cred_t *);
264extern void auto_unblock_others(fnnode_t *, uint_t);
265extern int auto_wait4mount(fnnode_t *);
266extern fnnode_t *auto_makefnnode(vtype_t, vfs_t *, char *, cred_t *,
267    struct autofs_globals *);
268extern void auto_freefnnode(fnnode_t *);
269extern void auto_disconnect(fnnode_t *, fnnode_t *);
270extern void auto_do_unmount(struct autofs_globals *);
271/*PRINTFLIKE4*/
272extern void auto_log(int verbose, zoneid_t zoneid, int level,
273	const char *fmt, ...)
274    __KPRINTFLIKE(4);
275/*PRINTFLIKE2*/
276extern void auto_dprint(int level, const char *fmt, ...)
277    __KPRINTFLIKE(2);
278extern int auto_calldaemon(zoneid_t, int, xdrproc_t, void *, xdrproc_t,
279	void *, int, bool_t);
280extern int auto_lookup_aux(fnnode_t *, char *, cred_t *);
281extern void auto_new_mount_thread(fnnode_t *, char *, cred_t *);
282extern int auto_nobrowse_option(char *);
283
284extern int unmount_subtree(fnnode_t *, boolean_t);
285extern void unmount_tree(struct autofs_globals *, boolean_t);
286extern void autofs_free_globals(struct autofs_globals *);
287extern void autofs_shutdown_zone(struct autofs_globals *);
288/*
289 * external routines not defined in any header file
290 */
291extern bool_t xdr_uid_t(XDR *, uid_t *);
292
293#endif	/* _KERNEL */
294
295/*
296 * autofs structures and defines needed for use with doors.
297 */
298#define	AUTOFS_NULL	0
299#define	AUTOFS_MOUNT	1
300#define	AUTOFS_UNMOUNT	2
301#define	AUTOFS_READDIR	3
302#define	AUTOFS_LOOKUP	4
303#define	AUTOFS_SRVINFO	5
304#define	AUTOFS_MNTINFO	6
305
306/*
307 * autofs_door_args is a generic structure used to grab the command
308 * from any of the argument structures passed in.
309 */
310
311typedef struct {
312	int cmd;
313	int xdr_len;
314	char xdr_arg[1];	/* buffer holding xdr encoded data */
315} autofs_door_args_t;
316
317
318typedef struct {
319	int res_status;
320	int xdr_len;
321	char xdr_res[1];	/* buffer holding xdr encoded data */
322} autofs_door_res_t;
323
324typedef enum autofs_res autofs_res_t;
325typedef enum autofs_stat autofs_stat_t;
326typedef enum autofs_action autofs_action_t;
327
328typedef struct {
329	void *	atsd_buf;
330	size_t	atsd_len;
331} autofs_tsd_t;
332
333typedef struct sec_desdata {
334	int		nd_sec_syncaddr_len;
335	int		nd_sec_knc_semantics;
336	int		nd_sec_netnamelen;
337	uint64_t	nd_sec_knc_rdev;
338	int		nd_sec_knc_unused[8];
339} sec_desdata_t;
340
341typedef struct sec_gssdata {
342	int			element_length;
343	rpc_gss_service_t	service;
344	char			uname[MAX_NAME_LEN];
345	char			inst[MAX_NAME_LEN];
346	char			realm[MAX_NAME_LEN];
347	uint_t			qop;
348} sec_gssdata_t;
349
350typedef struct nfs_secdata  {
351	sec_desdata_t	nfs_des_clntdata;
352	sec_gssdata_t	nfs_gss_clntdata;
353} nfs_secdata_t;
354
355/*
356 * Comma separated list of mntoptions which are inherited when the
357 * "restrict" option is present.  The RESTRICT option must be first!
358 * This define is shared between the kernel and the automount daemon.
359 */
360#define	RESTRICTED_MNTOPTS	\
361	MNTOPT_RESTRICT, MNTOPT_NOSUID, MNTOPT_NOSETUID, MNTOPT_NODEVICES
362
363/*
364 * AUTOFS syscall entry point
365 */
366enum autofssys_op { AUTOFS_UNMOUNTALL, AUTOFS_SETDOOR };
367
368#ifdef	_KERNEL
369extern int autofssys(enum autofssys_op, uintptr_t);
370
371#endif	/* _KERNEL */
372
373#ifdef	__cplusplus
374}
375#endif
376
377#endif	/* _SYS_FS_AUTOFS_H */
378