[AMDGPU] Add llvm.amdgcn.global.load.lds intrinsic
[llvm-project.git] / llvm / test / CodeGen / ARM / speculation-hardening-sls.ll
blob835583085c318f3c11a05235b6559d31912573a9
1 ; RUN: llc -mattr=harden-sls-retbr -mattr=harden-sls-blr -verify-machineinstrs -mtriple=armv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,ARM,HARDEN,HARDEN-COMDAT,ISBDSB -dump-input-context=100
2 ; RUN: llc -mattr=harden-sls-retbr -mattr=harden-sls-blr -verify-machineinstrs -mtriple=thumbv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,THUMB,HARDENTHUMB,HARDEN,HARDEN-COMDAT,ISBDSB -dump-input-context=100
3 ; RUN: llc -mattr=harden-sls-retbr -mattr=harden-sls-blr -mattr=+sb -verify-machineinstrs -mtriple=armv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,ARM,HARDEN,HARDEN-COMDAT,SB -dump-input-context=100
4 ; RUN: llc -mattr=harden-sls-retbr -mattr=harden-sls-blr -mattr=+sb -verify-machineinstrs -mtriple=thumbv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,THUMB,HARDENTHUMB,HARDEN,HARDEN-COMDAT,SB -dump-input-context=100
5 ; RUN: llc -mattr=harden-sls-retbr -mattr=harden-sls-blr -mattr=harden-sls-nocomdat -verify-machineinstrs -mtriple=armv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,ARM,HARDEN,HARDEN-COMDAT-OFF,ISBDSB -dump-input-context=100
6 ; RUN: llc -mattr=harden-sls-retbr -mattr=harden-sls-blr -mattr=harden-sls-nocomdat -verify-machineinstrs -mtriple=thumbv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,THUMB,HARDENTHUMB,HARDEN,HARDEN-COMDAT-OFF,ISBDSB -dump-input-context=100
7 ; RUN: llc -mattr=harden-sls-retbr -mattr=harden-sls-blr -mattr=harden-sls-nocomdat -mattr=+sb -verify-machineinstrs -mtriple=armv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,ARM,HARDEN,HARDEN-COMDAT-OFF,SB -dump-input-context=100
8 ; RUN: llc -mattr=harden-sls-retbr -mattr=harden-sls-blr -mattr=harden-sls-nocomdat -mattr=+sb -verify-machineinstrs -mtriple=thumbv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,THUMB,HARDENTHUMB,HARDEN,HARDEN-COMDAT-OFF,SB -dump-input-context=100
9 ; RUN: llc -verify-machineinstrs -mtriple=armv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,ARM,NOHARDENARM -dump-input-context=100
10 ; RUN: llc -verify-machineinstrs -mtriple=thumbv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,THUMB,NOHARDENTHUMB
11 ; RUN: llc -global-isel -global-isel-abort=0 -mattr=harden-sls-retbr -mattr=harden-sls-blr -verify-machineinstrs -mtriple=armv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,ARM,HARDEN,HARDEN-COMDAT,ISBDSB
12 ; RUN: llc -global-isel -global-isel-abort=0 -mattr=harden-sls-retbr -mattr=harden-sls-blr -verify-machineinstrs -mtriple=thumbv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,THUMB,HARDENTHUMB,HARDEN,HARDEN-COMDAT,ISBDSB
13 ; RUN: llc -global-isel -global-isel-abort=0 -mattr=harden-sls-retbr -mattr=harden-sls-nocomdat -mattr=harden-sls-blr -verify-machineinstrs -mtriple=armv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,ARM,HARDEN,HARDEN-COMDAT-OFF,ISBDSB
14 ; RUN: llc -global-isel -global-isel-abort=0 -mattr=harden-sls-retbr -mattr=harden-sls-nocomdat -mattr=harden-sls-blr -verify-machineinstrs -mtriple=thumbv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,THUMB,HARDENTHUMB,HARDEN,HARDEN-COMDAT-OFF,ISBDSB
15 ; RUN: llc -global-isel -global-isel-abort=0 -mattr=harden-sls-retbr -mattr=harden-sls-blr -mattr=+sb -verify-machineinstrs -mtriple=armv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,ARM,HARDEN,SB
16 ; RUN: llc -global-isel -global-isel-abort=0 -mattr=harden-sls-retbr -mattr=harden-sls-blr -mattr=+sb -verify-machineinstrs -mtriple=thumbv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,THUMB,HARDENTHUMB,HARDEN,SB
17 ; RUN: llc -fast-isel -mattr=harden-sls-retbr -mattr=harden-sls-blr -verify-machineinstrs -mtriple=armv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,ARM,HARDEN,HARDEN-COMDAT,ISBDSB
18 ; RUN: llc -fast-isel -mattr=harden-sls-retbr -mattr=harden-sls-blr -verify-machineinstrs -mtriple=thumbv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,THUMB,HARDENTHUMB,HARDEN,HARDEN-COMDAT,ISBDSB
19 ; RUN: llc -fast-isel -mattr=harden-sls-retbr -mattr=harden-sls-blr -mattr=harden-sls-nocomdat -verify-machineinstrs -mtriple=armv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,ARM,HARDEN,HARDEN-COMDAT-OFF,ISBDSB
20 ; RUN: llc -fast-isel -mattr=harden-sls-retbr -mattr=harden-sls-blr -mattr=harden-sls-nocomdat -verify-machineinstrs -mtriple=thumbv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,THUMB,HARDENTHUMB,HARDEN,HARDEN-COMDAT-OFF,ISBDSB
21 ; RUN: llc -fast-isel -mattr=harden-sls-retbr -mattr=harden-sls-blr -mattr=+sb -verify-machineinstrs -mtriple=armv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,ARM,HARDEN,SB
22 ; RUN: llc -fast-isel -mattr=harden-sls-retbr -mattr=harden-sls-blr -mattr=+sb -verify-machineinstrs -mtriple=thumbv8-linux-gnueabi < %s | FileCheck %s --check-prefixes=CHECK,THUMB,HARDENTHUMB,HARDEN,SB
24 ; Function Attrs: norecurse nounwind readnone
25 define dso_local i32 @double_return(i32 %a, i32 %b) local_unnamed_addr {
26 entry:
27   %cmp = icmp sgt i32 %a, 0
28   br i1 %cmp, label %if.then, label %if.else
30 if.then:                                          ; preds = %entry
31   ; Make a very easy, very likely to predicate return (BX LR), to test that
32   ; it will not get predicated when sls-hardening is enabled.
33   %mul = mul i32 %b, %a
34   ret i32 %mul
35 ; CHECK-LABEL: double_return:
36 ; HARDEN:          {{bx lr$}}
37 ; NOHARDENARM:     {{bxgt lr$}}
38 ; NOHARDENTHUMB:   {{bxgt lr$}}
39 ; ISBDSB-NEXT: dsb sy
40 ; ISBDSB-NEXT: isb
41 ; SB-NEXT:     {{ sb$}}
43 if.else:                                          ; preds = %entry
44   %div3 = sdiv i32 %a, %b
45   %div2 = sdiv i32 %a, %div3
46   %div1 = sdiv i32 %a, %div2
47   ret i32 %div1
49 ; CHECK:       {{bx lr$}}
50 ; ISBDSB-NEXT: dsb sy
51 ; ISBDSB-NEXT: isb
52 ; SB-NEXT:     {{ sb$}}
53 ; CHECK-NEXT: .Lfunc_end
56 @__const.indirect_branch.ptr = private unnamed_addr constant [2 x i8*] [i8* blockaddress(@indirect_branch, %return), i8* blockaddress(@indirect_branch, %l2)], align 8
58 ; Function Attrs: norecurse nounwind readnone
59 define dso_local i32 @indirect_branch(i32 %a, i32 %b, i32 %i) {
60 ; CHECK-LABEL: indirect_branch:
61 entry:
62   %idxprom = sext i32 %i to i64
63   %arrayidx = getelementptr inbounds [2 x i8*], [2 x i8*]* @__const.indirect_branch.ptr, i64 0, i64 %idxprom
64   %0 = load i8*, i8** %arrayidx, align 8
65   indirectbr i8* %0, [label %return, label %l2]
66 ; ARM:       bx r0
67 ; THUMB:     mov pc, r0
68 ; ISBDSB-NEXT: dsb sy
69 ; ISBDSB-NEXT: isb
70 ; SB-NEXT:     {{ sb$}}
72 l2:                                               ; preds = %entry
73   br label %return
74 ; CHECK:       {{bx lr$}}
75 ; ISBDSB-NEXT: dsb sy
76 ; ISBDSB-NEXT: isb
77 ; SB-NEXT:     {{ sb$}}
79 return:                                           ; preds = %entry, %l2
80   %retval.0 = phi i32 [ 1, %l2 ], [ 0, %entry ]
81   ret i32 %retval.0
82 ; CHECK:       {{bx lr$}}
83 ; ISBDSB-NEXT: dsb sy
84 ; ISBDSB-NEXT: isb
85 ; SB-NEXT:     {{ sb$}}
86 ; CHECK-NEXT: .Lfunc_end
89 define i32 @asmgoto() {
90 entry:
91 ; CHECK-LABEL: asmgoto:
92   callbr void asm sideeffect "B $0", "i"(i8* blockaddress(@asmgoto, %d))
93             to label %asm.fallthrough [label %d]
94      ; The asm goto above produces a direct branch:
95 ; CHECK:           @APP
96 ; CHECK-NEXT:      {{^[ \t]+b }}
97 ; CHECK-NEXT:      @NO_APP
98      ; For direct branches, no mitigation is needed.
99 ; ISDDSB-NOT: dsb sy
100 ; SB-NOT:     {{ sb$}}
102 asm.fallthrough:               ; preds = %entry
103   ret i32 0
104 ; CHECK:       {{bx lr$}}
105 ; ISBDSB-NEXT: dsb sy
106 ; ISBDSB-NEXT: isb
107 ; SB-NEXT:     {{ sb$}}
109 d:                             ; preds = %asm.fallthrough, %entry
110   ret i32 1
111 ; CHECK:       {{bx lr$}}
112 ; ISBDSB-NEXT: dsb sy
113 ; ISBDSB-NEXT: isb
114 ; SB-NEXT:     {{ sb$}}
115 ; CHECK-NEXT: .Lfunc_end
118 ; Check that indirect branches produced through switch jump tables are also
119 ; hardened:
120 define dso_local i32 @jumptable(i32 %a, i32 %b) {
121 ; CHECK-LABEL: jumptable:
122 entry:
123   switch i32 %b, label %sw.epilog [
124     i32 0, label %sw.bb
125     i32 1, label %sw.bb1
126     i32 3, label %sw.bb3
127     i32 4, label %sw.bb5
128   ]
129 ; ARM:             ldr pc, [{{r[0-9]}}, {{r[0-9]}}, lsl #2]
130 ; NOHARDENTHUMB:   tbb [pc, {{r[0-9]}}]
131 ; HARDENTHUMB:     mov pc, {{r[0-9]}}
132 ; ISBDSB-NEXT:     dsb sy
133 ; ISBDSB-NEXT:     isb
134 ; SB-NEXT:         {{ sb$}}
137 sw.bb:                                            ; preds = %entry
138   %add = shl nsw i32 %a, 1
139   br label %sw.bb1
141 sw.bb1:                                           ; preds = %entry, %sw.bb
142   %a.addr.0 = phi i32 [ %a, %entry ], [ %add, %sw.bb ]
143   %add2 = shl nsw i32 %a.addr.0, 1
144   br label %sw.bb3
146 sw.bb3:                                           ; preds = %entry, %sw.bb1
147   %a.addr.1 = phi i32 [ %a, %entry ], [ %add2, %sw.bb1 ]
148   %add4 = shl nsw i32 %a.addr.1, 1
149   br label %sw.bb5
151 sw.bb5:                                           ; preds = %entry, %sw.bb3
152   %a.addr.2 = phi i32 [ %a, %entry ], [ %add4, %sw.bb3 ]
153   %add6 = shl nsw i32 %a.addr.2, 1
154   br label %sw.epilog
156 sw.epilog:                                        ; preds = %sw.bb5, %entry
157   %a.addr.3 = phi i32 [ %a, %entry ], [ %add6, %sw.bb5 ]
158   ret i32 %a.addr.3
159 ; CHECK:       {{bx lr$}}
160 ; ISBDSB-NEXT: dsb sy
161 ; ISBDSB-NEXT: isb
162 ; SB-NEXT:     {{ sb$}}
165 define dso_local i32 @indirect_call(
166 i32 (...)* nocapture %f1, i32 (...)* nocapture %f2) {
167 entry:
168 ; CHECK-LABEL: indirect_call:
169   %callee.knr.cast = bitcast i32 (...)* %f1 to i32 ()*
170   %call = tail call i32 %callee.knr.cast()
171 ; HARDENARM: bl {{__llvm_slsblr_thunk_arm_r[0-9]+$}}
172 ; HARDENTHUMB: bl {{__llvm_slsblr_thunk_thumb_r[0-9]+$}}
173   %callee.knr.cast1 = bitcast i32 (...)* %f2 to i32 ()*
174   %call2 = tail call i32 %callee.knr.cast1()
175 ; HARDENARM: bl {{__llvm_slsblr_thunk_arm_r[0-9]+$}}
176 ; HARDENTHUMB: bl {{__llvm_slsblr_thunk_thumb_r[0-9]+$}}
177   %add = add nsw i32 %call2, %call
178   ret i32 %add
179 ; CHECK: .Lfunc_end
182 ; verify calling through a function pointer.
183 @a = dso_local local_unnamed_addr global i32 (...)* null, align 8
184 @b = dso_local local_unnamed_addr global i32 0, align 4
185 define dso_local void @indirect_call_global() local_unnamed_addr {
186 ; CHECK-LABEL: indirect_call_global:
187 entry:
188   %0 = load i32 ()*, i32 ()** bitcast (i32 (...)** @a to i32 ()**), align 8
189   %call = tail call i32 %0()  nounwind
190 ; HARDENARM: bl {{__llvm_slsblr_thunk_arm_r[0-9]+$}}
191 ; HARDENTHUMB: bl {{__llvm_slsblr_thunk_thumb_r[0-9]+$}}
192   store i32 %call, i32* @b, align 4
193   ret void
194 ; CHECK: .Lfunc_end
197 ; Verify that neither r12 nor lr are used as registers in indirect call
198 ; instructions when the sls-hardening-blr mitigation is enabled, as
199 ; (a) a linker is allowed to clobber r12 on calls, and
200 ; (b) the hardening transformation isn't correct if lr is the register holding
201 ;     the address of the function called.
202 define i32 @check_r12(i32 ()** %fp) {
203 entry:
204 ; CHECK-LABEL: check_r12:
205   %f = load i32 ()*, i32 ()** %fp, align 4
206   ; Force f to be moved into r12
207   %r12_f = tail call i32 ()* asm "add $0, $1, #0", "={r12},{r12}"(i32 ()* %f) nounwind
208   %call = call i32 %r12_f()
209 ; NOHARDENARM:     blx r12
210 ; NOHARDENTHUMB:   blx r12
211 ; HARDEN-NOT: bl {{__llvm_slsblr_thunk_(arm|thumb)_r12}}
212   ret i32 %call
213 ; CHECK: .Lfunc_end
216 define i32 @check_lr(i32 ()** %fp) {
217 entry:
218 ; CHECK-LABEL: check_lr:
219   %f = load i32 ()*, i32 ()** %fp, align 4
220   ; Force f to be moved into lr
221   %lr_f = tail call i32 ()* asm "add $0, $1, #0", "={lr},{lr}"(i32 ()* %f) nounwind
222   %call = call i32 %lr_f()
223 ; NOHARDENARM:     blx lr
224 ; NOHARDENTHUMB:   blx lr
225 ; HARDEN-NOT: bl {{__llvm_slsblr_thunk_(arm|thumb)_lr}}
226   ret i32 %call
227 ; CHECK: .Lfunc_end
230 ; Verify that even when sls-harden-blr is enabled, "blx r12" is still an
231 ; instruction that is accepted by the inline assembler
232 define void @verify_inline_asm_blx_r12(void ()* %g) {
233 entry:
234 ; CHECK-LABEL: verify_inline_asm_blx_r12:
235   %0 = bitcast void ()* %g to i8*
236   tail call void asm sideeffect "blx $0", "{r12}"(i8* %0) nounwind
237 ; CHECK: blx r12
238   ret void
239 ; CHECK:       {{bx lr$}}
240 ; ISBDSB-NEXT: dsb sy
241 ; ISBDSB-NEXT: isb
242 ; SB-NEXT:     {{ sb$}}
243 ; CHECK: .Lfunc_end
246 ; HARDEN-COMDAT:  .section {{.text.__llvm_slsblr_thunk_(arm|thumb)_r5}}
247 ; HARDEN-COMDAT:  .hidden {{__llvm_slsblr_thunk_(arm|thumb)_r5}}
248 ; HARDEN-COMDAT:  .weak {{__llvm_slsblr_thunk_(arm|thumb)_r5}}
249 ; HARDEN-COMDAT:  .type {{__llvm_slsblr_thunk_(arm|thumb)_r5}},%function
250 ; HARDEN-COMDAT-OFF-NOT:  .section {{.text.__llvm_slsblr_thunk_(arm|thumb)_r5}}
251 ; HARDEN-COMDAT-OFF-NOT:  .hidden {{__llvm_slsblr_thunk_(arm|thumb)_r5}}
252 ; HARDEN-COMDAT-OFF-NOT:  .weak {{__llvm_slsblr_thunk_(arm|thumb)_r5}}
253 ; HARDEN-COMDAT-OFF:      .type {{__llvm_slsblr_thunk_(arm|thumb)_r5}},%function
254 ; HARDEN-label: {{__llvm_slsblr_thunk_(arm|thumb)_r5}}:
255 ; HARDEN:    bx r5
256 ; ISBDSB-NEXT: dsb sy
257 ; ISBDSB-NEXT: isb
258 ; SB-NEXT:     dsb sy
259 ; SB-NEXT:     isb
260 ; HARDEN-NEXT: .Lfunc_end