1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 3
2; RUN: opt < %s -passes=asan -S | FileCheck %s
3; RUN: opt < %s -passes=asan -asan-recover -S | FileCheck %s --check-prefix=RECOV
4target datalayout = "e-p:64:64-p1:64:64-p2:32:32-p3:32:32-p4:64:64-p5:32:32-p6:32:32-p7:160:256:256:32-p8:128:128-i64:64-v16:16-v24:32-v32:32-v48:64-v96:128-v192:256-v256:256-v512:512-v1024:1024-v2048:2048-n32:64-S32-A5-G1-ni:7:8:9"
5target triple = "amdgcn-amd-amdhsa"
6
7define protected amdgpu_kernel void @generic_store(ptr addrspace(1) %p, i32 %i) sanitize_address {
8; CHECK-LABEL: define protected amdgpu_kernel void @generic_store(
9; CHECK-SAME: ptr addrspace(1) [[P:%.*]], i32 [[I:%.*]]) #[[ATTR0:[0-9]+]] {
10; CHECK-NEXT:  entry:
11; CHECK-NEXT:    [[Q:%.*]] = addrspacecast ptr addrspace(1) [[P]] to ptr
12; CHECK-NEXT:    [[TMP0:%.*]] = call i1 @llvm.amdgcn.is.shared(ptr [[Q]])
13; CHECK-NEXT:    [[TMP1:%.*]] = call i1 @llvm.amdgcn.is.private(ptr [[Q]])
14; CHECK-NEXT:    [[TMP2:%.*]] = or i1 [[TMP0]], [[TMP1]]
15; CHECK-NEXT:    [[TMP3:%.*]] = xor i1 [[TMP2]], true
16; CHECK-NEXT:    br i1 [[TMP3]], label [[TMP4:%.*]], label [[TMP21:%.*]]
17; CHECK:       4:
18; CHECK-NEXT:    [[TMP5:%.*]] = ptrtoint ptr [[Q]] to i64
19; CHECK-NEXT:    [[TMP6:%.*]] = lshr i64 [[TMP5]], 3
20; CHECK-NEXT:    [[TMP7:%.*]] = add i64 [[TMP6]], 2147450880
21; CHECK-NEXT:    [[TMP8:%.*]] = inttoptr i64 [[TMP7]] to ptr
22; CHECK-NEXT:    [[TMP9:%.*]] = load i8, ptr [[TMP8]], align 1
23; CHECK-NEXT:    [[TMP10:%.*]] = icmp ne i8 [[TMP9]], 0
24; CHECK-NEXT:    [[TMP11:%.*]] = and i64 [[TMP5]], 7
25; CHECK-NEXT:    [[TMP12:%.*]] = add i64 [[TMP11]], 3
26; CHECK-NEXT:    [[TMP13:%.*]] = trunc i64 [[TMP12]] to i8
27; CHECK-NEXT:    [[TMP14:%.*]] = icmp sge i8 [[TMP13]], [[TMP9]]
28; CHECK-NEXT:    [[TMP15:%.*]] = and i1 [[TMP10]], [[TMP14]]
29; CHECK-NEXT:    [[TMP16:%.*]] = call i64 @llvm.amdgcn.ballot.i64(i1 [[TMP15]])
30; CHECK-NEXT:    [[TMP17:%.*]] = icmp ne i64 [[TMP16]], 0
31; CHECK-NEXT:    br i1 [[TMP17]], label [[ASAN_REPORT:%.*]], label [[TMP20:%.*]], !prof [[PROF0:![0-9]+]]
32; CHECK:       asan.report:
33; CHECK-NEXT:    br i1 [[TMP15]], label [[TMP18:%.*]], label [[TMP19:%.*]]
34; CHECK:       18:
35; CHECK-NEXT:    call void @__asan_report_store4(i64 [[TMP5]]) #[[ATTR5:[0-9]+]]
36; CHECK-NEXT:    call void @llvm.amdgcn.unreachable()
37; CHECK-NEXT:    br label [[TMP19]]
38; CHECK:       19:
39; CHECK-NEXT:    br label [[TMP20]]
40; CHECK:       20:
41; CHECK-NEXT:    br label [[TMP21]]
42; CHECK:       21:
43; CHECK-NEXT:    store i32 0, ptr [[Q]], align 4
44; CHECK-NEXT:    ret void
45;
46; RECOV-LABEL: define protected amdgpu_kernel void @generic_store(
47; RECOV-SAME: ptr addrspace(1) [[P:%.*]], i32 [[I:%.*]]) #[[ATTR0:[0-9]+]] {
48; RECOV-NEXT:  entry:
49; RECOV-NEXT:    [[Q:%.*]] = addrspacecast ptr addrspace(1) [[P]] to ptr
50; RECOV-NEXT:    [[TMP0:%.*]] = call i1 @llvm.amdgcn.is.shared(ptr [[Q]])
51; RECOV-NEXT:    [[TMP1:%.*]] = call i1 @llvm.amdgcn.is.private(ptr [[Q]])
52; RECOV-NEXT:    [[TMP2:%.*]] = or i1 [[TMP0]], [[TMP1]]
53; RECOV-NEXT:    [[TMP3:%.*]] = xor i1 [[TMP2]], true
54; RECOV-NEXT:    br i1 [[TMP3]], label [[TMP4:%.*]], label [[TMP17:%.*]]
55; RECOV:       4:
56; RECOV-NEXT:    [[TMP5:%.*]] = ptrtoint ptr [[Q]] to i64
57; RECOV-NEXT:    [[TMP6:%.*]] = lshr i64 [[TMP5]], 3
58; RECOV-NEXT:    [[TMP7:%.*]] = add i64 [[TMP6]], 2147450880
59; RECOV-NEXT:    [[TMP8:%.*]] = inttoptr i64 [[TMP7]] to ptr
60; RECOV-NEXT:    [[TMP9:%.*]] = load i8, ptr [[TMP8]], align 1
61; RECOV-NEXT:    [[TMP10:%.*]] = icmp ne i8 [[TMP9]], 0
62; RECOV-NEXT:    [[TMP11:%.*]] = and i64 [[TMP5]], 7
63; RECOV-NEXT:    [[TMP12:%.*]] = add i64 [[TMP11]], 3
64; RECOV-NEXT:    [[TMP13:%.*]] = trunc i64 [[TMP12]] to i8
65; RECOV-NEXT:    [[TMP14:%.*]] = icmp sge i8 [[TMP13]], [[TMP9]]
66; RECOV-NEXT:    [[TMP15:%.*]] = and i1 [[TMP10]], [[TMP14]]
67; RECOV-NEXT:    br i1 [[TMP15]], label [[ASAN_REPORT:%.*]], label [[TMP16:%.*]], !prof [[PROF0:![0-9]+]]
68; RECOV:       asan.report:
69; RECOV-NEXT:    call void @__asan_report_store4_noabort(i64 [[TMP5]]) #[[ATTR3:[0-9]+]]
70; RECOV-NEXT:    br label [[TMP16]]
71; RECOV:       16:
72; RECOV-NEXT:    br label [[TMP17]]
73; RECOV:       17:
74; RECOV-NEXT:    store i32 0, ptr [[Q]], align 4
75; RECOV-NEXT:    ret void
76;
77entry:
78
79  %q = addrspacecast ptr addrspace(1) %p to ptr
80  store i32 0, ptr %q, align 4
81  ret void
82}
83
84define protected amdgpu_kernel void @generic_load(ptr addrspace(1) %p, i32 %i) sanitize_address {
85; CHECK-LABEL: define protected amdgpu_kernel void @generic_load(
86; CHECK-SAME: ptr addrspace(1) [[P:%.*]], i32 [[I:%.*]]) #[[ATTR0]] {
87; CHECK-NEXT:  entry:
88; CHECK-NEXT:    [[Q:%.*]] = addrspacecast ptr addrspace(1) [[P]] to ptr
89; CHECK-NEXT:    [[TMP0:%.*]] = call i1 @llvm.amdgcn.is.shared(ptr [[Q]])
90; CHECK-NEXT:    [[TMP1:%.*]] = call i1 @llvm.amdgcn.is.private(ptr [[Q]])
91; CHECK-NEXT:    [[TMP2:%.*]] = or i1 [[TMP0]], [[TMP1]]
92; CHECK-NEXT:    [[TMP3:%.*]] = xor i1 [[TMP2]], true
93; CHECK-NEXT:    br i1 [[TMP3]], label [[TMP4:%.*]], label [[TMP21:%.*]]
94; CHECK:       4:
95; CHECK-NEXT:    [[TMP5:%.*]] = ptrtoint ptr [[Q]] to i64
96; CHECK-NEXT:    [[TMP6:%.*]] = lshr i64 [[TMP5]], 3
97; CHECK-NEXT:    [[TMP7:%.*]] = add i64 [[TMP6]], 2147450880
98; CHECK-NEXT:    [[TMP8:%.*]] = inttoptr i64 [[TMP7]] to ptr
99; CHECK-NEXT:    [[TMP9:%.*]] = load i8, ptr [[TMP8]], align 1
100; CHECK-NEXT:    [[TMP10:%.*]] = icmp ne i8 [[TMP9]], 0
101; CHECK-NEXT:    [[TMP11:%.*]] = and i64 [[TMP5]], 7
102; CHECK-NEXT:    [[TMP12:%.*]] = add i64 [[TMP11]], 3
103; CHECK-NEXT:    [[TMP13:%.*]] = trunc i64 [[TMP12]] to i8
104; CHECK-NEXT:    [[TMP14:%.*]] = icmp sge i8 [[TMP13]], [[TMP9]]
105; CHECK-NEXT:    [[TMP15:%.*]] = and i1 [[TMP10]], [[TMP14]]
106; CHECK-NEXT:    [[TMP16:%.*]] = call i64 @llvm.amdgcn.ballot.i64(i1 [[TMP15]])
107; CHECK-NEXT:    [[TMP17:%.*]] = icmp ne i64 [[TMP16]], 0
108; CHECK-NEXT:    br i1 [[TMP17]], label [[ASAN_REPORT:%.*]], label [[TMP20:%.*]], !prof [[PROF0]]
109; CHECK:       asan.report:
110; CHECK-NEXT:    br i1 [[TMP15]], label [[TMP18:%.*]], label [[TMP19:%.*]]
111; CHECK:       18:
112; CHECK-NEXT:    call void @__asan_report_load4(i64 [[TMP5]]) #[[ATTR5]]
113; CHECK-NEXT:    call void @llvm.amdgcn.unreachable()
114; CHECK-NEXT:    br label [[TMP19]]
115; CHECK:       19:
116; CHECK-NEXT:    br label [[TMP20]]
117; CHECK:       20:
118; CHECK-NEXT:    br label [[TMP21]]
119; CHECK:       21:
120; CHECK-NEXT:    [[R:%.*]] = load i32, ptr [[Q]], align 4
121; CHECK-NEXT:    ret void
122;
123; RECOV-LABEL: define protected amdgpu_kernel void @generic_load(
124; RECOV-SAME: ptr addrspace(1) [[P:%.*]], i32 [[I:%.*]]) #[[ATTR0]] {
125; RECOV-NEXT:  entry:
126; RECOV-NEXT:    [[Q:%.*]] = addrspacecast ptr addrspace(1) [[P]] to ptr
127; RECOV-NEXT:    [[TMP0:%.*]] = call i1 @llvm.amdgcn.is.shared(ptr [[Q]])
128; RECOV-NEXT:    [[TMP1:%.*]] = call i1 @llvm.amdgcn.is.private(ptr [[Q]])
129; RECOV-NEXT:    [[TMP2:%.*]] = or i1 [[TMP0]], [[TMP1]]
130; RECOV-NEXT:    [[TMP3:%.*]] = xor i1 [[TMP2]], true
131; RECOV-NEXT:    br i1 [[TMP3]], label [[TMP4:%.*]], label [[TMP17:%.*]]
132; RECOV:       4:
133; RECOV-NEXT:    [[TMP5:%.*]] = ptrtoint ptr [[Q]] to i64
134; RECOV-NEXT:    [[TMP6:%.*]] = lshr i64 [[TMP5]], 3
135; RECOV-NEXT:    [[TMP7:%.*]] = add i64 [[TMP6]], 2147450880
136; RECOV-NEXT:    [[TMP8:%.*]] = inttoptr i64 [[TMP7]] to ptr
137; RECOV-NEXT:    [[TMP9:%.*]] = load i8, ptr [[TMP8]], align 1
138; RECOV-NEXT:    [[TMP10:%.*]] = icmp ne i8 [[TMP9]], 0
139; RECOV-NEXT:    [[TMP11:%.*]] = and i64 [[TMP5]], 7
140; RECOV-NEXT:    [[TMP12:%.*]] = add i64 [[TMP11]], 3
141; RECOV-NEXT:    [[TMP13:%.*]] = trunc i64 [[TMP12]] to i8
142; RECOV-NEXT:    [[TMP14:%.*]] = icmp sge i8 [[TMP13]], [[TMP9]]
143; RECOV-NEXT:    [[TMP15:%.*]] = and i1 [[TMP10]], [[TMP14]]
144; RECOV-NEXT:    br i1 [[TMP15]], label [[ASAN_REPORT:%.*]], label [[TMP16:%.*]], !prof [[PROF0]]
145; RECOV:       asan.report:
146; RECOV-NEXT:    call void @__asan_report_load4_noabort(i64 [[TMP5]]) #[[ATTR3]]
147; RECOV-NEXT:    br label [[TMP16]]
148; RECOV:       16:
149; RECOV-NEXT:    br label [[TMP17]]
150; RECOV:       17:
151; RECOV-NEXT:    [[R:%.*]] = load i32, ptr [[Q]], align 4
152; RECOV-NEXT:    ret void
153;
154entry:
155
156  %q = addrspacecast ptr addrspace(1) %p to ptr
157  %r = load i32, ptr %q, align 4
158  ret void
159}
160
161define protected amdgpu_kernel void @generic_store_8(ptr addrspace(1) %p) sanitize_address {
162; CHECK-LABEL: define protected amdgpu_kernel void @generic_store_8(
163; CHECK-SAME: ptr addrspace(1) [[P:%.*]]) #[[ATTR0]] {
164; CHECK-NEXT:  entry:
165; CHECK-NEXT:    [[Q:%.*]] = addrspacecast ptr addrspace(1) [[P]] to ptr
166; CHECK-NEXT:    [[TMP0:%.*]] = call i1 @llvm.amdgcn.is.shared(ptr [[Q]])
167; CHECK-NEXT:    [[TMP1:%.*]] = call i1 @llvm.amdgcn.is.private(ptr [[Q]])
168; CHECK-NEXT:    [[TMP2:%.*]] = or i1 [[TMP0]], [[TMP1]]
169; CHECK-NEXT:    [[TMP3:%.*]] = xor i1 [[TMP2]], true
170; CHECK-NEXT:    br i1 [[TMP3]], label [[TMP4:%.*]], label [[TMP16:%.*]]
171; CHECK:       4:
172; CHECK-NEXT:    [[TMP5:%.*]] = ptrtoint ptr [[Q]] to i64
173; CHECK-NEXT:    [[TMP6:%.*]] = lshr i64 [[TMP5]], 3
174; CHECK-NEXT:    [[TMP7:%.*]] = add i64 [[TMP6]], 2147450880
175; CHECK-NEXT:    [[TMP8:%.*]] = inttoptr i64 [[TMP7]] to ptr
176; CHECK-NEXT:    [[TMP9:%.*]] = load i8, ptr [[TMP8]], align 1
177; CHECK-NEXT:    [[TMP10:%.*]] = icmp ne i8 [[TMP9]], 0
178; CHECK-NEXT:    [[TMP11:%.*]] = call i64 @llvm.amdgcn.ballot.i64(i1 [[TMP10]])
179; CHECK-NEXT:    [[TMP12:%.*]] = icmp ne i64 [[TMP11]], 0
180; CHECK-NEXT:    br i1 [[TMP12]], label [[ASAN_REPORT:%.*]], label [[TMP15:%.*]], !prof [[PROF0]]
181; CHECK:       asan.report:
182; CHECK-NEXT:    br i1 [[TMP10]], label [[TMP13:%.*]], label [[TMP14:%.*]]
183; CHECK:       13:
184; CHECK-NEXT:    call void @__asan_report_store8(i64 [[TMP5]]) #[[ATTR5]]
185; CHECK-NEXT:    call void @llvm.amdgcn.unreachable()
186; CHECK-NEXT:    br label [[TMP14]]
187; CHECK:       14:
188; CHECK-NEXT:    br label [[TMP15]]
189; CHECK:       15:
190; CHECK-NEXT:    br label [[TMP16]]
191; CHECK:       16:
192; CHECK-NEXT:    store i64 0, ptr [[Q]], align 8
193; CHECK-NEXT:    ret void
194;
195; RECOV-LABEL: define protected amdgpu_kernel void @generic_store_8(
196; RECOV-SAME: ptr addrspace(1) [[P:%.*]]) #[[ATTR0]] {
197; RECOV-NEXT:  entry:
198; RECOV-NEXT:    [[Q:%.*]] = addrspacecast ptr addrspace(1) [[P]] to ptr
199; RECOV-NEXT:    [[TMP0:%.*]] = call i1 @llvm.amdgcn.is.shared(ptr [[Q]])
200; RECOV-NEXT:    [[TMP1:%.*]] = call i1 @llvm.amdgcn.is.private(ptr [[Q]])
201; RECOV-NEXT:    [[TMP2:%.*]] = or i1 [[TMP0]], [[TMP1]]
202; RECOV-NEXT:    [[TMP3:%.*]] = xor i1 [[TMP2]], true
203; RECOV-NEXT:    br i1 [[TMP3]], label [[TMP4:%.*]], label [[TMP12:%.*]]
204; RECOV:       4:
205; RECOV-NEXT:    [[TMP5:%.*]] = ptrtoint ptr [[Q]] to i64
206; RECOV-NEXT:    [[TMP6:%.*]] = lshr i64 [[TMP5]], 3
207; RECOV-NEXT:    [[TMP7:%.*]] = add i64 [[TMP6]], 2147450880
208; RECOV-NEXT:    [[TMP8:%.*]] = inttoptr i64 [[TMP7]] to ptr
209; RECOV-NEXT:    [[TMP9:%.*]] = load i8, ptr [[TMP8]], align 1
210; RECOV-NEXT:    [[TMP10:%.*]] = icmp ne i8 [[TMP9]], 0
211; RECOV-NEXT:    br i1 [[TMP10]], label [[ASAN_REPORT:%.*]], label [[TMP11:%.*]], !prof [[PROF0]]
212; RECOV:       asan.report:
213; RECOV-NEXT:    call void @__asan_report_store8_noabort(i64 [[TMP5]]) #[[ATTR3]]
214; RECOV-NEXT:    br label [[TMP11]]
215; RECOV:       11:
216; RECOV-NEXT:    br label [[TMP12]]
217; RECOV:       12:
218; RECOV-NEXT:    store i64 0, ptr [[Q]], align 8
219; RECOV-NEXT:    ret void
220;
221entry:
222  %q = addrspacecast ptr addrspace(1) %p to ptr
223  store i64 0, ptr %q, align 8
224  ret void
225}
226
227define protected amdgpu_kernel void @generic_load_8(ptr addrspace(1) %p) sanitize_address {
228; CHECK-LABEL: define protected amdgpu_kernel void @generic_load_8(
229; CHECK-SAME: ptr addrspace(1) [[P:%.*]]) #[[ATTR0]] {
230; CHECK-NEXT:  entry:
231; CHECK-NEXT:    [[Q:%.*]] = addrspacecast ptr addrspace(1) [[P]] to ptr
232; CHECK-NEXT:    [[TMP0:%.*]] = call i1 @llvm.amdgcn.is.shared(ptr [[Q]])
233; CHECK-NEXT:    [[TMP1:%.*]] = call i1 @llvm.amdgcn.is.private(ptr [[Q]])
234; CHECK-NEXT:    [[TMP2:%.*]] = or i1 [[TMP0]], [[TMP1]]
235; CHECK-NEXT:    [[TMP3:%.*]] = xor i1 [[TMP2]], true
236; CHECK-NEXT:    br i1 [[TMP3]], label [[TMP4:%.*]], label [[TMP16:%.*]]
237; CHECK:       4:
238; CHECK-NEXT:    [[TMP5:%.*]] = ptrtoint ptr [[Q]] to i64
239; CHECK-NEXT:    [[TMP6:%.*]] = lshr i64 [[TMP5]], 3
240; CHECK-NEXT:    [[TMP7:%.*]] = add i64 [[TMP6]], 2147450880
241; CHECK-NEXT:    [[TMP8:%.*]] = inttoptr i64 [[TMP7]] to ptr
242; CHECK-NEXT:    [[TMP9:%.*]] = load i8, ptr [[TMP8]], align 1
243; CHECK-NEXT:    [[TMP10:%.*]] = icmp ne i8 [[TMP9]], 0
244; CHECK-NEXT:    [[TMP11:%.*]] = call i64 @llvm.amdgcn.ballot.i64(i1 [[TMP10]])
245; CHECK-NEXT:    [[TMP12:%.*]] = icmp ne i64 [[TMP11]], 0
246; CHECK-NEXT:    br i1 [[TMP12]], label [[ASAN_REPORT:%.*]], label [[TMP15:%.*]], !prof [[PROF0]]
247; CHECK:       asan.report:
248; CHECK-NEXT:    br i1 [[TMP10]], label [[TMP13:%.*]], label [[TMP14:%.*]]
249; CHECK:       13:
250; CHECK-NEXT:    call void @__asan_report_load8(i64 [[TMP5]]) #[[ATTR5]]
251; CHECK-NEXT:    call void @llvm.amdgcn.unreachable()
252; CHECK-NEXT:    br label [[TMP14]]
253; CHECK:       14:
254; CHECK-NEXT:    br label [[TMP15]]
255; CHECK:       15:
256; CHECK-NEXT:    br label [[TMP16]]
257; CHECK:       16:
258; CHECK-NEXT:    [[R:%.*]] = load i64, ptr [[Q]], align 8
259; CHECK-NEXT:    ret void
260;
261; RECOV-LABEL: define protected amdgpu_kernel void @generic_load_8(
262; RECOV-SAME: ptr addrspace(1) [[P:%.*]]) #[[ATTR0]] {
263; RECOV-NEXT:  entry:
264; RECOV-NEXT:    [[Q:%.*]] = addrspacecast ptr addrspace(1) [[P]] to ptr
265; RECOV-NEXT:    [[TMP0:%.*]] = call i1 @llvm.amdgcn.is.shared(ptr [[Q]])
266; RECOV-NEXT:    [[TMP1:%.*]] = call i1 @llvm.amdgcn.is.private(ptr [[Q]])
267; RECOV-NEXT:    [[TMP2:%.*]] = or i1 [[TMP0]], [[TMP1]]
268; RECOV-NEXT:    [[TMP3:%.*]] = xor i1 [[TMP2]], true
269; RECOV-NEXT:    br i1 [[TMP3]], label [[TMP4:%.*]], label [[TMP12:%.*]]
270; RECOV:       4:
271; RECOV-NEXT:    [[TMP5:%.*]] = ptrtoint ptr [[Q]] to i64
272; RECOV-NEXT:    [[TMP6:%.*]] = lshr i64 [[TMP5]], 3
273; RECOV-NEXT:    [[TMP7:%.*]] = add i64 [[TMP6]], 2147450880
274; RECOV-NEXT:    [[TMP8:%.*]] = inttoptr i64 [[TMP7]] to ptr
275; RECOV-NEXT:    [[TMP9:%.*]] = load i8, ptr [[TMP8]], align 1
276; RECOV-NEXT:    [[TMP10:%.*]] = icmp ne i8 [[TMP9]], 0
277; RECOV-NEXT:    br i1 [[TMP10]], label [[ASAN_REPORT:%.*]], label [[TMP11:%.*]], !prof [[PROF0]]
278; RECOV:       asan.report:
279; RECOV-NEXT:    call void @__asan_report_load8_noabort(i64 [[TMP5]]) #[[ATTR3]]
280; RECOV-NEXT:    br label [[TMP11]]
281; RECOV:       11:
282; RECOV-NEXT:    br label [[TMP12]]
283; RECOV:       12:
284; RECOV-NEXT:    [[R:%.*]] = load i64, ptr [[Q]], align 8
285; RECOV-NEXT:    ret void
286;
287entry:
288  %q = addrspacecast ptr addrspace(1) %p to ptr
289  %r = load i64, ptr %q, align 8
290  ret void
291}
292