通常我們編譯程式時有很多算是每個人都有的共同習慣,例如我就是把 foo.c 編成foo.o。像這樣的編譯習慣,gnu make有一些內定規則來編譯, 也就是有的target你不寫,make也可以根據內定規則把他編譯出來。不用 對每個不同的.o寫不同的規則, 如果有個程式由foo.c foo1.c foo2.c......寫這些就寫得會發瘋了,例如
foo.o:foo.c gcc -c -o foo.o foo.c foo1.o:foo1.c gcc -c -o foo1.o foo1.c .... |
C程式 $(CC) -c $(CPPFLAGS) $(CFLAGS) xxx.c來編譯 或者找不到.c時會去找.cc, .cpp, .C檔 C++程式 $(CXX) -c $(CPPFLAGS) xxx.cpp TeX xxx.dvi 由xxx.tex產生 Pascal $(PC) -c $(PFLAGS) xxx.p |
因為可能有的時候你希望做些dependency檢查,或者加上一些gcc 用的旗標,不是很單純的編譯而已你可以給make自訂的內隱規則
自訂規則
你可以用pattern rule來做一些自定的內隱規則。像這樣
%.o : %.c prog.h $(CC) $(CFLAGS) $(DEBUG_FLAG) -c -o $@ $< |
%.pdf : %.sgml db2pdf $< |
pattern rule也可以有特定變數設值,特定樣式(pattern)的變數,例如
%.o : CFLAGS = -O |
還有更古老的一種叫suffix rule的方法來做,這種方法就有限制性 了,因為只能用在副檔名的規則。例如
.c.o: $(CC) -c -o $*.o $< .S.o: $(CC) -c -o $*.o $< |
因為這樣動態的編譯手法,它需要像在CVS裡面的%v %V %s這種東西來代替一些 動態改變的字串(幫你複習一下CVS)。所以有所謂的自動變數
$@ 同一個規則的目標名 $* 這個只有在內隱規則中有用。表示樣式或副檔名規則中對應到的字串。 $< 同一規則的第一個先決條件名,這個大部分用在suffix rule,因為 suffix rule只有一個檔。 $? 同一個規則的所有先決條件名,但是只有原始程式碼改過的比obj檔新才會 符合,也就是比target還新的先決條件檔案。 $^ 所有先決條件,但是有的make像solaris make可能不認得這個自動變數。 |
內隱規則內也預設了一些變數,例如
AR = ar CC = cc MAKE = make CXX = g++ |