selftests/landlock: Test ioctl(2) and ftruncate(2) with open(O_PATH)
authorGünther Noack <gnoack@google.com>
Fri, 19 Apr 2024 16:11:15 +0000 (16:11 +0000)
committerMickaël Salaün <mic@digikod.net>
Mon, 13 May 2024 04:58:31 +0000 (06:58 +0200)
ioctl(2) and ftruncate(2) operations on files opened with O_PATH
should always return EBADF, independent of the
LANDLOCK_ACCESS_FS_TRUNCATE and LANDLOCK_ACCESS_FS_IOCTL_DEV access
rights in that file hierarchy.

Suggested-by: Mickaël Salaün <mic@digikod.net>
Signed-off-by: Günther Noack <gnoack@google.com>
Link: https://lore.kernel.org/r/20240419161122.2023765-5-gnoack@google.com
Signed-off-by: Mickaël Salaün <mic@digikod.net>
tools/testing/selftests/landlock/fs_test.c

index 193dc58bac7a9ea356d46b886d43b9bc8a93fdb4..cb6e9330fcf5688cba89ca3a99666c88abec65fd 100644 (file)
@@ -3902,6 +3902,46 @@ static int test_fionread_ioctl(int fd)
        return 0;
 }
 
+TEST_F_FORK(layout1, o_path_ftruncate_and_ioctl)
+{
+       const struct landlock_ruleset_attr attr = {
+               .handled_access_fs = ACCESS_ALL,
+       };
+       int ruleset_fd, fd;
+
+       /*
+        * Checks that for files opened with O_PATH, both ioctl(2) and
+        * ftruncate(2) yield EBADF, as it is documented in open(2) for the
+        * O_PATH flag.
+        */
+       fd = open(dir_s1d1, O_PATH | O_CLOEXEC);
+       ASSERT_LE(0, fd);
+
+       EXPECT_EQ(EBADF, test_ftruncate(fd));
+       EXPECT_EQ(EBADF, test_fs_ioc_getflags_ioctl(fd));
+
+       ASSERT_EQ(0, close(fd));
+
+       /* Enables Landlock. */
+       ruleset_fd = landlock_create_ruleset(&attr, sizeof(attr), 0);
+       ASSERT_LE(0, ruleset_fd);
+       enforce_ruleset(_metadata, ruleset_fd);
+       ASSERT_EQ(0, close(ruleset_fd));
+
+       /*
+        * Checks that after enabling Landlock,
+        * - the file can still be opened with O_PATH
+        * - both ioctl and truncate still yield EBADF (not EACCES).
+        */
+       fd = open(dir_s1d1, O_PATH | O_CLOEXEC);
+       ASSERT_LE(0, fd);
+
+       EXPECT_EQ(EBADF, test_ftruncate(fd));
+       EXPECT_EQ(EBADF, test_fs_ioc_getflags_ioctl(fd));
+
+       ASSERT_EQ(0, close(fd));
+}
+
 /* clang-format off */
 FIXTURE(ioctl) {};