LINUX.ORG.RU

c++ build system

 ,


0

2

Подскажите пожалуйста, что лучше всего использовать сегодня для сборки? Я знаю про CMake, но не уверен умеет ли он следующее:

  • Самостоятельно поустанавливать флаги вроде -Wall (например pedantic, fail on errors и тому подобное) для gcc и clang
  • Самостоятельно выкачать откуда-нибудь dependencies для сборки, собрать их, положить куда-нибудь в src/build

Или для этого нужен Conan? Или Conan не умеет собирать?

В общем хочется что-то вроде cargo наверное.

Что сейчас самое удобное для новых проектов?

  • поставит те флаги, которые вы укажите в конфигурационном файле, автоматически ничего не сделает
  • выполнение внешних команд доступно
Silerus ★★ ()

Самостоятельно поустанавливать флаги вроде -Wall(например pedantic, fail on errors и тому подобное) для gcc и clang

В смысле за тебя будет флаги выбирать? Ишь чего удумал! cmake позволит тебе определить используемый тип компилятора, и, например, задать для случая gcc||clang какие-то флаги, которые ты задашь сам. Другие мейнстримовые системы сборки работают так же, так как флагов управления диагностиками - как собак нерезанных. При желаниие перед использованием флага можно протестировать, поддерживает ли его компилятор.

Самостоятельно выкачать откуда-нибудь dependencies для сборки, собрать их, положить куда-нибудь в src/build

cmake позволяет скачивать и распаковывать архивы, но вообще эту работу лучше поручить менеджеру зависимостей, такому как вышеупомянутый Conan

annulen ★★★★★ ()
Последнее исправление: annulen (всего исправлений: 1)

cmake. что надо то и соберет. флаги, опции, либы, таргеты и прочее ему указываются во входном файле. может вызывать разные бэкенды, например gnumake или ninja. формат входного файла простой, читаемый, можно генерировать автоматически по каким-то иным описаниям и проч.

alysnix ()
Ответ на: комментарий от annulen

В смысле за тебя будет флаги выбирать? Ишь чего удумал!

Ну да. Какие-нибудь осмысленные дефолты для debug/release + gcc/clang. Нет такого?

cmake позволяет скачивать и распаковывать архивы,

Я видел, что у cmake есть возможность задавать некоторые внешние зависимости при помощи find_package (при чем я имею ввиду, что есть какие-то уже сконфигурированные конфиги для find_package для некоторого количества известного софта), но я не уверен, что там много пакетов доступно. Как find_package сравним с зависимостями Conan? У кого больше? Как, например, при помощи find_package задать зависимость от внешнего libxxx? Есть какие-то репозитории а-ля AUR в Arch?

но вообще эту работу лучше поручить менеджеру зависимостей, такому как вышеупомянутый Conan

А самого Conan’а будет достаточно или к нему нужно прилепить cmake/make/etc?

PS А можно пример какого-нибудь минимального Conan конфига для сборки файла xxx.cpp в a.out с зависимостью от какой-нибудь libxxx?

dissident ()
Последнее исправление: dissident (всего исправлений: 7)
Ответ на: комментарий от Silerus

выполнение внешних команд доступно

Я имею ввиду не выполнение внешних команд, а какое-то хранилище с кем-то заботливо сделанными libxxx.cmake для find_package для какого-то общеизвестного софта. Как у cmake с этим?

dissident ()
Ответ на: комментарий от lovesan

MSBuild!

Правда? Ну VSCode от MS рулит. А ткните в пример пожалуйста для сборки файла xxx.cpp в a.out с зависимостью от какой-нибудь libxxx?

PS:

Lots of cryptic XML files, not human-readable and not intended to be edited directly. Hard to use external libraries dependencies. (c) https://caiorss.github.io/C-Cpp-Notes/building-systems.html :(

dissident ()
Последнее исправление: dissident (всего исправлений: 3)
Ответ на: комментарий от anonymous

Meson Build?

zdep = dependency('zlib', version : '>=1.2.8')
exe = executable('zlibprog', 'prog.c', dependencies : zdep)

(c) https://mesonbuild.com/Dependencies.html

А он много таких «zlib» умеет? Где найти список? Или то, что перечислено в https://mesonbuild.com/Dependencies.html и есть список? Как это сравнимо с Conan/CMake (в смысле по количеству dependencies в «репозитории»)?

dissident ()
Последнее исправление: dissident (всего исправлений: 1)
Ответ на: комментарий от dissident

Какие-нибудь осмысленные дефолты для debug/release + gcc/clang. Нет такого?

-Wall

Как find_package сравним с зависимостями Conan?

find_package по-умолчанию ищет в системе, либо в путях которые пользователь задал в CMAKE_PREFIX_PATH

У кого больше?

У Арча, конечно, больше)

Есть какие-то репозитории а-ля AUR в Arch?

В смысле? Ты из аура можешь себе либы поставить и find_package их найдет (если есть поддержка)

А самого Conan’а будет достаточно или к нему нужно прилепить cmake/make/etc?

Недостаточно, это разные инструменты выполняющие разную работу. Conan не знает ничего про языки программирования и как на них что компилится, а разрешает зависимости, качает исходники и при необходимости запускает системы сборки пакетов с нужными опциями

annulen ★★★★★ ()
Ответ на: комментарий от dissident

А они разве в зависимости умеют?

Искать или собирать? Искать - pkg-config (или в ручную, но так уже давно никто не делает), собирать - нет, репы в помощь или тот же Conan или аналоги

annulen ★★★★★ ()
Ответ на: комментарий от dissident

А он много таких «zlib» умеет?

https://mesonbuild.com/Dependencies.html#dependency-method

Например, все что находит pkg-config (т.е. практически любая бибилотека в никсах), будет работать

Как это сравнимо с Conan/CMake (в смысле по количеству dependencies в «репозитории»)?

С Conan никак не сравнимо, так как система сборки не собирает зависиморсти, а ищет системные. По-сравнению CMake - примерно то же самое, но в CMake используется разный код для этих методов обнаружения

annulen ★★★★★ ()
Последнее исправление: annulen (всего исправлений: 1)
Ответ на: комментарий от annulen

-Wall

Ну а если мне этого мало, а разбираться со всей кучей варнингов нет желания. Например хочется -Werror by default. Или например какого-нибудь predefined списка конфигураций -W*, вроде paranoid, normal, etc.

В смысле? Ты из аура можешь себе либы поставить и find_package их найдет (если есть поддержка)

Я имею ввиду что-нибудь вроде FindBZip2.cmake (c) https://gitlab.kitware.com/cmake/community/-/wikis/doc/tutorials/How-To-Find-Libraries. Т.е. у CMake есть уже ряд таких Find*.cmake.

У Арча, конечно, больше)

Ну так что, в качестве build system использовать makepkg?

Недостаточно, это разные инструменты выполняющие разную работу. Conan не знает ничего про языки программирования и как на них что компилится, а разрешает зависимости, качает исходники и при необходимости запускает системы сборки пакетов с нужными опциями

Спасибо понятно. Но у CMake таки есть эти Find*.cmake, т.е. я так понимаю, что часть работы по автоматической сборке зависимостей он таки умеет?

dissident ()
Ответ на: комментарий от annulen

autotools

А они разве в зависимости умеют?

Искать или собирать? Искать - pkg-config (или в ручную, но так уже давно никто не делает), собирать - нет, репы в помощь или тот же Conan или аналоги

Хочется и того и другого. Как у pacman. Чтобы был репозиторий с конфигами а-ля Find*.cmake или PKGBUILD, чтобы эти конфиги можно было в простой способ указать в конфиге проекта, чтобы build system их выкачал из github или где там указано в соотв. «PKGBUILD», собрал в src/build, туда же установил, собрал софт с нужными -Isrc/build/libxx/include (или где там будет указано в «PKGBUILD», сделал нужные ldd к src/build/libxxx.so и тому подобное.

Т.е. этакий makepkg для локальной сборки. Чтобы затем можно было просто сделать rm -rf src и следов не осталось.

Или я что-то неправильное хочу? Я так понимаю что FInd*.cmake или тот же Conan для этого и нужен. Или относительно флаг, вот здесь, например, https://www.youtube.com/watch?v=DHOlsEd0eDE товарищ советует использовать build system в частности для того, чтобы отлавливать разные ворнинги (не могу найти конкретную минуту, но он говорит что-то вроде «use build system from the beginning and don’t just build using shell script or similar, so that you can see different warning from the beginning of your project»). Я думал он имел ввиду, что, например, CMake автомагически содержит набор осмысленных флаг. Или он просто имел ввиду, что стоит их установить с начала? Какая тогда разница между myproject.cmake и myproject.sh в этом ключе?

dissident ()
Ответ на: комментарий от dissident

Т.е. у CMake есть уже ряд таких Find*.cmake.

find_package может использовать:

  1. Find-модули, идущие в комплекте с CMake
  2. Find-модули из собираемого проекта (можно писать свои или таскать с собой сторонние, есть даже целые библиотеки модулей вроде ECM)
  3. *Config.cmake файлы, установленные используемыми библиотеками

Кроме find_package можно использовать pkg-config или искать зависимости руками

Но у CMake таки есть эти Find*.cmake, т.е. я так понимаю, что часть работы по автоматической сборке зависимостей он таки умеет?

Нет, все эти Find-модули ищут зависимости, а не собирают

annulen ★★★★★ ()
Ответ на: комментарий от annulen

С Conan никак не сравнимо, так как система сборки не собирает зависиморсти, а ищет системные. По-сравнению CMake - примерно то же самое, но в CMake используется разный код для этих методов обнаружения

В общем если я правильно понимаю (мне нужно что-то вроде makepkg с автоматической сборкой зависимостей (которые уже кем-то заботливо сконфигурированы в каком-то репозитории, а в случае если нет с легкой возможностью добавлять свои просто создавая конфиги вроде Find*.cmake) и с «установкой» зависимостей и собранного в src/build или другой tmp, так, чтобы это все удалялось при помощи rm -rf src/build), то мне нужен Conan+CMake?

PS Я не имею ввиду каких-то очень сложных случаев, когда нужно собрать в chroot/docker, иначе не будет работать, но почему бы и нет. Conan так и делает?

dissident ()
Ответ на: комментарий от dissident

мне нужен Conan+CMake?

Нужно выбрать 1) менеджер зависимостей; 2) систему сборки для своего собственного кода. За редкими исключениями, первые и вторые дружат в любых комбинациях.

Conan так и делает?

Нет, Conan-пакеты в основном пишутся так, чтобы собираться в окружении пользователя, используя внутренние зависимости вместо системных, без привязок к каким-то средставм изоляции. Хочешь для верности собирать в чруте - пожалуйста, запускай Conan там. Часто бинарные пакеты собирают в общедоступных CI-системах, и потом уже локально не собирают.

annulen ★★★★★ ()
Ответ на: комментарий от annulen

find_package может использовать:

  • Find-модули, идущие в комплекте с CMake

Я не до конца понимаю.

Now CMake has a find_package() which opens a Find*.cmake file and searches after the library on the system

(c) https://stackoverflow.com/questions/20746936/what-use-is-find-package-if-you-need-to-specify-cmake-module-path-anyway

Т.е. какой смысл в существующем, например, FindBZip2.cmake если мне этот bzip все равно надо руками собрать и куда-то установить (пусть даже и в prefix=tmp). Там просто флаги для его «приклеивания», так?

  • Find-модули из собираемого проекта (можно писать свои или таскать с собой сторонние, есть даже целые библиотеки модулей вроде ECM)

Т.е. таскать с собой код этих модулей и соответствующие Find*.cmake? А это ECM не умеет само скачать как makepkg при помощи линков из PKGBUILD?

В общем я так понимаю, что нет.

В любом случае спасибо за разъяснения!

dissident ()
Последнее исправление: dissident (всего исправлений: 1)
Ответ на: комментарий от dissident

Т.е. какой смысл в существующем, например, FindBZip2.cmake если мне этот bzip все равно надо руками собрать и куда-то установить (пусть даже и в prefix=tmp).

Смысл в том, чтобы найти системные библиотеки. Весь софт из репозиториев так собирается. Другой вариант использования - можно подключить к проекту файлик, сгенерированный Conan’ом, и тогда find_package будет вместо системных пакетов находить то, что собрал Conan, т.е. один и тот же проект можно собирать и так, и так.

Там просто флаги для его «приклеивания», так?

Флаги компилятора и линковщика для сборки твоего проекта с данной зависимостью.

annulen ★★★★★ ()
Ответ на: комментарий от dissident

Т.е. таскать с собой код этих модулей и соответствующие Find*.cmake?

Это делается только при необходимости. У многих либ есть конфиг-файлы для cmake, или их можно подключать через pkg-config. В связке с Conan можно не использовать никакие find_package, find-модули и т.д., но тогда проект не будет собираться «в дикой природе» (что возможно и не требуется)

annulen ★★★★★ ()
Ответ на: комментарий от dissident

Или относительно флаг, вот здесь, например, https://www.youtube.com/watch?v=DHOlsEd0eDE товарищ советует использовать build system в частности для того, чтобы отлавливать разные ворнинги (не могу найти конкретную минуту, но он говорит что-то вроде «use build system from the beginning and don’t just build using shell script or similar, so that you can see different warning from the beginning of your project»).

Вот: https://youtu.be/DHOlsEd0eDE?t=1919

When I set up my build system I had many more warnings that I wasn't thinking about

Как это? Если флаги сам задал, то как он мог о них раньше не думать? Просто он сравниваеют свою «prototype command line» с простыней флаг на следующем слайде? Ну так точно так же их можно было задать в my_prototype_build_line.sh

PS А вот здесь пример использования Conan: https://youtu.be/DHOlsEd0eDE?t=3268. Правильно ли я понимаю, что строка:

C:\path\to\conan remote add bincrafters https://api.bintray.com/conan/bincrafters/public-conan

добавляет репозиторий, а строка:

C:\path\to\connan install .. --build missing

скачивает и собирает софт указынный в конфиге его проекта следуя конфигам из репозитория добавленного в первой строке? Или только собирает, а скачивать надо руками и «таскать с собой»?

dissident ()
Ответ на: комментарий от rumgot

Учи CMake - не пожалеешь. Только порог вхождения выше.

Я его использовал для плюсов (для плагинов к OpenOffice) еще в 2005 году для генерации sln и тому подобное. Понятно, что с тех пор многое изменилось. Но не настолько как хотелось бы. А хотелось бы репозитория вроде AUR и возможности просто написать в стиле:

add_source_dir(src)
depends(boost_filesystem)
add_flags(paranoid)
build_into(snap/docker/exe)

И все. Как в PKGCONFIG.

dissident ()
Ответ на: комментарий от dissident

в cmake есть ExternalProject.

Но вообще, стандартный способ работы с зависимостями в почти любом linux-дистре - это вручную устанавливать их из реп этого дистра, после чего находить с помощью cmake или pkg-config.

Lrrr ()
Ответ на: комментарий от fsb4000

Божественная система сборки теперь и на Linux/Mac, а не только на Windows.

Хорошая шутка про MSBuild. Поржал! :)

З.Ы. Мне приходилось много писать на шарпе, если что.

dave ★★★★★ ()
Последнее исправление: dave (всего исправлений: 1)

Самостоятельно поустанавливать флаги вроде -Wall (например pedantic, fail on errors и тому подобное) для gcc и clang

А кто мешает сделать вот так?

set_property(TARGET ${PROJECT} APPEND PROPERTY COMPILE_OPTIONS       -Wall
                                                                     -Wextra
                                                                     -Werror
                                                                     -pedantic
                                                                     -pg)
set_property(TARGET ${PROJECT} APPEND PROPERTY LINK_FLAGS            -pg)
set_property(TARGET ${PROJECT}        PROPERTY CXX_STANDARD          11)
set_property(TARGET ${PROJECT}        PROPERTY CXX_STANDARD_REQUIRED ON)
set_property(TARGET ${PROJECT}        PROPERTY CXX_EXTENSIONS        OFF)

Или вообще по хардкору: add_definitions(-Wall -Wextra -Werror -pedantic …)


Самостоятельно выкачать откуда-нибудь dependencies для сборки, собрать их, положить куда-нибудь в src/build

Use git submodules, Luke! Хотя можно сделать кастомные команды, наверное

XMs ★★★★★ ()
Последнее исправление: XMs (всего исправлений: 1)
Ответ на: комментарий от dissident

Find*.cmake или PKGBUILD, чтобы эти конфиги можно было в простой способ указать в конфиге проекта, чтобы build system их выкачал из github или где там указано в соотв. «PKGBUILD», собрал в src/build, туда же установил, собрал софт с нужными -Isrc/build/libxx/include (или где там будет указано в «PKGBUILD», сделал нужные ldd к src/build/libxxx.so и тому подобное.

vcpkg

LamerOk ★★★★★ ()

Самостоятельно поустанавливать флаги вроде -Wall (например pedantic, fail on errors и тому подобное) для gcc и clang

Самостоятельно выкачать откуда-нибудь dependencies для сборки, собрать их, положить куда-нибудь в src/build

Фигасебе люди задуряются.

Я кроме CиМейка и не знаю ничего особо и хватает. Обычно у меня основной проектый файл и другие подключаются модулями, проектый определяет все ключи сборки, модули их могут переопределить.

А про зависимости - ну блин, симейк требуется раз написать и забыть, как и проектные зависимости, ну совсем же редко меняются, вот еще что-то гуглить ради этой автоматизации, серьезно? Ведь это крайне редко нужно, крайне редко в проекты (вроде бы) попападают новые зависимости, и куда удобнее, проще и быстрее руками их разрулить все. Обычно я их подключаю ровно так же как остальные модули проекта, только в /third-party директорию.

bonta ★★★ ()
Ответ на: комментарий от dissident

find_package(libxxx) либо использует:

  • Если libxxx не знает о cmake, то: Findlibxxx.cmake, который либо присутствует как официальный cmake модуль, либо может быть самописным (стоит подготовить pull request для cmake)
  • libxxx-config.cmake для библиотек которые знают о cmake.
invy ★★★★★ ()
Последнее исправление: invy (всего исправлений: 2)

Что значит «самостоятельно»? CMake умеет внешние подпроекты. Умеет скачивать/клонировать их исходники, распаковывать, запускать произвольные команды конфигурирования, сборки и установки (ExternalProject_Add). Но описать весь процесс ты естественно должен сам.

CMake совсем не идеален и от некоторых его особенностей хочется поскорее все это развидеть. Но как инструмент, он свою задачу решает.

m0rph ★★★★★ ()
Ответ на: комментарий от RazrFalcon

Ну возможно на первый взгляд это выглядит страшно: https://github.com/roozbehid/dotnet-vcxproj/blob/master/Examples/VcxProj_Complex/ConsoleApplication/ConsoleApplication.vcxproj

Но обычно всё же это генерируется IDE. + в новых версиях довольно сильно упростили, особенно для C#.

Вот минимальный файл проекта:

<Project Sdk="Microsoft.NET.Sdk">

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>netcoreapp3.1</TargetFramework>
  </PropertyGroup>

</Project>

Я тут даже не указываю какие файлы собирать, он сам собирает все файлы в той же папке где и файл проекта.

Но можно и указать:

<Project Sdk="Microsoft.NET.Sdk">

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>netcoreapp3.1</TargetFramework>
  </PropertyGroup>

  <ItemGroup>
    <Compile Include="Program.cs" />
  </ItemGroup>

</Project>

А вот так добавлять библиотеки c https://www.nuget.org/:

<Project Sdk="Microsoft.NET.Sdk">

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>netcoreapp3.1</TargetFramework>
  </PropertyGroup>

  <ItemGroup>
    <Compile Include="Program.cs" />
    <Compile Include="SomeClass.cs" />
  </ItemGroup>

  <ItemGroup>
    <PackageReference Include="Lib1OnNuget" Version="1.*" />
    <PackageReference Include="Lib2OnNuget" Version="0.1.0" />
  </ItemGroup>

</Project>

Вот с такими примерами уже лучше выглядит система сборки? Или XML не может быть хорошим?

fsb4000 ★★★ ()
Ответ на: комментарий от fsb4000

Посмотрел на Cargo.toml, посмотрел на vcxproj - перекрестился.

Или XML не может быть хорошим?

XML - неплохой язык разметки. Но он не для людей. Как и json.

PS: он может собирать проекты по ссылке с гитхаба с указанием коммита?

RazrFalcon ★★★★★ ()
Ответ на: комментарий от RazrFalcon

json не язык разметки, а «язык» структурирования данных. лучше его придумать что-то текстовое сложно, поскольку он минимален. можно нагородить что-то пропороще, только с отступами(заменив ими скобки), по типу питона, но это уже на любителя.

alysnix ()
Ответ на: комментарий от RazrFalcon

он может собирать проекты по ссылке с гитхаба с указанием коммита?

нет, только nuget или локальные папки.

можно использовать git submodule, и дальше работать как с локальной зависимостью…

а напрямую нет…

fsb4000 ★★★ ()
Ответ на: комментарий от RazrFalcon

Я этого и не говорил. Речь о том, что использовать его для конфигов - бред. Там даже комментов нет.

по стандарту - нет. но можно и по стандарту вставить «комменты» в виде просто значений. типа __cm = «это такой коммент» а потом вы можете их игнорить или даже давать пользователю, как некие хинты, хелпы или что-то еще. очень даже удобно

alysnix ()

тред не читал

навскидку CMAKE умеет все перечисленное:

проставить опции компилятора (сам ничего от себя не ставит, но сделаешь это единоразово и забудешь):

add_compile_options

Выкачивание и построение зависимостей:

ExternalProject_Add

Поиск зависимостей на системе:

find_package

в общем, изучай ман по симейку

EugeneBas ★★ ()