1; RUN: llc < %s | FileCheck %s
2
3target datalayout = "e-p:16:16:16-i8:8:8-i16:16:16-i32:16:32-n8:16-a0:16:16"
4target triple = "msp430---elf"
5
6define void @test() #0 {
7entry:
8; CHECK: test:
9
10; CHECK: mov #1, r12
11; CHECK: call #f_i16
12  call void @f_i16(i16 1)
13
14; CHECK: mov #772, r12
15; CHECK: mov #258, r13
16; CHECK: call #f_i32
17  call void @f_i32(i32 16909060)
18
19; CHECK: mov #1800, r12
20; CHECK: mov #1286, r13
21; CHECK: mov #772, r14
22; CHECK: mov #258, r15
23; CHECK: call #f_i64
24  call void @f_i64(i64 72623859790382856)
25
26; CHECK: mov #772, r12
27; CHECK: mov #258, r13
28; CHECK: mov #1800, r14
29; CHECK: mov #1286, r15
30; CHECK: call #f_i32_i32
31  call void @f_i32_i32(i32 16909060, i32 84281096)
32
33; CHECK: mov #1, r12
34; CHECK: mov #772, r13
35; CHECK: mov #258, r14
36; CHECK: mov #2, r15
37; CHECK: call #f_i16_i32_i16
38  call void @f_i16_i32_i16(i16 1, i32 16909060, i16 2)
39
40; CHECK: mov #1286, 0(r1)
41; CHECK: mov #1, r12
42; CHECK: mov #772, r13
43; CHECK: mov #258, r14
44; CHECK: mov #1800, r15
45; CHECK: call #f_i16_i32_i32
46  call void @f_i16_i32_i32(i16 1, i32 16909060, i32 84281096)
47
48; CHECK: mov #258, 6(r1)
49; CHECK: mov #772, 4(r1)
50; CHECK: mov #1286, 2(r1)
51; CHECK: mov #1800, 0(r1)
52; CHECK: mov #1, r12
53; CHECK: mov #2, r13
54; CHECK: call #f_i16_i64_i16
55  call void @f_i16_i64_i16(i16 1, i64 72623859790382856, i16 2)
56
57; Check that r15 is not used and the last i32 argument passed through the stack.
58; CHECK: mov	#258, 10(r1)
59; CHECK: mov	#772, 8(r1)
60; CHECK: mov	#258, 6(r1)
61; CHECK: mov	#772, 4(r1)
62; CHECK: mov	#1286, 2(r1)
63; CHECK: mov	#1800, 0(r1)
64; CHECK: mov	#1, r12
65; CHECK: mov	#772, r13
66; CHECK: mov	#258, r14
67  call void @f_i16_i64_i32_i32(i16 1, i64 72623859790382856, i32 16909060, i32 16909060)
68
69; CHECK: mov	#258, 6(r1)
70; CHECK: mov	#772, 4(r1)
71; CHECK: mov	#1286, 2(r1)
72; CHECK: mov	#1800, 0(r1)
73; CHECK: mov	#1800, r12
74; CHECK: mov	#1286, r13
75; CHECK: mov	#772, r14
76; CHECK: mov	#258, r15
77; CHECK: call	#f_i64_i64
78  call void @f_i64_i64(i64 72623859790382856, i64 72623859790382856)
79
80  ret void
81}
82
83@g_i16 = common global i16 0, align 2
84@g_i32 = common global i32 0, align 2
85@g_i64 = common global i64 0, align 2
86
87define void @f_i16(i16 %a) #0 {
88; CHECK: f_i16:
89; CHECK: mov r12, &g_i16
90  store volatile i16 %a, i16* @g_i16, align 2
91  ret void
92}
93
94define void @f_i32(i32 %a) #0 {
95; CHECK: f_i32:
96; CHECK: mov r13, &g_i32+2
97; CHECK: mov r12, &g_i32
98  store volatile i32 %a, i32* @g_i32, align 2
99  ret void
100}
101
102define void @f_i64(i64 %a) #0 {
103; CHECK: f_i64:
104; CHECK: mov r15, &g_i64+6
105; CHECK: mov r14, &g_i64+4
106; CHECK: mov r13, &g_i64+2
107; CHECK: mov r12, &g_i64
108  store volatile i64 %a, i64* @g_i64, align 2
109  ret void
110}
111
112define void @f_i32_i32(i32 %a, i32 %b) #0 {
113; CHECK: f_i32_i32:
114; CHECK: mov r13, &g_i32+2
115; CHECK: mov r12, &g_i32
116  store volatile i32 %a, i32* @g_i32, align 2
117; CHECK: mov r15, &g_i32+2
118; CHECK: mov r14, &g_i32
119  store volatile i32 %b, i32* @g_i32, align 2
120  ret void
121}
122
123define void @f_i16_i32_i32(i16 %a, i32 %b, i32 %c) #0 {
124; CHECK: f_i16_i32_i32:
125; CHECK: mov r12, &g_i16
126  store volatile i16 %a, i16* @g_i16, align 2
127; CHECK: mov r14, &g_i32+2
128; CHECK: mov r13, &g_i32
129  store volatile i32 %b, i32* @g_i32, align 2
130; CHECK: mov r15, &g_i32
131; CHECK: mov 4(r4), &g_i32+2
132  store volatile i32 %c, i32* @g_i32, align 2
133  ret void
134}
135
136define void @f_i16_i32_i16(i16 %a, i32 %b, i16 %c) #0 {
137; CHECK: f_i16_i32_i16:
138; CHECK: mov r12, &g_i16
139  store volatile i16 %a, i16* @g_i16, align 2
140; CHECK: mov r14, &g_i32+2
141; CHECK: mov r13, &g_i32
142  store volatile i32 %b, i32* @g_i32, align 2
143; CHECK: mov r15, &g_i16
144  store volatile i16 %c, i16* @g_i16, align 2
145  ret void
146}
147
148define void @f_i16_i64_i16(i16 %a, i64 %b, i16 %c) #0 {
149; CHECK: f_i16_i64_i16:
150; CHECK: mov r12, &g_i16
151  store volatile i16 %a, i16* @g_i16, align 2
152;CHECK: mov 10(r4), &g_i64+6
153;CHECK: mov 8(r4), &g_i64+4
154;CHECK: mov 6(r4), &g_i64+2
155;CHECK: mov 4(r4), &g_i64
156  store volatile i64 %b, i64* @g_i64, align 2
157;CHECK: mov r13, &g_i16
158  store volatile i16 %c, i16* @g_i16, align 2
159  ret void
160}
161
162define void @f_i64_i64(i64 %a, i64 %b) #0 {
163; CHECK: f_i64_i64:
164; CHECK: mov	r15, &g_i64+6
165; CHECK: mov	r14, &g_i64+4
166; CHECK: mov	r13, &g_i64+2
167; CHECK: mov	r12, &g_i64
168  store volatile i64 %a, i64* @g_i64, align 2
169; CHECK-DAG: mov	10(r4), &g_i64+6
170; CHECK-DAG: mov	8(r4), &g_i64+4
171; CHECK-DAG: mov	6(r4), &g_i64+2
172; CHECK-DAG: mov	4(r4), &g_i64
173  store volatile i64 %b, i64* @g_i64, align 2
174  ret void
175}
176
177define void @f_i16_i64_i32_i32(i16 %a, i64 %b, i32 %c, i32 %d) #0 {
178; CHECK-LABEL: f_i16_i64_i32_i32:
179; CHECK: mov	r12, &g_i16
180  store volatile i16 %a, i16* @g_i16, align 2
181; CHECK: mov	10(r4), &g_i64+6
182; CHECK: mov	8(r4), &g_i64+4
183; CHECK: mov	6(r4), &g_i64+2
184; CHECK: mov	4(r4), &g_i64
185  store volatile i64 %b, i64* @g_i64, align 2
186; CHECK: mov	r14, &g_i32+2
187; CHECK: mov	r13, &g_i32
188  store volatile i32 %c, i32* @g_i32, align 2
189; CHECK: mov	14(r4), &g_i32+2
190; CHECK: mov	12(r4), &g_i32
191  store volatile i32 %d, i32* @g_i32, align 2
192  ret void
193}
194; MSP430 EABI p. 6.3
195; For helper functions which take two long long arguments
196; the first argument is passed in R8::R11 and the second argument
197; is in R12::R15.
198
199@g_i64_2 = common global i64 0, align 2
200
201define i64 @helper_call_i64() #0 {
202  %1 = load i64, i64* @g_i64, align 2
203  %2 = load i64, i64* @g_i64_2, align 2
204; CHECK-LABEL: helper_call_i64:
205; CHECK: mov	&g_i64, r8
206; CHECK: mov	&g_i64+2, r9
207; CHECK: mov	&g_i64+4, r10
208; CHECK: mov	&g_i64+6, r11
209; CHECK: mov	&g_i64_2, r12
210; CHECK: mov	&g_i64_2+2, r13
211; CHECK: mov	&g_i64_2+4, r14
212; CHECK: mov	&g_i64_2+6, r15
213; CHECK: call	#__mspabi_divlli
214  %3 = sdiv i64 %1, %2
215  ret i64 %3
216}
217
218attributes #0 = { nounwind "less-precise-fpmad"="false" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf"="true" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "unsafe-fp-math"="false" "use-soft-float"="false" }
219