xref: /llvm-project/llvm/test/CodeGen/RISCV/shadowcallstack.ll (revision 392807ec3e7243fee98bec5d59ea8ea58ad022cd)
1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
2; RUN: llc -mtriple=riscv32 -verify-machineinstrs < %s \
3; RUN:   | FileCheck %s --check-prefix=RV32
4; RUN: llc -mtriple=riscv64 -verify-machineinstrs < %s \
5; RUN:   | FileCheck %s --check-prefix=RV64
6; RUN: llc -mtriple=riscv32 -mattr=+experimental-zicfiss < %s \
7; RUN:   -verify-machineinstrs | FileCheck %s --check-prefix=RV32-ZICFISS
8; RUN: llc -mtriple=riscv64 -mattr=+experimental-zicfiss < %s \
9; RUN:   -verify-machineinstrs | FileCheck %s --check-prefix=RV64-ZICFISS
10
11define void @f1() shadowcallstack {
12; RV32-LABEL: f1:
13; RV32:       # %bb.0:
14; RV32-NEXT:    ret
15;
16; RV64-LABEL: f1:
17; RV64:       # %bb.0:
18; RV64-NEXT:    ret
19;
20; RV32-ZICFISS-LABEL: f1:
21; RV32-ZICFISS:       # %bb.0:
22; RV32-ZICFISS-NEXT:    ret
23;
24; RV64-ZICFISS-LABEL: f1:
25; RV64-ZICFISS:       # %bb.0:
26; RV64-ZICFISS-NEXT:    ret
27  ret void
28}
29
30declare void @foo()
31
32define void @f2() shadowcallstack {
33; RV32-LABEL: f2:
34; RV32:       # %bb.0:
35; RV32-NEXT:    tail foo
36;
37; RV64-LABEL: f2:
38; RV64:       # %bb.0:
39; RV64-NEXT:    tail foo
40;
41; RV32-ZICFISS-LABEL: f2:
42; RV32-ZICFISS:       # %bb.0:
43; RV32-ZICFISS-NEXT:    tail foo
44;
45; RV64-ZICFISS-LABEL: f2:
46; RV64-ZICFISS:       # %bb.0:
47; RV64-ZICFISS-NEXT:    tail foo
48  tail call void @foo()
49  ret void
50}
51
52declare i32 @bar()
53
54define i32 @f3() shadowcallstack {
55; RV32-LABEL: f3:
56; RV32:       # %bb.0:
57; RV32-NEXT:    addi gp, gp, 4
58; RV32-NEXT:    sw ra, -4(gp)
59; RV32-NEXT:    .cfi_escape 0x16, 0x03, 0x02, 0x73, 0x7c #
60; RV32-NEXT:    addi sp, sp, -16
61; RV32-NEXT:    .cfi_def_cfa_offset 16
62; RV32-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
63; RV32-NEXT:    .cfi_offset ra, -4
64; RV32-NEXT:    call bar
65; RV32-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
66; RV32-NEXT:    .cfi_restore ra
67; RV32-NEXT:    addi sp, sp, 16
68; RV32-NEXT:    .cfi_def_cfa_offset 0
69; RV32-NEXT:    lw ra, -4(gp)
70; RV32-NEXT:    addi gp, gp, -4
71; RV32-NEXT:    .cfi_restore gp
72; RV32-NEXT:    ret
73;
74; RV64-LABEL: f3:
75; RV64:       # %bb.0:
76; RV64-NEXT:    addi gp, gp, 8
77; RV64-NEXT:    sd ra, -8(gp)
78; RV64-NEXT:    .cfi_escape 0x16, 0x03, 0x02, 0x73, 0x78 #
79; RV64-NEXT:    addi sp, sp, -16
80; RV64-NEXT:    .cfi_def_cfa_offset 16
81; RV64-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
82; RV64-NEXT:    .cfi_offset ra, -8
83; RV64-NEXT:    call bar
84; RV64-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
85; RV64-NEXT:    .cfi_restore ra
86; RV64-NEXT:    addi sp, sp, 16
87; RV64-NEXT:    .cfi_def_cfa_offset 0
88; RV64-NEXT:    ld ra, -8(gp)
89; RV64-NEXT:    addi gp, gp, -8
90; RV64-NEXT:    .cfi_restore gp
91; RV64-NEXT:    ret
92;
93; RV32-ZICFISS-LABEL: f3:
94; RV32-ZICFISS:       # %bb.0:
95; RV32-ZICFISS-NEXT:    addi gp, gp, 4
96; RV32-ZICFISS-NEXT:    sw ra, -4(gp)
97; RV32-ZICFISS-NEXT:    .cfi_escape 0x16, 0x03, 0x02, 0x73, 0x7c #
98; RV32-ZICFISS-NEXT:    addi sp, sp, -16
99; RV32-ZICFISS-NEXT:    .cfi_def_cfa_offset 16
100; RV32-ZICFISS-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
101; RV32-ZICFISS-NEXT:    .cfi_offset ra, -4
102; RV32-ZICFISS-NEXT:    call bar
103; RV32-ZICFISS-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
104; RV32-ZICFISS-NEXT:    .cfi_restore ra
105; RV32-ZICFISS-NEXT:    addi sp, sp, 16
106; RV32-ZICFISS-NEXT:    .cfi_def_cfa_offset 0
107; RV32-ZICFISS-NEXT:    lw ra, -4(gp)
108; RV32-ZICFISS-NEXT:    addi gp, gp, -4
109; RV32-ZICFISS-NEXT:    .cfi_restore gp
110; RV32-ZICFISS-NEXT:    ret
111;
112; RV64-ZICFISS-LABEL: f3:
113; RV64-ZICFISS:       # %bb.0:
114; RV64-ZICFISS-NEXT:    addi gp, gp, 8
115; RV64-ZICFISS-NEXT:    sd ra, -8(gp)
116; RV64-ZICFISS-NEXT:    .cfi_escape 0x16, 0x03, 0x02, 0x73, 0x78 #
117; RV64-ZICFISS-NEXT:    addi sp, sp, -16
118; RV64-ZICFISS-NEXT:    .cfi_def_cfa_offset 16
119; RV64-ZICFISS-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
120; RV64-ZICFISS-NEXT:    .cfi_offset ra, -8
121; RV64-ZICFISS-NEXT:    call bar
122; RV64-ZICFISS-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
123; RV64-ZICFISS-NEXT:    .cfi_restore ra
124; RV64-ZICFISS-NEXT:    addi sp, sp, 16
125; RV64-ZICFISS-NEXT:    .cfi_def_cfa_offset 0
126; RV64-ZICFISS-NEXT:    ld ra, -8(gp)
127; RV64-ZICFISS-NEXT:    addi gp, gp, -8
128; RV64-ZICFISS-NEXT:    .cfi_restore gp
129; RV64-ZICFISS-NEXT:    ret
130  %res = call i32 @bar()
131  %res1 = add i32 %res, 1
132  ret i32 %res
133}
134
135define i32 @f4() shadowcallstack {
136; RV32-LABEL: f4:
137; RV32:       # %bb.0:
138; RV32-NEXT:    addi gp, gp, 4
139; RV32-NEXT:    sw ra, -4(gp)
140; RV32-NEXT:    .cfi_escape 0x16, 0x03, 0x02, 0x73, 0x7c #
141; RV32-NEXT:    addi sp, sp, -16
142; RV32-NEXT:    .cfi_def_cfa_offset 16
143; RV32-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
144; RV32-NEXT:    sw s0, 8(sp) # 4-byte Folded Spill
145; RV32-NEXT:    sw s1, 4(sp) # 4-byte Folded Spill
146; RV32-NEXT:    sw s2, 0(sp) # 4-byte Folded Spill
147; RV32-NEXT:    .cfi_offset ra, -4
148; RV32-NEXT:    .cfi_offset s0, -8
149; RV32-NEXT:    .cfi_offset s1, -12
150; RV32-NEXT:    .cfi_offset s2, -16
151; RV32-NEXT:    call bar
152; RV32-NEXT:    mv s0, a0
153; RV32-NEXT:    call bar
154; RV32-NEXT:    mv s1, a0
155; RV32-NEXT:    call bar
156; RV32-NEXT:    mv s2, a0
157; RV32-NEXT:    call bar
158; RV32-NEXT:    add s0, s0, s1
159; RV32-NEXT:    add a0, s2, a0
160; RV32-NEXT:    add a0, s0, a0
161; RV32-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
162; RV32-NEXT:    lw s0, 8(sp) # 4-byte Folded Reload
163; RV32-NEXT:    lw s1, 4(sp) # 4-byte Folded Reload
164; RV32-NEXT:    lw s2, 0(sp) # 4-byte Folded Reload
165; RV32-NEXT:    .cfi_restore ra
166; RV32-NEXT:    .cfi_restore s0
167; RV32-NEXT:    .cfi_restore s1
168; RV32-NEXT:    .cfi_restore s2
169; RV32-NEXT:    addi sp, sp, 16
170; RV32-NEXT:    .cfi_def_cfa_offset 0
171; RV32-NEXT:    lw ra, -4(gp)
172; RV32-NEXT:    addi gp, gp, -4
173; RV32-NEXT:    .cfi_restore gp
174; RV32-NEXT:    ret
175;
176; RV64-LABEL: f4:
177; RV64:       # %bb.0:
178; RV64-NEXT:    addi gp, gp, 8
179; RV64-NEXT:    sd ra, -8(gp)
180; RV64-NEXT:    .cfi_escape 0x16, 0x03, 0x02, 0x73, 0x78 #
181; RV64-NEXT:    addi sp, sp, -32
182; RV64-NEXT:    .cfi_def_cfa_offset 32
183; RV64-NEXT:    sd ra, 24(sp) # 8-byte Folded Spill
184; RV64-NEXT:    sd s0, 16(sp) # 8-byte Folded Spill
185; RV64-NEXT:    sd s1, 8(sp) # 8-byte Folded Spill
186; RV64-NEXT:    sd s2, 0(sp) # 8-byte Folded Spill
187; RV64-NEXT:    .cfi_offset ra, -8
188; RV64-NEXT:    .cfi_offset s0, -16
189; RV64-NEXT:    .cfi_offset s1, -24
190; RV64-NEXT:    .cfi_offset s2, -32
191; RV64-NEXT:    call bar
192; RV64-NEXT:    mv s0, a0
193; RV64-NEXT:    call bar
194; RV64-NEXT:    mv s1, a0
195; RV64-NEXT:    call bar
196; RV64-NEXT:    mv s2, a0
197; RV64-NEXT:    call bar
198; RV64-NEXT:    add s0, s0, s1
199; RV64-NEXT:    add a0, s2, a0
200; RV64-NEXT:    addw a0, s0, a0
201; RV64-NEXT:    ld ra, 24(sp) # 8-byte Folded Reload
202; RV64-NEXT:    ld s0, 16(sp) # 8-byte Folded Reload
203; RV64-NEXT:    ld s1, 8(sp) # 8-byte Folded Reload
204; RV64-NEXT:    ld s2, 0(sp) # 8-byte Folded Reload
205; RV64-NEXT:    .cfi_restore ra
206; RV64-NEXT:    .cfi_restore s0
207; RV64-NEXT:    .cfi_restore s1
208; RV64-NEXT:    .cfi_restore s2
209; RV64-NEXT:    addi sp, sp, 32
210; RV64-NEXT:    .cfi_def_cfa_offset 0
211; RV64-NEXT:    ld ra, -8(gp)
212; RV64-NEXT:    addi gp, gp, -8
213; RV64-NEXT:    .cfi_restore gp
214; RV64-NEXT:    ret
215;
216; RV32-ZICFISS-LABEL: f4:
217; RV32-ZICFISS:       # %bb.0:
218; RV32-ZICFISS-NEXT:    addi gp, gp, 4
219; RV32-ZICFISS-NEXT:    sw ra, -4(gp)
220; RV32-ZICFISS-NEXT:    .cfi_escape 0x16, 0x03, 0x02, 0x73, 0x7c #
221; RV32-ZICFISS-NEXT:    addi sp, sp, -16
222; RV32-ZICFISS-NEXT:    .cfi_def_cfa_offset 16
223; RV32-ZICFISS-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
224; RV32-ZICFISS-NEXT:    sw s0, 8(sp) # 4-byte Folded Spill
225; RV32-ZICFISS-NEXT:    sw s1, 4(sp) # 4-byte Folded Spill
226; RV32-ZICFISS-NEXT:    sw s2, 0(sp) # 4-byte Folded Spill
227; RV32-ZICFISS-NEXT:    .cfi_offset ra, -4
228; RV32-ZICFISS-NEXT:    .cfi_offset s0, -8
229; RV32-ZICFISS-NEXT:    .cfi_offset s1, -12
230; RV32-ZICFISS-NEXT:    .cfi_offset s2, -16
231; RV32-ZICFISS-NEXT:    call bar
232; RV32-ZICFISS-NEXT:    mv s0, a0
233; RV32-ZICFISS-NEXT:    call bar
234; RV32-ZICFISS-NEXT:    mv s1, a0
235; RV32-ZICFISS-NEXT:    call bar
236; RV32-ZICFISS-NEXT:    mv s2, a0
237; RV32-ZICFISS-NEXT:    call bar
238; RV32-ZICFISS-NEXT:    add s0, s0, s1
239; RV32-ZICFISS-NEXT:    add a0, s2, a0
240; RV32-ZICFISS-NEXT:    add a0, s0, a0
241; RV32-ZICFISS-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
242; RV32-ZICFISS-NEXT:    lw s0, 8(sp) # 4-byte Folded Reload
243; RV32-ZICFISS-NEXT:    lw s1, 4(sp) # 4-byte Folded Reload
244; RV32-ZICFISS-NEXT:    lw s2, 0(sp) # 4-byte Folded Reload
245; RV32-ZICFISS-NEXT:    .cfi_restore ra
246; RV32-ZICFISS-NEXT:    .cfi_restore s0
247; RV32-ZICFISS-NEXT:    .cfi_restore s1
248; RV32-ZICFISS-NEXT:    .cfi_restore s2
249; RV32-ZICFISS-NEXT:    addi sp, sp, 16
250; RV32-ZICFISS-NEXT:    .cfi_def_cfa_offset 0
251; RV32-ZICFISS-NEXT:    lw ra, -4(gp)
252; RV32-ZICFISS-NEXT:    addi gp, gp, -4
253; RV32-ZICFISS-NEXT:    .cfi_restore gp
254; RV32-ZICFISS-NEXT:    ret
255;
256; RV64-ZICFISS-LABEL: f4:
257; RV64-ZICFISS:       # %bb.0:
258; RV64-ZICFISS-NEXT:    addi gp, gp, 8
259; RV64-ZICFISS-NEXT:    sd ra, -8(gp)
260; RV64-ZICFISS-NEXT:    .cfi_escape 0x16, 0x03, 0x02, 0x73, 0x78 #
261; RV64-ZICFISS-NEXT:    addi sp, sp, -32
262; RV64-ZICFISS-NEXT:    .cfi_def_cfa_offset 32
263; RV64-ZICFISS-NEXT:    sd ra, 24(sp) # 8-byte Folded Spill
264; RV64-ZICFISS-NEXT:    sd s0, 16(sp) # 8-byte Folded Spill
265; RV64-ZICFISS-NEXT:    sd s1, 8(sp) # 8-byte Folded Spill
266; RV64-ZICFISS-NEXT:    sd s2, 0(sp) # 8-byte Folded Spill
267; RV64-ZICFISS-NEXT:    .cfi_offset ra, -8
268; RV64-ZICFISS-NEXT:    .cfi_offset s0, -16
269; RV64-ZICFISS-NEXT:    .cfi_offset s1, -24
270; RV64-ZICFISS-NEXT:    .cfi_offset s2, -32
271; RV64-ZICFISS-NEXT:    call bar
272; RV64-ZICFISS-NEXT:    mv s0, a0
273; RV64-ZICFISS-NEXT:    call bar
274; RV64-ZICFISS-NEXT:    mv s1, a0
275; RV64-ZICFISS-NEXT:    call bar
276; RV64-ZICFISS-NEXT:    mv s2, a0
277; RV64-ZICFISS-NEXT:    call bar
278; RV64-ZICFISS-NEXT:    add s0, s0, s1
279; RV64-ZICFISS-NEXT:    add a0, s2, a0
280; RV64-ZICFISS-NEXT:    addw a0, s0, a0
281; RV64-ZICFISS-NEXT:    ld ra, 24(sp) # 8-byte Folded Reload
282; RV64-ZICFISS-NEXT:    ld s0, 16(sp) # 8-byte Folded Reload
283; RV64-ZICFISS-NEXT:    ld s1, 8(sp) # 8-byte Folded Reload
284; RV64-ZICFISS-NEXT:    ld s2, 0(sp) # 8-byte Folded Reload
285; RV64-ZICFISS-NEXT:    .cfi_restore ra
286; RV64-ZICFISS-NEXT:    .cfi_restore s0
287; RV64-ZICFISS-NEXT:    .cfi_restore s1
288; RV64-ZICFISS-NEXT:    .cfi_restore s2
289; RV64-ZICFISS-NEXT:    addi sp, sp, 32
290; RV64-ZICFISS-NEXT:    .cfi_def_cfa_offset 0
291; RV64-ZICFISS-NEXT:    ld ra, -8(gp)
292; RV64-ZICFISS-NEXT:    addi gp, gp, -8
293; RV64-ZICFISS-NEXT:    .cfi_restore gp
294; RV64-ZICFISS-NEXT:    ret
295  %res1 = call i32 @bar()
296  %res2 = call i32 @bar()
297  %res3 = call i32 @bar()
298  %res4 = call i32 @bar()
299  %res12 = add i32 %res1, %res2
300  %res34 = add i32 %res3, %res4
301  %res1234 = add i32 %res12, %res34
302  ret i32 %res1234
303}
304
305define i32 @f5() shadowcallstack nounwind {
306; RV32-LABEL: f5:
307; RV32:       # %bb.0:
308; RV32-NEXT:    addi gp, gp, 4
309; RV32-NEXT:    sw ra, -4(gp)
310; RV32-NEXT:    addi sp, sp, -16
311; RV32-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
312; RV32-NEXT:    call bar
313; RV32-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
314; RV32-NEXT:    addi sp, sp, 16
315; RV32-NEXT:    lw ra, -4(gp)
316; RV32-NEXT:    addi gp, gp, -4
317; RV32-NEXT:    ret
318;
319; RV64-LABEL: f5:
320; RV64:       # %bb.0:
321; RV64-NEXT:    addi gp, gp, 8
322; RV64-NEXT:    sd ra, -8(gp)
323; RV64-NEXT:    addi sp, sp, -16
324; RV64-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
325; RV64-NEXT:    call bar
326; RV64-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
327; RV64-NEXT:    addi sp, sp, 16
328; RV64-NEXT:    ld ra, -8(gp)
329; RV64-NEXT:    addi gp, gp, -8
330; RV64-NEXT:    ret
331;
332; RV32-ZICFISS-LABEL: f5:
333; RV32-ZICFISS:       # %bb.0:
334; RV32-ZICFISS-NEXT:    addi gp, gp, 4
335; RV32-ZICFISS-NEXT:    sw ra, -4(gp)
336; RV32-ZICFISS-NEXT:    addi sp, sp, -16
337; RV32-ZICFISS-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
338; RV32-ZICFISS-NEXT:    call bar
339; RV32-ZICFISS-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
340; RV32-ZICFISS-NEXT:    addi sp, sp, 16
341; RV32-ZICFISS-NEXT:    lw ra, -4(gp)
342; RV32-ZICFISS-NEXT:    addi gp, gp, -4
343; RV32-ZICFISS-NEXT:    ret
344;
345; RV64-ZICFISS-LABEL: f5:
346; RV64-ZICFISS:       # %bb.0:
347; RV64-ZICFISS-NEXT:    addi gp, gp, 8
348; RV64-ZICFISS-NEXT:    sd ra, -8(gp)
349; RV64-ZICFISS-NEXT:    addi sp, sp, -16
350; RV64-ZICFISS-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
351; RV64-ZICFISS-NEXT:    call bar
352; RV64-ZICFISS-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
353; RV64-ZICFISS-NEXT:    addi sp, sp, 16
354; RV64-ZICFISS-NEXT:    ld ra, -8(gp)
355; RV64-ZICFISS-NEXT:    addi gp, gp, -8
356; RV64-ZICFISS-NEXT:    ret
357  %res = call i32 @bar()
358  %res1 = add i32 %res, 1
359  ret i32 %res
360}
361
362define void @f1_hw() "hw-shadow-stack" {
363; RV32-LABEL: f1_hw:
364; RV32:       # %bb.0:
365; RV32-NEXT:    ret
366;
367; RV64-LABEL: f1_hw:
368; RV64:       # %bb.0:
369; RV64-NEXT:    ret
370;
371; RV32-ZICFISS-LABEL: f1_hw:
372; RV32-ZICFISS:       # %bb.0:
373; RV32-ZICFISS-NEXT:    ret
374;
375; RV64-ZICFISS-LABEL: f1_hw:
376; RV64-ZICFISS:       # %bb.0:
377; RV64-ZICFISS-NEXT:    ret
378  ret void
379}
380
381define void @f2_hw() "hw-shadow-stack" {
382; RV32-LABEL: f2_hw:
383; RV32:       # %bb.0:
384; RV32-NEXT:    tail foo
385;
386; RV64-LABEL: f2_hw:
387; RV64:       # %bb.0:
388; RV64-NEXT:    tail foo
389;
390; RV32-ZICFISS-LABEL: f2_hw:
391; RV32-ZICFISS:       # %bb.0:
392; RV32-ZICFISS-NEXT:    tail foo
393;
394; RV64-ZICFISS-LABEL: f2_hw:
395; RV64-ZICFISS:       # %bb.0:
396; RV64-ZICFISS-NEXT:    tail foo
397  tail call void @foo()
398  ret void
399}
400
401define i32 @f3_hw() "hw-shadow-stack" {
402; RV32-LABEL: f3_hw:
403; RV32:       # %bb.0:
404; RV32-NEXT:    addi sp, sp, -16
405; RV32-NEXT:    .cfi_def_cfa_offset 16
406; RV32-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
407; RV32-NEXT:    .cfi_offset ra, -4
408; RV32-NEXT:    call bar
409; RV32-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
410; RV32-NEXT:    .cfi_restore ra
411; RV32-NEXT:    addi sp, sp, 16
412; RV32-NEXT:    .cfi_def_cfa_offset 0
413; RV32-NEXT:    ret
414;
415; RV64-LABEL: f3_hw:
416; RV64:       # %bb.0:
417; RV64-NEXT:    addi sp, sp, -16
418; RV64-NEXT:    .cfi_def_cfa_offset 16
419; RV64-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
420; RV64-NEXT:    .cfi_offset ra, -8
421; RV64-NEXT:    call bar
422; RV64-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
423; RV64-NEXT:    .cfi_restore ra
424; RV64-NEXT:    addi sp, sp, 16
425; RV64-NEXT:    .cfi_def_cfa_offset 0
426; RV64-NEXT:    ret
427;
428; RV32-ZICFISS-LABEL: f3_hw:
429; RV32-ZICFISS:       # %bb.0:
430; RV32-ZICFISS-NEXT:    sspush ra
431; RV32-ZICFISS-NEXT:    addi sp, sp, -16
432; RV32-ZICFISS-NEXT:    .cfi_def_cfa_offset 16
433; RV32-ZICFISS-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
434; RV32-ZICFISS-NEXT:    .cfi_offset ra, -4
435; RV32-ZICFISS-NEXT:    call bar
436; RV32-ZICFISS-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
437; RV32-ZICFISS-NEXT:    .cfi_restore ra
438; RV32-ZICFISS-NEXT:    addi sp, sp, 16
439; RV32-ZICFISS-NEXT:    .cfi_def_cfa_offset 0
440; RV32-ZICFISS-NEXT:    sspopchk ra
441; RV32-ZICFISS-NEXT:    ret
442;
443; RV64-ZICFISS-LABEL: f3_hw:
444; RV64-ZICFISS:       # %bb.0:
445; RV64-ZICFISS-NEXT:    sspush ra
446; RV64-ZICFISS-NEXT:    addi sp, sp, -16
447; RV64-ZICFISS-NEXT:    .cfi_def_cfa_offset 16
448; RV64-ZICFISS-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
449; RV64-ZICFISS-NEXT:    .cfi_offset ra, -8
450; RV64-ZICFISS-NEXT:    call bar
451; RV64-ZICFISS-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
452; RV64-ZICFISS-NEXT:    .cfi_restore ra
453; RV64-ZICFISS-NEXT:    addi sp, sp, 16
454; RV64-ZICFISS-NEXT:    .cfi_def_cfa_offset 0
455; RV64-ZICFISS-NEXT:    sspopchk ra
456; RV64-ZICFISS-NEXT:    ret
457  %res = call i32 @bar()
458  %res1 = add i32 %res, 1
459  ret i32 %res
460}
461
462define i32 @f4_hw() "hw-shadow-stack" {
463; RV32-LABEL: f4_hw:
464; RV32:       # %bb.0:
465; RV32-NEXT:    addi sp, sp, -16
466; RV32-NEXT:    .cfi_def_cfa_offset 16
467; RV32-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
468; RV32-NEXT:    sw s0, 8(sp) # 4-byte Folded Spill
469; RV32-NEXT:    sw s1, 4(sp) # 4-byte Folded Spill
470; RV32-NEXT:    sw s2, 0(sp) # 4-byte Folded Spill
471; RV32-NEXT:    .cfi_offset ra, -4
472; RV32-NEXT:    .cfi_offset s0, -8
473; RV32-NEXT:    .cfi_offset s1, -12
474; RV32-NEXT:    .cfi_offset s2, -16
475; RV32-NEXT:    call bar
476; RV32-NEXT:    mv s0, a0
477; RV32-NEXT:    call bar
478; RV32-NEXT:    mv s1, a0
479; RV32-NEXT:    call bar
480; RV32-NEXT:    mv s2, a0
481; RV32-NEXT:    call bar
482; RV32-NEXT:    add s0, s0, s1
483; RV32-NEXT:    add a0, s2, a0
484; RV32-NEXT:    add a0, s0, a0
485; RV32-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
486; RV32-NEXT:    lw s0, 8(sp) # 4-byte Folded Reload
487; RV32-NEXT:    lw s1, 4(sp) # 4-byte Folded Reload
488; RV32-NEXT:    lw s2, 0(sp) # 4-byte Folded Reload
489; RV32-NEXT:    .cfi_restore ra
490; RV32-NEXT:    .cfi_restore s0
491; RV32-NEXT:    .cfi_restore s1
492; RV32-NEXT:    .cfi_restore s2
493; RV32-NEXT:    addi sp, sp, 16
494; RV32-NEXT:    .cfi_def_cfa_offset 0
495; RV32-NEXT:    ret
496;
497; RV64-LABEL: f4_hw:
498; RV64:       # %bb.0:
499; RV64-NEXT:    addi sp, sp, -32
500; RV64-NEXT:    .cfi_def_cfa_offset 32
501; RV64-NEXT:    sd ra, 24(sp) # 8-byte Folded Spill
502; RV64-NEXT:    sd s0, 16(sp) # 8-byte Folded Spill
503; RV64-NEXT:    sd s1, 8(sp) # 8-byte Folded Spill
504; RV64-NEXT:    sd s2, 0(sp) # 8-byte Folded Spill
505; RV64-NEXT:    .cfi_offset ra, -8
506; RV64-NEXT:    .cfi_offset s0, -16
507; RV64-NEXT:    .cfi_offset s1, -24
508; RV64-NEXT:    .cfi_offset s2, -32
509; RV64-NEXT:    call bar
510; RV64-NEXT:    mv s0, a0
511; RV64-NEXT:    call bar
512; RV64-NEXT:    mv s1, a0
513; RV64-NEXT:    call bar
514; RV64-NEXT:    mv s2, a0
515; RV64-NEXT:    call bar
516; RV64-NEXT:    add s0, s0, s1
517; RV64-NEXT:    add a0, s2, a0
518; RV64-NEXT:    addw a0, s0, a0
519; RV64-NEXT:    ld ra, 24(sp) # 8-byte Folded Reload
520; RV64-NEXT:    ld s0, 16(sp) # 8-byte Folded Reload
521; RV64-NEXT:    ld s1, 8(sp) # 8-byte Folded Reload
522; RV64-NEXT:    ld s2, 0(sp) # 8-byte Folded Reload
523; RV64-NEXT:    .cfi_restore ra
524; RV64-NEXT:    .cfi_restore s0
525; RV64-NEXT:    .cfi_restore s1
526; RV64-NEXT:    .cfi_restore s2
527; RV64-NEXT:    addi sp, sp, 32
528; RV64-NEXT:    .cfi_def_cfa_offset 0
529; RV64-NEXT:    ret
530;
531; RV32-ZICFISS-LABEL: f4_hw:
532; RV32-ZICFISS:       # %bb.0:
533; RV32-ZICFISS-NEXT:    sspush ra
534; RV32-ZICFISS-NEXT:    addi sp, sp, -16
535; RV32-ZICFISS-NEXT:    .cfi_def_cfa_offset 16
536; RV32-ZICFISS-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
537; RV32-ZICFISS-NEXT:    sw s0, 8(sp) # 4-byte Folded Spill
538; RV32-ZICFISS-NEXT:    sw s1, 4(sp) # 4-byte Folded Spill
539; RV32-ZICFISS-NEXT:    sw s2, 0(sp) # 4-byte Folded Spill
540; RV32-ZICFISS-NEXT:    .cfi_offset ra, -4
541; RV32-ZICFISS-NEXT:    .cfi_offset s0, -8
542; RV32-ZICFISS-NEXT:    .cfi_offset s1, -12
543; RV32-ZICFISS-NEXT:    .cfi_offset s2, -16
544; RV32-ZICFISS-NEXT:    call bar
545; RV32-ZICFISS-NEXT:    mv s0, a0
546; RV32-ZICFISS-NEXT:    call bar
547; RV32-ZICFISS-NEXT:    mv s1, a0
548; RV32-ZICFISS-NEXT:    call bar
549; RV32-ZICFISS-NEXT:    mv s2, a0
550; RV32-ZICFISS-NEXT:    call bar
551; RV32-ZICFISS-NEXT:    add s0, s0, s1
552; RV32-ZICFISS-NEXT:    add a0, s2, a0
553; RV32-ZICFISS-NEXT:    add a0, s0, a0
554; RV32-ZICFISS-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
555; RV32-ZICFISS-NEXT:    lw s0, 8(sp) # 4-byte Folded Reload
556; RV32-ZICFISS-NEXT:    lw s1, 4(sp) # 4-byte Folded Reload
557; RV32-ZICFISS-NEXT:    lw s2, 0(sp) # 4-byte Folded Reload
558; RV32-ZICFISS-NEXT:    .cfi_restore ra
559; RV32-ZICFISS-NEXT:    .cfi_restore s0
560; RV32-ZICFISS-NEXT:    .cfi_restore s1
561; RV32-ZICFISS-NEXT:    .cfi_restore s2
562; RV32-ZICFISS-NEXT:    addi sp, sp, 16
563; RV32-ZICFISS-NEXT:    .cfi_def_cfa_offset 0
564; RV32-ZICFISS-NEXT:    sspopchk ra
565; RV32-ZICFISS-NEXT:    ret
566;
567; RV64-ZICFISS-LABEL: f4_hw:
568; RV64-ZICFISS:       # %bb.0:
569; RV64-ZICFISS-NEXT:    sspush ra
570; RV64-ZICFISS-NEXT:    addi sp, sp, -32
571; RV64-ZICFISS-NEXT:    .cfi_def_cfa_offset 32
572; RV64-ZICFISS-NEXT:    sd ra, 24(sp) # 8-byte Folded Spill
573; RV64-ZICFISS-NEXT:    sd s0, 16(sp) # 8-byte Folded Spill
574; RV64-ZICFISS-NEXT:    sd s1, 8(sp) # 8-byte Folded Spill
575; RV64-ZICFISS-NEXT:    sd s2, 0(sp) # 8-byte Folded Spill
576; RV64-ZICFISS-NEXT:    .cfi_offset ra, -8
577; RV64-ZICFISS-NEXT:    .cfi_offset s0, -16
578; RV64-ZICFISS-NEXT:    .cfi_offset s1, -24
579; RV64-ZICFISS-NEXT:    .cfi_offset s2, -32
580; RV64-ZICFISS-NEXT:    call bar
581; RV64-ZICFISS-NEXT:    mv s0, a0
582; RV64-ZICFISS-NEXT:    call bar
583; RV64-ZICFISS-NEXT:    mv s1, a0
584; RV64-ZICFISS-NEXT:    call bar
585; RV64-ZICFISS-NEXT:    mv s2, a0
586; RV64-ZICFISS-NEXT:    call bar
587; RV64-ZICFISS-NEXT:    add s0, s0, s1
588; RV64-ZICFISS-NEXT:    add a0, s2, a0
589; RV64-ZICFISS-NEXT:    addw a0, s0, a0
590; RV64-ZICFISS-NEXT:    ld ra, 24(sp) # 8-byte Folded Reload
591; RV64-ZICFISS-NEXT:    ld s0, 16(sp) # 8-byte Folded Reload
592; RV64-ZICFISS-NEXT:    ld s1, 8(sp) # 8-byte Folded Reload
593; RV64-ZICFISS-NEXT:    ld s2, 0(sp) # 8-byte Folded Reload
594; RV64-ZICFISS-NEXT:    .cfi_restore ra
595; RV64-ZICFISS-NEXT:    .cfi_restore s0
596; RV64-ZICFISS-NEXT:    .cfi_restore s1
597; RV64-ZICFISS-NEXT:    .cfi_restore s2
598; RV64-ZICFISS-NEXT:    addi sp, sp, 32
599; RV64-ZICFISS-NEXT:    .cfi_def_cfa_offset 0
600; RV64-ZICFISS-NEXT:    sspopchk ra
601; RV64-ZICFISS-NEXT:    ret
602  %res1 = call i32 @bar()
603  %res2 = call i32 @bar()
604  %res3 = call i32 @bar()
605  %res4 = call i32 @bar()
606  %res12 = add i32 %res1, %res2
607  %res34 = add i32 %res3, %res4
608  %res1234 = add i32 %res12, %res34
609  ret i32 %res1234
610}
611
612define i32 @f5_hw() "hw-shadow-stack" nounwind {
613; RV32-LABEL: f5_hw:
614; RV32:       # %bb.0:
615; RV32-NEXT:    addi sp, sp, -16
616; RV32-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
617; RV32-NEXT:    call bar
618; RV32-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
619; RV32-NEXT:    addi sp, sp, 16
620; RV32-NEXT:    ret
621;
622; RV64-LABEL: f5_hw:
623; RV64:       # %bb.0:
624; RV64-NEXT:    addi sp, sp, -16
625; RV64-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
626; RV64-NEXT:    call bar
627; RV64-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
628; RV64-NEXT:    addi sp, sp, 16
629; RV64-NEXT:    ret
630;
631; RV32-ZICFISS-LABEL: f5_hw:
632; RV32-ZICFISS:       # %bb.0:
633; RV32-ZICFISS-NEXT:    sspush ra
634; RV32-ZICFISS-NEXT:    addi sp, sp, -16
635; RV32-ZICFISS-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
636; RV32-ZICFISS-NEXT:    call bar
637; RV32-ZICFISS-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
638; RV32-ZICFISS-NEXT:    addi sp, sp, 16
639; RV32-ZICFISS-NEXT:    sspopchk ra
640; RV32-ZICFISS-NEXT:    ret
641;
642; RV64-ZICFISS-LABEL: f5_hw:
643; RV64-ZICFISS:       # %bb.0:
644; RV64-ZICFISS-NEXT:    sspush ra
645; RV64-ZICFISS-NEXT:    addi sp, sp, -16
646; RV64-ZICFISS-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
647; RV64-ZICFISS-NEXT:    call bar
648; RV64-ZICFISS-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
649; RV64-ZICFISS-NEXT:    addi sp, sp, 16
650; RV64-ZICFISS-NEXT:    sspopchk ra
651; RV64-ZICFISS-NEXT:    ret
652  %res = call i32 @bar()
653  %res1 = add i32 %res, 1
654  ret i32 %res
655}
656
657define void @f1_both() "hw-shadow-stack" shadowcallstack {
658; RV32-LABEL: f1_both:
659; RV32:       # %bb.0:
660; RV32-NEXT:    ret
661;
662; RV64-LABEL: f1_both:
663; RV64:       # %bb.0:
664; RV64-NEXT:    ret
665;
666; RV32-ZICFISS-LABEL: f1_both:
667; RV32-ZICFISS:       # %bb.0:
668; RV32-ZICFISS-NEXT:    ret
669;
670; RV64-ZICFISS-LABEL: f1_both:
671; RV64-ZICFISS:       # %bb.0:
672; RV64-ZICFISS-NEXT:    ret
673  ret void
674}
675
676define void @f2_both() "hw-shadow-stack" shadowcallstack {
677; RV32-LABEL: f2_both:
678; RV32:       # %bb.0:
679; RV32-NEXT:    tail foo
680;
681; RV64-LABEL: f2_both:
682; RV64:       # %bb.0:
683; RV64-NEXT:    tail foo
684;
685; RV32-ZICFISS-LABEL: f2_both:
686; RV32-ZICFISS:       # %bb.0:
687; RV32-ZICFISS-NEXT:    tail foo
688;
689; RV64-ZICFISS-LABEL: f2_both:
690; RV64-ZICFISS:       # %bb.0:
691; RV64-ZICFISS-NEXT:    tail foo
692  tail call void @foo()
693  ret void
694}
695
696define i32 @f3_both() "hw-shadow-stack" shadowcallstack {
697; RV32-LABEL: f3_both:
698; RV32:       # %bb.0:
699; RV32-NEXT:    addi gp, gp, 4
700; RV32-NEXT:    sw ra, -4(gp)
701; RV32-NEXT:    .cfi_escape 0x16, 0x03, 0x02, 0x73, 0x7c #
702; RV32-NEXT:    addi sp, sp, -16
703; RV32-NEXT:    .cfi_def_cfa_offset 16
704; RV32-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
705; RV32-NEXT:    .cfi_offset ra, -4
706; RV32-NEXT:    call bar
707; RV32-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
708; RV32-NEXT:    .cfi_restore ra
709; RV32-NEXT:    addi sp, sp, 16
710; RV32-NEXT:    .cfi_def_cfa_offset 0
711; RV32-NEXT:    lw ra, -4(gp)
712; RV32-NEXT:    addi gp, gp, -4
713; RV32-NEXT:    .cfi_restore gp
714; RV32-NEXT:    ret
715;
716; RV64-LABEL: f3_both:
717; RV64:       # %bb.0:
718; RV64-NEXT:    addi gp, gp, 8
719; RV64-NEXT:    sd ra, -8(gp)
720; RV64-NEXT:    .cfi_escape 0x16, 0x03, 0x02, 0x73, 0x78 #
721; RV64-NEXT:    addi sp, sp, -16
722; RV64-NEXT:    .cfi_def_cfa_offset 16
723; RV64-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
724; RV64-NEXT:    .cfi_offset ra, -8
725; RV64-NEXT:    call bar
726; RV64-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
727; RV64-NEXT:    .cfi_restore ra
728; RV64-NEXT:    addi sp, sp, 16
729; RV64-NEXT:    .cfi_def_cfa_offset 0
730; RV64-NEXT:    ld ra, -8(gp)
731; RV64-NEXT:    addi gp, gp, -8
732; RV64-NEXT:    .cfi_restore gp
733; RV64-NEXT:    ret
734;
735; RV32-ZICFISS-LABEL: f3_both:
736; RV32-ZICFISS:       # %bb.0:
737; RV32-ZICFISS-NEXT:    sspush ra
738; RV32-ZICFISS-NEXT:    addi sp, sp, -16
739; RV32-ZICFISS-NEXT:    .cfi_def_cfa_offset 16
740; RV32-ZICFISS-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
741; RV32-ZICFISS-NEXT:    .cfi_offset ra, -4
742; RV32-ZICFISS-NEXT:    call bar
743; RV32-ZICFISS-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
744; RV32-ZICFISS-NEXT:    .cfi_restore ra
745; RV32-ZICFISS-NEXT:    addi sp, sp, 16
746; RV32-ZICFISS-NEXT:    .cfi_def_cfa_offset 0
747; RV32-ZICFISS-NEXT:    sspopchk ra
748; RV32-ZICFISS-NEXT:    ret
749;
750; RV64-ZICFISS-LABEL: f3_both:
751; RV64-ZICFISS:       # %bb.0:
752; RV64-ZICFISS-NEXT:    sspush ra
753; RV64-ZICFISS-NEXT:    addi sp, sp, -16
754; RV64-ZICFISS-NEXT:    .cfi_def_cfa_offset 16
755; RV64-ZICFISS-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
756; RV64-ZICFISS-NEXT:    .cfi_offset ra, -8
757; RV64-ZICFISS-NEXT:    call bar
758; RV64-ZICFISS-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
759; RV64-ZICFISS-NEXT:    .cfi_restore ra
760; RV64-ZICFISS-NEXT:    addi sp, sp, 16
761; RV64-ZICFISS-NEXT:    .cfi_def_cfa_offset 0
762; RV64-ZICFISS-NEXT:    sspopchk ra
763; RV64-ZICFISS-NEXT:    ret
764  %res = call i32 @bar()
765  %res1 = add i32 %res, 1
766  ret i32 %res
767}
768
769define i32 @f4_both() "hw-shadow-stack" shadowcallstack {
770; RV32-LABEL: f4_both:
771; RV32:       # %bb.0:
772; RV32-NEXT:    addi gp, gp, 4
773; RV32-NEXT:    sw ra, -4(gp)
774; RV32-NEXT:    .cfi_escape 0x16, 0x03, 0x02, 0x73, 0x7c #
775; RV32-NEXT:    addi sp, sp, -16
776; RV32-NEXT:    .cfi_def_cfa_offset 16
777; RV32-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
778; RV32-NEXT:    sw s0, 8(sp) # 4-byte Folded Spill
779; RV32-NEXT:    sw s1, 4(sp) # 4-byte Folded Spill
780; RV32-NEXT:    sw s2, 0(sp) # 4-byte Folded Spill
781; RV32-NEXT:    .cfi_offset ra, -4
782; RV32-NEXT:    .cfi_offset s0, -8
783; RV32-NEXT:    .cfi_offset s1, -12
784; RV32-NEXT:    .cfi_offset s2, -16
785; RV32-NEXT:    call bar
786; RV32-NEXT:    mv s0, a0
787; RV32-NEXT:    call bar
788; RV32-NEXT:    mv s1, a0
789; RV32-NEXT:    call bar
790; RV32-NEXT:    mv s2, a0
791; RV32-NEXT:    call bar
792; RV32-NEXT:    add s0, s0, s1
793; RV32-NEXT:    add a0, s2, a0
794; RV32-NEXT:    add a0, s0, a0
795; RV32-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
796; RV32-NEXT:    lw s0, 8(sp) # 4-byte Folded Reload
797; RV32-NEXT:    lw s1, 4(sp) # 4-byte Folded Reload
798; RV32-NEXT:    lw s2, 0(sp) # 4-byte Folded Reload
799; RV32-NEXT:    .cfi_restore ra
800; RV32-NEXT:    .cfi_restore s0
801; RV32-NEXT:    .cfi_restore s1
802; RV32-NEXT:    .cfi_restore s2
803; RV32-NEXT:    addi sp, sp, 16
804; RV32-NEXT:    .cfi_def_cfa_offset 0
805; RV32-NEXT:    lw ra, -4(gp)
806; RV32-NEXT:    addi gp, gp, -4
807; RV32-NEXT:    .cfi_restore gp
808; RV32-NEXT:    ret
809;
810; RV64-LABEL: f4_both:
811; RV64:       # %bb.0:
812; RV64-NEXT:    addi gp, gp, 8
813; RV64-NEXT:    sd ra, -8(gp)
814; RV64-NEXT:    .cfi_escape 0x16, 0x03, 0x02, 0x73, 0x78 #
815; RV64-NEXT:    addi sp, sp, -32
816; RV64-NEXT:    .cfi_def_cfa_offset 32
817; RV64-NEXT:    sd ra, 24(sp) # 8-byte Folded Spill
818; RV64-NEXT:    sd s0, 16(sp) # 8-byte Folded Spill
819; RV64-NEXT:    sd s1, 8(sp) # 8-byte Folded Spill
820; RV64-NEXT:    sd s2, 0(sp) # 8-byte Folded Spill
821; RV64-NEXT:    .cfi_offset ra, -8
822; RV64-NEXT:    .cfi_offset s0, -16
823; RV64-NEXT:    .cfi_offset s1, -24
824; RV64-NEXT:    .cfi_offset s2, -32
825; RV64-NEXT:    call bar
826; RV64-NEXT:    mv s0, a0
827; RV64-NEXT:    call bar
828; RV64-NEXT:    mv s1, a0
829; RV64-NEXT:    call bar
830; RV64-NEXT:    mv s2, a0
831; RV64-NEXT:    call bar
832; RV64-NEXT:    add s0, s0, s1
833; RV64-NEXT:    add a0, s2, a0
834; RV64-NEXT:    addw a0, s0, a0
835; RV64-NEXT:    ld ra, 24(sp) # 8-byte Folded Reload
836; RV64-NEXT:    ld s0, 16(sp) # 8-byte Folded Reload
837; RV64-NEXT:    ld s1, 8(sp) # 8-byte Folded Reload
838; RV64-NEXT:    ld s2, 0(sp) # 8-byte Folded Reload
839; RV64-NEXT:    .cfi_restore ra
840; RV64-NEXT:    .cfi_restore s0
841; RV64-NEXT:    .cfi_restore s1
842; RV64-NEXT:    .cfi_restore s2
843; RV64-NEXT:    addi sp, sp, 32
844; RV64-NEXT:    .cfi_def_cfa_offset 0
845; RV64-NEXT:    ld ra, -8(gp)
846; RV64-NEXT:    addi gp, gp, -8
847; RV64-NEXT:    .cfi_restore gp
848; RV64-NEXT:    ret
849;
850; RV32-ZICFISS-LABEL: f4_both:
851; RV32-ZICFISS:       # %bb.0:
852; RV32-ZICFISS-NEXT:    sspush ra
853; RV32-ZICFISS-NEXT:    addi sp, sp, -16
854; RV32-ZICFISS-NEXT:    .cfi_def_cfa_offset 16
855; RV32-ZICFISS-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
856; RV32-ZICFISS-NEXT:    sw s0, 8(sp) # 4-byte Folded Spill
857; RV32-ZICFISS-NEXT:    sw s1, 4(sp) # 4-byte Folded Spill
858; RV32-ZICFISS-NEXT:    sw s2, 0(sp) # 4-byte Folded Spill
859; RV32-ZICFISS-NEXT:    .cfi_offset ra, -4
860; RV32-ZICFISS-NEXT:    .cfi_offset s0, -8
861; RV32-ZICFISS-NEXT:    .cfi_offset s1, -12
862; RV32-ZICFISS-NEXT:    .cfi_offset s2, -16
863; RV32-ZICFISS-NEXT:    call bar
864; RV32-ZICFISS-NEXT:    mv s0, a0
865; RV32-ZICFISS-NEXT:    call bar
866; RV32-ZICFISS-NEXT:    mv s1, a0
867; RV32-ZICFISS-NEXT:    call bar
868; RV32-ZICFISS-NEXT:    mv s2, a0
869; RV32-ZICFISS-NEXT:    call bar
870; RV32-ZICFISS-NEXT:    add s0, s0, s1
871; RV32-ZICFISS-NEXT:    add a0, s2, a0
872; RV32-ZICFISS-NEXT:    add a0, s0, a0
873; RV32-ZICFISS-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
874; RV32-ZICFISS-NEXT:    lw s0, 8(sp) # 4-byte Folded Reload
875; RV32-ZICFISS-NEXT:    lw s1, 4(sp) # 4-byte Folded Reload
876; RV32-ZICFISS-NEXT:    lw s2, 0(sp) # 4-byte Folded Reload
877; RV32-ZICFISS-NEXT:    .cfi_restore ra
878; RV32-ZICFISS-NEXT:    .cfi_restore s0
879; RV32-ZICFISS-NEXT:    .cfi_restore s1
880; RV32-ZICFISS-NEXT:    .cfi_restore s2
881; RV32-ZICFISS-NEXT:    addi sp, sp, 16
882; RV32-ZICFISS-NEXT:    .cfi_def_cfa_offset 0
883; RV32-ZICFISS-NEXT:    sspopchk ra
884; RV32-ZICFISS-NEXT:    ret
885;
886; RV64-ZICFISS-LABEL: f4_both:
887; RV64-ZICFISS:       # %bb.0:
888; RV64-ZICFISS-NEXT:    sspush ra
889; RV64-ZICFISS-NEXT:    addi sp, sp, -32
890; RV64-ZICFISS-NEXT:    .cfi_def_cfa_offset 32
891; RV64-ZICFISS-NEXT:    sd ra, 24(sp) # 8-byte Folded Spill
892; RV64-ZICFISS-NEXT:    sd s0, 16(sp) # 8-byte Folded Spill
893; RV64-ZICFISS-NEXT:    sd s1, 8(sp) # 8-byte Folded Spill
894; RV64-ZICFISS-NEXT:    sd s2, 0(sp) # 8-byte Folded Spill
895; RV64-ZICFISS-NEXT:    .cfi_offset ra, -8
896; RV64-ZICFISS-NEXT:    .cfi_offset s0, -16
897; RV64-ZICFISS-NEXT:    .cfi_offset s1, -24
898; RV64-ZICFISS-NEXT:    .cfi_offset s2, -32
899; RV64-ZICFISS-NEXT:    call bar
900; RV64-ZICFISS-NEXT:    mv s0, a0
901; RV64-ZICFISS-NEXT:    call bar
902; RV64-ZICFISS-NEXT:    mv s1, a0
903; RV64-ZICFISS-NEXT:    call bar
904; RV64-ZICFISS-NEXT:    mv s2, a0
905; RV64-ZICFISS-NEXT:    call bar
906; RV64-ZICFISS-NEXT:    add s0, s0, s1
907; RV64-ZICFISS-NEXT:    add a0, s2, a0
908; RV64-ZICFISS-NEXT:    addw a0, s0, a0
909; RV64-ZICFISS-NEXT:    ld ra, 24(sp) # 8-byte Folded Reload
910; RV64-ZICFISS-NEXT:    ld s0, 16(sp) # 8-byte Folded Reload
911; RV64-ZICFISS-NEXT:    ld s1, 8(sp) # 8-byte Folded Reload
912; RV64-ZICFISS-NEXT:    ld s2, 0(sp) # 8-byte Folded Reload
913; RV64-ZICFISS-NEXT:    .cfi_restore ra
914; RV64-ZICFISS-NEXT:    .cfi_restore s0
915; RV64-ZICFISS-NEXT:    .cfi_restore s1
916; RV64-ZICFISS-NEXT:    .cfi_restore s2
917; RV64-ZICFISS-NEXT:    addi sp, sp, 32
918; RV64-ZICFISS-NEXT:    .cfi_def_cfa_offset 0
919; RV64-ZICFISS-NEXT:    sspopchk ra
920; RV64-ZICFISS-NEXT:    ret
921  %res1 = call i32 @bar()
922  %res2 = call i32 @bar()
923  %res3 = call i32 @bar()
924  %res4 = call i32 @bar()
925  %res12 = add i32 %res1, %res2
926  %res34 = add i32 %res3, %res4
927  %res1234 = add i32 %res12, %res34
928  ret i32 %res1234
929}
930
931define i32 @f5_both() "hw-shadow-stack" shadowcallstack nounwind {
932; RV32-LABEL: f5_both:
933; RV32:       # %bb.0:
934; RV32-NEXT:    addi gp, gp, 4
935; RV32-NEXT:    sw ra, -4(gp)
936; RV32-NEXT:    addi sp, sp, -16
937; RV32-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
938; RV32-NEXT:    call bar
939; RV32-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
940; RV32-NEXT:    addi sp, sp, 16
941; RV32-NEXT:    lw ra, -4(gp)
942; RV32-NEXT:    addi gp, gp, -4
943; RV32-NEXT:    ret
944;
945; RV64-LABEL: f5_both:
946; RV64:       # %bb.0:
947; RV64-NEXT:    addi gp, gp, 8
948; RV64-NEXT:    sd ra, -8(gp)
949; RV64-NEXT:    addi sp, sp, -16
950; RV64-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
951; RV64-NEXT:    call bar
952; RV64-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
953; RV64-NEXT:    addi sp, sp, 16
954; RV64-NEXT:    ld ra, -8(gp)
955; RV64-NEXT:    addi gp, gp, -8
956; RV64-NEXT:    ret
957;
958; RV32-ZICFISS-LABEL: f5_both:
959; RV32-ZICFISS:       # %bb.0:
960; RV32-ZICFISS-NEXT:    sspush ra
961; RV32-ZICFISS-NEXT:    addi sp, sp, -16
962; RV32-ZICFISS-NEXT:    sw ra, 12(sp) # 4-byte Folded Spill
963; RV32-ZICFISS-NEXT:    call bar
964; RV32-ZICFISS-NEXT:    lw ra, 12(sp) # 4-byte Folded Reload
965; RV32-ZICFISS-NEXT:    addi sp, sp, 16
966; RV32-ZICFISS-NEXT:    sspopchk ra
967; RV32-ZICFISS-NEXT:    ret
968;
969; RV64-ZICFISS-LABEL: f5_both:
970; RV64-ZICFISS:       # %bb.0:
971; RV64-ZICFISS-NEXT:    sspush ra
972; RV64-ZICFISS-NEXT:    addi sp, sp, -16
973; RV64-ZICFISS-NEXT:    sd ra, 8(sp) # 8-byte Folded Spill
974; RV64-ZICFISS-NEXT:    call bar
975; RV64-ZICFISS-NEXT:    ld ra, 8(sp) # 8-byte Folded Reload
976; RV64-ZICFISS-NEXT:    addi sp, sp, 16
977; RV64-ZICFISS-NEXT:    sspopchk ra
978; RV64-ZICFISS-NEXT:    ret
979  %res = call i32 @bar()
980  %res1 = add i32 %res, 1
981  ret i32 %res
982}
983