xref: /llvm-project/llvm/test/CodeGen/RISCV/local-stack-slot-allocation.ll (revision 97982a8c605fac7c86d02e641a6cd7898b3ca343)
1069d7ef0Sluxufan; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
2069d7ef0Sluxufan; RUN: llc -mtriple=riscv32 -verify-machineinstrs < %s | FileCheck %s --check-prefix=RV32I
3069d7ef0Sluxufan; RUN: llc -mtriple=riscv64 -verify-machineinstrs < %s | FileCheck %s --check-prefix=RV64I
4069d7ef0Sluxufan
5069d7ef0Sluxufan; This test case test the LocalStackSlotAllocation pass that use a base register
6069d7ef0Sluxufan; for the frame index that its offset is out-of-range (for RISC-V. the immediate
7069d7ef0Sluxufan; is 12 bits for the load store instruction (excludes vector load / store))
8069d7ef0Sluxufandefine void @use_frame_base_reg() {
9069d7ef0Sluxufan; RV32I-LABEL: use_frame_base_reg:
10069d7ef0Sluxufan; RV32I:       # %bb.0:
11069d7ef0Sluxufan; RV32I-NEXT:    lui a0, 24
12069d7ef0Sluxufan; RV32I-NEXT:    addi a0, a0, 1712
13069d7ef0Sluxufan; RV32I-NEXT:    sub sp, sp, a0
14069d7ef0Sluxufan; RV32I-NEXT:    .cfi_def_cfa_offset 100016
15069d7ef0Sluxufan; RV32I-NEXT:    lui a0, 24
164554663bSLiDongjin; RV32I-NEXT:    addi a0, a0, 1704
17dc452a76SCraig Topper; RV32I-NEXT:    add a0, sp, a0
1893fde2eaSYingwei Zheng; RV32I-NEXT:    lbu zero, 4(a0)
1993fde2eaSYingwei Zheng; RV32I-NEXT:    lbu zero, 0(a0)
20069d7ef0Sluxufan; RV32I-NEXT:    lui a0, 24
21069d7ef0Sluxufan; RV32I-NEXT:    addi a0, a0, 1712
22069d7ef0Sluxufan; RV32I-NEXT:    add sp, sp, a0
23*97982a8cSdlav-sc; RV32I-NEXT:    .cfi_def_cfa_offset 0
24069d7ef0Sluxufan; RV32I-NEXT:    ret
25069d7ef0Sluxufan;
26069d7ef0Sluxufan; RV64I-LABEL: use_frame_base_reg:
27069d7ef0Sluxufan; RV64I:       # %bb.0:
28069d7ef0Sluxufan; RV64I-NEXT:    lui a0, 24
29069d7ef0Sluxufan; RV64I-NEXT:    addiw a0, a0, 1712
30069d7ef0Sluxufan; RV64I-NEXT:    sub sp, sp, a0
31069d7ef0Sluxufan; RV64I-NEXT:    .cfi_def_cfa_offset 100016
32069d7ef0Sluxufan; RV64I-NEXT:    lui a0, 24
334554663bSLiDongjin; RV64I-NEXT:    addiw a0, a0, 1704
34dc452a76SCraig Topper; RV64I-NEXT:    add a0, sp, a0
3593fde2eaSYingwei Zheng; RV64I-NEXT:    lbu zero, 4(a0)
3693fde2eaSYingwei Zheng; RV64I-NEXT:    lbu zero, 0(a0)
37069d7ef0Sluxufan; RV64I-NEXT:    lui a0, 24
38069d7ef0Sluxufan; RV64I-NEXT:    addiw a0, a0, 1712
39069d7ef0Sluxufan; RV64I-NEXT:    add sp, sp, a0
40*97982a8cSdlav-sc; RV64I-NEXT:    .cfi_def_cfa_offset 0
41069d7ef0Sluxufan; RV64I-NEXT:    ret
42069d7ef0Sluxufan
43069d7ef0Sluxufan  %va = alloca i8, align 4
44069d7ef0Sluxufan  %va1 = alloca i8, align 4
45069d7ef0Sluxufan  %large = alloca [ 100000 x i8 ]
461456b686SNikita Popov  %argp.cur = load volatile i8, ptr %va, align 4
471456b686SNikita Popov  %argp.next = load volatile i8, ptr %va1, align 4
48069d7ef0Sluxufan  ret void
49069d7ef0Sluxufan}
504554663bSLiDongjin
514554663bSLiDongjin; Test containing a load with its own local offset. Make sure isFrameOffsetLegal
5208177541SCraig Topper; considers it and creates a virtual base register.
534554663bSLiDongjindefine void @load_with_offset() {
544554663bSLiDongjin; RV32I-LABEL: load_with_offset:
554554663bSLiDongjin; RV32I:       # %bb.0:
5608177541SCraig Topper; RV32I-NEXT:    addi sp, sp, -2048
5708177541SCraig Topper; RV32I-NEXT:    addi sp, sp, -464
5808177541SCraig Topper; RV32I-NEXT:    .cfi_def_cfa_offset 2512
5908177541SCraig Topper; RV32I-NEXT:    addi a0, sp, 2012
6008177541SCraig Topper; RV32I-NEXT:    lbu a1, 0(a0)
6108177541SCraig Topper; RV32I-NEXT:    sb a1, 0(a0)
6208177541SCraig Topper; RV32I-NEXT:    addi sp, sp, 2032
6308177541SCraig Topper; RV32I-NEXT:    addi sp, sp, 480
64*97982a8cSdlav-sc; RV32I-NEXT:    .cfi_def_cfa_offset 0
654554663bSLiDongjin; RV32I-NEXT:    ret
664554663bSLiDongjin;
674554663bSLiDongjin; RV64I-LABEL: load_with_offset:
684554663bSLiDongjin; RV64I:       # %bb.0:
6908177541SCraig Topper; RV64I-NEXT:    addi sp, sp, -2048
7008177541SCraig Topper; RV64I-NEXT:    addi sp, sp, -464
7108177541SCraig Topper; RV64I-NEXT:    .cfi_def_cfa_offset 2512
7208177541SCraig Topper; RV64I-NEXT:    addi a0, sp, 2012
7308177541SCraig Topper; RV64I-NEXT:    lbu a1, 0(a0)
7408177541SCraig Topper; RV64I-NEXT:    sb a1, 0(a0)
7508177541SCraig Topper; RV64I-NEXT:    addi sp, sp, 2032
7608177541SCraig Topper; RV64I-NEXT:    addi sp, sp, 480
77*97982a8cSdlav-sc; RV64I-NEXT:    .cfi_def_cfa_offset 0
784554663bSLiDongjin; RV64I-NEXT:    ret
794554663bSLiDongjin
8008177541SCraig Topper  %va = alloca [2500 x i8], align 4
8108177541SCraig Topper  %va_gep = getelementptr [2000 x i8], ptr %va, i64 0, i64 2000
824554663bSLiDongjin  %load = load volatile i8, ptr %va_gep, align 4
8308177541SCraig Topper  store volatile i8 %load, ptr %va_gep, align 4
8408177541SCraig Topper  ret void
8508177541SCraig Topper}
8608177541SCraig Topper
8708177541SCraig Topper; Test containing a load with its own local offset that is smaller than the
8808177541SCraig Topper; previous test case. Make sure we don't create a virtual base register.
8908177541SCraig Topperdefine void @load_with_offset2() {
9008177541SCraig Topper; RV32I-LABEL: load_with_offset2:
9108177541SCraig Topper; RV32I:       # %bb.0:
9208177541SCraig Topper; RV32I-NEXT:    addi sp, sp, -2048
9308177541SCraig Topper; RV32I-NEXT:    addi sp, sp, -464
9408177541SCraig Topper; RV32I-NEXT:    .cfi_def_cfa_offset 2512
95026686baSCraig Topper; RV32I-NEXT:    lbu a0, 1412(sp)
96026686baSCraig Topper; RV32I-NEXT:    sb a0, 1412(sp)
9708177541SCraig Topper; RV32I-NEXT:    addi sp, sp, 2032
9808177541SCraig Topper; RV32I-NEXT:    addi sp, sp, 480
99*97982a8cSdlav-sc; RV32I-NEXT:    .cfi_def_cfa_offset 0
10008177541SCraig Topper; RV32I-NEXT:    ret
10108177541SCraig Topper;
10208177541SCraig Topper; RV64I-LABEL: load_with_offset2:
10308177541SCraig Topper; RV64I:       # %bb.0:
10408177541SCraig Topper; RV64I-NEXT:    addi sp, sp, -2048
10508177541SCraig Topper; RV64I-NEXT:    addi sp, sp, -464
10608177541SCraig Topper; RV64I-NEXT:    .cfi_def_cfa_offset 2512
107026686baSCraig Topper; RV64I-NEXT:    lbu a0, 1412(sp)
108026686baSCraig Topper; RV64I-NEXT:    sb a0, 1412(sp)
10908177541SCraig Topper; RV64I-NEXT:    addi sp, sp, 2032
11008177541SCraig Topper; RV64I-NEXT:    addi sp, sp, 480
111*97982a8cSdlav-sc; RV64I-NEXT:    .cfi_def_cfa_offset 0
11208177541SCraig Topper; RV64I-NEXT:    ret
11308177541SCraig Topper
11408177541SCraig Topper  %va = alloca [2500 x i8], align 4
11508177541SCraig Topper  %va_gep = getelementptr [2000 x i8], ptr %va, i64 0, i64 1400
11608177541SCraig Topper  %load = load volatile i8, ptr %va_gep, align 4
11708177541SCraig Topper  store volatile i8 %load, ptr %va_gep, align 4
1184554663bSLiDongjin  ret void
1194554663bSLiDongjin}
120c3028a23SCraig Topper
121c3028a23SCraig Topperdefine void @frame_pointer() "frame-pointer"="all" {
122c3028a23SCraig Topper; RV32I-LABEL: frame_pointer:
123c3028a23SCraig Topper; RV32I:       # %bb.0:
124c3028a23SCraig Topper; RV32I-NEXT:    addi sp, sp, -2032
125c3028a23SCraig Topper; RV32I-NEXT:    .cfi_def_cfa_offset 2032
126c3028a23SCraig Topper; RV32I-NEXT:    sw ra, 2028(sp) # 4-byte Folded Spill
127c3028a23SCraig Topper; RV32I-NEXT:    sw s0, 2024(sp) # 4-byte Folded Spill
128c3028a23SCraig Topper; RV32I-NEXT:    .cfi_offset ra, -4
129c3028a23SCraig Topper; RV32I-NEXT:    .cfi_offset s0, -8
130c3028a23SCraig Topper; RV32I-NEXT:    addi s0, sp, 2032
131c3028a23SCraig Topper; RV32I-NEXT:    .cfi_def_cfa s0, 0
132c3028a23SCraig Topper; RV32I-NEXT:    addi sp, sp, -480
133c3028a23SCraig Topper; RV32I-NEXT:    lbu a0, -1960(s0)
134c3028a23SCraig Topper; RV32I-NEXT:    sb a0, -1960(s0)
135c3028a23SCraig Topper; RV32I-NEXT:    addi sp, sp, 480
136*97982a8cSdlav-sc; RV32I-NEXT:    .cfi_def_cfa sp, 2032
137c3028a23SCraig Topper; RV32I-NEXT:    lw ra, 2028(sp) # 4-byte Folded Reload
138c3028a23SCraig Topper; RV32I-NEXT:    lw s0, 2024(sp) # 4-byte Folded Reload
139*97982a8cSdlav-sc; RV32I-NEXT:    .cfi_restore ra
140*97982a8cSdlav-sc; RV32I-NEXT:    .cfi_restore s0
141c3028a23SCraig Topper; RV32I-NEXT:    addi sp, sp, 2032
142*97982a8cSdlav-sc; RV32I-NEXT:    .cfi_def_cfa_offset 0
143c3028a23SCraig Topper; RV32I-NEXT:    ret
144c3028a23SCraig Topper;
145c3028a23SCraig Topper; RV64I-LABEL: frame_pointer:
146c3028a23SCraig Topper; RV64I:       # %bb.0:
147c3028a23SCraig Topper; RV64I-NEXT:    addi sp, sp, -2032
148c3028a23SCraig Topper; RV64I-NEXT:    .cfi_def_cfa_offset 2032
149c3028a23SCraig Topper; RV64I-NEXT:    sd ra, 2024(sp) # 8-byte Folded Spill
150c3028a23SCraig Topper; RV64I-NEXT:    sd s0, 2016(sp) # 8-byte Folded Spill
151c3028a23SCraig Topper; RV64I-NEXT:    .cfi_offset ra, -8
152c3028a23SCraig Topper; RV64I-NEXT:    .cfi_offset s0, -16
153c3028a23SCraig Topper; RV64I-NEXT:    addi s0, sp, 2032
154c3028a23SCraig Topper; RV64I-NEXT:    .cfi_def_cfa s0, 0
155c3028a23SCraig Topper; RV64I-NEXT:    addi sp, sp, -496
156c3028a23SCraig Topper; RV64I-NEXT:    addi a0, s0, -1972
157c3028a23SCraig Topper; RV64I-NEXT:    lbu a1, 0(a0)
158c3028a23SCraig Topper; RV64I-NEXT:    sb a1, 0(a0)
159c3028a23SCraig Topper; RV64I-NEXT:    addi sp, sp, 496
160*97982a8cSdlav-sc; RV64I-NEXT:    .cfi_def_cfa sp, 2032
161c3028a23SCraig Topper; RV64I-NEXT:    ld ra, 2024(sp) # 8-byte Folded Reload
162c3028a23SCraig Topper; RV64I-NEXT:    ld s0, 2016(sp) # 8-byte Folded Reload
163*97982a8cSdlav-sc; RV64I-NEXT:    .cfi_restore ra
164*97982a8cSdlav-sc; RV64I-NEXT:    .cfi_restore s0
165c3028a23SCraig Topper; RV64I-NEXT:    addi sp, sp, 2032
166*97982a8cSdlav-sc; RV64I-NEXT:    .cfi_def_cfa_offset 0
167c3028a23SCraig Topper; RV64I-NEXT:    ret
168c3028a23SCraig Topper
169c3028a23SCraig Topper  %va = alloca [2500 x i8], align 4
170c3028a23SCraig Topper  %va_gep = getelementptr [2000 x i8], ptr %va, i64 0, i64 552
171c3028a23SCraig Topper  %load = load volatile i8, ptr %va_gep, align 4
172c3028a23SCraig Topper  store volatile i8 %load, ptr %va_gep, align 4
173c3028a23SCraig Topper  ret void
174c3028a23SCraig Topper}
175