linux-fsdevel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Amir Goldstein <amir73il@gmail.com>
To: Jan Kara <jack@suse.cz>
Cc: Matthew Bobrowski <repnop@google.com>,
	Christian Brauner <brauner@kernel.org>,
	linux-fsdevel@vger.kernel.org, linux-api@vger.kernel.org
Subject: [RFC][PATCH] fanotify: Enable FAN_REPORT_FID on more filesystem types
Date: Tue, 11 Apr 2023 15:40:37 +0300	[thread overview]
Message-ID: <20230411124037.1629654-1-amir73il@gmail.com> (raw)

If kernel supports FAN_REPORT_ANY_FID, use this flag to allow testing
also filesystems that do not support fsid or NFS file handles (e.g. fuse).

Signed-off-by: Amir Goldstein <amir73il@gmail.com>
---

Jan,

I wanted to run an idea by you.

My motivation is to close functional gaps between fanotify and inotify.

One of the largest gaps right now is that FAN_REPORT_FID is limited
to a subset of local filesystems.

The idea is to report fid's that are "good enough" and that there
is no need to require that fid's can be used by open_by_handle_at()
because that is a non-requirement for most use cases, unpriv listener
in particular.

I chose a rather generic name for the flag to opt-in for "good enough"
fid's.  At first, I was going to make those fid's self describing the
fact that they are not NFS file handles, but in the name of simplicity
to the API, I decided that this is not needed.

The patch below is from the LTP test [1] that verifies reported fid's.
I am posting it because I think that the function fanotify_get_fid()
demonstrates well, how a would-be fanotify library could be used to get
a canonical fid.

That would-be routine can easily return the source of the fid values
for a given filesystem and that information is constant for all objects
on a given filesystem instance.

The choise to encode an actual file_handle of type FILEID_INO64 may
seem controversial at first, but it simplifies things so much, that I
grew very fond of it.

The LTP patch also demonstrated how terribly trivial it would be to
adapt any existing fanotify programs to support any fs.

Kernel patches [2] are pretty simple IMO and
man page patch [3] demonstrates that the API changes are minimal.

Thoughts?

Amir.

P.S.: Apropos closing gaps to inotify, I have WIP patches to add
      FAN_UNMOUNT and possibly FAN_IGNORED events.

[1] https://github.com/amir73il/ltp/commits/fan_report_any_fid
[2] https://github.com/amir73il/linux/commits/fan_report_any_fid
[3] https://github.com/amir73il/man-pages/commits/fan_report_any_fid

 include/lapi/fanotify.h                       |  3 ++
 testcases/kernel/syscalls/fanotify/fanotify.h | 32 +++++++++++++++----
 .../kernel/syscalls/fanotify/fanotify13.c     | 16 +++++++---
 3 files changed, 41 insertions(+), 10 deletions(-)

diff --git a/include/lapi/fanotify.h b/include/lapi/fanotify.h
index 4bd1a113c..511b35bbd 100644
--- a/include/lapi/fanotify.h
+++ b/include/lapi/fanotify.h
@@ -32,6 +32,9 @@
 #define FAN_REPORT_DFID_NAME_TARGET (FAN_REPORT_DFID_NAME | \
 				     FAN_REPORT_FID | FAN_REPORT_TARGET_FID)
 #endif
+#ifndef FAN_REPORT_ANY_FID
+#define FAN_REPORT_ANY_FID	0x00002000
+#endif
 
 /* Non-uapi convenience macros */
 #ifndef FAN_REPORT_DFID_NAME_FID
diff --git a/testcases/kernel/syscalls/fanotify/fanotify.h b/testcases/kernel/syscalls/fanotify/fanotify.h
index 51078103e..b02295138 100644
--- a/testcases/kernel/syscalls/fanotify/fanotify.h
+++ b/testcases/kernel/syscalls/fanotify/fanotify.h
@@ -72,6 +72,10 @@ static inline int safe_fanotify_mark(const char *file, const int lineno,
 #define MAX_HANDLE_SZ		128
 #endif
 
+#ifndef FILEID_INO64
+#define FILEID_INO64		0x80
+#endif
+
 /*
  * Helper function used to obtain fsid and file_handle for a given path.
  * Used by test files correlated to FAN_REPORT_FID functionality.
@@ -80,21 +84,37 @@ static inline void fanotify_get_fid(const char *path, __kernel_fsid_t *fsid,
 				    struct file_handle *handle)
 {
 	int mount_id;
+	struct statx stx;
 	struct statfs stats;
 
+	if (statx(AT_FDCWD, path, 0, 0, &stx) == -1)
+		tst_brk(TBROK | TERRNO,
+			"statx(%s, ...) failed", path);
 	if (statfs(path, &stats) == -1)
 		tst_brk(TBROK | TERRNO,
 			"statfs(%s, ...) failed", path);
 	memcpy(fsid, &stats.f_fsid, sizeof(stats.f_fsid));
 
+	if (!fsid->val[0] && !fsid->val[1]) {
+		/* Fallback to fsid encoded from stx_dev */
+		fsid->val[0] = stx.stx_dev_major;
+		fsid->val[1] = stx.stx_dev_minor;
+	}
+
 	if (name_to_handle_at(AT_FDCWD, path, handle, &mount_id, 0) == -1) {
-		if (errno == EOPNOTSUPP) {
-			tst_brk(TCONF,
-				"filesystem %s does not support file handles",
-				tst_device->fs_type);
+		if (errno != EOPNOTSUPP) {
+			tst_brk(TBROK | TERRNO,
+				"name_to_handle_at(AT_FDCWD, %s, ...) failed", path);
 		}
-		tst_brk(TBROK | TERRNO,
-			"name_to_handle_at(AT_FDCWD, %s, ...) failed", path);
+
+		tst_res(TINFO,
+			"filesystem %s does not support file handles - using ino as fid",
+			tst_device->fs_type);
+
+		/* Fallback to fid encoded from stx_ino */
+		handle->handle_type = FILEID_INO64;
+		handle->handle_bytes = sizeof(stx.stx_ino);
+		memcpy(handle->f_handle, (void *)&stx.stx_ino, sizeof(stx.stx_ino));
 	}
 }
 
diff --git a/testcases/kernel/syscalls/fanotify/fanotify13.c b/testcases/kernel/syscalls/fanotify/fanotify13.c
index c3daaf3a2..e50ad0f75 100644
--- a/testcases/kernel/syscalls/fanotify/fanotify13.c
+++ b/testcases/kernel/syscalls/fanotify/fanotify13.c
@@ -90,6 +90,7 @@ static struct test_case_t {
 
 static int nofid_fd;
 static int fanotify_fd;
+static int fanotify_init_flags;
 static int filesystem_mark_unsupported;
 static char events_buf[BUF_SIZE];
 static struct event_t event_set[EVENT_MAX];
@@ -143,15 +144,16 @@ static void do_test(unsigned int number)
 	struct fanotify_mark_type *mark = &tc->mark;
 
 	tst_res(TINFO,
-		"Test #%d: FAN_REPORT_FID with mark flag: %s",
-		number, mark->name);
+		"Test #%d: %s with mark flag: %s", number,
+		(fanotify_init_flags & FAN_REPORT_ANY_FID) ?
+			"FAN_REPORT_ANY_FID" : "FAN_REPORT_FID", mark->name);
 
 	if (filesystem_mark_unsupported && mark->flag & FAN_MARK_FILESYSTEM) {
 		tst_res(TCONF, "FAN_MARK_FILESYSTEM not supported in kernel?");
 		return;
 	}
 
-	fanotify_fd = SAFE_FANOTIFY_INIT(FAN_CLASS_NOTIF | FAN_REPORT_FID, O_RDONLY);
+	fanotify_fd = SAFE_FANOTIFY_INIT(FAN_CLASS_NOTIF | fanotify_init_flags, O_RDONLY);
 
 	/*
 	 * Place marks on a set of objects and setup the expected masks
@@ -261,7 +263,13 @@ out:
 
 static void do_setup(void)
 {
-	REQUIRE_FANOTIFY_INIT_FLAGS_SUPPORTED_ON_FS(FAN_REPORT_FID, MOUNT_PATH);
+	/* Try FAN_REPORT_ANY_FID */
+	fanotify_init_flags = FAN_REPORT_FID | FAN_REPORT_ANY_FID;
+	if (fanotify_init_flags_supported_on_fs(fanotify_init_flags, MOUNT_PATH)) {
+		/* Fallback to FAN_REPORT_FID */
+		fanotify_init_flags = FAN_REPORT_FID;
+		REQUIRE_FANOTIFY_INIT_FLAGS_SUPPORTED_ON_FS(fanotify_init_flags, MOUNT_PATH);
+	}
 
 	filesystem_mark_unsupported = fanotify_mark_supported_by_kernel(FAN_MARK_FILESYSTEM);
 
-- 
2.34.1


             reply	other threads:[~2023-04-11 12:40 UTC|newest]

Thread overview: 13+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2023-04-11 12:40 Amir Goldstein [this message]
2023-04-12 18:43 ` [RFC][PATCH] fanotify: Enable FAN_REPORT_FID on more filesystem types Jan Kara
2023-04-13  9:25   ` Amir Goldstein
2023-04-17 16:27     ` Jan Kara
2023-09-20  8:26       ` Amir Goldstein
2023-09-20 10:27         ` Jeff Layton
2023-09-20 11:04         ` Jan Kara
2023-09-20 12:41           ` Amir Goldstein
2023-09-20 13:48             ` Jan Kara
2023-09-20 15:12               ` Amir Goldstein
2023-09-20 16:36                 ` Jan Kara
2023-10-18 18:35                   ` Amir Goldstein
2023-10-25 14:11           ` Amir Goldstein

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20230411124037.1629654-1-amir73il@gmail.com \
    --to=amir73il@gmail.com \
    --cc=brauner@kernel.org \
    --cc=jack@suse.cz \
    --cc=linux-api@vger.kernel.org \
    --cc=linux-fsdevel@vger.kernel.org \
    --cc=repnop@google.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).