Как добавить и реализовать флаги конфигурации в Autotools?

Часть программы нашей исследовательской группы имеет дополнительные функции, предоставляемые библиотекой ctemplate. На нашем устаревшем кластере мы не можем собрать программное обеспечение из-за компиляции, поэтому я хотел бы отделить эту функциональность и контролировать, включена она или нет с помощью флага configure, такого как --disable-ctemplate.

Программное обеспечение, написанное на C++, использует систему сборки Autotools, с которой у меня нет большого опыта. Насколько я понимаю, для выполнения этой задачи мне нужно сделать следующее:

  1. Добавьте новый флаг в сценарий настройки, создав новую запись AC_ARG_ENABLE в configure.ac.

  2. Добавьте несколько операторов #ifdef (или, возможно, #ifndef) вокруг кода, использующего библиотеку ctemplate, и вокруг любого кода, вызывающего этот код.

Я думаю, что первый шаг будет выглядеть примерно так:

AC_ARG_ENABLE(ctemplate,
[  --disable-ctemplate    Disable HTML output],
[case "${enableval}" in
  yes) ctemplate=false ;;
  no)  ctemplate=true ;;
  *) AC_MSG_ERROR(bad value ${enableval} for --disable-ctemplate) ;;
esac],[ctemplate=true])
AM_CONDITIONAL(NOCTEMPLATE, test x$ctemplate = xfalse)

хотя я не знаю, верна ли логика, так как я адаптировал этот пример из примеров, в которых использовалось --enable-FLAG вместо --disable-FLAG.

На втором этапе я оберну разделы флагами препроцессора, такими как

#ifndef NOCTEMPLATE
void Class::MethodUsingCtemplate(...)
{
    ...
}
#endif

Будет ли это правильно «подключать» все, если я сделаю configure --disable-ctemplate?

Кроме того, будет ли это гарантировать, что программа не попадет в библиотеку ctemplate для компиляции? Если нет, то все это зря; крайне важно, чтобы я мог предотвратить компиляцию библиотеки ctemplate и зависимых компонентов.

Повторюсь, я не знаком ни с C++, ни с Autotools; Я применил очень наивный первый подход к решению этой проблемы. Если у вас есть опыт в этой области, я был бы очень признателен за ваши исправления и любые объяснения, которые вы могли бы предложить.


person gotgenes    schedule 18.08.2009    source источник
comment
+1. Это должно быть в руководстве по Autotools, а не требовать, чтобы люди собирали его вместе, искали его в списке рассылки или Stack Overflow.   -  person jww    schedule 13.09.2018


Ответы (3)


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

В configure.ac я поместил следующие строки кода

# This adds the option of compiling without using the ctemplate library,
# which has proved troublesome for compilation on some platforms
AC_ARG_ENABLE(ctemplate,
  [ --disable-ctemplate   Disable compilation with ctemplate and HTML output],
  [case "${enableval}" in
     yes | no ) WITH_CTEMPLATE="${enableval}" ;;
     *) AC_MSG_ERROR(bad value ${enableval} for --disable-ctemplate) ;;
   esac],
  [WITH_CTEMPLATE="yes"]
)

dnl Make sure we register this option with Automake, so we know whether to
dnl descend into ctemplate for more configuration or not
AM_CONDITIONAL([WITH_CTEMPLATE], [test "x$WITH_CTEMPLATE" = "xyes"])

# Define CTEMPLATE in config.h if we're going to compile against it
if test "x$WITH_CTEMPLATE" = "xyes"; then
    AC_DEFINE([CTEMPLATE], [], ["build using ctemplate library"])
    AC_MSG_NOTICE([ctemplate will be used, HTML output enabled])
else
    AC_MSG_NOTICE([ctemplate will not be used, HTML output disabled])
fi

На следующем шаге я изменил Makefile.am на верхнем уровне на следующее:

if WITH_CTEMPLATE
  MAYBE_CTEMPLATE = ctemplate
endif

SUBDIRS = boost libgsl $(MAYBE_CTEMPLATE) libutil ...

На нижнем уровне Makefile.ams я добавил

if WITH_CTEMPLATE
    # some change to the configuration
else
    # some other change to the configuration
endif

Наконец, мне нужно было убедиться, что один из ключевых заголовочных файлов C++ (включенный в другие части кода) содержит следующее:

#ifdef HAVE_CONFIG_H
#    include "config.h"
#endif

config.h содержит любые новые определения, созданные с помощью AC_DEFINE, поэтому этот файл должен быть включен в части, которые проверяют, определено ли определение макроса, созданное этим маршрутом (или не определено).

Это заняло много времени и заставило меня разочароваться; Я могу только надеяться, что документирование этого объяснения здесь спасет кого-то еще от той же участи.

person gotgenes    schedule 23.08.2009

Вы определенно на правильном пути. Поначалу автоинструменты могут показаться очень сложными, но одно из их преимуществ заключается в том, что тысячи проектов уже сделали то, что вы хотите сделать. Все, что вам нужно сделать, это найти их.

Вот ссылка на поиск кода Google для AC_ARG_DISABLE. Сходить с ума.

person anthony    schedule 18.08.2009
comment
Есть ли AC_ARG_DISABLE в стандартных Autotools? Я не нашел документации для него в Google. Для него очень мало совпадений по сравнению с AC_ARG_ENABLE в поиске кода Google. (Сравните с google.com/codesearch?hl=en&q=AC_ARG_ENABLE+disable). - person gotgenes; 19.08.2009
comment
В некоторых из этих проектов есть макрос, определяющий AC_ARG_DISABLE. Почему бы им не включить это в стандартный пакет? - person nlucaroni; 16.05.2011

Чтобы предотвратить попытку компиляции сборки в подкаталоге ctemplate, вам нужно сделать что-то вроде:

if CTEMPLATE
SUBDIRS += ctemplate
endif

в Makefile.am

person William Pursell    schedule 18.08.2009