1/*
2  FUSE: Filesystem in Userspace
3  Copyright (C) 2001-2007  Miklos Szeredi <miklos@szeredi.hu>
4
5  This program can be distributed under the terms of the GNU LGPLv2.
6  See the file COPYING.LIB.
7*/
8
9#ifndef _FUSE_OPT_H_
10#define _FUSE_OPT_H_
11
12/** @file
13 *
14 * This file defines the option parsing interface of FUSE
15 */
16
17#ifdef __cplusplus
18extern "C" {
19#endif
20
21/**
22 * Option description
23 *
24 * This structure describes a single option, and action associated
25 * with it, in case it matches.
26 *
27 * More than one such match may occur, in which case the action for
28 * each match is executed.
29 *
30 * There are three possible actions in case of a match:
31 *
32 * i) An integer (int or unsigned) variable determined by 'offset' is
33 *    set to 'value'
34 *
35 * ii) The processing function is called, with 'value' as the key
36 *
37 * iii) An integer (any) or string (char *) variable determined by
38 *    'offset' is set to the value of an option parameter
39 *
40 * 'offset' should normally be either set to
41 *
42 *  - 'offsetof(struct foo, member)'  actions i) and iii)
43 *
44 *  - -1			      action ii)
45 *
46 * The 'offsetof()' macro is defined in the <stddef.h> header.
47 *
48 * The template determines which options match, and also have an
49 * effect on the action.  Normally the action is either i) or ii), but
50 * if a format is present in the template, then action iii) is
51 * performed.
52 *
53 * The types of templates are:
54 *
55 * 1) "-x", "-foo", "--foo", "--foo-bar", etc.	These match only
56 *   themselves.  Invalid values are "--" and anything beginning
57 *   with "-o"
58 *
59 * 2) "foo", "foo-bar", etc.  These match "-ofoo", "-ofoo-bar" or
60 *    the relevant option in a comma separated option list
61 *
62 * 3) "bar=", "--foo=", etc.  These are variations of 1) and 2)
63 *    which have a parameter
64 *
65 * 4) "bar=%s", "--foo=%lu", etc.  Same matching as above but perform
66 *    action iii).
67 *
68 * 5) "-x ", etc.  Matches either "-xparam" or "-x param" as
69 *    two separate arguments
70 *
71 * 6) "-x %s", etc.  Combination of 4) and 5)
72 *
73 * If the format is "%s", memory is allocated for the string unlike
74 * with scanf().
75 */
76struct fuse_opt {
77	/** Matching template and optional parameter formatting */
78	const char *templ;
79
80	/**
81	 * Offset of variable within 'data' parameter of fuse_opt_parse()
82	 * or -1
83	 */
84	unsigned long offset;
85
86	/**
87	 * Value to set the variable to, or to be passed as 'key' to the
88	 * processing function.	 Ignored if template has a format
89	 */
90	int value;
91};
92
93/**
94 * Key option.	In case of a match, the processing function will be
95 * called with the specified key.
96 */
97#define FUSE_OPT_KEY(templ, key) { templ, -1U, key }
98
99/**
100 * Last option.	 An array of 'struct fuse_opt' must end with a NULL
101 * template value
102 */
103#define FUSE_OPT_END { NULL, 0, 0 }
104
105/**
106 * Argument list
107 */
108struct fuse_args {
109	/** Argument count */
110	int argc;
111
112	/** Argument vector.  NULL terminated */
113	char **argv;
114
115	/** Is 'argv' allocated? */
116	int allocated;
117};
118
119/**
120 * Initializer for 'struct fuse_args'
121 */
122#define FUSE_ARGS_INIT(argc, argv) { argc, argv, 0 }
123
124/**
125 * Key value passed to the processing function if an option did not
126 * match any template
127 */
128#define FUSE_OPT_KEY_OPT     -1
129
130/**
131 * Key value passed to the processing function for all non-options
132 *
133 * Non-options are the arguments beginning with a character other than
134 * '-' or all arguments after the special '--' option
135 */
136#define FUSE_OPT_KEY_NONOPT  -2
137
138/**
139 * Special key value for options to keep
140 *
141 * Argument is not passed to processing function, but behave as if the
142 * processing function returned 1
143 */
144#define FUSE_OPT_KEY_KEEP -3
145
146/**
147 * Special key value for options to discard
148 *
149 * Argument is not passed to processing function, but behave as if the
150 * processing function returned zero
151 */
152#define FUSE_OPT_KEY_DISCARD -4
153
154/**
155 * Processing function
156 *
157 * This function is called if
158 *    - option did not match any 'struct fuse_opt'
159 *    - argument is a non-option
160 *    - option did match and offset was set to -1
161 *
162 * The 'arg' parameter will always contain the whole argument or
163 * option including the parameter if exists.  A two-argument option
164 * ("-x foo") is always converted to single argument option of the
165 * form "-xfoo" before this function is called.
166 *
167 * Options of the form '-ofoo' are passed to this function without the
168 * '-o' prefix.
169 *
170 * The return value of this function determines whether this argument
171 * is to be inserted into the output argument vector, or discarded.
172 *
173 * @param data is the user data passed to the fuse_opt_parse() function
174 * @param arg is the whole argument or option
175 * @param key determines why the processing function was called
176 * @param outargs the current output argument list
177 * @return -1 on error, 0 if arg is to be discarded, 1 if arg should be kept
178 */
179typedef int (*fuse_opt_proc_t)(void *data, const char *arg, int key,
180			       struct fuse_args *outargs);
181
182/**
183 * Option parsing function
184 *
185 * If 'args' was returned from a previous call to fuse_opt_parse() or
186 * it was constructed from
187 *
188 * A NULL 'args' is equivalent to an empty argument vector
189 *
190 * A NULL 'opts' is equivalent to an 'opts' array containing a single
191 * end marker
192 *
193 * A NULL 'proc' is equivalent to a processing function always
194 * returning '1'
195 *
196 * @param args is the input and output argument list
197 * @param data is the user data
198 * @param opts is the option description array
199 * @param proc is the processing function
200 * @return -1 on error, 0 on success
201 */
202int fuse_opt_parse(struct fuse_args *args, void *data,
203		   const struct fuse_opt opts[], fuse_opt_proc_t proc);
204
205/**
206 * Add an option to a comma separated option list
207 *
208 * @param opts is a pointer to an option list, may point to a NULL value
209 * @param opt is the option to add
210 * @return -1 on allocation error, 0 on success
211 */
212int fuse_opt_add_opt(char **opts, const char *opt);
213
214/**
215 * Add an option, escaping commas, to a comma separated option list
216 *
217 * @param opts is a pointer to an option list, may point to a NULL value
218 * @param opt is the option to add
219 * @return -1 on allocation error, 0 on success
220 */
221int fuse_opt_add_opt_escaped(char **opts, const char *opt);
222
223/**
224 * Add an argument to a NULL terminated argument vector
225 *
226 * @param args is the structure containing the current argument list
227 * @param arg is the new argument to add
228 * @return -1 on allocation error, 0 on success
229 */
230int fuse_opt_add_arg(struct fuse_args *args, const char *arg);
231
232/**
233 * Add an argument at the specified position in a NULL terminated
234 * argument vector
235 *
236 * Adds the argument to the N-th position.  This is useful for adding
237 * options at the beginning of the array which must not come after the
238 * special '--' option.
239 *
240 * @param args is the structure containing the current argument list
241 * @param pos is the position at which to add the argument
242 * @param arg is the new argument to add
243 * @return -1 on allocation error, 0 on success
244 */
245int fuse_opt_insert_arg(struct fuse_args *args, int pos, const char *arg);
246
247/**
248 * Free the contents of argument list
249 *
250 * The structure itself is not freed
251 *
252 * @param args is the structure containing the argument list
253 */
254void fuse_opt_free_args(struct fuse_args *args);
255
256
257/**
258 * Check if an option matches
259 *
260 * @param opts is the option description array
261 * @param opt is the option to match
262 * @return 1 if a match is found, 0 if not
263 */
264int fuse_opt_match(const struct fuse_opt opts[], const char *opt);
265
266#ifdef __cplusplus
267}
268#endif
269
270#endif /* _FUSE_OPT_H_ */
271