交叉编译NumCpp到ARM上的方法(以全志V853为例)
-
前段时间,在电脑上安装了Ubuntu/Windows系统双系统,现在拿Ubuntu系统试试水。
NumCpp是类似Numpy的C++版本,可以方便的进行一些矩阵的操作,现在我们来把它交叉编译到ARM上去。
1. 获取源码
要交叉编译NumCpp,首先要获取依赖库boost源代码以及NumCpp的源代码。
在这里我使用的是boost1.68,可以从下面这个网址下载。
https://www.boost.org/Boost C++ Libraries https://www.boost.org/
NumCpp可以从GitHub上clone下来
https://github.com/dpilger26/NumCppGitHub - dpilger26/NumCpp: C++ implementation of the Python Numpy library C++ implementation of the Python Numpy library. Contribute to dpilger26/NumCpp development by creating an account on GitHub. https://github.com/dpilger26/NumCpp
2. 交叉编译boost
将下载好的压缩包解压。
cd boost_1_68_0 ./bootstrap.sh --with-libraries=all --with-toolset=gcc
其中,--with-libraries可以选择自己想要安装的库。
执行完这一步之后,打开新生成的project-config.jam,修改下面这几行中的gcc部分。一定要注意空格!(每一个空格缺一不可),其中的arm-openwrt-linux-gcc的路径可以换成你的交叉编译器的路径
if ! gcc in [ feature.values <toolset> ] { using gcc : arm : /home/xinzhe/toolchains/rootfsbuilt/arm/toolchain-sunxi-musl-gcc-830/toolchain/bin/arm-openwrt-linux-gcc ; }
之后执行
./b2
检查输出的log中的编译器是否已经是交叉编译器,然后再执行
./b2 install --prefix=/home/xinzhe/Documents/boost_arm
其中--prefix后面是你想要的boost库安装路径。
安装完成后,检查安装的boost库是否为ARM版本。
3.交叉编译NumCpp
Clone完成NumCpp之后,进入NumCpp文件夹。
由于我之前编译过x86-64版本的NumCpp,因此在编译ARM版本的时候,需要修改CMakeLists.txt,让cmake找到ARM版本的boost库。
在CMakeLists.txt中寻找Boost有关代码的上方加入
set(CMAKE_FIND_ROOT_PATH /home/xinzhe/Documents/boost_arm) set(CMAKE_FIND_ROOT_PATH /home/xinzhe/Documents/boost_arm) if(NUMCPP_NO_USE_BOOST) target_compile_definitions(${ALL_INTERFACE_TARGET} INTERFACE -DNUMCPP_NO_USE_BOOST) else() find_package(Boost 1.68.0 REQUIRED COMPONENTS date_time ) target_link_libraries(${ALL_INTERFACE_TARGET} INTERFACE Boost::boost $<$<OR:$<CXX_COMPILER_ID:Clang>,$<CXX_COMPILER_ID:GNU>>:Boost::date_time> ) endif()
同时,在NumCpp文件夹里,创建一个Compile.cmake文件,来指定交叉编译器。内容如下:
set(CMAKE_SYSTEM_NAME Linux) set(TOOLCHAIN_PATH /home/xinzhe/toolchains/rootfsbuilt/arm/toolchain-sunxi-musl-gcc-830/toolchain/arm-openwrt-linux-muslgnueabi) set(CMAKE_C_COMPILER /home/xinzhe/toolchains/rootfsbuilt/arm/toolchain-sunxi-musl-gcc-830/toolchain/bin/arm-openwrt-linux-gcc) set(CMAKE_CXX_COMPILER /home/xinzhe/toolchains/rootfsbuilt/arm/toolchain-sunxi-musl-gcc-830/toolchain/bin/arm-openwrt-linux-g++)
其中的TOOLCHAIN_PATH、CMAKE_C_COMPILER、CMAKE_CXX_COMPILER替换成自己的交叉编译工具。
然后在NumCpp文件夹下执行下面的操作
mkdir build cd build cmake .. -DCMAKE_TOOLCHAIN_FILE=../Compile.cmake
然后检查输出的log中,C编译工具是否为交叉编译工具,以及找到的boost库是否为我们刚刚创建的ARM版本的。
检查完毕后,修改/NumCpp/build目录下的cmake_install.cmake,修改其中的CMAKE_INSTALL_PREFIX为自己想要安装的目录。
# Install script for directory: /home/xinzhe/Documents/NumCpp # Set the install prefix if(NOT DEFINED CMAKE_INSTALL_PREFIX) set(CMAKE_INSTALL_PREFIX "/home/xinzhe/Documents/boost_arm") endif() string(REGEX REPLACE "/$" "" CMAKE_INSTALL_PREFIX "${CMAKE_INSTALL_PREFIX}")
然后执行:
cmake --build . --target install
我们就在boost_arm下得到了ARM版本的boost和ARM版本的NumCpp的编译结果文件
4. 编译自己的代码
创建NumCpp_arm文件夹,放入自己的main.cpp,并创建Compile.cmake(同上),CMakeLists.txt。
其中CMakeLists.txt代码如下:
cmake_minimum_required(VERSION 3.20) project("HelloWorld" CXX) add_executable(${PROJECT_NAME} main.cpp) set(CMAKE_FIND_ROOT_PATH /home/xinzhe/Documents/boost_arm) set(CMAKE_CXX_STANDARD 17) set(CMAKE_CXX_FLAGS "-g -std=c++17 -lstdc++fs") find_package(NumCpp 2.10.1 REQUIRED) target_link_libraries(${PROJECT_NAME} NumCpp::NumCpp stdc++fs )
其中的CMAKE_CXX_FLAGS的设置,以及stdc++fs添加到target_link_libraries里,是为了防止一下的报错。
xinzhe@xinzhe-G3-3590:~/Documents/NumCpp/examples/NumCpp_arm/build$ make Consolidate compiler generated dependencies of target HelloWorld [ 50%] Linking CXX executable HelloWorld CMakeFiles/HelloWorld.dir/main.cpp.o: In function `std::filesystem::exists(std::filesystem::__cxx11::path const&)': main.cpp:(.text._ZNSt10filesystem6existsERKNS_7__cxx114pathE[_ZNSt10filesystem6existsERKNS_7__cxx114pathE]+0x1c): undefined reference to `std::filesystem::status(std::filesystem::__cxx11::path const&)' CMakeFiles/HelloWorld.dir/main.cpp.o: In function `std::filesystem::__cxx11::path::path<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >, std::filesystem::__cxx11::path>(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, std::filesystem::__cxx11::path::format)': main.cpp:(.text._ZNSt10filesystem7__cxx114pathC2INSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES1_EERKT_NS1_6formatE[_ZNSt10filesystem7__cxx114pathC5INSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES1_EERKT_NS1_6formatE]+0x60): undefined reference to `std::filesystem::__cxx11::path::_M_split_cmpts()' collect2: error: ld returned 1 exit status make[2]: *** [CMakeFiles/HelloWorld.dir/build.make:98: HelloWorld] Error 1 make[1]: *** [CMakeFiles/Makefile2:83: CMakeFiles/HelloWorld.dir/all] Error 2 make: *** [Makefile:91: all] Error 2
然后,我们执行一下操作
mkdir build cd build cmake .. -DCMAKE_TOOLCHAIN_FILE=../Compile.cmake
检查输出的log,交叉编译工具对不对,boost与NumCpp是否为ARM版本。
最后执行
make
下面的是我的编译结果,可以看到编译成功
xinzhe@xinzhe-G3-3590:~/Documents/NumCpp/examples/NumCpp_arm/build$ make [ 50%] Building CXX object CMakeFiles/HelloWorld.dir/main.cpp.o [100%] Linking CXX executable HelloWorld [100%] Built target HelloWorld
检查一下生成的可执行文件是够为ARM版本。
xinzhe@xinzhe-G3-3590:~/Documents/NumCpp/examples/NumCpp_arm/build$ file HelloWorld HelloWorld: ELF 32-bit LSB executable, ARM, EABI5 version 1 (SYSV), dynamically linked, interpreter /lib/ld-musl-armhf.so.1, with debug_info, not stripped
5.移植到V853上
将HelloWorld文件和boost_arm整个文件夹push到板子上
xinzhe@xinzhe-G3-3590:~/Documents/NumCpp/examples/NumCpp_arm/build$ adb push HelloWorld /root HelloWorld: 1 file pushed. 3.6 MB/s (2607428 bytes in 0.684s)
然后到HelloWorld所在目录下执行
root@TinaLinux:~# export LD_LIBRARY_PATH=/root/boost_arm/lib:$LD_LIBRARY_PATH
可以看到我的HelloWorld正常执行
root@TinaLinux:~# ./HelloWorld [[0.452916, 0.119087, -0.459488, -0.733428, 0.374606, 0.244954, -0.237323, -0.109258, 0.907443, -0.413274, -0.157849, 0.158918, 0.0474297, -0.519952, 1.38254, -0.174767, -0.911914, -0.812675, -0.506005, -0.222257, -0.192745, -1.04207, 0.424627, 0.217617, 0.277484, -0.0261248, -0.0865481, -0.371074, -0.275607, 0.937942,
到这里,交叉编译就完成啦,希望各位小伙伴也能顺利进行!
原文链接:https://blog.csdn.net/where_are_u/article/details/129863901
Copyright © 2024 深圳全志在线有限公司 粤ICP备2021084185号 粤公网安备44030502007680号