Mit ifdef und ifndef-Direktiven
Ich versuche, um zu überprüfen, ob eine variable definiert ist, mit ifndef/ifdef
, aber ich bekomme immer eine not found
Fehler von der Ausführung. Ich bin mit GNU Make 3.81
, und hier ist ein Ausschnitt von dem, was ich habe:
all: _images
$(call clean, .)
$(call compile, .)
@$(OPENER) *.pdf &
_images:
$(call clean, "images")
$(call compile, "images")
define clean
@rm -f ${1}/*.log ${1}/*.aux ${1}/*.pdf
endef
define compile
ifdef ${1}
dir = ${1}
else
dir = .
endif
ifdef ${2}
outdir = ${2}
else
outdir = ${1}
endif
@$(COMPILER) -output-directory ${outdir} ${dir}/*.tex
endef
Und der genaue Fehler:
$ make
ifdef "images"
/bin/sh: 1: ifdef: not found
make: *** [_images] Error 127
Bearbeiten:
Angesichts Barmar Kommentare, hier geht die Schlussfolgerungen:
Den Inhalt einer definieren, sind shell-Befehlszeilen, nicht-Direktiven;
zu Bruchlinien innerhalb der Befehle in einen block definieren, der Zeilenumbruch maskiert werden müssen -- mit \;
auch, jeder block entspricht einem-liner-Befehle separat ausgeführt wird, die jeweils in einem anderen shell-Ausführung, was bedeutet, dass, definieren von lokalen Variablen funktioniert nicht, wenn die Absicht ist, den Zugriff auf die variable Wert in der nächsten one-liner block.
Dank tripleee für das nette umgehen.
- Der Inhalt einer
define
sind shell-Befehl Linien, nichtmake
Richtlinien. - Wusste es nicht, Barmar, danke! Also, ist es
directive
andere alsdefine
dass ich kann verwenden, um zu erstellen "Funktionen" in ein makefile? Oder gibt es eine Möglichkeit, um dieifdef/ifndef
Vergleiche möglich? - Warum nicht mit der shell
if
Befehl? - Ah, habe gerade was du meintest ^^. Ich werde das ausprobieren, vielen Dank!
- Barmar, es scheint, ich kann nur schreiben
if
Anweisungen in eine Zeile; wenn ich mehr als eine Zeile, ist es nicht korrekt zu analysieren. Ich habe bemerkt aber, dass die Schale eingesetzt istsh
, nichtbash
; ist es einsh
Einschränkung, oder es ist aufgrund der makefile-syntax? Kennen Sie eine Abhilfe für dieses? - Sie haben zu entkommen die Zeilenumbrüche mit
`. Otherwise,
machen` behandelt jede Zeile als separates shell-Befehl auszuführen, statt dass alle von Ihnen wie ein Skript. - homer sagt: hmmm... blöd
make
... Barmar, ich danke Ihnen sehr! Ich werde nach einer Antwort auf Ihre Kommentare. - Der Inhalt einer
define
werden können, machen Richtlinien. Versuchen Sie es.
Du musst angemeldet sein, um einen Kommentar abzugeben.
Können Sie kombinieren die shell-Einrichtungen mit Machen, um eine ziemlich prägnante definition.
Den Doppel-dollar ist eine Flucht die Pässe ein einzelnes dollar-Zeichen auf der shell. Das Konstrukt
${variable:-value}
gibt den Wert von$variable
es sei denn, es ist nicht gesetzt oder leer ist, in welchem Fall es gibtvalue
. Da${1}
und${2}
ersetzt werden durch statische strings, bevor die shell wertet diesen Ausdruck, wir nehmen den Umweg der Zuordnung zu Variablen vor der Prüfung Ihnen.Diese auch veranschaulicht, wie eine Verbindung von zwei "one-Liner" in einem einzigen shell-Aufruf. Das Semikolon ist eine Anweisung terminator (im Grunde gleichwertig zum Zeilenumbruch) und die Sequenz für einen backslash und ein newline-führt die nächste Zeile zusammengeführt werden mit der aktuellen Zeile in eine einzige "logische Linie".
Dies ist Komplex genug, dass ich würde empfehlen, dass Sie ausgelassen
@
aber ich habe es in nur um zu zeigen, wo es hingehört. Wenn Sie möchten silent-Betrieb, wenn man einmal es richtig zu Debuggen, führen Sie mitmake -s
.${...:-...}
verwendet wird (: Danke!