From cffa61e7b4a1defb1d8453aaefed28477c749d20 Mon Sep 17 00:00:00 2001 From: Alessio Balsini Date: Thu, 27 Jan 2022 14:44:24 +0000 Subject: [PATCH] ANDROID: fs/fuse: Use extended init flags for FUSE_PASSTHROUGH Starting with FUSE 7.36, all the fields for the 32-bit FUSE init flags have been allocated, so commit 53db28933e952 ("fuse: extend init flags") introduces the new 32-bit flags2 field in fuse_init_in and fuse_init_out. That change also adds the FUSE_INIT_RESERVED flag that doesn't have any specific purpose yet, is just reserved and should not be used, and (un)fortunately collides with FUSE_PASSTHROUGH. This change fixes the conflict by simply setting the FUSE_PASSTHROUGH value to the next, latest unused fuse2 bit. Although this is not the best design choice, userspace will know what FUSE_PASSTHROUGH bit to choose based on the FUSE major and minor version for FUSE version: - < 7.36: FUSE_PASSTHROUGH is the 31st bit of flags; - otherwise: FUSE_PASSTHROUGH is the 31st bit of flags2. Test: launch_cvd (both android-mainline and android13-5.10) \ `logcat FuseDaemon:V \*:S` shows no FUSE passthrough errors Bug: 215310351 Signed-off-by: Alessio Balsini Change-Id: I85d7582008b8c093b3172b3f41c6cdf09863dd45 --- fs/fuse/inode.c | 3 ++- include/uapi/linux/fuse.h | 13 ++++++++++++- 2 files changed, 14 insertions(+), 2 deletions(-) diff --git a/fs/fuse/inode.c b/fs/fuse/inode.c index f7dd8e9b2da1..973a723e3397 100644 --- a/fs/fuse/inode.c +++ b/fs/fuse/inode.c @@ -1227,7 +1227,6 @@ void fuse_send_init(struct fuse_mount *fm) FUSE_PARALLEL_DIROPS | FUSE_HANDLE_KILLPRIV | FUSE_POSIX_ACL | FUSE_ABORT_ERROR | FUSE_MAX_PAGES | FUSE_CACHE_SYMLINKS | FUSE_NO_OPENDIR_SUPPORT | FUSE_EXPLICIT_INVAL_DATA | - FUSE_PASSTHROUGH | FUSE_HANDLE_KILLPRIV_V2 | FUSE_SETXATTR_EXT; #ifdef CONFIG_FUSE_DAX if (fm->fc->dax) @@ -1236,6 +1235,8 @@ void fuse_send_init(struct fuse_mount *fm) if (fm->fc->auto_submounts) ia->in.flags |= FUSE_SUBMOUNTS; + ia->in.flags |= FUSE_PASSTHROUGH; + ia->args.opcode = FUSE_INIT; ia->args.in_numargs = 1; ia->args.in_args[0].size = sizeof(ia->in); diff --git a/include/uapi/linux/fuse.h b/include/uapi/linux/fuse.h index 574cbae01826..58d748bafb88 100644 --- a/include/uapi/linux/fuse.h +++ b/include/uapi/linux/fuse.h @@ -372,7 +372,18 @@ struct fuse_file_lock { #define FUSE_SUBMOUNTS (1 << 27) #define FUSE_HANDLE_KILLPRIV_V2 (1 << 28) #define FUSE_SETXATTR_EXT (1 << 29) -#define FUSE_PASSTHROUGH (1 << 31) + +/* + * For FUSE < 7.36 FUSE_PASSTHROUGH has value (1 << 31). + * This condition check is not really required, but would prevent having a + * broken commit in the tree. + */ +#if FUSE_KERNEL_VERSION > 7 || \ + (FUSE_KERNEL_VERSION == 7 && FUSE_KERNEL_MINOR_VERSION >= 36) +#define FUSE_PASSTHROUGH (1ULL << 63) +#else +#define FUSE_PASSTHROUGH (1 << 31) +#endif /** * CUSE INIT request/reply flags