0

.cpp ファイルを .o ファイル経由で実行可能ファイルに自動的にコンパイルおよびリンクするメイクファイルを作成しようとしています。私がうまくいかないのは、自動化された(または手動でさえも)依存関係の生成です。以下のコメント付きコードのコメントを外すと、実行時に何も再コンパイルされませんmake buildmake: Nothing to be done for 'build'.xh(または.hファイル)が変更されたとしても、私が得るのは. 私はこの質問から学ぼうとしています: Makefile、ヘッダーの依存関係、特に dmckee の答え。このメイクファイルが機能しないのはなぜですか?

明確化: すべてをコンパイルできますが、ヘッダー ファイルを変更しても、それに依存する .cpp ファイルは更新されません。したがって、たとえば、ソース全体をコンパイルする#defineと、ヘッダー ファイルで a を変更してから を実行すると、次のようmake buildになりますNothing to be done for 'build'.(以下のコードのコメント チャンクのコメントを解除した場合)。

CC=gcc
CFLAGS=-O2 -Wall
LDFLAGS=-lSDL -lstdc++
SOURCES=$(wildcard *.cpp)
OBJECTS=$(patsubst %.cpp, obj/%.o,$(SOURCES))
TARGET=bin/test.bin

# Nothing happens when i uncomment the following. (automated attempt)
#depend: .depend
#
#.depend: $(SOURCES)
#   rm -f ./.depend
#   $(CC) $(CFLAGS) -MM $^ >> ./.depend;
#
#include .depend

# And nothing happens when i uncomment the following. x.cpp and x.h are files in my project. (manual attempt)
#x.o: x.cpp x.h


clean:
    rm -f $(TARGET)
    rm -f $(OBJECTS)

run: build
    ./$(TARGET)

build: $(TARGET)

$(TARGET): $(OBJECTS)
    @mkdir -p $(@D)
    $(CC) $(LDFLAGS) $(OBJECTS) -o $@

obj/%.o: %.cpp
    @mkdir -p $(@D)
    $(CC) -c $(CFLAGS) $< -o $@
4

2 に答える 2

2

これには数回の反復が必要になる場合があります。

1)最初のアプローチの結果を再現できません(「何も起こらない」よりも明確にする必要があります。Makeは実際に出力を生成しませんか?)。これ:

depend: .depend

.depend: $(SOURCES)
    rm -f ./.depend
    $(CC) $(CFLAGS) -MM $^ >> ./.depend;

include .depend

意図したとおりに機能しているようです。$(info sources: $(SOURCES))その変数に、含まれていると思われるファイル名が含まれていることを確認することをお勧めします。

2)2番目のアプローチの結果を再現できません(「何も起こらない」よりも明確にする必要があります。Makeは実際に出力を生成しませんか?)。x.o: x.cpp x.h最初のアプローチがコメントアウトされたときに試しましたね。

編集:
に集中しましょうx.o。含まれています#include "x.h"か?最初のセクションのコメントを外すとmake x.o、Makeは生成(または変更)し.dependますか?.dependに関連する行はありx.oますか?もしそうなら、それは何ですか?次に変更x.hしてからmake x.o、Makeは何をしますか?

于 2012-07-06T23:10:03.590 に答える
1

で解決できる依存関係は 1 種類だけです$(CC) -MM-DDO_SOMETHING_ELSEコマンド オプションの変更 (例: ) や、ライブラリによってエクスポートされた別のシンボル セットなど、他にもさまざまなものがあります。従来の make では、一貫性のない実行可能ファイルのデバッグがとても楽しくなります。

そこでmakeppの出番です。依存関係は自動的に検出されます。あらゆる種類の依存関係がこれを保証するときはいつでも、ターゲットを再構築するだけではありません。さらに、すべてをつなぎ合わせて、必要なものをボトムアップで構築します。つまり、リンカーに-lmystuffオプションがあり、libmystuff.so または .a をビルドするルールがある場合、それだけで時間内にビルドされます。同様に、まだ存在していないファイルを含めることもできます — あなたのソリューションでは不可能です。

于 2012-07-08T15:12:39.430 に答える