Как написать " CMakeLists.txt " для большого проекта с подкаталогами mutiple?
Я работаю над проектом моделирования: принимая встроенный C кодовая база с целевой платформы и попытка имитировать ее на хост-компьютере для отладки или одного шага в код.
ОС: Ubuntu Linux 14.04, IDE: CodeLite, генератор Makefile: Cmake. Я запутался в том, как писать CMakeLists.txt для проекта. Ниже приведена структура кодовой базы (все это написано в C):
|ARQSim
|-->ARQSim.h
|-->ARQSim.c
|-->BaseStationCode
| |->downlink.c
| |->neoncopy.c
| |->armCore
| | |->common
| | | |->Bsconfig.h
| | | |->config.h
| | |->MacSource
| | | |->lib
| | | | |->arqCommon.h
| | | | |->OverTheAir.h
| | | |->source
| | | | |->beacon.c
| | | | |->proxyDhcp.c
| | | | |->ARQ
| | | | | |->arqCommon.c
| | | | | |->arqInterface.c
| | | | | |->fragmentation
| | | | | | |->fragBookkeeping.c
| | | | | | |->fragProcessAck.c
| | | | | |->reassembly
| | | | | | |->reasmBookkeeping.c
| | | | | | |->reasmProcessAck.c
Я совершенно новичок в Cmake. Я прочитал много ресурсов по CMake и потокам здесь, в StackOverflow. Но я каждый раз путаюсь. Несколько вопросов у меня есть:
- мне нужен только один CMakeLists.txt в корневом каталоге или в каждом каталоге нужны разные CMakeLists.файл txt?
- как рекурсивно добавлять исходные файлы в CMakeLists.txt?
- каковы основные команды, которые мне нужно поместить в CMakeLists.txt для MakeFile поколение?
любая обратная связь с благодарностью. Особенно, если кто-то может дать мне пример, основанный на структуре кода, упомянутого выше. Спасибо.
1 ответов
мне нужен только один
CMakeLists.txt
в корневом каталоге или в каждом каталоге требуется другой ?
обычно у вас будет по одному на каждом уровне дерева где это имеет смысл
например:
root/
+--- CMakeLists.txt // your root CMakeLists
+--- foo/
| +--- CMakeLists.txt // foo component's CMakeLists
| +--- foo.c
| +--- tests/
| +--- CMakeLists.txt // foo test's CMakeLists
| +--- foo_tests.c
+--- bar/
+--- CMakeLists.txt // bar component's CMakeLists
+--- bar.c
+--- bar_impl/ // no CMakeLists for this dir, it is part of bar
| +--- bar_impl.c
+--- tests/
+--- CMakeLists.txt // bar test's CMakeLists
+--- bar_tests.c
корневые CMakeLists проекта.txt:
в вашем проекте root CMakeLists.txt
вы указываете минимальное требование cmake, имя проекта и включаете подкаталоги, которые имеют различные компоненты в них
root/CMakeLists.txt
:
cmake_minimum_required (VERSION 3.5)
project (my_project C)
add_subdirectory(foo)
add_subdirectory(bar)
Компонентные CMakeLists.txt:
тогда в каждом подкаталоге компонента у вас есть другой CMakeLists.txt
файл, в который вы добавляете библиотеки, исполняемые файлы и т. д.
root/foo/CMakeLists.txt
:
add_library(foo foo.c)
target_include_directories(foo PUBLIC ${CMAKE_CURRENT_SOURCE_DIR})
add_subdirectory(tests)
root/foo/tests/CMakeLists.txt
:
add_executable(foo_test foo_tests.c)
target_link_libraries(foo_test foo)
вы следуете этой структуре для бара так далее...
root/foo/CMakeLists.txt
:
add_library(bar
bar.c
bar_impl/bar_impl.c)
target_include_directories(bar PUBLIC ${CMAKE_CURRENT_SOURCE_DIR})
target_link_libraries(bar foo)
add_subdirectory(tests)
root/bar/tests/CMakeLists.txt
:
add_executable(bar_test bar_tests.c)
target_link_libraries(bar_test bar)
создание файлов сборки:
чтобы загрузить свою сборку, вы указываете cmake на свой root/CMakeLists.txt
cd root
mkdir build
cd build
cmake ..
(или используйте диспетчер сборки ide для создания конфигурации сборки)
более дальнеишее чтение
для получения подробной информации о различных функциях, которые я использовал здесь, обратитесь к документация:
наконец, чтобы ответить на ваш второй вопрос:
как рекурсивно добавлять исходные файлы в CMakeLists.txt?
это не рекомендуется (см. этот обсуждение для получения дополнительной информации).
лучше явно перечислить каждый файл, который вы хотите включить в свою цель.
обратите внимание, что если у вас есть исходные файлы в нескольких отдельных каталогах, но все они принадлежат к одной логической цели, тогда вам не нужен CMakeLists.txt
файл для каждого каталога - просто перечислите подкаталог в имени файла
пример:
foo/
+--- foo.c
+--- bar.c
+--- baz/
+--- baz.c
+--- bang.c
если вы хотите одну цель foo
для всех вышеуказанные файлы, вы создали бы его следующим образом:
add_library(foo
foo.c
bar.c
baz/baz.c
baz/bang.c)
или если вы действительно хотите использовать переменную для хранения списка SRCS
set(SRCS
foo.c
bar.c
baz/baz.c
baz/bang.c)
add_library(foo ${SRCS})