本文介绍了用gnu make正确构建一个git子模块的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我目前正在尝试编写一个Makefile,以正确构建一个包含git子模块的项目.该子模块具有自己的一组makefile,并一次生成多个目标,包括一些库.

I currently try to write a Makefile that build properly a project which contains a git submodule. This submodule have its own set of makefiles and produce several targets at once, including some libraries.

此Makefile应该具有以下属性.

This Makefile should have the following properties.

  • 即使使用并行构建,也不要重建两次子模块.
  • 在子模块代码已更改时更新子模块目标(也许因为我浏览了主存储库的修订版.
  • 子模块库更改后,重新链接主项目.
  • 请勿在顶级项目中复制粘贴子模块的Makefile(即保持Makefile递归).
  • Don't rebuild twice the submodule even with parallel build.
  • Update the submodule targets when the submodule code has changed (maybebecause I navigated through the revisions of the main repository).
  • Re-link the main project when the submodule library have changed.
  • Don't copy-paste the Makefiles of the submodule in the top-level project (i.e. keep the Makefiles recursive).

仅是设定想法,这似乎是可行的.

Just to set the ideas, here is something that seems to work.

FOO_SUBDIR := $(CURDIR)/foo
LDFLAGS := -L$(FOO_SUBDIR)

FOO_LIBSFILES := $(FOO_SUBDIR)/libfoo.a $(FOO_SUBDIR)/libgnufoo.a
FOO_LDLIBS := -lfoo -lgnufoo


.PHONY: all
all: main

# There are theoretically 3 main binaries
main: main.c $(FOO_LIBSFILES)
    gcc -o $@ $< $(LDFLAGS) $(FOO_LDLIBS)

$(FOO_LIBSFILES): libfoo
    @# Do nothing

.PHONY: libfoo
libfoo:
    $(MAKE) -C $(FOO_SUBDIR)

我似乎添加了空食谱,但我不明白为什么.

It seems to work sice I added the empty recipe, but I don't understand why.

想法是始终依靠子模块的Makefile来重建(或不重建)libfoo.alibgnufoo.a,并让主Makefile决定是否需要重建main.没有空的配方,它将无法正常工作.修改foo/foo.c时,将重建libfoo.a,但make不会重建main.

The idea is to always rely on the submodule's Makefile to rebuild (or not) libfoo.a and libgnufoo.a, and let the main Makefile decide whether main need to be rebuilt. Without the empty recipe it doesn't work. When a foo/foo.c is modified, then libfoo.a is rebuilt, but make doesn't rebuild main.

我有一种空的配方力量可以检查目标文件的日期的感觉.但是我找不到有关此行为的文档.

I have the feeling that the empty recipe force make to check the date of the target files. But I can't find documentation about this behavior.

这是正确的方法吗?我应该注意的任何陷阱?有什么更晦涩的方法可以做到这一点吗?或有关此行为的任何文档?

Is this the right way to go? Any pitfall I should be aware of? Any less obscure way to do this? Or any documentation about this behavior?

谢谢.

推荐答案

您的解决方案通常是正确的-在您的顶层Makefile中,添加了可用于子项目的目标.这是通过独立的子文件处理独立(子)项目的唯一正确方法.

Your solution is correct in general - in your toplevel makefile you've added targets that works the subproject. It is the only proper way to work with a standalone (sub-)project, via its own makefile.

您要询问的特定问题与不终止依赖libfoo的规则有关,并且GNU make要求规则具有命令,即使它是无操作的也是如此.改为执行此操作:

The specific problem you are asking about has to do with not terminating the libfoo dependent rule, and GNU make requires a rule to have commands, even if it is a no-op. Do this instead:

$(FOO_LIBSFILES): libfoo ;

这实际上是相同的无操作,但是更惯用.

This is effectively the same no-op, but more idiomatic.

这篇关于用gnu make正确构建一个git子模块的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

07-25 05:35