2607 Stimmen

Was ist der Zweck von .PHONY in einem Makefile?

Was bedeutet .PHONY in einem Makefile bedeuten? Ich bin durchgegangen ce aber das ist zu kompliziert.

Kann mir das jemand mit einfachen Worten erklären?

2950voto

Eli Bendersky Punkte 246100

Standardmäßig sind Makefile-Ziele "Dateiziele" - sie werden verwendet, um Dateien aus anderen Dateien zu erstellen. Make geht davon aus, dass sein Ziel eine Datei ist, und das macht das Schreiben von Makefiles relativ einfach:

foo: bar
  create_one_from_the_other foo bar

Manchmal möchten Sie jedoch, dass Ihr Makefile Befehle ausführt, die keine physischen Dateien im Dateisystem darstellen. Gute Beispiele hierfür sind die üblichen Ziele "clean" und "all". Wahrscheinlich ist das nicht der Fall, aber Sie Mai haben möglicherweise eine Datei namens clean in Ihrem Hauptverzeichnis. In einem solchen Fall wird Make verwirrt sein, weil standardmäßig die clean Ziel wird mit dieser Datei verknüpft und Make führt es nur aus, wenn die Datei in Bezug auf ihre Abhängigkeiten nicht aktuell zu sein scheint.

Diese besonderen Ziele werden als gefälscht und Sie können Make ausdrücklich mitteilen, dass sie nicht mit Dateien verknüpft sind, z. B.:

.PHONY: clean
clean:
  rm -rf *.o

Jetzt make clean wird wie erwartet ausgeführt, auch wenn Sie eine Datei namens clean .

In Bezug auf Make ist ein falsches Ziel einfach ein Ziel, das immer veraltet ist, wenn Sie also fragen make <phony_target> wird es unabhängig vom Zustand des Dateisystems ausgeführt. Einige gängige make Ziele, die oft gefälscht sind, sind: all , install , clean , distclean , TAGS , info , check .

875voto

George Y. Punkte 10705

Nehmen wir an, Sie haben install Ziel, was in Makefiles sehr üblich ist. Wenn Sie no verwenden. .PHONY und eine Datei namens install in demselben Verzeichnis wie das Makefile existiert, dann make install wird reichen nichts . Das liegt daran, dass Make die Regel so interpretiert, dass sie bedeutet: "Führe dieses und jenes Rezept aus, um die Datei namens install ". Da die Datei bereits vorhanden ist und sich ihre Abhängigkeiten nicht geändert haben, wird nichts unternommen.

Wenn Sie jedoch die install target PHONY, teilt es dem make-Tool mit, dass das Ziel fiktiv ist und dass make nicht erwarten sollte, dass es die tatsächliche Datei erstellt. Daher wird es nicht prüfen, ob die install Datei existiert, d.h.: a) das Verhalten wird nicht verändert, wenn die Datei existiert und b) zusätzliche stat() wird nicht aufgerufen.

Generell sollten alle Targets in Ihrem Makefile, die keine Ausgabedatei mit dem gleichen Namen wie der Target-Name erzeugen, PHONY sein. Dies beinhaltet typischerweise all , install , clean , distclean , und so weiter.

242voto

prerit jain Punkte 1869

ANMERKUNG : Das Make-Tool liest das Makefile und überprüft die Änderungszeitstempel der Dateien auf beiden Seiten des ':'-Symbols in einer Regel.

Beispiel

In einem Verzeichnis 'test' sind folgende Dateien vorhanden:

prerit@vvdn105:~/test$ ls
hello  hello.c  makefile

In makefile wird eine Regel wie folgt definiert:

hello:hello.c
    cc hello.c -o hello

Nehmen wir nun an, dass die Datei "hello" eine Textdatei ist, die Daten enthält und nach der Datei "hello.c" erstellt wurde. Der Zeitstempel für die Änderung (oder Erstellung) von 'hello' ist also neuer als der von 'hello.c'. Wenn wir also 'make hello' von der Kommandozeile aus aufrufen, wird es Folgendes ausgeben:

make: `hello' is up to date.

Rufen Sie nun die Datei "hello.c" auf und fügen Sie einige Leerzeichen ein, die die Codesyntax oder -logik nicht beeinträchtigen, und speichern und beenden Sie die Datei. Jetzt ist der Änderungszeitstempel von hello.c neuer als der von 'hello'. Wenn Sie nun 'make hello' aufrufen, wird es die Befehle wie folgt ausführen:

cc hello.c -o hello

Und die Datei 'hello' (Textdatei) wird mit einer neuen Binärdatei 'hello' (Ergebnis des obigen Kompilierungsbefehls) überschrieben.

Wenn wir .PHONY im Makefile wie folgt verwenden:

.PHONY:hello

hello:hello.c
    cc hello.c -o hello

und dann 'make hello' aufrufen, wird es jede Datei im pwd 'test' ignorieren und den Befehl jedes Mal ausführen.

Nehmen wir nun an, dass für das Ziel "hallo" keine Abhängigkeiten deklariert sind:

hello:
    cc hello.c -o hello

und die Datei 'hello' ist bereits im pwd 'test' vorhanden, dann wird 'make hello' immer als:

make: `hello' is up to date.

107voto

YourBestBet Punkte 1403
.PHONY: install
  • bedeutet, dass das Wort "install" in diesem Fall keinen Dateinamen darstellt Makefile;
  • bedeutet, dass das Makefile nichts mit einer Datei namens "install" zu tun hat im selben Verzeichnis.

57voto

JohnMcG Punkte 8423

Es ist ein Build-Ziel, das kein Dateiname ist.

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X