Exemple #1
0
/* ----------------------------------------------------- */
int main(int argc,char* argv[])
{
	signal(SIGINT, fs_sigint_handler); 
	fs_set_limit_attr();
	if (mpinit(0, 50)) return -1;

	voolefs.tc = 10;
	voolefs.tpool = threadpool_init(voolefs.tc ,10);
	voolefs.cinc  = 8;
	voolefs.phost = mpcalloc(sizeof(struct host));
	voolefs.phost->host = inet_addr("123.125.149.11");
	voolefs.phost->port = htons(4869);
	voolefs.hostc = 1; 
	voolefs.semc = 20;

	char* pmpoint = fs_create_mountpoint();
	struct fuse_args args = FUSE_ARGS_INIT(argc, argv);	
	char *fsname =(char*)mpcalloc(256);
	sprintf(fsname,"-osubtype=%s,fsname=%s",argv[0],pmpoint);
	mpfree(pmpoint);
	int ret = fuse_opt_parse(&args, NULL,NULL,NULL /*&voolefs, voolefs_opts, fs_opt_proc*/);
	int multithreaded = 0;
	int foreground = 0;
	ret = fuse_opt_insert_arg(&args,1,fsname);
/*	if (fuse_is_lib_option("ac_attr_timeout="))
		fuse_opt_insert_arg(&args, 1, "-oauto_cache,ac_attr_timeout=0");
*/	ret = fuse_parse_cmdline(&args, &voolefs.mountpoint, &multithreaded, &foreground);
	voolefs.ch = fuse_mount(voolefs.mountpoint, &args);
//	event_reinit(voolefs.ev_base);
	if(voolefs.ch)
	{
		ret = fcntl(fuse_chan_fd(voolefs.ch), F_SETFD, FD_CLOEXEC);
		voolefs.fuse = fuse_new(voolefs.ch,&args,&oper,sizeof(struct fuse_operations),NULL);
		if (voolefs.fuse == NULL)
		{
			fs_cleanup();
			abort();
		}
		fs_daemonize(0);
		voole_net_create();
/*		if( multithreaded)
			ret = fuse_loop_mt(voolefs.fuse);
		else
*/			ret = fuse_loop(voolefs.fuse);
	}
	if( voolefs.fuse )
		fuse_remove_signal_handlers(fuse_get_session(voolefs.fuse));
	mpfree(fsname);
	if( voolefs.peventbase )
	{
		event_base_free(voolefs.peventbase);
		voolefs.peventbase = NULL;
	}
	return ret;
}
Exemple #2
0
int
fuse_main(int argc, char **argv, const struct fuse_operations *ops, void *data)
{
	struct fuse *fuse;
	char *mp = NULL;
	int mt;

	fuse = fuse_setup(argc, argv, ops, sizeof(*ops), &mp, &mt, data);
	if (!fuse)
		return (-1);

	return (fuse_loop(fuse));
}
Exemple #3
0
int main(int argc, char *argv[])
{
    int argctr;
    int flags;
    struct fuse *fuse;

    if(argc < 2) {
        fprintf(stderr,
                "usage: %s unmount_cmd [options] \n"
                "Options:\n"
                "    -d      enable debug output\n"
                "    -s      disable multithreaded operation\n",
                argv[0]);
        exit(1);
    }

    argctr = 1;
    unmount_cmd = argv[argctr++];

    set_signal_handlers();
    atexit(cleanup);

    flags = FUSE_MULTITHREAD;
    for(; argctr < argc && argv[argctr][0] == '-'; argctr ++) {
        switch(argv[argctr][1]) {
        case 'd':
            flags |= FUSE_DEBUG;
            break;

        case 's':
            flags &= ~FUSE_MULTITHREAD;
            break;

        default:
            fprintf(stderr, "invalid option: %s\n", argv[argctr]);
            exit(1);
        }
    }
    if(argctr != argc) {
        fprintf(stderr, "missing or surplus argument\n");
        exit(1);
    }

    fuse = fuse_new(0, flags);
    fuse_set_operations(fuse, &xmp_oper);
    fuse_loop(fuse);

    return 0;
}
Exemple #4
0
int
guestfs_impl_mount_local_run (guestfs_h *g)
{
  int r, mounted;

  gl_lock_lock (mount_local_lock);
  mounted = g->localmountpoint != NULL;
  gl_lock_unlock (mount_local_lock);

  if (!mounted) {
    error (g, _("you must call guestfs_mount_local first"));
    return -1;
  }

  /* Test if root is mounted.  We do this by using a side-effect of
   * guestfs_exists (which is that it calls NEED_ROOT).
   */
  guestfs_push_error_handler (g, NULL, NULL);
  r = guestfs_exists (g, "/");
  guestfs_pop_error_handler (g);
  if (r == -1) {
    error (g, _("you must call 'guestfs_mount' first to mount a filesystem on '/'.\nNote: '%s' is still mounted.  Use 'guestunmount %s' to clean up."),
           g->localmountpoint, g->localmountpoint);
    return -1;
  }

  debug (g, "%s: entering fuse_loop", __func__);

  /* Enter the main loop. */
  r = fuse_loop (g->fuse);
  if (r != 0)
    perrorf (g, _("fuse_loop: %s"), g->localmountpoint);

  debug (g, "%s: leaving fuse_loop", __func__);

  guestfs_int_free_fuse (g);
  gl_lock_lock (mount_local_lock);
  g->localmountpoint = NULL;
  gl_lock_unlock (mount_local_lock);

  /* By inspection, I found that fuse_loop only returns 0 or -1, but
   * don't rely on this in future.
   */
  return r == 0 ? 0 : -1;
}
Exemple #5
0
int uproc_run(uproc_ctx_t *ctx) {
    struct fuse *fuse;
    char *mountpoint = (char*)ctx->mount_point;
    int multithreaded = 0;
    int res;

    argv[3] = (char*)ctx->mount_point;
    uproc_instance = ctx;

    fuse = fuse_setup(argc, argv, &uproc_ops, sizeof(uproc_ops), &mountpoint,
                 &multithreaded, NULL);
    if (fuse == NULL)
        return -1;

    ctx->fuse = fuse;
    res = fuse_loop(fuse);

    fuse_teardown(fuse, mountpoint);

    uproc_destroy(ctx);

    return res;
}
Exemple #6
0
static void
ifuse_get_signal(unused int num)
{
	struct fuse *f;
	pid_t child;
	int status;

	if (sigse != NULL) {
		child = fork();

		if (child < 0)
			return ;

		f = sigse->args;
		if (child == 0) {
			fuse_unmount(f->fc->dir, f->fc);
			sigse = NULL;
			exit(0);
		}

		fuse_loop(f);
		wait(&status);
	}
}
Exemple #7
0
int fuse_main_real(int argc, char *argv[], const struct fuse_operations *op,
		   size_t op_size, void *user_data)
{
	struct fuse *fuse;
	char *mountpoint;
	int multithreaded;
	int res;

	fuse = fuse_setup(argc, argv, op, op_size, &mountpoint,
			  &multithreaded, user_data);
	if (fuse == NULL)
		return 1;

	if (multithreaded)
		res = fuse_loop_mt(fuse);
	else
		res = fuse_loop(fuse);

	fuse_teardown(fuse, mountpoint);
	if (res == -1)
		return 1;

	return 0;
}
Exemple #8
0
int main(int argc, char *argv[])
{
	if(argc <= 2) {
		QString arg = "-h";
		if(argc > 1)
			arg = argv[1];
		if(arg == QStringLiteral("-h") || arg == QStringLiteral("--help")) {
			std::cout << argv[0] << " FUSE_options --dbfs DBFS_options" << std::endl;
			std::cout << "FUSE_options" << std::endl;
			std::cout << "\tuse -h --dbfs switch to print FUSE options" << std::endl;
			std::cout << "DBFS_options" << std::endl;
			std::cout << "\t--dbfs\t" << "DBFS options separator, all options prior this will be ignored by DBFS" << std::endl;
			std::cout << "\t--host <host>\t" << "Database host" << std::endl;
			std::cout << "\t--port <port>\t" << "Database port" << std::endl;
			std::cout << "\t -u" << std::endl;
			std::cout << "\t--user <user>\t" << "Database user" << std::endl;
			std::cout << "\t -p" << std::endl;
			std::cout << "\t--password [<password>]\t" << "Database user password, use -p without password for interactive input." << std::endl;
			std::cout << "\t--database <database>\t" << "Database name" << std::endl;
			std::cout << "\t--db-schema\t" << "Database schema name" << std::endl;
			std::cout << "\t--table-name\t" << "DBFS table name, default is 'dbfs'" << std::endl;
			std::cout << "\t--create\t" << "Create DBFS tables" << std::endl;
			exit(0);
		}
	}

	int dbfs_switch_index;
	for(dbfs_switch_index = 1; dbfs_switch_index < argc; dbfs_switch_index++)
		if(argv[dbfs_switch_index] == QLatin1String("--dbfs")) {
			break;
		}

	QScopedPointer<qf::core::LogDevice> file_log_device(qf::core::FileLogDevice::install());
	file_log_device->setDomainTresholds(argc - dbfs_switch_index, argv + dbfs_switch_index);
	file_log_device->setPrettyDomain(true);

	QString o_database;
	QString o_user;
	QString o_password;
	QString o_host;
	int o_port = 0;
	QString o_db_schema;
	QString o_table_name;
	bool o_create_db = false;
	bool o_ask_passwd = false;

	for(int i=dbfs_switch_index + 1; i<argc; i++) {
		QString arg = argv[i];
		if(arg == QStringLiteral("--host")) {
			if(i<argc-1) {
				i++;
				o_host = argv[i];
			}
		}
		else if(arg == QStringLiteral("--port")) {
			if(i<argc-1) {
				i++;
				o_port = QString(argv[i]).toInt();
			}
		}
		else if(arg == QStringLiteral("-u") || arg == QStringLiteral("--user")) {
			if(i<argc-1) {
				i++;
				o_user = argv[i];
			}
		}
		else if(arg == QStringLiteral("-p") || arg == QStringLiteral("--password")) {
			if(i<argc-1) {
				QString p = argv[i+1];
				if(p.startsWith('-')) {
					o_ask_passwd = true;
				}
				else {
					o_password = p;
					i++;
				}
			}
			else {
				o_ask_passwd = true;
			}
		}
		else if(arg == QStringLiteral("--database")) {
			if(i<argc-1) {
				i++;
				o_database = argv[i];
			}
		}
		else if(arg == QStringLiteral("--db-schema")) {
			if(i<argc-1) {
				i++;
				o_db_schema = argv[i];
			}
		}
		else if(arg == QStringLiteral("--table-name")) {
			if(i<argc-1) {
				i++;
				o_table_name = argv[i];
			}
		}
		else if(arg == QStringLiteral("--create")) {
			o_create_db = true;
		}
	}

	if(o_ask_passwd) {
		char pwd[256];
		std::cout << "Please, enter your password: "******"Empty database name.";
		exit(1);
	}

	qfs::DbFsDriver *dbfs_drv = nullptr;
	qf::core::sql::Connection db_connection;
	if(dbfs_switch_index < (argc - 1)) {
		db_connection = QSqlDatabase::addDatabase("QPSQL");
		db_connection.setHostName(o_host);
		if(o_port > 0)
			db_connection.setPort(o_port);
		db_connection.setDatabaseName(o_database);
		db_connection.setUserName(o_user);
		db_connection.setPassword(o_password);
		//qfInfo() << o_host << o_port << o_user << o_database;
		bool ok = db_connection.open();
		if(!ok) {
			qfError() << db_connection.lastError().text();
			exit(1);
		}
		if(!o_db_schema.isEmpty()) {
			if(!db_connection.setCurrentSchema(o_db_schema)) {
				qfError() << "Error setting db schema to:" << o_db_schema;
				exit(1);
			}
		}
		dbfs_drv = new qfs::DbFsDriver();
		dbfs_drv->setConnectionName(db_connection.connectionName());

		if(!o_table_name.isEmpty()) {
			dbfs_drv->setTableName(o_table_name);
		}
		if(o_create_db) {
			if(!dbfs_drv->createDbFs()) {
				qfError() << "Error creating dbfs table" << dbfs_drv->tableName();
			}
			exit(1);
		}

		qfsqldbfs_setdriver(dbfs_drv);
	}

	int fuse_argc = dbfs_switch_index;

	/// FUSE variables
	struct fuse_args fuse_arguments = FUSE_ARGS_INIT(fuse_argc, argv);
	struct fuse_chan *fuse_channel = NULL;
	struct fuse *fuse_handle = NULL;
	char *mount_point = nullptr;

	if (fuse_parse_cmdline(&fuse_arguments, &mount_point, NULL, NULL) == -1) {
		qfError() << "fuse_parse_cmdline() - Error parsing fuse command line arguments!";
		exit(1);
	}

	/// Tell FUSE where the local mountpoint is
	fuse_channel = fuse_mount(mount_point, &fuse_arguments);
	if (fuse_channel == NULL){
		qfError()<<"fuse_mount() failed";
		exit(1);
	}

	// Tell FUSE about implementations of FS operations
	struct fuse_operations fuse_ops;
	memset(&fuse_ops, 0, sizeof(fuse_ops));
	fuse_ops.getattr = qfsqldbfs_getattr;
	fuse_ops.readdir = qfsqldbfs_readdir;
	fuse_ops.open = qfsqldbfs_open;
	fuse_ops.read = qfsqldbfs_read;
	fuse_ops.write = qfsqldbfs_write;
	fuse_ops.fsync = qfsqldbfs_fsync;
	fuse_ops.flush = qfsqldbfs_flush;
	fuse_ops.release = qfsqldbfs_release;
	fuse_ops.mknod = qfsqldbfs_mknod;
	fuse_ops.mkdir = qfsqldbfs_mkdir;
	fuse_ops.unlink = qfsqldbfs_unlink;
	fuse_ops.rmdir = qfsqldbfs_rmdir;
	fuse_ops.utime = qfsqldbfs_utime;
	fuse_ops.truncate = qfsqldbfs_truncate;
	fuse_ops.ftruncate = qfsqldbfs_ftruncate;
	fuse_ops.chmod = qfsqldbfs_chmod;
	fuse_ops.chown = qfsqldbfs_chown;
	fuse_ops.create = qfsqldbfs_create;
	fuse_ops.rename = qfsqldbfs_rename;

	fuse_handle = fuse_new(fuse_channel, &fuse_arguments, &fuse_ops, sizeof(fuse_ops), NULL);
	if (fuse_handle == NULL){
		qfError()<<"fuse_new() failed";
		exit(1);
	}

	if(dbfs_drv) {
#ifdef USE_QT_EVENT_LOOP
		qfInfo() << "Using Qt event loop with FUSE in separated thread";
		TheApp *app = new TheApp(argc, argv);
		s_fuseThread = new FuseThread(fuse_handle, fuse_channel, QString::fromUtf8(mount_point));
		dbfs_drv->moveToThread(s_fuseThread);
		QObject::connect(s_fuseThread, &QThread::finished, app, &TheApp::onFuseThreadFinished, Qt::QueuedConnection);
		s_fuseThread->start();

		set_signal_handlers();

		{
			/// setup SQL notify
			QSqlDatabase notify_db = QSqlDatabase::addDatabase("QPSQL", "DBFS_Notify");
			notify_db.setHostName(db_connection.hostName());
			notify_db.setPort(db_connection.port());
			notify_db.setUserName(db_connection.userName());
			notify_db.setPassword(db_connection.password());
			notify_db.setDatabaseName(db_connection.databaseName());
			bool ok = notify_db.open();
			if(!ok) {
				qfError() << "Error connect DBFS notify connection" << notify_db.lastError().text();
			}
			else {
				QSqlDriver *drv = notify_db.driver();
				//qRegisterMetaType<QSqlDriver::NotificationSource>("QSqlDriver::NotificationSource");
				QObject::connect(drv, SIGNAL(notification(QString,QSqlDriver::NotificationSource,QVariant)), dbfs_drv, SLOT(onSqlNotify(QString,QSqlDriver::NotificationSource,QVariant)), Qt::DirectConnection);
				//QObject::connect(drv, SIGNAL(notification(QString,QSqlDriver::NotificationSource,QVariant)), app, SLOT(onSqlNotify(QString,QSqlDriver::NotificationSource,QVariant)));
				drv->subscribeToNotification(qfs::DbFsDriver::CHANNEL_INVALIDATE_DBFS_DRIVER_CACHE);
				qfInfo() << drv << "subscribedToNotifications:" << drv->subscribedToNotifications().join(", ");
			}
		}

		app->exec();

		qfInfo() << "Waiting for FUSE thread to join ...";
		s_fuseThread->wait();
#else
		qfInfo() << "Using FUSE event loop";
		fuse_loop(fuse_handle);
		qfInfo() << "FUSE has quit its event loop";
#endif

		qfsqldbfs_setdriver(nullptr);
		QF_SAFE_DELETE(dbfs_drv);
#ifdef USE_QT_EVENT_LOOP
		QF_SAFE_DELETE(s_fuseThread);
		QF_SAFE_DELETE(app);
#endif
	}
	else {
		// used just to print FUSE help
		fuse_loop(fuse_handle);
	}

	qfInfo() << "bye";
	return 0;
}
Exemple #9
0
int main(int argc, char *argv[])
{
	char c;
	int did_explicit_auth = 0;
	char *tickets = NULL;
	struct fuse_args fa;
	fa.argc = 0;
	fa.argv = string_array_new();
	fa.allocated = 1;

	debug_config(argv[0]);

	while((c = getopt(argc, argv, "a:b:d:Dfhi:m:o:t:v")) != -1) {
		switch (c) {
		case 'd':
			debug_flags_set(optarg);
			break;
		case 'D':
			enable_small_file_optimizations = 0;
			break;
		case 'b':
			chirp_reli_blocksize_set(atoi(optarg));
			break;
		case 'i':
			tickets = xxstrdup(optarg);
			break;
		case 'm':
			fa.argc += 1;
			fa.argv = string_array_append(fa.argv, optarg);
			break;
		case 'o':
			debug_config_file(optarg);
			break;
		case 'a':
			auth_register_byname(optarg);
			did_explicit_auth = 1;
			break;
		case 't':
			chirp_fuse_timeout = string_time_parse(optarg);
			break;
		case 'f':
			run_in_foreground = 1;
			break;
		case 'v':
			cctools_version_print(stdout, argv[0]);
			return 0;
			break;
		case 'h':
		default:
			show_help(argv[0]);
			return 1;
			break;
		}
	}

	cctools_version_debug(D_DEBUG, argv[0]);

	if((argc - optind) != 1) {
		show_help(argv[0]);
		return 1;
	}

	fuse_mountpoint = argv[optind];

	if(!did_explicit_auth)
		auth_register_all();
	if(tickets) {
		auth_ticket_load(tickets);
		free(tickets);
	} else if(getenv(CHIRP_CLIENT_TICKETS)) {
		auth_ticket_load(getenv(CHIRP_CLIENT_TICKETS));
	} else {
		auth_ticket_load(NULL);
	}

	file_table = itable_create(0);

	signal(SIGHUP, exit_handler);
	signal(SIGINT, exit_handler);
	signal(SIGTERM, exit_handler);

	fuse_chan = fuse_mount(fuse_mountpoint, &fa);
	if(!fuse_chan) {
		fprintf(stderr, "chirp_fuse: couldn't access %s\n", fuse_mountpoint);
		return 1;
	}

	fuse_instance = fuse_new(fuse_chan, &fa, &chirp_fuse_operations, sizeof(chirp_fuse_operations), 0);
	if(!fuse_instance) {
		fuse_unmount(fuse_mountpoint, fuse_chan);
		fprintf(stderr, "chirp_fuse: couldn't access %s\n", fuse_mountpoint);
		return 1;
	}

	printf("chirp_fuse: mounted chirp on %s\n", fuse_mountpoint);
#ifdef CCTOOLS_OPSYS_DARWIN
	printf("chirp_fuse: to unmount: umount %s\n", fuse_mountpoint);
#else
	printf("chirp_fuse: to unmount: fusermount -u %s\n", fuse_mountpoint);
#endif

	fflush(0);

	if(!run_in_foreground)
		daemon(0, 0);

	fuse_loop(fuse_instance);

	fuse_unmount(fuse_mountpoint, fuse_chan);
	fuse_destroy(fuse_instance);

	free(fa.argv);

	return 0;
}
Exemple #10
0
int main( int argc, char * const argv[] )
#endif
{
	libregf_error_t *error                      = NULL;
	system_character_t *mount_point             = NULL;
	system_character_t *option_codepage         = NULL;
	system_character_t *option_extended_options = NULL;
	system_character_t *source                  = NULL;
	char *program                               = "regfmount";
	system_integer_t option                     = 0;
	int result                                  = 0;
	int verbose                                 = 0;

#if defined( HAVE_LIBFUSE ) || defined( HAVE_LIBOSXFUSE )
	struct fuse_operations regfmount_fuse_operations;

	struct fuse_args regfmount_fuse_arguments = FUSE_ARGS_INIT(0, NULL);
	struct fuse_chan *regfmount_fuse_channel  = NULL;
	struct fuse *regfmount_fuse_handle        = NULL;

#elif defined( HAVE_LIBDOKAN )
	DOKAN_OPERATIONS regfmount_dokan_operations;
	DOKAN_OPTIONS regfmount_dokan_options;
#endif

	libcnotify_stream_set(
	 stderr,
	 NULL );
	libcnotify_verbose_set(
	 1 );

	if( libclocale_initialize(
	     "regftools",
	     &error ) != 1 )
	{
		fprintf(
		 stderr,
		 "Unable to initialize locale values.\n" );

		goto on_error;
	}
	if( regftools_output_initialize(
	     _IONBF,
	     &error ) != 1 )
	{
		fprintf(
		 stderr,
		 "Unable to initialize output settings.\n" );

		goto on_error;
	}
	regftools_output_version_fprint(
	 stdout,
	 program );

	while( ( option = regftools_getopt(
	                   argc,
	                   argv,
	                   _SYSTEM_STRING( "c:hvVX:" ) ) ) != (system_integer_t) -1 )
	{
		switch( option )
		{
			case (system_integer_t) '?':
			default:
				fprintf(
				 stderr,
				 "Invalid argument: %" PRIs_SYSTEM "\n",
				 argv[ optind - 1 ] );

				usage_fprint(
				 stdout );

				return( EXIT_FAILURE );

			case (system_integer_t) 'c':
				option_codepage = optarg;

				break;

			case (system_integer_t) 'h':
				usage_fprint(
				 stdout );

				return( EXIT_SUCCESS );

			case (system_integer_t) 'v':
				verbose = 1;

				break;

			case (system_integer_t) 'V':
				regftools_output_copyright_fprint(
				 stdout );

				return( EXIT_SUCCESS );

			case (system_integer_t) 'X':
				option_extended_options = optarg;

				break;
		}
	}
	if( optind == argc )
	{
		fprintf(
		 stderr,
		 "Missing source file.\n" );

		usage_fprint(
		 stdout );

		return( EXIT_FAILURE );
	}
	source = argv[ optind++ ];

	if( optind == argc )
	{
		fprintf(
		 stderr,
		 "Missing mount point.\n" );

		usage_fprint(
		 stdout );

		return( EXIT_FAILURE );
	}
	mount_point = argv[ optind ];

	libcnotify_verbose_set(
	 verbose );
	libregf_notify_set_stream(
	 stderr,
	 NULL );
	libregf_notify_set_verbose(
	 verbose );

	if( mount_handle_initialize(
	     &regfmount_mount_handle,
	     &error ) != 1 )
	{
		fprintf(
		 stderr,
		 "Unable to initialize mount handle.\n" );

		goto on_error;
	}
	if( option_codepage != NULL )
	{
		result = mount_handle_set_ascii_codepage(
		          regfmount_mount_handle,
		          option_codepage,
		          &error );

		if( result == -1 )
		{
			fprintf(
			 stderr,
			 "Unable to set ASCII codepage in mount handle.\n" );

			goto on_error;
		}
		else if( result == 0 )
		{
			fprintf(
			 stderr,
			 "Unsupported ASCII codepage defaulting to: windows-1252.\n" );
		}
	}
	if( mount_handle_open(
	     regfmount_mount_handle,
	     source,
	     &error ) != 1 )
	{
		fprintf(
		 stderr,
		 "Unable to open source file\n" );

		goto on_error;
	}
#if defined( HAVE_LIBFUSE ) || defined( HAVE_LIBOSXFUSE )
	if( option_extended_options != NULL )
	{
		/* This argument is required but ignored
		 */
		if( fuse_opt_add_arg(
		     &regfmount_fuse_arguments,
		     "" ) != 0 )
		{
			fprintf(
			 stderr,
			 "Unable add fuse arguments.\n" );

			goto on_error;
		}
		if( fuse_opt_add_arg(
		     &regfmount_fuse_arguments,
		     "-o" ) != 0 )
		{
			fprintf(
			 stderr,
			 "Unable add fuse arguments.\n" );

			goto on_error;
		}
		if( fuse_opt_add_arg(
		     &regfmount_fuse_arguments,
		     option_extended_options ) != 0 )
		{
			fprintf(
			 stderr,
			 "Unable add fuse arguments.\n" );

			goto on_error;
		}
	}
	if( memory_set(
	     &regfmount_fuse_operations,
	     0,
	     sizeof( struct fuse_operations ) ) == NULL )
	{
		fprintf(
		 stderr,
		 "Unable to clear fuse operations.\n" );

		goto on_error;
	}
	regfmount_fuse_operations.open       = &mount_fuse_open;
	regfmount_fuse_operations.read       = &mount_fuse_read;
	regfmount_fuse_operations.release    = &mount_fuse_release;
	regfmount_fuse_operations.opendir    = &mount_fuse_opendir;
	regfmount_fuse_operations.readdir    = &mount_fuse_readdir;
	regfmount_fuse_operations.releasedir = &mount_fuse_releasedir;
	regfmount_fuse_operations.getattr    = &mount_fuse_getattr;
	regfmount_fuse_operations.destroy    = &mount_fuse_destroy;

	regfmount_fuse_channel = fuse_mount(
	                          mount_point,
	                          &regfmount_fuse_arguments );

	if( regfmount_fuse_channel == NULL )
	{
		fprintf(
		 stderr,
		 "Unable to create fuse channel.\n" );

		goto on_error;
	}
	regfmount_fuse_handle = fuse_new(
	                         regfmount_fuse_channel,
	                         &regfmount_fuse_arguments,
	                         &regfmount_fuse_operations,
	                         sizeof( struct fuse_operations ),
	                         regfmount_mount_handle );

	if( regfmount_fuse_handle == NULL )
	{
		fprintf(
		 stderr,
		 "Unable to create fuse handle.\n" );

		goto on_error;
	}
	if( verbose == 0 )
	{
		if( fuse_daemonize(
		     0 ) != 0 )
		{
			fprintf(
			 stderr,
			 "Unable to daemonize fuse.\n" );

			goto on_error;
		}
	}
	result = fuse_loop(
	          regfmount_fuse_handle );

	if( result != 0 )
	{
		fprintf(
		 stderr,
		 "Unable to run fuse loop.\n" );

		goto on_error;
	}
	fuse_destroy(
	 regfmount_fuse_handle );

	fuse_opt_free_args(
	 &regfmount_fuse_arguments );

	return( EXIT_SUCCESS );

#elif defined( HAVE_LIBDOKAN )
	if( memory_set(
	     &regfmount_dokan_operations,
	     0,
	     sizeof( DOKAN_OPERATIONS ) ) == NULL )
	{
		fprintf(
		 stderr,
		 "Unable to clear dokan operations.\n" );

		goto on_error;
	}
	if( memory_set(
	     &regfmount_dokan_options,
	     0,
	     sizeof( DOKAN_OPTIONS ) ) == NULL )
	{
		fprintf(
		 stderr,
		 "Unable to clear dokan options.\n" );

		goto on_error;
	}
	regfmount_dokan_options.Version     = DOKAN_VERSION;
	regfmount_dokan_options.ThreadCount = 0;
	regfmount_dokan_options.MountPoint  = mount_point;

	if( verbose != 0 )
	{
		regfmount_dokan_options.Options |= DOKAN_OPTION_STDERR;
#if defined( HAVE_DEBUG_OUTPUT )
		regfmount_dokan_options.Options |= DOKAN_OPTION_DEBUG;
#endif
	}
/* This will only affect the drive properties
	regfmount_dokan_options.Options |= DOKAN_OPTION_REMOVABLE;
*/

#if ( DOKAN_VERSION >= 600 ) && ( DOKAN_VERSION < 800 )
	regfmount_dokan_options.Options |= DOKAN_OPTION_KEEP_ALIVE;

	regfmount_dokan_operations.CreateFile           = &mount_dokan_CreateFile;
	regfmount_dokan_operations.OpenDirectory        = &mount_dokan_OpenDirectory;
	regfmount_dokan_operations.CreateDirectory      = NULL;
	regfmount_dokan_operations.Cleanup              = NULL;
	regfmount_dokan_operations.CloseFile            = &mount_dokan_CloseFile;
	regfmount_dokan_operations.ReadFile             = &mount_dokan_ReadFile;
	regfmount_dokan_operations.WriteFile            = NULL;
	regfmount_dokan_operations.FlushFileBuffers     = NULL;
	regfmount_dokan_operations.GetFileInformation   = &mount_dokan_GetFileInformation;
	regfmount_dokan_operations.FindFiles            = &mount_dokan_FindFiles;
	regfmount_dokan_operations.FindFilesWithPattern = NULL;
	regfmount_dokan_operations.SetFileAttributes    = NULL;
	regfmount_dokan_operations.SetFileTime          = NULL;
	regfmount_dokan_operations.DeleteFile           = NULL;
	regfmount_dokan_operations.DeleteDirectory      = NULL;
	regfmount_dokan_operations.MoveFile             = NULL;
	regfmount_dokan_operations.SetEndOfFile         = NULL;
	regfmount_dokan_operations.SetAllocationSize    = NULL;
	regfmount_dokan_operations.LockFile             = NULL;
	regfmount_dokan_operations.UnlockFile           = NULL;
	regfmount_dokan_operations.GetFileSecurity      = NULL;
	regfmount_dokan_operations.SetFileSecurity      = NULL;
	regfmount_dokan_operations.GetDiskFreeSpace     = NULL;
	regfmount_dokan_operations.GetVolumeInformation = &mount_dokan_GetVolumeInformation;
	regfmount_dokan_operations.Unmount              = &mount_dokan_Unmount;

#else
	regfmount_dokan_operations.ZwCreateFile         = &mount_dokan_ZwCreateFile;
	regfmount_dokan_operations.Cleanup              = NULL;
	regfmount_dokan_operations.CloseFile            = &mount_dokan_CloseFile;
	regfmount_dokan_operations.ReadFile             = &mount_dokan_ReadFile;
	regfmount_dokan_operations.WriteFile            = NULL;
	regfmount_dokan_operations.FlushFileBuffers     = NULL;
	regfmount_dokan_operations.GetFileInformation   = &mount_dokan_GetFileInformation;
	regfmount_dokan_operations.FindFiles            = &mount_dokan_FindFiles;
	regfmount_dokan_operations.FindFilesWithPattern = NULL;
	regfmount_dokan_operations.SetFileAttributes    = NULL;
	regfmount_dokan_operations.SetFileTime          = NULL;
	regfmount_dokan_operations.DeleteFile           = NULL;
	regfmount_dokan_operations.DeleteDirectory      = NULL;
	regfmount_dokan_operations.MoveFile             = NULL;
	regfmount_dokan_operations.SetEndOfFile         = NULL;
	regfmount_dokan_operations.SetAllocationSize    = NULL;
	regfmount_dokan_operations.LockFile             = NULL;
	regfmount_dokan_operations.UnlockFile           = NULL;
	regfmount_dokan_operations.GetFileSecurity      = NULL;
	regfmount_dokan_operations.SetFileSecurity      = NULL;
	regfmount_dokan_operations.GetDiskFreeSpace     = NULL;
	regfmount_dokan_operations.GetVolumeInformation = &mount_dokan_GetVolumeInformation;
	regfmount_dokan_operations.Unmounted            = NULL;
	regfmount_dokan_operations.FindStreams          = NULL;
	regfmount_dokan_operations.Mounted              = NULL;

#endif /* ( DOKAN_VERSION >= 600 ) && ( DOKAN_VERSION < 800 ) */

	result = DokanMain(
	          &regfmount_dokan_options,
	          &regfmount_dokan_operations );

	switch( result )
	{
		case DOKAN_SUCCESS:
			break;

		case DOKAN_ERROR:
			fprintf(
			 stderr,
			 "Unable to run dokan main: generic error\n" );
			break;

		case DOKAN_DRIVE_LETTER_ERROR:
			fprintf(
			 stderr,
			 "Unable to run dokan main: bad drive letter\n" );
			break;

		case DOKAN_DRIVER_INSTALL_ERROR:
			fprintf(
			 stderr,
			 "Unable to run dokan main: unable to load driver\n" );
			break;

		case DOKAN_START_ERROR:
			fprintf(
			 stderr,
			 "Unable to run dokan main: driver error\n" );
			break;

		case DOKAN_MOUNT_ERROR:
			fprintf(
			 stderr,
			 "Unable to run dokan main: unable to assign drive letter\n" );
			break;

		case DOKAN_MOUNT_POINT_ERROR:
			fprintf(
			 stderr,
			 "Unable to run dokan main: mount point error\n" );
			break;

		default:
			fprintf(
			 stderr,
			 "Unable to run dokan main: unknown error: %d\n",
			 result );
			break;
	}
	return( EXIT_SUCCESS );

#else
	fprintf(
	 stderr,
	 "No sub system to mount REGF format.\n" );

	return( EXIT_FAILURE );
#endif

on_error:
	if( error != NULL )
	{
		libcnotify_print_error_backtrace(
		 error );
		libcerror_error_free(
		 &error );
	}
#if defined( HAVE_LIBFUSE ) || defined( HAVE_LIBOSXFUSE )
	if( regfmount_fuse_handle != NULL )
	{
		fuse_destroy(
		 regfmount_fuse_handle );
	}
	fuse_opt_free_args(
	 &regfmount_fuse_arguments );
#endif
	if( regfmount_mount_handle != NULL )
	{
		mount_handle_free(
		 &regfmount_mount_handle,
		 NULL );
	}
	return( EXIT_FAILURE );
}
Exemple #11
0
// run fskit with fuse
int fskit_fuse_main( struct fskit_fuse_state* state, int argc, char** argv ) {

   int rc = 0;

   // set up FUSE
   struct fuse_args args = FUSE_ARGS_INIT(argc, argv);
   struct fuse_chan* ch = NULL;
   struct fuse* fs = NULL;
   int multithreaded = 1;
   int foreground = 0;
   char* mountpoint = NULL;

   // parse command-line...
   rc = fuse_parse_cmdline( &args, &mountpoint, &multithreaded, &foreground );
   if( rc < 0 ) {

      fskit_error("fuse_parse_cmdline rc = %d\n", rc );
      fuse_opt_free_args(&args);

      return rc;
   }

   if( mountpoint == NULL ) {

      fskit_error("%s", "No mountpoint given\n");
      fuse_opt_free_args(&args);

      return rc;
   }

   state->mountpoint = strdup( mountpoint );

   // mount
   ch = fuse_mount( mountpoint, &args );
   if( ch == NULL ) {

      rc = -errno;
      fskit_error("fuse_mount failed, errno = %d\n", rc );

      fuse_opt_free_args(&args);

      if( rc == 0 ) {
          rc = -EPERM;
      }

      return rc;
   }

   // create the filesystem
   fs = fuse_new( ch, &args, &state->ops, sizeof(state->ops), state );
   fuse_opt_free_args(&args);

   if( fs == NULL ) {

      // failed
      rc = -errno;
      fskit_error("fuse_new failed, errno = %d\n", rc );

      fuse_unmount( mountpoint, ch );

      if( rc == 0 ) {
          rc = -EPERM;
      }

      return rc;
   }

   // daemonize if running in the background
   fskit_debug("FUSE daemonize: foreground=%d\n", foreground);
   rc = fuse_daemonize( foreground );
   if( rc != 0 ) {

      // failed
      fskit_error("fuse_daemonize(%d) rc = %d\n", foreground, rc );

      fuse_unmount( mountpoint, ch );
      fuse_destroy( fs );

      return rc;
   }

   // set up FUSE signal handlers
   rc = fuse_set_signal_handlers( fuse_get_session(fs) );
   if( rc < 0 ) {

      // failed
      fskit_error("fuse_set_signal_handlers rc = %d\n", rc );

      fuse_unmount( mountpoint, ch );
      fuse_destroy( fs );
      return rc;
   }

   // if we have a post-mount callback, call it now, since FUSE is ready to receive requests
   if( state->postmount != NULL ) {

      rc = (*state->postmount)( state, state->postmount_cls );
      if( rc != 0 ) {

         fskit_error("fskit postmount callback rc = %d\n", rc );

         fuse_unmount( mountpoint, ch );
         fuse_destroy( fs );

         return rc;
      }
   }

   // run the filesystem--start processing requests
   fskit_debug("%s", "FUSE main loop entered\n");
   if( multithreaded ) {
      rc = fuse_loop_mt( fs );
   }
   else {
      rc = fuse_loop( fs );
   }

   fskit_debug("%s", "FUSE main loop finished\n");
   fuse_teardown( fs, mountpoint );

   return rc;
}
int main(int argc, char* argv[])
{
	struct fuse_args mount_args = FUSE_ARGS_INIT(0, NULL);
	struct fuse_args newfs_args = FUSE_ARGS_INIT(0, NULL);
	const char* spec = NULL;
	const char* mount_point = NULL;
	char* mount_options;
	int debug = 0;
	struct fuse_chan* fc = NULL;
	struct fuse* fh = NULL;
	int opt;

	printf("FUSE exfat %u.%u.%u\n",
			EXFAT_VERSION_MAJOR, EXFAT_VERSION_MINOR, EXFAT_VERSION_PATCH);

	mount_options = strdup(default_options);
	if (mount_options == NULL)
	{
		exfat_error("failed to allocate options string");
		return 1;
	}

	while ((opt = getopt(argc, argv, "dno:Vv")) != -1)
	{
		switch (opt)
		{
		case 'd':
			debug = 1;
			break;
		case 'n':
			break;
		case 'o':
			mount_options = add_option(mount_options, optarg, NULL);
			if (mount_options == NULL)
				return 1;
			break;
		case 'V':
			free(mount_options);
			puts("Copyright (C) 2010-2014  Andrew Nayenko");
			return 0;
		case 'v':
			break;
		default:
			free(mount_options);
			usage(argv[0]);
			break;
		}
	}
	if (argc - optind != 2)
	{
		free(mount_options);
		usage(argv[0]);
	}
	spec = argv[optind];
	mount_point = argv[optind + 1];

	if (exfat_mount(&ef, spec, mount_options) != 0)
	{
		free(mount_options);
		return 1;
	}

	if (ef.ro == -1) /* read-only fallback was used */
	{
		mount_options = add_option(mount_options, "ro", NULL);
		if (mount_options == NULL)
		{
			exfat_unmount(&ef);
			return 1;
		}
	}

	mount_options = add_fuse_options(mount_options, spec);
	if (mount_options == NULL)
	{
		exfat_unmount(&ef);
		return 1;
	}

	/* create arguments for fuse_mount() */
	if (fuse_opt_add_arg(&mount_args, "exfat") != 0 ||
		fuse_opt_add_arg(&mount_args, "-o") != 0 ||
		fuse_opt_add_arg(&mount_args, mount_options) != 0)
	{
		exfat_unmount(&ef);
		free(mount_options);
		return 1;
	}

	free(mount_options);

	/* create FUSE mount point */
	fc = fuse_mount(mount_point, &mount_args);
	fuse_opt_free_args(&mount_args);
	if (fc == NULL)
	{
		exfat_unmount(&ef);
		return 1;
	}

	/* create arguments for fuse_new() */
	if (fuse_opt_add_arg(&newfs_args, "") != 0 ||
		(debug && fuse_opt_add_arg(&newfs_args, "-d") != 0))
	{
		fuse_unmount(mount_point, fc);
		exfat_unmount(&ef);
		return 1;
	}

	/* create new FUSE file system */
	fh = fuse_new(fc, &newfs_args, &fuse_exfat_ops,
			sizeof(struct fuse_operations), NULL);
	fuse_opt_free_args(&newfs_args);
	if (fh == NULL)
	{
		fuse_unmount(mount_point, fc);
		exfat_unmount(&ef);
		return 1;
	}

	/* exit session on HUP, TERM and INT signals and ignore PIPE signal */
	if (fuse_set_signal_handlers(fuse_get_session(fh)) != 0)
	{
		fuse_unmount(mount_point, fc);
		fuse_destroy(fh);
		exfat_unmount(&ef);
		exfat_error("failed to set signal handlers");
		return 1;
	}

	/* go to background (unless "-d" option is passed) and run FUSE
	   main loop */
	if (fuse_daemonize(debug) == 0)
	{
		if (fuse_loop(fh) != 0)
			exfat_error("FUSE loop failure");
	}
	else
		exfat_error("failed to daemonize");

	fuse_remove_signal_handlers(fuse_get_session(fh));
	/* note that fuse_unmount() must be called BEFORE fuse_destroy() */
	fuse_unmount(mount_point, fc);
	fuse_destroy(fh);
	return 0;
}
Exemple #13
0
int fuse_main_real(int argc,char *argv[],const struct fuse_operations *op,size_t op_size,void *user_data) {
  struct fuse *fuse = fuse_setup(argc,argv,op,op_size,NULL,0,user_data);
  fuse_loop(fuse);
  fuse_teardown(fuse,fuse->mountpoint);
  return 0;
}
Exemple #14
0
int main(int argc, char *argv[]) {
    if (sizeof(void*) > sizeof(uint64_t)) {
        fprintf(stderr,"%s: This program cannot be run on your system because of FUSE design limitation\n", PROGRAM);
        return EXIT_FAILURE;
    }
    struct fuse_args args = FUSE_ARGS_INIT(argc, argv);
    FuseZipData *data = NULL;
    struct fusezip_param param;
    param.help = false;
    param.version = false;
    param.readonly = false;
    param.strArgCount = 0;
    param.usePasswd = false;
    param.fileName = NULL;

    if (fuse_opt_parse(&args, &param, fusezip_opts, process_arg)) {
        fuse_opt_free_args(&args);
        return EXIT_FAILURE;
    }

    // if all work is done inside options parsing...
    if (param.help) {
        fuse_opt_free_args(&args);
        return EXIT_SUCCESS;
    }
    
    // pass version switch to HELP library to see it's version
    if (!param.version) {
        // no file name passed
        if (param.fileName == NULL) {
            print_usage();
            fuse_opt_free_args(&args);
            return EXIT_FAILURE;
        }

        openlog(PROGRAM, LOG_PID, LOG_USER);
        if ((data = initFuseZip(PROGRAM, param.fileName, param.readonly))
                == NULL) {
            fuse_opt_free_args(&args);
            return EXIT_FAILURE;
        }
        // try password
        if (param.usePasswd) {
            int try_count = 3;
            while (try_count--) {
                if (data->try_passwd(getpass("Enter password: "******"Incorrect!\n");
            }
            if (try_count < 0) {
                fuse_opt_free_args(&args);
                fprintf(stderr,"%s quit!\n", PROGRAM);
                return EXIT_FAILURE;
            }
        }
    }

    static struct fuse_operations fusezip_oper;
    /* {{{ */
    fusezip_oper.init       =   fusezip_init;
    fusezip_oper.destroy    =   fusezip_destroy;
    fusezip_oper.readdir    =   fusezip_readdir;
    fusezip_oper.getattr    =   fusezip_getattr;
    fusezip_oper.statfs     =   fusezip_statfs;
    fusezip_oper.open       =   fusezip_open;
    fusezip_oper.read       =   fusezip_read;
    fusezip_oper.write      =   fusezip_write;
    fusezip_oper.release    =   fusezip_release;
    fusezip_oper.unlink     =   fusezip_unlink;
    fusezip_oper.rmdir      =   fusezip_rmdir;
    fusezip_oper.mkdir      =   fusezip_mkdir;
    fusezip_oper.rename     =   fusezip_rename;
    fusezip_oper.create     =   fusezip_create;
    fusezip_oper.chmod      =   fusezip_chmod;
    fusezip_oper.chown      =   fusezip_chown;
    fusezip_oper.flush      =   fusezip_flush;
    fusezip_oper.fsync      =   fusezip_fsync;
    fusezip_oper.fsyncdir   =   fusezip_fsyncdir;
    fusezip_oper.opendir    =   fusezip_opendir;
    fusezip_oper.releasedir =   fusezip_releasedir;
    fusezip_oper.access     =   fusezip_access;
    fusezip_oper.utimens    =   fusezip_utimens;
    fusezip_oper.ftruncate  =   fusezip_ftruncate;
    fusezip_oper.truncate   =   fusezip_truncate;
    fusezip_oper.setxattr   =   fusezip_setxattr;
    fusezip_oper.getxattr   =   fusezip_getxattr;
    fusezip_oper.listxattr  =   fusezip_listxattr;
    fusezip_oper.removexattr=   fusezip_removexattr;
    fusezip_oper.readlink   =   fusezip_readlink;
    fusezip_oper.symlink    =   fusezip_symlink;

#if FUSE_VERSION >= 28
    // don't allow NULL path
    fusezip_oper.flag_nullpath_ok = 0;
#endif
    /* }}} */

    struct fuse *fuse;
    char *mountpoint;
    // this flag ignored because libzip does not supports multithreading
    int multithreaded;
    int res;

    fuse = fuse_setup(args.argc, args.argv, &fusezip_oper, sizeof(fusezip_oper), &mountpoint, &multithreaded, data);
    fuse_opt_free_args(&args);
    if (fuse == NULL) {
        delete data;
        return EXIT_FAILURE;
    }
    res = fuse_loop(fuse);
    fuse_teardown(fuse, mountpoint);
    return (res == 0) ? EXIT_SUCCESS : EXIT_FAILURE;
}
/*
 * Class:     org_catacombae_jfuse_FUSE
 * Method:    mountNative26
 * Signature: (Lorg/catacombae/jfuse/FUSE26FileSystem;Ljava/lang/String;[Ljava/lang/String;Lorg/catacombae/jfuse/FUSE26Capabilities;Lorg/catacombae/jfuse/MacFUSE20Capabilities;)Z
 */
JNIEXPORT jboolean JNICALL Java_org_catacombae_jfuse_FUSE_mountNative26(
        JNIEnv *env, jclass cls, jobject fileSystem, jstring mountPoint,
        jobjectArray optionStrings, jobject fuseCapabilities,
        jobject macFuseCapabilities) {
#define _FNAME_ "Java_org_catacombae_jfuse_FUSE_mountNative26"
    CSLogTraceEnter(_FNAME_ "(%p, %p, %p, %p, %p, %p, %p)", env, cls,
            fileSystem, mountPoint, optionStrings, fuseCapabilities,
            macFuseCapabilities);

    jboolean res = JNI_FALSE;

    jFUSEContext *context = new jFUSEContext(env, fileSystem);

    if(!fillFUSE26Operations(env, fuseCapabilities, &jfuse_operations))
        CSPanicWithMessage("Could not fill FUSE 2.6 operations!");
    else
        CSLogDebug("Filled FUSE 2.6 operations.");

    if(jfuse_operations.init != NULL) {
        context->setInitEnabled(true);
    }

#if defined(__APPLE__) || defined(__DARWIN__)
#if (__FreeBSD__ >= 10)
    if(macFuseCapabilities != NULL) {
        if(!fillMacFUSE20Operations(env, macFuseCapabilities,
                &jfuse_operations))
            CSPanicWithMessage("Could not fill MacFUSE 2.0 operations!");
        else {
            CSLogDebug("Filled MacFUSE 2.0 operations.");
            if(jfuse_operations.getxtimes != NULL ||
                    jfuse_operations.setbkuptime != NULL ||
                    jfuse_operations.setcrtime != NULL ||
                    jfuse_operations.setchgtime != NULL) {
                CSLogDebug("Requesting enabling of xtimes.");
                context->setXtimesEnabled(true);
                if(jfuse_operations.init == NULL) {
                    CSLogDebug("Adding operation 'init' to fuse_operations for "
                            "support enabling of xtimes...");
                    jfuse_operations.init = jfuse_init;
                }
            }
        }
    }
    else
        CSLogDebug("No MacFUSE 2.0 operations to fill.");
#endif /*__FreeBSD__ >= 10 */
#endif /* defined(__APPLE__) || defined(__DARWIN__) */

    /* Read mountpoint. */
    jboolean isCopy;
    const char *utf8MountPoint = env->GetStringUTFChars(mountPoint, &isCopy);

    /* Read options. */
    struct fuse_args args = FUSE_ARGS_INIT(0, NULL);
    if(fuse_opt_add_arg(&args, utf8MountPoint) != 0)
        CSPanicWithMessage("fuse_opt_add_arg failed unexpectedly.");

    jsize optionStringsLength = env->GetArrayLength(optionStrings);
    CSLogDebug("Reading option strings (length=%ld)...", (long)optionStringsLength);
    for(int i = 0; i < optionStringsLength; ++i) {
        jstring cur = (jstring)env->GetObjectArrayElement(optionStrings, i);
        const char *utfChars = env->GetStringUTFChars(cur, NULL);

        CSLogDebug("  Adding option %d: \"%s\"", i, utfChars);
        int addArgRetval = fuse_opt_add_arg(&args, utfChars);
        if(addArgRetval != 0)
            CSPanicWithMessage("fuse_opt_add_arg failed unexpectedly with "
                    "retval=%d, errno: %d (%s)", addArgRetval, errno,
                    strerror(errno));

        env->ReleaseStringUTFChars(cur, utfChars);
        env->DeleteLocalRef(cur);
    }

    if(fuse_parse_cmdline(&args, NULL, NULL, NULL) != 0)
        CSLogError("fuse_parse_cmdline didn't return 0.");
    else {
        /*
         * FUSE regular mount procedure:
         *
         * Init:
         * - fuse_mount:
         *     (char *mountpoint, struct fuse_args *args)-> (struct fuse_chan*)
         * - fuse_new:
         *     (struct fuse_chan *ch, struct fuse_args *args,
         *      struct fuse_operations *op, size_t op_size, void *user_data)
         *     ->(struct fuse*)
         * Running:
         * - fuse_loop / fuse_loop_mt:
         *     (struct fuse*)->(int)
         *   Main loop, running until file system is unmounted.
         * Cleanup:
         * - fuse_unmount:
         *     (char *mountpoint, struct fuse_chan *ch)->(void)
         * - fuse_destroy:
         *     (struct fuse* f)->(void)
         *
         *
         * FUSE lowlevel mount procedure:
         *
         * Init:
         * - fuse_mount:
         *     (char *mountpoint, struct fuse_args *args)->(struct fuse_chan*)
         * - fuse_lowlevel_new:
         *     (struct fuse_args *args, struct fuse_lowlevel_ops *op,
         *       size_t op_size, void *userdata) -> (struct fuse_session*)
         * - fuse_session_add_chan:
         *     (struct fuse_session *se, struct fuse_chan *ch)->(void)
         * Running:
         * - fuse_session_loop / fuse_session_loop_mt:
         *     (struct fuse_session *se)->(int)
         * Cleanup:
         * - fuse_session_remove_chan:
         *     (struct fuse_chan *ch)->(void)
         * - fuse_session_destroy:
         *     (struct fuse_session *se)->(void)
         * - fuse_unmount:
         *     (char *mountpoint, struct fuse_chan *ch)->(void)
         */
        fuse_chan *chan = NULL;
        fuse *fh = NULL;

        CSLogDebug("Invoking fuse_mount...");
        chan = fuse_mount(utf8MountPoint, &args);
        CSLogDebug("   done. result=%p", chan);
        if(chan != NULL) {
            CSLogDebug("Invoking fuse_new...");
            fh = fuse_new(chan, &args, &jfuse_operations,
                    sizeof (jfuse_operations), context);
            CSLogDebug("   done. result=%p", fh);
            if(fh != NULL) {
#if defined(__NetBSD__)
	        int sighandler_res = 0;
#else
                int sighandler_res =
		  fuse_set_signal_handlers(fuse_get_session(fh));
#endif /* defined(__NetBSD__) */
		if(sighandler_res == 0) {
                    CSLogDebug("Invoking fuse_loop...");
                    int fuseLoopRetval = fuse_loop(fh);
                    CSLogDebug("  done. result=%d", fuseLoopRetval);
                    if(fuseLoopRetval != 0)
                        CSLogError("fuse_loop exited with a non-zero value: %d "
                            "(errno is %d (%s)", fuseLoopRetval, errno,
                            strerror(errno));
                    else
                        res = JNI_TRUE;

#if !defined(__NetBSD__)
                    fuse_remove_signal_handlers(fuse_get_session(fh));
#endif
                }
                else
                    CSLogError("Couldn't set signal handlers!");
            }
            else
                CSLogError("fuse_new exited with an error. (errno is %d (%s))",
                    errno, strerror(errno));
        }
        else
            CSLogError("fuse_mount exited with an error. (errno is %d (%s))",
                errno, strerror(errno));

        fuse_opt_free_args(&args);

        if(chan != NULL) {
            CSLogDebug("Unmounting \"%s\"... (chan=%p)", utf8MountPoint, chan);
            fuse_unmount(utf8MountPoint, chan);
        }
        if(fh != NULL) {
            CSLogDebug("Destroying fuse filehandle %p...", fh);
            fuse_destroy(fh);
        }

        delete context;
    }

    CSLogTraceLeave(_FNAME_ "(%p, %p, %p, %p, %p, %p, %p): %d", env, cls,
            fileSystem, mountPoint, optionStrings, fuseCapabilities,
            macFuseCapabilities, res);
    return res;
#undef _FNAME_
}