Cross-compile to Beagleboard-XM using CMake and Clang - c++

I am trying to make a cross-compilation toolchain script for my BeagleBoard XM, but it doesn't work : the basic c++ includes (<algorithm>, etc...) aren't found when compiling.
Here is my toolchain file, made by following these two tutorials:
http://clang.llvm.org/docs/CrossCompilation.html
http://www.cmake.org/Wiki/CMake_Cross_Compiling#The_toolchain_file
The file:
set(CMAKE_SYSTEM_NAME Linux)
set(CMAKE_SYSTEM_VERSION 1)
set(CMAKE_SYSTEM_PROCESSOR arm)
set(FLOAT_ABI_SUFFIX "")
set(CMAKE_C_COMPILER clang)
set(CMAKE_CXX_COMPILER clang++)
set(CMAKE_CXX_FLAGS "-target armv7a-unknown-eabi -mfloat-abi=hard -mcpu=cortex-a8 --sysroot=/mnt/beagle/")
# where is the target environment
SET(CMAKE_FIND_ROOT_PATH /mnt/beagle /mnt/beagle/usr)
# search for programs in the build host directories
SET(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER)
# for libraries and headers in the target directories
SET(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY)
SET(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY)
/mnt/beagle is a SD Card with a copy of the system in my BeagleBoard, with all the necessary development packages, etc. installed.
Both the host and the guest are under Debian Jessie.
As a side question, I also have the android SDK & NDK installed. Is it possible to use them as a cross-compile environment, since it's ARMv7, or does the android NDK bring significant changes ?

Related

Export as 32-bit with CMake & C++ won't work

I have been trying to make a program for Windows with C++ and Linux. I imported some libraries and wrote the code. Now this is the config for CMakeLists.txt
cmake_minimum_required(VERSION 3.10)
set(CMAKE_BUILD_TYPE Release)
set(CMAKE_C_COMPILER gcc)
set(CMAKE_C_FLAGS -m32)
set(CMAKE_CXX_COMPILER g++)
set(CMAKE_CXX_FLAGS "-std=c++14 -DCMAKE_BUILD_TYPE=release64 -m32")
set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER)
set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY)
set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY)
project(qpsm)
add_executable(
a.exe
main.cpp
)
add_executable(
a.run
main.cpp
)
I know it's not very efficent, but it does the job for Linux. When it compiles for Windows and I try to open it on a Windows Machine it gives me the error with the title Not supported 16 Bit-Application that a feature called "\??\C:\Users\kroyz\Downloads\a.exe" cannot be run due to a incompatibility with 64-Bit Versions.
I know I am very bad at trying to explain things and errors so let me know if I did something wrong
Regards,
Alex

Standard library issue when cross-compiling

I'm trying to cross compile to an ARM with linux from my x86 with a linux.
The issue appears to be that when including some standard library headers like iostream or string, even if those are included from the path where the cross compiler is, and its standard library, some of the dependencies of those headers seems to be included from my local standard library.
The headers from my local standard library have some x86 specific type definitions which do not exist on ARM hence the compilation fails.
The error shown is:
[01m[K/usr/include/bits/floatn.h:87:9:[m[K [01;31m[Kerror: [m[K?[01m[K__float128[m[K? does not name a type; did you mean ?[01m[K__cfloat128[m[K??
87 | typedef [01;31m[K__float128[m[K _Float128;
| [01;31m[K^~~~~~~~~~[m[K
| [32m[K__cfloat128[m[K
In file included from [01m[K/opt/fslc-wayland/3.1/sysroots/aarch64-fslc-linux/usr/include/c++/9.3.0/cwchar:44[m[K,
from [01m[K/opt/fslc-wayland/3.1/sysroots/aarch64-fslc-linux/usr/include/c++/9.3.0/bits/postypes.h:40[m[K,
from [01m[K/opt/fslc-wayland/3.1/sysroots/aarch64-fslc-linux/usr/include/c++/9.3.0/iosfwd:40[m[K,
from [01m[K/opt/fslc-wayland/3.1/sysroots/aarch64-fslc-linux/usr/include/c++/9.3.0/ios:38[m[K,
from [01m[K/opt/fslc-wayland/3.1/sysroots/aarch64-fslc-linux/usr/include/c++/9.3.0/ostream:38[m[K,
from [01m[K/opt/fslc-wayland/3.1/sysroots/aarch64-fslc-linux/usr/include/c++/9.3.0/iostream:39[m[K,
from [01m[K/home/lorandpetok/cross_ws/src/rvc_robot/rvc_ui/include/ConsoleMenu.h:5[m[K,
from [01m[K/home/lorandpetok/cross_ws/src/rvc_robot/rvc_ui/src/ConsoleMenu.cpp:1[m[K:<
Here you can see that I include iostream, the includes cascade down to cwchar which in turn includes floatn.h from my local x86 library.
The compiler used for cross compilation is gcc 9.3.0
My cmake toolchain file used:
set(ARTHERO_SYSROOTS "/opt/fslc-wayland/3.1/sysroots")
set(CMAKE_SYSTEM_NAME Linux)
set(CMAKE_SYSTEM_PROCESSOR armv8-a)
set(TOOLCHAIN_PREFIX ${ARTHERO_SYSROOTS}/x86_64-fslcsdk-linux/usr/bin/aarch64-fslc-linux/aarch64-fslc-linux-)
set(CMAKE_C_COMPILER ${TOOLCHAIN_PREFIX}gcc)
set(CMAKE_CXX_COMPILER ${TOOLCHAIN_PREFIX}g++)
set(CMAKE_SYSROOT ${ARTHERO_SYSROOTS}/aarch64-fslc-linux)
set(CMAKE_PREFIX_PATH ${CMAKE_SYSROOT}/usr/lib/cmake ${CMAKE_SYSROOT}/opt/ros/melodic/share)
set(CMAKE_FIND_ROOT_PATH ${CMAKE_SYSROOT} ${CATKIN_DEVEL_PREFIX})
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_MODULE_PATH ${CMAKE_SYSROOT}/opt/ros/melodic/share)
set(LD_LIBRARY_PATH ${CMAKE_SYSROOT}/opt/ros/melodic/lib)
set(COMPILER_FLAGS " -march=armv8-a -mtune=cortex-a53")
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${COMPILER_FLAGS}" CACHE STRING "" FORCE)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${COMPILER_FLAGS}" CACHE STRING "" FORCE)
include_directories(/opt/fslc-wayland/3.1/sysroots/aarch64-fslc-linux/opt/ros/melodic/include/)
What could make the compiler or cmake to include the header from my local standard library and how should i tell it to look in the correct path?

gcc link error:cmake cross compile can't find secondary libraries even if the rpath is set using cmake

I'm trying cross compile arm program which depends on lots libraries. Explicit include the lib*.so can solve this but its not decent and in my project is almost impossible.
simplified problem is like below, e.g.
mainexe -> libcv_highgui.so(founded) -> libjpeg.so(missing)
but at linking time, i got error:
ld: warning: libjpeg.so.8, needed by /opt/tkfs/usr/local/lib/libopencv_highgui.so.2.4.10, not found (try using -rpath or -rpath-link)
I have added rpath, and I checked ./build/CMakeFiles/mainexe.dir/link.txt, rpath is already there:
arm-linux-gnueabihf-g++ main.cpp.o -Wl,-rpath,/opt/tkfs/:/opt/tkfs/usr/lib/arm-linux-gnueabihf /opt/tkfs/usr/local/lib/libopencv_core.so.2.4.10 -Wl,-rpath-link,/opt/tkfs/usr/local/lib
here is my cmake file:
cmake_minimum_required(VERSION 3.5)
project(testopencv)
set(CMAKE_EXPORT_COMPILE_COMMANDS "ON")
SET(CMAKE_SYSTEM_NAME Linux)
SET(ROOTFS_DIR "/opt/tkfs/")
set(CMAKE_CXX_COMPILER "arm-linux-gnueabihf-g++")
set(CMAKE_C_COMPILER "arm-linux-gnueabihf-gcc")
set(CMAKE_SKIP_BUILD_RPATH FALSE)
set(CMAKE_BUILD_WITH_INSTALL_RPATH TRUE)
set(CMAKE_INSTALL_RPATH_USE_LINK_PATH TRUE)
set(CMAKE_FIND_ROOT_PATH
${ROOTFS_DIR}
${ROOTFS_DIR}/usr/lib/
${ROOTFS_DIR}/usr/lib/arm-linux-gnueabihf
)
set(CMAKE_INSTALL_RPATH ${ROOTFS_DIR};${ROOTFS_DIR}/usr/lib/arm-linux-gnueabihf;${ROOTFS_DIR}/opt/ros/indigo/lib)
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_SYSROOT "${ROOTFS_DIR}/")
find_package( OpenCV COMPONENTS core highgui)
add_executable( main src/main.cpp )
target_link_libraries(main ${OpenCV_LIBS})
env:
all ld_library_path is set to empty;
3 gcc version is identical 4.8.4(host, cross compile, arm dev board)
both machine is ubuntu 14.04.
all libs like libjpeg.so.8 are in $rootfs/usr/lib/arm-linux-gnueabihf

CMake cross compile

I'm having problem with my cmake cross compiler project.
My cross compiler did not find used libraries. I setup my cross compiler with this tutorial Cross Compiler.
Now i need libs they are installed on my RaspberryPi. I have snychronised my /lib and /usr direcotry from Pi to my Computer in /opt/cross/rasp. This is my Toolchain file:
# this one is important
SET(CMAKE_SYSTEM_NAME Linux)
#this one not so much
SET(CMAKE_SYSTEM_VERSION 1)
# specify the cross compiler
SET(CMAKE_C_COMPILER
/opt/cross/x-tools/arm-unknown-linux-gnueabi/bin/arm-unknown-linux-gnueabi-gcc)
SET(CMAKE_CXX_COMPILER
/opt/cross/x-tools/arm-unknown-linux-gnueabi/bin/arm-unknown-linux-gnueabi-g++)
# where is the target environment
SET(CMAKE_FIND_ROOT_PATH /opt/cross/rasp)
# search for programs in the build host directories
SET(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER)
# for libraries and headers in the target directories
SET(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY)
SET(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY)
But when i try to compile my program i get following Linking Error:
/opt/cross/x-tools/arm-unknown-linux-gnueabi/lib/gcc/arm-unknown-linux-gnueabi/4.9.1/../../../../arm-unknown-linux-gnueabi/bin/ld: warning: libltdl.so.7, needed by /opt/cross/rasp/usr/local/lib/libgphoto2.so, not found (try using -rpath or -rpath-link)
/opt/cross/x-tools/arm-unknown-linux-gnueabi/lib/gcc/arm-unknown-linux-gnueabi/4.9.1/../../../../arm-unknown-linux-gnueabi/bin/ld: warning: libexif.so.12, needed by /opt/cross/rasp/usr/local/lib/libgphoto2.so, not found (try using -rpath or -rpath-link)
On my RaspberrPi is compiling without errors possible.
The problem seems link to a misinterpretation of etc/ld.so.conf see fixing-rpath-link-issues-with-cross-compilers
In order to add the missing rpath-link, you can append to the toolchain cmake file :
SET(CMAKE_EXE_LINKER_FLAGS "-Wl,-rpath-link=/opt/cross/rasp/lib/arm-linux-gnueabihf:/opt/cross/rasp/usr/lib/arm-linux-gnueabihf")
I believe your cross-compile linker needs a --sysroot change. In the toolchain file you can use:
set(CMAKE_SYSROOT "/opt/cross/rasp")
Should anyone be looking for another reference, aside from the original question, I recommend reading through the ARM cross-compile guide I wrote for Takeoff Technical:
https://takeofftechnical.com/x-compile-cpp-bbb

CMake variable persisting between runs even though it was reset

I'm trying to cross compile from Ubuntu to Windows, using CMake. I have everything configured (Installed both mingw32 and mingw64), and I have the relevant toolchain files for both. The problem is that a variable that I set in one toolchain file, after it is used, persists in the second run with the other toolchain file one as well.
These are my toolchain files:
Windows 64 bit: (Toolchain-Ubuntu-mingw64.cmake)
set(CMAKE_SYSTEM_NAME Windows)
unset(PROCESSOR_ARCHITECTURE CACHE)
set(PROCESSOR_ARCHITECTURE x64)
message("===Processor architecture: " ${PROCESSOR_ARCHITECTURE})
set(TOOLCHAIN_PREFIX x86_64-w64-mingw32)
set(CMAKE_C_COMPILER ${TOOLCHAIN_PREFIX}-gcc)
set(CMAKE_CXX_COMPILER ${TOOLCHAIN_PREFIX}-g++)
set(CMAKE_RC_COMPILER ${TOOLCHAIN_PREFIX}-windres)
set(CMAKE_FIND_ROOT_PATH /usr/${TOOLCHAIN_PREFIX})
set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER)
set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY)
set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY)
Windows 32 bit: (Toolchain-Ubuntu-mingw32.cmake)
set(CMAKE_SYSTEM_NAME Windows)
unset(PROCESSOR_ARCHITECTURE CACHE)
set(PROCESSOR_ARCHITECTURE x86)
message("===Processor architecture: " ${PROCESSOR_ARCHITECTURE})
set(TOOLCHAIN_PREFIX i686-w64-mingw32)
set(CMAKE_C_COMPILER ${TOOLCHAIN_PREFIX}-gcc)
set(CMAKE_CXX_COMPILER ${TOOLCHAIN_PREFIX}-g++)
set(CMAKE_RC_COMPILER ${TOOLCHAIN_PREFIX}-windres)
set(CMAKE_FIND_ROOT_PATH /usr/${TOOLCHAIN_PREFIX})
set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER)
set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY)
set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY)
And this is the top of my CMakeLists.txt file:
cmake_minimum_required(VERSION 2.8)
project("project")
set(SOURCE_FILE_LIST main.c)
set(ARCH_PROJECT_NAME ${PROJECT_NAME}${PROCESSOR_ARCHITECTURE})
message("Project - " ${ARCH_PROJECT_NAME})
...
When I run
cmake -DCMAKE_TOOLCHAIN_FILE=../cmake-toolchains/Toolchain-Ubuntu-mingw64.cmake ../src/
The output starts with:
===Processor architecture: x64
Project - projectx64
The unexpected part comes when I run:
cmake -DCMAKE_TOOLCHAIN_FILE=../cmake-toolchains/Toolchain-Ubuntu-mingw32.cmake ../src/
and the output still starts with
===Processor architecture: x64
Project - projectx64
What can I do to fix this behaviour?
CMake will cache many of the values it finds during the setup process. Frustratingly it does this to the point that attempting to recreate the projects with a new option specified on the command line simply doesn't work. The only solution I've found is to either delete the entire build directory, or the specific cache file in the build directory, called CMakeCache.txt I believe.