(Sollten Sie Fragen haben, wenden Sie sich an erstaunlich geschrieben GNU make manual. Aber denken Sie daran, dass, genau wie Makefile, dieses Handbuch vollständig gelesen werden sollte, bevor Sie die Konzepte in die Praxis umsetzen).
Ich konnte nicht herausfinden, wie es leicht gemacht wird. Soweit ich weiß, müssen Sie einige manuelle Arbeit machen.
Später werde ich beschreiben, wie es gemacht werden könnte und zeigen Skripte, die current_makefile
Variable einzuführen. Ich möchte jedoch ein wichtiges Konzept an erster Stelle betonen.
Sie sollten verstehen, dass, wenn wir eine Art von Variable current_makefile
hatten, die zu dem aktuellen Makefile-Namen erweitert wird, dann muss es während des Lesens von Makefiles geändert werden. Das bedeutet, dass innerhalb des "sofortigen" Erweiterungskontexts verwendet werden sollte - d. H. Innerhalb von Befehlen, die ausgeführt werden während Lesen des Makefiles. Die meisten Befehle werden jedoch ausgeführt, nachdem Makefiles gelesen wurden. Daher wird bei einigen Befehlen der korrekte Wert problemlos ausgegeben, während an bestimmten Stellen, an denen die Erweiterung "defered" verwendet wird, immer der Name des Stammmakefile angezeigt wird.
Wenn Sie diese Variable beispielsweise im Regeltext verwenden möchten, müssen Sie Tricks ausführen, da der Regeltext immer eine verzögerte Erweiterung hat. Also, wenn Sie die Regel
rule:
echo In makefile $(current_makefile):
echo Making target [email protected]
haben, wird es immer den Namen des Root-Makefile drucken. Stattdessen sofortige Expansion zu erzwingen, müssen Sie eine andere Variable mit Make-Datei spezifischen Namen erstellen (das heißt Namen dieser Variablen sollten in jedem Make-Datei unterschiedlich sein):
this_makefile_unique_name := $(current_makefile)
rule:
echo In makefile $(current_makefile):
echo Making target [email protected]
oder verwenden eval :.
define make_rule
rule:
echo In makefile $(1):
echo Making target [email protected]
$(eval $(call make_rule,$(current_makefile)))
Wenn Sie nur den Namen der aktuellen Make-Datei für Debug-Zwecke zu nutzen, sollten Sie spezielle Debugging-Funktionen, wie Warnung oder Info :.
$(warning We're in makefile $(current_makefile))
Diese Funktionen verwenden die "sofortige" Erweiterung und geben den korrekten Wert aus.
Wie ein solches $ (current_makefile) definieren?
Sie müssen Makefile-Einschlüsse manuell bearbeiten. Wenn Sie ein Makefile einschließen, wird sein Name an den Anfang des Stapels platziert. Wenn Sie vom eingeschlossenen Makefile zum äußeren zurückkehren, wird der oberste Name aus dem Stapel herausgenommen. Dies wird durch Einfügen von Sonder Anrufe an den Anfang und das Ende der Make-Datei erreicht:
# Beginning of makefile
$(eval $(makefile_names_push))
#... makefile text
$(warning $(current_makefile))
#...
$(eval $(makefile_names_pop))
#End of file
definieren Sie nun die Funktionen am Anfang Ihrer Wurzel Make-Datei.
lastword=$(word $(words $(1)),$(1))
define makefile_names_push
current_makefile := $$(CURDIR)/$$(call lastword,$$(MAKEFILE_LIST))
makefile_stack :=$$(makefile_stack) $$(current_makefile)
endef
define makefile_names_pop
makefile_stack := $$(filter-out $$(current_makefile),$$(makefile_stack))
current_makefile := $$(call lastword,$$(makefile_stack))
endef
Wenn Sie sicher sind, dass Ihr Make ist neu genug (Version 3.81+), ersetzen lastword
Anruf mit eingebauter Funktion :.
#inctead of $$(call lastword,$$(MAKEFILE_LIST))
$$(lastword $$(MAKEFILE_LIST))
Ist es sinnvoll?
Total nutzlos. Eine einzige Verwendung, die hier nützlich sein könnte, besteht darin, 100 Makefiles zu erstellen, die symbolische Links zu einem Makefile sind, wobei die Regeln in diesen Makefiles von ihren Namen abhängen. Dies kann jedoch innerhalb einer im Handbuch beschriebenen Makefile- und Foreach-Eval-Technik erreicht werden. Also meine Post war eine komplette Zeitverschwendung, obwohl ich ein bisschen Spaß hatte :-)
Darf ich fragen, warum Sie das brauchen? – erelender