Библиотеки кросс-компиляции CMAKE не найдены
У меня странные проблемы с моими кросс-компиляторными проектами cmake.
Найдены мои собственные библиотеки, но нет (системных) библиотек из моего набора инструментов.
Ранее я использовал KDevelop на Debian Squeeze Machine. Теперь на моей новой машине с Debian Wheezy настройка не удалась. Не находит системные библиотеки вроде m
или же pthread
,
На моей старой машине следующее работало отлично, но я не помню, чтобы я сделал что-то особенное, чтобы сделать эту работу.
Вот один из моих CMakeLists.txt
файлы
cmake_minimum_required(VERSION 2.8)
SET(CMAKE_SYSTEM_NAME Linux)
SET(CMAKE_SYSTEM_VERSION 2.6.36.4)
SET(CMAKE_C_COMPILER arm-angstrom-linux-gnueabi-gcc)
SET(CMAKE_CXX_COMPILER arm-angstrom-linux-gnueabi-g++)
include_directories(../include
../../../sample/include)
project(testmain)
add_executable(testmain
some_c-source-file.c)
set(CMAKE_LIBRARY_PATH ../lib/arm-26/lib
../../../sample/lib/arm-26/lib)
find_library(LIBS_TEST NAMES akku)
find_library(LIBS_M NAMES m)
find_library(LIBS_PTHREAD NAMES pthread )
target_link_libraries(akkumain
${LIBS_TEST}
${LIBS_M}
${LIBS_PTHREAD})
set(CMAKE_C_FLAGS "-Wall -Werror")
set(CMAKE_C_FLAGS_DEBUG "-g3 -O2 -rdynamic")
set(CMAKE_C_FLAGS_RELEASE "-g0 -O0")
set(CMAKE_CXX_FLAGS "-Wall -Werror")
set(CMAKE_CXX_FLAGS_DEBUG "-g3 -O2 -rdynamic")
set(CMAKE_CXX_FLAGS_RELEASE "-g0 -O0")
Это сообщение отображается при попытке компилирования с использованием KDevelop: (повторюсь: это работало на моей старой машине)
/home/user/testmain/build> /usr/bin/cmake -DCMAKE_BUILD_TYPE=Debug /home/user/testmain/
-- The C compiler identification is GNU 4.3.3
-- The CXX compiler identification is GNU 4.3.3
-- Check for working C compiler: /usr/local/angstrom/arm/bin/arm-angstrom-linux-gnueabi-gcc
-- Check for working C compiler: /usr/local/angstrom/arm/bin/arm-angstrom-linux-gnueabi-gcc -- works
-- Detecting C compiler ABI info
-- Detecting C compiler ABI info - done
-- Check for working CXX compiler: /usr/local/angstrom/arm/bin/arm-angstrom-linux-gnueabi-g++
-- Check for working CXX compiler: /usr/local/angstrom/arm/bin/arm-angstrom-linux-gnueabi-g++ -- works
-- Detecting CXX compiler ABI info
-- Detecting CXX compiler ABI info - done
CMake Error: The following variables are used in this project, but they are set to NOTFOUND.
Please set them or make sure they are set and tested correctly in the CMake files:
LIBS_M
linked by target "akkumain" in directory /home/user/testmain
LIBS_PTHREAD
linked by target "akkumain" in directory /home/user/testmain
Итак, LIBS_TEST найден. Но нет libm
или же libpthread
, Я пробовал это с разными проектами: все мои библиотеки найдены, но ни одна из "системных" библиотек.
Я уже пробовал разные вещи, как
set(CMAKE_FIND_LIBRARY_PREFIXES lib )
set(CMAKE_FIND_LIBRARY_SUFFIXES .a )
и еще кое-что я не помню.
Единственное, что РАБОТАЕТ, это когда я указываю каталог вручную:
find_library(ASTLIBS_M NAMES m PATHS /usr/local/angstrom/arm/arm-angstrom-linux-gnueabi/usr/lib)
После указания этого на мой CMakeLists.txt
библиотека найдена, и я могу без проблем скомпилировать свой проект.
НО: Это не то, что я хочу, потому что у меня много проектов и много библиотек, и я не хочу редактировать все свои CMakeLists.txt
...:(
Кто-нибудь знает, что заставило мою старую машину найти системные библиотеки, не указывая ничего особенного в моих файлах IDE/CMake?
Изменить:я только что заметил для одного из моих исполняемых файлов, что на этапе компоновщика он выдает некоторые ошибки, что он не может найти некоторые символы из glibc - кажется, что-то более неправильно с моей системой Debian Wheezy.- Я надеюсь, что я могу понять это...
Редактировать:
Может быть, я должен дать краткое резюме: мой код компилируется хорошо, но все библиотеки из моего набора инструментов не найдены, но если я добавлю путь к библиотекам моего набора инструментов вручную, он компилируется, но на этапе компоновки происходит сбой.
2 ответа
Есть определенные пути по умолчанию, где CMake find_library
модуль поиска. Если ваши системные библиотеки на вашей старой машине окажутся в одном из таких мест, они будут найдены без какой-либо дополнительной работы.
Однако, поскольку путь вашей новой машины к этим библиотекам выглядит следующим образом: "/usr/local/angstrom/arm/arm-angstrom-linux-gnueabi/usr/lib", вам нужно будет сообщить об этом CMake.
Один из таких способов, как вы показали (добавление пути явно). Но в этом случае путь, вероятно, специфичен только для этой машины, поэтому вам лучше установить этот путь только при вызове CMake на этой машине. Вы можете добавить его в CMAKE_PREFIX_PATH
например:
cmake . -DCMAKE_PREFIX_PATH=/usr/local/angstrom/arm/arm-angstrom-linux-gnueabi/usr
(Примечание: путь в этом случае добавляется "lib", когда find_library
называется).
Или если вы хотите повлиять только на find_library
пути поиска и не все find_xxx
модули, набор CMAKE_LIBRARY_PATH
cmake . -DCMAKE_LIBRARY_PATH=/usr/local/angstrom/arm/arm-angstrom-linux-gnueabi/usr/lib
Вы когда-нибудь пробовали использовать файл toolchain? Я также кросс-компиляцию в ARM и AVR много, и это работает очень хорошо без хлопот (я также использую KDevelop, и он прекрасно работает вместе с CMake). Главное - указать путь к корневой файловой системе вашей цепочки инструментов через переменную CMAKE_FIND_ROOT_PATH. Попробуйте поместить все это в файл, который я обычно называю по архитектуре, к которой я кросс-компилирую (в данном случае я назвал ее arm-unknown-linux-gnueabi.cmake):
# the name of the target operating system
SET(CMAKE_SYSTEM_NAME Linux)
# which C and C++ compiler to use
SET(CMAKE_C_COMPILER arm-unknown-linux-gnueabi-gcc)
SET(CMAKE_CXX_COMPILER arm-unknown-linux-gnueabi-g++)
# here is the target environment located
SET(CMAKE_FIND_ROOT_PATH /home/claudio/TS-7400/rootfs)
# adjust the default behaviour of the FIND_XXX() commands:
# search headers and libraries in the target environment, search
# programs in the host environment
set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER)
set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY BOTH)
set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE BOTH)
Обратите внимание, что переменные CMAKE_FIND_ROOT_PATH_MODE_xxx определяют, где переменные CMake
будет искать двоичные файлы, библиотеки и заголовочные файлы. Я обычно устанавливаю PROGRAM на NEVER
поэтому он никогда не использует двоичные файлы вашей корневой файловой системы с несколькими архитектурами, поскольку они все равно не будут работать на вашем хост-компьютере. Для библиотек и заголовочных файлов BOTH
означает, что сначала он будет искать указанный вами ROOT_PATH, а затем, если он не найдет что-либо, будет проходить через каталоги вашей системы хост-машины.
Таким образом, всякий раз, когда вы хотите кросс-компилировать проект, все, что вам нужно сделать, это создать каталог сборки (чтобы он не смешивал ваши исходники с файлами, созданными во время сборки), а затем запустить cmake, указав нужный файл цепочки инструментов использовать (я полагаю, ваш CMakeLists.txt
это вместе с вашим набором инструментов в том же каталоге, где находятся ваши источники - project_sources_dir в моем примере):
cd project_sources_dir
mkdir build
cd build
cmake -DCMAKE_TOOLCHAIN_FILE=../arm-unknown-linux-gnueabi.cmake ..
Весь смысл использования файла инструментария состоит в том, что, если вы хотите скомпилировать точно такой же проект для вашего хост-компьютера, вам не нужно менять ни одной строки в вашем CMakeLists.txt
, Просто запустите cmake без указания файла цепочки инструментов:
cd project_sources_dir
mkdir build
cd build
cmake ..
и ваш проект готов для компиляции native для вашей хост-машины. Если всего этого недостаточно, вы можете найти более подробную информацию здесь о CMake Cross Compiling