From 4eed36910fa73cfe3fe62530850d427e6841e14f Mon Sep 17 00:00:00 2001 From: Nikolaus Rath Date: Wed, 23 Aug 2017 23:39:27 +0200 Subject: Added examples/printcap --- ChangeLog.rst | 3 ++ example/Makefile.am | 2 +- example/meson.build | 2 +- example/printcap.c | 130 ++++++++++++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 135 insertions(+), 2 deletions(-) create mode 100644 example/printcap.c diff --git a/ChangeLog.rst b/ChangeLog.rst index 0b3e886..c798918 100644 --- a/ChangeLog.rst +++ b/ChangeLog.rst @@ -1,6 +1,9 @@ Unreleased Changes ================== +* There's a new `printcap` example that can be used to determine the + capabilities of the running kernel. + * `fuse_loop_mt()` now returns the minus the actual errno if there was an error (instead of just -1). diff --git a/example/Makefile.am b/example/Makefile.am index c83c81f..db87ade 100644 --- a/example/Makefile.am +++ b/example/Makefile.am @@ -6,7 +6,7 @@ noinst_PROGRAMS = passthrough passthrough_fh null hello hello_ll \ ioctl ioctl_client poll poll_client \ passthrough_ll notify_inval_inode \ notify_store_retrieve notify_inval_entry \ - cuse cuse_client + cuse cuse_client printcap LDADD = ../lib/libfuse3.la passthrough_fh_LDADD = ../lib/libfuse3.la @passthrough_fh_libs@ diff --git a/example/meson.build b/example/meson.build index b6f4418..13dae10 100644 --- a/example/meson.build +++ b/example/meson.build @@ -2,7 +2,7 @@ # (even though this isn't actually Python code) examples = [ 'passthrough', 'passthrough_fh', - 'null', 'hello', 'hello_ll', + 'null', 'hello', 'hello_ll', 'printcap', 'ioctl', 'ioctl_client', 'poll_client', 'cuse', 'cuse_client' ] diff --git a/example/printcap.c b/example/printcap.c new file mode 100644 index 0000000..218b526 --- /dev/null +++ b/example/printcap.c @@ -0,0 +1,130 @@ +/* + FUSE: Filesystem in Userspace + Copyright (C) 2017 Nikolaus Rath + + This program can be distributed under the terms of the GNU GPL. + See the file COPYING. +*/ + +/** @file + * + * minimal example filesystem that prints out all capabilities + * supported by the kernel and then exits. + * + * Compile with: + * + * gcc -Wall protocol_info.c `pkg-config fuse3 --cflags --libs` -o protocol_info + * + * ## Source code ## + * \include @file + */ + +#define FUSE_USE_VERSION 31 + +#include + +#include +#include +#include +#include +#include + +struct fuse_session *se; + +static void pc_init(void *userdata, + struct fuse_conn_info *conn) +{ + (void) userdata; + + printf("Protocol version: %d.%d\n", conn->proto_major, + conn->proto_minor); + printf("Capabilities:\n"); + if(conn->capable & FUSE_CAP_WRITEBACK_CACHE) + printf("\tFUSE_CAP_WRITEBACK_CACHE\n"); + if(conn->capable & FUSE_CAP_ASYNC_READ) + printf("\tFUSE_CAP_ASYNC_READ\n"); + if(conn->capable & FUSE_CAP_POSIX_LOCKS) + printf("\tFUSE_CAP_POSIX_LOCKS\n"); + if(conn->capable & FUSE_CAP_ATOMIC_O_TRUNC) + printf("\tFUSE_CAP_ATOMIC_O_TRUNC\n"); + if(conn->capable & FUSE_CAP_EXPORT_SUPPORT) + printf("\tFUSE_CAP_EXPORT_SUPPORT\n"); + if(conn->capable & FUSE_CAP_DONT_MASK) + printf("\tFUSE_CAP_DONT_MASK\n"); + if(conn->capable & FUSE_CAP_SPLICE_MOVE) + printf("\tFUSE_CAP_SPLICE_MOVE\n"); + if(conn->capable & FUSE_CAP_SPLICE_READ) + printf("\tFUSE_CAP_SPLICE_READ\n"); + if(conn->capable & FUSE_CAP_SPLICE_WRITE) + printf("\tFUSE_CAP_SPLICE_WRITE\n"); + if(conn->capable & FUSE_CAP_FLOCK_LOCKS) + printf("\tFUSE_CAP_FLOCK_LOCKS\n"); + if(conn->capable & FUSE_CAP_IOCTL_DIR) + printf("\tFUSE_CAP_IOCTL_DIR\n"); + if(conn->capable & FUSE_CAP_AUTO_INVAL_DATA) + printf("\tFUSE_CAP_AUTO_INVAL_DATA\n"); + if(conn->capable & FUSE_CAP_READDIRPLUS) + printf("\tFUSE_CAP_READDIRPLUS\n"); + if(conn->capable & FUSE_CAP_READDIRPLUS_AUTO) + printf("\tFUSE_CAP_READDIRPLUS_AUTO\n"); + if(conn->capable & FUSE_CAP_ASYNC_DIO) + printf("\tFUSE_CAP_ASYNC_DIO\n"); + if(conn->capable & FUSE_CAP_WRITEBACK_CACHE) + printf("\tFUSE_CAP_WRITEBACK_CACHE\n"); + if(conn->capable & FUSE_CAP_NO_OPEN_SUPPORT) + printf("\tFUSE_CAP_NO_OPEN_SUPPORT\n"); + if(conn->capable & FUSE_CAP_PARALLEL_DIROPS) + printf("\tFUSE_CAP_PARALLEL_DIROPS\n"); + if(conn->capable & FUSE_CAP_POSIX_ACL) + printf("\tFUSE_CAP_POSIX_ACL\n"); + fuse_session_exit(se); +} + + +static struct fuse_lowlevel_ops pc_oper = { + .init = pc_init, +}; + +int main(int argc, char **argv) +{ + struct fuse_args args = FUSE_ARGS_INIT(argc, argv); + char *mountpoint; + int ret = -1; + int fd; + + mountpoint = strdup("/tmp/fuse_printcap_XXXXXX"); + fd = mkstemp(mountpoint); + if(fd == -1) { + perror("mkstemp"); + return 1; + } + + printf("FUSE library version %s\n", fuse_pkgversion()); + fuse_lowlevel_version(); + + se = fuse_session_new(&args, &pc_oper, + sizeof(pc_oper), NULL); + if (se == NULL) + goto err_out1; + + if (fuse_set_signal_handlers(se) != 0) + goto err_out2; + + if (fuse_session_mount(se, mountpoint) != 0) + goto err_out3; + + ret = fuse_session_loop(se); + + fuse_session_unmount(se); +err_out3: + fuse_remove_signal_handlers(se); +err_out2: + fuse_session_destroy(se); +err_out1: + close(fd); + unlink(mountpoint); + free(mountpoint); + fuse_opt_free_args(&args); + + return ret ? 1 : 0; +} -- cgit v1.2.3