2016-09-07 9 views
0

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

Моя цель - создать libfile.a для распространения как статической библиотеки. Дерево проекта выглядит следующим образом:

project 
    | 
    +-src 
     +- <some cpp and hpp files> 
     | 
     + containers 
      | 
      +- <other cpp and hpp files> 

Я легко создать configure.ac файл и Makefile.am с. Структура дерева изменилась следующим образом:

project 
    | 
    +- configure.ac 
    +- Makefile.am 
    +-src 
     +- <some cpp and hpp files> 
     + Makefile.am 
     | 
     + containers 
      | 
      +- <other cpp and hpp files> 

Теперь, когда я иду: (*)

aclocal; autoreconf --install; autoconf; ./configure 
make 

.o files генерируются для всех .*pp files, содержащиеся в src, но терпит неудачу, когда он начинает генерировать эти цели в src/containers , Таким образом, Makefile не генерируется должным образом. Что я делаю не так? Кто-нибудь может мне помочь?

PS здесь есть файлы, связанные:

# --- configure.ac --- 

AC_PREREQ([2.68]) 
AC_INIT([filea], [1.0], [[email protected]]) 
AM_INIT_AUTOMAKE([filea], [1.0]) 
AC_CONFIG_SRCDIR([src/HashFunctions.cpp]) 
AC_CONFIG_HEADERS([config.h]) 

AC_PROG_CXX 
AC_PROG_RANLIB 

AC_CHECK_HEADERS([stddef.h stdint.h string.h]) 
AC_HEADER_STDBOOL 

AC_C_INLINE 
AC_TYPE_SIZE_T 
AC_TYPE_UINT16_T 
AC_TYPE_UINT32_T 
AC_TYPE_UINT8_T 

AC_FUNC_MALLOC 
AC_FUNC_MKTIME 
AC_CHECK_FUNCS([memset]) 

AC_OUTPUT([Makefile src/Makefile]) 

# --- Makefile.am --- 

AUTOMAKE_OPTIONS = foreign 
SUBDIRS = src 


# --- src/Makefile.am --- 

lib_LIBRARIES = libfile.a 
libfile_a_SOURCES = \ 
    ConfigLib.hpp \ 
    ConfigLib.cpp \ 
    HashFunctions.cpp \ 
    HashFunctions.hpp \ 
    Logger.hpp \ 
    Logger.cpp \ 
    Queue.hpp 

libfile_a_SOURCES += \ 
    containers/SafeContainer.cpp \ 
    containers/SafeInterger.cpp \ 
    containers/SafeMap.cpp 

EDIT 1 как предложено Brett Hale команды, помеченные (*) были заменены на следующие:

autoreconf -fvi 

Выход:

autoreconf: Entering directory `.' 
autoreconf: configure.ac: not using Gettext 
autoreconf: running: aclocal --force 
autoreconf: configure.ac: tracing 
autoreconf: configure.ac: not using Libtool 
autoreconf: running: /usr/bin/autoconf --force 
autoreconf: running: /usr/bin/autoheader --force 
autoreconf: running: automake --add-missing --copy --force-missing 
autoreconf: Leaving directory `.' 

При переходе с:

./configure 
make 

Еще нет правил не найдено для генерации цели в подкаталоге.

EDIT 2 я переключился на нерекурсивна подход (спасибо Karel Zak's blog) и, наконец, я могу make мой LIB.

+0

Можете ли вы попробовать использовать: 'autoreconf -fvi' вместо' aclocal; ....; 'команды? –

+0

Могу ли я предложить исследовать [SCons] (http://scons.org), [CMake] (https://cmake.org) и другие системы сборки - даже простые [make] (https: //www.gnu. org/software/make /) - * ничего *, но ужас, который является 'autoconf' /' automake' ... –

+0

@JesperJuhl - да, cmake начинался с чистых намерений ... только чтобы найти, что это * проблемы и эффективно изобретать колесо без 20-летнего опыта работы с автотелами - наряду с синтаксисом, используемым нигде больше - в отличие от bash/m4. –

ответ

0

Все еще я не знаю, что я делал неправильно, следуя типичным recursive approach; но, наконец, я сделал эту работу, перейдя на non-recursive approach (как я писал в EDIT 2). This article в блоге Karel Zak мне очень помог!

# -- new configure.ac file -- 
AC_PREREQ([2.68]) 
AC_INIT([filea], [1.0], [[email protected]]) 
AM_INIT_AUTOMAKE([filea], [1.0]) 
AC_CONFIG_HEADERS([config.h]) 
AC_CONFIG_SRCDIR([src/HashFunctions.cpp]) 

AM_INIT_AUTOMAKE([filea], [1.0]) 
LT_INIT 

AC_CANONICAL_HOST 
AC_PROG_LIBTOOL 
AC_PROG_GREP 
AC_PROG_EGREP 
AC_PROG_CXX 
... 
AC_HEADER_STDBOOL 
AC_C_INLINE 
AC_TYPE_PID_T 
AC_TYPE_SIZE_T 
AC_TYPE_SSIZE_T 
AC_TYPE_UINT8_T 
AC_TYPE_UINT16_T 
AC_TYPE_UINT32_T 

AC_FUNC_ERROR_AT_LINE 
AC_FUNC_FORK 
AC_FUNC_MALLOC 
AC_FUNC_MKTIME 
AC_CHECK_FUNCS([memset socket]) 

AC_OUTPUT([Makefile]) # the makefile is only one! 
         # In the subdirectory I have created few 
         # Makemodule.am included in the "main makefile.am" 

# --- makefile.am --- 
AUTOMAKE_OPTIONS = foreign 
lib_LIBRARIES = filea.a 

libfilea_a_SOURCES = 
include src/Makemodule.am 
include src/containers/Makemodule.am # now filea_a_SOURCES is a 
            # "global variable" 
# -- src/Makemodule.am 
libfilea_a_SOURCES += \ 
    src/ConfigLib.hpp \ 
    src/ConfigLib.cpp \ 
    src/HashFunctions.cpp \ 
    src/HashFunctions.hpp \ 
    src/Logger.hpp \ 
    src/Logger.cpp \ 
    src/Queue.hpp 

# -- src/containers/Makemodule.am 
libfile_a_SOURCES += \ 
    src/containers/SafeContainer.cpp \ 
    src/containers/SafeInterger.cpp \ 
    src/containers/SafeMap.cpp 

Обратите внимание, что теперь, даже если Makemodule.am файлы размещаются на разных уровнях в дереве дир всякий раз, когда имя файла набирается в одном этих модулей, он должен предшествовать ее относительный путь. Этот путь относится к местоположению Makefile.