AC_OUTPUT 简介
AC_OUTPUT
是 GNU Autoconf 工具中的一个关键宏,用于指定 configure 脚本最终应该生成哪些输出文件。AC_OUTPUT
是 Autoconf 自动化构建系统的核心部分之一,但需要注意的是,在较新版本的 Autoconf 中,它已被 AC_CONFIG_FILES
系列宏所取代。
基本用法
AC_OUTPUT([file...], [extra-cmds], [init-cmds])
- file…: 要生成的文件列表,通常以
.in
结尾的文件为模板 - extra-cmds (可选): 生成文件后要执行的额外命令
- init-cmds (可选): 初始化命令,在生成文件前执行
典型示例
AC_OUTPUT([Makefile src/Makefile config.h])
这表示 configure 脚本将从 Makefile.in
, src/Makefile.in
和 config.h.in
生成相应的输出文件。
工作原理
- configure 脚本会查找
.in
文件作为模板 - 替换模板中的变量(如
@VARIABLE@
)为实际值 - 生成最终输出文件
现代替代方案
在现代 Autoconf 中,推荐使用更专门的宏替代 AC_OUTPUT
:
AC_CONFIG_FILES
: 用于生成普通文件(如 Makefile)AC_CONFIG_HEADERS
: 专门用于生成 config.h 等头文件AC_CONFIG_LINKS
: 用于创建符号链接
例如,上面的例子可以改写为:
AC_CONFIG_FILES([Makefile src/Makefile])
AC_CONFIG_HEADERS([config.h])
AC_OUTPUT
注意事项
- 在 Autoconf 2.50 及以后版本中,
AC_OUTPUT
可以不带参数使用,前提是已经使用了上述AC_CONFIG_*
宏 - 模板文件通常以
.in
为后缀 - 替换的变量形式为
@VARIABLE_NAME@
AC_OUTPUT
通常是configure.ac
文件的最后一个宏
历史背景
AC_OUTPUT
是 Autoconf 早期的核心输出宏,随着 Autoconf 的发展,其功能被分解为更专门的宏。虽然它仍然被支持且广泛使用,但在新项目中推荐使用更现代的 AC_CONFIG_*
系列宏。
与 AC_CONFIG_FILES 的关系
AC_OUTPUT
和 AC_CONFIG_FILES
的主要区别在于:
AC_CONFIG_FILES
更模块化,可以在 configure.ac 中多次调用AC_OUTPUT
通常是集中式的,一般在文件末尾调用一次- 现代实践中,先用
AC_CONFIG_FILES
等宏声明输出文件,最后用无参的AC_OUTPUT
结束
直接使用无参 AC_OUTPUT
的行为概述
在 Autoconf 2.50 及以后的版本中,如果直接调用 AC_OUTPUT
而不带任何参数,其行为如下:
默认行为
自动收集所有已声明的输出文件:
- 会包含所有之前通过
AC_CONFIG_FILES
、AC_CONFIG_HEADERS
和AC_CONFIG_LINKS
宏指定的文件 - 例如:
AC_CONFIG_FILES([Makefile]) AC_CONFIG_HEADERS([config.h]) AC_OUTPUT # 将生成 Makefile 和 config.h
- 会包含所有之前通过
执行标准输出生成过程:
- 处理所有收集到的文件模板(.in 文件)
- 执行变量替换(将
@VAR@
替换为实际值) - 生成最终输出文件
使用场景
这种无参形式是现代 Autoconf 的推荐用法,因为它:
- 使
configure.ac
更模块化 - 允许在不同位置声明输出文件
- 更清晰地分离文件声明和输出阶段
注意事项
旧版本兼容性:
- 在 Autoconf 2.50 之前,
AC_OUTPUT
必须带参数 - 无参调用会导致错误
- 在 Autoconf 2.50 之前,
必须至少有一个输出声明:
- 如果没有使用任何
AC_CONFIG_*
宏就调用无参AC_OUTPUT
,configure 脚本会报错 - 错误示例:
# configure.ac 中只有这一行: AC_OUTPUT # 错误:没有指定任何输出文件
- 如果没有使用任何
典型现代用法:
# 在文件各处声明需要的输出 AC_CONFIG_HEADERS([config.h]) AC_CONFIG_FILES([Makefile src/Makefile tests/Makefile]) # 其他配置... # 最后生成所有输出 AC_OUTPUT
这种设计使得 Autoconf 配置更加灵活和可维护,是当前推荐的做法。