xref: /llvm-project/llvm/test/CodeGen/AVR/directmem.ll (revision 9ef1d37ffb5f56a9b949a6307bbb16c2ea0130e3)
1; RUN: llc -mattr=sram,addsubiw < %s -mtriple=avr | FileCheck %s
2; RUN: llc -mattr=sram,avrtiny < %s -mtriple=avr | FileCheck %s --check-prefix=CHECK-TINY
3
4@char = common global i8 0
5@char.array = common global [3 x i8] zeroinitializer
6@char.static = internal global i8 0
7
8@int = common global i16 0
9@int.array = common global [3 x i16] zeroinitializer
10@int.static = internal global i16 0
11
12@long = common global i32 0
13@long.array = common global [3 x i32] zeroinitializer
14@long.static = internal global i32 0
15
16@longlong = common global i64 0
17@longlong.array = common global [3 x i64] zeroinitializer
18@longlong.static = internal global i64 0
19
20define void @global8_store() {
21; CHECK-LABEL: global8_store:
22; CHECK: ldi [[REG:r[0-9]+]], 6
23; CHECK: sts char, [[REG]]
24;
25; CHECK-TINY-LABEL: global8_store:
26; CHECK-TINY: ldi [[REG:r[0-9]+]], 6
27; CHECK-TINY: sts char, [[REG]]
28  store i8 6, ptr @char
29  ret void
30}
31
32define i8 @global8_load() {
33; CHECK-LABEL: global8_load:
34; CHECK: lds r24, char
35;
36; CHECK-TINY-LABEL: global8_load:
37; CHECK-TINY: lds r24, char
38  %result = load i8, ptr @char
39  ret i8 %result
40}
41
42define void @array8_store() {
43; CHECK-LABEL: array8_store:
44; CHECK: ldi [[REG1:r[0-9]+]], 3
45; CHECK: sts char.array+2, [[REG1]]
46; CHECK: ldi [[REG3:r[0-9]+]], 1
47; CHECK: ldi [[REG2:r[0-9]+]], 2
48; CHECK: sts char.array+1, [[REG2]]
49; CHECK: sts char.array, [[REG3]]
50;
51; CHECK-TINY-LABEL: array8_store:
52; CHECK-TINY: ldi [[REG1:r[0-9]+]], 3
53; CHECK-TINY: sts char.array+2, [[REG1]]
54  store i8 1, ptr @char.array
55  store i8 2, ptr getelementptr inbounds ([3 x i8], ptr @char.array, i32 0, i64 1)
56  store i8 3, ptr getelementptr inbounds ([3 x i8], ptr @char.array, i32 0, i64 2)
57  ret void
58}
59
60define i8 @array8_load() {
61; CHECK-LABEL: array8_load:
62; CHECK: lds r24, char.array+2
63;
64; CHECK-TINY-LABEL: array8_load:
65; CHECK-TINY: lds r24, char.array+2
66  %result = load i8, ptr getelementptr inbounds ([3 x i8], ptr @char.array, i32 0, i64 2)
67  ret i8 %result
68}
69
70define i8 @static8_inc() {
71; CHECK-LABEL: static8_inc:
72; CHECK: lds r24, char.static
73; CHECK: inc r24
74; CHECK: sts char.static, r24
75;
76; CHECK-TINY-LABEL: static8_inc:
77; CHECK-TINY: lds r24, char.static
78; CHECK-TINY: inc r24
79; CHECK-TINY: sts char.static, r24
80  %1 = load i8, ptr @char.static
81  %inc = add nsw i8 %1, 1
82  store i8 %inc, ptr @char.static
83  ret i8 %inc
84}
85
86define void @global16_store() {
87; CHECK-LABEL: global16_store:
88; CHECK: ldi [[REG1:r[0-9]+]], 187
89; CHECK: ldi [[REG2:r[0-9]+]], 170
90; CHECK: sts int+1, [[REG2]]
91; CHECK: sts int, [[REG1]]
92  store i16 43707, ptr @int
93  ret void
94}
95
96define i16 @global16_load() {
97; CHECK-LABEL: global16_load:
98; CHECK: lds r24, int
99; CHECK: lds r25, int+1
100  %result = load i16, ptr @int
101  ret i16 %result
102}
103
104define void @array16_store() {
105; CHECK-LABEL: array16_store:
106
107; CHECK: ldi [[REG1:r[0-9]+]], 221
108; CHECK: ldi [[REG2:r[0-9]+]], 170
109; CHECK: sts int.array+5, [[REG2]]
110; CHECK: sts int.array+4, [[REG1]]
111
112; CHECK: ldi [[REG1:r[0-9]+]], 204
113; CHECK: ldi [[REG2:r[0-9]+]], 170
114; CHECK: sts int.array+3, [[REG2]]
115; CHECK: sts int.array+2, [[REG1]]
116
117; CHECK: ldi [[REG1:r[0-9]+]], 187
118; CHECK: ldi [[REG2:r[0-9]+]], 170
119; CHECK: sts int.array+1, [[REG2]]
120; CHECK: sts int.array, [[REG1]]
121  store i16 43707, ptr @int.array
122  store i16 43724, ptr getelementptr inbounds ([3 x i16], ptr @int.array, i32 0, i64 1)
123  store i16 43741, ptr getelementptr inbounds ([3 x i16], ptr @int.array, i32 0, i64 2)
124  ret void
125}
126
127define i16 @array16_load() {
128; CHECK-LABEL: array16_load:
129; CHECK: lds r24, int.array+4
130; CHECK: lds r25, int.array+5
131  %result = load i16, ptr getelementptr inbounds ([3 x i16], ptr @int.array, i32 0, i64 2)
132  ret i16 %result
133}
134
135define i16 @static16_inc() {
136; CHECK-LABEL: static16_inc:
137; CHECK: lds r24, int.static
138; CHECK: lds r25, int.static+1
139; CHECK: adiw r24, 1
140; CHECK: sts int.static+1, r25
141; CHECK: sts int.static, r24
142  %1 = load i16, ptr @int.static
143  %inc = add nsw i16 %1, 1
144  store i16 %inc, ptr @int.static
145  ret i16 %inc
146}
147
148define void @global32_store() {
149; CHECK-LABEL: global32_store:
150; CHECK: ldi [[REG1:r[0-9]+]], 187
151; CHECK: ldi [[REG2:r[0-9]+]], 170
152; CHECK: sts long+3, [[REG2]]
153; CHECK: sts long+2, [[REG1]]
154; CHECK: ldi [[REG1:r[0-9]+]], 221
155; CHECK: ldi [[REG2:r[0-9]+]], 204
156; CHECK: sts long+1, [[REG2]]
157; CHECK: sts long, [[REG1]]
158  store i32 2864434397, ptr @long
159  ret void
160}
161
162define i32 @global32_load() {
163; CHECK-LABEL: global32_load:
164; CHECK: lds r22, long
165; CHECK: lds r23, long+1
166; CHECK: lds r24, long+2
167; CHECK: lds r25, long+3
168  %result = load i32, ptr @long
169  ret i32 %result
170}
171
172define void @array32_store() {
173; CHECK-LABEL: array32_store:
174
175; CHECK: ldi [[REG1:r[0-9]+]], 170
176; CHECK: ldi [[REG2:r[0-9]+]], 153
177; CHECK: sts long.array+11, [[REG2]]
178; CHECK: sts long.array+10, [[REG1]]
179
180; CHECK: ldi [[REG1:r[0-9]+]], 204
181; CHECK: ldi [[REG2:r[0-9]+]], 187
182; CHECK: sts long.array+9, [[REG2]]
183; CHECK: sts long.array+8, [[REG1]]
184
185; CHECK: ldi [[REG1:r[0-9]+]], 102
186; CHECK: ldi [[REG2:r[0-9]+]], 85
187; CHECK: sts long.array+7, [[REG2]]
188; CHECK: sts long.array+6, [[REG1]]
189
190; CHECK: ldi [[REG1:r[0-9]+]], 136
191; CHECK: ldi [[REG2:r[0-9]+]], 119
192; CHECK: sts long.array+5, [[REG2]]
193; CHECK: sts long.array+4, [[REG1]]
194
195; CHECK: ldi [[REG1:r[0-9]+]], 27
196; CHECK: ldi [[REG2:r[0-9]+]], 172
197; CHECK: sts long.array+3, [[REG2]]
198; CHECK: sts long.array+2, [[REG1]]
199
200; CHECK: ldi [[REG1:r[0-9]+]], 68
201; CHECK: ldi [[REG2:r[0-9]+]], 13
202; CHECK: sts long.array+1, [[REG2]]
203; CHECK: sts long.array, [[REG1]]
204  store i32 2887454020, ptr @long.array
205  store i32 1432778632, ptr getelementptr inbounds ([3 x i32], ptr @long.array, i32 0, i64 1)
206  store i32 2578103244, ptr getelementptr inbounds ([3 x i32], ptr @long.array, i32 0, i64 2)
207  ret void
208}
209
210define i32 @array32_load() {
211; CHECK-LABEL: array32_load:
212; CHECK: lds r22, long.array+8
213; CHECK: lds r23, long.array+9
214; CHECK: lds r24, long.array+10
215; CHECK: lds r25, long.array+11
216  %result = load i32, ptr getelementptr inbounds ([3 x i32], ptr @long.array, i32 0, i64 2)
217  ret i32 %result
218}
219
220define i32 @static32_inc() {
221; CHECK-LABEL: static32_inc:
222; CHECK: lds r22, long.static
223; CHECK: lds r23, long.static+1
224; CHECK: lds r24, long.static+2
225; CHECK: lds r25, long.static+3
226; CHECK: subi r22, 255
227; CHECK: sbci r23, 255
228; CHECK: sbci r24, 255
229; CHECK: sbci r25, 255
230; CHECK-DAG: sts long.static+3, r25
231; CHECK-DAG: sts long.static+2, r24
232; CHECK-DAG: sts long.static+1, r23
233; CHECK-DAG: sts long.static, r22
234  %1 = load i32, ptr @long.static
235  %inc = add nsw i32 %1, 1
236  store i32 %inc, ptr @long.static
237  ret i32 %inc
238}
239
240define void @global64_store() {
241; CHECK-LABEL: global64_store:
242; CHECK: ldi [[REG1:r[0-9]+]], 34
243; CHECK: ldi [[REG2:r[0-9]+]], 17
244; CHECK: sts longlong+7, [[REG2]]
245; CHECK: sts longlong+6, [[REG1]]
246; CHECK: ldi [[REG1:r[0-9]+]], 68
247; CHECK: ldi [[REG2:r[0-9]+]], 51
248; CHECK: sts longlong+5, [[REG2]]
249; CHECK: sts longlong+4, [[REG1]]
250; CHECK: ldi [[REG1:r[0-9]+]], 102
251; CHECK: ldi [[REG2:r[0-9]+]], 85
252; CHECK: sts longlong+3, [[REG2]]
253; CHECK: sts longlong+2, [[REG1]]
254; CHECK: ldi [[REG1:r[0-9]+]], 136
255; CHECK: ldi [[REG2:r[0-9]+]], 119
256; CHECK: sts longlong+1, [[REG2]]
257; CHECK: sts longlong, [[REG1]]
258  store i64 1234605616436508552, ptr @longlong
259  ret void
260}
261
262define i64 @global64_load() {
263; CHECK-LABEL: global64_load:
264; CHECK: lds r18, longlong
265; CHECK: lds r19, longlong+1
266; CHECK: lds r20, longlong+2
267; CHECK: lds r21, longlong+3
268; CHECK: lds r22, longlong+4
269; CHECK: lds r23, longlong+5
270; CHECK: lds r24, longlong+6
271; CHECK: lds r25, longlong+7
272  %result = load i64, ptr @longlong
273  ret i64 %result
274}
275
276define void @array64_store() {
277; CHECK-LABEL: array64_store:
278; CHECK: ldi [[REG1:r[0-9]+]], 34
279; CHECK: ldi [[REG2:r[0-9]+]], 17
280; CHECK: sts longlong.array+7, [[REG2]]
281; CHECK: sts longlong.array+6, [[REG1]]
282; CHECK: ldi [[REG1:r[0-9]+]], 68
283; CHECK: ldi [[REG2:r[0-9]+]], 51
284; CHECK: sts longlong.array+5, [[REG2]]
285; CHECK: sts longlong.array+4, [[REG1]]
286; CHECK: ldi [[REG1:r[0-9]+]], 102
287; CHECK: ldi [[REG2:r[0-9]+]], 85
288; CHECK: sts longlong.array+3, [[REG2]]
289; CHECK: sts longlong.array+2, [[REG1]]
290; CHECK: ldi [[REG1:r[0-9]+]], 136
291; CHECK: ldi [[REG2:r[0-9]+]], 119
292; CHECK: sts longlong.array+1, [[REG2]]
293; CHECK: sts longlong.array, [[REG1]]
294  store i64 1234605616436508552, ptr @longlong.array
295  store i64 81985529216486895, ptr getelementptr inbounds ([3 x i64], ptr @longlong.array, i64 0, i64 1)
296  store i64 1836475854449306472, ptr getelementptr inbounds ([3 x i64], ptr @longlong.array, i64 0, i64 2)
297  ret void
298}
299
300define i64 @array64_load() {
301; CHECK-LABEL: array64_load:
302; CHECK: lds r18, longlong.array+16
303; CHECK: lds r19, longlong.array+17
304; CHECK: lds r20, longlong.array+18
305; CHECK: lds r21, longlong.array+19
306; CHECK: lds r22, longlong.array+20
307; CHECK: lds r23, longlong.array+21
308; CHECK: lds r24, longlong.array+22
309; CHECK: lds r25, longlong.array+23
310  %result = load i64, ptr getelementptr inbounds ([3 x i64], ptr @longlong.array, i64 0, i64 2)
311  ret i64 %result
312}
313
314define i64 @static64_inc() {
315; CHECK-LABEL: static64_inc:
316; CHECK: lds r18, longlong.static
317; CHECK: lds r19, longlong.static+1
318; CHECK: lds r20, longlong.static+2
319; CHECK: lds r21, longlong.static+3
320; CHECK: lds r22, longlong.static+4
321; CHECK: lds r23, longlong.static+5
322; CHECK: lds r24, longlong.static+6
323; CHECK: lds r25, longlong.static+7
324; CHECK: subi r18, 255
325; CHECK: sbci r19, 255
326; CHECK: sbci r20, 255
327; CHECK: sbci r21, 255
328; CHECK: sbci r22, 255
329; CHECK: sbci r23, 255
330; CHECK: sbci r24, 255
331; CHECK: sbci r25, 255
332; CHECK-DAG: sts longlong.static+7, r25
333; CHECK-DAG: sts longlong.static+6, r24
334; CHECK-DAG: sts longlong.static+5, r23
335; CHECK-DAG: sts longlong.static+4, r22
336; CHECK-DAG: sts longlong.static+3, r21
337; CHECK-DAG: sts longlong.static+2, r20
338; CHECK-DAG: sts longlong.static+1, r19
339; CHECK-DAG: sts longlong.static, r18
340  %1 = load i64, ptr @longlong.static
341  %inc = add nsw i64 %1, 1
342  store i64 %inc, ptr @longlong.static
343  ret i64 %inc
344}
345
346define i8 @constantaddr_read8() {
347; CHECK-LABEL: constantaddr_read8:
348; CHECK: lds r24, 1234
349  %1 = load i8, ptr inttoptr (i16 1234 to ptr)
350  ret i8 %1
351}
352
353define i16 @constantaddr_read16() {
354; CHECK-LABEL: constantaddr_read16:
355; CHECK: lds r24, 1234
356; CHECK: lds r25, 1235
357  %1 = load i16, ptr inttoptr (i16 1234 to ptr)
358  ret i16 %1
359}
360
361define void @constantaddr_write8() {
362; CHECK-LABEL: constantaddr_write8:
363; CHECK: sts 1234
364  store i8 22, ptr inttoptr (i16 1234 to ptr)
365  ret void
366}
367
368define void @constantaddr_write16() {
369; CHECK-LABEL: constantaddr_write16:
370; CHECK: sts 1235
371; CHECK: sts 1234
372  store i16 2222, ptr inttoptr (i16 1234 to ptr)
373  ret void
374}
375