1 // Copyright 2016 The Gemmlowp Authors. All Rights Reserved.
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 // http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14
15 #ifndef GEMMLOWP_META_STREAMS_ARM_32_H_
16 #define GEMMLOWP_META_STREAMS_ARM_32_H_
17
18 #ifdef GEMMLOWP_NEON_32
19
20 #include <cassert>
21 #include <cstdint>
22
23 namespace gemmlowp {
24 namespace meta {
25
26 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)27 inline void Stream<uint8_t, 1, 8, 0, RowMajorWithSum>::Pack(
28 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
29 #ifdef DEBUG
30 #ifdef DEBUG_METAGEMM_VERBOSE
31 std::cout << __FILE__ << "(" << __LINE__
32 << ") RowMajorWithSum<uint8_t, 1, 8, 0, RowMajorWithSum>::Pack()"
33 << std::endl
34 << std::flush;
35 #endif
36 #endif
37 int params_count_copy = params.count;
38 asm volatile(
39 "vmov.i16 q8, #0\n"
40
41 "1:"
42 "subs %[count], %[count], #8\n"
43
44 // Load Aggregate Store: 1x8.
45 "vld1.32 {d0}, [%[in]]!\n"
46 "vaddw.u8 q8, q8, d0\n"
47 "vst1.32 {d0}, [%[out]:64]!\n"
48
49 "bne 1b\n"
50
51 // Aggregator Reduction.
52 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
53 "vdup.32 q1, %[additive_sum_offset]\n"
54 "vpaddl.u16 q8, q8\n"
55 "vpadd.u32 d16, d16, d17\n"
56 "vpadd.u32 d16, d16, d16\n"
57 "vmul.i32 q8, q8, d0[0]\n"
58 "vadd.i32 q8, q8, q1\n"
59 "vst1.32 {d16, d17}, [%[out]:64]\n"
60 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
61 : [stride] "r"(params.stride),
62 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
63 [additive_sum_offset] "r"(params.additive_sum_offset)
64 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
65 }
66
67 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)68 inline void Stream<uint8_t, 1, 8, 1, RowMajorWithSum>::Pack(
69 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
70 #ifdef DEBUG
71 #ifdef DEBUG_METAGEMM_VERBOSE
72 std::cout << __FILE__ << "(" << __LINE__
73 << ") RowMajorWithSum<uint8_t, 1, 8, 1, RowMajorWithSum>::Pack()"
74 << std::endl
75 << std::flush;
76 #endif
77 #endif
78 int params_count_copy = params.count;
79 asm volatile(
80 "vmov.i16 q8, #0\n"
81
82 // Reduce count by leftovers.
83 "subs %[count], %[count], #1\n"
84 "beq 2f\n"
85
86 "1:"
87 "subs %[count], %[count], #8\n"
88
89 // Load Aggregate Store: 1x8.
90 "vld1.32 {d0}, [%[in]]!\n"
91 "vaddw.u8 q8, q8, d0\n"
92 "vst1.32 {d0}, [%[out]:64]!\n"
93
94 "bne 1b\n"
95
96 "2:"
97
98 // Load Aggregate Store: 1x1.
99 "vmov.i8 d0, #0\n"
100 "vld1.8 {d0[0]}, [%[in]]!\n"
101 "vaddw.u8 q8, q8, d0\n"
102 "vst1.32 {d0}, [%[out]:64]!\n"
103
104 // Aggregator Reduction.
105 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
106 "vdup.32 q1, %[additive_sum_offset]\n"
107 "vpaddl.u16 q8, q8\n"
108 "vpadd.u32 d16, d16, d17\n"
109 "vpadd.u32 d16, d16, d16\n"
110 "vmul.i32 q8, q8, d0[0]\n"
111 "vadd.i32 q8, q8, q1\n"
112 "vst1.32 {d16, d17}, [%[out]:64]\n"
113 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
114 : [stride] "r"(params.stride),
115 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
116 [additive_sum_offset] "r"(params.additive_sum_offset)
117 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
118 }
119
120 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)121 inline void Stream<uint8_t, 1, 8, 2, RowMajorWithSum>::Pack(
122 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
123 #ifdef DEBUG
124 #ifdef DEBUG_METAGEMM_VERBOSE
125 std::cout << __FILE__ << "(" << __LINE__
126 << ") RowMajorWithSum<uint8_t, 1, 8, 2, RowMajorWithSum>::Pack()"
127 << std::endl
128 << std::flush;
129 #endif
130 #endif
131 int params_count_copy = params.count;
132 asm volatile(
133 "vmov.i16 q8, #0\n"
134
135 // Reduce count by leftovers.
136 "subs %[count], %[count], #2\n"
137 "beq 2f\n"
138
139 "1:"
140 "subs %[count], %[count], #8\n"
141
142 // Load Aggregate Store: 1x8.
143 "vld1.32 {d0}, [%[in]]!\n"
144 "vaddw.u8 q8, q8, d0\n"
145 "vst1.32 {d0}, [%[out]:64]!\n"
146
147 "bne 1b\n"
148
149 "2:"
150
151 // Load Aggregate Store: 1x2.
152 "vmov.i8 d0, #0\n"
153 "vld1.16 {d0[0]}, [%[in]]!\n"
154 "vaddw.u8 q8, q8, d0\n"
155 "vst1.32 {d0}, [%[out]:64]!\n"
156
157 // Aggregator Reduction.
158 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
159 "vdup.32 q1, %[additive_sum_offset]\n"
160 "vpaddl.u16 q8, q8\n"
161 "vpadd.u32 d16, d16, d17\n"
162 "vpadd.u32 d16, d16, d16\n"
163 "vmul.i32 q8, q8, d0[0]\n"
164 "vadd.i32 q8, q8, q1\n"
165 "vst1.32 {d16, d17}, [%[out]:64]\n"
166 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
167 : [stride] "r"(params.stride),
168 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
169 [additive_sum_offset] "r"(params.additive_sum_offset)
170 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
171 }
172
173 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)174 inline void Stream<uint8_t, 1, 8, 3, RowMajorWithSum>::Pack(
175 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
176 #ifdef DEBUG
177 #ifdef DEBUG_METAGEMM_VERBOSE
178 std::cout << __FILE__ << "(" << __LINE__
179 << ") RowMajorWithSum<uint8_t, 1, 8, 3, RowMajorWithSum>::Pack()"
180 << std::endl
181 << std::flush;
182 #endif
183 #endif
184 int params_count_copy = params.count;
185 asm volatile(
186 "vmov.i16 q8, #0\n"
187
188 // Reduce count by leftovers.
189 "subs %[count], %[count], #3\n"
190 "beq 2f\n"
191
192 "1:"
193 "subs %[count], %[count], #8\n"
194
195 // Load Aggregate Store: 1x8.
196 "vld1.32 {d0}, [%[in]]!\n"
197 "vaddw.u8 q8, q8, d0\n"
198 "vst1.32 {d0}, [%[out]:64]!\n"
199
200 "bne 1b\n"
201
202 "2:"
203
204 // Load Aggregate Store: 1x3.
205 "vmov.i8 d0, #0\n"
206 "vld1.16 {d0[0]}, [%[in]]!\n"
207 "vld1.8 {d0[2]}, [%[in]]!\n"
208 "vaddw.u8 q8, q8, d0\n"
209 "vst1.32 {d0}, [%[out]:64]!\n"
210
211 // Aggregator Reduction.
212 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
213 "vdup.32 q1, %[additive_sum_offset]\n"
214 "vpaddl.u16 q8, q8\n"
215 "vpadd.u32 d16, d16, d17\n"
216 "vpadd.u32 d16, d16, d16\n"
217 "vmul.i32 q8, q8, d0[0]\n"
218 "vadd.i32 q8, q8, q1\n"
219 "vst1.32 {d16, d17}, [%[out]:64]\n"
220 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
221 : [stride] "r"(params.stride),
222 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
223 [additive_sum_offset] "r"(params.additive_sum_offset)
224 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
225 }
226
227 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)228 inline void Stream<uint8_t, 1, 8, 4, RowMajorWithSum>::Pack(
229 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
230 #ifdef DEBUG
231 #ifdef DEBUG_METAGEMM_VERBOSE
232 std::cout << __FILE__ << "(" << __LINE__
233 << ") RowMajorWithSum<uint8_t, 1, 8, 4, RowMajorWithSum>::Pack()"
234 << std::endl
235 << std::flush;
236 #endif
237 #endif
238 int params_count_copy = params.count;
239 asm volatile(
240 "vmov.i16 q8, #0\n"
241
242 // Reduce count by leftovers.
243 "subs %[count], %[count], #4\n"
244 "beq 2f\n"
245
246 "1:"
247 "subs %[count], %[count], #8\n"
248
249 // Load Aggregate Store: 1x8.
250 "vld1.32 {d0}, [%[in]]!\n"
251 "vaddw.u8 q8, q8, d0\n"
252 "vst1.32 {d0}, [%[out]:64]!\n"
253
254 "bne 1b\n"
255
256 "2:"
257
258 // Load Aggregate Store: 1x4.
259 "vmov.i8 d0, #0\n"
260 "vld1.32 {d0[0]}, [%[in]]!\n"
261 "vaddw.u8 q8, q8, d0\n"
262 "vst1.32 {d0}, [%[out]:64]!\n"
263
264 // Aggregator Reduction.
265 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
266 "vdup.32 q1, %[additive_sum_offset]\n"
267 "vpaddl.u16 q8, q8\n"
268 "vpadd.u32 d16, d16, d17\n"
269 "vpadd.u32 d16, d16, d16\n"
270 "vmul.i32 q8, q8, d0[0]\n"
271 "vadd.i32 q8, q8, q1\n"
272 "vst1.32 {d16, d17}, [%[out]:64]\n"
273 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
274 : [stride] "r"(params.stride),
275 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
276 [additive_sum_offset] "r"(params.additive_sum_offset)
277 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
278 }
279
280 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)281 inline void Stream<uint8_t, 1, 8, 5, RowMajorWithSum>::Pack(
282 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
283 #ifdef DEBUG
284 #ifdef DEBUG_METAGEMM_VERBOSE
285 std::cout << __FILE__ << "(" << __LINE__
286 << ") RowMajorWithSum<uint8_t, 1, 8, 5, RowMajorWithSum>::Pack()"
287 << std::endl
288 << std::flush;
289 #endif
290 #endif
291 int params_count_copy = params.count;
292 asm volatile(
293 "vmov.i16 q8, #0\n"
294
295 // Reduce count by leftovers.
296 "subs %[count], %[count], #5\n"
297 "beq 2f\n"
298
299 "1:"
300 "subs %[count], %[count], #8\n"
301
302 // Load Aggregate Store: 1x8.
303 "vld1.32 {d0}, [%[in]]!\n"
304 "vaddw.u8 q8, q8, d0\n"
305 "vst1.32 {d0}, [%[out]:64]!\n"
306
307 "bne 1b\n"
308
309 "2:"
310
311 // Load Aggregate Store: 1x5.
312 "vmov.i8 d0, #0\n"
313 "vld1.32 {d0[0]}, [%[in]]!\n"
314 "vld1.8 {d0[4]}, [%[in]]!\n"
315 "vaddw.u8 q8, q8, d0\n"
316 "vst1.32 {d0}, [%[out]:64]!\n"
317
318 // Aggregator Reduction.
319 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
320 "vdup.32 q1, %[additive_sum_offset]\n"
321 "vpaddl.u16 q8, q8\n"
322 "vpadd.u32 d16, d16, d17\n"
323 "vpadd.u32 d16, d16, d16\n"
324 "vmul.i32 q8, q8, d0[0]\n"
325 "vadd.i32 q8, q8, q1\n"
326 "vst1.32 {d16, d17}, [%[out]:64]\n"
327 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
328 : [stride] "r"(params.stride),
329 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
330 [additive_sum_offset] "r"(params.additive_sum_offset)
331 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
332 }
333
334 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)335 inline void Stream<uint8_t, 1, 8, 6, RowMajorWithSum>::Pack(
336 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
337 #ifdef DEBUG
338 #ifdef DEBUG_METAGEMM_VERBOSE
339 std::cout << __FILE__ << "(" << __LINE__
340 << ") RowMajorWithSum<uint8_t, 1, 8, 6, RowMajorWithSum>::Pack()"
341 << std::endl
342 << std::flush;
343 #endif
344 #endif
345 int params_count_copy = params.count;
346 asm volatile(
347 "vmov.i16 q8, #0\n"
348
349 // Reduce count by leftovers.
350 "subs %[count], %[count], #6\n"
351 "beq 2f\n"
352
353 "1:"
354 "subs %[count], %[count], #8\n"
355
356 // Load Aggregate Store: 1x8.
357 "vld1.32 {d0}, [%[in]]!\n"
358 "vaddw.u8 q8, q8, d0\n"
359 "vst1.32 {d0}, [%[out]:64]!\n"
360
361 "bne 1b\n"
362
363 "2:"
364
365 // Load Aggregate Store: 1x6.
366 "vmov.i8 d0, #0\n"
367 "vld1.32 {d0[0]}, [%[in]]!\n"
368 "vld1.16 {d0[2]}, [%[in]]!\n"
369 "vaddw.u8 q8, q8, d0\n"
370 "vst1.32 {d0}, [%[out]:64]!\n"
371
372 // Aggregator Reduction.
373 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
374 "vdup.32 q1, %[additive_sum_offset]\n"
375 "vpaddl.u16 q8, q8\n"
376 "vpadd.u32 d16, d16, d17\n"
377 "vpadd.u32 d16, d16, d16\n"
378 "vmul.i32 q8, q8, d0[0]\n"
379 "vadd.i32 q8, q8, q1\n"
380 "vst1.32 {d16, d17}, [%[out]:64]\n"
381 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
382 : [stride] "r"(params.stride),
383 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
384 [additive_sum_offset] "r"(params.additive_sum_offset)
385 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
386 }
387
388 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)389 inline void Stream<uint8_t, 1, 8, 7, RowMajorWithSum>::Pack(
390 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
391 #ifdef DEBUG
392 #ifdef DEBUG_METAGEMM_VERBOSE
393 std::cout << __FILE__ << "(" << __LINE__
394 << ") RowMajorWithSum<uint8_t, 1, 8, 7, RowMajorWithSum>::Pack()"
395 << std::endl
396 << std::flush;
397 #endif
398 #endif
399 int params_count_copy = params.count;
400 asm volatile(
401 "vmov.i16 q8, #0\n"
402
403 // Reduce count by leftovers.
404 "subs %[count], %[count], #7\n"
405 "beq 2f\n"
406
407 "1:"
408 "subs %[count], %[count], #8\n"
409
410 // Load Aggregate Store: 1x8.
411 "vld1.32 {d0}, [%[in]]!\n"
412 "vaddw.u8 q8, q8, d0\n"
413 "vst1.32 {d0}, [%[out]:64]!\n"
414
415 "bne 1b\n"
416
417 "2:"
418
419 // Load Aggregate Store: 1x7.
420 "vmov.i8 d0, #0\n"
421 "vld1.32 {d0[0]}, [%[in]]!\n"
422 "vld1.16 {d0[2]}, [%[in]]!\n"
423 "vld1.8 {d0[6]}, [%[in]]!\n"
424 "vaddw.u8 q8, q8, d0\n"
425 "vst1.32 {d0}, [%[out]:64]!\n"
426
427 // Aggregator Reduction.
428 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
429 "vdup.32 q1, %[additive_sum_offset]\n"
430 "vpaddl.u16 q8, q8\n"
431 "vpadd.u32 d16, d16, d17\n"
432 "vpadd.u32 d16, d16, d16\n"
433 "vmul.i32 q8, q8, d0[0]\n"
434 "vadd.i32 q8, q8, q1\n"
435 "vst1.32 {d16, d17}, [%[out]:64]\n"
436 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
437 : [stride] "r"(params.stride),
438 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
439 [additive_sum_offset] "r"(params.additive_sum_offset)
440 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
441 }
442
443 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)444 inline void Stream<uint8_t, 2, 8, 0, RowMajorWithSum>::Pack(
445 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
446 #ifdef DEBUG
447 #ifdef DEBUG_METAGEMM_VERBOSE
448 std::cout << __FILE__ << "(" << __LINE__
449 << ") RowMajorWithSum<uint8_t, 2, 8, 0, RowMajorWithSum>::Pack()"
450 << std::endl
451 << std::flush;
452 #endif
453 #endif
454 int params_count_copy = params.count;
455 asm volatile(
456 "add r0, %[in], %[stride]\n"
457 "vmov.i16 q8, #0\n"
458 "vmov.i16 q9, #0\n"
459
460 "1:"
461 "subs %[count], %[count], #8\n"
462
463 // Load Aggregate Store: 2x8.
464 "vld1.32 {d0}, [%[in]]!\n"
465 "vld1.32 {d1}, [r0]!\n"
466 "vaddw.u8 q8, q8, d0\n"
467 "vaddw.u8 q9, q9, d1\n"
468 "vst1.32 {d0, d1}, [%[out]:128]!\n"
469
470 "bne 1b\n"
471
472 // Aggregator Reduction.
473 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
474 "vdup.32 q1, %[additive_sum_offset]\n"
475 "vpaddl.u16 q8, q8\n"
476 "vpaddl.u16 q9, q9\n"
477 "vpadd.u32 d16, d16, d17\n"
478 "vpadd.u32 d18, d18, d19\n"
479 "vpadd.u32 d16, d16, d18\n"
480 "vmul.i32 q8, q8, d0[0]\n"
481 "vadd.i32 q8, q8, q1\n"
482 "vst1.32 {d16, d17}, [%[out]:128]\n"
483 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
484 : [stride] "r"(params.stride),
485 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
486 [additive_sum_offset] "r"(params.additive_sum_offset)
487 : "r0", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc",
488 "memory");
489 }
490
491 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)492 inline void Stream<uint8_t, 2, 8, 1, RowMajorWithSum>::Pack(
493 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
494 #ifdef DEBUG
495 #ifdef DEBUG_METAGEMM_VERBOSE
496 std::cout << __FILE__ << "(" << __LINE__
497 << ") RowMajorWithSum<uint8_t, 2, 8, 1, RowMajorWithSum>::Pack()"
498 << std::endl
499 << std::flush;
500 #endif
501 #endif
502 int params_count_copy = params.count;
503 asm volatile(
504 "add r0, %[in], %[stride]\n"
505 "vmov.i16 q8, #0\n"
506 "vmov.i16 q9, #0\n"
507
508 // Reduce count by leftovers.
509 "subs %[count], %[count], #1\n"
510 "beq 2f\n"
511
512 "1:"
513 "subs %[count], %[count], #8\n"
514
515 // Load Aggregate Store: 2x8.
516 "vld1.32 {d0}, [%[in]]!\n"
517 "vld1.32 {d1}, [r0]!\n"
518 "vaddw.u8 q8, q8, d0\n"
519 "vaddw.u8 q9, q9, d1\n"
520 "vst1.32 {d0, d1}, [%[out]:128]!\n"
521
522 "bne 1b\n"
523
524 "2:"
525
526 // Load Aggregate Store: 2x1.
527 "vmov.i8 d0, #0\n"
528 "vmov.i8 d1, #0\n"
529 "vld1.8 {d0[0]}, [%[in]]!\n"
530 "vld1.8 {d1[0]}, [r0]!\n"
531 "vaddw.u8 q8, q8, d0\n"
532 "vaddw.u8 q9, q9, d1\n"
533 "vst1.32 {d0, d1}, [%[out]:128]!\n"
534
535 // Aggregator Reduction.
536 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
537 "vdup.32 q1, %[additive_sum_offset]\n"
538 "vpaddl.u16 q8, q8\n"
539 "vpaddl.u16 q9, q9\n"
540 "vpadd.u32 d16, d16, d17\n"
541 "vpadd.u32 d18, d18, d19\n"
542 "vpadd.u32 d16, d16, d18\n"
543 "vmul.i32 q8, q8, d0[0]\n"
544 "vadd.i32 q8, q8, q1\n"
545 "vst1.32 {d16, d17}, [%[out]:128]\n"
546 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
547 : [stride] "r"(params.stride),
548 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
549 [additive_sum_offset] "r"(params.additive_sum_offset)
550 : "r0", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc",
551 "memory");
552 }
553
554 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)555 inline void Stream<uint8_t, 2, 8, 2, RowMajorWithSum>::Pack(
556 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
557 #ifdef DEBUG
558 #ifdef DEBUG_METAGEMM_VERBOSE
559 std::cout << __FILE__ << "(" << __LINE__
560 << ") RowMajorWithSum<uint8_t, 2, 8, 2, RowMajorWithSum>::Pack()"
561 << std::endl
562 << std::flush;
563 #endif
564 #endif
565 int params_count_copy = params.count;
566 asm volatile(
567 "add r0, %[in], %[stride]\n"
568 "vmov.i16 q8, #0\n"
569 "vmov.i16 q9, #0\n"
570
571 // Reduce count by leftovers.
572 "subs %[count], %[count], #2\n"
573 "beq 2f\n"
574
575 "1:"
576 "subs %[count], %[count], #8\n"
577
578 // Load Aggregate Store: 2x8.
579 "vld1.32 {d0}, [%[in]]!\n"
580 "vld1.32 {d1}, [r0]!\n"
581 "vaddw.u8 q8, q8, d0\n"
582 "vaddw.u8 q9, q9, d1\n"
583 "vst1.32 {d0, d1}, [%[out]:128]!\n"
584
585 "bne 1b\n"
586
587 "2:"
588
589 // Load Aggregate Store: 2x2.
590 "vmov.i8 d0, #0\n"
591 "vmov.i8 d1, #0\n"
592 "vld1.16 {d0[0]}, [%[in]]!\n"
593 "vld1.16 {d1[0]}, [r0]!\n"
594 "vaddw.u8 q8, q8, d0\n"
595 "vaddw.u8 q9, q9, d1\n"
596 "vst1.32 {d0, d1}, [%[out]:128]!\n"
597
598 // Aggregator Reduction.
599 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
600 "vdup.32 q1, %[additive_sum_offset]\n"
601 "vpaddl.u16 q8, q8\n"
602 "vpaddl.u16 q9, q9\n"
603 "vpadd.u32 d16, d16, d17\n"
604 "vpadd.u32 d18, d18, d19\n"
605 "vpadd.u32 d16, d16, d18\n"
606 "vmul.i32 q8, q8, d0[0]\n"
607 "vadd.i32 q8, q8, q1\n"
608 "vst1.32 {d16, d17}, [%[out]:128]\n"
609 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
610 : [stride] "r"(params.stride),
611 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
612 [additive_sum_offset] "r"(params.additive_sum_offset)
613 : "r0", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc",
614 "memory");
615 }
616
617 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)618 inline void Stream<uint8_t, 2, 8, 3, RowMajorWithSum>::Pack(
619 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
620 #ifdef DEBUG
621 #ifdef DEBUG_METAGEMM_VERBOSE
622 std::cout << __FILE__ << "(" << __LINE__
623 << ") RowMajorWithSum<uint8_t, 2, 8, 3, RowMajorWithSum>::Pack()"
624 << std::endl
625 << std::flush;
626 #endif
627 #endif
628 int params_count_copy = params.count;
629 asm volatile(
630 "add r0, %[in], %[stride]\n"
631 "vmov.i16 q8, #0\n"
632 "vmov.i16 q9, #0\n"
633
634 // Reduce count by leftovers.
635 "subs %[count], %[count], #3\n"
636 "beq 2f\n"
637
638 "1:"
639 "subs %[count], %[count], #8\n"
640
641 // Load Aggregate Store: 2x8.
642 "vld1.32 {d0}, [%[in]]!\n"
643 "vld1.32 {d1}, [r0]!\n"
644 "vaddw.u8 q8, q8, d0\n"
645 "vaddw.u8 q9, q9, d1\n"
646 "vst1.32 {d0, d1}, [%[out]:128]!\n"
647
648 "bne 1b\n"
649
650 "2:"
651
652 // Load Aggregate Store: 2x3.
653 "vmov.i8 d0, #0\n"
654 "vmov.i8 d1, #0\n"
655 "vld1.16 {d0[0]}, [%[in]]!\n"
656 "vld1.8 {d0[2]}, [%[in]]!\n"
657 "vld1.16 {d1[0]}, [r0]!\n"
658 "vld1.8 {d1[2]}, [r0]!\n"
659 "vaddw.u8 q8, q8, d0\n"
660 "vaddw.u8 q9, q9, d1\n"
661 "vst1.32 {d0, d1}, [%[out]:128]!\n"
662
663 // Aggregator Reduction.
664 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
665 "vdup.32 q1, %[additive_sum_offset]\n"
666 "vpaddl.u16 q8, q8\n"
667 "vpaddl.u16 q9, q9\n"
668 "vpadd.u32 d16, d16, d17\n"
669 "vpadd.u32 d18, d18, d19\n"
670 "vpadd.u32 d16, d16, d18\n"
671 "vmul.i32 q8, q8, d0[0]\n"
672 "vadd.i32 q8, q8, q1\n"
673 "vst1.32 {d16, d17}, [%[out]:128]\n"
674 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
675 : [stride] "r"(params.stride),
676 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
677 [additive_sum_offset] "r"(params.additive_sum_offset)
678 : "r0", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc",
679 "memory");
680 }
681
682 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)683 inline void Stream<uint8_t, 2, 8, 4, RowMajorWithSum>::Pack(
684 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
685 #ifdef DEBUG
686 #ifdef DEBUG_METAGEMM_VERBOSE
687 std::cout << __FILE__ << "(" << __LINE__
688 << ") RowMajorWithSum<uint8_t, 2, 8, 4, RowMajorWithSum>::Pack()"
689 << std::endl
690 << std::flush;
691 #endif
692 #endif
693 int params_count_copy = params.count;
694 asm volatile(
695 "add r0, %[in], %[stride]\n"
696 "vmov.i16 q8, #0\n"
697 "vmov.i16 q9, #0\n"
698
699 // Reduce count by leftovers.
700 "subs %[count], %[count], #4\n"
701 "beq 2f\n"
702
703 "1:"
704 "subs %[count], %[count], #8\n"
705
706 // Load Aggregate Store: 2x8.
707 "vld1.32 {d0}, [%[in]]!\n"
708 "vld1.32 {d1}, [r0]!\n"
709 "vaddw.u8 q8, q8, d0\n"
710 "vaddw.u8 q9, q9, d1\n"
711 "vst1.32 {d0, d1}, [%[out]:128]!\n"
712
713 "bne 1b\n"
714
715 "2:"
716
717 // Load Aggregate Store: 2x4.
718 "vmov.i8 d0, #0\n"
719 "vmov.i8 d1, #0\n"
720 "vld1.32 {d0[0]}, [%[in]]!\n"
721 "vld1.32 {d1[0]}, [r0]!\n"
722 "vaddw.u8 q8, q8, d0\n"
723 "vaddw.u8 q9, q9, d1\n"
724 "vst1.32 {d0, d1}, [%[out]:128]!\n"
725
726 // Aggregator Reduction.
727 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
728 "vdup.32 q1, %[additive_sum_offset]\n"
729 "vpaddl.u16 q8, q8\n"
730 "vpaddl.u16 q9, q9\n"
731 "vpadd.u32 d16, d16, d17\n"
732 "vpadd.u32 d18, d18, d19\n"
733 "vpadd.u32 d16, d16, d18\n"
734 "vmul.i32 q8, q8, d0[0]\n"
735 "vadd.i32 q8, q8, q1\n"
736 "vst1.32 {d16, d17}, [%[out]:128]\n"
737 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
738 : [stride] "r"(params.stride),
739 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
740 [additive_sum_offset] "r"(params.additive_sum_offset)
741 : "r0", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc",
742 "memory");
743 }
744
745 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)746 inline void Stream<uint8_t, 2, 8, 5, RowMajorWithSum>::Pack(
747 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
748 #ifdef DEBUG
749 #ifdef DEBUG_METAGEMM_VERBOSE
750 std::cout << __FILE__ << "(" << __LINE__
751 << ") RowMajorWithSum<uint8_t, 2, 8, 5, RowMajorWithSum>::Pack()"
752 << std::endl
753 << std::flush;
754 #endif
755 #endif
756 int params_count_copy = params.count;
757 asm volatile(
758 "add r0, %[in], %[stride]\n"
759 "vmov.i16 q8, #0\n"
760 "vmov.i16 q9, #0\n"
761
762 // Reduce count by leftovers.
763 "subs %[count], %[count], #5\n"
764 "beq 2f\n"
765
766 "1:"
767 "subs %[count], %[count], #8\n"
768
769 // Load Aggregate Store: 2x8.
770 "vld1.32 {d0}, [%[in]]!\n"
771 "vld1.32 {d1}, [r0]!\n"
772 "vaddw.u8 q8, q8, d0\n"
773 "vaddw.u8 q9, q9, d1\n"
774 "vst1.32 {d0, d1}, [%[out]:128]!\n"
775
776 "bne 1b\n"
777
778 "2:"
779
780 // Load Aggregate Store: 2x5.
781 "vmov.i8 d0, #0\n"
782 "vmov.i8 d1, #0\n"
783 "vld1.32 {d0[0]}, [%[in]]!\n"
784 "vld1.8 {d0[4]}, [%[in]]!\n"
785 "vld1.32 {d1[0]}, [r0]!\n"
786 "vld1.8 {d1[4]}, [r0]!\n"
787 "vaddw.u8 q8, q8, d0\n"
788 "vaddw.u8 q9, q9, d1\n"
789 "vst1.32 {d0, d1}, [%[out]:128]!\n"
790
791 // Aggregator Reduction.
792 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
793 "vdup.32 q1, %[additive_sum_offset]\n"
794 "vpaddl.u16 q8, q8\n"
795 "vpaddl.u16 q9, q9\n"
796 "vpadd.u32 d16, d16, d17\n"
797 "vpadd.u32 d18, d18, d19\n"
798 "vpadd.u32 d16, d16, d18\n"
799 "vmul.i32 q8, q8, d0[0]\n"
800 "vadd.i32 q8, q8, q1\n"
801 "vst1.32 {d16, d17}, [%[out]:128]\n"
802 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
803 : [stride] "r"(params.stride),
804 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
805 [additive_sum_offset] "r"(params.additive_sum_offset)
806 : "r0", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc",
807 "memory");
808 }
809
810 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)811 inline void Stream<uint8_t, 2, 8, 6, RowMajorWithSum>::Pack(
812 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
813 #ifdef DEBUG
814 #ifdef DEBUG_METAGEMM_VERBOSE
815 std::cout << __FILE__ << "(" << __LINE__
816 << ") RowMajorWithSum<uint8_t, 2, 8, 6, RowMajorWithSum>::Pack()"
817 << std::endl
818 << std::flush;
819 #endif
820 #endif
821 int params_count_copy = params.count;
822 asm volatile(
823 "add r0, %[in], %[stride]\n"
824 "vmov.i16 q8, #0\n"
825 "vmov.i16 q9, #0\n"
826
827 // Reduce count by leftovers.
828 "subs %[count], %[count], #6\n"
829 "beq 2f\n"
830
831 "1:"
832 "subs %[count], %[count], #8\n"
833
834 // Load Aggregate Store: 2x8.
835 "vld1.32 {d0}, [%[in]]!\n"
836 "vld1.32 {d1}, [r0]!\n"
837 "vaddw.u8 q8, q8, d0\n"
838 "vaddw.u8 q9, q9, d1\n"
839 "vst1.32 {d0, d1}, [%[out]:128]!\n"
840
841 "bne 1b\n"
842
843 "2:"
844
845 // Load Aggregate Store: 2x6.
846 "vmov.i8 d0, #0\n"
847 "vmov.i8 d1, #0\n"
848 "vld1.32 {d0[0]}, [%[in]]!\n"
849 "vld1.16 {d0[2]}, [%[in]]!\n"
850 "vld1.32 {d1[0]}, [r0]!\n"
851 "vld1.16 {d1[2]}, [r0]!\n"
852 "vaddw.u8 q8, q8, d0\n"
853 "vaddw.u8 q9, q9, d1\n"
854 "vst1.32 {d0, d1}, [%[out]:128]!\n"
855
856 // Aggregator Reduction.
857 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
858 "vdup.32 q1, %[additive_sum_offset]\n"
859 "vpaddl.u16 q8, q8\n"
860 "vpaddl.u16 q9, q9\n"
861 "vpadd.u32 d16, d16, d17\n"
862 "vpadd.u32 d18, d18, d19\n"
863 "vpadd.u32 d16, d16, d18\n"
864 "vmul.i32 q8, q8, d0[0]\n"
865 "vadd.i32 q8, q8, q1\n"
866 "vst1.32 {d16, d17}, [%[out]:128]\n"
867 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
868 : [stride] "r"(params.stride),
869 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
870 [additive_sum_offset] "r"(params.additive_sum_offset)
871 : "r0", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc",
872 "memory");
873 }
874
875 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)876 inline void Stream<uint8_t, 2, 8, 7, RowMajorWithSum>::Pack(
877 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
878 #ifdef DEBUG
879 #ifdef DEBUG_METAGEMM_VERBOSE
880 std::cout << __FILE__ << "(" << __LINE__
881 << ") RowMajorWithSum<uint8_t, 2, 8, 7, RowMajorWithSum>::Pack()"
882 << std::endl
883 << std::flush;
884 #endif
885 #endif
886 int params_count_copy = params.count;
887 asm volatile(
888 "add r0, %[in], %[stride]\n"
889 "vmov.i16 q8, #0\n"
890 "vmov.i16 q9, #0\n"
891
892 // Reduce count by leftovers.
893 "subs %[count], %[count], #7\n"
894 "beq 2f\n"
895
896 "1:"
897 "subs %[count], %[count], #8\n"
898
899 // Load Aggregate Store: 2x8.
900 "vld1.32 {d0}, [%[in]]!\n"
901 "vld1.32 {d1}, [r0]!\n"
902 "vaddw.u8 q8, q8, d0\n"
903 "vaddw.u8 q9, q9, d1\n"
904 "vst1.32 {d0, d1}, [%[out]:128]!\n"
905
906 "bne 1b\n"
907
908 "2:"
909
910 // Load Aggregate Store: 2x7.
911 "vmov.i8 d0, #0\n"
912 "vmov.i8 d1, #0\n"
913 "vld1.32 {d0[0]}, [%[in]]!\n"
914 "vld1.16 {d0[2]}, [%[in]]!\n"
915 "vld1.8 {d0[6]}, [%[in]]!\n"
916 "vld1.32 {d1[0]}, [r0]!\n"
917 "vld1.16 {d1[2]}, [r0]!\n"
918 "vld1.8 {d1[6]}, [r0]!\n"
919 "vaddw.u8 q8, q8, d0\n"
920 "vaddw.u8 q9, q9, d1\n"
921 "vst1.32 {d0, d1}, [%[out]:128]!\n"
922
923 // Aggregator Reduction.
924 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
925 "vdup.32 q1, %[additive_sum_offset]\n"
926 "vpaddl.u16 q8, q8\n"
927 "vpaddl.u16 q9, q9\n"
928 "vpadd.u32 d16, d16, d17\n"
929 "vpadd.u32 d18, d18, d19\n"
930 "vpadd.u32 d16, d16, d18\n"
931 "vmul.i32 q8, q8, d0[0]\n"
932 "vadd.i32 q8, q8, q1\n"
933 "vst1.32 {d16, d17}, [%[out]:128]\n"
934 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
935 : [stride] "r"(params.stride),
936 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
937 [additive_sum_offset] "r"(params.additive_sum_offset)
938 : "r0", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc",
939 "memory");
940 }
941
942 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)943 inline void Stream<uint8_t, 3, 8, 0, RowMajorWithSum>::Pack(
944 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
945 #ifdef DEBUG
946 #ifdef DEBUG_METAGEMM_VERBOSE
947 std::cout << __FILE__ << "(" << __LINE__
948 << ") RowMajorWithSum<uint8_t, 3, 8, 0, RowMajorWithSum>::Pack()"
949 << std::endl
950 << std::flush;
951 #endif
952 #endif
953 int params_count_copy = params.count;
954 asm volatile(
955 "add r0, %[in], %[stride]\n"
956 "add r1, r0, %[stride]\n"
957 "vmov.i16 q8, #0\n"
958 "vmov.i16 q9, #0\n"
959 "vmov.i16 q10, #0\n"
960
961 "1:"
962 "subs %[count], %[count], #8\n"
963
964 // Load Aggregate Store: 3x8.
965 "vld1.32 {d0}, [%[in]]!\n"
966 "vld1.32 {d1}, [r0]!\n"
967 "vld1.32 {d2}, [r1]!\n"
968 "vaddw.u8 q8, q8, d0\n"
969 "vaddw.u8 q9, q9, d1\n"
970 "vaddw.u8 q10, q10, d2\n"
971 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
972
973 "bne 1b\n"
974
975 // Aggregator Reduction.
976 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
977 "vdup.32 q1, %[additive_sum_offset]\n"
978 "vpaddl.u16 q8, q8\n"
979 "vpaddl.u16 q9, q9\n"
980 "vpaddl.u16 q10, q10\n"
981 "vpadd.u32 d16, d16, d17\n"
982 "vpadd.u32 d18, d18, d19\n"
983 "vpadd.u32 d20, d20, d21\n"
984 "vpadd.u32 d16, d16, d18\n"
985 "vpadd.u32 d17, d20, d20\n"
986 "vmul.i32 q8, q8, d0[0]\n"
987 "vadd.i32 q8, q8, q1\n"
988 "vst1.32 {d16, d17}, [%[out]:64]\n"
989 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
990 : [stride] "r"(params.stride),
991 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
992 [additive_sum_offset] "r"(params.additive_sum_offset)
993 : "r0", "r1", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20",
994 "d21", "cc", "memory");
995 }
996
997 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)998 inline void Stream<uint8_t, 3, 8, 1, RowMajorWithSum>::Pack(
999 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
1000 #ifdef DEBUG
1001 #ifdef DEBUG_METAGEMM_VERBOSE
1002 std::cout << __FILE__ << "(" << __LINE__
1003 << ") RowMajorWithSum<uint8_t, 3, 8, 1, RowMajorWithSum>::Pack()"
1004 << std::endl
1005 << std::flush;
1006 #endif
1007 #endif
1008 int params_count_copy = params.count;
1009 asm volatile(
1010 "add r0, %[in], %[stride]\n"
1011 "add r1, r0, %[stride]\n"
1012 "vmov.i16 q8, #0\n"
1013 "vmov.i16 q9, #0\n"
1014 "vmov.i16 q10, #0\n"
1015
1016 // Reduce count by leftovers.
1017 "subs %[count], %[count], #1\n"
1018 "beq 2f\n"
1019
1020 "1:"
1021 "subs %[count], %[count], #8\n"
1022
1023 // Load Aggregate Store: 3x8.
1024 "vld1.32 {d0}, [%[in]]!\n"
1025 "vld1.32 {d1}, [r0]!\n"
1026 "vld1.32 {d2}, [r1]!\n"
1027 "vaddw.u8 q8, q8, d0\n"
1028 "vaddw.u8 q9, q9, d1\n"
1029 "vaddw.u8 q10, q10, d2\n"
1030 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
1031
1032 "bne 1b\n"
1033
1034 "2:"
1035
1036 // Load Aggregate Store: 3x1.
1037 "vmov.i8 d0, #0\n"
1038 "vmov.i8 d1, #0\n"
1039 "vmov.i8 d2, #0\n"
1040 "vld1.8 {d0[0]}, [%[in]]!\n"
1041 "vld1.8 {d1[0]}, [r0]!\n"
1042 "vld1.8 {d2[0]}, [r1]!\n"
1043 "vaddw.u8 q8, q8, d0\n"
1044 "vaddw.u8 q9, q9, d1\n"
1045 "vaddw.u8 q10, q10, d2\n"
1046 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
1047
1048 // Aggregator Reduction.
1049 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
1050 "vdup.32 q1, %[additive_sum_offset]\n"
1051 "vpaddl.u16 q8, q8\n"
1052 "vpaddl.u16 q9, q9\n"
1053 "vpaddl.u16 q10, q10\n"
1054 "vpadd.u32 d16, d16, d17\n"
1055 "vpadd.u32 d18, d18, d19\n"
1056 "vpadd.u32 d20, d20, d21\n"
1057 "vpadd.u32 d16, d16, d18\n"
1058 "vpadd.u32 d17, d20, d20\n"
1059 "vmul.i32 q8, q8, d0[0]\n"
1060 "vadd.i32 q8, q8, q1\n"
1061 "vst1.32 {d16, d17}, [%[out]:64]\n"
1062 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
1063 : [stride] "r"(params.stride),
1064 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
1065 [additive_sum_offset] "r"(params.additive_sum_offset)
1066 : "r0", "r1", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20",
1067 "d21", "cc", "memory");
1068 }
1069
1070 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)1071 inline void Stream<uint8_t, 3, 8, 2, RowMajorWithSum>::Pack(
1072 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
1073 #ifdef DEBUG
1074 #ifdef DEBUG_METAGEMM_VERBOSE
1075 std::cout << __FILE__ << "(" << __LINE__
1076 << ") RowMajorWithSum<uint8_t, 3, 8, 2, RowMajorWithSum>::Pack()"
1077 << std::endl
1078 << std::flush;
1079 #endif
1080 #endif
1081 int params_count_copy = params.count;
1082 asm volatile(
1083 "add r0, %[in], %[stride]\n"
1084 "add r1, r0, %[stride]\n"
1085 "vmov.i16 q8, #0\n"
1086 "vmov.i16 q9, #0\n"
1087 "vmov.i16 q10, #0\n"
1088
1089 // Reduce count by leftovers.
1090 "subs %[count], %[count], #2\n"
1091 "beq 2f\n"
1092
1093 "1:"
1094 "subs %[count], %[count], #8\n"
1095
1096 // Load Aggregate Store: 3x8.
1097 "vld1.32 {d0}, [%[in]]!\n"
1098 "vld1.32 {d1}, [r0]!\n"
1099 "vld1.32 {d2}, [r1]!\n"
1100 "vaddw.u8 q8, q8, d0\n"
1101 "vaddw.u8 q9, q9, d1\n"
1102 "vaddw.u8 q10, q10, d2\n"
1103 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
1104
1105 "bne 1b\n"
1106
1107 "2:"
1108
1109 // Load Aggregate Store: 3x2.
1110 "vmov.i8 d0, #0\n"
1111 "vmov.i8 d1, #0\n"
1112 "vmov.i8 d2, #0\n"
1113 "vld1.16 {d0[0]}, [%[in]]!\n"
1114 "vld1.16 {d1[0]}, [r0]!\n"
1115 "vld1.16 {d2[0]}, [r1]!\n"
1116 "vaddw.u8 q8, q8, d0\n"
1117 "vaddw.u8 q9, q9, d1\n"
1118 "vaddw.u8 q10, q10, d2\n"
1119 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
1120
1121 // Aggregator Reduction.
1122 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
1123 "vdup.32 q1, %[additive_sum_offset]\n"
1124 "vpaddl.u16 q8, q8\n"
1125 "vpaddl.u16 q9, q9\n"
1126 "vpaddl.u16 q10, q10\n"
1127 "vpadd.u32 d16, d16, d17\n"
1128 "vpadd.u32 d18, d18, d19\n"
1129 "vpadd.u32 d20, d20, d21\n"
1130 "vpadd.u32 d16, d16, d18\n"
1131 "vpadd.u32 d17, d20, d20\n"
1132 "vmul.i32 q8, q8, d0[0]\n"
1133 "vadd.i32 q8, q8, q1\n"
1134 "vst1.32 {d16, d17}, [%[out]:64]\n"
1135 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
1136 : [stride] "r"(params.stride),
1137 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
1138 [additive_sum_offset] "r"(params.additive_sum_offset)
1139 : "r0", "r1", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20",
1140 "d21", "cc", "memory");
1141 }
1142
1143 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)1144 inline void Stream<uint8_t, 3, 8, 3, RowMajorWithSum>::Pack(
1145 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
1146 #ifdef DEBUG
1147 #ifdef DEBUG_METAGEMM_VERBOSE
1148 std::cout << __FILE__ << "(" << __LINE__
1149 << ") RowMajorWithSum<uint8_t, 3, 8, 3, RowMajorWithSum>::Pack()"
1150 << std::endl
1151 << std::flush;
1152 #endif
1153 #endif
1154 int params_count_copy = params.count;
1155 asm volatile(
1156 "add r0, %[in], %[stride]\n"
1157 "add r1, r0, %[stride]\n"
1158 "vmov.i16 q8, #0\n"
1159 "vmov.i16 q9, #0\n"
1160 "vmov.i16 q10, #0\n"
1161
1162 // Reduce count by leftovers.
1163 "subs %[count], %[count], #3\n"
1164 "beq 2f\n"
1165
1166 "1:"
1167 "subs %[count], %[count], #8\n"
1168
1169 // Load Aggregate Store: 3x8.
1170 "vld1.32 {d0}, [%[in]]!\n"
1171 "vld1.32 {d1}, [r0]!\n"
1172 "vld1.32 {d2}, [r1]!\n"
1173 "vaddw.u8 q8, q8, d0\n"
1174 "vaddw.u8 q9, q9, d1\n"
1175 "vaddw.u8 q10, q10, d2\n"
1176 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
1177
1178 "bne 1b\n"
1179
1180 "2:"
1181
1182 // Load Aggregate Store: 3x3.
1183 "vmov.i8 d0, #0\n"
1184 "vmov.i8 d1, #0\n"
1185 "vmov.i8 d2, #0\n"
1186 "vld1.16 {d0[0]}, [%[in]]!\n"
1187 "vld1.8 {d0[2]}, [%[in]]!\n"
1188 "vld1.16 {d1[0]}, [r0]!\n"
1189 "vld1.8 {d1[2]}, [r0]!\n"
1190 "vld1.16 {d2[0]}, [r1]!\n"
1191 "vld1.8 {d2[2]}, [r1]!\n"
1192 "vaddw.u8 q8, q8, d0\n"
1193 "vaddw.u8 q9, q9, d1\n"
1194 "vaddw.u8 q10, q10, d2\n"
1195 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
1196
1197 // Aggregator Reduction.
1198 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
1199 "vdup.32 q1, %[additive_sum_offset]\n"
1200 "vpaddl.u16 q8, q8\n"
1201 "vpaddl.u16 q9, q9\n"
1202 "vpaddl.u16 q10, q10\n"
1203 "vpadd.u32 d16, d16, d17\n"
1204 "vpadd.u32 d18, d18, d19\n"
1205 "vpadd.u32 d20, d20, d21\n"
1206 "vpadd.u32 d16, d16, d18\n"
1207 "vpadd.u32 d17, d20, d20\n"
1208 "vmul.i32 q8, q8, d0[0]\n"
1209 "vadd.i32 q8, q8, q1\n"
1210 "vst1.32 {d16, d17}, [%[out]:64]\n"
1211 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
1212 : [stride] "r"(params.stride),
1213 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
1214 [additive_sum_offset] "r"(params.additive_sum_offset)
1215 : "r0", "r1", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20",
1216 "d21", "cc", "memory");
1217 }
1218
1219 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)1220 inline void Stream<uint8_t, 3, 8, 4, RowMajorWithSum>::Pack(
1221 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
1222 #ifdef DEBUG
1223 #ifdef DEBUG_METAGEMM_VERBOSE
1224 std::cout << __FILE__ << "(" << __LINE__
1225 << ") RowMajorWithSum<uint8_t, 3, 8, 4, RowMajorWithSum>::Pack()"
1226 << std::endl
1227 << std::flush;
1228 #endif
1229 #endif
1230 int params_count_copy = params.count;
1231 asm volatile(
1232 "add r0, %[in], %[stride]\n"
1233 "add r1, r0, %[stride]\n"
1234 "vmov.i16 q8, #0\n"
1235 "vmov.i16 q9, #0\n"
1236 "vmov.i16 q10, #0\n"
1237
1238 // Reduce count by leftovers.
1239 "subs %[count], %[count], #4\n"
1240 "beq 2f\n"
1241
1242 "1:"
1243 "subs %[count], %[count], #8\n"
1244
1245 // Load Aggregate Store: 3x8.
1246 "vld1.32 {d0}, [%[in]]!\n"
1247 "vld1.32 {d1}, [r0]!\n"
1248 "vld1.32 {d2}, [r1]!\n"
1249 "vaddw.u8 q8, q8, d0\n"
1250 "vaddw.u8 q9, q9, d1\n"
1251 "vaddw.u8 q10, q10, d2\n"
1252 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
1253
1254 "bne 1b\n"
1255
1256 "2:"
1257
1258 // Load Aggregate Store: 3x4.
1259 "vmov.i8 d0, #0\n"
1260 "vmov.i8 d1, #0\n"
1261 "vmov.i8 d2, #0\n"
1262 "vld1.32 {d0[0]}, [%[in]]!\n"
1263 "vld1.32 {d1[0]}, [r0]!\n"
1264 "vld1.32 {d2[0]}, [r1]!\n"
1265 "vaddw.u8 q8, q8, d0\n"
1266 "vaddw.u8 q9, q9, d1\n"
1267 "vaddw.u8 q10, q10, d2\n"
1268 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
1269
1270 // Aggregator Reduction.
1271 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
1272 "vdup.32 q1, %[additive_sum_offset]\n"
1273 "vpaddl.u16 q8, q8\n"
1274 "vpaddl.u16 q9, q9\n"
1275 "vpaddl.u16 q10, q10\n"
1276 "vpadd.u32 d16, d16, d17\n"
1277 "vpadd.u32 d18, d18, d19\n"
1278 "vpadd.u32 d20, d20, d21\n"
1279 "vpadd.u32 d16, d16, d18\n"
1280 "vpadd.u32 d17, d20, d20\n"
1281 "vmul.i32 q8, q8, d0[0]\n"
1282 "vadd.i32 q8, q8, q1\n"
1283 "vst1.32 {d16, d17}, [%[out]:64]\n"
1284 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
1285 : [stride] "r"(params.stride),
1286 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
1287 [additive_sum_offset] "r"(params.additive_sum_offset)
1288 : "r0", "r1", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20",
1289 "d21", "cc", "memory");
1290 }
1291
1292 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)1293 inline void Stream<uint8_t, 3, 8, 5, RowMajorWithSum>::Pack(
1294 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
1295 #ifdef DEBUG
1296 #ifdef DEBUG_METAGEMM_VERBOSE
1297 std::cout << __FILE__ << "(" << __LINE__
1298 << ") RowMajorWithSum<uint8_t, 3, 8, 5, RowMajorWithSum>::Pack()"
1299 << std::endl
1300 << std::flush;
1301 #endif
1302 #endif
1303 int params_count_copy = params.count;
1304 asm volatile(
1305 "add r0, %[in], %[stride]\n"
1306 "add r1, r0, %[stride]\n"
1307 "vmov.i16 q8, #0\n"
1308 "vmov.i16 q9, #0\n"
1309 "vmov.i16 q10, #0\n"
1310
1311 // Reduce count by leftovers.
1312 "subs %[count], %[count], #5\n"
1313 "beq 2f\n"
1314
1315 "1:"
1316 "subs %[count], %[count], #8\n"
1317
1318 // Load Aggregate Store: 3x8.
1319 "vld1.32 {d0}, [%[in]]!\n"
1320 "vld1.32 {d1}, [r0]!\n"
1321 "vld1.32 {d2}, [r1]!\n"
1322 "vaddw.u8 q8, q8, d0\n"
1323 "vaddw.u8 q9, q9, d1\n"
1324 "vaddw.u8 q10, q10, d2\n"
1325 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
1326
1327 "bne 1b\n"
1328
1329 "2:"
1330
1331 // Load Aggregate Store: 3x5.
1332 "vmov.i8 d0, #0\n"
1333 "vmov.i8 d1, #0\n"
1334 "vmov.i8 d2, #0\n"
1335 "vld1.32 {d0[0]}, [%[in]]!\n"
1336 "vld1.8 {d0[4]}, [%[in]]!\n"
1337 "vld1.32 {d1[0]}, [r0]!\n"
1338 "vld1.8 {d1[4]}, [r0]!\n"
1339 "vld1.32 {d2[0]}, [r1]!\n"
1340 "vld1.8 {d2[4]}, [r1]!\n"
1341 "vaddw.u8 q8, q8, d0\n"
1342 "vaddw.u8 q9, q9, d1\n"
1343 "vaddw.u8 q10, q10, d2\n"
1344 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
1345
1346 // Aggregator Reduction.
1347 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
1348 "vdup.32 q1, %[additive_sum_offset]\n"
1349 "vpaddl.u16 q8, q8\n"
1350 "vpaddl.u16 q9, q9\n"
1351 "vpaddl.u16 q10, q10\n"
1352 "vpadd.u32 d16, d16, d17\n"
1353 "vpadd.u32 d18, d18, d19\n"
1354 "vpadd.u32 d20, d20, d21\n"
1355 "vpadd.u32 d16, d16, d18\n"
1356 "vpadd.u32 d17, d20, d20\n"
1357 "vmul.i32 q8, q8, d0[0]\n"
1358 "vadd.i32 q8, q8, q1\n"
1359 "vst1.32 {d16, d17}, [%[out]:64]\n"
1360 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
1361 : [stride] "r"(params.stride),
1362 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
1363 [additive_sum_offset] "r"(params.additive_sum_offset)
1364 : "r0", "r1", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20",
1365 "d21", "cc", "memory");
1366 }
1367
1368 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)1369 inline void Stream<uint8_t, 3, 8, 6, RowMajorWithSum>::Pack(
1370 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
1371 #ifdef DEBUG
1372 #ifdef DEBUG_METAGEMM_VERBOSE
1373 std::cout << __FILE__ << "(" << __LINE__
1374 << ") RowMajorWithSum<uint8_t, 3, 8, 6, RowMajorWithSum>::Pack()"
1375 << std::endl
1376 << std::flush;
1377 #endif
1378 #endif
1379 int params_count_copy = params.count;
1380 asm volatile(
1381 "add r0, %[in], %[stride]\n"
1382 "add r1, r0, %[stride]\n"
1383 "vmov.i16 q8, #0\n"
1384 "vmov.i16 q9, #0\n"
1385 "vmov.i16 q10, #0\n"
1386
1387 // Reduce count by leftovers.
1388 "subs %[count], %[count], #6\n"
1389 "beq 2f\n"
1390
1391 "1:"
1392 "subs %[count], %[count], #8\n"
1393
1394 // Load Aggregate Store: 3x8.
1395 "vld1.32 {d0}, [%[in]]!\n"
1396 "vld1.32 {d1}, [r0]!\n"
1397 "vld1.32 {d2}, [r1]!\n"
1398 "vaddw.u8 q8, q8, d0\n"
1399 "vaddw.u8 q9, q9, d1\n"
1400 "vaddw.u8 q10, q10, d2\n"
1401 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
1402
1403 "bne 1b\n"
1404
1405 "2:"
1406
1407 // Load Aggregate Store: 3x6.
1408 "vmov.i8 d0, #0\n"
1409 "vmov.i8 d1, #0\n"
1410 "vmov.i8 d2, #0\n"
1411 "vld1.32 {d0[0]}, [%[in]]!\n"
1412 "vld1.16 {d0[2]}, [%[in]]!\n"
1413 "vld1.32 {d1[0]}, [r0]!\n"
1414 "vld1.16 {d1[2]}, [r0]!\n"
1415 "vld1.32 {d2[0]}, [r1]!\n"
1416 "vld1.16 {d2[2]}, [r1]!\n"
1417 "vaddw.u8 q8, q8, d0\n"
1418 "vaddw.u8 q9, q9, d1\n"
1419 "vaddw.u8 q10, q10, d2\n"
1420 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
1421
1422 // Aggregator Reduction.
1423 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
1424 "vdup.32 q1, %[additive_sum_offset]\n"
1425 "vpaddl.u16 q8, q8\n"
1426 "vpaddl.u16 q9, q9\n"
1427 "vpaddl.u16 q10, q10\n"
1428 "vpadd.u32 d16, d16, d17\n"
1429 "vpadd.u32 d18, d18, d19\n"
1430 "vpadd.u32 d20, d20, d21\n"
1431 "vpadd.u32 d16, d16, d18\n"
1432 "vpadd.u32 d17, d20, d20\n"
1433 "vmul.i32 q8, q8, d0[0]\n"
1434 "vadd.i32 q8, q8, q1\n"
1435 "vst1.32 {d16, d17}, [%[out]:64]\n"
1436 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
1437 : [stride] "r"(params.stride),
1438 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
1439 [additive_sum_offset] "r"(params.additive_sum_offset)
1440 : "r0", "r1", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20",
1441 "d21", "cc", "memory");
1442 }
1443
1444 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)1445 inline void Stream<uint8_t, 3, 8, 7, RowMajorWithSum>::Pack(
1446 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
1447 #ifdef DEBUG
1448 #ifdef DEBUG_METAGEMM_VERBOSE
1449 std::cout << __FILE__ << "(" << __LINE__
1450 << ") RowMajorWithSum<uint8_t, 3, 8, 7, RowMajorWithSum>::Pack()"
1451 << std::endl
1452 << std::flush;
1453 #endif
1454 #endif
1455 int params_count_copy = params.count;
1456 asm volatile(
1457 "add r0, %[in], %[stride]\n"
1458 "add r1, r0, %[stride]\n"
1459 "vmov.i16 q8, #0\n"
1460 "vmov.i16 q9, #0\n"
1461 "vmov.i16 q10, #0\n"
1462
1463 // Reduce count by leftovers.
1464 "subs %[count], %[count], #7\n"
1465 "beq 2f\n"
1466
1467 "1:"
1468 "subs %[count], %[count], #8\n"
1469
1470 // Load Aggregate Store: 3x8.
1471 "vld1.32 {d0}, [%[in]]!\n"
1472 "vld1.32 {d1}, [r0]!\n"
1473 "vld1.32 {d2}, [r1]!\n"
1474 "vaddw.u8 q8, q8, d0\n"
1475 "vaddw.u8 q9, q9, d1\n"
1476 "vaddw.u8 q10, q10, d2\n"
1477 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
1478
1479 "bne 1b\n"
1480
1481 "2:"
1482
1483 // Load Aggregate Store: 3x7.
1484 "vmov.i8 d0, #0\n"
1485 "vmov.i8 d1, #0\n"
1486 "vmov.i8 d2, #0\n"
1487 "vld1.32 {d0[0]}, [%[in]]!\n"
1488 "vld1.16 {d0[2]}, [%[in]]!\n"
1489 "vld1.8 {d0[6]}, [%[in]]!\n"
1490 "vld1.32 {d1[0]}, [r0]!\n"
1491 "vld1.16 {d1[2]}, [r0]!\n"
1492 "vld1.8 {d1[6]}, [r0]!\n"
1493 "vld1.32 {d2[0]}, [r1]!\n"
1494 "vld1.16 {d2[2]}, [r1]!\n"
1495 "vld1.8 {d2[6]}, [r1]!\n"
1496 "vaddw.u8 q8, q8, d0\n"
1497 "vaddw.u8 q9, q9, d1\n"
1498 "vaddw.u8 q10, q10, d2\n"
1499 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
1500
1501 // Aggregator Reduction.
1502 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
1503 "vdup.32 q1, %[additive_sum_offset]\n"
1504 "vpaddl.u16 q8, q8\n"
1505 "vpaddl.u16 q9, q9\n"
1506 "vpaddl.u16 q10, q10\n"
1507 "vpadd.u32 d16, d16, d17\n"
1508 "vpadd.u32 d18, d18, d19\n"
1509 "vpadd.u32 d20, d20, d21\n"
1510 "vpadd.u32 d16, d16, d18\n"
1511 "vpadd.u32 d17, d20, d20\n"
1512 "vmul.i32 q8, q8, d0[0]\n"
1513 "vadd.i32 q8, q8, q1\n"
1514 "vst1.32 {d16, d17}, [%[out]:64]\n"
1515 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
1516 : [stride] "r"(params.stride),
1517 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
1518 [additive_sum_offset] "r"(params.additive_sum_offset)
1519 : "r0", "r1", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20",
1520 "d21", "cc", "memory");
1521 }
1522
1523 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)1524 inline void Stream<uint8_t, 4, 8, 0, RowMajorWithSum>::Pack(
1525 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
1526 #ifdef DEBUG
1527 #ifdef DEBUG_METAGEMM_VERBOSE
1528 std::cout << __FILE__ << "(" << __LINE__
1529 << ") RowMajorWithSum<uint8_t, 4, 8, 0, RowMajorWithSum>::Pack()"
1530 << std::endl
1531 << std::flush;
1532 #endif
1533 #endif
1534 int params_count_copy = params.count;
1535 asm volatile(
1536 "add r0, %[in], %[stride]\n"
1537 "add r1, r0, %[stride]\n"
1538 "add r2, r1, %[stride]\n"
1539 "vmov.i16 q8, #0\n"
1540 "vmov.i16 q9, #0\n"
1541 "vmov.i16 q10, #0\n"
1542 "vmov.i16 q11, #0\n"
1543
1544 "1:"
1545 "subs %[count], %[count], #8\n"
1546
1547 // Load Aggregate Store: 4x8.
1548 "vld1.32 {d0}, [%[in]]!\n"
1549 "vld1.32 {d1}, [r0]!\n"
1550 "vld1.32 {d2}, [r1]!\n"
1551 "vld1.32 {d3}, [r2]!\n"
1552 "vaddw.u8 q8, q8, d0\n"
1553 "vaddw.u8 q9, q9, d1\n"
1554 "vaddw.u8 q10, q10, d2\n"
1555 "vaddw.u8 q11, q11, d3\n"
1556 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
1557
1558 "bne 1b\n"
1559
1560 // Aggregator Reduction.
1561 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
1562 "vdup.32 q1, %[additive_sum_offset]\n"
1563 "vpaddl.u16 q8, q8\n"
1564 "vpaddl.u16 q9, q9\n"
1565 "vpaddl.u16 q10, q10\n"
1566 "vpaddl.u16 q11, q11\n"
1567 "vpadd.u32 d16, d16, d17\n"
1568 "vpadd.u32 d18, d18, d19\n"
1569 "vpadd.u32 d20, d20, d21\n"
1570 "vpadd.u32 d22, d22, d23\n"
1571 "vpadd.u32 d16, d16, d18\n"
1572 "vpadd.u32 d17, d20, d22\n"
1573 "vmul.i32 q8, q8, d0[0]\n"
1574 "vadd.i32 q8, q8, q1\n"
1575 "vst1.32 {d16, d17}, [%[out]:128]\n"
1576 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
1577 : [stride] "r"(params.stride),
1578 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
1579 [additive_sum_offset] "r"(params.additive_sum_offset)
1580 : "r0", "r1", "r2", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19",
1581 "d20", "d21", "d22", "d23", "cc", "memory");
1582 }
1583
1584 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)1585 inline void Stream<uint8_t, 4, 8, 1, RowMajorWithSum>::Pack(
1586 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
1587 #ifdef DEBUG
1588 #ifdef DEBUG_METAGEMM_VERBOSE
1589 std::cout << __FILE__ << "(" << __LINE__
1590 << ") RowMajorWithSum<uint8_t, 4, 8, 1, RowMajorWithSum>::Pack()"
1591 << std::endl
1592 << std::flush;
1593 #endif
1594 #endif
1595 int params_count_copy = params.count;
1596 asm volatile(
1597 "add r0, %[in], %[stride]\n"
1598 "add r1, r0, %[stride]\n"
1599 "add r2, r1, %[stride]\n"
1600 "vmov.i16 q8, #0\n"
1601 "vmov.i16 q9, #0\n"
1602 "vmov.i16 q10, #0\n"
1603 "vmov.i16 q11, #0\n"
1604
1605 // Reduce count by leftovers.
1606 "subs %[count], %[count], #1\n"
1607 "beq 2f\n"
1608
1609 "1:"
1610 "subs %[count], %[count], #8\n"
1611
1612 // Load Aggregate Store: 4x8.
1613 "vld1.32 {d0}, [%[in]]!\n"
1614 "vld1.32 {d1}, [r0]!\n"
1615 "vld1.32 {d2}, [r1]!\n"
1616 "vld1.32 {d3}, [r2]!\n"
1617 "vaddw.u8 q8, q8, d0\n"
1618 "vaddw.u8 q9, q9, d1\n"
1619 "vaddw.u8 q10, q10, d2\n"
1620 "vaddw.u8 q11, q11, d3\n"
1621 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
1622
1623 "bne 1b\n"
1624
1625 "2:"
1626
1627 // Load Aggregate Store: 4x1.
1628 "vmov.i8 d0, #0\n"
1629 "vmov.i8 d1, #0\n"
1630 "vmov.i8 d2, #0\n"
1631 "vmov.i8 d3, #0\n"
1632 "vld1.8 {d0[0]}, [%[in]]!\n"
1633 "vld1.8 {d1[0]}, [r0]!\n"
1634 "vld1.8 {d2[0]}, [r1]!\n"
1635 "vld1.8 {d3[0]}, [r2]!\n"
1636 "vaddw.u8 q8, q8, d0\n"
1637 "vaddw.u8 q9, q9, d1\n"
1638 "vaddw.u8 q10, q10, d2\n"
1639 "vaddw.u8 q11, q11, d3\n"
1640 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
1641
1642 // Aggregator Reduction.
1643 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
1644 "vdup.32 q1, %[additive_sum_offset]\n"
1645 "vpaddl.u16 q8, q8\n"
1646 "vpaddl.u16 q9, q9\n"
1647 "vpaddl.u16 q10, q10\n"
1648 "vpaddl.u16 q11, q11\n"
1649 "vpadd.u32 d16, d16, d17\n"
1650 "vpadd.u32 d18, d18, d19\n"
1651 "vpadd.u32 d20, d20, d21\n"
1652 "vpadd.u32 d22, d22, d23\n"
1653 "vpadd.u32 d16, d16, d18\n"
1654 "vpadd.u32 d17, d20, d22\n"
1655 "vmul.i32 q8, q8, d0[0]\n"
1656 "vadd.i32 q8, q8, q1\n"
1657 "vst1.32 {d16, d17}, [%[out]:128]\n"
1658 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
1659 : [stride] "r"(params.stride),
1660 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
1661 [additive_sum_offset] "r"(params.additive_sum_offset)
1662 : "r0", "r1", "r2", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19",
1663 "d20", "d21", "d22", "d23", "cc", "memory");
1664 }
1665
1666 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)1667 inline void Stream<uint8_t, 4, 8, 2, RowMajorWithSum>::Pack(
1668 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
1669 #ifdef DEBUG
1670 #ifdef DEBUG_METAGEMM_VERBOSE
1671 std::cout << __FILE__ << "(" << __LINE__
1672 << ") RowMajorWithSum<uint8_t, 4, 8, 2, RowMajorWithSum>::Pack()"
1673 << std::endl
1674 << std::flush;
1675 #endif
1676 #endif
1677 int params_count_copy = params.count;
1678 asm volatile(
1679 "add r0, %[in], %[stride]\n"
1680 "add r1, r0, %[stride]\n"
1681 "add r2, r1, %[stride]\n"
1682 "vmov.i16 q8, #0\n"
1683 "vmov.i16 q9, #0\n"
1684 "vmov.i16 q10, #0\n"
1685 "vmov.i16 q11, #0\n"
1686
1687 // Reduce count by leftovers.
1688 "subs %[count], %[count], #2\n"
1689 "beq 2f\n"
1690
1691 "1:"
1692 "subs %[count], %[count], #8\n"
1693
1694 // Load Aggregate Store: 4x8.
1695 "vld1.32 {d0}, [%[in]]!\n"
1696 "vld1.32 {d1}, [r0]!\n"
1697 "vld1.32 {d2}, [r1]!\n"
1698 "vld1.32 {d3}, [r2]!\n"
1699 "vaddw.u8 q8, q8, d0\n"
1700 "vaddw.u8 q9, q9, d1\n"
1701 "vaddw.u8 q10, q10, d2\n"
1702 "vaddw.u8 q11, q11, d3\n"
1703 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
1704
1705 "bne 1b\n"
1706
1707 "2:"
1708
1709 // Load Aggregate Store: 4x2.
1710 "vmov.i8 d0, #0\n"
1711 "vmov.i8 d1, #0\n"
1712 "vmov.i8 d2, #0\n"
1713 "vmov.i8 d3, #0\n"
1714 "vld1.16 {d0[0]}, [%[in]]!\n"
1715 "vld1.16 {d1[0]}, [r0]!\n"
1716 "vld1.16 {d2[0]}, [r1]!\n"
1717 "vld1.16 {d3[0]}, [r2]!\n"
1718 "vaddw.u8 q8, q8, d0\n"
1719 "vaddw.u8 q9, q9, d1\n"
1720 "vaddw.u8 q10, q10, d2\n"
1721 "vaddw.u8 q11, q11, d3\n"
1722 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
1723
1724 // Aggregator Reduction.
1725 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
1726 "vdup.32 q1, %[additive_sum_offset]\n"
1727 "vpaddl.u16 q8, q8\n"
1728 "vpaddl.u16 q9, q9\n"
1729 "vpaddl.u16 q10, q10\n"
1730 "vpaddl.u16 q11, q11\n"
1731 "vpadd.u32 d16, d16, d17\n"
1732 "vpadd.u32 d18, d18, d19\n"
1733 "vpadd.u32 d20, d20, d21\n"
1734 "vpadd.u32 d22, d22, d23\n"
1735 "vpadd.u32 d16, d16, d18\n"
1736 "vpadd.u32 d17, d20, d22\n"
1737 "vmul.i32 q8, q8, d0[0]\n"
1738 "vadd.i32 q8, q8, q1\n"
1739 "vst1.32 {d16, d17}, [%[out]:128]\n"
1740 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
1741 : [stride] "r"(params.stride),
1742 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
1743 [additive_sum_offset] "r"(params.additive_sum_offset)
1744 : "r0", "r1", "r2", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19",
1745 "d20", "d21", "d22", "d23", "cc", "memory");
1746 }
1747
1748 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)1749 inline void Stream<uint8_t, 4, 8, 3, RowMajorWithSum>::Pack(
1750 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
1751 #ifdef DEBUG
1752 #ifdef DEBUG_METAGEMM_VERBOSE
1753 std::cout << __FILE__ << "(" << __LINE__
1754 << ") RowMajorWithSum<uint8_t, 4, 8, 3, RowMajorWithSum>::Pack()"
1755 << std::endl
1756 << std::flush;
1757 #endif
1758 #endif
1759 int params_count_copy = params.count;
1760 asm volatile(
1761 "add r0, %[in], %[stride]\n"
1762 "add r1, r0, %[stride]\n"
1763 "add r2, r1, %[stride]\n"
1764 "vmov.i16 q8, #0\n"
1765 "vmov.i16 q9, #0\n"
1766 "vmov.i16 q10, #0\n"
1767 "vmov.i16 q11, #0\n"
1768
1769 // Reduce count by leftovers.
1770 "subs %[count], %[count], #3\n"
1771 "beq 2f\n"
1772
1773 "1:"
1774 "subs %[count], %[count], #8\n"
1775
1776 // Load Aggregate Store: 4x8.
1777 "vld1.32 {d0}, [%[in]]!\n"
1778 "vld1.32 {d1}, [r0]!\n"
1779 "vld1.32 {d2}, [r1]!\n"
1780 "vld1.32 {d3}, [r2]!\n"
1781 "vaddw.u8 q8, q8, d0\n"
1782 "vaddw.u8 q9, q9, d1\n"
1783 "vaddw.u8 q10, q10, d2\n"
1784 "vaddw.u8 q11, q11, d3\n"
1785 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
1786
1787 "bne 1b\n"
1788
1789 "2:"
1790
1791 // Load Aggregate Store: 4x3.
1792 "vmov.i8 d0, #0\n"
1793 "vmov.i8 d1, #0\n"
1794 "vmov.i8 d2, #0\n"
1795 "vmov.i8 d3, #0\n"
1796 "vld1.16 {d0[0]}, [%[in]]!\n"
1797 "vld1.8 {d0[2]}, [%[in]]!\n"
1798 "vld1.16 {d1[0]}, [r0]!\n"
1799 "vld1.8 {d1[2]}, [r0]!\n"
1800 "vld1.16 {d2[0]}, [r1]!\n"
1801 "vld1.8 {d2[2]}, [r1]!\n"
1802 "vld1.16 {d3[0]}, [r2]!\n"
1803 "vld1.8 {d3[2]}, [r2]!\n"
1804 "vaddw.u8 q8, q8, d0\n"
1805 "vaddw.u8 q9, q9, d1\n"
1806 "vaddw.u8 q10, q10, d2\n"
1807 "vaddw.u8 q11, q11, d3\n"
1808 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
1809
1810 // Aggregator Reduction.
1811 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
1812 "vdup.32 q1, %[additive_sum_offset]\n"
1813 "vpaddl.u16 q8, q8\n"
1814 "vpaddl.u16 q9, q9\n"
1815 "vpaddl.u16 q10, q10\n"
1816 "vpaddl.u16 q11, q11\n"
1817 "vpadd.u32 d16, d16, d17\n"
1818 "vpadd.u32 d18, d18, d19\n"
1819 "vpadd.u32 d20, d20, d21\n"
1820 "vpadd.u32 d22, d22, d23\n"
1821 "vpadd.u32 d16, d16, d18\n"
1822 "vpadd.u32 d17, d20, d22\n"
1823 "vmul.i32 q8, q8, d0[0]\n"
1824 "vadd.i32 q8, q8, q1\n"
1825 "vst1.32 {d16, d17}, [%[out]:128]\n"
1826 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
1827 : [stride] "r"(params.stride),
1828 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
1829 [additive_sum_offset] "r"(params.additive_sum_offset)
1830 : "r0", "r1", "r2", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19",
1831 "d20", "d21", "d22", "d23", "cc", "memory");
1832 }
1833
1834 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)1835 inline void Stream<uint8_t, 4, 8, 4, RowMajorWithSum>::Pack(
1836 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
1837 #ifdef DEBUG
1838 #ifdef DEBUG_METAGEMM_VERBOSE
1839 std::cout << __FILE__ << "(" << __LINE__
1840 << ") RowMajorWithSum<uint8_t, 4, 8, 4, RowMajorWithSum>::Pack()"
1841 << std::endl
1842 << std::flush;
1843 #endif
1844 #endif
1845 int params_count_copy = params.count;
1846 asm volatile(
1847 "add r0, %[in], %[stride]\n"
1848 "add r1, r0, %[stride]\n"
1849 "add r2, r1, %[stride]\n"
1850 "vmov.i16 q8, #0\n"
1851 "vmov.i16 q9, #0\n"
1852 "vmov.i16 q10, #0\n"
1853 "vmov.i16 q11, #0\n"
1854
1855 // Reduce count by leftovers.
1856 "subs %[count], %[count], #4\n"
1857 "beq 2f\n"
1858
1859 "1:"
1860 "subs %[count], %[count], #8\n"
1861
1862 // Load Aggregate Store: 4x8.
1863 "vld1.32 {d0}, [%[in]]!\n"
1864 "vld1.32 {d1}, [r0]!\n"
1865 "vld1.32 {d2}, [r1]!\n"
1866 "vld1.32 {d3}, [r2]!\n"
1867 "vaddw.u8 q8, q8, d0\n"
1868 "vaddw.u8 q9, q9, d1\n"
1869 "vaddw.u8 q10, q10, d2\n"
1870 "vaddw.u8 q11, q11, d3\n"
1871 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
1872
1873 "bne 1b\n"
1874
1875 "2:"
1876
1877 // Load Aggregate Store: 4x4.
1878 "vmov.i8 d0, #0\n"
1879 "vmov.i8 d1, #0\n"
1880 "vmov.i8 d2, #0\n"
1881 "vmov.i8 d3, #0\n"
1882 "vld1.32 {d0[0]}, [%[in]]!\n"
1883 "vld1.32 {d1[0]}, [r0]!\n"
1884 "vld1.32 {d2[0]}, [r1]!\n"
1885 "vld1.32 {d3[0]}, [r2]!\n"
1886 "vaddw.u8 q8, q8, d0\n"
1887 "vaddw.u8 q9, q9, d1\n"
1888 "vaddw.u8 q10, q10, d2\n"
1889 "vaddw.u8 q11, q11, d3\n"
1890 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
1891
1892 // Aggregator Reduction.
1893 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
1894 "vdup.32 q1, %[additive_sum_offset]\n"
1895 "vpaddl.u16 q8, q8\n"
1896 "vpaddl.u16 q9, q9\n"
1897 "vpaddl.u16 q10, q10\n"
1898 "vpaddl.u16 q11, q11\n"
1899 "vpadd.u32 d16, d16, d17\n"
1900 "vpadd.u32 d18, d18, d19\n"
1901 "vpadd.u32 d20, d20, d21\n"
1902 "vpadd.u32 d22, d22, d23\n"
1903 "vpadd.u32 d16, d16, d18\n"
1904 "vpadd.u32 d17, d20, d22\n"
1905 "vmul.i32 q8, q8, d0[0]\n"
1906 "vadd.i32 q8, q8, q1\n"
1907 "vst1.32 {d16, d17}, [%[out]:128]\n"
1908 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
1909 : [stride] "r"(params.stride),
1910 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
1911 [additive_sum_offset] "r"(params.additive_sum_offset)
1912 : "r0", "r1", "r2", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19",
1913 "d20", "d21", "d22", "d23", "cc", "memory");
1914 }
1915
1916 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)1917 inline void Stream<uint8_t, 4, 8, 5, RowMajorWithSum>::Pack(
1918 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
1919 #ifdef DEBUG
1920 #ifdef DEBUG_METAGEMM_VERBOSE
1921 std::cout << __FILE__ << "(" << __LINE__
1922 << ") RowMajorWithSum<uint8_t, 4, 8, 5, RowMajorWithSum>::Pack()"
1923 << std::endl
1924 << std::flush;
1925 #endif
1926 #endif
1927 int params_count_copy = params.count;
1928 asm volatile(
1929 "add r0, %[in], %[stride]\n"
1930 "add r1, r0, %[stride]\n"
1931 "add r2, r1, %[stride]\n"
1932 "vmov.i16 q8, #0\n"
1933 "vmov.i16 q9, #0\n"
1934 "vmov.i16 q10, #0\n"
1935 "vmov.i16 q11, #0\n"
1936
1937 // Reduce count by leftovers.
1938 "subs %[count], %[count], #5\n"
1939 "beq 2f\n"
1940
1941 "1:"
1942 "subs %[count], %[count], #8\n"
1943
1944 // Load Aggregate Store: 4x8.
1945 "vld1.32 {d0}, [%[in]]!\n"
1946 "vld1.32 {d1}, [r0]!\n"
1947 "vld1.32 {d2}, [r1]!\n"
1948 "vld1.32 {d3}, [r2]!\n"
1949 "vaddw.u8 q8, q8, d0\n"
1950 "vaddw.u8 q9, q9, d1\n"
1951 "vaddw.u8 q10, q10, d2\n"
1952 "vaddw.u8 q11, q11, d3\n"
1953 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
1954
1955 "bne 1b\n"
1956
1957 "2:"
1958
1959 // Load Aggregate Store: 4x5.
1960 "vmov.i8 d0, #0\n"
1961 "vmov.i8 d1, #0\n"
1962 "vmov.i8 d2, #0\n"
1963 "vmov.i8 d3, #0\n"
1964 "vld1.32 {d0[0]}, [%[in]]!\n"
1965 "vld1.8 {d0[4]}, [%[in]]!\n"
1966 "vld1.32 {d1[0]}, [r0]!\n"
1967 "vld1.8 {d1[4]}, [r0]!\n"
1968 "vld1.32 {d2[0]}, [r1]!\n"
1969 "vld1.8 {d2[4]}, [r1]!\n"
1970 "vld1.32 {d3[0]}, [r2]!\n"
1971 "vld1.8 {d3[4]}, [r2]!\n"
1972 "vaddw.u8 q8, q8, d0\n"
1973 "vaddw.u8 q9, q9, d1\n"
1974 "vaddw.u8 q10, q10, d2\n"
1975 "vaddw.u8 q11, q11, d3\n"
1976 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
1977
1978 // Aggregator Reduction.
1979 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
1980 "vdup.32 q1, %[additive_sum_offset]\n"
1981 "vpaddl.u16 q8, q8\n"
1982 "vpaddl.u16 q9, q9\n"
1983 "vpaddl.u16 q10, q10\n"
1984 "vpaddl.u16 q11, q11\n"
1985 "vpadd.u32 d16, d16, d17\n"
1986 "vpadd.u32 d18, d18, d19\n"
1987 "vpadd.u32 d20, d20, d21\n"
1988 "vpadd.u32 d22, d22, d23\n"
1989 "vpadd.u32 d16, d16, d18\n"
1990 "vpadd.u32 d17, d20, d22\n"
1991 "vmul.i32 q8, q8, d0[0]\n"
1992 "vadd.i32 q8, q8, q1\n"
1993 "vst1.32 {d16, d17}, [%[out]:128]\n"
1994 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
1995 : [stride] "r"(params.stride),
1996 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
1997 [additive_sum_offset] "r"(params.additive_sum_offset)
1998 : "r0", "r1", "r2", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19",
1999 "d20", "d21", "d22", "d23", "cc", "memory");
2000 }
2001
2002 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)2003 inline void Stream<uint8_t, 4, 8, 6, RowMajorWithSum>::Pack(
2004 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
2005 #ifdef DEBUG
2006 #ifdef DEBUG_METAGEMM_VERBOSE
2007 std::cout << __FILE__ << "(" << __LINE__
2008 << ") RowMajorWithSum<uint8_t, 4, 8, 6, RowMajorWithSum>::Pack()"
2009 << std::endl
2010 << std::flush;
2011 #endif
2012 #endif
2013 int params_count_copy = params.count;
2014 asm volatile(
2015 "add r0, %[in], %[stride]\n"
2016 "add r1, r0, %[stride]\n"
2017 "add r2, r1, %[stride]\n"
2018 "vmov.i16 q8, #0\n"
2019 "vmov.i16 q9, #0\n"
2020 "vmov.i16 q10, #0\n"
2021 "vmov.i16 q11, #0\n"
2022
2023 // Reduce count by leftovers.
2024 "subs %[count], %[count], #6\n"
2025 "beq 2f\n"
2026
2027 "1:"
2028 "subs %[count], %[count], #8\n"
2029
2030 // Load Aggregate Store: 4x8.
2031 "vld1.32 {d0}, [%[in]]!\n"
2032 "vld1.32 {d1}, [r0]!\n"
2033 "vld1.32 {d2}, [r1]!\n"
2034 "vld1.32 {d3}, [r2]!\n"
2035 "vaddw.u8 q8, q8, d0\n"
2036 "vaddw.u8 q9, q9, d1\n"
2037 "vaddw.u8 q10, q10, d2\n"
2038 "vaddw.u8 q11, q11, d3\n"
2039 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
2040
2041 "bne 1b\n"
2042
2043 "2:"
2044
2045 // Load Aggregate Store: 4x6.
2046 "vmov.i8 d0, #0\n"
2047 "vmov.i8 d1, #0\n"
2048 "vmov.i8 d2, #0\n"
2049 "vmov.i8 d3, #0\n"
2050 "vld1.32 {d0[0]}, [%[in]]!\n"
2051 "vld1.16 {d0[2]}, [%[in]]!\n"
2052 "vld1.32 {d1[0]}, [r0]!\n"
2053 "vld1.16 {d1[2]}, [r0]!\n"
2054 "vld1.32 {d2[0]}, [r1]!\n"
2055 "vld1.16 {d2[2]}, [r1]!\n"
2056 "vld1.32 {d3[0]}, [r2]!\n"
2057 "vld1.16 {d3[2]}, [r2]!\n"
2058 "vaddw.u8 q8, q8, d0\n"
2059 "vaddw.u8 q9, q9, d1\n"
2060 "vaddw.u8 q10, q10, d2\n"
2061 "vaddw.u8 q11, q11, d3\n"
2062 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
2063
2064 // Aggregator Reduction.
2065 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
2066 "vdup.32 q1, %[additive_sum_offset]\n"
2067 "vpaddl.u16 q8, q8\n"
2068 "vpaddl.u16 q9, q9\n"
2069 "vpaddl.u16 q10, q10\n"
2070 "vpaddl.u16 q11, q11\n"
2071 "vpadd.u32 d16, d16, d17\n"
2072 "vpadd.u32 d18, d18, d19\n"
2073 "vpadd.u32 d20, d20, d21\n"
2074 "vpadd.u32 d22, d22, d23\n"
2075 "vpadd.u32 d16, d16, d18\n"
2076 "vpadd.u32 d17, d20, d22\n"
2077 "vmul.i32 q8, q8, d0[0]\n"
2078 "vadd.i32 q8, q8, q1\n"
2079 "vst1.32 {d16, d17}, [%[out]:128]\n"
2080 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
2081 : [stride] "r"(params.stride),
2082 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
2083 [additive_sum_offset] "r"(params.additive_sum_offset)
2084 : "r0", "r1", "r2", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19",
2085 "d20", "d21", "d22", "d23", "cc", "memory");
2086 }
2087
2088 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)2089 inline void Stream<uint8_t, 4, 8, 7, RowMajorWithSum>::Pack(
2090 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
2091 #ifdef DEBUG
2092 #ifdef DEBUG_METAGEMM_VERBOSE
2093 std::cout << __FILE__ << "(" << __LINE__
2094 << ") RowMajorWithSum<uint8_t, 4, 8, 7, RowMajorWithSum>::Pack()"
2095 << std::endl
2096 << std::flush;
2097 #endif
2098 #endif
2099 int params_count_copy = params.count;
2100 asm volatile(
2101 "add r0, %[in], %[stride]\n"
2102 "add r1, r0, %[stride]\n"
2103 "add r2, r1, %[stride]\n"
2104 "vmov.i16 q8, #0\n"
2105 "vmov.i16 q9, #0\n"
2106 "vmov.i16 q10, #0\n"
2107 "vmov.i16 q11, #0\n"
2108
2109 // Reduce count by leftovers.
2110 "subs %[count], %[count], #7\n"
2111 "beq 2f\n"
2112
2113 "1:"
2114 "subs %[count], %[count], #8\n"
2115
2116 // Load Aggregate Store: 4x8.
2117 "vld1.32 {d0}, [%[in]]!\n"
2118 "vld1.32 {d1}, [r0]!\n"
2119 "vld1.32 {d2}, [r1]!\n"
2120 "vld1.32 {d3}, [r2]!\n"
2121 "vaddw.u8 q8, q8, d0\n"
2122 "vaddw.u8 q9, q9, d1\n"
2123 "vaddw.u8 q10, q10, d2\n"
2124 "vaddw.u8 q11, q11, d3\n"
2125 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
2126
2127 "bne 1b\n"
2128
2129 "2:"
2130
2131 // Load Aggregate Store: 4x7.
2132 "vmov.i8 d0, #0\n"
2133 "vmov.i8 d1, #0\n"
2134 "vmov.i8 d2, #0\n"
2135 "vmov.i8 d3, #0\n"
2136 "vld1.32 {d0[0]}, [%[in]]!\n"
2137 "vld1.16 {d0[2]}, [%[in]]!\n"
2138 "vld1.8 {d0[6]}, [%[in]]!\n"
2139 "vld1.32 {d1[0]}, [r0]!\n"
2140 "vld1.16 {d1[2]}, [r0]!\n"
2141 "vld1.8 {d1[6]}, [r0]!\n"
2142 "vld1.32 {d2[0]}, [r1]!\n"
2143 "vld1.16 {d2[2]}, [r1]!\n"
2144 "vld1.8 {d2[6]}, [r1]!\n"
2145 "vld1.32 {d3[0]}, [r2]!\n"
2146 "vld1.16 {d3[2]}, [r2]!\n"
2147 "vld1.8 {d3[6]}, [r2]!\n"
2148 "vaddw.u8 q8, q8, d0\n"
2149 "vaddw.u8 q9, q9, d1\n"
2150 "vaddw.u8 q10, q10, d2\n"
2151 "vaddw.u8 q11, q11, d3\n"
2152 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
2153
2154 // Aggregator Reduction.
2155 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
2156 "vdup.32 q1, %[additive_sum_offset]\n"
2157 "vpaddl.u16 q8, q8\n"
2158 "vpaddl.u16 q9, q9\n"
2159 "vpaddl.u16 q10, q10\n"
2160 "vpaddl.u16 q11, q11\n"
2161 "vpadd.u32 d16, d16, d17\n"
2162 "vpadd.u32 d18, d18, d19\n"
2163 "vpadd.u32 d20, d20, d21\n"
2164 "vpadd.u32 d22, d22, d23\n"
2165 "vpadd.u32 d16, d16, d18\n"
2166 "vpadd.u32 d17, d20, d22\n"
2167 "vmul.i32 q8, q8, d0[0]\n"
2168 "vadd.i32 q8, q8, q1\n"
2169 "vst1.32 {d16, d17}, [%[out]:128]\n"
2170 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
2171 : [stride] "r"(params.stride),
2172 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
2173 [additive_sum_offset] "r"(params.additive_sum_offset)
2174 : "r0", "r1", "r2", "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19",
2175 "d20", "d21", "d22", "d23", "cc", "memory");
2176 }
2177
2178 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)2179 inline void Stream<uint8_t, 5, 8, 0, RowMajorWithSum>::Pack(
2180 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
2181 #ifdef DEBUG
2182 #ifdef DEBUG_METAGEMM_VERBOSE
2183 std::cout << __FILE__ << "(" << __LINE__
2184 << ") RowMajorWithSum<uint8_t, 5, 8, 0, RowMajorWithSum>::Pack()"
2185 << std::endl
2186 << std::flush;
2187 #endif
2188 #endif
2189 int params_count_copy = params.count;
2190 asm volatile(
2191 "add r0, %[in], %[stride]\n"
2192 "add r1, r0, %[stride]\n"
2193 "add r2, r1, %[stride]\n"
2194 "add r3, r2, %[stride]\n"
2195 "vmov.i16 q8, #0\n"
2196 "vmov.i16 q9, #0\n"
2197 "vmov.i16 q10, #0\n"
2198 "vmov.i16 q11, #0\n"
2199 "vmov.i16 q12, #0\n"
2200
2201 "1:"
2202 "subs %[count], %[count], #8\n"
2203
2204 // Load Aggregate Store: 5x8.
2205 "vld1.32 {d0}, [%[in]]!\n"
2206 "vld1.32 {d1}, [r0]!\n"
2207 "vld1.32 {d2}, [r1]!\n"
2208 "vld1.32 {d3}, [r2]!\n"
2209 "vld1.32 {d4}, [r3]!\n"
2210 "vaddw.u8 q8, q8, d0\n"
2211 "vaddw.u8 q9, q9, d1\n"
2212 "vaddw.u8 q10, q10, d2\n"
2213 "vaddw.u8 q11, q11, d3\n"
2214 "vaddw.u8 q12, q12, d4\n"
2215 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
2216 "vst1.32 {d4}, [%[out]:64]!\n"
2217
2218 "bne 1b\n"
2219
2220 // Aggregator Reduction.
2221 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
2222 "vdup.32 q1, %[additive_sum_offset]\n"
2223 "vpaddl.u16 q8, q8\n"
2224 "vpaddl.u16 q9, q9\n"
2225 "vpaddl.u16 q10, q10\n"
2226 "vpaddl.u16 q11, q11\n"
2227 "vpaddl.u16 q12, q12\n"
2228 "vpadd.u32 d16, d16, d17\n"
2229 "vpadd.u32 d18, d18, d19\n"
2230 "vpadd.u32 d20, d20, d21\n"
2231 "vpadd.u32 d22, d22, d23\n"
2232 "vpadd.u32 d24, d24, d25\n"
2233 "vpadd.u32 d16, d16, d18\n"
2234 "vpadd.u32 d17, d20, d22\n"
2235 "vpadd.u32 d18, d24, d24\n"
2236 "vmul.i32 q8, q8, d0[0]\n"
2237 "vmul.i32 q9, q9, d0[0]\n"
2238 "vadd.i32 q8, q8, q1\n"
2239 "vadd.i32 q9, q9, q1\n"
2240 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
2241 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
2242 : [stride] "r"(params.stride),
2243 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
2244 [additive_sum_offset] "r"(params.additive_sum_offset)
2245 : "r0", "r1", "r2", "r3", "d0", "d1", "d2", "d3", "d4", "d16", "d17",
2246 "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "cc", "memory");
2247 }
2248
2249 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)2250 inline void Stream<uint8_t, 5, 8, 1, RowMajorWithSum>::Pack(
2251 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
2252 #ifdef DEBUG
2253 #ifdef DEBUG_METAGEMM_VERBOSE
2254 std::cout << __FILE__ << "(" << __LINE__
2255 << ") RowMajorWithSum<uint8_t, 5, 8, 1, RowMajorWithSum>::Pack()"
2256 << std::endl
2257 << std::flush;
2258 #endif
2259 #endif
2260 int params_count_copy = params.count;
2261 asm volatile(
2262 "add r0, %[in], %[stride]\n"
2263 "add r1, r0, %[stride]\n"
2264 "add r2, r1, %[stride]\n"
2265 "add r3, r2, %[stride]\n"
2266 "vmov.i16 q8, #0\n"
2267 "vmov.i16 q9, #0\n"
2268 "vmov.i16 q10, #0\n"
2269 "vmov.i16 q11, #0\n"
2270 "vmov.i16 q12, #0\n"
2271
2272 // Reduce count by leftovers.
2273 "subs %[count], %[count], #1\n"
2274 "beq 2f\n"
2275
2276 "1:"
2277 "subs %[count], %[count], #8\n"
2278
2279 // Load Aggregate Store: 5x8.
2280 "vld1.32 {d0}, [%[in]]!\n"
2281 "vld1.32 {d1}, [r0]!\n"
2282 "vld1.32 {d2}, [r1]!\n"
2283 "vld1.32 {d3}, [r2]!\n"
2284 "vld1.32 {d4}, [r3]!\n"
2285 "vaddw.u8 q8, q8, d0\n"
2286 "vaddw.u8 q9, q9, d1\n"
2287 "vaddw.u8 q10, q10, d2\n"
2288 "vaddw.u8 q11, q11, d3\n"
2289 "vaddw.u8 q12, q12, d4\n"
2290 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
2291 "vst1.32 {d4}, [%[out]:64]!\n"
2292
2293 "bne 1b\n"
2294
2295 "2:"
2296
2297 // Load Aggregate Store: 5x1.
2298 "vmov.i8 d0, #0\n"
2299 "vmov.i8 d1, #0\n"
2300 "vmov.i8 d2, #0\n"
2301 "vmov.i8 d3, #0\n"
2302 "vmov.i8 d4, #0\n"
2303 "vld1.8 {d0[0]}, [%[in]]!\n"
2304 "vld1.8 {d1[0]}, [r0]!\n"
2305 "vld1.8 {d2[0]}, [r1]!\n"
2306 "vld1.8 {d3[0]}, [r2]!\n"
2307 "vld1.8 {d4[0]}, [r3]!\n"
2308 "vaddw.u8 q8, q8, d0\n"
2309 "vaddw.u8 q9, q9, d1\n"
2310 "vaddw.u8 q10, q10, d2\n"
2311 "vaddw.u8 q11, q11, d3\n"
2312 "vaddw.u8 q12, q12, d4\n"
2313 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
2314 "vst1.32 {d4}, [%[out]:64]!\n"
2315
2316 // Aggregator Reduction.
2317 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
2318 "vdup.32 q1, %[additive_sum_offset]\n"
2319 "vpaddl.u16 q8, q8\n"
2320 "vpaddl.u16 q9, q9\n"
2321 "vpaddl.u16 q10, q10\n"
2322 "vpaddl.u16 q11, q11\n"
2323 "vpaddl.u16 q12, q12\n"
2324 "vpadd.u32 d16, d16, d17\n"
2325 "vpadd.u32 d18, d18, d19\n"
2326 "vpadd.u32 d20, d20, d21\n"
2327 "vpadd.u32 d22, d22, d23\n"
2328 "vpadd.u32 d24, d24, d25\n"
2329 "vpadd.u32 d16, d16, d18\n"
2330 "vpadd.u32 d17, d20, d22\n"
2331 "vpadd.u32 d18, d24, d24\n"
2332 "vmul.i32 q8, q8, d0[0]\n"
2333 "vmul.i32 q9, q9, d0[0]\n"
2334 "vadd.i32 q8, q8, q1\n"
2335 "vadd.i32 q9, q9, q1\n"
2336 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
2337 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
2338 : [stride] "r"(params.stride),
2339 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
2340 [additive_sum_offset] "r"(params.additive_sum_offset)
2341 : "r0", "r1", "r2", "r3", "d0", "d1", "d2", "d3", "d4", "d16", "d17",
2342 "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "cc", "memory");
2343 }
2344
2345 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)2346 inline void Stream<uint8_t, 5, 8, 2, RowMajorWithSum>::Pack(
2347 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
2348 #ifdef DEBUG
2349 #ifdef DEBUG_METAGEMM_VERBOSE
2350 std::cout << __FILE__ << "(" << __LINE__
2351 << ") RowMajorWithSum<uint8_t, 5, 8, 2, RowMajorWithSum>::Pack()"
2352 << std::endl
2353 << std::flush;
2354 #endif
2355 #endif
2356 int params_count_copy = params.count;
2357 asm volatile(
2358 "add r0, %[in], %[stride]\n"
2359 "add r1, r0, %[stride]\n"
2360 "add r2, r1, %[stride]\n"
2361 "add r3, r2, %[stride]\n"
2362 "vmov.i16 q8, #0\n"
2363 "vmov.i16 q9, #0\n"
2364 "vmov.i16 q10, #0\n"
2365 "vmov.i16 q11, #0\n"
2366 "vmov.i16 q12, #0\n"
2367
2368 // Reduce count by leftovers.
2369 "subs %[count], %[count], #2\n"
2370 "beq 2f\n"
2371
2372 "1:"
2373 "subs %[count], %[count], #8\n"
2374
2375 // Load Aggregate Store: 5x8.
2376 "vld1.32 {d0}, [%[in]]!\n"
2377 "vld1.32 {d1}, [r0]!\n"
2378 "vld1.32 {d2}, [r1]!\n"
2379 "vld1.32 {d3}, [r2]!\n"
2380 "vld1.32 {d4}, [r3]!\n"
2381 "vaddw.u8 q8, q8, d0\n"
2382 "vaddw.u8 q9, q9, d1\n"
2383 "vaddw.u8 q10, q10, d2\n"
2384 "vaddw.u8 q11, q11, d3\n"
2385 "vaddw.u8 q12, q12, d4\n"
2386 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
2387 "vst1.32 {d4}, [%[out]:64]!\n"
2388
2389 "bne 1b\n"
2390
2391 "2:"
2392
2393 // Load Aggregate Store: 5x2.
2394 "vmov.i8 d0, #0\n"
2395 "vmov.i8 d1, #0\n"
2396 "vmov.i8 d2, #0\n"
2397 "vmov.i8 d3, #0\n"
2398 "vmov.i8 d4, #0\n"
2399 "vld1.16 {d0[0]}, [%[in]]!\n"
2400 "vld1.16 {d1[0]}, [r0]!\n"
2401 "vld1.16 {d2[0]}, [r1]!\n"
2402 "vld1.16 {d3[0]}, [r2]!\n"
2403 "vld1.16 {d4[0]}, [r3]!\n"
2404 "vaddw.u8 q8, q8, d0\n"
2405 "vaddw.u8 q9, q9, d1\n"
2406 "vaddw.u8 q10, q10, d2\n"
2407 "vaddw.u8 q11, q11, d3\n"
2408 "vaddw.u8 q12, q12, d4\n"
2409 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
2410 "vst1.32 {d4}, [%[out]:64]!\n"
2411
2412 // Aggregator Reduction.
2413 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
2414 "vdup.32 q1, %[additive_sum_offset]\n"
2415 "vpaddl.u16 q8, q8\n"
2416 "vpaddl.u16 q9, q9\n"
2417 "vpaddl.u16 q10, q10\n"
2418 "vpaddl.u16 q11, q11\n"
2419 "vpaddl.u16 q12, q12\n"
2420 "vpadd.u32 d16, d16, d17\n"
2421 "vpadd.u32 d18, d18, d19\n"
2422 "vpadd.u32 d20, d20, d21\n"
2423 "vpadd.u32 d22, d22, d23\n"
2424 "vpadd.u32 d24, d24, d25\n"
2425 "vpadd.u32 d16, d16, d18\n"
2426 "vpadd.u32 d17, d20, d22\n"
2427 "vpadd.u32 d18, d24, d24\n"
2428 "vmul.i32 q8, q8, d0[0]\n"
2429 "vmul.i32 q9, q9, d0[0]\n"
2430 "vadd.i32 q8, q8, q1\n"
2431 "vadd.i32 q9, q9, q1\n"
2432 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
2433 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
2434 : [stride] "r"(params.stride),
2435 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
2436 [additive_sum_offset] "r"(params.additive_sum_offset)
2437 : "r0", "r1", "r2", "r3", "d0", "d1", "d2", "d3", "d4", "d16", "d17",
2438 "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "cc", "memory");
2439 }
2440
2441 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)2442 inline void Stream<uint8_t, 5, 8, 3, RowMajorWithSum>::Pack(
2443 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
2444 #ifdef DEBUG
2445 #ifdef DEBUG_METAGEMM_VERBOSE
2446 std::cout << __FILE__ << "(" << __LINE__
2447 << ") RowMajorWithSum<uint8_t, 5, 8, 3, RowMajorWithSum>::Pack()"
2448 << std::endl
2449 << std::flush;
2450 #endif
2451 #endif
2452 int params_count_copy = params.count;
2453 asm volatile(
2454 "add r0, %[in], %[stride]\n"
2455 "add r1, r0, %[stride]\n"
2456 "add r2, r1, %[stride]\n"
2457 "add r3, r2, %[stride]\n"
2458 "vmov.i16 q8, #0\n"
2459 "vmov.i16 q9, #0\n"
2460 "vmov.i16 q10, #0\n"
2461 "vmov.i16 q11, #0\n"
2462 "vmov.i16 q12, #0\n"
2463
2464 // Reduce count by leftovers.
2465 "subs %[count], %[count], #3\n"
2466 "beq 2f\n"
2467
2468 "1:"
2469 "subs %[count], %[count], #8\n"
2470
2471 // Load Aggregate Store: 5x8.
2472 "vld1.32 {d0}, [%[in]]!\n"
2473 "vld1.32 {d1}, [r0]!\n"
2474 "vld1.32 {d2}, [r1]!\n"
2475 "vld1.32 {d3}, [r2]!\n"
2476 "vld1.32 {d4}, [r3]!\n"
2477 "vaddw.u8 q8, q8, d0\n"
2478 "vaddw.u8 q9, q9, d1\n"
2479 "vaddw.u8 q10, q10, d2\n"
2480 "vaddw.u8 q11, q11, d3\n"
2481 "vaddw.u8 q12, q12, d4\n"
2482 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
2483 "vst1.32 {d4}, [%[out]:64]!\n"
2484
2485 "bne 1b\n"
2486
2487 "2:"
2488
2489 // Load Aggregate Store: 5x3.
2490 "vmov.i8 d0, #0\n"
2491 "vmov.i8 d1, #0\n"
2492 "vmov.i8 d2, #0\n"
2493 "vmov.i8 d3, #0\n"
2494 "vmov.i8 d4, #0\n"
2495 "vld1.16 {d0[0]}, [%[in]]!\n"
2496 "vld1.8 {d0[2]}, [%[in]]!\n"
2497 "vld1.16 {d1[0]}, [r0]!\n"
2498 "vld1.8 {d1[2]}, [r0]!\n"
2499 "vld1.16 {d2[0]}, [r1]!\n"
2500 "vld1.8 {d2[2]}, [r1]!\n"
2501 "vld1.16 {d3[0]}, [r2]!\n"
2502 "vld1.8 {d3[2]}, [r2]!\n"
2503 "vld1.16 {d4[0]}, [r3]!\n"
2504 "vld1.8 {d4[2]}, [r3]!\n"
2505 "vaddw.u8 q8, q8, d0\n"
2506 "vaddw.u8 q9, q9, d1\n"
2507 "vaddw.u8 q10, q10, d2\n"
2508 "vaddw.u8 q11, q11, d3\n"
2509 "vaddw.u8 q12, q12, d4\n"
2510 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
2511 "vst1.32 {d4}, [%[out]:64]!\n"
2512
2513 // Aggregator Reduction.
2514 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
2515 "vdup.32 q1, %[additive_sum_offset]\n"
2516 "vpaddl.u16 q8, q8\n"
2517 "vpaddl.u16 q9, q9\n"
2518 "vpaddl.u16 q10, q10\n"
2519 "vpaddl.u16 q11, q11\n"
2520 "vpaddl.u16 q12, q12\n"
2521 "vpadd.u32 d16, d16, d17\n"
2522 "vpadd.u32 d18, d18, d19\n"
2523 "vpadd.u32 d20, d20, d21\n"
2524 "vpadd.u32 d22, d22, d23\n"
2525 "vpadd.u32 d24, d24, d25\n"
2526 "vpadd.u32 d16, d16, d18\n"
2527 "vpadd.u32 d17, d20, d22\n"
2528 "vpadd.u32 d18, d24, d24\n"
2529 "vmul.i32 q8, q8, d0[0]\n"
2530 "vmul.i32 q9, q9, d0[0]\n"
2531 "vadd.i32 q8, q8, q1\n"
2532 "vadd.i32 q9, q9, q1\n"
2533 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
2534 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
2535 : [stride] "r"(params.stride),
2536 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
2537 [additive_sum_offset] "r"(params.additive_sum_offset)
2538 : "r0", "r1", "r2", "r3", "d0", "d1", "d2", "d3", "d4", "d16", "d17",
2539 "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "cc", "memory");
2540 }
2541
2542 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)2543 inline void Stream<uint8_t, 5, 8, 4, RowMajorWithSum>::Pack(
2544 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
2545 #ifdef DEBUG
2546 #ifdef DEBUG_METAGEMM_VERBOSE
2547 std::cout << __FILE__ << "(" << __LINE__
2548 << ") RowMajorWithSum<uint8_t, 5, 8, 4, RowMajorWithSum>::Pack()"
2549 << std::endl
2550 << std::flush;
2551 #endif
2552 #endif
2553 int params_count_copy = params.count;
2554 asm volatile(
2555 "add r0, %[in], %[stride]\n"
2556 "add r1, r0, %[stride]\n"
2557 "add r2, r1, %[stride]\n"
2558 "add r3, r2, %[stride]\n"
2559 "vmov.i16 q8, #0\n"
2560 "vmov.i16 q9, #0\n"
2561 "vmov.i16 q10, #0\n"
2562 "vmov.i16 q11, #0\n"
2563 "vmov.i16 q12, #0\n"
2564
2565 // Reduce count by leftovers.
2566 "subs %[count], %[count], #4\n"
2567 "beq 2f\n"
2568
2569 "1:"
2570 "subs %[count], %[count], #8\n"
2571
2572 // Load Aggregate Store: 5x8.
2573 "vld1.32 {d0}, [%[in]]!\n"
2574 "vld1.32 {d1}, [r0]!\n"
2575 "vld1.32 {d2}, [r1]!\n"
2576 "vld1.32 {d3}, [r2]!\n"
2577 "vld1.32 {d4}, [r3]!\n"
2578 "vaddw.u8 q8, q8, d0\n"
2579 "vaddw.u8 q9, q9, d1\n"
2580 "vaddw.u8 q10, q10, d2\n"
2581 "vaddw.u8 q11, q11, d3\n"
2582 "vaddw.u8 q12, q12, d4\n"
2583 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
2584 "vst1.32 {d4}, [%[out]:64]!\n"
2585
2586 "bne 1b\n"
2587
2588 "2:"
2589
2590 // Load Aggregate Store: 5x4.
2591 "vmov.i8 d0, #0\n"
2592 "vmov.i8 d1, #0\n"
2593 "vmov.i8 d2, #0\n"
2594 "vmov.i8 d3, #0\n"
2595 "vmov.i8 d4, #0\n"
2596 "vld1.32 {d0[0]}, [%[in]]!\n"
2597 "vld1.32 {d1[0]}, [r0]!\n"
2598 "vld1.32 {d2[0]}, [r1]!\n"
2599 "vld1.32 {d3[0]}, [r2]!\n"
2600 "vld1.32 {d4[0]}, [r3]!\n"
2601 "vaddw.u8 q8, q8, d0\n"
2602 "vaddw.u8 q9, q9, d1\n"
2603 "vaddw.u8 q10, q10, d2\n"
2604 "vaddw.u8 q11, q11, d3\n"
2605 "vaddw.u8 q12, q12, d4\n"
2606 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
2607 "vst1.32 {d4}, [%[out]:64]!\n"
2608
2609 // Aggregator Reduction.
2610 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
2611 "vdup.32 q1, %[additive_sum_offset]\n"
2612 "vpaddl.u16 q8, q8\n"
2613 "vpaddl.u16 q9, q9\n"
2614 "vpaddl.u16 q10, q10\n"
2615 "vpaddl.u16 q11, q11\n"
2616 "vpaddl.u16 q12, q12\n"
2617 "vpadd.u32 d16, d16, d17\n"
2618 "vpadd.u32 d18, d18, d19\n"
2619 "vpadd.u32 d20, d20, d21\n"
2620 "vpadd.u32 d22, d22, d23\n"
2621 "vpadd.u32 d24, d24, d25\n"
2622 "vpadd.u32 d16, d16, d18\n"
2623 "vpadd.u32 d17, d20, d22\n"
2624 "vpadd.u32 d18, d24, d24\n"
2625 "vmul.i32 q8, q8, d0[0]\n"
2626 "vmul.i32 q9, q9, d0[0]\n"
2627 "vadd.i32 q8, q8, q1\n"
2628 "vadd.i32 q9, q9, q1\n"
2629 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
2630 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
2631 : [stride] "r"(params.stride),
2632 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
2633 [additive_sum_offset] "r"(params.additive_sum_offset)
2634 : "r0", "r1", "r2", "r3", "d0", "d1", "d2", "d3", "d4", "d16", "d17",
2635 "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "cc", "memory");
2636 }
2637
2638 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)2639 inline void Stream<uint8_t, 5, 8, 5, RowMajorWithSum>::Pack(
2640 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
2641 #ifdef DEBUG
2642 #ifdef DEBUG_METAGEMM_VERBOSE
2643 std::cout << __FILE__ << "(" << __LINE__
2644 << ") RowMajorWithSum<uint8_t, 5, 8, 5, RowMajorWithSum>::Pack()"
2645 << std::endl
2646 << std::flush;
2647 #endif
2648 #endif
2649 int params_count_copy = params.count;
2650 asm volatile(
2651 "add r0, %[in], %[stride]\n"
2652 "add r1, r0, %[stride]\n"
2653 "add r2, r1, %[stride]\n"
2654 "add r3, r2, %[stride]\n"
2655 "vmov.i16 q8, #0\n"
2656 "vmov.i16 q9, #0\n"
2657 "vmov.i16 q10, #0\n"
2658 "vmov.i16 q11, #0\n"
2659 "vmov.i16 q12, #0\n"
2660
2661 // Reduce count by leftovers.
2662 "subs %[count], %[count], #5\n"
2663 "beq 2f\n"
2664
2665 "1:"
2666 "subs %[count], %[count], #8\n"
2667
2668 // Load Aggregate Store: 5x8.
2669 "vld1.32 {d0}, [%[in]]!\n"
2670 "vld1.32 {d1}, [r0]!\n"
2671 "vld1.32 {d2}, [r1]!\n"
2672 "vld1.32 {d3}, [r2]!\n"
2673 "vld1.32 {d4}, [r3]!\n"
2674 "vaddw.u8 q8, q8, d0\n"
2675 "vaddw.u8 q9, q9, d1\n"
2676 "vaddw.u8 q10, q10, d2\n"
2677 "vaddw.u8 q11, q11, d3\n"
2678 "vaddw.u8 q12, q12, d4\n"
2679 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
2680 "vst1.32 {d4}, [%[out]:64]!\n"
2681
2682 "bne 1b\n"
2683
2684 "2:"
2685
2686 // Load Aggregate Store: 5x5.
2687 "vmov.i8 d0, #0\n"
2688 "vmov.i8 d1, #0\n"
2689 "vmov.i8 d2, #0\n"
2690 "vmov.i8 d3, #0\n"
2691 "vmov.i8 d4, #0\n"
2692 "vld1.32 {d0[0]}, [%[in]]!\n"
2693 "vld1.8 {d0[4]}, [%[in]]!\n"
2694 "vld1.32 {d1[0]}, [r0]!\n"
2695 "vld1.8 {d1[4]}, [r0]!\n"
2696 "vld1.32 {d2[0]}, [r1]!\n"
2697 "vld1.8 {d2[4]}, [r1]!\n"
2698 "vld1.32 {d3[0]}, [r2]!\n"
2699 "vld1.8 {d3[4]}, [r2]!\n"
2700 "vld1.32 {d4[0]}, [r3]!\n"
2701 "vld1.8 {d4[4]}, [r3]!\n"
2702 "vaddw.u8 q8, q8, d0\n"
2703 "vaddw.u8 q9, q9, d1\n"
2704 "vaddw.u8 q10, q10, d2\n"
2705 "vaddw.u8 q11, q11, d3\n"
2706 "vaddw.u8 q12, q12, d4\n"
2707 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
2708 "vst1.32 {d4}, [%[out]:64]!\n"
2709
2710 // Aggregator Reduction.
2711 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
2712 "vdup.32 q1, %[additive_sum_offset]\n"
2713 "vpaddl.u16 q8, q8\n"
2714 "vpaddl.u16 q9, q9\n"
2715 "vpaddl.u16 q10, q10\n"
2716 "vpaddl.u16 q11, q11\n"
2717 "vpaddl.u16 q12, q12\n"
2718 "vpadd.u32 d16, d16, d17\n"
2719 "vpadd.u32 d18, d18, d19\n"
2720 "vpadd.u32 d20, d20, d21\n"
2721 "vpadd.u32 d22, d22, d23\n"
2722 "vpadd.u32 d24, d24, d25\n"
2723 "vpadd.u32 d16, d16, d18\n"
2724 "vpadd.u32 d17, d20, d22\n"
2725 "vpadd.u32 d18, d24, d24\n"
2726 "vmul.i32 q8, q8, d0[0]\n"
2727 "vmul.i32 q9, q9, d0[0]\n"
2728 "vadd.i32 q8, q8, q1\n"
2729 "vadd.i32 q9, q9, q1\n"
2730 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
2731 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
2732 : [stride] "r"(params.stride),
2733 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
2734 [additive_sum_offset] "r"(params.additive_sum_offset)
2735 : "r0", "r1", "r2", "r3", "d0", "d1", "d2", "d3", "d4", "d16", "d17",
2736 "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "cc", "memory");
2737 }
2738
2739 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)2740 inline void Stream<uint8_t, 5, 8, 6, RowMajorWithSum>::Pack(
2741 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
2742 #ifdef DEBUG
2743 #ifdef DEBUG_METAGEMM_VERBOSE
2744 std::cout << __FILE__ << "(" << __LINE__
2745 << ") RowMajorWithSum<uint8_t, 5, 8, 6, RowMajorWithSum>::Pack()"
2746 << std::endl
2747 << std::flush;
2748 #endif
2749 #endif
2750 int params_count_copy = params.count;
2751 asm volatile(
2752 "add r0, %[in], %[stride]\n"
2753 "add r1, r0, %[stride]\n"
2754 "add r2, r1, %[stride]\n"
2755 "add r3, r2, %[stride]\n"
2756 "vmov.i16 q8, #0\n"
2757 "vmov.i16 q9, #0\n"
2758 "vmov.i16 q10, #0\n"
2759 "vmov.i16 q11, #0\n"
2760 "vmov.i16 q12, #0\n"
2761
2762 // Reduce count by leftovers.
2763 "subs %[count], %[count], #6\n"
2764 "beq 2f\n"
2765
2766 "1:"
2767 "subs %[count], %[count], #8\n"
2768
2769 // Load Aggregate Store: 5x8.
2770 "vld1.32 {d0}, [%[in]]!\n"
2771 "vld1.32 {d1}, [r0]!\n"
2772 "vld1.32 {d2}, [r1]!\n"
2773 "vld1.32 {d3}, [r2]!\n"
2774 "vld1.32 {d4}, [r3]!\n"
2775 "vaddw.u8 q8, q8, d0\n"
2776 "vaddw.u8 q9, q9, d1\n"
2777 "vaddw.u8 q10, q10, d2\n"
2778 "vaddw.u8 q11, q11, d3\n"
2779 "vaddw.u8 q12, q12, d4\n"
2780 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
2781 "vst1.32 {d4}, [%[out]:64]!\n"
2782
2783 "bne 1b\n"
2784
2785 "2:"
2786
2787 // Load Aggregate Store: 5x6.
2788 "vmov.i8 d0, #0\n"
2789 "vmov.i8 d1, #0\n"
2790 "vmov.i8 d2, #0\n"
2791 "vmov.i8 d3, #0\n"
2792 "vmov.i8 d4, #0\n"
2793 "vld1.32 {d0[0]}, [%[in]]!\n"
2794 "vld1.16 {d0[2]}, [%[in]]!\n"
2795 "vld1.32 {d1[0]}, [r0]!\n"
2796 "vld1.16 {d1[2]}, [r0]!\n"
2797 "vld1.32 {d2[0]}, [r1]!\n"
2798 "vld1.16 {d2[2]}, [r1]!\n"
2799 "vld1.32 {d3[0]}, [r2]!\n"
2800 "vld1.16 {d3[2]}, [r2]!\n"
2801 "vld1.32 {d4[0]}, [r3]!\n"
2802 "vld1.16 {d4[2]}, [r3]!\n"
2803 "vaddw.u8 q8, q8, d0\n"
2804 "vaddw.u8 q9, q9, d1\n"
2805 "vaddw.u8 q10, q10, d2\n"
2806 "vaddw.u8 q11, q11, d3\n"
2807 "vaddw.u8 q12, q12, d4\n"
2808 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
2809 "vst1.32 {d4}, [%[out]:64]!\n"
2810
2811 // Aggregator Reduction.
2812 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
2813 "vdup.32 q1, %[additive_sum_offset]\n"
2814 "vpaddl.u16 q8, q8\n"
2815 "vpaddl.u16 q9, q9\n"
2816 "vpaddl.u16 q10, q10\n"
2817 "vpaddl.u16 q11, q11\n"
2818 "vpaddl.u16 q12, q12\n"
2819 "vpadd.u32 d16, d16, d17\n"
2820 "vpadd.u32 d18, d18, d19\n"
2821 "vpadd.u32 d20, d20, d21\n"
2822 "vpadd.u32 d22, d22, d23\n"
2823 "vpadd.u32 d24, d24, d25\n"
2824 "vpadd.u32 d16, d16, d18\n"
2825 "vpadd.u32 d17, d20, d22\n"
2826 "vpadd.u32 d18, d24, d24\n"
2827 "vmul.i32 q8, q8, d0[0]\n"
2828 "vmul.i32 q9, q9, d0[0]\n"
2829 "vadd.i32 q8, q8, q1\n"
2830 "vadd.i32 q9, q9, q1\n"
2831 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
2832 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
2833 : [stride] "r"(params.stride),
2834 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
2835 [additive_sum_offset] "r"(params.additive_sum_offset)
2836 : "r0", "r1", "r2", "r3", "d0", "d1", "d2", "d3", "d4", "d16", "d17",
2837 "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "cc", "memory");
2838 }
2839
2840 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)2841 inline void Stream<uint8_t, 5, 8, 7, RowMajorWithSum>::Pack(
2842 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
2843 #ifdef DEBUG
2844 #ifdef DEBUG_METAGEMM_VERBOSE
2845 std::cout << __FILE__ << "(" << __LINE__
2846 << ") RowMajorWithSum<uint8_t, 5, 8, 7, RowMajorWithSum>::Pack()"
2847 << std::endl
2848 << std::flush;
2849 #endif
2850 #endif
2851 int params_count_copy = params.count;
2852 asm volatile(
2853 "add r0, %[in], %[stride]\n"
2854 "add r1, r0, %[stride]\n"
2855 "add r2, r1, %[stride]\n"
2856 "add r3, r2, %[stride]\n"
2857 "vmov.i16 q8, #0\n"
2858 "vmov.i16 q9, #0\n"
2859 "vmov.i16 q10, #0\n"
2860 "vmov.i16 q11, #0\n"
2861 "vmov.i16 q12, #0\n"
2862
2863 // Reduce count by leftovers.
2864 "subs %[count], %[count], #7\n"
2865 "beq 2f\n"
2866
2867 "1:"
2868 "subs %[count], %[count], #8\n"
2869
2870 // Load Aggregate Store: 5x8.
2871 "vld1.32 {d0}, [%[in]]!\n"
2872 "vld1.32 {d1}, [r0]!\n"
2873 "vld1.32 {d2}, [r1]!\n"
2874 "vld1.32 {d3}, [r2]!\n"
2875 "vld1.32 {d4}, [r3]!\n"
2876 "vaddw.u8 q8, q8, d0\n"
2877 "vaddw.u8 q9, q9, d1\n"
2878 "vaddw.u8 q10, q10, d2\n"
2879 "vaddw.u8 q11, q11, d3\n"
2880 "vaddw.u8 q12, q12, d4\n"
2881 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
2882 "vst1.32 {d4}, [%[out]:64]!\n"
2883
2884 "bne 1b\n"
2885
2886 "2:"
2887
2888 // Load Aggregate Store: 5x7.
2889 "vmov.i8 d0, #0\n"
2890 "vmov.i8 d1, #0\n"
2891 "vmov.i8 d2, #0\n"
2892 "vmov.i8 d3, #0\n"
2893 "vmov.i8 d4, #0\n"
2894 "vld1.32 {d0[0]}, [%[in]]!\n"
2895 "vld1.16 {d0[2]}, [%[in]]!\n"
2896 "vld1.8 {d0[6]}, [%[in]]!\n"
2897 "vld1.32 {d1[0]}, [r0]!\n"
2898 "vld1.16 {d1[2]}, [r0]!\n"
2899 "vld1.8 {d1[6]}, [r0]!\n"
2900 "vld1.32 {d2[0]}, [r1]!\n"
2901 "vld1.16 {d2[2]}, [r1]!\n"
2902 "vld1.8 {d2[6]}, [r1]!\n"
2903 "vld1.32 {d3[0]}, [r2]!\n"
2904 "vld1.16 {d3[2]}, [r2]!\n"
2905 "vld1.8 {d3[6]}, [r2]!\n"
2906 "vld1.32 {d4[0]}, [r3]!\n"
2907 "vld1.16 {d4[2]}, [r3]!\n"
2908 "vld1.8 {d4[6]}, [r3]!\n"
2909 "vaddw.u8 q8, q8, d0\n"
2910 "vaddw.u8 q9, q9, d1\n"
2911 "vaddw.u8 q10, q10, d2\n"
2912 "vaddw.u8 q11, q11, d3\n"
2913 "vaddw.u8 q12, q12, d4\n"
2914 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
2915 "vst1.32 {d4}, [%[out]:64]!\n"
2916
2917 // Aggregator Reduction.
2918 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
2919 "vdup.32 q1, %[additive_sum_offset]\n"
2920 "vpaddl.u16 q8, q8\n"
2921 "vpaddl.u16 q9, q9\n"
2922 "vpaddl.u16 q10, q10\n"
2923 "vpaddl.u16 q11, q11\n"
2924 "vpaddl.u16 q12, q12\n"
2925 "vpadd.u32 d16, d16, d17\n"
2926 "vpadd.u32 d18, d18, d19\n"
2927 "vpadd.u32 d20, d20, d21\n"
2928 "vpadd.u32 d22, d22, d23\n"
2929 "vpadd.u32 d24, d24, d25\n"
2930 "vpadd.u32 d16, d16, d18\n"
2931 "vpadd.u32 d17, d20, d22\n"
2932 "vpadd.u32 d18, d24, d24\n"
2933 "vmul.i32 q8, q8, d0[0]\n"
2934 "vmul.i32 q9, q9, d0[0]\n"
2935 "vadd.i32 q8, q8, q1\n"
2936 "vadd.i32 q9, q9, q1\n"
2937 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
2938 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
2939 : [stride] "r"(params.stride),
2940 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
2941 [additive_sum_offset] "r"(params.additive_sum_offset)
2942 : "r0", "r1", "r2", "r3", "d0", "d1", "d2", "d3", "d4", "d16", "d17",
2943 "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "cc", "memory");
2944 }
2945
2946 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)2947 inline void Stream<uint8_t, 6, 8, 0, RowMajorWithSum>::Pack(
2948 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
2949 #ifdef DEBUG
2950 #ifdef DEBUG_METAGEMM_VERBOSE
2951 std::cout << __FILE__ << "(" << __LINE__
2952 << ") RowMajorWithSum<uint8_t, 6, 8, 0, RowMajorWithSum>::Pack()"
2953 << std::endl
2954 << std::flush;
2955 #endif
2956 #endif
2957 int params_count_copy = params.count;
2958 asm volatile(
2959 "add r0, %[in], %[stride]\n"
2960 "add r1, r0, %[stride]\n"
2961 "add r2, r1, %[stride]\n"
2962 "add r3, r2, %[stride]\n"
2963 "add r4, r3, %[stride]\n"
2964 "vmov.i16 q8, #0\n"
2965 "vmov.i16 q9, #0\n"
2966 "vmov.i16 q10, #0\n"
2967 "vmov.i16 q11, #0\n"
2968 "vmov.i16 q12, #0\n"
2969 "vmov.i16 q13, #0\n"
2970
2971 "1:"
2972 "subs %[count], %[count], #8\n"
2973
2974 // Load Aggregate Store: 6x8.
2975 "vld1.32 {d0}, [%[in]]!\n"
2976 "vld1.32 {d1}, [r0]!\n"
2977 "vld1.32 {d2}, [r1]!\n"
2978 "vld1.32 {d3}, [r2]!\n"
2979 "vld1.32 {d4}, [r3]!\n"
2980 "vld1.32 {d5}, [r4]!\n"
2981 "vaddw.u8 q8, q8, d0\n"
2982 "vaddw.u8 q9, q9, d1\n"
2983 "vaddw.u8 q10, q10, d2\n"
2984 "vaddw.u8 q11, q11, d3\n"
2985 "vaddw.u8 q12, q12, d4\n"
2986 "vaddw.u8 q13, q13, d5\n"
2987 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
2988 "vst1.32 {d4, d5}, [%[out]:128]!\n"
2989
2990 "bne 1b\n"
2991
2992 // Aggregator Reduction.
2993 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
2994 "vdup.32 q1, %[additive_sum_offset]\n"
2995 "vpaddl.u16 q8, q8\n"
2996 "vpaddl.u16 q9, q9\n"
2997 "vpaddl.u16 q10, q10\n"
2998 "vpaddl.u16 q11, q11\n"
2999 "vpaddl.u16 q12, q12\n"
3000 "vpaddl.u16 q13, q13\n"
3001 "vpadd.u32 d16, d16, d17\n"
3002 "vpadd.u32 d18, d18, d19\n"
3003 "vpadd.u32 d20, d20, d21\n"
3004 "vpadd.u32 d22, d22, d23\n"
3005 "vpadd.u32 d24, d24, d25\n"
3006 "vpadd.u32 d26, d26, d27\n"
3007 "vpadd.u32 d16, d16, d18\n"
3008 "vpadd.u32 d17, d20, d22\n"
3009 "vpadd.u32 d18, d24, d26\n"
3010 "vmul.i32 q8, q8, d0[0]\n"
3011 "vmul.i32 q9, q9, d0[0]\n"
3012 "vadd.i32 q8, q8, q1\n"
3013 "vadd.i32 q9, q9, q1\n"
3014 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
3015 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
3016 : [stride] "r"(params.stride),
3017 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
3018 [additive_sum_offset] "r"(params.additive_sum_offset)
3019 : "r0", "r1", "r2", "r3", "r4", "d0", "d1", "d2", "d3", "d4", "d5", "d16",
3020 "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26",
3021 "d27", "cc", "memory");
3022 }
3023
3024 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)3025 inline void Stream<uint8_t, 6, 8, 1, RowMajorWithSum>::Pack(
3026 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
3027 #ifdef DEBUG
3028 #ifdef DEBUG_METAGEMM_VERBOSE
3029 std::cout << __FILE__ << "(" << __LINE__
3030 << ") RowMajorWithSum<uint8_t, 6, 8, 1, RowMajorWithSum>::Pack()"
3031 << std::endl
3032 << std::flush;
3033 #endif
3034 #endif
3035 int params_count_copy = params.count;
3036 asm volatile(
3037 "add r0, %[in], %[stride]\n"
3038 "add r1, r0, %[stride]\n"
3039 "add r2, r1, %[stride]\n"
3040 "add r3, r2, %[stride]\n"
3041 "add r4, r3, %[stride]\n"
3042 "vmov.i16 q8, #0\n"
3043 "vmov.i16 q9, #0\n"
3044 "vmov.i16 q10, #0\n"
3045 "vmov.i16 q11, #0\n"
3046 "vmov.i16 q12, #0\n"
3047 "vmov.i16 q13, #0\n"
3048
3049 // Reduce count by leftovers.
3050 "subs %[count], %[count], #1\n"
3051 "beq 2f\n"
3052
3053 "1:"
3054 "subs %[count], %[count], #8\n"
3055
3056 // Load Aggregate Store: 6x8.
3057 "vld1.32 {d0}, [%[in]]!\n"
3058 "vld1.32 {d1}, [r0]!\n"
3059 "vld1.32 {d2}, [r1]!\n"
3060 "vld1.32 {d3}, [r2]!\n"
3061 "vld1.32 {d4}, [r3]!\n"
3062 "vld1.32 {d5}, [r4]!\n"
3063 "vaddw.u8 q8, q8, d0\n"
3064 "vaddw.u8 q9, q9, d1\n"
3065 "vaddw.u8 q10, q10, d2\n"
3066 "vaddw.u8 q11, q11, d3\n"
3067 "vaddw.u8 q12, q12, d4\n"
3068 "vaddw.u8 q13, q13, d5\n"
3069 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
3070 "vst1.32 {d4, d5}, [%[out]:128]!\n"
3071
3072 "bne 1b\n"
3073
3074 "2:"
3075
3076 // Load Aggregate Store: 6x1.
3077 "vmov.i8 d0, #0\n"
3078 "vmov.i8 d1, #0\n"
3079 "vmov.i8 d2, #0\n"
3080 "vmov.i8 d3, #0\n"
3081 "vmov.i8 d4, #0\n"
3082 "vmov.i8 d5, #0\n"
3083 "vld1.8 {d0[0]}, [%[in]]!\n"
3084 "vld1.8 {d1[0]}, [r0]!\n"
3085 "vld1.8 {d2[0]}, [r1]!\n"
3086 "vld1.8 {d3[0]}, [r2]!\n"
3087 "vld1.8 {d4[0]}, [r3]!\n"
3088 "vld1.8 {d5[0]}, [r4]!\n"
3089 "vaddw.u8 q8, q8, d0\n"
3090 "vaddw.u8 q9, q9, d1\n"
3091 "vaddw.u8 q10, q10, d2\n"
3092 "vaddw.u8 q11, q11, d3\n"
3093 "vaddw.u8 q12, q12, d4\n"
3094 "vaddw.u8 q13, q13, d5\n"
3095 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
3096 "vst1.32 {d4, d5}, [%[out]:128]!\n"
3097
3098 // Aggregator Reduction.
3099 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
3100 "vdup.32 q1, %[additive_sum_offset]\n"
3101 "vpaddl.u16 q8, q8\n"
3102 "vpaddl.u16 q9, q9\n"
3103 "vpaddl.u16 q10, q10\n"
3104 "vpaddl.u16 q11, q11\n"
3105 "vpaddl.u16 q12, q12\n"
3106 "vpaddl.u16 q13, q13\n"
3107 "vpadd.u32 d16, d16, d17\n"
3108 "vpadd.u32 d18, d18, d19\n"
3109 "vpadd.u32 d20, d20, d21\n"
3110 "vpadd.u32 d22, d22, d23\n"
3111 "vpadd.u32 d24, d24, d25\n"
3112 "vpadd.u32 d26, d26, d27\n"
3113 "vpadd.u32 d16, d16, d18\n"
3114 "vpadd.u32 d17, d20, d22\n"
3115 "vpadd.u32 d18, d24, d26\n"
3116 "vmul.i32 q8, q8, d0[0]\n"
3117 "vmul.i32 q9, q9, d0[0]\n"
3118 "vadd.i32 q8, q8, q1\n"
3119 "vadd.i32 q9, q9, q1\n"
3120 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
3121 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
3122 : [stride] "r"(params.stride),
3123 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
3124 [additive_sum_offset] "r"(params.additive_sum_offset)
3125 : "r0", "r1", "r2", "r3", "r4", "d0", "d1", "d2", "d3", "d4", "d5", "d16",
3126 "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26",
3127 "d27", "cc", "memory");
3128 }
3129
3130 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)3131 inline void Stream<uint8_t, 6, 8, 2, RowMajorWithSum>::Pack(
3132 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
3133 #ifdef DEBUG
3134 #ifdef DEBUG_METAGEMM_VERBOSE
3135 std::cout << __FILE__ << "(" << __LINE__
3136 << ") RowMajorWithSum<uint8_t, 6, 8, 2, RowMajorWithSum>::Pack()"
3137 << std::endl
3138 << std::flush;
3139 #endif
3140 #endif
3141 int params_count_copy = params.count;
3142 asm volatile(
3143 "add r0, %[in], %[stride]\n"
3144 "add r1, r0, %[stride]\n"
3145 "add r2, r1, %[stride]\n"
3146 "add r3, r2, %[stride]\n"
3147 "add r4, r3, %[stride]\n"
3148 "vmov.i16 q8, #0\n"
3149 "vmov.i16 q9, #0\n"
3150 "vmov.i16 q10, #0\n"
3151 "vmov.i16 q11, #0\n"
3152 "vmov.i16 q12, #0\n"
3153 "vmov.i16 q13, #0\n"
3154
3155 // Reduce count by leftovers.
3156 "subs %[count], %[count], #2\n"
3157 "beq 2f\n"
3158
3159 "1:"
3160 "subs %[count], %[count], #8\n"
3161
3162 // Load Aggregate Store: 6x8.
3163 "vld1.32 {d0}, [%[in]]!\n"
3164 "vld1.32 {d1}, [r0]!\n"
3165 "vld1.32 {d2}, [r1]!\n"
3166 "vld1.32 {d3}, [r2]!\n"
3167 "vld1.32 {d4}, [r3]!\n"
3168 "vld1.32 {d5}, [r4]!\n"
3169 "vaddw.u8 q8, q8, d0\n"
3170 "vaddw.u8 q9, q9, d1\n"
3171 "vaddw.u8 q10, q10, d2\n"
3172 "vaddw.u8 q11, q11, d3\n"
3173 "vaddw.u8 q12, q12, d4\n"
3174 "vaddw.u8 q13, q13, d5\n"
3175 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
3176 "vst1.32 {d4, d5}, [%[out]:128]!\n"
3177
3178 "bne 1b\n"
3179
3180 "2:"
3181
3182 // Load Aggregate Store: 6x2.
3183 "vmov.i8 d0, #0\n"
3184 "vmov.i8 d1, #0\n"
3185 "vmov.i8 d2, #0\n"
3186 "vmov.i8 d3, #0\n"
3187 "vmov.i8 d4, #0\n"
3188 "vmov.i8 d5, #0\n"
3189 "vld1.16 {d0[0]}, [%[in]]!\n"
3190 "vld1.16 {d1[0]}, [r0]!\n"
3191 "vld1.16 {d2[0]}, [r1]!\n"
3192 "vld1.16 {d3[0]}, [r2]!\n"
3193 "vld1.16 {d4[0]}, [r3]!\n"
3194 "vld1.16 {d5[0]}, [r4]!\n"
3195 "vaddw.u8 q8, q8, d0\n"
3196 "vaddw.u8 q9, q9, d1\n"
3197 "vaddw.u8 q10, q10, d2\n"
3198 "vaddw.u8 q11, q11, d3\n"
3199 "vaddw.u8 q12, q12, d4\n"
3200 "vaddw.u8 q13, q13, d5\n"
3201 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
3202 "vst1.32 {d4, d5}, [%[out]:128]!\n"
3203
3204 // Aggregator Reduction.
3205 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
3206 "vdup.32 q1, %[additive_sum_offset]\n"
3207 "vpaddl.u16 q8, q8\n"
3208 "vpaddl.u16 q9, q9\n"
3209 "vpaddl.u16 q10, q10\n"
3210 "vpaddl.u16 q11, q11\n"
3211 "vpaddl.u16 q12, q12\n"
3212 "vpaddl.u16 q13, q13\n"
3213 "vpadd.u32 d16, d16, d17\n"
3214 "vpadd.u32 d18, d18, d19\n"
3215 "vpadd.u32 d20, d20, d21\n"
3216 "vpadd.u32 d22, d22, d23\n"
3217 "vpadd.u32 d24, d24, d25\n"
3218 "vpadd.u32 d26, d26, d27\n"
3219 "vpadd.u32 d16, d16, d18\n"
3220 "vpadd.u32 d17, d20, d22\n"
3221 "vpadd.u32 d18, d24, d26\n"
3222 "vmul.i32 q8, q8, d0[0]\n"
3223 "vmul.i32 q9, q9, d0[0]\n"
3224 "vadd.i32 q8, q8, q1\n"
3225 "vadd.i32 q9, q9, q1\n"
3226 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
3227 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
3228 : [stride] "r"(params.stride),
3229 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
3230 [additive_sum_offset] "r"(params.additive_sum_offset)
3231 : "r0", "r1", "r2", "r3", "r4", "d0", "d1", "d2", "d3", "d4", "d5", "d16",
3232 "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26",
3233 "d27", "cc", "memory");
3234 }
3235
3236 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)3237 inline void Stream<uint8_t, 6, 8, 3, RowMajorWithSum>::Pack(
3238 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
3239 #ifdef DEBUG
3240 #ifdef DEBUG_METAGEMM_VERBOSE
3241 std::cout << __FILE__ << "(" << __LINE__
3242 << ") RowMajorWithSum<uint8_t, 6, 8, 3, RowMajorWithSum>::Pack()"
3243 << std::endl
3244 << std::flush;
3245 #endif
3246 #endif
3247 int params_count_copy = params.count;
3248 asm volatile(
3249 "add r0, %[in], %[stride]\n"
3250 "add r1, r0, %[stride]\n"
3251 "add r2, r1, %[stride]\n"
3252 "add r3, r2, %[stride]\n"
3253 "add r4, r3, %[stride]\n"
3254 "vmov.i16 q8, #0\n"
3255 "vmov.i16 q9, #0\n"
3256 "vmov.i16 q10, #0\n"
3257 "vmov.i16 q11, #0\n"
3258 "vmov.i16 q12, #0\n"
3259 "vmov.i16 q13, #0\n"
3260
3261 // Reduce count by leftovers.
3262 "subs %[count], %[count], #3\n"
3263 "beq 2f\n"
3264
3265 "1:"
3266 "subs %[count], %[count], #8\n"
3267
3268 // Load Aggregate Store: 6x8.
3269 "vld1.32 {d0}, [%[in]]!\n"
3270 "vld1.32 {d1}, [r0]!\n"
3271 "vld1.32 {d2}, [r1]!\n"
3272 "vld1.32 {d3}, [r2]!\n"
3273 "vld1.32 {d4}, [r3]!\n"
3274 "vld1.32 {d5}, [r4]!\n"
3275 "vaddw.u8 q8, q8, d0\n"
3276 "vaddw.u8 q9, q9, d1\n"
3277 "vaddw.u8 q10, q10, d2\n"
3278 "vaddw.u8 q11, q11, d3\n"
3279 "vaddw.u8 q12, q12, d4\n"
3280 "vaddw.u8 q13, q13, d5\n"
3281 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
3282 "vst1.32 {d4, d5}, [%[out]:128]!\n"
3283
3284 "bne 1b\n"
3285
3286 "2:"
3287
3288 // Load Aggregate Store: 6x3.
3289 "vmov.i8 d0, #0\n"
3290 "vmov.i8 d1, #0\n"
3291 "vmov.i8 d2, #0\n"
3292 "vmov.i8 d3, #0\n"
3293 "vmov.i8 d4, #0\n"
3294 "vmov.i8 d5, #0\n"
3295 "vld1.16 {d0[0]}, [%[in]]!\n"
3296 "vld1.8 {d0[2]}, [%[in]]!\n"
3297 "vld1.16 {d1[0]}, [r0]!\n"
3298 "vld1.8 {d1[2]}, [r0]!\n"
3299 "vld1.16 {d2[0]}, [r1]!\n"
3300 "vld1.8 {d2[2]}, [r1]!\n"
3301 "vld1.16 {d3[0]}, [r2]!\n"
3302 "vld1.8 {d3[2]}, [r2]!\n"
3303 "vld1.16 {d4[0]}, [r3]!\n"
3304 "vld1.8 {d4[2]}, [r3]!\n"
3305 "vld1.16 {d5[0]}, [r4]!\n"
3306 "vld1.8 {d5[2]}, [r4]!\n"
3307 "vaddw.u8 q8, q8, d0\n"
3308 "vaddw.u8 q9, q9, d1\n"
3309 "vaddw.u8 q10, q10, d2\n"
3310 "vaddw.u8 q11, q11, d3\n"
3311 "vaddw.u8 q12, q12, d4\n"
3312 "vaddw.u8 q13, q13, d5\n"
3313 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
3314 "vst1.32 {d4, d5}, [%[out]:128]!\n"
3315
3316 // Aggregator Reduction.
3317 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
3318 "vdup.32 q1, %[additive_sum_offset]\n"
3319 "vpaddl.u16 q8, q8\n"
3320 "vpaddl.u16 q9, q9\n"
3321 "vpaddl.u16 q10, q10\n"
3322 "vpaddl.u16 q11, q11\n"
3323 "vpaddl.u16 q12, q12\n"
3324 "vpaddl.u16 q13, q13\n"
3325 "vpadd.u32 d16, d16, d17\n"
3326 "vpadd.u32 d18, d18, d19\n"
3327 "vpadd.u32 d20, d20, d21\n"
3328 "vpadd.u32 d22, d22, d23\n"
3329 "vpadd.u32 d24, d24, d25\n"
3330 "vpadd.u32 d26, d26, d27\n"
3331 "vpadd.u32 d16, d16, d18\n"
3332 "vpadd.u32 d17, d20, d22\n"
3333 "vpadd.u32 d18, d24, d26\n"
3334 "vmul.i32 q8, q8, d0[0]\n"
3335 "vmul.i32 q9, q9, d0[0]\n"
3336 "vadd.i32 q8, q8, q1\n"
3337 "vadd.i32 q9, q9, q1\n"
3338 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
3339 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
3340 : [stride] "r"(params.stride),
3341 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
3342 [additive_sum_offset] "r"(params.additive_sum_offset)
3343 : "r0", "r1", "r2", "r3", "r4", "d0", "d1", "d2", "d3", "d4", "d5", "d16",
3344 "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26",
3345 "d27", "cc", "memory");
3346 }
3347
3348 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)3349 inline void Stream<uint8_t, 6, 8, 4, RowMajorWithSum>::Pack(
3350 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
3351 #ifdef DEBUG
3352 #ifdef DEBUG_METAGEMM_VERBOSE
3353 std::cout << __FILE__ << "(" << __LINE__
3354 << ") RowMajorWithSum<uint8_t, 6, 8, 4, RowMajorWithSum>::Pack()"
3355 << std::endl
3356 << std::flush;
3357 #endif
3358 #endif
3359 int params_count_copy = params.count;
3360 asm volatile(
3361 "add r0, %[in], %[stride]\n"
3362 "add r1, r0, %[stride]\n"
3363 "add r2, r1, %[stride]\n"
3364 "add r3, r2, %[stride]\n"
3365 "add r4, r3, %[stride]\n"
3366 "vmov.i16 q8, #0\n"
3367 "vmov.i16 q9, #0\n"
3368 "vmov.i16 q10, #0\n"
3369 "vmov.i16 q11, #0\n"
3370 "vmov.i16 q12, #0\n"
3371 "vmov.i16 q13, #0\n"
3372
3373 // Reduce count by leftovers.
3374 "subs %[count], %[count], #4\n"
3375 "beq 2f\n"
3376
3377 "1:"
3378 "subs %[count], %[count], #8\n"
3379
3380 // Load Aggregate Store: 6x8.
3381 "vld1.32 {d0}, [%[in]]!\n"
3382 "vld1.32 {d1}, [r0]!\n"
3383 "vld1.32 {d2}, [r1]!\n"
3384 "vld1.32 {d3}, [r2]!\n"
3385 "vld1.32 {d4}, [r3]!\n"
3386 "vld1.32 {d5}, [r4]!\n"
3387 "vaddw.u8 q8, q8, d0\n"
3388 "vaddw.u8 q9, q9, d1\n"
3389 "vaddw.u8 q10, q10, d2\n"
3390 "vaddw.u8 q11, q11, d3\n"
3391 "vaddw.u8 q12, q12, d4\n"
3392 "vaddw.u8 q13, q13, d5\n"
3393 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
3394 "vst1.32 {d4, d5}, [%[out]:128]!\n"
3395
3396 "bne 1b\n"
3397
3398 "2:"
3399
3400 // Load Aggregate Store: 6x4.
3401 "vmov.i8 d0, #0\n"
3402 "vmov.i8 d1, #0\n"
3403 "vmov.i8 d2, #0\n"
3404 "vmov.i8 d3, #0\n"
3405 "vmov.i8 d4, #0\n"
3406 "vmov.i8 d5, #0\n"
3407 "vld1.32 {d0[0]}, [%[in]]!\n"
3408 "vld1.32 {d1[0]}, [r0]!\n"
3409 "vld1.32 {d2[0]}, [r1]!\n"
3410 "vld1.32 {d3[0]}, [r2]!\n"
3411 "vld1.32 {d4[0]}, [r3]!\n"
3412 "vld1.32 {d5[0]}, [r4]!\n"
3413 "vaddw.u8 q8, q8, d0\n"
3414 "vaddw.u8 q9, q9, d1\n"
3415 "vaddw.u8 q10, q10, d2\n"
3416 "vaddw.u8 q11, q11, d3\n"
3417 "vaddw.u8 q12, q12, d4\n"
3418 "vaddw.u8 q13, q13, d5\n"
3419 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
3420 "vst1.32 {d4, d5}, [%[out]:128]!\n"
3421
3422 // Aggregator Reduction.
3423 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
3424 "vdup.32 q1, %[additive_sum_offset]\n"
3425 "vpaddl.u16 q8, q8\n"
3426 "vpaddl.u16 q9, q9\n"
3427 "vpaddl.u16 q10, q10\n"
3428 "vpaddl.u16 q11, q11\n"
3429 "vpaddl.u16 q12, q12\n"
3430 "vpaddl.u16 q13, q13\n"
3431 "vpadd.u32 d16, d16, d17\n"
3432 "vpadd.u32 d18, d18, d19\n"
3433 "vpadd.u32 d20, d20, d21\n"
3434 "vpadd.u32 d22, d22, d23\n"
3435 "vpadd.u32 d24, d24, d25\n"
3436 "vpadd.u32 d26, d26, d27\n"
3437 "vpadd.u32 d16, d16, d18\n"
3438 "vpadd.u32 d17, d20, d22\n"
3439 "vpadd.u32 d18, d24, d26\n"
3440 "vmul.i32 q8, q8, d0[0]\n"
3441 "vmul.i32 q9, q9, d0[0]\n"
3442 "vadd.i32 q8, q8, q1\n"
3443 "vadd.i32 q9, q9, q1\n"
3444 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
3445 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
3446 : [stride] "r"(params.stride),
3447 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
3448 [additive_sum_offset] "r"(params.additive_sum_offset)
3449 : "r0", "r1", "r2", "r3", "r4", "d0", "d1", "d2", "d3", "d4", "d5", "d16",
3450 "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26",
3451 "d27", "cc", "memory");
3452 }
3453
3454 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)3455 inline void Stream<uint8_t, 6, 8, 5, RowMajorWithSum>::Pack(
3456 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
3457 #ifdef DEBUG
3458 #ifdef DEBUG_METAGEMM_VERBOSE
3459 std::cout << __FILE__ << "(" << __LINE__
3460 << ") RowMajorWithSum<uint8_t, 6, 8, 5, RowMajorWithSum>::Pack()"
3461 << std::endl
3462 << std::flush;
3463 #endif
3464 #endif
3465 int params_count_copy = params.count;
3466 asm volatile(
3467 "add r0, %[in], %[stride]\n"
3468 "add r1, r0, %[stride]\n"
3469 "add r2, r1, %[stride]\n"
3470 "add r3, r2, %[stride]\n"
3471 "add r4, r3, %[stride]\n"
3472 "vmov.i16 q8, #0\n"
3473 "vmov.i16 q9, #0\n"
3474 "vmov.i16 q10, #0\n"
3475 "vmov.i16 q11, #0\n"
3476 "vmov.i16 q12, #0\n"
3477 "vmov.i16 q13, #0\n"
3478
3479 // Reduce count by leftovers.
3480 "subs %[count], %[count], #5\n"
3481 "beq 2f\n"
3482
3483 "1:"
3484 "subs %[count], %[count], #8\n"
3485
3486 // Load Aggregate Store: 6x8.
3487 "vld1.32 {d0}, [%[in]]!\n"
3488 "vld1.32 {d1}, [r0]!\n"
3489 "vld1.32 {d2}, [r1]!\n"
3490 "vld1.32 {d3}, [r2]!\n"
3491 "vld1.32 {d4}, [r3]!\n"
3492 "vld1.32 {d5}, [r4]!\n"
3493 "vaddw.u8 q8, q8, d0\n"
3494 "vaddw.u8 q9, q9, d1\n"
3495 "vaddw.u8 q10, q10, d2\n"
3496 "vaddw.u8 q11, q11, d3\n"
3497 "vaddw.u8 q12, q12, d4\n"
3498 "vaddw.u8 q13, q13, d5\n"
3499 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
3500 "vst1.32 {d4, d5}, [%[out]:128]!\n"
3501
3502 "bne 1b\n"
3503
3504 "2:"
3505
3506 // Load Aggregate Store: 6x5.
3507 "vmov.i8 d0, #0\n"
3508 "vmov.i8 d1, #0\n"
3509 "vmov.i8 d2, #0\n"
3510 "vmov.i8 d3, #0\n"
3511 "vmov.i8 d4, #0\n"
3512 "vmov.i8 d5, #0\n"
3513 "vld1.32 {d0[0]}, [%[in]]!\n"
3514 "vld1.8 {d0[4]}, [%[in]]!\n"
3515 "vld1.32 {d1[0]}, [r0]!\n"
3516 "vld1.8 {d1[4]}, [r0]!\n"
3517 "vld1.32 {d2[0]}, [r1]!\n"
3518 "vld1.8 {d2[4]}, [r1]!\n"
3519 "vld1.32 {d3[0]}, [r2]!\n"
3520 "vld1.8 {d3[4]}, [r2]!\n"
3521 "vld1.32 {d4[0]}, [r3]!\n"
3522 "vld1.8 {d4[4]}, [r3]!\n"
3523 "vld1.32 {d5[0]}, [r4]!\n"
3524 "vld1.8 {d5[4]}, [r4]!\n"
3525 "vaddw.u8 q8, q8, d0\n"
3526 "vaddw.u8 q9, q9, d1\n"
3527 "vaddw.u8 q10, q10, d2\n"
3528 "vaddw.u8 q11, q11, d3\n"
3529 "vaddw.u8 q12, q12, d4\n"
3530 "vaddw.u8 q13, q13, d5\n"
3531 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
3532 "vst1.32 {d4, d5}, [%[out]:128]!\n"
3533
3534 // Aggregator Reduction.
3535 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
3536 "vdup.32 q1, %[additive_sum_offset]\n"
3537 "vpaddl.u16 q8, q8\n"
3538 "vpaddl.u16 q9, q9\n"
3539 "vpaddl.u16 q10, q10\n"
3540 "vpaddl.u16 q11, q11\n"
3541 "vpaddl.u16 q12, q12\n"
3542 "vpaddl.u16 q13, q13\n"
3543 "vpadd.u32 d16, d16, d17\n"
3544 "vpadd.u32 d18, d18, d19\n"
3545 "vpadd.u32 d20, d20, d21\n"
3546 "vpadd.u32 d22, d22, d23\n"
3547 "vpadd.u32 d24, d24, d25\n"
3548 "vpadd.u32 d26, d26, d27\n"
3549 "vpadd.u32 d16, d16, d18\n"
3550 "vpadd.u32 d17, d20, d22\n"
3551 "vpadd.u32 d18, d24, d26\n"
3552 "vmul.i32 q8, q8, d0[0]\n"
3553 "vmul.i32 q9, q9, d0[0]\n"
3554 "vadd.i32 q8, q8, q1\n"
3555 "vadd.i32 q9, q9, q1\n"
3556 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
3557 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
3558 : [stride] "r"(params.stride),
3559 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
3560 [additive_sum_offset] "r"(params.additive_sum_offset)
3561 : "r0", "r1", "r2", "r3", "r4", "d0", "d1", "d2", "d3", "d4", "d5", "d16",
3562 "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26",
3563 "d27", "cc", "memory");
3564 }
3565
3566 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)3567 inline void Stream<uint8_t, 6, 8, 6, RowMajorWithSum>::Pack(
3568 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
3569 #ifdef DEBUG
3570 #ifdef DEBUG_METAGEMM_VERBOSE
3571 std::cout << __FILE__ << "(" << __LINE__
3572 << ") RowMajorWithSum<uint8_t, 6, 8, 6, RowMajorWithSum>::Pack()"
3573 << std::endl
3574 << std::flush;
3575 #endif
3576 #endif
3577 int params_count_copy = params.count;
3578 asm volatile(
3579 "add r0, %[in], %[stride]\n"
3580 "add r1, r0, %[stride]\n"
3581 "add r2, r1, %[stride]\n"
3582 "add r3, r2, %[stride]\n"
3583 "add r4, r3, %[stride]\n"
3584 "vmov.i16 q8, #0\n"
3585 "vmov.i16 q9, #0\n"
3586 "vmov.i16 q10, #0\n"
3587 "vmov.i16 q11, #0\n"
3588 "vmov.i16 q12, #0\n"
3589 "vmov.i16 q13, #0\n"
3590
3591 // Reduce count by leftovers.
3592 "subs %[count], %[count], #6\n"
3593 "beq 2f\n"
3594
3595 "1:"
3596 "subs %[count], %[count], #8\n"
3597
3598 // Load Aggregate Store: 6x8.
3599 "vld1.32 {d0}, [%[in]]!\n"
3600 "vld1.32 {d1}, [r0]!\n"
3601 "vld1.32 {d2}, [r1]!\n"
3602 "vld1.32 {d3}, [r2]!\n"
3603 "vld1.32 {d4}, [r3]!\n"
3604 "vld1.32 {d5}, [r4]!\n"
3605 "vaddw.u8 q8, q8, d0\n"
3606 "vaddw.u8 q9, q9, d1\n"
3607 "vaddw.u8 q10, q10, d2\n"
3608 "vaddw.u8 q11, q11, d3\n"
3609 "vaddw.u8 q12, q12, d4\n"
3610 "vaddw.u8 q13, q13, d5\n"
3611 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
3612 "vst1.32 {d4, d5}, [%[out]:128]!\n"
3613
3614 "bne 1b\n"
3615
3616 "2:"
3617
3618 // Load Aggregate Store: 6x6.
3619 "vmov.i8 d0, #0\n"
3620 "vmov.i8 d1, #0\n"
3621 "vmov.i8 d2, #0\n"
3622 "vmov.i8 d3, #0\n"
3623 "vmov.i8 d4, #0\n"
3624 "vmov.i8 d5, #0\n"
3625 "vld1.32 {d0[0]}, [%[in]]!\n"
3626 "vld1.16 {d0[2]}, [%[in]]!\n"
3627 "vld1.32 {d1[0]}, [r0]!\n"
3628 "vld1.16 {d1[2]}, [r0]!\n"
3629 "vld1.32 {d2[0]}, [r1]!\n"
3630 "vld1.16 {d2[2]}, [r1]!\n"
3631 "vld1.32 {d3[0]}, [r2]!\n"
3632 "vld1.16 {d3[2]}, [r2]!\n"
3633 "vld1.32 {d4[0]}, [r3]!\n"
3634 "vld1.16 {d4[2]}, [r3]!\n"
3635 "vld1.32 {d5[0]}, [r4]!\n"
3636 "vld1.16 {d5[2]}, [r4]!\n"
3637 "vaddw.u8 q8, q8, d0\n"
3638 "vaddw.u8 q9, q9, d1\n"
3639 "vaddw.u8 q10, q10, d2\n"
3640 "vaddw.u8 q11, q11, d3\n"
3641 "vaddw.u8 q12, q12, d4\n"
3642 "vaddw.u8 q13, q13, d5\n"
3643 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
3644 "vst1.32 {d4, d5}, [%[out]:128]!\n"
3645
3646 // Aggregator Reduction.
3647 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
3648 "vdup.32 q1, %[additive_sum_offset]\n"
3649 "vpaddl.u16 q8, q8\n"
3650 "vpaddl.u16 q9, q9\n"
3651 "vpaddl.u16 q10, q10\n"
3652 "vpaddl.u16 q11, q11\n"
3653 "vpaddl.u16 q12, q12\n"
3654 "vpaddl.u16 q13, q13\n"
3655 "vpadd.u32 d16, d16, d17\n"
3656 "vpadd.u32 d18, d18, d19\n"
3657 "vpadd.u32 d20, d20, d21\n"
3658 "vpadd.u32 d22, d22, d23\n"
3659 "vpadd.u32 d24, d24, d25\n"
3660 "vpadd.u32 d26, d26, d27\n"
3661 "vpadd.u32 d16, d16, d18\n"
3662 "vpadd.u32 d17, d20, d22\n"
3663 "vpadd.u32 d18, d24, d26\n"
3664 "vmul.i32 q8, q8, d0[0]\n"
3665 "vmul.i32 q9, q9, d0[0]\n"
3666 "vadd.i32 q8, q8, q1\n"
3667 "vadd.i32 q9, q9, q1\n"
3668 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
3669 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
3670 : [stride] "r"(params.stride),
3671 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
3672 [additive_sum_offset] "r"(params.additive_sum_offset)
3673 : "r0", "r1", "r2", "r3", "r4", "d0", "d1", "d2", "d3", "d4", "d5", "d16",
3674 "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26",
3675 "d27", "cc", "memory");
3676 }
3677
3678 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)3679 inline void Stream<uint8_t, 6, 8, 7, RowMajorWithSum>::Pack(
3680 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
3681 #ifdef DEBUG
3682 #ifdef DEBUG_METAGEMM_VERBOSE
3683 std::cout << __FILE__ << "(" << __LINE__
3684 << ") RowMajorWithSum<uint8_t, 6, 8, 7, RowMajorWithSum>::Pack()"
3685 << std::endl
3686 << std::flush;
3687 #endif
3688 #endif
3689 int params_count_copy = params.count;
3690 asm volatile(
3691 "add r0, %[in], %[stride]\n"
3692 "add r1, r0, %[stride]\n"
3693 "add r2, r1, %[stride]\n"
3694 "add r3, r2, %[stride]\n"
3695 "add r4, r3, %[stride]\n"
3696 "vmov.i16 q8, #0\n"
3697 "vmov.i16 q9, #0\n"
3698 "vmov.i16 q10, #0\n"
3699 "vmov.i16 q11, #0\n"
3700 "vmov.i16 q12, #0\n"
3701 "vmov.i16 q13, #0\n"
3702
3703 // Reduce count by leftovers.
3704 "subs %[count], %[count], #7\n"
3705 "beq 2f\n"
3706
3707 "1:"
3708 "subs %[count], %[count], #8\n"
3709
3710 // Load Aggregate Store: 6x8.
3711 "vld1.32 {d0}, [%[in]]!\n"
3712 "vld1.32 {d1}, [r0]!\n"
3713 "vld1.32 {d2}, [r1]!\n"
3714 "vld1.32 {d3}, [r2]!\n"
3715 "vld1.32 {d4}, [r3]!\n"
3716 "vld1.32 {d5}, [r4]!\n"
3717 "vaddw.u8 q8, q8, d0\n"
3718 "vaddw.u8 q9, q9, d1\n"
3719 "vaddw.u8 q10, q10, d2\n"
3720 "vaddw.u8 q11, q11, d3\n"
3721 "vaddw.u8 q12, q12, d4\n"
3722 "vaddw.u8 q13, q13, d5\n"
3723 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
3724 "vst1.32 {d4, d5}, [%[out]:128]!\n"
3725
3726 "bne 1b\n"
3727
3728 "2:"
3729
3730 // Load Aggregate Store: 6x7.
3731 "vmov.i8 d0, #0\n"
3732 "vmov.i8 d1, #0\n"
3733 "vmov.i8 d2, #0\n"
3734 "vmov.i8 d3, #0\n"
3735 "vmov.i8 d4, #0\n"
3736 "vmov.i8 d5, #0\n"
3737 "vld1.32 {d0[0]}, [%[in]]!\n"
3738 "vld1.16 {d0[2]}, [%[in]]!\n"
3739 "vld1.8 {d0[6]}, [%[in]]!\n"
3740 "vld1.32 {d1[0]}, [r0]!\n"
3741 "vld1.16 {d1[2]}, [r0]!\n"
3742 "vld1.8 {d1[6]}, [r0]!\n"
3743 "vld1.32 {d2[0]}, [r1]!\n"
3744 "vld1.16 {d2[2]}, [r1]!\n"
3745 "vld1.8 {d2[6]}, [r1]!\n"
3746 "vld1.32 {d3[0]}, [r2]!\n"
3747 "vld1.16 {d3[2]}, [r2]!\n"
3748 "vld1.8 {d3[6]}, [r2]!\n"
3749 "vld1.32 {d4[0]}, [r3]!\n"
3750 "vld1.16 {d4[2]}, [r3]!\n"
3751 "vld1.8 {d4[6]}, [r3]!\n"
3752 "vld1.32 {d5[0]}, [r4]!\n"
3753 "vld1.16 {d5[2]}, [r4]!\n"
3754 "vld1.8 {d5[6]}, [r4]!\n"
3755 "vaddw.u8 q8, q8, d0\n"
3756 "vaddw.u8 q9, q9, d1\n"
3757 "vaddw.u8 q10, q10, d2\n"
3758 "vaddw.u8 q11, q11, d3\n"
3759 "vaddw.u8 q12, q12, d4\n"
3760 "vaddw.u8 q13, q13, d5\n"
3761 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
3762 "vst1.32 {d4, d5}, [%[out]:128]!\n"
3763
3764 // Aggregator Reduction.
3765 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
3766 "vdup.32 q1, %[additive_sum_offset]\n"
3767 "vpaddl.u16 q8, q8\n"
3768 "vpaddl.u16 q9, q9\n"
3769 "vpaddl.u16 q10, q10\n"
3770 "vpaddl.u16 q11, q11\n"
3771 "vpaddl.u16 q12, q12\n"
3772 "vpaddl.u16 q13, q13\n"
3773 "vpadd.u32 d16, d16, d17\n"
3774 "vpadd.u32 d18, d18, d19\n"
3775 "vpadd.u32 d20, d20, d21\n"
3776 "vpadd.u32 d22, d22, d23\n"
3777 "vpadd.u32 d24, d24, d25\n"
3778 "vpadd.u32 d26, d26, d27\n"
3779 "vpadd.u32 d16, d16, d18\n"
3780 "vpadd.u32 d17, d20, d22\n"
3781 "vpadd.u32 d18, d24, d26\n"
3782 "vmul.i32 q8, q8, d0[0]\n"
3783 "vmul.i32 q9, q9, d0[0]\n"
3784 "vadd.i32 q8, q8, q1\n"
3785 "vadd.i32 q9, q9, q1\n"
3786 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
3787 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
3788 : [stride] "r"(params.stride),
3789 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset),
3790 [additive_sum_offset] "r"(params.additive_sum_offset)
3791 : "r0", "r1", "r2", "r3", "r4", "d0", "d1", "d2", "d3", "d4", "d5", "d16",
3792 "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26",
3793 "d27", "cc", "memory");
3794 }
3795
3796 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)3797 inline void Stream<uint8_t, 7, 8, 0, RowMajorWithSum>::Pack(
3798 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
3799 #ifdef DEBUG
3800 #ifdef DEBUG_METAGEMM_VERBOSE
3801 std::cout << __FILE__ << "(" << __LINE__
3802 << ") RowMajorWithSum<uint8_t, 7, 8, 0, RowMajorWithSum>::Pack()"
3803 << std::endl
3804 << std::flush;
3805 #endif
3806 #endif
3807 int params_count_copy = params.count;
3808 asm volatile(
3809 "add r0, %[in], %[stride]\n"
3810 "add r1, r0, %[stride]\n"
3811 "add r2, r1, %[stride]\n"
3812 "add r3, r2, %[stride]\n"
3813 "add r4, r3, %[stride]\n"
3814 "add r5, r4, %[stride]\n"
3815 "vmov.i16 q8, #0\n"
3816 "vmov.i16 q9, #0\n"
3817 "vmov.i16 q10, #0\n"
3818 "vmov.i16 q11, #0\n"
3819 "vmov.i16 q12, #0\n"
3820 "vmov.i16 q13, #0\n"
3821 "vmov.i16 q14, #0\n"
3822
3823 "1:"
3824 "subs %[count], %[count], #8\n"
3825
3826 // Load Aggregate Store: 7x8.
3827 "vld1.32 {d0}, [%[in]]!\n"
3828 "vld1.32 {d1}, [r0]!\n"
3829 "vld1.32 {d2}, [r1]!\n"
3830 "vld1.32 {d3}, [r2]!\n"
3831 "vld1.32 {d4}, [r3]!\n"
3832 "vld1.32 {d5}, [r4]!\n"
3833 "vld1.32 {d6}, [r5]!\n"
3834 "vaddw.u8 q8, q8, d0\n"
3835 "vaddw.u8 q9, q9, d1\n"
3836 "vaddw.u8 q10, q10, d2\n"
3837 "vaddw.u8 q11, q11, d3\n"
3838 "vaddw.u8 q12, q12, d4\n"
3839 "vaddw.u8 q13, q13, d5\n"
3840 "vaddw.u8 q14, q14, d6\n"
3841 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
3842 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
3843
3844 "bne 1b\n"
3845
3846 // Aggregator Reduction.
3847 "ldr r0, %[multiplicative_sum_offset]\n"
3848 "ldr r1, %[additive_sum_offset]\n"
3849 "vmov.32 d0[0], r0\n"
3850 "vdup.32 q1, r1\n"
3851 "vpaddl.u16 q8, q8\n"
3852 "vpaddl.u16 q9, q9\n"
3853 "vpaddl.u16 q10, q10\n"
3854 "vpaddl.u16 q11, q11\n"
3855 "vpaddl.u16 q12, q12\n"
3856 "vpaddl.u16 q13, q13\n"
3857 "vpaddl.u16 q14, q14\n"
3858 "vpadd.u32 d16, d16, d17\n"
3859 "vpadd.u32 d18, d18, d19\n"
3860 "vpadd.u32 d20, d20, d21\n"
3861 "vpadd.u32 d22, d22, d23\n"
3862 "vpadd.u32 d24, d24, d25\n"
3863 "vpadd.u32 d26, d26, d27\n"
3864 "vpadd.u32 d28, d28, d29\n"
3865 "vpadd.u32 d16, d16, d18\n"
3866 "vpadd.u32 d17, d20, d22\n"
3867 "vpadd.u32 d18, d24, d26\n"
3868 "vpadd.u32 d19, d28, d28\n"
3869 "vmul.i32 q8, q8, d0[0]\n"
3870 "vmul.i32 q9, q9, d0[0]\n"
3871 "vadd.i32 q8, q8, q1\n"
3872 "vadd.i32 q9, q9, q1\n"
3873 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
3874 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
3875 : [stride] "r"(params.stride),
3876 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
3877 [additive_sum_offset] "m"(params.additive_sum_offset)
3878 : "r0", "r1", "r2", "r3", "r4", "r5", "d0", "d1", "d2", "d3", "d4", "d5",
3879 "d6", "d16", "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24",
3880 "d25", "d26", "d27", "d28", "d29", "cc", "memory");
3881 }
3882
3883 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)3884 inline void Stream<uint8_t, 7, 8, 1, RowMajorWithSum>::Pack(
3885 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
3886 #ifdef DEBUG
3887 #ifdef DEBUG_METAGEMM_VERBOSE
3888 std::cout << __FILE__ << "(" << __LINE__
3889 << ") RowMajorWithSum<uint8_t, 7, 8, 1, RowMajorWithSum>::Pack()"
3890 << std::endl
3891 << std::flush;
3892 #endif
3893 #endif
3894 int params_count_copy = params.count;
3895 asm volatile(
3896 "add r0, %[in], %[stride]\n"
3897 "add r1, r0, %[stride]\n"
3898 "add r2, r1, %[stride]\n"
3899 "add r3, r2, %[stride]\n"
3900 "add r4, r3, %[stride]\n"
3901 "add r5, r4, %[stride]\n"
3902 "vmov.i16 q8, #0\n"
3903 "vmov.i16 q9, #0\n"
3904 "vmov.i16 q10, #0\n"
3905 "vmov.i16 q11, #0\n"
3906 "vmov.i16 q12, #0\n"
3907 "vmov.i16 q13, #0\n"
3908 "vmov.i16 q14, #0\n"
3909
3910 // Reduce count by leftovers.
3911 "subs %[count], %[count], #1\n"
3912 "beq 2f\n"
3913
3914 "1:"
3915 "subs %[count], %[count], #8\n"
3916
3917 // Load Aggregate Store: 7x8.
3918 "vld1.32 {d0}, [%[in]]!\n"
3919 "vld1.32 {d1}, [r0]!\n"
3920 "vld1.32 {d2}, [r1]!\n"
3921 "vld1.32 {d3}, [r2]!\n"
3922 "vld1.32 {d4}, [r3]!\n"
3923 "vld1.32 {d5}, [r4]!\n"
3924 "vld1.32 {d6}, [r5]!\n"
3925 "vaddw.u8 q8, q8, d0\n"
3926 "vaddw.u8 q9, q9, d1\n"
3927 "vaddw.u8 q10, q10, d2\n"
3928 "vaddw.u8 q11, q11, d3\n"
3929 "vaddw.u8 q12, q12, d4\n"
3930 "vaddw.u8 q13, q13, d5\n"
3931 "vaddw.u8 q14, q14, d6\n"
3932 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
3933 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
3934
3935 "bne 1b\n"
3936
3937 "2:"
3938
3939 // Load Aggregate Store: 7x1.
3940 "vmov.i8 d0, #0\n"
3941 "vmov.i8 d1, #0\n"
3942 "vmov.i8 d2, #0\n"
3943 "vmov.i8 d3, #0\n"
3944 "vmov.i8 d4, #0\n"
3945 "vmov.i8 d5, #0\n"
3946 "vmov.i8 d6, #0\n"
3947 "vld1.8 {d0[0]}, [%[in]]!\n"
3948 "vld1.8 {d1[0]}, [r0]!\n"
3949 "vld1.8 {d2[0]}, [r1]!\n"
3950 "vld1.8 {d3[0]}, [r2]!\n"
3951 "vld1.8 {d4[0]}, [r3]!\n"
3952 "vld1.8 {d5[0]}, [r4]!\n"
3953 "vld1.8 {d6[0]}, [r5]!\n"
3954 "vaddw.u8 q8, q8, d0\n"
3955 "vaddw.u8 q9, q9, d1\n"
3956 "vaddw.u8 q10, q10, d2\n"
3957 "vaddw.u8 q11, q11, d3\n"
3958 "vaddw.u8 q12, q12, d4\n"
3959 "vaddw.u8 q13, q13, d5\n"
3960 "vaddw.u8 q14, q14, d6\n"
3961 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
3962 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
3963
3964 // Aggregator Reduction.
3965 "ldr r0, %[multiplicative_sum_offset]\n"
3966 "ldr r1, %[additive_sum_offset]\n"
3967 "vmov.32 d0[0], r0\n"
3968 "vdup.32 q1, r1\n"
3969 "vpaddl.u16 q8, q8\n"
3970 "vpaddl.u16 q9, q9\n"
3971 "vpaddl.u16 q10, q10\n"
3972 "vpaddl.u16 q11, q11\n"
3973 "vpaddl.u16 q12, q12\n"
3974 "vpaddl.u16 q13, q13\n"
3975 "vpaddl.u16 q14, q14\n"
3976 "vpadd.u32 d16, d16, d17\n"
3977 "vpadd.u32 d18, d18, d19\n"
3978 "vpadd.u32 d20, d20, d21\n"
3979 "vpadd.u32 d22, d22, d23\n"
3980 "vpadd.u32 d24, d24, d25\n"
3981 "vpadd.u32 d26, d26, d27\n"
3982 "vpadd.u32 d28, d28, d29\n"
3983 "vpadd.u32 d16, d16, d18\n"
3984 "vpadd.u32 d17, d20, d22\n"
3985 "vpadd.u32 d18, d24, d26\n"
3986 "vpadd.u32 d19, d28, d28\n"
3987 "vmul.i32 q8, q8, d0[0]\n"
3988 "vmul.i32 q9, q9, d0[0]\n"
3989 "vadd.i32 q8, q8, q1\n"
3990 "vadd.i32 q9, q9, q1\n"
3991 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
3992 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
3993 : [stride] "r"(params.stride),
3994 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
3995 [additive_sum_offset] "m"(params.additive_sum_offset)
3996 : "r0", "r1", "r2", "r3", "r4", "r5", "d0", "d1", "d2", "d3", "d4", "d5",
3997 "d6", "d16", "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24",
3998 "d25", "d26", "d27", "d28", "d29", "cc", "memory");
3999 }
4000
4001 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)4002 inline void Stream<uint8_t, 7, 8, 2, RowMajorWithSum>::Pack(
4003 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
4004 #ifdef DEBUG
4005 #ifdef DEBUG_METAGEMM_VERBOSE
4006 std::cout << __FILE__ << "(" << __LINE__
4007 << ") RowMajorWithSum<uint8_t, 7, 8, 2, RowMajorWithSum>::Pack()"
4008 << std::endl
4009 << std::flush;
4010 #endif
4011 #endif
4012 int params_count_copy = params.count;
4013 asm volatile(
4014 "add r0, %[in], %[stride]\n"
4015 "add r1, r0, %[stride]\n"
4016 "add r2, r1, %[stride]\n"
4017 "add r3, r2, %[stride]\n"
4018 "add r4, r3, %[stride]\n"
4019 "add r5, r4, %[stride]\n"
4020 "vmov.i16 q8, #0\n"
4021 "vmov.i16 q9, #0\n"
4022 "vmov.i16 q10, #0\n"
4023 "vmov.i16 q11, #0\n"
4024 "vmov.i16 q12, #0\n"
4025 "vmov.i16 q13, #0\n"
4026 "vmov.i16 q14, #0\n"
4027
4028 // Reduce count by leftovers.
4029 "subs %[count], %[count], #2\n"
4030 "beq 2f\n"
4031
4032 "1:"
4033 "subs %[count], %[count], #8\n"
4034
4035 // Load Aggregate Store: 7x8.
4036 "vld1.32 {d0}, [%[in]]!\n"
4037 "vld1.32 {d1}, [r0]!\n"
4038 "vld1.32 {d2}, [r1]!\n"
4039 "vld1.32 {d3}, [r2]!\n"
4040 "vld1.32 {d4}, [r3]!\n"
4041 "vld1.32 {d5}, [r4]!\n"
4042 "vld1.32 {d6}, [r5]!\n"
4043 "vaddw.u8 q8, q8, d0\n"
4044 "vaddw.u8 q9, q9, d1\n"
4045 "vaddw.u8 q10, q10, d2\n"
4046 "vaddw.u8 q11, q11, d3\n"
4047 "vaddw.u8 q12, q12, d4\n"
4048 "vaddw.u8 q13, q13, d5\n"
4049 "vaddw.u8 q14, q14, d6\n"
4050 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
4051 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
4052
4053 "bne 1b\n"
4054
4055 "2:"
4056
4057 // Load Aggregate Store: 7x2.
4058 "vmov.i8 d0, #0\n"
4059 "vmov.i8 d1, #0\n"
4060 "vmov.i8 d2, #0\n"
4061 "vmov.i8 d3, #0\n"
4062 "vmov.i8 d4, #0\n"
4063 "vmov.i8 d5, #0\n"
4064 "vmov.i8 d6, #0\n"
4065 "vld1.16 {d0[0]}, [%[in]]!\n"
4066 "vld1.16 {d1[0]}, [r0]!\n"
4067 "vld1.16 {d2[0]}, [r1]!\n"
4068 "vld1.16 {d3[0]}, [r2]!\n"
4069 "vld1.16 {d4[0]}, [r3]!\n"
4070 "vld1.16 {d5[0]}, [r4]!\n"
4071 "vld1.16 {d6[0]}, [r5]!\n"
4072 "vaddw.u8 q8, q8, d0\n"
4073 "vaddw.u8 q9, q9, d1\n"
4074 "vaddw.u8 q10, q10, d2\n"
4075 "vaddw.u8 q11, q11, d3\n"
4076 "vaddw.u8 q12, q12, d4\n"
4077 "vaddw.u8 q13, q13, d5\n"
4078 "vaddw.u8 q14, q14, d6\n"
4079 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
4080 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
4081
4082 // Aggregator Reduction.
4083 "ldr r0, %[multiplicative_sum_offset]\n"
4084 "ldr r1, %[additive_sum_offset]\n"
4085 "vmov.32 d0[0], r0\n"
4086 "vdup.32 q1, r1\n"
4087 "vpaddl.u16 q8, q8\n"
4088 "vpaddl.u16 q9, q9\n"
4089 "vpaddl.u16 q10, q10\n"
4090 "vpaddl.u16 q11, q11\n"
4091 "vpaddl.u16 q12, q12\n"
4092 "vpaddl.u16 q13, q13\n"
4093 "vpaddl.u16 q14, q14\n"
4094 "vpadd.u32 d16, d16, d17\n"
4095 "vpadd.u32 d18, d18, d19\n"
4096 "vpadd.u32 d20, d20, d21\n"
4097 "vpadd.u32 d22, d22, d23\n"
4098 "vpadd.u32 d24, d24, d25\n"
4099 "vpadd.u32 d26, d26, d27\n"
4100 "vpadd.u32 d28, d28, d29\n"
4101 "vpadd.u32 d16, d16, d18\n"
4102 "vpadd.u32 d17, d20, d22\n"
4103 "vpadd.u32 d18, d24, d26\n"
4104 "vpadd.u32 d19, d28, d28\n"
4105 "vmul.i32 q8, q8, d0[0]\n"
4106 "vmul.i32 q9, q9, d0[0]\n"
4107 "vadd.i32 q8, q8, q1\n"
4108 "vadd.i32 q9, q9, q1\n"
4109 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
4110 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
4111 : [stride] "r"(params.stride),
4112 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
4113 [additive_sum_offset] "m"(params.additive_sum_offset)
4114 : "r0", "r1", "r2", "r3", "r4", "r5", "d0", "d1", "d2", "d3", "d4", "d5",
4115 "d6", "d16", "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24",
4116 "d25", "d26", "d27", "d28", "d29", "cc", "memory");
4117 }
4118
4119 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)4120 inline void Stream<uint8_t, 7, 8, 3, RowMajorWithSum>::Pack(
4121 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
4122 #ifdef DEBUG
4123 #ifdef DEBUG_METAGEMM_VERBOSE
4124 std::cout << __FILE__ << "(" << __LINE__
4125 << ") RowMajorWithSum<uint8_t, 7, 8, 3, RowMajorWithSum>::Pack()"
4126 << std::endl
4127 << std::flush;
4128 #endif
4129 #endif
4130 int params_count_copy = params.count;
4131 asm volatile(
4132 "add r0, %[in], %[stride]\n"
4133 "add r1, r0, %[stride]\n"
4134 "add r2, r1, %[stride]\n"
4135 "add r3, r2, %[stride]\n"
4136 "add r4, r3, %[stride]\n"
4137 "add r5, r4, %[stride]\n"
4138 "vmov.i16 q8, #0\n"
4139 "vmov.i16 q9, #0\n"
4140 "vmov.i16 q10, #0\n"
4141 "vmov.i16 q11, #0\n"
4142 "vmov.i16 q12, #0\n"
4143 "vmov.i16 q13, #0\n"
4144 "vmov.i16 q14, #0\n"
4145
4146 // Reduce count by leftovers.
4147 "subs %[count], %[count], #3\n"
4148 "beq 2f\n"
4149
4150 "1:"
4151 "subs %[count], %[count], #8\n"
4152
4153 // Load Aggregate Store: 7x8.
4154 "vld1.32 {d0}, [%[in]]!\n"
4155 "vld1.32 {d1}, [r0]!\n"
4156 "vld1.32 {d2}, [r1]!\n"
4157 "vld1.32 {d3}, [r2]!\n"
4158 "vld1.32 {d4}, [r3]!\n"
4159 "vld1.32 {d5}, [r4]!\n"
4160 "vld1.32 {d6}, [r5]!\n"
4161 "vaddw.u8 q8, q8, d0\n"
4162 "vaddw.u8 q9, q9, d1\n"
4163 "vaddw.u8 q10, q10, d2\n"
4164 "vaddw.u8 q11, q11, d3\n"
4165 "vaddw.u8 q12, q12, d4\n"
4166 "vaddw.u8 q13, q13, d5\n"
4167 "vaddw.u8 q14, q14, d6\n"
4168 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
4169 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
4170
4171 "bne 1b\n"
4172
4173 "2:"
4174
4175 // Load Aggregate Store: 7x3.
4176 "vmov.i8 d0, #0\n"
4177 "vmov.i8 d1, #0\n"
4178 "vmov.i8 d2, #0\n"
4179 "vmov.i8 d3, #0\n"
4180 "vmov.i8 d4, #0\n"
4181 "vmov.i8 d5, #0\n"
4182 "vmov.i8 d6, #0\n"
4183 "vld1.16 {d0[0]}, [%[in]]!\n"
4184 "vld1.8 {d0[2]}, [%[in]]!\n"
4185 "vld1.16 {d1[0]}, [r0]!\n"
4186 "vld1.8 {d1[2]}, [r0]!\n"
4187 "vld1.16 {d2[0]}, [r1]!\n"
4188 "vld1.8 {d2[2]}, [r1]!\n"
4189 "vld1.16 {d3[0]}, [r2]!\n"
4190 "vld1.8 {d3[2]}, [r2]!\n"
4191 "vld1.16 {d4[0]}, [r3]!\n"
4192 "vld1.8 {d4[2]}, [r3]!\n"
4193 "vld1.16 {d5[0]}, [r4]!\n"
4194 "vld1.8 {d5[2]}, [r4]!\n"
4195 "vld1.16 {d6[0]}, [r5]!\n"
4196 "vld1.8 {d6[2]}, [r5]!\n"
4197 "vaddw.u8 q8, q8, d0\n"
4198 "vaddw.u8 q9, q9, d1\n"
4199 "vaddw.u8 q10, q10, d2\n"
4200 "vaddw.u8 q11, q11, d3\n"
4201 "vaddw.u8 q12, q12, d4\n"
4202 "vaddw.u8 q13, q13, d5\n"
4203 "vaddw.u8 q14, q14, d6\n"
4204 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
4205 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
4206
4207 // Aggregator Reduction.
4208 "ldr r0, %[multiplicative_sum_offset]\n"
4209 "ldr r1, %[additive_sum_offset]\n"
4210 "vmov.32 d0[0], r0\n"
4211 "vdup.32 q1, r1\n"
4212 "vpaddl.u16 q8, q8\n"
4213 "vpaddl.u16 q9, q9\n"
4214 "vpaddl.u16 q10, q10\n"
4215 "vpaddl.u16 q11, q11\n"
4216 "vpaddl.u16 q12, q12\n"
4217 "vpaddl.u16 q13, q13\n"
4218 "vpaddl.u16 q14, q14\n"
4219 "vpadd.u32 d16, d16, d17\n"
4220 "vpadd.u32 d18, d18, d19\n"
4221 "vpadd.u32 d20, d20, d21\n"
4222 "vpadd.u32 d22, d22, d23\n"
4223 "vpadd.u32 d24, d24, d25\n"
4224 "vpadd.u32 d26, d26, d27\n"
4225 "vpadd.u32 d28, d28, d29\n"
4226 "vpadd.u32 d16, d16, d18\n"
4227 "vpadd.u32 d17, d20, d22\n"
4228 "vpadd.u32 d18, d24, d26\n"
4229 "vpadd.u32 d19, d28, d28\n"
4230 "vmul.i32 q8, q8, d0[0]\n"
4231 "vmul.i32 q9, q9, d0[0]\n"
4232 "vadd.i32 q8, q8, q1\n"
4233 "vadd.i32 q9, q9, q1\n"
4234 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
4235 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
4236 : [stride] "r"(params.stride),
4237 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
4238 [additive_sum_offset] "m"(params.additive_sum_offset)
4239 : "r0", "r1", "r2", "r3", "r4", "r5", "d0", "d1", "d2", "d3", "d4", "d5",
4240 "d6", "d16", "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24",
4241 "d25", "d26", "d27", "d28", "d29", "cc", "memory");
4242 }
4243
4244 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)4245 inline void Stream<uint8_t, 7, 8, 4, RowMajorWithSum>::Pack(
4246 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
4247 #ifdef DEBUG
4248 #ifdef DEBUG_METAGEMM_VERBOSE
4249 std::cout << __FILE__ << "(" << __LINE__
4250 << ") RowMajorWithSum<uint8_t, 7, 8, 4, RowMajorWithSum>::Pack()"
4251 << std::endl
4252 << std::flush;
4253 #endif
4254 #endif
4255 int params_count_copy = params.count;
4256 asm volatile(
4257 "add r0, %[in], %[stride]\n"
4258 "add r1, r0, %[stride]\n"
4259 "add r2, r1, %[stride]\n"
4260 "add r3, r2, %[stride]\n"
4261 "add r4, r3, %[stride]\n"
4262 "add r5, r4, %[stride]\n"
4263 "vmov.i16 q8, #0\n"
4264 "vmov.i16 q9, #0\n"
4265 "vmov.i16 q10, #0\n"
4266 "vmov.i16 q11, #0\n"
4267 "vmov.i16 q12, #0\n"
4268 "vmov.i16 q13, #0\n"
4269 "vmov.i16 q14, #0\n"
4270
4271 // Reduce count by leftovers.
4272 "subs %[count], %[count], #4\n"
4273 "beq 2f\n"
4274
4275 "1:"
4276 "subs %[count], %[count], #8\n"
4277
4278 // Load Aggregate Store: 7x8.
4279 "vld1.32 {d0}, [%[in]]!\n"
4280 "vld1.32 {d1}, [r0]!\n"
4281 "vld1.32 {d2}, [r1]!\n"
4282 "vld1.32 {d3}, [r2]!\n"
4283 "vld1.32 {d4}, [r3]!\n"
4284 "vld1.32 {d5}, [r4]!\n"
4285 "vld1.32 {d6}, [r5]!\n"
4286 "vaddw.u8 q8, q8, d0\n"
4287 "vaddw.u8 q9, q9, d1\n"
4288 "vaddw.u8 q10, q10, d2\n"
4289 "vaddw.u8 q11, q11, d3\n"
4290 "vaddw.u8 q12, q12, d4\n"
4291 "vaddw.u8 q13, q13, d5\n"
4292 "vaddw.u8 q14, q14, d6\n"
4293 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
4294 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
4295
4296 "bne 1b\n"
4297
4298 "2:"
4299
4300 // Load Aggregate Store: 7x4.
4301 "vmov.i8 d0, #0\n"
4302 "vmov.i8 d1, #0\n"
4303 "vmov.i8 d2, #0\n"
4304 "vmov.i8 d3, #0\n"
4305 "vmov.i8 d4, #0\n"
4306 "vmov.i8 d5, #0\n"
4307 "vmov.i8 d6, #0\n"
4308 "vld1.32 {d0[0]}, [%[in]]!\n"
4309 "vld1.32 {d1[0]}, [r0]!\n"
4310 "vld1.32 {d2[0]}, [r1]!\n"
4311 "vld1.32 {d3[0]}, [r2]!\n"
4312 "vld1.32 {d4[0]}, [r3]!\n"
4313 "vld1.32 {d5[0]}, [r4]!\n"
4314 "vld1.32 {d6[0]}, [r5]!\n"
4315 "vaddw.u8 q8, q8, d0\n"
4316 "vaddw.u8 q9, q9, d1\n"
4317 "vaddw.u8 q10, q10, d2\n"
4318 "vaddw.u8 q11, q11, d3\n"
4319 "vaddw.u8 q12, q12, d4\n"
4320 "vaddw.u8 q13, q13, d5\n"
4321 "vaddw.u8 q14, q14, d6\n"
4322 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
4323 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
4324
4325 // Aggregator Reduction.
4326 "ldr r0, %[multiplicative_sum_offset]\n"
4327 "ldr r1, %[additive_sum_offset]\n"
4328 "vmov.32 d0[0], r0\n"
4329 "vdup.32 q1, r1\n"
4330 "vpaddl.u16 q8, q8\n"
4331 "vpaddl.u16 q9, q9\n"
4332 "vpaddl.u16 q10, q10\n"
4333 "vpaddl.u16 q11, q11\n"
4334 "vpaddl.u16 q12, q12\n"
4335 "vpaddl.u16 q13, q13\n"
4336 "vpaddl.u16 q14, q14\n"
4337 "vpadd.u32 d16, d16, d17\n"
4338 "vpadd.u32 d18, d18, d19\n"
4339 "vpadd.u32 d20, d20, d21\n"
4340 "vpadd.u32 d22, d22, d23\n"
4341 "vpadd.u32 d24, d24, d25\n"
4342 "vpadd.u32 d26, d26, d27\n"
4343 "vpadd.u32 d28, d28, d29\n"
4344 "vpadd.u32 d16, d16, d18\n"
4345 "vpadd.u32 d17, d20, d22\n"
4346 "vpadd.u32 d18, d24, d26\n"
4347 "vpadd.u32 d19, d28, d28\n"
4348 "vmul.i32 q8, q8, d0[0]\n"
4349 "vmul.i32 q9, q9, d0[0]\n"
4350 "vadd.i32 q8, q8, q1\n"
4351 "vadd.i32 q9, q9, q1\n"
4352 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
4353 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
4354 : [stride] "r"(params.stride),
4355 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
4356 [additive_sum_offset] "m"(params.additive_sum_offset)
4357 : "r0", "r1", "r2", "r3", "r4", "r5", "d0", "d1", "d2", "d3", "d4", "d5",
4358 "d6", "d16", "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24",
4359 "d25", "d26", "d27", "d28", "d29", "cc", "memory");
4360 }
4361
4362 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)4363 inline void Stream<uint8_t, 7, 8, 5, RowMajorWithSum>::Pack(
4364 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
4365 #ifdef DEBUG
4366 #ifdef DEBUG_METAGEMM_VERBOSE
4367 std::cout << __FILE__ << "(" << __LINE__
4368 << ") RowMajorWithSum<uint8_t, 7, 8, 5, RowMajorWithSum>::Pack()"
4369 << std::endl
4370 << std::flush;
4371 #endif
4372 #endif
4373 int params_count_copy = params.count;
4374 asm volatile(
4375 "add r0, %[in], %[stride]\n"
4376 "add r1, r0, %[stride]\n"
4377 "add r2, r1, %[stride]\n"
4378 "add r3, r2, %[stride]\n"
4379 "add r4, r3, %[stride]\n"
4380 "add r5, r4, %[stride]\n"
4381 "vmov.i16 q8, #0\n"
4382 "vmov.i16 q9, #0\n"
4383 "vmov.i16 q10, #0\n"
4384 "vmov.i16 q11, #0\n"
4385 "vmov.i16 q12, #0\n"
4386 "vmov.i16 q13, #0\n"
4387 "vmov.i16 q14, #0\n"
4388
4389 // Reduce count by leftovers.
4390 "subs %[count], %[count], #5\n"
4391 "beq 2f\n"
4392
4393 "1:"
4394 "subs %[count], %[count], #8\n"
4395
4396 // Load Aggregate Store: 7x8.
4397 "vld1.32 {d0}, [%[in]]!\n"
4398 "vld1.32 {d1}, [r0]!\n"
4399 "vld1.32 {d2}, [r1]!\n"
4400 "vld1.32 {d3}, [r2]!\n"
4401 "vld1.32 {d4}, [r3]!\n"
4402 "vld1.32 {d5}, [r4]!\n"
4403 "vld1.32 {d6}, [r5]!\n"
4404 "vaddw.u8 q8, q8, d0\n"
4405 "vaddw.u8 q9, q9, d1\n"
4406 "vaddw.u8 q10, q10, d2\n"
4407 "vaddw.u8 q11, q11, d3\n"
4408 "vaddw.u8 q12, q12, d4\n"
4409 "vaddw.u8 q13, q13, d5\n"
4410 "vaddw.u8 q14, q14, d6\n"
4411 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
4412 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
4413
4414 "bne 1b\n"
4415
4416 "2:"
4417
4418 // Load Aggregate Store: 7x5.
4419 "vmov.i8 d0, #0\n"
4420 "vmov.i8 d1, #0\n"
4421 "vmov.i8 d2, #0\n"
4422 "vmov.i8 d3, #0\n"
4423 "vmov.i8 d4, #0\n"
4424 "vmov.i8 d5, #0\n"
4425 "vmov.i8 d6, #0\n"
4426 "vld1.32 {d0[0]}, [%[in]]!\n"
4427 "vld1.8 {d0[4]}, [%[in]]!\n"
4428 "vld1.32 {d1[0]}, [r0]!\n"
4429 "vld1.8 {d1[4]}, [r0]!\n"
4430 "vld1.32 {d2[0]}, [r1]!\n"
4431 "vld1.8 {d2[4]}, [r1]!\n"
4432 "vld1.32 {d3[0]}, [r2]!\n"
4433 "vld1.8 {d3[4]}, [r2]!\n"
4434 "vld1.32 {d4[0]}, [r3]!\n"
4435 "vld1.8 {d4[4]}, [r3]!\n"
4436 "vld1.32 {d5[0]}, [r4]!\n"
4437 "vld1.8 {d5[4]}, [r4]!\n"
4438 "vld1.32 {d6[0]}, [r5]!\n"
4439 "vld1.8 {d6[4]}, [r5]!\n"
4440 "vaddw.u8 q8, q8, d0\n"
4441 "vaddw.u8 q9, q9, d1\n"
4442 "vaddw.u8 q10, q10, d2\n"
4443 "vaddw.u8 q11, q11, d3\n"
4444 "vaddw.u8 q12, q12, d4\n"
4445 "vaddw.u8 q13, q13, d5\n"
4446 "vaddw.u8 q14, q14, d6\n"
4447 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
4448 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
4449
4450 // Aggregator Reduction.
4451 "ldr r0, %[multiplicative_sum_offset]\n"
4452 "ldr r1, %[additive_sum_offset]\n"
4453 "vmov.32 d0[0], r0\n"
4454 "vdup.32 q1, r1\n"
4455 "vpaddl.u16 q8, q8\n"
4456 "vpaddl.u16 q9, q9\n"
4457 "vpaddl.u16 q10, q10\n"
4458 "vpaddl.u16 q11, q11\n"
4459 "vpaddl.u16 q12, q12\n"
4460 "vpaddl.u16 q13, q13\n"
4461 "vpaddl.u16 q14, q14\n"
4462 "vpadd.u32 d16, d16, d17\n"
4463 "vpadd.u32 d18, d18, d19\n"
4464 "vpadd.u32 d20, d20, d21\n"
4465 "vpadd.u32 d22, d22, d23\n"
4466 "vpadd.u32 d24, d24, d25\n"
4467 "vpadd.u32 d26, d26, d27\n"
4468 "vpadd.u32 d28, d28, d29\n"
4469 "vpadd.u32 d16, d16, d18\n"
4470 "vpadd.u32 d17, d20, d22\n"
4471 "vpadd.u32 d18, d24, d26\n"
4472 "vpadd.u32 d19, d28, d28\n"
4473 "vmul.i32 q8, q8, d0[0]\n"
4474 "vmul.i32 q9, q9, d0[0]\n"
4475 "vadd.i32 q8, q8, q1\n"
4476 "vadd.i32 q9, q9, q1\n"
4477 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
4478 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
4479 : [stride] "r"(params.stride),
4480 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
4481 [additive_sum_offset] "m"(params.additive_sum_offset)
4482 : "r0", "r1", "r2", "r3", "r4", "r5", "d0", "d1", "d2", "d3", "d4", "d5",
4483 "d6", "d16", "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24",
4484 "d25", "d26", "d27", "d28", "d29", "cc", "memory");
4485 }
4486
4487 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)4488 inline void Stream<uint8_t, 7, 8, 6, RowMajorWithSum>::Pack(
4489 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
4490 #ifdef DEBUG
4491 #ifdef DEBUG_METAGEMM_VERBOSE
4492 std::cout << __FILE__ << "(" << __LINE__
4493 << ") RowMajorWithSum<uint8_t, 7, 8, 6, RowMajorWithSum>::Pack()"
4494 << std::endl
4495 << std::flush;
4496 #endif
4497 #endif
4498 int params_count_copy = params.count;
4499 asm volatile(
4500 "add r0, %[in], %[stride]\n"
4501 "add r1, r0, %[stride]\n"
4502 "add r2, r1, %[stride]\n"
4503 "add r3, r2, %[stride]\n"
4504 "add r4, r3, %[stride]\n"
4505 "add r5, r4, %[stride]\n"
4506 "vmov.i16 q8, #0\n"
4507 "vmov.i16 q9, #0\n"
4508 "vmov.i16 q10, #0\n"
4509 "vmov.i16 q11, #0\n"
4510 "vmov.i16 q12, #0\n"
4511 "vmov.i16 q13, #0\n"
4512 "vmov.i16 q14, #0\n"
4513
4514 // Reduce count by leftovers.
4515 "subs %[count], %[count], #6\n"
4516 "beq 2f\n"
4517
4518 "1:"
4519 "subs %[count], %[count], #8\n"
4520
4521 // Load Aggregate Store: 7x8.
4522 "vld1.32 {d0}, [%[in]]!\n"
4523 "vld1.32 {d1}, [r0]!\n"
4524 "vld1.32 {d2}, [r1]!\n"
4525 "vld1.32 {d3}, [r2]!\n"
4526 "vld1.32 {d4}, [r3]!\n"
4527 "vld1.32 {d5}, [r4]!\n"
4528 "vld1.32 {d6}, [r5]!\n"
4529 "vaddw.u8 q8, q8, d0\n"
4530 "vaddw.u8 q9, q9, d1\n"
4531 "vaddw.u8 q10, q10, d2\n"
4532 "vaddw.u8 q11, q11, d3\n"
4533 "vaddw.u8 q12, q12, d4\n"
4534 "vaddw.u8 q13, q13, d5\n"
4535 "vaddw.u8 q14, q14, d6\n"
4536 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
4537 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
4538
4539 "bne 1b\n"
4540
4541 "2:"
4542
4543 // Load Aggregate Store: 7x6.
4544 "vmov.i8 d0, #0\n"
4545 "vmov.i8 d1, #0\n"
4546 "vmov.i8 d2, #0\n"
4547 "vmov.i8 d3, #0\n"
4548 "vmov.i8 d4, #0\n"
4549 "vmov.i8 d5, #0\n"
4550 "vmov.i8 d6, #0\n"
4551 "vld1.32 {d0[0]}, [%[in]]!\n"
4552 "vld1.16 {d0[2]}, [%[in]]!\n"
4553 "vld1.32 {d1[0]}, [r0]!\n"
4554 "vld1.16 {d1[2]}, [r0]!\n"
4555 "vld1.32 {d2[0]}, [r1]!\n"
4556 "vld1.16 {d2[2]}, [r1]!\n"
4557 "vld1.32 {d3[0]}, [r2]!\n"
4558 "vld1.16 {d3[2]}, [r2]!\n"
4559 "vld1.32 {d4[0]}, [r3]!\n"
4560 "vld1.16 {d4[2]}, [r3]!\n"
4561 "vld1.32 {d5[0]}, [r4]!\n"
4562 "vld1.16 {d5[2]}, [r4]!\n"
4563 "vld1.32 {d6[0]}, [r5]!\n"
4564 "vld1.16 {d6[2]}, [r5]!\n"
4565 "vaddw.u8 q8, q8, d0\n"
4566 "vaddw.u8 q9, q9, d1\n"
4567 "vaddw.u8 q10, q10, d2\n"
4568 "vaddw.u8 q11, q11, d3\n"
4569 "vaddw.u8 q12, q12, d4\n"
4570 "vaddw.u8 q13, q13, d5\n"
4571 "vaddw.u8 q14, q14, d6\n"
4572 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
4573 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
4574
4575 // Aggregator Reduction.
4576 "ldr r0, %[multiplicative_sum_offset]\n"
4577 "ldr r1, %[additive_sum_offset]\n"
4578 "vmov.32 d0[0], r0\n"
4579 "vdup.32 q1, r1\n"
4580 "vpaddl.u16 q8, q8\n"
4581 "vpaddl.u16 q9, q9\n"
4582 "vpaddl.u16 q10, q10\n"
4583 "vpaddl.u16 q11, q11\n"
4584 "vpaddl.u16 q12, q12\n"
4585 "vpaddl.u16 q13, q13\n"
4586 "vpaddl.u16 q14, q14\n"
4587 "vpadd.u32 d16, d16, d17\n"
4588 "vpadd.u32 d18, d18, d19\n"
4589 "vpadd.u32 d20, d20, d21\n"
4590 "vpadd.u32 d22, d22, d23\n"
4591 "vpadd.u32 d24, d24, d25\n"
4592 "vpadd.u32 d26, d26, d27\n"
4593 "vpadd.u32 d28, d28, d29\n"
4594 "vpadd.u32 d16, d16, d18\n"
4595 "vpadd.u32 d17, d20, d22\n"
4596 "vpadd.u32 d18, d24, d26\n"
4597 "vpadd.u32 d19, d28, d28\n"
4598 "vmul.i32 q8, q8, d0[0]\n"
4599 "vmul.i32 q9, q9, d0[0]\n"
4600 "vadd.i32 q8, q8, q1\n"
4601 "vadd.i32 q9, q9, q1\n"
4602 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
4603 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
4604 : [stride] "r"(params.stride),
4605 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
4606 [additive_sum_offset] "m"(params.additive_sum_offset)
4607 : "r0", "r1", "r2", "r3", "r4", "r5", "d0", "d1", "d2", "d3", "d4", "d5",
4608 "d6", "d16", "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24",
4609 "d25", "d26", "d27", "d28", "d29", "cc", "memory");
4610 }
4611
4612 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)4613 inline void Stream<uint8_t, 7, 8, 7, RowMajorWithSum>::Pack(
4614 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
4615 #ifdef DEBUG
4616 #ifdef DEBUG_METAGEMM_VERBOSE
4617 std::cout << __FILE__ << "(" << __LINE__
4618 << ") RowMajorWithSum<uint8_t, 7, 8, 7, RowMajorWithSum>::Pack()"
4619 << std::endl
4620 << std::flush;
4621 #endif
4622 #endif
4623 int params_count_copy = params.count;
4624 asm volatile(
4625 "add r0, %[in], %[stride]\n"
4626 "add r1, r0, %[stride]\n"
4627 "add r2, r1, %[stride]\n"
4628 "add r3, r2, %[stride]\n"
4629 "add r4, r3, %[stride]\n"
4630 "add r5, r4, %[stride]\n"
4631 "vmov.i16 q8, #0\n"
4632 "vmov.i16 q9, #0\n"
4633 "vmov.i16 q10, #0\n"
4634 "vmov.i16 q11, #0\n"
4635 "vmov.i16 q12, #0\n"
4636 "vmov.i16 q13, #0\n"
4637 "vmov.i16 q14, #0\n"
4638
4639 // Reduce count by leftovers.
4640 "subs %[count], %[count], #7\n"
4641 "beq 2f\n"
4642
4643 "1:"
4644 "subs %[count], %[count], #8\n"
4645
4646 // Load Aggregate Store: 7x8.
4647 "vld1.32 {d0}, [%[in]]!\n"
4648 "vld1.32 {d1}, [r0]!\n"
4649 "vld1.32 {d2}, [r1]!\n"
4650 "vld1.32 {d3}, [r2]!\n"
4651 "vld1.32 {d4}, [r3]!\n"
4652 "vld1.32 {d5}, [r4]!\n"
4653 "vld1.32 {d6}, [r5]!\n"
4654 "vaddw.u8 q8, q8, d0\n"
4655 "vaddw.u8 q9, q9, d1\n"
4656 "vaddw.u8 q10, q10, d2\n"
4657 "vaddw.u8 q11, q11, d3\n"
4658 "vaddw.u8 q12, q12, d4\n"
4659 "vaddw.u8 q13, q13, d5\n"
4660 "vaddw.u8 q14, q14, d6\n"
4661 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
4662 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
4663
4664 "bne 1b\n"
4665
4666 "2:"
4667
4668 // Load Aggregate Store: 7x7.
4669 "vmov.i8 d0, #0\n"
4670 "vmov.i8 d1, #0\n"
4671 "vmov.i8 d2, #0\n"
4672 "vmov.i8 d3, #0\n"
4673 "vmov.i8 d4, #0\n"
4674 "vmov.i8 d5, #0\n"
4675 "vmov.i8 d6, #0\n"
4676 "vld1.32 {d0[0]}, [%[in]]!\n"
4677 "vld1.16 {d0[2]}, [%[in]]!\n"
4678 "vld1.8 {d0[6]}, [%[in]]!\n"
4679 "vld1.32 {d1[0]}, [r0]!\n"
4680 "vld1.16 {d1[2]}, [r0]!\n"
4681 "vld1.8 {d1[6]}, [r0]!\n"
4682 "vld1.32 {d2[0]}, [r1]!\n"
4683 "vld1.16 {d2[2]}, [r1]!\n"
4684 "vld1.8 {d2[6]}, [r1]!\n"
4685 "vld1.32 {d3[0]}, [r2]!\n"
4686 "vld1.16 {d3[2]}, [r2]!\n"
4687 "vld1.8 {d3[6]}, [r2]!\n"
4688 "vld1.32 {d4[0]}, [r3]!\n"
4689 "vld1.16 {d4[2]}, [r3]!\n"
4690 "vld1.8 {d4[6]}, [r3]!\n"
4691 "vld1.32 {d5[0]}, [r4]!\n"
4692 "vld1.16 {d5[2]}, [r4]!\n"
4693 "vld1.8 {d5[6]}, [r4]!\n"
4694 "vld1.32 {d6[0]}, [r5]!\n"
4695 "vld1.16 {d6[2]}, [r5]!\n"
4696 "vld1.8 {d6[6]}, [r5]!\n"
4697 "vaddw.u8 q8, q8, d0\n"
4698 "vaddw.u8 q9, q9, d1\n"
4699 "vaddw.u8 q10, q10, d2\n"
4700 "vaddw.u8 q11, q11, d3\n"
4701 "vaddw.u8 q12, q12, d4\n"
4702 "vaddw.u8 q13, q13, d5\n"
4703 "vaddw.u8 q14, q14, d6\n"
4704 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
4705 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
4706
4707 // Aggregator Reduction.
4708 "ldr r0, %[multiplicative_sum_offset]\n"
4709 "ldr r1, %[additive_sum_offset]\n"
4710 "vmov.32 d0[0], r0\n"
4711 "vdup.32 q1, r1\n"
4712 "vpaddl.u16 q8, q8\n"
4713 "vpaddl.u16 q9, q9\n"
4714 "vpaddl.u16 q10, q10\n"
4715 "vpaddl.u16 q11, q11\n"
4716 "vpaddl.u16 q12, q12\n"
4717 "vpaddl.u16 q13, q13\n"
4718 "vpaddl.u16 q14, q14\n"
4719 "vpadd.u32 d16, d16, d17\n"
4720 "vpadd.u32 d18, d18, d19\n"
4721 "vpadd.u32 d20, d20, d21\n"
4722 "vpadd.u32 d22, d22, d23\n"
4723 "vpadd.u32 d24, d24, d25\n"
4724 "vpadd.u32 d26, d26, d27\n"
4725 "vpadd.u32 d28, d28, d29\n"
4726 "vpadd.u32 d16, d16, d18\n"
4727 "vpadd.u32 d17, d20, d22\n"
4728 "vpadd.u32 d18, d24, d26\n"
4729 "vpadd.u32 d19, d28, d28\n"
4730 "vmul.i32 q8, q8, d0[0]\n"
4731 "vmul.i32 q9, q9, d0[0]\n"
4732 "vadd.i32 q8, q8, q1\n"
4733 "vadd.i32 q9, q9, q1\n"
4734 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
4735 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
4736 : [stride] "r"(params.stride),
4737 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
4738 [additive_sum_offset] "m"(params.additive_sum_offset)
4739 : "r0", "r1", "r2", "r3", "r4", "r5", "d0", "d1", "d2", "d3", "d4", "d5",
4740 "d6", "d16", "d17", "d18", "d19", "d20", "d21", "d22", "d23", "d24",
4741 "d25", "d26", "d27", "d28", "d29", "cc", "memory");
4742 }
4743
4744 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)4745 inline void Stream<uint8_t, 8, 8, 0, RowMajorWithSum>::Pack(
4746 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
4747 #ifdef DEBUG
4748 #ifdef DEBUG_METAGEMM_VERBOSE
4749 std::cout << __FILE__ << "(" << __LINE__
4750 << ") RowMajorWithSum<uint8_t, 8, 8, 0, RowMajorWithSum>::Pack()"
4751 << std::endl
4752 << std::flush;
4753 #endif
4754 #endif
4755 int params_count_copy = params.count;
4756 asm volatile(
4757 "add r0, %[in], %[stride]\n"
4758 "add r1, r0, %[stride]\n"
4759 "add r2, r1, %[stride]\n"
4760 "add r3, r2, %[stride]\n"
4761 "add r4, r3, %[stride]\n"
4762 "add r5, r4, %[stride]\n"
4763 "add r6, r5, %[stride]\n"
4764 "vmov.i16 q8, #0\n"
4765 "vmov.i16 q9, #0\n"
4766 "vmov.i16 q10, #0\n"
4767 "vmov.i16 q11, #0\n"
4768 "vmov.i16 q12, #0\n"
4769 "vmov.i16 q13, #0\n"
4770 "vmov.i16 q14, #0\n"
4771 "vmov.i16 q15, #0\n"
4772
4773 "1:"
4774 "subs %[count], %[count], #8\n"
4775
4776 // Load Aggregate Store: 8x8.
4777 "vld1.32 {d0}, [%[in]]!\n"
4778 "vld1.32 {d1}, [r0]!\n"
4779 "vld1.32 {d2}, [r1]!\n"
4780 "vld1.32 {d3}, [r2]!\n"
4781 "vld1.32 {d4}, [r3]!\n"
4782 "vld1.32 {d5}, [r4]!\n"
4783 "vld1.32 {d6}, [r5]!\n"
4784 "vld1.32 {d7}, [r6]!\n"
4785 "vaddw.u8 q8, q8, d0\n"
4786 "vaddw.u8 q9, q9, d1\n"
4787 "vaddw.u8 q10, q10, d2\n"
4788 "vaddw.u8 q11, q11, d3\n"
4789 "vaddw.u8 q12, q12, d4\n"
4790 "vaddw.u8 q13, q13, d5\n"
4791 "vaddw.u8 q14, q14, d6\n"
4792 "vaddw.u8 q15, q15, d7\n"
4793 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
4794 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
4795
4796 "bne 1b\n"
4797
4798 // Aggregator Reduction.
4799 "ldr r0, %[multiplicative_sum_offset]\n"
4800 "ldr r1, %[additive_sum_offset]\n"
4801 "vmov.32 d0[0], r0\n"
4802 "vdup.32 q1, r1\n"
4803 "vpaddl.u16 q8, q8\n"
4804 "vpaddl.u16 q9, q9\n"
4805 "vpaddl.u16 q10, q10\n"
4806 "vpaddl.u16 q11, q11\n"
4807 "vpaddl.u16 q12, q12\n"
4808 "vpaddl.u16 q13, q13\n"
4809 "vpaddl.u16 q14, q14\n"
4810 "vpaddl.u16 q15, q15\n"
4811 "vpadd.u32 d16, d16, d17\n"
4812 "vpadd.u32 d18, d18, d19\n"
4813 "vpadd.u32 d20, d20, d21\n"
4814 "vpadd.u32 d22, d22, d23\n"
4815 "vpadd.u32 d24, d24, d25\n"
4816 "vpadd.u32 d26, d26, d27\n"
4817 "vpadd.u32 d28, d28, d29\n"
4818 "vpadd.u32 d30, d30, d31\n"
4819 "vpadd.u32 d16, d16, d18\n"
4820 "vpadd.u32 d17, d20, d22\n"
4821 "vpadd.u32 d18, d24, d26\n"
4822 "vpadd.u32 d19, d28, d30\n"
4823 "vmul.i32 q8, q8, d0[0]\n"
4824 "vmul.i32 q9, q9, d0[0]\n"
4825 "vadd.i32 q8, q8, q1\n"
4826 "vadd.i32 q9, q9, q1\n"
4827 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
4828 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
4829 : [stride] "r"(params.stride),
4830 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
4831 [additive_sum_offset] "m"(params.additive_sum_offset)
4832 : "r0", "r1", "r2", "r3", "r4", "r5", "r6", "d0", "d1", "d2", "d3", "d4",
4833 "d5", "d6", "d7", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
4834 "d23", "d24", "d25", "d26", "d27", "d28", "d29", "d30", "d31", "cc",
4835 "memory");
4836 }
4837
4838 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)4839 inline void Stream<uint8_t, 8, 8, 1, RowMajorWithSum>::Pack(
4840 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
4841 #ifdef DEBUG
4842 #ifdef DEBUG_METAGEMM_VERBOSE
4843 std::cout << __FILE__ << "(" << __LINE__
4844 << ") RowMajorWithSum<uint8_t, 8, 8, 1, RowMajorWithSum>::Pack()"
4845 << std::endl
4846 << std::flush;
4847 #endif
4848 #endif
4849 int params_count_copy = params.count;
4850 asm volatile(
4851 "add r0, %[in], %[stride]\n"
4852 "add r1, r0, %[stride]\n"
4853 "add r2, r1, %[stride]\n"
4854 "add r3, r2, %[stride]\n"
4855 "add r4, r3, %[stride]\n"
4856 "add r5, r4, %[stride]\n"
4857 "add r6, r5, %[stride]\n"
4858 "vmov.i16 q8, #0\n"
4859 "vmov.i16 q9, #0\n"
4860 "vmov.i16 q10, #0\n"
4861 "vmov.i16 q11, #0\n"
4862 "vmov.i16 q12, #0\n"
4863 "vmov.i16 q13, #0\n"
4864 "vmov.i16 q14, #0\n"
4865 "vmov.i16 q15, #0\n"
4866
4867 // Reduce count by leftovers.
4868 "subs %[count], %[count], #1\n"
4869 "beq 2f\n"
4870
4871 "1:"
4872 "subs %[count], %[count], #8\n"
4873
4874 // Load Aggregate Store: 8x8.
4875 "vld1.32 {d0}, [%[in]]!\n"
4876 "vld1.32 {d1}, [r0]!\n"
4877 "vld1.32 {d2}, [r1]!\n"
4878 "vld1.32 {d3}, [r2]!\n"
4879 "vld1.32 {d4}, [r3]!\n"
4880 "vld1.32 {d5}, [r4]!\n"
4881 "vld1.32 {d6}, [r5]!\n"
4882 "vld1.32 {d7}, [r6]!\n"
4883 "vaddw.u8 q8, q8, d0\n"
4884 "vaddw.u8 q9, q9, d1\n"
4885 "vaddw.u8 q10, q10, d2\n"
4886 "vaddw.u8 q11, q11, d3\n"
4887 "vaddw.u8 q12, q12, d4\n"
4888 "vaddw.u8 q13, q13, d5\n"
4889 "vaddw.u8 q14, q14, d6\n"
4890 "vaddw.u8 q15, q15, d7\n"
4891 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
4892 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
4893
4894 "bne 1b\n"
4895
4896 "2:"
4897
4898 // Load Aggregate Store: 8x1.
4899 "vmov.i8 d0, #0\n"
4900 "vmov.i8 d1, #0\n"
4901 "vmov.i8 d2, #0\n"
4902 "vmov.i8 d3, #0\n"
4903 "vmov.i8 d4, #0\n"
4904 "vmov.i8 d5, #0\n"
4905 "vmov.i8 d6, #0\n"
4906 "vmov.i8 d7, #0\n"
4907 "vld1.8 {d0[0]}, [%[in]]!\n"
4908 "vld1.8 {d1[0]}, [r0]!\n"
4909 "vld1.8 {d2[0]}, [r1]!\n"
4910 "vld1.8 {d3[0]}, [r2]!\n"
4911 "vld1.8 {d4[0]}, [r3]!\n"
4912 "vld1.8 {d5[0]}, [r4]!\n"
4913 "vld1.8 {d6[0]}, [r5]!\n"
4914 "vld1.8 {d7[0]}, [r6]!\n"
4915 "vaddw.u8 q8, q8, d0\n"
4916 "vaddw.u8 q9, q9, d1\n"
4917 "vaddw.u8 q10, q10, d2\n"
4918 "vaddw.u8 q11, q11, d3\n"
4919 "vaddw.u8 q12, q12, d4\n"
4920 "vaddw.u8 q13, q13, d5\n"
4921 "vaddw.u8 q14, q14, d6\n"
4922 "vaddw.u8 q15, q15, d7\n"
4923 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
4924 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
4925
4926 // Aggregator Reduction.
4927 "ldr r0, %[multiplicative_sum_offset]\n"
4928 "ldr r1, %[additive_sum_offset]\n"
4929 "vmov.32 d0[0], r0\n"
4930 "vdup.32 q1, r1\n"
4931 "vpaddl.u16 q8, q8\n"
4932 "vpaddl.u16 q9, q9\n"
4933 "vpaddl.u16 q10, q10\n"
4934 "vpaddl.u16 q11, q11\n"
4935 "vpaddl.u16 q12, q12\n"
4936 "vpaddl.u16 q13, q13\n"
4937 "vpaddl.u16 q14, q14\n"
4938 "vpaddl.u16 q15, q15\n"
4939 "vpadd.u32 d16, d16, d17\n"
4940 "vpadd.u32 d18, d18, d19\n"
4941 "vpadd.u32 d20, d20, d21\n"
4942 "vpadd.u32 d22, d22, d23\n"
4943 "vpadd.u32 d24, d24, d25\n"
4944 "vpadd.u32 d26, d26, d27\n"
4945 "vpadd.u32 d28, d28, d29\n"
4946 "vpadd.u32 d30, d30, d31\n"
4947 "vpadd.u32 d16, d16, d18\n"
4948 "vpadd.u32 d17, d20, d22\n"
4949 "vpadd.u32 d18, d24, d26\n"
4950 "vpadd.u32 d19, d28, d30\n"
4951 "vmul.i32 q8, q8, d0[0]\n"
4952 "vmul.i32 q9, q9, d0[0]\n"
4953 "vadd.i32 q8, q8, q1\n"
4954 "vadd.i32 q9, q9, q1\n"
4955 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
4956 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
4957 : [stride] "r"(params.stride),
4958 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
4959 [additive_sum_offset] "m"(params.additive_sum_offset)
4960 : "r0", "r1", "r2", "r3", "r4", "r5", "r6", "d0", "d1", "d2", "d3", "d4",
4961 "d5", "d6", "d7", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
4962 "d23", "d24", "d25", "d26", "d27", "d28", "d29", "d30", "d31", "cc",
4963 "memory");
4964 }
4965
4966 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)4967 inline void Stream<uint8_t, 8, 8, 2, RowMajorWithSum>::Pack(
4968 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
4969 #ifdef DEBUG
4970 #ifdef DEBUG_METAGEMM_VERBOSE
4971 std::cout << __FILE__ << "(" << __LINE__
4972 << ") RowMajorWithSum<uint8_t, 8, 8, 2, RowMajorWithSum>::Pack()"
4973 << std::endl
4974 << std::flush;
4975 #endif
4976 #endif
4977 int params_count_copy = params.count;
4978 asm volatile(
4979 "add r0, %[in], %[stride]\n"
4980 "add r1, r0, %[stride]\n"
4981 "add r2, r1, %[stride]\n"
4982 "add r3, r2, %[stride]\n"
4983 "add r4, r3, %[stride]\n"
4984 "add r5, r4, %[stride]\n"
4985 "add r6, r5, %[stride]\n"
4986 "vmov.i16 q8, #0\n"
4987 "vmov.i16 q9, #0\n"
4988 "vmov.i16 q10, #0\n"
4989 "vmov.i16 q11, #0\n"
4990 "vmov.i16 q12, #0\n"
4991 "vmov.i16 q13, #0\n"
4992 "vmov.i16 q14, #0\n"
4993 "vmov.i16 q15, #0\n"
4994
4995 // Reduce count by leftovers.
4996 "subs %[count], %[count], #2\n"
4997 "beq 2f\n"
4998
4999 "1:"
5000 "subs %[count], %[count], #8\n"
5001
5002 // Load Aggregate Store: 8x8.
5003 "vld1.32 {d0}, [%[in]]!\n"
5004 "vld1.32 {d1}, [r0]!\n"
5005 "vld1.32 {d2}, [r1]!\n"
5006 "vld1.32 {d3}, [r2]!\n"
5007 "vld1.32 {d4}, [r3]!\n"
5008 "vld1.32 {d5}, [r4]!\n"
5009 "vld1.32 {d6}, [r5]!\n"
5010 "vld1.32 {d7}, [r6]!\n"
5011 "vaddw.u8 q8, q8, d0\n"
5012 "vaddw.u8 q9, q9, d1\n"
5013 "vaddw.u8 q10, q10, d2\n"
5014 "vaddw.u8 q11, q11, d3\n"
5015 "vaddw.u8 q12, q12, d4\n"
5016 "vaddw.u8 q13, q13, d5\n"
5017 "vaddw.u8 q14, q14, d6\n"
5018 "vaddw.u8 q15, q15, d7\n"
5019 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
5020 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
5021
5022 "bne 1b\n"
5023
5024 "2:"
5025
5026 // Load Aggregate Store: 8x2.
5027 "vmov.i8 d0, #0\n"
5028 "vmov.i8 d1, #0\n"
5029 "vmov.i8 d2, #0\n"
5030 "vmov.i8 d3, #0\n"
5031 "vmov.i8 d4, #0\n"
5032 "vmov.i8 d5, #0\n"
5033 "vmov.i8 d6, #0\n"
5034 "vmov.i8 d7, #0\n"
5035 "vld1.16 {d0[0]}, [%[in]]!\n"
5036 "vld1.16 {d1[0]}, [r0]!\n"
5037 "vld1.16 {d2[0]}, [r1]!\n"
5038 "vld1.16 {d3[0]}, [r2]!\n"
5039 "vld1.16 {d4[0]}, [r3]!\n"
5040 "vld1.16 {d5[0]}, [r4]!\n"
5041 "vld1.16 {d6[0]}, [r5]!\n"
5042 "vld1.16 {d7[0]}, [r6]!\n"
5043 "vaddw.u8 q8, q8, d0\n"
5044 "vaddw.u8 q9, q9, d1\n"
5045 "vaddw.u8 q10, q10, d2\n"
5046 "vaddw.u8 q11, q11, d3\n"
5047 "vaddw.u8 q12, q12, d4\n"
5048 "vaddw.u8 q13, q13, d5\n"
5049 "vaddw.u8 q14, q14, d6\n"
5050 "vaddw.u8 q15, q15, d7\n"
5051 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
5052 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
5053
5054 // Aggregator Reduction.
5055 "ldr r0, %[multiplicative_sum_offset]\n"
5056 "ldr r1, %[additive_sum_offset]\n"
5057 "vmov.32 d0[0], r0\n"
5058 "vdup.32 q1, r1\n"
5059 "vpaddl.u16 q8, q8\n"
5060 "vpaddl.u16 q9, q9\n"
5061 "vpaddl.u16 q10, q10\n"
5062 "vpaddl.u16 q11, q11\n"
5063 "vpaddl.u16 q12, q12\n"
5064 "vpaddl.u16 q13, q13\n"
5065 "vpaddl.u16 q14, q14\n"
5066 "vpaddl.u16 q15, q15\n"
5067 "vpadd.u32 d16, d16, d17\n"
5068 "vpadd.u32 d18, d18, d19\n"
5069 "vpadd.u32 d20, d20, d21\n"
5070 "vpadd.u32 d22, d22, d23\n"
5071 "vpadd.u32 d24, d24, d25\n"
5072 "vpadd.u32 d26, d26, d27\n"
5073 "vpadd.u32 d28, d28, d29\n"
5074 "vpadd.u32 d30, d30, d31\n"
5075 "vpadd.u32 d16, d16, d18\n"
5076 "vpadd.u32 d17, d20, d22\n"
5077 "vpadd.u32 d18, d24, d26\n"
5078 "vpadd.u32 d19, d28, d30\n"
5079 "vmul.i32 q8, q8, d0[0]\n"
5080 "vmul.i32 q9, q9, d0[0]\n"
5081 "vadd.i32 q8, q8, q1\n"
5082 "vadd.i32 q9, q9, q1\n"
5083 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
5084 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
5085 : [stride] "r"(params.stride),
5086 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
5087 [additive_sum_offset] "m"(params.additive_sum_offset)
5088 : "r0", "r1", "r2", "r3", "r4", "r5", "r6", "d0", "d1", "d2", "d3", "d4",
5089 "d5", "d6", "d7", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
5090 "d23", "d24", "d25", "d26", "d27", "d28", "d29", "d30", "d31", "cc",
5091 "memory");
5092 }
5093
5094 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)5095 inline void Stream<uint8_t, 8, 8, 3, RowMajorWithSum>::Pack(
5096 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
5097 #ifdef DEBUG
5098 #ifdef DEBUG_METAGEMM_VERBOSE
5099 std::cout << __FILE__ << "(" << __LINE__
5100 << ") RowMajorWithSum<uint8_t, 8, 8, 3, RowMajorWithSum>::Pack()"
5101 << std::endl
5102 << std::flush;
5103 #endif
5104 #endif
5105 int params_count_copy = params.count;
5106 asm volatile(
5107 "add r0, %[in], %[stride]\n"
5108 "add r1, r0, %[stride]\n"
5109 "add r2, r1, %[stride]\n"
5110 "add r3, r2, %[stride]\n"
5111 "add r4, r3, %[stride]\n"
5112 "add r5, r4, %[stride]\n"
5113 "add r6, r5, %[stride]\n"
5114 "vmov.i16 q8, #0\n"
5115 "vmov.i16 q9, #0\n"
5116 "vmov.i16 q10, #0\n"
5117 "vmov.i16 q11, #0\n"
5118 "vmov.i16 q12, #0\n"
5119 "vmov.i16 q13, #0\n"
5120 "vmov.i16 q14, #0\n"
5121 "vmov.i16 q15, #0\n"
5122
5123 // Reduce count by leftovers.
5124 "subs %[count], %[count], #3\n"
5125 "beq 2f\n"
5126
5127 "1:"
5128 "subs %[count], %[count], #8\n"
5129
5130 // Load Aggregate Store: 8x8.
5131 "vld1.32 {d0}, [%[in]]!\n"
5132 "vld1.32 {d1}, [r0]!\n"
5133 "vld1.32 {d2}, [r1]!\n"
5134 "vld1.32 {d3}, [r2]!\n"
5135 "vld1.32 {d4}, [r3]!\n"
5136 "vld1.32 {d5}, [r4]!\n"
5137 "vld1.32 {d6}, [r5]!\n"
5138 "vld1.32 {d7}, [r6]!\n"
5139 "vaddw.u8 q8, q8, d0\n"
5140 "vaddw.u8 q9, q9, d1\n"
5141 "vaddw.u8 q10, q10, d2\n"
5142 "vaddw.u8 q11, q11, d3\n"
5143 "vaddw.u8 q12, q12, d4\n"
5144 "vaddw.u8 q13, q13, d5\n"
5145 "vaddw.u8 q14, q14, d6\n"
5146 "vaddw.u8 q15, q15, d7\n"
5147 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
5148 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
5149
5150 "bne 1b\n"
5151
5152 "2:"
5153
5154 // Load Aggregate Store: 8x3.
5155 "vmov.i8 d0, #0\n"
5156 "vmov.i8 d1, #0\n"
5157 "vmov.i8 d2, #0\n"
5158 "vmov.i8 d3, #0\n"
5159 "vmov.i8 d4, #0\n"
5160 "vmov.i8 d5, #0\n"
5161 "vmov.i8 d6, #0\n"
5162 "vmov.i8 d7, #0\n"
5163 "vld1.16 {d0[0]}, [%[in]]!\n"
5164 "vld1.8 {d0[2]}, [%[in]]!\n"
5165 "vld1.16 {d1[0]}, [r0]!\n"
5166 "vld1.8 {d1[2]}, [r0]!\n"
5167 "vld1.16 {d2[0]}, [r1]!\n"
5168 "vld1.8 {d2[2]}, [r1]!\n"
5169 "vld1.16 {d3[0]}, [r2]!\n"
5170 "vld1.8 {d3[2]}, [r2]!\n"
5171 "vld1.16 {d4[0]}, [r3]!\n"
5172 "vld1.8 {d4[2]}, [r3]!\n"
5173 "vld1.16 {d5[0]}, [r4]!\n"
5174 "vld1.8 {d5[2]}, [r4]!\n"
5175 "vld1.16 {d6[0]}, [r5]!\n"
5176 "vld1.8 {d6[2]}, [r5]!\n"
5177 "vld1.16 {d7[0]}, [r6]!\n"
5178 "vld1.8 {d7[2]}, [r6]!\n"
5179 "vaddw.u8 q8, q8, d0\n"
5180 "vaddw.u8 q9, q9, d1\n"
5181 "vaddw.u8 q10, q10, d2\n"
5182 "vaddw.u8 q11, q11, d3\n"
5183 "vaddw.u8 q12, q12, d4\n"
5184 "vaddw.u8 q13, q13, d5\n"
5185 "vaddw.u8 q14, q14, d6\n"
5186 "vaddw.u8 q15, q15, d7\n"
5187 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
5188 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
5189
5190 // Aggregator Reduction.
5191 "ldr r0, %[multiplicative_sum_offset]\n"
5192 "ldr r1, %[additive_sum_offset]\n"
5193 "vmov.32 d0[0], r0\n"
5194 "vdup.32 q1, r1\n"
5195 "vpaddl.u16 q8, q8\n"
5196 "vpaddl.u16 q9, q9\n"
5197 "vpaddl.u16 q10, q10\n"
5198 "vpaddl.u16 q11, q11\n"
5199 "vpaddl.u16 q12, q12\n"
5200 "vpaddl.u16 q13, q13\n"
5201 "vpaddl.u16 q14, q14\n"
5202 "vpaddl.u16 q15, q15\n"
5203 "vpadd.u32 d16, d16, d17\n"
5204 "vpadd.u32 d18, d18, d19\n"
5205 "vpadd.u32 d20, d20, d21\n"
5206 "vpadd.u32 d22, d22, d23\n"
5207 "vpadd.u32 d24, d24, d25\n"
5208 "vpadd.u32 d26, d26, d27\n"
5209 "vpadd.u32 d28, d28, d29\n"
5210 "vpadd.u32 d30, d30, d31\n"
5211 "vpadd.u32 d16, d16, d18\n"
5212 "vpadd.u32 d17, d20, d22\n"
5213 "vpadd.u32 d18, d24, d26\n"
5214 "vpadd.u32 d19, d28, d30\n"
5215 "vmul.i32 q8, q8, d0[0]\n"
5216 "vmul.i32 q9, q9, d0[0]\n"
5217 "vadd.i32 q8, q8, q1\n"
5218 "vadd.i32 q9, q9, q1\n"
5219 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
5220 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
5221 : [stride] "r"(params.stride),
5222 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
5223 [additive_sum_offset] "m"(params.additive_sum_offset)
5224 : "r0", "r1", "r2", "r3", "r4", "r5", "r6", "d0", "d1", "d2", "d3", "d4",
5225 "d5", "d6", "d7", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
5226 "d23", "d24", "d25", "d26", "d27", "d28", "d29", "d30", "d31", "cc",
5227 "memory");
5228 }
5229
5230 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)5231 inline void Stream<uint8_t, 8, 8, 4, RowMajorWithSum>::Pack(
5232 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
5233 #ifdef DEBUG
5234 #ifdef DEBUG_METAGEMM_VERBOSE
5235 std::cout << __FILE__ << "(" << __LINE__
5236 << ") RowMajorWithSum<uint8_t, 8, 8, 4, RowMajorWithSum>::Pack()"
5237 << std::endl
5238 << std::flush;
5239 #endif
5240 #endif
5241 int params_count_copy = params.count;
5242 asm volatile(
5243 "add r0, %[in], %[stride]\n"
5244 "add r1, r0, %[stride]\n"
5245 "add r2, r1, %[stride]\n"
5246 "add r3, r2, %[stride]\n"
5247 "add r4, r3, %[stride]\n"
5248 "add r5, r4, %[stride]\n"
5249 "add r6, r5, %[stride]\n"
5250 "vmov.i16 q8, #0\n"
5251 "vmov.i16 q9, #0\n"
5252 "vmov.i16 q10, #0\n"
5253 "vmov.i16 q11, #0\n"
5254 "vmov.i16 q12, #0\n"
5255 "vmov.i16 q13, #0\n"
5256 "vmov.i16 q14, #0\n"
5257 "vmov.i16 q15, #0\n"
5258
5259 // Reduce count by leftovers.
5260 "subs %[count], %[count], #4\n"
5261 "beq 2f\n"
5262
5263 "1:"
5264 "subs %[count], %[count], #8\n"
5265
5266 // Load Aggregate Store: 8x8.
5267 "vld1.32 {d0}, [%[in]]!\n"
5268 "vld1.32 {d1}, [r0]!\n"
5269 "vld1.32 {d2}, [r1]!\n"
5270 "vld1.32 {d3}, [r2]!\n"
5271 "vld1.32 {d4}, [r3]!\n"
5272 "vld1.32 {d5}, [r4]!\n"
5273 "vld1.32 {d6}, [r5]!\n"
5274 "vld1.32 {d7}, [r6]!\n"
5275 "vaddw.u8 q8, q8, d0\n"
5276 "vaddw.u8 q9, q9, d1\n"
5277 "vaddw.u8 q10, q10, d2\n"
5278 "vaddw.u8 q11, q11, d3\n"
5279 "vaddw.u8 q12, q12, d4\n"
5280 "vaddw.u8 q13, q13, d5\n"
5281 "vaddw.u8 q14, q14, d6\n"
5282 "vaddw.u8 q15, q15, d7\n"
5283 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
5284 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
5285
5286 "bne 1b\n"
5287
5288 "2:"
5289
5290 // Load Aggregate Store: 8x4.
5291 "vmov.i8 d0, #0\n"
5292 "vmov.i8 d1, #0\n"
5293 "vmov.i8 d2, #0\n"
5294 "vmov.i8 d3, #0\n"
5295 "vmov.i8 d4, #0\n"
5296 "vmov.i8 d5, #0\n"
5297 "vmov.i8 d6, #0\n"
5298 "vmov.i8 d7, #0\n"
5299 "vld1.32 {d0[0]}, [%[in]]!\n"
5300 "vld1.32 {d1[0]}, [r0]!\n"
5301 "vld1.32 {d2[0]}, [r1]!\n"
5302 "vld1.32 {d3[0]}, [r2]!\n"
5303 "vld1.32 {d4[0]}, [r3]!\n"
5304 "vld1.32 {d5[0]}, [r4]!\n"
5305 "vld1.32 {d6[0]}, [r5]!\n"
5306 "vld1.32 {d7[0]}, [r6]!\n"
5307 "vaddw.u8 q8, q8, d0\n"
5308 "vaddw.u8 q9, q9, d1\n"
5309 "vaddw.u8 q10, q10, d2\n"
5310 "vaddw.u8 q11, q11, d3\n"
5311 "vaddw.u8 q12, q12, d4\n"
5312 "vaddw.u8 q13, q13, d5\n"
5313 "vaddw.u8 q14, q14, d6\n"
5314 "vaddw.u8 q15, q15, d7\n"
5315 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
5316 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
5317
5318 // Aggregator Reduction.
5319 "ldr r0, %[multiplicative_sum_offset]\n"
5320 "ldr r1, %[additive_sum_offset]\n"
5321 "vmov.32 d0[0], r0\n"
5322 "vdup.32 q1, r1\n"
5323 "vpaddl.u16 q8, q8\n"
5324 "vpaddl.u16 q9, q9\n"
5325 "vpaddl.u16 q10, q10\n"
5326 "vpaddl.u16 q11, q11\n"
5327 "vpaddl.u16 q12, q12\n"
5328 "vpaddl.u16 q13, q13\n"
5329 "vpaddl.u16 q14, q14\n"
5330 "vpaddl.u16 q15, q15\n"
5331 "vpadd.u32 d16, d16, d17\n"
5332 "vpadd.u32 d18, d18, d19\n"
5333 "vpadd.u32 d20, d20, d21\n"
5334 "vpadd.u32 d22, d22, d23\n"
5335 "vpadd.u32 d24, d24, d25\n"
5336 "vpadd.u32 d26, d26, d27\n"
5337 "vpadd.u32 d28, d28, d29\n"
5338 "vpadd.u32 d30, d30, d31\n"
5339 "vpadd.u32 d16, d16, d18\n"
5340 "vpadd.u32 d17, d20, d22\n"
5341 "vpadd.u32 d18, d24, d26\n"
5342 "vpadd.u32 d19, d28, d30\n"
5343 "vmul.i32 q8, q8, d0[0]\n"
5344 "vmul.i32 q9, q9, d0[0]\n"
5345 "vadd.i32 q8, q8, q1\n"
5346 "vadd.i32 q9, q9, q1\n"
5347 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
5348 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
5349 : [stride] "r"(params.stride),
5350 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
5351 [additive_sum_offset] "m"(params.additive_sum_offset)
5352 : "r0", "r1", "r2", "r3", "r4", "r5", "r6", "d0", "d1", "d2", "d3", "d4",
5353 "d5", "d6", "d7", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
5354 "d23", "d24", "d25", "d26", "d27", "d28", "d29", "d30", "d31", "cc",
5355 "memory");
5356 }
5357
5358 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)5359 inline void Stream<uint8_t, 8, 8, 5, RowMajorWithSum>::Pack(
5360 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
5361 #ifdef DEBUG
5362 #ifdef DEBUG_METAGEMM_VERBOSE
5363 std::cout << __FILE__ << "(" << __LINE__
5364 << ") RowMajorWithSum<uint8_t, 8, 8, 5, RowMajorWithSum>::Pack()"
5365 << std::endl
5366 << std::flush;
5367 #endif
5368 #endif
5369 int params_count_copy = params.count;
5370 asm volatile(
5371 "add r0, %[in], %[stride]\n"
5372 "add r1, r0, %[stride]\n"
5373 "add r2, r1, %[stride]\n"
5374 "add r3, r2, %[stride]\n"
5375 "add r4, r3, %[stride]\n"
5376 "add r5, r4, %[stride]\n"
5377 "add r6, r5, %[stride]\n"
5378 "vmov.i16 q8, #0\n"
5379 "vmov.i16 q9, #0\n"
5380 "vmov.i16 q10, #0\n"
5381 "vmov.i16 q11, #0\n"
5382 "vmov.i16 q12, #0\n"
5383 "vmov.i16 q13, #0\n"
5384 "vmov.i16 q14, #0\n"
5385 "vmov.i16 q15, #0\n"
5386
5387 // Reduce count by leftovers.
5388 "subs %[count], %[count], #5\n"
5389 "beq 2f\n"
5390
5391 "1:"
5392 "subs %[count], %[count], #8\n"
5393
5394 // Load Aggregate Store: 8x8.
5395 "vld1.32 {d0}, [%[in]]!\n"
5396 "vld1.32 {d1}, [r0]!\n"
5397 "vld1.32 {d2}, [r1]!\n"
5398 "vld1.32 {d3}, [r2]!\n"
5399 "vld1.32 {d4}, [r3]!\n"
5400 "vld1.32 {d5}, [r4]!\n"
5401 "vld1.32 {d6}, [r5]!\n"
5402 "vld1.32 {d7}, [r6]!\n"
5403 "vaddw.u8 q8, q8, d0\n"
5404 "vaddw.u8 q9, q9, d1\n"
5405 "vaddw.u8 q10, q10, d2\n"
5406 "vaddw.u8 q11, q11, d3\n"
5407 "vaddw.u8 q12, q12, d4\n"
5408 "vaddw.u8 q13, q13, d5\n"
5409 "vaddw.u8 q14, q14, d6\n"
5410 "vaddw.u8 q15, q15, d7\n"
5411 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
5412 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
5413
5414 "bne 1b\n"
5415
5416 "2:"
5417
5418 // Load Aggregate Store: 8x5.
5419 "vmov.i8 d0, #0\n"
5420 "vmov.i8 d1, #0\n"
5421 "vmov.i8 d2, #0\n"
5422 "vmov.i8 d3, #0\n"
5423 "vmov.i8 d4, #0\n"
5424 "vmov.i8 d5, #0\n"
5425 "vmov.i8 d6, #0\n"
5426 "vmov.i8 d7, #0\n"
5427 "vld1.32 {d0[0]}, [%[in]]!\n"
5428 "vld1.8 {d0[4]}, [%[in]]!\n"
5429 "vld1.32 {d1[0]}, [r0]!\n"
5430 "vld1.8 {d1[4]}, [r0]!\n"
5431 "vld1.32 {d2[0]}, [r1]!\n"
5432 "vld1.8 {d2[4]}, [r1]!\n"
5433 "vld1.32 {d3[0]}, [r2]!\n"
5434 "vld1.8 {d3[4]}, [r2]!\n"
5435 "vld1.32 {d4[0]}, [r3]!\n"
5436 "vld1.8 {d4[4]}, [r3]!\n"
5437 "vld1.32 {d5[0]}, [r4]!\n"
5438 "vld1.8 {d5[4]}, [r4]!\n"
5439 "vld1.32 {d6[0]}, [r5]!\n"
5440 "vld1.8 {d6[4]}, [r5]!\n"
5441 "vld1.32 {d7[0]}, [r6]!\n"
5442 "vld1.8 {d7[4]}, [r6]!\n"
5443 "vaddw.u8 q8, q8, d0\n"
5444 "vaddw.u8 q9, q9, d1\n"
5445 "vaddw.u8 q10, q10, d2\n"
5446 "vaddw.u8 q11, q11, d3\n"
5447 "vaddw.u8 q12, q12, d4\n"
5448 "vaddw.u8 q13, q13, d5\n"
5449 "vaddw.u8 q14, q14, d6\n"
5450 "vaddw.u8 q15, q15, d7\n"
5451 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
5452 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
5453
5454 // Aggregator Reduction.
5455 "ldr r0, %[multiplicative_sum_offset]\n"
5456 "ldr r1, %[additive_sum_offset]\n"
5457 "vmov.32 d0[0], r0\n"
5458 "vdup.32 q1, r1\n"
5459 "vpaddl.u16 q8, q8\n"
5460 "vpaddl.u16 q9, q9\n"
5461 "vpaddl.u16 q10, q10\n"
5462 "vpaddl.u16 q11, q11\n"
5463 "vpaddl.u16 q12, q12\n"
5464 "vpaddl.u16 q13, q13\n"
5465 "vpaddl.u16 q14, q14\n"
5466 "vpaddl.u16 q15, q15\n"
5467 "vpadd.u32 d16, d16, d17\n"
5468 "vpadd.u32 d18, d18, d19\n"
5469 "vpadd.u32 d20, d20, d21\n"
5470 "vpadd.u32 d22, d22, d23\n"
5471 "vpadd.u32 d24, d24, d25\n"
5472 "vpadd.u32 d26, d26, d27\n"
5473 "vpadd.u32 d28, d28, d29\n"
5474 "vpadd.u32 d30, d30, d31\n"
5475 "vpadd.u32 d16, d16, d18\n"
5476 "vpadd.u32 d17, d20, d22\n"
5477 "vpadd.u32 d18, d24, d26\n"
5478 "vpadd.u32 d19, d28, d30\n"
5479 "vmul.i32 q8, q8, d0[0]\n"
5480 "vmul.i32 q9, q9, d0[0]\n"
5481 "vadd.i32 q8, q8, q1\n"
5482 "vadd.i32 q9, q9, q1\n"
5483 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
5484 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
5485 : [stride] "r"(params.stride),
5486 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
5487 [additive_sum_offset] "m"(params.additive_sum_offset)
5488 : "r0", "r1", "r2", "r3", "r4", "r5", "r6", "d0", "d1", "d2", "d3", "d4",
5489 "d5", "d6", "d7", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
5490 "d23", "d24", "d25", "d26", "d27", "d28", "d29", "d30", "d31", "cc",
5491 "memory");
5492 }
5493
5494 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)5495 inline void Stream<uint8_t, 8, 8, 6, RowMajorWithSum>::Pack(
5496 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
5497 #ifdef DEBUG
5498 #ifdef DEBUG_METAGEMM_VERBOSE
5499 std::cout << __FILE__ << "(" << __LINE__
5500 << ") RowMajorWithSum<uint8_t, 8, 8, 6, RowMajorWithSum>::Pack()"
5501 << std::endl
5502 << std::flush;
5503 #endif
5504 #endif
5505 int params_count_copy = params.count;
5506 asm volatile(
5507 "add r0, %[in], %[stride]\n"
5508 "add r1, r0, %[stride]\n"
5509 "add r2, r1, %[stride]\n"
5510 "add r3, r2, %[stride]\n"
5511 "add r4, r3, %[stride]\n"
5512 "add r5, r4, %[stride]\n"
5513 "add r6, r5, %[stride]\n"
5514 "vmov.i16 q8, #0\n"
5515 "vmov.i16 q9, #0\n"
5516 "vmov.i16 q10, #0\n"
5517 "vmov.i16 q11, #0\n"
5518 "vmov.i16 q12, #0\n"
5519 "vmov.i16 q13, #0\n"
5520 "vmov.i16 q14, #0\n"
5521 "vmov.i16 q15, #0\n"
5522
5523 // Reduce count by leftovers.
5524 "subs %[count], %[count], #6\n"
5525 "beq 2f\n"
5526
5527 "1:"
5528 "subs %[count], %[count], #8\n"
5529
5530 // Load Aggregate Store: 8x8.
5531 "vld1.32 {d0}, [%[in]]!\n"
5532 "vld1.32 {d1}, [r0]!\n"
5533 "vld1.32 {d2}, [r1]!\n"
5534 "vld1.32 {d3}, [r2]!\n"
5535 "vld1.32 {d4}, [r3]!\n"
5536 "vld1.32 {d5}, [r4]!\n"
5537 "vld1.32 {d6}, [r5]!\n"
5538 "vld1.32 {d7}, [r6]!\n"
5539 "vaddw.u8 q8, q8, d0\n"
5540 "vaddw.u8 q9, q9, d1\n"
5541 "vaddw.u8 q10, q10, d2\n"
5542 "vaddw.u8 q11, q11, d3\n"
5543 "vaddw.u8 q12, q12, d4\n"
5544 "vaddw.u8 q13, q13, d5\n"
5545 "vaddw.u8 q14, q14, d6\n"
5546 "vaddw.u8 q15, q15, d7\n"
5547 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
5548 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
5549
5550 "bne 1b\n"
5551
5552 "2:"
5553
5554 // Load Aggregate Store: 8x6.
5555 "vmov.i8 d0, #0\n"
5556 "vmov.i8 d1, #0\n"
5557 "vmov.i8 d2, #0\n"
5558 "vmov.i8 d3, #0\n"
5559 "vmov.i8 d4, #0\n"
5560 "vmov.i8 d5, #0\n"
5561 "vmov.i8 d6, #0\n"
5562 "vmov.i8 d7, #0\n"
5563 "vld1.32 {d0[0]}, [%[in]]!\n"
5564 "vld1.16 {d0[2]}, [%[in]]!\n"
5565 "vld1.32 {d1[0]}, [r0]!\n"
5566 "vld1.16 {d1[2]}, [r0]!\n"
5567 "vld1.32 {d2[0]}, [r1]!\n"
5568 "vld1.16 {d2[2]}, [r1]!\n"
5569 "vld1.32 {d3[0]}, [r2]!\n"
5570 "vld1.16 {d3[2]}, [r2]!\n"
5571 "vld1.32 {d4[0]}, [r3]!\n"
5572 "vld1.16 {d4[2]}, [r3]!\n"
5573 "vld1.32 {d5[0]}, [r4]!\n"
5574 "vld1.16 {d5[2]}, [r4]!\n"
5575 "vld1.32 {d6[0]}, [r5]!\n"
5576 "vld1.16 {d6[2]}, [r5]!\n"
5577 "vld1.32 {d7[0]}, [r6]!\n"
5578 "vld1.16 {d7[2]}, [r6]!\n"
5579 "vaddw.u8 q8, q8, d0\n"
5580 "vaddw.u8 q9, q9, d1\n"
5581 "vaddw.u8 q10, q10, d2\n"
5582 "vaddw.u8 q11, q11, d3\n"
5583 "vaddw.u8 q12, q12, d4\n"
5584 "vaddw.u8 q13, q13, d5\n"
5585 "vaddw.u8 q14, q14, d6\n"
5586 "vaddw.u8 q15, q15, d7\n"
5587 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
5588 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
5589
5590 // Aggregator Reduction.
5591 "ldr r0, %[multiplicative_sum_offset]\n"
5592 "ldr r1, %[additive_sum_offset]\n"
5593 "vmov.32 d0[0], r0\n"
5594 "vdup.32 q1, r1\n"
5595 "vpaddl.u16 q8, q8\n"
5596 "vpaddl.u16 q9, q9\n"
5597 "vpaddl.u16 q10, q10\n"
5598 "vpaddl.u16 q11, q11\n"
5599 "vpaddl.u16 q12, q12\n"
5600 "vpaddl.u16 q13, q13\n"
5601 "vpaddl.u16 q14, q14\n"
5602 "vpaddl.u16 q15, q15\n"
5603 "vpadd.u32 d16, d16, d17\n"
5604 "vpadd.u32 d18, d18, d19\n"
5605 "vpadd.u32 d20, d20, d21\n"
5606 "vpadd.u32 d22, d22, d23\n"
5607 "vpadd.u32 d24, d24, d25\n"
5608 "vpadd.u32 d26, d26, d27\n"
5609 "vpadd.u32 d28, d28, d29\n"
5610 "vpadd.u32 d30, d30, d31\n"
5611 "vpadd.u32 d16, d16, d18\n"
5612 "vpadd.u32 d17, d20, d22\n"
5613 "vpadd.u32 d18, d24, d26\n"
5614 "vpadd.u32 d19, d28, d30\n"
5615 "vmul.i32 q8, q8, d0[0]\n"
5616 "vmul.i32 q9, q9, d0[0]\n"
5617 "vadd.i32 q8, q8, q1\n"
5618 "vadd.i32 q9, q9, q1\n"
5619 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
5620 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
5621 : [stride] "r"(params.stride),
5622 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
5623 [additive_sum_offset] "m"(params.additive_sum_offset)
5624 : "r0", "r1", "r2", "r3", "r4", "r5", "r6", "d0", "d1", "d2", "d3", "d4",
5625 "d5", "d6", "d7", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
5626 "d23", "d24", "d25", "d26", "d27", "d28", "d29", "d30", "d31", "cc",
5627 "memory");
5628 }
5629
5630 template <>
Pack(const uint8_t * in,const RowMajorWithSum & params,uint8_t * out)5631 inline void Stream<uint8_t, 8, 8, 7, RowMajorWithSum>::Pack(
5632 const uint8_t* in, const RowMajorWithSum& params, uint8_t* out) {
5633 #ifdef DEBUG
5634 #ifdef DEBUG_METAGEMM_VERBOSE
5635 std::cout << __FILE__ << "(" << __LINE__
5636 << ") RowMajorWithSum<uint8_t, 8, 8, 7, RowMajorWithSum>::Pack()"
5637 << std::endl
5638 << std::flush;
5639 #endif
5640 #endif
5641 int params_count_copy = params.count;
5642 asm volatile(
5643 "add r0, %[in], %[stride]\n"
5644 "add r1, r0, %[stride]\n"
5645 "add r2, r1, %[stride]\n"
5646 "add r3, r2, %[stride]\n"
5647 "add r4, r3, %[stride]\n"
5648 "add r5, r4, %[stride]\n"
5649 "add r6, r5, %[stride]\n"
5650 "vmov.i16 q8, #0\n"
5651 "vmov.i16 q9, #0\n"
5652 "vmov.i16 q10, #0\n"
5653 "vmov.i16 q11, #0\n"
5654 "vmov.i16 q12, #0\n"
5655 "vmov.i16 q13, #0\n"
5656 "vmov.i16 q14, #0\n"
5657 "vmov.i16 q15, #0\n"
5658
5659 // Reduce count by leftovers.
5660 "subs %[count], %[count], #7\n"
5661 "beq 2f\n"
5662
5663 "1:"
5664 "subs %[count], %[count], #8\n"
5665
5666 // Load Aggregate Store: 8x8.
5667 "vld1.32 {d0}, [%[in]]!\n"
5668 "vld1.32 {d1}, [r0]!\n"
5669 "vld1.32 {d2}, [r1]!\n"
5670 "vld1.32 {d3}, [r2]!\n"
5671 "vld1.32 {d4}, [r3]!\n"
5672 "vld1.32 {d5}, [r4]!\n"
5673 "vld1.32 {d6}, [r5]!\n"
5674 "vld1.32 {d7}, [r6]!\n"
5675 "vaddw.u8 q8, q8, d0\n"
5676 "vaddw.u8 q9, q9, d1\n"
5677 "vaddw.u8 q10, q10, d2\n"
5678 "vaddw.u8 q11, q11, d3\n"
5679 "vaddw.u8 q12, q12, d4\n"
5680 "vaddw.u8 q13, q13, d5\n"
5681 "vaddw.u8 q14, q14, d6\n"
5682 "vaddw.u8 q15, q15, d7\n"
5683 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
5684 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
5685
5686 "bne 1b\n"
5687
5688 "2:"
5689
5690 // Load Aggregate Store: 8x7.
5691 "vmov.i8 d0, #0\n"
5692 "vmov.i8 d1, #0\n"
5693 "vmov.i8 d2, #0\n"
5694 "vmov.i8 d3, #0\n"
5695 "vmov.i8 d4, #0\n"
5696 "vmov.i8 d5, #0\n"
5697 "vmov.i8 d6, #0\n"
5698 "vmov.i8 d7, #0\n"
5699 "vld1.32 {d0[0]}, [%[in]]!\n"
5700 "vld1.16 {d0[2]}, [%[in]]!\n"
5701 "vld1.8 {d0[6]}, [%[in]]!\n"
5702 "vld1.32 {d1[0]}, [r0]!\n"
5703 "vld1.16 {d1[2]}, [r0]!\n"
5704 "vld1.8 {d1[6]}, [r0]!\n"
5705 "vld1.32 {d2[0]}, [r1]!\n"
5706 "vld1.16 {d2[2]}, [r1]!\n"
5707 "vld1.8 {d2[6]}, [r1]!\n"
5708 "vld1.32 {d3[0]}, [r2]!\n"
5709 "vld1.16 {d3[2]}, [r2]!\n"
5710 "vld1.8 {d3[6]}, [r2]!\n"
5711 "vld1.32 {d4[0]}, [r3]!\n"
5712 "vld1.16 {d4[2]}, [r3]!\n"
5713 "vld1.8 {d4[6]}, [r3]!\n"
5714 "vld1.32 {d5[0]}, [r4]!\n"
5715 "vld1.16 {d5[2]}, [r4]!\n"
5716 "vld1.8 {d5[6]}, [r4]!\n"
5717 "vld1.32 {d6[0]}, [r5]!\n"
5718 "vld1.16 {d6[2]}, [r5]!\n"
5719 "vld1.8 {d6[6]}, [r5]!\n"
5720 "vld1.32 {d7[0]}, [r6]!\n"
5721 "vld1.16 {d7[2]}, [r6]!\n"
5722 "vld1.8 {d7[6]}, [r6]!\n"
5723 "vaddw.u8 q8, q8, d0\n"
5724 "vaddw.u8 q9, q9, d1\n"
5725 "vaddw.u8 q10, q10, d2\n"
5726 "vaddw.u8 q11, q11, d3\n"
5727 "vaddw.u8 q12, q12, d4\n"
5728 "vaddw.u8 q13, q13, d5\n"
5729 "vaddw.u8 q14, q14, d6\n"
5730 "vaddw.u8 q15, q15, d7\n"
5731 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
5732 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
5733
5734 // Aggregator Reduction.
5735 "ldr r0, %[multiplicative_sum_offset]\n"
5736 "ldr r1, %[additive_sum_offset]\n"
5737 "vmov.32 d0[0], r0\n"
5738 "vdup.32 q1, r1\n"
5739 "vpaddl.u16 q8, q8\n"
5740 "vpaddl.u16 q9, q9\n"
5741 "vpaddl.u16 q10, q10\n"
5742 "vpaddl.u16 q11, q11\n"
5743 "vpaddl.u16 q12, q12\n"
5744 "vpaddl.u16 q13, q13\n"
5745 "vpaddl.u16 q14, q14\n"
5746 "vpaddl.u16 q15, q15\n"
5747 "vpadd.u32 d16, d16, d17\n"
5748 "vpadd.u32 d18, d18, d19\n"
5749 "vpadd.u32 d20, d20, d21\n"
5750 "vpadd.u32 d22, d22, d23\n"
5751 "vpadd.u32 d24, d24, d25\n"
5752 "vpadd.u32 d26, d26, d27\n"
5753 "vpadd.u32 d28, d28, d29\n"
5754 "vpadd.u32 d30, d30, d31\n"
5755 "vpadd.u32 d16, d16, d18\n"
5756 "vpadd.u32 d17, d20, d22\n"
5757 "vpadd.u32 d18, d24, d26\n"
5758 "vpadd.u32 d19, d28, d30\n"
5759 "vmul.i32 q8, q8, d0[0]\n"
5760 "vmul.i32 q9, q9, d0[0]\n"
5761 "vadd.i32 q8, q8, q1\n"
5762 "vadd.i32 q9, q9, q1\n"
5763 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
5764 : [count] "+r"(params_count_copy), [in] "+r"(in), [out] "+r"(out)
5765 : [stride] "r"(params.stride),
5766 [multiplicative_sum_offset] "m"(params.multiplicative_sum_offset),
5767 [additive_sum_offset] "m"(params.additive_sum_offset)
5768 : "r0", "r1", "r2", "r3", "r4", "r5", "r6", "d0", "d1", "d2", "d3", "d4",
5769 "d5", "d6", "d7", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
5770 "d23", "d24", "d25", "d26", "d27", "d28", "d29", "d30", "d31", "cc",
5771 "memory");
5772 }
5773
5774 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)5775 inline void Stream<uint8_t, 1, 8, 0, ColumnMajorWithSum>::Pack(
5776 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
5777 #ifdef DEBUG
5778 #ifdef DEBUG_METAGEMM_VERBOSE
5779 std::cout
5780 << __FILE__ << "(" << __LINE__
5781 << ") ColumnMajorWithSum<uint8_t, 1, 8, 0, ColumnMajorWithSum>::Pack()"
5782 << std::endl
5783 << std::flush;
5784 #endif
5785 #endif
5786 int params_count_copy = params.count;
5787 int params_stride_copy = params.stride;
5788 asm volatile(
5789 "vmov.i16 q8, #0\n"
5790
5791 "1:"
5792 "subs %[count], %[count], #8\n"
5793
5794 // Load Aggregate Store - column major 1x8
5795 "vld1.8 {d0[0]}, [%[in]], %[stride]\n"
5796 "vld1.8 {d0[1]}, [%[in]], %[stride]\n"
5797 "vld1.8 {d0[2]}, [%[in]], %[stride]\n"
5798 "vld1.8 {d0[3]}, [%[in]], %[stride]\n"
5799 "vld1.8 {d0[4]}, [%[in]], %[stride]\n"
5800 "vld1.8 {d0[5]}, [%[in]], %[stride]\n"
5801 "vld1.8 {d0[6]}, [%[in]], %[stride]\n"
5802 "vld1.8 {d0[7]}, [%[in]], %[stride]\n"
5803 "pld [%[in]]\n"
5804 "vaddw.u8 q8, q8, d0\n"
5805 "vst1.32 {d0}, [%[out]:64]!\n"
5806
5807 "bne 1b\n"
5808
5809 // Aggregator Reduction.
5810 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
5811 "vdup.32 q1, %[additive_sum_offset]\n"
5812 "vpaddl.u16 q8, q8\n"
5813 "vpadd.u32 d16, d16, d17\n"
5814 "vpadd.u32 d16, d16, d16\n"
5815 "vmul.i32 q8, q8, d0[0]\n"
5816 "vadd.i32 q8, q8, q1\n"
5817 "vst1.32 {d16, d17}, [%[out]:64]\n"
5818 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
5819 [out] "+r"(out), [in] "+r"(in)
5820 : [additive_sum_offset] "r"(params.additive_sum_offset),
5821 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
5822 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
5823 }
5824
5825 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)5826 inline void Stream<uint8_t, 1, 8, 1, ColumnMajorWithSum>::Pack(
5827 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
5828 #ifdef DEBUG
5829 #ifdef DEBUG_METAGEMM_VERBOSE
5830 std::cout
5831 << __FILE__ << "(" << __LINE__
5832 << ") ColumnMajorWithSum<uint8_t, 1, 8, 1, ColumnMajorWithSum>::Pack()"
5833 << std::endl
5834 << std::flush;
5835 #endif
5836 #endif
5837 int params_count_copy = params.count;
5838 int params_stride_copy = params.stride;
5839 asm volatile(
5840 "vmov.i16 q8, #0\n"
5841
5842 // Reduce count by leftovers.
5843 "subs %[count], %[count], #1\n"
5844 "beq 2f\n"
5845
5846 "1:"
5847 "subs %[count], %[count], #8\n"
5848
5849 // Load Aggregate Store - column major 1x8
5850 "vld1.8 {d0[0]}, [%[in]], %[stride]\n"
5851 "vld1.8 {d0[1]}, [%[in]], %[stride]\n"
5852 "vld1.8 {d0[2]}, [%[in]], %[stride]\n"
5853 "vld1.8 {d0[3]}, [%[in]], %[stride]\n"
5854 "vld1.8 {d0[4]}, [%[in]], %[stride]\n"
5855 "vld1.8 {d0[5]}, [%[in]], %[stride]\n"
5856 "vld1.8 {d0[6]}, [%[in]], %[stride]\n"
5857 "vld1.8 {d0[7]}, [%[in]], %[stride]\n"
5858 "pld [%[in]]\n"
5859 "vaddw.u8 q8, q8, d0\n"
5860 "vst1.32 {d0}, [%[out]:64]!\n"
5861
5862 "bne 1b\n"
5863
5864 "2:"
5865
5866 // Load Aggregate Store - column major 1x1
5867 "vmov.i8 d0, #0\n"
5868 "vld1.8 {d0[0]}, [%[in]], %[stride]\n"
5869 "pld [%[in]]\n"
5870 "vaddw.u8 q8, q8, d0\n"
5871 "vst1.32 {d0}, [%[out]:64]!\n"
5872
5873 // Aggregator Reduction.
5874 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
5875 "vdup.32 q1, %[additive_sum_offset]\n"
5876 "vpaddl.u16 q8, q8\n"
5877 "vpadd.u32 d16, d16, d17\n"
5878 "vpadd.u32 d16, d16, d16\n"
5879 "vmul.i32 q8, q8, d0[0]\n"
5880 "vadd.i32 q8, q8, q1\n"
5881 "vst1.32 {d16, d17}, [%[out]:64]\n"
5882 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
5883 [out] "+r"(out), [in] "+r"(in)
5884 : [additive_sum_offset] "r"(params.additive_sum_offset),
5885 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
5886 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
5887 }
5888
5889 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)5890 inline void Stream<uint8_t, 1, 8, 2, ColumnMajorWithSum>::Pack(
5891 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
5892 #ifdef DEBUG
5893 #ifdef DEBUG_METAGEMM_VERBOSE
5894 std::cout
5895 << __FILE__ << "(" << __LINE__
5896 << ") ColumnMajorWithSum<uint8_t, 1, 8, 2, ColumnMajorWithSum>::Pack()"
5897 << std::endl
5898 << std::flush;
5899 #endif
5900 #endif
5901 int params_count_copy = params.count;
5902 int params_stride_copy = params.stride;
5903 asm volatile(
5904 "vmov.i16 q8, #0\n"
5905
5906 // Reduce count by leftovers.
5907 "subs %[count], %[count], #2\n"
5908 "beq 2f\n"
5909
5910 "1:"
5911 "subs %[count], %[count], #8\n"
5912
5913 // Load Aggregate Store - column major 1x8
5914 "vld1.8 {d0[0]}, [%[in]], %[stride]\n"
5915 "vld1.8 {d0[1]}, [%[in]], %[stride]\n"
5916 "vld1.8 {d0[2]}, [%[in]], %[stride]\n"
5917 "vld1.8 {d0[3]}, [%[in]], %[stride]\n"
5918 "vld1.8 {d0[4]}, [%[in]], %[stride]\n"
5919 "vld1.8 {d0[5]}, [%[in]], %[stride]\n"
5920 "vld1.8 {d0[6]}, [%[in]], %[stride]\n"
5921 "vld1.8 {d0[7]}, [%[in]], %[stride]\n"
5922 "pld [%[in]]\n"
5923 "vaddw.u8 q8, q8, d0\n"
5924 "vst1.32 {d0}, [%[out]:64]!\n"
5925
5926 "bne 1b\n"
5927
5928 "2:"
5929
5930 // Load Aggregate Store - column major 1x2
5931 "vmov.i8 d0, #0\n"
5932 "vld1.8 {d0[0]}, [%[in]], %[stride]\n"
5933 "vld1.8 {d0[1]}, [%[in]], %[stride]\n"
5934 "pld [%[in]]\n"
5935 "vaddw.u8 q8, q8, d0\n"
5936 "vst1.32 {d0}, [%[out]:64]!\n"
5937
5938 // Aggregator Reduction.
5939 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
5940 "vdup.32 q1, %[additive_sum_offset]\n"
5941 "vpaddl.u16 q8, q8\n"
5942 "vpadd.u32 d16, d16, d17\n"
5943 "vpadd.u32 d16, d16, d16\n"
5944 "vmul.i32 q8, q8, d0[0]\n"
5945 "vadd.i32 q8, q8, q1\n"
5946 "vst1.32 {d16, d17}, [%[out]:64]\n"
5947 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
5948 [out] "+r"(out), [in] "+r"(in)
5949 : [additive_sum_offset] "r"(params.additive_sum_offset),
5950 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
5951 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
5952 }
5953
5954 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)5955 inline void Stream<uint8_t, 1, 8, 3, ColumnMajorWithSum>::Pack(
5956 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
5957 #ifdef DEBUG
5958 #ifdef DEBUG_METAGEMM_VERBOSE
5959 std::cout
5960 << __FILE__ << "(" << __LINE__
5961 << ") ColumnMajorWithSum<uint8_t, 1, 8, 3, ColumnMajorWithSum>::Pack()"
5962 << std::endl
5963 << std::flush;
5964 #endif
5965 #endif
5966 int params_count_copy = params.count;
5967 int params_stride_copy = params.stride;
5968 asm volatile(
5969 "vmov.i16 q8, #0\n"
5970
5971 // Reduce count by leftovers.
5972 "subs %[count], %[count], #3\n"
5973 "beq 2f\n"
5974
5975 "1:"
5976 "subs %[count], %[count], #8\n"
5977
5978 // Load Aggregate Store - column major 1x8
5979 "vld1.8 {d0[0]}, [%[in]], %[stride]\n"
5980 "vld1.8 {d0[1]}, [%[in]], %[stride]\n"
5981 "vld1.8 {d0[2]}, [%[in]], %[stride]\n"
5982 "vld1.8 {d0[3]}, [%[in]], %[stride]\n"
5983 "vld1.8 {d0[4]}, [%[in]], %[stride]\n"
5984 "vld1.8 {d0[5]}, [%[in]], %[stride]\n"
5985 "vld1.8 {d0[6]}, [%[in]], %[stride]\n"
5986 "vld1.8 {d0[7]}, [%[in]], %[stride]\n"
5987 "pld [%[in]]\n"
5988 "vaddw.u8 q8, q8, d0\n"
5989 "vst1.32 {d0}, [%[out]:64]!\n"
5990
5991 "bne 1b\n"
5992
5993 "2:"
5994
5995 // Load Aggregate Store - column major 1x3
5996 "vmov.i8 d0, #0\n"
5997 "vld1.8 {d0[0]}, [%[in]], %[stride]\n"
5998 "vld1.8 {d0[1]}, [%[in]], %[stride]\n"
5999 "vld1.8 {d0[2]}, [%[in]], %[stride]\n"
6000 "pld [%[in]]\n"
6001 "vaddw.u8 q8, q8, d0\n"
6002 "vst1.32 {d0}, [%[out]:64]!\n"
6003
6004 // Aggregator Reduction.
6005 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
6006 "vdup.32 q1, %[additive_sum_offset]\n"
6007 "vpaddl.u16 q8, q8\n"
6008 "vpadd.u32 d16, d16, d17\n"
6009 "vpadd.u32 d16, d16, d16\n"
6010 "vmul.i32 q8, q8, d0[0]\n"
6011 "vadd.i32 q8, q8, q1\n"
6012 "vst1.32 {d16, d17}, [%[out]:64]\n"
6013 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
6014 [out] "+r"(out), [in] "+r"(in)
6015 : [additive_sum_offset] "r"(params.additive_sum_offset),
6016 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
6017 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
6018 }
6019
6020 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)6021 inline void Stream<uint8_t, 1, 8, 4, ColumnMajorWithSum>::Pack(
6022 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
6023 #ifdef DEBUG
6024 #ifdef DEBUG_METAGEMM_VERBOSE
6025 std::cout
6026 << __FILE__ << "(" << __LINE__
6027 << ") ColumnMajorWithSum<uint8_t, 1, 8, 4, ColumnMajorWithSum>::Pack()"
6028 << std::endl
6029 << std::flush;
6030 #endif
6031 #endif
6032 int params_count_copy = params.count;
6033 int params_stride_copy = params.stride;
6034 asm volatile(
6035 "vmov.i16 q8, #0\n"
6036
6037 // Reduce count by leftovers.
6038 "subs %[count], %[count], #4\n"
6039 "beq 2f\n"
6040
6041 "1:"
6042 "subs %[count], %[count], #8\n"
6043
6044 // Load Aggregate Store - column major 1x8
6045 "vld1.8 {d0[0]}, [%[in]], %[stride]\n"
6046 "vld1.8 {d0[1]}, [%[in]], %[stride]\n"
6047 "vld1.8 {d0[2]}, [%[in]], %[stride]\n"
6048 "vld1.8 {d0[3]}, [%[in]], %[stride]\n"
6049 "vld1.8 {d0[4]}, [%[in]], %[stride]\n"
6050 "vld1.8 {d0[5]}, [%[in]], %[stride]\n"
6051 "vld1.8 {d0[6]}, [%[in]], %[stride]\n"
6052 "vld1.8 {d0[7]}, [%[in]], %[stride]\n"
6053 "pld [%[in]]\n"
6054 "vaddw.u8 q8, q8, d0\n"
6055 "vst1.32 {d0}, [%[out]:64]!\n"
6056
6057 "bne 1b\n"
6058
6059 "2:"
6060
6061 // Load Aggregate Store - column major 1x4
6062 "vmov.i8 d0, #0\n"
6063 "vld1.8 {d0[0]}, [%[in]], %[stride]\n"
6064 "vld1.8 {d0[1]}, [%[in]], %[stride]\n"
6065 "vld1.8 {d0[2]}, [%[in]], %[stride]\n"
6066 "vld1.8 {d0[3]}, [%[in]], %[stride]\n"
6067 "pld [%[in]]\n"
6068 "vaddw.u8 q8, q8, d0\n"
6069 "vst1.32 {d0}, [%[out]:64]!\n"
6070
6071 // Aggregator Reduction.
6072 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
6073 "vdup.32 q1, %[additive_sum_offset]\n"
6074 "vpaddl.u16 q8, q8\n"
6075 "vpadd.u32 d16, d16, d17\n"
6076 "vpadd.u32 d16, d16, d16\n"
6077 "vmul.i32 q8, q8, d0[0]\n"
6078 "vadd.i32 q8, q8, q1\n"
6079 "vst1.32 {d16, d17}, [%[out]:64]\n"
6080 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
6081 [out] "+r"(out), [in] "+r"(in)
6082 : [additive_sum_offset] "r"(params.additive_sum_offset),
6083 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
6084 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
6085 }
6086
6087 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)6088 inline void Stream<uint8_t, 1, 8, 5, ColumnMajorWithSum>::Pack(
6089 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
6090 #ifdef DEBUG
6091 #ifdef DEBUG_METAGEMM_VERBOSE
6092 std::cout
6093 << __FILE__ << "(" << __LINE__
6094 << ") ColumnMajorWithSum<uint8_t, 1, 8, 5, ColumnMajorWithSum>::Pack()"
6095 << std::endl
6096 << std::flush;
6097 #endif
6098 #endif
6099 int params_count_copy = params.count;
6100 int params_stride_copy = params.stride;
6101 asm volatile(
6102 "vmov.i16 q8, #0\n"
6103
6104 // Reduce count by leftovers.
6105 "subs %[count], %[count], #5\n"
6106 "beq 2f\n"
6107
6108 "1:"
6109 "subs %[count], %[count], #8\n"
6110
6111 // Load Aggregate Store - column major 1x8
6112 "vld1.8 {d0[0]}, [%[in]], %[stride]\n"
6113 "vld1.8 {d0[1]}, [%[in]], %[stride]\n"
6114 "vld1.8 {d0[2]}, [%[in]], %[stride]\n"
6115 "vld1.8 {d0[3]}, [%[in]], %[stride]\n"
6116 "vld1.8 {d0[4]}, [%[in]], %[stride]\n"
6117 "vld1.8 {d0[5]}, [%[in]], %[stride]\n"
6118 "vld1.8 {d0[6]}, [%[in]], %[stride]\n"
6119 "vld1.8 {d0[7]}, [%[in]], %[stride]\n"
6120 "pld [%[in]]\n"
6121 "vaddw.u8 q8, q8, d0\n"
6122 "vst1.32 {d0}, [%[out]:64]!\n"
6123
6124 "bne 1b\n"
6125
6126 "2:"
6127
6128 // Load Aggregate Store - column major 1x5
6129 "vmov.i8 d0, #0\n"
6130 "vld1.8 {d0[0]}, [%[in]], %[stride]\n"
6131 "vld1.8 {d0[1]}, [%[in]], %[stride]\n"
6132 "vld1.8 {d0[2]}, [%[in]], %[stride]\n"
6133 "vld1.8 {d0[3]}, [%[in]], %[stride]\n"
6134 "vld1.8 {d0[4]}, [%[in]], %[stride]\n"
6135 "pld [%[in]]\n"
6136 "vaddw.u8 q8, q8, d0\n"
6137 "vst1.32 {d0}, [%[out]:64]!\n"
6138
6139 // Aggregator Reduction.
6140 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
6141 "vdup.32 q1, %[additive_sum_offset]\n"
6142 "vpaddl.u16 q8, q8\n"
6143 "vpadd.u32 d16, d16, d17\n"
6144 "vpadd.u32 d16, d16, d16\n"
6145 "vmul.i32 q8, q8, d0[0]\n"
6146 "vadd.i32 q8, q8, q1\n"
6147 "vst1.32 {d16, d17}, [%[out]:64]\n"
6148 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
6149 [out] "+r"(out), [in] "+r"(in)
6150 : [additive_sum_offset] "r"(params.additive_sum_offset),
6151 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
6152 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
6153 }
6154
6155 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)6156 inline void Stream<uint8_t, 1, 8, 6, ColumnMajorWithSum>::Pack(
6157 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
6158 #ifdef DEBUG
6159 #ifdef DEBUG_METAGEMM_VERBOSE
6160 std::cout
6161 << __FILE__ << "(" << __LINE__
6162 << ") ColumnMajorWithSum<uint8_t, 1, 8, 6, ColumnMajorWithSum>::Pack()"
6163 << std::endl
6164 << std::flush;
6165 #endif
6166 #endif
6167 int params_count_copy = params.count;
6168 int params_stride_copy = params.stride;
6169 asm volatile(
6170 "vmov.i16 q8, #0\n"
6171
6172 // Reduce count by leftovers.
6173 "subs %[count], %[count], #6\n"
6174 "beq 2f\n"
6175
6176 "1:"
6177 "subs %[count], %[count], #8\n"
6178
6179 // Load Aggregate Store - column major 1x8
6180 "vld1.8 {d0[0]}, [%[in]], %[stride]\n"
6181 "vld1.8 {d0[1]}, [%[in]], %[stride]\n"
6182 "vld1.8 {d0[2]}, [%[in]], %[stride]\n"
6183 "vld1.8 {d0[3]}, [%[in]], %[stride]\n"
6184 "vld1.8 {d0[4]}, [%[in]], %[stride]\n"
6185 "vld1.8 {d0[5]}, [%[in]], %[stride]\n"
6186 "vld1.8 {d0[6]}, [%[in]], %[stride]\n"
6187 "vld1.8 {d0[7]}, [%[in]], %[stride]\n"
6188 "pld [%[in]]\n"
6189 "vaddw.u8 q8, q8, d0\n"
6190 "vst1.32 {d0}, [%[out]:64]!\n"
6191
6192 "bne 1b\n"
6193
6194 "2:"
6195
6196 // Load Aggregate Store - column major 1x6
6197 "vmov.i8 d0, #0\n"
6198 "vld1.8 {d0[0]}, [%[in]], %[stride]\n"
6199 "vld1.8 {d0[1]}, [%[in]], %[stride]\n"
6200 "vld1.8 {d0[2]}, [%[in]], %[stride]\n"
6201 "vld1.8 {d0[3]}, [%[in]], %[stride]\n"
6202 "vld1.8 {d0[4]}, [%[in]], %[stride]\n"
6203 "vld1.8 {d0[5]}, [%[in]], %[stride]\n"
6204 "pld [%[in]]\n"
6205 "vaddw.u8 q8, q8, d0\n"
6206 "vst1.32 {d0}, [%[out]:64]!\n"
6207
6208 // Aggregator Reduction.
6209 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
6210 "vdup.32 q1, %[additive_sum_offset]\n"
6211 "vpaddl.u16 q8, q8\n"
6212 "vpadd.u32 d16, d16, d17\n"
6213 "vpadd.u32 d16, d16, d16\n"
6214 "vmul.i32 q8, q8, d0[0]\n"
6215 "vadd.i32 q8, q8, q1\n"
6216 "vst1.32 {d16, d17}, [%[out]:64]\n"
6217 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
6218 [out] "+r"(out), [in] "+r"(in)
6219 : [additive_sum_offset] "r"(params.additive_sum_offset),
6220 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
6221 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
6222 }
6223
6224 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)6225 inline void Stream<uint8_t, 1, 8, 7, ColumnMajorWithSum>::Pack(
6226 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
6227 #ifdef DEBUG
6228 #ifdef DEBUG_METAGEMM_VERBOSE
6229 std::cout
6230 << __FILE__ << "(" << __LINE__
6231 << ") ColumnMajorWithSum<uint8_t, 1, 8, 7, ColumnMajorWithSum>::Pack()"
6232 << std::endl
6233 << std::flush;
6234 #endif
6235 #endif
6236 int params_count_copy = params.count;
6237 int params_stride_copy = params.stride;
6238 asm volatile(
6239 "vmov.i16 q8, #0\n"
6240
6241 // Reduce count by leftovers.
6242 "subs %[count], %[count], #7\n"
6243 "beq 2f\n"
6244
6245 "1:"
6246 "subs %[count], %[count], #8\n"
6247
6248 // Load Aggregate Store - column major 1x8
6249 "vld1.8 {d0[0]}, [%[in]], %[stride]\n"
6250 "vld1.8 {d0[1]}, [%[in]], %[stride]\n"
6251 "vld1.8 {d0[2]}, [%[in]], %[stride]\n"
6252 "vld1.8 {d0[3]}, [%[in]], %[stride]\n"
6253 "vld1.8 {d0[4]}, [%[in]], %[stride]\n"
6254 "vld1.8 {d0[5]}, [%[in]], %[stride]\n"
6255 "vld1.8 {d0[6]}, [%[in]], %[stride]\n"
6256 "vld1.8 {d0[7]}, [%[in]], %[stride]\n"
6257 "pld [%[in]]\n"
6258 "vaddw.u8 q8, q8, d0\n"
6259 "vst1.32 {d0}, [%[out]:64]!\n"
6260
6261 "bne 1b\n"
6262
6263 "2:"
6264
6265 // Load Aggregate Store - column major 1x7
6266 "vmov.i8 d0, #0\n"
6267 "vld1.8 {d0[0]}, [%[in]], %[stride]\n"
6268 "vld1.8 {d0[1]}, [%[in]], %[stride]\n"
6269 "vld1.8 {d0[2]}, [%[in]], %[stride]\n"
6270 "vld1.8 {d0[3]}, [%[in]], %[stride]\n"
6271 "vld1.8 {d0[4]}, [%[in]], %[stride]\n"
6272 "vld1.8 {d0[5]}, [%[in]], %[stride]\n"
6273 "vld1.8 {d0[6]}, [%[in]], %[stride]\n"
6274 "pld [%[in]]\n"
6275 "vaddw.u8 q8, q8, d0\n"
6276 "vst1.32 {d0}, [%[out]:64]!\n"
6277
6278 // Aggregator Reduction.
6279 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
6280 "vdup.32 q1, %[additive_sum_offset]\n"
6281 "vpaddl.u16 q8, q8\n"
6282 "vpadd.u32 d16, d16, d17\n"
6283 "vpadd.u32 d16, d16, d16\n"
6284 "vmul.i32 q8, q8, d0[0]\n"
6285 "vadd.i32 q8, q8, q1\n"
6286 "vst1.32 {d16, d17}, [%[out]:64]\n"
6287 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
6288 [out] "+r"(out), [in] "+r"(in)
6289 : [additive_sum_offset] "r"(params.additive_sum_offset),
6290 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
6291 : "d0", "d2", "d3", "d16", "d17", "cc", "memory");
6292 }
6293
6294 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)6295 inline void Stream<uint8_t, 2, 8, 0, ColumnMajorWithSum>::Pack(
6296 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
6297 #ifdef DEBUG
6298 #ifdef DEBUG_METAGEMM_VERBOSE
6299 std::cout
6300 << __FILE__ << "(" << __LINE__
6301 << ") ColumnMajorWithSum<uint8_t, 2, 8, 0, ColumnMajorWithSum>::Pack()"
6302 << std::endl
6303 << std::flush;
6304 #endif
6305 #endif
6306 int params_count_copy = params.count;
6307 int params_stride_copy = params.stride;
6308 asm volatile(
6309 "vmov.i16 q8, #0\n"
6310 "vmov.i16 q9, #0\n"
6311
6312 "1:"
6313 "subs %[count], %[count], #8\n"
6314
6315 // Load Aggregate Store - column major 2x8
6316 "vld1.16 {d0[0]}, [%[in]], %[stride]\n"
6317 "vld1.16 {d0[1]}, [%[in]], %[stride]\n"
6318 "vld1.16 {d0[2]}, [%[in]], %[stride]\n"
6319 "vld1.16 {d0[3]}, [%[in]], %[stride]\n"
6320 "vld1.16 {d1[0]}, [%[in]], %[stride]\n"
6321 "vld1.16 {d1[1]}, [%[in]], %[stride]\n"
6322 "vld1.16 {d1[2]}, [%[in]], %[stride]\n"
6323 "vld1.16 {d1[3]}, [%[in]], %[stride]\n"
6324 "pld [%[in]]\n"
6325 "vuzp.8 d0, d1\n"
6326 "vaddw.u8 q8, q8, d0\n"
6327 "vaddw.u8 q9, q9, d1\n"
6328 "vst1.32 {d0, d1}, [%[out]:128]!\n"
6329
6330 "bne 1b\n"
6331
6332 // Aggregator Reduction.
6333 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
6334 "vdup.32 q1, %[additive_sum_offset]\n"
6335 "vpaddl.u16 q8, q8\n"
6336 "vpaddl.u16 q9, q9\n"
6337 "vpadd.u32 d16, d16, d17\n"
6338 "vpadd.u32 d18, d18, d19\n"
6339 "vpadd.u32 d16, d16, d18\n"
6340 "vmul.i32 q8, q8, d0[0]\n"
6341 "vadd.i32 q8, q8, q1\n"
6342 "vst1.32 {d16, d17}, [%[out]:128]\n"
6343 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
6344 [out] "+r"(out), [in] "+r"(in)
6345 : [additive_sum_offset] "r"(params.additive_sum_offset),
6346 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
6347 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc", "memory");
6348 }
6349
6350 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)6351 inline void Stream<uint8_t, 2, 8, 1, ColumnMajorWithSum>::Pack(
6352 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
6353 #ifdef DEBUG
6354 #ifdef DEBUG_METAGEMM_VERBOSE
6355 std::cout
6356 << __FILE__ << "(" << __LINE__
6357 << ") ColumnMajorWithSum<uint8_t, 2, 8, 1, ColumnMajorWithSum>::Pack()"
6358 << std::endl
6359 << std::flush;
6360 #endif
6361 #endif
6362 int params_count_copy = params.count;
6363 int params_stride_copy = params.stride;
6364 asm volatile(
6365 "vmov.i16 q8, #0\n"
6366 "vmov.i16 q9, #0\n"
6367
6368 // Reduce count by leftovers.
6369 "subs %[count], %[count], #1\n"
6370 "beq 2f\n"
6371
6372 "1:"
6373 "subs %[count], %[count], #8\n"
6374
6375 // Load Aggregate Store - column major 2x8
6376 "vld1.16 {d0[0]}, [%[in]], %[stride]\n"
6377 "vld1.16 {d0[1]}, [%[in]], %[stride]\n"
6378 "vld1.16 {d0[2]}, [%[in]], %[stride]\n"
6379 "vld1.16 {d0[3]}, [%[in]], %[stride]\n"
6380 "vld1.16 {d1[0]}, [%[in]], %[stride]\n"
6381 "vld1.16 {d1[1]}, [%[in]], %[stride]\n"
6382 "vld1.16 {d1[2]}, [%[in]], %[stride]\n"
6383 "vld1.16 {d1[3]}, [%[in]], %[stride]\n"
6384 "pld [%[in]]\n"
6385 "vuzp.8 d0, d1\n"
6386 "vaddw.u8 q8, q8, d0\n"
6387 "vaddw.u8 q9, q9, d1\n"
6388 "vst1.32 {d0, d1}, [%[out]:128]!\n"
6389
6390 "bne 1b\n"
6391
6392 "2:"
6393
6394 // Load Aggregate Store - column major 2x1
6395 "vmov.i8 d0, #0\n"
6396 "vmov.i8 d1, #0\n"
6397 "vld1.16 {d0[0]}, [%[in]], %[stride]\n"
6398 "pld [%[in]]\n"
6399 "vuzp.8 d0, d1\n"
6400 "vaddw.u8 q8, q8, d0\n"
6401 "vaddw.u8 q9, q9, d1\n"
6402 "vst1.32 {d0, d1}, [%[out]:128]!\n"
6403
6404 // Aggregator Reduction.
6405 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
6406 "vdup.32 q1, %[additive_sum_offset]\n"
6407 "vpaddl.u16 q8, q8\n"
6408 "vpaddl.u16 q9, q9\n"
6409 "vpadd.u32 d16, d16, d17\n"
6410 "vpadd.u32 d18, d18, d19\n"
6411 "vpadd.u32 d16, d16, d18\n"
6412 "vmul.i32 q8, q8, d0[0]\n"
6413 "vadd.i32 q8, q8, q1\n"
6414 "vst1.32 {d16, d17}, [%[out]:128]\n"
6415 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
6416 [out] "+r"(out), [in] "+r"(in)
6417 : [additive_sum_offset] "r"(params.additive_sum_offset),
6418 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
6419 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc", "memory");
6420 }
6421
6422 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)6423 inline void Stream<uint8_t, 2, 8, 2, ColumnMajorWithSum>::Pack(
6424 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
6425 #ifdef DEBUG
6426 #ifdef DEBUG_METAGEMM_VERBOSE
6427 std::cout
6428 << __FILE__ << "(" << __LINE__
6429 << ") ColumnMajorWithSum<uint8_t, 2, 8, 2, ColumnMajorWithSum>::Pack()"
6430 << std::endl
6431 << std::flush;
6432 #endif
6433 #endif
6434 int params_count_copy = params.count;
6435 int params_stride_copy = params.stride;
6436 asm volatile(
6437 "vmov.i16 q8, #0\n"
6438 "vmov.i16 q9, #0\n"
6439
6440 // Reduce count by leftovers.
6441 "subs %[count], %[count], #2\n"
6442 "beq 2f\n"
6443
6444 "1:"
6445 "subs %[count], %[count], #8\n"
6446
6447 // Load Aggregate Store - column major 2x8
6448 "vld1.16 {d0[0]}, [%[in]], %[stride]\n"
6449 "vld1.16 {d0[1]}, [%[in]], %[stride]\n"
6450 "vld1.16 {d0[2]}, [%[in]], %[stride]\n"
6451 "vld1.16 {d0[3]}, [%[in]], %[stride]\n"
6452 "vld1.16 {d1[0]}, [%[in]], %[stride]\n"
6453 "vld1.16 {d1[1]}, [%[in]], %[stride]\n"
6454 "vld1.16 {d1[2]}, [%[in]], %[stride]\n"
6455 "vld1.16 {d1[3]}, [%[in]], %[stride]\n"
6456 "pld [%[in]]\n"
6457 "vuzp.8 d0, d1\n"
6458 "vaddw.u8 q8, q8, d0\n"
6459 "vaddw.u8 q9, q9, d1\n"
6460 "vst1.32 {d0, d1}, [%[out]:128]!\n"
6461
6462 "bne 1b\n"
6463
6464 "2:"
6465
6466 // Load Aggregate Store - column major 2x2
6467 "vmov.i8 d0, #0\n"
6468 "vmov.i8 d1, #0\n"
6469 "vld1.16 {d0[0]}, [%[in]], %[stride]\n"
6470 "vld1.16 {d0[1]}, [%[in]], %[stride]\n"
6471 "pld [%[in]]\n"
6472 "vuzp.8 d0, d1\n"
6473 "vaddw.u8 q8, q8, d0\n"
6474 "vaddw.u8 q9, q9, d1\n"
6475 "vst1.32 {d0, d1}, [%[out]:128]!\n"
6476
6477 // Aggregator Reduction.
6478 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
6479 "vdup.32 q1, %[additive_sum_offset]\n"
6480 "vpaddl.u16 q8, q8\n"
6481 "vpaddl.u16 q9, q9\n"
6482 "vpadd.u32 d16, d16, d17\n"
6483 "vpadd.u32 d18, d18, d19\n"
6484 "vpadd.u32 d16, d16, d18\n"
6485 "vmul.i32 q8, q8, d0[0]\n"
6486 "vadd.i32 q8, q8, q1\n"
6487 "vst1.32 {d16, d17}, [%[out]:128]\n"
6488 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
6489 [out] "+r"(out), [in] "+r"(in)
6490 : [additive_sum_offset] "r"(params.additive_sum_offset),
6491 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
6492 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc", "memory");
6493 }
6494
6495 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)6496 inline void Stream<uint8_t, 2, 8, 3, ColumnMajorWithSum>::Pack(
6497 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
6498 #ifdef DEBUG
6499 #ifdef DEBUG_METAGEMM_VERBOSE
6500 std::cout
6501 << __FILE__ << "(" << __LINE__
6502 << ") ColumnMajorWithSum<uint8_t, 2, 8, 3, ColumnMajorWithSum>::Pack()"
6503 << std::endl
6504 << std::flush;
6505 #endif
6506 #endif
6507 int params_count_copy = params.count;
6508 int params_stride_copy = params.stride;
6509 asm volatile(
6510 "vmov.i16 q8, #0\n"
6511 "vmov.i16 q9, #0\n"
6512
6513 // Reduce count by leftovers.
6514 "subs %[count], %[count], #3\n"
6515 "beq 2f\n"
6516
6517 "1:"
6518 "subs %[count], %[count], #8\n"
6519
6520 // Load Aggregate Store - column major 2x8
6521 "vld1.16 {d0[0]}, [%[in]], %[stride]\n"
6522 "vld1.16 {d0[1]}, [%[in]], %[stride]\n"
6523 "vld1.16 {d0[2]}, [%[in]], %[stride]\n"
6524 "vld1.16 {d0[3]}, [%[in]], %[stride]\n"
6525 "vld1.16 {d1[0]}, [%[in]], %[stride]\n"
6526 "vld1.16 {d1[1]}, [%[in]], %[stride]\n"
6527 "vld1.16 {d1[2]}, [%[in]], %[stride]\n"
6528 "vld1.16 {d1[3]}, [%[in]], %[stride]\n"
6529 "pld [%[in]]\n"
6530 "vuzp.8 d0, d1\n"
6531 "vaddw.u8 q8, q8, d0\n"
6532 "vaddw.u8 q9, q9, d1\n"
6533 "vst1.32 {d0, d1}, [%[out]:128]!\n"
6534
6535 "bne 1b\n"
6536
6537 "2:"
6538
6539 // Load Aggregate Store - column major 2x3
6540 "vmov.i8 d0, #0\n"
6541 "vmov.i8 d1, #0\n"
6542 "vld1.16 {d0[0]}, [%[in]], %[stride]\n"
6543 "vld1.16 {d0[1]}, [%[in]], %[stride]\n"
6544 "vld1.16 {d0[2]}, [%[in]], %[stride]\n"
6545 "pld [%[in]]\n"
6546 "vuzp.8 d0, d1\n"
6547 "vaddw.u8 q8, q8, d0\n"
6548 "vaddw.u8 q9, q9, d1\n"
6549 "vst1.32 {d0, d1}, [%[out]:128]!\n"
6550
6551 // Aggregator Reduction.
6552 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
6553 "vdup.32 q1, %[additive_sum_offset]\n"
6554 "vpaddl.u16 q8, q8\n"
6555 "vpaddl.u16 q9, q9\n"
6556 "vpadd.u32 d16, d16, d17\n"
6557 "vpadd.u32 d18, d18, d19\n"
6558 "vpadd.u32 d16, d16, d18\n"
6559 "vmul.i32 q8, q8, d0[0]\n"
6560 "vadd.i32 q8, q8, q1\n"
6561 "vst1.32 {d16, d17}, [%[out]:128]\n"
6562 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
6563 [out] "+r"(out), [in] "+r"(in)
6564 : [additive_sum_offset] "r"(params.additive_sum_offset),
6565 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
6566 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc", "memory");
6567 }
6568
6569 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)6570 inline void Stream<uint8_t, 2, 8, 4, ColumnMajorWithSum>::Pack(
6571 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
6572 #ifdef DEBUG
6573 #ifdef DEBUG_METAGEMM_VERBOSE
6574 std::cout
6575 << __FILE__ << "(" << __LINE__
6576 << ") ColumnMajorWithSum<uint8_t, 2, 8, 4, ColumnMajorWithSum>::Pack()"
6577 << std::endl
6578 << std::flush;
6579 #endif
6580 #endif
6581 int params_count_copy = params.count;
6582 int params_stride_copy = params.stride;
6583 asm volatile(
6584 "vmov.i16 q8, #0\n"
6585 "vmov.i16 q9, #0\n"
6586
6587 // Reduce count by leftovers.
6588 "subs %[count], %[count], #4\n"
6589 "beq 2f\n"
6590
6591 "1:"
6592 "subs %[count], %[count], #8\n"
6593
6594 // Load Aggregate Store - column major 2x8
6595 "vld1.16 {d0[0]}, [%[in]], %[stride]\n"
6596 "vld1.16 {d0[1]}, [%[in]], %[stride]\n"
6597 "vld1.16 {d0[2]}, [%[in]], %[stride]\n"
6598 "vld1.16 {d0[3]}, [%[in]], %[stride]\n"
6599 "vld1.16 {d1[0]}, [%[in]], %[stride]\n"
6600 "vld1.16 {d1[1]}, [%[in]], %[stride]\n"
6601 "vld1.16 {d1[2]}, [%[in]], %[stride]\n"
6602 "vld1.16 {d1[3]}, [%[in]], %[stride]\n"
6603 "pld [%[in]]\n"
6604 "vuzp.8 d0, d1\n"
6605 "vaddw.u8 q8, q8, d0\n"
6606 "vaddw.u8 q9, q9, d1\n"
6607 "vst1.32 {d0, d1}, [%[out]:128]!\n"
6608
6609 "bne 1b\n"
6610
6611 "2:"
6612
6613 // Load Aggregate Store - column major 2x4
6614 "vmov.i8 d0, #0\n"
6615 "vmov.i8 d1, #0\n"
6616 "vld1.16 {d0[0]}, [%[in]], %[stride]\n"
6617 "vld1.16 {d0[1]}, [%[in]], %[stride]\n"
6618 "vld1.16 {d0[2]}, [%[in]], %[stride]\n"
6619 "vld1.16 {d0[3]}, [%[in]], %[stride]\n"
6620 "pld [%[in]]\n"
6621 "vuzp.8 d0, d1\n"
6622 "vaddw.u8 q8, q8, d0\n"
6623 "vaddw.u8 q9, q9, d1\n"
6624 "vst1.32 {d0, d1}, [%[out]:128]!\n"
6625
6626 // Aggregator Reduction.
6627 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
6628 "vdup.32 q1, %[additive_sum_offset]\n"
6629 "vpaddl.u16 q8, q8\n"
6630 "vpaddl.u16 q9, q9\n"
6631 "vpadd.u32 d16, d16, d17\n"
6632 "vpadd.u32 d18, d18, d19\n"
6633 "vpadd.u32 d16, d16, d18\n"
6634 "vmul.i32 q8, q8, d0[0]\n"
6635 "vadd.i32 q8, q8, q1\n"
6636 "vst1.32 {d16, d17}, [%[out]:128]\n"
6637 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
6638 [out] "+r"(out), [in] "+r"(in)
6639 : [additive_sum_offset] "r"(params.additive_sum_offset),
6640 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
6641 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc", "memory");
6642 }
6643
6644 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)6645 inline void Stream<uint8_t, 2, 8, 5, ColumnMajorWithSum>::Pack(
6646 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
6647 #ifdef DEBUG
6648 #ifdef DEBUG_METAGEMM_VERBOSE
6649 std::cout
6650 << __FILE__ << "(" << __LINE__
6651 << ") ColumnMajorWithSum<uint8_t, 2, 8, 5, ColumnMajorWithSum>::Pack()"
6652 << std::endl
6653 << std::flush;
6654 #endif
6655 #endif
6656 int params_count_copy = params.count;
6657 int params_stride_copy = params.stride;
6658 asm volatile(
6659 "vmov.i16 q8, #0\n"
6660 "vmov.i16 q9, #0\n"
6661
6662 // Reduce count by leftovers.
6663 "subs %[count], %[count], #5\n"
6664 "beq 2f\n"
6665
6666 "1:"
6667 "subs %[count], %[count], #8\n"
6668
6669 // Load Aggregate Store - column major 2x8
6670 "vld1.16 {d0[0]}, [%[in]], %[stride]\n"
6671 "vld1.16 {d0[1]}, [%[in]], %[stride]\n"
6672 "vld1.16 {d0[2]}, [%[in]], %[stride]\n"
6673 "vld1.16 {d0[3]}, [%[in]], %[stride]\n"
6674 "vld1.16 {d1[0]}, [%[in]], %[stride]\n"
6675 "vld1.16 {d1[1]}, [%[in]], %[stride]\n"
6676 "vld1.16 {d1[2]}, [%[in]], %[stride]\n"
6677 "vld1.16 {d1[3]}, [%[in]], %[stride]\n"
6678 "pld [%[in]]\n"
6679 "vuzp.8 d0, d1\n"
6680 "vaddw.u8 q8, q8, d0\n"
6681 "vaddw.u8 q9, q9, d1\n"
6682 "vst1.32 {d0, d1}, [%[out]:128]!\n"
6683
6684 "bne 1b\n"
6685
6686 "2:"
6687
6688 // Load Aggregate Store - column major 2x5
6689 "vmov.i8 d0, #0\n"
6690 "vmov.i8 d1, #0\n"
6691 "vld1.16 {d0[0]}, [%[in]], %[stride]\n"
6692 "vld1.16 {d0[1]}, [%[in]], %[stride]\n"
6693 "vld1.16 {d0[2]}, [%[in]], %[stride]\n"
6694 "vld1.16 {d0[3]}, [%[in]], %[stride]\n"
6695 "vld1.16 {d1[0]}, [%[in]], %[stride]\n"
6696 "pld [%[in]]\n"
6697 "vuzp.8 d0, d1\n"
6698 "vaddw.u8 q8, q8, d0\n"
6699 "vaddw.u8 q9, q9, d1\n"
6700 "vst1.32 {d0, d1}, [%[out]:128]!\n"
6701
6702 // Aggregator Reduction.
6703 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
6704 "vdup.32 q1, %[additive_sum_offset]\n"
6705 "vpaddl.u16 q8, q8\n"
6706 "vpaddl.u16 q9, q9\n"
6707 "vpadd.u32 d16, d16, d17\n"
6708 "vpadd.u32 d18, d18, d19\n"
6709 "vpadd.u32 d16, d16, d18\n"
6710 "vmul.i32 q8, q8, d0[0]\n"
6711 "vadd.i32 q8, q8, q1\n"
6712 "vst1.32 {d16, d17}, [%[out]:128]\n"
6713 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
6714 [out] "+r"(out), [in] "+r"(in)
6715 : [additive_sum_offset] "r"(params.additive_sum_offset),
6716 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
6717 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc", "memory");
6718 }
6719
6720 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)6721 inline void Stream<uint8_t, 2, 8, 6, ColumnMajorWithSum>::Pack(
6722 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
6723 #ifdef DEBUG
6724 #ifdef DEBUG_METAGEMM_VERBOSE
6725 std::cout
6726 << __FILE__ << "(" << __LINE__
6727 << ") ColumnMajorWithSum<uint8_t, 2, 8, 6, ColumnMajorWithSum>::Pack()"
6728 << std::endl
6729 << std::flush;
6730 #endif
6731 #endif
6732 int params_count_copy = params.count;
6733 int params_stride_copy = params.stride;
6734 asm volatile(
6735 "vmov.i16 q8, #0\n"
6736 "vmov.i16 q9, #0\n"
6737
6738 // Reduce count by leftovers.
6739 "subs %[count], %[count], #6\n"
6740 "beq 2f\n"
6741
6742 "1:"
6743 "subs %[count], %[count], #8\n"
6744
6745 // Load Aggregate Store - column major 2x8
6746 "vld1.16 {d0[0]}, [%[in]], %[stride]\n"
6747 "vld1.16 {d0[1]}, [%[in]], %[stride]\n"
6748 "vld1.16 {d0[2]}, [%[in]], %[stride]\n"
6749 "vld1.16 {d0[3]}, [%[in]], %[stride]\n"
6750 "vld1.16 {d1[0]}, [%[in]], %[stride]\n"
6751 "vld1.16 {d1[1]}, [%[in]], %[stride]\n"
6752 "vld1.16 {d1[2]}, [%[in]], %[stride]\n"
6753 "vld1.16 {d1[3]}, [%[in]], %[stride]\n"
6754 "pld [%[in]]\n"
6755 "vuzp.8 d0, d1\n"
6756 "vaddw.u8 q8, q8, d0\n"
6757 "vaddw.u8 q9, q9, d1\n"
6758 "vst1.32 {d0, d1}, [%[out]:128]!\n"
6759
6760 "bne 1b\n"
6761
6762 "2:"
6763
6764 // Load Aggregate Store - column major 2x6
6765 "vmov.i8 d0, #0\n"
6766 "vmov.i8 d1, #0\n"
6767 "vld1.16 {d0[0]}, [%[in]], %[stride]\n"
6768 "vld1.16 {d0[1]}, [%[in]], %[stride]\n"
6769 "vld1.16 {d0[2]}, [%[in]], %[stride]\n"
6770 "vld1.16 {d0[3]}, [%[in]], %[stride]\n"
6771 "vld1.16 {d1[0]}, [%[in]], %[stride]\n"
6772 "vld1.16 {d1[1]}, [%[in]], %[stride]\n"
6773 "pld [%[in]]\n"
6774 "vuzp.8 d0, d1\n"
6775 "vaddw.u8 q8, q8, d0\n"
6776 "vaddw.u8 q9, q9, d1\n"
6777 "vst1.32 {d0, d1}, [%[out]:128]!\n"
6778
6779 // Aggregator Reduction.
6780 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
6781 "vdup.32 q1, %[additive_sum_offset]\n"
6782 "vpaddl.u16 q8, q8\n"
6783 "vpaddl.u16 q9, q9\n"
6784 "vpadd.u32 d16, d16, d17\n"
6785 "vpadd.u32 d18, d18, d19\n"
6786 "vpadd.u32 d16, d16, d18\n"
6787 "vmul.i32 q8, q8, d0[0]\n"
6788 "vadd.i32 q8, q8, q1\n"
6789 "vst1.32 {d16, d17}, [%[out]:128]\n"
6790 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
6791 [out] "+r"(out), [in] "+r"(in)
6792 : [additive_sum_offset] "r"(params.additive_sum_offset),
6793 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
6794 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc", "memory");
6795 }
6796
6797 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)6798 inline void Stream<uint8_t, 2, 8, 7, ColumnMajorWithSum>::Pack(
6799 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
6800 #ifdef DEBUG
6801 #ifdef DEBUG_METAGEMM_VERBOSE
6802 std::cout
6803 << __FILE__ << "(" << __LINE__
6804 << ") ColumnMajorWithSum<uint8_t, 2, 8, 7, ColumnMajorWithSum>::Pack()"
6805 << std::endl
6806 << std::flush;
6807 #endif
6808 #endif
6809 int params_count_copy = params.count;
6810 int params_stride_copy = params.stride;
6811 asm volatile(
6812 "vmov.i16 q8, #0\n"
6813 "vmov.i16 q9, #0\n"
6814
6815 // Reduce count by leftovers.
6816 "subs %[count], %[count], #7\n"
6817 "beq 2f\n"
6818
6819 "1:"
6820 "subs %[count], %[count], #8\n"
6821
6822 // Load Aggregate Store - column major 2x8
6823 "vld1.16 {d0[0]}, [%[in]], %[stride]\n"
6824 "vld1.16 {d0[1]}, [%[in]], %[stride]\n"
6825 "vld1.16 {d0[2]}, [%[in]], %[stride]\n"
6826 "vld1.16 {d0[3]}, [%[in]], %[stride]\n"
6827 "vld1.16 {d1[0]}, [%[in]], %[stride]\n"
6828 "vld1.16 {d1[1]}, [%[in]], %[stride]\n"
6829 "vld1.16 {d1[2]}, [%[in]], %[stride]\n"
6830 "vld1.16 {d1[3]}, [%[in]], %[stride]\n"
6831 "pld [%[in]]\n"
6832 "vuzp.8 d0, d1\n"
6833 "vaddw.u8 q8, q8, d0\n"
6834 "vaddw.u8 q9, q9, d1\n"
6835 "vst1.32 {d0, d1}, [%[out]:128]!\n"
6836
6837 "bne 1b\n"
6838
6839 "2:"
6840
6841 // Load Aggregate Store - column major 2x7
6842 "vmov.i8 d0, #0\n"
6843 "vmov.i8 d1, #0\n"
6844 "vld1.16 {d0[0]}, [%[in]], %[stride]\n"
6845 "vld1.16 {d0[1]}, [%[in]], %[stride]\n"
6846 "vld1.16 {d0[2]}, [%[in]], %[stride]\n"
6847 "vld1.16 {d0[3]}, [%[in]], %[stride]\n"
6848 "vld1.16 {d1[0]}, [%[in]], %[stride]\n"
6849 "vld1.16 {d1[1]}, [%[in]], %[stride]\n"
6850 "vld1.16 {d1[2]}, [%[in]], %[stride]\n"
6851 "pld [%[in]]\n"
6852 "vuzp.8 d0, d1\n"
6853 "vaddw.u8 q8, q8, d0\n"
6854 "vaddw.u8 q9, q9, d1\n"
6855 "vst1.32 {d0, d1}, [%[out]:128]!\n"
6856
6857 // Aggregator Reduction.
6858 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
6859 "vdup.32 q1, %[additive_sum_offset]\n"
6860 "vpaddl.u16 q8, q8\n"
6861 "vpaddl.u16 q9, q9\n"
6862 "vpadd.u32 d16, d16, d17\n"
6863 "vpadd.u32 d18, d18, d19\n"
6864 "vpadd.u32 d16, d16, d18\n"
6865 "vmul.i32 q8, q8, d0[0]\n"
6866 "vadd.i32 q8, q8, q1\n"
6867 "vst1.32 {d16, d17}, [%[out]:128]\n"
6868 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
6869 [out] "+r"(out), [in] "+r"(in)
6870 : [additive_sum_offset] "r"(params.additive_sum_offset),
6871 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
6872 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "cc", "memory");
6873 }
6874
6875 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)6876 inline void Stream<uint8_t, 3, 8, 0, ColumnMajorWithSum>::Pack(
6877 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
6878 #ifdef DEBUG
6879 #ifdef DEBUG_METAGEMM_VERBOSE
6880 std::cout
6881 << __FILE__ << "(" << __LINE__
6882 << ") ColumnMajorWithSum<uint8_t, 3, 8, 0, ColumnMajorWithSum>::Pack()"
6883 << std::endl
6884 << std::flush;
6885 #endif
6886 #endif
6887 int params_count_copy = params.count;
6888 int params_stride_copy = params.stride;
6889 asm volatile(
6890 "vmov.i16 q8, #0\n"
6891 "vmov.i16 q9, #0\n"
6892 "vmov.i16 q10, #0\n"
6893
6894 "1:"
6895 "subs %[count], %[count], #8\n"
6896
6897 // Load Aggregate Store - column major 3x8
6898 "vld3.8 {d0[0], d1[0], d2[0]}, [%[in]], %[stride]\n"
6899 "vld3.8 {d0[1], d1[1], d2[1]}, [%[in]], %[stride]\n"
6900 "vld3.8 {d0[2], d1[2], d2[2]}, [%[in]], %[stride]\n"
6901 "vld3.8 {d0[3], d1[3], d2[3]}, [%[in]], %[stride]\n"
6902 "vld3.8 {d0[4], d1[4], d2[4]}, [%[in]], %[stride]\n"
6903 "vld3.8 {d0[5], d1[5], d2[5]}, [%[in]], %[stride]\n"
6904 "vld3.8 {d0[6], d1[6], d2[6]}, [%[in]], %[stride]\n"
6905 "vld3.8 {d0[7], d1[7], d2[7]}, [%[in]], %[stride]\n"
6906 "vaddw.u8 q8, q8, d0\n"
6907 "vaddw.u8 q9, q9, d1\n"
6908 "vaddw.u8 q10, q10, d2\n"
6909 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
6910
6911 "bne 1b\n"
6912
6913 // Aggregator Reduction.
6914 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
6915 "vdup.32 q1, %[additive_sum_offset]\n"
6916 "vpaddl.u16 q8, q8\n"
6917 "vpaddl.u16 q9, q9\n"
6918 "vpaddl.u16 q10, q10\n"
6919 "vpadd.u32 d16, d16, d17\n"
6920 "vpadd.u32 d18, d18, d19\n"
6921 "vpadd.u32 d20, d20, d21\n"
6922 "vpadd.u32 d16, d16, d18\n"
6923 "vpadd.u32 d17, d20, d20\n"
6924 "vmul.i32 q8, q8, d0[0]\n"
6925 "vadd.i32 q8, q8, q1\n"
6926 "vst1.32 {d16, d17}, [%[out]:64]\n"
6927 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
6928 [out] "+r"(out), [in] "+r"(in)
6929 : [additive_sum_offset] "r"(params.additive_sum_offset),
6930 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
6931 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "cc",
6932 "memory");
6933 }
6934
6935 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)6936 inline void Stream<uint8_t, 3, 8, 1, ColumnMajorWithSum>::Pack(
6937 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
6938 #ifdef DEBUG
6939 #ifdef DEBUG_METAGEMM_VERBOSE
6940 std::cout
6941 << __FILE__ << "(" << __LINE__
6942 << ") ColumnMajorWithSum<uint8_t, 3, 8, 1, ColumnMajorWithSum>::Pack()"
6943 << std::endl
6944 << std::flush;
6945 #endif
6946 #endif
6947 int params_count_copy = params.count;
6948 int params_stride_copy = params.stride;
6949 asm volatile(
6950 "vmov.i16 q8, #0\n"
6951 "vmov.i16 q9, #0\n"
6952 "vmov.i16 q10, #0\n"
6953
6954 // Reduce count by leftovers.
6955 "subs %[count], %[count], #1\n"
6956 "beq 2f\n"
6957
6958 "1:"
6959 "subs %[count], %[count], #8\n"
6960
6961 // Load Aggregate Store - column major 3x8
6962 "vld3.8 {d0[0], d1[0], d2[0]}, [%[in]], %[stride]\n"
6963 "vld3.8 {d0[1], d1[1], d2[1]}, [%[in]], %[stride]\n"
6964 "vld3.8 {d0[2], d1[2], d2[2]}, [%[in]], %[stride]\n"
6965 "vld3.8 {d0[3], d1[3], d2[3]}, [%[in]], %[stride]\n"
6966 "vld3.8 {d0[4], d1[4], d2[4]}, [%[in]], %[stride]\n"
6967 "vld3.8 {d0[5], d1[5], d2[5]}, [%[in]], %[stride]\n"
6968 "vld3.8 {d0[6], d1[6], d2[6]}, [%[in]], %[stride]\n"
6969 "vld3.8 {d0[7], d1[7], d2[7]}, [%[in]], %[stride]\n"
6970 "vaddw.u8 q8, q8, d0\n"
6971 "vaddw.u8 q9, q9, d1\n"
6972 "vaddw.u8 q10, q10, d2\n"
6973 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
6974
6975 "bne 1b\n"
6976
6977 "2:"
6978
6979 // Load Aggregate Store - column major 3x1
6980 "vmov.i8 d0, #0\n"
6981 "vmov.i8 d1, #0\n"
6982 "vmov.i8 d2, #0\n"
6983 "vld3.8 {d0[0], d1[0], d2[0]}, [%[in]], %[stride]\n"
6984 "vaddw.u8 q8, q8, d0\n"
6985 "vaddw.u8 q9, q9, d1\n"
6986 "vaddw.u8 q10, q10, d2\n"
6987 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
6988
6989 // Aggregator Reduction.
6990 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
6991 "vdup.32 q1, %[additive_sum_offset]\n"
6992 "vpaddl.u16 q8, q8\n"
6993 "vpaddl.u16 q9, q9\n"
6994 "vpaddl.u16 q10, q10\n"
6995 "vpadd.u32 d16, d16, d17\n"
6996 "vpadd.u32 d18, d18, d19\n"
6997 "vpadd.u32 d20, d20, d21\n"
6998 "vpadd.u32 d16, d16, d18\n"
6999 "vpadd.u32 d17, d20, d20\n"
7000 "vmul.i32 q8, q8, d0[0]\n"
7001 "vadd.i32 q8, q8, q1\n"
7002 "vst1.32 {d16, d17}, [%[out]:64]\n"
7003 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
7004 [out] "+r"(out), [in] "+r"(in)
7005 : [additive_sum_offset] "r"(params.additive_sum_offset),
7006 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
7007 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "cc",
7008 "memory");
7009 }
7010
7011 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)7012 inline void Stream<uint8_t, 3, 8, 2, ColumnMajorWithSum>::Pack(
7013 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
7014 #ifdef DEBUG
7015 #ifdef DEBUG_METAGEMM_VERBOSE
7016 std::cout
7017 << __FILE__ << "(" << __LINE__
7018 << ") ColumnMajorWithSum<uint8_t, 3, 8, 2, ColumnMajorWithSum>::Pack()"
7019 << std::endl
7020 << std::flush;
7021 #endif
7022 #endif
7023 int params_count_copy = params.count;
7024 int params_stride_copy = params.stride;
7025 asm volatile(
7026 "vmov.i16 q8, #0\n"
7027 "vmov.i16 q9, #0\n"
7028 "vmov.i16 q10, #0\n"
7029
7030 // Reduce count by leftovers.
7031 "subs %[count], %[count], #2\n"
7032 "beq 2f\n"
7033
7034 "1:"
7035 "subs %[count], %[count], #8\n"
7036
7037 // Load Aggregate Store - column major 3x8
7038 "vld3.8 {d0[0], d1[0], d2[0]}, [%[in]], %[stride]\n"
7039 "vld3.8 {d0[1], d1[1], d2[1]}, [%[in]], %[stride]\n"
7040 "vld3.8 {d0[2], d1[2], d2[2]}, [%[in]], %[stride]\n"
7041 "vld3.8 {d0[3], d1[3], d2[3]}, [%[in]], %[stride]\n"
7042 "vld3.8 {d0[4], d1[4], d2[4]}, [%[in]], %[stride]\n"
7043 "vld3.8 {d0[5], d1[5], d2[5]}, [%[in]], %[stride]\n"
7044 "vld3.8 {d0[6], d1[6], d2[6]}, [%[in]], %[stride]\n"
7045 "vld3.8 {d0[7], d1[7], d2[7]}, [%[in]], %[stride]\n"
7046 "vaddw.u8 q8, q8, d0\n"
7047 "vaddw.u8 q9, q9, d1\n"
7048 "vaddw.u8 q10, q10, d2\n"
7049 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
7050
7051 "bne 1b\n"
7052
7053 "2:"
7054
7055 // Load Aggregate Store - column major 3x2
7056 "vmov.i8 d0, #0\n"
7057 "vmov.i8 d1, #0\n"
7058 "vmov.i8 d2, #0\n"
7059 "vld3.8 {d0[0], d1[0], d2[0]}, [%[in]], %[stride]\n"
7060 "vld3.8 {d0[1], d1[1], d2[1]}, [%[in]], %[stride]\n"
7061 "vaddw.u8 q8, q8, d0\n"
7062 "vaddw.u8 q9, q9, d1\n"
7063 "vaddw.u8 q10, q10, d2\n"
7064 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
7065
7066 // Aggregator Reduction.
7067 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
7068 "vdup.32 q1, %[additive_sum_offset]\n"
7069 "vpaddl.u16 q8, q8\n"
7070 "vpaddl.u16 q9, q9\n"
7071 "vpaddl.u16 q10, q10\n"
7072 "vpadd.u32 d16, d16, d17\n"
7073 "vpadd.u32 d18, d18, d19\n"
7074 "vpadd.u32 d20, d20, d21\n"
7075 "vpadd.u32 d16, d16, d18\n"
7076 "vpadd.u32 d17, d20, d20\n"
7077 "vmul.i32 q8, q8, d0[0]\n"
7078 "vadd.i32 q8, q8, q1\n"
7079 "vst1.32 {d16, d17}, [%[out]:64]\n"
7080 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
7081 [out] "+r"(out), [in] "+r"(in)
7082 : [additive_sum_offset] "r"(params.additive_sum_offset),
7083 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
7084 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "cc",
7085 "memory");
7086 }
7087
7088 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)7089 inline void Stream<uint8_t, 3, 8, 3, ColumnMajorWithSum>::Pack(
7090 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
7091 #ifdef DEBUG
7092 #ifdef DEBUG_METAGEMM_VERBOSE
7093 std::cout
7094 << __FILE__ << "(" << __LINE__
7095 << ") ColumnMajorWithSum<uint8_t, 3, 8, 3, ColumnMajorWithSum>::Pack()"
7096 << std::endl
7097 << std::flush;
7098 #endif
7099 #endif
7100 int params_count_copy = params.count;
7101 int params_stride_copy = params.stride;
7102 asm volatile(
7103 "vmov.i16 q8, #0\n"
7104 "vmov.i16 q9, #0\n"
7105 "vmov.i16 q10, #0\n"
7106
7107 // Reduce count by leftovers.
7108 "subs %[count], %[count], #3\n"
7109 "beq 2f\n"
7110
7111 "1:"
7112 "subs %[count], %[count], #8\n"
7113
7114 // Load Aggregate Store - column major 3x8
7115 "vld3.8 {d0[0], d1[0], d2[0]}, [%[in]], %[stride]\n"
7116 "vld3.8 {d0[1], d1[1], d2[1]}, [%[in]], %[stride]\n"
7117 "vld3.8 {d0[2], d1[2], d2[2]}, [%[in]], %[stride]\n"
7118 "vld3.8 {d0[3], d1[3], d2[3]}, [%[in]], %[stride]\n"
7119 "vld3.8 {d0[4], d1[4], d2[4]}, [%[in]], %[stride]\n"
7120 "vld3.8 {d0[5], d1[5], d2[5]}, [%[in]], %[stride]\n"
7121 "vld3.8 {d0[6], d1[6], d2[6]}, [%[in]], %[stride]\n"
7122 "vld3.8 {d0[7], d1[7], d2[7]}, [%[in]], %[stride]\n"
7123 "vaddw.u8 q8, q8, d0\n"
7124 "vaddw.u8 q9, q9, d1\n"
7125 "vaddw.u8 q10, q10, d2\n"
7126 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
7127
7128 "bne 1b\n"
7129
7130 "2:"
7131
7132 // Load Aggregate Store - column major 3x3
7133 "vmov.i8 d0, #0\n"
7134 "vmov.i8 d1, #0\n"
7135 "vmov.i8 d2, #0\n"
7136 "vld3.8 {d0[0], d1[0], d2[0]}, [%[in]], %[stride]\n"
7137 "vld3.8 {d0[1], d1[1], d2[1]}, [%[in]], %[stride]\n"
7138 "vld3.8 {d0[2], d1[2], d2[2]}, [%[in]], %[stride]\n"
7139 "vaddw.u8 q8, q8, d0\n"
7140 "vaddw.u8 q9, q9, d1\n"
7141 "vaddw.u8 q10, q10, d2\n"
7142 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
7143
7144 // Aggregator Reduction.
7145 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
7146 "vdup.32 q1, %[additive_sum_offset]\n"
7147 "vpaddl.u16 q8, q8\n"
7148 "vpaddl.u16 q9, q9\n"
7149 "vpaddl.u16 q10, q10\n"
7150 "vpadd.u32 d16, d16, d17\n"
7151 "vpadd.u32 d18, d18, d19\n"
7152 "vpadd.u32 d20, d20, d21\n"
7153 "vpadd.u32 d16, d16, d18\n"
7154 "vpadd.u32 d17, d20, d20\n"
7155 "vmul.i32 q8, q8, d0[0]\n"
7156 "vadd.i32 q8, q8, q1\n"
7157 "vst1.32 {d16, d17}, [%[out]:64]\n"
7158 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
7159 [out] "+r"(out), [in] "+r"(in)
7160 : [additive_sum_offset] "r"(params.additive_sum_offset),
7161 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
7162 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "cc",
7163 "memory");
7164 }
7165
7166 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)7167 inline void Stream<uint8_t, 3, 8, 4, ColumnMajorWithSum>::Pack(
7168 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
7169 #ifdef DEBUG
7170 #ifdef DEBUG_METAGEMM_VERBOSE
7171 std::cout
7172 << __FILE__ << "(" << __LINE__
7173 << ") ColumnMajorWithSum<uint8_t, 3, 8, 4, ColumnMajorWithSum>::Pack()"
7174 << std::endl
7175 << std::flush;
7176 #endif
7177 #endif
7178 int params_count_copy = params.count;
7179 int params_stride_copy = params.stride;
7180 asm volatile(
7181 "vmov.i16 q8, #0\n"
7182 "vmov.i16 q9, #0\n"
7183 "vmov.i16 q10, #0\n"
7184
7185 // Reduce count by leftovers.
7186 "subs %[count], %[count], #4\n"
7187 "beq 2f\n"
7188
7189 "1:"
7190 "subs %[count], %[count], #8\n"
7191
7192 // Load Aggregate Store - column major 3x8
7193 "vld3.8 {d0[0], d1[0], d2[0]}, [%[in]], %[stride]\n"
7194 "vld3.8 {d0[1], d1[1], d2[1]}, [%[in]], %[stride]\n"
7195 "vld3.8 {d0[2], d1[2], d2[2]}, [%[in]], %[stride]\n"
7196 "vld3.8 {d0[3], d1[3], d2[3]}, [%[in]], %[stride]\n"
7197 "vld3.8 {d0[4], d1[4], d2[4]}, [%[in]], %[stride]\n"
7198 "vld3.8 {d0[5], d1[5], d2[5]}, [%[in]], %[stride]\n"
7199 "vld3.8 {d0[6], d1[6], d2[6]}, [%[in]], %[stride]\n"
7200 "vld3.8 {d0[7], d1[7], d2[7]}, [%[in]], %[stride]\n"
7201 "vaddw.u8 q8, q8, d0\n"
7202 "vaddw.u8 q9, q9, d1\n"
7203 "vaddw.u8 q10, q10, d2\n"
7204 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
7205
7206 "bne 1b\n"
7207
7208 "2:"
7209
7210 // Load Aggregate Store - column major 3x4
7211 "vmov.i8 d0, #0\n"
7212 "vmov.i8 d1, #0\n"
7213 "vmov.i8 d2, #0\n"
7214 "vld3.8 {d0[0], d1[0], d2[0]}, [%[in]], %[stride]\n"
7215 "vld3.8 {d0[1], d1[1], d2[1]}, [%[in]], %[stride]\n"
7216 "vld3.8 {d0[2], d1[2], d2[2]}, [%[in]], %[stride]\n"
7217 "vld3.8 {d0[3], d1[3], d2[3]}, [%[in]], %[stride]\n"
7218 "vaddw.u8 q8, q8, d0\n"
7219 "vaddw.u8 q9, q9, d1\n"
7220 "vaddw.u8 q10, q10, d2\n"
7221 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
7222
7223 // Aggregator Reduction.
7224 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
7225 "vdup.32 q1, %[additive_sum_offset]\n"
7226 "vpaddl.u16 q8, q8\n"
7227 "vpaddl.u16 q9, q9\n"
7228 "vpaddl.u16 q10, q10\n"
7229 "vpadd.u32 d16, d16, d17\n"
7230 "vpadd.u32 d18, d18, d19\n"
7231 "vpadd.u32 d20, d20, d21\n"
7232 "vpadd.u32 d16, d16, d18\n"
7233 "vpadd.u32 d17, d20, d20\n"
7234 "vmul.i32 q8, q8, d0[0]\n"
7235 "vadd.i32 q8, q8, q1\n"
7236 "vst1.32 {d16, d17}, [%[out]:64]\n"
7237 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
7238 [out] "+r"(out), [in] "+r"(in)
7239 : [additive_sum_offset] "r"(params.additive_sum_offset),
7240 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
7241 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "cc",
7242 "memory");
7243 }
7244
7245 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)7246 inline void Stream<uint8_t, 3, 8, 5, ColumnMajorWithSum>::Pack(
7247 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
7248 #ifdef DEBUG
7249 #ifdef DEBUG_METAGEMM_VERBOSE
7250 std::cout
7251 << __FILE__ << "(" << __LINE__
7252 << ") ColumnMajorWithSum<uint8_t, 3, 8, 5, ColumnMajorWithSum>::Pack()"
7253 << std::endl
7254 << std::flush;
7255 #endif
7256 #endif
7257 int params_count_copy = params.count;
7258 int params_stride_copy = params.stride;
7259 asm volatile(
7260 "vmov.i16 q8, #0\n"
7261 "vmov.i16 q9, #0\n"
7262 "vmov.i16 q10, #0\n"
7263
7264 // Reduce count by leftovers.
7265 "subs %[count], %[count], #5\n"
7266 "beq 2f\n"
7267
7268 "1:"
7269 "subs %[count], %[count], #8\n"
7270
7271 // Load Aggregate Store - column major 3x8
7272 "vld3.8 {d0[0], d1[0], d2[0]}, [%[in]], %[stride]\n"
7273 "vld3.8 {d0[1], d1[1], d2[1]}, [%[in]], %[stride]\n"
7274 "vld3.8 {d0[2], d1[2], d2[2]}, [%[in]], %[stride]\n"
7275 "vld3.8 {d0[3], d1[3], d2[3]}, [%[in]], %[stride]\n"
7276 "vld3.8 {d0[4], d1[4], d2[4]}, [%[in]], %[stride]\n"
7277 "vld3.8 {d0[5], d1[5], d2[5]}, [%[in]], %[stride]\n"
7278 "vld3.8 {d0[6], d1[6], d2[6]}, [%[in]], %[stride]\n"
7279 "vld3.8 {d0[7], d1[7], d2[7]}, [%[in]], %[stride]\n"
7280 "vaddw.u8 q8, q8, d0\n"
7281 "vaddw.u8 q9, q9, d1\n"
7282 "vaddw.u8 q10, q10, d2\n"
7283 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
7284
7285 "bne 1b\n"
7286
7287 "2:"
7288
7289 // Load Aggregate Store - column major 3x5
7290 "vmov.i8 d0, #0\n"
7291 "vmov.i8 d1, #0\n"
7292 "vmov.i8 d2, #0\n"
7293 "vld3.8 {d0[0], d1[0], d2[0]}, [%[in]], %[stride]\n"
7294 "vld3.8 {d0[1], d1[1], d2[1]}, [%[in]], %[stride]\n"
7295 "vld3.8 {d0[2], d1[2], d2[2]}, [%[in]], %[stride]\n"
7296 "vld3.8 {d0[3], d1[3], d2[3]}, [%[in]], %[stride]\n"
7297 "vld3.8 {d0[4], d1[4], d2[4]}, [%[in]], %[stride]\n"
7298 "vaddw.u8 q8, q8, d0\n"
7299 "vaddw.u8 q9, q9, d1\n"
7300 "vaddw.u8 q10, q10, d2\n"
7301 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
7302
7303 // Aggregator Reduction.
7304 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
7305 "vdup.32 q1, %[additive_sum_offset]\n"
7306 "vpaddl.u16 q8, q8\n"
7307 "vpaddl.u16 q9, q9\n"
7308 "vpaddl.u16 q10, q10\n"
7309 "vpadd.u32 d16, d16, d17\n"
7310 "vpadd.u32 d18, d18, d19\n"
7311 "vpadd.u32 d20, d20, d21\n"
7312 "vpadd.u32 d16, d16, d18\n"
7313 "vpadd.u32 d17, d20, d20\n"
7314 "vmul.i32 q8, q8, d0[0]\n"
7315 "vadd.i32 q8, q8, q1\n"
7316 "vst1.32 {d16, d17}, [%[out]:64]\n"
7317 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
7318 [out] "+r"(out), [in] "+r"(in)
7319 : [additive_sum_offset] "r"(params.additive_sum_offset),
7320 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
7321 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "cc",
7322 "memory");
7323 }
7324
7325 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)7326 inline void Stream<uint8_t, 3, 8, 6, ColumnMajorWithSum>::Pack(
7327 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
7328 #ifdef DEBUG
7329 #ifdef DEBUG_METAGEMM_VERBOSE
7330 std::cout
7331 << __FILE__ << "(" << __LINE__
7332 << ") ColumnMajorWithSum<uint8_t, 3, 8, 6, ColumnMajorWithSum>::Pack()"
7333 << std::endl
7334 << std::flush;
7335 #endif
7336 #endif
7337 int params_count_copy = params.count;
7338 int params_stride_copy = params.stride;
7339 asm volatile(
7340 "vmov.i16 q8, #0\n"
7341 "vmov.i16 q9, #0\n"
7342 "vmov.i16 q10, #0\n"
7343
7344 // Reduce count by leftovers.
7345 "subs %[count], %[count], #6\n"
7346 "beq 2f\n"
7347
7348 "1:"
7349 "subs %[count], %[count], #8\n"
7350
7351 // Load Aggregate Store - column major 3x8
7352 "vld3.8 {d0[0], d1[0], d2[0]}, [%[in]], %[stride]\n"
7353 "vld3.8 {d0[1], d1[1], d2[1]}, [%[in]], %[stride]\n"
7354 "vld3.8 {d0[2], d1[2], d2[2]}, [%[in]], %[stride]\n"
7355 "vld3.8 {d0[3], d1[3], d2[3]}, [%[in]], %[stride]\n"
7356 "vld3.8 {d0[4], d1[4], d2[4]}, [%[in]], %[stride]\n"
7357 "vld3.8 {d0[5], d1[5], d2[5]}, [%[in]], %[stride]\n"
7358 "vld3.8 {d0[6], d1[6], d2[6]}, [%[in]], %[stride]\n"
7359 "vld3.8 {d0[7], d1[7], d2[7]}, [%[in]], %[stride]\n"
7360 "vaddw.u8 q8, q8, d0\n"
7361 "vaddw.u8 q9, q9, d1\n"
7362 "vaddw.u8 q10, q10, d2\n"
7363 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
7364
7365 "bne 1b\n"
7366
7367 "2:"
7368
7369 // Load Aggregate Store - column major 3x6
7370 "vmov.i8 d0, #0\n"
7371 "vmov.i8 d1, #0\n"
7372 "vmov.i8 d2, #0\n"
7373 "vld3.8 {d0[0], d1[0], d2[0]}, [%[in]], %[stride]\n"
7374 "vld3.8 {d0[1], d1[1], d2[1]}, [%[in]], %[stride]\n"
7375 "vld3.8 {d0[2], d1[2], d2[2]}, [%[in]], %[stride]\n"
7376 "vld3.8 {d0[3], d1[3], d2[3]}, [%[in]], %[stride]\n"
7377 "vld3.8 {d0[4], d1[4], d2[4]}, [%[in]], %[stride]\n"
7378 "vld3.8 {d0[5], d1[5], d2[5]}, [%[in]], %[stride]\n"
7379 "vaddw.u8 q8, q8, d0\n"
7380 "vaddw.u8 q9, q9, d1\n"
7381 "vaddw.u8 q10, q10, d2\n"
7382 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
7383
7384 // Aggregator Reduction.
7385 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
7386 "vdup.32 q1, %[additive_sum_offset]\n"
7387 "vpaddl.u16 q8, q8\n"
7388 "vpaddl.u16 q9, q9\n"
7389 "vpaddl.u16 q10, q10\n"
7390 "vpadd.u32 d16, d16, d17\n"
7391 "vpadd.u32 d18, d18, d19\n"
7392 "vpadd.u32 d20, d20, d21\n"
7393 "vpadd.u32 d16, d16, d18\n"
7394 "vpadd.u32 d17, d20, d20\n"
7395 "vmul.i32 q8, q8, d0[0]\n"
7396 "vadd.i32 q8, q8, q1\n"
7397 "vst1.32 {d16, d17}, [%[out]:64]\n"
7398 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
7399 [out] "+r"(out), [in] "+r"(in)
7400 : [additive_sum_offset] "r"(params.additive_sum_offset),
7401 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
7402 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "cc",
7403 "memory");
7404 }
7405
7406 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)7407 inline void Stream<uint8_t, 3, 8, 7, ColumnMajorWithSum>::Pack(
7408 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
7409 #ifdef DEBUG
7410 #ifdef DEBUG_METAGEMM_VERBOSE
7411 std::cout
7412 << __FILE__ << "(" << __LINE__
7413 << ") ColumnMajorWithSum<uint8_t, 3, 8, 7, ColumnMajorWithSum>::Pack()"
7414 << std::endl
7415 << std::flush;
7416 #endif
7417 #endif
7418 int params_count_copy = params.count;
7419 int params_stride_copy = params.stride;
7420 asm volatile(
7421 "vmov.i16 q8, #0\n"
7422 "vmov.i16 q9, #0\n"
7423 "vmov.i16 q10, #0\n"
7424
7425 // Reduce count by leftovers.
7426 "subs %[count], %[count], #7\n"
7427 "beq 2f\n"
7428
7429 "1:"
7430 "subs %[count], %[count], #8\n"
7431
7432 // Load Aggregate Store - column major 3x8
7433 "vld3.8 {d0[0], d1[0], d2[0]}, [%[in]], %[stride]\n"
7434 "vld3.8 {d0[1], d1[1], d2[1]}, [%[in]], %[stride]\n"
7435 "vld3.8 {d0[2], d1[2], d2[2]}, [%[in]], %[stride]\n"
7436 "vld3.8 {d0[3], d1[3], d2[3]}, [%[in]], %[stride]\n"
7437 "vld3.8 {d0[4], d1[4], d2[4]}, [%[in]], %[stride]\n"
7438 "vld3.8 {d0[5], d1[5], d2[5]}, [%[in]], %[stride]\n"
7439 "vld3.8 {d0[6], d1[6], d2[6]}, [%[in]], %[stride]\n"
7440 "vld3.8 {d0[7], d1[7], d2[7]}, [%[in]], %[stride]\n"
7441 "vaddw.u8 q8, q8, d0\n"
7442 "vaddw.u8 q9, q9, d1\n"
7443 "vaddw.u8 q10, q10, d2\n"
7444 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
7445
7446 "bne 1b\n"
7447
7448 "2:"
7449
7450 // Load Aggregate Store - column major 3x7
7451 "vmov.i8 d0, #0\n"
7452 "vmov.i8 d1, #0\n"
7453 "vmov.i8 d2, #0\n"
7454 "vld3.8 {d0[0], d1[0], d2[0]}, [%[in]], %[stride]\n"
7455 "vld3.8 {d0[1], d1[1], d2[1]}, [%[in]], %[stride]\n"
7456 "vld3.8 {d0[2], d1[2], d2[2]}, [%[in]], %[stride]\n"
7457 "vld3.8 {d0[3], d1[3], d2[3]}, [%[in]], %[stride]\n"
7458 "vld3.8 {d0[4], d1[4], d2[4]}, [%[in]], %[stride]\n"
7459 "vld3.8 {d0[5], d1[5], d2[5]}, [%[in]], %[stride]\n"
7460 "vld3.8 {d0[6], d1[6], d2[6]}, [%[in]], %[stride]\n"
7461 "vaddw.u8 q8, q8, d0\n"
7462 "vaddw.u8 q9, q9, d1\n"
7463 "vaddw.u8 q10, q10, d2\n"
7464 "vst1.32 {d0, d1, d2}, [%[out]:64]!\n"
7465
7466 // Aggregator Reduction.
7467 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
7468 "vdup.32 q1, %[additive_sum_offset]\n"
7469 "vpaddl.u16 q8, q8\n"
7470 "vpaddl.u16 q9, q9\n"
7471 "vpaddl.u16 q10, q10\n"
7472 "vpadd.u32 d16, d16, d17\n"
7473 "vpadd.u32 d18, d18, d19\n"
7474 "vpadd.u32 d20, d20, d21\n"
7475 "vpadd.u32 d16, d16, d18\n"
7476 "vpadd.u32 d17, d20, d20\n"
7477 "vmul.i32 q8, q8, d0[0]\n"
7478 "vadd.i32 q8, q8, q1\n"
7479 "vst1.32 {d16, d17}, [%[out]:64]\n"
7480 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
7481 [out] "+r"(out), [in] "+r"(in)
7482 : [additive_sum_offset] "r"(params.additive_sum_offset),
7483 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
7484 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "cc",
7485 "memory");
7486 }
7487
7488 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)7489 inline void Stream<uint8_t, 4, 8, 0, ColumnMajorWithSum>::Pack(
7490 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
7491 #ifdef DEBUG
7492 #ifdef DEBUG_METAGEMM_VERBOSE
7493 std::cout
7494 << __FILE__ << "(" << __LINE__
7495 << ") ColumnMajorWithSum<uint8_t, 4, 8, 0, ColumnMajorWithSum>::Pack()"
7496 << std::endl
7497 << std::flush;
7498 #endif
7499 #endif
7500 int params_count_copy = params.count;
7501 int params_stride_copy = params.stride;
7502 asm volatile(
7503 "vmov.i16 q8, #0\n"
7504 "vmov.i16 q9, #0\n"
7505 "vmov.i16 q10, #0\n"
7506 "vmov.i16 q11, #0\n"
7507
7508 "1:"
7509 "subs %[count], %[count], #8\n"
7510
7511 // Load Aggregate Store - column major 4x8
7512 "vld1.32 {d0[0]}, [%[in]], %[stride]\n"
7513 "vld1.32 {d1[0]}, [%[in]], %[stride]\n"
7514 "vld1.32 {d2[0]}, [%[in]], %[stride]\n"
7515 "vld1.32 {d3[0]}, [%[in]], %[stride]\n"
7516 "vld1.32 {d0[1]}, [%[in]], %[stride]\n"
7517 "vld1.32 {d1[1]}, [%[in]], %[stride]\n"
7518 "vld1.32 {d2[1]}, [%[in]], %[stride]\n"
7519 "vld1.32 {d3[1]}, [%[in]], %[stride]\n"
7520 "pld [%[in]]\n"
7521 "vtrn.16 d0, d2\n"
7522 "vtrn.16 d1, d3\n"
7523 "vtrn.8 d0, d1\n"
7524 "vtrn.8 d2, d3\n"
7525 "vaddw.u8 q8, q8, d0\n"
7526 "vaddw.u8 q9, q9, d1\n"
7527 "vaddw.u8 q10, q10, d2\n"
7528 "vaddw.u8 q11, q11, d3\n"
7529 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
7530
7531 "bne 1b\n"
7532
7533 // Aggregator Reduction.
7534 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
7535 "vdup.32 q1, %[additive_sum_offset]\n"
7536 "vpaddl.u16 q8, q8\n"
7537 "vpaddl.u16 q9, q9\n"
7538 "vpaddl.u16 q10, q10\n"
7539 "vpaddl.u16 q11, q11\n"
7540 "vpadd.u32 d16, d16, d17\n"
7541 "vpadd.u32 d18, d18, d19\n"
7542 "vpadd.u32 d20, d20, d21\n"
7543 "vpadd.u32 d22, d22, d23\n"
7544 "vpadd.u32 d16, d16, d18\n"
7545 "vpadd.u32 d17, d20, d22\n"
7546 "vmul.i32 q8, q8, d0[0]\n"
7547 "vadd.i32 q8, q8, q1\n"
7548 "vst1.32 {d16, d17}, [%[out]:128]\n"
7549 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
7550 [out] "+r"(out), [in] "+r"(in)
7551 : [additive_sum_offset] "r"(params.additive_sum_offset),
7552 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
7553 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
7554 "d23", "cc", "memory");
7555 }
7556
7557 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)7558 inline void Stream<uint8_t, 4, 8, 1, ColumnMajorWithSum>::Pack(
7559 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
7560 #ifdef DEBUG
7561 #ifdef DEBUG_METAGEMM_VERBOSE
7562 std::cout
7563 << __FILE__ << "(" << __LINE__
7564 << ") ColumnMajorWithSum<uint8_t, 4, 8, 1, ColumnMajorWithSum>::Pack()"
7565 << std::endl
7566 << std::flush;
7567 #endif
7568 #endif
7569 int params_count_copy = params.count;
7570 int params_stride_copy = params.stride;
7571 asm volatile(
7572 "vmov.i16 q8, #0\n"
7573 "vmov.i16 q9, #0\n"
7574 "vmov.i16 q10, #0\n"
7575 "vmov.i16 q11, #0\n"
7576
7577 // Reduce count by leftovers.
7578 "subs %[count], %[count], #1\n"
7579 "beq 2f\n"
7580
7581 "1:"
7582 "subs %[count], %[count], #8\n"
7583
7584 // Load Aggregate Store - column major 4x8
7585 "vld1.32 {d0[0]}, [%[in]], %[stride]\n"
7586 "vld1.32 {d1[0]}, [%[in]], %[stride]\n"
7587 "vld1.32 {d2[0]}, [%[in]], %[stride]\n"
7588 "vld1.32 {d3[0]}, [%[in]], %[stride]\n"
7589 "vld1.32 {d0[1]}, [%[in]], %[stride]\n"
7590 "vld1.32 {d1[1]}, [%[in]], %[stride]\n"
7591 "vld1.32 {d2[1]}, [%[in]], %[stride]\n"
7592 "vld1.32 {d3[1]}, [%[in]], %[stride]\n"
7593 "pld [%[in]]\n"
7594 "vtrn.16 d0, d2\n"
7595 "vtrn.16 d1, d3\n"
7596 "vtrn.8 d0, d1\n"
7597 "vtrn.8 d2, d3\n"
7598 "vaddw.u8 q8, q8, d0\n"
7599 "vaddw.u8 q9, q9, d1\n"
7600 "vaddw.u8 q10, q10, d2\n"
7601 "vaddw.u8 q11, q11, d3\n"
7602 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
7603
7604 "bne 1b\n"
7605
7606 "2:"
7607
7608 // Load Aggregate Store - column major 4x1
7609 "vmov.i8 d0, #0\n"
7610 "vmov.i8 d1, #0\n"
7611 "vmov.i8 d2, #0\n"
7612 "vmov.i8 d3, #0\n"
7613 "vld1.32 {d0[0]}, [%[in]], %[stride]\n"
7614 "pld [%[in]]\n"
7615 "vtrn.16 d0, d2\n"
7616 "vtrn.16 d1, d3\n"
7617 "vtrn.8 d0, d1\n"
7618 "vtrn.8 d2, d3\n"
7619 "vaddw.u8 q8, q8, d0\n"
7620 "vaddw.u8 q9, q9, d1\n"
7621 "vaddw.u8 q10, q10, d2\n"
7622 "vaddw.u8 q11, q11, d3\n"
7623 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
7624
7625 // Aggregator Reduction.
7626 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
7627 "vdup.32 q1, %[additive_sum_offset]\n"
7628 "vpaddl.u16 q8, q8\n"
7629 "vpaddl.u16 q9, q9\n"
7630 "vpaddl.u16 q10, q10\n"
7631 "vpaddl.u16 q11, q11\n"
7632 "vpadd.u32 d16, d16, d17\n"
7633 "vpadd.u32 d18, d18, d19\n"
7634 "vpadd.u32 d20, d20, d21\n"
7635 "vpadd.u32 d22, d22, d23\n"
7636 "vpadd.u32 d16, d16, d18\n"
7637 "vpadd.u32 d17, d20, d22\n"
7638 "vmul.i32 q8, q8, d0[0]\n"
7639 "vadd.i32 q8, q8, q1\n"
7640 "vst1.32 {d16, d17}, [%[out]:128]\n"
7641 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
7642 [out] "+r"(out), [in] "+r"(in)
7643 : [additive_sum_offset] "r"(params.additive_sum_offset),
7644 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
7645 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
7646 "d23", "cc", "memory");
7647 }
7648
7649 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)7650 inline void Stream<uint8_t, 4, 8, 2, ColumnMajorWithSum>::Pack(
7651 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
7652 #ifdef DEBUG
7653 #ifdef DEBUG_METAGEMM_VERBOSE
7654 std::cout
7655 << __FILE__ << "(" << __LINE__
7656 << ") ColumnMajorWithSum<uint8_t, 4, 8, 2, ColumnMajorWithSum>::Pack()"
7657 << std::endl
7658 << std::flush;
7659 #endif
7660 #endif
7661 int params_count_copy = params.count;
7662 int params_stride_copy = params.stride;
7663 asm volatile(
7664 "vmov.i16 q8, #0\n"
7665 "vmov.i16 q9, #0\n"
7666 "vmov.i16 q10, #0\n"
7667 "vmov.i16 q11, #0\n"
7668
7669 // Reduce count by leftovers.
7670 "subs %[count], %[count], #2\n"
7671 "beq 2f\n"
7672
7673 "1:"
7674 "subs %[count], %[count], #8\n"
7675
7676 // Load Aggregate Store - column major 4x8
7677 "vld1.32 {d0[0]}, [%[in]], %[stride]\n"
7678 "vld1.32 {d1[0]}, [%[in]], %[stride]\n"
7679 "vld1.32 {d2[0]}, [%[in]], %[stride]\n"
7680 "vld1.32 {d3[0]}, [%[in]], %[stride]\n"
7681 "vld1.32 {d0[1]}, [%[in]], %[stride]\n"
7682 "vld1.32 {d1[1]}, [%[in]], %[stride]\n"
7683 "vld1.32 {d2[1]}, [%[in]], %[stride]\n"
7684 "vld1.32 {d3[1]}, [%[in]], %[stride]\n"
7685 "pld [%[in]]\n"
7686 "vtrn.16 d0, d2\n"
7687 "vtrn.16 d1, d3\n"
7688 "vtrn.8 d0, d1\n"
7689 "vtrn.8 d2, d3\n"
7690 "vaddw.u8 q8, q8, d0\n"
7691 "vaddw.u8 q9, q9, d1\n"
7692 "vaddw.u8 q10, q10, d2\n"
7693 "vaddw.u8 q11, q11, d3\n"
7694 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
7695
7696 "bne 1b\n"
7697
7698 "2:"
7699
7700 // Load Aggregate Store - column major 4x2
7701 "vmov.i8 d0, #0\n"
7702 "vmov.i8 d1, #0\n"
7703 "vmov.i8 d2, #0\n"
7704 "vmov.i8 d3, #0\n"
7705 "vld1.32 {d0[0]}, [%[in]], %[stride]\n"
7706 "vld1.32 {d1[0]}, [%[in]], %[stride]\n"
7707 "pld [%[in]]\n"
7708 "vtrn.16 d0, d2\n"
7709 "vtrn.16 d1, d3\n"
7710 "vtrn.8 d0, d1\n"
7711 "vtrn.8 d2, d3\n"
7712 "vaddw.u8 q8, q8, d0\n"
7713 "vaddw.u8 q9, q9, d1\n"
7714 "vaddw.u8 q10, q10, d2\n"
7715 "vaddw.u8 q11, q11, d3\n"
7716 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
7717
7718 // Aggregator Reduction.
7719 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
7720 "vdup.32 q1, %[additive_sum_offset]\n"
7721 "vpaddl.u16 q8, q8\n"
7722 "vpaddl.u16 q9, q9\n"
7723 "vpaddl.u16 q10, q10\n"
7724 "vpaddl.u16 q11, q11\n"
7725 "vpadd.u32 d16, d16, d17\n"
7726 "vpadd.u32 d18, d18, d19\n"
7727 "vpadd.u32 d20, d20, d21\n"
7728 "vpadd.u32 d22, d22, d23\n"
7729 "vpadd.u32 d16, d16, d18\n"
7730 "vpadd.u32 d17, d20, d22\n"
7731 "vmul.i32 q8, q8, d0[0]\n"
7732 "vadd.i32 q8, q8, q1\n"
7733 "vst1.32 {d16, d17}, [%[out]:128]\n"
7734 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
7735 [out] "+r"(out), [in] "+r"(in)
7736 : [additive_sum_offset] "r"(params.additive_sum_offset),
7737 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
7738 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
7739 "d23", "cc", "memory");
7740 }
7741
7742 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)7743 inline void Stream<uint8_t, 4, 8, 3, ColumnMajorWithSum>::Pack(
7744 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
7745 #ifdef DEBUG
7746 #ifdef DEBUG_METAGEMM_VERBOSE
7747 std::cout
7748 << __FILE__ << "(" << __LINE__
7749 << ") ColumnMajorWithSum<uint8_t, 4, 8, 3, ColumnMajorWithSum>::Pack()"
7750 << std::endl
7751 << std::flush;
7752 #endif
7753 #endif
7754 int params_count_copy = params.count;
7755 int params_stride_copy = params.stride;
7756 asm volatile(
7757 "vmov.i16 q8, #0\n"
7758 "vmov.i16 q9, #0\n"
7759 "vmov.i16 q10, #0\n"
7760 "vmov.i16 q11, #0\n"
7761
7762 // Reduce count by leftovers.
7763 "subs %[count], %[count], #3\n"
7764 "beq 2f\n"
7765
7766 "1:"
7767 "subs %[count], %[count], #8\n"
7768
7769 // Load Aggregate Store - column major 4x8
7770 "vld1.32 {d0[0]}, [%[in]], %[stride]\n"
7771 "vld1.32 {d1[0]}, [%[in]], %[stride]\n"
7772 "vld1.32 {d2[0]}, [%[in]], %[stride]\n"
7773 "vld1.32 {d3[0]}, [%[in]], %[stride]\n"
7774 "vld1.32 {d0[1]}, [%[in]], %[stride]\n"
7775 "vld1.32 {d1[1]}, [%[in]], %[stride]\n"
7776 "vld1.32 {d2[1]}, [%[in]], %[stride]\n"
7777 "vld1.32 {d3[1]}, [%[in]], %[stride]\n"
7778 "pld [%[in]]\n"
7779 "vtrn.16 d0, d2\n"
7780 "vtrn.16 d1, d3\n"
7781 "vtrn.8 d0, d1\n"
7782 "vtrn.8 d2, d3\n"
7783 "vaddw.u8 q8, q8, d0\n"
7784 "vaddw.u8 q9, q9, d1\n"
7785 "vaddw.u8 q10, q10, d2\n"
7786 "vaddw.u8 q11, q11, d3\n"
7787 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
7788
7789 "bne 1b\n"
7790
7791 "2:"
7792
7793 // Load Aggregate Store - column major 4x3
7794 "vmov.i8 d0, #0\n"
7795 "vmov.i8 d1, #0\n"
7796 "vmov.i8 d2, #0\n"
7797 "vmov.i8 d3, #0\n"
7798 "vld1.32 {d0[0]}, [%[in]], %[stride]\n"
7799 "vld1.32 {d1[0]}, [%[in]], %[stride]\n"
7800 "vld1.32 {d2[0]}, [%[in]], %[stride]\n"
7801 "pld [%[in]]\n"
7802 "vtrn.16 d0, d2\n"
7803 "vtrn.16 d1, d3\n"
7804 "vtrn.8 d0, d1\n"
7805 "vtrn.8 d2, d3\n"
7806 "vaddw.u8 q8, q8, d0\n"
7807 "vaddw.u8 q9, q9, d1\n"
7808 "vaddw.u8 q10, q10, d2\n"
7809 "vaddw.u8 q11, q11, d3\n"
7810 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
7811
7812 // Aggregator Reduction.
7813 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
7814 "vdup.32 q1, %[additive_sum_offset]\n"
7815 "vpaddl.u16 q8, q8\n"
7816 "vpaddl.u16 q9, q9\n"
7817 "vpaddl.u16 q10, q10\n"
7818 "vpaddl.u16 q11, q11\n"
7819 "vpadd.u32 d16, d16, d17\n"
7820 "vpadd.u32 d18, d18, d19\n"
7821 "vpadd.u32 d20, d20, d21\n"
7822 "vpadd.u32 d22, d22, d23\n"
7823 "vpadd.u32 d16, d16, d18\n"
7824 "vpadd.u32 d17, d20, d22\n"
7825 "vmul.i32 q8, q8, d0[0]\n"
7826 "vadd.i32 q8, q8, q1\n"
7827 "vst1.32 {d16, d17}, [%[out]:128]\n"
7828 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
7829 [out] "+r"(out), [in] "+r"(in)
7830 : [additive_sum_offset] "r"(params.additive_sum_offset),
7831 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
7832 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
7833 "d23", "cc", "memory");
7834 }
7835
7836 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)7837 inline void Stream<uint8_t, 4, 8, 4, ColumnMajorWithSum>::Pack(
7838 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
7839 #ifdef DEBUG
7840 #ifdef DEBUG_METAGEMM_VERBOSE
7841 std::cout
7842 << __FILE__ << "(" << __LINE__
7843 << ") ColumnMajorWithSum<uint8_t, 4, 8, 4, ColumnMajorWithSum>::Pack()"
7844 << std::endl
7845 << std::flush;
7846 #endif
7847 #endif
7848 int params_count_copy = params.count;
7849 int params_stride_copy = params.stride;
7850 asm volatile(
7851 "vmov.i16 q8, #0\n"
7852 "vmov.i16 q9, #0\n"
7853 "vmov.i16 q10, #0\n"
7854 "vmov.i16 q11, #0\n"
7855
7856 // Reduce count by leftovers.
7857 "subs %[count], %[count], #4\n"
7858 "beq 2f\n"
7859
7860 "1:"
7861 "subs %[count], %[count], #8\n"
7862
7863 // Load Aggregate Store - column major 4x8
7864 "vld1.32 {d0[0]}, [%[in]], %[stride]\n"
7865 "vld1.32 {d1[0]}, [%[in]], %[stride]\n"
7866 "vld1.32 {d2[0]}, [%[in]], %[stride]\n"
7867 "vld1.32 {d3[0]}, [%[in]], %[stride]\n"
7868 "vld1.32 {d0[1]}, [%[in]], %[stride]\n"
7869 "vld1.32 {d1[1]}, [%[in]], %[stride]\n"
7870 "vld1.32 {d2[1]}, [%[in]], %[stride]\n"
7871 "vld1.32 {d3[1]}, [%[in]], %[stride]\n"
7872 "pld [%[in]]\n"
7873 "vtrn.16 d0, d2\n"
7874 "vtrn.16 d1, d3\n"
7875 "vtrn.8 d0, d1\n"
7876 "vtrn.8 d2, d3\n"
7877 "vaddw.u8 q8, q8, d0\n"
7878 "vaddw.u8 q9, q9, d1\n"
7879 "vaddw.u8 q10, q10, d2\n"
7880 "vaddw.u8 q11, q11, d3\n"
7881 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
7882
7883 "bne 1b\n"
7884
7885 "2:"
7886
7887 // Load Aggregate Store - column major 4x4
7888 "vmov.i8 d0, #0\n"
7889 "vmov.i8 d1, #0\n"
7890 "vmov.i8 d2, #0\n"
7891 "vmov.i8 d3, #0\n"
7892 "vld1.32 {d0[0]}, [%[in]], %[stride]\n"
7893 "vld1.32 {d1[0]}, [%[in]], %[stride]\n"
7894 "vld1.32 {d2[0]}, [%[in]], %[stride]\n"
7895 "vld1.32 {d3[0]}, [%[in]], %[stride]\n"
7896 "pld [%[in]]\n"
7897 "vtrn.16 d0, d2\n"
7898 "vtrn.16 d1, d3\n"
7899 "vtrn.8 d0, d1\n"
7900 "vtrn.8 d2, d3\n"
7901 "vaddw.u8 q8, q8, d0\n"
7902 "vaddw.u8 q9, q9, d1\n"
7903 "vaddw.u8 q10, q10, d2\n"
7904 "vaddw.u8 q11, q11, d3\n"
7905 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
7906
7907 // Aggregator Reduction.
7908 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
7909 "vdup.32 q1, %[additive_sum_offset]\n"
7910 "vpaddl.u16 q8, q8\n"
7911 "vpaddl.u16 q9, q9\n"
7912 "vpaddl.u16 q10, q10\n"
7913 "vpaddl.u16 q11, q11\n"
7914 "vpadd.u32 d16, d16, d17\n"
7915 "vpadd.u32 d18, d18, d19\n"
7916 "vpadd.u32 d20, d20, d21\n"
7917 "vpadd.u32 d22, d22, d23\n"
7918 "vpadd.u32 d16, d16, d18\n"
7919 "vpadd.u32 d17, d20, d22\n"
7920 "vmul.i32 q8, q8, d0[0]\n"
7921 "vadd.i32 q8, q8, q1\n"
7922 "vst1.32 {d16, d17}, [%[out]:128]\n"
7923 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
7924 [out] "+r"(out), [in] "+r"(in)
7925 : [additive_sum_offset] "r"(params.additive_sum_offset),
7926 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
7927 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
7928 "d23", "cc", "memory");
7929 }
7930
7931 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)7932 inline void Stream<uint8_t, 4, 8, 5, ColumnMajorWithSum>::Pack(
7933 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
7934 #ifdef DEBUG
7935 #ifdef DEBUG_METAGEMM_VERBOSE
7936 std::cout
7937 << __FILE__ << "(" << __LINE__
7938 << ") ColumnMajorWithSum<uint8_t, 4, 8, 5, ColumnMajorWithSum>::Pack()"
7939 << std::endl
7940 << std::flush;
7941 #endif
7942 #endif
7943 int params_count_copy = params.count;
7944 int params_stride_copy = params.stride;
7945 asm volatile(
7946 "vmov.i16 q8, #0\n"
7947 "vmov.i16 q9, #0\n"
7948 "vmov.i16 q10, #0\n"
7949 "vmov.i16 q11, #0\n"
7950
7951 // Reduce count by leftovers.
7952 "subs %[count], %[count], #5\n"
7953 "beq 2f\n"
7954
7955 "1:"
7956 "subs %[count], %[count], #8\n"
7957
7958 // Load Aggregate Store - column major 4x8
7959 "vld1.32 {d0[0]}, [%[in]], %[stride]\n"
7960 "vld1.32 {d1[0]}, [%[in]], %[stride]\n"
7961 "vld1.32 {d2[0]}, [%[in]], %[stride]\n"
7962 "vld1.32 {d3[0]}, [%[in]], %[stride]\n"
7963 "vld1.32 {d0[1]}, [%[in]], %[stride]\n"
7964 "vld1.32 {d1[1]}, [%[in]], %[stride]\n"
7965 "vld1.32 {d2[1]}, [%[in]], %[stride]\n"
7966 "vld1.32 {d3[1]}, [%[in]], %[stride]\n"
7967 "pld [%[in]]\n"
7968 "vtrn.16 d0, d2\n"
7969 "vtrn.16 d1, d3\n"
7970 "vtrn.8 d0, d1\n"
7971 "vtrn.8 d2, d3\n"
7972 "vaddw.u8 q8, q8, d0\n"
7973 "vaddw.u8 q9, q9, d1\n"
7974 "vaddw.u8 q10, q10, d2\n"
7975 "vaddw.u8 q11, q11, d3\n"
7976 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
7977
7978 "bne 1b\n"
7979
7980 "2:"
7981
7982 // Load Aggregate Store - column major 4x5
7983 "vmov.i8 d0, #0\n"
7984 "vmov.i8 d1, #0\n"
7985 "vmov.i8 d2, #0\n"
7986 "vmov.i8 d3, #0\n"
7987 "vld1.32 {d0[0]}, [%[in]], %[stride]\n"
7988 "vld1.32 {d1[0]}, [%[in]], %[stride]\n"
7989 "vld1.32 {d2[0]}, [%[in]], %[stride]\n"
7990 "vld1.32 {d3[0]}, [%[in]], %[stride]\n"
7991 "vld1.32 {d0[1]}, [%[in]], %[stride]\n"
7992 "pld [%[in]]\n"
7993 "vtrn.16 d0, d2\n"
7994 "vtrn.16 d1, d3\n"
7995 "vtrn.8 d0, d1\n"
7996 "vtrn.8 d2, d3\n"
7997 "vaddw.u8 q8, q8, d0\n"
7998 "vaddw.u8 q9, q9, d1\n"
7999 "vaddw.u8 q10, q10, d2\n"
8000 "vaddw.u8 q11, q11, d3\n"
8001 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
8002
8003 // Aggregator Reduction.
8004 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
8005 "vdup.32 q1, %[additive_sum_offset]\n"
8006 "vpaddl.u16 q8, q8\n"
8007 "vpaddl.u16 q9, q9\n"
8008 "vpaddl.u16 q10, q10\n"
8009 "vpaddl.u16 q11, q11\n"
8010 "vpadd.u32 d16, d16, d17\n"
8011 "vpadd.u32 d18, d18, d19\n"
8012 "vpadd.u32 d20, d20, d21\n"
8013 "vpadd.u32 d22, d22, d23\n"
8014 "vpadd.u32 d16, d16, d18\n"
8015 "vpadd.u32 d17, d20, d22\n"
8016 "vmul.i32 q8, q8, d0[0]\n"
8017 "vadd.i32 q8, q8, q1\n"
8018 "vst1.32 {d16, d17}, [%[out]:128]\n"
8019 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
8020 [out] "+r"(out), [in] "+r"(in)
8021 : [additive_sum_offset] "r"(params.additive_sum_offset),
8022 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
8023 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
8024 "d23", "cc", "memory");
8025 }
8026
8027 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)8028 inline void Stream<uint8_t, 4, 8, 6, ColumnMajorWithSum>::Pack(
8029 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
8030 #ifdef DEBUG
8031 #ifdef DEBUG_METAGEMM_VERBOSE
8032 std::cout
8033 << __FILE__ << "(" << __LINE__
8034 << ") ColumnMajorWithSum<uint8_t, 4, 8, 6, ColumnMajorWithSum>::Pack()"
8035 << std::endl
8036 << std::flush;
8037 #endif
8038 #endif
8039 int params_count_copy = params.count;
8040 int params_stride_copy = params.stride;
8041 asm volatile(
8042 "vmov.i16 q8, #0\n"
8043 "vmov.i16 q9, #0\n"
8044 "vmov.i16 q10, #0\n"
8045 "vmov.i16 q11, #0\n"
8046
8047 // Reduce count by leftovers.
8048 "subs %[count], %[count], #6\n"
8049 "beq 2f\n"
8050
8051 "1:"
8052 "subs %[count], %[count], #8\n"
8053
8054 // Load Aggregate Store - column major 4x8
8055 "vld1.32 {d0[0]}, [%[in]], %[stride]\n"
8056 "vld1.32 {d1[0]}, [%[in]], %[stride]\n"
8057 "vld1.32 {d2[0]}, [%[in]], %[stride]\n"
8058 "vld1.32 {d3[0]}, [%[in]], %[stride]\n"
8059 "vld1.32 {d0[1]}, [%[in]], %[stride]\n"
8060 "vld1.32 {d1[1]}, [%[in]], %[stride]\n"
8061 "vld1.32 {d2[1]}, [%[in]], %[stride]\n"
8062 "vld1.32 {d3[1]}, [%[in]], %[stride]\n"
8063 "pld [%[in]]\n"
8064 "vtrn.16 d0, d2\n"
8065 "vtrn.16 d1, d3\n"
8066 "vtrn.8 d0, d1\n"
8067 "vtrn.8 d2, d3\n"
8068 "vaddw.u8 q8, q8, d0\n"
8069 "vaddw.u8 q9, q9, d1\n"
8070 "vaddw.u8 q10, q10, d2\n"
8071 "vaddw.u8 q11, q11, d3\n"
8072 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
8073
8074 "bne 1b\n"
8075
8076 "2:"
8077
8078 // Load Aggregate Store - column major 4x6
8079 "vmov.i8 d0, #0\n"
8080 "vmov.i8 d1, #0\n"
8081 "vmov.i8 d2, #0\n"
8082 "vmov.i8 d3, #0\n"
8083 "vld1.32 {d0[0]}, [%[in]], %[stride]\n"
8084 "vld1.32 {d1[0]}, [%[in]], %[stride]\n"
8085 "vld1.32 {d2[0]}, [%[in]], %[stride]\n"
8086 "vld1.32 {d3[0]}, [%[in]], %[stride]\n"
8087 "vld1.32 {d0[1]}, [%[in]], %[stride]\n"
8088 "vld1.32 {d1[1]}, [%[in]], %[stride]\n"
8089 "pld [%[in]]\n"
8090 "vtrn.16 d0, d2\n"
8091 "vtrn.16 d1, d3\n"
8092 "vtrn.8 d0, d1\n"
8093 "vtrn.8 d2, d3\n"
8094 "vaddw.u8 q8, q8, d0\n"
8095 "vaddw.u8 q9, q9, d1\n"
8096 "vaddw.u8 q10, q10, d2\n"
8097 "vaddw.u8 q11, q11, d3\n"
8098 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
8099
8100 // Aggregator Reduction.
8101 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
8102 "vdup.32 q1, %[additive_sum_offset]\n"
8103 "vpaddl.u16 q8, q8\n"
8104 "vpaddl.u16 q9, q9\n"
8105 "vpaddl.u16 q10, q10\n"
8106 "vpaddl.u16 q11, q11\n"
8107 "vpadd.u32 d16, d16, d17\n"
8108 "vpadd.u32 d18, d18, d19\n"
8109 "vpadd.u32 d20, d20, d21\n"
8110 "vpadd.u32 d22, d22, d23\n"
8111 "vpadd.u32 d16, d16, d18\n"
8112 "vpadd.u32 d17, d20, d22\n"
8113 "vmul.i32 q8, q8, d0[0]\n"
8114 "vadd.i32 q8, q8, q1\n"
8115 "vst1.32 {d16, d17}, [%[out]:128]\n"
8116 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
8117 [out] "+r"(out), [in] "+r"(in)
8118 : [additive_sum_offset] "r"(params.additive_sum_offset),
8119 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
8120 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
8121 "d23", "cc", "memory");
8122 }
8123
8124 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)8125 inline void Stream<uint8_t, 4, 8, 7, ColumnMajorWithSum>::Pack(
8126 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
8127 #ifdef DEBUG
8128 #ifdef DEBUG_METAGEMM_VERBOSE
8129 std::cout
8130 << __FILE__ << "(" << __LINE__
8131 << ") ColumnMajorWithSum<uint8_t, 4, 8, 7, ColumnMajorWithSum>::Pack()"
8132 << std::endl
8133 << std::flush;
8134 #endif
8135 #endif
8136 int params_count_copy = params.count;
8137 int params_stride_copy = params.stride;
8138 asm volatile(
8139 "vmov.i16 q8, #0\n"
8140 "vmov.i16 q9, #0\n"
8141 "vmov.i16 q10, #0\n"
8142 "vmov.i16 q11, #0\n"
8143
8144 // Reduce count by leftovers.
8145 "subs %[count], %[count], #7\n"
8146 "beq 2f\n"
8147
8148 "1:"
8149 "subs %[count], %[count], #8\n"
8150
8151 // Load Aggregate Store - column major 4x8
8152 "vld1.32 {d0[0]}, [%[in]], %[stride]\n"
8153 "vld1.32 {d1[0]}, [%[in]], %[stride]\n"
8154 "vld1.32 {d2[0]}, [%[in]], %[stride]\n"
8155 "vld1.32 {d3[0]}, [%[in]], %[stride]\n"
8156 "vld1.32 {d0[1]}, [%[in]], %[stride]\n"
8157 "vld1.32 {d1[1]}, [%[in]], %[stride]\n"
8158 "vld1.32 {d2[1]}, [%[in]], %[stride]\n"
8159 "vld1.32 {d3[1]}, [%[in]], %[stride]\n"
8160 "pld [%[in]]\n"
8161 "vtrn.16 d0, d2\n"
8162 "vtrn.16 d1, d3\n"
8163 "vtrn.8 d0, d1\n"
8164 "vtrn.8 d2, d3\n"
8165 "vaddw.u8 q8, q8, d0\n"
8166 "vaddw.u8 q9, q9, d1\n"
8167 "vaddw.u8 q10, q10, d2\n"
8168 "vaddw.u8 q11, q11, d3\n"
8169 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
8170
8171 "bne 1b\n"
8172
8173 "2:"
8174
8175 // Load Aggregate Store - column major 4x7
8176 "vmov.i8 d0, #0\n"
8177 "vmov.i8 d1, #0\n"
8178 "vmov.i8 d2, #0\n"
8179 "vmov.i8 d3, #0\n"
8180 "vld1.32 {d0[0]}, [%[in]], %[stride]\n"
8181 "vld1.32 {d1[0]}, [%[in]], %[stride]\n"
8182 "vld1.32 {d2[0]}, [%[in]], %[stride]\n"
8183 "vld1.32 {d3[0]}, [%[in]], %[stride]\n"
8184 "vld1.32 {d0[1]}, [%[in]], %[stride]\n"
8185 "vld1.32 {d1[1]}, [%[in]], %[stride]\n"
8186 "vld1.32 {d2[1]}, [%[in]], %[stride]\n"
8187 "pld [%[in]]\n"
8188 "vtrn.16 d0, d2\n"
8189 "vtrn.16 d1, d3\n"
8190 "vtrn.8 d0, d1\n"
8191 "vtrn.8 d2, d3\n"
8192 "vaddw.u8 q8, q8, d0\n"
8193 "vaddw.u8 q9, q9, d1\n"
8194 "vaddw.u8 q10, q10, d2\n"
8195 "vaddw.u8 q11, q11, d3\n"
8196 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
8197
8198 // Aggregator Reduction.
8199 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
8200 "vdup.32 q1, %[additive_sum_offset]\n"
8201 "vpaddl.u16 q8, q8\n"
8202 "vpaddl.u16 q9, q9\n"
8203 "vpaddl.u16 q10, q10\n"
8204 "vpaddl.u16 q11, q11\n"
8205 "vpadd.u32 d16, d16, d17\n"
8206 "vpadd.u32 d18, d18, d19\n"
8207 "vpadd.u32 d20, d20, d21\n"
8208 "vpadd.u32 d22, d22, d23\n"
8209 "vpadd.u32 d16, d16, d18\n"
8210 "vpadd.u32 d17, d20, d22\n"
8211 "vmul.i32 q8, q8, d0[0]\n"
8212 "vadd.i32 q8, q8, q1\n"
8213 "vst1.32 {d16, d17}, [%[out]:128]\n"
8214 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
8215 [out] "+r"(out), [in] "+r"(in)
8216 : [additive_sum_offset] "r"(params.additive_sum_offset),
8217 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
8218 : "d0", "d1", "d2", "d3", "d16", "d17", "d18", "d19", "d20", "d21", "d22",
8219 "d23", "cc", "memory");
8220 }
8221
8222 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)8223 inline void Stream<uint8_t, 5, 8, 0, ColumnMajorWithSum>::Pack(
8224 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
8225 #ifdef DEBUG
8226 #ifdef DEBUG_METAGEMM_VERBOSE
8227 std::cout
8228 << __FILE__ << "(" << __LINE__
8229 << ") ColumnMajorWithSum<uint8_t, 5, 8, 0, ColumnMajorWithSum>::Pack()"
8230 << std::endl
8231 << std::flush;
8232 #endif
8233 #endif
8234 int params_count_copy = params.count;
8235 int params_stride_copy = params.stride;
8236 asm volatile(
8237 "sub %[stride], %[stride], #4\n"
8238 "vmov.i16 q8, #0\n"
8239 "vmov.i16 q9, #0\n"
8240 "vmov.i16 q10, #0\n"
8241 "vmov.i16 q11, #0\n"
8242 "vmov.i16 q12, #0\n"
8243
8244 "1:"
8245 "subs %[count], %[count], #8\n"
8246
8247 // Load Aggregate Store - column major 5x8
8248 "vld1.32 {d0[0]}, [%[in]]!\n"
8249 "vld1.8 {d4[0]}, [%[in]], %[stride]\n"
8250 "vld1.32 {d1[0]}, [%[in]]!\n"
8251 "vld1.8 {d4[1]}, [%[in]], %[stride]\n"
8252 "vld1.32 {d2[0]}, [%[in]]!\n"
8253 "vld1.8 {d4[2]}, [%[in]], %[stride]\n"
8254 "vld1.32 {d3[0]}, [%[in]]!\n"
8255 "vld1.8 {d4[3]}, [%[in]], %[stride]\n"
8256 "vld1.32 {d0[1]}, [%[in]]!\n"
8257 "vld1.8 {d4[4]}, [%[in]], %[stride]\n"
8258 "vld1.32 {d1[1]}, [%[in]]!\n"
8259 "vld1.8 {d4[5]}, [%[in]], %[stride]\n"
8260 "vld1.32 {d2[1]}, [%[in]]!\n"
8261 "vld1.8 {d4[6]}, [%[in]], %[stride]\n"
8262 "vld1.32 {d3[1]}, [%[in]]!\n"
8263 "vld1.8 {d4[7]}, [%[in]], %[stride]\n"
8264 "pld [%[in]]\n"
8265 "vtrn.16 d0, d2\n"
8266 "vtrn.16 d1, d3\n"
8267 "vtrn.8 d0, d1\n"
8268 "vtrn.8 d2, d3\n"
8269 "vaddw.u8 q8, q8, d0\n"
8270 "vaddw.u8 q9, q9, d1\n"
8271 "vaddw.u8 q10, q10, d2\n"
8272 "vaddw.u8 q11, q11, d3\n"
8273 "vaddw.u8 q12, q12, d4\n"
8274 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
8275 "vst1.32 {d4}, [%[out]:64]!\n"
8276
8277 "bne 1b\n"
8278
8279 // Aggregator Reduction.
8280 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
8281 "vdup.32 q1, %[additive_sum_offset]\n"
8282 "vpaddl.u16 q8, q8\n"
8283 "vpaddl.u16 q9, q9\n"
8284 "vpaddl.u16 q10, q10\n"
8285 "vpaddl.u16 q11, q11\n"
8286 "vpaddl.u16 q12, q12\n"
8287 "vpadd.u32 d16, d16, d17\n"
8288 "vpadd.u32 d18, d18, d19\n"
8289 "vpadd.u32 d20, d20, d21\n"
8290 "vpadd.u32 d22, d22, d23\n"
8291 "vpadd.u32 d24, d24, d25\n"
8292 "vpadd.u32 d16, d16, d18\n"
8293 "vpadd.u32 d17, d20, d22\n"
8294 "vpadd.u32 d18, d24, d24\n"
8295 "vmul.i32 q8, q8, d0[0]\n"
8296 "vmul.i32 q9, q9, d0[0]\n"
8297 "vadd.i32 q8, q8, q1\n"
8298 "vadd.i32 q9, q9, q1\n"
8299 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
8300 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
8301 [out] "+r"(out), [in] "+r"(in)
8302 : [additive_sum_offset] "r"(params.additive_sum_offset),
8303 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
8304 : "d0", "d1", "d2", "d3", "d4", "d16", "d17", "d18", "d19", "d20", "d21",
8305 "d22", "d23", "d24", "d25", "cc", "memory");
8306 }
8307
8308 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)8309 inline void Stream<uint8_t, 5, 8, 1, ColumnMajorWithSum>::Pack(
8310 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
8311 #ifdef DEBUG
8312 #ifdef DEBUG_METAGEMM_VERBOSE
8313 std::cout
8314 << __FILE__ << "(" << __LINE__
8315 << ") ColumnMajorWithSum<uint8_t, 5, 8, 1, ColumnMajorWithSum>::Pack()"
8316 << std::endl
8317 << std::flush;
8318 #endif
8319 #endif
8320 int params_count_copy = params.count;
8321 int params_stride_copy = params.stride;
8322 asm volatile(
8323 "sub %[stride], %[stride], #4\n"
8324 "vmov.i16 q8, #0\n"
8325 "vmov.i16 q9, #0\n"
8326 "vmov.i16 q10, #0\n"
8327 "vmov.i16 q11, #0\n"
8328 "vmov.i16 q12, #0\n"
8329
8330 // Reduce count by leftovers.
8331 "subs %[count], %[count], #1\n"
8332 "beq 2f\n"
8333
8334 "1:"
8335 "subs %[count], %[count], #8\n"
8336
8337 // Load Aggregate Store - column major 5x8
8338 "vld1.32 {d0[0]}, [%[in]]!\n"
8339 "vld1.8 {d4[0]}, [%[in]], %[stride]\n"
8340 "vld1.32 {d1[0]}, [%[in]]!\n"
8341 "vld1.8 {d4[1]}, [%[in]], %[stride]\n"
8342 "vld1.32 {d2[0]}, [%[in]]!\n"
8343 "vld1.8 {d4[2]}, [%[in]], %[stride]\n"
8344 "vld1.32 {d3[0]}, [%[in]]!\n"
8345 "vld1.8 {d4[3]}, [%[in]], %[stride]\n"
8346 "vld1.32 {d0[1]}, [%[in]]!\n"
8347 "vld1.8 {d4[4]}, [%[in]], %[stride]\n"
8348 "vld1.32 {d1[1]}, [%[in]]!\n"
8349 "vld1.8 {d4[5]}, [%[in]], %[stride]\n"
8350 "vld1.32 {d2[1]}, [%[in]]!\n"
8351 "vld1.8 {d4[6]}, [%[in]], %[stride]\n"
8352 "vld1.32 {d3[1]}, [%[in]]!\n"
8353 "vld1.8 {d4[7]}, [%[in]], %[stride]\n"
8354 "pld [%[in]]\n"
8355 "vtrn.16 d0, d2\n"
8356 "vtrn.16 d1, d3\n"
8357 "vtrn.8 d0, d1\n"
8358 "vtrn.8 d2, d3\n"
8359 "vaddw.u8 q8, q8, d0\n"
8360 "vaddw.u8 q9, q9, d1\n"
8361 "vaddw.u8 q10, q10, d2\n"
8362 "vaddw.u8 q11, q11, d3\n"
8363 "vaddw.u8 q12, q12, d4\n"
8364 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
8365 "vst1.32 {d4}, [%[out]:64]!\n"
8366
8367 "bne 1b\n"
8368
8369 "2:"
8370
8371 // Load Aggregate Store - column major 5x1
8372 "vmov.i8 d0, #0\n"
8373 "vmov.i8 d1, #0\n"
8374 "vmov.i8 d2, #0\n"
8375 "vmov.i8 d3, #0\n"
8376 "vmov.i8 d4, #0\n"
8377 "vld1.32 {d0[0]}, [%[in]]!\n"
8378 "vld1.8 {d4[0]}, [%[in]], %[stride]\n"
8379 "pld [%[in]]\n"
8380 "vtrn.16 d0, d2\n"
8381 "vtrn.16 d1, d3\n"
8382 "vtrn.8 d0, d1\n"
8383 "vtrn.8 d2, d3\n"
8384 "vaddw.u8 q8, q8, d0\n"
8385 "vaddw.u8 q9, q9, d1\n"
8386 "vaddw.u8 q10, q10, d2\n"
8387 "vaddw.u8 q11, q11, d3\n"
8388 "vaddw.u8 q12, q12, d4\n"
8389 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
8390 "vst1.32 {d4}, [%[out]:64]!\n"
8391
8392 // Aggregator Reduction.
8393 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
8394 "vdup.32 q1, %[additive_sum_offset]\n"
8395 "vpaddl.u16 q8, q8\n"
8396 "vpaddl.u16 q9, q9\n"
8397 "vpaddl.u16 q10, q10\n"
8398 "vpaddl.u16 q11, q11\n"
8399 "vpaddl.u16 q12, q12\n"
8400 "vpadd.u32 d16, d16, d17\n"
8401 "vpadd.u32 d18, d18, d19\n"
8402 "vpadd.u32 d20, d20, d21\n"
8403 "vpadd.u32 d22, d22, d23\n"
8404 "vpadd.u32 d24, d24, d25\n"
8405 "vpadd.u32 d16, d16, d18\n"
8406 "vpadd.u32 d17, d20, d22\n"
8407 "vpadd.u32 d18, d24, d24\n"
8408 "vmul.i32 q8, q8, d0[0]\n"
8409 "vmul.i32 q9, q9, d0[0]\n"
8410 "vadd.i32 q8, q8, q1\n"
8411 "vadd.i32 q9, q9, q1\n"
8412 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
8413 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
8414 [out] "+r"(out), [in] "+r"(in)
8415 : [additive_sum_offset] "r"(params.additive_sum_offset),
8416 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
8417 : "d0", "d1", "d2", "d3", "d4", "d16", "d17", "d18", "d19", "d20", "d21",
8418 "d22", "d23", "d24", "d25", "cc", "memory");
8419 }
8420
8421 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)8422 inline void Stream<uint8_t, 5, 8, 2, ColumnMajorWithSum>::Pack(
8423 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
8424 #ifdef DEBUG
8425 #ifdef DEBUG_METAGEMM_VERBOSE
8426 std::cout
8427 << __FILE__ << "(" << __LINE__
8428 << ") ColumnMajorWithSum<uint8_t, 5, 8, 2, ColumnMajorWithSum>::Pack()"
8429 << std::endl
8430 << std::flush;
8431 #endif
8432 #endif
8433 int params_count_copy = params.count;
8434 int params_stride_copy = params.stride;
8435 asm volatile(
8436 "sub %[stride], %[stride], #4\n"
8437 "vmov.i16 q8, #0\n"
8438 "vmov.i16 q9, #0\n"
8439 "vmov.i16 q10, #0\n"
8440 "vmov.i16 q11, #0\n"
8441 "vmov.i16 q12, #0\n"
8442
8443 // Reduce count by leftovers.
8444 "subs %[count], %[count], #2\n"
8445 "beq 2f\n"
8446
8447 "1:"
8448 "subs %[count], %[count], #8\n"
8449
8450 // Load Aggregate Store - column major 5x8
8451 "vld1.32 {d0[0]}, [%[in]]!\n"
8452 "vld1.8 {d4[0]}, [%[in]], %[stride]\n"
8453 "vld1.32 {d1[0]}, [%[in]]!\n"
8454 "vld1.8 {d4[1]}, [%[in]], %[stride]\n"
8455 "vld1.32 {d2[0]}, [%[in]]!\n"
8456 "vld1.8 {d4[2]}, [%[in]], %[stride]\n"
8457 "vld1.32 {d3[0]}, [%[in]]!\n"
8458 "vld1.8 {d4[3]}, [%[in]], %[stride]\n"
8459 "vld1.32 {d0[1]}, [%[in]]!\n"
8460 "vld1.8 {d4[4]}, [%[in]], %[stride]\n"
8461 "vld1.32 {d1[1]}, [%[in]]!\n"
8462 "vld1.8 {d4[5]}, [%[in]], %[stride]\n"
8463 "vld1.32 {d2[1]}, [%[in]]!\n"
8464 "vld1.8 {d4[6]}, [%[in]], %[stride]\n"
8465 "vld1.32 {d3[1]}, [%[in]]!\n"
8466 "vld1.8 {d4[7]}, [%[in]], %[stride]\n"
8467 "pld [%[in]]\n"
8468 "vtrn.16 d0, d2\n"
8469 "vtrn.16 d1, d3\n"
8470 "vtrn.8 d0, d1\n"
8471 "vtrn.8 d2, d3\n"
8472 "vaddw.u8 q8, q8, d0\n"
8473 "vaddw.u8 q9, q9, d1\n"
8474 "vaddw.u8 q10, q10, d2\n"
8475 "vaddw.u8 q11, q11, d3\n"
8476 "vaddw.u8 q12, q12, d4\n"
8477 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
8478 "vst1.32 {d4}, [%[out]:64]!\n"
8479
8480 "bne 1b\n"
8481
8482 "2:"
8483
8484 // Load Aggregate Store - column major 5x2
8485 "vmov.i8 d0, #0\n"
8486 "vmov.i8 d1, #0\n"
8487 "vmov.i8 d2, #0\n"
8488 "vmov.i8 d3, #0\n"
8489 "vmov.i8 d4, #0\n"
8490 "vld1.32 {d0[0]}, [%[in]]!\n"
8491 "vld1.8 {d4[0]}, [%[in]], %[stride]\n"
8492 "vld1.32 {d1[0]}, [%[in]]!\n"
8493 "vld1.8 {d4[1]}, [%[in]], %[stride]\n"
8494 "pld [%[in]]\n"
8495 "vtrn.16 d0, d2\n"
8496 "vtrn.16 d1, d3\n"
8497 "vtrn.8 d0, d1\n"
8498 "vtrn.8 d2, d3\n"
8499 "vaddw.u8 q8, q8, d0\n"
8500 "vaddw.u8 q9, q9, d1\n"
8501 "vaddw.u8 q10, q10, d2\n"
8502 "vaddw.u8 q11, q11, d3\n"
8503 "vaddw.u8 q12, q12, d4\n"
8504 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
8505 "vst1.32 {d4}, [%[out]:64]!\n"
8506
8507 // Aggregator Reduction.
8508 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
8509 "vdup.32 q1, %[additive_sum_offset]\n"
8510 "vpaddl.u16 q8, q8\n"
8511 "vpaddl.u16 q9, q9\n"
8512 "vpaddl.u16 q10, q10\n"
8513 "vpaddl.u16 q11, q11\n"
8514 "vpaddl.u16 q12, q12\n"
8515 "vpadd.u32 d16, d16, d17\n"
8516 "vpadd.u32 d18, d18, d19\n"
8517 "vpadd.u32 d20, d20, d21\n"
8518 "vpadd.u32 d22, d22, d23\n"
8519 "vpadd.u32 d24, d24, d25\n"
8520 "vpadd.u32 d16, d16, d18\n"
8521 "vpadd.u32 d17, d20, d22\n"
8522 "vpadd.u32 d18, d24, d24\n"
8523 "vmul.i32 q8, q8, d0[0]\n"
8524 "vmul.i32 q9, q9, d0[0]\n"
8525 "vadd.i32 q8, q8, q1\n"
8526 "vadd.i32 q9, q9, q1\n"
8527 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
8528 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
8529 [out] "+r"(out), [in] "+r"(in)
8530 : [additive_sum_offset] "r"(params.additive_sum_offset),
8531 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
8532 : "d0", "d1", "d2", "d3", "d4", "d16", "d17", "d18", "d19", "d20", "d21",
8533 "d22", "d23", "d24", "d25", "cc", "memory");
8534 }
8535
8536 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)8537 inline void Stream<uint8_t, 5, 8, 3, ColumnMajorWithSum>::Pack(
8538 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
8539 #ifdef DEBUG
8540 #ifdef DEBUG_METAGEMM_VERBOSE
8541 std::cout
8542 << __FILE__ << "(" << __LINE__
8543 << ") ColumnMajorWithSum<uint8_t, 5, 8, 3, ColumnMajorWithSum>::Pack()"
8544 << std::endl
8545 << std::flush;
8546 #endif
8547 #endif
8548 int params_count_copy = params.count;
8549 int params_stride_copy = params.stride;
8550 asm volatile(
8551 "sub %[stride], %[stride], #4\n"
8552 "vmov.i16 q8, #0\n"
8553 "vmov.i16 q9, #0\n"
8554 "vmov.i16 q10, #0\n"
8555 "vmov.i16 q11, #0\n"
8556 "vmov.i16 q12, #0\n"
8557
8558 // Reduce count by leftovers.
8559 "subs %[count], %[count], #3\n"
8560 "beq 2f\n"
8561
8562 "1:"
8563 "subs %[count], %[count], #8\n"
8564
8565 // Load Aggregate Store - column major 5x8
8566 "vld1.32 {d0[0]}, [%[in]]!\n"
8567 "vld1.8 {d4[0]}, [%[in]], %[stride]\n"
8568 "vld1.32 {d1[0]}, [%[in]]!\n"
8569 "vld1.8 {d4[1]}, [%[in]], %[stride]\n"
8570 "vld1.32 {d2[0]}, [%[in]]!\n"
8571 "vld1.8 {d4[2]}, [%[in]], %[stride]\n"
8572 "vld1.32 {d3[0]}, [%[in]]!\n"
8573 "vld1.8 {d4[3]}, [%[in]], %[stride]\n"
8574 "vld1.32 {d0[1]}, [%[in]]!\n"
8575 "vld1.8 {d4[4]}, [%[in]], %[stride]\n"
8576 "vld1.32 {d1[1]}, [%[in]]!\n"
8577 "vld1.8 {d4[5]}, [%[in]], %[stride]\n"
8578 "vld1.32 {d2[1]}, [%[in]]!\n"
8579 "vld1.8 {d4[6]}, [%[in]], %[stride]\n"
8580 "vld1.32 {d3[1]}, [%[in]]!\n"
8581 "vld1.8 {d4[7]}, [%[in]], %[stride]\n"
8582 "pld [%[in]]\n"
8583 "vtrn.16 d0, d2\n"
8584 "vtrn.16 d1, d3\n"
8585 "vtrn.8 d0, d1\n"
8586 "vtrn.8 d2, d3\n"
8587 "vaddw.u8 q8, q8, d0\n"
8588 "vaddw.u8 q9, q9, d1\n"
8589 "vaddw.u8 q10, q10, d2\n"
8590 "vaddw.u8 q11, q11, d3\n"
8591 "vaddw.u8 q12, q12, d4\n"
8592 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
8593 "vst1.32 {d4}, [%[out]:64]!\n"
8594
8595 "bne 1b\n"
8596
8597 "2:"
8598
8599 // Load Aggregate Store - column major 5x3
8600 "vmov.i8 d0, #0\n"
8601 "vmov.i8 d1, #0\n"
8602 "vmov.i8 d2, #0\n"
8603 "vmov.i8 d3, #0\n"
8604 "vmov.i8 d4, #0\n"
8605 "vld1.32 {d0[0]}, [%[in]]!\n"
8606 "vld1.8 {d4[0]}, [%[in]], %[stride]\n"
8607 "vld1.32 {d1[0]}, [%[in]]!\n"
8608 "vld1.8 {d4[1]}, [%[in]], %[stride]\n"
8609 "vld1.32 {d2[0]}, [%[in]]!\n"
8610 "vld1.8 {d4[2]}, [%[in]], %[stride]\n"
8611 "pld [%[in]]\n"
8612 "vtrn.16 d0, d2\n"
8613 "vtrn.16 d1, d3\n"
8614 "vtrn.8 d0, d1\n"
8615 "vtrn.8 d2, d3\n"
8616 "vaddw.u8 q8, q8, d0\n"
8617 "vaddw.u8 q9, q9, d1\n"
8618 "vaddw.u8 q10, q10, d2\n"
8619 "vaddw.u8 q11, q11, d3\n"
8620 "vaddw.u8 q12, q12, d4\n"
8621 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
8622 "vst1.32 {d4}, [%[out]:64]!\n"
8623
8624 // Aggregator Reduction.
8625 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
8626 "vdup.32 q1, %[additive_sum_offset]\n"
8627 "vpaddl.u16 q8, q8\n"
8628 "vpaddl.u16 q9, q9\n"
8629 "vpaddl.u16 q10, q10\n"
8630 "vpaddl.u16 q11, q11\n"
8631 "vpaddl.u16 q12, q12\n"
8632 "vpadd.u32 d16, d16, d17\n"
8633 "vpadd.u32 d18, d18, d19\n"
8634 "vpadd.u32 d20, d20, d21\n"
8635 "vpadd.u32 d22, d22, d23\n"
8636 "vpadd.u32 d24, d24, d25\n"
8637 "vpadd.u32 d16, d16, d18\n"
8638 "vpadd.u32 d17, d20, d22\n"
8639 "vpadd.u32 d18, d24, d24\n"
8640 "vmul.i32 q8, q8, d0[0]\n"
8641 "vmul.i32 q9, q9, d0[0]\n"
8642 "vadd.i32 q8, q8, q1\n"
8643 "vadd.i32 q9, q9, q1\n"
8644 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
8645 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
8646 [out] "+r"(out), [in] "+r"(in)
8647 : [additive_sum_offset] "r"(params.additive_sum_offset),
8648 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
8649 : "d0", "d1", "d2", "d3", "d4", "d16", "d17", "d18", "d19", "d20", "d21",
8650 "d22", "d23", "d24", "d25", "cc", "memory");
8651 }
8652
8653 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)8654 inline void Stream<uint8_t, 5, 8, 4, ColumnMajorWithSum>::Pack(
8655 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
8656 #ifdef DEBUG
8657 #ifdef DEBUG_METAGEMM_VERBOSE
8658 std::cout
8659 << __FILE__ << "(" << __LINE__
8660 << ") ColumnMajorWithSum<uint8_t, 5, 8, 4, ColumnMajorWithSum>::Pack()"
8661 << std::endl
8662 << std::flush;
8663 #endif
8664 #endif
8665 int params_count_copy = params.count;
8666 int params_stride_copy = params.stride;
8667 asm volatile(
8668 "sub %[stride], %[stride], #4\n"
8669 "vmov.i16 q8, #0\n"
8670 "vmov.i16 q9, #0\n"
8671 "vmov.i16 q10, #0\n"
8672 "vmov.i16 q11, #0\n"
8673 "vmov.i16 q12, #0\n"
8674
8675 // Reduce count by leftovers.
8676 "subs %[count], %[count], #4\n"
8677 "beq 2f\n"
8678
8679 "1:"
8680 "subs %[count], %[count], #8\n"
8681
8682 // Load Aggregate Store - column major 5x8
8683 "vld1.32 {d0[0]}, [%[in]]!\n"
8684 "vld1.8 {d4[0]}, [%[in]], %[stride]\n"
8685 "vld1.32 {d1[0]}, [%[in]]!\n"
8686 "vld1.8 {d4[1]}, [%[in]], %[stride]\n"
8687 "vld1.32 {d2[0]}, [%[in]]!\n"
8688 "vld1.8 {d4[2]}, [%[in]], %[stride]\n"
8689 "vld1.32 {d3[0]}, [%[in]]!\n"
8690 "vld1.8 {d4[3]}, [%[in]], %[stride]\n"
8691 "vld1.32 {d0[1]}, [%[in]]!\n"
8692 "vld1.8 {d4[4]}, [%[in]], %[stride]\n"
8693 "vld1.32 {d1[1]}, [%[in]]!\n"
8694 "vld1.8 {d4[5]}, [%[in]], %[stride]\n"
8695 "vld1.32 {d2[1]}, [%[in]]!\n"
8696 "vld1.8 {d4[6]}, [%[in]], %[stride]\n"
8697 "vld1.32 {d3[1]}, [%[in]]!\n"
8698 "vld1.8 {d4[7]}, [%[in]], %[stride]\n"
8699 "pld [%[in]]\n"
8700 "vtrn.16 d0, d2\n"
8701 "vtrn.16 d1, d3\n"
8702 "vtrn.8 d0, d1\n"
8703 "vtrn.8 d2, d3\n"
8704 "vaddw.u8 q8, q8, d0\n"
8705 "vaddw.u8 q9, q9, d1\n"
8706 "vaddw.u8 q10, q10, d2\n"
8707 "vaddw.u8 q11, q11, d3\n"
8708 "vaddw.u8 q12, q12, d4\n"
8709 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
8710 "vst1.32 {d4}, [%[out]:64]!\n"
8711
8712 "bne 1b\n"
8713
8714 "2:"
8715
8716 // Load Aggregate Store - column major 5x4
8717 "vmov.i8 d0, #0\n"
8718 "vmov.i8 d1, #0\n"
8719 "vmov.i8 d2, #0\n"
8720 "vmov.i8 d3, #0\n"
8721 "vmov.i8 d4, #0\n"
8722 "vld1.32 {d0[0]}, [%[in]]!\n"
8723 "vld1.8 {d4[0]}, [%[in]], %[stride]\n"
8724 "vld1.32 {d1[0]}, [%[in]]!\n"
8725 "vld1.8 {d4[1]}, [%[in]], %[stride]\n"
8726 "vld1.32 {d2[0]}, [%[in]]!\n"
8727 "vld1.8 {d4[2]}, [%[in]], %[stride]\n"
8728 "vld1.32 {d3[0]}, [%[in]]!\n"
8729 "vld1.8 {d4[3]}, [%[in]], %[stride]\n"
8730 "pld [%[in]]\n"
8731 "vtrn.16 d0, d2\n"
8732 "vtrn.16 d1, d3\n"
8733 "vtrn.8 d0, d1\n"
8734 "vtrn.8 d2, d3\n"
8735 "vaddw.u8 q8, q8, d0\n"
8736 "vaddw.u8 q9, q9, d1\n"
8737 "vaddw.u8 q10, q10, d2\n"
8738 "vaddw.u8 q11, q11, d3\n"
8739 "vaddw.u8 q12, q12, d4\n"
8740 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
8741 "vst1.32 {d4}, [%[out]:64]!\n"
8742
8743 // Aggregator Reduction.
8744 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
8745 "vdup.32 q1, %[additive_sum_offset]\n"
8746 "vpaddl.u16 q8, q8\n"
8747 "vpaddl.u16 q9, q9\n"
8748 "vpaddl.u16 q10, q10\n"
8749 "vpaddl.u16 q11, q11\n"
8750 "vpaddl.u16 q12, q12\n"
8751 "vpadd.u32 d16, d16, d17\n"
8752 "vpadd.u32 d18, d18, d19\n"
8753 "vpadd.u32 d20, d20, d21\n"
8754 "vpadd.u32 d22, d22, d23\n"
8755 "vpadd.u32 d24, d24, d25\n"
8756 "vpadd.u32 d16, d16, d18\n"
8757 "vpadd.u32 d17, d20, d22\n"
8758 "vpadd.u32 d18, d24, d24\n"
8759 "vmul.i32 q8, q8, d0[0]\n"
8760 "vmul.i32 q9, q9, d0[0]\n"
8761 "vadd.i32 q8, q8, q1\n"
8762 "vadd.i32 q9, q9, q1\n"
8763 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
8764 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
8765 [out] "+r"(out), [in] "+r"(in)
8766 : [additive_sum_offset] "r"(params.additive_sum_offset),
8767 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
8768 : "d0", "d1", "d2", "d3", "d4", "d16", "d17", "d18", "d19", "d20", "d21",
8769 "d22", "d23", "d24", "d25", "cc", "memory");
8770 }
8771
8772 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)8773 inline void Stream<uint8_t, 5, 8, 5, ColumnMajorWithSum>::Pack(
8774 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
8775 #ifdef DEBUG
8776 #ifdef DEBUG_METAGEMM_VERBOSE
8777 std::cout
8778 << __FILE__ << "(" << __LINE__
8779 << ") ColumnMajorWithSum<uint8_t, 5, 8, 5, ColumnMajorWithSum>::Pack()"
8780 << std::endl
8781 << std::flush;
8782 #endif
8783 #endif
8784 int params_count_copy = params.count;
8785 int params_stride_copy = params.stride;
8786 asm volatile(
8787 "sub %[stride], %[stride], #4\n"
8788 "vmov.i16 q8, #0\n"
8789 "vmov.i16 q9, #0\n"
8790 "vmov.i16 q10, #0\n"
8791 "vmov.i16 q11, #0\n"
8792 "vmov.i16 q12, #0\n"
8793
8794 // Reduce count by leftovers.
8795 "subs %[count], %[count], #5\n"
8796 "beq 2f\n"
8797
8798 "1:"
8799 "subs %[count], %[count], #8\n"
8800
8801 // Load Aggregate Store - column major 5x8
8802 "vld1.32 {d0[0]}, [%[in]]!\n"
8803 "vld1.8 {d4[0]}, [%[in]], %[stride]\n"
8804 "vld1.32 {d1[0]}, [%[in]]!\n"
8805 "vld1.8 {d4[1]}, [%[in]], %[stride]\n"
8806 "vld1.32 {d2[0]}, [%[in]]!\n"
8807 "vld1.8 {d4[2]}, [%[in]], %[stride]\n"
8808 "vld1.32 {d3[0]}, [%[in]]!\n"
8809 "vld1.8 {d4[3]}, [%[in]], %[stride]\n"
8810 "vld1.32 {d0[1]}, [%[in]]!\n"
8811 "vld1.8 {d4[4]}, [%[in]], %[stride]\n"
8812 "vld1.32 {d1[1]}, [%[in]]!\n"
8813 "vld1.8 {d4[5]}, [%[in]], %[stride]\n"
8814 "vld1.32 {d2[1]}, [%[in]]!\n"
8815 "vld1.8 {d4[6]}, [%[in]], %[stride]\n"
8816 "vld1.32 {d3[1]}, [%[in]]!\n"
8817 "vld1.8 {d4[7]}, [%[in]], %[stride]\n"
8818 "pld [%[in]]\n"
8819 "vtrn.16 d0, d2\n"
8820 "vtrn.16 d1, d3\n"
8821 "vtrn.8 d0, d1\n"
8822 "vtrn.8 d2, d3\n"
8823 "vaddw.u8 q8, q8, d0\n"
8824 "vaddw.u8 q9, q9, d1\n"
8825 "vaddw.u8 q10, q10, d2\n"
8826 "vaddw.u8 q11, q11, d3\n"
8827 "vaddw.u8 q12, q12, d4\n"
8828 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
8829 "vst1.32 {d4}, [%[out]:64]!\n"
8830
8831 "bne 1b\n"
8832
8833 "2:"
8834
8835 // Load Aggregate Store - column major 5x5
8836 "vmov.i8 d0, #0\n"
8837 "vmov.i8 d1, #0\n"
8838 "vmov.i8 d2, #0\n"
8839 "vmov.i8 d3, #0\n"
8840 "vmov.i8 d4, #0\n"
8841 "vld1.32 {d0[0]}, [%[in]]!\n"
8842 "vld1.8 {d4[0]}, [%[in]], %[stride]\n"
8843 "vld1.32 {d1[0]}, [%[in]]!\n"
8844 "vld1.8 {d4[1]}, [%[in]], %[stride]\n"
8845 "vld1.32 {d2[0]}, [%[in]]!\n"
8846 "vld1.8 {d4[2]}, [%[in]], %[stride]\n"
8847 "vld1.32 {d3[0]}, [%[in]]!\n"
8848 "vld1.8 {d4[3]}, [%[in]], %[stride]\n"
8849 "vld1.32 {d0[1]}, [%[in]]!\n"
8850 "vld1.8 {d4[4]}, [%[in]], %[stride]\n"
8851 "pld [%[in]]\n"
8852 "vtrn.16 d0, d2\n"
8853 "vtrn.16 d1, d3\n"
8854 "vtrn.8 d0, d1\n"
8855 "vtrn.8 d2, d3\n"
8856 "vaddw.u8 q8, q8, d0\n"
8857 "vaddw.u8 q9, q9, d1\n"
8858 "vaddw.u8 q10, q10, d2\n"
8859 "vaddw.u8 q11, q11, d3\n"
8860 "vaddw.u8 q12, q12, d4\n"
8861 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
8862 "vst1.32 {d4}, [%[out]:64]!\n"
8863
8864 // Aggregator Reduction.
8865 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
8866 "vdup.32 q1, %[additive_sum_offset]\n"
8867 "vpaddl.u16 q8, q8\n"
8868 "vpaddl.u16 q9, q9\n"
8869 "vpaddl.u16 q10, q10\n"
8870 "vpaddl.u16 q11, q11\n"
8871 "vpaddl.u16 q12, q12\n"
8872 "vpadd.u32 d16, d16, d17\n"
8873 "vpadd.u32 d18, d18, d19\n"
8874 "vpadd.u32 d20, d20, d21\n"
8875 "vpadd.u32 d22, d22, d23\n"
8876 "vpadd.u32 d24, d24, d25\n"
8877 "vpadd.u32 d16, d16, d18\n"
8878 "vpadd.u32 d17, d20, d22\n"
8879 "vpadd.u32 d18, d24, d24\n"
8880 "vmul.i32 q8, q8, d0[0]\n"
8881 "vmul.i32 q9, q9, d0[0]\n"
8882 "vadd.i32 q8, q8, q1\n"
8883 "vadd.i32 q9, q9, q1\n"
8884 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
8885 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
8886 [out] "+r"(out), [in] "+r"(in)
8887 : [additive_sum_offset] "r"(params.additive_sum_offset),
8888 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
8889 : "d0", "d1", "d2", "d3", "d4", "d16", "d17", "d18", "d19", "d20", "d21",
8890 "d22", "d23", "d24", "d25", "cc", "memory");
8891 }
8892
8893 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)8894 inline void Stream<uint8_t, 5, 8, 6, ColumnMajorWithSum>::Pack(
8895 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
8896 #ifdef DEBUG
8897 #ifdef DEBUG_METAGEMM_VERBOSE
8898 std::cout
8899 << __FILE__ << "(" << __LINE__
8900 << ") ColumnMajorWithSum<uint8_t, 5, 8, 6, ColumnMajorWithSum>::Pack()"
8901 << std::endl
8902 << std::flush;
8903 #endif
8904 #endif
8905 int params_count_copy = params.count;
8906 int params_stride_copy = params.stride;
8907 asm volatile(
8908 "sub %[stride], %[stride], #4\n"
8909 "vmov.i16 q8, #0\n"
8910 "vmov.i16 q9, #0\n"
8911 "vmov.i16 q10, #0\n"
8912 "vmov.i16 q11, #0\n"
8913 "vmov.i16 q12, #0\n"
8914
8915 // Reduce count by leftovers.
8916 "subs %[count], %[count], #6\n"
8917 "beq 2f\n"
8918
8919 "1:"
8920 "subs %[count], %[count], #8\n"
8921
8922 // Load Aggregate Store - column major 5x8
8923 "vld1.32 {d0[0]}, [%[in]]!\n"
8924 "vld1.8 {d4[0]}, [%[in]], %[stride]\n"
8925 "vld1.32 {d1[0]}, [%[in]]!\n"
8926 "vld1.8 {d4[1]}, [%[in]], %[stride]\n"
8927 "vld1.32 {d2[0]}, [%[in]]!\n"
8928 "vld1.8 {d4[2]}, [%[in]], %[stride]\n"
8929 "vld1.32 {d3[0]}, [%[in]]!\n"
8930 "vld1.8 {d4[3]}, [%[in]], %[stride]\n"
8931 "vld1.32 {d0[1]}, [%[in]]!\n"
8932 "vld1.8 {d4[4]}, [%[in]], %[stride]\n"
8933 "vld1.32 {d1[1]}, [%[in]]!\n"
8934 "vld1.8 {d4[5]}, [%[in]], %[stride]\n"
8935 "vld1.32 {d2[1]}, [%[in]]!\n"
8936 "vld1.8 {d4[6]}, [%[in]], %[stride]\n"
8937 "vld1.32 {d3[1]}, [%[in]]!\n"
8938 "vld1.8 {d4[7]}, [%[in]], %[stride]\n"
8939 "pld [%[in]]\n"
8940 "vtrn.16 d0, d2\n"
8941 "vtrn.16 d1, d3\n"
8942 "vtrn.8 d0, d1\n"
8943 "vtrn.8 d2, d3\n"
8944 "vaddw.u8 q8, q8, d0\n"
8945 "vaddw.u8 q9, q9, d1\n"
8946 "vaddw.u8 q10, q10, d2\n"
8947 "vaddw.u8 q11, q11, d3\n"
8948 "vaddw.u8 q12, q12, d4\n"
8949 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
8950 "vst1.32 {d4}, [%[out]:64]!\n"
8951
8952 "bne 1b\n"
8953
8954 "2:"
8955
8956 // Load Aggregate Store - column major 5x6
8957 "vmov.i8 d0, #0\n"
8958 "vmov.i8 d1, #0\n"
8959 "vmov.i8 d2, #0\n"
8960 "vmov.i8 d3, #0\n"
8961 "vmov.i8 d4, #0\n"
8962 "vld1.32 {d0[0]}, [%[in]]!\n"
8963 "vld1.8 {d4[0]}, [%[in]], %[stride]\n"
8964 "vld1.32 {d1[0]}, [%[in]]!\n"
8965 "vld1.8 {d4[1]}, [%[in]], %[stride]\n"
8966 "vld1.32 {d2[0]}, [%[in]]!\n"
8967 "vld1.8 {d4[2]}, [%[in]], %[stride]\n"
8968 "vld1.32 {d3[0]}, [%[in]]!\n"
8969 "vld1.8 {d4[3]}, [%[in]], %[stride]\n"
8970 "vld1.32 {d0[1]}, [%[in]]!\n"
8971 "vld1.8 {d4[4]}, [%[in]], %[stride]\n"
8972 "vld1.32 {d1[1]}, [%[in]]!\n"
8973 "vld1.8 {d4[5]}, [%[in]], %[stride]\n"
8974 "pld [%[in]]\n"
8975 "vtrn.16 d0, d2\n"
8976 "vtrn.16 d1, d3\n"
8977 "vtrn.8 d0, d1\n"
8978 "vtrn.8 d2, d3\n"
8979 "vaddw.u8 q8, q8, d0\n"
8980 "vaddw.u8 q9, q9, d1\n"
8981 "vaddw.u8 q10, q10, d2\n"
8982 "vaddw.u8 q11, q11, d3\n"
8983 "vaddw.u8 q12, q12, d4\n"
8984 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
8985 "vst1.32 {d4}, [%[out]:64]!\n"
8986
8987 // Aggregator Reduction.
8988 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
8989 "vdup.32 q1, %[additive_sum_offset]\n"
8990 "vpaddl.u16 q8, q8\n"
8991 "vpaddl.u16 q9, q9\n"
8992 "vpaddl.u16 q10, q10\n"
8993 "vpaddl.u16 q11, q11\n"
8994 "vpaddl.u16 q12, q12\n"
8995 "vpadd.u32 d16, d16, d17\n"
8996 "vpadd.u32 d18, d18, d19\n"
8997 "vpadd.u32 d20, d20, d21\n"
8998 "vpadd.u32 d22, d22, d23\n"
8999 "vpadd.u32 d24, d24, d25\n"
9000 "vpadd.u32 d16, d16, d18\n"
9001 "vpadd.u32 d17, d20, d22\n"
9002 "vpadd.u32 d18, d24, d24\n"
9003 "vmul.i32 q8, q8, d0[0]\n"
9004 "vmul.i32 q9, q9, d0[0]\n"
9005 "vadd.i32 q8, q8, q1\n"
9006 "vadd.i32 q9, q9, q1\n"
9007 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
9008 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
9009 [out] "+r"(out), [in] "+r"(in)
9010 : [additive_sum_offset] "r"(params.additive_sum_offset),
9011 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
9012 : "d0", "d1", "d2", "d3", "d4", "d16", "d17", "d18", "d19", "d20", "d21",
9013 "d22", "d23", "d24", "d25", "cc", "memory");
9014 }
9015
9016 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)9017 inline void Stream<uint8_t, 5, 8, 7, ColumnMajorWithSum>::Pack(
9018 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
9019 #ifdef DEBUG
9020 #ifdef DEBUG_METAGEMM_VERBOSE
9021 std::cout
9022 << __FILE__ << "(" << __LINE__
9023 << ") ColumnMajorWithSum<uint8_t, 5, 8, 7, ColumnMajorWithSum>::Pack()"
9024 << std::endl
9025 << std::flush;
9026 #endif
9027 #endif
9028 int params_count_copy = params.count;
9029 int params_stride_copy = params.stride;
9030 asm volatile(
9031 "sub %[stride], %[stride], #4\n"
9032 "vmov.i16 q8, #0\n"
9033 "vmov.i16 q9, #0\n"
9034 "vmov.i16 q10, #0\n"
9035 "vmov.i16 q11, #0\n"
9036 "vmov.i16 q12, #0\n"
9037
9038 // Reduce count by leftovers.
9039 "subs %[count], %[count], #7\n"
9040 "beq 2f\n"
9041
9042 "1:"
9043 "subs %[count], %[count], #8\n"
9044
9045 // Load Aggregate Store - column major 5x8
9046 "vld1.32 {d0[0]}, [%[in]]!\n"
9047 "vld1.8 {d4[0]}, [%[in]], %[stride]\n"
9048 "vld1.32 {d1[0]}, [%[in]]!\n"
9049 "vld1.8 {d4[1]}, [%[in]], %[stride]\n"
9050 "vld1.32 {d2[0]}, [%[in]]!\n"
9051 "vld1.8 {d4[2]}, [%[in]], %[stride]\n"
9052 "vld1.32 {d3[0]}, [%[in]]!\n"
9053 "vld1.8 {d4[3]}, [%[in]], %[stride]\n"
9054 "vld1.32 {d0[1]}, [%[in]]!\n"
9055 "vld1.8 {d4[4]}, [%[in]], %[stride]\n"
9056 "vld1.32 {d1[1]}, [%[in]]!\n"
9057 "vld1.8 {d4[5]}, [%[in]], %[stride]\n"
9058 "vld1.32 {d2[1]}, [%[in]]!\n"
9059 "vld1.8 {d4[6]}, [%[in]], %[stride]\n"
9060 "vld1.32 {d3[1]}, [%[in]]!\n"
9061 "vld1.8 {d4[7]}, [%[in]], %[stride]\n"
9062 "pld [%[in]]\n"
9063 "vtrn.16 d0, d2\n"
9064 "vtrn.16 d1, d3\n"
9065 "vtrn.8 d0, d1\n"
9066 "vtrn.8 d2, d3\n"
9067 "vaddw.u8 q8, q8, d0\n"
9068 "vaddw.u8 q9, q9, d1\n"
9069 "vaddw.u8 q10, q10, d2\n"
9070 "vaddw.u8 q11, q11, d3\n"
9071 "vaddw.u8 q12, q12, d4\n"
9072 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
9073 "vst1.32 {d4}, [%[out]:64]!\n"
9074
9075 "bne 1b\n"
9076
9077 "2:"
9078
9079 // Load Aggregate Store - column major 5x7
9080 "vmov.i8 d0, #0\n"
9081 "vmov.i8 d1, #0\n"
9082 "vmov.i8 d2, #0\n"
9083 "vmov.i8 d3, #0\n"
9084 "vmov.i8 d4, #0\n"
9085 "vld1.32 {d0[0]}, [%[in]]!\n"
9086 "vld1.8 {d4[0]}, [%[in]], %[stride]\n"
9087 "vld1.32 {d1[0]}, [%[in]]!\n"
9088 "vld1.8 {d4[1]}, [%[in]], %[stride]\n"
9089 "vld1.32 {d2[0]}, [%[in]]!\n"
9090 "vld1.8 {d4[2]}, [%[in]], %[stride]\n"
9091 "vld1.32 {d3[0]}, [%[in]]!\n"
9092 "vld1.8 {d4[3]}, [%[in]], %[stride]\n"
9093 "vld1.32 {d0[1]}, [%[in]]!\n"
9094 "vld1.8 {d4[4]}, [%[in]], %[stride]\n"
9095 "vld1.32 {d1[1]}, [%[in]]!\n"
9096 "vld1.8 {d4[5]}, [%[in]], %[stride]\n"
9097 "vld1.32 {d2[1]}, [%[in]]!\n"
9098 "vld1.8 {d4[6]}, [%[in]], %[stride]\n"
9099 "pld [%[in]]\n"
9100 "vtrn.16 d0, d2\n"
9101 "vtrn.16 d1, d3\n"
9102 "vtrn.8 d0, d1\n"
9103 "vtrn.8 d2, d3\n"
9104 "vaddw.u8 q8, q8, d0\n"
9105 "vaddw.u8 q9, q9, d1\n"
9106 "vaddw.u8 q10, q10, d2\n"
9107 "vaddw.u8 q11, q11, d3\n"
9108 "vaddw.u8 q12, q12, d4\n"
9109 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
9110 "vst1.32 {d4}, [%[out]:64]!\n"
9111
9112 // Aggregator Reduction.
9113 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
9114 "vdup.32 q1, %[additive_sum_offset]\n"
9115 "vpaddl.u16 q8, q8\n"
9116 "vpaddl.u16 q9, q9\n"
9117 "vpaddl.u16 q10, q10\n"
9118 "vpaddl.u16 q11, q11\n"
9119 "vpaddl.u16 q12, q12\n"
9120 "vpadd.u32 d16, d16, d17\n"
9121 "vpadd.u32 d18, d18, d19\n"
9122 "vpadd.u32 d20, d20, d21\n"
9123 "vpadd.u32 d22, d22, d23\n"
9124 "vpadd.u32 d24, d24, d25\n"
9125 "vpadd.u32 d16, d16, d18\n"
9126 "vpadd.u32 d17, d20, d22\n"
9127 "vpadd.u32 d18, d24, d24\n"
9128 "vmul.i32 q8, q8, d0[0]\n"
9129 "vmul.i32 q9, q9, d0[0]\n"
9130 "vadd.i32 q8, q8, q1\n"
9131 "vadd.i32 q9, q9, q1\n"
9132 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
9133 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
9134 [out] "+r"(out), [in] "+r"(in)
9135 : [additive_sum_offset] "r"(params.additive_sum_offset),
9136 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
9137 : "d0", "d1", "d2", "d3", "d4", "d16", "d17", "d18", "d19", "d20", "d21",
9138 "d22", "d23", "d24", "d25", "cc", "memory");
9139 }
9140
9141 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)9142 inline void Stream<uint8_t, 6, 8, 0, ColumnMajorWithSum>::Pack(
9143 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
9144 #ifdef DEBUG
9145 #ifdef DEBUG_METAGEMM_VERBOSE
9146 std::cout
9147 << __FILE__ << "(" << __LINE__
9148 << ") ColumnMajorWithSum<uint8_t, 6, 8, 0, ColumnMajorWithSum>::Pack()"
9149 << std::endl
9150 << std::flush;
9151 #endif
9152 #endif
9153 int params_count_copy = params.count;
9154 int params_stride_copy = params.stride;
9155 asm volatile(
9156 "sub %[stride], %[stride], #4\n"
9157 "vmov.i16 q8, #0\n"
9158 "vmov.i16 q9, #0\n"
9159 "vmov.i16 q10, #0\n"
9160 "vmov.i16 q11, #0\n"
9161 "vmov.i16 q12, #0\n"
9162 "vmov.i16 q13, #0\n"
9163
9164 "1:"
9165 "subs %[count], %[count], #8\n"
9166
9167 // Load Aggregate Store - column major 6x8
9168 "vld1.32 {d0[0]}, [%[in]]!\n"
9169 "vld1.16 {d4[0]}, [%[in]], %[stride]\n"
9170 "vld1.32 {d1[0]}, [%[in]]!\n"
9171 "vld1.16 {d4[1]}, [%[in]], %[stride]\n"
9172 "vld1.32 {d2[0]}, [%[in]]!\n"
9173 "vld1.16 {d4[2]}, [%[in]], %[stride]\n"
9174 "vld1.32 {d3[0]}, [%[in]]!\n"
9175 "vld1.16 {d4[3]}, [%[in]], %[stride]\n"
9176 "vld1.32 {d0[1]}, [%[in]]!\n"
9177 "vld1.16 {d5[0]}, [%[in]], %[stride]\n"
9178 "vld1.32 {d1[1]}, [%[in]]!\n"
9179 "vld1.16 {d5[1]}, [%[in]], %[stride]\n"
9180 "vld1.32 {d2[1]}, [%[in]]!\n"
9181 "vld1.16 {d5[2]}, [%[in]], %[stride]\n"
9182 "vld1.32 {d3[1]}, [%[in]]!\n"
9183 "vld1.16 {d5[3]}, [%[in]], %[stride]\n"
9184 "pld [%[in]]\n"
9185 "vtrn.16 d0, d2\n"
9186 "vtrn.16 d1, d3\n"
9187 "vuzp.8 d4, d5\n"
9188 "vtrn.8 d0, d1\n"
9189 "vtrn.8 d2, d3\n"
9190 "vaddw.u8 q8, q8, d0\n"
9191 "vaddw.u8 q9, q9, d1\n"
9192 "vaddw.u8 q10, q10, d2\n"
9193 "vaddw.u8 q11, q11, d3\n"
9194 "vaddw.u8 q12, q12, d4\n"
9195 "vaddw.u8 q13, q13, d5\n"
9196 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
9197 "vst1.32 {d4, d5}, [%[out]:128]!\n"
9198
9199 "bne 1b\n"
9200
9201 // Aggregator Reduction.
9202 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
9203 "vdup.32 q1, %[additive_sum_offset]\n"
9204 "vpaddl.u16 q8, q8\n"
9205 "vpaddl.u16 q9, q9\n"
9206 "vpaddl.u16 q10, q10\n"
9207 "vpaddl.u16 q11, q11\n"
9208 "vpaddl.u16 q12, q12\n"
9209 "vpaddl.u16 q13, q13\n"
9210 "vpadd.u32 d16, d16, d17\n"
9211 "vpadd.u32 d18, d18, d19\n"
9212 "vpadd.u32 d20, d20, d21\n"
9213 "vpadd.u32 d22, d22, d23\n"
9214 "vpadd.u32 d24, d24, d25\n"
9215 "vpadd.u32 d26, d26, d27\n"
9216 "vpadd.u32 d16, d16, d18\n"
9217 "vpadd.u32 d17, d20, d22\n"
9218 "vpadd.u32 d18, d24, d26\n"
9219 "vmul.i32 q8, q8, d0[0]\n"
9220 "vmul.i32 q9, q9, d0[0]\n"
9221 "vadd.i32 q8, q8, q1\n"
9222 "vadd.i32 q9, q9, q1\n"
9223 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
9224 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
9225 [out] "+r"(out), [in] "+r"(in)
9226 : [additive_sum_offset] "r"(params.additive_sum_offset),
9227 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
9228 : "d0", "d1", "d2", "d3", "d4", "d5", "d16", "d17", "d18", "d19", "d20",
9229 "d21", "d22", "d23", "d24", "d25", "d26", "d27", "cc", "memory");
9230 }
9231
9232 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)9233 inline void Stream<uint8_t, 6, 8, 1, ColumnMajorWithSum>::Pack(
9234 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
9235 #ifdef DEBUG
9236 #ifdef DEBUG_METAGEMM_VERBOSE
9237 std::cout
9238 << __FILE__ << "(" << __LINE__
9239 << ") ColumnMajorWithSum<uint8_t, 6, 8, 1, ColumnMajorWithSum>::Pack()"
9240 << std::endl
9241 << std::flush;
9242 #endif
9243 #endif
9244 int params_count_copy = params.count;
9245 int params_stride_copy = params.stride;
9246 asm volatile(
9247 "sub %[stride], %[stride], #4\n"
9248 "vmov.i16 q8, #0\n"
9249 "vmov.i16 q9, #0\n"
9250 "vmov.i16 q10, #0\n"
9251 "vmov.i16 q11, #0\n"
9252 "vmov.i16 q12, #0\n"
9253 "vmov.i16 q13, #0\n"
9254
9255 // Reduce count by leftovers.
9256 "subs %[count], %[count], #1\n"
9257 "beq 2f\n"
9258
9259 "1:"
9260 "subs %[count], %[count], #8\n"
9261
9262 // Load Aggregate Store - column major 6x8
9263 "vld1.32 {d0[0]}, [%[in]]!\n"
9264 "vld1.16 {d4[0]}, [%[in]], %[stride]\n"
9265 "vld1.32 {d1[0]}, [%[in]]!\n"
9266 "vld1.16 {d4[1]}, [%[in]], %[stride]\n"
9267 "vld1.32 {d2[0]}, [%[in]]!\n"
9268 "vld1.16 {d4[2]}, [%[in]], %[stride]\n"
9269 "vld1.32 {d3[0]}, [%[in]]!\n"
9270 "vld1.16 {d4[3]}, [%[in]], %[stride]\n"
9271 "vld1.32 {d0[1]}, [%[in]]!\n"
9272 "vld1.16 {d5[0]}, [%[in]], %[stride]\n"
9273 "vld1.32 {d1[1]}, [%[in]]!\n"
9274 "vld1.16 {d5[1]}, [%[in]], %[stride]\n"
9275 "vld1.32 {d2[1]}, [%[in]]!\n"
9276 "vld1.16 {d5[2]}, [%[in]], %[stride]\n"
9277 "vld1.32 {d3[1]}, [%[in]]!\n"
9278 "vld1.16 {d5[3]}, [%[in]], %[stride]\n"
9279 "pld [%[in]]\n"
9280 "vtrn.16 d0, d2\n"
9281 "vtrn.16 d1, d3\n"
9282 "vuzp.8 d4, d5\n"
9283 "vtrn.8 d0, d1\n"
9284 "vtrn.8 d2, d3\n"
9285 "vaddw.u8 q8, q8, d0\n"
9286 "vaddw.u8 q9, q9, d1\n"
9287 "vaddw.u8 q10, q10, d2\n"
9288 "vaddw.u8 q11, q11, d3\n"
9289 "vaddw.u8 q12, q12, d4\n"
9290 "vaddw.u8 q13, q13, d5\n"
9291 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
9292 "vst1.32 {d4, d5}, [%[out]:128]!\n"
9293
9294 "bne 1b\n"
9295
9296 "2:"
9297
9298 // Load Aggregate Store - column major 6x1
9299 "vmov.i8 d0, #0\n"
9300 "vmov.i8 d1, #0\n"
9301 "vmov.i8 d2, #0\n"
9302 "vmov.i8 d3, #0\n"
9303 "vmov.i8 d4, #0\n"
9304 "vmov.i8 d5, #0\n"
9305 "vld1.32 {d0[0]}, [%[in]]!\n"
9306 "vld1.16 {d4[0]}, [%[in]], %[stride]\n"
9307 "pld [%[in]]\n"
9308 "vtrn.16 d0, d2\n"
9309 "vtrn.16 d1, d3\n"
9310 "vuzp.8 d4, d5\n"
9311 "vtrn.8 d0, d1\n"
9312 "vtrn.8 d2, d3\n"
9313 "vaddw.u8 q8, q8, d0\n"
9314 "vaddw.u8 q9, q9, d1\n"
9315 "vaddw.u8 q10, q10, d2\n"
9316 "vaddw.u8 q11, q11, d3\n"
9317 "vaddw.u8 q12, q12, d4\n"
9318 "vaddw.u8 q13, q13, d5\n"
9319 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
9320 "vst1.32 {d4, d5}, [%[out]:128]!\n"
9321
9322 // Aggregator Reduction.
9323 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
9324 "vdup.32 q1, %[additive_sum_offset]\n"
9325 "vpaddl.u16 q8, q8\n"
9326 "vpaddl.u16 q9, q9\n"
9327 "vpaddl.u16 q10, q10\n"
9328 "vpaddl.u16 q11, q11\n"
9329 "vpaddl.u16 q12, q12\n"
9330 "vpaddl.u16 q13, q13\n"
9331 "vpadd.u32 d16, d16, d17\n"
9332 "vpadd.u32 d18, d18, d19\n"
9333 "vpadd.u32 d20, d20, d21\n"
9334 "vpadd.u32 d22, d22, d23\n"
9335 "vpadd.u32 d24, d24, d25\n"
9336 "vpadd.u32 d26, d26, d27\n"
9337 "vpadd.u32 d16, d16, d18\n"
9338 "vpadd.u32 d17, d20, d22\n"
9339 "vpadd.u32 d18, d24, d26\n"
9340 "vmul.i32 q8, q8, d0[0]\n"
9341 "vmul.i32 q9, q9, d0[0]\n"
9342 "vadd.i32 q8, q8, q1\n"
9343 "vadd.i32 q9, q9, q1\n"
9344 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
9345 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
9346 [out] "+r"(out), [in] "+r"(in)
9347 : [additive_sum_offset] "r"(params.additive_sum_offset),
9348 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
9349 : "d0", "d1", "d2", "d3", "d4", "d5", "d16", "d17", "d18", "d19", "d20",
9350 "d21", "d22", "d23", "d24", "d25", "d26", "d27", "cc", "memory");
9351 }
9352
9353 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)9354 inline void Stream<uint8_t, 6, 8, 2, ColumnMajorWithSum>::Pack(
9355 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
9356 #ifdef DEBUG
9357 #ifdef DEBUG_METAGEMM_VERBOSE
9358 std::cout
9359 << __FILE__ << "(" << __LINE__
9360 << ") ColumnMajorWithSum<uint8_t, 6, 8, 2, ColumnMajorWithSum>::Pack()"
9361 << std::endl
9362 << std::flush;
9363 #endif
9364 #endif
9365 int params_count_copy = params.count;
9366 int params_stride_copy = params.stride;
9367 asm volatile(
9368 "sub %[stride], %[stride], #4\n"
9369 "vmov.i16 q8, #0\n"
9370 "vmov.i16 q9, #0\n"
9371 "vmov.i16 q10, #0\n"
9372 "vmov.i16 q11, #0\n"
9373 "vmov.i16 q12, #0\n"
9374 "vmov.i16 q13, #0\n"
9375
9376 // Reduce count by leftovers.
9377 "subs %[count], %[count], #2\n"
9378 "beq 2f\n"
9379
9380 "1:"
9381 "subs %[count], %[count], #8\n"
9382
9383 // Load Aggregate Store - column major 6x8
9384 "vld1.32 {d0[0]}, [%[in]]!\n"
9385 "vld1.16 {d4[0]}, [%[in]], %[stride]\n"
9386 "vld1.32 {d1[0]}, [%[in]]!\n"
9387 "vld1.16 {d4[1]}, [%[in]], %[stride]\n"
9388 "vld1.32 {d2[0]}, [%[in]]!\n"
9389 "vld1.16 {d4[2]}, [%[in]], %[stride]\n"
9390 "vld1.32 {d3[0]}, [%[in]]!\n"
9391 "vld1.16 {d4[3]}, [%[in]], %[stride]\n"
9392 "vld1.32 {d0[1]}, [%[in]]!\n"
9393 "vld1.16 {d5[0]}, [%[in]], %[stride]\n"
9394 "vld1.32 {d1[1]}, [%[in]]!\n"
9395 "vld1.16 {d5[1]}, [%[in]], %[stride]\n"
9396 "vld1.32 {d2[1]}, [%[in]]!\n"
9397 "vld1.16 {d5[2]}, [%[in]], %[stride]\n"
9398 "vld1.32 {d3[1]}, [%[in]]!\n"
9399 "vld1.16 {d5[3]}, [%[in]], %[stride]\n"
9400 "pld [%[in]]\n"
9401 "vtrn.16 d0, d2\n"
9402 "vtrn.16 d1, d3\n"
9403 "vuzp.8 d4, d5\n"
9404 "vtrn.8 d0, d1\n"
9405 "vtrn.8 d2, d3\n"
9406 "vaddw.u8 q8, q8, d0\n"
9407 "vaddw.u8 q9, q9, d1\n"
9408 "vaddw.u8 q10, q10, d2\n"
9409 "vaddw.u8 q11, q11, d3\n"
9410 "vaddw.u8 q12, q12, d4\n"
9411 "vaddw.u8 q13, q13, d5\n"
9412 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
9413 "vst1.32 {d4, d5}, [%[out]:128]!\n"
9414
9415 "bne 1b\n"
9416
9417 "2:"
9418
9419 // Load Aggregate Store - column major 6x2
9420 "vmov.i8 d0, #0\n"
9421 "vmov.i8 d1, #0\n"
9422 "vmov.i8 d2, #0\n"
9423 "vmov.i8 d3, #0\n"
9424 "vmov.i8 d4, #0\n"
9425 "vmov.i8 d5, #0\n"
9426 "vld1.32 {d0[0]}, [%[in]]!\n"
9427 "vld1.16 {d4[0]}, [%[in]], %[stride]\n"
9428 "vld1.32 {d1[0]}, [%[in]]!\n"
9429 "vld1.16 {d4[1]}, [%[in]], %[stride]\n"
9430 "pld [%[in]]\n"
9431 "vtrn.16 d0, d2\n"
9432 "vtrn.16 d1, d3\n"
9433 "vuzp.8 d4, d5\n"
9434 "vtrn.8 d0, d1\n"
9435 "vtrn.8 d2, d3\n"
9436 "vaddw.u8 q8, q8, d0\n"
9437 "vaddw.u8 q9, q9, d1\n"
9438 "vaddw.u8 q10, q10, d2\n"
9439 "vaddw.u8 q11, q11, d3\n"
9440 "vaddw.u8 q12, q12, d4\n"
9441 "vaddw.u8 q13, q13, d5\n"
9442 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
9443 "vst1.32 {d4, d5}, [%[out]:128]!\n"
9444
9445 // Aggregator Reduction.
9446 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
9447 "vdup.32 q1, %[additive_sum_offset]\n"
9448 "vpaddl.u16 q8, q8\n"
9449 "vpaddl.u16 q9, q9\n"
9450 "vpaddl.u16 q10, q10\n"
9451 "vpaddl.u16 q11, q11\n"
9452 "vpaddl.u16 q12, q12\n"
9453 "vpaddl.u16 q13, q13\n"
9454 "vpadd.u32 d16, d16, d17\n"
9455 "vpadd.u32 d18, d18, d19\n"
9456 "vpadd.u32 d20, d20, d21\n"
9457 "vpadd.u32 d22, d22, d23\n"
9458 "vpadd.u32 d24, d24, d25\n"
9459 "vpadd.u32 d26, d26, d27\n"
9460 "vpadd.u32 d16, d16, d18\n"
9461 "vpadd.u32 d17, d20, d22\n"
9462 "vpadd.u32 d18, d24, d26\n"
9463 "vmul.i32 q8, q8, d0[0]\n"
9464 "vmul.i32 q9, q9, d0[0]\n"
9465 "vadd.i32 q8, q8, q1\n"
9466 "vadd.i32 q9, q9, q1\n"
9467 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
9468 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
9469 [out] "+r"(out), [in] "+r"(in)
9470 : [additive_sum_offset] "r"(params.additive_sum_offset),
9471 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
9472 : "d0", "d1", "d2", "d3", "d4", "d5", "d16", "d17", "d18", "d19", "d20",
9473 "d21", "d22", "d23", "d24", "d25", "d26", "d27", "cc", "memory");
9474 }
9475
9476 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)9477 inline void Stream<uint8_t, 6, 8, 3, ColumnMajorWithSum>::Pack(
9478 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
9479 #ifdef DEBUG
9480 #ifdef DEBUG_METAGEMM_VERBOSE
9481 std::cout
9482 << __FILE__ << "(" << __LINE__
9483 << ") ColumnMajorWithSum<uint8_t, 6, 8, 3, ColumnMajorWithSum>::Pack()"
9484 << std::endl
9485 << std::flush;
9486 #endif
9487 #endif
9488 int params_count_copy = params.count;
9489 int params_stride_copy = params.stride;
9490 asm volatile(
9491 "sub %[stride], %[stride], #4\n"
9492 "vmov.i16 q8, #0\n"
9493 "vmov.i16 q9, #0\n"
9494 "vmov.i16 q10, #0\n"
9495 "vmov.i16 q11, #0\n"
9496 "vmov.i16 q12, #0\n"
9497 "vmov.i16 q13, #0\n"
9498
9499 // Reduce count by leftovers.
9500 "subs %[count], %[count], #3\n"
9501 "beq 2f\n"
9502
9503 "1:"
9504 "subs %[count], %[count], #8\n"
9505
9506 // Load Aggregate Store - column major 6x8
9507 "vld1.32 {d0[0]}, [%[in]]!\n"
9508 "vld1.16 {d4[0]}, [%[in]], %[stride]\n"
9509 "vld1.32 {d1[0]}, [%[in]]!\n"
9510 "vld1.16 {d4[1]}, [%[in]], %[stride]\n"
9511 "vld1.32 {d2[0]}, [%[in]]!\n"
9512 "vld1.16 {d4[2]}, [%[in]], %[stride]\n"
9513 "vld1.32 {d3[0]}, [%[in]]!\n"
9514 "vld1.16 {d4[3]}, [%[in]], %[stride]\n"
9515 "vld1.32 {d0[1]}, [%[in]]!\n"
9516 "vld1.16 {d5[0]}, [%[in]], %[stride]\n"
9517 "vld1.32 {d1[1]}, [%[in]]!\n"
9518 "vld1.16 {d5[1]}, [%[in]], %[stride]\n"
9519 "vld1.32 {d2[1]}, [%[in]]!\n"
9520 "vld1.16 {d5[2]}, [%[in]], %[stride]\n"
9521 "vld1.32 {d3[1]}, [%[in]]!\n"
9522 "vld1.16 {d5[3]}, [%[in]], %[stride]\n"
9523 "pld [%[in]]\n"
9524 "vtrn.16 d0, d2\n"
9525 "vtrn.16 d1, d3\n"
9526 "vuzp.8 d4, d5\n"
9527 "vtrn.8 d0, d1\n"
9528 "vtrn.8 d2, d3\n"
9529 "vaddw.u8 q8, q8, d0\n"
9530 "vaddw.u8 q9, q9, d1\n"
9531 "vaddw.u8 q10, q10, d2\n"
9532 "vaddw.u8 q11, q11, d3\n"
9533 "vaddw.u8 q12, q12, d4\n"
9534 "vaddw.u8 q13, q13, d5\n"
9535 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
9536 "vst1.32 {d4, d5}, [%[out]:128]!\n"
9537
9538 "bne 1b\n"
9539
9540 "2:"
9541
9542 // Load Aggregate Store - column major 6x3
9543 "vmov.i8 d0, #0\n"
9544 "vmov.i8 d1, #0\n"
9545 "vmov.i8 d2, #0\n"
9546 "vmov.i8 d3, #0\n"
9547 "vmov.i8 d4, #0\n"
9548 "vmov.i8 d5, #0\n"
9549 "vld1.32 {d0[0]}, [%[in]]!\n"
9550 "vld1.16 {d4[0]}, [%[in]], %[stride]\n"
9551 "vld1.32 {d1[0]}, [%[in]]!\n"
9552 "vld1.16 {d4[1]}, [%[in]], %[stride]\n"
9553 "vld1.32 {d2[0]}, [%[in]]!\n"
9554 "vld1.16 {d4[2]}, [%[in]], %[stride]\n"
9555 "pld [%[in]]\n"
9556 "vtrn.16 d0, d2\n"
9557 "vtrn.16 d1, d3\n"
9558 "vuzp.8 d4, d5\n"
9559 "vtrn.8 d0, d1\n"
9560 "vtrn.8 d2, d3\n"
9561 "vaddw.u8 q8, q8, d0\n"
9562 "vaddw.u8 q9, q9, d1\n"
9563 "vaddw.u8 q10, q10, d2\n"
9564 "vaddw.u8 q11, q11, d3\n"
9565 "vaddw.u8 q12, q12, d4\n"
9566 "vaddw.u8 q13, q13, d5\n"
9567 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
9568 "vst1.32 {d4, d5}, [%[out]:128]!\n"
9569
9570 // Aggregator Reduction.
9571 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
9572 "vdup.32 q1, %[additive_sum_offset]\n"
9573 "vpaddl.u16 q8, q8\n"
9574 "vpaddl.u16 q9, q9\n"
9575 "vpaddl.u16 q10, q10\n"
9576 "vpaddl.u16 q11, q11\n"
9577 "vpaddl.u16 q12, q12\n"
9578 "vpaddl.u16 q13, q13\n"
9579 "vpadd.u32 d16, d16, d17\n"
9580 "vpadd.u32 d18, d18, d19\n"
9581 "vpadd.u32 d20, d20, d21\n"
9582 "vpadd.u32 d22, d22, d23\n"
9583 "vpadd.u32 d24, d24, d25\n"
9584 "vpadd.u32 d26, d26, d27\n"
9585 "vpadd.u32 d16, d16, d18\n"
9586 "vpadd.u32 d17, d20, d22\n"
9587 "vpadd.u32 d18, d24, d26\n"
9588 "vmul.i32 q8, q8, d0[0]\n"
9589 "vmul.i32 q9, q9, d0[0]\n"
9590 "vadd.i32 q8, q8, q1\n"
9591 "vadd.i32 q9, q9, q1\n"
9592 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
9593 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
9594 [out] "+r"(out), [in] "+r"(in)
9595 : [additive_sum_offset] "r"(params.additive_sum_offset),
9596 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
9597 : "d0", "d1", "d2", "d3", "d4", "d5", "d16", "d17", "d18", "d19", "d20",
9598 "d21", "d22", "d23", "d24", "d25", "d26", "d27", "cc", "memory");
9599 }
9600
9601 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)9602 inline void Stream<uint8_t, 6, 8, 4, ColumnMajorWithSum>::Pack(
9603 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
9604 #ifdef DEBUG
9605 #ifdef DEBUG_METAGEMM_VERBOSE
9606 std::cout
9607 << __FILE__ << "(" << __LINE__
9608 << ") ColumnMajorWithSum<uint8_t, 6, 8, 4, ColumnMajorWithSum>::Pack()"
9609 << std::endl
9610 << std::flush;
9611 #endif
9612 #endif
9613 int params_count_copy = params.count;
9614 int params_stride_copy = params.stride;
9615 asm volatile(
9616 "sub %[stride], %[stride], #4\n"
9617 "vmov.i16 q8, #0\n"
9618 "vmov.i16 q9, #0\n"
9619 "vmov.i16 q10, #0\n"
9620 "vmov.i16 q11, #0\n"
9621 "vmov.i16 q12, #0\n"
9622 "vmov.i16 q13, #0\n"
9623
9624 // Reduce count by leftovers.
9625 "subs %[count], %[count], #4\n"
9626 "beq 2f\n"
9627
9628 "1:"
9629 "subs %[count], %[count], #8\n"
9630
9631 // Load Aggregate Store - column major 6x8
9632 "vld1.32 {d0[0]}, [%[in]]!\n"
9633 "vld1.16 {d4[0]}, [%[in]], %[stride]\n"
9634 "vld1.32 {d1[0]}, [%[in]]!\n"
9635 "vld1.16 {d4[1]}, [%[in]], %[stride]\n"
9636 "vld1.32 {d2[0]}, [%[in]]!\n"
9637 "vld1.16 {d4[2]}, [%[in]], %[stride]\n"
9638 "vld1.32 {d3[0]}, [%[in]]!\n"
9639 "vld1.16 {d4[3]}, [%[in]], %[stride]\n"
9640 "vld1.32 {d0[1]}, [%[in]]!\n"
9641 "vld1.16 {d5[0]}, [%[in]], %[stride]\n"
9642 "vld1.32 {d1[1]}, [%[in]]!\n"
9643 "vld1.16 {d5[1]}, [%[in]], %[stride]\n"
9644 "vld1.32 {d2[1]}, [%[in]]!\n"
9645 "vld1.16 {d5[2]}, [%[in]], %[stride]\n"
9646 "vld1.32 {d3[1]}, [%[in]]!\n"
9647 "vld1.16 {d5[3]}, [%[in]], %[stride]\n"
9648 "pld [%[in]]\n"
9649 "vtrn.16 d0, d2\n"
9650 "vtrn.16 d1, d3\n"
9651 "vuzp.8 d4, d5\n"
9652 "vtrn.8 d0, d1\n"
9653 "vtrn.8 d2, d3\n"
9654 "vaddw.u8 q8, q8, d0\n"
9655 "vaddw.u8 q9, q9, d1\n"
9656 "vaddw.u8 q10, q10, d2\n"
9657 "vaddw.u8 q11, q11, d3\n"
9658 "vaddw.u8 q12, q12, d4\n"
9659 "vaddw.u8 q13, q13, d5\n"
9660 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
9661 "vst1.32 {d4, d5}, [%[out]:128]!\n"
9662
9663 "bne 1b\n"
9664
9665 "2:"
9666
9667 // Load Aggregate Store - column major 6x4
9668 "vmov.i8 d0, #0\n"
9669 "vmov.i8 d1, #0\n"
9670 "vmov.i8 d2, #0\n"
9671 "vmov.i8 d3, #0\n"
9672 "vmov.i8 d4, #0\n"
9673 "vmov.i8 d5, #0\n"
9674 "vld1.32 {d0[0]}, [%[in]]!\n"
9675 "vld1.16 {d4[0]}, [%[in]], %[stride]\n"
9676 "vld1.32 {d1[0]}, [%[in]]!\n"
9677 "vld1.16 {d4[1]}, [%[in]], %[stride]\n"
9678 "vld1.32 {d2[0]}, [%[in]]!\n"
9679 "vld1.16 {d4[2]}, [%[in]], %[stride]\n"
9680 "vld1.32 {d3[0]}, [%[in]]!\n"
9681 "vld1.16 {d4[3]}, [%[in]], %[stride]\n"
9682 "pld [%[in]]\n"
9683 "vtrn.16 d0, d2\n"
9684 "vtrn.16 d1, d3\n"
9685 "vuzp.8 d4, d5\n"
9686 "vtrn.8 d0, d1\n"
9687 "vtrn.8 d2, d3\n"
9688 "vaddw.u8 q8, q8, d0\n"
9689 "vaddw.u8 q9, q9, d1\n"
9690 "vaddw.u8 q10, q10, d2\n"
9691 "vaddw.u8 q11, q11, d3\n"
9692 "vaddw.u8 q12, q12, d4\n"
9693 "vaddw.u8 q13, q13, d5\n"
9694 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
9695 "vst1.32 {d4, d5}, [%[out]:128]!\n"
9696
9697 // Aggregator Reduction.
9698 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
9699 "vdup.32 q1, %[additive_sum_offset]\n"
9700 "vpaddl.u16 q8, q8\n"
9701 "vpaddl.u16 q9, q9\n"
9702 "vpaddl.u16 q10, q10\n"
9703 "vpaddl.u16 q11, q11\n"
9704 "vpaddl.u16 q12, q12\n"
9705 "vpaddl.u16 q13, q13\n"
9706 "vpadd.u32 d16, d16, d17\n"
9707 "vpadd.u32 d18, d18, d19\n"
9708 "vpadd.u32 d20, d20, d21\n"
9709 "vpadd.u32 d22, d22, d23\n"
9710 "vpadd.u32 d24, d24, d25\n"
9711 "vpadd.u32 d26, d26, d27\n"
9712 "vpadd.u32 d16, d16, d18\n"
9713 "vpadd.u32 d17, d20, d22\n"
9714 "vpadd.u32 d18, d24, d26\n"
9715 "vmul.i32 q8, q8, d0[0]\n"
9716 "vmul.i32 q9, q9, d0[0]\n"
9717 "vadd.i32 q8, q8, q1\n"
9718 "vadd.i32 q9, q9, q1\n"
9719 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
9720 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
9721 [out] "+r"(out), [in] "+r"(in)
9722 : [additive_sum_offset] "r"(params.additive_sum_offset),
9723 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
9724 : "d0", "d1", "d2", "d3", "d4", "d5", "d16", "d17", "d18", "d19", "d20",
9725 "d21", "d22", "d23", "d24", "d25", "d26", "d27", "cc", "memory");
9726 }
9727
9728 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)9729 inline void Stream<uint8_t, 6, 8, 5, ColumnMajorWithSum>::Pack(
9730 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
9731 #ifdef DEBUG
9732 #ifdef DEBUG_METAGEMM_VERBOSE
9733 std::cout
9734 << __FILE__ << "(" << __LINE__
9735 << ") ColumnMajorWithSum<uint8_t, 6, 8, 5, ColumnMajorWithSum>::Pack()"
9736 << std::endl
9737 << std::flush;
9738 #endif
9739 #endif
9740 int params_count_copy = params.count;
9741 int params_stride_copy = params.stride;
9742 asm volatile(
9743 "sub %[stride], %[stride], #4\n"
9744 "vmov.i16 q8, #0\n"
9745 "vmov.i16 q9, #0\n"
9746 "vmov.i16 q10, #0\n"
9747 "vmov.i16 q11, #0\n"
9748 "vmov.i16 q12, #0\n"
9749 "vmov.i16 q13, #0\n"
9750
9751 // Reduce count by leftovers.
9752 "subs %[count], %[count], #5\n"
9753 "beq 2f\n"
9754
9755 "1:"
9756 "subs %[count], %[count], #8\n"
9757
9758 // Load Aggregate Store - column major 6x8
9759 "vld1.32 {d0[0]}, [%[in]]!\n"
9760 "vld1.16 {d4[0]}, [%[in]], %[stride]\n"
9761 "vld1.32 {d1[0]}, [%[in]]!\n"
9762 "vld1.16 {d4[1]}, [%[in]], %[stride]\n"
9763 "vld1.32 {d2[0]}, [%[in]]!\n"
9764 "vld1.16 {d4[2]}, [%[in]], %[stride]\n"
9765 "vld1.32 {d3[0]}, [%[in]]!\n"
9766 "vld1.16 {d4[3]}, [%[in]], %[stride]\n"
9767 "vld1.32 {d0[1]}, [%[in]]!\n"
9768 "vld1.16 {d5[0]}, [%[in]], %[stride]\n"
9769 "vld1.32 {d1[1]}, [%[in]]!\n"
9770 "vld1.16 {d5[1]}, [%[in]], %[stride]\n"
9771 "vld1.32 {d2[1]}, [%[in]]!\n"
9772 "vld1.16 {d5[2]}, [%[in]], %[stride]\n"
9773 "vld1.32 {d3[1]}, [%[in]]!\n"
9774 "vld1.16 {d5[3]}, [%[in]], %[stride]\n"
9775 "pld [%[in]]\n"
9776 "vtrn.16 d0, d2\n"
9777 "vtrn.16 d1, d3\n"
9778 "vuzp.8 d4, d5\n"
9779 "vtrn.8 d0, d1\n"
9780 "vtrn.8 d2, d3\n"
9781 "vaddw.u8 q8, q8, d0\n"
9782 "vaddw.u8 q9, q9, d1\n"
9783 "vaddw.u8 q10, q10, d2\n"
9784 "vaddw.u8 q11, q11, d3\n"
9785 "vaddw.u8 q12, q12, d4\n"
9786 "vaddw.u8 q13, q13, d5\n"
9787 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
9788 "vst1.32 {d4, d5}, [%[out]:128]!\n"
9789
9790 "bne 1b\n"
9791
9792 "2:"
9793
9794 // Load Aggregate Store - column major 6x5
9795 "vmov.i8 d0, #0\n"
9796 "vmov.i8 d1, #0\n"
9797 "vmov.i8 d2, #0\n"
9798 "vmov.i8 d3, #0\n"
9799 "vmov.i8 d4, #0\n"
9800 "vmov.i8 d5, #0\n"
9801 "vld1.32 {d0[0]}, [%[in]]!\n"
9802 "vld1.16 {d4[0]}, [%[in]], %[stride]\n"
9803 "vld1.32 {d1[0]}, [%[in]]!\n"
9804 "vld1.16 {d4[1]}, [%[in]], %[stride]\n"
9805 "vld1.32 {d2[0]}, [%[in]]!\n"
9806 "vld1.16 {d4[2]}, [%[in]], %[stride]\n"
9807 "vld1.32 {d3[0]}, [%[in]]!\n"
9808 "vld1.16 {d4[3]}, [%[in]], %[stride]\n"
9809 "vld1.32 {d0[1]}, [%[in]]!\n"
9810 "vld1.16 {d5[0]}, [%[in]], %[stride]\n"
9811 "pld [%[in]]\n"
9812 "vtrn.16 d0, d2\n"
9813 "vtrn.16 d1, d3\n"
9814 "vuzp.8 d4, d5\n"
9815 "vtrn.8 d0, d1\n"
9816 "vtrn.8 d2, d3\n"
9817 "vaddw.u8 q8, q8, d0\n"
9818 "vaddw.u8 q9, q9, d1\n"
9819 "vaddw.u8 q10, q10, d2\n"
9820 "vaddw.u8 q11, q11, d3\n"
9821 "vaddw.u8 q12, q12, d4\n"
9822 "vaddw.u8 q13, q13, d5\n"
9823 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
9824 "vst1.32 {d4, d5}, [%[out]:128]!\n"
9825
9826 // Aggregator Reduction.
9827 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
9828 "vdup.32 q1, %[additive_sum_offset]\n"
9829 "vpaddl.u16 q8, q8\n"
9830 "vpaddl.u16 q9, q9\n"
9831 "vpaddl.u16 q10, q10\n"
9832 "vpaddl.u16 q11, q11\n"
9833 "vpaddl.u16 q12, q12\n"
9834 "vpaddl.u16 q13, q13\n"
9835 "vpadd.u32 d16, d16, d17\n"
9836 "vpadd.u32 d18, d18, d19\n"
9837 "vpadd.u32 d20, d20, d21\n"
9838 "vpadd.u32 d22, d22, d23\n"
9839 "vpadd.u32 d24, d24, d25\n"
9840 "vpadd.u32 d26, d26, d27\n"
9841 "vpadd.u32 d16, d16, d18\n"
9842 "vpadd.u32 d17, d20, d22\n"
9843 "vpadd.u32 d18, d24, d26\n"
9844 "vmul.i32 q8, q8, d0[0]\n"
9845 "vmul.i32 q9, q9, d0[0]\n"
9846 "vadd.i32 q8, q8, q1\n"
9847 "vadd.i32 q9, q9, q1\n"
9848 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
9849 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
9850 [out] "+r"(out), [in] "+r"(in)
9851 : [additive_sum_offset] "r"(params.additive_sum_offset),
9852 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
9853 : "d0", "d1", "d2", "d3", "d4", "d5", "d16", "d17", "d18", "d19", "d20",
9854 "d21", "d22", "d23", "d24", "d25", "d26", "d27", "cc", "memory");
9855 }
9856
9857 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)9858 inline void Stream<uint8_t, 6, 8, 6, ColumnMajorWithSum>::Pack(
9859 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
9860 #ifdef DEBUG
9861 #ifdef DEBUG_METAGEMM_VERBOSE
9862 std::cout
9863 << __FILE__ << "(" << __LINE__
9864 << ") ColumnMajorWithSum<uint8_t, 6, 8, 6, ColumnMajorWithSum>::Pack()"
9865 << std::endl
9866 << std::flush;
9867 #endif
9868 #endif
9869 int params_count_copy = params.count;
9870 int params_stride_copy = params.stride;
9871 asm volatile(
9872 "sub %[stride], %[stride], #4\n"
9873 "vmov.i16 q8, #0\n"
9874 "vmov.i16 q9, #0\n"
9875 "vmov.i16 q10, #0\n"
9876 "vmov.i16 q11, #0\n"
9877 "vmov.i16 q12, #0\n"
9878 "vmov.i16 q13, #0\n"
9879
9880 // Reduce count by leftovers.
9881 "subs %[count], %[count], #6\n"
9882 "beq 2f\n"
9883
9884 "1:"
9885 "subs %[count], %[count], #8\n"
9886
9887 // Load Aggregate Store - column major 6x8
9888 "vld1.32 {d0[0]}, [%[in]]!\n"
9889 "vld1.16 {d4[0]}, [%[in]], %[stride]\n"
9890 "vld1.32 {d1[0]}, [%[in]]!\n"
9891 "vld1.16 {d4[1]}, [%[in]], %[stride]\n"
9892 "vld1.32 {d2[0]}, [%[in]]!\n"
9893 "vld1.16 {d4[2]}, [%[in]], %[stride]\n"
9894 "vld1.32 {d3[0]}, [%[in]]!\n"
9895 "vld1.16 {d4[3]}, [%[in]], %[stride]\n"
9896 "vld1.32 {d0[1]}, [%[in]]!\n"
9897 "vld1.16 {d5[0]}, [%[in]], %[stride]\n"
9898 "vld1.32 {d1[1]}, [%[in]]!\n"
9899 "vld1.16 {d5[1]}, [%[in]], %[stride]\n"
9900 "vld1.32 {d2[1]}, [%[in]]!\n"
9901 "vld1.16 {d5[2]}, [%[in]], %[stride]\n"
9902 "vld1.32 {d3[1]}, [%[in]]!\n"
9903 "vld1.16 {d5[3]}, [%[in]], %[stride]\n"
9904 "pld [%[in]]\n"
9905 "vtrn.16 d0, d2\n"
9906 "vtrn.16 d1, d3\n"
9907 "vuzp.8 d4, d5\n"
9908 "vtrn.8 d0, d1\n"
9909 "vtrn.8 d2, d3\n"
9910 "vaddw.u8 q8, q8, d0\n"
9911 "vaddw.u8 q9, q9, d1\n"
9912 "vaddw.u8 q10, q10, d2\n"
9913 "vaddw.u8 q11, q11, d3\n"
9914 "vaddw.u8 q12, q12, d4\n"
9915 "vaddw.u8 q13, q13, d5\n"
9916 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
9917 "vst1.32 {d4, d5}, [%[out]:128]!\n"
9918
9919 "bne 1b\n"
9920
9921 "2:"
9922
9923 // Load Aggregate Store - column major 6x6
9924 "vmov.i8 d0, #0\n"
9925 "vmov.i8 d1, #0\n"
9926 "vmov.i8 d2, #0\n"
9927 "vmov.i8 d3, #0\n"
9928 "vmov.i8 d4, #0\n"
9929 "vmov.i8 d5, #0\n"
9930 "vld1.32 {d0[0]}, [%[in]]!\n"
9931 "vld1.16 {d4[0]}, [%[in]], %[stride]\n"
9932 "vld1.32 {d1[0]}, [%[in]]!\n"
9933 "vld1.16 {d4[1]}, [%[in]], %[stride]\n"
9934 "vld1.32 {d2[0]}, [%[in]]!\n"
9935 "vld1.16 {d4[2]}, [%[in]], %[stride]\n"
9936 "vld1.32 {d3[0]}, [%[in]]!\n"
9937 "vld1.16 {d4[3]}, [%[in]], %[stride]\n"
9938 "vld1.32 {d0[1]}, [%[in]]!\n"
9939 "vld1.16 {d5[0]}, [%[in]], %[stride]\n"
9940 "vld1.32 {d1[1]}, [%[in]]!\n"
9941 "vld1.16 {d5[1]}, [%[in]], %[stride]\n"
9942 "pld [%[in]]\n"
9943 "vtrn.16 d0, d2\n"
9944 "vtrn.16 d1, d3\n"
9945 "vuzp.8 d4, d5\n"
9946 "vtrn.8 d0, d1\n"
9947 "vtrn.8 d2, d3\n"
9948 "vaddw.u8 q8, q8, d0\n"
9949 "vaddw.u8 q9, q9, d1\n"
9950 "vaddw.u8 q10, q10, d2\n"
9951 "vaddw.u8 q11, q11, d3\n"
9952 "vaddw.u8 q12, q12, d4\n"
9953 "vaddw.u8 q13, q13, d5\n"
9954 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
9955 "vst1.32 {d4, d5}, [%[out]:128]!\n"
9956
9957 // Aggregator Reduction.
9958 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
9959 "vdup.32 q1, %[additive_sum_offset]\n"
9960 "vpaddl.u16 q8, q8\n"
9961 "vpaddl.u16 q9, q9\n"
9962 "vpaddl.u16 q10, q10\n"
9963 "vpaddl.u16 q11, q11\n"
9964 "vpaddl.u16 q12, q12\n"
9965 "vpaddl.u16 q13, q13\n"
9966 "vpadd.u32 d16, d16, d17\n"
9967 "vpadd.u32 d18, d18, d19\n"
9968 "vpadd.u32 d20, d20, d21\n"
9969 "vpadd.u32 d22, d22, d23\n"
9970 "vpadd.u32 d24, d24, d25\n"
9971 "vpadd.u32 d26, d26, d27\n"
9972 "vpadd.u32 d16, d16, d18\n"
9973 "vpadd.u32 d17, d20, d22\n"
9974 "vpadd.u32 d18, d24, d26\n"
9975 "vmul.i32 q8, q8, d0[0]\n"
9976 "vmul.i32 q9, q9, d0[0]\n"
9977 "vadd.i32 q8, q8, q1\n"
9978 "vadd.i32 q9, q9, q1\n"
9979 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
9980 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
9981 [out] "+r"(out), [in] "+r"(in)
9982 : [additive_sum_offset] "r"(params.additive_sum_offset),
9983 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
9984 : "d0", "d1", "d2", "d3", "d4", "d5", "d16", "d17", "d18", "d19", "d20",
9985 "d21", "d22", "d23", "d24", "d25", "d26", "d27", "cc", "memory");
9986 }
9987
9988 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)9989 inline void Stream<uint8_t, 6, 8, 7, ColumnMajorWithSum>::Pack(
9990 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
9991 #ifdef DEBUG
9992 #ifdef DEBUG_METAGEMM_VERBOSE
9993 std::cout
9994 << __FILE__ << "(" << __LINE__
9995 << ") ColumnMajorWithSum<uint8_t, 6, 8, 7, ColumnMajorWithSum>::Pack()"
9996 << std::endl
9997 << std::flush;
9998 #endif
9999 #endif
10000 int params_count_copy = params.count;
10001 int params_stride_copy = params.stride;
10002 asm volatile(
10003 "sub %[stride], %[stride], #4\n"
10004 "vmov.i16 q8, #0\n"
10005 "vmov.i16 q9, #0\n"
10006 "vmov.i16 q10, #0\n"
10007 "vmov.i16 q11, #0\n"
10008 "vmov.i16 q12, #0\n"
10009 "vmov.i16 q13, #0\n"
10010
10011 // Reduce count by leftovers.
10012 "subs %[count], %[count], #7\n"
10013 "beq 2f\n"
10014
10015 "1:"
10016 "subs %[count], %[count], #8\n"
10017
10018 // Load Aggregate Store - column major 6x8
10019 "vld1.32 {d0[0]}, [%[in]]!\n"
10020 "vld1.16 {d4[0]}, [%[in]], %[stride]\n"
10021 "vld1.32 {d1[0]}, [%[in]]!\n"
10022 "vld1.16 {d4[1]}, [%[in]], %[stride]\n"
10023 "vld1.32 {d2[0]}, [%[in]]!\n"
10024 "vld1.16 {d4[2]}, [%[in]], %[stride]\n"
10025 "vld1.32 {d3[0]}, [%[in]]!\n"
10026 "vld1.16 {d4[3]}, [%[in]], %[stride]\n"
10027 "vld1.32 {d0[1]}, [%[in]]!\n"
10028 "vld1.16 {d5[0]}, [%[in]], %[stride]\n"
10029 "vld1.32 {d1[1]}, [%[in]]!\n"
10030 "vld1.16 {d5[1]}, [%[in]], %[stride]\n"
10031 "vld1.32 {d2[1]}, [%[in]]!\n"
10032 "vld1.16 {d5[2]}, [%[in]], %[stride]\n"
10033 "vld1.32 {d3[1]}, [%[in]]!\n"
10034 "vld1.16 {d5[3]}, [%[in]], %[stride]\n"
10035 "pld [%[in]]\n"
10036 "vtrn.16 d0, d2\n"
10037 "vtrn.16 d1, d3\n"
10038 "vuzp.8 d4, d5\n"
10039 "vtrn.8 d0, d1\n"
10040 "vtrn.8 d2, d3\n"
10041 "vaddw.u8 q8, q8, d0\n"
10042 "vaddw.u8 q9, q9, d1\n"
10043 "vaddw.u8 q10, q10, d2\n"
10044 "vaddw.u8 q11, q11, d3\n"
10045 "vaddw.u8 q12, q12, d4\n"
10046 "vaddw.u8 q13, q13, d5\n"
10047 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
10048 "vst1.32 {d4, d5}, [%[out]:128]!\n"
10049
10050 "bne 1b\n"
10051
10052 "2:"
10053
10054 // Load Aggregate Store - column major 6x7
10055 "vmov.i8 d0, #0\n"
10056 "vmov.i8 d1, #0\n"
10057 "vmov.i8 d2, #0\n"
10058 "vmov.i8 d3, #0\n"
10059 "vmov.i8 d4, #0\n"
10060 "vmov.i8 d5, #0\n"
10061 "vld1.32 {d0[0]}, [%[in]]!\n"
10062 "vld1.16 {d4[0]}, [%[in]], %[stride]\n"
10063 "vld1.32 {d1[0]}, [%[in]]!\n"
10064 "vld1.16 {d4[1]}, [%[in]], %[stride]\n"
10065 "vld1.32 {d2[0]}, [%[in]]!\n"
10066 "vld1.16 {d4[2]}, [%[in]], %[stride]\n"
10067 "vld1.32 {d3[0]}, [%[in]]!\n"
10068 "vld1.16 {d4[3]}, [%[in]], %[stride]\n"
10069 "vld1.32 {d0[1]}, [%[in]]!\n"
10070 "vld1.16 {d5[0]}, [%[in]], %[stride]\n"
10071 "vld1.32 {d1[1]}, [%[in]]!\n"
10072 "vld1.16 {d5[1]}, [%[in]], %[stride]\n"
10073 "vld1.32 {d2[1]}, [%[in]]!\n"
10074 "vld1.16 {d5[2]}, [%[in]], %[stride]\n"
10075 "pld [%[in]]\n"
10076 "vtrn.16 d0, d2\n"
10077 "vtrn.16 d1, d3\n"
10078 "vuzp.8 d4, d5\n"
10079 "vtrn.8 d0, d1\n"
10080 "vtrn.8 d2, d3\n"
10081 "vaddw.u8 q8, q8, d0\n"
10082 "vaddw.u8 q9, q9, d1\n"
10083 "vaddw.u8 q10, q10, d2\n"
10084 "vaddw.u8 q11, q11, d3\n"
10085 "vaddw.u8 q12, q12, d4\n"
10086 "vaddw.u8 q13, q13, d5\n"
10087 "vst1.32 {d0, d1, d2, d3}, [%[out]:128]!\n"
10088 "vst1.32 {d4, d5}, [%[out]:128]!\n"
10089
10090 // Aggregator Reduction.
10091 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
10092 "vdup.32 q1, %[additive_sum_offset]\n"
10093 "vpaddl.u16 q8, q8\n"
10094 "vpaddl.u16 q9, q9\n"
10095 "vpaddl.u16 q10, q10\n"
10096 "vpaddl.u16 q11, q11\n"
10097 "vpaddl.u16 q12, q12\n"
10098 "vpaddl.u16 q13, q13\n"
10099 "vpadd.u32 d16, d16, d17\n"
10100 "vpadd.u32 d18, d18, d19\n"
10101 "vpadd.u32 d20, d20, d21\n"
10102 "vpadd.u32 d22, d22, d23\n"
10103 "vpadd.u32 d24, d24, d25\n"
10104 "vpadd.u32 d26, d26, d27\n"
10105 "vpadd.u32 d16, d16, d18\n"
10106 "vpadd.u32 d17, d20, d22\n"
10107 "vpadd.u32 d18, d24, d26\n"
10108 "vmul.i32 q8, q8, d0[0]\n"
10109 "vmul.i32 q9, q9, d0[0]\n"
10110 "vadd.i32 q8, q8, q1\n"
10111 "vadd.i32 q9, q9, q1\n"
10112 "vst1.32 {d16, d17, d18, d19}, [%[out]:128]\n"
10113 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
10114 [out] "+r"(out), [in] "+r"(in)
10115 : [additive_sum_offset] "r"(params.additive_sum_offset),
10116 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
10117 : "d0", "d1", "d2", "d3", "d4", "d5", "d16", "d17", "d18", "d19", "d20",
10118 "d21", "d22", "d23", "d24", "d25", "d26", "d27", "cc", "memory");
10119 }
10120
10121 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)10122 inline void Stream<uint8_t, 7, 8, 0, ColumnMajorWithSum>::Pack(
10123 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
10124 #ifdef DEBUG
10125 #ifdef DEBUG_METAGEMM_VERBOSE
10126 std::cout
10127 << __FILE__ << "(" << __LINE__
10128 << ") ColumnMajorWithSum<uint8_t, 7, 8, 0, ColumnMajorWithSum>::Pack()"
10129 << std::endl
10130 << std::flush;
10131 #endif
10132 #endif
10133 int params_count_copy = params.count;
10134 int params_stride_copy = params.stride;
10135 asm volatile(
10136 "sub %[stride], %[stride], #4\n"
10137 "vmov.i16 q8, #0\n"
10138 "vmov.i16 q9, #0\n"
10139 "vmov.i16 q10, #0\n"
10140 "vmov.i16 q11, #0\n"
10141 "vmov.i16 q12, #0\n"
10142 "vmov.i16 q13, #0\n"
10143 "vmov.i16 q14, #0\n"
10144
10145 "1:"
10146 "subs %[count], %[count], #8\n"
10147
10148 // Load Aggregate Store - column major 7x8
10149 "vld1.32 {d0[0]}, [%[in]]!\n"
10150 "vld3.8 {d4[0], d5[0], d6[0]}, [%[in]], %[stride]\n"
10151 "vld1.32 {d1[0]}, [%[in]]!\n"
10152 "vld3.8 {d4[1], d5[1], d6[1]}, [%[in]], %[stride]\n"
10153 "vld1.32 {d2[0]}, [%[in]]!\n"
10154 "vld3.8 {d4[2], d5[2], d6[2]}, [%[in]], %[stride]\n"
10155 "vld1.32 {d3[0]}, [%[in]]!\n"
10156 "vld3.8 {d4[3], d5[3], d6[3]}, [%[in]], %[stride]\n"
10157 "vld1.32 {d0[1]}, [%[in]]!\n"
10158 "vld3.8 {d4[4], d5[4], d6[4]}, [%[in]], %[stride]\n"
10159 "vld1.32 {d1[1]}, [%[in]]!\n"
10160 "vld3.8 {d4[5], d5[5], d6[5]}, [%[in]], %[stride]\n"
10161 "vld1.32 {d2[1]}, [%[in]]!\n"
10162 "vld3.8 {d4[6], d5[6], d6[6]}, [%[in]], %[stride]\n"
10163 "vld1.32 {d3[1]}, [%[in]]!\n"
10164 "vld3.8 {d4[7], d5[7], d6[7]}, [%[in]], %[stride]\n"
10165 "pld [%[in]]\n"
10166 "vtrn.16 d0, d2\n"
10167 "vtrn.16 d1, d3\n"
10168 "vtrn.8 d0, d1\n"
10169 "vtrn.8 d2, d3\n"
10170 "vaddw.u8 q8, q8, d0\n"
10171 "vaddw.u8 q9, q9, d1\n"
10172 "vaddw.u8 q10, q10, d2\n"
10173 "vaddw.u8 q11, q11, d3\n"
10174 "vaddw.u8 q12, q12, d4\n"
10175 "vaddw.u8 q13, q13, d5\n"
10176 "vaddw.u8 q14, q14, d6\n"
10177 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
10178 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
10179
10180 "bne 1b\n"
10181
10182 // Aggregator Reduction.
10183 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
10184 "vdup.32 q1, %[additive_sum_offset]\n"
10185 "vpaddl.u16 q8, q8\n"
10186 "vpaddl.u16 q9, q9\n"
10187 "vpaddl.u16 q10, q10\n"
10188 "vpaddl.u16 q11, q11\n"
10189 "vpaddl.u16 q12, q12\n"
10190 "vpaddl.u16 q13, q13\n"
10191 "vpaddl.u16 q14, q14\n"
10192 "vpadd.u32 d16, d16, d17\n"
10193 "vpadd.u32 d18, d18, d19\n"
10194 "vpadd.u32 d20, d20, d21\n"
10195 "vpadd.u32 d22, d22, d23\n"
10196 "vpadd.u32 d24, d24, d25\n"
10197 "vpadd.u32 d26, d26, d27\n"
10198 "vpadd.u32 d28, d28, d29\n"
10199 "vpadd.u32 d16, d16, d18\n"
10200 "vpadd.u32 d17, d20, d22\n"
10201 "vpadd.u32 d18, d24, d26\n"
10202 "vpadd.u32 d19, d28, d28\n"
10203 "vmul.i32 q8, q8, d0[0]\n"
10204 "vmul.i32 q9, q9, d0[0]\n"
10205 "vadd.i32 q8, q8, q1\n"
10206 "vadd.i32 q9, q9, q1\n"
10207 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
10208 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
10209 [out] "+r"(out), [in] "+r"(in)
10210 : [additive_sum_offset] "r"(params.additive_sum_offset),
10211 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
10212 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d16", "d17", "d18", "d19",
10213 "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28", "d29",
10214 "cc", "memory");
10215 }
10216
10217 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)10218 inline void Stream<uint8_t, 7, 8, 1, ColumnMajorWithSum>::Pack(
10219 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
10220 #ifdef DEBUG
10221 #ifdef DEBUG_METAGEMM_VERBOSE
10222 std::cout
10223 << __FILE__ << "(" << __LINE__
10224 << ") ColumnMajorWithSum<uint8_t, 7, 8, 1, ColumnMajorWithSum>::Pack()"
10225 << std::endl
10226 << std::flush;
10227 #endif
10228 #endif
10229 int params_count_copy = params.count;
10230 int params_stride_copy = params.stride;
10231 asm volatile(
10232 "sub %[stride], %[stride], #4\n"
10233 "vmov.i16 q8, #0\n"
10234 "vmov.i16 q9, #0\n"
10235 "vmov.i16 q10, #0\n"
10236 "vmov.i16 q11, #0\n"
10237 "vmov.i16 q12, #0\n"
10238 "vmov.i16 q13, #0\n"
10239 "vmov.i16 q14, #0\n"
10240
10241 // Reduce count by leftovers.
10242 "subs %[count], %[count], #1\n"
10243 "beq 2f\n"
10244
10245 "1:"
10246 "subs %[count], %[count], #8\n"
10247
10248 // Load Aggregate Store - column major 7x8
10249 "vld1.32 {d0[0]}, [%[in]]!\n"
10250 "vld3.8 {d4[0], d5[0], d6[0]}, [%[in]], %[stride]\n"
10251 "vld1.32 {d1[0]}, [%[in]]!\n"
10252 "vld3.8 {d4[1], d5[1], d6[1]}, [%[in]], %[stride]\n"
10253 "vld1.32 {d2[0]}, [%[in]]!\n"
10254 "vld3.8 {d4[2], d5[2], d6[2]}, [%[in]], %[stride]\n"
10255 "vld1.32 {d3[0]}, [%[in]]!\n"
10256 "vld3.8 {d4[3], d5[3], d6[3]}, [%[in]], %[stride]\n"
10257 "vld1.32 {d0[1]}, [%[in]]!\n"
10258 "vld3.8 {d4[4], d5[4], d6[4]}, [%[in]], %[stride]\n"
10259 "vld1.32 {d1[1]}, [%[in]]!\n"
10260 "vld3.8 {d4[5], d5[5], d6[5]}, [%[in]], %[stride]\n"
10261 "vld1.32 {d2[1]}, [%[in]]!\n"
10262 "vld3.8 {d4[6], d5[6], d6[6]}, [%[in]], %[stride]\n"
10263 "vld1.32 {d3[1]}, [%[in]]!\n"
10264 "vld3.8 {d4[7], d5[7], d6[7]}, [%[in]], %[stride]\n"
10265 "pld [%[in]]\n"
10266 "vtrn.16 d0, d2\n"
10267 "vtrn.16 d1, d3\n"
10268 "vtrn.8 d0, d1\n"
10269 "vtrn.8 d2, d3\n"
10270 "vaddw.u8 q8, q8, d0\n"
10271 "vaddw.u8 q9, q9, d1\n"
10272 "vaddw.u8 q10, q10, d2\n"
10273 "vaddw.u8 q11, q11, d3\n"
10274 "vaddw.u8 q12, q12, d4\n"
10275 "vaddw.u8 q13, q13, d5\n"
10276 "vaddw.u8 q14, q14, d6\n"
10277 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
10278 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
10279
10280 "bne 1b\n"
10281
10282 "2:"
10283
10284 // Load Aggregate Store - column major 7x1
10285 "vmov.i8 d0, #0\n"
10286 "vmov.i8 d1, #0\n"
10287 "vmov.i8 d2, #0\n"
10288 "vmov.i8 d3, #0\n"
10289 "vmov.i8 d4, #0\n"
10290 "vmov.i8 d5, #0\n"
10291 "vmov.i8 d6, #0\n"
10292 "vld1.32 {d0[0]}, [%[in]]!\n"
10293 "vld3.8 {d4[0], d5[0], d6[0]}, [%[in]], %[stride]\n"
10294 "pld [%[in]]\n"
10295 "vtrn.16 d0, d2\n"
10296 "vtrn.16 d1, d3\n"
10297 "vtrn.8 d0, d1\n"
10298 "vtrn.8 d2, d3\n"
10299 "vaddw.u8 q8, q8, d0\n"
10300 "vaddw.u8 q9, q9, d1\n"
10301 "vaddw.u8 q10, q10, d2\n"
10302 "vaddw.u8 q11, q11, d3\n"
10303 "vaddw.u8 q12, q12, d4\n"
10304 "vaddw.u8 q13, q13, d5\n"
10305 "vaddw.u8 q14, q14, d6\n"
10306 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
10307 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
10308
10309 // Aggregator Reduction.
10310 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
10311 "vdup.32 q1, %[additive_sum_offset]\n"
10312 "vpaddl.u16 q8, q8\n"
10313 "vpaddl.u16 q9, q9\n"
10314 "vpaddl.u16 q10, q10\n"
10315 "vpaddl.u16 q11, q11\n"
10316 "vpaddl.u16 q12, q12\n"
10317 "vpaddl.u16 q13, q13\n"
10318 "vpaddl.u16 q14, q14\n"
10319 "vpadd.u32 d16, d16, d17\n"
10320 "vpadd.u32 d18, d18, d19\n"
10321 "vpadd.u32 d20, d20, d21\n"
10322 "vpadd.u32 d22, d22, d23\n"
10323 "vpadd.u32 d24, d24, d25\n"
10324 "vpadd.u32 d26, d26, d27\n"
10325 "vpadd.u32 d28, d28, d29\n"
10326 "vpadd.u32 d16, d16, d18\n"
10327 "vpadd.u32 d17, d20, d22\n"
10328 "vpadd.u32 d18, d24, d26\n"
10329 "vpadd.u32 d19, d28, d28\n"
10330 "vmul.i32 q8, q8, d0[0]\n"
10331 "vmul.i32 q9, q9, d0[0]\n"
10332 "vadd.i32 q8, q8, q1\n"
10333 "vadd.i32 q9, q9, q1\n"
10334 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
10335 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
10336 [out] "+r"(out), [in] "+r"(in)
10337 : [additive_sum_offset] "r"(params.additive_sum_offset),
10338 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
10339 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d16", "d17", "d18", "d19",
10340 "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28", "d29",
10341 "cc", "memory");
10342 }
10343
10344 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)10345 inline void Stream<uint8_t, 7, 8, 2, ColumnMajorWithSum>::Pack(
10346 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
10347 #ifdef DEBUG
10348 #ifdef DEBUG_METAGEMM_VERBOSE
10349 std::cout
10350 << __FILE__ << "(" << __LINE__
10351 << ") ColumnMajorWithSum<uint8_t, 7, 8, 2, ColumnMajorWithSum>::Pack()"
10352 << std::endl
10353 << std::flush;
10354 #endif
10355 #endif
10356 int params_count_copy = params.count;
10357 int params_stride_copy = params.stride;
10358 asm volatile(
10359 "sub %[stride], %[stride], #4\n"
10360 "vmov.i16 q8, #0\n"
10361 "vmov.i16 q9, #0\n"
10362 "vmov.i16 q10, #0\n"
10363 "vmov.i16 q11, #0\n"
10364 "vmov.i16 q12, #0\n"
10365 "vmov.i16 q13, #0\n"
10366 "vmov.i16 q14, #0\n"
10367
10368 // Reduce count by leftovers.
10369 "subs %[count], %[count], #2\n"
10370 "beq 2f\n"
10371
10372 "1:"
10373 "subs %[count], %[count], #8\n"
10374
10375 // Load Aggregate Store - column major 7x8
10376 "vld1.32 {d0[0]}, [%[in]]!\n"
10377 "vld3.8 {d4[0], d5[0], d6[0]}, [%[in]], %[stride]\n"
10378 "vld1.32 {d1[0]}, [%[in]]!\n"
10379 "vld3.8 {d4[1], d5[1], d6[1]}, [%[in]], %[stride]\n"
10380 "vld1.32 {d2[0]}, [%[in]]!\n"
10381 "vld3.8 {d4[2], d5[2], d6[2]}, [%[in]], %[stride]\n"
10382 "vld1.32 {d3[0]}, [%[in]]!\n"
10383 "vld3.8 {d4[3], d5[3], d6[3]}, [%[in]], %[stride]\n"
10384 "vld1.32 {d0[1]}, [%[in]]!\n"
10385 "vld3.8 {d4[4], d5[4], d6[4]}, [%[in]], %[stride]\n"
10386 "vld1.32 {d1[1]}, [%[in]]!\n"
10387 "vld3.8 {d4[5], d5[5], d6[5]}, [%[in]], %[stride]\n"
10388 "vld1.32 {d2[1]}, [%[in]]!\n"
10389 "vld3.8 {d4[6], d5[6], d6[6]}, [%[in]], %[stride]\n"
10390 "vld1.32 {d3[1]}, [%[in]]!\n"
10391 "vld3.8 {d4[7], d5[7], d6[7]}, [%[in]], %[stride]\n"
10392 "pld [%[in]]\n"
10393 "vtrn.16 d0, d2\n"
10394 "vtrn.16 d1, d3\n"
10395 "vtrn.8 d0, d1\n"
10396 "vtrn.8 d2, d3\n"
10397 "vaddw.u8 q8, q8, d0\n"
10398 "vaddw.u8 q9, q9, d1\n"
10399 "vaddw.u8 q10, q10, d2\n"
10400 "vaddw.u8 q11, q11, d3\n"
10401 "vaddw.u8 q12, q12, d4\n"
10402 "vaddw.u8 q13, q13, d5\n"
10403 "vaddw.u8 q14, q14, d6\n"
10404 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
10405 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
10406
10407 "bne 1b\n"
10408
10409 "2:"
10410
10411 // Load Aggregate Store - column major 7x2
10412 "vmov.i8 d0, #0\n"
10413 "vmov.i8 d1, #0\n"
10414 "vmov.i8 d2, #0\n"
10415 "vmov.i8 d3, #0\n"
10416 "vmov.i8 d4, #0\n"
10417 "vmov.i8 d5, #0\n"
10418 "vmov.i8 d6, #0\n"
10419 "vld1.32 {d0[0]}, [%[in]]!\n"
10420 "vld3.8 {d4[0], d5[0], d6[0]}, [%[in]], %[stride]\n"
10421 "vld1.32 {d1[0]}, [%[in]]!\n"
10422 "vld3.8 {d4[1], d5[1], d6[1]}, [%[in]], %[stride]\n"
10423 "pld [%[in]]\n"
10424 "vtrn.16 d0, d2\n"
10425 "vtrn.16 d1, d3\n"
10426 "vtrn.8 d0, d1\n"
10427 "vtrn.8 d2, d3\n"
10428 "vaddw.u8 q8, q8, d0\n"
10429 "vaddw.u8 q9, q9, d1\n"
10430 "vaddw.u8 q10, q10, d2\n"
10431 "vaddw.u8 q11, q11, d3\n"
10432 "vaddw.u8 q12, q12, d4\n"
10433 "vaddw.u8 q13, q13, d5\n"
10434 "vaddw.u8 q14, q14, d6\n"
10435 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
10436 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
10437
10438 // Aggregator Reduction.
10439 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
10440 "vdup.32 q1, %[additive_sum_offset]\n"
10441 "vpaddl.u16 q8, q8\n"
10442 "vpaddl.u16 q9, q9\n"
10443 "vpaddl.u16 q10, q10\n"
10444 "vpaddl.u16 q11, q11\n"
10445 "vpaddl.u16 q12, q12\n"
10446 "vpaddl.u16 q13, q13\n"
10447 "vpaddl.u16 q14, q14\n"
10448 "vpadd.u32 d16, d16, d17\n"
10449 "vpadd.u32 d18, d18, d19\n"
10450 "vpadd.u32 d20, d20, d21\n"
10451 "vpadd.u32 d22, d22, d23\n"
10452 "vpadd.u32 d24, d24, d25\n"
10453 "vpadd.u32 d26, d26, d27\n"
10454 "vpadd.u32 d28, d28, d29\n"
10455 "vpadd.u32 d16, d16, d18\n"
10456 "vpadd.u32 d17, d20, d22\n"
10457 "vpadd.u32 d18, d24, d26\n"
10458 "vpadd.u32 d19, d28, d28\n"
10459 "vmul.i32 q8, q8, d0[0]\n"
10460 "vmul.i32 q9, q9, d0[0]\n"
10461 "vadd.i32 q8, q8, q1\n"
10462 "vadd.i32 q9, q9, q1\n"
10463 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
10464 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
10465 [out] "+r"(out), [in] "+r"(in)
10466 : [additive_sum_offset] "r"(params.additive_sum_offset),
10467 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
10468 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d16", "d17", "d18", "d19",
10469 "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28", "d29",
10470 "cc", "memory");
10471 }
10472
10473 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)10474 inline void Stream<uint8_t, 7, 8, 3, ColumnMajorWithSum>::Pack(
10475 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
10476 #ifdef DEBUG
10477 #ifdef DEBUG_METAGEMM_VERBOSE
10478 std::cout
10479 << __FILE__ << "(" << __LINE__
10480 << ") ColumnMajorWithSum<uint8_t, 7, 8, 3, ColumnMajorWithSum>::Pack()"
10481 << std::endl
10482 << std::flush;
10483 #endif
10484 #endif
10485 int params_count_copy = params.count;
10486 int params_stride_copy = params.stride;
10487 asm volatile(
10488 "sub %[stride], %[stride], #4\n"
10489 "vmov.i16 q8, #0\n"
10490 "vmov.i16 q9, #0\n"
10491 "vmov.i16 q10, #0\n"
10492 "vmov.i16 q11, #0\n"
10493 "vmov.i16 q12, #0\n"
10494 "vmov.i16 q13, #0\n"
10495 "vmov.i16 q14, #0\n"
10496
10497 // Reduce count by leftovers.
10498 "subs %[count], %[count], #3\n"
10499 "beq 2f\n"
10500
10501 "1:"
10502 "subs %[count], %[count], #8\n"
10503
10504 // Load Aggregate Store - column major 7x8
10505 "vld1.32 {d0[0]}, [%[in]]!\n"
10506 "vld3.8 {d4[0], d5[0], d6[0]}, [%[in]], %[stride]\n"
10507 "vld1.32 {d1[0]}, [%[in]]!\n"
10508 "vld3.8 {d4[1], d5[1], d6[1]}, [%[in]], %[stride]\n"
10509 "vld1.32 {d2[0]}, [%[in]]!\n"
10510 "vld3.8 {d4[2], d5[2], d6[2]}, [%[in]], %[stride]\n"
10511 "vld1.32 {d3[0]}, [%[in]]!\n"
10512 "vld3.8 {d4[3], d5[3], d6[3]}, [%[in]], %[stride]\n"
10513 "vld1.32 {d0[1]}, [%[in]]!\n"
10514 "vld3.8 {d4[4], d5[4], d6[4]}, [%[in]], %[stride]\n"
10515 "vld1.32 {d1[1]}, [%[in]]!\n"
10516 "vld3.8 {d4[5], d5[5], d6[5]}, [%[in]], %[stride]\n"
10517 "vld1.32 {d2[1]}, [%[in]]!\n"
10518 "vld3.8 {d4[6], d5[6], d6[6]}, [%[in]], %[stride]\n"
10519 "vld1.32 {d3[1]}, [%[in]]!\n"
10520 "vld3.8 {d4[7], d5[7], d6[7]}, [%[in]], %[stride]\n"
10521 "pld [%[in]]\n"
10522 "vtrn.16 d0, d2\n"
10523 "vtrn.16 d1, d3\n"
10524 "vtrn.8 d0, d1\n"
10525 "vtrn.8 d2, d3\n"
10526 "vaddw.u8 q8, q8, d0\n"
10527 "vaddw.u8 q9, q9, d1\n"
10528 "vaddw.u8 q10, q10, d2\n"
10529 "vaddw.u8 q11, q11, d3\n"
10530 "vaddw.u8 q12, q12, d4\n"
10531 "vaddw.u8 q13, q13, d5\n"
10532 "vaddw.u8 q14, q14, d6\n"
10533 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
10534 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
10535
10536 "bne 1b\n"
10537
10538 "2:"
10539
10540 // Load Aggregate Store - column major 7x3
10541 "vmov.i8 d0, #0\n"
10542 "vmov.i8 d1, #0\n"
10543 "vmov.i8 d2, #0\n"
10544 "vmov.i8 d3, #0\n"
10545 "vmov.i8 d4, #0\n"
10546 "vmov.i8 d5, #0\n"
10547 "vmov.i8 d6, #0\n"
10548 "vld1.32 {d0[0]}, [%[in]]!\n"
10549 "vld3.8 {d4[0], d5[0], d6[0]}, [%[in]], %[stride]\n"
10550 "vld1.32 {d1[0]}, [%[in]]!\n"
10551 "vld3.8 {d4[1], d5[1], d6[1]}, [%[in]], %[stride]\n"
10552 "vld1.32 {d2[0]}, [%[in]]!\n"
10553 "vld3.8 {d4[2], d5[2], d6[2]}, [%[in]], %[stride]\n"
10554 "pld [%[in]]\n"
10555 "vtrn.16 d0, d2\n"
10556 "vtrn.16 d1, d3\n"
10557 "vtrn.8 d0, d1\n"
10558 "vtrn.8 d2, d3\n"
10559 "vaddw.u8 q8, q8, d0\n"
10560 "vaddw.u8 q9, q9, d1\n"
10561 "vaddw.u8 q10, q10, d2\n"
10562 "vaddw.u8 q11, q11, d3\n"
10563 "vaddw.u8 q12, q12, d4\n"
10564 "vaddw.u8 q13, q13, d5\n"
10565 "vaddw.u8 q14, q14, d6\n"
10566 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
10567 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
10568
10569 // Aggregator Reduction.
10570 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
10571 "vdup.32 q1, %[additive_sum_offset]\n"
10572 "vpaddl.u16 q8, q8\n"
10573 "vpaddl.u16 q9, q9\n"
10574 "vpaddl.u16 q10, q10\n"
10575 "vpaddl.u16 q11, q11\n"
10576 "vpaddl.u16 q12, q12\n"
10577 "vpaddl.u16 q13, q13\n"
10578 "vpaddl.u16 q14, q14\n"
10579 "vpadd.u32 d16, d16, d17\n"
10580 "vpadd.u32 d18, d18, d19\n"
10581 "vpadd.u32 d20, d20, d21\n"
10582 "vpadd.u32 d22, d22, d23\n"
10583 "vpadd.u32 d24, d24, d25\n"
10584 "vpadd.u32 d26, d26, d27\n"
10585 "vpadd.u32 d28, d28, d29\n"
10586 "vpadd.u32 d16, d16, d18\n"
10587 "vpadd.u32 d17, d20, d22\n"
10588 "vpadd.u32 d18, d24, d26\n"
10589 "vpadd.u32 d19, d28, d28\n"
10590 "vmul.i32 q8, q8, d0[0]\n"
10591 "vmul.i32 q9, q9, d0[0]\n"
10592 "vadd.i32 q8, q8, q1\n"
10593 "vadd.i32 q9, q9, q1\n"
10594 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
10595 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
10596 [out] "+r"(out), [in] "+r"(in)
10597 : [additive_sum_offset] "r"(params.additive_sum_offset),
10598 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
10599 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d16", "d17", "d18", "d19",
10600 "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28", "d29",
10601 "cc", "memory");
10602 }
10603
10604 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)10605 inline void Stream<uint8_t, 7, 8, 4, ColumnMajorWithSum>::Pack(
10606 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
10607 #ifdef DEBUG
10608 #ifdef DEBUG_METAGEMM_VERBOSE
10609 std::cout
10610 << __FILE__ << "(" << __LINE__
10611 << ") ColumnMajorWithSum<uint8_t, 7, 8, 4, ColumnMajorWithSum>::Pack()"
10612 << std::endl
10613 << std::flush;
10614 #endif
10615 #endif
10616 int params_count_copy = params.count;
10617 int params_stride_copy = params.stride;
10618 asm volatile(
10619 "sub %[stride], %[stride], #4\n"
10620 "vmov.i16 q8, #0\n"
10621 "vmov.i16 q9, #0\n"
10622 "vmov.i16 q10, #0\n"
10623 "vmov.i16 q11, #0\n"
10624 "vmov.i16 q12, #0\n"
10625 "vmov.i16 q13, #0\n"
10626 "vmov.i16 q14, #0\n"
10627
10628 // Reduce count by leftovers.
10629 "subs %[count], %[count], #4\n"
10630 "beq 2f\n"
10631
10632 "1:"
10633 "subs %[count], %[count], #8\n"
10634
10635 // Load Aggregate Store - column major 7x8
10636 "vld1.32 {d0[0]}, [%[in]]!\n"
10637 "vld3.8 {d4[0], d5[0], d6[0]}, [%[in]], %[stride]\n"
10638 "vld1.32 {d1[0]}, [%[in]]!\n"
10639 "vld3.8 {d4[1], d5[1], d6[1]}, [%[in]], %[stride]\n"
10640 "vld1.32 {d2[0]}, [%[in]]!\n"
10641 "vld3.8 {d4[2], d5[2], d6[2]}, [%[in]], %[stride]\n"
10642 "vld1.32 {d3[0]}, [%[in]]!\n"
10643 "vld3.8 {d4[3], d5[3], d6[3]}, [%[in]], %[stride]\n"
10644 "vld1.32 {d0[1]}, [%[in]]!\n"
10645 "vld3.8 {d4[4], d5[4], d6[4]}, [%[in]], %[stride]\n"
10646 "vld1.32 {d1[1]}, [%[in]]!\n"
10647 "vld3.8 {d4[5], d5[5], d6[5]}, [%[in]], %[stride]\n"
10648 "vld1.32 {d2[1]}, [%[in]]!\n"
10649 "vld3.8 {d4[6], d5[6], d6[6]}, [%[in]], %[stride]\n"
10650 "vld1.32 {d3[1]}, [%[in]]!\n"
10651 "vld3.8 {d4[7], d5[7], d6[7]}, [%[in]], %[stride]\n"
10652 "pld [%[in]]\n"
10653 "vtrn.16 d0, d2\n"
10654 "vtrn.16 d1, d3\n"
10655 "vtrn.8 d0, d1\n"
10656 "vtrn.8 d2, d3\n"
10657 "vaddw.u8 q8, q8, d0\n"
10658 "vaddw.u8 q9, q9, d1\n"
10659 "vaddw.u8 q10, q10, d2\n"
10660 "vaddw.u8 q11, q11, d3\n"
10661 "vaddw.u8 q12, q12, d4\n"
10662 "vaddw.u8 q13, q13, d5\n"
10663 "vaddw.u8 q14, q14, d6\n"
10664 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
10665 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
10666
10667 "bne 1b\n"
10668
10669 "2:"
10670
10671 // Load Aggregate Store - column major 7x4
10672 "vmov.i8 d0, #0\n"
10673 "vmov.i8 d1, #0\n"
10674 "vmov.i8 d2, #0\n"
10675 "vmov.i8 d3, #0\n"
10676 "vmov.i8 d4, #0\n"
10677 "vmov.i8 d5, #0\n"
10678 "vmov.i8 d6, #0\n"
10679 "vld1.32 {d0[0]}, [%[in]]!\n"
10680 "vld3.8 {d4[0], d5[0], d6[0]}, [%[in]], %[stride]\n"
10681 "vld1.32 {d1[0]}, [%[in]]!\n"
10682 "vld3.8 {d4[1], d5[1], d6[1]}, [%[in]], %[stride]\n"
10683 "vld1.32 {d2[0]}, [%[in]]!\n"
10684 "vld3.8 {d4[2], d5[2], d6[2]}, [%[in]], %[stride]\n"
10685 "vld1.32 {d3[0]}, [%[in]]!\n"
10686 "vld3.8 {d4[3], d5[3], d6[3]}, [%[in]], %[stride]\n"
10687 "pld [%[in]]\n"
10688 "vtrn.16 d0, d2\n"
10689 "vtrn.16 d1, d3\n"
10690 "vtrn.8 d0, d1\n"
10691 "vtrn.8 d2, d3\n"
10692 "vaddw.u8 q8, q8, d0\n"
10693 "vaddw.u8 q9, q9, d1\n"
10694 "vaddw.u8 q10, q10, d2\n"
10695 "vaddw.u8 q11, q11, d3\n"
10696 "vaddw.u8 q12, q12, d4\n"
10697 "vaddw.u8 q13, q13, d5\n"
10698 "vaddw.u8 q14, q14, d6\n"
10699 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
10700 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
10701
10702 // Aggregator Reduction.
10703 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
10704 "vdup.32 q1, %[additive_sum_offset]\n"
10705 "vpaddl.u16 q8, q8\n"
10706 "vpaddl.u16 q9, q9\n"
10707 "vpaddl.u16 q10, q10\n"
10708 "vpaddl.u16 q11, q11\n"
10709 "vpaddl.u16 q12, q12\n"
10710 "vpaddl.u16 q13, q13\n"
10711 "vpaddl.u16 q14, q14\n"
10712 "vpadd.u32 d16, d16, d17\n"
10713 "vpadd.u32 d18, d18, d19\n"
10714 "vpadd.u32 d20, d20, d21\n"
10715 "vpadd.u32 d22, d22, d23\n"
10716 "vpadd.u32 d24, d24, d25\n"
10717 "vpadd.u32 d26, d26, d27\n"
10718 "vpadd.u32 d28, d28, d29\n"
10719 "vpadd.u32 d16, d16, d18\n"
10720 "vpadd.u32 d17, d20, d22\n"
10721 "vpadd.u32 d18, d24, d26\n"
10722 "vpadd.u32 d19, d28, d28\n"
10723 "vmul.i32 q8, q8, d0[0]\n"
10724 "vmul.i32 q9, q9, d0[0]\n"
10725 "vadd.i32 q8, q8, q1\n"
10726 "vadd.i32 q9, q9, q1\n"
10727 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
10728 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
10729 [out] "+r"(out), [in] "+r"(in)
10730 : [additive_sum_offset] "r"(params.additive_sum_offset),
10731 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
10732 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d16", "d17", "d18", "d19",
10733 "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28", "d29",
10734 "cc", "memory");
10735 }
10736
10737 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)10738 inline void Stream<uint8_t, 7, 8, 5, ColumnMajorWithSum>::Pack(
10739 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
10740 #ifdef DEBUG
10741 #ifdef DEBUG_METAGEMM_VERBOSE
10742 std::cout
10743 << __FILE__ << "(" << __LINE__
10744 << ") ColumnMajorWithSum<uint8_t, 7, 8, 5, ColumnMajorWithSum>::Pack()"
10745 << std::endl
10746 << std::flush;
10747 #endif
10748 #endif
10749 int params_count_copy = params.count;
10750 int params_stride_copy = params.stride;
10751 asm volatile(
10752 "sub %[stride], %[stride], #4\n"
10753 "vmov.i16 q8, #0\n"
10754 "vmov.i16 q9, #0\n"
10755 "vmov.i16 q10, #0\n"
10756 "vmov.i16 q11, #0\n"
10757 "vmov.i16 q12, #0\n"
10758 "vmov.i16 q13, #0\n"
10759 "vmov.i16 q14, #0\n"
10760
10761 // Reduce count by leftovers.
10762 "subs %[count], %[count], #5\n"
10763 "beq 2f\n"
10764
10765 "1:"
10766 "subs %[count], %[count], #8\n"
10767
10768 // Load Aggregate Store - column major 7x8
10769 "vld1.32 {d0[0]}, [%[in]]!\n"
10770 "vld3.8 {d4[0], d5[0], d6[0]}, [%[in]], %[stride]\n"
10771 "vld1.32 {d1[0]}, [%[in]]!\n"
10772 "vld3.8 {d4[1], d5[1], d6[1]}, [%[in]], %[stride]\n"
10773 "vld1.32 {d2[0]}, [%[in]]!\n"
10774 "vld3.8 {d4[2], d5[2], d6[2]}, [%[in]], %[stride]\n"
10775 "vld1.32 {d3[0]}, [%[in]]!\n"
10776 "vld3.8 {d4[3], d5[3], d6[3]}, [%[in]], %[stride]\n"
10777 "vld1.32 {d0[1]}, [%[in]]!\n"
10778 "vld3.8 {d4[4], d5[4], d6[4]}, [%[in]], %[stride]\n"
10779 "vld1.32 {d1[1]}, [%[in]]!\n"
10780 "vld3.8 {d4[5], d5[5], d6[5]}, [%[in]], %[stride]\n"
10781 "vld1.32 {d2[1]}, [%[in]]!\n"
10782 "vld3.8 {d4[6], d5[6], d6[6]}, [%[in]], %[stride]\n"
10783 "vld1.32 {d3[1]}, [%[in]]!\n"
10784 "vld3.8 {d4[7], d5[7], d6[7]}, [%[in]], %[stride]\n"
10785 "pld [%[in]]\n"
10786 "vtrn.16 d0, d2\n"
10787 "vtrn.16 d1, d3\n"
10788 "vtrn.8 d0, d1\n"
10789 "vtrn.8 d2, d3\n"
10790 "vaddw.u8 q8, q8, d0\n"
10791 "vaddw.u8 q9, q9, d1\n"
10792 "vaddw.u8 q10, q10, d2\n"
10793 "vaddw.u8 q11, q11, d3\n"
10794 "vaddw.u8 q12, q12, d4\n"
10795 "vaddw.u8 q13, q13, d5\n"
10796 "vaddw.u8 q14, q14, d6\n"
10797 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
10798 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
10799
10800 "bne 1b\n"
10801
10802 "2:"
10803
10804 // Load Aggregate Store - column major 7x5
10805 "vmov.i8 d0, #0\n"
10806 "vmov.i8 d1, #0\n"
10807 "vmov.i8 d2, #0\n"
10808 "vmov.i8 d3, #0\n"
10809 "vmov.i8 d4, #0\n"
10810 "vmov.i8 d5, #0\n"
10811 "vmov.i8 d6, #0\n"
10812 "vld1.32 {d0[0]}, [%[in]]!\n"
10813 "vld3.8 {d4[0], d5[0], d6[0]}, [%[in]], %[stride]\n"
10814 "vld1.32 {d1[0]}, [%[in]]!\n"
10815 "vld3.8 {d4[1], d5[1], d6[1]}, [%[in]], %[stride]\n"
10816 "vld1.32 {d2[0]}, [%[in]]!\n"
10817 "vld3.8 {d4[2], d5[2], d6[2]}, [%[in]], %[stride]\n"
10818 "vld1.32 {d3[0]}, [%[in]]!\n"
10819 "vld3.8 {d4[3], d5[3], d6[3]}, [%[in]], %[stride]\n"
10820 "vld1.32 {d0[1]}, [%[in]]!\n"
10821 "vld3.8 {d4[4], d5[4], d6[4]}, [%[in]], %[stride]\n"
10822 "pld [%[in]]\n"
10823 "vtrn.16 d0, d2\n"
10824 "vtrn.16 d1, d3\n"
10825 "vtrn.8 d0, d1\n"
10826 "vtrn.8 d2, d3\n"
10827 "vaddw.u8 q8, q8, d0\n"
10828 "vaddw.u8 q9, q9, d1\n"
10829 "vaddw.u8 q10, q10, d2\n"
10830 "vaddw.u8 q11, q11, d3\n"
10831 "vaddw.u8 q12, q12, d4\n"
10832 "vaddw.u8 q13, q13, d5\n"
10833 "vaddw.u8 q14, q14, d6\n"
10834 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
10835 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
10836
10837 // Aggregator Reduction.
10838 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
10839 "vdup.32 q1, %[additive_sum_offset]\n"
10840 "vpaddl.u16 q8, q8\n"
10841 "vpaddl.u16 q9, q9\n"
10842 "vpaddl.u16 q10, q10\n"
10843 "vpaddl.u16 q11, q11\n"
10844 "vpaddl.u16 q12, q12\n"
10845 "vpaddl.u16 q13, q13\n"
10846 "vpaddl.u16 q14, q14\n"
10847 "vpadd.u32 d16, d16, d17\n"
10848 "vpadd.u32 d18, d18, d19\n"
10849 "vpadd.u32 d20, d20, d21\n"
10850 "vpadd.u32 d22, d22, d23\n"
10851 "vpadd.u32 d24, d24, d25\n"
10852 "vpadd.u32 d26, d26, d27\n"
10853 "vpadd.u32 d28, d28, d29\n"
10854 "vpadd.u32 d16, d16, d18\n"
10855 "vpadd.u32 d17, d20, d22\n"
10856 "vpadd.u32 d18, d24, d26\n"
10857 "vpadd.u32 d19, d28, d28\n"
10858 "vmul.i32 q8, q8, d0[0]\n"
10859 "vmul.i32 q9, q9, d0[0]\n"
10860 "vadd.i32 q8, q8, q1\n"
10861 "vadd.i32 q9, q9, q1\n"
10862 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
10863 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
10864 [out] "+r"(out), [in] "+r"(in)
10865 : [additive_sum_offset] "r"(params.additive_sum_offset),
10866 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
10867 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d16", "d17", "d18", "d19",
10868 "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28", "d29",
10869 "cc", "memory");
10870 }
10871
10872 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)10873 inline void Stream<uint8_t, 7, 8, 6, ColumnMajorWithSum>::Pack(
10874 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
10875 #ifdef DEBUG
10876 #ifdef DEBUG_METAGEMM_VERBOSE
10877 std::cout
10878 << __FILE__ << "(" << __LINE__
10879 << ") ColumnMajorWithSum<uint8_t, 7, 8, 6, ColumnMajorWithSum>::Pack()"
10880 << std::endl
10881 << std::flush;
10882 #endif
10883 #endif
10884 int params_count_copy = params.count;
10885 int params_stride_copy = params.stride;
10886 asm volatile(
10887 "sub %[stride], %[stride], #4\n"
10888 "vmov.i16 q8, #0\n"
10889 "vmov.i16 q9, #0\n"
10890 "vmov.i16 q10, #0\n"
10891 "vmov.i16 q11, #0\n"
10892 "vmov.i16 q12, #0\n"
10893 "vmov.i16 q13, #0\n"
10894 "vmov.i16 q14, #0\n"
10895
10896 // Reduce count by leftovers.
10897 "subs %[count], %[count], #6\n"
10898 "beq 2f\n"
10899
10900 "1:"
10901 "subs %[count], %[count], #8\n"
10902
10903 // Load Aggregate Store - column major 7x8
10904 "vld1.32 {d0[0]}, [%[in]]!\n"
10905 "vld3.8 {d4[0], d5[0], d6[0]}, [%[in]], %[stride]\n"
10906 "vld1.32 {d1[0]}, [%[in]]!\n"
10907 "vld3.8 {d4[1], d5[1], d6[1]}, [%[in]], %[stride]\n"
10908 "vld1.32 {d2[0]}, [%[in]]!\n"
10909 "vld3.8 {d4[2], d5[2], d6[2]}, [%[in]], %[stride]\n"
10910 "vld1.32 {d3[0]}, [%[in]]!\n"
10911 "vld3.8 {d4[3], d5[3], d6[3]}, [%[in]], %[stride]\n"
10912 "vld1.32 {d0[1]}, [%[in]]!\n"
10913 "vld3.8 {d4[4], d5[4], d6[4]}, [%[in]], %[stride]\n"
10914 "vld1.32 {d1[1]}, [%[in]]!\n"
10915 "vld3.8 {d4[5], d5[5], d6[5]}, [%[in]], %[stride]\n"
10916 "vld1.32 {d2[1]}, [%[in]]!\n"
10917 "vld3.8 {d4[6], d5[6], d6[6]}, [%[in]], %[stride]\n"
10918 "vld1.32 {d3[1]}, [%[in]]!\n"
10919 "vld3.8 {d4[7], d5[7], d6[7]}, [%[in]], %[stride]\n"
10920 "pld [%[in]]\n"
10921 "vtrn.16 d0, d2\n"
10922 "vtrn.16 d1, d3\n"
10923 "vtrn.8 d0, d1\n"
10924 "vtrn.8 d2, d3\n"
10925 "vaddw.u8 q8, q8, d0\n"
10926 "vaddw.u8 q9, q9, d1\n"
10927 "vaddw.u8 q10, q10, d2\n"
10928 "vaddw.u8 q11, q11, d3\n"
10929 "vaddw.u8 q12, q12, d4\n"
10930 "vaddw.u8 q13, q13, d5\n"
10931 "vaddw.u8 q14, q14, d6\n"
10932 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
10933 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
10934
10935 "bne 1b\n"
10936
10937 "2:"
10938
10939 // Load Aggregate Store - column major 7x6
10940 "vmov.i8 d0, #0\n"
10941 "vmov.i8 d1, #0\n"
10942 "vmov.i8 d2, #0\n"
10943 "vmov.i8 d3, #0\n"
10944 "vmov.i8 d4, #0\n"
10945 "vmov.i8 d5, #0\n"
10946 "vmov.i8 d6, #0\n"
10947 "vld1.32 {d0[0]}, [%[in]]!\n"
10948 "vld3.8 {d4[0], d5[0], d6[0]}, [%[in]], %[stride]\n"
10949 "vld1.32 {d1[0]}, [%[in]]!\n"
10950 "vld3.8 {d4[1], d5[1], d6[1]}, [%[in]], %[stride]\n"
10951 "vld1.32 {d2[0]}, [%[in]]!\n"
10952 "vld3.8 {d4[2], d5[2], d6[2]}, [%[in]], %[stride]\n"
10953 "vld1.32 {d3[0]}, [%[in]]!\n"
10954 "vld3.8 {d4[3], d5[3], d6[3]}, [%[in]], %[stride]\n"
10955 "vld1.32 {d0[1]}, [%[in]]!\n"
10956 "vld3.8 {d4[4], d5[4], d6[4]}, [%[in]], %[stride]\n"
10957 "vld1.32 {d1[1]}, [%[in]]!\n"
10958 "vld3.8 {d4[5], d5[5], d6[5]}, [%[in]], %[stride]\n"
10959 "pld [%[in]]\n"
10960 "vtrn.16 d0, d2\n"
10961 "vtrn.16 d1, d3\n"
10962 "vtrn.8 d0, d1\n"
10963 "vtrn.8 d2, d3\n"
10964 "vaddw.u8 q8, q8, d0\n"
10965 "vaddw.u8 q9, q9, d1\n"
10966 "vaddw.u8 q10, q10, d2\n"
10967 "vaddw.u8 q11, q11, d3\n"
10968 "vaddw.u8 q12, q12, d4\n"
10969 "vaddw.u8 q13, q13, d5\n"
10970 "vaddw.u8 q14, q14, d6\n"
10971 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
10972 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
10973
10974 // Aggregator Reduction.
10975 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
10976 "vdup.32 q1, %[additive_sum_offset]\n"
10977 "vpaddl.u16 q8, q8\n"
10978 "vpaddl.u16 q9, q9\n"
10979 "vpaddl.u16 q10, q10\n"
10980 "vpaddl.u16 q11, q11\n"
10981 "vpaddl.u16 q12, q12\n"
10982 "vpaddl.u16 q13, q13\n"
10983 "vpaddl.u16 q14, q14\n"
10984 "vpadd.u32 d16, d16, d17\n"
10985 "vpadd.u32 d18, d18, d19\n"
10986 "vpadd.u32 d20, d20, d21\n"
10987 "vpadd.u32 d22, d22, d23\n"
10988 "vpadd.u32 d24, d24, d25\n"
10989 "vpadd.u32 d26, d26, d27\n"
10990 "vpadd.u32 d28, d28, d29\n"
10991 "vpadd.u32 d16, d16, d18\n"
10992 "vpadd.u32 d17, d20, d22\n"
10993 "vpadd.u32 d18, d24, d26\n"
10994 "vpadd.u32 d19, d28, d28\n"
10995 "vmul.i32 q8, q8, d0[0]\n"
10996 "vmul.i32 q9, q9, d0[0]\n"
10997 "vadd.i32 q8, q8, q1\n"
10998 "vadd.i32 q9, q9, q1\n"
10999 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
11000 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
11001 [out] "+r"(out), [in] "+r"(in)
11002 : [additive_sum_offset] "r"(params.additive_sum_offset),
11003 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
11004 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d16", "d17", "d18", "d19",
11005 "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28", "d29",
11006 "cc", "memory");
11007 }
11008
11009 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)11010 inline void Stream<uint8_t, 7, 8, 7, ColumnMajorWithSum>::Pack(
11011 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
11012 #ifdef DEBUG
11013 #ifdef DEBUG_METAGEMM_VERBOSE
11014 std::cout
11015 << __FILE__ << "(" << __LINE__
11016 << ") ColumnMajorWithSum<uint8_t, 7, 8, 7, ColumnMajorWithSum>::Pack()"
11017 << std::endl
11018 << std::flush;
11019 #endif
11020 #endif
11021 int params_count_copy = params.count;
11022 int params_stride_copy = params.stride;
11023 asm volatile(
11024 "sub %[stride], %[stride], #4\n"
11025 "vmov.i16 q8, #0\n"
11026 "vmov.i16 q9, #0\n"
11027 "vmov.i16 q10, #0\n"
11028 "vmov.i16 q11, #0\n"
11029 "vmov.i16 q12, #0\n"
11030 "vmov.i16 q13, #0\n"
11031 "vmov.i16 q14, #0\n"
11032
11033 // Reduce count by leftovers.
11034 "subs %[count], %[count], #7\n"
11035 "beq 2f\n"
11036
11037 "1:"
11038 "subs %[count], %[count], #8\n"
11039
11040 // Load Aggregate Store - column major 7x8
11041 "vld1.32 {d0[0]}, [%[in]]!\n"
11042 "vld3.8 {d4[0], d5[0], d6[0]}, [%[in]], %[stride]\n"
11043 "vld1.32 {d1[0]}, [%[in]]!\n"
11044 "vld3.8 {d4[1], d5[1], d6[1]}, [%[in]], %[stride]\n"
11045 "vld1.32 {d2[0]}, [%[in]]!\n"
11046 "vld3.8 {d4[2], d5[2], d6[2]}, [%[in]], %[stride]\n"
11047 "vld1.32 {d3[0]}, [%[in]]!\n"
11048 "vld3.8 {d4[3], d5[3], d6[3]}, [%[in]], %[stride]\n"
11049 "vld1.32 {d0[1]}, [%[in]]!\n"
11050 "vld3.8 {d4[4], d5[4], d6[4]}, [%[in]], %[stride]\n"
11051 "vld1.32 {d1[1]}, [%[in]]!\n"
11052 "vld3.8 {d4[5], d5[5], d6[5]}, [%[in]], %[stride]\n"
11053 "vld1.32 {d2[1]}, [%[in]]!\n"
11054 "vld3.8 {d4[6], d5[6], d6[6]}, [%[in]], %[stride]\n"
11055 "vld1.32 {d3[1]}, [%[in]]!\n"
11056 "vld3.8 {d4[7], d5[7], d6[7]}, [%[in]], %[stride]\n"
11057 "pld [%[in]]\n"
11058 "vtrn.16 d0, d2\n"
11059 "vtrn.16 d1, d3\n"
11060 "vtrn.8 d0, d1\n"
11061 "vtrn.8 d2, d3\n"
11062 "vaddw.u8 q8, q8, d0\n"
11063 "vaddw.u8 q9, q9, d1\n"
11064 "vaddw.u8 q10, q10, d2\n"
11065 "vaddw.u8 q11, q11, d3\n"
11066 "vaddw.u8 q12, q12, d4\n"
11067 "vaddw.u8 q13, q13, d5\n"
11068 "vaddw.u8 q14, q14, d6\n"
11069 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
11070 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
11071
11072 "bne 1b\n"
11073
11074 "2:"
11075
11076 // Load Aggregate Store - column major 7x7
11077 "vmov.i8 d0, #0\n"
11078 "vmov.i8 d1, #0\n"
11079 "vmov.i8 d2, #0\n"
11080 "vmov.i8 d3, #0\n"
11081 "vmov.i8 d4, #0\n"
11082 "vmov.i8 d5, #0\n"
11083 "vmov.i8 d6, #0\n"
11084 "vld1.32 {d0[0]}, [%[in]]!\n"
11085 "vld3.8 {d4[0], d5[0], d6[0]}, [%[in]], %[stride]\n"
11086 "vld1.32 {d1[0]}, [%[in]]!\n"
11087 "vld3.8 {d4[1], d5[1], d6[1]}, [%[in]], %[stride]\n"
11088 "vld1.32 {d2[0]}, [%[in]]!\n"
11089 "vld3.8 {d4[2], d5[2], d6[2]}, [%[in]], %[stride]\n"
11090 "vld1.32 {d3[0]}, [%[in]]!\n"
11091 "vld3.8 {d4[3], d5[3], d6[3]}, [%[in]], %[stride]\n"
11092 "vld1.32 {d0[1]}, [%[in]]!\n"
11093 "vld3.8 {d4[4], d5[4], d6[4]}, [%[in]], %[stride]\n"
11094 "vld1.32 {d1[1]}, [%[in]]!\n"
11095 "vld3.8 {d4[5], d5[5], d6[5]}, [%[in]], %[stride]\n"
11096 "vld1.32 {d2[1]}, [%[in]]!\n"
11097 "vld3.8 {d4[6], d5[6], d6[6]}, [%[in]], %[stride]\n"
11098 "pld [%[in]]\n"
11099 "vtrn.16 d0, d2\n"
11100 "vtrn.16 d1, d3\n"
11101 "vtrn.8 d0, d1\n"
11102 "vtrn.8 d2, d3\n"
11103 "vaddw.u8 q8, q8, d0\n"
11104 "vaddw.u8 q9, q9, d1\n"
11105 "vaddw.u8 q10, q10, d2\n"
11106 "vaddw.u8 q11, q11, d3\n"
11107 "vaddw.u8 q12, q12, d4\n"
11108 "vaddw.u8 q13, q13, d5\n"
11109 "vaddw.u8 q14, q14, d6\n"
11110 "vst1.32 {d0, d1, d2, d3}, [%[out]:64]!\n"
11111 "vst1.32 {d4, d5, d6}, [%[out]:64]!\n"
11112
11113 // Aggregator Reduction.
11114 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
11115 "vdup.32 q1, %[additive_sum_offset]\n"
11116 "vpaddl.u16 q8, q8\n"
11117 "vpaddl.u16 q9, q9\n"
11118 "vpaddl.u16 q10, q10\n"
11119 "vpaddl.u16 q11, q11\n"
11120 "vpaddl.u16 q12, q12\n"
11121 "vpaddl.u16 q13, q13\n"
11122 "vpaddl.u16 q14, q14\n"
11123 "vpadd.u32 d16, d16, d17\n"
11124 "vpadd.u32 d18, d18, d19\n"
11125 "vpadd.u32 d20, d20, d21\n"
11126 "vpadd.u32 d22, d22, d23\n"
11127 "vpadd.u32 d24, d24, d25\n"
11128 "vpadd.u32 d26, d26, d27\n"
11129 "vpadd.u32 d28, d28, d29\n"
11130 "vpadd.u32 d16, d16, d18\n"
11131 "vpadd.u32 d17, d20, d22\n"
11132 "vpadd.u32 d18, d24, d26\n"
11133 "vpadd.u32 d19, d28, d28\n"
11134 "vmul.i32 q8, q8, d0[0]\n"
11135 "vmul.i32 q9, q9, d0[0]\n"
11136 "vadd.i32 q8, q8, q1\n"
11137 "vadd.i32 q9, q9, q1\n"
11138 "vst1.32 {d16, d17, d18, d19}, [%[out]:64]\n"
11139 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
11140 [out] "+r"(out), [in] "+r"(in)
11141 : [additive_sum_offset] "r"(params.additive_sum_offset),
11142 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
11143 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d16", "d17", "d18", "d19",
11144 "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28", "d29",
11145 "cc", "memory");
11146 }
11147
11148 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)11149 inline void Stream<uint8_t, 8, 8, 0, ColumnMajorWithSum>::Pack(
11150 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
11151 #ifdef DEBUG
11152 #ifdef DEBUG_METAGEMM_VERBOSE
11153 std::cout
11154 << __FILE__ << "(" << __LINE__
11155 << ") ColumnMajorWithSum<uint8_t, 8, 8, 0, ColumnMajorWithSum>::Pack()"
11156 << std::endl
11157 << std::flush;
11158 #endif
11159 #endif
11160 int params_count_copy = params.count;
11161 int params_stride_copy = params.stride;
11162 asm volatile(
11163 "vmov.i16 q8, #0\n"
11164 "vmov.i16 q9, #0\n"
11165 "vmov.i16 q10, #0\n"
11166 "vmov.i16 q11, #0\n"
11167 "vmov.i16 q12, #0\n"
11168 "vmov.i16 q13, #0\n"
11169 "vmov.i16 q14, #0\n"
11170 "vmov.i16 q15, #0\n"
11171
11172 "1:"
11173 "subs %[count], %[count], #8\n"
11174
11175 // Load Aggregate Store - column major 8x8
11176 "vld1.32 {d0}, [%[in]], %[stride]\n"
11177 "vld1.32 {d1}, [%[in]], %[stride]\n"
11178 "vld1.32 {d2}, [%[in]], %[stride]\n"
11179 "vld1.32 {d3}, [%[in]], %[stride]\n"
11180 "vld1.32 {d4}, [%[in]], %[stride]\n"
11181 "vld1.32 {d5}, [%[in]], %[stride]\n"
11182 "vld1.32 {d6}, [%[in]], %[stride]\n"
11183 "vld1.32 {d7}, [%[in]], %[stride]\n"
11184 "pld [%[in]]\n"
11185 "vtrn.8 d0, d1\n"
11186 "vtrn.8 d2, d3\n"
11187 "vtrn.8 d4, d5\n"
11188 "vtrn.8 d6, d7\n"
11189 "vtrn.16 d0, d2\n"
11190 "vtrn.16 d1, d3\n"
11191 "vtrn.16 d4, d6\n"
11192 "vtrn.16 d5, d7\n"
11193 "vtrn.32 d0, d4\n"
11194 "vtrn.32 d1, d5\n"
11195 "vtrn.32 d2, d6\n"
11196 "vtrn.32 d3, d7\n"
11197 "vaddw.u8 q8, q8, d0\n"
11198 "vaddw.u8 q9, q9, d1\n"
11199 "vaddw.u8 q10, q10, d2\n"
11200 "vaddw.u8 q11, q11, d3\n"
11201 "vaddw.u8 q12, q12, d4\n"
11202 "vaddw.u8 q13, q13, d5\n"
11203 "vaddw.u8 q14, q14, d6\n"
11204 "vaddw.u8 q15, q15, d7\n"
11205 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
11206 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
11207
11208 "bne 1b\n"
11209
11210 // Aggregator Reduction.
11211 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
11212 "vdup.32 q1, %[additive_sum_offset]\n"
11213 "vpaddl.u16 q8, q8\n"
11214 "vpaddl.u16 q9, q9\n"
11215 "vpaddl.u16 q10, q10\n"
11216 "vpaddl.u16 q11, q11\n"
11217 "vpaddl.u16 q12, q12\n"
11218 "vpaddl.u16 q13, q13\n"
11219 "vpaddl.u16 q14, q14\n"
11220 "vpaddl.u16 q15, q15\n"
11221 "vpadd.u32 d16, d16, d17\n"
11222 "vpadd.u32 d18, d18, d19\n"
11223 "vpadd.u32 d20, d20, d21\n"
11224 "vpadd.u32 d22, d22, d23\n"
11225 "vpadd.u32 d24, d24, d25\n"
11226 "vpadd.u32 d26, d26, d27\n"
11227 "vpadd.u32 d28, d28, d29\n"
11228 "vpadd.u32 d30, d30, d31\n"
11229 "vpadd.u32 d16, d16, d18\n"
11230 "vpadd.u32 d17, d20, d22\n"
11231 "vpadd.u32 d18, d24, d26\n"
11232 "vpadd.u32 d19, d28, d30\n"
11233 "vmul.i32 q8, q8, d0[0]\n"
11234 "vmul.i32 q9, q9, d0[0]\n"
11235 "vadd.i32 q8, q8, q1\n"
11236 "vadd.i32 q9, q9, q1\n"
11237 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
11238 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
11239 [out] "+r"(out), [in] "+r"(in)
11240 : [additive_sum_offset] "r"(params.additive_sum_offset),
11241 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
11242 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d7", "d16", "d17", "d18",
11243 "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28",
11244 "d29", "d30", "d31", "cc", "memory");
11245 }
11246
11247 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)11248 inline void Stream<uint8_t, 8, 8, 1, ColumnMajorWithSum>::Pack(
11249 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
11250 #ifdef DEBUG
11251 #ifdef DEBUG_METAGEMM_VERBOSE
11252 std::cout
11253 << __FILE__ << "(" << __LINE__
11254 << ") ColumnMajorWithSum<uint8_t, 8, 8, 1, ColumnMajorWithSum>::Pack()"
11255 << std::endl
11256 << std::flush;
11257 #endif
11258 #endif
11259 int params_count_copy = params.count;
11260 int params_stride_copy = params.stride;
11261 asm volatile(
11262 "vmov.i16 q8, #0\n"
11263 "vmov.i16 q9, #0\n"
11264 "vmov.i16 q10, #0\n"
11265 "vmov.i16 q11, #0\n"
11266 "vmov.i16 q12, #0\n"
11267 "vmov.i16 q13, #0\n"
11268 "vmov.i16 q14, #0\n"
11269 "vmov.i16 q15, #0\n"
11270
11271 // Reduce count by leftovers.
11272 "subs %[count], %[count], #1\n"
11273 "beq 2f\n"
11274
11275 "1:"
11276 "subs %[count], %[count], #8\n"
11277
11278 // Load Aggregate Store - column major 8x8
11279 "vld1.32 {d0}, [%[in]], %[stride]\n"
11280 "vld1.32 {d1}, [%[in]], %[stride]\n"
11281 "vld1.32 {d2}, [%[in]], %[stride]\n"
11282 "vld1.32 {d3}, [%[in]], %[stride]\n"
11283 "vld1.32 {d4}, [%[in]], %[stride]\n"
11284 "vld1.32 {d5}, [%[in]], %[stride]\n"
11285 "vld1.32 {d6}, [%[in]], %[stride]\n"
11286 "vld1.32 {d7}, [%[in]], %[stride]\n"
11287 "pld [%[in]]\n"
11288 "vtrn.8 d0, d1\n"
11289 "vtrn.8 d2, d3\n"
11290 "vtrn.8 d4, d5\n"
11291 "vtrn.8 d6, d7\n"
11292 "vtrn.16 d0, d2\n"
11293 "vtrn.16 d1, d3\n"
11294 "vtrn.16 d4, d6\n"
11295 "vtrn.16 d5, d7\n"
11296 "vtrn.32 d0, d4\n"
11297 "vtrn.32 d1, d5\n"
11298 "vtrn.32 d2, d6\n"
11299 "vtrn.32 d3, d7\n"
11300 "vaddw.u8 q8, q8, d0\n"
11301 "vaddw.u8 q9, q9, d1\n"
11302 "vaddw.u8 q10, q10, d2\n"
11303 "vaddw.u8 q11, q11, d3\n"
11304 "vaddw.u8 q12, q12, d4\n"
11305 "vaddw.u8 q13, q13, d5\n"
11306 "vaddw.u8 q14, q14, d6\n"
11307 "vaddw.u8 q15, q15, d7\n"
11308 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
11309 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
11310
11311 "bne 1b\n"
11312
11313 "2:"
11314
11315 // Load Aggregate Store - column major 8x1
11316 "vmov.i8 d0, #0\n"
11317 "vmov.i8 d1, #0\n"
11318 "vmov.i8 d2, #0\n"
11319 "vmov.i8 d3, #0\n"
11320 "vmov.i8 d4, #0\n"
11321 "vmov.i8 d5, #0\n"
11322 "vmov.i8 d6, #0\n"
11323 "vmov.i8 d7, #0\n"
11324 "vld1.32 {d0}, [%[in]], %[stride]\n"
11325 "pld [%[in]]\n"
11326 "vtrn.8 d0, d1\n"
11327 "vtrn.8 d2, d3\n"
11328 "vtrn.8 d4, d5\n"
11329 "vtrn.8 d6, d7\n"
11330 "vtrn.16 d0, d2\n"
11331 "vtrn.16 d1, d3\n"
11332 "vtrn.16 d4, d6\n"
11333 "vtrn.16 d5, d7\n"
11334 "vtrn.32 d0, d4\n"
11335 "vtrn.32 d1, d5\n"
11336 "vtrn.32 d2, d6\n"
11337 "vtrn.32 d3, d7\n"
11338 "vaddw.u8 q8, q8, d0\n"
11339 "vaddw.u8 q9, q9, d1\n"
11340 "vaddw.u8 q10, q10, d2\n"
11341 "vaddw.u8 q11, q11, d3\n"
11342 "vaddw.u8 q12, q12, d4\n"
11343 "vaddw.u8 q13, q13, d5\n"
11344 "vaddw.u8 q14, q14, d6\n"
11345 "vaddw.u8 q15, q15, d7\n"
11346 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
11347 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
11348
11349 // Aggregator Reduction.
11350 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
11351 "vdup.32 q1, %[additive_sum_offset]\n"
11352 "vpaddl.u16 q8, q8\n"
11353 "vpaddl.u16 q9, q9\n"
11354 "vpaddl.u16 q10, q10\n"
11355 "vpaddl.u16 q11, q11\n"
11356 "vpaddl.u16 q12, q12\n"
11357 "vpaddl.u16 q13, q13\n"
11358 "vpaddl.u16 q14, q14\n"
11359 "vpaddl.u16 q15, q15\n"
11360 "vpadd.u32 d16, d16, d17\n"
11361 "vpadd.u32 d18, d18, d19\n"
11362 "vpadd.u32 d20, d20, d21\n"
11363 "vpadd.u32 d22, d22, d23\n"
11364 "vpadd.u32 d24, d24, d25\n"
11365 "vpadd.u32 d26, d26, d27\n"
11366 "vpadd.u32 d28, d28, d29\n"
11367 "vpadd.u32 d30, d30, d31\n"
11368 "vpadd.u32 d16, d16, d18\n"
11369 "vpadd.u32 d17, d20, d22\n"
11370 "vpadd.u32 d18, d24, d26\n"
11371 "vpadd.u32 d19, d28, d30\n"
11372 "vmul.i32 q8, q8, d0[0]\n"
11373 "vmul.i32 q9, q9, d0[0]\n"
11374 "vadd.i32 q8, q8, q1\n"
11375 "vadd.i32 q9, q9, q1\n"
11376 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
11377 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
11378 [out] "+r"(out), [in] "+r"(in)
11379 : [additive_sum_offset] "r"(params.additive_sum_offset),
11380 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
11381 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d7", "d16", "d17", "d18",
11382 "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28",
11383 "d29", "d30", "d31", "cc", "memory");
11384 }
11385
11386 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)11387 inline void Stream<uint8_t, 8, 8, 2, ColumnMajorWithSum>::Pack(
11388 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
11389 #ifdef DEBUG
11390 #ifdef DEBUG_METAGEMM_VERBOSE
11391 std::cout
11392 << __FILE__ << "(" << __LINE__
11393 << ") ColumnMajorWithSum<uint8_t, 8, 8, 2, ColumnMajorWithSum>::Pack()"
11394 << std::endl
11395 << std::flush;
11396 #endif
11397 #endif
11398 int params_count_copy = params.count;
11399 int params_stride_copy = params.stride;
11400 asm volatile(
11401 "vmov.i16 q8, #0\n"
11402 "vmov.i16 q9, #0\n"
11403 "vmov.i16 q10, #0\n"
11404 "vmov.i16 q11, #0\n"
11405 "vmov.i16 q12, #0\n"
11406 "vmov.i16 q13, #0\n"
11407 "vmov.i16 q14, #0\n"
11408 "vmov.i16 q15, #0\n"
11409
11410 // Reduce count by leftovers.
11411 "subs %[count], %[count], #2\n"
11412 "beq 2f\n"
11413
11414 "1:"
11415 "subs %[count], %[count], #8\n"
11416
11417 // Load Aggregate Store - column major 8x8
11418 "vld1.32 {d0}, [%[in]], %[stride]\n"
11419 "vld1.32 {d1}, [%[in]], %[stride]\n"
11420 "vld1.32 {d2}, [%[in]], %[stride]\n"
11421 "vld1.32 {d3}, [%[in]], %[stride]\n"
11422 "vld1.32 {d4}, [%[in]], %[stride]\n"
11423 "vld1.32 {d5}, [%[in]], %[stride]\n"
11424 "vld1.32 {d6}, [%[in]], %[stride]\n"
11425 "vld1.32 {d7}, [%[in]], %[stride]\n"
11426 "pld [%[in]]\n"
11427 "vtrn.8 d0, d1\n"
11428 "vtrn.8 d2, d3\n"
11429 "vtrn.8 d4, d5\n"
11430 "vtrn.8 d6, d7\n"
11431 "vtrn.16 d0, d2\n"
11432 "vtrn.16 d1, d3\n"
11433 "vtrn.16 d4, d6\n"
11434 "vtrn.16 d5, d7\n"
11435 "vtrn.32 d0, d4\n"
11436 "vtrn.32 d1, d5\n"
11437 "vtrn.32 d2, d6\n"
11438 "vtrn.32 d3, d7\n"
11439 "vaddw.u8 q8, q8, d0\n"
11440 "vaddw.u8 q9, q9, d1\n"
11441 "vaddw.u8 q10, q10, d2\n"
11442 "vaddw.u8 q11, q11, d3\n"
11443 "vaddw.u8 q12, q12, d4\n"
11444 "vaddw.u8 q13, q13, d5\n"
11445 "vaddw.u8 q14, q14, d6\n"
11446 "vaddw.u8 q15, q15, d7\n"
11447 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
11448 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
11449
11450 "bne 1b\n"
11451
11452 "2:"
11453
11454 // Load Aggregate Store - column major 8x2
11455 "vmov.i8 d0, #0\n"
11456 "vmov.i8 d1, #0\n"
11457 "vmov.i8 d2, #0\n"
11458 "vmov.i8 d3, #0\n"
11459 "vmov.i8 d4, #0\n"
11460 "vmov.i8 d5, #0\n"
11461 "vmov.i8 d6, #0\n"
11462 "vmov.i8 d7, #0\n"
11463 "vld1.32 {d0}, [%[in]], %[stride]\n"
11464 "vld1.32 {d1}, [%[in]], %[stride]\n"
11465 "pld [%[in]]\n"
11466 "vtrn.8 d0, d1\n"
11467 "vtrn.8 d2, d3\n"
11468 "vtrn.8 d4, d5\n"
11469 "vtrn.8 d6, d7\n"
11470 "vtrn.16 d0, d2\n"
11471 "vtrn.16 d1, d3\n"
11472 "vtrn.16 d4, d6\n"
11473 "vtrn.16 d5, d7\n"
11474 "vtrn.32 d0, d4\n"
11475 "vtrn.32 d1, d5\n"
11476 "vtrn.32 d2, d6\n"
11477 "vtrn.32 d3, d7\n"
11478 "vaddw.u8 q8, q8, d0\n"
11479 "vaddw.u8 q9, q9, d1\n"
11480 "vaddw.u8 q10, q10, d2\n"
11481 "vaddw.u8 q11, q11, d3\n"
11482 "vaddw.u8 q12, q12, d4\n"
11483 "vaddw.u8 q13, q13, d5\n"
11484 "vaddw.u8 q14, q14, d6\n"
11485 "vaddw.u8 q15, q15, d7\n"
11486 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
11487 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
11488
11489 // Aggregator Reduction.
11490 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
11491 "vdup.32 q1, %[additive_sum_offset]\n"
11492 "vpaddl.u16 q8, q8\n"
11493 "vpaddl.u16 q9, q9\n"
11494 "vpaddl.u16 q10, q10\n"
11495 "vpaddl.u16 q11, q11\n"
11496 "vpaddl.u16 q12, q12\n"
11497 "vpaddl.u16 q13, q13\n"
11498 "vpaddl.u16 q14, q14\n"
11499 "vpaddl.u16 q15, q15\n"
11500 "vpadd.u32 d16, d16, d17\n"
11501 "vpadd.u32 d18, d18, d19\n"
11502 "vpadd.u32 d20, d20, d21\n"
11503 "vpadd.u32 d22, d22, d23\n"
11504 "vpadd.u32 d24, d24, d25\n"
11505 "vpadd.u32 d26, d26, d27\n"
11506 "vpadd.u32 d28, d28, d29\n"
11507 "vpadd.u32 d30, d30, d31\n"
11508 "vpadd.u32 d16, d16, d18\n"
11509 "vpadd.u32 d17, d20, d22\n"
11510 "vpadd.u32 d18, d24, d26\n"
11511 "vpadd.u32 d19, d28, d30\n"
11512 "vmul.i32 q8, q8, d0[0]\n"
11513 "vmul.i32 q9, q9, d0[0]\n"
11514 "vadd.i32 q8, q8, q1\n"
11515 "vadd.i32 q9, q9, q1\n"
11516 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
11517 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
11518 [out] "+r"(out), [in] "+r"(in)
11519 : [additive_sum_offset] "r"(params.additive_sum_offset),
11520 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
11521 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d7", "d16", "d17", "d18",
11522 "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28",
11523 "d29", "d30", "d31", "cc", "memory");
11524 }
11525
11526 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)11527 inline void Stream<uint8_t, 8, 8, 3, ColumnMajorWithSum>::Pack(
11528 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
11529 #ifdef DEBUG
11530 #ifdef DEBUG_METAGEMM_VERBOSE
11531 std::cout
11532 << __FILE__ << "(" << __LINE__
11533 << ") ColumnMajorWithSum<uint8_t, 8, 8, 3, ColumnMajorWithSum>::Pack()"
11534 << std::endl
11535 << std::flush;
11536 #endif
11537 #endif
11538 int params_count_copy = params.count;
11539 int params_stride_copy = params.stride;
11540 asm volatile(
11541 "vmov.i16 q8, #0\n"
11542 "vmov.i16 q9, #0\n"
11543 "vmov.i16 q10, #0\n"
11544 "vmov.i16 q11, #0\n"
11545 "vmov.i16 q12, #0\n"
11546 "vmov.i16 q13, #0\n"
11547 "vmov.i16 q14, #0\n"
11548 "vmov.i16 q15, #0\n"
11549
11550 // Reduce count by leftovers.
11551 "subs %[count], %[count], #3\n"
11552 "beq 2f\n"
11553
11554 "1:"
11555 "subs %[count], %[count], #8\n"
11556
11557 // Load Aggregate Store - column major 8x8
11558 "vld1.32 {d0}, [%[in]], %[stride]\n"
11559 "vld1.32 {d1}, [%[in]], %[stride]\n"
11560 "vld1.32 {d2}, [%[in]], %[stride]\n"
11561 "vld1.32 {d3}, [%[in]], %[stride]\n"
11562 "vld1.32 {d4}, [%[in]], %[stride]\n"
11563 "vld1.32 {d5}, [%[in]], %[stride]\n"
11564 "vld1.32 {d6}, [%[in]], %[stride]\n"
11565 "vld1.32 {d7}, [%[in]], %[stride]\n"
11566 "pld [%[in]]\n"
11567 "vtrn.8 d0, d1\n"
11568 "vtrn.8 d2, d3\n"
11569 "vtrn.8 d4, d5\n"
11570 "vtrn.8 d6, d7\n"
11571 "vtrn.16 d0, d2\n"
11572 "vtrn.16 d1, d3\n"
11573 "vtrn.16 d4, d6\n"
11574 "vtrn.16 d5, d7\n"
11575 "vtrn.32 d0, d4\n"
11576 "vtrn.32 d1, d5\n"
11577 "vtrn.32 d2, d6\n"
11578 "vtrn.32 d3, d7\n"
11579 "vaddw.u8 q8, q8, d0\n"
11580 "vaddw.u8 q9, q9, d1\n"
11581 "vaddw.u8 q10, q10, d2\n"
11582 "vaddw.u8 q11, q11, d3\n"
11583 "vaddw.u8 q12, q12, d4\n"
11584 "vaddw.u8 q13, q13, d5\n"
11585 "vaddw.u8 q14, q14, d6\n"
11586 "vaddw.u8 q15, q15, d7\n"
11587 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
11588 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
11589
11590 "bne 1b\n"
11591
11592 "2:"
11593
11594 // Load Aggregate Store - column major 8x3
11595 "vmov.i8 d0, #0\n"
11596 "vmov.i8 d1, #0\n"
11597 "vmov.i8 d2, #0\n"
11598 "vmov.i8 d3, #0\n"
11599 "vmov.i8 d4, #0\n"
11600 "vmov.i8 d5, #0\n"
11601 "vmov.i8 d6, #0\n"
11602 "vmov.i8 d7, #0\n"
11603 "vld1.32 {d0}, [%[in]], %[stride]\n"
11604 "vld1.32 {d1}, [%[in]], %[stride]\n"
11605 "vld1.32 {d2}, [%[in]], %[stride]\n"
11606 "pld [%[in]]\n"
11607 "vtrn.8 d0, d1\n"
11608 "vtrn.8 d2, d3\n"
11609 "vtrn.8 d4, d5\n"
11610 "vtrn.8 d6, d7\n"
11611 "vtrn.16 d0, d2\n"
11612 "vtrn.16 d1, d3\n"
11613 "vtrn.16 d4, d6\n"
11614 "vtrn.16 d5, d7\n"
11615 "vtrn.32 d0, d4\n"
11616 "vtrn.32 d1, d5\n"
11617 "vtrn.32 d2, d6\n"
11618 "vtrn.32 d3, d7\n"
11619 "vaddw.u8 q8, q8, d0\n"
11620 "vaddw.u8 q9, q9, d1\n"
11621 "vaddw.u8 q10, q10, d2\n"
11622 "vaddw.u8 q11, q11, d3\n"
11623 "vaddw.u8 q12, q12, d4\n"
11624 "vaddw.u8 q13, q13, d5\n"
11625 "vaddw.u8 q14, q14, d6\n"
11626 "vaddw.u8 q15, q15, d7\n"
11627 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
11628 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
11629
11630 // Aggregator Reduction.
11631 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
11632 "vdup.32 q1, %[additive_sum_offset]\n"
11633 "vpaddl.u16 q8, q8\n"
11634 "vpaddl.u16 q9, q9\n"
11635 "vpaddl.u16 q10, q10\n"
11636 "vpaddl.u16 q11, q11\n"
11637 "vpaddl.u16 q12, q12\n"
11638 "vpaddl.u16 q13, q13\n"
11639 "vpaddl.u16 q14, q14\n"
11640 "vpaddl.u16 q15, q15\n"
11641 "vpadd.u32 d16, d16, d17\n"
11642 "vpadd.u32 d18, d18, d19\n"
11643 "vpadd.u32 d20, d20, d21\n"
11644 "vpadd.u32 d22, d22, d23\n"
11645 "vpadd.u32 d24, d24, d25\n"
11646 "vpadd.u32 d26, d26, d27\n"
11647 "vpadd.u32 d28, d28, d29\n"
11648 "vpadd.u32 d30, d30, d31\n"
11649 "vpadd.u32 d16, d16, d18\n"
11650 "vpadd.u32 d17, d20, d22\n"
11651 "vpadd.u32 d18, d24, d26\n"
11652 "vpadd.u32 d19, d28, d30\n"
11653 "vmul.i32 q8, q8, d0[0]\n"
11654 "vmul.i32 q9, q9, d0[0]\n"
11655 "vadd.i32 q8, q8, q1\n"
11656 "vadd.i32 q9, q9, q1\n"
11657 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
11658 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
11659 [out] "+r"(out), [in] "+r"(in)
11660 : [additive_sum_offset] "r"(params.additive_sum_offset),
11661 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
11662 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d7", "d16", "d17", "d18",
11663 "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28",
11664 "d29", "d30", "d31", "cc", "memory");
11665 }
11666
11667 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)11668 inline void Stream<uint8_t, 8, 8, 4, ColumnMajorWithSum>::Pack(
11669 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
11670 #ifdef DEBUG
11671 #ifdef DEBUG_METAGEMM_VERBOSE
11672 std::cout
11673 << __FILE__ << "(" << __LINE__
11674 << ") ColumnMajorWithSum<uint8_t, 8, 8, 4, ColumnMajorWithSum>::Pack()"
11675 << std::endl
11676 << std::flush;
11677 #endif
11678 #endif
11679 int params_count_copy = params.count;
11680 int params_stride_copy = params.stride;
11681 asm volatile(
11682 "vmov.i16 q8, #0\n"
11683 "vmov.i16 q9, #0\n"
11684 "vmov.i16 q10, #0\n"
11685 "vmov.i16 q11, #0\n"
11686 "vmov.i16 q12, #0\n"
11687 "vmov.i16 q13, #0\n"
11688 "vmov.i16 q14, #0\n"
11689 "vmov.i16 q15, #0\n"
11690
11691 // Reduce count by leftovers.
11692 "subs %[count], %[count], #4\n"
11693 "beq 2f\n"
11694
11695 "1:"
11696 "subs %[count], %[count], #8\n"
11697
11698 // Load Aggregate Store - column major 8x8
11699 "vld1.32 {d0}, [%[in]], %[stride]\n"
11700 "vld1.32 {d1}, [%[in]], %[stride]\n"
11701 "vld1.32 {d2}, [%[in]], %[stride]\n"
11702 "vld1.32 {d3}, [%[in]], %[stride]\n"
11703 "vld1.32 {d4}, [%[in]], %[stride]\n"
11704 "vld1.32 {d5}, [%[in]], %[stride]\n"
11705 "vld1.32 {d6}, [%[in]], %[stride]\n"
11706 "vld1.32 {d7}, [%[in]], %[stride]\n"
11707 "pld [%[in]]\n"
11708 "vtrn.8 d0, d1\n"
11709 "vtrn.8 d2, d3\n"
11710 "vtrn.8 d4, d5\n"
11711 "vtrn.8 d6, d7\n"
11712 "vtrn.16 d0, d2\n"
11713 "vtrn.16 d1, d3\n"
11714 "vtrn.16 d4, d6\n"
11715 "vtrn.16 d5, d7\n"
11716 "vtrn.32 d0, d4\n"
11717 "vtrn.32 d1, d5\n"
11718 "vtrn.32 d2, d6\n"
11719 "vtrn.32 d3, d7\n"
11720 "vaddw.u8 q8, q8, d0\n"
11721 "vaddw.u8 q9, q9, d1\n"
11722 "vaddw.u8 q10, q10, d2\n"
11723 "vaddw.u8 q11, q11, d3\n"
11724 "vaddw.u8 q12, q12, d4\n"
11725 "vaddw.u8 q13, q13, d5\n"
11726 "vaddw.u8 q14, q14, d6\n"
11727 "vaddw.u8 q15, q15, d7\n"
11728 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
11729 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
11730
11731 "bne 1b\n"
11732
11733 "2:"
11734
11735 // Load Aggregate Store - column major 8x4
11736 "vmov.i8 d0, #0\n"
11737 "vmov.i8 d1, #0\n"
11738 "vmov.i8 d2, #0\n"
11739 "vmov.i8 d3, #0\n"
11740 "vmov.i8 d4, #0\n"
11741 "vmov.i8 d5, #0\n"
11742 "vmov.i8 d6, #0\n"
11743 "vmov.i8 d7, #0\n"
11744 "vld1.32 {d0}, [%[in]], %[stride]\n"
11745 "vld1.32 {d1}, [%[in]], %[stride]\n"
11746 "vld1.32 {d2}, [%[in]], %[stride]\n"
11747 "vld1.32 {d3}, [%[in]], %[stride]\n"
11748 "pld [%[in]]\n"
11749 "vtrn.8 d0, d1\n"
11750 "vtrn.8 d2, d3\n"
11751 "vtrn.8 d4, d5\n"
11752 "vtrn.8 d6, d7\n"
11753 "vtrn.16 d0, d2\n"
11754 "vtrn.16 d1, d3\n"
11755 "vtrn.16 d4, d6\n"
11756 "vtrn.16 d5, d7\n"
11757 "vtrn.32 d0, d4\n"
11758 "vtrn.32 d1, d5\n"
11759 "vtrn.32 d2, d6\n"
11760 "vtrn.32 d3, d7\n"
11761 "vaddw.u8 q8, q8, d0\n"
11762 "vaddw.u8 q9, q9, d1\n"
11763 "vaddw.u8 q10, q10, d2\n"
11764 "vaddw.u8 q11, q11, d3\n"
11765 "vaddw.u8 q12, q12, d4\n"
11766 "vaddw.u8 q13, q13, d5\n"
11767 "vaddw.u8 q14, q14, d6\n"
11768 "vaddw.u8 q15, q15, d7\n"
11769 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
11770 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
11771
11772 // Aggregator Reduction.
11773 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
11774 "vdup.32 q1, %[additive_sum_offset]\n"
11775 "vpaddl.u16 q8, q8\n"
11776 "vpaddl.u16 q9, q9\n"
11777 "vpaddl.u16 q10, q10\n"
11778 "vpaddl.u16 q11, q11\n"
11779 "vpaddl.u16 q12, q12\n"
11780 "vpaddl.u16 q13, q13\n"
11781 "vpaddl.u16 q14, q14\n"
11782 "vpaddl.u16 q15, q15\n"
11783 "vpadd.u32 d16, d16, d17\n"
11784 "vpadd.u32 d18, d18, d19\n"
11785 "vpadd.u32 d20, d20, d21\n"
11786 "vpadd.u32 d22, d22, d23\n"
11787 "vpadd.u32 d24, d24, d25\n"
11788 "vpadd.u32 d26, d26, d27\n"
11789 "vpadd.u32 d28, d28, d29\n"
11790 "vpadd.u32 d30, d30, d31\n"
11791 "vpadd.u32 d16, d16, d18\n"
11792 "vpadd.u32 d17, d20, d22\n"
11793 "vpadd.u32 d18, d24, d26\n"
11794 "vpadd.u32 d19, d28, d30\n"
11795 "vmul.i32 q8, q8, d0[0]\n"
11796 "vmul.i32 q9, q9, d0[0]\n"
11797 "vadd.i32 q8, q8, q1\n"
11798 "vadd.i32 q9, q9, q1\n"
11799 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
11800 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
11801 [out] "+r"(out), [in] "+r"(in)
11802 : [additive_sum_offset] "r"(params.additive_sum_offset),
11803 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
11804 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d7", "d16", "d17", "d18",
11805 "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28",
11806 "d29", "d30", "d31", "cc", "memory");
11807 }
11808
11809 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)11810 inline void Stream<uint8_t, 8, 8, 5, ColumnMajorWithSum>::Pack(
11811 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
11812 #ifdef DEBUG
11813 #ifdef DEBUG_METAGEMM_VERBOSE
11814 std::cout
11815 << __FILE__ << "(" << __LINE__
11816 << ") ColumnMajorWithSum<uint8_t, 8, 8, 5, ColumnMajorWithSum>::Pack()"
11817 << std::endl
11818 << std::flush;
11819 #endif
11820 #endif
11821 int params_count_copy = params.count;
11822 int params_stride_copy = params.stride;
11823 asm volatile(
11824 "vmov.i16 q8, #0\n"
11825 "vmov.i16 q9, #0\n"
11826 "vmov.i16 q10, #0\n"
11827 "vmov.i16 q11, #0\n"
11828 "vmov.i16 q12, #0\n"
11829 "vmov.i16 q13, #0\n"
11830 "vmov.i16 q14, #0\n"
11831 "vmov.i16 q15, #0\n"
11832
11833 // Reduce count by leftovers.
11834 "subs %[count], %[count], #5\n"
11835 "beq 2f\n"
11836
11837 "1:"
11838 "subs %[count], %[count], #8\n"
11839
11840 // Load Aggregate Store - column major 8x8
11841 "vld1.32 {d0}, [%[in]], %[stride]\n"
11842 "vld1.32 {d1}, [%[in]], %[stride]\n"
11843 "vld1.32 {d2}, [%[in]], %[stride]\n"
11844 "vld1.32 {d3}, [%[in]], %[stride]\n"
11845 "vld1.32 {d4}, [%[in]], %[stride]\n"
11846 "vld1.32 {d5}, [%[in]], %[stride]\n"
11847 "vld1.32 {d6}, [%[in]], %[stride]\n"
11848 "vld1.32 {d7}, [%[in]], %[stride]\n"
11849 "pld [%[in]]\n"
11850 "vtrn.8 d0, d1\n"
11851 "vtrn.8 d2, d3\n"
11852 "vtrn.8 d4, d5\n"
11853 "vtrn.8 d6, d7\n"
11854 "vtrn.16 d0, d2\n"
11855 "vtrn.16 d1, d3\n"
11856 "vtrn.16 d4, d6\n"
11857 "vtrn.16 d5, d7\n"
11858 "vtrn.32 d0, d4\n"
11859 "vtrn.32 d1, d5\n"
11860 "vtrn.32 d2, d6\n"
11861 "vtrn.32 d3, d7\n"
11862 "vaddw.u8 q8, q8, d0\n"
11863 "vaddw.u8 q9, q9, d1\n"
11864 "vaddw.u8 q10, q10, d2\n"
11865 "vaddw.u8 q11, q11, d3\n"
11866 "vaddw.u8 q12, q12, d4\n"
11867 "vaddw.u8 q13, q13, d5\n"
11868 "vaddw.u8 q14, q14, d6\n"
11869 "vaddw.u8 q15, q15, d7\n"
11870 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
11871 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
11872
11873 "bne 1b\n"
11874
11875 "2:"
11876
11877 // Load Aggregate Store - column major 8x5
11878 "vmov.i8 d0, #0\n"
11879 "vmov.i8 d1, #0\n"
11880 "vmov.i8 d2, #0\n"
11881 "vmov.i8 d3, #0\n"
11882 "vmov.i8 d4, #0\n"
11883 "vmov.i8 d5, #0\n"
11884 "vmov.i8 d6, #0\n"
11885 "vmov.i8 d7, #0\n"
11886 "vld1.32 {d0}, [%[in]], %[stride]\n"
11887 "vld1.32 {d1}, [%[in]], %[stride]\n"
11888 "vld1.32 {d2}, [%[in]], %[stride]\n"
11889 "vld1.32 {d3}, [%[in]], %[stride]\n"
11890 "vld1.32 {d4}, [%[in]], %[stride]\n"
11891 "pld [%[in]]\n"
11892 "vtrn.8 d0, d1\n"
11893 "vtrn.8 d2, d3\n"
11894 "vtrn.8 d4, d5\n"
11895 "vtrn.8 d6, d7\n"
11896 "vtrn.16 d0, d2\n"
11897 "vtrn.16 d1, d3\n"
11898 "vtrn.16 d4, d6\n"
11899 "vtrn.16 d5, d7\n"
11900 "vtrn.32 d0, d4\n"
11901 "vtrn.32 d1, d5\n"
11902 "vtrn.32 d2, d6\n"
11903 "vtrn.32 d3, d7\n"
11904 "vaddw.u8 q8, q8, d0\n"
11905 "vaddw.u8 q9, q9, d1\n"
11906 "vaddw.u8 q10, q10, d2\n"
11907 "vaddw.u8 q11, q11, d3\n"
11908 "vaddw.u8 q12, q12, d4\n"
11909 "vaddw.u8 q13, q13, d5\n"
11910 "vaddw.u8 q14, q14, d6\n"
11911 "vaddw.u8 q15, q15, d7\n"
11912 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
11913 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
11914
11915 // Aggregator Reduction.
11916 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
11917 "vdup.32 q1, %[additive_sum_offset]\n"
11918 "vpaddl.u16 q8, q8\n"
11919 "vpaddl.u16 q9, q9\n"
11920 "vpaddl.u16 q10, q10\n"
11921 "vpaddl.u16 q11, q11\n"
11922 "vpaddl.u16 q12, q12\n"
11923 "vpaddl.u16 q13, q13\n"
11924 "vpaddl.u16 q14, q14\n"
11925 "vpaddl.u16 q15, q15\n"
11926 "vpadd.u32 d16, d16, d17\n"
11927 "vpadd.u32 d18, d18, d19\n"
11928 "vpadd.u32 d20, d20, d21\n"
11929 "vpadd.u32 d22, d22, d23\n"
11930 "vpadd.u32 d24, d24, d25\n"
11931 "vpadd.u32 d26, d26, d27\n"
11932 "vpadd.u32 d28, d28, d29\n"
11933 "vpadd.u32 d30, d30, d31\n"
11934 "vpadd.u32 d16, d16, d18\n"
11935 "vpadd.u32 d17, d20, d22\n"
11936 "vpadd.u32 d18, d24, d26\n"
11937 "vpadd.u32 d19, d28, d30\n"
11938 "vmul.i32 q8, q8, d0[0]\n"
11939 "vmul.i32 q9, q9, d0[0]\n"
11940 "vadd.i32 q8, q8, q1\n"
11941 "vadd.i32 q9, q9, q1\n"
11942 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
11943 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
11944 [out] "+r"(out), [in] "+r"(in)
11945 : [additive_sum_offset] "r"(params.additive_sum_offset),
11946 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
11947 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d7", "d16", "d17", "d18",
11948 "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28",
11949 "d29", "d30", "d31", "cc", "memory");
11950 }
11951
11952 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)11953 inline void Stream<uint8_t, 8, 8, 6, ColumnMajorWithSum>::Pack(
11954 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
11955 #ifdef DEBUG
11956 #ifdef DEBUG_METAGEMM_VERBOSE
11957 std::cout
11958 << __FILE__ << "(" << __LINE__
11959 << ") ColumnMajorWithSum<uint8_t, 8, 8, 6, ColumnMajorWithSum>::Pack()"
11960 << std::endl
11961 << std::flush;
11962 #endif
11963 #endif
11964 int params_count_copy = params.count;
11965 int params_stride_copy = params.stride;
11966 asm volatile(
11967 "vmov.i16 q8, #0\n"
11968 "vmov.i16 q9, #0\n"
11969 "vmov.i16 q10, #0\n"
11970 "vmov.i16 q11, #0\n"
11971 "vmov.i16 q12, #0\n"
11972 "vmov.i16 q13, #0\n"
11973 "vmov.i16 q14, #0\n"
11974 "vmov.i16 q15, #0\n"
11975
11976 // Reduce count by leftovers.
11977 "subs %[count], %[count], #6\n"
11978 "beq 2f\n"
11979
11980 "1:"
11981 "subs %[count], %[count], #8\n"
11982
11983 // Load Aggregate Store - column major 8x8
11984 "vld1.32 {d0}, [%[in]], %[stride]\n"
11985 "vld1.32 {d1}, [%[in]], %[stride]\n"
11986 "vld1.32 {d2}, [%[in]], %[stride]\n"
11987 "vld1.32 {d3}, [%[in]], %[stride]\n"
11988 "vld1.32 {d4}, [%[in]], %[stride]\n"
11989 "vld1.32 {d5}, [%[in]], %[stride]\n"
11990 "vld1.32 {d6}, [%[in]], %[stride]\n"
11991 "vld1.32 {d7}, [%[in]], %[stride]\n"
11992 "pld [%[in]]\n"
11993 "vtrn.8 d0, d1\n"
11994 "vtrn.8 d2, d3\n"
11995 "vtrn.8 d4, d5\n"
11996 "vtrn.8 d6, d7\n"
11997 "vtrn.16 d0, d2\n"
11998 "vtrn.16 d1, d3\n"
11999 "vtrn.16 d4, d6\n"
12000 "vtrn.16 d5, d7\n"
12001 "vtrn.32 d0, d4\n"
12002 "vtrn.32 d1, d5\n"
12003 "vtrn.32 d2, d6\n"
12004 "vtrn.32 d3, d7\n"
12005 "vaddw.u8 q8, q8, d0\n"
12006 "vaddw.u8 q9, q9, d1\n"
12007 "vaddw.u8 q10, q10, d2\n"
12008 "vaddw.u8 q11, q11, d3\n"
12009 "vaddw.u8 q12, q12, d4\n"
12010 "vaddw.u8 q13, q13, d5\n"
12011 "vaddw.u8 q14, q14, d6\n"
12012 "vaddw.u8 q15, q15, d7\n"
12013 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
12014 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
12015
12016 "bne 1b\n"
12017
12018 "2:"
12019
12020 // Load Aggregate Store - column major 8x6
12021 "vmov.i8 d0, #0\n"
12022 "vmov.i8 d1, #0\n"
12023 "vmov.i8 d2, #0\n"
12024 "vmov.i8 d3, #0\n"
12025 "vmov.i8 d4, #0\n"
12026 "vmov.i8 d5, #0\n"
12027 "vmov.i8 d6, #0\n"
12028 "vmov.i8 d7, #0\n"
12029 "vld1.32 {d0}, [%[in]], %[stride]\n"
12030 "vld1.32 {d1}, [%[in]], %[stride]\n"
12031 "vld1.32 {d2}, [%[in]], %[stride]\n"
12032 "vld1.32 {d3}, [%[in]], %[stride]\n"
12033 "vld1.32 {d4}, [%[in]], %[stride]\n"
12034 "vld1.32 {d5}, [%[in]], %[stride]\n"
12035 "pld [%[in]]\n"
12036 "vtrn.8 d0, d1\n"
12037 "vtrn.8 d2, d3\n"
12038 "vtrn.8 d4, d5\n"
12039 "vtrn.8 d6, d7\n"
12040 "vtrn.16 d0, d2\n"
12041 "vtrn.16 d1, d3\n"
12042 "vtrn.16 d4, d6\n"
12043 "vtrn.16 d5, d7\n"
12044 "vtrn.32 d0, d4\n"
12045 "vtrn.32 d1, d5\n"
12046 "vtrn.32 d2, d6\n"
12047 "vtrn.32 d3, d7\n"
12048 "vaddw.u8 q8, q8, d0\n"
12049 "vaddw.u8 q9, q9, d1\n"
12050 "vaddw.u8 q10, q10, d2\n"
12051 "vaddw.u8 q11, q11, d3\n"
12052 "vaddw.u8 q12, q12, d4\n"
12053 "vaddw.u8 q13, q13, d5\n"
12054 "vaddw.u8 q14, q14, d6\n"
12055 "vaddw.u8 q15, q15, d7\n"
12056 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
12057 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
12058
12059 // Aggregator Reduction.
12060 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
12061 "vdup.32 q1, %[additive_sum_offset]\n"
12062 "vpaddl.u16 q8, q8\n"
12063 "vpaddl.u16 q9, q9\n"
12064 "vpaddl.u16 q10, q10\n"
12065 "vpaddl.u16 q11, q11\n"
12066 "vpaddl.u16 q12, q12\n"
12067 "vpaddl.u16 q13, q13\n"
12068 "vpaddl.u16 q14, q14\n"
12069 "vpaddl.u16 q15, q15\n"
12070 "vpadd.u32 d16, d16, d17\n"
12071 "vpadd.u32 d18, d18, d19\n"
12072 "vpadd.u32 d20, d20, d21\n"
12073 "vpadd.u32 d22, d22, d23\n"
12074 "vpadd.u32 d24, d24, d25\n"
12075 "vpadd.u32 d26, d26, d27\n"
12076 "vpadd.u32 d28, d28, d29\n"
12077 "vpadd.u32 d30, d30, d31\n"
12078 "vpadd.u32 d16, d16, d18\n"
12079 "vpadd.u32 d17, d20, d22\n"
12080 "vpadd.u32 d18, d24, d26\n"
12081 "vpadd.u32 d19, d28, d30\n"
12082 "vmul.i32 q8, q8, d0[0]\n"
12083 "vmul.i32 q9, q9, d0[0]\n"
12084 "vadd.i32 q8, q8, q1\n"
12085 "vadd.i32 q9, q9, q1\n"
12086 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
12087 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
12088 [out] "+r"(out), [in] "+r"(in)
12089 : [additive_sum_offset] "r"(params.additive_sum_offset),
12090 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
12091 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d7", "d16", "d17", "d18",
12092 "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28",
12093 "d29", "d30", "d31", "cc", "memory");
12094 }
12095
12096 template <>
Pack(const uint8_t * in,const ColumnMajorWithSum & params,uint8_t * out)12097 inline void Stream<uint8_t, 8, 8, 7, ColumnMajorWithSum>::Pack(
12098 const uint8_t* in, const ColumnMajorWithSum& params, uint8_t* out) {
12099 #ifdef DEBUG
12100 #ifdef DEBUG_METAGEMM_VERBOSE
12101 std::cout
12102 << __FILE__ << "(" << __LINE__
12103 << ") ColumnMajorWithSum<uint8_t, 8, 8, 7, ColumnMajorWithSum>::Pack()"
12104 << std::endl
12105 << std::flush;
12106 #endif
12107 #endif
12108 int params_count_copy = params.count;
12109 int params_stride_copy = params.stride;
12110 asm volatile(
12111 "vmov.i16 q8, #0\n"
12112 "vmov.i16 q9, #0\n"
12113 "vmov.i16 q10, #0\n"
12114 "vmov.i16 q11, #0\n"
12115 "vmov.i16 q12, #0\n"
12116 "vmov.i16 q13, #0\n"
12117 "vmov.i16 q14, #0\n"
12118 "vmov.i16 q15, #0\n"
12119
12120 // Reduce count by leftovers.
12121 "subs %[count], %[count], #7\n"
12122 "beq 2f\n"
12123
12124 "1:"
12125 "subs %[count], %[count], #8\n"
12126
12127 // Load Aggregate Store - column major 8x8
12128 "vld1.32 {d0}, [%[in]], %[stride]\n"
12129 "vld1.32 {d1}, [%[in]], %[stride]\n"
12130 "vld1.32 {d2}, [%[in]], %[stride]\n"
12131 "vld1.32 {d3}, [%[in]], %[stride]\n"
12132 "vld1.32 {d4}, [%[in]], %[stride]\n"
12133 "vld1.32 {d5}, [%[in]], %[stride]\n"
12134 "vld1.32 {d6}, [%[in]], %[stride]\n"
12135 "vld1.32 {d7}, [%[in]], %[stride]\n"
12136 "pld [%[in]]\n"
12137 "vtrn.8 d0, d1\n"
12138 "vtrn.8 d2, d3\n"
12139 "vtrn.8 d4, d5\n"
12140 "vtrn.8 d6, d7\n"
12141 "vtrn.16 d0, d2\n"
12142 "vtrn.16 d1, d3\n"
12143 "vtrn.16 d4, d6\n"
12144 "vtrn.16 d5, d7\n"
12145 "vtrn.32 d0, d4\n"
12146 "vtrn.32 d1, d5\n"
12147 "vtrn.32 d2, d6\n"
12148 "vtrn.32 d3, d7\n"
12149 "vaddw.u8 q8, q8, d0\n"
12150 "vaddw.u8 q9, q9, d1\n"
12151 "vaddw.u8 q10, q10, d2\n"
12152 "vaddw.u8 q11, q11, d3\n"
12153 "vaddw.u8 q12, q12, d4\n"
12154 "vaddw.u8 q13, q13, d5\n"
12155 "vaddw.u8 q14, q14, d6\n"
12156 "vaddw.u8 q15, q15, d7\n"
12157 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
12158 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
12159
12160 "bne 1b\n"
12161
12162 "2:"
12163
12164 // Load Aggregate Store - column major 8x7
12165 "vmov.i8 d0, #0\n"
12166 "vmov.i8 d1, #0\n"
12167 "vmov.i8 d2, #0\n"
12168 "vmov.i8 d3, #0\n"
12169 "vmov.i8 d4, #0\n"
12170 "vmov.i8 d5, #0\n"
12171 "vmov.i8 d6, #0\n"
12172 "vmov.i8 d7, #0\n"
12173 "vld1.32 {d0}, [%[in]], %[stride]\n"
12174 "vld1.32 {d1}, [%[in]], %[stride]\n"
12175 "vld1.32 {d2}, [%[in]], %[stride]\n"
12176 "vld1.32 {d3}, [%[in]], %[stride]\n"
12177 "vld1.32 {d4}, [%[in]], %[stride]\n"
12178 "vld1.32 {d5}, [%[in]], %[stride]\n"
12179 "vld1.32 {d6}, [%[in]], %[stride]\n"
12180 "pld [%[in]]\n"
12181 "vtrn.8 d0, d1\n"
12182 "vtrn.8 d2, d3\n"
12183 "vtrn.8 d4, d5\n"
12184 "vtrn.8 d6, d7\n"
12185 "vtrn.16 d0, d2\n"
12186 "vtrn.16 d1, d3\n"
12187 "vtrn.16 d4, d6\n"
12188 "vtrn.16 d5, d7\n"
12189 "vtrn.32 d0, d4\n"
12190 "vtrn.32 d1, d5\n"
12191 "vtrn.32 d2, d6\n"
12192 "vtrn.32 d3, d7\n"
12193 "vaddw.u8 q8, q8, d0\n"
12194 "vaddw.u8 q9, q9, d1\n"
12195 "vaddw.u8 q10, q10, d2\n"
12196 "vaddw.u8 q11, q11, d3\n"
12197 "vaddw.u8 q12, q12, d4\n"
12198 "vaddw.u8 q13, q13, d5\n"
12199 "vaddw.u8 q14, q14, d6\n"
12200 "vaddw.u8 q15, q15, d7\n"
12201 "vst1.32 {d0, d1, d2, d3}, [%[out]:256]!\n"
12202 "vst1.32 {d4, d5, d6, d7}, [%[out]:256]!\n"
12203
12204 // Aggregator Reduction.
12205 "vmov.32 d0[0], %[multiplicative_sum_offset]\n"
12206 "vdup.32 q1, %[additive_sum_offset]\n"
12207 "vpaddl.u16 q8, q8\n"
12208 "vpaddl.u16 q9, q9\n"
12209 "vpaddl.u16 q10, q10\n"
12210 "vpaddl.u16 q11, q11\n"
12211 "vpaddl.u16 q12, q12\n"
12212 "vpaddl.u16 q13, q13\n"
12213 "vpaddl.u16 q14, q14\n"
12214 "vpaddl.u16 q15, q15\n"
12215 "vpadd.u32 d16, d16, d17\n"
12216 "vpadd.u32 d18, d18, d19\n"
12217 "vpadd.u32 d20, d20, d21\n"
12218 "vpadd.u32 d22, d22, d23\n"
12219 "vpadd.u32 d24, d24, d25\n"
12220 "vpadd.u32 d26, d26, d27\n"
12221 "vpadd.u32 d28, d28, d29\n"
12222 "vpadd.u32 d30, d30, d31\n"
12223 "vpadd.u32 d16, d16, d18\n"
12224 "vpadd.u32 d17, d20, d22\n"
12225 "vpadd.u32 d18, d24, d26\n"
12226 "vpadd.u32 d19, d28, d30\n"
12227 "vmul.i32 q8, q8, d0[0]\n"
12228 "vmul.i32 q9, q9, d0[0]\n"
12229 "vadd.i32 q8, q8, q1\n"
12230 "vadd.i32 q9, q9, q1\n"
12231 "vst1.32 {d16, d17, d18, d19}, [%[out]:256]\n"
12232 : [count] "+r"(params_count_copy), [stride] "+r"(params_stride_copy),
12233 [out] "+r"(out), [in] "+r"(in)
12234 : [additive_sum_offset] "r"(params.additive_sum_offset),
12235 [multiplicative_sum_offset] "r"(params.multiplicative_sum_offset)
12236 : "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d7", "d16", "d17", "d18",
12237 "d19", "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28",
12238 "d29", "d30", "d31", "cc", "memory");
12239 }
12240
12241 } // namespace meta
12242 } // namespace gemmlowp
12243
12244 #else
12245 #warning "Meta gemm for arm32 requires: GEMMLOWP_NEON_32!"
12246 #endif
12247
12248 #endif // GEMMLOWP_META_STREAMS_ARM_32_H_
12249