summaryrefslogtreecommitdiff
path: root/test/CodeGen/XCore/epilogue_prologue.ll
diff options
context:
space:
mode:
Diffstat (limited to 'test/CodeGen/XCore/epilogue_prologue.ll')
-rw-r--r--test/CodeGen/XCore/epilogue_prologue.ll125
1 files changed, 104 insertions, 21 deletions
diff --git a/test/CodeGen/XCore/epilogue_prologue.ll b/test/CodeGen/XCore/epilogue_prologue.ll
index ffbe7a1571..2898ae5dc8 100644
--- a/test/CodeGen/XCore/epilogue_prologue.ll
+++ b/test/CodeGen/XCore/epilogue_prologue.ll
@@ -1,7 +1,11 @@
; RUN: llc < %s -march=xcore | FileCheck %s
; RUN: llc < %s -march=xcore -disable-fp-elim | FileCheck %s -check-prefix=CHECKFP
+; When using SP for small frames, we don't need any scratch registers (SR).
+; When using SP for large frames, we may need two scratch registers.
+; When using FP, for large or small frames, we may need one scratch register.
+; FP + small frame: spill FP+SR = entsp 2
; CHECKFP-LABEL: f1
; CHECKFP: entsp 2
; CHECKFP-NEXT: stw r10, sp[1]
@@ -10,6 +14,7 @@
; CHECKFP-NEXT: ldw r10, sp[1]
; CHECKFP-NEXT: retsp 2
;
+; !FP + small frame: no spills = no stack adjustment needed
; CHECK-LABEL: f1
; CHECK: stw lr, sp[0]
; CHECK: ldw lr, sp[0]
@@ -21,6 +26,7 @@ entry:
}
+; FP + small frame: spill FP+SR+R0+LR = entsp 3 + extsp 1
; CHECKFP-LABEL:f3
; CHECKFP: entsp 3
; CHECKFP-NEXT: stw r10, sp[1]
@@ -36,14 +42,15 @@ entry:
; CHECKFP-NEXT: ldw r10, sp[1]
; CHECKFP-NEXT: retsp 3
;
+; !FP + small frame: spill R0+LR = entsp 2
; CHECK-LABEL: f3
; CHECK: entsp 2
-; CHECK: stw [[REG:r[4-9]+]], sp[1]
-; CHECK: mov [[REG]], r0
-; CHECK: bl f2
-; CHECK: mov r0, [[REG]]
-; CHECK: ldw [[REG]], sp[1]
-; CHECK: retsp 2
+; CHECK-NEXT: stw [[REG:r[4-9]+]], sp[1]
+; CHECK-NEXT: mov [[REG]], r0
+; CHECK-NEXT: bl f2
+; CHECK-NEXT: mov r0, [[REG]]
+; CHECK-NEXT: ldw [[REG]], sp[1]
+; CHECK-NEXT: retsp 2
declare void @f2()
define i32 @f3(i32 %i) nounwind {
entry:
@@ -52,6 +59,7 @@ entry:
}
+; FP + large frame: spill FP+SR = entsp 2 + 100000
; CHECKFP-LABEL: f4
; CHECKFP: extsp 65535
; CHECKFP-NEXT: .Ltmp{{[0-9]+}}
@@ -71,23 +79,32 @@ entry:
; CHECKFP-NEXT: ldaw sp, sp[34467]
; CHECKFP-NEXT: retsp 0
;
+; !FP + large frame: spill SR+SR = entsp 2 + 100000
; CHECK-LABEL: f4
; CHECK: extsp 65535
; CHECK-NEXT: .Ltmp{{[0-9]+}}
; CHECK-NEXT: .cfi_def_cfa_offset 262140
-; CHECK-NEXT: extsp 34465
+; CHECK-NEXT: extsp 34467
; CHECK-NEXT: .Ltmp{{[0-9]+}}
-; CHECK-NEXT: .cfi_def_cfa_offset 400000
+; CHECK-NEXT: .cfi_def_cfa_offset 400008
; CHECK-NEXT: ldaw sp, sp[65535]
-; CHECK-NEXT: ldaw sp, sp[34465]
+; CHECK-NEXT: ldaw sp, sp[34467]
; CHECK-NEXT: retsp 0
define void @f4() {
entry:
- %0 = alloca [100000 x i32], align 4
+ %0 = alloca [100000 x i32]
ret void
}
+; FP + large frame: spill FP+SR+R4+LR = entsp 3 + 200000 + extsp 1
+; CHECKFP: .section .cp.rodata.cst4,"aMc",@progbits,4
+; CHECKFP-NEXT: .align 4
+; CHECKFP-NEXT: .LCPI[[CNST0:[0-9_]+]]:
+; CHECKFP-NEXT: .long 200002
+; CHECKFP-NEXT: .LCPI[[CNST1:[0-9_]+]]:
+; CHECKFP-NEXT: .long 200001
+; CHECKFP-NEXT: .text
; CHECKFP-LABEL: f6
; CHECKFP: entsp 65535
; CHECKFP-NEXT: .Ltmp{{[0-9]+}}
@@ -100,26 +117,47 @@ entry:
; CHECKFP-NEXT: extsp 65535
; CHECKFP-NEXT: .Ltmp{{[0-9]+}}
; CHECKFP-NEXT: .cfi_def_cfa_offset 786420
-; CHECKFP-NEXT: extsp 3396
+; CHECKFP-NEXT: extsp 3398
; CHECKFP-NEXT: .Ltmp{{[0-9]+}}
-; CHECKFP-NEXT: .cfi_def_cfa_offset 800004
+; CHECKFP-NEXT: .cfi_def_cfa_offset 800012
; CHECKFP-NEXT: stw r10, sp[1]
; CHECKFP-NEXT: .Ltmp{{[0-9]+}}
-; CHECKFP-NEXT: .cfi_offset 10, -800000
+; CHECKFP-NEXT: .cfi_offset 10, -800008
; CHECKFP-NEXT: ldaw r10, sp[0]
; CHECKFP-NEXT: .Ltmp{{[0-9]+}}
; CHECKFP-NEXT: .cfi_def_cfa_register 10
+; CHECKFP-NEXT: ldw r1, cp[.LCPI[[CNST0]]]
+; CHECKFP-NEXT: stw [[REG:r[4-9]+]], r10[r1]
+; CHECKFP-NEXT: .Ltmp{{[0-9]+}}
+; CHECKFP-NEXT: .cfi_offset 4, -4
+; CHECKFP-NEXT: mov [[REG]], r0
; CHECKFP-NEXT: extsp 1
; CHECKFP-NEXT: ldaw r0, r10[2]
; CHECKFP-NEXT: bl f5
; CHECKFP-NEXT: ldaw sp, sp[1]
+; CHECKFP-NEXT: ldw r1, cp[.LCPI3_1]
+; CHECKFP-NEXT: ldaw r0, r10[r1]
+; CHECKFP-NEXT: extsp 1
+; CHECKFP-NEXT: bl f5
+; CHECKFP-NEXT: ldaw sp, sp[1]
+; CHECKFP-NEXT: mov r0, [[REG]]
+; CHECKFP-NEXT: ldw r1, cp[.LCPI[[CNST0]]]
+; CHECKFP-NEXT: ldw [[REG]], r10[r1]
; CHECKFP-NEXT: set sp, r10
; CHECKFP-NEXT: ldw r10, sp[1]
; CHECKFP-NEXT: ldaw sp, sp[65535]
; CHECKFP-NEXT: ldaw sp, sp[65535]
; CHECKFP-NEXT: ldaw sp, sp[65535]
-; CHECKFP-NEXT: retsp 3396
+; CHECKFP-NEXT: retsp 3398
;
+; !FP + large frame: spill SR+SR+R4+LR = entsp 4 + 200000
+; CHECK: .section .cp.rodata.cst4,"aMc",@progbits,4
+; CHECK-NEXT: .align 4
+; CHECK-NEXT: .LCPI[[CNST0:[0-9_]+]]:
+; CHECK-NEXT: .long 200003
+; CHECK-NEXT: .LCPI[[CNST1:[0-9_]+]]:
+; CHECK-NEXT: .long 200002
+; CHECK-NEXT: .text
; CHECK-LABEL: f6
; CHECK: entsp 65535
; CHECK-NEXT: .Ltmp{{[0-9]+}}
@@ -132,20 +170,65 @@ entry:
; CHECK-NEXT: extsp 65535
; CHECK-NEXT: .Ltmp{{[0-9]+}}
; CHECK-NEXT: .cfi_def_cfa_offset 786420
-; CHECK-NEXT: extsp 3395
+; CHECK-NEXT: extsp 3399
; CHECK-NEXT: .Ltmp{{[0-9]+}}
-; CHECK-NEXT: .cfi_def_cfa_offset 800000
-; CHECK-NEXT: ldaw r0, sp[1]
+; CHECK-NEXT: .cfi_def_cfa_offset 800016
+; CHECK-NEXT: ldaw r1, sp[0]
+; CHECK-NEXT: ldw r2, cp[.LCPI[[CNST0]]]
+; CHECK-NEXT: stw [[REG:r[4-9]+]], r1[r2]
+; CHECK-NEXT: .Ltmp{{[0-9]+}}
+; CHECK-NEXT: .cfi_offset 4, -4
+; CHECK-NEXT: mov [[REG]], r0
+; CHECK-NEXT: ldaw r0, sp[3]
+; CHECK-NEXT: bl f5
+; CHECK-NEXT: ldaw r0, sp[0]
+; CHECK-NEXT: ldw r1, cp[.LCPI[[CNST1]]]
+; CHECK-NEXT: ldaw r0, r0[r1]
; CHECK-NEXT: bl f5
+; CHECK-NEXT: mov r0, [[REG]]
+; CHECK-NEXT: ldaw [[REG]], sp[0]
+; CHECK-NEXT: ldw r1, cp[.LCPI[[CNST0]]]
+; CHECK-NEXT: ldw [[REG]], [[REG]][r1]
; CHECK-NEXT: ldaw sp, sp[65535]
; CHECK-NEXT: ldaw sp, sp[65535]
; CHECK-NEXT: ldaw sp, sp[65535]
-; CHECK-NEXT: retsp 3395
+; CHECK-NEXT: retsp 3399
declare void @f5(i32*)
-define void @f6() {
+define i32 @f6(i32 %i) {
+entry:
+ %0 = alloca [200000 x i32]
+ %1 = getelementptr inbounds [200000 x i32]* %0, i32 0, i32 0
+ call void @f5(i32* %1)
+ %2 = getelementptr inbounds [200000 x i32]* %0, i32 0, i32 199999
+ call void @f5(i32* %2)
+ ret i32 %i
+}
+
+
+; FP + large frame: spill FP+SR+LR = entsp 2 + 32768 + extsp 1
+; CHECKFP-LABEL:f8
+; CHECKFP: entsp 32770
+; CHECKFP-NEXT: stw r10, sp[1]
+; CHECKFP-NEXT: ldaw r10, sp[0]
+; CHECKFP-NEXT: mkmsk r1, 15
+; CHECKFP-NEXT: ldaw r0, r10[r1]
+; CHECKFP-NEXT: extsp 1
+; CHECKFP-NEXT: bl f5
+; CHECKFP-NEXT: ldaw sp, sp[1]
+; CHECKFP-NEXT: set sp, r10
+; CHECKFP-NEXT: ldw r10, sp[1]
+; CHECKFP-NEXT: retsp 32770
+;
+; !FP + large frame: spill SR+SR+LR = entsp 3 + 32768
+; CHECK-LABEL:f8
+; CHECK: entsp 32771
+; CHECK-NEXT: ldaw r0, sp[32768]
+; CHECK-NEXT: bl f5
+; CHECK-NEXT: retsp 32771
+define void @f8() nounwind {
entry:
- %0 = alloca [199999 x i32], align 4
- %1 = getelementptr inbounds [199999 x i32]* %0, i32 0, i32 0
+ %0 = alloca [32768 x i32]
+ %1 = getelementptr inbounds [32768 x i32]* %0, i32 0, i32 32765
call void @f5(i32* %1)
ret void
}