Extract memcpy wrapper used by Copy operator into a microkernel
PiperOrigin-RevId: 344180743
diff --git a/BUILD.bazel b/BUILD.bazel
index 845637b..5b4802b 100644
--- a/BUILD.bazel
+++ b/BUILD.bazel
@@ -518,6 +518,7 @@
"src/x32-zip/x3-scalar.c",
"src/x32-zip/x4-scalar.c",
"src/x32-zip/xm-scalar.c",
+ "src/xx-copy/memcpy.c",
]
WASM_UKERNELS = [
diff --git a/CMakeLists.txt b/CMakeLists.txt
index 201d6b4..205b4ad 100755
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -639,7 +639,8 @@
src/x32-zip/x2-scalar.c
src/x32-zip/x3-scalar.c
src/x32-zip/x4-scalar.c
- src/x32-zip/xm-scalar.c)
+ src/x32-zip/xm-scalar.c
+ src/xx-copy/memcpy.c)
SET(XNNPACK_PSIMD_ACCMATH_MICROKERNEL_SRCS
src/qs8-requantization/fp32-psimd.c
diff --git a/src/init.c b/src/init.c
index 4d5fd02..e4757d4 100644
--- a/src/init.c
+++ b/src/init.c
@@ -92,6 +92,13 @@
}
#endif
+ /**************************** XX micro-kernels ****************************/
+ #ifndef XNN_NO_XX_OPERATORS
+ init_flags |= XNN_INIT_FLAG_XX;
+
+ xnn_params.xx.copy = (xnn_univector_ukernel_function) xnn_xx_copy_ukernel__memcpy;
+ #endif
+
if (cpuinfo_has_arm_neon()) {
/**************************** QS8 micro-kernels ****************************/
#ifndef XNN_NO_QS8_OPERATORS
@@ -734,6 +741,13 @@
#elif XNN_ARCH_ARM64
+ /**************************** XX micro-kernels ****************************/
+ #ifndef XNN_NO_XX_OPERATORS
+ init_flags |= XNN_INIT_FLAG_XX;
+
+ xnn_params.xx.copy = (xnn_univector_ukernel_function) xnn_xx_copy_ukernel__memcpy;
+ #endif
+
/**************************** QS8 micro-kernels ****************************/
#ifndef XNN_NO_QS8_OPERATORS
init_flags |= XNN_INIT_FLAG_QS8;
@@ -1367,6 +1381,13 @@
return;
}
+ /**************************** XX micro-kernels ****************************/
+ #ifndef XNN_NO_XX_OPERATORS
+ init_flags |= XNN_INIT_FLAG_XX;
+
+ xnn_params.xx.copy = (xnn_univector_ukernel_function) xnn_xx_copy_ukernel__memcpy;
+ #endif
+
/**************************** QS8 micro-kernels ****************************/
#ifndef XNN_NO_QS8_OPERATORS
init_flags |= XNN_INIT_FLAG_QS8;
@@ -2013,6 +2034,14 @@
#endif // XNN_NO_X32_OPERATORS
#elif XNN_ARCH_WASMSIMD
+
+ /**************************** XX micro-kernels ****************************/
+ #ifndef XNN_NO_XX_OPERATORS
+ init_flags |= XNN_INIT_FLAG_XX;
+
+ xnn_params.xx.copy = (xnn_univector_ukernel_function) xnn_xx_copy_ukernel__memcpy;
+ #endif
+
/**************************** QS8 micro-kernels ****************************/
#ifndef XNN_NO_QS8_OPERATORS
init_flags |= XNN_INIT_FLAG_QS8;
@@ -2523,6 +2552,14 @@
#endif // XNN_NO_X32_OPERATORS
#elif XNN_ARCH_WASM
+
+ /**************************** XX micro-kernels ****************************/
+ #ifndef XNN_NO_XX_OPERATORS
+ init_flags |= XNN_INIT_FLAG_XX;
+
+ xnn_params.xx.copy = (xnn_univector_ukernel_function) xnn_xx_copy_ukernel__memcpy;
+ #endif
+
/**************************** QU8 micro-kernels ****************************/
#ifndef XNN_NO_QU8_OPERATORS
init_flags |= XNN_INIT_FLAG_QU8;
diff --git a/src/operators/unary-elementwise-nc.c b/src/operators/unary-elementwise-nc.c
index 027e19e..472f4d6 100644
--- a/src/operators/unary-elementwise-nc.c
+++ b/src/operators/unary-elementwise-nc.c
@@ -263,10 +263,6 @@
ceiling_op_out);
}
-static void memcpy_ukernel(size_t size, const void* input, void* output, const void* params) {
- memcpy(output, input, size);
-}
-
enum xnn_status xnn_create_copy_nc_x32(
size_t channels,
size_t input_stride,
@@ -278,7 +274,7 @@
channels, input_stride, output_stride, flags,
NULL, 0,
xnn_operator_type_copy_nc_x32,
- memcpy_ukernel,
+ xnn_params.xx.copy,
copy_op_out);
}
diff --git a/src/xnnpack/params.h b/src/xnnpack/params.h
index 085a057..1cd5f53 100644
--- a/src/xnnpack/params.h
+++ b/src/xnnpack/params.h
@@ -1979,12 +1979,17 @@
#define XNN_INIT_FLAG_U8 0x00000080
// Indicates that X8 XNNPACK microkernels are available for use.
#define XNN_INIT_FLAG_X8 0x00000100
+// Indicates that XX XNNPACK microkernels are available for use.
+#define XNN_INIT_FLAG_XX 0x00000200
struct xnn_parameters {
// Bitwise combination of XNN_INIT_FLAG_* flags
uint32_t init_flags;
struct xnn_allocator allocator;
struct {
+ xnn_univector_ukernel_function copy;
+ } xx;
+ struct {
struct gemm_parameters gemm;
struct dwconv_parameters dwconv[XNN_MAX_QS8_DWCONV_UKERNELS];
struct gavgpool_parameters gavgpool;
diff --git a/src/xnnpack/vunary.h b/src/xnnpack/vunary.h
index c4cbeae..b4442e2 100644
--- a/src/xnnpack/vunary.h
+++ b/src/xnnpack/vunary.h
@@ -599,6 +599,15 @@
DECLARE_F32_RELU_UKERNEL_FUNCTION(xnn_f32_relu_ukernel__wasm32_shr_x2)
DECLARE_F32_RELU_UKERNEL_FUNCTION(xnn_f32_relu_ukernel__wasm32_shr_x4)
+#define DECLARE_XX_VUNARY_UKERNEL_FUNCTION(fn_name) \
+ XNN_INTERNAL void fn_name( \
+ size_t size, \
+ const void* input, \
+ void* output, \
+ const void* params);
+
+DECLARE_XX_VUNARY_UKERNEL_FUNCTION(xnn_xx_copy_ukernel__memcpy)
+
#ifdef __cplusplus
} // extern "C"
#endif
diff --git a/src/xx-copy/memcpy.c b/src/xx-copy/memcpy.c
new file mode 100644
index 0000000..d247f99
--- /dev/null
+++ b/src/xx-copy/memcpy.c
@@ -0,0 +1,17 @@
+// Copyright 2020 Google LLC
+//
+// This source code is licensed under the BSD-style license found in the
+// LICENSE file in the root directory of this source tree.
+
+#include <assert.h>
+#include <string.h>
+
+#include <xnnpack/common.h>
+#include <xnnpack/vunary.h>
+
+
+void xnn_xx_copy_ukernel__memcpy(size_t size, const void* input, void* output, const void* params) {
+ assert(size != 0);
+
+ memcpy(output, input, size);
+}