Autotools:如何设置全局编译标志

Posted

技术标签:

【中文标题】Autotools:如何设置全局编译标志【英文标题】:Autotools : how to set global compilation flag 【发布时间】:2010-09-24 08:08:57 【问题描述】:

我有一个包含多个源目录的项目:

src/A
   /B
   /C

在每个 Makefile.am 中都包含

AM_CXXFLAGS = -fPIC -Wall -Wextra

如何避免在每个源文件夹中重复此操作?

我尝试修改 src/Makefile.am 和 configure.in,但没有成功。我以为我可以使用 AC_PROG_CXX 全局设置编译标志,但找不到太多关于如何使用这些宏的文档(您有任何指向此类文档的指针吗?)。

提前致谢

【问题讨论】:

【参考方案1】:

你可以做几件事:

(1) 一种解决方案是在您的所有 Makefile.ams 上包含一个通用的 makefile 片段:

include $(top_srcdir)/common.mk
...
bin_PROGRAMS = foo
foo_SOURCES = ...

在这种情况下你会写

AM_CXXFLAGS = -fpic -Wall -Wextra

common.mk,将来只需编辑此文件即可更轻松地向所有Makefile.ams 添加更多宏或规则。

(2) 另一种解决方案是在您的configure.ac 中全局设置这些变量(名称configure.in 早已被弃用),如:

...
AC_SUBST([AM_CXXFLAGS], [-fpic -Wall -Wextra])
...

那么你甚至不必在你的Makefile.ams 中说任何东西,它们会自动继承这个全局定义。缺点是您不能轻易选择退出(使用第一个解决方案很容易决定不包含common.mk)并且依赖关系对于第三方人员来说并不是很明确(当他们阅读Makefile.am时他们有没有提示标志可能来自哪里)。

(3) 第三种解决方案是按照orsogufo 的建议:覆盖configure.ac 中的用户变量CXXFLAGS。我建议不要这样做,因为它破坏了 GNU 构建系统的一项功能:允许用户在 make-time 覆盖此变量。例如,您可能想要输入

make CXXFLAGS='-O0 -ggdb' 

在调试一段代码时,这将覆盖CXXFLAGS 的任何定义(但 不是AM_CXXFLAGS 中的那些)。老实说,大多数项目都无法正确支持这一点,因为它们与CXXFLAGS 开玩笑。

最后,我应该提到-fpic-Wall-Werror 不是可移植选项。 根据您的项目范围,您可能希望为这些添加配置检查(gnulib 最近获得了新的宏来测试警告标志,libtool 可用于构建共享库)。

【讨论】:

在 Makefile.am 中使用 include 习惯用法会使 automake 输出 Makefile 和 Makefile.in 的依赖关系,最终返回到包含文件和 automake 文件。因此,更改此设置也会导致稍后更新。 如果您对标志进行 AC_SUBST,实际上很容易选择退出。在 Makefile.am 中,如果您分配 AM_CPPFLAGS,它们会覆盖。您可以通过什么都不做来选择加入,或者通过执行 AM_CPPFLAGS = @AM_CPPFLAGS@ ...,或者通过不将 @AM_CPPFLAGS@ 放入作业中来选择退出。 警告标志并不像您声称的那样属于 CPPFLAGS,因为它们是由编译器而不是预处理器使用的。 我是否遗漏了什么,或者AC_SUBST 是否需要在多个标志周围加上引号'',以避免在运行configure 时出现shell 错误?【参考方案2】:

在 configure.ac 中使用 EXTRA_CFLAGS

例如你的情况是这样的:

EXTRA_CFLAGS=-fPIC -Wall -Wextra

【讨论】:

以上是关于Autotools:如何设置全局编译标志的主要内容,如果未能解决你的问题,请参考以下文章

如何在 c++ Autotools 项目中使用不同版本的 g++ 进行编译

autotools,如果找不到交叉编译器,如何失败

如何让 autotools 使用英特尔编译器进行编译?

CMake:隐藏子目标的-WShadow全局编译标志

如何使用 Autotools 生成的 Makefile 在 Vim 中编译单个 C 文件

Autotools:将 -D 与变量一起使用适用于除一个编译之外的所有编译(C 编程)