1 | // RUN: %clang_hwasan -mllvm -hwasan-globals=0 -g %s -o %t |
2 | // RUN: %env_hwasan_opts=decorate_proc_maps=1 %run %t 2>&1 | FileCheck %s --check-prefix=A |
3 | // RUN: %env_hwasan_opts=decorate_proc_maps=1 %run %t 2>&1 | FileCheck %s --check-prefix=B |
4 | |
5 | // A: rw-p {{.*}}hwasan threads] |
6 | // A-NEXT: ---p {{.*}}shadow gap] |
7 | // A-NEXT: rw-p {{.*}}low shadow] |
8 | // A-NEXT: ---p {{.*}}shadow gap] |
9 | // A-NEXT: rw-p {{.*}}high shadow] |
10 | |
11 | // B-DAG: rw-p {{.*}}SizeClassAllocator: region info] |
12 | // B-DAG: rw-p {{.*}}LargeMmapAllocator] |
13 | // B-DAG: rw-p {{.*}}StackStore] |
14 | |
15 | #include <errno.h> |
16 | #include <fcntl.h> |
17 | #include <pthread.h> |
18 | #include <stdio.h> |
19 | #include <stdlib.h> |
20 | #include <sys/stat.h> |
21 | #include <sys/types.h> |
22 | #include <unistd.h> |
23 | |
24 | void CopyFdToFd(int in_fd, int out_fd) { |
25 | const size_t kBufSize = 0x10000; |
26 | static char buf[kBufSize]; |
27 | while (1) { |
28 | ssize_t got = read(fd: in_fd, buf: buf, nbytes: kBufSize); |
29 | if (got > 0) { |
30 | write(fd: out_fd, buf: buf, n: got); |
31 | } else if (got == 0) { |
32 | break; |
33 | } else if (errno != EAGAIN || errno != EWOULDBLOCK || errno != EINTR) { |
34 | fprintf(stderr, format: "error reading file, errno %d\n" , errno); |
35 | abort(); |
36 | } |
37 | } |
38 | } |
39 | |
40 | void *ThreadFn(void *arg) { |
41 | (void)arg; |
42 | int fd = open(file: "/proc/self/maps" , O_RDONLY); |
43 | CopyFdToFd(in_fd: fd, out_fd: 2); |
44 | close(fd: fd); |
45 | return NULL; |
46 | } |
47 | |
48 | int main(void) { |
49 | pthread_t t; |
50 | void * volatile res = malloc(size: 100); |
51 | void * volatile res2 = malloc(size: 1000000); |
52 | pthread_create(newthread: &t, attr: 0, start_routine: ThreadFn, arg: 0); |
53 | pthread_join(th: t, thread_return: 0); |
54 | int ret_val = (int)(size_t)res; |
55 | free(ptr: res); |
56 | free(ptr: res2); |
57 | return ret_val; |
58 | } |
59 | |