blob: b80d75326ecfc4370e2402c943f5269fe4591c5b [file] [log] [blame]
Viet-Hoa Dofd472f02023-03-15 14:05:06 +00001/*
2 * Copyright (c) 2022-2023 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
25#include "src/cpu/kernels/lut/list.h"
26
27#ifdef __aarch64__
28#ifdef ARM_COMPUTE_ENABLE_SVE
29
30namespace arm_compute
31{
32namespace cpu
33{
SiCong Li3f70cd02023-05-17 13:46:13 +010034void lut_u8_sve2(
Viet-Hoa Dofd472f02023-03-15 14:05:06 +000035 const uint8_t *table,
36 size_t num_strings,
37 size_t string_length,
38 const uint8_t *const *input,
39 uint8_t *const *output)
40{
41 __asm__ __volatile__(
42 "ptrue p0.b\n"
43 "cntd x25\n"
44 "addvl %x[table], %x[table], #8\n"
45 "ld1b { z16.b }, p0/Z, [%x[table], #-8, MUL VL]\n"
46 "tbnz x25, #5, 1f\n"
47 "ld1b { z17.b }, p0/Z, [%x[table], #-7, MUL VL]\n"
48 "tbnz x25, #4, 1f\n"
49 "ld1b { z18.b }, p0/Z, [%x[table], #-6, MUL VL]\n"
50 "ld1b { z19.b }, p0/Z, [%x[table], #-5, MUL VL]\n"
51 "tbnz x25, #3, 1f\n"
52 "ld1b { z20.b }, p0/Z, [%x[table], #-4, MUL VL]\n"
53 "ld1b { z21.b }, p0/Z, [%x[table], #-3, MUL VL]\n"
54 "ld1b { z22.b }, p0/Z, [%x[table], #-2, MUL VL]\n"
55 "ld1b { z23.b }, p0/Z, [%x[table], #-1, MUL VL]\n"
56 "tbnz x25, #2, 1f\n"
57 "ld1b { z24.b }, p0/Z, [%x[table]]\n"
58 "ld1b { z25.b }, p0/Z, [%x[table], #1, MUL VL]\n"
59 "ld1b { z26.b }, p0/Z, [%x[table], #2, MUL VL]\n"
60 "ld1b { z27.b }, p0/Z, [%x[table], #3, MUL VL]\n"
61 "ld1b { z28.b }, p0/Z, [%x[table], #4, MUL VL]\n"
62 "ld1b { z29.b }, p0/Z, [%x[table], #5, MUL VL]\n"
63 "ld1b { z30.b }, p0/Z, [%x[table], #6, MUL VL]\n"
64 "ld1b { z31.b }, p0/Z, [%x[table], #7, MUL VL]\n"
65 "1:" // Table load done
66 "mov x24, #0x0\n"
67 "2:" // string loop
68 "ldr x23, [%x[input], x24, LSL #0x3]\n"
69 "ldr x22, [%x[output], x24, LSL #0x3]\n"
70 "tbnz x25, #5, 14f\n"
71 "tbnz x25, #4, 11f\n"
72 "tbnz x25, #3, 8f\n"
73 "tbnz x25, #2, 5f\n"
74 "mov z12.b, #0x10\n"
75 "mov x21, %x[string_length]\n"
76 "ptrue p5.b\n"
77 "ptrue p4.b\n"
78 "ptrue p3.b\n"
79 "ptrue p2.b\n"
80 "ptrue p1.b\n"
81 "ptrue p0.b\n"
82 "3:" // 16 rounds: width loop
83 "addvl x20, x21, #-6\n"
84 "cmp x20, XZR\n"
85 "bge 4f\n"
86 "mov x20, #0x0\n"
87 "addvl x20, x20, #1\n"
88 "whilelt p5.b, XZR, x21\n"
89 "whilelt p4.b, x20, x21\n"
90 "addvl x20, x20, #1\n"
91 "whilelt p3.b, x20, x21\n"
92 "addvl x20, x20, #1\n"
93 "whilelt p2.b, x20, x21\n"
94 "addvl x20, x20, #1\n"
95 "whilelt p1.b, x20, x21\n"
96 "addvl x20, x20, #1\n"
97 "whilelt p0.b, x20, x21\n"
98 "4:" // 16 rounds: predicate OK
99 "ld1b { z11.b }, p5/Z, [x23]\n"
100 "ld1b { z10.b }, p4/Z, [x23, #1, MUL VL]\n"
101 "tbl z9.b, { z16.b }, z11.b\n"
102 "ld1b { z8.b }, p3/Z, [x23, #2, MUL VL]\n"
103 "ld1b { z7.b }, p2/Z, [x23, #3, MUL VL]\n"
104 "sub z11.b, z11.b, z12.b\n"
105 "ld1b { z6.b }, p1/Z, [x23, #4, MUL VL]\n"
106 "ld1b { z5.b }, p0/Z, [x23, #5, MUL VL]\n"
107 "tbl z4.b, { z16.b }, z10.b\n"
108 "sub z10.b, z10.b, z12.b\n"
109 "tbl z3.b, { z16.b }, z8.b\n"
110 "sub z8.b, z8.b, z12.b\n"
111 "tbl z2.b, { z16.b }, z7.b\n"
112 "sub z7.b, z7.b, z12.b\n"
113 "tbl z1.b, { z16.b }, z6.b\n"
114 "sub z6.b, z6.b, z12.b\n"
115 "tbl z0.b, { z16.b }, z5.b\n"
116 "sub z5.b, z5.b, z12.b\n"
117 ".inst 0x052b2e29 // tbx z9.b, z17.b, z11.b\n"
118 "sub z11.b, z11.b, z12.b\n"
119 ".inst 0x052a2e24 // tbx z4.b, z17.b, z10.b\n"
120 "sub z10.b, z10.b, z12.b\n"
121 ".inst 0x05282e23 // tbx z3.b, z17.b, z8.b\n"
122 "sub z8.b, z8.b, z12.b\n"
123 ".inst 0x05272e22 // tbx z2.b, z17.b, z7.b\n"
124 "sub z7.b, z7.b, z12.b\n"
125 ".inst 0x05262e21 // tbx z1.b, z17.b, z6.b\n"
126 "sub z6.b, z6.b, z12.b\n"
127 ".inst 0x05252e20 // tbx z0.b, z17.b, z5.b\n"
128 "sub z5.b, z5.b, z12.b\n"
129 ".inst 0x052b2e49 // tbx z9.b, z18.b, z11.b\n"
130 "sub z11.b, z11.b, z12.b\n"
131 ".inst 0x052a2e44 // tbx z4.b, z18.b, z10.b\n"
132 "sub z10.b, z10.b, z12.b\n"
133 ".inst 0x05282e43 // tbx z3.b, z18.b, z8.b\n"
134 "sub z8.b, z8.b, z12.b\n"
135 ".inst 0x05272e42 // tbx z2.b, z18.b, z7.b\n"
136 "sub z7.b, z7.b, z12.b\n"
137 ".inst 0x05262e41 // tbx z1.b, z18.b, z6.b\n"
138 "sub z6.b, z6.b, z12.b\n"
139 ".inst 0x05252e40 // tbx z0.b, z18.b, z5.b\n"
140 "sub z5.b, z5.b, z12.b\n"
141 ".inst 0x052b2e69 // tbx z9.b, z19.b, z11.b\n"
142 "sub z11.b, z11.b, z12.b\n"
143 ".inst 0x052a2e64 // tbx z4.b, z19.b, z10.b\n"
144 "sub z10.b, z10.b, z12.b\n"
145 ".inst 0x05282e63 // tbx z3.b, z19.b, z8.b\n"
146 "sub z8.b, z8.b, z12.b\n"
147 ".inst 0x05272e62 // tbx z2.b, z19.b, z7.b\n"
148 "sub z7.b, z7.b, z12.b\n"
149 ".inst 0x05262e61 // tbx z1.b, z19.b, z6.b\n"
150 "sub z6.b, z6.b, z12.b\n"
151 ".inst 0x05252e60 // tbx z0.b, z19.b, z5.b\n"
152 "sub z5.b, z5.b, z12.b\n"
153 ".inst 0x052b2e89 // tbx z9.b, z20.b, z11.b\n"
154 "sub z11.b, z11.b, z12.b\n"
155 ".inst 0x052a2e84 // tbx z4.b, z20.b, z10.b\n"
156 "sub z10.b, z10.b, z12.b\n"
157 ".inst 0x05282e83 // tbx z3.b, z20.b, z8.b\n"
158 "sub z8.b, z8.b, z12.b\n"
159 ".inst 0x05272e82 // tbx z2.b, z20.b, z7.b\n"
160 "sub z7.b, z7.b, z12.b\n"
161 ".inst 0x05262e81 // tbx z1.b, z20.b, z6.b\n"
162 "sub z6.b, z6.b, z12.b\n"
163 ".inst 0x05252e80 // tbx z0.b, z20.b, z5.b\n"
164 "sub z5.b, z5.b, z12.b\n"
165 ".inst 0x052b2ea9 // tbx z9.b, z21.b, z11.b\n"
166 "sub z11.b, z11.b, z12.b\n"
167 ".inst 0x052a2ea4 // tbx z4.b, z21.b, z10.b\n"
168 "sub z10.b, z10.b, z12.b\n"
169 ".inst 0x05282ea3 // tbx z3.b, z21.b, z8.b\n"
170 "sub z8.b, z8.b, z12.b\n"
171 ".inst 0x05272ea2 // tbx z2.b, z21.b, z7.b\n"
172 "sub z7.b, z7.b, z12.b\n"
173 ".inst 0x05262ea1 // tbx z1.b, z21.b, z6.b\n"
174 "sub z6.b, z6.b, z12.b\n"
175 ".inst 0x05252ea0 // tbx z0.b, z21.b, z5.b\n"
176 "sub z5.b, z5.b, z12.b\n"
177 ".inst 0x052b2ec9 // tbx z9.b, z22.b, z11.b\n"
178 "sub z11.b, z11.b, z12.b\n"
179 ".inst 0x052a2ec4 // tbx z4.b, z22.b, z10.b\n"
180 "sub z10.b, z10.b, z12.b\n"
181 ".inst 0x05282ec3 // tbx z3.b, z22.b, z8.b\n"
182 "sub z8.b, z8.b, z12.b\n"
183 ".inst 0x05272ec2 // tbx z2.b, z22.b, z7.b\n"
184 "sub z7.b, z7.b, z12.b\n"
185 ".inst 0x05262ec1 // tbx z1.b, z22.b, z6.b\n"
186 "sub z6.b, z6.b, z12.b\n"
187 ".inst 0x05252ec0 // tbx z0.b, z22.b, z5.b\n"
188 "sub z5.b, z5.b, z12.b\n"
189 ".inst 0x052b2ee9 // tbx z9.b, z23.b, z11.b\n"
190 "sub z11.b, z11.b, z12.b\n"
191 ".inst 0x052a2ee4 // tbx z4.b, z23.b, z10.b\n"
192 "sub z10.b, z10.b, z12.b\n"
193 ".inst 0x05282ee3 // tbx z3.b, z23.b, z8.b\n"
194 "sub z8.b, z8.b, z12.b\n"
195 ".inst 0x05272ee2 // tbx z2.b, z23.b, z7.b\n"
196 "sub z7.b, z7.b, z12.b\n"
197 ".inst 0x05262ee1 // tbx z1.b, z23.b, z6.b\n"
198 "sub z6.b, z6.b, z12.b\n"
199 ".inst 0x05252ee0 // tbx z0.b, z23.b, z5.b\n"
200 "sub z5.b, z5.b, z12.b\n"
201 ".inst 0x052b2f09 // tbx z9.b, z24.b, z11.b\n"
202 "sub z11.b, z11.b, z12.b\n"
203 ".inst 0x052a2f04 // tbx z4.b, z24.b, z10.b\n"
204 "sub z10.b, z10.b, z12.b\n"
205 ".inst 0x05282f03 // tbx z3.b, z24.b, z8.b\n"
206 "sub z8.b, z8.b, z12.b\n"
207 ".inst 0x05272f02 // tbx z2.b, z24.b, z7.b\n"
208 "sub z7.b, z7.b, z12.b\n"
209 ".inst 0x05262f01 // tbx z1.b, z24.b, z6.b\n"
210 "sub z6.b, z6.b, z12.b\n"
211 ".inst 0x05252f00 // tbx z0.b, z24.b, z5.b\n"
212 "sub z5.b, z5.b, z12.b\n"
213 ".inst 0x052b2f29 // tbx z9.b, z25.b, z11.b\n"
214 "sub z11.b, z11.b, z12.b\n"
215 ".inst 0x052a2f24 // tbx z4.b, z25.b, z10.b\n"
216 "sub z10.b, z10.b, z12.b\n"
217 ".inst 0x05282f23 // tbx z3.b, z25.b, z8.b\n"
218 "sub z8.b, z8.b, z12.b\n"
219 ".inst 0x05272f22 // tbx z2.b, z25.b, z7.b\n"
220 "sub z7.b, z7.b, z12.b\n"
221 ".inst 0x05262f21 // tbx z1.b, z25.b, z6.b\n"
222 "sub z6.b, z6.b, z12.b\n"
223 ".inst 0x05252f20 // tbx z0.b, z25.b, z5.b\n"
224 "sub z5.b, z5.b, z12.b\n"
225 ".inst 0x052b2f49 // tbx z9.b, z26.b, z11.b\n"
226 "sub z11.b, z11.b, z12.b\n"
227 ".inst 0x052a2f44 // tbx z4.b, z26.b, z10.b\n"
228 "sub z10.b, z10.b, z12.b\n"
229 ".inst 0x05282f43 // tbx z3.b, z26.b, z8.b\n"
230 "sub z8.b, z8.b, z12.b\n"
231 ".inst 0x05272f42 // tbx z2.b, z26.b, z7.b\n"
232 "sub z7.b, z7.b, z12.b\n"
233 ".inst 0x05262f41 // tbx z1.b, z26.b, z6.b\n"
234 "sub z6.b, z6.b, z12.b\n"
235 ".inst 0x05252f40 // tbx z0.b, z26.b, z5.b\n"
236 "sub z5.b, z5.b, z12.b\n"
237 ".inst 0x052b2f69 // tbx z9.b, z27.b, z11.b\n"
238 "sub z11.b, z11.b, z12.b\n"
239 ".inst 0x052a2f64 // tbx z4.b, z27.b, z10.b\n"
240 "sub z10.b, z10.b, z12.b\n"
241 ".inst 0x05282f63 // tbx z3.b, z27.b, z8.b\n"
242 "sub z8.b, z8.b, z12.b\n"
243 ".inst 0x05272f62 // tbx z2.b, z27.b, z7.b\n"
244 "sub z7.b, z7.b, z12.b\n"
245 ".inst 0x05262f61 // tbx z1.b, z27.b, z6.b\n"
246 "sub z6.b, z6.b, z12.b\n"
247 ".inst 0x05252f60 // tbx z0.b, z27.b, z5.b\n"
248 "sub z5.b, z5.b, z12.b\n"
249 ".inst 0x052b2f89 // tbx z9.b, z28.b, z11.b\n"
250 "sub z11.b, z11.b, z12.b\n"
251 ".inst 0x052a2f84 // tbx z4.b, z28.b, z10.b\n"
252 "sub z10.b, z10.b, z12.b\n"
253 ".inst 0x05282f83 // tbx z3.b, z28.b, z8.b\n"
254 "sub z8.b, z8.b, z12.b\n"
255 ".inst 0x05272f82 // tbx z2.b, z28.b, z7.b\n"
256 "sub z7.b, z7.b, z12.b\n"
257 ".inst 0x05262f81 // tbx z1.b, z28.b, z6.b\n"
258 "sub z6.b, z6.b, z12.b\n"
259 ".inst 0x05252f80 // tbx z0.b, z28.b, z5.b\n"
260 "sub z5.b, z5.b, z12.b\n"
261 ".inst 0x052b2fa9 // tbx z9.b, z29.b, z11.b\n"
262 "sub z11.b, z11.b, z12.b\n"
263 ".inst 0x052a2fa4 // tbx z4.b, z29.b, z10.b\n"
264 "sub z10.b, z10.b, z12.b\n"
265 ".inst 0x05282fa3 // tbx z3.b, z29.b, z8.b\n"
266 "sub z8.b, z8.b, z12.b\n"
267 ".inst 0x05272fa2 // tbx z2.b, z29.b, z7.b\n"
268 "sub z7.b, z7.b, z12.b\n"
269 ".inst 0x05262fa1 // tbx z1.b, z29.b, z6.b\n"
270 "sub z6.b, z6.b, z12.b\n"
271 ".inst 0x05252fa0 // tbx z0.b, z29.b, z5.b\n"
272 "sub z5.b, z5.b, z12.b\n"
273 "addvl x21, x21, #-6\n"
274 ".inst 0x052b2fc9 // tbx z9.b, z30.b, z11.b\n"
275 "sub z11.b, z11.b, z12.b\n"
276 ".inst 0x052a2fc4 // tbx z4.b, z30.b, z10.b\n"
277 "sub z10.b, z10.b, z12.b\n"
278 ".inst 0x05282fc3 // tbx z3.b, z30.b, z8.b\n"
279 "sub z8.b, z8.b, z12.b\n"
280 ".inst 0x05272fc2 // tbx z2.b, z30.b, z7.b\n"
281 "sub z7.b, z7.b, z12.b\n"
282 ".inst 0x05262fc1 // tbx z1.b, z30.b, z6.b\n"
283 "sub z6.b, z6.b, z12.b\n"
284 ".inst 0x05252fc0 // tbx z0.b, z30.b, z5.b\n"
285 "sub z5.b, z5.b, z12.b\n"
286 "cmp x21, XZR\n"
287 ".inst 0x052b2fe9 // tbx z9.b, z31.b, z11.b\n"
288 ".inst 0x052a2fe4 // tbx z4.b, z31.b, z10.b\n"
289 ".inst 0x05282fe3 // tbx z3.b, z31.b, z8.b\n"
290 "st1b { z9.b }, p5, [x22]\n"
291 ".inst 0x05272fe2 // tbx z2.b, z31.b, z7.b\n"
292 ".inst 0x05262fe1 // tbx z1.b, z31.b, z6.b\n"
293 "st1b { z4.b }, p4, [x22, #1, MUL VL]\n"
294 ".inst 0x05252fe0 // tbx z0.b, z31.b, z5.b\n"
295 "st1b { z3.b }, p3, [x22, #2, MUL VL]\n"
296 "addvl x23, x23, #6\n"
297 "st1b { z2.b }, p2, [x22, #3, MUL VL]\n"
298 "st1b { z1.b }, p1, [x22, #4, MUL VL]\n"
299 "st1b { z0.b }, p0, [x22, #5, MUL VL]\n"
300 "addvl x22, x22, #6\n"
301 "bgt 3b\n"
302 "b 17f\n"
303 "5:" // 256 bits
304 "mov z12.b, #0x20\n"
305 "mov x21, %x[string_length]\n"
306 "ptrue p5.b\n"
307 "ptrue p4.b\n"
308 "ptrue p3.b\n"
309 "ptrue p2.b\n"
310 "ptrue p1.b\n"
311 "ptrue p0.b\n"
312 "6:" // 8 rounds: width loop
313 "addvl x20, x21, #-6\n"
314 "cmp x20, XZR\n"
315 "bge 7f\n"
316 "mov x20, #0x0\n"
317 "addvl x20, x20, #1\n"
318 "whilelt p5.b, XZR, x21\n"
319 "whilelt p4.b, x20, x21\n"
320 "addvl x20, x20, #1\n"
321 "whilelt p3.b, x20, x21\n"
322 "addvl x20, x20, #1\n"
323 "whilelt p2.b, x20, x21\n"
324 "addvl x20, x20, #1\n"
325 "whilelt p1.b, x20, x21\n"
326 "addvl x20, x20, #1\n"
327 "whilelt p0.b, x20, x21\n"
328 "7:" // 8 rounds: predicate OK
329 "ld1b { z11.b }, p5/Z, [x23]\n"
330 "ld1b { z10.b }, p4/Z, [x23, #1, MUL VL]\n"
331 "tbl z9.b, { z16.b }, z11.b\n"
332 "ld1b { z8.b }, p3/Z, [x23, #2, MUL VL]\n"
333 "ld1b { z7.b }, p2/Z, [x23, #3, MUL VL]\n"
334 "sub z11.b, z11.b, z12.b\n"
335 "ld1b { z6.b }, p1/Z, [x23, #4, MUL VL]\n"
336 "ld1b { z5.b }, p0/Z, [x23, #5, MUL VL]\n"
337 "tbl z4.b, { z16.b }, z10.b\n"
338 "sub z10.b, z10.b, z12.b\n"
339 "tbl z3.b, { z16.b }, z8.b\n"
340 "sub z8.b, z8.b, z12.b\n"
341 "tbl z2.b, { z16.b }, z7.b\n"
342 "sub z7.b, z7.b, z12.b\n"
343 "tbl z1.b, { z16.b }, z6.b\n"
344 "sub z6.b, z6.b, z12.b\n"
345 "tbl z0.b, { z16.b }, z5.b\n"
346 "sub z5.b, z5.b, z12.b\n"
347 ".inst 0x052b2e29 // tbx z9.b, z17.b, z11.b\n"
348 "sub z11.b, z11.b, z12.b\n"
349 ".inst 0x052a2e24 // tbx z4.b, z17.b, z10.b\n"
350 "sub z10.b, z10.b, z12.b\n"
351 ".inst 0x05282e23 // tbx z3.b, z17.b, z8.b\n"
352 "sub z8.b, z8.b, z12.b\n"
353 ".inst 0x05272e22 // tbx z2.b, z17.b, z7.b\n"
354 "sub z7.b, z7.b, z12.b\n"
355 ".inst 0x05262e21 // tbx z1.b, z17.b, z6.b\n"
356 "sub z6.b, z6.b, z12.b\n"
357 ".inst 0x05252e20 // tbx z0.b, z17.b, z5.b\n"
358 "sub z5.b, z5.b, z12.b\n"
359 ".inst 0x052b2e49 // tbx z9.b, z18.b, z11.b\n"
360 "sub z11.b, z11.b, z12.b\n"
361 ".inst 0x052a2e44 // tbx z4.b, z18.b, z10.b\n"
362 "sub z10.b, z10.b, z12.b\n"
363 ".inst 0x05282e43 // tbx z3.b, z18.b, z8.b\n"
364 "sub z8.b, z8.b, z12.b\n"
365 ".inst 0x05272e42 // tbx z2.b, z18.b, z7.b\n"
366 "sub z7.b, z7.b, z12.b\n"
367 ".inst 0x05262e41 // tbx z1.b, z18.b, z6.b\n"
368 "sub z6.b, z6.b, z12.b\n"
369 ".inst 0x05252e40 // tbx z0.b, z18.b, z5.b\n"
370 "sub z5.b, z5.b, z12.b\n"
371 ".inst 0x052b2e69 // tbx z9.b, z19.b, z11.b\n"
372 "sub z11.b, z11.b, z12.b\n"
373 ".inst 0x052a2e64 // tbx z4.b, z19.b, z10.b\n"
374 "sub z10.b, z10.b, z12.b\n"
375 ".inst 0x05282e63 // tbx z3.b, z19.b, z8.b\n"
376 "sub z8.b, z8.b, z12.b\n"
377 ".inst 0x05272e62 // tbx z2.b, z19.b, z7.b\n"
378 "sub z7.b, z7.b, z12.b\n"
379 ".inst 0x05262e61 // tbx z1.b, z19.b, z6.b\n"
380 "sub z6.b, z6.b, z12.b\n"
381 ".inst 0x05252e60 // tbx z0.b, z19.b, z5.b\n"
382 "sub z5.b, z5.b, z12.b\n"
383 ".inst 0x052b2e89 // tbx z9.b, z20.b, z11.b\n"
384 "sub z11.b, z11.b, z12.b\n"
385 ".inst 0x052a2e84 // tbx z4.b, z20.b, z10.b\n"
386 "sub z10.b, z10.b, z12.b\n"
387 ".inst 0x05282e83 // tbx z3.b, z20.b, z8.b\n"
388 "sub z8.b, z8.b, z12.b\n"
389 ".inst 0x05272e82 // tbx z2.b, z20.b, z7.b\n"
390 "sub z7.b, z7.b, z12.b\n"
391 ".inst 0x05262e81 // tbx z1.b, z20.b, z6.b\n"
392 "sub z6.b, z6.b, z12.b\n"
393 ".inst 0x05252e80 // tbx z0.b, z20.b, z5.b\n"
394 "sub z5.b, z5.b, z12.b\n"
395 ".inst 0x052b2ea9 // tbx z9.b, z21.b, z11.b\n"
396 "sub z11.b, z11.b, z12.b\n"
397 ".inst 0x052a2ea4 // tbx z4.b, z21.b, z10.b\n"
398 "sub z10.b, z10.b, z12.b\n"
399 ".inst 0x05282ea3 // tbx z3.b, z21.b, z8.b\n"
400 "sub z8.b, z8.b, z12.b\n"
401 ".inst 0x05272ea2 // tbx z2.b, z21.b, z7.b\n"
402 "sub z7.b, z7.b, z12.b\n"
403 ".inst 0x05262ea1 // tbx z1.b, z21.b, z6.b\n"
404 "sub z6.b, z6.b, z12.b\n"
405 ".inst 0x05252ea0 // tbx z0.b, z21.b, z5.b\n"
406 "sub z5.b, z5.b, z12.b\n"
407 "addvl x21, x21, #-6\n"
408 ".inst 0x052b2ec9 // tbx z9.b, z22.b, z11.b\n"
409 "sub z11.b, z11.b, z12.b\n"
410 ".inst 0x052a2ec4 // tbx z4.b, z22.b, z10.b\n"
411 "sub z10.b, z10.b, z12.b\n"
412 ".inst 0x05282ec3 // tbx z3.b, z22.b, z8.b\n"
413 "sub z8.b, z8.b, z12.b\n"
414 ".inst 0x05272ec2 // tbx z2.b, z22.b, z7.b\n"
415 "sub z7.b, z7.b, z12.b\n"
416 ".inst 0x05262ec1 // tbx z1.b, z22.b, z6.b\n"
417 "sub z6.b, z6.b, z12.b\n"
418 ".inst 0x05252ec0 // tbx z0.b, z22.b, z5.b\n"
419 "sub z5.b, z5.b, z12.b\n"
420 "cmp x21, XZR\n"
421 ".inst 0x052b2ee9 // tbx z9.b, z23.b, z11.b\n"
422 ".inst 0x052a2ee4 // tbx z4.b, z23.b, z10.b\n"
423 ".inst 0x05282ee3 // tbx z3.b, z23.b, z8.b\n"
424 "st1b { z9.b }, p5, [x22]\n"
425 ".inst 0x05272ee2 // tbx z2.b, z23.b, z7.b\n"
426 ".inst 0x05262ee1 // tbx z1.b, z23.b, z6.b\n"
427 "st1b { z4.b }, p4, [x22, #1, MUL VL]\n"
428 ".inst 0x05252ee0 // tbx z0.b, z23.b, z5.b\n"
429 "st1b { z3.b }, p3, [x22, #2, MUL VL]\n"
430 "addvl x23, x23, #6\n"
431 "st1b { z2.b }, p2, [x22, #3, MUL VL]\n"
432 "st1b { z1.b }, p1, [x22, #4, MUL VL]\n"
433 "st1b { z0.b }, p0, [x22, #5, MUL VL]\n"
434 "addvl x22, x22, #6\n"
435 "bgt 6b\n"
436 "b 17f\n"
437 "8:" // 512 bits
438 "mov z12.b, #0x40\n"
439 "mov x21, %x[string_length]\n"
440 "ptrue p5.b\n"
441 "ptrue p4.b\n"
442 "ptrue p3.b\n"
443 "ptrue p2.b\n"
444 "ptrue p1.b\n"
445 "ptrue p0.b\n"
446 "9:" // 4 rounds: width loop
447 "addvl x20, x21, #-6\n"
448 "cmp x20, XZR\n"
449 "bge 10f\n"
450 "mov x20, #0x0\n"
451 "addvl x20, x20, #1\n"
452 "whilelt p5.b, XZR, x21\n"
453 "whilelt p4.b, x20, x21\n"
454 "addvl x20, x20, #1\n"
455 "whilelt p3.b, x20, x21\n"
456 "addvl x20, x20, #1\n"
457 "whilelt p2.b, x20, x21\n"
458 "addvl x20, x20, #1\n"
459 "whilelt p1.b, x20, x21\n"
460 "addvl x20, x20, #1\n"
461 "whilelt p0.b, x20, x21\n"
462 "10:" // 4 rounds: predicate OK
463 "ld1b { z11.b }, p5/Z, [x23]\n"
464 "ld1b { z10.b }, p4/Z, [x23, #1, MUL VL]\n"
465 "tbl z9.b, { z16.b }, z11.b\n"
466 "ld1b { z8.b }, p3/Z, [x23, #2, MUL VL]\n"
467 "ld1b { z7.b }, p2/Z, [x23, #3, MUL VL]\n"
468 "sub z11.b, z11.b, z12.b\n"
469 "ld1b { z6.b }, p1/Z, [x23, #4, MUL VL]\n"
470 "ld1b { z5.b }, p0/Z, [x23, #5, MUL VL]\n"
471 "tbl z4.b, { z16.b }, z10.b\n"
472 "sub z10.b, z10.b, z12.b\n"
473 "tbl z3.b, { z16.b }, z8.b\n"
474 "sub z8.b, z8.b, z12.b\n"
475 "tbl z2.b, { z16.b }, z7.b\n"
476 "sub z7.b, z7.b, z12.b\n"
477 "tbl z1.b, { z16.b }, z6.b\n"
478 "sub z6.b, z6.b, z12.b\n"
479 "tbl z0.b, { z16.b }, z5.b\n"
480 "sub z5.b, z5.b, z12.b\n"
481 ".inst 0x052b2e29 // tbx z9.b, z17.b, z11.b\n"
482 "sub z11.b, z11.b, z12.b\n"
483 ".inst 0x052a2e24 // tbx z4.b, z17.b, z10.b\n"
484 "sub z10.b, z10.b, z12.b\n"
485 ".inst 0x05282e23 // tbx z3.b, z17.b, z8.b\n"
486 "sub z8.b, z8.b, z12.b\n"
487 ".inst 0x05272e22 // tbx z2.b, z17.b, z7.b\n"
488 "sub z7.b, z7.b, z12.b\n"
489 ".inst 0x05262e21 // tbx z1.b, z17.b, z6.b\n"
490 "sub z6.b, z6.b, z12.b\n"
491 ".inst 0x05252e20 // tbx z0.b, z17.b, z5.b\n"
492 "sub z5.b, z5.b, z12.b\n"
493 "addvl x21, x21, #-6\n"
494 ".inst 0x052b2e49 // tbx z9.b, z18.b, z11.b\n"
495 "sub z11.b, z11.b, z12.b\n"
496 ".inst 0x052a2e44 // tbx z4.b, z18.b, z10.b\n"
497 "sub z10.b, z10.b, z12.b\n"
498 ".inst 0x05282e43 // tbx z3.b, z18.b, z8.b\n"
499 "sub z8.b, z8.b, z12.b\n"
500 ".inst 0x05272e42 // tbx z2.b, z18.b, z7.b\n"
501 "sub z7.b, z7.b, z12.b\n"
502 ".inst 0x05262e41 // tbx z1.b, z18.b, z6.b\n"
503 "sub z6.b, z6.b, z12.b\n"
504 ".inst 0x05252e40 // tbx z0.b, z18.b, z5.b\n"
505 "sub z5.b, z5.b, z12.b\n"
506 "cmp x21, XZR\n"
507 ".inst 0x052b2e69 // tbx z9.b, z19.b, z11.b\n"
508 ".inst 0x052a2e64 // tbx z4.b, z19.b, z10.b\n"
509 ".inst 0x05282e63 // tbx z3.b, z19.b, z8.b\n"
510 "st1b { z9.b }, p5, [x22]\n"
511 ".inst 0x05272e62 // tbx z2.b, z19.b, z7.b\n"
512 ".inst 0x05262e61 // tbx z1.b, z19.b, z6.b\n"
513 "st1b { z4.b }, p4, [x22, #1, MUL VL]\n"
514 ".inst 0x05252e60 // tbx z0.b, z19.b, z5.b\n"
515 "st1b { z3.b }, p3, [x22, #2, MUL VL]\n"
516 "addvl x23, x23, #6\n"
517 "st1b { z2.b }, p2, [x22, #3, MUL VL]\n"
518 "st1b { z1.b }, p1, [x22, #4, MUL VL]\n"
519 "st1b { z0.b }, p0, [x22, #5, MUL VL]\n"
520 "addvl x22, x22, #6\n"
521 "bgt 9b\n"
522 "b 17f\n"
523 "11:" // 1024 bits
524 "mov z12.b, #0x80\n"
525 "mov x21, %x[string_length]\n"
526 "ptrue p5.b\n"
527 "ptrue p4.b\n"
528 "ptrue p3.b\n"
529 "ptrue p2.b\n"
530 "ptrue p1.b\n"
531 "ptrue p0.b\n"
532 "12:" // 2 rounds: width loop
533 "addvl x20, x21, #-6\n"
534 "cmp x20, XZR\n"
535 "bge 13f\n"
536 "mov x20, #0x0\n"
537 "addvl x20, x20, #1\n"
538 "whilelt p5.b, XZR, x21\n"
539 "whilelt p4.b, x20, x21\n"
540 "addvl x20, x20, #1\n"
541 "whilelt p3.b, x20, x21\n"
542 "addvl x20, x20, #1\n"
543 "whilelt p2.b, x20, x21\n"
544 "addvl x20, x20, #1\n"
545 "whilelt p1.b, x20, x21\n"
546 "addvl x20, x20, #1\n"
547 "whilelt p0.b, x20, x21\n"
548 "13:" // 2 rounds: predicate OK
549 "ld1b { z11.b }, p5/Z, [x23]\n"
550 "ld1b { z10.b }, p4/Z, [x23, #1, MUL VL]\n"
551 "addvl x21, x21, #-6\n"
552 "ld1b { z8.b }, p3/Z, [x23, #2, MUL VL]\n"
553 "ld1b { z7.b }, p2/Z, [x23, #3, MUL VL]\n"
554 "tbl z9.b, { z16.b }, z11.b\n"
555 "ld1b { z6.b }, p1/Z, [x23, #4, MUL VL]\n"
556 "ld1b { z5.b }, p0/Z, [x23, #5, MUL VL]\n"
557 "sub z11.b, z11.b, z12.b\n"
558 "tbl z4.b, { z16.b }, z10.b\n"
559 "sub z10.b, z10.b, z12.b\n"
560 "tbl z3.b, { z16.b }, z8.b\n"
561 "sub z8.b, z8.b, z12.b\n"
562 "tbl z2.b, { z16.b }, z7.b\n"
563 "sub z7.b, z7.b, z12.b\n"
564 "tbl z1.b, { z16.b }, z6.b\n"
565 "sub z6.b, z6.b, z12.b\n"
566 "tbl z0.b, { z16.b }, z5.b\n"
567 "sub z5.b, z5.b, z12.b\n"
568 "cmp x21, XZR\n"
569 ".inst 0x052b2e29 // tbx z9.b, z17.b, z11.b\n"
570 ".inst 0x052a2e24 // tbx z4.b, z17.b, z10.b\n"
571 ".inst 0x05282e23 // tbx z3.b, z17.b, z8.b\n"
572 "st1b { z9.b }, p5, [x22]\n"
573 ".inst 0x05272e22 // tbx z2.b, z17.b, z7.b\n"
574 ".inst 0x05262e21 // tbx z1.b, z17.b, z6.b\n"
575 "st1b { z4.b }, p4, [x22, #1, MUL VL]\n"
576 ".inst 0x05252e20 // tbx z0.b, z17.b, z5.b\n"
577 "st1b { z3.b }, p3, [x22, #2, MUL VL]\n"
578 "addvl x23, x23, #6\n"
579 "st1b { z2.b }, p2, [x22, #3, MUL VL]\n"
580 "st1b { z1.b }, p1, [x22, #4, MUL VL]\n"
581 "st1b { z0.b }, p0, [x22, #5, MUL VL]\n"
582 "addvl x22, x22, #6\n"
583 "bgt 12b\n"
584 "b 17f\n"
585 "14:" // 2048 bits
586 "mov x21, %x[string_length]\n"
587 "ptrue p5.b\n"
588 "ptrue p4.b\n"
589 "ptrue p3.b\n"
590 "ptrue p2.b\n"
591 "ptrue p1.b\n"
592 "ptrue p0.b\n"
593 "15:" // 1 rounds: width loop
594 "addvl x20, x21, #-6\n"
595 "cmp x20, XZR\n"
596 "bge 16f\n"
597 "mov x20, #0x0\n"
598 "addvl x20, x20, #1\n"
599 "whilelt p5.b, XZR, x21\n"
600 "whilelt p4.b, x20, x21\n"
601 "addvl x20, x20, #1\n"
602 "whilelt p3.b, x20, x21\n"
603 "addvl x20, x20, #1\n"
604 "whilelt p2.b, x20, x21\n"
605 "addvl x20, x20, #1\n"
606 "whilelt p1.b, x20, x21\n"
607 "addvl x20, x20, #1\n"
608 "whilelt p0.b, x20, x21\n"
609 "16:" // 1 rounds: predicate OK
610 "addvl x21, x21, #-6\n"
611 "ld1b { z11.b }, p5/Z, [x23]\n"
612 "ld1b { z10.b }, p4/Z, [x23, #1, MUL VL]\n"
613 "ld1b { z8.b }, p3/Z, [x23, #2, MUL VL]\n"
614 "ld1b { z7.b }, p2/Z, [x23, #3, MUL VL]\n"
615 "cmp x21, XZR\n"
616 "ld1b { z6.b }, p1/Z, [x23, #4, MUL VL]\n"
617 "ld1b { z5.b }, p0/Z, [x23, #5, MUL VL]\n"
618 "tbl z9.b, { z16.b }, z11.b\n"
619 "tbl z4.b, { z16.b }, z10.b\n"
620 "tbl z3.b, { z16.b }, z8.b\n"
621 "st1b { z9.b }, p5, [x22]\n"
622 "tbl z2.b, { z16.b }, z7.b\n"
623 "tbl z1.b, { z16.b }, z6.b\n"
624 "st1b { z4.b }, p4, [x22, #1, MUL VL]\n"
625 "tbl z0.b, { z16.b }, z5.b\n"
626 "st1b { z3.b }, p3, [x22, #2, MUL VL]\n"
627 "addvl x23, x23, #6\n"
628 "st1b { z2.b }, p2, [x22, #3, MUL VL]\n"
629 "st1b { z1.b }, p1, [x22, #4, MUL VL]\n"
630 "st1b { z0.b }, p0, [x22, #5, MUL VL]\n"
631 "addvl x22, x22, #6\n"
632 "bgt 15b\n"
633 "17:" // SVE body done
634 "add x24, x24, #0x1\n"
635 "cmp x24, %x[num_strings]\n"
636 "bne 2b\n"
637 : [table] "+&r"(table)
638 : [input] "r"(input), [num_strings] "r"(num_strings), [output] "r"(output), [string_length] "r"(string_length)
639 : "cc", "memory", "p0", "p1", "p2", "p3", "p4", "p5", "x20", "x21", "x22", "x23", "x24", "x25", "z0", "z1", "z2", "z3", "z4", "z5", "z6", "z7", "z8", "z9", "z10", "z11", "z12", "z16", "z17", "z18", "z19", "z20", "z21", "z22", "z23", "z24", "z25", "z26", "z27", "z28", "z29", "z30", "z31");
640}
641
642} // namespace cpu
643} // namespace arm_compute
644
645#endif // ARM_COMPUTE_ENABLE_SVE
646#endif // __aarch64__