Home | History | Annotate | Line # | Download | only in librefuse
      1 /* $NetBSD: fuse.h,v 1.36 2025/01/26 02:06:39 pho Exp $ */
      2 
      3 /*
      4  * Copyright  2007 Alistair Crooks.  All rights reserved.
      5  *
      6  * Redistribution and use in source and binary forms, with or without
      7  * modification, are permitted provided that the following conditions
      8  * are met:
      9  * 1. Redistributions of source code must retain the above copyright
     10  *    notice, this list of conditions and the following disclaimer.
     11  * 2. Redistributions in binary form must reproduce the above copyright
     12  *    notice, this list of conditions and the following disclaimer in the
     13  *    documentation and/or other materials provided with the distribution.
     14  * 3. The name of the author may not be used to endorse or promote
     15  *    products derived from this software without specific prior written
     16  *    permission.
     17  *
     18  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
     19  * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
     20  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
     21  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
     22  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
     23  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
     24  * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
     25  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
     26  * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
     27  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
     28  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     29  */
     30 #ifndef FUSE_H_
     31 #define FUSE_H_	20211204
     32 
     33 #include <fcntl.h>
     34 #include <fuse_opt.h>
     35 #include <refuse/buf.h>
     36 #include <refuse/chan.h>
     37 #include <refuse/legacy.h>
     38 #include <refuse/poll.h>
     39 #include <refuse/session.h>
     40 #include <sys/cdefs.h>
     41 #include <sys/stat.h>
     42 #include <sys/statvfs.h>
     43 #include <sys/types.h>
     44 #include <utime.h>
     45 
     46 /* This used to be (maj) * 10 + (min) until FUSE 3.10, and then
     47  * changed to (maj) * 100 + (min). We can't just use the "newer"
     48  * definition because filesystems in the wild still use the older one
     49  * in their FUSE_USE_VERSION request. */
     50 #define FUSE_MAKE_VERSION(maj, min)					\
     51 	(((maj) > 3 || ((maj) == 3 && (min) >= 10))			\
     52 	? (maj) * 100 + (min)						\
     53 	: (maj) *  10 + (min))
     54 
     55 /* The latest version of FUSE API currently provided by ReFUSE. This
     56  * is an implementation detail. User code should not rely on this
     57  * constant. */
     58 #define _REFUSE_MAJOR_VERSION_	3
     59 #define _REFUSE_MINOR_VERSION_	10
     60 
     61 #define _REFUSE_VERSION_	FUSE_MAKE_VERSION(_REFUSE_MAJOR_VERSION_, _REFUSE_MINOR_VERSION_)
     62 
     63 /* FUSE_USE_VERSION is expected to be defined by user code to
     64  * determine the API to be used. Although defining this macro is
     65  * mandatory in the original FUSE implementation, refuse hasn't
     66  * required this so we only emit a warning if it's undefined. */
     67 #if defined(FUSE_USE_VERSION)
     68 #	if FUSE_USE_VERSION > _REFUSE_VERSION_
     69 #		warning "The requested API version is higher than the latest one supported by refuse."
     70 #	elif FUSE_USE_VERSION < 11
     71 #		warning "The requested API version is lower than the oldest one supported by refuse."
     72 #	endif
     73 #else
     74 #	if !defined(_REFUSE_IMPLEMENTATION_)
     75 #		warning "User code including <fuse.h> should define FUSE_USE_VERSION before including this header. Defaulting to the latest version."
     76 #		define FUSE_USE_VERSION	_REFUSE_VERSION_
     77 #	endif
     78 #endif
     79 
     80 /* FUSE_VERSION is supposed to be the latest version of FUSE API
     81  * supported by the library. However, due to the way how original FUSE
     82  * is implemented, some filesystems set FUSE_USE_VERSION to some old
     83  * one and then expect the actual API version exposed by the library
     84  * to be something newer if FUSE_VERSION is higher than that. ReFUSE
     85  * doesn't work that way, so this has to be always identical to
     86  * FUSE_USE_VERSION.
     87  */
     88 #if defined(FUSE_USE_VERSION)
     89 #	define FUSE_VERSION		FUSE_USE_VERSION
     90 #	define FUSE_MAJOR_VERSION	(FUSE_VERSION / 10)
     91 #	define FUSE_MINOR_VERSION	(FUSE_VERSION % 10)
     92 #endif
     93 
     94 #ifdef __cplusplus
     95 extern "C" {
     96 #endif
     97 
     98 struct fuse;
     99 
    100 struct fuse_file_info {
    101 	int32_t		flags;
    102 	uint32_t	fh_old;			/* Removed as of FUSE 3.0. */
    103 	int32_t		writepage:1;
    104 	uint32_t	direct_io:1;
    105 	uint32_t	keep_cache:1;
    106 	uint32_t	flush:1;
    107 	uint32_t	nonseekable:1;		/* Added on FUSE 2.8. */
    108 	uint32_t	flock_release:1;	/* Added on FUSE 2.9. */
    109 	uint32_t	cache_readdir:1;	/* Added on FUSE 3.5. */
    110 	uint32_t	padding:26;
    111 	uint64_t	fh;
    112 	uint64_t	lock_owner;		/* Added on FUSE 2.6. */
    113 	uint32_t	poll_events;		/* Added on FUSE 3.0. */
    114 };
    115 
    116 struct fuse_conn_info {
    117 	uint32_t	proto_major;
    118 	uint32_t	proto_minor;
    119 	uint32_t	async_read;		/* Removed as of FUSE 3.0. */
    120 	uint32_t	max_write;
    121 	uint32_t	max_read;		/* Added on FUSE 3.0. */
    122 	uint32_t	max_readahead;
    123 	uint32_t	capable;		/* Added on FUSE 2.8. */
    124 	uint32_t	want;			/* Added on FUSE 2.8. */
    125 	uint32_t	max_background;		/* Added on FUSE 3.0. */
    126 	uint32_t	congestion_threshold;	/* Added on FUSE 3.0. */
    127 	uint32_t	time_gran;		/* Added on FUSE 3.0. */
    128 	uint32_t	reserved[22];
    129 };
    130 
    131 /* equivalent'ish of puffs_cc */
    132 struct fuse_context {
    133 	struct fuse	*fuse;
    134 	uid_t		uid;
    135 	gid_t		gid;
    136 	pid_t		pid;
    137 	void		*private_data;
    138 	mode_t		umask;			/* Added on FUSE 2.8. */
    139 };
    140 
    141 /* Capability bits for fuse_conn_info.capable and
    142  * fuse_conn_info.want */
    143 #define FUSE_CAP_ASYNC_READ		(1 << 0)
    144 #define FUSE_CAP_POSIX_LOCKS		(1 << 1)
    145 #define FUSE_CAP_ATOMIC_O_TRUNC		(1 << 3)
    146 #define FUSE_CAP_EXPORT_SUPPORT		(1 << 4)
    147 #define FUSE_CAP_BIG_WRITES		(1 << 5)	/* Removed as of FUSE 3.0. */
    148 #define FUSE_CAP_DONT_MASK		(1 << 6)
    149 #define FUSE_CAP_SPLICE_WRITE		(1 << 7)	/* Added on FUSE 3.0. */
    150 #define FUSE_CAP_SPLICE_MOVE		(1 << 8)	/* Added on FUSE 3.0. */
    151 #define FUSE_CAP_SPLICE_READ		(1 << 9)	/* Added on FUSE 3.0. */
    152 #define FUSE_CAP_FLOCK_LOCKS		(1 << 10)	/* Added on FUSE 3.0. */
    153 #define FUSE_CAP_IOCTL_DIR		(1 << 11)	/* Added on FUSE 3.0. */
    154 #define FUSE_CAP_AUTO_INVAL_DATA	(1 << 12)	/* Added on FUSE 3.0. */
    155 #define FUSE_CAP_READDIRPLUS		(1 << 13)	/* Added on FUSE 3.0. */
    156 #define FUSE_CAP_READDIRPLUS_AUTO	(1 << 14)	/* Added on FUSE 3.0. */
    157 #define FUSE_CAP_ASYNC_DIO		(1 << 15)	/* Added on FUSE 3.0. */
    158 #define FUSE_CAP_WRITEBACK_CACHE	(1 << 16)	/* Added on FUSE 3.0. */
    159 #define FUSE_CAP_NO_OPEN_SUPPORT	(1 << 17)	/* Added on FUSE 3.0. */
    160 #define FUSE_CAP_PARALLEL_DIROPS	(1 << 18)	/* Added on FUSE 3.0. */
    161 #define FUSE_CAP_POSIX_ACL		(1 << 19)	/* Added on FUSE 3.0. */
    162 #define FUSE_CAP_HANDLE_KILLPRIV	(1 << 20)	/* Added on FUSE 3.0. */
    163 #define FUSE_CAP_CACHE_SYMLINKS		(1 << 23)	/* Added on FUSE 3.10. */
    164 #define FUSE_CAP_NO_OPENDIR_SUPPORT	(1 << 24)	/* Added on FUSE 3.5. */
    165 
    166 /* ioctl flags */
    167 #define FUSE_IOCTL_COMPAT	(1 << 0)
    168 #define FUSE_IOCTL_UNRESTRICTED	(1 << 1)
    169 #define FUSE_IOCTL_RETRY	(1 << 2)
    170 #define FUSE_IOCTL_DIR		(1 << 4)	/* Added on FUSE 2.9. */
    171 #define FUSE_IOCTL_MAX_IOV	256
    172 
    173 /* readdir() flags, appeared on FUSE 3.0. */
    174 enum fuse_readdir_flags {
    175 	FUSE_READDIR_PLUS	= (1 << 0),
    176 };
    177 enum fuse_fill_dir_flags {
    178 	FUSE_FILL_DIR_PLUS	= (1 << 1),
    179 };
    180 
    181 /* Configuration of the high-level API, appeared on FUSE 3.0. */
    182 struct fuse_config {
    183 	int		set_gid;
    184 	unsigned int	gid;
    185 	int		set_uid;
    186 	unsigned int	uid;
    187 	int		set_mode;
    188 	unsigned int	umask;
    189 	double		entry_timeout;
    190 	double		negative_timeout;
    191 	double		attr_timeout;
    192 	int		intr;
    193 	int		intr_signal;
    194 	int		remember;
    195 	int		hard_remove;
    196 	int		use_ino;
    197 	int		readdir_ino;
    198 	int		direct_io;
    199 	int		kernel_cache;
    200 	int		auto_cache;
    201 	int		ac_attr_timeout_set;
    202 	double		ac_attr_timeout;
    203 	int		nullpath_ok;
    204 };
    205 
    206 /* Configuration of fuse_loop_mt(), appeared on FUSE 3.2. */
    207 struct fuse_loop_config {
    208 	int		clone_fd;
    209 	unsigned int	max_idle_threads;
    210 };
    211 
    212 /**
    213  * Argument list
    214  */
    215 struct fuse_args {
    216 	int	argc;
    217 	char	**argv;
    218 	int	allocated;
    219 };
    220 
    221 /**
    222  * Initializer for 'struct fuse_args'
    223  */
    224 #define FUSE_ARGS_INIT(argc, argv) { argc, argv, 0 }
    225 
    226 /* Functions that have existed since the beginning and have never
    227  * changed between API versions. */
    228 int fuse_loop(struct fuse *);
    229 void fuse_exit(struct fuse *);
    230 struct fuse_context *fuse_get_context(void);
    231 
    232 /* Print available library options. Appeared on FUSE 3.1. */
    233 void fuse_lib_help(struct fuse_args *args);
    234 
    235 /* Daemonize the calling process. Appeared on FUSE 2.6.
    236  *
    237  * NOTE: This function used to have a wrong prototype in librefuse at
    238  * the time when FUSE_H_ < 20211204. */
    239 int fuse_daemonize(int foreground) __RENAME(fuse_daemonize_rev1);
    240 
    241 /* Check if a request has been interrupted. Appeared on FUSE 2.6. */
    242 int fuse_interrupted(void);
    243 
    244 /* Invalidate cache for a given path. Appeared on FUSE 3.2. */
    245 int fuse_invalidate_path(struct fuse *fuse, const char *path);
    246 
    247 /* Get the version number of the library. Appeared on FUSE 2.7. */
    248 int fuse_version(void);
    249 
    250 /* Get the version string of the library. Appeared on FUSE 3.0. */
    251 const char *fuse_pkgversion(void);
    252 
    253 /* Get the current supplementary group IDs for the current request, or
    254  * return -errno on failure. Appeared on FUSE 2.8. */
    255 int fuse_getgroups(int size, gid_t list[]);
    256 
    257 /* Start the cleanup thread when using option "-oremember". Appeared
    258  * on FUSE 2.9. */
    259 int fuse_start_cleanup_thread(struct fuse *fuse);
    260 
    261 /* Stop the cleanup thread when using "-oremember". Appeared on FUSE
    262  * 2.9. */
    263 void fuse_stop_cleanup_thread(struct fuse *fuse);
    264 
    265 /* Iterate over cache removing stale entries, used in conjunction with
    266  * "-oremember". Return the number of seconds until the next
    267  * cleanup. Appeared on FUSE 2.9. */
    268 int fuse_clean_cache(struct fuse *fuse);
    269 
    270 /* Generic implementation of fuse_main(). The exact type of "op" is
    271  * determined by op_version. This is only an implementation detail:
    272  * user code should never call this directly. */
    273 int __fuse_main(int argc, char* argv[],
    274 		const void* op, int op_version, void* user_data);
    275 
    276 /* NOTE: Compatibility headers are included
    277  * unconditionally. Declarations in these headers all have a version
    278  * postfix, and need to be aliased depending on FUSE_USE_VERSION. */
    279 #include <refuse/v11.h>
    280 #include <refuse/v21.h>
    281 #include <refuse/v22.h>
    282 #include <refuse/v23.h>
    283 #include <refuse/v25.h>
    284 #include <refuse/v26.h>
    285 #include <refuse/v28.h>
    286 #include <refuse/v29.h>
    287 #include <refuse/v30.h>
    288 #include <refuse/v32.h>
    289 #include <refuse/v34.h>
    290 #include <refuse/v35.h>
    291 #include <refuse/v38.h>
    292 
    293 /* NOTE: refuse/fs.h relies on some typedef's in refuse/v*.h */
    294 #include <refuse/fs.h>
    295 
    296 #define _MK_FUSE_OPERATIONS_(VER)	__CONCAT(fuse_operations_v,VER)
    297 
    298 /* Version specific types and functions. */
    299 #if defined(FUSE_USE_VERSION)
    300 /* ===== FUSE 1.x ===== */
    301 #	if FUSE_USE_VERSION < 21
    302 		/* Types */
    303 #		define _FUSE_OP_VERSION__	11 /* Implementation detail */
    304 #		define fuse_dirfil_t		fuse_dirfil_t_v11
    305 #		define fuse_operations		_MK_FUSE_OPERATIONS_(_FUSE_OP_VERSION__)
    306 		/* Functions */
    307 static __inline int
    308 fuse_main(int argc, char *argv[], const struct fuse_operations *op) {
    309     return __fuse_main(argc, argv, op, _FUSE_OP_VERSION__, NULL);
    310 }
    311 #		define fuse_mount		fuse_mount_v11
    312 #		define fuse_unmount		fuse_unmount_v11
    313 static __inline struct fuse *
    314 fuse_new(int fd, int flags, const struct fuse_operations *op) {
    315     return fuse_new_v11(fd, flags, op, _FUSE_OP_VERSION__);
    316 }
    317 #		define fuse_destroy		fuse_destroy_v11
    318 #		define fuse_loop_mt		fuse_loop_mt_v11
    319 
    320 /* ===== FUSE 2.1 ===== */
    321 #	elif FUSE_USE_VERSION == 21
    322 		/* Types */
    323 #		define _FUSE_OP_VERSION__	21
    324 #		define fuse_dirfil_t		fuse_dirfil_t_v11
    325 #		define fuse_operations		_MK_FUSE_OPERATIONS_(_FUSE_OP_VERSION__)
    326 		/* Functions */
    327 static __inline int
    328 fuse_main(int argc, char *argv[], const struct fuse_operations *op) {
    329     return __fuse_main(argc, argv, op, _FUSE_OP_VERSION__, NULL);
    330 }
    331 #		define fuse_mount		fuse_mount_v21
    332 #		define fuse_unmount		fuse_unmount_v11
    333 static __inline struct fuse *
    334 fuse_new(int fd, const char *opts, const struct fuse_operations *op) {
    335     return fuse_new_v21(fd, opts, op, _FUSE_OP_VERSION__, NULL);
    336 }
    337 #		define fuse_destroy		fuse_destroy_v11
    338 #		define fuse_loop_mt		fuse_loop_mt_v11
    339 
    340 /* ===== FUSE 2.2 ===== */
    341 #	elif FUSE_USE_VERSION == 22
    342 		/* Types */
    343 #		define _FUSE_OP_VERSION__	22
    344 #		define fuse_dirfil_t		fuse_dirfil_t_v22
    345 #		define fuse_operations		_MK_FUSE_OPERATIONS_(_FUSE_OP_VERSION__)
    346 		/* Functions */
    347 static __inline int
    348 fuse_main(int argc, char *argv[], const struct fuse_operations *op) {
    349     return __fuse_main(argc, argv, op, _FUSE_OP_VERSION__, NULL);
    350 }
    351 #		define fuse_mount		fuse_mount_v21
    352 #		define fuse_unmount		fuse_unmount_v11
    353 static __inline struct fuse *
    354 fuse_new(int fd, const char *opts, const struct fuse_operations *op) {
    355     return fuse_new_v21(fd, opts, op, _FUSE_OP_VERSION__, NULL);
    356 }
    357 #		define fuse_destroy		fuse_destroy_v11
    358 #		define fuse_loop_mt		fuse_loop_mt_v11
    359 static __inline struct fuse *
    360 fuse_setup(int argc, char *argv[], const struct fuse_operations *op,
    361 	   size_t op_size __attribute__((__unused__)),
    362 	   char **mountpoint, int *multithreaded, int *fd) {
    363     return fuse_setup_v22(argc, argv, op, _FUSE_OP_VERSION__,
    364 			  mountpoint, multithreaded, fd);
    365 }
    366 #		define fuse_teardown		fuse_teardown_v22
    367 
    368 /* ===== FUSE 2.3, 2.4 ===== */
    369 #	elif FUSE_USE_VERSION >= 23 && FUSE_USE_VERSION <= 24
    370 		/* Types */
    371 #		define _FUSE_OP_VERSION__	23
    372 #		define fuse_dirfil_t		fuse_dirfil_t_v22
    373 #		define fuse_fill_dir_t		fuse_fill_dir_t_v23
    374 #		define fuse_operations		_MK_FUSE_OPERATIONS_(_FUSE_OP_VERSION__)
    375 		/* Functions */
    376 static __inline int
    377 fuse_main(int argc, char *argv[], const struct fuse_operations *op) {
    378     return __fuse_main(argc, argv, op, _FUSE_OP_VERSION__, NULL);
    379 }
    380 #		define fuse_mount		fuse_mount_v21
    381 #		define fuse_unmount		fuse_unmount_v11
    382 static __inline struct fuse *
    383 fuse_new(int fd, const char *opts, const struct fuse_operations *op,
    384 	 size_t op_size __attribute__((__unused__))) {
    385     return fuse_new_v21(fd, opts, op, _FUSE_OP_VERSION__, NULL);
    386 }
    387 #		define fuse_destroy		fuse_destroy_v11
    388 #		define fuse_loop_mt		fuse_loop_mt_v11
    389 static __inline struct fuse *
    390 fuse_setup(int argc, char *argv[], const struct fuse_operations *op,
    391 	   size_t op_size __attribute__((__unused__)),
    392 	   char **mountpoint, int *multithreaded, int *fd) {
    393     return fuse_setup_v22(argc, argv, op, _FUSE_OP_VERSION__,
    394 			  mountpoint, multithreaded, fd);
    395 }
    396 #		define fuse_teardown		fuse_teardown_v22
    397 
    398 /* ===== FUSE 2.5 ===== */
    399 #	elif FUSE_USE_VERSION == 25
    400 		/* Types */
    401 #		define _FUSE_OP_VERSION__	25
    402 #		define fuse_dirfil_t		fuse_dirfil_t_v22
    403 #		define fuse_fill_dir_t		fuse_fill_dir_t_v23
    404 #		define fuse_operations		_MK_FUSE_OPERATIONS_(_FUSE_OP_VERSION__)
    405 		/* Functions */
    406 static __inline int
    407 fuse_main(int argc, char *argv[], const struct fuse_operations *op) {
    408     return __fuse_main(argc, argv, op, _FUSE_OP_VERSION__, NULL);
    409 }
    410 #		define fuse_mount		fuse_mount_v25
    411 #		define fuse_unmount		fuse_unmount_v11
    412 static __inline struct fuse *
    413 fuse_new(int fd, struct fuse_args *args, const struct fuse_operations *op,
    414 	 size_t op_size __attribute__((__unused__))) {
    415     return fuse_new_v25(fd, args, op, _FUSE_OP_VERSION__, NULL);
    416 }
    417 #		define fuse_destroy		fuse_destroy_v11
    418 #		define fuse_loop_mt		fuse_loop_mt_v11
    419 static __inline struct fuse *
    420 fuse_setup(int argc, char *argv[], const struct fuse_operations *op,
    421 	   size_t op_size __attribute__((__unused__)),
    422 	   char **mountpoint, int *multithreaded, int *fd) {
    423     return fuse_setup_v22(argc, argv, op, _FUSE_OP_VERSION__,
    424 			  mountpoint, multithreaded, fd);
    425 }
    426 #		define fuse_teardown		fuse_teardown_v22
    427 #		define fuse_parse_cmdline	fuse_parse_cmdline_v25
    428 
    429 /* ===== FUSE 2.6, 2.7 ===== */
    430 #	elif FUSE_USE_VERSION >= 26 && FUSE_USE_VERSION <= 27
    431 		/* Types */
    432 #		define _FUSE_OP_VERSION__	26
    433 #		define fuse_dirfil_t		fuse_dirfil_t_v22
    434 #		define fuse_fill_dir_t		fuse_fill_dir_t_v23
    435 #		define fuse_operations		_MK_FUSE_OPERATIONS_(_FUSE_OP_VERSION__)
    436 		/* Functions */
    437 static __inline struct fuse_fs *
    438 fuse_fs_new(const struct fuse_operations *op,
    439 	    size_t op_size __attribute__((__unused__)), void *user_data) {
    440     return __fuse_fs_new(op, _FUSE_OP_VERSION__, user_data);
    441 }
    442 #		define fuse_fs_getattr		fuse_fs_getattr_v27
    443 #		define fuse_fs_rename		fuse_fs_rename_v27
    444 #		define fuse_fs_chmod		fuse_fs_chmod_v27
    445 #		define fuse_fs_chown		fuse_fs_chown_v27
    446 #		define fuse_fs_readdir		fuse_fs_readdir_v27
    447 #		define fuse_fs_truncate		fuse_fs_truncate_v27
    448 #		define fuse_fs_utimens		fuse_fs_utimens_v27
    449 #		define fuse_fs_init		fuse_fs_init_v27
    450 static __inline int
    451 fuse_main(int argc, char *argv[], const struct fuse_operations *op, void* user_data) {
    452     return __fuse_main(argc, argv, op, _FUSE_OP_VERSION__, user_data);
    453 }
    454 #		define fuse_mount		fuse_mount_v26
    455 #		define fuse_unmount		fuse_unmount_v26
    456 static __inline struct fuse *
    457 fuse_new(struct fuse_chan *ch, struct fuse_args *args,
    458 	 const struct fuse_operations *op,
    459 	 size_t op_size __attribute__((__unused__)), void *user_data) {
    460     return fuse_new_v26(ch, args, op, _FUSE_OP_VERSION__, user_data);
    461 }
    462 #		define fuse_destroy		fuse_destroy_v11
    463 #		define fuse_loop_mt		fuse_loop_mt_v11
    464 static __inline struct fuse *
    465 fuse_setup(int argc, char *argv[], const struct fuse_operations *op,
    466 	   size_t op_size __attribute__((__unused__)),
    467 	   char **mountpoint, int *multithreaded, void *user_data) {
    468     return fuse_setup_v26(argc, argv, op, _FUSE_OP_VERSION__,
    469 			  mountpoint, multithreaded, user_data);
    470 }
    471 #		define fuse_teardown		fuse_teardown_v26
    472 #		define fuse_parse_cmdline	fuse_parse_cmdline_v25
    473 
    474 /* ===== FUSE 2.8 ===== */
    475 #	elif FUSE_USE_VERSION == 28
    476 		/* Types */
    477 #		define _FUSE_OP_VERSION__	28
    478 #		define fuse_dirfil_t		fuse_dirfil_t_v22
    479 #		define fuse_fill_dir_t		fuse_fill_dir_t_v23
    480 #		define fuse_operations		_MK_FUSE_OPERATIONS_(_FUSE_OP_VERSION__)
    481 		/* Functions */
    482 static __inline struct fuse_fs *
    483 fuse_fs_new(const struct fuse_operations *op,
    484 	    size_t op_size __attribute__((__unused__)), void *user_data) {
    485     return __fuse_fs_new(op, _FUSE_OP_VERSION__, user_data);
    486 }
    487 #		define fuse_fs_getattr		fuse_fs_getattr_v27
    488 #		define fuse_fs_rename		fuse_fs_rename_v27
    489 #		define fuse_fs_chmod		fuse_fs_chmod_v27
    490 #		define fuse_fs_chown		fuse_fs_chown_v27
    491 #		define fuse_fs_readdir		fuse_fs_readdir_v27
    492 #		define fuse_fs_truncate		fuse_fs_truncate_v27
    493 #		define fuse_fs_utimens		fuse_fs_utimens_v27
    494 #		define fuse_fs_ioctl		fuse_fs_ioctl_v28
    495 #		define fuse_fs_init		fuse_fs_init_v27
    496 static __inline int
    497 fuse_main(int argc, char *argv[], const struct fuse_operations *op, void* user_data) {
    498     return __fuse_main(argc, argv, op, _FUSE_OP_VERSION__, user_data);
    499 }
    500 #		define fuse_mount		fuse_mount_v26
    501 #		define fuse_unmount		fuse_unmount_v26
    502 static __inline struct fuse *
    503 fuse_new(struct fuse_chan *ch, struct fuse_args *args,
    504 	 const struct fuse_operations *op,
    505 	 size_t op_size __attribute__((__unused__)), void *user_data) {
    506     return fuse_new_v26(ch, args, op, _FUSE_OP_VERSION__, user_data);
    507 }
    508 #		define fuse_destroy		fuse_destroy_v11
    509 #		define fuse_loop_mt		fuse_loop_mt_v11
    510 static __inline struct fuse *
    511 fuse_setup(int argc, char *argv[], const struct fuse_operations *op,
    512 	   size_t op_size __attribute__((__unused__)),
    513 	   char **mountpoint, int *multithreaded, void *user_data) {
    514     return fuse_setup_v26(argc, argv, op, _FUSE_OP_VERSION__,
    515 			  mountpoint, multithreaded, user_data);
    516 }
    517 #		define fuse_teardown		fuse_teardown_v26
    518 #		define fuse_parse_cmdline	fuse_parse_cmdline_v25
    519 
    520 /* ===== FUSE 2.9 ===== */
    521 #	elif FUSE_USE_VERSION == 29
    522 		/* Types */
    523 #		define _FUSE_OP_VERSION__	29
    524 #		define fuse_dirfil_t		fuse_dirfil_t_v22
    525 #		define fuse_fill_dir_t		fuse_fill_dir_t_v23
    526 #		define fuse_operations		_MK_FUSE_OPERATIONS_(_FUSE_OP_VERSION__)
    527 		/* Functions */
    528 static __inline struct fuse_fs *
    529 fuse_fs_new(const struct fuse_operations *op,
    530 	    size_t op_size __attribute__((__unused__)), void *user_data) {
    531     return __fuse_fs_new(op, _FUSE_OP_VERSION__, user_data);
    532 }
    533 #		define fuse_fs_getattr		fuse_fs_getattr_v27
    534 #		define fuse_fs_rename		fuse_fs_rename_v27
    535 #		define fuse_fs_chmod		fuse_fs_chmod_v27
    536 #		define fuse_fs_chown		fuse_fs_chown_v27
    537 #		define fuse_fs_readdir		fuse_fs_readdir_v27
    538 #		define fuse_fs_truncate		fuse_fs_truncate_v27
    539 #		define fuse_fs_utimens		fuse_fs_utimens_v27
    540 #		define fuse_fs_ioctl		fuse_fs_ioctl_v28
    541 #		define fuse_fs_init		fuse_fs_init_v27
    542 static __inline int
    543 fuse_main(int argc, char *argv[], const struct fuse_operations *op, void* user_data) {
    544     return __fuse_main(argc, argv, op, _FUSE_OP_VERSION__, user_data);
    545 }
    546 #		define fuse_mount		fuse_mount_v26
    547 #		define fuse_unmount		fuse_unmount_v26
    548 static __inline struct fuse *
    549 fuse_new(struct fuse_chan *ch, struct fuse_args *args,
    550 	 const struct fuse_operations *op,
    551 	 size_t op_size __attribute__((__unused__)), void *user_data) {
    552     return fuse_new_v26(ch, args, op, _FUSE_OP_VERSION__, user_data);
    553 }
    554 #		define fuse_destroy		fuse_destroy_v11
    555 #		define fuse_loop_mt		fuse_loop_mt_v11
    556 static __inline struct fuse *
    557 fuse_setup(int argc, char *argv[], const struct fuse_operations *op,
    558 	   size_t op_size __attribute__((__unused__)),
    559 	   char **mountpoint, int *multithreaded, void *user_data) {
    560     return fuse_setup_v26(argc, argv, op, _FUSE_OP_VERSION__,
    561 			  mountpoint, multithreaded, user_data);
    562 }
    563 #		define fuse_teardown		fuse_teardown_v26
    564 #		define fuse_parse_cmdline	fuse_parse_cmdline_v25
    565 
    566 /* ===== FUSE 3.0, 3.1 ===== */
    567 #	elif FUSE_USE_VERSION >= 30 && FUSE_USE_VERSION <= 31
    568 		/* Types */
    569 #		define _FUSE_OP_VERSION__	30
    570 #		define fuse_fill_dir_t		fuse_fill_dir_t_v30
    571 #		define fuse_operations		_MK_FUSE_OPERATIONS_(_FUSE_OP_VERSION__)
    572 		/* Functions */
    573 static __inline struct fuse_fs *
    574 fuse_fs_new(const struct fuse_operations *op,
    575 	    size_t op_size __attribute__((__unused__)), void *user_data) {
    576     return __fuse_fs_new(op, _FUSE_OP_VERSION__, user_data);
    577 }
    578 #		define fuse_fs_getattr		fuse_fs_getattr_v30
    579 #		define fuse_fs_rename		fuse_fs_rename_v30
    580 #		define fuse_fs_chmod		fuse_fs_chmod_v30
    581 #		define fuse_fs_chown		fuse_fs_chown_v30
    582 #		define fuse_fs_readdir		fuse_fs_readdir_v30
    583 #		define fuse_fs_truncate		fuse_fs_truncate_v30
    584 #		define fuse_fs_utimens		fuse_fs_utimens_v30
    585 #		define fuse_fs_ioctl		fuse_fs_ioctl_v28
    586 #		define fuse_fs_init		fuse_fs_init_v30
    587 static __inline int
    588 fuse_main(int argc, char *argv[], const struct fuse_operations *op, void* user_data) {
    589     return __fuse_main(argc, argv, op, _FUSE_OP_VERSION__, user_data);
    590 }
    591 #		define fuse_mount		fuse_mount_v30
    592 #		define fuse_unmount		fuse_unmount_v30
    593 static __inline struct fuse *
    594 fuse_new(struct fuse_args *args, const struct fuse_operations *op,
    595 	 size_t op_size __attribute__((__unused__)), void *user_data) {
    596     return fuse_new_v30(args, op, _FUSE_OP_VERSION__, user_data);
    597 }
    598 #		define fuse_destroy		fuse_destroy_v30
    599 #		define fuse_loop_mt		fuse_loop_mt_v30
    600 		/* fuse_setup(3) and fuse_teardown(3) have been removed as of FUSE 3.0. */
    601 #		define fuse_parse_cmdline	fuse_parse_cmdline_v30
    602 
    603 /* ===== FUSE 3.2, 3.3 ===== */
    604 #	elif FUSE_USE_VERSION >= 32 && FUSE_USE_VERSION <= 33
    605 		/* Types */
    606 #		define _FUSE_OP_VERSION__	30
    607 #		define fuse_fill_dir_t		fuse_fill_dir_t_v30
    608 #		define fuse_operations		_MK_FUSE_OPERATIONS_(_FUSE_OP_VERSION__)
    609 		/* Functions */
    610 static __inline struct fuse_fs *
    611 fuse_fs_new(const struct fuse_operations *op,
    612 	    size_t op_size __attribute__((__unused__)), void *user_data) {
    613     return __fuse_fs_new(op, _FUSE_OP_VERSION__, user_data);
    614 }
    615 #		define fuse_fs_getattr		fuse_fs_getattr_v30
    616 #		define fuse_fs_rename		fuse_fs_rename_v30
    617 #		define fuse_fs_chmod		fuse_fs_chmod_v30
    618 #		define fuse_fs_chown		fuse_fs_chown_v30
    619 #		define fuse_fs_readdir		fuse_fs_readdir_v30
    620 #		define fuse_fs_truncate		fuse_fs_truncate_v30
    621 #		define fuse_fs_utimens		fuse_fs_utimens_v30
    622 #		define fuse_fs_ioctl		fuse_fs_ioctl_v28
    623 #		define fuse_fs_init		fuse_fs_init_v30
    624 static __inline int
    625 fuse_main(int argc, char *argv[], const struct fuse_operations *op, void* user_data) {
    626     return __fuse_main(argc, argv, op, _FUSE_OP_VERSION__, user_data);
    627 }
    628 #		define fuse_mount		fuse_mount_v30
    629 #		define fuse_unmount		fuse_unmount_v30
    630 static __inline struct fuse *
    631 fuse_new(struct fuse_args *args, const struct fuse_operations *op,
    632 	 size_t op_size __attribute__((__unused__)), void *user_data) {
    633     return fuse_new_v30(args, op, _FUSE_OP_VERSION__, user_data);
    634 }
    635 #		define fuse_destroy		fuse_destroy_v30
    636 #		define fuse_loop_mt		fuse_loop_mt_v32
    637 #		define fuse_parse_cmdline	fuse_parse_cmdline_v30
    638 
    639 /* ===== FUSE 3.4 ===== */
    640 #	elif FUSE_USE_VERSION == 34
    641 		/* Types */
    642 #		define _FUSE_OP_VERSION__	34
    643 #		define fuse_fill_dir_t		fuse_fill_dir_t_v30
    644 #		define fuse_operations		_MK_FUSE_OPERATIONS_(_FUSE_OP_VERSION__)
    645 		/* Functions */
    646 static __inline struct fuse_fs *
    647 fuse_fs_new(const struct fuse_operations *op,
    648 	    size_t op_size __attribute__((__unused__)), void *user_data) {
    649     return __fuse_fs_new(op, _FUSE_OP_VERSION__, user_data);
    650 }
    651 #		define fuse_fs_getattr		fuse_fs_getattr_v30
    652 #		define fuse_fs_rename		fuse_fs_rename_v30
    653 #		define fuse_fs_chmod		fuse_fs_chmod_v30
    654 #		define fuse_fs_chown		fuse_fs_chown_v30
    655 #		define fuse_fs_readdir		fuse_fs_readdir_v30
    656 #		define fuse_fs_truncate		fuse_fs_truncate_v30
    657 #		define fuse_fs_utimens		fuse_fs_utimens_v30
    658 #		define fuse_fs_ioctl		fuse_fs_ioctl_v28
    659 #		define fuse_fs_init		fuse_fs_init_v30
    660 static __inline int
    661 fuse_main(int argc, char *argv[], const struct fuse_operations *op, void* user_data) {
    662     return __fuse_main(argc, argv, op, _FUSE_OP_VERSION__, user_data);
    663 }
    664 #		define fuse_mount		fuse_mount_v30
    665 #		define fuse_unmount		fuse_unmount_v30
    666 static __inline struct fuse *
    667 fuse_new(struct fuse_args *args, const struct fuse_operations *op,
    668 	 size_t op_size __attribute__((__unused__)), void *user_data) {
    669     return fuse_new_v30(args, op, _FUSE_OP_VERSION__, user_data);
    670 }
    671 #		define fuse_destroy		fuse_destroy_v30
    672 #		define fuse_loop_mt		fuse_loop_mt_v32
    673 #		define fuse_parse_cmdline	fuse_parse_cmdline_v30
    674 
    675 /* ===== FUSE 3.5, 3.6, 3.7 ===== */
    676 #	elif FUSE_USE_VERSION >= 35 && FUSE_USE_VERSION <= 37
    677 		/* Types */
    678 #		define _FUSE_OP_VERSION__	35
    679 #		define fuse_fill_dir_t		fuse_fill_dir_t_v30
    680 #		define fuse_operations		_MK_FUSE_OPERATIONS_(_FUSE_OP_VERSION__)
    681 		/* Functions */
    682 static __inline struct fuse_fs *
    683 fuse_fs_new(const struct fuse_operations *op,
    684 	    size_t op_size __attribute__((__unused__)), void *user_data) {
    685     return __fuse_fs_new(op, _FUSE_OP_VERSION__, user_data);
    686 }
    687 #		define fuse_fs_getattr		fuse_fs_getattr_v30
    688 #		define fuse_fs_rename		fuse_fs_rename_v30
    689 #		define fuse_fs_chmod		fuse_fs_chmod_v30
    690 #		define fuse_fs_chown		fuse_fs_chown_v30
    691 #		define fuse_fs_readdir		fuse_fs_readdir_v30
    692 #		define fuse_fs_truncate		fuse_fs_truncate_v30
    693 #		define fuse_fs_utimens		fuse_fs_utimens_v30
    694 #		define fuse_fs_ioctl		fuse_fs_ioctl_v35
    695 #		define fuse_fs_init		fuse_fs_init_v30
    696 static __inline int
    697 fuse_main(int argc, char *argv[], const struct fuse_operations *op, void* user_data) {
    698     return __fuse_main(argc, argv, op, _FUSE_OP_VERSION__, user_data);
    699 }
    700 #		define fuse_mount		fuse_mount_v30
    701 #		define fuse_unmount		fuse_unmount_v30
    702 static __inline struct fuse *
    703 fuse_new(struct fuse_args *args, const struct fuse_operations *op,
    704 	 size_t op_size __attribute__((__unused__)), void *user_data) {
    705     return fuse_new_v30(args, op, _FUSE_OP_VERSION__, user_data);
    706 }
    707 #		define fuse_destroy		fuse_destroy_v30
    708 #		define fuse_loop_mt		fuse_loop_mt_v32
    709 #		define fuse_parse_cmdline	fuse_parse_cmdline_v30
    710 
    711 /* ===== FUSE 3.8, 3.9, 3.10 ===== */
    712 #	elif FUSE_USE_VERSION >= 38 && FUSE_USE_VERSION <= 310
    713 		/* Types */
    714 #		define _FUSE_OP_VERSION__	38
    715 #		define fuse_fill_dir_t		fuse_fill_dir_t_v30
    716 #		define fuse_operations		_MK_FUSE_OPERATIONS_(_FUSE_OP_VERSION__)
    717 		/* Functions */
    718 static __inline struct fuse_fs *
    719 fuse_fs_new(const struct fuse_operations *op,
    720 	    size_t op_size __attribute__((__unused__)), void *user_data) {
    721     return __fuse_fs_new(op, _FUSE_OP_VERSION__, user_data);
    722 }
    723 #		define fuse_fs_getattr		fuse_fs_getattr_v30
    724 #		define fuse_fs_rename		fuse_fs_rename_v30
    725 #		define fuse_fs_chmod		fuse_fs_chmod_v30
    726 #		define fuse_fs_chown		fuse_fs_chown_v30
    727 #		define fuse_fs_readdir		fuse_fs_readdir_v30
    728 #		define fuse_fs_truncate		fuse_fs_truncate_v30
    729 #		define fuse_fs_utimens		fuse_fs_utimens_v30
    730 #		define fuse_fs_ioctl		fuse_fs_ioctl_v35
    731 #		define fuse_fs_init		fuse_fs_init_v30
    732 static __inline int
    733 fuse_main(int argc, char *argv[], const struct fuse_operations *op, void* user_data) {
    734     return __fuse_main(argc, argv, op, _FUSE_OP_VERSION__, user_data);
    735 }
    736 #		define fuse_mount		fuse_mount_v30
    737 #		define fuse_unmount		fuse_unmount_v30
    738 static __inline struct fuse *
    739 fuse_new(struct fuse_args *args, const struct fuse_operations *op,
    740 	 size_t op_size __attribute__((__unused__)), void *user_data) {
    741     return fuse_new_v30(args, op, _FUSE_OP_VERSION__, user_data);
    742 }
    743 #		define fuse_destroy		fuse_destroy_v30
    744 #		define fuse_loop_mt		fuse_loop_mt_v32
    745 #		define fuse_parse_cmdline	fuse_parse_cmdline_v30
    746 
    747 #	endif
    748 #endif /* defined(FUSE_USE_VERSION) */
    749 
    750 #ifdef __cplusplus
    751 }
    752 #endif
    753 
    754 #endif
    755