2017-02-09 94 views
5

GNU Make ma opcję -B, która zmusza make do ignorowania istniejących celów. Pozwala to na odbudowanie celu, ale także przebudowuje wszystkie drzewa zależności celu. Zastanawiam się, czy istnieje sposób na wymuszenie przebudowy celu bez odbudowywania jego zależności (używając opcji GNU Make, ustawień w Makefile, kompatybilnym oprogramowaniu podobnym do make)?Czy istnieje sposób na wymuszenie przebudowy celu (make -B) bez odbudowywania jego zależności?

Ilustracja problemu:

$ mkdir test; cd test 
$ unexpand -t4 >Makefile <<EOF 
huge: 
    @echo "rebuilding huge"; date >huge 
small: huge 
    @echo "rebuilding small"; sh -c 'cat huge; date' >small 
EOF 
$ make small 
rebuilding huge 
rebuilding small 
$ ls 
huge Makefile small 
$ make small 
make: 'small' is up to date. 
$ make -B small 
rebuilding huge # how to get rid of this line? 
rebuilding small 
$ make --version | head -n3 
GNU Make 4.0 
Built for x86_64-pc-linux-gnu 
Copyright (C) 1988-2013 Free Software Foundation, Inc. 

Oczywiście można rm small; make small, ale jest tam wbudowany w sposób?

+0

Does [to pytanie] (http://stackoverflow.com/questions/12199237/telling-make-to-ignore-dependencies-when-the-top-target-have-been-created)? – sycko

+0

Dzięki, ale niewiele: jak pokazałem przy użyciu 'ls', zachowano tutaj' ogromny' (bez '.SECONDARY:' target), a odbudowanie jest raczej wynikiem '-B'. –

Odpowiedz

3

Jednym ze sposobów jest użycie opcji -o dla wszystkich celów, które nie mają być przerobione:

-o FILE, --old-file=FILE, --assume-old=FILE 
     Consider FILE to be very old and don't remake it. 

EDYCJA

myślę, że jesteś błędnej dokumentacji dla -B; mówi:

-B, --always-make 
     Unconditionally make all targets. 

pamiętać, że wszystkie celetutaj; huge jest niewątpliwie celem, więc jeśli użyjesz -B, zostanie on przetworzony.

Jednak również błędnie przeczytałem twoje pytanie. Myślałem, że chce odbudować small bez odbudowy huge chociaż huge jest nowy, ale starasz się dostać small zostać przebudowany chociaż huge ma nie zmieniło, prawda?

Zdecydowanie nie chcesz używać -B. Ta opcja wcale nie jest tym, czego szukasz.

Normalnie ludzie to zrobić poprzez usunięcie small:

rm -f small 
make small 

To może być przydatne, aby mieć możliwość, że przymusowe dany cel mają być odtworzone, ale ta opcja nie istnieje.

Można użyć -W huge, ale znowu oznacza to, że musisz znać nazwę warunku wstępnego, a nie tylko cel, który chcesz zbudować.

+0

Dzięki, 'make -B -o huge small' naprawdę działa, ale nie jest idealny, chyba że takie zależności można uzyskać automatycznie ... –

+0

Zgadzam się, że nie jest idealny, ale poprosiłeś o dowolną metodę :) – MadScientist

+0

Tak, to jest dlaczego przegłosowałem (ale nie jestem gotowy, aby oznaczyć odpowiedź jako zaakceptowaną). Właściwie, jeśli opcja zrobiła to, co sama mówi (uważaj cel za bardzo stary i zmusić go do przetworzenia, zamiast ignorować jako bardzo nowy), odpowiedź byłaby idealna. –

2

pliku pod dość bolesnego Hack:

huge: 
    @echo "rebuilding huge"; date >huge 

small: $(if $(filter just,${MAKECMDGOALS}),huge) 
    @echo "rebuilding small"; sh -c 'cat huge; date' >small 

.PHONY: just 
just: ; 

Teraz możesz

$ make -B just small 
+0

To jest naprawdę paskudne! –

+0

Dzięki, to jest jak dotąd najbardziej "inwokalnie automatyczne", ale niestety nie będzie działać z '$ <', '$ ^' itp. W regułach. –

3

Pomoże to:

touch huge; make small 

?

+0

Dzięki, działa (i tak robi 'make -W ogromny mały'), ale nie jest idealny, chyba że takie zależności można uzyskać automatycznie ... –

0

Cóż, do tej pory używam tego częściowe rozwiązanie:

$ cat >~/bin/remake <<'EOF' 
#!/bin/sh 
# http://stackoverflow.com/questions/42139227 
for f in "[email protected]"; do 
    if [ -f "$f" ]; then 
    # Make the file very old; it's safer than removing. 
    touch [email protected] "$f" 
    fi 
done 
make "[email protected]" 
EOF 
$ chmod u+x ~/bin/remake 
$ # PATH="$HOME/bin:$PATH" in .bashrc 
$ remake --debug=b small 
GNU Make 4.0 
Built for x86_64-pc-linux-gnu 
Copyright (C) 1988-2013 Free Software Foundation, Inc. 
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html> 
This is free software: you are free to change and redistribute it. 
There is NO WARRANTY, to the extent permitted by law. 
Reading makefiles... 
Updating goal targets.... 
Prerequisite 'huge' is newer than target 'small'. 
Must remake target 'small'. 
rebuilding small