diff options
Diffstat (limited to 'testcases/kernel/syscalls/fanotify/fanotify14.c')
-rw-r--r-- | testcases/kernel/syscalls/fanotify/fanotify14.c | 198 |
1 files changed, 150 insertions, 48 deletions
diff --git a/testcases/kernel/syscalls/fanotify/fanotify14.c b/testcases/kernel/syscalls/fanotify/fanotify14.c index bfa0349fe..4596511f0 100644 --- a/testcases/kernel/syscalls/fanotify/fanotify14.c +++ b/testcases/kernel/syscalls/fanotify/fanotify14.c @@ -19,6 +19,9 @@ * * ceaf69f8eadc fanotify: do not allow setting dirent events in mask of non-dir * 8698e3bab4dd fanotify: refine the validation checks on non-dir inode mask + * + * The pipes test cases are regression tests for commit: + * 69562eb0bd3e fanotify: disallow mount/sb marks on kernel internal pseudo fs */ #define _GNU_SOURCE @@ -40,6 +43,7 @@ #define FLAGS_DESC(flags) {(flags), (#flags)} +static int pipes[2] = {-1, -1}; static int fanotify_fd; static int fan_report_target_fid_unsupported; static int ignore_mark_unsupported; @@ -60,94 +64,179 @@ static struct test_case_t { /* when mask.flags == 0, fanotify_init() is expected to fail */ struct test_case_flags_t mask; int expected_errno; + int *pfd; } test_cases[] = { /* FAN_REPORT_FID without class FAN_CLASS_NOTIF is not valid */ - {FLAGS_DESC(FAN_CLASS_CONTENT | FAN_REPORT_FID), {}, {}, EINVAL}, + { + .init = FLAGS_DESC(FAN_CLASS_CONTENT | FAN_REPORT_FID), + .expected_errno = EINVAL, + }, /* FAN_REPORT_FID without class FAN_CLASS_NOTIF is not valid */ - {FLAGS_DESC(FAN_CLASS_PRE_CONTENT | FAN_REPORT_FID), {}, {}, EINVAL}, + { + .init = FLAGS_DESC(FAN_CLASS_PRE_CONTENT | FAN_REPORT_FID), + .expected_errno = EINVAL, + }, /* INODE_EVENTS in mask without class FAN_REPORT_FID are not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF), FLAGS_DESC(0), FLAGS_DESC(INODE_EVENTS), - EINVAL}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF), + .mark = FLAGS_DESC(FAN_MARK_INODE), + .mask = FLAGS_DESC(INODE_EVENTS), + .expected_errno = EINVAL, + }, /* INODE_EVENTS in mask with FAN_MARK_MOUNT are not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_FID), - FLAGS_DESC(FAN_MARK_MOUNT), FLAGS_DESC(INODE_EVENTS), EINVAL}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_FID), + .mark = FLAGS_DESC(FAN_MARK_MOUNT), + .mask = FLAGS_DESC(INODE_EVENTS), + .expected_errno = EINVAL, + }, /* FAN_REPORT_NAME without FAN_REPORT_DIR_FID is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_NAME), {}, {}, EINVAL}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_NAME), + .expected_errno = EINVAL, + }, /* FAN_REPORT_NAME without FAN_REPORT_DIR_FID is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_FID | FAN_REPORT_NAME), {}, - {}, EINVAL}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_FID | FAN_REPORT_NAME), + .expected_errno = EINVAL, + }, /* FAN_REPORT_TARGET_FID without FAN_REPORT_FID is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_TARGET_FID | FAN_REPORT_DFID_NAME), - {}, {}, EINVAL}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_TARGET_FID | FAN_REPORT_DFID_NAME), + .expected_errno = EINVAL, + }, /* FAN_REPORT_TARGET_FID without FAN_REPORT_NAME is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_TARGET_FID | FAN_REPORT_DFID_FID), - {}, {}, EINVAL}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_TARGET_FID | FAN_REPORT_DFID_FID), + .expected_errno = EINVAL, + }, /* FAN_RENAME without FAN_REPORT_NAME is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_FID), FLAGS_DESC(0), - FLAGS_DESC(FAN_RENAME), EINVAL}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_FID), + .mark = FLAGS_DESC(FAN_MARK_INODE), + .mask = FLAGS_DESC(FAN_RENAME), + .expected_errno = EINVAL, + }, /* With FAN_MARK_ONLYDIR on non-dir is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF), FLAGS_DESC(FAN_MARK_ONLYDIR), - FLAGS_DESC(FAN_OPEN), ENOTDIR}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF), + .mark = FLAGS_DESC(FAN_MARK_ONLYDIR), + .mask = FLAGS_DESC(FAN_OPEN), + .expected_errno = ENOTDIR, + }, /* With FAN_REPORT_TARGET_FID, FAN_DELETE on non-dir is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME_TARGET), - FLAGS_DESC(0), FLAGS_DESC(FAN_DELETE), ENOTDIR}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME_TARGET), + .mark = FLAGS_DESC(FAN_MARK_INODE), + .mask = FLAGS_DESC(FAN_DELETE), + .expected_errno = ENOTDIR, + }, /* With FAN_REPORT_TARGET_FID, FAN_RENAME on non-dir is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME_TARGET), - FLAGS_DESC(0), FLAGS_DESC(FAN_RENAME), ENOTDIR}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME_TARGET), + .mark = FLAGS_DESC(FAN_MARK_INODE), + .mask = FLAGS_DESC(FAN_RENAME), + .expected_errno = ENOTDIR, + }, /* With FAN_REPORT_TARGET_FID, FAN_ONDIR on non-dir is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME_TARGET), - FLAGS_DESC(0), FLAGS_DESC(FAN_OPEN | FAN_ONDIR), ENOTDIR}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME_TARGET), + .mark = FLAGS_DESC(FAN_MARK_INODE), + .mask = FLAGS_DESC(FAN_OPEN | FAN_ONDIR), + .expected_errno = ENOTDIR, + }, /* With FAN_REPORT_TARGET_FID, FAN_EVENT_ON_CHILD on non-dir is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME_TARGET), - FLAGS_DESC(0), FLAGS_DESC(FAN_OPEN | FAN_EVENT_ON_CHILD), - ENOTDIR}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME_TARGET), + .mark = FLAGS_DESC(FAN_MARK_INODE), + .mask = FLAGS_DESC(FAN_OPEN | FAN_EVENT_ON_CHILD), + .expected_errno = ENOTDIR, + }, /* FAN_MARK_IGNORE_SURV with FAN_DELETE on non-dir is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME), - FLAGS_DESC(FAN_MARK_IGNORE_SURV), FLAGS_DESC(FAN_DELETE), - ENOTDIR}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME), + .mark = FLAGS_DESC(FAN_MARK_IGNORE_SURV), + .mask = FLAGS_DESC(FAN_DELETE), + .expected_errno = ENOTDIR, + }, /* FAN_MARK_IGNORE_SURV with FAN_RENAME on non-dir is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME), - FLAGS_DESC(FAN_MARK_IGNORE_SURV), FLAGS_DESC(FAN_RENAME), - ENOTDIR}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME), + .mark = FLAGS_DESC(FAN_MARK_IGNORE_SURV), + .mask = FLAGS_DESC(FAN_RENAME), + .expected_errno = ENOTDIR, + }, /* FAN_MARK_IGNORE_SURV with FAN_ONDIR on non-dir is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME), - FLAGS_DESC(FAN_MARK_IGNORE_SURV), - FLAGS_DESC(FAN_OPEN | FAN_ONDIR), ENOTDIR}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME), + .mark = FLAGS_DESC(FAN_MARK_IGNORE_SURV), + .mask = FLAGS_DESC(FAN_OPEN | FAN_ONDIR), + .expected_errno = ENOTDIR, + }, /* FAN_MARK_IGNORE_SURV with FAN_EVENT_ON_CHILD on non-dir is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME), - FLAGS_DESC(FAN_MARK_IGNORE_SURV), - FLAGS_DESC(FAN_OPEN | FAN_EVENT_ON_CHILD), ENOTDIR}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF | FAN_REPORT_DFID_NAME), + .mark = FLAGS_DESC(FAN_MARK_IGNORE_SURV), + .mask = FLAGS_DESC(FAN_OPEN | FAN_EVENT_ON_CHILD), + .expected_errno = ENOTDIR, + }, /* FAN_MARK_IGNORE without FAN_MARK_IGNORED_SURV_MODIFY on directory is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF), FLAGS_DESC(FAN_MARK_IGNORE), - FLAGS_DESC(FAN_OPEN), EISDIR}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF), + .mark = FLAGS_DESC(FAN_MARK_IGNORE), + .mask = FLAGS_DESC(FAN_OPEN), + .expected_errno = EISDIR, + }, /* FAN_MARK_IGNORE without FAN_MARK_IGNORED_SURV_MODIFY on mount mark is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF), - FLAGS_DESC(FAN_MARK_MOUNT | FAN_MARK_IGNORE), - FLAGS_DESC(FAN_OPEN), EINVAL}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF), + .mark = FLAGS_DESC(FAN_MARK_MOUNT | FAN_MARK_IGNORE), + .mask = FLAGS_DESC(FAN_OPEN), + .expected_errno = EINVAL, + }, /* FAN_MARK_IGNORE without FAN_MARK_IGNORED_SURV_MODIFY on filesystem mark is not valid */ - {FLAGS_DESC(FAN_CLASS_NOTIF), - FLAGS_DESC(FAN_MARK_FILESYSTEM | FAN_MARK_IGNORE), - FLAGS_DESC(FAN_OPEN), EINVAL}, + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF), + .mark = FLAGS_DESC(FAN_MARK_FILESYSTEM | FAN_MARK_IGNORE), + .mask = FLAGS_DESC(FAN_OPEN), + .expected_errno = EINVAL, + }, + /* mount mark on anonymous pipe is not valid */ + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF), + .mark = FLAGS_DESC(FAN_MARK_MOUNT), + .mask = { FAN_ACCESS, "anonymous pipe"}, + .pfd = pipes, + .expected_errno = EINVAL, + }, + /* filesystem mark on anonymous pipe is not valid */ + { + .init = FLAGS_DESC(FAN_CLASS_NOTIF), + .mark = FLAGS_DESC(FAN_MARK_FILESYSTEM), + .mask = { FAN_ACCESS, "anonymous pipe"}, + .pfd = pipes, + .expected_errno = EINVAL, + }, }; static void do_test(unsigned int number) @@ -185,11 +274,17 @@ static void do_test(unsigned int number) /* Set mark on non-dir only when expecting error ENOTDIR */ const char *path = tc->expected_errno == ENOTDIR ? FILE1 : MNTPOINT; + int dirfd = AT_FDCWD; + + if (tc->pfd) { + dirfd = tc->pfd[0]; + path = NULL; + } - tst_res(TINFO, "Testing fanotify_mark(FAN_MARK_ADD | %s, %s)", + tst_res(TINFO, "Testing %s with %s", tc->mark.desc, tc->mask.desc); TST_EXP_FD_OR_FAIL(fanotify_mark(fanotify_fd, FAN_MARK_ADD | tc->mark.flags, - tc->mask.flags, AT_FDCWD, path), + tc->mask.flags, dirfd, path), tc->expected_errno); /* @@ -231,12 +326,18 @@ static void do_setup(void) /* Create temporary test file to place marks on */ SAFE_FILE_PRINTF(FILE1, "0"); + /* Create anonymous pipes to place marks on */ + SAFE_PIPE2(pipes, O_CLOEXEC); } static void do_cleanup(void) { if (fanotify_fd > 0) SAFE_CLOSE(fanotify_fd); + if (pipes[0] != -1) + SAFE_CLOSE(pipes[0]); + if (pipes[1] != -1) + SAFE_CLOSE(pipes[1]); } static struct tst_test test = { @@ -251,6 +352,7 @@ static struct tst_test test = { .tags = (const struct tst_tag[]) { {"linux-git", "ceaf69f8eadc"}, {"linux-git", "8698e3bab4dd"}, + {"linux-git", "69562eb0bd3e"}, {} } }; |