工作中主要是通过ndk交叉编译生产arm平台的可执行程序及库,但实际调试代码时还是在x86上会更方便一些,因此对于自己编写或者移植过来的代码中没有makefile的就需要自己编写makefile来进行编译。
(一)单目录多文件Makefile编写
目录机构如下:
├── Libusb.c
├── Libusb.h
├── main.c
├── makefile
├── Makefile
├── mybluetooth.c
├── mybluetooth.h
├── obex.c
├── ObexDef.h
├── obex.h
├── ObexPack.c
└── ObexPack.h
一、 执行gcc分别编译
CFLAGS:= -g #-fshort-wchar
all : main
main : main.o mybluetooth.o Libusb.o obex.o ObexPack.o
gcc $(CFLAGS) -o main main.o mybluetooth.o Libusb.o obex.o ObexPack.o -lbluetooth `pkg-config --cflags --libs libusb-1.0` -lusb
main.o : main.c
gcc $(CFLAGS) -c main.c
Libusb.o: Libusb.c
gcc $(CFLAGS) -c Libusb.c `pkg-config --libs --cflags libusb-1.0` -lusb
mybluetooth.o : mybluetooth.c
gcc $(CFLAGS) -c mybluetooth.c -lbluetooth
obex.o: obex.c
gcc $(CFLAGS) -c obex.c
ObexPack.o: ObexPack.c
gcc $(CFLAGS) -c ObexPack.c
clean:
rm -rf *.o main .*.swp
二、使用makefile的自动推导功能
CC = gcc
CFLAGS = -g -Wall -I/usr/include/libusb-1.0 -lusb-1.0 -lusb -lbluetooth
OBJS= Libusb.o main.o mybluetooth.o obex.o ObexPack.o
main: $(OBJS)
$(CC) -o main $(OBJS) $(CFLAGS)
#以下可以不用写
#main.o: ObexDef.h
#obex.o: obex.h
#ObexPack.o: ObexPack.h ObexDef.h
#Libusb.o: Libusb.h
#mybluetooth.o: mybluetooth.h
.PHONY: clean
clean:
rm $(OBJS) main
(二)多目录多文件makefile编写
以下引用自博客园多目录下多文件 makefile编写
在编写多目录的makefile时,一般会用到如下的几个函数和变量;
函数:
wildcard 这是扩展通配符函数,功能是展开成一列所有符合由其参数描述的文 件名,文件间以空格间隔;比如:罗列出src下的所有.c文件:$(wildcard ${SRC}/*.c)
patsubst 这是匹配替换函数, patsubst ( 需要匹配的文件样式,匹配替换成什么文件,需要匹配的源文件)函数。比如:用src下的*.c替换成对应的 *.o文件存放到obj中:$(patsubst %.c, ${OBJ}/%.o, $(notdir $(SOURCE)))
notdir 这是去除路径函数,在上面patsubst函数中已经使用过,去除SOURCE中文件的所有目录,只留下文件名;
变量:
$@:表示目标文件;一般是在规则中这么用:gcc -o $@ $(object);
$^:表示所有依赖文件;一般是在规则中这么用:gcc -o $@ $^ ;用所有依赖文件链接成目的文件;
$<:表示第一个依赖文件;在规则中使用:gcc -o $@ -c $< ;其实这个时候就是每个依赖文件生成一个目的文件;
makefile模板:
#把所有的目录做成变量,方便修改和移植
BIN = ./bin
SRC = ./src
INC = ./include
OBJ = ./obj
#提前所有源文件(即:*.c文件)和所有中间文件(即:*.o)
SOURCE = $(wildcard ${SRC}/*.c)
OBJECT = $(patsubst %.c,${OBJ}/%.o,$(notdir ${SOURCE}))
#设置最后目标文件
TARGET = main
BIN_TARGET = ${BIN}/${TARGET}
CC = gcc
CFLAGS = -g -Wall -I${INC}
#用所有中间文件生成目的文件,规则中可以用 $^替换掉 ${OBJECT}
${BIN_TARGET}:${OBJECT}
$(CC) -o $@ ${OBJECT}
#生成各个中间文件
${OBJ}/%.o:${SRC}/%.c
$(CC) $(CFLAGS) -o $@ -c $<
.PHONY:clean
clean:
find $(OBJ) -name *.o -exec rm -rf {} \; #这个是find命令,不懂的可以查下资料
rm -rf $(BIN_TARGET)