1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "sandbox/linux/seccomp-bpf-helpers/baseline_policy.h"
9 #include <sys/syscall.h>
10 #include <sys/types.h>
14 #include "base/posix/eintr_wrapper.h"
15 #include "base/threading/thread.h"
16 #include "build/build_config.h"
17 #include "sandbox/linux/seccomp-bpf-helpers/sigsys_handlers.h"
18 #include "sandbox/linux/seccomp-bpf/bpf_tests.h"
19 #include "sandbox/linux/seccomp-bpf/sandbox_bpf.h"
20 #include "sandbox/linux/services/linux_syscalls.h"
21 #include "sandbox/linux/services/thread_helpers.h"
22 #include "sandbox/linux/tests/unit_tests.h"
28 // |pid| is the return value of a fork()-like call. This
29 // makes sure that if fork() succeeded the child exits
30 // and the parent waits for it.
31 void HandlePostForkReturn(pid_t pid) {
32 const int kChildExitCode = 1;
35 PCHECK(pid == HANDLE_EINTR(waitpid(pid, &status, 0)));
36 CHECK(WIFEXITED(status));
37 CHECK_EQ(kChildExitCode, WEXITSTATUS(status));
38 } else if (pid == 0) {
39 _exit(kChildExitCode);
43 // Check that HandlePostForkReturn works.
44 TEST(BaselinePolicy, HandlePostForkReturn) {
46 HandlePostForkReturn(pid);
49 BPF_TEST_C(BaselinePolicy, FchmodErrno, BaselinePolicy) {
50 int ret = fchmod(-1, 07777);
51 BPF_ASSERT_EQ(-1, ret);
52 // Without the sandbox, this would EBADF instead.
53 BPF_ASSERT_EQ(EPERM, errno);
56 // TODO(jln): make this work with the sanitizers.
57 #if !defined(ADDRESS_SANITIZER) && !defined(THREAD_SANITIZER)
59 BPF_TEST_C(BaselinePolicy, ForkErrno, BaselinePolicy) {
62 const int fork_errno = errno;
63 HandlePostForkReturn(pid);
65 BPF_ASSERT_EQ(-1, pid);
66 BPF_ASSERT_EQ(EPERM, fork_errno);
69 pid_t ForkX86Glibc() {
70 return syscall(__NR_clone, CLONE_PARENT_SETTID | SIGCHLD);
73 BPF_TEST_C(BaselinePolicy, ForkX86Eperm, BaselinePolicy) {
75 pid_t pid = ForkX86Glibc();
76 const int fork_errno = errno;
77 HandlePostForkReturn(pid);
79 BPF_ASSERT_EQ(-1, pid);
80 BPF_ASSERT_EQ(EPERM, fork_errno);
83 pid_t ForkARMGlibc() {
84 return syscall(__NR_clone,
85 CLONE_CHILD_SETTID | CLONE_CHILD_CLEARTID | SIGCHLD);
88 BPF_TEST_C(BaselinePolicy, ForkArmEperm, BaselinePolicy) {
90 pid_t pid = ForkARMGlibc();
91 const int fork_errno = errno;
92 HandlePostForkReturn(pid);
94 BPF_ASSERT_EQ(-1, pid);
95 BPF_ASSERT_EQ(EPERM, fork_errno);
98 BPF_TEST_C(BaselinePolicy, CreateThread, BaselinePolicy) {
99 base::Thread thread("sandbox_tests");
100 BPF_ASSERT(thread.Start());
103 BPF_DEATH_TEST_C(BaselinePolicy,
104 DisallowedCloneFlagCrashes,
105 DEATH_MESSAGE(GetCloneErrorMessageContentForTests()),
107 pid_t pid = syscall(__NR_clone, CLONE_THREAD | SIGCHLD);
108 HandlePostForkReturn(pid);
111 #endif // !defined(ADDRESS_SANITIZER) && !defined(THREAD_SANITIZER)
115 } // namespace sandbox