!!! Makefileのごく簡単な解説 Makefileは,一見すると複雑ですが,ルールさえ分かれば構造は単純です. !! Makefileの基本構造 6< 8< (作りたいもの): (その元になる材料) __[TAB]__(実際の作り方) <-- 先頭が空白ではなくTAB >8 >9 (作りたいもの) の後にコロン(:)を書き,続いて(その元になる材料)を記述します. 次の行に,'''先頭にTAB''',続いて(実際の作り方)を記述します. ! 具体例 main.c,sub.cの二つのソースファイルから exe という実行バイナリを作成するには, 8< % gcc main.c sub.c -o exe >8 とすることは既に習っていると思いますが,これでは,どちらか一方のソースだけを修正した場合でも 両方をコンパイルし直さなければなりません. したがって,普通は 8< % gcc -c main.c % gcc -c sub.c % gcc main.o sub.o -o exe >8 のように,別々に'''オブジェクトファイル'''を生成して,最後にリンクします. さて,ソースファイルの数が増えてくると(例えば,20個とか),これらを手動で入力・管理していくことが面倒になります (し,間違いのもとにもなります).そこで,Makefileを利用します. 6< 8< exe: main.o sub.o gcc -o exe main.o sub.o main.o: main.c gcc -c main.c sub.o: sub.c gcc -c sub.c >8 * gccの前はTABであることに注意しましょう. >9 makeコマンドは, 8< % make (作りたいもの) >8 として実行するのが基本ですが,(作りたいもの)を省略した場合には,一番最初の(作りたいもの)が作成されます.つまり, 8< % make >8 とすれば,exeを作成することになります. この際,makeコマンドは,exeの元材料であるオブジェクトファイル(main.o と sub.o)を使って,gcc -o exe main.o sub.oを実行しようとします. ただし,main.o,sub.o についても,それぞれMakefileに材料と作り方が記述されていますので,次のような順序で動作します. * まず,main.oとmain.cのタイムスタンプを比較して,main.oの方が古ければ(main.cに編集が加えられていうことになるので)gcc -c main.cを実行してmain.oを作り直します.もちろん,main.oが存在しないときも同様にコンパイルされます. * sub.oとsub.cについても同様に動作します.(もしsub.cが編集されていなければ何も起こりません) * このように,main.o,sub.oを最新に更新した上で,一番上のgcc -o exe main.o sub.oが実行され,exeが出来上がります. このように,ある実行形式を作りたいとき,その材料がどれなのか,どうやって作るのか,といった'''「各ファイルの依存関係」を記述したものがMakefile'''です. ! 一般的な例 一般的なMakefileの例 8< CC = gcc CFLAGS = -O4 -Wall -I../include DEST = ~/bin LDFLAGS = -L../lib LIBS = -lm OBJS = main.o sub.o PROGRAM = exe all: $(PROGRAM) $(PROGRAM): $(OBJS) $(CC) $(OBJS) $(LDFLAGS) $(LIBS) -o $(PROGRAM) clean: rm -f *.o *~ $(PROGRAM) install: $(PROGRAM) install -s $(PROGRAM) $(DEST) >8 はじめの方の「○=○」という記述は,単に後で使う変数の定義です. 実行バイナリを作成する部分は以下です.基本に忠実に,作りたいもの,その元となる材料,実際の作り方が書かれているだけです. 8< $(PROGRAM): $(OBJS) $(CC) $(OBJS) $(LDFLAGS) $(LIBS) -o $(PROGRAM) >8 以下の部分は make install と実行したときにのみ,参照されます.若干変則的ですが,makeコマンドは「installの作成には材料$(PROGRAM)が必要で,実際の作り方は実行バイナリを所定のディレクトリにコピーすること」と解釈します.つまり,'''installというファイルは作成されません'''が,installコマンドを実行した時点でmakeは終了します. 8< install: $(PROGRAM) install -s $(PROGRAM) $(DEST) >8 以下の部分も少々変則的です.作りたいもの(all)とその材料は示されてますが,実際の作り方が記述されていません. allを作りたければ,まず$(PROGRAM)を作れ,という意味になります. 8< all: $(PROGRAM) >8 !! 注意点 ■先頭のTAB (実際の作り方)は,'''必ずTABの後に書く必要があります'''.コピー&ペースト等でMakefileを作成すると,TABがスペースに置き換わってしまって動かない!というトラブルがよく起こります.注意しましょう. ■暗黙のルール 先ほどのMakefileには「main.cとsub.cから,それぞれmain.oとsub.oを作成する」ための方法が書かれていません. このように,*.cから*.oを作成する手順は省略することも可能です. ただし,コンパイル時には,最適化オプション-Oやインクルードファイルの所在を明示する-Iオプションが使われることが普通ですので,CFLAGSにその内容を定義しておきます.(*.cから*.oが自動作成される際には,CFLAGSをオプションとみなします)