1 // RUN: %clang_cc1 -triple arm64-none-linux-gnu -target-feature +neon \
2 // RUN: -disable-O0-optnone -emit-llvm -o - %s | opt -S -mem2reg | FileCheck %s
3 
4 #include <arm_neon.h>
5 
6 // CHECK-LABEL: define float @test_vdups_lane_f32(<2 x float> %a) #0 {
7 // CHECK:   [[VDUPS_LANE:%.*]] = extractelement <2 x float> %a, i32 1
8 // CHECK:   ret float [[VDUPS_LANE]]
test_vdups_lane_f32(float32x2_t a)9 float32_t test_vdups_lane_f32(float32x2_t a) {
10   return vdups_lane_f32(a, 1);
11 }
12 
13 
14 // CHECK-LABEL: define double @test_vdupd_lane_f64(<1 x double> %a) #0 {
15 // CHECK:   [[VDUPD_LANE:%.*]] = extractelement <1 x double> %a, i32 0
16 // CHECK:   ret double [[VDUPD_LANE]]
test_vdupd_lane_f64(float64x1_t a)17 float64_t test_vdupd_lane_f64(float64x1_t a) {
18   return vdupd_lane_f64(a, 0);
19 }
20 
21 
22 // CHECK-LABEL: define float @test_vdups_laneq_f32(<4 x float> %a) #1 {
23 // CHECK:   [[VGETQ_LANE:%.*]] = extractelement <4 x float> %a, i32 3
24 // CHECK:   ret float [[VGETQ_LANE]]
test_vdups_laneq_f32(float32x4_t a)25 float32_t test_vdups_laneq_f32(float32x4_t a) {
26   return vdups_laneq_f32(a, 3);
27 }
28 
29 
30 // CHECK-LABEL: define double @test_vdupd_laneq_f64(<2 x double> %a) #1 {
31 // CHECK:   [[VGETQ_LANE:%.*]] = extractelement <2 x double> %a, i32 1
32 // CHECK:   ret double [[VGETQ_LANE]]
test_vdupd_laneq_f64(float64x2_t a)33 float64_t test_vdupd_laneq_f64(float64x2_t a) {
34   return vdupd_laneq_f64(a, 1);
35 }
36 
37 
38 // CHECK-LABEL: define i8 @test_vdupb_lane_s8(<8 x i8> %a) #0 {
39 // CHECK:   [[VGET_LANE:%.*]] = extractelement <8 x i8> %a, i32 7
40 // CHECK:   ret i8 [[VGET_LANE]]
test_vdupb_lane_s8(int8x8_t a)41 int8_t test_vdupb_lane_s8(int8x8_t a) {
42   return vdupb_lane_s8(a, 7);
43 }
44 
45 
46 // CHECK-LABEL: define i16 @test_vduph_lane_s16(<4 x i16> %a) #0 {
47 // CHECK:   [[VGET_LANE:%.*]] = extractelement <4 x i16> %a, i32 3
48 // CHECK:   ret i16 [[VGET_LANE]]
test_vduph_lane_s16(int16x4_t a)49 int16_t test_vduph_lane_s16(int16x4_t a) {
50   return vduph_lane_s16(a, 3);
51 }
52 
53 
54 // CHECK-LABEL: define i32 @test_vdups_lane_s32(<2 x i32> %a) #0 {
55 // CHECK:   [[VGET_LANE:%.*]] = extractelement <2 x i32> %a, i32 1
56 // CHECK:   ret i32 [[VGET_LANE]]
test_vdups_lane_s32(int32x2_t a)57 int32_t test_vdups_lane_s32(int32x2_t a) {
58   return vdups_lane_s32(a, 1);
59 }
60 
61 
62 // CHECK-LABEL: define i64 @test_vdupd_lane_s64(<1 x i64> %a) #0 {
63 // CHECK:   [[VGET_LANE:%.*]] = extractelement <1 x i64> %a, i32 0
64 // CHECK:   ret i64 [[VGET_LANE]]
test_vdupd_lane_s64(int64x1_t a)65 int64_t test_vdupd_lane_s64(int64x1_t a) {
66   return vdupd_lane_s64(a, 0);
67 }
68 
69 
70 // CHECK-LABEL: define i8 @test_vdupb_lane_u8(<8 x i8> %a) #0 {
71 // CHECK:   [[VGET_LANE:%.*]] = extractelement <8 x i8> %a, i32 7
72 // CHECK:   ret i8 [[VGET_LANE]]
test_vdupb_lane_u8(uint8x8_t a)73 uint8_t test_vdupb_lane_u8(uint8x8_t a) {
74   return vdupb_lane_u8(a, 7);
75 }
76 
77 
78 // CHECK-LABEL: define i16 @test_vduph_lane_u16(<4 x i16> %a) #0 {
79 // CHECK:   [[VGET_LANE:%.*]] = extractelement <4 x i16> %a, i32 3
80 // CHECK:   ret i16 [[VGET_LANE]]
test_vduph_lane_u16(uint16x4_t a)81 uint16_t test_vduph_lane_u16(uint16x4_t a) {
82   return vduph_lane_u16(a, 3);
83 }
84 
85 
86 // CHECK-LABEL: define i32 @test_vdups_lane_u32(<2 x i32> %a) #0 {
87 // CHECK:   [[VGET_LANE:%.*]] = extractelement <2 x i32> %a, i32 1
88 // CHECK:   ret i32 [[VGET_LANE]]
test_vdups_lane_u32(uint32x2_t a)89 uint32_t test_vdups_lane_u32(uint32x2_t a) {
90   return vdups_lane_u32(a, 1);
91 }
92 
93 
94 // CHECK-LABEL: define i64 @test_vdupd_lane_u64(<1 x i64> %a) #0 {
95 // CHECK:   [[VGET_LANE:%.*]] = extractelement <1 x i64> %a, i32 0
96 // CHECK:   ret i64 [[VGET_LANE]]
test_vdupd_lane_u64(uint64x1_t a)97 uint64_t test_vdupd_lane_u64(uint64x1_t a) {
98   return vdupd_lane_u64(a, 0);
99 }
100 
101 // CHECK-LABEL: define i8 @test_vdupb_laneq_s8(<16 x i8> %a) #1 {
102 // CHECK:   [[VGETQ_LANE:%.*]] = extractelement <16 x i8> %a, i32 15
103 // CHECK:   ret i8 [[VGETQ_LANE]]
test_vdupb_laneq_s8(int8x16_t a)104 int8_t test_vdupb_laneq_s8(int8x16_t a) {
105   return vdupb_laneq_s8(a, 15);
106 }
107 
108 
109 // CHECK-LABEL: define i16 @test_vduph_laneq_s16(<8 x i16> %a) #1 {
110 // CHECK:   [[VGETQ_LANE:%.*]] = extractelement <8 x i16> %a, i32 7
111 // CHECK:   ret i16 [[VGETQ_LANE]]
test_vduph_laneq_s16(int16x8_t a)112 int16_t test_vduph_laneq_s16(int16x8_t a) {
113   return vduph_laneq_s16(a, 7);
114 }
115 
116 
117 // CHECK-LABEL: define i32 @test_vdups_laneq_s32(<4 x i32> %a) #1 {
118 // CHECK:   [[VGETQ_LANE:%.*]] = extractelement <4 x i32> %a, i32 3
119 // CHECK:   ret i32 [[VGETQ_LANE]]
test_vdups_laneq_s32(int32x4_t a)120 int32_t test_vdups_laneq_s32(int32x4_t a) {
121   return vdups_laneq_s32(a, 3);
122 }
123 
124 
125 // CHECK-LABEL: define i64 @test_vdupd_laneq_s64(<2 x i64> %a) #1 {
126 // CHECK:   [[VGETQ_LANE:%.*]] = extractelement <2 x i64> %a, i32 1
127 // CHECK:   ret i64 [[VGETQ_LANE]]
test_vdupd_laneq_s64(int64x2_t a)128 int64_t test_vdupd_laneq_s64(int64x2_t a) {
129   return vdupd_laneq_s64(a, 1);
130 }
131 
132 
133 // CHECK-LABEL: define i8 @test_vdupb_laneq_u8(<16 x i8> %a) #1 {
134 // CHECK:   [[VGETQ_LANE:%.*]] = extractelement <16 x i8> %a, i32 15
135 // CHECK:   ret i8 [[VGETQ_LANE]]
test_vdupb_laneq_u8(uint8x16_t a)136 uint8_t test_vdupb_laneq_u8(uint8x16_t a) {
137   return vdupb_laneq_u8(a, 15);
138 }
139 
140 
141 // CHECK-LABEL: define i16 @test_vduph_laneq_u16(<8 x i16> %a) #1 {
142 // CHECK:   [[VGETQ_LANE:%.*]] = extractelement <8 x i16> %a, i32 7
143 // CHECK:   ret i16 [[VGETQ_LANE]]
test_vduph_laneq_u16(uint16x8_t a)144 uint16_t test_vduph_laneq_u16(uint16x8_t a) {
145   return vduph_laneq_u16(a, 7);
146 }
147 
148 
149 // CHECK-LABEL: define i32 @test_vdups_laneq_u32(<4 x i32> %a) #1 {
150 // CHECK:   [[VGETQ_LANE:%.*]] = extractelement <4 x i32> %a, i32 3
151 // CHECK:   ret i32 [[VGETQ_LANE]]
test_vdups_laneq_u32(uint32x4_t a)152 uint32_t test_vdups_laneq_u32(uint32x4_t a) {
153   return vdups_laneq_u32(a, 3);
154 }
155 
156 
157 // CHECK-LABEL: define i64 @test_vdupd_laneq_u64(<2 x i64> %a) #1 {
158 // CHECK:   [[VGETQ_LANE:%.*]] = extractelement <2 x i64> %a, i32 1
159 // CHECK:   ret i64 [[VGETQ_LANE]]
test_vdupd_laneq_u64(uint64x2_t a)160 uint64_t test_vdupd_laneq_u64(uint64x2_t a) {
161   return vdupd_laneq_u64(a, 1);
162 }
163 
164 // CHECK-LABEL: define i8 @test_vdupb_lane_p8(<8 x i8> %a) #0 {
165 // CHECK:   [[VGET_LANE:%.*]] = extractelement <8 x i8> %a, i32 7
166 // CHECK:   ret i8 [[VGET_LANE]]
test_vdupb_lane_p8(poly8x8_t a)167 poly8_t test_vdupb_lane_p8(poly8x8_t a) {
168   return vdupb_lane_p8(a, 7);
169 }
170 
171 // CHECK-LABEL: define i16 @test_vduph_lane_p16(<4 x i16> %a) #0 {
172 // CHECK:   [[VGET_LANE:%.*]] = extractelement <4 x i16> %a, i32 3
173 // CHECK:   ret i16 [[VGET_LANE]]
test_vduph_lane_p16(poly16x4_t a)174 poly16_t test_vduph_lane_p16(poly16x4_t a) {
175   return vduph_lane_p16(a, 3);
176 }
177 
178 // CHECK-LABEL: define i8 @test_vdupb_laneq_p8(<16 x i8> %a) #1 {
179 // CHECK:   [[VGETQ_LANE:%.*]] = extractelement <16 x i8> %a, i32 15
180 // CHECK:   ret i8 [[VGETQ_LANE]]
test_vdupb_laneq_p8(poly8x16_t a)181 poly8_t test_vdupb_laneq_p8(poly8x16_t a) {
182   return vdupb_laneq_p8(a, 15);
183 }
184 
185 // CHECK-LABEL: define i16 @test_vduph_laneq_p16(<8 x i16> %a) #1 {
186 // CHECK:   [[VGETQ_LANE:%.*]] = extractelement <8 x i16> %a, i32 7
187 // CHECK:   ret i16 [[VGETQ_LANE]]
test_vduph_laneq_p16(poly16x8_t a)188 poly16_t test_vduph_laneq_p16(poly16x8_t a) {
189   return vduph_laneq_p16(a, 7);
190 }
191 
192 // CHECK: attributes #0 ={{.*}}"min-legal-vector-width"="64"
193 // CHECK: attributes #1 ={{.*}}"min-legal-vector-width"="128"
194