blob: 064ffe243937dafd06a99604684d5929f12cf276 [file] [log] [blame]
Frank Barchard8b0f0262019-11-27 23:18:40 -08001// Copyright 2019 Google LLC
2//
3// This source code is licensed under the BSD-style license found in the
4// LICENSE file in the root directory of this source tree.
5
6#include <xnnpack/assembly.h>
7
8.syntax unified
9
10// void xnn_f32_gemm_ukernel_4x8__aarch32_neon_ld64(
Frank Barchard72d6afb2019-11-30 19:21:26 -080011// size_t mr, r0
12// size_t nc, r1
Frank Barchardf917cbd2019-12-04 23:02:08 -080013// size_t kc, r2 -> r5
Frank Barchard72d6afb2019-11-30 19:21:26 -080014// const uint8_t*restrict a, r3
Frank Barchardf917cbd2019-12-04 23:02:08 -080015// size_t a_stride, sp + 96 -> (r7)
Frank Barchard61cad892019-12-02 13:06:15 -080016// const void*restrict w, sp + 100 -> r9
Frank Barchardf917cbd2019-12-04 23:02:08 -080017// uint8_t*restrict c, sp + 104 -> r11
Frank Barchard61cad892019-12-02 13:06:15 -080018// size_t cm_stride, sp + 108 -> (r6)
Frank Barchardf917cbd2019-12-04 23:02:08 -080019// size_t cn_stride, sp + 112 -> r7
Marat Dukhaneb09a6b2020-04-08 17:34:32 -070020// const union xnn_f32_minmax_params params[restrict static 1]) sp + 116 -> (r7)
Frank Barchard8b0f0262019-11-27 23:18:40 -080021
22
23// inner loop registers
24
Frank Barchard61cad892019-12-02 13:06:15 -080025// A0 r3 d0
26// A1 r12 d1
27// A2 r10 d2
28// A3 r0 d3
Frank Barchard8b0f0262019-11-27 23:18:40 -080029
Frank Barchard72d6afb2019-11-30 19:21:26 -080030// B r9 d8, d9, d10, d11
31// B d12, d13, d14, d15
Frank Barchard8b0f0262019-11-27 23:18:40 -080032
Frank Barchardf917cbd2019-12-04 23:02:08 -080033// C0 r11 d16-d17 q8 d18-d19 q9
Frank Barchard72d6afb2019-11-30 19:21:26 -080034// C1 r4 d20-d21 q10 d22-d23 q11
Frank Barchard61cad892019-12-02 13:06:15 -080035// C2 r8 d24-d25 q12 d26-d27 q13
36// C3 r6 d28-d29 q14 d30-d31 q15
Frank Barchard72d6afb2019-11-30 19:21:26 -080037
Frank Barchard61cad892019-12-02 13:06:15 -080038// Clamp (r5) d4 d5 d6 d7
Frank Barchard8b0f0262019-11-27 23:18:40 -080039
40BEGIN_FUNCTION xnn_f32_gemm_ukernel_4x8__aarch32_neon_ld64
41 .arm
42#ifndef __APPLE__
43 .arch armv7-a
44 .fpu neon
45#endif
Frank Barchard61cad892019-12-02 13:06:15 -080046 // Push 96 bytes
Frank Barchardf917cbd2019-12-04 23:02:08 -080047 PUSH {r4, r5, r6, r7, r8, r9, r10, r11} // 32
Frank Barchard61cad892019-12-02 13:06:15 -080048 VPUSH {d8-d15} // +64 = 96
Frank Barchard72d6afb2019-11-30 19:21:26 -080049
Frank Barchardf917cbd2019-12-04 23:02:08 -080050 LDR r7, [sp, 96] // a_stride
Frank Barchardf917cbd2019-12-04 23:02:08 -080051 LDR r11, [sp, 104] // c
52 LDR r6, [sp, 108] // cm_stride
Frank Barchard9b499d62020-02-12 11:05:00 -080053 LDR r9, [sp, 100] // w
Marat Dukhaneb09a6b2020-04-08 17:34:32 -070054 LDR r5, [sp, 116] // params
Frank Barchardf917cbd2019-12-04 23:02:08 -080055
Frank Barchard72d6afb2019-11-30 19:21:26 -080056 // Clamp A and C pointers
Frank Barchard61cad892019-12-02 13:06:15 -080057 CMP r0, 2 // if mr >= 2
Frank Barchardf917cbd2019-12-04 23:02:08 -080058 ADD r12, r3, r7 // a1 = a0 + a_stride
59 ADD r4, r11, r6 // c1 = c0 + cm_stride
Frank Barchard61cad892019-12-02 13:06:15 -080060 MOVLO r12, r3 // a1
Frank Barchardf917cbd2019-12-04 23:02:08 -080061 MOVLO r4, r11 // c1
Frank Barchard61cad892019-12-02 13:06:15 -080062 // if mr > 2
Frank Barchardf917cbd2019-12-04 23:02:08 -080063 ADD r10, r12, r7 // a2 = a1 + a_stride
64 ADD r8, r4, r6 // c2 = c1 + cm_stride
Frank Barchard61cad892019-12-02 13:06:15 -080065 MOVLS r10, r12 // a2
66 MOVLS r8, r4 // c2
67
68 CMP r0, 4 // if mr >=4
Frank Barchardf917cbd2019-12-04 23:02:08 -080069 ADD r0, r10, r7 // a3 = a2 + a_stride
70 ADD r6, r8, r6 // c3 = c2 + cm_stride
Frank Barchard61cad892019-12-02 13:06:15 -080071 MOVLO r0, r10 // a3
72 MOVLO r6, r8 // c3
73
Marat Dukhaneb09a6b2020-04-08 17:34:32 -070074 // Load min/max values
Frank Barchardb738ad22019-12-10 00:02:50 -080075 VLD1.32 {d4[], d5[]}, [r5]!
76 LDR r7, [sp, 112] // cn_stride
77 VLD1.32 {d6[], d7[]}, [r5]
Frank Barchard61cad892019-12-02 13:06:15 -080078
Frank Barchard8b0f0262019-11-27 23:18:40 -0800791:
Frank Barchard72d6afb2019-11-30 19:21:26 -080080 # Load initial bias from w into accumulators
Frank Barchard61cad892019-12-02 13:06:15 -080081 VLDM r9!, {d16-d19} // Bias
Frank Barchardf917cbd2019-12-04 23:02:08 -080082 SUBS r5, r2, 8
Frank Barchard61cad892019-12-02 13:06:15 -080083 VMOV q10, q8
84 VMOV q11, q9
85 VMOV q12, q8
86 VMOV q13, q9
87 VMOV q14, q8
88 VMOV q15, q9
Frank Barchard9b499d62020-02-12 11:05:00 -080089 BLO 5f // less than 2 channels?
Frank Barchard8b0f0262019-11-27 23:18:40 -080090
Frank Barchard72d6afb2019-11-30 19:21:26 -080091 // Main loop - 2 floats of A (8 bytes)
922:
Frank Barchard61cad892019-12-02 13:06:15 -080093 VLD1.32 {d0}, [r3]! // A0
Frank Barchard72d6afb2019-11-30 19:21:26 -080094 VLDM r9!, {d8-d11} // B0
Frank Barchard61cad892019-12-02 13:06:15 -080095 VLD1.32 {d1}, [r12]! // A1
96 VLD1.32 {d2}, [r10]! // A2
97 VLD1.32 {d3}, [ r0]! // A3
98
99 VMLA.F32 q8, q4, d0[0]
100 VMLA.F32 q9, q5, d0[0]
101 VMLA.F32 q10, q4, d1[0]
102 VMLA.F32 q11, q5, d1[0]
Frank Barchard72d6afb2019-11-30 19:21:26 -0800103 VLDM r9!, {d12-d15} // B1
Frank Barchard61cad892019-12-02 13:06:15 -0800104 VMLA.F32 q12, q4, d2[0]
105 VMLA.F32 q13, q5, d2[0]
106 VMLA.F32 q14, q4, d3[0]
107 VMLA.F32 q15, q5, d3[0]
108 VMLA.F32 q8, q6, d0[1]
109 VMLA.F32 q9, q7, d0[1]
110 VMLA.F32 q10, q6, d1[1]
111 VMLA.F32 q11, q7, d1[1]
112 VMLA.F32 q12, q6, d2[1]
113 VMLA.F32 q13, q7, d2[1]
Frank Barchardf917cbd2019-12-04 23:02:08 -0800114 SUBS r5, r5, 8
Frank Barchard61cad892019-12-02 13:06:15 -0800115 VMLA.F32 q14, q6, d3[1]
116 VMLA.F32 q15, q7, d3[1]
117 BHS 2b
Frank Barchard8b0f0262019-11-27 23:18:40 -0800118
Frank Barchard61cad892019-12-02 13:06:15 -0800119 // Is there a remainder?- 1 floats of A (4 bytes)
Frank Barchardf917cbd2019-12-04 23:02:08 -0800120 TST r5, 4
Frank Barchard9b499d62020-02-12 11:05:00 -0800121 BNE 5f
Frank Barchard8b0f0262019-11-27 23:18:40 -0800122
Frank Barchard61cad892019-12-02 13:06:15 -08001234:
124 // Clamp
Marat Dukhana51cf482020-04-08 16:16:19 -0700125 VMAX.F32 q8, q8, q2
Frank Barchard0090f5b2019-12-16 17:02:57 -0800126 SUBS r1, r1, 8
Marat Dukhana51cf482020-04-08 16:16:19 -0700127 VMAX.F32 q9, q9, q2
128 VMAX.F32 q10, q10, q2
129 VMAX.F32 q11, q11, q2
130 VMAX.F32 q12, q12, q2
131 VMAX.F32 q13, q13, q2
132 VMAX.F32 q14, q14, q2
133 VMAX.F32 q15, q15, q2
134 VMIN.F32 q8, q8, q3
135 VMIN.F32 q9, q9, q3
136 VMIN.F32 q10, q10, q3
137 VMIN.F32 q11, q11, q3
138 VMIN.F32 q12, q12, q3
139 VMIN.F32 q13, q13, q3
140 VMIN.F32 q14, q14, q3
141 VMIN.F32 q15, q15, q3
Frank Barchard72d6afb2019-11-30 19:21:26 -0800142
Frank Barchard61cad892019-12-02 13:06:15 -0800143 // Store full 4 x 8
Frank Barchardf917cbd2019-12-04 23:02:08 -0800144 BLO 10f
145 VST1.32 {d16-d19}, [r11], r7
Frank Barchard61cad892019-12-02 13:06:15 -0800146 SUB r0, r0, r2
Frank Barchardf917cbd2019-12-04 23:02:08 -0800147 VST1.32 {d20-d23}, [r4], r7
Frank Barchard61cad892019-12-02 13:06:15 -0800148 SUB r10, r10, r2
Frank Barchardf917cbd2019-12-04 23:02:08 -0800149 VST1.32 {d24-d27}, [r8], r7
Frank Barchard61cad892019-12-02 13:06:15 -0800150 SUB r12, r12, r2
Frank Barchardf917cbd2019-12-04 23:02:08 -0800151 VST1.32 {d28-d31}, [r6], r7
Frank Barchard61cad892019-12-02 13:06:15 -0800152 SUB r3, r3, r2
Frank Barchardf917cbd2019-12-04 23:02:08 -0800153 BHI 1b
Frank Barchard8b0f0262019-11-27 23:18:40 -0800154
Frank Barchard61cad892019-12-02 13:06:15 -0800155 VPOP {d8-d15}
Frank Barchardf917cbd2019-12-04 23:02:08 -0800156 POP {r4, r5, r6, r7, r8, r9, r10, r11}
157 BX lr
Frank Barchard8b0f0262019-11-27 23:18:40 -0800158
Frank Barchard9b499d62020-02-12 11:05:00 -08001595:
Frank Barchard61cad892019-12-02 13:06:15 -0800160 // Remainder- 1 floats of A (4 bytes)
161 VLDM r3!, {s0} // A0
162 VLDM r9!, {d8-d11} // B0
163 VLDM r12!, {s2} // A1
164 VLDM r10!, {s4} // A2
165 VLDM r0!, {s6} // A3
166 VMLA.F32 q8, q4, d0[0]
167 VMLA.F32 q9, q5, d0[0]
168 VMLA.F32 q10, q4, d1[0]
169 VMLA.F32 q11, q5, d1[0]
170 VMLA.F32 q12, q4, d2[0]
171 VMLA.F32 q13, q5, d2[0]
172 VMLA.F32 q14, q4, d3[0]
173 VMLA.F32 q15, q5, d3[0]
174 B 4b
Frank Barchard8b0f0262019-11-27 23:18:40 -0800175
Frank Barchard9b499d62020-02-12 11:05:00 -0800176 // Store odd width
Frank Barchard8b0f0262019-11-27 23:18:40 -080017710:
Frank Barchard61cad892019-12-02 13:06:15 -0800178 TST r1, 4
Frank Barchardf917cbd2019-12-04 23:02:08 -0800179 BEQ 11f
180 VST1.32 {d16-d17}, [r11]!
181 VMOV q8, q9
182 VST1.32 {d20-d21}, [r4]!
183 VMOV q10, q11
184 VST1.32 {d24-d25}, [r8]!
185 VMOV q12, q13
186 VST1.32 {d28-d29}, [r6]!
187 VMOV q14, q15
Frank Barchard61cad892019-12-02 13:06:15 -0800188
Frank Barchard8b0f0262019-11-27 23:18:40 -080018911:
Frank Barchardf917cbd2019-12-04 23:02:08 -0800190 TST r1, 2
191 BEQ 12f
192 VST1.32 {d16}, [r11]!
193 VMOV d16, d17
194 VST1.32 {d20}, [r4]!
195 VMOV d20, d21
196 VST1.32 {d24}, [r8]!
197 VMOV d24, d25
198 VST1.32 {d28}, [r6]!
199 VMOV d28, d29
Frank Barchard8b0f0262019-11-27 23:18:40 -0800200
20112:
Frank Barchardf917cbd2019-12-04 23:02:08 -0800202 TST r1, 1
203 BEQ 13f
204 VST1.32 {d16[0]}, [r11]
205 VST1.32 {d20[0]}, [r4]
206 VST1.32 {d24[0]}, [r8]
207 VST1.32 {d28[0]}, [r6]
208
20913:
210 VPOP {d8-d15}
211 POP {r4, r5, r6, r7, r8, r9, r10, r11}
212 BX lr
Frank Barchard8b0f0262019-11-27 23:18:40 -0800213
214END_FUNCTION xnn_f32_gemm_ukernel_4x8__aarch32_neon_ld64
215
216#ifdef __ELF__
217.section ".note.GNU-stack","",%progbits
218#endif
219
220
221