make: nic do zrobienia dla `` wszystkich ''

98

Przechodzę przez np. Pgm, aby utworzyć plik make.

http://mrbook.org/tutorials/make/

Mój folder eg_make_creation zawiera następujące pliki,

desktop:~/eg_make_creation$ ls
factorial.c  functions.h  hello  hello.c  main.c  Makefile

Makefile

# I am a comment, and I want to say that the variable CC will be
# the compiler to use.
CC=gcc
# Hwy!, I am comment no.2. I want to say that CFLAGS will be the
#options I'll pass to the compiler
CFLAGS=-c -Wall

all:hello

hello:main.o factorial.o hello.o
  $(CC) main.o factorial.o hello.o -o hello

main.o:main.c
  $(CC) $(CFLAGS) main.c

factorial.o:factorial.c
  $(CC) $(CFLAGS) factorial.c

hello.o:hello.c
  $(CC) $(CFLAGS) hello.c

clean:
  rm -rf *o hello

błąd:

desktop:~/eg_make_creation$ make all
make: Nothing to be done for `all'.

Proszę, pomóż mi zrozumieć, jak skompilować ten program.

Angus
źródło
12
Spróbuj zrobić „wyczyść”, a następnie „zrób wszystko”
Paul R,
11
To nie jest błąd, po prostu oznacza, że hellojest aktualny. Zmień cleanna, rm -f *.o hellozanim zrobi coś nieoczekiwanego, a następnie uruchom make clean alli sprawdź, czy to działa.
Mat
1
Powinieneś także dodać .phony: all clean, ponieważ alli cleannie są nazwami plików.
Kerrek SB
3
Nie umieszczaj -c w swoich CFLAGS.
wildplasser

Odpowiedzi:

122

Czasami błąd „Nic do zrobienia dla wszystkich” może być spowodowany spacjami przed poleceniem w regule makefile zamiast tabulacji. Upewnij się, że w regułach używasz tabulatorów zamiast spacji.

all:
<\t>$(CC) $(CFLAGS) ...

zamiast

all:
    $(CC) $(CFLAGS) ...

Opis składni reguł znajdziesz w podręczniku GNU make: https://www.gnu.org/software/make/manual/make.html#Rule-Syntax

VirtualVDX
źródło
obj-m + = hello.o all: </t> make -C / lib / modules / $ (shell uname -r) / build M = $ (PWD) modules clean: make -C / lib / modules / $ ( shell uname -r) / build M = $ (PWD) clean
Narendra Jaggi
czy powyższy plik jest prawidłowym plikiem?
Narendra Jaggi
W kontekście plików makefile rodzic-dziecko, czasami błąd „Nic do zrobienia dla wszystkich” może być spowodowany nieprawidłowym oznaczeniem celów potomnych jako zadeklarowanych jako .PHONY w nadrzędnym pliku Makefile.
donhector
Miałem all : src/server/mod_wsgi.la, na co się zmieniłem all : </t> src/server/mod_wsgi.la. Teraz pojawia się błąd: make: execvp: src/server/mod_wsgi.la: Permission denied Makefile:29: recipe for target 'all' failed make: *** [all] Error 127po sudo make. Jakaś pomoc?
Mooncrater
@Mooncrater Zobacz gnu.org/software/make/manual/make.html#Rule-Syntax . Tutaj czytamy: Wiersze receptury zaczynają się od znaku tabulacji (lub pierwszego znaku w wartości zmiennej .RECIPEPREFIX; patrz Zmienne specjalne). Pierwsza linia receptury może pojawić się w wierszu po wymaganiach wstępnych ze znakiem tabulatora lub może pojawić się w tym samym wierszu ze średnikiem. Tak czy inaczej, efekt jest taki sam. Twój warunek stał się po prostu przepisem. W tym przypadku nie potrzebujesz karty.
VirtualVDX
31

Usuń helloplik z folderu i spróbuj ponownie.

allCel zależy od hellocelu. helloCel najpierw próbuje znaleźć odpowiedni plik w systemie plików. Jeśli go znajdzie i jest aktualny w plikach zależnych - nie ma nic do zrobienia.

Weekens
źródło
obj-m + = hello.o all: </t> make -C / lib / modules / $ (shell uname -r) / build M = $ (PWD) modules clean: make -C / lib / modules / $ ( shell uname -r) / build M = $ (PWD) clean
Narendra Jaggi
czy powyższy jest prawidłowym plikiem make?
Narendra Jaggi
21

Kiedy podajesz tylko make, tworzy pierwszą regułę w twoim makefile, tj. "All". Określono, że „all” zależy od „hello”, które zależy od main.o, factorial.o i hello.o. Dlatego „make” próbuje sprawdzić, czy te pliki są obecne.

Jeśli są obecne, 'make' sprawdza, czy ich zależności, np. Main.o ma zależność main.c, uległy zmianie. Jeśli się zmieniły, make je odbudowuje, w przeciwnym razie pomija regułę. Podobnie, rekurencyjnie kontynuuje budowanie plików, które się zmieniły, i na końcu uruchamia najwyższe polecenie, „wszystko” w twoim przypadku, aby dać ci plik wykonywalny, w twoim przypadku „cześć”.

Jeśli ich nie ma, niech ślepo buduje wszystko zgodnie z regułą.

Wracając do twojego problemu, to nie jest błąd, ale „make” mówi, że każda zależność w twoim pliku makefile jest aktualna i nie musi nic robić!

Chethan Ravindranath
źródło
16

Make zachowuje się poprawnie. hellojuż istnieje i nie jest starszy niż .cpliki, dlatego nie ma więcej pracy do wykonania. Istnieją cztery scenariusze, w których make będzie musiał (ponownie) zbudować:

  • Jeśli zmodyfikujesz jeden ze swoich .cplików, będzie on nowszy niż helloi będzie musiał zostać przebudowany po uruchomieniu make.
  • Jeśli usuniesz hello, będzie oczywiście musiał go odbudować
  • Dzięki tej -Bopcji możesz zmusić make do odbudowania wszystkiego .make -B all
  • make clean allusunie helloi będzie wymagać przebudowy. (Proponuję spojrzeć na komentarz @ Mat na tematrm -f *.o hello
Aaron McDaid
źródło
4

Myślę, że przegapiłeś kartę w dziewiątej linii. Wiersz po all: hello musi być pustą kartą. Upewnij się, że masz pustą kartę w dziewiątej linii. Dzięki temu interpreter zrozumie, że chcesz użyć domyślnej receptury dla makefile.

Techie
źródło
4

To nie jest błąd; polecenie make w unixie działa w oparciu o znaczniki czasu. To znaczy, powiedzmy, że jeśli dokonałeś pewnych zmian factorial.cppi kompilowałeś za pomocą, makemake pokazuje informację, że tylko cc -o factorial.cpppolecenie jest wykonywane. Następnym razem, jeśli wykonasz to samo polecenie, tj. makeBez wprowadzania zmian w żadnym pliku z rozszerzeniem.cpp rozszerzeniem, kompilator powie, że plik wyjściowy jest aktualny. Kompilator podaje te informacje, dopóki nie wprowadzimy pewnych zmian w jakimkolwiek file.cpp.

Zaletą programu makefilejest to, że skraca czas ponownej kompilacji, kompilując jedyne zmodyfikowane pliki i bezpośrednio używając .oplików object ( ) niezmodyfikowanych plików.

muneshwar
źródło
0

Dotarłem do tego osobliwego, trudnego do debugowania błędu inną drogą. Mój problem polegał na tym, że użyłem reguły wzorca na etapie budowania, gdy cel i zależność znajdowały się w różnych katalogach. Coś takiego:

foo/apple.o: bar/apple.c $(FOODEPS)

%.o: %.c
    $(CC) $< -o $@

Skonfigurowałem w ten sposób kilka zależności i próbowałem użyć dla nich jednego przepisu wzoru. Najwyraźniej pojedyncze zastąpienie „%” tutaj nie zadziała. Ustaliłem jasne zasady dla każdej zależności i znalazłem się z powrotem wśród szczeniąt i jednorożców!

foo/apple.o: bar/apple.c $(FOODEPS)
    $(CC) $< -o $@

Mam nadzieję, że to komuś pomoże!

sfaleron
źródło