Browse Source

use mul for the first multiply, drop accumulator clear instructions, about 5% speed performance gains

tags/20171225
nihui 8 years ago
parent
commit
32cd5f2a5c
3 changed files with 36 additions and 60 deletions
  1. +11
    -34
      src/layer/arm/convolution_3x3.h
  2. +15
    -16
      src/layer/arm/convolution_5x5.h
  3. +10
    -10
      src/layer/arm/convolution_7x7.h

+ 11
- 34
src/layer/arm/convolution_3x3.h View File

@@ -79,9 +79,7 @@ static void conv3x3s1_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
for (; nn>0; nn--)
{
float32x4_t _sum1 = vld1q_f32(outptr);
float32x4_t _sum2 = vdupq_n_f32(0.f);
float32x4_t _sum3 = vld1q_f32(outptr2);
float32x4_t _sum4 = vdupq_n_f32(0.f);

float32x4_t _r00 = vld1q_f32(r0);
float32x4_t _r00n = vld1q_f32(r0 + 4);
@@ -104,7 +102,7 @@ static void conv3x3s1_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
float32x4_t _r32 = vextq_f32(_r30, _r30n, 2);

_sum1 = vfmaq_laneq_f32(_sum1, _r00, _k0123, 0);
_sum2 = vfmaq_laneq_f32(_sum2, _r01, _k0123, 1);
float32x4_t _sum2 = vmulq_laneq_f32(_r01, _k0123, 1);
_sum1 = vfmaq_laneq_f32(_sum1, _r02, _k0123, 2);
_sum2 = vfmaq_laneq_f32(_sum2, _r10, _k3456, 0);
_sum1 = vfmaq_laneq_f32(_sum1, _r11, _k3456, 1);
@@ -114,7 +112,7 @@ static void conv3x3s1_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
_sum1 = vfmaq_laneq_f32(_sum1, _r22, _k6789, 2);

_sum3 = vfmaq_laneq_f32(_sum3, _r10, _k0123, 0);
_sum4 = vfmaq_laneq_f32(_sum4, _r11, _k0123, 1);
float32x4_t _sum4 = vmulq_laneq_f32(_r11, _k0123, 1);
_sum3 = vfmaq_laneq_f32(_sum3, _r12, _k0123, 2);
_sum4 = vfmaq_laneq_f32(_sum4, _r20, _k3456, 0);
_sum3 = vfmaq_laneq_f32(_sum3, _r21, _k3456, 1);
@@ -140,16 +138,10 @@ static void conv3x3s1_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
if (nn > 0)
{
asm volatile(
"veor q6, q6 \n"
"veor q15, q15 \n"

"pld [%3, #192] \n"
"vld1.f32 {d18-d20}, [%3 :64] \n"// r0
"add %3, #16 \n"

"veor q13, q13 \n"
"veor q14, q14 \n"

"vext.32 q11, q9, q10, #1 \n"
"vext.32 q12, q9, q10, #2 \n"

@@ -159,8 +151,8 @@ static void conv3x3s1_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
"vld1.f32 {d14-d15}, [%1 :64] \n"// _sum

"vmla.f32 q7, q9, %e14[0] \n"
"vmla.f32 q6, q11, %e14[1] \n"
"vmla.f32 q13, q12, %f14[0] \n"
"vmul.f32 q6, q11, %e14[1] \n"
"vmul.f32 q13, q12, %f14[0] \n"

"pld [%4, #192] \n"
"vld1.f32 {d18-d20}, [%4] \n"// r1
@@ -178,8 +170,8 @@ static void conv3x3s1_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
"vld1.f32 {d16-d17}, [%2] \n"// _sum2

"vmla.f32 q8, q9, %e14[0] \n"
"vmla.f32 q14, q11, %e14[1] \n"
"vmla.f32 q15, q12, %f14[0] \n"
"vmul.f32 q14, q11, %e14[1] \n"
"vmul.f32 q15, q12, %f14[0] \n"

"pld [%5, #192] \n"
"vld1.f32 {d18-d20}, [%5 :64] \n"// r2
@@ -210,17 +202,13 @@ static void conv3x3s1_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
"vmla.f32 q15, q12, %f16[0] \n"

"vadd.f32 q7, q7, q6 \n"
"veor q6, q6 \n"

"pld [%3, #192] \n"
"vld1.f32 {d18-d20}, [%3 :64] \n"// r0

"vadd.f32 q8, q8, q14 \n"
"veor q14, q14 \n"
"vadd.f32 q7, q7, q13 \n"
"veor q13, q13 \n"
"vadd.f32 q8, q8, q15 \n"
"veor q15, q15 \n"

"vext.32 q11, q9, q10, #1 \n"
"vext.32 q12, q9, q10, #2 \n"
@@ -346,7 +334,6 @@ static void conv3x3s1_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
for (; nn>0; nn--)
{
float32x4_t _sum1 = vld1q_f32(outptr);
float32x4_t _sum2 = vdupq_n_f32(0.f);

float32x4_t _r00 = vld1q_f32(r0);
float32x4_t _r00n = vld1q_f32(r0 + 4);
@@ -364,7 +351,7 @@ static void conv3x3s1_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
float32x4_t _r22 = vextq_f32(_r20, _r20n, 2);

_sum1 = vfmaq_laneq_f32(_sum1, _r00, _k0123, 0);
_sum2 = vfmaq_laneq_f32(_sum2, _r01, _k0123, 1);
float32x4_t _sum2 = vmulq_laneq_f32(_r01, _k0123, 1);
_sum1 = vfmaq_laneq_f32(_sum1, _r02, _k0123, 2);
_sum2 = vfmaq_laneq_f32(_sum2, _r10, _k3456, 0);
_sum1 = vfmaq_laneq_f32(_sum1, _r11, _k3456, 1);
@@ -390,9 +377,6 @@ static void conv3x3s1_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
"vld1.f32 {d16-d18}, [%2] \n"// r0
"add %2, #16 \n"

"veor q13, q13 \n"
"veor q14, q14 \n"

"vext.32 q10, q8, q9, #1 \n"
"vext.32 q11, q8, q9, #2 \n"

@@ -402,8 +386,8 @@ static void conv3x3s1_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
"vld1.f32 {d14-d15}, [%1] \n"// _sum

"vmla.f32 q7, q8, %e10[0] \n"
"vmla.f32 q13, q10, %e10[1] \n"
"vmla.f32 q14, q11, %f10[0] \n"
"vmul.f32 q13, q10, %e10[1] \n"
"vmul.f32 q14, q11, %f10[0] \n"

"pld [%3, #192] \n"
"vld1.f32 {d16-d18}, [%3] \n"// r1
@@ -434,9 +418,7 @@ static void conv3x3s1_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
"add %2, #16 \n"

"vadd.f32 q7, q7, q13 \n"
"veor q13, q13 \n"
"vadd.f32 q7, q7, q14 \n"
"veor q14, q14 \n"

"vext.32 q10, q8, q9, #1 \n"
"vext.32 q11, q8, q9, #2 \n"
@@ -2364,21 +2346,18 @@ static void conv3x3s2_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
"pld [%2, #256] \n"
"vld2.f32 {d4-d7}, [%2]! \n"

"veor q10, q10 \n"
"veor q11, q11 \n"

"0: \n"
"pld [%1, #128] \n"
"vld1.f32 {d0-d1}, [%1] \n"

"vmla.f32 q0, q2, %e10[0] \n"
"vmla.f32 q10, q3, %e10[1] \n"
"vmul.f32 q10, q3, %e10[1] \n"

"pld [%2, #128] \n"
"vld2.f32 {d16-d17}, [%2] \n"
"vext.32 q1, q2, q8, #1 \n"

"vmla.f32 q11, q1, %f10[0] \n"
"vmul.f32 q11, q1, %f10[0] \n"

"pld [%3, #256] \n"
"vld2.f32 {d4-d7}, [%3]! \n"
@@ -2408,9 +2387,7 @@ static void conv3x3s2_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
"vld2.f32 {d4-d7}, [%2]! \n"

"vadd.f32 q0, q0, q10 \n"
"veor q10, q10 \n"
"vadd.f32 q0, q0, q11 \n"
"veor q11, q11 \n"

"subs %0, #1 \n"
"vst1.f32 {d0-d1}, [%1]! \n"


+ 15
- 16
src/layer/arm/convolution_5x5.h View File

@@ -645,19 +645,19 @@ static void conv5x5s1_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
"0: \n"

"vld1.f32 {d14-d15}, [%1] \n"// _sum = vld1q_f32(outptr+j);
"veor q13, q13 \n"// _sum2 = 0;
"veor q14, q14 \n"// _sum3 = 0;
// "veor q13, q13 \n"// _sum2 = 0;
// "veor q14, q14 \n"// _sum3 = 0;

"vext.32 q10, q8, q9, #1 \n"// _r01
"vext.32 q11, q8, q9, #2 \n"// _r02
"vext.32 q12, q8, q9, #3 \n"// _r03

"vmla.f32 q7, q8, %e14[0] \n"
"vmla.f32 q13, q10, %e14[1] \n"
"vmul.f32 q13, q10, %e14[1] \n"

"pld [%3, #256] \n"

"vmla.f32 q14, q11, %f14[0] \n"
"vmul.f32 q14, q11, %f14[0] \n"
"vmul.f32 q15, q12, %f14[1] \n"
"vmla.f32 q7, q9, %e15[0] \n"

@@ -1019,18 +1019,17 @@ static void conv5x5s2_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
if (nn > 0)
{
asm volatile(
"veor q15, q15 \n"// _sump3 = 0;
"pld [%1, #128] \n"
"veor q13, q13 \n"// _sump2 = 0;
"pld [%2, #256] \n"
"veor q14, q14 \n"// _sump3 = 0;
// "veor q15, q15 \n"// _sump3 = 0;
// "veor q13, q13 \n"// _sump2 = 0;
// "veor q14, q14 \n"// _sump3 = 0;

"pld [%2, #256] \n"
"vld2.f32 {d16-d19}, [%2]! \n"// q8 = 0 2 4 6 q9 = 1 3 5 7

"pld [%2, #256] \n"

"vld2.f32 {d20-d23}, [%2] \n"// q10 = 8 10 12 14 q11 = 9 11 13 15

"pld [%1, #128] \n"
"0: \n"

"vld1.f32 {d14-d15}, [%1] \n"// q7 = outptr
@@ -1040,12 +1039,12 @@ static void conv5x5s2_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
"vext.32 q10, q8, q10, #2 \n"// q10 = 4 6 8 10

"vmla.f32 q7, q8, %e14[0] \n"
"vmla.f32 q13, q9, %e14[1] \n"
"vmul.f32 q13, q9, %e14[1] \n"

"pld [%3, #256] \n"

"vmla.f32 q14, q12, %f14[0] \n"
"vmla.f32 q15, q11, %f14[1] \n"
"vmul.f32 q14, q12, %f14[0] \n"
"vmul.f32 q15, q11, %f14[1] \n"
"vmla.f32 q7, q10, %e15[0] \n"

"vld2.f32 {d16-d19}, [%3]! \n"
@@ -1123,8 +1122,8 @@ static void conv5x5s2_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke

"vadd.f32 q14, q14, q15 \n"
"vadd.f32 q7, q7, q13 \n"
"veor q15, q15 \n"// _sump3 = 0;
"veor q13, q13 \n"// _sump2 = 0;
// "veor q15, q15 \n"// _sump3 = 0;
// "veor q13, q13 \n"// _sump2 = 0;

"pld [%2, #256] \n"

@@ -1132,7 +1131,7 @@ static void conv5x5s2_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke

"vld2.f32 {d20-d23}, [%2] \n"// q10 = 8 10 12 14 q11 = 9 11 13 15

"veor q14, q14 \n"// _sump3 = 0;
// "veor q14, q14 \n"// _sump3 = 0;

"vst1.f32 {d14-d15}, [%1]! \n"



+ 10
- 10
src/layer/arm/convolution_7x7.h View File

@@ -241,9 +241,9 @@ static void conv7x7s1_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke

"pld [%1, #256] \n"
"vld1.f32 {d24-d25}, [%1] \n"// _sum
"veor q13, q13 \n"// _sum2 = 0;
"veor q14, q14 \n"// _sum3 = 0;
"veor q15, q15 \n"// _sum4 = 0;
// "veor q13, q13 \n"// _sum2 = 0;
// "veor q14, q14 \n"// _sum3 = 0;
// "veor q15, q15 \n"// _sum4 = 0;

"pld [%9, #256] \n"
"vld1.f32 {d8-d11}, [%9] \n"// q4 q5 = k0123 k4567
@@ -255,12 +255,12 @@ static void conv7x7s1_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke

"pld [%2, #256] \n"
"vld1.f32 {d4-d7}, [%2] \n"// q2 = 4 5 6 7 q3 = 8 9 10 11
"vmla.f32 q13, q2, d10[0] \n"
"vmul.f32 q13, q2, d10[0] \n"

"vext.32 q1, q0, q2, #1 \n"// q1 = 1 2 3 4
"vext.32 q10, q2, q3, #1 \n"// q10= 5 6 7 8
"vmla.f32 q14, q1, d8[1] \n"
"vmla.f32 q15, q10, d10[1] \n"
"vmul.f32 q14, q1, d8[1] \n"
"vmul.f32 q15, q10, d10[1] \n"

"vext.32 q8, q0, q2, #2 \n"// q8 = 2 3 4 5
"vext.32 q11, q2, q3, #2 \n"// q11= 6 7 8 9
@@ -788,8 +788,8 @@ static void conv7x7s2_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke

"pld [%1, #256] \n"
"vld1.f32 {d26-d27}, [%1] \n"// _sum
"veor q14, q14 \n"// _sum2 = 0;
"veor q15, q15 \n"// _sum3 = 0;
// "veor q14, q14 \n"// _sum2 = 0;
// "veor q15, q15 \n"// _sum3 = 0;

"pld [%9, #256] \n"
"vld1.f32 {d8-d11}, [%9] \n"// q4 q5 = k0123 k4567
@@ -798,12 +798,12 @@ static void conv7x7s2_neon(const Mat& bottom_blob, Mat& top_blob, const Mat& _ke
"pld [%2, #512] \n"
"vld2.f32 {d0-d3}, [%2]! \n"// q0 = 0 2 4 6 q1 = 1 3 5 7
"vmla.f32 q13, q0, d8[0] \n"
"vmla.f32 q14, q1, d8[1] \n"
"vmul.f32 q14, q1, d8[1] \n"

"vld2.f32 {d4-d7}, [%2] \n"// q2 = 8 10 12 14 q3 = 9 11 13 15
"vext.32 q8, q0, q2, #1 \n"// q8 = 2 4 6 8
"vext.32 q9, q1, q3, #1 \n"// q9 = 3 5 7 9
"vmla.f32 q15, q8, d9[0] \n"
"vmul.f32 q15, q8, d9[0] \n"
"vmla.f32 q13, q9, d9[1] \n"

"vext.32 q10, q0, q2, #2 \n"// q10= 4 6 8 10


Loading…
Cancel
Save