Привязка к внешнему объектному файлу (.o) с помощью autoconf

#makefile #gnu #autotools #configure #autoconf

#makefile #gnu #автоинструменты #настройка #автоконфискация

Вопрос:

Для рабочих целей мне нужно связать с объектным файлом, сгенерированным другой программой и найденным в ее папке, дело в том, что я не нашел информации об этом виде связи. Я думаю, что если я жестко закодирую пути и поставлю name-of-obj.o перед package_LDADD переменной, должно сработать, но дело в том, что я не хочу делать это таким образом.

Если объект не найден, я хочу, чтобы настройка завершилась ошибкой, и сообщить пользователю, что name-of-obj.o отсутствует.

Я пытался с помощью AC_LIBOBJ([name-of-obj.o]) , но при этом будет предпринята попытка найти в корневом каталоге имя obj.c и скомпилировать его.

Есть какой-нибудь совет или решение по этой проблеме?

Спасибо!

Ответ №1:

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

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

Я думаю, что если я жестко закодирую пути и поставлю name-of-obj.o перед package_LDADD переменной, должно сработать, но дело в том, что я не хочу делать это таким образом.

Я так понимаю, что вы хотите избежать части «жестко закодировать пути». Добавление элемента в соответствующую LDADD переменную не подлежит обсуждению; это правильный способ включить ваш объект в ссылку.

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

Что ж, тогда, похоже, ключевым моментом является заставить configure выполнить поиск вашего объектного файла. Autoconf не имеет встроенного механизма для выполнения такого поиска, но это всего лишь генератор сценариев оболочки на основе макросов, поэтому вы можете написать такой поиск в shell script Autoconf, возможно, что-то вроде этого:

 AC_MSG_CHECKING([for name-of-obj.o])
OTHER_LOCATION=
for my_dir in
    /some/location/other_program/src
    /another/location/other_program.12345/src
    $srcdir/../relative/location/other_program/src; do
  AS_IF([test -r "${my_dir}/name-of-obj.o"], [
    # optionally, perform any desired test to check that the object is usable
    # ... perhaps one using AC_LINK_IFELSE ...
    # if it passes, then
    OTHER_LOCATION=${my_dir}
    break
  ])
done

# Check whether the object was in fact discovered, and act appropriately
AS_IF([test "x${OTHER_LOCATION}" = x], [
  # Not found
  AC_MSG_RESULT([not found])
  AC_MSG_ERROR([Cannot configure without name-of-obj.o])
], [
  AC_MSG_RESULT([${OTHER_LOCATION}/name-of-obj.o])
  AC_SUBST([OTHER_LOCATION])
])
  

Это функционально, но, конечно, вы могли бы приукрасить, например, предоставив конструктору пакетов указывать местоположение для использования с помощью аргумента командной строки ( AC_ARG_WITH(...) ). И если вы хотите сделать это для нескольких объектов, то вы, вероятно, захотите обернуть хотя бы часть этого в пользовательский макрос.

Сторона Automake задействована гораздо меньше. Чтобы связать объект, вам просто нужно добавить его в соответствующую LDADD переменную, используя созданную выше выходную переменную, такую как:

 foo_LDADD = $(OTHER_LOCATION)/name-of-obj.o
  

Обратите внимание, что если вы создаете только одну целевую программу, то вы можете использовать general LDADD вместо foo_LDADD , но обратите внимание, что по умолчанию это альтернативы, а не дополнения.


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

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