Jak mogę utworzyć zmienną w locie z makefile, której wartością byłaby cała zawartość innego pliku danych.
82
Domyślam się, że chcesz ustawić zmienną w swoim Makefile na zawartość innego pliku:
FILE=test.txt
VARIABLE=`cat $(FILE)`
target:
echo $(VARIABLE)
VARIABLE
jest ciągiem znakówcat $(FILE)
(w cudzysłowach), który w przepisie jest interpretowany tylko przez powłokę. Spróbuj wydrukować jego wartość$(info ${VARIABLE})
.VARIABLE
obietnicę. To jedyna wersja, która działa ze starszymi wersjamimake
. Zarówno:=
i$(shell ...)
są rozszerzeniami GNU.cat
każdym razem, gdy reguła zostanie wykonana. Zwykle nie jest to zamierzone i należy go ostrzec, ponieważ jest powolne. Poza tym, jeśli plik jest potokiem, ma niezamierzone efekty uboczne. Przypisanie powinno być z,:=
aby reguła nie była oceniana, gdy zmienna jest zastępowana, ale gdy zmienna jest zdefiniowana. Wartość zastępcza powinna być$(shell cat $(FILE))
taka, abycat
polecenie było wykonywane w miejscu przez producenta, a nie później według reguł receptury.cat
raczej na skomplikowanych regułach alternatywnych sprawi, że pliki makefile będą znacznie prostsze do zrozumienia i będą prawie tak przenośne, a czasem bardziej przenośne.Zakładając, że marka GNU:
źródło
GNU make w wersji 4.2 obsługuje operacje odczytu plików, więc w odniesieniu do świetnej odpowiedzi Maxima Egorushkina istnieje opcjonalny sposób rozwiązania tego problemu teraz:
źródło
cat
nie istnieje w systemie Windows. Rozwiązanie, które działa w systemach Linux i Windows:Objaśnienie: Wygląda na to, że w systemie Windows zawsze
OS
zdefiniowano zmienną środowiskową równą „Windows_NT”. W ten sposób dla systemu Windowstype
używane jest polecenie, dla innych niż Windowscat
jest używane.źródło
Znacznie prostsze, odkąd
$(file op filename)
dodano:Strona podręcznika tutaj: https://www.gnu.org/software/make/manual/html_node/File-Function.html#index-file_002c-reading-from
źródło
Jeśli używasz programu GNU make, innym sposobem uzyskania tego efektu jest użycie make „include” innego pliku makefile:
Z Makefile:
Utwórz plik „MyFile.mak” z zawartością:
źródło
Makefile:1: "./MyFile.mak": No such file or directory
make -v
dajeGNU Make 3.81
include ./MyFile
Ponieważ platforma nie została określona, wygląda to tak, jak działa na Solarisie:
źródło
Oto bardziej przenośne rozwiązanie, które działa z
MAKE
wersją 3, w którejfile
dyrektywa nie jest dostępna. Wadą jest to, że wymaga utworzenia tymczasowego pliku w procesie.Głównym pomysłem jest użycie
define
dyrektywy, która jest specjalnie zaprojektowana do deklarowania zmiennych wielowierszowych. Oczywiście możesz uniknąć używaniashell
i pliku tymczasowego, jeśli możesz jawnie zapisać zawartość pliku na użytek Makefile.Pamiętaj, że jeśli twój plik zawiera
$
znaki,MAKE
spróbuje rozwinąć je jako zmienne / dyrektywy, gdymy_variable
zostanie rozwinięty (lub gdy zostanie przypisany, zdefiniujesz go:=
). Jeśli chcesz tego uniknąć, musisz uciec przed dołączeniem zawartości pliku. Na przykład zamiastcat
ciebie możesz to zrobić:źródło