5.編寫recipe

ignorantshr發表於2019-01-06

本系列文章均翻譯自make官方文件:make Manual,github同步專案:question

使用者使用不同的shell程式,但是在makefiles總是使用/bin/sh執行recipe,除非makefile指定了其它的shell。

recipe語法

Makefile有兩種語法:make語法和shell語法。make不會去理解shell語法,執行簡單的翻譯就交給shell去處理。recipe使用的是shell語法。

每個recipe所在行都要有tab開頭,除了第一行recipe可能會被附加到目標行(分號隔開)。

分割recipe行

例1:

all :
        @echo no\
space
        @echo no\
        space
        @echo one \
        space
        @echo one\
         space

輸出:

nospace
nospace
one space
one space

例2:

all : ; @echo 'hello \
        world' ; echo "hello \
    world"

輸出:

hello \
world
hello     world

想要使用單引號,並且不想出現\,那麼可以將其轉換為make變數:

HELLO = 'hello \
world'

all : ; @echo $(HELLO)

輸出:

hello world

在recipes中使用變數

不會重新構建的目標不會被擴充套件,即不會呼叫新的recipe。

如果想要$出現在recipe中,必須鍵入兩個引用:$$

LIST = one two three
all:
        for i in $(LIST); do \
            echo $$i; \
        done

recipe輸出

正常情況下make在執行recipe之前會列印它。

如果recipe前加上了@符號,就不會列印recipe,當傳給shell處理的時候該符號會被丟棄掉。

給make-n--just-print的flag時候,只會輸出大部分recipe而不執行,帶有@符號的行也會被列印出來。

flag-s--silent會阻止echoing,就像所有的行都加了@符號。

recipe執行

執行recipe時,每行recipe都會呼叫一個新的sub-shell來執行,除非定義.ONESHELL特殊目標。所以本行的shell變數和諸如cd的目錄不會影響後續的recipe。

make的遞迴使用

意思就是在makefile檔案中使用make作為命令。當你現要為子系統分離makefile的時候很有用。

subsystem:
        cd subdir && $(MAKE)

相關文章