LINUX.ORG.RU

Вопрос по Automake

 ,


0

3

Всем здравствуйте.

В процессе использования GNU Autotools (предыстория) заметил, что иногда, в зависимости от проекта, файл компилируется командой

# Такой вариант используется в базовом amhello
gcc -c -o file.o file.c

а иногда

# Такой вариант используется, напр., в strace и gstreamer
gcc -c -o file.o `test -f file.c || echo $(srcdir)/`file.c

Причём VPATH-сборки корректно работают в обоих случаях – просто точный путь до файла вычисляется либо в стадии конфигурации (./configure), либо в стадии сборки (make).

В документации эта разница никак не описана.

Если копаться в истории, то видно, что второй вариант появился с коммитом dd16cf3641508379a977c37b25fbbae93358bc40 и стал опциональным (в зависимости от значения флага GENERIC) с коммитом 29ade8c79e328cb9f0ed0f132386b4a55027661c.

Копание в исходном коде Automake не приблизило меня к пониманию, за каким рожном появилась такая хитровыдуманная проверка и, главное, что влияет на значение флага GENERIC.

Кто-нибудь может пояснить?

Cast @Harald

★★★★★

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

Копни чуть глубже в историю и найди первый десяток коммитов с этим GENERIC-костылем. Где-нибудь там (скорее всего) будет пояснение что это и зачем. Спустя 20 лет другого пути примерно нет.

anonymous
()
test -f file.c || echo $(srcdir)/

Эта команда возвращает пустую строку, если file.c найден, и $(srcdir)/ в противном случае

//мимокэп

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

Чувак, спасибо.

Я уже копнул. Ссылка на второй коммит.

  • automake.in (&add_depend2): Transform `GENERIC’.

Get rid of the ad hoc transformation of @EXT@.o:' which in addition was broken by the@ -> %’ patch.

  • depend2.am: Adjust to use ?GENERIC?.

Только это по-прежнему нихрена не объясняет. Потому и написал сюда.

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

Всё верно. С этим мы уже разобрались ранее.

В случае сборки “in-tree” срабатывает первая ветка, в случае “out-of-tree” (оно же “VPATH build”) — вторая.

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

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

Из предыдущей темы:

[…] я бы предположил, что файл из локального каталога (если есть) должен иметь более высокий приоритет, чем тот же файл из VPATH.

Мне кажется это и есть ответ. По относительному пути находится файл из каталога сборки. А его наличие может зависеть от чего-то во время самой сборки, поэтому проверяют в последний момент.

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

Спасибо за ответ.

Но мой вопрос, ещё раз, заключается немного в другом.

Почему в некоторых проектах путь к файлу вычисляется на этапе выполнения configure (т е путь получается жёстко прошит в сгенерированных Makefile’ах), а в некоторых — он становится вот таким, «динамическим» ? Я пытался сравнить исходные configure.ac и Makefile.am — и так и не нашёл, что влияет на вид конечного Makefile.

Bass ★★★★★
() автор топика

Не знаю.

Если в документации ответа нет, предлагю написать этот вопрос автору изменений. Или кто там сейчас действующий мейнтейнер.

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

если тип сборки (обычная или VPATH) можно определить на этапе запуска configure.

А если нельзя? Вариант с test -f — универсальный, он сработает в любом случае. Надо оно тебе или нет — решай сам, autotools же просто «фреймворк».

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

Не так чтобы простые проекты, но что-то получилось. Установка по крайней мере одной из этих переменных (в любое значение, даже пустое):

foo_CFLAGS =
foo_CPPFLAGS =

превращает

gcc -DHAVE_CONFIG_H -I.     -g -O2 -MT foo.o -MD -MP -MF .deps/foo.Tpo -c -o foo.o foo.c

в

gcc -DHAVE_CONFIG_H -I.     -g -O2 -MT foo-foo.o -MD -MP -MF .deps/foo-foo.Tpo -c -o foo-foo.o `test -f 'foo.c' || echo './'`foo.c

Как можно заметить у объектный файлов дополнительно появился префикс приложения (foo-).

В depend2.am кстати есть рядом с test -f:

## For non-suffix rules, we must emulate a VPATH search on %SOURCE%.

Ещё из automake.in (оно из секции о info-файлах, но это тот же флаг вроде):

  # We can output two kinds of rules: the "generic" rules use Make
  # suffix rules and are appropriate when $source and $dest do not lie
  # in a sub-directory; the "specific" rules are needed in the other
  # case.
  #
  # The former are output only once (this is not really apparent here,
  # but just remember that some logic deeper in Automake will not
  # output the same rule twice); while the later need to be output for
  # each Texinfo source.

Generic правила в выходном Makefile не перечисляют именя файлов явно, а non-generic выписывают для каждого файла свои правила (при этом generic правила в выходном файле тоже есть). Каким боком ко всему этому флаги, я не понял. Может быть это баг.

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

Установка по крайней мере одной из этих переменных (в любое значение, даже пустое):

foo_CFLAGS =
foo_CPPFLAGS =

Спасибо тебе, добрый человек.

Попробовал – подтверждаю: добавление CFLAGS/CPPFLAGS действительно приводит к переходу из «generic»-режима в «specific»-режим.

Проблему можно считать решённой.

Bass ★★★★★
() автор топика
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.