blob: a08f8cbd702eb06eb6429ad0a74e548e21abeb26 [file] [log] [blame]
Tim Northovere3d42362013-02-01 11:40:47 +00001; RUN: llc -verify-machineinstrs < %s -mtriple=aarch64-none-linux-gnu | FileCheck %s
Tim Northover71d04222014-05-22 07:40:55 +00002; RUN: llc -verify-machineinstrs < %s -mtriple=arm64-none-linux-gnu -arm64-load-store-opt=0 | FileCheck %s
Tim Northovere0e3aef2013-01-31 12:12:40 +00003
4declare void @callee_stack0()
5declare void @callee_stack8([8 x i32], i64)
6declare void @callee_stack16([8 x i32], i64, i64)
7
8define void @caller_to0_from0() nounwind {
Stephen Lind24ab202013-07-14 06:24:09 +00009; CHECK-LABEL: caller_to0_from0:
Tim Northovere0e3aef2013-01-31 12:12:40 +000010; CHECK-NEXT: // BB
11 tail call void @callee_stack0()
12 ret void
13; CHECK-NEXT: b callee_stack0
14}
15
16define void @caller_to0_from8([8 x i32], i64) nounwind{
Stephen Lind24ab202013-07-14 06:24:09 +000017; CHECK-LABEL: caller_to0_from8:
Tim Northovere0e3aef2013-01-31 12:12:40 +000018; CHECK-NEXT: // BB
19
20 tail call void @callee_stack0()
21 ret void
22; CHECK-NEXT: b callee_stack0
23}
24
25define void @caller_to8_from0() {
Stephen Lind24ab202013-07-14 06:24:09 +000026; CHECK-LABEL: caller_to8_from0:
Tim Northovere0e3aef2013-01-31 12:12:40 +000027
28; Caller isn't going to clean up any extra stack we allocate, so it
29; can't be a tail call.
30 tail call void @callee_stack8([8 x i32] undef, i64 42)
31 ret void
32; CHECK: bl callee_stack8
33}
34
35define void @caller_to8_from8([8 x i32], i64 %a) {
Stephen Lind24ab202013-07-14 06:24:09 +000036; CHECK-LABEL: caller_to8_from8:
Tim Northovere0e3aef2013-01-31 12:12:40 +000037; CHECK-NOT: sub sp, sp,
38
39; This should reuse our stack area for the 42
40 tail call void @callee_stack8([8 x i32] undef, i64 42)
41 ret void
42; CHECK: str {{x[0-9]+}}, [sp]
43; CHECK-NEXT: b callee_stack8
44}
45
46define void @caller_to16_from8([8 x i32], i64 %a) {
Stephen Lind24ab202013-07-14 06:24:09 +000047; CHECK-LABEL: caller_to16_from8:
Tim Northovere0e3aef2013-01-31 12:12:40 +000048
49; Shouldn't be a tail call: we can't use SP+8 because our caller might
50; have something there. This may sound obvious but implementation does
51; some funky aligning.
52 tail call void @callee_stack16([8 x i32] undef, i64 undef, i64 undef)
53; CHECK: bl callee_stack16
54 ret void
55}
56
57define void @caller_to8_from24([8 x i32], i64 %a, i64 %b, i64 %c) {
Stephen Lind24ab202013-07-14 06:24:09 +000058; CHECK-LABEL: caller_to8_from24:
Tim Northovere0e3aef2013-01-31 12:12:40 +000059; CHECK-NOT: sub sp, sp
60
61; Reuse our area, putting "42" at incoming sp
62 tail call void @callee_stack8([8 x i32] undef, i64 42)
63 ret void
64; CHECK: str {{x[0-9]+}}, [sp]
65; CHECK-NEXT: b callee_stack8
66}
67
68define void @caller_to16_from16([8 x i32], i64 %a, i64 %b) {
Stephen Lind24ab202013-07-14 06:24:09 +000069; CHECK-LABEL: caller_to16_from16:
Tim Northovere0e3aef2013-01-31 12:12:40 +000070; CHECK-NOT: sub sp, sp,
71
72; Here we want to make sure that both loads happen before the stores:
73; otherwise either %a or %b will be wrongly clobbered.
74 tail call void @callee_stack16([8 x i32] undef, i64 %b, i64 %a)
75 ret void
76
Tim Northover71d04222014-05-22 07:40:55 +000077; CHECK: ldr [[VAL0:x[0-9]+]],
78; CHECK: ldr [[VAL1:x[0-9]+]],
79; CHECK: str [[VAL1]],
80; CHECK: str [[VAL0]],
Tim Northovere0e3aef2013-01-31 12:12:40 +000081
82; CHECK-NOT: add sp, sp,
83; CHECK: b callee_stack16
84}
85
86@func = global void(i32)* null
87
88define void @indirect_tail() {
Stephen Lind24ab202013-07-14 06:24:09 +000089; CHECK-LABEL: indirect_tail:
Tim Northovere0e3aef2013-01-31 12:12:40 +000090; CHECK-NOT: sub sp, sp
91
92 %fptr = load void(i32)** @func
93 tail call void %fptr(i32 42)
94 ret void
Tim Northover71d04222014-05-22 07:40:55 +000095; CHECK: ldr [[FPTR:x[1-9]+]], [{{x[0-9]+}}, {{#?}}:lo12:func]
96; CHECK: movz w0, #{{42|0x2a}}
Tim Northovere0e3aef2013-01-31 12:12:40 +000097; CHECK: br [[FPTR]]
Tim Northoverb65f6b02013-05-29 19:32:06 +000098}