Automatyzacja kompilacji Automatyzacja kompilacji 1/28
Automatyzacja kompilacji 2/28 Wstęp Polecenia kompilacji gcc -Wall -c komunikat.c -o komunikat.o gcc -Wall -c main.c -o main.o gcc -Wall -c test.c -o test.o gcc -lm komunikat.o main.o test.o -o program
Automatyzacja kompilacji 3/28 Polecenia kompilacji Prosta automatyzacja for f in *.c; do gcc -Wall -c $f -o ${f%c}o done gcc -lm *.o -o program
Automatyzacja kompilacji 4/28 Pierwszy makefile Reguła: cel: zależności polecenie gdzie cel nazwa pliku, który ma powstać z tej reguły zależności lista plików, od których zależy cel, tzn. zmiana któregokolwiek z tych plików oznacza, że cel też się zmieni, polecenie jest to polecenie, za pomocą którego ma zostać wytworzony cel.
Automatyzacja kompilacji 5/28 Pierwszy makefile Przykładowa reguła: komunikat.o: komunikat.c komunikat.h gcc -Wall -c komunikat.c -o komunikat.o Zależności gcc -MM plik.c
Automatyzacja kompilacji 6/28 Pierwszy makefile Przykładowy makefile program: komunikat.o main.o test.o gcc -lm komunikat.o main.o test.o -o program komunikat.o: komunikat.c komunikat.h gcc -Wall -c komunikat.c -o komunikat.o main.o: main.c test.h gcc -Wall -c main.c -o main.o test.o: test.c test.h komunikat.h gcc -Wall -c test.c -o test.o
Automatyzacja kompilacji 7/28 Wykorzystanie makefile Wywołanie Jeśli plik z regułami nazywa się Makefile $ make gcc -Wall -c komunikat.c -o komunikat.o gcc -Wall -c main.c -o main.o gcc -Wall -c test.c -o test.o gcc -lm komunikat.o main.o test.o -o program W innym przypadku $ make -f nazwa_pliku
Automatyzacja kompilacji 8/28 Reguły jak polecenia program: komunikat.o main.o test.o gcc -lm komunikat.o main.o test.o -o program komunikat.o: komunikat.c komunikat.h gcc -Wall -c komunikat.c -o komunikat.o main.o: main.c test.h gcc -Wall -c main.c -o main.o test.o: test.c test.h komunikat.h gcc -Wall -c test.c -o test.o clean: rm -f program komunikat.o main.o test.o
Automatyzacja kompilacji 9/28 Reguły jak polecenia program: komunikat.o main.o test.o gcc -lm komunikat.o main.o test.o -o program komunikat.o: komunikat.c komunikat.h gcc -Wall -c komunikat.c -o komunikat.o main.o: main.c test.h gcc -Wall -c main.c -o main.o test.o: test.c test.h komunikat.h gcc -Wall -c test.c -o test.o.phony: clean clean: rm -f program komunikat.o main.o test.o
Automatyzacja kompilacji 10/28 Zmienne i funkcje Zmienne objects=komunikat.o main.o test.o program: $(objects) gcc -lm $(objects) -o program komunikat.o: komunikat.c komunikat.h gcc -Wall -c komunikat.c -o komunikat.o main.o: main.c test.h gcc -Wall -c main.c -o main.o test.o: test.c test.h komunikat.h gcc -Wall -c test.c -o test.o.phony: clean clean: rm -f program $(objects)
Automatyzacja kompilacji 11/28 Zmienne i funkcje Wbudowane funkcje sources=komunikat.c main.c test.c objects=$(patsubst %.c,%.o,$(sources)) $(patsubst wz_wejściowy,wz_wynikowy,lista_wyrazów) objects=$(sources:.c=.o) sources=$(wildcard *.c)
Automatyzacja kompilacji 12/28 Zmienne automatyczne $@ nazwa pliku docelowego $< nazwa pierwszego pliku pełniącego funkcję wymagania wstępnego w danej regule $^ nazwy wszystkich plików pełniących funkcje wymagań wstępnych, bez powtórzeń $+ nazwy wszystkich plików pełniących funkcje wymagań wstępnych, z powtórzeniami $? nazwy plików pełniących funkcje wymagań wstępnych, nowszych od pliku docelowego $* w przypadku reguły przyrostkowej nazwa pliku docelowego, bez rozszerzenia
Automatyzacja kompilacji 13/28 Zmienne automatyczne wykorzystanie sources=komunikat.c main.c test.c objects=$(sources:.c=.o) program: $(objects) gcc -lm $^ -o $@ komunikat.o: komunikat.c komunikat.h gcc -Wall -c $< -o $@ main.o: main.c test.h gcc -Wall -c $< -o $@ test.o: test.c test.h komunikat.h gcc -Wall -c $< -o $@.PHONY: clean clean: rm -f program $(objects)
Automatyzacja kompilacji 14/28 Reguły wzorców Deklarowanie reguły wzorca %.o: %.c gcc -Wall -c $< -o $@ Reguła przyrostkowa.suffixes=.cxx.cxx.o: g++ -Wall -c $< -o $@
Automatyzacja kompilacji 15/28 Przykład użycia reguły wzorca sources=komunikat.c main.c test.c objects=$(sources:.c=.o) program: $(objects) gcc -lm $^ -o $@ komunikat.o: komunikat.c komunikat.h main.o: main.c test.h test.o: test.c test.h komunikat.h %.o: %.c gcc -Wall -c $< -o $@.PHONY: clean clean: rm -f program $(objects)
Automatyzacja kompilacji 16/28 Użycie wbudowanych reguł wzorców sources=komunikat.c main.c test.c objects=$(sources:.c=.o) program: $(objects) gcc -lm $^ -o $@ komunikat.o: komunikat.c komunikat.h main.o: main.c test.h test.o: test.c test.h komunikat.h.phony: clean clean: rm -f program $(objects)
Automatyzacja kompilacji 17/28 Wbudowane reguły Poprzednio wykorzystano regułę %.o: %.c $(CC) $(CFLAGS) $(CPPFLAGS) -c -o $@ $< Można ją modyfikować definiując zmienne CC=gcc CFLAGS=-Wall
Automatyzacja kompilacji 18/28 Typowe zmienne wykorzystywane w regułach niejawnych Zmienna Wartość domyślna Opis CC gcc Kompilator języka C CXX g++ Kompilator języka C++ CFLAGS pusta Flagi przekazywane do kompilatora C CXXFLAGS pusta Flagi przekazywane do kompilatora C++ CPPFLAGS pusta Flagi przekazywane do preprocesora C
Automatyzacja kompilacji 19/28 Domyślne reguły przyrostkowe Język Rozszerzenia Polecenie C.c $(CC) -c $(CPPFLAGS) $(CFLAGS) C++.cpp,.cc,.C $(CXX) -c $(CPPFLAGS) $(CXXFLAGS) Asembler.s $(AS) $(ASLAGS) Asembler.S $(CPP) $(CPPLAGS) Pascal.p $(PC) -c $(PFLAGS) Fortran.f $(FC) -c $(FFLAGS) Fortran.F $(FC) -c $(FFLAGS) &(CPPFLAGS)
Automatyzacja kompilacji 20/28 Konstrukcje warunkowe Konstrukcja ifeq ifneq ifdef ifndef Znaczenie Sprawdza, czy dwie wartości są sobie równe Sprawdza, czy dwie wartości są od siebie różne Sprawdza, czy zdefiniowano daną zmienną Sprawdza, czy nie zdefiniowano danej zmiennej
Automatyzacja kompilacji 21/28 Konstrukcje warunkowe Przykład konstrukcji if ifeq ($(shell uname -o), "GNU/Linux") CPPFLAGS += -DLINUX else CPPFLAGS += -DOS_UNKNOWN endif
Automatyzacja kompilacji 22/28 Konstrukcje warunkowe Testowanie definicji zmiennych ifdef debug CFLAGS += -g else CFLAGS += -O2 endif Wywołanie $ make debug=1
Automatyzacja kompilacji 23/28 Narzędzia alternatywne do make Cons SCons ant nm imake CMake
Automatyzacja kompilacji 24/28 Wykorzystanie SCons Najprostszy przykład Zawartość pliku SConstruct: Program( hello.c ) Program hello powstaje na podstawie pliku hello.c, przy pomocy kompilatora C. Tworzenie plików obiektowych: Object( hello.c ) Tworzenie biblioteki: Library( hello.c )
Automatyzacja kompilacji 25/28 Instrukcje SCons Podawanie nazwy celu Program( new_hello, hello.c ) Cel zależy od wielu źródeł Program( new_program, [ prog.c, file1.c, file2.c ]) lub Program( new_program, Glob( *.c ))
Automatyzacja kompilacji 26/28 Wykorzystanie bibliotek Library( foo, [ f1.c, f2.c, f3.c ]) Program( prog.c, LIBS=[ foo, bar ], LIBPATH=. ) Program( prog.c, LIBS = m, LIBPATH = [ /usr/lib, /usr/local/lib ])
Automatyzacja kompilacji 27/28 Zależności Domyślnie wykorzystywana jest suma MD5 Decider( MD5 ) Zachowanie takie jak make Decider( timestamp-newer ) Oraz połączenie obu Decider( MD5-timestamp )
Automatyzacja kompilacji 28/28 W wykładzie wykorzystano materiały Środowisko programisty, http://mediawiki.ilab.pl/index.php/%c5%9arodowisko programisty J. Fusco, Linux. Niezbędnik programisty, Helion, 2009