Makefile的使用技巧

1、 makefile中的两种变量
COMPILE=$(CC)$(CFLAGS) -c
在使用COMPILE的时候,CC和CFLAGS才会展开,并且是每次都会展开,所以当定义COMPILE的时候,即使CC和CFLAGS还没有值,都没有关系,只要当使用COMPILE时,CC和CFLAGS有值就可以了。
OBJS=$(wildcard *.o)
OBJS每次在引用的时候,获取目标文件的列表,每一次可能都不同,并且每次计算通配符导致运行速度变慢。
 
COMPILE=:$(CC)$(CFLAGS) -c
在执行这行后,在使用COMPILE时,其值不会再变化,即使CC和CFLAGS变化了。当然可以显示的赋值给COMPILE来改变其值。
 
2、 使用函数
wildcard
SRCS := $(wildcard *.c)
获得所有的C文件列表
 
patsubst
OBJS := $(patsubst %.c,%.o,$( wildcard *.c ))
获得所有c文件对应的o文件列表
 
3、 特殊符号
%.o: %.c
        gcc -Wall -c -o $@ $<
将所有的C文件编译成O文件。
 
4、 两种编译方式
gcc -o myprogram 1.c 2.c
将1.c和2.c编译成myprogram程序。
 
gcc -c -o 1.o 1.c
将1.c编译成O文件。
 
5、 依赖性计算
gcc -M init.c > init.d
将所有的依赖文件(包括系统文件)写入d文件
gcc -MM init.c > init.d
将不包括系统文件的依赖文件写入d文件
 

6、 智能makefile模板

# Lines starting with the pound sign are comments.
#
# This is one of two options you might need to tweak.
 
EXECUTABLE = myprogram
 
# You can modify the below as well, but probably
# won't need to.
#
 
# CC is for the name of the C compiler. CPPFLAGS denotes pre-processor flags, such as -I options. CFLAGS denotes flags for the C compiler.
# CXXFLAGS denotes flags for the C++ compiler. You may add additional
# settings here, such as PFLAGS, if you are using other languages such  as Pascal.
 
CC = gcc
CPPFLAGS = 
CFLAGS = -Wall -O2
CXXFLAGS = $(CFLAGS)
COMPILE = $(CC) $(CPPFLAGS) $(CFLAGS) -c
 
SRCS := $(wildcard *.c)
OBJS := $(patsubst %.c,%.o,$(SRCS))
DEPS := $(patsubst %.c,%.d,$(SRCS))
 
# "all" is the default target. Simply make it point to myprogram.
 
all: $(EXECUTABLE)
 
# Define the components of the program, and how to link them together.
# These components are defined as dependencies; that is, they must be made up-to-date before the code is linked.
 
#最终的二进制程序依赖于d文件和o文件
$(EXECUTABLE): $(DEPS) $(OBJS)   
    $(CC) -o $(EXECUTABLE) $(OBJS)
 
# Specify that the dependency files depend on the C source files.
#生成d文件,d文件内容包括两行,o文件的依赖关系,d文件的依赖关系
%.d: %.c
    $(CC) -M $(CPPFLAGS) $< > $@
    $(CC) -M $(CPPFLAGS) $< | sed ‘s/\.o/.d/’ >> $@
 
# Specify that all .o files depend on .c files, and indicate how
# the .c files are converted (compiled) to the .o files.
#由c文件生成o文件
%.o: %.c
    $(COMPILE) -o $@ $<
 
#删除四类文件
clean:
    -rm $(OBJS) $(EXECUTABLE) $(DEPS) *~
 
explain:
    @echo "The following information represents your program:"
    @echo "Final executable name: $(EXECUTABLE)"
    @echo "Source files:     $(SRCS)"
    @echo "Object files:     $(OBJS)"
    @echo "Dependency files:   $(DEPS)"
 
depend: $(DEPS)
    @echo "Dependencies are now up-to-date."
 
#将d文件内容导入makefile中
-include $(DEPS)
7、 级联嵌套makefile

# Lines starting with the pound sign are comments.
#
# This is one of two options you might need to tweak.
 
EXECUTABLE = myprogram
 
# You can modify the below as well, but probably
# won't need to.
#
 
# CC is for the name of the C compiler. CPPFLAGS denotes pre-processor
# flags, such as -I options. CFLAGS denotes flags for the C compiler.
# CXXFLAGS denotes flags for the C++ compiler. You may add additional
# settings here, such as PFLAGS, if you are using other languages such
# as Pascal.
 
CC = gcc
CPPFLAGS = 
CFLAGS = -Wall -O2
CXXFLAGS = $(CFLAGS)
COMPILE = $(CC) $(CPPFLAGS) $(CFLAGS) -c
 
SRCS := $(wildcard *.c)
OBJS := $(patsubst %.c,%.o,$(SRCS))
DEPS := $(patsubst %.c,%.d,$(SRCS))
 
DIRS= input format
 
# "all" is the default target. Simply make it point to myprogram.
 
all: $(EXECUTABLE)
 
subdirs:
    @for dir in $(DIRS); do $(MAKE) -C $$dir; done
 
# Define the components of the program, and how to link them together.
# These components are defined as dependencies; that is, they must be
# made up-to-date before the code is linked.
 
$(EXECUTABLE): subdirs $(DEPS) $(OBJS)
    $(CC) -o $(EXECUTABLE) $(OBJS)
 
# Specify that the dependency files depend on the C source files.
# sed s///.o/.d/
 
%.d: %.c
    $(CC) -M $(CPPFLAGS) $< > $@
    $(CC) -M $(CPPFLAGS) $< | sed ‘s/\.o/.d/’ >> $@
 
# Specify that all .o files depend on .c files, and indicate how
# the .c files are converted (compiled) to the .o files.
 
%.o: %.c
    $(COMPILE) -o $@ $<
 
clean:
    -rm $(OBJS) $(EXECUTABLE) $(DEPS) *~
    @for dir in $(DIRS); do $(MAKE) -C $$dir clean; done
 
explain:
    @echo "The following information represents your program:"
    @echo "Final executable name: $(EXECUTABLE)"
    @echo "Source files:     $(SRCS)"
    @echo "Object files:     $(OBJS)"
    @echo "Dependency files:   $(DEPS)"
    @echo "Subdictionary: $(DIRS)"
 
depend: $(DEPS)
    @for dir in $(DIRS); do $(MAKE) -C $$dir; done
    @echo "Dependencies are now up-to-date."
 
-include $(DEPS)
8、 多目录结构,单执行目标文件

DIR_INC=./include
DIR_SRC=./src
DIR_OBJ=./obj
DIR_BIN=./bin
SRC=$(wildcard ${DIR_SRC}/*.cpp)
OBJ=$(patsubst %.cpp, ${DIR_OBJ}/%.o, $(notdir ${SRC}))
TARGET=main
BIN_TARGET=${DIR_BIN}/${TARGET}
INC=-I${DIR_INC}
LIB=

${BIN_TARGET}:${OBJ}
    g++ -o $@ ${OBJ} -g ${LIB}
${DIR_OBJ}/%.o:${DIR_SRC}/%.cpp
    g++ -o $@ -c $< ${INC} -g
clean:
    find ${DIR_OBJ} -name *.o -exec rm -rf {} \;

你可能感兴趣的:(模板,makefile)