1 | // RUN: %clangxx %s -o %t && %run %t %p |
2 | |
3 | // UNSUPPORTED: android |
4 | |
5 | #include <assert.h> |
6 | #include <errno.h> |
7 | #include <linux/filter.h> |
8 | #include <linux/seccomp.h> |
9 | #include <stdint.h> |
10 | #include <string.h> |
11 | #include <sys/mman.h> |
12 | #include <sys/prctl.h> |
13 | |
14 | #ifndef PR_SCHED_CORE |
15 | # define PR_SCHED_CORE 62 |
16 | #endif |
17 | |
18 | #ifndef PR_SCHED_CORE_CREATE |
19 | # define PR_SCHED_CORE_CREATE 1 |
20 | #endif |
21 | |
22 | #ifndef PR_SCHED_CORE_GET |
23 | # define PR_SCHED_CORE_GET 0 |
24 | #endif |
25 | |
26 | #ifndef PR_SET_VMA |
27 | # define PR_SET_VMA 0x53564d41 |
28 | # define PR_SET_VMA_ANON_NAME 0 |
29 | #endif |
30 | |
31 | int main() { |
32 | int res; |
33 | res = prctl(PR_SCHED_CORE, PR_SCHED_CORE_CREATE, 0, 0, 0); |
34 | if (res < 0) { |
35 | assert(errno == EINVAL || errno == ENODEV); |
36 | } else { |
37 | uint64_t cookie = 0; |
38 | res = prctl(PR_SCHED_CORE, PR_SCHED_CORE_GET, 0, 0, &cookie); |
39 | if (res < 0) { |
40 | assert(errno == EINVAL); |
41 | } else { |
42 | assert(cookie != 0); |
43 | } |
44 | } |
45 | |
46 | int signum; |
47 | res = prctl(PR_GET_PDEATHSIG, reinterpret_cast<unsigned long>(&signum)); |
48 | if (res < 0) { |
49 | assert(errno == EINVAL); |
50 | } else { |
51 | assert(signum == 0); |
52 | } |
53 | |
54 | char invname[81], vlname[] = "prctl" ; |
55 | for (auto i = 0; i < sizeof(invname); i++) { |
56 | invname[i] = 0x1e; |
57 | } |
58 | invname[80] = 0; |
59 | auto p = |
60 | mmap(addr: nullptr, len: 128, PROT_READ | PROT_WRITE, MAP_ANON | MAP_PRIVATE, fd: -1, offset: 0); |
61 | assert(p != MAP_FAILED); |
62 | // regardless of kernel support, the name is invalid |
63 | res = prctl(PR_SET_VMA, PR_SET_VMA_ANON_NAME, (uintptr_t)p, 128, |
64 | (uintptr_t)invname); |
65 | assert(res == -1); |
66 | assert(errno == EINVAL); |
67 | res = prctl(PR_SET_VMA, PR_SET_VMA_ANON_NAME, (uintptr_t)p, 128, |
68 | (uintptr_t)vlname); |
69 | if (res < 0) { |
70 | assert(errno == EINVAL); |
71 | } |
72 | munmap(addr: p, len: 128); |
73 | |
74 | res = prctl(PR_SET_NAME, "tname" ); |
75 | if (res == 0) { |
76 | char name[16]; |
77 | res = prctl(PR_GET_NAME, name); |
78 | if (res == 0) { |
79 | assert(!strcmp(name, "tname" )); |
80 | } |
81 | } |
82 | |
83 | sock_filter f[] = {{.code = (BPF_LD | BPF_W | BPF_ABS), |
84 | .k = (uint32_t)(SKF_AD_OFF | SKF_AD_CPU)}, |
85 | {.code = (BPF_RET | BPF_A), .k = 0}}; |
86 | sock_fprog pr = {.len = 2, .filter = f}; |
87 | |
88 | res = prctl(PR_SET_SECCOMP, SECCOMP_MODE_FILTER, &pr); |
89 | assert(res == -1); |
90 | |
91 | return 0; |
92 | } |
93 | |