1
; RUN: llc -verify-machineinstrs < %s -mtriple=aarch64-none-linux-gnu | FileCheck %s
3
@var1_32 = global i32 0
4
@var2_32 = global i32 0
6
@var1_64 = global i64 0
7
@var2_64 = global i64 0
9
define void @logical_32bit() minsize {
10
; CHECK-LABEL: logical_32bit:
11
%val1 = load i32, i32* @var1_32
12
%val2 = load i32, i32* @var2_32
14
; First check basic and/bic/or/orn/eor/eon patterns with no shift
15
%neg_val2 = xor i32 -1, %val2
17
%and_noshift = and i32 %val1, %val2
18
; CHECK: and {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}
19
store volatile i32 %and_noshift, i32* @var1_32
20
%bic_noshift = and i32 %neg_val2, %val1
21
; CHECK: bic {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}
22
store volatile i32 %bic_noshift, i32* @var1_32
24
%or_noshift = or i32 %val1, %val2
25
; CHECK: orr {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}
26
store volatile i32 %or_noshift, i32* @var1_32
27
%orn_noshift = or i32 %neg_val2, %val1
28
; CHECK: orn {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}
29
store volatile i32 %orn_noshift, i32* @var1_32
31
%xor_noshift = xor i32 %val1, %val2
32
; CHECK: eor {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}
33
store volatile i32 %xor_noshift, i32* @var1_32
34
%xorn_noshift = xor i32 %neg_val2, %val1
35
; CHECK: eon {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}
36
store volatile i32 %xorn_noshift, i32* @var1_32
38
; Check the maximum shift on each
39
%operand_lsl31 = shl i32 %val2, 31
40
%neg_operand_lsl31 = xor i32 -1, %operand_lsl31
42
%and_lsl31 = and i32 %val1, %operand_lsl31
43
; CHECK: and {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, lsl #31
44
store volatile i32 %and_lsl31, i32* @var1_32
45
%bic_lsl31 = and i32 %val1, %neg_operand_lsl31
46
; CHECK: bic {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, lsl #31
47
store volatile i32 %bic_lsl31, i32* @var1_32
49
%or_lsl31 = or i32 %val1, %operand_lsl31
50
; CHECK: orr {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, lsl #31
51
store volatile i32 %or_lsl31, i32* @var1_32
52
%orn_lsl31 = or i32 %val1, %neg_operand_lsl31
53
; CHECK: orn {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, lsl #31
54
store volatile i32 %orn_lsl31, i32* @var1_32
56
%xor_lsl31 = xor i32 %val1, %operand_lsl31
57
; CHECK: eor {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, lsl #31
58
store volatile i32 %xor_lsl31, i32* @var1_32
59
%xorn_lsl31 = xor i32 %val1, %neg_operand_lsl31
60
; CHECK: eon {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, lsl #31
61
store volatile i32 %xorn_lsl31, i32* @var1_32
63
; Check other shifts on a subset
64
%operand_asr10 = ashr i32 %val2, 10
65
%neg_operand_asr10 = xor i32 -1, %operand_asr10
67
%bic_asr10 = and i32 %val1, %neg_operand_asr10
68
; CHECK: bic {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, asr #10
69
store volatile i32 %bic_asr10, i32* @var1_32
70
%xor_asr10 = xor i32 %val1, %operand_asr10
71
; CHECK: eor {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, asr #10
72
store volatile i32 %xor_asr10, i32* @var1_32
74
%operand_lsr1 = lshr i32 %val2, 1
75
%neg_operand_lsr1 = xor i32 -1, %operand_lsr1
77
%orn_lsr1 = or i32 %val1, %neg_operand_lsr1
78
; CHECK: orn {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, lsr #1
79
store volatile i32 %orn_lsr1, i32* @var1_32
80
%xor_lsr1 = xor i32 %val1, %operand_lsr1
81
; CHECK: eor {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, lsr #1
82
store volatile i32 %xor_lsr1, i32* @var1_32
84
%operand_ror20_big = shl i32 %val2, 12
85
%operand_ror20_small = lshr i32 %val2, 20
86
%operand_ror20 = or i32 %operand_ror20_big, %operand_ror20_small
87
%neg_operand_ror20 = xor i32 -1, %operand_ror20
89
%xorn_ror20 = xor i32 %val1, %neg_operand_ror20
90
; CHECK: eon {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, ror #20
91
store volatile i32 %xorn_ror20, i32* @var1_32
92
%and_ror20 = and i32 %val1, %operand_ror20
93
; CHECK: and {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, ror #20
94
store volatile i32 %and_ror20, i32* @var1_32
99
define void @logical_64bit() minsize {
100
; CHECK-LABEL: logical_64bit:
101
%val1 = load i64, i64* @var1_64
102
%val2 = load i64, i64* @var2_64
104
; First check basic and/bic/or/orn/eor/eon patterns with no shift
105
%neg_val2 = xor i64 -1, %val2
107
%and_noshift = and i64 %val1, %val2
108
; CHECK: and {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}
109
store volatile i64 %and_noshift, i64* @var1_64
110
%bic_noshift = and i64 %neg_val2, %val1
111
; CHECK: bic {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}
112
store volatile i64 %bic_noshift, i64* @var1_64
114
%or_noshift = or i64 %val1, %val2
115
; CHECK: orr {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}
116
store volatile i64 %or_noshift, i64* @var1_64
117
%orn_noshift = or i64 %neg_val2, %val1
118
; CHECK: orn {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}
119
store volatile i64 %orn_noshift, i64* @var1_64
121
%xor_noshift = xor i64 %val1, %val2
122
; CHECK: eor {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}
123
store volatile i64 %xor_noshift, i64* @var1_64
124
%xorn_noshift = xor i64 %neg_val2, %val1
125
; CHECK: eon {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}
126
store volatile i64 %xorn_noshift, i64* @var1_64
128
; Check the maximum shift on each
129
%operand_lsl63 = shl i64 %val2, 63
130
%neg_operand_lsl63 = xor i64 -1, %operand_lsl63
132
%and_lsl63 = and i64 %val1, %operand_lsl63
133
; CHECK: and {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}, lsl #63
134
store volatile i64 %and_lsl63, i64* @var1_64
135
%bic_lsl63 = and i64 %val1, %neg_operand_lsl63
136
; CHECK: bic {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}, lsl #63
137
store volatile i64 %bic_lsl63, i64* @var1_64
139
%or_lsl63 = or i64 %val1, %operand_lsl63
140
; CHECK: orr {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}, lsl #63
141
store volatile i64 %or_lsl63, i64* @var1_64
142
%orn_lsl63 = or i64 %val1, %neg_operand_lsl63
143
; CHECK: orn {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}, lsl #63
144
store volatile i64 %orn_lsl63, i64* @var1_64
146
%xor_lsl63 = xor i64 %val1, %operand_lsl63
147
; CHECK: eor {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}, lsl #63
148
store volatile i64 %xor_lsl63, i64* @var1_64
149
%xorn_lsl63 = xor i64 %val1, %neg_operand_lsl63
150
; CHECK: eon {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}, lsl #63
151
store volatile i64 %xorn_lsl63, i64* @var1_64
153
; Check other shifts on a subset
154
%operand_asr10 = ashr i64 %val2, 10
155
%neg_operand_asr10 = xor i64 -1, %operand_asr10
157
%bic_asr10 = and i64 %val1, %neg_operand_asr10
158
; CHECK: bic {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}, asr #10
159
store volatile i64 %bic_asr10, i64* @var1_64
160
%xor_asr10 = xor i64 %val1, %operand_asr10
161
; CHECK: eor {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}, asr #10
162
store volatile i64 %xor_asr10, i64* @var1_64
164
%operand_lsr1 = lshr i64 %val2, 1
165
%neg_operand_lsr1 = xor i64 -1, %operand_lsr1
167
%orn_lsr1 = or i64 %val1, %neg_operand_lsr1
168
; CHECK: orn {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}, lsr #1
169
store volatile i64 %orn_lsr1, i64* @var1_64
170
%xor_lsr1 = xor i64 %val1, %operand_lsr1
171
; CHECK: eor {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}, lsr #1
172
store volatile i64 %xor_lsr1, i64* @var1_64
174
; Construct a rotate-right from a bunch of other logical
175
; operations. DAGCombiner should ensure we the ROTR during
177
%operand_ror20_big = shl i64 %val2, 44
178
%operand_ror20_small = lshr i64 %val2, 20
179
%operand_ror20 = or i64 %operand_ror20_big, %operand_ror20_small
180
%neg_operand_ror20 = xor i64 -1, %operand_ror20
182
%xorn_ror20 = xor i64 %val1, %neg_operand_ror20
183
; CHECK: eon {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}, ror #20
184
store volatile i64 %xorn_ror20, i64* @var1_64
185
%and_ror20 = and i64 %val1, %operand_ror20
186
; CHECK: and {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}, ror #20
187
store volatile i64 %and_ror20, i64* @var1_64
192
define void @flag_setting() {
193
; CHECK-LABEL: flag_setting:
194
%val1 = load i64, i64* @var1_64
195
%val2 = load i64, i64* @var2_64
197
; CHECK: tst {{x[0-9]+}}, {{x[0-9]+}}
199
%simple_and = and i64 %val1, %val2
200
%tst1 = icmp sgt i64 %simple_and, 0
201
br i1 %tst1, label %ret, label %test2
204
; CHECK: tst {{x[0-9]+}}, {{x[0-9]+}}, lsl #63
206
%shifted_op = shl i64 %val2, 63
207
%shifted_and = and i64 %val1, %shifted_op
208
%tst2 = icmp slt i64 %shifted_and, 0
209
br i1 %tst2, label %ret, label %test3
212
; CHECK: tst {{x[0-9]+}}, {{x[0-9]+}}, asr #12
214
%asr_op = ashr i64 %val2, 12
215
%asr_and = and i64 %asr_op, %val1
216
%tst3 = icmp sgt i64 %asr_and, 0
217
br i1 %tst3, label %ret, label %other_exit
220
store volatile i64 %val1, i64* @var1_64