GNU make part 12 Copyright by Sun Young
GNU make -part 1/2 Copyright by Sun. Young Kim 작 성 자: 김선영 메 com 일: sunyzero (at) gmail (dot) 버 전: 1. 30
what is make ? v 컴파일 작업을 쉘 스크립트를 이용한다면? #!/bin/sh COMPILER=gcc OPTIONS="-Wall -g -I. . /include/mod -I. . /include/symbol" SRC_FILENAMES="myproj. c mod_a. c mod_b. c mod_c. c mod_d. c" for i in $SRC_FILENAMES do if [ -f ${i}. c ]; then $COMPILER $OPTIONS ${i}. c -c -o ${i}. o else echo "${i}. c is not exist" fi done Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
make something? v 만국 공통의 예제인 "안녕 세상!" 의 경우 § (소스 코드는 알아서 짜도록 합시다) $ make hello cc hello. c -o hello v make 와 hello. c § 어떻게? : 확장자 규칙(suffix rule)에 의해서. § hello. c 대신에 hello. cc 가 있다면? $ make hello g++ hello. cc -o hello Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
Makefile, makefile v Makefile, makefile § make 유틸리티가 시작하면서 읽어들이는 스크립트 파일명 § makefile , Makefile 이 동시에 존재하면 makefile 이 읽힌다. » Makefile 은 암묵적으로 확장된 make 의 규칙으로 작성되었음을 암시 » UNIX 기본 make 는 기능이 미약하여 GNU make를 주로 사용함 § 기본적인 형태의 Makefile CC = gcc helloworld : helloworld. c $(CC) -o helloworld. c § makefile 이 발견되지 않으면 make 기본값으로 작동한다. Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
target, prerequisite, command (con't) v make 가 target 을 만들기 위한 조건 § prerequisites 가 전부 충족되어야 한다. § 이미 target 이 존재하는 경우에는 갱신시간을 비교한다. » target 이 prerequisites 보다 나중에 갱신되었다면 다시 작업하지 않는다. » 따라서 prerequisites 에는 target 를 만들기 위한 모든 의존관계가 서술돼야 한다 § 모든 prerequisites 가 충족되어지면 target 을 만들기 위한 command 가 실행된다. INCS 1 = io_epoll. h OBJS 1 = c_main. o mng_io. o mng_thread. o io_epoll_pthread : $(OBJS 1) $(INCS 1) $(CC) $(CFLAGS) $(OBJS) $(LOADLIBES) $(LDLIBS) –o $@ Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
default target v default target § makefile에 가장 먼저 등장하는 target 을 의미 § make 는 아무런 목표를 지정하지 않았을 때 default target 만을 처리한다. § 암묵적으로 default target 은 이름을 all 로 지정한다. » all 은 실제 파일명이 아닌 다른 의존관계의 target 을 지정한다. (phony target) » 따라서 make 와 make all 은 동일하다. OUT = helloworld hiworld all: $(OUT) helloworld: helloworld. o hiworld: hiworld. o helloworld. o: helloworld. c hiworld. o: hiworld. c Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
include makefile v include FILENAMES. . . § 공통적으로 사용되는 내용을 모듈처럼 주로 사용 § 다른 파일의 내용을 삽입한다. § 관습적으로. mk 확장자를 사용한다. include. . /common. mk pref. mk # include. . /common. mk and pref. mk with current position Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
variable(macro) setting (con’t) v recursively expanded setting § assignment : » name = value § retrieve : » $(name) or ${name} § 선언되는 시점에서 value 에 다른 변수가 포함되어있으면 계속 확장하면서 해석함 Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
variable(macro) setting (cont) v simply expanded setting § assignment : » name : = value § retrieve : » $(name) or ${name} § 선언되는 시점에서 value 에 다른 변수가 포함되어있으면 확장하지 않음 Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
variable(macro) setting (cont) v difference : recursively / simply expanded setting RECURSIVELY_SRC = $(SRC_LIST) SIMPLY_SRC : = $(SRC_LIST) SRC_LIST = main. c common. c modules. c # RECURSIVELY_SRC = “main. c common. c modules. c”. # SIMPLY_SRC = nothing. SRC_LIST = main. c common. c modules. c RECURSIVELY_SRC = $(SRC_LIST) SIMPLY_SRC : = $(SRC_LIST) # RECURSIVELY_SRC = “main. c common. c modules. c”. # SIMPLY_SRC is same as RECURSIVELY_SRC. Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
implicit rule v GNU make가 자동 처리하는 규칙 § 확장자 혹은 패턴에 따라서 자동처리하는 rule을 가짐 § % 메타문자는 모든 이름과 매칭됨 » %. c , %. o 등등 » foo, bar 를 만들기 위해서 foo. o, bar. o 를 만들려고 하고, » foo. o, bar. o 를 만들기 위해서 foo. c , bar. c 만 기술해도 %. o: %. c 룰에 의해서 자동으로 implicit rule 이 적용됨. SUFFIXES: # remove "suffix rule" list # implicit rule : complie rule for C sources %. o: %. c # $<, $@ is automatic variables $(CC) -c $< -o $@ foo. o : foo. c bar. o : bar. c Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
implicit rule (con't) v example § foo, bar 를 만들기 위해서 foo. o, bar. o 를 만들려고 하고, § foo. o, bar. o 를 만들기 위해서 foo. c , bar. c 를 찾으려고 함 » 찾으면? %. o: %. c 의 implicit rule 의 command에 의해서 컴파일 작동. SUFFIXES: %. o: %. c $(CC) -c $< -o $@ %: %. o $(CC) $< -o $@ all : foo bar #foo : foo. o #bar : bar. o #foo. o : foo. c #bar. o : bar. c Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
implicit rule (con't) v matching result. SUFFIXES: %. o: %. c $(CC) -c $< -o $@ %: %. o $(CC) $< -o $@ all : foo bar $(CC) -c foo. c -o foo. o $(CC) foo. o -o foo $(CC) -c bar. c -o bar. o $(CC) bar. o -o bar Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
default implicit rules v C Language § $(CC) $(CFLAGS) $(CPPFLAGS) -c -o N. c § $(CC) $(CFLAGS) $(CPPFLAGS) N. c $(LOADLIBES) $(LDLIBS) -o N v C++ Language § $(CXX) $(CXXFLAGS) $(CPPFLAGS) -c -o N. cc § $(CXX) $(CXXFLAGS) $(CPPFLAGS) N. c $(LOADLIBES) $(LDLIBS) -o N Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
default implicit rules (con't) v Linking object file § $(CC) $(LDFLAGS) N. o $(LOADLIBES) $(LDLIBS) x: y. o z. o $ make cc -c x. c -o x. o cc -c y. c -o y. o cc -c z. c -o z. o cc x. o y. o z. o -o x Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
default implicit rules (con't) v Archive (%. o): %. c $(CC) $(CFLAGS) $(CPPFLAGS) -c $< -o $*. o $(AR) r $@ $*. o -$(RM) $*. o Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
predefined variables v built-in variables of make utility [default value] § CC : [cc] make 가 사용할 C compiler 지정 § CPPFLAGS : 전처리기(cpp)가 사용할 플래그 (= 주로 헤더 위치) § CFLAGS : C 컴파일시에 사용될 플래그(옵션)을 지정 § CXXFLAGS : C++ 컴파일시에 사용될 플래그(옵션)을 지정 § LOADLIBES : 추가할 library 검색 위치 리스트 § LDLIBS : linking library 리스트 Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
predefined variables (con't) v built-in variables of make utility § AR : [ar] archive 관리 유틸리티 지정 § ARFLAGS : [rv] AR 유틸리티가 사용할 플래그 § LDFLAGS : linker 가 사용할 플래그(옵션)을 지정 § CPP : [$(CC) -E], C Pre-Processor (전처리기) 를 지정 § MAKE : [make] make 유틸리티 지정 § RM : [rm -f]삭제를 위한 명령어 Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
predefined variables (con't) v predefined variables in Makefile CC = gcc CFLAGS = -Wall -g CPPFLAGS = -I. . /include LDLIBS = -lm all: helloworld goodmorningworld helloworld: helloworld. o goodmorningworld: goodmorningworld. o $ make gcc -Wall -g -I. . /include gcc helloworld. o -lm -o helloworld gcc -Wall -g -I. . /include gcc -c -o helloworld. c goodmorningworld. o -c -o goodmorningworld. c -lm -o goodmorningworld Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
pattern rule v override implicit rule with specified pattern. § The pattern may be used filename or suffix. § "%" means any filenames. SUFFIXES: %. o: %. c gcc -Wall -g -c $< -o $@ %: %. o gcc $< -o $@ %_test. o: %. c gcc -DTEST_COVER -Wall -g -c $< -o $@ all: helloworld goodmorningworld helloworld_test goodmorningworld_test Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
suffix rule v suffix 에 따라서 자동 처리하는 implicit rule 지정 (old fashion) § make 는 내부적으로 suffix 에 따라서 자동처리하는 default implicit rule 을 가짐 §. SUFFIXES 에 suffix rule 을 적용할 접미사의 리스트를 지정함 » 기존의 리스트를 삭제할때는 우선 빈 리스트인 ". SUFFIXES: " 을 먼저 지정 § double suffix 인 경우 즉. c. o 의 경우에는. c 가. o 파일로 변경될때의 규칙을 의미. SUFFIXES: . c. o # suffix rule: from object, to binary. o: $(CC) $< $(LOADLIBES) $(LDLIBS) -o $@ # suffix rule: from. c code, to object. c. o: $(CC) -c $(CFLAGS) $(CPPFLAGS) -o $@ $< Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
suffix rule (con't) v built-in macro 만 정의된 경우에 기본 suffix rule 으로도 컴파일 가능 § makefile 이 없더라도 make hiworld 하면? suffix rule에 의해 hiworld. c 를 검색함 v. SUFFIXES: 에 아무것도 지정하지 않으면 suffix rule 을 해제함 § 아래는 기존의 suffix rule을 해제하고, ". c. pc" 룰만 지정하는 경우임. SUFFIXES: . c. pc. c: $(CC) $(CFLAGS) $(CPPFLAGS) -o $@ $<. pc. c: $(PROC) $(INC_PROC) $(ORAFLAGS) iname=$< oname=$@ Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
suffix rule (con't) v default suffix rules. c: $(LINK. c) $^ $(LOADLIBES) $(LDLIBS) -o $@. c. o: $(COMPILE. c) $(OUTPUT_OPTION) $<. cc: $(LINK. cc) $^ $(LOADLIBES) $(LDLIBS) -o $@. cc. o: $(COMPILE. cc) $(OUTPUT_OPTION) $<. o: $(LINK. o) $^ $(LOADLIBES) $(LDLIBS) -o $@ v default suffix list (. SUFFIXES). SUFFIXES: . out. a. ln. o. c. cc. C. cpp. p. f. F. r. y. l. s. S. mod. sym. def. h. info. dvi. texinfo. texi. txinfo. w. ch. web. sh. elc. el Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
automatic variables (con't) v example OUT = libgreeting. a CC = gcc CFLAGS = -Wall (%. o): %. c $(CC) $(CFLAGS) -c $< -o $% @echo "[ Add '$%' into '$@' ]" $(AR) $(ARFLAGS) $@ $% all: $(OUT) libgreeting. a: libgreeting. a(lib_greet_ko. o) libgreeting. a(lib_greet_en. o) ranlib $@ clean: -$(RM) $(OUT) *. o Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
automatic variables (con't) $ make gcc -Wall -c lib_greet_ko. c -o lib_greet_ko. o [ Add 'lib_greet_ko. o' into 'libgreeting. a' ] ar rv libgreeting. a lib_greet_ko. o ar: creating libgreeting. a a - lib_greet_ko. o gcc -Wall -c lib_greet_en. c -o lib_greet_en. o [ Add 'lib_greet_en. o' into 'libgreeting. a' ] ar rv libgreeting. a lib_greet_en. o a - lib_greet_en. o ranlib libgreeting. a Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
automatic variables (con't) OUT = libgreeting. a CC = gcc CFLAGS = -Wall (%. o): %. c 1 $(CC) $(CFLAGS) -c $< -o $% 2 @echo "[ Add '$%' into '$@' ]" 3 $(AR) $(ARFLAGS) $@ $% all: $(OUT) $ make gcc -Wall -c lib_greet_ko. c -o lib_greet_ko. o [ Add 'lib_greet_ko. o' into 'libgreeting. a' ] ar rv libgreeting. a lib_greet_ko. o libgreeting. a: libgreeting. a(lib_greet_ko. o) libgreeting. a(lib_greet_en. o) ar: creating libgreeting. a 4 ranlib $@ clean: -$(RM) $(OUT) *. o a - lib_greet_ko. o gcc -Wall -c lib_greet_en. c -o lib_greet_en. o [ Add 'lib_greet_en. o' into 'libgreeting. a' ] ar rv libgreeting. a lib_greet_en. o a - lib_greet_en. o ranlib libgreeting. a Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
build archive v example § AR, ARFLAGS 를 pre-define 시킨 뒤 사용 CC = gcc CFLAGS = -Wall –g CPPFLAGS = -I. . /include AR = ar ARFLAGS = ruv. . . (생략). . . IPCWRAP_OBJ = sem_handle. o shm_handle. o libipcwrap. a : $(IPCWRAP_OBJ) $(ARFLAGS) $@ $(IPCWRAP_OBJ) Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
build archive (con't) $ make libipcwrap. a gcc -Wall -g -I. . /include -c sem_handle. c -o. obj/sem_handle. o gcc -Wall -g -I. . /include -c shm_handle. c -o. obj/shm_handle. o ++ Building IPC Wrapper library. . . (libipcwrap. a) ar ruv libipcwrap. a. obj/sem_handle. o. obj/shm_handle. o ar: creating libipcwrap. a a -. obj/sem_handle. o a -. obj/shm_handle. o $ make "libipcwrap. a(msq_handle. o)" gcc -Wall -g -I. . /include -c -o msq_handle. c ar ruv libipcwrap. a msq_handle. o a - msq_handle. o rm msq_handle. o Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
special built-in target (con't) v Not used phony target OUT = fork_test regex_test CC = gcc all: $(OUT) clean: -$(RM) $(OUT) *. o $ ls Makefile all. c fork_test. c regex_test. c $ make gcc -Wall fork_test. c -o fork_test gcc -Wall regex_test. c gcc -Wall all. c fork_test regex_test caused error -o regex_test -o all by all. c . . . (생략). . . collect 2: ld returned 1 exit status make: *** [all] 오류 1 Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
special built-in target (con't) v solutions § specify phony target § or using pattern rule OUT = fork_test regex_test CC = gcc. PHONY: all clean all: $(OUT) clean: -$(RM) $(OUT) *. o Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
phony target v definition § phony target(가짜 목표)는 target 이 실제 파일명이 아닌 경우 § 다른 target 을 실행하기 위한 명칭으로만 사용되는 경우 § make 에게 phony 임을 명시하지 않으면 SUFFIX 룰이 지정되어 파일을 검사하게 됨 v synopsis / objectives §. PHONY 라는 special target 에 지정함 § performance 를 높이기 위해서 사용 (suffix 룰에 의한 검색이 일어나지 않음). PHONY: target_name. . . target_name : . . . Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
phony target (con't) v ordinary makefile example § 만일 all. c 가 존재한다면? (helloworld, hiworld 를 만들고 all. c 와 링킹하려 할것임) OUT = helloworld hiworld. SUFFIXES: . c. o all : $(OUT) clean : rm –f *. o $(OUT) v Good! §. PHONY 에 all, clean 을 등록함 (all. c 나 clean. c 가 존재한다고 하더라도 문제 없음). . . (생략). . PHONY: all clean all : $(OUT) clean : rm –f *. o $(OUT) Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
phony target (con't) v other phony target § GNU make standard phony target name by usage § all : default target (compile the entire program) § install : compile the program and copy the executables, libraries, and so on § uninstall : delete all the installed files § clean : delete all files from the current directory that are created by building § TAGS : update a tags table for this program § dist : create a distribution tar file for this program § check : perform self-test (if any) Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
appending setting v appending setting § assignment : » name += value § 기존의 변수에 새로운 내용을 추가할때 사용 § make 명령행에서 overriding 된 경우는 무시됨 § simply expanded setting 으로 대체가능 » name : = $(name) value Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
overriding variable v overriding variables § make VAR=VALUE. . . » make CFLAGS='-ggdb' » make "CFLAGS = -Wall" "CPPFLAGS = -I. . /inc" § make 명령을 실행하면서 변수를 지정함 § makefile 안에 있는 내용보다 우선권을 가짐 § makefile 을 직접 수정하는 것보다 좋은 이유? » makefile 이 여러 디렉토리에 분산되었을때 효율적 Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
overriding variable (con't) v override § override <expression> » override VAR = NEW_VALUE » override VAR : = NEW_VALUE » override VAR += APPENDED_VALUE § 명령행에서 overriding 된 변수가 있을 경우에도 무시되지 않고 overriding 됨 Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
pattern specified v pattern-specific variable values § PATTERN. . . : VARIABLE-ASSIGNMENT § PATTERN. . . : override VARIABLE-ASSIGNMENT %_test. o : CFLAGS = -g debug_obj : CFLAGS = -pg debug_obj : main. o modules. o testcode. o Copyright by Sun. Young Kim <sunyzero (at) gmail (dot) com>
- Slides: 45