Optimized TFLM Reshape for kelvin - Add a TFLM patch which contains a Kelvin-specific kernel for reshape, which is implemented using an optimized memcpy. - Add the `opt` library, which at the moment simply contains the optimized memcpy routine. - Wrap up the `reshape_test` from TFLM into a buildable target. Change-Id: I77f54fdc635838e8d272e47a8ff8654e7f23373e
diff --git a/tests/tflm/BUILD b/tests/tflm/BUILD new file mode 100644 index 0000000..de9127f --- /dev/null +++ b/tests/tflm/BUILD
@@ -0,0 +1,18 @@ +load("//build_tools/bazel:kelvin.bzl", "kelvin_test") +package(default_visibility = ["//visibility:public"]) + +kelvin_test( + name = "reshape_test", + srcs = [ + "@tflite-micro//tensorflow/lite/micro/kernels:reshape_test.cc", + ], + deps = [ + "//crt:crt_header", + "@tflite-micro//tensorflow/lite/c:common", + "@tflite-micro//tensorflow/lite/kernels/internal:tensor", + "@tflite-micro//tensorflow/lite/micro/kernels:kernel_runner", + "@tflite-micro//tensorflow/lite/micro/testing:micro_test", + "@tflite-micro//tensorflow/lite/micro:micro_utils", + "@tflite-micro//tensorflow/lite/micro:test_helpers", + ], +)
diff --git a/tflm/opt/BUILD b/tflm/opt/BUILD new file mode 100644 index 0000000..abf99e6 --- /dev/null +++ b/tflm/opt/BUILD
@@ -0,0 +1,16 @@ +package(default_visibility = ["//visibility:public"]) + +cc_library( + name = "opt", + srcs = [ + "memcpy.cc", + ], + hdrs = [ + "opt.h", + ], + deps = [ + "//crt:crt_header", + ], + alwayslink = True, + target_compatible_with = ["@kelvin_sw//platforms/cpu:kelvin"], +)
diff --git a/tflm/opt/memcpy.cc b/tflm/opt/memcpy.cc new file mode 100644 index 0000000..24df6f3 --- /dev/null +++ b/tflm/opt/memcpy.cc
@@ -0,0 +1,29 @@ +// Copyright 2023 Google LLC +// Licensed under the Apache License, Version 2.0, see LICENSE for details. +// SPDX-License-Identifier: Apache-2.0 + +#include "crt/kelvin.h" + +namespace kelvin::opt { + +void *memcpy(void *dst, const void *src, size_t n) { + const uint8_t *s = reinterpret_cast<const uint8_t *>(src); + uint8_t *d = reinterpret_cast<uint8_t *>(dst); + int vl; + while (true) { + if (n <= 0) break; + getvl_b_x_m(vl, n); + n -= vl; + vld_b_lp_xx_m(v0, s, vl); + vst_b_lp_xx_m(v0, d, vl); + + if (n <= 0) break; + getvl_b_x_m(vl, n); + n -= vl; + vld_b_lp_xx_m(v4, s, vl); + vst_b_lp_xx_m(v4, d, vl); + } + return dst; +} + +} // namespace kelvin::opt
diff --git a/tflm/opt/opt.h b/tflm/opt/opt.h new file mode 100644 index 0000000..5574daf --- /dev/null +++ b/tflm/opt/opt.h
@@ -0,0 +1,12 @@ +// Copyright 2023 Google LLC +// Licensed under the Apache License, Version 2.0, see LICENSE for details. +// SPDX-License-Identifier: Apache-2.0 + +#ifndef OPT_OPT_H_ +#define OPT_OPT_H_ + +namespace kelvin::opt { +void *memcpy(void *dst, const void *src, size_t n); +} // namespace kelvin::opt + +#endif // OPT_OPT_H_