调试 GNU make

发布于 2024-08-11 05:05:52 字数 50 浏览 4 评论 0原文

make 中是否有命令行方式来找出目标的哪些先决条件未更新?

Is there a command line way in make to find out which of the prerequisites of a target is not updated?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(7

风柔一江水 2024-08-18 05:05:52
make -d

应该为您提供更多足够的信息来调试您的 makefile。

请注意:分析输出需要一些时间和精力,但将输出加载到您最喜欢的编辑器中并进行搜索将有很大帮助。

如果指定您感兴趣的特定目标,则可以大大减少调试输出量。因此,如果您只对 dodgy 目标感兴趣,而不仅仅是 make -d< /code> 可能会产生一百种不同的东西,尝试一下:(

make clean
make -d dodgy

当然假设你有一个 clean 目标)。

make --debugmake -d 相同,但您也可以指定:

make --debug=FLAGS

其中标志可以是:

  • a 用于所有调试(与make -dmake --debug)。
  • b 用于基本调试。
  • v 用于稍微更详细的基本调试。
  • i 用于隐式规则。
  • j 用于调用信息。
  • m 获取 makefile 重制期间的信息。

看起来 make --debug=b 是满足您需求的最佳选择,如以下记录所示:

pax@paxbox> cat makefile
c:a b
    touch c

pax@paxbox> touch a b ; make
touch c

pax@paxbox> make
make: 'c' is up to date.

pax@paxbox> touch a ; make --debug=b
GNU Make 3.81
Copyright (C) 2006  Free Software Foundation, Inc. Blah, blah, blah.
Reading makefiles...
Updating goal targets....
 Prerequisite 'a' is newer than target 'c'.
Must remake target 'c'.
touch c
Successfully remade target file 'c'.
make -d

should give you more than enough information to debug your makefile.

Be warned: it will take some time and effort to analyze the output but loading the output into your favorite editor and doing searches will assist a lot.

You can greatly reduce the amount of debugging output if you specify the specific target you're interested in. So if you're only interested in the dodgy target, instead of just make -d which may make a hundred different things, try:

make clean
make -d dodgy

(assuming you have a clean target of course).

The make --debug is identical to make -d but you can also specify:

make --debug=FLAGS

where flags can be:

  • a for all debugging (same as make -d and make --debug).
  • b for basic debugging.
  • v for slightly more verbose basic debugging.
  • i for implicit rules.
  • j for invocation information.
  • m for information during makefile remakes.

It looks like make --debug=b is the best option for what you need, as shown in the following transcript:

pax@paxbox> cat makefile
c:a b
    touch c

pax@paxbox> touch a b ; make
touch c

pax@paxbox> make
make: 'c' is up to date.

pax@paxbox> touch a ; make --debug=b
GNU Make 3.81
Copyright (C) 2006  Free Software Foundation, Inc. Blah, blah, blah.
Reading makefiles...
Updating goal targets....
 Prerequisite 'a' is newer than target 'c'.
Must remake target 'c'.
touch c
Successfully remade target file 'c'.
画▽骨i 2024-08-18 05:05:52

您在寻找 Make 的“演练”吗?它会打印出 make 正在做什么,但实际上并不这样做,让您可以看到发生了什么。

该标志是-n,像make -n一样使用它。

Are you looking for Make's "dry run"? It will print out what make is doing without actually doing so, allowing you to see what happens.

The flag is -n, use it like make -n.

旧伤慢歌 2024-08-18 05:05:52

我通常做的不是像之前的回答者所说的那样使用 -d 。

我要么:

  1. 使用 -p 打印数据库,以查看已创建哪些规则。如果您有第二个扩展规则并且正在动态创建规则,尤其是递归 make,这会很方便。
  2. 大量使用 $(info) 函数。
  3. 使用 DrDobbs 文章 调试 Makefiles 中描述的提示和技巧,

下面是我的一些代码用于打印值:

define pv
$(info $(1) [$(origin $(1))] : >|$($(1))|<)
endef

define pva
$(foreach t,$(1),$(call pv,$(t)))
endef

define itemizer
$(foreach t,$($(1)),$(info $(t)))
endef

What I usually do is not go using -d as previous answerers said.

I either:

  1. Use -p to print the database, to see what rules have been created. This is handy if you have second expansion rules and are creating rules on the fly, especially recursive make.
  2. Heavy use of $(info) function.
  3. Use the tips and trick described in this DrDobbs article Debugging Makefiles

Below is some code I'm using for printing out values:

define pv
$(info $(1) [$(origin $(1))] : >|$($(1))|<)
endef

define pva
$(foreach t,$(1),$(call pv,$(t)))
endef

define itemizer
$(foreach t,$($(1)),$(info $(t)))
endef
舂唻埖巳落 2024-08-18 05:05:52

还有带有调试器和更好的跟踪/错误输出的 GNU make:Remake

这两个虽然仍然相关,但有点旧了。

There's also GNU make with a debugger and better trace/error output: Remake

Both of these, while still relevant, are a bit old.

贪了杯 2024-08-18 05:05:52

你的问题有点不清楚。如果你想查看哪些必备文件最近没有被修改,可以使用 ls -l 查看它们的修改时间。如果你想看看 make 正在做什么,试试这个:

# Make will announce when it is making this target, and why.
sometarget: preq1 preq2 preq3
    @echo making $@
    @echo The following preqs are newer than the target: $?
    do_things

Your question is a little unclear. If you want to see which prerequisite files have not been modified recently, use ls -l to see their modification time. If you want to see what make is doing, try this:

# Make will announce when it is making this target, and why.
sometarget: preq1 preq2 preq3
    @echo making $@
    @echo The following preqs are newer than the target: $?
    do_things
长不大的小祸害 2024-08-18 05:05:52

有几次我也使用过这个(旧但仍然有效)交互约翰·格雷厄姆·卡明 (John Graham-Cumming) 制作调试器

Few times I've also used this (old but still working) interactive make debugger by John Graham-Cumming

空城仅有旧梦在 2024-08-18 05:05:52

我正在使用 make gnu make 模板来定义每个目标的 make 规则;

模板就像编写规则的宏,这里对其进行了解释 https:// /www.gnu.org/software/make/manual/html_node/Eval-Function.html

当您的 make 系统包含一个核心 makefile 来生成每个项目类型的所有规则时,此功能非常有用;如果它说要做一个共享库,那么它会编写编译共享库的规则;对于其他类型的目标等。

在此示例中:如果将 SHOW_RULES=1 添加到 make 命令行,它还会显示由 PROGRAM_target_setup_template 生成的规则文本;以及生成规则本身(使用 eval)。

 # this one defines the target for real
 $(foreach prog, $(TARGETS), $(eval $(call PROGRAM_target_setup_template,$(prog))))

 ifneq "$(SHOW_RULES)" ""
 $(foreach prog, $(TARGETS), $(info $(call PROGRAM_target_setup_template,$(prog))))
 endif
  • $(call ... ) 调用模板
  • $(info ... ) 打印模板替换的结果; ( eval 会调用解析输出并添加到当前 make 文件中)

有关我的 make 文件的更多信息: http://mosermichael.github.io/cstuff/all/projects/2011/06/17/make-system.html

i am using make gnu make templates to define the make rules per target;

Templates are like macros that write rules, they are explained here https://www.gnu.org/software/make/manual/html_node/Eval-Function.html

this feature is useful when you have a make system that includes a core makefile to generate all rules per project type; if it says to do a shared library then it writes the rules to compile a shared library; etc. for other types of targets.

in this example: if you add SHOW_RULES=1 to the make command line it also shows the text of the rules that are generated by the PROGRAM_target_setup_template ; along with generating the rules themselves (with eval).

 # this one defines the target for real
 $(foreach prog, $(TARGETS), $(eval $(call PROGRAM_target_setup_template,$(prog))))

 ifneq "$(SHOW_RULES)" ""
 $(foreach prog, $(TARGETS), $(info $(call PROGRAM_target_setup_template,$(prog))))
 endif
  • $(call ... ) invokes the template
  • $(info ... ) prints the result of template substitution; ( eval would have invoked parsing of the output and addition to the current make file )

More about my make files here: http://mosermichael.github.io/cstuff/all/projects/2011/06/17/make-system.html

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文