2009-11-17 133 views
61

make中是否有命令行方式來找出目標的哪些先決條件未更新?調試GNU make

+0

是不是有像詳細模式?難道你不能在每個目標上進行一些'echo'調試來弄清楚嗎? – Earlz 2009-11-17 00:58:48

回答

85
make -d 

應該給你足夠多的信息調試你的makefile。

被警告:分析輸出需要花費一些時間和精力,但將輸出加載到您喜歡的編輯器中,並且執行搜索將有很大幫助。

可以大大減少調試輸出量,如果你指定你感興趣的特定目標。因此,如果你只在dodgy目標感興趣,而不是僅僅make -d這可能使一百個不同的東西,嘗試:

make clean 
make -d dodgy 

(假設你有一個clean目標當然)。

make --debug是相同的make -d但你也可以指定:

make --debug=FLAGS 

其中標誌可以是:

  • a所有調試(同make -dmake --debug)。
  • b進行基本調試。
  • v稍微更詳細的基本調試。
  • i隱式規則。
  • j用於調用信息。
  • m在makefile重製期間獲取信息。

看起來make --debug=b是你需要什麼是最好的選擇,因爲顯示在下面的成績單:

[email protected]> cat makefile 
c:a b 
    touch c 

[email protected]> touch a b ; make 
touch c 

[email protected]> make 
make: 'c' is up to date. 

[email protected]> 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'. 
+4

另一個建議是,如果你想擺脫內建的隱式規則,你可以使用'-r'標誌和'-d'一起。 – 2009-11-17 15:07:26

17

您是否在尋找製作的「預演」?它會打印出製作過程中沒有做的事,讓你看到會發生什麼。

該標誌是-n,使用它就像make -n

+0

這是我最喜歡的,'-d'太冗長了(甚至是'--debug = b')。特別是如果你堅持遞歸make(唉!)。 – 2011-07-13 13:34:20

7

你的問題有點不清楚。如果您想查看哪些先決條件文件最近未被修改,請使用ls -l來查看它們的修改時間。如果你想看到什麼使正在做,試試這個:

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

我打算建議$?以及 – 2009-11-17 01:22:51

+0

不是一個真正的命令行解決方案,但仍然有用。只有在設置了env-var的情況下,纔可以通過僅執行回顯來使其成爲命令行。 – paxdiablo 2009-11-17 01:34:20

1

幾聲我也使用this(舊的但仍然有效)交互式調試器作者:John Graham-Cumming

5

我通常所做的並不是像前面的回答者那樣使用-d。

我可以:

  1. 使用-p打印的數據庫,看規則已經創造了什麼。如果您有第二個擴展規則並且正在創建規則,那麼這非常方便,特別是遞歸make。
  2. 大量使用$(info)函數。
  3. 使用此DrDobbs文章Debugging 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 
0

我使用GNU使使模板定義按目標制定規則;

模板都是這樣寫的規則宏,他們在這裏https://www.gnu.org/software/make/manual/html_node/Eval-Function.html

當你有化妝系統,包括核心的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 
  • $(叫...)調用模板
  • $(信息...)打印模板替換的結果; (EVAL會調用輸出和另外的分析當前的make文件)

更多關於我的make文件在這裏:http://mosermichael.github.io/cstuff/all/projects/2011/06/17/make-system.html