• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2018-2020 Arm Limited.
3  *
4  * SPDX-License-Identifier: MIT
5  *
6  * Permission is hereby granted, free of charge, to any person obtaining a copy
7  * of this software and associated documentation files (the "Software"), to
8  * deal in the Software without restriction, including without limitation the
9  * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
10  * sell copies of the Software, and to permit persons to whom the Software is
11  * furnished to do so, subject to the following conditions:
12  *
13  * The above copyright notice and this permission notice shall be included in all
14  * copies or substantial portions of the Software.
15  *
16  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19  * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
22  * SOFTWARE.
23  */
24 #ifndef ARM_COMPUTE_WRAPPER_GET_LANE_H
25 #define ARM_COMPUTE_WRAPPER_GET_LANE_H
26 
27 #include <arm_neon.h>
28 
29 namespace arm_compute
30 {
31 namespace wrapper
32 {
33 #define VGETLANE_IMPL_8(stype, vtype, postfix)                         \
34     inline stype vgetlane(const vtype vector, const unsigned int lane) \
35     {                                                                  \
36         switch(lane)                                                   \
37         {                                                              \
38             case 0:                                                    \
39                 return vget_lane_##postfix(vector, 0);                 \
40             case 1:                                                    \
41                 return vget_lane_##postfix(vector, 1);                 \
42             case 2:                                                    \
43                 return vget_lane_##postfix(vector, 2);                 \
44             case 3:                                                    \
45                 return vget_lane_##postfix(vector, 3);                 \
46             case 4:                                                    \
47                 return vget_lane_##postfix(vector, 4);                 \
48             case 5:                                                    \
49                 return vget_lane_##postfix(vector, 5);                 \
50             case 6:                                                    \
51                 return vget_lane_##postfix(vector, 6);                 \
52             case 7:                                                    \
53                 return vget_lane_##postfix(vector, 7);                 \
54             default:                                                   \
55                 ARM_COMPUTE_ERROR("Invalid lane");                     \
56         }                                                              \
57     }
58 
59 #define VGETLANE_IMPL_4(stype, vtype, postfix)                         \
60     inline stype vgetlane(const vtype vector, const unsigned int lane) \
61     {                                                                  \
62         switch(lane)                                                   \
63         {                                                              \
64             case 0:                                                    \
65                 return vget_lane_##postfix(vector, 0);                 \
66             case 1:                                                    \
67                 return vget_lane_##postfix(vector, 1);                 \
68             case 2:                                                    \
69                 return vget_lane_##postfix(vector, 2);                 \
70             case 3:                                                    \
71                 return vget_lane_##postfix(vector, 3);                 \
72             default:                                                   \
73                 ARM_COMPUTE_ERROR("Invalid lane");                     \
74         }                                                              \
75     }
76 
77 #define VGETLANE_IMPL_2(stype, vtype, postfix)                         \
78     inline stype vgetlane(const vtype vector, const unsigned int lane) \
79     {                                                                  \
80         switch(lane)                                                   \
81         {                                                              \
82             case 0:                                                    \
83                 return vget_lane_##postfix(vector, 0);                 \
84             case 1:                                                    \
85                 return vget_lane_##postfix(vector, 1);                 \
86             default:                                                   \
87                 ARM_COMPUTE_ERROR("Invalid lane");                     \
88         }                                                              \
89     }
90 
91 VGETLANE_IMPL_8(uint8_t, uint8x8_t, u8)
92 VGETLANE_IMPL_8(int8_t, int8x8_t, s8)
93 VGETLANE_IMPL_4(uint16_t, uint16x4_t, u16)
94 VGETLANE_IMPL_4(int16_t, int16x4_t, s16)
95 VGETLANE_IMPL_2(uint32_t, uint32x2_t, u32)
96 VGETLANE_IMPL_2(int32_t, int32x2_t, s32)
97 VGETLANE_IMPL_2(float, float32x2_t, f32)
98 #ifdef __ARM_FEATURE_FP16_VECTOR_ARITHMETIC
99 VGETLANE_IMPL_4(float16_t, float16x4_t, f16)
100 #endif // __ARM_FEATURE_FP16_VECTOR_ARITHMETIC
101 
102 #define VGETQLANE_IMPL_16(stype, vtype, postfix)                       \
103     inline stype vgetlane(const vtype vector, const unsigned int lane) \
104     {                                                                  \
105         switch(lane)                                                   \
106         {                                                              \
107             case 0:                                                    \
108                 return vgetq_lane_##postfix(vector, 0);                \
109             case 1:                                                    \
110                 return vgetq_lane_##postfix(vector, 1);                \
111             case 2:                                                    \
112                 return vgetq_lane_##postfix(vector, 2);                \
113             case 3:                                                    \
114                 return vgetq_lane_##postfix(vector, 3);                \
115             case 4:                                                    \
116                 return vgetq_lane_##postfix(vector, 4);                \
117             case 5:                                                    \
118                 return vgetq_lane_##postfix(vector, 5);                \
119             case 6:                                                    \
120                 return vgetq_lane_##postfix(vector, 6);                \
121             case 7:                                                    \
122                 return vgetq_lane_##postfix(vector, 7);                \
123             case 8:                                                    \
124                 return vgetq_lane_##postfix(vector, 8);                \
125             case 9:                                                    \
126                 return vgetq_lane_##postfix(vector, 9);                \
127             case 10:                                                   \
128                 return vgetq_lane_##postfix(vector, 10);               \
129             case 11:                                                   \
130                 return vgetq_lane_##postfix(vector, 11);               \
131             case 12:                                                   \
132                 return vgetq_lane_##postfix(vector, 12);               \
133             case 13:                                                   \
134                 return vgetq_lane_##postfix(vector, 13);               \
135             case 14:                                                   \
136                 return vgetq_lane_##postfix(vector, 14);               \
137             case 15:                                                   \
138                 return vgetq_lane_##postfix(vector, 15);               \
139             default:                                                   \
140                 ARM_COMPUTE_ERROR("Invalid lane");                     \
141         }                                                              \
142     }
143 
144 #define VGETQLANE_IMPL_8(stype, vtype, postfix)                        \
145     inline stype vgetlane(const vtype vector, const unsigned int lane) \
146     {                                                                  \
147         switch(lane)                                                   \
148         {                                                              \
149             case 0:                                                    \
150                 return vgetq_lane_##postfix(vector, 0);                \
151             case 1:                                                    \
152                 return vgetq_lane_##postfix(vector, 1);                \
153             case 2:                                                    \
154                 return vgetq_lane_##postfix(vector, 2);                \
155             case 3:                                                    \
156                 return vgetq_lane_##postfix(vector, 3);                \
157             case 4:                                                    \
158                 return vgetq_lane_##postfix(vector, 4);                \
159             case 5:                                                    \
160                 return vgetq_lane_##postfix(vector, 5);                \
161             case 6:                                                    \
162                 return vgetq_lane_##postfix(vector, 6);                \
163             case 7:                                                    \
164                 return vgetq_lane_##postfix(vector, 7);                \
165             default:                                                   \
166                 ARM_COMPUTE_ERROR("Invalid lane");                     \
167         }                                                              \
168     }
169 
170 #define VGETQLANE_IMPL_4(stype, vtype, postfix)                        \
171     inline stype vgetlane(const vtype vector, const unsigned int lane) \
172     {                                                                  \
173         switch(lane)                                                   \
174         {                                                              \
175             case 0:                                                    \
176                 return vgetq_lane_##postfix(vector, 0);                \
177             case 1:                                                    \
178                 return vgetq_lane_##postfix(vector, 1);                \
179             case 2:                                                    \
180                 return vgetq_lane_##postfix(vector, 2);                \
181             case 3:                                                    \
182                 return vgetq_lane_##postfix(vector, 3);                \
183             default:                                                   \
184                 ARM_COMPUTE_ERROR("Invalid lane");                     \
185         }                                                              \
186     }
187 
188 #define VGETQLANE_IMPL_2(stype, vtype, postfix)                        \
189     inline stype vgetlane(const vtype vector, const unsigned int lane) \
190     {                                                                  \
191         switch(lane)                                                   \
192         {                                                              \
193             case 0:                                                    \
194                 return vgetq_lane_##postfix(vector, 0);                \
195             case 1:                                                    \
196                 return vgetq_lane_##postfix(vector, 1);                \
197             default:                                                   \
198                 ARM_COMPUTE_ERROR("Invalid lane");                     \
199         }                                                              \
200     }
201 
202 VGETQLANE_IMPL_16(uint8_t, uint8x16_t, u8)
203 VGETQLANE_IMPL_16(int8_t, int8x16_t, s8)
204 VGETQLANE_IMPL_8(uint16_t, uint16x8_t, u16)
205 VGETQLANE_IMPL_8(int16_t, int16x8_t, s16)
206 VGETQLANE_IMPL_4(uint32_t, uint32x4_t, u32)
207 VGETQLANE_IMPL_4(int32_t, int32x4_t, s32)
208 VGETQLANE_IMPL_4(float, float32x4_t, f32)
209 VGETQLANE_IMPL_2(int64_t, int64x2_t, s64)
210 #ifdef __ARM_FEATURE_FP16_VECTOR_ARITHMETIC
211 VGETQLANE_IMPL_8(float16_t, float16x8_t, f16)
212 #endif // __ARM_FEATURE_FP16_VECTOR_ARITHMETIC
213 
214 #undef VGETLANE_IMPL_8
215 #undef VGETLANE_IMPL_4
216 #undef VGETLANE_IMPL_2
217 
218 #undef VGETQLANE_IMPL_16
219 #undef VGETQLANE_IMPL_8
220 #undef VGETQLANE_IMPL_4
221 } // namespace wrapper
222 } // namespace arm_compute
223 #endif /* ARM_COMPUTE_WRAPPER_GET_LANE_H */
224