]> git.ipfire.org Git - thirdparty/util-linux.git/blame - libmount/src/optmap.c
libmount: fix mount.nfs segfault, rely on assert() rather than on nonnull
[thirdparty/util-linux.git] / libmount / src / optmap.c
CommitLineData
078edb2d
KZ
1/*
2 * Copyright (C) 2010 Karel Zak <kzak@redhat.com>
3 *
4 * This file may be redistributed under the terms of the
5 * GNU Lesser General Public License.
192c6aad
KZ
6 */
7
8/**
9 * SECTION: optmap
10 * @title: Option maps
11 * @short_description: description for mount options
078edb2d 12 *
078edb2d
KZ
13 * The mount(2) linux syscall uses two arguments for mount options:
14 *
3d735589
KZ
15 * @mountflags: (see MS_* macros in linux/fs.h)
16 *
17 * @mountdata: (usully a comma separated string of options)
078edb2d 18 *
0f32f1e2 19 * The libmount uses options-map(s) to describe mount options.
078edb2d
KZ
20 *
21 * The option description (map entry) includes:
22 *
0f32f1e2 23 * @name: and argument name
3d735589
KZ
24 *
25 * @id: (in the map unique identifier or a mountflags, e.g MS_RDONLY)
26 *
66b8b8cd 27 * @mask: (MNT_INVERT, MNT_NOMTAB)
078edb2d 28 *
0f32f1e2 29 * The option argument value is defined by:
078edb2d 30 *
0f32f1e2 31 * "=" -- required argument, e.g "comment="
3d735589 32 *
0f32f1e2 33 * "[=]" -- optional argument, e.g. "loop[=]"
078edb2d 34 *
3d735589
KZ
35 * Example:
36 *
37 * <informalexample>
38 * <programlisting>
39 * #define MY_MS_FOO (1 << 1)
40 * #define MY_MS_BAR (1 << 2)
41 *
68164f6c 42 * libmnt_optmap myoptions[] = {
66b8b8cd
KZ
43 * { "foo", MY_MS_FOO },
44 * { "nofoo", MY_MS_FOO | MNT_INVERT },
0f32f1e2 45 * { "bar=", MY_MS_BAR },
3d735589
KZ
46 * { NULL }
47 * };
48 * </programlisting>
49 * </informalexample>
50 *
078edb2d
KZ
51 * The libmount defines two basic built-in options maps:
52 *
3d735589
KZ
53 * @MNT_LINUX_MAP: fs-independent kernel mount options (usually MS_* flags)
54 *
55 * @MNT_USERSPACE_MAP: userspace specific mount options (e.g. "user", "loop")
078edb2d 56 *
192c6aad
KZ
57 * For more details about option map struct see "struct mnt_optmap" in
58 * mount/mount.h.
078edb2d 59 */
078edb2d
KZ
60#include "mountP.h"
61
62/*
63 * fs-independent mount flags (built-in MNT_LINUX_MAP)
64 */
68164f6c 65static const struct libmnt_optmap linux_flags_map[] =
078edb2d 66{
66b8b8cd
KZ
67 { "ro", MS_RDONLY }, /* read-only */
68 { "rw", MS_RDONLY, MNT_INVERT }, /* read-write */
69 { "exec", MS_NOEXEC, MNT_INVERT }, /* permit execution of binaries */
70 { "noexec", MS_NOEXEC }, /* don't execute binaries */
71 { "suid", MS_NOSUID, MNT_INVERT }, /* honor suid executables */
72 { "nosuid", MS_NOSUID }, /* don't honor suid executables */
73 { "dev", MS_NODEV, MNT_INVERT }, /* interpret device files */
74 { "nodev", MS_NODEV }, /* don't interpret devices */
078edb2d 75
66b8b8cd
KZ
76 { "sync", MS_SYNCHRONOUS }, /* synchronous I/O */
77 { "async", MS_SYNCHRONOUS, MNT_INVERT },/* asynchronous I/O */
078edb2d 78
66b8b8cd 79 { "dirsync", MS_DIRSYNC }, /* synchronous directory modifications */
f84fa6f7 80 { "remount", MS_REMOUNT, MNT_NOMTAB }, /* alter flags of mounted FS */
66b8b8cd
KZ
81 { "bind", MS_BIND }, /* Remount part of tree elsewhere */
82 { "rbind", MS_BIND | MS_REC }, /* Idem, plus mounted subtrees */
078edb2d 83#ifdef MS_NOSUB
66b8b8cd
KZ
84 { "sub", MS_NOSUB, MNT_INVERT }, /* allow submounts */
85 { "nosub", MS_NOSUB }, /* don't allow submounts */
078edb2d
KZ
86#endif
87#ifdef MS_SILENT
5af1532e 88 { "silent", MS_SILENT }, /* be quiet */
66b8b8cd 89 { "loud", MS_SILENT, MNT_INVERT }, /* print out messages. */
078edb2d
KZ
90#endif
91#ifdef MS_MANDLOCK
66b8b8cd
KZ
92 { "mand", MS_MANDLOCK }, /* Allow mandatory locks on this FS */
93 { "nomand", MS_MANDLOCK, MNT_INVERT }, /* Forbid mandatory locks on this FS */
078edb2d
KZ
94#endif
95#ifdef MS_NOATIME
66b8b8cd
KZ
96 { "atime", MS_NOATIME, MNT_INVERT }, /* Update access time */
97 { "noatime", MS_NOATIME }, /* Do not update access time */
078edb2d
KZ
98#endif
99#ifdef MS_I_VERSION
66b8b8cd
KZ
100 { "iversion", MS_I_VERSION }, /* Update inode I_version time */
101 { "noiversion", MS_I_VERSION, MNT_INVERT},/* Don't update inode I_version time */
078edb2d
KZ
102#endif
103#ifdef MS_NODIRATIME
66b8b8cd
KZ
104 { "diratime", MS_NODIRATIME, MNT_INVERT }, /* Update dir access times */
105 { "nodiratime", MS_NODIRATIME }, /* Do not update dir access times */
078edb2d
KZ
106#endif
107#ifdef MS_RELATIME
66b8b8cd
KZ
108 { "relatime", MS_RELATIME }, /* Update access times relative to mtime/ctime */
109 { "norelatime", MS_RELATIME, MNT_INVERT }, /* Update access time without regard to mtime/ctime */
078edb2d
KZ
110#endif
111#ifdef MS_STRICTATIME
66b8b8cd
KZ
112 { "strictatime", MS_STRICTATIME }, /* Strict atime semantics */
113 { "nostrictatime", MS_STRICTATIME, MNT_INVERT }, /* kernel default atime */
6498ece0
KZ
114#endif
115#ifdef MS_PROPAGATION
116 { "unbindable", MS_UNBINDABLE, MNT_NOHLPS | MNT_NOMTAB }, /* Unbindable */
117 { "runbindable", MS_UNBINDABLE | MS_REC, MNT_NOHLPS | MNT_NOMTAB },
118 { "private", MS_PRIVATE, MNT_NOHLPS | MNT_NOMTAB }, /* Private */
119 { "rprivate", MS_PRIVATE | MS_REC, MNT_NOHLPS | MNT_NOMTAB },
120 { "slave", MS_SLAVE, MNT_NOHLPS | MNT_NOMTAB }, /* Slave */
121 { "rslave", MS_SLAVE | MS_REC, MNT_NOHLPS | MNT_NOMTAB },
122 { "shared", MS_SHARED, MNT_NOHLPS | MNT_NOMTAB }, /* Shared */
123 { "rshared", MS_SHARED | MS_REC, MNT_NOHLPS | MNT_NOMTAB },
078edb2d
KZ
124#endif
125 { NULL, 0, 0 }
126};
127
128/*
129 * userspace mount option (built-in MNT_USERSPACE_MAP)
130 */
68164f6c 131static const struct libmnt_optmap userspace_opts_map[] =
078edb2d 132{
76a06ca4 133 { "defaults", 0, 0 }, /* default options */
078edb2d 134
5810d870
KZ
135 { "auto", MNT_MS_NOAUTO, MNT_NOHLPS | MNT_INVERT | MNT_NOMTAB }, /* Can be mounted using -a */
136 { "noauto", MNT_MS_NOAUTO, MNT_NOHLPS | MNT_NOMTAB }, /* Can only be mounted explicitly */
078edb2d 137
699abc83 138 { "user[=]", MNT_MS_USER }, /* Allow ordinary user to mount (mtab) */
078edb2d
KZ
139 { "nouser", MNT_MS_USER, MNT_INVERT | MNT_NOMTAB }, /* Forbid ordinary user to mount */
140
141 { "users", MNT_MS_USERS, MNT_NOMTAB }, /* Allow ordinary users to mount */
142 { "nousers", MNT_MS_USERS, MNT_INVERT | MNT_NOMTAB }, /* Forbid ordinary users to mount */
143
144 { "owner", MNT_MS_OWNER, MNT_NOMTAB }, /* Let the owner of the device mount */
145 { "noowner", MNT_MS_OWNER, MNT_INVERT | MNT_NOMTAB }, /* Device owner has no special privs */
146
147 { "group", MNT_MS_GROUP, MNT_NOMTAB }, /* Let the group of the device mount */
148 { "nogroup", MNT_MS_GROUP, MNT_INVERT | MNT_NOMTAB }, /* Device group has no special privs */
149
94b0c44f
KZ
150 /*
151 * Note that traditional init scripts assume _netdev option in /etc/mtab to
152 * umount network block devices on shutdown.
153 */
078edb2d
KZ
154 { "_netdev", MNT_MS_NETDEV }, /* Device requires network */
155
5810d870
KZ
156 { "comment=", MNT_MS_COMMENT, MNT_NOHLPS | MNT_NOMTAB },/* fstab comment only */
157 { "x-", MNT_MS_XCOMMENT, MNT_NOHLPS | MNT_NOMTAB | MNT_PREFIX }, /* x- options */
078edb2d 158
5810d870
KZ
159 { "loop[=]", MNT_MS_LOOP, MNT_NOHLPS }, /* use the loop device */
160 { "offset=", MNT_MS_OFFSET, MNT_NOHLPS | MNT_NOMTAB }, /* loop device offset */
161 { "sizelimit=", MNT_MS_SIZELIMIT, MNT_NOHLPS | MNT_NOMTAB }, /* loop device size limit */
162 { "encryption=", MNT_MS_ENCRYPTION, MNT_NOHLPS | MNT_NOMTAB }, /* loop device encryption */
078edb2d
KZ
163
164 { "nofail", MNT_MS_NOFAIL, MNT_NOMTAB }, /* Do not fail if ENOENT on dev */
165
0f32f1e2 166 { "uhelper=", MNT_MS_UHELPER }, /* /sbin/umount.<helper> */
f309b8a7 167
5810d870 168 { "helper=", MNT_MS_HELPER }, /* /sbin/mount.<helper> */
4b658e09 169
078edb2d
KZ
170 { NULL, 0, 0 }
171};
172
173/**
174 * mnt_get_builtin_map:
175 * @id: map id -- MNT_LINUX_MAP or MNT_USERSPACE_MAP
176 *
177 * MNT_LINUX_MAP - Linux kernel fs-independent mount options
178 * (usually MS_* flags, see linux/fs.h)
179 *
180 * MNT_USERSPACE_MAP - userpace mount(8) specific mount options
181 * (e.g user=, _netdev, ...)
182 *
192c6aad 183 * Returns: static built-in libmount map.
078edb2d 184 */
68164f6c 185const struct libmnt_optmap *mnt_get_builtin_optmap(int id)
078edb2d
KZ
186{
187 assert(id);
188
189 if (id == MNT_LINUX_MAP)
190 return linux_flags_map;
191 else if (id == MNT_USERSPACE_MAP)
192 return userspace_opts_map;
193 return NULL;
194}
195
196/*
197 * Lookups for the @name in @maps and returns a map and in @mapent
198 * returns the map entry
199 */
68164f6c
KZ
200const struct libmnt_optmap *mnt_optmap_get_entry(
201 struct libmnt_optmap const **maps,
078edb2d
KZ
202 int nmaps,
203 const char *name,
204 size_t namelen,
68164f6c 205 const struct libmnt_optmap **mapent)
078edb2d
KZ
206{
207 int i;
208
209 assert(maps);
210 assert(nmaps);
211 assert(name);
212 assert(namelen);
078edb2d 213
3661b841
KZ
214 if (mapent)
215 *mapent = NULL;
078edb2d
KZ
216
217 for (i = 0; i < nmaps; i++) {
68164f6c
KZ
218 const struct libmnt_optmap *map = maps[i];
219 const struct libmnt_optmap *ent;
078edb2d
KZ
220 const char *p;
221
222 for (ent = map; ent && ent->name; ent++) {
699abc83
KZ
223 if (ent->mask & MNT_PREFIX) {
224 if (startswith(name, ent->name)) {
225 if (mapent)
226 *mapent = ent;
227 return map;
228 }
229 continue;
230 }
078edb2d
KZ
231 if (strncmp(ent->name, name, namelen))
232 continue;
233 p = ent->name + namelen;
234 if (*p == '\0' || *p == '=' || *p == '[') {
3661b841
KZ
235 if (mapent)
236 *mapent = ent;
078edb2d
KZ
237 return map;
238 }
239 }
240 }
241 return NULL;
242}
243