Revert "[lldb][test] Remove compiler version check and use regex" (#124101)
[llvm-project.git] / compiler-rt / test / hwasan / TestCases / deep-recursion.c
blob764ec5692372b4a7325edfb026246d3fd000b099
1 // RUN: %clang_hwasan -O1 %s -o %t
2 // RUN: %env_hwasan_opts=stack_history_size=1 not %run %t 2>&1 | FileCheck %s --check-prefix=D1
3 // RUN: %env_hwasan_opts=stack_history_size=2 not %run %t 2>&1 | FileCheck %s --check-prefix=D2
4 // RUN: %env_hwasan_opts=stack_history_size=3 not %run %t 2>&1 | FileCheck %s --check-prefix=D3
5 // RUN: %env_hwasan_opts=stack_history_size=5 not %run %t 2>&1 | FileCheck %s --check-prefix=D5
6 // RUN: not %run %t 2>&1 | FileCheck %s --check-prefix=DEFAULT
8 // Run the same tests as above, but using the __hwasan_add_frame_record libcall.
9 // The output should be the exact same.
10 // RUN: %clang_hwasan -O1 %s -o %t -mllvm -hwasan-record-stack-history=libcall
11 // RUN: %env_hwasan_opts=stack_history_size=1 not %run %t 2>&1 | FileCheck %s --check-prefix=D1
12 // RUN: %env_hwasan_opts=stack_history_size=2 not %run %t 2>&1 | FileCheck %s --check-prefix=D2
13 // RUN: %env_hwasan_opts=stack_history_size=3 not %run %t 2>&1 | FileCheck %s --check-prefix=D3
14 // RUN: %env_hwasan_opts=stack_history_size=5 not %run %t 2>&1 | FileCheck %s --check-prefix=D5
15 // RUN: not %run %t 2>&1 | FileCheck %s --check-prefix=DEFAULT
17 // Stack histories are currently not recorded on x86.
18 // XFAIL: target=x86_64{{.*}}
20 #include <assert.h>
21 #include <sanitizer/hwasan_interface.h>
22 #include <stdlib.h>
24 // At least -O1 is needed for this function to not have a stack frame on
25 // AArch64.
26 void USE(void *x) { // pretend_to_do_something(void *x)
27 __asm__ __volatile__("" : : "r" (x) : "memory");
30 volatile int four = 4;
32 __attribute__((noinline)) void OOB() {
33 int x[4];
34 int y[4];
36 // Tags for stack-allocated variables can occasionally be zero, resulting in
37 // a false negative for this test. The tag allocation algorithm is not easy
38 // to fix, hence we work around it: if the tag is zero, we use the
39 // neighboring variable instead, which must have a different (hence non-zero)
40 // tag.
41 if (__hwasan_tag_pointer(x, 0) == x) {
42 assert(__hwasan_tag_pointer(y, 0) != y);
43 y[four] = 0;
44 } else {
45 x[four] = 0;
47 USE(&x[0]);
48 USE(&y[0]);
50 __attribute__((noinline)) void FUNC1() { int x; USE(&x); OOB(); }
51 __attribute__((noinline)) void FUNC2() { int x; USE(&x); FUNC1(); }
52 __attribute__((noinline)) void FUNC3() { int x; USE(&x); FUNC2(); }
53 __attribute__((noinline)) void FUNC4() { int x; USE(&x); FUNC3(); }
54 __attribute__((noinline)) void FUNC5() { int x; USE(&x); FUNC4(); }
55 __attribute__((noinline)) void FUNC6() { int x; USE(&x); FUNC5(); }
56 __attribute__((noinline)) void FUNC7() { int x; USE(&x); FUNC6(); }
57 __attribute__((noinline)) void FUNC8() { int x; USE(&x); FUNC7(); }
58 __attribute__((noinline)) void FUNC9() { int x; USE(&x); FUNC8(); }
59 __attribute__((noinline)) void FUNC10() { int x; USE(&x); FUNC9(); }
61 int main() { FUNC10(); }
63 // D1: Previously allocated frames
64 // D1: in OOB
65 // D1-NOT: in FUNC
66 // D1: Memory tags around the buggy address
68 // D2: Previously allocated frames
69 // D2: in OOB
70 // D2: in FUNC1
71 // D2-NOT: in FUNC
72 // D2: Memory tags around the buggy address
74 // D3: Previously allocated frames
75 // D3: in OOB
76 // D3: in FUNC1
77 // D3: in FUNC2
78 // D3-NOT: in FUNC
79 // D3: Memory tags around the buggy address
81 // D5: Previously allocated frames
82 // D5: in OOB
83 // D5: in FUNC1
84 // D5: in FUNC2
85 // D5: in FUNC3
86 // D5: in FUNC4
87 // D5-NOT: in FUNC
88 // D5: Memory tags around the buggy address
90 // DEFAULT: Previously allocated frames
91 // DEFAULT: in OOB
92 // DEFAULT: in FUNC1
93 // DEFAULT: in FUNC2
94 // DEFAULT: in FUNC3
95 // DEFAULT: in FUNC4
96 // DEFAULT: in FUNC5
97 // DEFAULT: in FUNC6
98 // DEFAULT: in FUNC7
99 // DEFAULT: in FUNC8
100 // DEFAULT: in FUNC9
101 // DEFAULT: in FUNC10
102 // DEFAULT-NOT: in FUNC
103 // DEFAULT: Memory tags around the buggy address