Skip site navigation (1)Skip section navigation (2)
Date:      Fri, 15 Mar 2019 18:06:52 +0000 (UTC)
From:      Alan Somers <asomers@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-projects@freebsd.org
Subject:   svn commit: r345195 - projects/fuse2/tests/sys/fs/fuse
Message-ID:  <201903151806.x2FI6qin080250@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: asomers
Date: Fri Mar 15 18:06:51 2019
New Revision: 345195
URL: https://svnweb.freebsd.org/changeset/base/345195

Log:
  fuse(4): add tests for ENOSYS special cases
  
  PR:		236557
  Sponsored by:	The FreeBSD Foundation

Modified:
  projects/fuse2/tests/sys/fs/fuse/access.cc
  projects/fuse2/tests/sys/fs/fuse/create.cc
  projects/fuse2/tests/sys/fs/fuse/flush.cc
  projects/fuse2/tests/sys/fs/fuse/fsync.cc
  projects/fuse2/tests/sys/fs/fuse/fsyncdir.cc
  projects/fuse2/tests/sys/fs/fuse/xattr.cc

Modified: projects/fuse2/tests/sys/fs/fuse/access.cc
==============================================================================
--- projects/fuse2/tests/sys/fs/fuse/access.cc	Fri Mar 15 17:19:36 2019	(r345194)
+++ projects/fuse2/tests/sys/fs/fuse/access.cc	Fri Mar 15 18:06:51 2019	(r345195)
@@ -41,6 +41,18 @@ using namespace testing;
 
 class Access: public FuseTest {
 public:
+void expect_access(uint64_t ino, mode_t access_mode, int error)
+{
+	EXPECT_CALL(*m_mock, process(
+		ResultOf([=](auto in) {
+			return (in->header.opcode == FUSE_ACCESS &&
+				in->header.nodeid == ino &&
+				in->body.access.mask == access_mode);
+		}, Eq(true)),
+		_)
+	).WillOnce(Invoke(ReturnErrno(error)));
+}
+
 void expect_lookup(const char *relpath, uint64_t ino)
 {
 	FuseTest::expect_lookup(relpath, ino, S_IFREG | 0644, 1);
@@ -59,20 +71,33 @@ TEST_F(Access, DISABLED_eaccess)
 	mode_t	access_mode = X_OK;
 
 	expect_lookup(RELPATH, ino);
-	EXPECT_CALL(*m_mock, process(
-		ResultOf([=](auto in) {
-			return (in->header.opcode == FUSE_ACCESS &&
-				in->header.nodeid == ino &&
-				in->body.access.mask == access_mode);
-		}, Eq(true)),
-		_)
-	).WillOnce(Invoke(ReturnErrno(EACCES)));
+	expect_access(ino, access_mode, EACCES);
 
-
 	ASSERT_NE(0, access(FULLPATH, access_mode));
 	ASSERT_EQ(EACCES, errno);
 }
 
+/*
+ * If the filesystem returns ENOSYS, then it is treated as a permanent success,
+ * and subsequent VOP_ACCESS calls will succeed automatically without querying
+ * the daemon.
+ */
+/* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236557 */
+/* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236291 */
+TEST_F(Access, DISABLED_enosys)
+{
+	const char FULLPATH[] = "mountpoint/some_file.txt";
+	const char RELPATH[] = "some_file.txt";
+	uint64_t ino = 42;
+	mode_t	access_mode = R_OK;
+
+	expect_lookup(RELPATH, ino);
+	expect_access(ino, access_mode, ENOSYS);
+
+	ASSERT_EQ(0, access(FULLPATH, access_mode)) << strerror(errno);
+	ASSERT_EQ(0, access(FULLPATH, access_mode)) << strerror(errno);
+}
+
 /* The successful case of FUSE_ACCESS.  */
 /* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236291 */
 TEST_F(Access, DISABLED_ok)
@@ -83,14 +108,7 @@ TEST_F(Access, DISABLED_ok)
 	mode_t	access_mode = R_OK;
 
 	expect_lookup(RELPATH, ino);
-	EXPECT_CALL(*m_mock, process(
-		ResultOf([=](auto in) {
-			return (in->header.opcode == FUSE_ACCESS &&
-				in->header.nodeid == ino &&
-				in->body.access.mask == access_mode);
-		}, Eq(true)),
-		_)
-	).WillOnce(Invoke(ReturnErrno(0)));
+	expect_access(ino, access_mode, 0);
 
 	ASSERT_EQ(0, access(FULLPATH, access_mode)) << strerror(errno);
 }

Modified: projects/fuse2/tests/sys/fs/fuse/create.cc
==============================================================================
--- projects/fuse2/tests/sys/fs/fuse/create.cc	Fri Mar 15 17:19:36 2019	(r345194)
+++ projects/fuse2/tests/sys/fs/fuse/create.cc	Fri Mar 15 18:06:51 2019	(r345195)
@@ -114,6 +114,7 @@ TEST_F(Create, eexist)
  * to FUSE_MKNOD/FUSE_OPEN
  */
 /* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236236 */
+/* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236557 */
 TEST_F(Create, DISABLED_Enosys)
 {
 	const char FULLPATH[] = "mountpoint/some_file.txt";

Modified: projects/fuse2/tests/sys/fs/fuse/flush.cc
==============================================================================
--- projects/fuse2/tests/sys/fs/fuse/flush.cc	Fri Mar 15 17:19:36 2019	(r345194)
+++ projects/fuse2/tests/sys/fs/fuse/flush.cc	Fri Mar 15 18:06:51 2019	(r345195)
@@ -134,6 +134,35 @@ TEST_F(Flush, DISABLED_eio)
 	ASSERT_TRUE(0 == close(fd) || errno == EIO) << strerror(errno);
 }
 
+/*
+ * If the filesystem returns ENOSYS, it will be treated as success and
+ * no more FUSE_FLUSH operations will be sent to the daemon
+ */
+/* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236405 */
+/* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236557 */
+TEST_F(Flush, DISABLED_enosys)
+{
+	const char FULLPATH[] = "mountpoint/some_file.txt";
+	const char RELPATH[] = "some_file.txt";
+	uint64_t ino = 42;
+	int fd, fd2;
+
+	expect_lookup(RELPATH, ino);
+	expect_open(ino, 0, 1);
+	expect_getattr(ino, 0);
+	/* On the 2nd close, FUSE_FLUSH won't be sent at all */
+	expect_flush(ino, 1, 0, ReturnErrno(ENOSYS));
+	expect_release();
+
+	fd = open(FULLPATH, O_WRONLY);
+	EXPECT_LE(0, fd) << strerror(errno);
+
+	fd2 = dup(fd);
+
+	EXPECT_EQ(0, close(fd2)) << strerror(errno);
+	EXPECT_EQ(0, close(fd)) << strerror(errno);
+}
+
 /* A FUSE_FLUSH should be sent on close(2) */
 /* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236405 */
 TEST_F(Flush, DISABLED_flush)

Modified: projects/fuse2/tests/sys/fs/fuse/fsync.cc
==============================================================================
--- projects/fuse2/tests/sys/fs/fuse/fsync.cc	Fri Mar 15 17:19:36 2019	(r345194)
+++ projects/fuse2/tests/sys/fs/fuse/fsync.cc	Fri Mar 15 18:06:51 2019	(r345195)
@@ -56,7 +56,6 @@ void expect_fsync(uint64_t ino, uint32_t flags, int er
 		ResultOf([=](auto in) {
 			return (in->header.opcode == FUSE_FSYNC &&
 				in->header.nodeid == ino &&
-				//(pid_t)in->header.pid == getpid() &&
 				in->body.fsync.fh == FH &&
 				in->body.fsync.fsync_flags == flags);
 		}, Eq(true)),
@@ -174,6 +173,39 @@ TEST_F(Fsync, DISABLED_eio)
 
 	/* Deliberately leak fd.  close(2) will be tested in release.cc */
 }
+
+/*
+ * If the filesystem returns ENOSYS, it will be treated as success and
+ * subsequent calls to VOP_FSYNC will succeed automatically without being sent
+ * to the filesystem daemon
+ */
+/* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236474 */
+/* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236557 */
+TEST_F(Fsync, DISABLED_enosys)
+{
+	const char FULLPATH[] = "mountpoint/some_file.txt";
+	const char RELPATH[] = "some_file.txt";
+	const char *CONTENTS = "abcdefgh";
+	ssize_t bufsize = strlen(CONTENTS);
+	uint64_t ino = 42;
+	int fd;
+
+	expect_lookup(RELPATH, ino);
+	expect_open(ino, 0, 1);
+	expect_getattr(ino, 0);
+	expect_write(ino, bufsize, CONTENTS);
+	expect_fsync(ino, FUSE_FSYNC_FDATASYNC, ENOSYS);
+
+	fd = open(FULLPATH, O_RDWR);
+	ASSERT_LE(0, fd) << strerror(errno);
+	ASSERT_EQ(bufsize, write(fd, CONTENTS, bufsize)) << strerror(errno);
+	EXPECT_EQ(0, fdatasync(fd));
+
+	/* Subsequent calls shouldn't query the daemon*/
+	EXPECT_EQ(0, fdatasync(fd));
+	/* Deliberately leak fd.  close(2) will be tested in release.cc */
+}
+
 
 /* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236474 */
 TEST_F(Fsync, DISABLED_fdatasync)

Modified: projects/fuse2/tests/sys/fs/fuse/fsyncdir.cc
==============================================================================
--- projects/fuse2/tests/sys/fs/fuse/fsyncdir.cc	Fri Mar 15 17:19:36 2019	(r345194)
+++ projects/fuse2/tests/sys/fs/fuse/fsyncdir.cc	Fri Mar 15 18:06:51 2019	(r345195)
@@ -119,6 +119,34 @@ TEST_F(FsyncDir, DISABLED_eio)
 	/* Deliberately leak fd.  close(2) will be tested in release.cc */
 }
 
+/*
+ * If the filesystem returns ENOSYS, it will be treated as success and
+ * subsequent calls to VOP_FSYNC will succeed automatically without being sent
+ * to the filesystem daemon
+ */
+/* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236474 */
+/* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236557 */
+TEST_F(FsyncDir, DISABLED_enosys)
+{
+	const char FULLPATH[] = "mountpoint/some_dir";
+	const char RELPATH[] = "some_dir";
+	uint64_t ino = 42;
+	int fd;
+
+	expect_lookup(RELPATH, ino);
+	expect_opendir(ino);
+	expect_fsyncdir(ino, FUSE_FSYNC_FDATASYNC, ENOSYS);
+
+	fd = open(FULLPATH, O_DIRECTORY);
+	ASSERT_LE(0, fd) << strerror(errno);
+	EXPECT_EQ(0, fsync(fd)) << strerror(errno);
+
+	/* Subsequent calls shouldn't query the daemon*/
+	EXPECT_EQ(0, fsync(fd)) << strerror(errno);
+
+	/* Deliberately leak fd.  close(2) will be tested in release.cc */
+}
+
 /* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236474 */
 TEST_F(FsyncDir, DISABLED_fsyncdata)
 {

Modified: projects/fuse2/tests/sys/fs/fuse/xattr.cc
==============================================================================
--- projects/fuse2/tests/sys/fs/fuse/xattr.cc	Fri Mar 15 17:19:36 2019	(r345194)
+++ projects/fuse2/tests/sys/fs/fuse/xattr.cc	Fri Mar 15 18:06:51 2019	(r345195)
@@ -130,6 +130,32 @@ TEST_F(Getxattr, enoattr)
 }
 
 /*
+ * If the filesystem returns ENOSYS, then it will be treated as a permanent
+ * failure and all future VOP_GETEXTATTR calls will fail with EOPNOTSUPP
+ * without querying the filesystem daemon
+ */
+/* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236557 */
+TEST_F(Getxattr, DISABLED_enosys)
+{
+	char data[80];
+	uint64_t ino = 42;
+	int ns = EXTATTR_NAMESPACE_USER;
+	ssize_t r;
+
+	expect_lookup(RELPATH, ino, S_IFREG | 0644, 1);
+	expect_getxattr(ino, "user.foo", ReturnErrno(ENOSYS));
+
+	r = extattr_get_file(FULLPATH, ns, "foo", data, sizeof(data));
+	ASSERT_EQ(-1, r);
+	EXPECT_EQ(EOPNOTSUPP, errno);
+
+	/* Subsequent attempts should not query the filesystem at all */
+	r = extattr_get_file(FULLPATH, ns, "foo", data, sizeof(data));
+	ASSERT_EQ(-1, r);
+	EXPECT_EQ(EOPNOTSUPP, errno);
+}
+
+/*
  * On FreeBSD, if the user passes an insufficiently large buffer then the
  * filesystem is supposed to copy as much of the attribute's value as will fit.
  *
@@ -228,6 +254,28 @@ TEST_F(Getxattr, user)
 }
 
 /*
+ * If the filesystem returns ENOSYS, then it will be treated as a permanent
+ * failure and all future VOP_LISTEXTATTR calls will fail with EOPNOTSUPP
+ * without querying the filesystem daemon
+ */
+/* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236557 */
+TEST_F(Listxattr, DISABLED_enosys)
+{
+	uint64_t ino = 42;
+	int ns = EXTATTR_NAMESPACE_USER;
+
+	expect_lookup(RELPATH, ino, S_IFREG | 0644, 1);
+	expect_listxattr(ino, 0, ReturnErrno(ENOSYS));
+
+	ASSERT_EQ(-1, extattr_list_file(FULLPATH, ns, NULL, 0));
+	EXPECT_EQ(EOPNOTSUPP, errno);
+
+	/* Subsequent attempts should not query the filesystem at all */
+	ASSERT_EQ(-1, extattr_list_file(FULLPATH, ns, NULL, 0));
+	EXPECT_EQ(EOPNOTSUPP, errno);
+}
+
+/*
  * Listing extended attributes failed because they aren't configured on this
  * filesystem
  */
@@ -425,6 +473,28 @@ TEST_F(Removexattr, enoattr)
 	ASSERT_EQ(ENOATTR, errno);
 }
 
+/*
+ * If the filesystem returns ENOSYS, then it will be treated as a permanent
+ * failure and all future VOP_DELETEEXTATTR calls will fail with EOPNOTSUPP
+ * without querying the filesystem daemon
+ */
+/* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236557 */
+TEST_F(Removexattr, DISABLED_enosys)
+{
+	uint64_t ino = 42;
+	int ns = EXTATTR_NAMESPACE_USER;
+
+	expect_lookup(RELPATH, ino, S_IFREG | 0644, 1);
+	expect_removexattr(ino, "user.foo", ENOSYS);
+
+	ASSERT_EQ(-1, extattr_delete_file(FULLPATH, ns, "foo"));
+	EXPECT_EQ(EOPNOTSUPP, errno);
+
+	/* Subsequent attempts should not query the filesystem at all */
+	ASSERT_EQ(-1, extattr_delete_file(FULLPATH, ns, "foo"));
+	EXPECT_EQ(EOPNOTSUPP, errno);
+}
+
 /* Successfully remove a user xattr */
 TEST_F(Removexattr, user)
 {
@@ -449,6 +519,33 @@ TEST_F(Removexattr, system)
 
 	ASSERT_EQ(0, extattr_delete_file(FULLPATH, ns, "foo"))
 		<< strerror(errno);
+}
+
+/*
+ * If the filesystem returns ENOSYS, then it will be treated as a permanent
+ * failure and all future VOP_SETEXTATTR calls will fail with EOPNOTSUPP
+ * without querying the filesystem daemon
+ */
+/* https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=236557 */
+TEST_F(Setxattr, DISABLED_enosys)
+{
+	uint64_t ino = 42;
+	const char value[] = "whatever";
+	ssize_t value_len = strlen(value) + 1;
+	int ns = EXTATTR_NAMESPACE_USER;
+	ssize_t r;
+
+	expect_lookup(RELPATH, ino, S_IFREG | 0644, 1);
+	expect_setxattr(ino, "user.foo", value, ReturnErrno(ENOSYS));
+
+	r = extattr_set_file(FULLPATH, ns, "foo", (void*)value, value_len);
+	ASSERT_EQ(-1, r);
+	EXPECT_EQ(EOPNOTSUPP, errno);
+
+	/* Subsequent attempts should not query the filesystem at all */
+	r = extattr_set_file(FULLPATH, ns, "foo", (void*)value, value_len);
+	ASSERT_EQ(-1, r);
+	EXPECT_EQ(EOPNOTSUPP, errno);
 }
 
 /*



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201903151806.x2FI6qin080250>