From b344d693855525c1755b660c0b5c456e183fae89 Mon Sep 17 00:00:00 2001 From: Lemonorn Date: Fri, 1 Sep 2023 06:36:54 +0000 Subject: [PATCH 01/36] lemon base --- .DS_Store | Bin 0 -> 8196 bytes core | 0 lemon/mobilenet.yml | 15 +++++++++++++++ 3 files changed, 15 insertions(+) create mode 100644 .DS_Store create mode 100644 core create mode 100644 lemon/mobilenet.yml diff --git a/.DS_Store b/.DS_Store new file mode 100644 index 0000000000000000000000000000000000000000..4b4042400355c9b52fbfa9e2ef16c69bd34f1e0f GIT binary patch literal 8196 zcmeHM&2AGh5FV#Vvq_*735i~i_QI`HZ9zpGkdm}H1X`$?mLB*?lO{APHrXiIkhURJ z?mPh;cm~VMJvu8ff*z%T$SaHx;BU&ON3zf^o9GV%0 zzvnel62TK2k^xWT(mkq^L!Gi4(KZhZ1BL;^fMLKeU>Nup7{Hm$ixqS3%eSUA3>XHk zBm;bZuu-|p2XZ2%*gDXND*$8?k3~Tr_W*&h1DOxxL`nh0nDX|(0w@cv7)-+P-sb9% z`9MyjlyG7aPAr(21veBXW(Up|>csL=n$|F27>F`p<5328_8Og2Q@y`?$931M<1J69 z0_w^yQP3k=&=4m;cIYkc{Vsa_vKz*-9||_BVcVGbn3^HXS0u2C(Jl07K)#M(cR~o= zLZ913KJ4@8By1u37{cbLNC#A=ZQ7!hKi29q5^U5sNx={9&AYHS+%`>ffi`JJYGMvY zSk}i(KAlGVf^8Z$iCH}Ah3DWalz5}CJWmbi9dm1_r(4c`M#hx7p_NOVg!C+obqc%N z)Qwwd`l8s7=3jzfgNyZQL@eg~soFQecm=-$Dp8g8(eBVL_$i3~3TADD{NTK*Bc$mG zJ;&Nrz-3gMGpTB)gb!`7gs)X<#0q{?%`~hiW6etR3}cscZNZYNofJ_JjcKe9TTs}^ zUFzYR8Mguq!J-*!pk+b~sy^&@gM9r~@48OkUtRsq5_8GaeA=?IR`z=Kb*1GED}K!% z^ozCLOa9kx&2QC%{=VnA(|)b~!f6hxi?=qtj$d;+&7J@|jV4rH9Xg$cH!OOCPNOfz zsmK?Wm9a9_#ih|`eQjgeUVpeTUbaV%)>oJ92lqF|QTyzC^kIDQ2@8V4 zf)kx?$iJuUXY^v+eP8KyT(83el%rE1&_ST}$kP{xC#gnyhW4N3mf&DJ;E8^wd&I*ngxN#TOOFajm>E9t z&4FDgp_jt=O^iRFu0FcpOVvz5OKhFGp4e_xy&Uvfu(^jYuEK*FdVbh;vC*oi6m&fN zB4N){P_sBghwyTbo+1Hv;SZ8gw@C1!jy(+{(}`nXPQF;;_y1D-_y0J!d2Sdm4EzTS zu;f-{s|ZIfPvWpo{H|@I9-;EW^(ImZ2pVx6hZNUw$mu@}(YK+>G5J7Fq{I`HzyBe? Nod4$h7om5ho8MYRW`_U( literal 0 HcmV?d00001 diff --git a/core b/core new file mode 100644 index 000000000..e69de29bb diff --git a/lemon/mobilenet.yml b/lemon/mobilenet.yml new file mode 100644 index 000000000..555ca32cc --- /dev/null +++ b/lemon/mobilenet.yml @@ -0,0 +1,15 @@ +models: + mobilenet_v1: + platform: tensorflow + model_file_path: https://cnbj1.fds.api.xiaomi.com/mace/miai-models/mobilenet-v1/mobilenet-v1-1.0.pb + model_sha256_checksum: 71b10f540ece33c49a7b51f5d4095fc9bd78ce46ebf0300487b2ee23d71294e6 + subgraphs: + - input_tensors: + - input + input_shapes: + - 1,224,224,3 + output_tensors: + - MobilenetV1/Predictions/Reshape_1 + output_shapes: + - 1,1001 + runtime: gpu From beb2aa527e86d48851f336cd73a5b0701a806db9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?BIN=20LI18=20=E6=9D=8E=E6=BB=A8?= Date: Fri, 1 Sep 2023 17:48:46 +0800 Subject: [PATCH 02/36] Fix building hexagon_nn --- CMakeLists.txt | 1 + mace/flows/CMakeLists.txt | 3 +++ mace/runtimes/CMakeLists.txt | 3 +++ mace/runtimes/hexagon/CMakeLists.txt | 2 +- 4 files changed, 8 insertions(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index fe0f17c6e..e3487083b 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -102,6 +102,7 @@ if(MACE_ENABLE_RPCMEM) endif(MACE_ENABLE_RPCMEM) if(MACE_ENABLE_HEXAGON_DSP OR MACE_ENABLE_HEXAGON_HTA) + set(MACE_ENABLE_HEXAGON ON) if(ANDROID_ABI STREQUAL "arm64-v8a") # Use gold linker to avoid linking check of libcdsprpc.so set(MACE_LINKER_FLAGS "${MACE_LINKER_FLAGS} -fuse-ld=gold") diff --git a/mace/flows/CMakeLists.txt b/mace/flows/CMakeLists.txt index 066e377e7..176d37d43 100644 --- a/mace/flows/CMakeLists.txt +++ b/mace/flows/CMakeLists.txt @@ -23,4 +23,7 @@ target_link_libraries(flows PRIVATE core cpu_flow) if(MACE_ENABLE_OPENCL) target_link_libraries(flows PRIVATE opencl_flow) endif(MACE_ENABLE_OPENCL) +if(MACE_ENABLE_HEXAGON) + target_link_libraries(flows PRIVATE hexagon_flow) +endif(MACE_ENABLE_HEXAGON) install(TARGETS flows ARCHIVE DESTINATION lib) diff --git a/mace/runtimes/CMakeLists.txt b/mace/runtimes/CMakeLists.txt index aa420c7c6..cd5aea752 100644 --- a/mace/runtimes/CMakeLists.txt +++ b/mace/runtimes/CMakeLists.txt @@ -23,4 +23,7 @@ target_link_libraries(runtimes PRIVATE core cpu_runtime) if(MACE_ENABLE_OPENCL) target_link_libraries(runtimes PRIVATE opencl_runtime) endif(MACE_ENABLE_OPENCL) +if(MACE_ENABLE_HEXAGON) + target_link_libraries(runtimes PRIVATE hexagon_runtime) +endif(MACE_ENABLE_HEXAGON) install(TARGETS runtimes ARCHIVE DESTINATION lib) diff --git a/mace/runtimes/hexagon/CMakeLists.txt b/mace/runtimes/hexagon/CMakeLists.txt index 30d2bb00f..e8e976202 100644 --- a/mace/runtimes/hexagon/CMakeLists.txt +++ b/mace/runtimes/hexagon/CMakeLists.txt @@ -27,5 +27,5 @@ add_library(hexagon_runtime STATIC ${HEXAGON_SRCS}) if(MACE_ENABLE_OPENCL) add_dependencies(hexagon_runtime opencl_clhpp) endif(MACE_ENABLE_OPENCL) -target_link_libraries(hexagon_runtime core) +target_link_libraries(hexagon_runtime core hexagon_controller) install(TARGETS hexagon_runtime ARCHIVE DESTINATION lib) From d102645ac92cb5f773be0b378e4a7603039a8eb4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?BIN=20LI18=20=E6=9D=8E=E6=BB=A8?= Date: Tue, 12 Sep 2023 14:53:44 +0800 Subject: [PATCH 03/36] Add MACE_ENABLE_CPU to build scripts --- tools/cmake/cmake-build-aarch64-linux-gnu.sh | 1 + tools/cmake/cmake-build-arm-linux-gnueabihf.sh | 1 + tools/cmake/cmake-build-arm64-v8a.sh | 1 + tools/cmake/cmake-build-armeabi-v7a.sh | 1 + tools/cmake/cmake-build-host.sh | 1 + 5 files changed, 5 insertions(+) diff --git a/tools/cmake/cmake-build-aarch64-linux-gnu.sh b/tools/cmake/cmake-build-aarch64-linux-gnu.sh index a90bcf201..dbb1edda4 100755 --- a/tools/cmake/cmake-build-aarch64-linux-gnu.sh +++ b/tools/cmake/cmake-build-aarch64-linux-gnu.sh @@ -40,6 +40,7 @@ cmake -DCROSSTOOL_ROOT=${LINARO_AARCH64_LINUX_GNU} \ -DCMAKE_BUILD_TYPE=Release \ -DMACE_ENABLE_NEON=${MACE_ENABLE_NEON} \ -DMACE_ENABLE_QUANTIZE=${MACE_ENABLE_QUANTIZE} \ + -DMACE_ENABLE_CPU=${MACE_ENABLE_CPU} \ -DMACE_ENABLE_OPENCL=${MACE_ENABLE_OPENCL} \ -DMACE_ENABLE_BFLOAT16=${DMACE_ENABLE_BFLOAT16} \ -DMACE_ENABLE_OPT_SIZE=ON \ diff --git a/tools/cmake/cmake-build-arm-linux-gnueabihf.sh b/tools/cmake/cmake-build-arm-linux-gnueabihf.sh index 3275edbda..a37bd321f 100755 --- a/tools/cmake/cmake-build-arm-linux-gnueabihf.sh +++ b/tools/cmake/cmake-build-arm-linux-gnueabihf.sh @@ -40,6 +40,7 @@ cmake -DCROSSTOOL_ROOT=${LINARO_ARM_LINUX_GNUEABIHF} \ -DCMAKE_BUILD_TYPE=Release \ -DMACE_ENABLE_NEON=${MACE_ENABLE_NEON} \ -DMACE_ENABLE_QUANTIZE=${MACE_ENABLE_QUANTIZE} \ + -DMACE_ENABLE_CPU=${MACE_ENABLE_CPU} \ -DMACE_ENABLE_OPENCL=${MACE_ENABLE_OPENCL} \ -DMACE_ENABLE_BFLOAT16=${DMACE_ENABLE_BFLOAT16} \ -DMACE_ENABLE_OPT_SIZE=ON \ diff --git a/tools/cmake/cmake-build-arm64-v8a.sh b/tools/cmake/cmake-build-arm64-v8a.sh index f2b356c25..4391b0dc3 100755 --- a/tools/cmake/cmake-build-arm64-v8a.sh +++ b/tools/cmake/cmake-build-arm64-v8a.sh @@ -63,6 +63,7 @@ cmake -DANDROID_ABI="arm64-v8a" \ -DANDROID_STL=c++_shared \ -DMACE_ENABLE_NEON=${MACE_ENABLE_NEON} \ -DMACE_ENABLE_QUANTIZE=${MACE_ENABLE_QUANTIZE} \ + -DMACE_ENABLE_CPU=${MACE_ENABLE_CPU} \ -DMACE_ENABLE_OPENCL=${MACE_ENABLE_OPENCL} \ -DMACE_ENABLE_HEXAGON_DSP=${MACE_ENABLE_HEXAGON_DSP} \ -DMACE_ENABLE_HEXAGON_HTA=${MACE_ENABLE_HEXAGON_HTA} \ diff --git a/tools/cmake/cmake-build-armeabi-v7a.sh b/tools/cmake/cmake-build-armeabi-v7a.sh index 2a2f1f596..1b83654fe 100755 --- a/tools/cmake/cmake-build-armeabi-v7a.sh +++ b/tools/cmake/cmake-build-armeabi-v7a.sh @@ -55,6 +55,7 @@ cmake -DANDROID_ABI="armeabi-v7a" \ -DANDROID_STL=c++_shared \ -DMACE_ENABLE_NEON=${MACE_ENABLE_NEON} \ -DMACE_ENABLE_QUANTIZE=${MACE_ENABLE_QUANTIZE} \ + -DMACE_ENABLE_CPU=${MACE_ENABLE_CPU} \ -DMACE_ENABLE_OPENCL=${MACE_ENABLE_OPENCL} \ -DMACE_ENABLE_HEXAGON_DSP=${MACE_ENABLE_HEXAGON_DSP} \ -DMACE_ENABLE_HEXAGON_HTA=${MACE_ENABLE_HEXAGON_HTA} \ diff --git a/tools/cmake/cmake-build-host.sh b/tools/cmake/cmake-build-host.sh index 54165424a..99fda917e 100755 --- a/tools/cmake/cmake-build-host.sh +++ b/tools/cmake/cmake-build-host.sh @@ -22,6 +22,7 @@ fi mkdir -p ${BUILD_DIR} && cd ${BUILD_DIR} cmake -DMACE_ENABLE_NEON=OFF \ -DMACE_ENABLE_QUANTIZE=OFF \ + -DMACE_ENABLE_CPU=${MACE_ENABLE_CPU} \ -DMACE_ENABLE_OPENCL=OFF \ -DMACE_ENABLE_BFLOAT16=${DMACE_ENABLE_BFLOAT16} \ -DMACE_ENABLE_TESTS=ON \ From eb06ba65d2dd38ed7bb67be4f3b9d9587f457037 Mon Sep 17 00:00:00 2001 From: Lemonorn Date: Thu, 14 Sep 2023 10:11:33 +0000 Subject: [PATCH 04/36] compile success with qnx --- .bazelrc | 3 -- CMakeLists.txt | 2 + cmake/toolchains/aarch64-linux-gnu.cmake | 4 +- cmake/toolchains/qnx.cmake | 13 +++++ include/mace/port/env.h | 8 ++- mace/port/CMakeLists.txt | 4 ++ mace/port/qnx/CMakeLists.txt | 5 ++ mace/port/qnx/env.cc | 66 ++++++++++++++++++++++++ mace/port/qnx/env.h | 35 +++++++++++++ mace/tools/CMakeLists.txt | 4 +- mace/utils/CMakeLists.txt | 4 +- third_party/gflags/gflags.cmake | 2 +- third_party/third_party.cmake | 2 + tools/cmake/cmake-build-armeabi-v7a.sh | 2 +- tools/cmake/cmake-build-qnx.sh | 42 +++++++++++++++ tools/python/utils/device.py | 41 +++++++++++++++ 16 files changed, 224 insertions(+), 13 deletions(-) delete mode 100644 .bazelrc create mode 100644 cmake/toolchains/qnx.cmake create mode 100644 mace/port/qnx/CMakeLists.txt create mode 100644 mace/port/qnx/env.cc create mode 100644 mace/port/qnx/env.h create mode 100644 tools/cmake/cmake-build-qnx.sh diff --git a/.bazelrc b/.bazelrc deleted file mode 100644 index e56bae6ae..000000000 --- a/.bazelrc +++ /dev/null @@ -1,3 +0,0 @@ -# To support new bazelrc file list: -# https://github.com/bazelbuild/bazel/issues/4502 -import %workspace%/tools/bazel.rc diff --git a/CMakeLists.txt b/CMakeLists.txt index e3487083b..5fcbc694e 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,6 +1,8 @@ # new CUDA support requires 3.8 for Linux/Mac, and 3.9 for Windows cmake_minimum_required(VERSION 3.2 FATAL_ERROR) message("CMAKE_VERSION: ${CMAKE_VERSION}") +message("CROSSTOOL_ROOT: ${CROSSTOOL_ROOT}") +message("CMAKE_TOOLCHAIN_FILE: ${CMAKE_TOOLCHAIN_FILE}") project(mace C CXX) option(MACE_ENABLE_CPU "whether to enable CPU support" OFF) diff --git a/cmake/toolchains/aarch64-linux-gnu.cmake b/cmake/toolchains/aarch64-linux-gnu.cmake index aff7afab1..92c9ba63e 100644 --- a/cmake/toolchains/aarch64-linux-gnu.cmake +++ b/cmake/toolchains/aarch64-linux-gnu.cmake @@ -4,12 +4,12 @@ set(CMAKE_SYSTEM_NAME Linux) set(CMAKE_SYSTEM_PROCESSOR aarch64) -set(CMAKE_C_COMPILER "${CROSSTOOL_ROOT}/bin/aarch64-linux-gnu-gcc") +set( "${CROSSTOOL_ROOT}/bin/aarch64-linux-gnu-gcc") set(CMAKE_CXX_COMPILER "${CROSSTOOL_ROOT}/bin/aarch64-linux-gnu-g++") set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER) set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY) set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY) -set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY) +set(CMAKE_FIND_ROOCMAKE_C_COMPILERT_PATH_MODE_PACKAGE ONLY) set(CMAKE_CXX_FLAGS "-march=armv8-a ${CMAKE_CXX_FLAGS}") diff --git a/cmake/toolchains/qnx.cmake b/cmake/toolchains/qnx.cmake new file mode 100644 index 000000000..3701f3dcc --- /dev/null +++ b/cmake/toolchains/qnx.cmake @@ -0,0 +1,13 @@ +set(CMAKE_SYSTEM_NAME QNX) +set(CMAKE_SYSTEM_PROCESSOR aarch64) + +set(CMAKE_C_COMPILER "${CROSSTOOL_ROOT}/qnx700/host/linux/x86_64/usr/bin/ntoaarch64-gcc") +set(CMAKE_CXX_COMPILER "${CROSSTOOL_ROOT}/qnx700/host/linux/x86_64/usr/bin/ntoaarch64-g++") +set(CMAKE_FIND_ROOT_PATH "${CROSSTOOL_ROOT}/qnx700/target/qnx7") + +set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER) +set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY) +set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY) + +set(CMAKE_CXX_FLAGS "-D_XOPEN_SOURCE=500 -D_QNX_SOURCE ${CMAKE_CXX_FLAGS}") +set(MACE_CC_FLAGS "-D_XOPEN_SOURCE=500 -D_QNX_SOURCE ${MACE_CC_FLAGS}") \ No newline at end of file diff --git a/include/mace/port/env.h b/include/mace/port/env.h index c0b711b3d..12c6938f2 100644 --- a/include/mace/port/env.h +++ b/include/mace/port/env.h @@ -22,10 +22,14 @@ #include #include -#ifdef _WIN32 +#if defined(_WIN32) #include #endif +#if defined(__QNX__) +void *memalign(size_t __alignment, size_t __size); +#endif + #include #include "mace/public/mace.h" @@ -101,7 +105,7 @@ inline MaceStatus Memalign(void **memptr, size_t alignment, size_t size) { return MaceStatus::MACE_SUCCESS; } #else -#if defined(__ANDROID__) || defined(__hexagon__) +#if defined(__ANDROID__) || defined(__hexagon__) || defined(__QNX__) *memptr = memalign(alignment, size); if (*memptr == nullptr) { return MaceStatus::MACE_OUT_OF_RESOURCES; diff --git a/mace/port/CMakeLists.txt b/mace/port/CMakeLists.txt index 13523cb93..aa7972393 100644 --- a/mace/port/CMakeLists.txt +++ b/mace/port/CMakeLists.txt @@ -18,6 +18,10 @@ elseif(APPLE) elseif(WIN32) add_subdirectory(windows) add_library(port ALIAS port_windows) +elseif(QNX) + add_subdirectory(posix) + add_subdirectory(qnx) + add_library(port ALIAS port_qnx) else(WIN32) add_subdirectory(posix) add_subdirectory(linux_base) diff --git a/mace/port/qnx/CMakeLists.txt b/mace/port/qnx/CMakeLists.txt new file mode 100644 index 000000000..05377721d --- /dev/null +++ b/mace/port/qnx/CMakeLists.txt @@ -0,0 +1,5 @@ +add_library(port_qnx STATIC + env.cc +) + +target_link_libraries(port_qnx port_posix) \ No newline at end of file diff --git a/mace/port/qnx/env.cc b/mace/port/qnx/env.cc new file mode 100644 index 000000000..bfc25f3cd --- /dev/null +++ b/mace/port/qnx/env.cc @@ -0,0 +1,66 @@ +#include "mace/port/qnx/env.h" + +#include + +#include +#include +#include + +#include +#include +#include +#include + +#include "mace/port/env.h" +#include "mace/port/posix/file_system.h" +#include "mace/port/posix/time.h" +#include "mace/utils/logging.h" + +namespace mace { +namespace port { + +int64_t NowMicros() { + return mace::port::posix::NowMicros(); +} + +MaceStatus QnxEnv::AdviseFree(void *addr, size_t length) { + MACE_UNUSED(addr); + MACE_UNUSED(length); + return MaceStatus::MACE_SUCCESS; +} + +FileSystem *QnxEnv::GetFileSystem() { + return &posix_file_system_; +} + +MaceStatus QnxEnv::GetCPUMaxFreq(std::vector *max_freqs) { + MACE_UNUSED(max_freqs); + return MaceStatus::MACE_UNSUPPORTED; +} + +MaceStatus QnxEnv::SchedSetAffinity(const std::vector &cpu_ids) { + MACE_UNUSED(cpu_ids); + return MaceStatus::MACE_SUCCESS; +} + +LogWriter *QnxEnv::GetLogWriter() { + return &log_writer_; +} + +std::vector QnxEnv::GetBackTraceUnsafe(int max_steps) { + return std::vector(); +} + +std::unique_ptr QnxEnv::NewMallocLogger( + std::ostringstream *oss, + const std::string &name) { + return make_unique(); +} + +Env *Env::Default() { + static QnxEnv qnx_env; + return &qnx_env; +} + +} // namespace port +} // namespace mace \ No newline at end of file diff --git a/mace/port/qnx/env.h b/mace/port/qnx/env.h new file mode 100644 index 000000000..52c96513f --- /dev/null +++ b/mace/port/qnx/env.h @@ -0,0 +1,35 @@ +#ifndef MACE_PORT_QNX_ENV_H_ +#define MACE_PORT_QNX_ENV_H_ + +#include + +#include "mace/port/env.h" +#include "mace/port/posix/file_system.h" +#include "mace/port/logger.h" + +namespace mace { +namespace port { + +class QnxEnv : public Env { +public: + int64_t NowMicros() override; + MaceStatus AdviseFree(void *addr, size_t length) override; + MaceStatus GetCPUMaxFreq(std::vector *max_freqs) override; + FileSystem *GetFileSystem() override; + MaceStatus SchedSetAffinity(const std::vector &cpu_ids) override; + LogWriter *GetLogWriter() override; + std::vector GetBackTraceUnsafe(int max_steps) override; + std::unique_ptr NewMallocLogger( + std::ostringstream *oss, + const std::string &name) override; + +protected: + PosixFileSystem posix_file_system_; +private: + LogWriter log_writer_; +}; + +} // namespace port +} // namespace mace + +#endif // MACE_PORT_QNX_ENV_H_ \ No newline at end of file diff --git a/mace/tools/CMakeLists.txt b/mace/tools/CMakeLists.txt index a4ad8ccb7..b3ee7be95 100644 --- a/mace/tools/CMakeLists.txt +++ b/mace/tools/CMakeLists.txt @@ -8,8 +8,8 @@ target_link_libraries(mace_run extra_link_libs_target gflags ) -if(NOT ANDROID) - target_link_libraries(mace_run pthread) +if(NOT ANDROID AND NOT QNX) + target_link_libraries(mace_run) endif() if(MACE_ENABLE_HEXAGON_DSP) diff --git a/mace/utils/CMakeLists.txt b/mace/utils/CMakeLists.txt index 7d7b5c05b..d4c9fea3c 100644 --- a/mace/utils/CMakeLists.txt +++ b/mace/utils/CMakeLists.txt @@ -5,6 +5,6 @@ add_library(utils STATIC statistics.cc ) -if(NOT ANDROID AND NOT WIN32) +if(NOT ANDROID AND NOT WIN32 AND NOT QNX) target_link_libraries(utils PUBLIC pthread) -endif(NOT ANDROID AND NOT WIN32) +endif(NOT ANDROID AND NOT WIN32 AND NOT QNX) diff --git a/third_party/gflags/gflags.cmake b/third_party/gflags/gflags.cmake index 2a4f0343d..151697f45 100644 --- a/third_party/gflags/gflags.cmake +++ b/third_party/gflags/gflags.cmake @@ -28,7 +28,7 @@ ExternalProject_Add( -DCMAKE_C_COMPILER_LAUNCHER=${CMAKE_C_COMPILER_LAUNCHER} -DBUILD_STATIC_LIBS=ON -DBUILD_TESTING=OFF - -DCMAKE_BUILD_TYPE=Release + -DCMAKE_BUILD_TYPE=Release -DCMAKE_GENERATOR=${CMAKE_GENERATOR} ${THIRD_PARTY_EXTRA_CMAKE_ARGS} ) diff --git a/third_party/third_party.cmake b/third_party/third_party.cmake index 349aeb0f6..c08c849fc 100644 --- a/third_party/third_party.cmake +++ b/third_party/third_party.cmake @@ -2,6 +2,8 @@ set(MACE_THIRD_PARTY_DIR "${PROJECT_BINARY_DIR}/third_party" CACHE STRING "Third # Forwarding the cross compile flags set(THIRD_PARTY_EXTRA_CMAKE_ARGS + -DCMAKE_C_COMPILER=${CMAKE_C_COMPILER} + -DCMAKE_CXX_COMPILER=${CMAKE_CXX_COMPILER} -DCMAKE_C_FLAGS=${MACE_CC_FLAGS} -DCMAKE_CXX_FLAGS=${MACE_CC_FLAGS} ) diff --git a/tools/cmake/cmake-build-armeabi-v7a.sh b/tools/cmake/cmake-build-armeabi-v7a.sh index 1b83654fe..dd2ca311a 100755 --- a/tools/cmake/cmake-build-armeabi-v7a.sh +++ b/tools/cmake/cmake-build-armeabi-v7a.sh @@ -70,5 +70,5 @@ cmake -DANDROID_ABI="armeabi-v7a" \ -DMACE_ENABLE_RPCMEM=ON \ -DCMAKE_INSTALL_PREFIX=install \ ../../.. -make -j$(nproc)1 && make install +make -j$(nproc) && make install cd ../../.. diff --git a/tools/cmake/cmake-build-qnx.sh b/tools/cmake/cmake-build-qnx.sh new file mode 100644 index 000000000..cdc351003 --- /dev/null +++ b/tools/cmake/cmake-build-qnx.sh @@ -0,0 +1,42 @@ +set -e + +MACE_ROOT_DIR=$(pwd) + +# build for arm linux aarch64 +if [[ -z "$BUILD_DIR" ]]; then + BUILD_DIR=build/cmake-build/qnx +fi + +if [[ -z "$QNX_BIN_DIR" ]]; then + echo "please set \$QNX_BIN_DIR as your qnx toolchain root" + exit 1 +fi + +MACE_ENABLE_CPU=ON + +MACE_ENABLE_CODE_MODE=OFF +if [[ "$RUNMODE" == "code" ]]; then + MACE_ENABLE_CODE_MODE=ON +fi + +DMACE_ENABLE_BFLOAT16=OFF +if [[ "$BFLOAT16" == "ON" ]]; then + DMACE_ENABLE_BFLOAT16=ON +fi + +mkdir -p ${BUILD_DIR} && cd ${BUILD_DIR} +cmake -DQNX=True \ + -DCROSSTOOL_ROOT=/container/qxx \ + -DCMAKE_TOOLCHAIN_FILE=${MACE_ROOT_DIR}/cmake/toolchains/qnx.cmake \ + -DMACE_ENABLE_NEON=OFF \ + -DMACE_ENABLE_QUANTIZE=OFF \ + -DMACE_ENABLE_OPENCL=OFF \ + -DMACE_ENABLE_CPU=${MACE_ENABLE_CPU} \ + -DMACE_ENABLE_BFLOAT16=${DMACE_ENABLE_BFLOAT16} \ + -DMACE_ENABLE_TESTS=ON \ + -DMACE_ENABLE_BENCHMARKS=ON \ + -DMACE_ENABLE_CODE_MODE=${MACE_ENABLE_CODE_MODE} \ + -DCMAKE_INSTALL_PREFIX=install \ + ../../.. +make -j$(nproc) VERBOSE=1 && make install +cd ../../.. \ No newline at end of file diff --git a/tools/python/utils/device.py b/tools/python/utils/device.py index 8492e4565..4d23ba683 100644 --- a/tools/python/utils/device.py +++ b/tools/python/utils/device.py @@ -128,6 +128,46 @@ def pull(self, target, out_dir): def mkdir(self, dirname): execute("mkdir -p %s" % dirname) +class QnxDevice(Device): + def __init__(self, device_id, target_abi): + super(AndroidDevice, self).__init__(device_id, target_abi) + + @staticmethod + def list_devices(): + return ["qnx"] + + def install(self, target, install_dir, install_deps=False): + install_dir = os.path.abspath(install_dir) + + execute("lemon run mkdir -p %s" % (install_dir)) + if os.path.isdir(target.path): + for file in os.listdir(target.path): + execute("lemon send %s %s" % (file, install_dir), False) + else: + execute("lemon send %s %s" % (target.path, install_dir), False) + + for lib in target.libs: + execute("lemon send %s %s" % (lib, install_dir), False) + + device_target = copy.deepcopy(target) + device_target.path = "%s/%s" % (install_dir, + os.path.basename(target.path)) + device_target.libs = ["%s/%s" % (install_dir, os.path.basename(lib)) + for lib in target.libs] + device_target.envs.append("LD_LIBRARY_PATH=%s" % install_dir) + return device_target + + def run(self, target): + execute("lemon run %s", target) + + def pull(self, target, out_dir): + execute("lemon fetch %s %s" % (target, out_dir)) + + def mkdir(self, dirname): + execute("lemon run mkdir -p %s" % (dirname)) + + def info(self): + pass class AndroidDevice(Device): def __init__(self, device_id, target_abi): @@ -284,6 +324,7 @@ def mkdir(self, dirname): def device_class(target_abi): device_dispatch = { "host": "HostDevice", + "qnx": "QnxDevice", "armeabi-v7a": "AndroidDevice", "arm64-v8a": "AndroidDevice", "arm-linux-gnueabihf": "ArmLinuxDevice", From b0b714f5c593fd5d67097551b01923da52fe3930 Mon Sep 17 00:00:00 2001 From: Lemonorn Date: Thu, 14 Sep 2023 10:11:33 +0000 Subject: [PATCH 05/36] compile success with qnx --- .bazelrc | 3 -- CMakeLists.txt | 2 + cmake/toolchains/aarch64-linux-gnu.cmake | 4 +- cmake/toolchains/qnx.cmake | 13 +++++ core | 0 include/mace/port/env.h | 8 ++- lemon/mobilenet.yml | 15 ------ mace/libmace/CMakeLists.txt | 17 ++++-- mace/port/CMakeLists.txt | 4 ++ mace/port/qnx/CMakeLists.txt | 5 ++ mace/port/qnx/env.cc | 66 ++++++++++++++++++++++++ mace/port/qnx/env.h | 35 +++++++++++++ mace/tools/CMakeLists.txt | 4 +- mace/tools/mace_run.cc | 2 +- mace/utils/CMakeLists.txt | 4 +- test/ccbenchmark/CMakeLists.txt | 8 ++- third_party/gflags/gflags.cmake | 2 +- third_party/third_party.cmake | 2 + tools/cmake/cmake-build-armeabi-v7a.sh | 2 +- tools/cmake/cmake-build-host.sh | 3 +- tools/cmake/cmake-build-qnx.sh | 42 +++++++++++++++ tools/python/py_proto/__init__.py | 9 ++-- tools/python/utils/config_parser.py | 7 ++- tools/python/utils/device.py | 41 +++++++++++++++ 24 files changed, 257 insertions(+), 41 deletions(-) delete mode 100644 .bazelrc create mode 100644 cmake/toolchains/qnx.cmake delete mode 100644 core delete mode 100644 lemon/mobilenet.yml create mode 100644 mace/port/qnx/CMakeLists.txt create mode 100644 mace/port/qnx/env.cc create mode 100644 mace/port/qnx/env.h create mode 100644 tools/cmake/cmake-build-qnx.sh diff --git a/.bazelrc b/.bazelrc deleted file mode 100644 index e56bae6ae..000000000 --- a/.bazelrc +++ /dev/null @@ -1,3 +0,0 @@ -# To support new bazelrc file list: -# https://github.com/bazelbuild/bazel/issues/4502 -import %workspace%/tools/bazel.rc diff --git a/CMakeLists.txt b/CMakeLists.txt index e3487083b..5fcbc694e 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,6 +1,8 @@ # new CUDA support requires 3.8 for Linux/Mac, and 3.9 for Windows cmake_minimum_required(VERSION 3.2 FATAL_ERROR) message("CMAKE_VERSION: ${CMAKE_VERSION}") +message("CROSSTOOL_ROOT: ${CROSSTOOL_ROOT}") +message("CMAKE_TOOLCHAIN_FILE: ${CMAKE_TOOLCHAIN_FILE}") project(mace C CXX) option(MACE_ENABLE_CPU "whether to enable CPU support" OFF) diff --git a/cmake/toolchains/aarch64-linux-gnu.cmake b/cmake/toolchains/aarch64-linux-gnu.cmake index aff7afab1..92c9ba63e 100644 --- a/cmake/toolchains/aarch64-linux-gnu.cmake +++ b/cmake/toolchains/aarch64-linux-gnu.cmake @@ -4,12 +4,12 @@ set(CMAKE_SYSTEM_NAME Linux) set(CMAKE_SYSTEM_PROCESSOR aarch64) -set(CMAKE_C_COMPILER "${CROSSTOOL_ROOT}/bin/aarch64-linux-gnu-gcc") +set( "${CROSSTOOL_ROOT}/bin/aarch64-linux-gnu-gcc") set(CMAKE_CXX_COMPILER "${CROSSTOOL_ROOT}/bin/aarch64-linux-gnu-g++") set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER) set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY) set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY) -set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY) +set(CMAKE_FIND_ROOCMAKE_C_COMPILERT_PATH_MODE_PACKAGE ONLY) set(CMAKE_CXX_FLAGS "-march=armv8-a ${CMAKE_CXX_FLAGS}") diff --git a/cmake/toolchains/qnx.cmake b/cmake/toolchains/qnx.cmake new file mode 100644 index 000000000..3701f3dcc --- /dev/null +++ b/cmake/toolchains/qnx.cmake @@ -0,0 +1,13 @@ +set(CMAKE_SYSTEM_NAME QNX) +set(CMAKE_SYSTEM_PROCESSOR aarch64) + +set(CMAKE_C_COMPILER "${CROSSTOOL_ROOT}/qnx700/host/linux/x86_64/usr/bin/ntoaarch64-gcc") +set(CMAKE_CXX_COMPILER "${CROSSTOOL_ROOT}/qnx700/host/linux/x86_64/usr/bin/ntoaarch64-g++") +set(CMAKE_FIND_ROOT_PATH "${CROSSTOOL_ROOT}/qnx700/target/qnx7") + +set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER) +set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY) +set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY) + +set(CMAKE_CXX_FLAGS "-D_XOPEN_SOURCE=500 -D_QNX_SOURCE ${CMAKE_CXX_FLAGS}") +set(MACE_CC_FLAGS "-D_XOPEN_SOURCE=500 -D_QNX_SOURCE ${MACE_CC_FLAGS}") \ No newline at end of file diff --git a/core b/core deleted file mode 100644 index e69de29bb..000000000 diff --git a/include/mace/port/env.h b/include/mace/port/env.h index c0b711b3d..12c6938f2 100644 --- a/include/mace/port/env.h +++ b/include/mace/port/env.h @@ -22,10 +22,14 @@ #include #include -#ifdef _WIN32 +#if defined(_WIN32) #include #endif +#if defined(__QNX__) +void *memalign(size_t __alignment, size_t __size); +#endif + #include #include "mace/public/mace.h" @@ -101,7 +105,7 @@ inline MaceStatus Memalign(void **memptr, size_t alignment, size_t size) { return MaceStatus::MACE_SUCCESS; } #else -#if defined(__ANDROID__) || defined(__hexagon__) +#if defined(__ANDROID__) || defined(__hexagon__) || defined(__QNX__) *memptr = memalign(alignment, size); if (*memptr == nullptr) { return MaceStatus::MACE_OUT_OF_RESOURCES; diff --git a/lemon/mobilenet.yml b/lemon/mobilenet.yml deleted file mode 100644 index 555ca32cc..000000000 --- a/lemon/mobilenet.yml +++ /dev/null @@ -1,15 +0,0 @@ -models: - mobilenet_v1: - platform: tensorflow - model_file_path: https://cnbj1.fds.api.xiaomi.com/mace/miai-models/mobilenet-v1/mobilenet-v1-1.0.pb - model_sha256_checksum: 71b10f540ece33c49a7b51f5d4095fc9bd78ce46ebf0300487b2ee23d71294e6 - subgraphs: - - input_tensors: - - input - input_shapes: - - 1,224,224,3 - output_tensors: - - MobilenetV1/Predictions/Reshape_1 - output_shapes: - - 1,1001 - runtime: gpu diff --git a/mace/libmace/CMakeLists.txt b/mace/libmace/CMakeLists.txt index f3fd27413..d499d0200 100644 --- a/mace/libmace/CMakeLists.txt +++ b/mace/libmace/CMakeLists.txt @@ -28,20 +28,24 @@ target_link_libraries(mace_API ops flows runtimes) set(STATIC_LIB ${CMAKE_BINARY_DIR}/mace/libmace/libmace_static.a) set(BASE_PATH ${CMAKE_BINARY_DIR}) -set(PORT_LIBS "addlib ${CMAKE_BINARY_DIR}/mace/port/posix/libport_posix.a\n" - "addlib ${CMAKE_BINARY_DIR}/mace/port/linux_base/libport_linux_base.a\n") +set(PORT_LIBS "addlib ${CMAKE_BINARY_DIR}/mace/port/posix/libport_posix.a\n") if(ANDROID) set(PORT_LIBS ${PORT_LIBS} - "addlib ${CMAKE_BINARY_DIR}/mace/port/android/libport_android.a") + "addlib ${CMAKE_BINARY_DIR}/mace/port/android/libport_android.a\n" + "addlib ${CMAKE_BINARY_DIR}/mace/port/linux_base/libport_linux_base.a\n") if(MACE_ENABLE_RPCMEM) set(PORT_LIBS ${PORT_LIBS} "\naddlib ${PROJECT_SOURCE_DIR}/third_party/rpcmem/${ANDROID_ABI}/rpcmem.a") endif() +elseif(QNX) + set(PORT_LIBS ${PORT_LIBS} + "addlib ${CMAKE_BINARY_DIR}/mace/port/qnx/libport_qnx.a") elseif(WIN32) set(STATIC_LIB ${CMAKE_BINARY_DIR}/mace/libmace/libmace_static.lib) else(WIN32) set(PORT_LIBS ${PORT_LIBS} - "addlib ${CMAKE_BINARY_DIR}/mace/port/linux/libport_linux.a") + "addlib ${CMAKE_BINARY_DIR}/mace/port/linux/libport_linux.a\n" + "addlib ${CMAKE_BINARY_DIR}/mace/port/linux_base/libport_linux_base.a\n") endif(ANDROID) set(FLOW_LIBS "addlib ${CMAKE_BINARY_DIR}/mace/flows/libflows.a\n" @@ -109,6 +113,11 @@ elseif(ANDROID) COMMAND ${_CMAKE_TOOLCHAIN_PREFIX}ar -M < ${CMAKE_BINARY_DIR}/mace/libmace/mace.mri DEPENDS mace_API ops flows runtimes core utils proto generated_version generated_opencl_kernel libprotobuf_lite port_base port_posix port_linux_base port_android ) +elseif(QNX) + add_custom_target(combined ALL + COMMAND ${CROSSTOOL_ROOT}/qnx700/host/linux/x86_64/usr/bin/ntoaarch64-ar -M < ${CMAKE_BINARY_DIR}/mace/libmace/mace.mri + DEPENDS mace_API ops flows runtimes core utils proto generated_version generated_opencl_kernel libprotobuf_lite port_base port_posix port_qnx + ) else() #linux add_custom_target(combined ALL COMMAND ar -M < ${CMAKE_BINARY_DIR}/mace/libmace/mace.mri diff --git a/mace/port/CMakeLists.txt b/mace/port/CMakeLists.txt index 13523cb93..aa7972393 100644 --- a/mace/port/CMakeLists.txt +++ b/mace/port/CMakeLists.txt @@ -18,6 +18,10 @@ elseif(APPLE) elseif(WIN32) add_subdirectory(windows) add_library(port ALIAS port_windows) +elseif(QNX) + add_subdirectory(posix) + add_subdirectory(qnx) + add_library(port ALIAS port_qnx) else(WIN32) add_subdirectory(posix) add_subdirectory(linux_base) diff --git a/mace/port/qnx/CMakeLists.txt b/mace/port/qnx/CMakeLists.txt new file mode 100644 index 000000000..05377721d --- /dev/null +++ b/mace/port/qnx/CMakeLists.txt @@ -0,0 +1,5 @@ +add_library(port_qnx STATIC + env.cc +) + +target_link_libraries(port_qnx port_posix) \ No newline at end of file diff --git a/mace/port/qnx/env.cc b/mace/port/qnx/env.cc new file mode 100644 index 000000000..967adf5ca --- /dev/null +++ b/mace/port/qnx/env.cc @@ -0,0 +1,66 @@ +#include "mace/port/qnx/env.h" + +#include + +#include +#include +#include + +#include +#include +#include +#include + +#include "mace/port/env.h" +#include "mace/port/posix/file_system.h" +#include "mace/port/posix/time.h" +#include "mace/utils/logging.h" + +namespace mace { +namespace port { + +int64_t QnxEnv::NowMicros() { + return mace::port::posix::NowMicros(); +} + +MaceStatus QnxEnv::AdviseFree(void *addr, size_t length) { + MACE_UNUSED(addr); + MACE_UNUSED(length); + return MaceStatus::MACE_SUCCESS; +} + +FileSystem *QnxEnv::GetFileSystem() { + return &posix_file_system_; +} + +MaceStatus QnxEnv::GetCPUMaxFreq(std::vector *max_freqs) { + MACE_UNUSED(max_freqs); + return MaceStatus::MACE_UNSUPPORTED; +} + +MaceStatus QnxEnv::SchedSetAffinity(const std::vector &cpu_ids) { + MACE_UNUSED(cpu_ids); + return MaceStatus::MACE_SUCCESS; +} + +LogWriter *QnxEnv::GetLogWriter() { + return &log_writer_; +} + +std::vector QnxEnv::GetBackTraceUnsafe(int max_steps) { + return std::vector(); +} + +std::unique_ptr QnxEnv::NewMallocLogger( + std::ostringstream *oss, + const std::string &name) { + return make_unique(); +} + +Env *Env::Default() { + static QnxEnv qnx_env; + return &qnx_env; +} + +} // namespace port +} // namespace mace \ No newline at end of file diff --git a/mace/port/qnx/env.h b/mace/port/qnx/env.h new file mode 100644 index 000000000..622b8edcc --- /dev/null +++ b/mace/port/qnx/env.h @@ -0,0 +1,35 @@ +#ifndef MACE_PORT_QNX_ENV_H_ +#define MACE_PORT_QNX_ENV_H_ + +#include + +#include "mace/port/env.h" +#include "mace/port/posix/file_system.h" +#include "mace/port/logger.h" + +namespace mace { +namespace port { + +class QnxEnv : public Env { +public: + int64_t NowMicros() override; + MaceStatus AdviseFree(void *addr, size_t length) override; + MaceStatus GetCPUMaxFreq(std::vector *max_freqs) override; + MaceStatus SchedSetAffinity(const std::vector &cpu_ids) override; + FileSystem *GetFileSystem() override; + LogWriter *GetLogWriter() override; + std::vector GetBackTraceUnsafe(int max_steps) override; + std::unique_ptr NewMallocLogger( + std::ostringstream *oss, + const std::string &name) override; + +protected: + PosixFileSystem posix_file_system_; +private: + LogWriter log_writer_; +}; + +} // namespace port +} // namespace mace + +#endif // MACE_PORT_QNX_ENV_H_ \ No newline at end of file diff --git a/mace/tools/CMakeLists.txt b/mace/tools/CMakeLists.txt index a4ad8ccb7..b3ee7be95 100644 --- a/mace/tools/CMakeLists.txt +++ b/mace/tools/CMakeLists.txt @@ -8,8 +8,8 @@ target_link_libraries(mace_run extra_link_libs_target gflags ) -if(NOT ANDROID) - target_link_libraries(mace_run pthread) +if(NOT ANDROID AND NOT QNX) + target_link_libraries(mace_run) endif() if(MACE_ENABLE_HEXAGON_DSP) diff --git a/mace/tools/mace_run.cc b/mace/tools/mace_run.cc index 17930c5ed..b7fe5fa5a 100644 --- a/mace/tools/mace_run.cc +++ b/mace/tools/mace_run.cc @@ -199,7 +199,7 @@ std::shared_ptr ReadInputDataFromFile( in_file.read(buffer_in.get(), file_data_size); in_file.close(); } else { - LOG(FATAL) << "Open input file failed"; + LOG(FATAL) << "Open input file(" << file_path << ") failed"; return nullptr; } diff --git a/mace/utils/CMakeLists.txt b/mace/utils/CMakeLists.txt index 7d7b5c05b..d4c9fea3c 100644 --- a/mace/utils/CMakeLists.txt +++ b/mace/utils/CMakeLists.txt @@ -5,6 +5,6 @@ add_library(utils STATIC statistics.cc ) -if(NOT ANDROID AND NOT WIN32) +if(NOT ANDROID AND NOT WIN32 AND NOT QNX) target_link_libraries(utils PUBLIC pthread) -endif(NOT ANDROID AND NOT WIN32) +endif(NOT ANDROID AND NOT WIN32 AND NOT QNX) diff --git a/test/ccbenchmark/CMakeLists.txt b/test/ccbenchmark/CMakeLists.txt index 39c267ac3..89d4ba9ab 100644 --- a/test/ccbenchmark/CMakeLists.txt +++ b/test/ccbenchmark/CMakeLists.txt @@ -1,7 +1,11 @@ include_directories("${CMAKE_CURRENT_SOURCE_DIR}") -if(NOT APPLE) - set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fopenmp") +if(QNX) + set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -lgomp -Wno-error=unknown-pragmas") +else() + if (NOT APPLE) + set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fopenmp") + endif() endif() file(GLOB MACE_BENCHMARK_TEST_SRCS diff --git a/third_party/gflags/gflags.cmake b/third_party/gflags/gflags.cmake index 2a4f0343d..151697f45 100644 --- a/third_party/gflags/gflags.cmake +++ b/third_party/gflags/gflags.cmake @@ -28,7 +28,7 @@ ExternalProject_Add( -DCMAKE_C_COMPILER_LAUNCHER=${CMAKE_C_COMPILER_LAUNCHER} -DBUILD_STATIC_LIBS=ON -DBUILD_TESTING=OFF - -DCMAKE_BUILD_TYPE=Release + -DCMAKE_BUILD_TYPE=Release -DCMAKE_GENERATOR=${CMAKE_GENERATOR} ${THIRD_PARTY_EXTRA_CMAKE_ARGS} ) diff --git a/third_party/third_party.cmake b/third_party/third_party.cmake index 349aeb0f6..c08c849fc 100644 --- a/third_party/third_party.cmake +++ b/third_party/third_party.cmake @@ -2,6 +2,8 @@ set(MACE_THIRD_PARTY_DIR "${PROJECT_BINARY_DIR}/third_party" CACHE STRING "Third # Forwarding the cross compile flags set(THIRD_PARTY_EXTRA_CMAKE_ARGS + -DCMAKE_C_COMPILER=${CMAKE_C_COMPILER} + -DCMAKE_CXX_COMPILER=${CMAKE_CXX_COMPILER} -DCMAKE_C_FLAGS=${MACE_CC_FLAGS} -DCMAKE_CXX_FLAGS=${MACE_CC_FLAGS} ) diff --git a/tools/cmake/cmake-build-armeabi-v7a.sh b/tools/cmake/cmake-build-armeabi-v7a.sh index 1b83654fe..dd2ca311a 100755 --- a/tools/cmake/cmake-build-armeabi-v7a.sh +++ b/tools/cmake/cmake-build-armeabi-v7a.sh @@ -70,5 +70,5 @@ cmake -DANDROID_ABI="armeabi-v7a" \ -DMACE_ENABLE_RPCMEM=ON \ -DCMAKE_INSTALL_PREFIX=install \ ../../.. -make -j$(nproc)1 && make install +make -j$(nproc) && make install cd ../../.. diff --git a/tools/cmake/cmake-build-host.sh b/tools/cmake/cmake-build-host.sh index 99fda917e..940296902 100755 --- a/tools/cmake/cmake-build-host.sh +++ b/tools/cmake/cmake-build-host.sh @@ -29,6 +29,7 @@ cmake -DMACE_ENABLE_NEON=OFF \ -DMACE_ENABLE_BENCHMARKS=ON \ -DMACE_ENABLE_CODE_MODE=${MACE_ENABLE_CODE_MODE} \ -DCMAKE_INSTALL_PREFIX=install \ + -DCMAKE_BUILD_TYPE=Debug \ ../../.. -make -j$(nproc) && make install +make -j$(nproc) VERBOSE=1 -B && make install cd ../../.. diff --git a/tools/cmake/cmake-build-qnx.sh b/tools/cmake/cmake-build-qnx.sh new file mode 100644 index 000000000..fb4e8e975 --- /dev/null +++ b/tools/cmake/cmake-build-qnx.sh @@ -0,0 +1,42 @@ +set -e + +MACE_ROOT_DIR=$(pwd) + +# build for arm linux aarch64 +if [[ -z "$BUILD_DIR" ]]; then + BUILD_DIR=build/cmake-build/qnx +fi + +if [[ -z "$QNX_BIN_DIR" ]]; then + echo "please set \$QNX_BIN_DIR as your qnx toolchain root" + exit 1 +fi + +MACE_ENABLE_CPU=ON + +MACE_ENABLE_CODE_MODE=OFF +if [[ "$RUNMODE" == "code" ]]; then + MACE_ENABLE_CODE_MODE=ON +fi + +DMACE_ENABLE_BFLOAT16=OFF +if [[ "$BFLOAT16" == "ON" ]]; then + DMACE_ENABLE_BFLOAT16=ON +fi + +mkdir -p ${BUILD_DIR} && cd ${BUILD_DIR} +cmake -DQNX=True \ + -DCROSSTOOL_ROOT=${QNX_BIN_DIR} \ + -DCMAKE_TOOLCHAIN_FILE=${MACE_ROOT_DIR}/cmake/toolchains/qnx.cmake \ + -DMACE_ENABLE_NEON=OFF \ + -DMACE_ENABLE_QUANTIZE=OFF \ + -DMACE_ENABLE_OPENCL=OFF \ + -DMACE_ENABLE_CPU=${MACE_ENABLE_CPU} \ + -DMACE_ENABLE_BFLOAT16=${DMACE_ENABLE_BFLOAT16} \ + -DMACE_ENABLE_TESTS=ON \ + -DMACE_ENABLE_BENCHMARKS=ON \ + -DMACE_ENABLE_CODE_MODE=${MACE_ENABLE_CODE_MODE} \ + -DCMAKE_INSTALL_PREFIX=install \ + ../../.. +make -j$(nproc) VERBOSE=1 && make install +cd ../../.. \ No newline at end of file diff --git a/tools/python/py_proto/__init__.py b/tools/python/py_proto/__init__.py index fb090e23f..4745e68fc 100644 --- a/tools/python/py_proto/__init__.py +++ b/tools/python/py_proto/__init__.py @@ -23,6 +23,10 @@ cwd = os.path.dirname(__file__) try: + # cmake is much more faster than bazel, so try it first + device.execute("bash tools/cmake/cmake-generate-proto-py-host.sh") +except: + MaceLogger.warning("Cmake error, use bazel.") device.execute("bazel build //mace/proto:mace_py") device.execute("cp -f bazel-genfiles/mace/proto/mace_pb2.py %s" % cwd) @@ -32,7 +36,4 @@ device.execute("bazel build //third_party/caffe:caffe_py") device.execute( - "cp -f bazel-genfiles/third_party/caffe/caffe_pb2.py %s" % cwd) -except: # noqa - MaceLogger.warning("No bazel, use cmake.") - device.execute("bash tools/cmake/cmake-generate-proto-py-host.sh") + "cp -f bazel-genfiles/third_party/caffe/caffe_pb2.py %s" % cwd) \ No newline at end of file diff --git a/tools/python/utils/config_parser.py b/tools/python/utils/config_parser.py index 0368bb2c3..808762a23 100644 --- a/tools/python/utils/config_parser.py +++ b/tools/python/utils/config_parser.py @@ -56,7 +56,12 @@ def sanitize_load(s): # sub ${} to env value s = re.sub(r"\${(\w+)}", lambda x: os.environ[x.group(1)], s) - return yaml.load(s) + ret = None + try: + ret = yaml.load(s) + except: + ret = yaml.full_load(s) + return ret def parse(path): diff --git a/tools/python/utils/device.py b/tools/python/utils/device.py index 8492e4565..4d23ba683 100644 --- a/tools/python/utils/device.py +++ b/tools/python/utils/device.py @@ -128,6 +128,46 @@ def pull(self, target, out_dir): def mkdir(self, dirname): execute("mkdir -p %s" % dirname) +class QnxDevice(Device): + def __init__(self, device_id, target_abi): + super(AndroidDevice, self).__init__(device_id, target_abi) + + @staticmethod + def list_devices(): + return ["qnx"] + + def install(self, target, install_dir, install_deps=False): + install_dir = os.path.abspath(install_dir) + + execute("lemon run mkdir -p %s" % (install_dir)) + if os.path.isdir(target.path): + for file in os.listdir(target.path): + execute("lemon send %s %s" % (file, install_dir), False) + else: + execute("lemon send %s %s" % (target.path, install_dir), False) + + for lib in target.libs: + execute("lemon send %s %s" % (lib, install_dir), False) + + device_target = copy.deepcopy(target) + device_target.path = "%s/%s" % (install_dir, + os.path.basename(target.path)) + device_target.libs = ["%s/%s" % (install_dir, os.path.basename(lib)) + for lib in target.libs] + device_target.envs.append("LD_LIBRARY_PATH=%s" % install_dir) + return device_target + + def run(self, target): + execute("lemon run %s", target) + + def pull(self, target, out_dir): + execute("lemon fetch %s %s" % (target, out_dir)) + + def mkdir(self, dirname): + execute("lemon run mkdir -p %s" % (dirname)) + + def info(self): + pass class AndroidDevice(Device): def __init__(self, device_id, target_abi): @@ -284,6 +324,7 @@ def mkdir(self, dirname): def device_class(target_abi): device_dispatch = { "host": "HostDevice", + "qnx": "QnxDevice", "armeabi-v7a": "AndroidDevice", "arm64-v8a": "AndroidDevice", "arm-linux-gnueabihf": "ArmLinuxDevice", From 0b5874c4133110bfbfef65a967190d8242ca4230 Mon Sep 17 00:00:00 2001 From: linepi <2428513224@qq.com> Date: Fri, 22 Sep 2023 12:13:47 +0800 Subject: [PATCH 06/36] success in compiling qnx dsp --- CMakeLists.txt | 15 +- cmake/toolchains/qnx.cmake | 2 +- mace/libmace/CMakeLists.txt | 7 +- mace/port/qnx/env.cc | 2 - mace/rpcmems/CMakeLists.txt | 2 +- mace/rpcmems/qualcomm/qualcomm_rpcmem.cc | 13 +- mace/rpcmems/qualcomm/qualcomm_rpcmem.h | 4 + .../hexagon/dsp/hexagon_dsp_wrapper.cc | 2 + mace/tools/CMakeLists.txt | 5 + mace/tools/dbg.h | 1007 +++++++++++++++++ mace/tools/mace_run.cc | 7 +- third_party/googletest/googletest.cmake | 1 - third_party/nnlib/nnlib.cmake | 7 + .../nnlib/qnx/libhexagon_controller.so | Bin 0 -> 38680 bytes third_party/rpcmem/qnx/libfastrpc_pmem.so | Bin 0 -> 241856 bytes third_party/rpcmem/qnx/rpcmem_qnx.h | 881 ++++++++++++++ third_party/rpcmem/rpcmem.cmake | 5 + tools/cmake/cmake-build-arm64-v8a.sh | 2 +- tools/cmake/cmake-build-host.sh | 4 +- tools/cmake/cmake-build-qnx.sh | 5 +- tools/python/run_model.py | 10 + tools/python/run_target.py | 2 + tools/python/utils/device.py | 19 +- 23 files changed, 1966 insertions(+), 36 deletions(-) create mode 100644 mace/tools/dbg.h create mode 100755 third_party/nnlib/qnx/libhexagon_controller.so create mode 100755 third_party/rpcmem/qnx/libfastrpc_pmem.so create mode 100644 third_party/rpcmem/qnx/rpcmem_qnx.h diff --git a/CMakeLists.txt b/CMakeLists.txt index f356de3f8..3f6f1288c 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -42,7 +42,10 @@ if(MACE_ENABLE_OPT_SIZE) if(APPLE) set(MACE_LINKER_FLAGS "${MACE_LINKER_FLAGS} -Wl,-dead_strip -Wl,-dead_strip_dylibs") else(APPLE) - set(MACE_LINKER_FLAGS "${MACE_LINKER_FLAGS} -Wl,--strip-all -Wl,--gc-sections") + set(MACE_LINKER_FLAGS "${MACE_LINKER_FLAGS} -Wl,--gc-sections") + if(NOT (CMAKE_BUILD_TYPE STREQUAL "Debug")) + set(MACE_LINKER_FLAGS "${MACE_LINKER_FLAGS} -Wl,--strip-all") + endif() set(MACE_CC_FLAGS "${MACE_CC_FLAGS} -ffunction-sections -fdata-sections") endif(APPLE) set(MACE_CC_FLAGS "${MACE_CC_FLAGS} -fvisibility=hidden -fvisibility-inlines-hidden") @@ -105,24 +108,20 @@ endif(MACE_ENABLE_RPCMEM) if(MACE_ENABLE_HEXAGON_DSP OR MACE_ENABLE_HEXAGON_HTA) set(MACE_ENABLE_HEXAGON ON) - if(ANDROID_ABI STREQUAL "arm64-v8a") + if(ANDROID_ABI STREQUAL "arm64-v8a" OR QNX) # Use gold linker to avoid linking check of libcdsprpc.so set(MACE_LINKER_FLAGS "${MACE_LINKER_FLAGS} -fuse-ld=gold") - endif(ANDROID_ABI STREQUAL "arm64-v8a") + endif() endif(MACE_ENABLE_HEXAGON_DSP OR MACE_ENABLE_HEXAGON_HTA) if(MACE_ENABLE_HEXAGON_DSP) if(NOT ANDROID AND NOT QNX) message(FATAL_ERROR "Hexagon DSP is only supported on Android and Qnx") endif() - # TODO => -DMACE_ENABLE_HEXAGON_DSP + add_definitions(-DMACE_ENABLE_RPCMEM) add_definitions(-DMACE_ENABLE_HEXAGON) endif(MACE_ENABLE_HEXAGON_DSP) -if(MACE_ENABLE_RPCMEM) - add_definitions(-DMACE_ENABLE_RPCMEM) -endif(MACE_ENABLE_RPCMEM) - if(MACE_ENABLE_HEXAGON_HTA) if(NOT ANDROID AND NOT QNX) message(FATAL_ERROR "Hexagon HTA is only supported on Android and Qnx") diff --git a/cmake/toolchains/qnx.cmake b/cmake/toolchains/qnx.cmake index 3701f3dcc..665aecb10 100644 --- a/cmake/toolchains/qnx.cmake +++ b/cmake/toolchains/qnx.cmake @@ -9,5 +9,5 @@ set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER) set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY) set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY) -set(CMAKE_CXX_FLAGS "-D_XOPEN_SOURCE=500 -D_QNX_SOURCE ${CMAKE_CXX_FLAGS}") +set(CMAKE_CXX_FLAGS "-D_XOPEN_SOURCE=500 -D_QNX_SOURCE ${CMAKE_CXX_FLAGS} -Wno-unused-variable") set(MACE_CC_FLAGS "-D_XOPEN_SOURCE=500 -D_QNX_SOURCE ${MACE_CC_FLAGS}") \ No newline at end of file diff --git a/mace/libmace/CMakeLists.txt b/mace/libmace/CMakeLists.txt index d499d0200..8621cd78d 100644 --- a/mace/libmace/CMakeLists.txt +++ b/mace/libmace/CMakeLists.txt @@ -38,8 +38,7 @@ if(ANDROID) "\naddlib ${PROJECT_SOURCE_DIR}/third_party/rpcmem/${ANDROID_ABI}/rpcmem.a") endif() elseif(QNX) - set(PORT_LIBS ${PORT_LIBS} - "addlib ${CMAKE_BINARY_DIR}/mace/port/qnx/libport_qnx.a") + set(PORT_LIBS ${PORT_LIBS} "addlib ${CMAKE_BINARY_DIR}/mace/port/qnx/libport_qnx.a") elseif(WIN32) set(STATIC_LIB ${CMAKE_BINARY_DIR}/mace/libmace/libmace_static.lib) else(WIN32) @@ -52,18 +51,21 @@ set(FLOW_LIBS "addlib ${CMAKE_BINARY_DIR}/mace/flows/libflows.a\n" "addlib ${CMAKE_BINARY_DIR}/mace/flows/cpu/libcpu_flow.a\n") set(RUNTIME_LIBS "addlib ${CMAKE_BINARY_DIR}/mace/runtimes/libruntimes.a\n" "addlib ${CMAKE_BINARY_DIR}/mace/runtimes/cpu/libcpu_runtime.a\n") + if(MACE_ENABLE_OPENCL) set(FLOW_LIBS ${FLOW_LIBS} "addlib ${CMAKE_BINARY_DIR}/mace/flows/opencl/libopencl_flow.a\n") set(RUNTIME_LIBS ${RUNTIME_LIBS} "addlib ${CMAKE_BINARY_DIR}/mace/runtimes/opencl/libopencl_runtime.a\n") endif(MACE_ENABLE_OPENCL) + if(MACE_ENABLE_HEXAGON) set(FLOW_LIBS ${FLOW_LIBS} "addlib ${CMAKE_BINARY_DIR}/mace/flows/hexagon/libhexagon_flow.a\n") set(RUNTIME_LIBS ${RUNTIME_LIBS} "addlib ${CMAKE_BINARY_DIR}/mace/runtimes/hexagon/libhexagon_runtime.a\n") endif(MACE_ENABLE_HEXAGON) + if(MACE_ENABLE_MTK_APU) set(FLOW_LIBS ${FLOW_LIBS} "addlib ${CMAKE_BINARY_DIR}/mace/flows/apu/libapu_flow.a\n") @@ -134,6 +136,7 @@ add_dependencies(mace_static combined) set_target_properties(mace_static PROPERTIES IMPORTED_LOCATION ${STATIC_LIB} ) + if(ANDROID) set_target_properties(mace_static PROPERTIES INTERFACE_LINK_LIBRARIES log diff --git a/mace/port/qnx/env.cc b/mace/port/qnx/env.cc index c69c7442b..1ffc34276 100644 --- a/mace/port/qnx/env.cc +++ b/mace/port/qnx/env.cc @@ -35,8 +35,6 @@ FileSystem *QnxEnv::GetFileSystem() { } MaceStatus QnxEnv::GetCPUMaxFreq(std::vector *max_freqs) { - int num_cpu = _syspage_ptr->num_cpu; - assert(num_cpu == 8); // small cores max_freqs->push_back(1785608000); max_freqs->push_back(1785608000); diff --git a/mace/rpcmems/CMakeLists.txt b/mace/rpcmems/CMakeLists.txt index 6a80145fe..60caaa4dc 100644 --- a/mace/rpcmems/CMakeLists.txt +++ b/mace/rpcmems/CMakeLists.txt @@ -6,7 +6,7 @@ set(RPCMEMS_SRCS if(ANDROID_ABI STREQUAL "arm64-v8a") set(RPCMEMS_SRCS ${RPCMEMS_SRCS} mtk/mtk_rpcmem.cc mtk/mtk_ion_wrapper.cc) -endif(ANDROID_ABI STREQUAL "arm64-v8a") +endif() add_library(rpcmems STATIC ${RPCMEMS_SRCS}) target_link_libraries(rpcmems PRIVATE rpcmem) diff --git a/mace/rpcmems/qualcomm/qualcomm_rpcmem.cc b/mace/rpcmems/qualcomm/qualcomm_rpcmem.cc index f6d5f0258..ad6a4908a 100644 --- a/mace/rpcmems/qualcomm/qualcomm_rpcmem.cc +++ b/mace/rpcmems/qualcomm/qualcomm_rpcmem.cc @@ -13,18 +13,29 @@ // limitations under the License. #include "mace/rpcmems/qualcomm/qualcomm_rpcmem.h" - +#include "third_party/rpcmem/qnx/rpcmem_qnx.h" #include "mace/utils/logging.h" +#ifdef __QNX__ +#define mace_rpcmem_init(...) rpcmem_init() +#define mace_rpcmem_deinit(...) rpcmem_deinit() +#define mace_rpcmem_alloc(a,b,c,d) rpcmem_alloc(b,c,d) +#define mace_rpcmem_free(a,b) rpcmem_free(b) +#define mace_rpcmem_to_fd(a,b) rpcmem_to_fd(b) +#define mace_rpcmem_sync_cache(...) 0 +#endif + namespace mace { QualcommRpcmem::QualcommRpcmem() { mace_rpcmem_init(&rm); +#ifndef __QNX__ if (rm.flag != 0) { LOG(WARNING) << "QualcommRpcmem, rpcmem_init failed!"; valid_detected_ = true; valid_ = false; } +#endif } QualcommRpcmem::~QualcommRpcmem() { diff --git a/mace/rpcmems/qualcomm/qualcomm_rpcmem.h b/mace/rpcmems/qualcomm/qualcomm_rpcmem.h index d3d1b6a32..088aff040 100644 --- a/mace/rpcmems/qualcomm/qualcomm_rpcmem.h +++ b/mace/rpcmems/qualcomm/qualcomm_rpcmem.h @@ -16,7 +16,9 @@ #define MACE_RPCMEMS_QUALCOMM_QUALCOMM_RPCMEM_H_ #include "mace/core/memory/rpcmem/rpcmem.h" +#ifndef __QNX__ #include "third_party/rpcmem/rpcmem.h" +#endif namespace mace { class QualcommRpcmem : public Rpcmem { @@ -32,8 +34,10 @@ class QualcommRpcmem : public Rpcmem { RpcmemType GetRpcmemType() override; +#ifndef __QNX__ private: rpcmem rm; +#endif }; } // namespace mace diff --git a/mace/runtimes/hexagon/dsp/hexagon_dsp_wrapper.cc b/mace/runtimes/hexagon/dsp/hexagon_dsp_wrapper.cc index f21832e64..751658447 100644 --- a/mace/runtimes/hexagon/dsp/hexagon_dsp_wrapper.cc +++ b/mace/runtimes/hexagon/dsp/hexagon_dsp_wrapper.cc @@ -368,10 +368,12 @@ void HexagonDSPWrapper::PrintGraph() { } void HexagonDSPWrapper::PrintMemStats() { +#ifndef __QNX__ HAP_mem_stats mem_stats; MACE_CHECK(hexagon_nn_get_mem_stats(&mem_stats) == 0); LOG(INFO) << "Hexagon memory: " << mem_stats.bytes_free << " bytes free, " << mem_stats.bytes_used << " bytes used."; +#endif } void HexagonDSPWrapper::SetDebugLevel(int level) { diff --git a/mace/tools/CMakeLists.txt b/mace/tools/CMakeLists.txt index b3ee7be95..68c63c422 100644 --- a/mace/tools/CMakeLists.txt +++ b/mace/tools/CMakeLists.txt @@ -13,6 +13,11 @@ if(NOT ANDROID AND NOT QNX) endif() if(MACE_ENABLE_HEXAGON_DSP) + if(QNX) + # target_link_libraries(mace_run $ENV{HEXAGON_SDK_ROOT}/libs/common/qnx/ship/qnx_Release_aarch64/libfastrpc_pmem.so) + # target_link_libraries(mace_run $ENV{HEXAGON_SDK_ROOT}/libs/common/remote/ship/qnx_Release_aarch64/libcdsprpc.so) + # target_link_libraries(mace_run $ENV{QNX_TARGET}/aarch64le/usr/lib/libc++.so) + endif() target_link_libraries(mace_run hexagon_controller) endif() diff --git a/mace/tools/dbg.h b/mace/tools/dbg.h new file mode 100644 index 000000000..c657fcd1a --- /dev/null +++ b/mace/tools/dbg.h @@ -0,0 +1,1007 @@ +/***************************************************************************** + + dbg(...) macro + +License (MIT): + + Copyright (c) 2019 David Peter + + Permission is hereby granted, free of charge, to any person obtaining a copy + of this software and associated documentation files (the "Software"), to + deal in the Software without restriction, including without limitation the + rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + sell copies of the Software, and to permit persons to whom the Software is + furnished to do so, subject to the following conditions: + + The above copyright notice and this permission notice shall be included in + all copies or substantial portions of the Software. + + THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + SOFTWARE. + +*****************************************************************************/ + +#ifndef DBG_MACRO_DBG_H +#define DBG_MACRO_DBG_H + +#if defined(__unix__) || (defined(__APPLE__) && defined(__MACH__)) +#define DBG_MACRO_UNIX +#elif defined(_MSC_VER) +#define DBG_MACRO_WINDOWS +#endif + +#ifndef DBG_MACRO_NO_WARNING +#pragma message("WARNING: the 'dbg.h' header is included in your code base") +#endif // DBG_MACRO_NO_WARNING + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#ifdef DBG_MACRO_UNIX +#include +#endif + +#if __cplusplus >= 201703L +#define DBG_MACRO_CXX_STANDARD 17 +#elif __cplusplus >= 201402L +#define DBG_MACRO_CXX_STANDARD 14 +#else +#define DBG_MACRO_CXX_STANDARD 11 +#endif + +#if DBG_MACRO_CXX_STANDARD >= 17 +#include +#include +#endif + +namespace dbg { + +inline bool isColorizedOutputEnabled() { +#if defined(DBG_MACRO_FORCE_COLOR) + return true; +#elif defined(DBG_MACRO_UNIX) + return isatty(fileno(stderr)); +#else + return true; +#endif +} + +struct time {}; + +namespace pretty_function { + +// Compiler-agnostic version of __PRETTY_FUNCTION__ and constants to +// extract the template argument in `type_name_impl` + +#if defined(__clang__) +#define DBG_MACRO_PRETTY_FUNCTION __PRETTY_FUNCTION__ +static constexpr size_t PREFIX_LENGTH = + sizeof("const char *dbg::type_name_impl() [T = ") - 1; +static constexpr size_t SUFFIX_LENGTH = sizeof("]") - 1; +#elif defined(__GNUC__) && !defined(__clang__) +#define DBG_MACRO_PRETTY_FUNCTION __PRETTY_FUNCTION__ +static constexpr size_t PREFIX_LENGTH = + sizeof("const char* dbg::type_name_impl() [with T = ") - 1; +static constexpr size_t SUFFIX_LENGTH = sizeof("]") - 1; +#elif defined(_MSC_VER) +#define DBG_MACRO_PRETTY_FUNCTION __FUNCSIG__ +static constexpr size_t PREFIX_LENGTH = + sizeof("const char *__cdecl dbg::type_name_impl<") - 1; +static constexpr size_t SUFFIX_LENGTH = sizeof(">(void)") - 1; +#else +#error "This compiler is currently not supported by dbg_macro." +#endif + +} // namespace pretty_function + +// Formatting helpers + +template +struct print_formatted { + static_assert(std::is_integral::value, + "Only integral types are supported."); + + print_formatted(T value, int numeric_base) + : inner(value), base(numeric_base) {} + + operator T() const { return inner; } + + const char* prefix() const { + switch (base) { + case 8: + return "0o"; + case 16: + return "0x"; + case 2: + return "0b"; + default: + return ""; + } + } + + T inner; + int base; +}; + +template +print_formatted hex(T value) { + return print_formatted{value, 16}; +} + +template +print_formatted oct(T value) { + return print_formatted{value, 8}; +} + +template +print_formatted bin(T value) { + return print_formatted{value, 2}; +} + +// Implementation of 'type_name()' + +template +const char* type_name_impl() { + return DBG_MACRO_PRETTY_FUNCTION; +} + +template +struct type_tag {}; + +template +typename std::enable_if<(std::rank::value == 0), std::string>::type +get_type_name(type_tag) { + namespace pf = pretty_function; + + std::string type = type_name_impl(); + return type.substr(pf::PREFIX_LENGTH, + type.size() - pf::PREFIX_LENGTH - pf::SUFFIX_LENGTH); +} + +template +std::string type_name() { + if (std::is_volatile::value) { + if (std::is_pointer::value) { + return type_name::type>() + " volatile"; + } else { + return "volatile " + type_name::type>(); + } + } + if (std::is_const::value) { + if (std::is_pointer::value) { + return type_name::type>() + " const"; + } else { + return "const " + type_name::type>(); + } + } + if (std::is_pointer::value) { + return type_name::type>() + "*"; + } + if (std::is_lvalue_reference::value) { + return type_name::type>() + "&"; + } + if (std::is_rvalue_reference::value) { + return type_name::type>() + "&&"; + } + return get_type_name(type_tag{}); +} + +// Prefer bitsize variant over standard integral types +#define DBG_MACRO_REGISTER_TYPE_ASSOC(t_std, t_bit) \ + inline constexpr const char* get_type_name(type_tag) { \ + return std::is_same::value ? #t_bit : #t_std; \ + } + +DBG_MACRO_REGISTER_TYPE_ASSOC(unsigned char, uint8_t) +DBG_MACRO_REGISTER_TYPE_ASSOC(unsigned short, uint16_t) +DBG_MACRO_REGISTER_TYPE_ASSOC(unsigned int, uint32_t) +DBG_MACRO_REGISTER_TYPE_ASSOC(unsigned long, uint64_t) +DBG_MACRO_REGISTER_TYPE_ASSOC(signed char, int8_t) +DBG_MACRO_REGISTER_TYPE_ASSOC(short, int16_t) +DBG_MACRO_REGISTER_TYPE_ASSOC(int, int32_t) +DBG_MACRO_REGISTER_TYPE_ASSOC(long, int64_t) + +inline std::string get_type_name(type_tag) { + return "std::string"; +} + +template +typename std::enable_if<(std::rank::value == 1), std::string>::type +get_array_dim() { + return "[" + std::to_string(std::extent::value) + "]"; +} + +template +typename std::enable_if<(std::rank::value > 1), std::string>::type +get_array_dim() { + return "[" + std::to_string(std::extent::value) + "]" + + get_array_dim::type>(); +} + +template +typename std::enable_if<(std::rank::value > 0), std::string>::type +get_type_name(type_tag) { + return type_name::type>() + get_array_dim(); +} + +template +std::string get_type_name(type_tag>) { + return "std::array<" + type_name() + ", " + std::to_string(N) + ">"; +} + +template +std::string get_type_name(type_tag>>) { + return "std::vector<" + type_name() + ">"; +} + +template +std::string get_type_name(type_tag>) { + return "std::pair<" + type_name() + ", " + type_name() + ">"; +} + +template +std::string type_list_to_string() { + std::string result; + auto unused = {(result += type_name() + ", ", 0)..., 0}; + static_cast(unused); + +#if DBG_MACRO_CXX_STANDARD >= 17 + if constexpr (sizeof...(T) > 0) { +#else + if (sizeof...(T) > 0) { +#endif + result.pop_back(); + result.pop_back(); + } + return result; +} + +template +std::string get_type_name(type_tag>) { + return "std::tuple<" + type_list_to_string() + ">"; +} + +template +inline std::string get_type_name(type_tag>) { + return type_name(); +} + +// Implementation of 'is_detected' to specialize for container-like types + +namespace detail_detector { + +struct nonesuch { + nonesuch() = delete; + ~nonesuch() = delete; + nonesuch(nonesuch const&) = delete; + void operator=(nonesuch const&) = delete; +}; + +template +using void_t = void; + +template + class Op, + class... Args> +struct detector { + using value_t = std::false_type; + using type = Default; +}; + +template class Op, class... Args> +struct detector>, Op, Args...> { + using value_t = std::true_type; + using type = Op; +}; + +} // namespace detail_detector + +template