1 ; RUN: opt < %s -msan -msan-check-access-address=0 -S | FileCheck %s
2 ; RUN: opt < %s -msan -msan-check-access-address=0 -msan-track-origins=1 -S | FileCheck %s
3 ; RUN: opt < %s -msan -msan-check-access-address=0 -msan-track-origins=2 -S | FileCheck %s
5 target datalayout = "e-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-a0:0:64-s0:64:64-f80:128:128-n8:16:32:64-S128"
6 target triple = "x86_64-unknown-linux-gnu"
8 ; atomicrmw xchg: store clean shadow, return clean shadow
10 define i32 @AtomicRmwXchg(i32* %p, i32 %x) sanitize_memory {
12 %0 = atomicrmw xchg i32* %p, i32 %x seq_cst
16 ; CHECK: @AtomicRmwXchg
18 ; CHECK: atomicrmw xchg {{.*}} seq_cst
19 ; CHECK: store i32 0, {{.*}} @__msan_retval_tls
23 ; atomicrmw max: exactly the same as above
25 define i32 @AtomicRmwMax(i32* %p, i32 %x) sanitize_memory {
27 %0 = atomicrmw max i32* %p, i32 %x seq_cst
31 ; CHECK: @AtomicRmwMax
33 ; CHECK: atomicrmw max {{.*}} seq_cst
34 ; CHECK: store i32 0, {{.*}} @__msan_retval_tls
38 ; cmpxchg: the same as above, but also check %a shadow
40 define i32 @Cmpxchg(i32* %p, i32 %a, i32 %b) sanitize_memory {
42 %pair = cmpxchg i32* %p, i32 %a, i32 %b seq_cst seq_cst
43 %0 = extractvalue { i32, i1 } %pair, 0
48 ; CHECK: store { i32, i1 } zeroinitializer,
51 ; CHECK: @__msan_warning
52 ; CHECK: cmpxchg {{.*}} seq_cst seq_cst
53 ; CHECK: store i32 0, {{.*}} @__msan_retval_tls
57 ; relaxed cmpxchg: bump up to "release monotonic"
59 define i32 @CmpxchgMonotonic(i32* %p, i32 %a, i32 %b) sanitize_memory {
61 %pair = cmpxchg i32* %p, i32 %a, i32 %b monotonic monotonic
62 %0 = extractvalue { i32, i1 } %pair, 0
66 ; CHECK: @CmpxchgMonotonic
67 ; CHECK: store { i32, i1 } zeroinitializer,
70 ; CHECK: @__msan_warning
71 ; CHECK: cmpxchg {{.*}} release monotonic
72 ; CHECK: store i32 0, {{.*}} @__msan_retval_tls
76 ; atomic load: preserve alignment, load shadow value after app value
78 define i32 @AtomicLoad(i32* %p) sanitize_memory {
80 %0 = load atomic i32, i32* %p seq_cst, align 16
85 ; CHECK: load atomic i32, i32* {{.*}} seq_cst, align 16
86 ; CHECK: [[SHADOW:%[01-9a-z_]+]] = load i32, i32* {{.*}}, align 16
87 ; CHECK: store i32 {{.*}}[[SHADOW]], {{.*}} @__msan_retval_tls
91 ; atomic load: preserve alignment, load shadow value after app value
93 define i32 @AtomicLoadAcquire(i32* %p) sanitize_memory {
95 %0 = load atomic i32, i32* %p acquire, align 16
99 ; CHECK: @AtomicLoadAcquire
100 ; CHECK: load atomic i32, i32* {{.*}} acquire, align 16
101 ; CHECK: [[SHADOW:%[01-9a-z_]+]] = load i32, i32* {{.*}}, align 16
102 ; CHECK: store i32 {{.*}}[[SHADOW]], {{.*}} @__msan_retval_tls
106 ; atomic load monotonic: bump up to load acquire
108 define i32 @AtomicLoadMonotonic(i32* %p) sanitize_memory {
110 %0 = load atomic i32, i32* %p monotonic, align 16
114 ; CHECK: @AtomicLoadMonotonic
115 ; CHECK: load atomic i32, i32* {{.*}} acquire, align 16
116 ; CHECK: [[SHADOW:%[01-9a-z_]+]] = load i32, i32* {{.*}}, align 16
117 ; CHECK: store i32 {{.*}}[[SHADOW]], {{.*}} @__msan_retval_tls
121 ; atomic load unordered: bump up to load acquire
123 define i32 @AtomicLoadUnordered(i32* %p) sanitize_memory {
125 %0 = load atomic i32, i32* %p unordered, align 16
129 ; CHECK: @AtomicLoadUnordered
130 ; CHECK: load atomic i32, i32* {{.*}} acquire, align 16
131 ; CHECK: [[SHADOW:%[01-9a-z_]+]] = load i32, i32* {{.*}}, align 16
132 ; CHECK: store i32 {{.*}}[[SHADOW]], {{.*}} @__msan_retval_tls
136 ; atomic store: preserve alignment, store clean shadow value before app value
138 define void @AtomicStore(i32* %p, i32 %x) sanitize_memory {
140 store atomic i32 %x, i32* %p seq_cst, align 16
144 ; CHECK: @AtomicStore
145 ; CHECK-NOT: @__msan_param_tls
146 ; CHECK: store i32 0, i32* {{.*}}, align 16
147 ; CHECK: store atomic i32 %x, i32* %p seq_cst, align 16
151 ; atomic store: preserve alignment, store clean shadow value before app value
153 define void @AtomicStoreRelease(i32* %p, i32 %x) sanitize_memory {
155 store atomic i32 %x, i32* %p release, align 16
159 ; CHECK: @AtomicStoreRelease
160 ; CHECK-NOT: @__msan_param_tls
161 ; CHECK: store i32 0, i32* {{.*}}, align 16
162 ; CHECK: store atomic i32 %x, i32* %p release, align 16
166 ; atomic store monotonic: bumped up to store release
168 define void @AtomicStoreMonotonic(i32* %p, i32 %x) sanitize_memory {
170 store atomic i32 %x, i32* %p monotonic, align 16
174 ; CHECK: @AtomicStoreMonotonic
175 ; CHECK-NOT: @__msan_param_tls
176 ; CHECK: store i32 0, i32* {{.*}}, align 16
177 ; CHECK: store atomic i32 %x, i32* %p release, align 16
181 ; atomic store unordered: bumped up to store release
183 define void @AtomicStoreUnordered(i32* %p, i32 %x) sanitize_memory {
185 store atomic i32 %x, i32* %p unordered, align 16
189 ; CHECK: @AtomicStoreUnordered
190 ; CHECK-NOT: @__msan_param_tls
191 ; CHECK: store i32 0, i32* {{.*}}, align 16
192 ; CHECK: store atomic i32 %x, i32* %p release, align 16