From 8e434d68f98c5701ff2fbc3f91b098fa2eca9de0 Mon Sep 17 00:00:00 2001 From: Teddy-Yangjiale <12411723@mail.sustech.edu.cn> Date: Tue, 12 May 2026 02:22:19 +0800 Subject: [PATCH] dnn: vectorize SigmoidFunctor using universal intrinsics (cherry picked from commit 4b1c861ab75c2913945d06a9a1f8b074cfe48f2f) --- .../cpu_kernels/activation_kernels.simd.hpp | 26 ++++++++++++++++--- 1 file changed, 22 insertions(+), 4 deletions(-) diff --git a/modules/dnn/src/layers/cpu_kernels/activation_kernels.simd.hpp b/modules/dnn/src/layers/cpu_kernels/activation_kernels.simd.hpp index 1f2185687f..a59fe1fb56 100644 --- a/modules/dnn/src/layers/cpu_kernels/activation_kernels.simd.hpp +++ b/modules/dnn/src/layers/cpu_kernels/activation_kernels.simd.hpp @@ -97,12 +97,30 @@ static void activationSigmoid(const void* input, void* output, size_t i = 0; #if (CV_SIMD || CV_SIMD_SCALABLE) const int vlanes = VTraits::vlanes(); - v_float32 one = vx_setall_f32(1.f), z = vx_setzero_f32(); + const size_t step2 = (size_t)vlanes * 2; + + v_float32 one = vx_setall_f32(1.f); + v_float32 min_val = vx_setall_f32(-80.f), max_val = vx_setall_f32(88.f); + + // Using identity: 1 / (1 + exp(-x)) == 1 - (1 / (1 + exp(x))). + // Clamping x to [-80.f, 88.f] prevents v_exp overflow and subnormal underflow. + for (; i + step2 <= len; i += step2) { + v_float32 x0 = vx_load(inp + i); + v_float32 x1 = vx_load(inp + i + vlanes); + + x0 = v_min(v_max(x0, min_val), max_val); + x1 = v_min(v_max(x1, min_val), max_val); + + v_float32 y0 = v_sub(one, v_div(one, v_add(one, v_exp(x0)))); + v_float32 y1 = v_sub(one, v_div(one, v_add(one, v_exp(x1)))); + + vx_store(out + i, y0); + vx_store(out + i + vlanes, y1); + } for (; i + vlanes <= len; i += vlanes) { v_float32 x = vx_load(inp + i); - v_float32 t = v_exp(v_sub(z, x)); - t = v_div(one, v_add(one, t)); - vx_store(out + i, t); + x = v_min(v_max(x, min_val), max_val); + vx_store(out + i, v_sub(one, v_div(one, v_add(one, v_exp(x))))); } #endif for (; i < len; i++) {