如何使用 autotools 构建静态和共享库?

问题描述

我正在学习使用 Autotools。我正在用这些工具编写我的第一个程序,但是我遇到了一个问题。我正在尝试制作使用两个库的程序:一个是静态的,一个是共享的。我配置了 Makefile.amconfigure.ac,但我不知道它们是否应该如此。当我运行命令 make 时,它返回一个错误

code.c:37: undefined reference to `function1'.

它为每个函数都给出了这样的错误。程序好像找不到头文件或源文件

我所有的文件都在一个文件夹中。

configure.ac

AC_PREREQ([2.69])
AC_INIT([code],[1.0])
LT_INIT
AM_INIT_AUTomake
AC_CONfig_SRCDIR([code.c])
AC_CONfig_MACRO_Dirs([m4])
AC_PROG_CC 
AC_CHECK_HEADERS([stdio.h])
AC_CONfig_FILES([Makefile])
AC_OUTPUT

Makefile.am

ACLOCAL_AMFLAGS = -I m4

bin_PROGRAMS = code
code_SOURCES = code.c libcodes.la libcode.a libo.h libp.h

lib_LIBRARIES = libcode.a
libcode_a_SOURCES = functionsp.c

code_DEPENDENCIES = libcodes.la
lib_LTLIBRARIES = libcodes.la
libcodes_la_SOURCES = functionso.c
libcodes_la_LDFLAGS = -version-info 1:0:0
code_LDFLAGS = -rpath /usr/local/lib

解决方法

程序似乎找不到头文件或源文件?

不,“未定义的引用”是链接错误。这意味着链接器正在尝试解析函数调用,但它没有看到该函数的任何实现。这通常意味着链接命令行上指定的库存在问题。

实际上,您的 Makefile.am 中与链接相关的设置都是错误的,并且还有其他影响较小的问题。

首先,链接程序所需但未通过 configure 定位的库应通过 Makefile.am 变量或程序特定的 LDADD 变量在 foo_LDADD 中指定。 foo_DEPENDENCIES 变量不用于此目的——它的内容出现在生成的 makefile 中作为程序目标的依赖项,但没有其他地方。特别是,它们不包含在链接命令行中。实际上,foo_DEPENDENCIES 变量很少使用。

尤其不应将库指定为程序源。它们不是来源,因此指定它们没有任何有用的效果。

说到库,将假定的库安装目录硬编码到您的 Makefile.am 中是一种糟糕的形式,并且会为自己设置问题,因为该目录可以由用户在 configure 和/或 {{ 1次。幸运的是,每个可配置的安装目录都有一个相应的变量供您参考。在 make 的情况下,它是 lib

此外,就风格而言,您似乎围绕构建阶段组织了 libdir,但这是不寻常的,至少我觉得很难遵循。 Makefile.am 文件通常围绕命名的目标组织,通常首先指定所有这些目标。

总的来说,你可能想要更像这样的东西:

Makefile.am