1241519Sattilio/*- 2241519Sattilio * Copyright (c) 2005 Jean-Sebastien Pedron 3241519Sattilio * Copyright (c) 2005 Csaba Henk 4241519Sattilio * All rights reserved. 5241519Sattilio * 6241519Sattilio * Redistribution and use in source and binary forms, with or without 7241519Sattilio * modification, are permitted provided that the following conditions 8241519Sattilio * are met: 9241519Sattilio * 1. Redistributions of source code must retain the above copyright 10241519Sattilio * notice, this list of conditions and the following disclaimer. 11241519Sattilio * 2. Redistributions in binary form must reproduce the above copyright 12241519Sattilio * notice, this list of conditions and the following disclaimer in the 13241519Sattilio * documentation and/or other materials provided with the distribution. 14241519Sattilio * 15241519Sattilio * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 16241519Sattilio * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 17241519Sattilio * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 18241519Sattilio * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 19241519Sattilio * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 20241519Sattilio * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 21241519Sattilio * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 22241519Sattilio * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 23241519Sattilio * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 24241519Sattilio * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 25241519Sattilio * SUCH DAMAGE. 26241519Sattilio * 27241519Sattilio */ 28241519Sattilio 29241519Sattilio#include <sys/cdefs.h> 30241519Sattilio__FBSDID("$FreeBSD$"); 31241519Sattilio 32241519Sattilio#include <sys/param.h> 33241519Sattilio#include <sys/mount.h> 34241519Sattilio#include <sys/uio.h> 35241519Sattilio#include <sys/stat.h> 36241519Sattilio#include <sys/sysctl.h> 37241519Sattilio 38241519Sattilio#include <err.h> 39241519Sattilio#include <stdio.h> 40241519Sattilio#include <stdlib.h> 41241519Sattilio#include <string.h> 42241519Sattilio#include <sysexits.h> 43241519Sattilio#include <unistd.h> 44241519Sattilio#include <fcntl.h> 45241519Sattilio#include <signal.h> 46241519Sattilio#include <getopt.h> 47241519Sattilio#include <limits.h> 48241519Sattilio#include <osreldate.h> 49241519Sattilio#include <paths.h> 50241519Sattilio 51241519Sattilio#include "mntopts.h" 52241519Sattilio 53241519Sattilio#ifndef FUSE4BSD_VERSION 54241519Sattilio#define FUSE4BSD_VERSION "0.3.9-pre1" 55241519Sattilio#endif 56241519Sattilio 57241519Sattiliovoid __usage_short(void); 58241519Sattiliovoid usage(void); 59241519Sattiliovoid helpmsg(void); 60241519Sattiliovoid showversion(void); 61241519Sattilioint init_backgrounded(void); 62241519Sattilio 63241720Sedstatic struct mntopt mopts[] = { 64241519Sattilio #define ALTF_PRIVATE 0x01 65241519Sattilio { "private", 0, ALTF_PRIVATE, 1 }, 66241519Sattilio { "neglect_shares", 0, 0x02, 1 }, 67241519Sattilio { "push_symlinks_in", 0, 0x04, 1 }, 68241519Sattilio { "allow_other", 0, 0x08, 1 }, 69241519Sattilio { "default_permissions", 0, 0x10, 1 }, 70241519Sattilio #define ALTF_MAXREAD 0x20 71241519Sattilio { "max_read=", 0, ALTF_MAXREAD, 1 }, 72241519Sattilio #define ALTF_SUBTYPE 0x40 73241519Sattilio { "subtype=", 0, ALTF_SUBTYPE, 1 }, 74241519Sattilio #define ALTF_SYNC_UNMOUNT 0x80 75241519Sattilio { "sync_unmount", 0, ALTF_SYNC_UNMOUNT, 1 }, 76282959Strasz /* 77282959Strasz * MOPT_AUTOMOUNTED, included by MOPT_STDOPTS, does not fit into 78282959Strasz * the 'flags' argument to nmount(2). We have to abuse altflags 79282959Strasz * to pass it, as string, via iovec. 80282959Strasz */ 81282959Strasz #define ALTF_AUTOMOUNTED 0x100 82282959Strasz { "automounted", 0, ALTF_AUTOMOUNTED, 1 }, 83241519Sattilio /* Linux specific options, we silently ignore them */ 84241519Sattilio { "fsname=", 0, 0x00, 1 }, 85241519Sattilio { "fd=", 0, 0x00, 1 }, 86241519Sattilio { "rootmode=", 0, 0x00, 1 }, 87241519Sattilio { "user_id=", 0, 0x00, 1 }, 88241519Sattilio { "group_id=", 0, 0x00, 1 }, 89241519Sattilio { "large_read", 0, 0x00, 1 }, 90241519Sattilio /* "nonempty", just the first two chars are stripped off during parsing */ 91241519Sattilio { "nempty", 0, 0x00, 1 }, 92241519Sattilio MOPT_STDOPTS, 93241519Sattilio MOPT_END 94241519Sattilio}; 95241519Sattilio 96241519Sattiliostruct mntval { 97241519Sattilio int mv_flag; 98241519Sattilio void *mv_value; 99241519Sattilio int mv_len; 100241519Sattilio}; 101241519Sattilio 102241720Sedstatic struct mntval mvals[] = { 103241519Sattilio { ALTF_MAXREAD, NULL, 0 }, 104241519Sattilio { ALTF_SUBTYPE, NULL, 0 }, 105241519Sattilio { 0, NULL, 0 } 106241519Sattilio}; 107241519Sattilio 108241519Sattilio#define DEFAULT_MOUNT_FLAGS ALTF_PRIVATE | ALTF_SYNC_UNMOUNT 109241519Sattilio 110241519Sattilioint 111241519Sattiliomain(int argc, char *argv[]) 112241519Sattilio{ 113241519Sattilio struct iovec *iov; 114241519Sattilio int mntflags, iovlen, verbose = 0; 115241519Sattilio char *dev = NULL, *dir = NULL, mntpath[MAXPATHLEN]; 116241519Sattilio char *devo = NULL, *diro = NULL; 117241519Sattilio char ndev[128], fdstr[15]; 118241519Sattilio int i, done = 0, reject_allow_other = 0, safe_level = 0; 119241519Sattilio int altflags = DEFAULT_MOUNT_FLAGS; 120241519Sattilio int __altflags = DEFAULT_MOUNT_FLAGS; 121241522Sattilio int ch = 0; 122241519Sattilio struct mntopt *mo; 123241519Sattilio struct mntval *mv; 124241519Sattilio static struct option longopts[] = { 125241519Sattilio {"reject-allow_other", no_argument, NULL, 'A'}, 126241519Sattilio {"safe", no_argument, NULL, 'S'}, 127241519Sattilio {"daemon", required_argument, NULL, 'D'}, 128241519Sattilio {"daemon_opts", required_argument, NULL, 'O'}, 129241519Sattilio {"special", required_argument, NULL, 's'}, 130241519Sattilio {"mountpath", required_argument, NULL, 'm'}, 131241519Sattilio {"version", no_argument, NULL, 'V'}, 132241519Sattilio {"help", no_argument, NULL, 'h'}, 133241519Sattilio {0,0,0,0} 134241519Sattilio }; 135241519Sattilio int pid = 0; 136241519Sattilio int fd = -1, fdx; 137241519Sattilio char *ep; 138241519Sattilio char *daemon_str = NULL, *daemon_opts = NULL; 139241519Sattilio 140241519Sattilio /* 141241519Sattilio * We want a parsing routine which is not sensitive to 142241519Sattilio * the position of args/opts; it should extract the 143241519Sattilio * first two args and stop at the beginning of the rest. 144241519Sattilio * (This makes it easier to call mount_fusefs from external 145241519Sattilio * utils than it is with a strict "util flags args" syntax.) 146241519Sattilio */ 147241519Sattilio 148241519Sattilio iov = NULL; 149241519Sattilio iovlen = 0; 150241519Sattilio mntflags = 0; 151241519Sattilio /* All in all, I feel it more robust this way... */ 152241519Sattilio unsetenv("POSIXLY_CORRECT"); 153241519Sattilio if (getenv("MOUNT_FUSEFS_IGNORE_UNKNOWN")) 154241519Sattilio getmnt_silent = 1; 155241519Sattilio if (getenv("MOUNT_FUSEFS_VERBOSE")) 156241519Sattilio verbose = 1; 157241519Sattilio 158241519Sattilio do { 159241519Sattilio for (i = 0; i < 3; i++) { 160241519Sattilio if (optind < argc && argv[optind][0] != '-') { 161241519Sattilio if (dir) { 162241519Sattilio done = 1; 163241519Sattilio break; 164241519Sattilio } 165241519Sattilio if (dev) 166241519Sattilio dir = argv[optind]; 167241519Sattilio else 168241519Sattilio dev = argv[optind]; 169241519Sattilio optind++; 170241519Sattilio } 171241519Sattilio } 172241519Sattilio switch(ch) { 173241519Sattilio case 'A': 174241519Sattilio reject_allow_other = 1; 175241519Sattilio break; 176241519Sattilio case 'S': 177241519Sattilio safe_level = 1; 178241519Sattilio break; 179241519Sattilio case 'D': 180241519Sattilio if (daemon_str) 181241519Sattilio errx(1, "daemon specified inconsistently"); 182241519Sattilio daemon_str = optarg; 183241519Sattilio break; 184241519Sattilio case 'O': 185241519Sattilio if (daemon_opts) 186241519Sattilio errx(1, "daemon opts specified inconsistently"); 187241519Sattilio daemon_opts = optarg; 188241519Sattilio break; 189241519Sattilio case 'o': 190241519Sattilio getmntopts(optarg, mopts, &mntflags, &altflags); 191241519Sattilio for (mv = mvals; mv->mv_flag; ++mv) { 192241519Sattilio if (! (altflags & mv->mv_flag)) 193241519Sattilio continue; 194241519Sattilio for (mo = mopts; mo->m_flag; ++mo) { 195241519Sattilio char *p, *q; 196241519Sattilio 197241519Sattilio if (mo->m_flag != mv->mv_flag) 198241519Sattilio continue; 199241519Sattilio p = strstr(optarg, mo->m_option); 200241519Sattilio if (p) { 201241519Sattilio p += strlen(mo->m_option); 202241519Sattilio q = p; 203241519Sattilio while (*q != '\0' && *q != ',') 204241519Sattilio q++; 205241519Sattilio mv->mv_len = q - p + 1; 206241519Sattilio mv->mv_value = malloc(mv->mv_len); 207241519Sattilio memcpy(mv->mv_value, p, mv->mv_len - 1); 208241519Sattilio ((char *)mv->mv_value)[mv->mv_len - 1] = '\0'; 209241519Sattilio break; 210241519Sattilio } 211241519Sattilio } 212241519Sattilio } 213241519Sattilio break; 214241519Sattilio case 's': 215241519Sattilio if (devo) 216241519Sattilio errx(1, "special specified inconsistently"); 217241519Sattilio devo = optarg; 218241519Sattilio break; 219241519Sattilio case 'm': 220241519Sattilio if (diro) 221241519Sattilio errx(1, "mount path specified inconsistently"); 222241519Sattilio diro = optarg; 223241519Sattilio break; 224241519Sattilio case 'v': 225241519Sattilio verbose = 1; 226241519Sattilio break; 227241519Sattilio case 'h': 228241519Sattilio helpmsg(); 229241519Sattilio break; 230241519Sattilio case 'V': 231241519Sattilio showversion(); 232241519Sattilio break; 233241519Sattilio case '\0': 234241519Sattilio break; 235241519Sattilio case '?': 236241519Sattilio default: 237241519Sattilio usage(); 238241519Sattilio } 239241519Sattilio if (done) 240241519Sattilio break; 241241519Sattilio } while ((ch = getopt_long(argc, argv, "AvVho:SD:O:s:m:", longopts, NULL)) != -1); 242241519Sattilio 243241519Sattilio argc -= optind; 244241519Sattilio argv += optind; 245241519Sattilio 246241519Sattilio if (devo) { 247241519Sattilio if (dev) 248241519Sattilio errx(1, "special specified inconsistently"); 249241519Sattilio dev = devo; 250241519Sattilio } else if (diro) 251241519Sattilio errx(1, "if mountpoint is given via an option, special should also be given via an option"); 252241519Sattilio 253241519Sattilio if (diro) { 254241519Sattilio if (dir) 255241519Sattilio errx(1, "mount path specified inconsistently"); 256241519Sattilio dir = diro; 257241519Sattilio } 258241519Sattilio 259241519Sattilio if ((! dev) && argc > 0) { 260241519Sattilio dev = *argv++; 261241519Sattilio argc--; 262241519Sattilio } 263241519Sattilio 264241519Sattilio if ((! dir) && argc > 0) { 265241519Sattilio dir = *argv++; 266241519Sattilio argc--; 267241519Sattilio } 268241519Sattilio 269241519Sattilio if (! (dev && dir)) 270241519Sattilio errx(1, "missing special and/or mountpoint"); 271241519Sattilio 272241519Sattilio for (mo = mopts; mo->m_flag; ++mo) { 273241519Sattilio if (altflags & mo->m_flag) { 274241519Sattilio int iov_done = 0; 275241519Sattilio 276241519Sattilio if (reject_allow_other && 277241519Sattilio strcmp(mo->m_option, "allow_other") == 0) 278241519Sattilio /* 279241519Sattilio * reject_allow_other is stronger than a 280241519Sattilio * negative of allow_other: if this is set, 281241519Sattilio * allow_other is blocked, period. 282241519Sattilio */ 283241519Sattilio errx(1, "\"allow_other\" usage is banned by respective option"); 284241519Sattilio 285241519Sattilio for (mv = mvals; mv->mv_flag; ++mv) { 286241519Sattilio if (mo->m_flag != mv->mv_flag) 287241519Sattilio continue; 288241519Sattilio if (mv->mv_value) { 289241519Sattilio build_iovec(&iov, &iovlen, mo->m_option, mv->mv_value, mv->mv_len); 290241519Sattilio iov_done = 1; 291241519Sattilio break; 292241519Sattilio } 293241519Sattilio } 294241519Sattilio if (! iov_done) 295241519Sattilio build_iovec(&iov, &iovlen, mo->m_option, 296241519Sattilio __DECONST(void *, ""), -1); 297241519Sattilio } 298241519Sattilio if (__altflags & mo->m_flag) { 299241519Sattilio char *uscore_opt; 300241519Sattilio 301241519Sattilio if (asprintf(&uscore_opt, "__%s", mo->m_option) == -1) 302241519Sattilio err(1, "failed to allocate memory"); 303241519Sattilio build_iovec(&iov, &iovlen, uscore_opt, 304241519Sattilio __DECONST(void *, ""), -1); 305241519Sattilio free(uscore_opt); 306241519Sattilio } 307241519Sattilio } 308241519Sattilio 309241519Sattilio if (getenv("MOUNT_FUSEFS_SAFE")) 310241519Sattilio safe_level = 1; 311241519Sattilio 312241519Sattilio if (safe_level > 0 && (argc > 0 || daemon_str || daemon_opts)) 313241519Sattilio errx(1, "safe mode, spawning daemon not allowed"); 314241519Sattilio 315241519Sattilio if ((argc > 0 && (daemon_str || daemon_opts)) || 316241519Sattilio (daemon_opts && ! daemon_str)) 317241519Sattilio errx(1, "daemon specified inconsistently"); 318241519Sattilio 319241519Sattilio /* 320241519Sattilio * Resolve the mountpoint with realpath(3) and remove unnecessary 321241519Sattilio * slashes from the devicename if there are any. 322241519Sattilio */ 323241519Sattilio if (checkpath(dir, mntpath) != 0) 324241519Sattilio err(1, "%s", mntpath); 325241519Sattilio (void)rmslashes(dev, dev); 326241519Sattilio 327241519Sattilio if (strcmp(dev, "auto") == 0) 328241519Sattilio dev = __DECONST(char *, "/dev/fuse"); 329241519Sattilio 330241519Sattilio if (strcmp(dev, "/dev/fuse") == 0) { 331241519Sattilio if (! (argc > 0 || daemon_str)) { 332241519Sattilio fprintf(stderr, "Please also specify the fuse daemon to run when mounting via the multiplexer!\n"); 333241519Sattilio usage(); 334241519Sattilio } 335241519Sattilio if ((fd = open(dev, O_RDWR)) < 0) 336241519Sattilio err(1, "failed to open fuse device"); 337241519Sattilio } else { 338241519Sattilio fdx = strtol(dev, &ep, 10); 339241519Sattilio if (*ep == '\0') 340241519Sattilio fd = fdx; 341241519Sattilio } 342241519Sattilio 343241519Sattilio /* Identifying device */ 344241519Sattilio if (fd >= 0) { 345241519Sattilio struct stat sbuf; 346241519Sattilio char *ndevbas, *lep; 347241519Sattilio 348241519Sattilio if (fstat(fd, &sbuf) == -1) 349241519Sattilio err(1, "cannot stat device file descriptor"); 350241519Sattilio 351241519Sattilio strcpy(ndev, _PATH_DEV); 352241519Sattilio ndevbas = ndev + strlen(_PATH_DEV); 353241519Sattilio devname_r(sbuf.st_rdev, S_IFCHR, ndevbas, 354241519Sattilio sizeof(ndev) - strlen(_PATH_DEV)); 355241519Sattilio 356241519Sattilio if (strncmp(ndevbas, "fuse", 4)) 357241519Sattilio errx(1, "mounting inappropriate device"); 358241519Sattilio 359241519Sattilio strtol(ndevbas + 4, &lep, 10); 360241519Sattilio if (*lep != '\0') 361241519Sattilio errx(1, "mounting inappropriate device"); 362241519Sattilio 363241519Sattilio dev = ndev; 364241519Sattilio } 365241519Sattilio 366241519Sattilio if (argc > 0 || daemon_str) { 367241519Sattilio char *fds; 368241519Sattilio 369241519Sattilio if (fd < 0 && (fd = open(dev, O_RDWR)) < 0) 370241519Sattilio err(1, "failed to open fuse device"); 371241519Sattilio 372241519Sattilio if (asprintf(&fds, "%d", fd) == -1) 373241519Sattilio err(1, "failed to allocate memory"); 374241519Sattilio setenv("FUSE_DEV_FD", fds, 1); 375241519Sattilio free(fds); 376241519Sattilio setenv("FUSE_NO_MOUNT", "1", 1); 377241519Sattilio 378241519Sattilio if (daemon_str) { 379241519Sattilio char *bgdaemon; 380241519Sattilio int len; 381241519Sattilio 382241519Sattilio if (! daemon_opts) 383241519Sattilio daemon_opts = __DECONST(char *, ""); 384241519Sattilio 385241519Sattilio len = strlen(daemon_str) + 1 + strlen(daemon_opts) + 386241519Sattilio 2 + 1; 387241519Sattilio bgdaemon = calloc(1, len); 388241519Sattilio 389241519Sattilio if (! bgdaemon) 390241519Sattilio err(1, "failed to allocate memory"); 391241519Sattilio 392241519Sattilio strlcpy(bgdaemon, daemon_str, len); 393241519Sattilio strlcat(bgdaemon, " ", len); 394241519Sattilio strlcat(bgdaemon, daemon_opts, len); 395241519Sattilio strlcat(bgdaemon, " &", len); 396241519Sattilio 397241519Sattilio if (system(bgdaemon)) 398241519Sattilio err(1, "failed to call fuse daemon"); 399241519Sattilio } else { 400241519Sattilio if ((pid = fork()) < 0) 401241519Sattilio err(1, "failed to fork for fuse daemon"); 402241519Sattilio 403241519Sattilio if (pid == 0) { 404241519Sattilio execvp(argv[0], argv); 405241519Sattilio err(1, "failed to exec fuse daemon"); 406241519Sattilio } 407241519Sattilio } 408241519Sattilio } 409241519Sattilio 410241519Sattilio if (fd >= 0 && ! init_backgrounded() && close(fd) < 0) { 411241519Sattilio if (pid) 412241519Sattilio kill(pid, SIGKILL); 413241519Sattilio err(1, "failed to close fuse device"); 414241519Sattilio } 415241519Sattilio 416241519Sattilio /* Prepare the options vector for nmount(). build_iovec() is declared 417241519Sattilio * in mntopts.h. */ 418241519Sattilio sprintf(fdstr, "%d", fd); 419241519Sattilio build_iovec(&iov, &iovlen, "fstype", __DECONST(void *, "fusefs"), -1); 420241519Sattilio build_iovec(&iov, &iovlen, "fspath", mntpath, -1); 421241519Sattilio build_iovec(&iov, &iovlen, "from", dev, -1); 422241519Sattilio build_iovec(&iov, &iovlen, "fd", fdstr, -1); 423241519Sattilio 424241519Sattilio if (verbose) 425241519Sattilio fprintf(stderr, "mounting fuse daemon on device %s\n", dev); 426241519Sattilio 427241519Sattilio if (nmount(iov, iovlen, mntflags) < 0) 428241519Sattilio err(EX_OSERR, "%s on %s", dev, mntpath); 429241519Sattilio 430241519Sattilio exit(0); 431241519Sattilio} 432241519Sattilio 433241519Sattiliovoid 434241519Sattilio__usage_short(void) { 435241519Sattilio fprintf(stderr, 436241519Sattilio "usage:\n%s [-A|-S|-v|-V|-h|-D daemon|-O args|-s special|-m node|-o option...] special node [daemon args...]\n\n", 437241720Sed getprogname()); 438241519Sattilio} 439241519Sattilio 440241519Sattiliovoid 441241519Sattiliousage(void) 442241519Sattilio{ 443241519Sattilio struct mntopt *mo; 444241519Sattilio 445241519Sattilio __usage_short(); 446241519Sattilio 447241519Sattilio fprintf(stderr, "known options:\n"); 448241519Sattilio for (mo = mopts; mo->m_flag; ++mo) 449241519Sattilio fprintf(stderr, "\t%s\n", mo->m_option); 450241519Sattilio 451241519Sattilio fprintf(stderr, "\n(use -h for a detailed description of these options)\n"); 452241519Sattilio exit(EX_USAGE); 453241519Sattilio} 454241519Sattilio 455241519Sattiliovoid 456241519Sattiliohelpmsg(void) 457241519Sattilio{ 458241519Sattilio if (! getenv("MOUNT_FUSEFS_CALL_BY_LIB")) { 459241519Sattilio __usage_short(); 460241519Sattilio fprintf(stderr, "description of options:\n"); 461241519Sattilio } 462241519Sattilio 463241519Sattilio /* 464241519Sattilio * The main use case of this function is giving info embedded in general 465241519Sattilio * FUSE lib help output. Therefore the style and the content of the output 466241519Sattilio * tries to fit there as much as possible. 467241519Sattilio */ 468241519Sattilio fprintf(stderr, 469241519Sattilio " -o allow_other allow access to other users\n" 470241519Sattilio /* " -o nonempty allow mounts over non-empty file/dir\n" */ 471241519Sattilio " -o default_permissions enable permission checking by kernel\n" 472241519Sattilio /* 473241519Sattilio " -o fsname=NAME set filesystem name\n" 474241519Sattilio " -o large_read issue large read requests (2.4 only)\n" 475241519Sattilio */ 476241519Sattilio " -o subtype=NAME set filesystem type\n" 477241519Sattilio " -o max_read=N set maximum size of read requests\n" 478241519Sattilio " -o noprivate allow secondary mounting of the filesystem\n" 479241519Sattilio " -o neglect_shares don't report EBUSY when unmount attempted\n" 480241519Sattilio " in presence of secondary mounts\n" 481241519Sattilio " -o push_symlinks_in prefix absolute symlinks with mountpoint\n" 482241519Sattilio " -o sync_unmount do unmount synchronously\n" 483241519Sattilio ); 484241519Sattilio exit(EX_USAGE); 485241519Sattilio} 486241519Sattilio 487241519Sattiliovoid 488241519Sattilioshowversion(void) 489241519Sattilio{ 490241519Sattilio puts("mount_fusefs [fuse4bsd] version: " FUSE4BSD_VERSION); 491241519Sattilio exit(EX_USAGE); 492241519Sattilio} 493241519Sattilio 494241519Sattilioint 495241519Sattilioinit_backgrounded(void) 496241519Sattilio{ 497241519Sattilio int ibg; 498241519Sattilio size_t len; 499241519Sattilio 500241519Sattilio len = sizeof(ibg); 501241519Sattilio 502241519Sattilio if (sysctlbyname("vfs.fuse.init_backgrounded", &ibg, &len, NULL, 0)) 503241519Sattilio return (0); 504241519Sattilio 505241519Sattilio return (ibg); 506241519Sattilio} 507