c - Makefile递归不传递CPPFLAGS

标签 c variables makefile build-process gnu-make

首先,如果我最终发布的帖子太长,我深表歉意,但我认为否则会丢失信息。

我想在每个构建中包含我的存储库版本。 有一个主要的 makefile,它控制着各自子目录中的其他一些。 子项目是“自动生成的”。

我正在尝试将包含 svnversion 的变量传递给内部 Makefiles,如下所示:

# Main Makefile

SUBDIRS = sd1 sd2
REPO_VERSION = `svnversion`
export ECHO = @echo
export CPPFLAGS

all: versioned
    $(ECHO) "Build of all projects in $(PWD) finished."

clean :
    $(ECHO) "Cleaning up entire project tree..."
    -for d in $(SUBDIRS); do ($(ECHO) "Cleaning up \"$$d\""; $(MAKE) -C $$d clean ); done

.PHONY: versioned unversioned $(SUBDIRS)

versioned:  CPPFLAGS = -DREPO_VERSION=\"v$(REPO_VERSION)\"

versioned:  subdirs

unversioned:    subdirs

versioned unversioned:
    $(ECHO) "Build $@ finished."

subdirs: $(SUBDIRS)

$(SUBDIRS):
    $(ECHO) "== Building $@                      =="
    $(ECHO) "    [ CPPFLAGS = \"$(CPPFLAGS)\" ]"
    ( cd $@ && \
        ( [ -f Makefile ] || \
            ( aclocal       && \
            autoheader  && \
            automake --foreign --add-missing && \
            autoconf    && \
            configure ) )   && \
        $(MAKE) \
        )

每个子目录都有一个 Makefile.amconfigure.ac,如下所示:

Makefile.am:

# Makefile.am in "sd1" and "sd2"

bin_PROGRAMS = app
app_SOURCES = source.c

configure.ac:

AC_PREREQ(2.59)

AC_INIT([app], [1.00], [<suport@domain>])
AM_INIT_AUTOMAKE

AC_CONFIG_HEADER([config.h])

# Checks for programs.
AC_PROG_CC
AC_PROG_CPP
AC_PROG_INSTALL
AC_PROG_LN_S
AC_PROG_MAKE_SET

# Checks for header files.
AC_HEADER_STDC

# Checks for typedefs, structures, and compiler characteristics.
AC_C_CONST
AC_TYPE_SIZE_T

# Output configuration files.
AC_CONFIG_FILES([Makefile])
AC_OUTPUT

我预计这会起作用,但是 autotools 在运行时将 REPO_VERSION 嵌入到 makefile 中,并且在进一步构建中忽略主 Makefile 的 REPO_VERSION 中的更改。

一段输出看起来像这样:

== Building sd1                      ==
    [ CPPFLAGS = "-DREPO_VERSION="1050"" ]
( cd sd1 && \
        ( [ -f Makefile ] || \
                ( aclocal               && \
                autoheader      && \
                automake --foreign --add-missing && \
                autoconf        && \
                configure ) )   && \
        make \
        )
make[1]: Entrando no diretório `./recursive/sd1'
make  all-am
make[2]: Entrando no diretório `./recursive/sd1'
gcc -DHAVE_CONFIG_H -I.   -DREPO_VERSION=\"1049M\"  -g -O2 -MT source.o -MD -MP -MF .deps/source.Tpo -c -o source.o source.c
mv -f .deps/source.Tpo .deps/source.Po
gcc  -g -O2   -o app source.o
make[2]: Saindo do diretório `./recursive/sd1'
make[1]: Saindo do diretório `./recursive/sd1'

程序输出:

> ./sd1/appVersão = [1049M].

这显然不是我想要的。

这里有人可以提供解决此问题的方法吗?

谢谢。

最佳答案

在你的顶级make文件中添加

export REPO_VERSION

并修改每个 Makefile.am 以具有

REPO_VERSION ?= unknown
AM_CPPFLAGS = -DREPO_VERSION="$(REPO_VERSION)"

export 指令使得 REPO_VERSION 的值被导出到递归 make 调用。 Makefile.am 片段为 REPO_VERSION 设置默认值(如果未给出)(例如,make 从子目录中的 shell 运行)并且 AM_CPPFLAGS 为该 Makefile 中的所有目标指定默认值 CPPFLAGS。如果您有特定于目标的 _CPPFLAGS 变量,您应该向其中添加 $(AM_CPPFLAGS) 或在其中包含 -DREPO_VERSION="$(REPO_VERSION)"。通过更多的努力,您可以将一些内容添加到 configure.ac 文件中,以便可以在配置时设置 REPO_VERSION 的默认值。

关于c - Makefile递归不传递CPPFLAGS,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9262931/

相关文章:

Java Makefile 输出单个可执行文件

c - C 中的简单 nginx if 语句

c++ - 构建小型中小企业客户端的未定义引用

c - 我不明白这个简单的循环如何改变文件指针位置

c# - C#变量UserInput找不到定义

javascript - 是否可以在 JavaScript 函数内从调用者的作用域访问变量?

cross-platform - 可移植 makefile 创建目录

c - 用于 Linux 的 C 语言示例 NPAPI 插件

php - 如何限制mysql中number的最大值?

c++ - 将选定的文件传递给 Eclipse 中的 Make 目标