基本Makefile
假设现在有3个文件,file2.h是函数声明,file2.c是函数定义,文件file1.c调用file2.c中的函数。则Makefile文件的编写如下:

helloworld:file1.o file2.o
gcc file1.o file2.o -o helloworld
file1.o:file1.c file2.h
gcc -c file1.c -o file1.o
file2.o:file2.c file2.h
gcc -c file2.c -o file2.o
clean:
rm -rf *.o helloworld

2 自动推导

helloworld:file1.o file2.o
gcc file1.o file2.o -o helloworld
%.o:%.c
gcc -c $< -o $@
clean:
rm -rf *.o helloworld

3 变量使用

CC= gcc
CFLAGS= -I/home/mymakefile/include
LDFLAGS= -L/home/mymakefile/lib
LIBS = -lsocket -lmath
CFLAGS= -g -Wall -O2
#PATH = /path/to/bin
SRCS=file1.c file2.c
OBJS=file1.o file2.o
TARGET=helloworld $(TARGET):$(OBJS)
$(CC) $(CFLAGS) $(OBJS) -o $(TARGET)
%.o:%.c
$(CC) -c $< -o $@
clean:
rm -rf $(OBJS) $(TARGET)

4 特殊符号使用
这里$^因为会包含依赖的文件名,如果包含的该文件存在,那么将返回其含路径的文件名
所以$(wildcard $^)就是用来过滤$^包含的所有文件并且该文件确实在本地存在.

自动化变量$?代表依赖文件列表中被改变过的所有文件。
自动化变量$^代表所有通过目录搜索得到的依赖文件的完整路径名(目录 + 一般文件名)列表。
自动化变量$@代表规则的目标。
自动化变量$<代表规则中通过目录搜索得到的依赖文件列表的第一个依赖文件。
自动化变量$(@D)

5 关键词使用

wildcard
subst
  用法是$(subst FROM,TO,TEXT),即将TEXT中的东西从FROM变为TO
TARGETS = 111.cpp 222.cpp 333.cpp
OTARGETS= $(subst cpp,o,$(TARGETS))
LTARGETS= $(subst cpp,lo,$(TARGETS))

patsubst <pattern>,<replacement>,<text> )
(patsubst %.c,%.o,x.c.c bar.c)

把字串“x.c.c bar.c”符合模式[%.c]的单词替换成[%.o],返回结果是“x.c.o bar.o”

$(wildcard PATTERN...) 。在Makefile中,它被展开为已经存在的、使用空格分开的、匹配此模式的所有文件列表。
一般我们可以使用“$(wildcard *.c)”来获取工作目录下的所有的.c文件列表。

可以使用“$(patsubst %.c,%.o,$(wildcard *.c))”,首先使用“wildcard”函数获取工作目录下的.c文件列表;之后将列表中所有文件名的后缀.c替换为.o。

filter

6 选项使用

7 进入子目录

在学习Makefile过程中,一般是Makefile文件和源码、头文件存放在同一个目录中,但对于我们实际的工作过程中,通常是分开的。分开主要有两种方式,一种是根据模块,一种是根据文件的不同。如下面两图:

     

对于第一种,按照文件类型进行划分代码,只需要一个Makefile文件就可以,具体的形式如下所示:

 ###########################################
# Makefile
# By Guo Jianwei
# --
# EMAIL: gjianw217@.com
###########################################
NAME = app
BIN = bin/debug/$(NAME) CC = gcc
CXX = g++ LINKOPT = -O3
FLAGS = $(LINKOPT) LIBS =
CFLAGS = $(LIBS)
CXXFLAGS = $(LIBS) -g INCS = -I$(INCPATH)/common\
-I$(INCPATH)/third-party SRCPATH = src/
INCPATH = include SRCS = $(shell find $(SRCPATH) -name '*.c' -o -name '*.cpp' \
-o -name '*.cc' \
| grep -v 'socket') OBJS = $(filter %.o,$(SRCS:%.c=%.c.o))
OBJS += $(filter %.o,$(SRCS:%.cpp=%.cpp.o))
OBJS += $(filter %.o,$(SRCS:%.cc=%.cc.o)) .PHONY: clean print all: print $(BIN) print:
@echo "===================================================="
@echo " $(BIN)"
@echo "====================================================" $(BIN): $(OBJS)
$(CXX) $(FLAGS) -o $@ $^ %.c.o: %.c
$(CXX) $(CFLAGS) $(INCS) -o $@ -c $^ %.cpp.o: %.cpp
$(CXX) $(CXXFLAGS) $(INCS) -o $@ -c $^ %.cc.o: %.cc
$(CXX) $(CXXFLAGS) $(INCS) -o $@ -c $^ clean:
rm -rf $(BIN) $(OBJS)

对于第二种,按照功能进行组织代码,在每个功能模块中,都需要包含一个Makefile文件,具体的形式如下:

 #Makefile
###########################################
# Makefile
# By Guo Jianwei
# --
# EMAIL: gjianw217@.com
###########################################
OBJ=fun1/fun1.o\
fun2/fun2.o\
main.o
DEL=fun1/fun1.h\
fun2/fun2.h
SRC=$(patsubst %.o,%.cpp,$(OBJ))
TARGET=app
.PHONY:all fun1 fun2 app
all:fun1 fun2 app
fun1:
$(MAKE) -C fun1
fun2:
$(MAKE) -C fun2
$(TARGET):$(OBJ)
g++ -o $(TARGET) $(OBJ) $(DEL)
%.o:%.cpp
g++ -c $< $(DEL)
clean:
rm $(OBJ) $(TARGET) ###########################################
#Makefile fun1
# By Guo Jianwei
# --
# EMAIL: gjianw217@.com
###########################################
OBJ=\
fun1.o
DEP=\
fun1.h
SRC=\
fun1.cpp
$(OBJ):$(SRC)
@echo "fun1 fun1"
g++ -c $< $(DEP) ###########################################
#Makefile fun2
# By Guo Jianwei
# --
# EMAIL: gjianw217@.com
###########################################
OBJ=fun2.o
DEP=$(patsubst %.o,%.h,$(OBJ))
SRC=$(patsubst %.o,%.cpp,$(OBJ))
CXX=g++
CFLAGS= -O2 -c -Wall -g
#$(OBJ):$(SRC)
# $(CXX) $(CFLAGS) $<
$(OBJ):%.o:%.cpp
$(CXX) $(CFLAGS) $< $(DEP)

完整的测试代码

1. Linux驱动开发之开篇--Makefile的更多相关文章

  1. Linux驱动开发之开篇--HelloWorld

    Linux驱动的编写,大致分为两个过程,第一个过程为测试阶段,即为某一具体的设备,添加必要的驱动模块,为了节省编译时间,需要将代码单独放在一处,在编译时,只需要要调用内核的头文件即可:第二个过程为布置 ...

  2. 嵌入式Linux驱动开发日记

    嵌入式Linux驱动开发日记 主机硬件环境 开发机:虚拟机Ubuntu12.04 内存: 1G 硬盘:80GB 目标板硬件环境 CPU: SP5V210 (开发板:QT210) SDRAM: 512M ...

  3. Linux驱动开发学习的一些必要步骤

      1. 学会写简单的makefile 2. 编一应用程序,可以用makefile跑起来 3. 学会写驱动的makefile 4. 写一简单char驱动,makefile编译通过,可以insmod, ...

  4. Linux 驱动开发

    linux驱动开发总结(一) 基础性总结 1, linux驱动一般分为3大类: * 字符设备 * 块设备 * 网络设备 2, 开发环境构建: * 交叉工具链构建 * NFS和tftp服务器安装 3, ...

  5. s3c6410 Linux 驱动开发环境搭建

    s3c6410 Linux 驱动开发环境搭建 -- 既然你是做Linux开发的,你还用虚拟机? 非常多人都在win下做开发,于是SD_writer.exe之类的烧写工具"大行其道" ...

  6. 嵌入式linux驱动开发之点亮led(驱动编程思想之初体验)

    这节我们就开始开始进行实战啦!这里顺便说一下啊,出来做开发的基础很重要啊,基础不好,迟早是要恶补的.个人深刻觉得像这种嵌入式的开发对C语言和微机接口与原理是非常依赖的,必须要有深厚的基础才能hold的 ...

  7. 【转】linux驱动开发的经典书籍

    原文网址:http://www.cnblogs.com/xmphoenix/archive/2012/03/27/2420044.html Linux驱动学习的最大困惑在于书籍的缺乏,市面上最常见的书 ...

  8. Linux驱动开发 -- 打开dev_dbg()

    Linux驱动开发 -- 打开dev_dbg() -- :: 分类: LINUX linux设备驱动调试,我们在内核中看到内核使用dev_dbg来控制输出信息,这个函数的实质是调用printk(KER ...

  9. 驱动编程思想之初体验 --------------- 嵌入式linux驱动开发之点亮LED

    这节我们就开始开始进行实战啦!这里顺便说一下啊,出来做开发的基础很重要啊,基础不好,迟早是要恶补的.个人深刻觉得像这种嵌入式的开发对C语言和微机接口与原理是非常依赖的,必须要有深厚的基础才能hold的 ...

随机推荐

  1. Honda HDS IMMO PCM Code calculator Free Download

    HDS IMMO PCM Code calculator software for Honda vehicle models is free download available in Eobd2.f ...

  2. 浅谈JS执行环境及作用域

     今天刚刚开通博客,也是第一次写博文,略感紧张.作为一个表达能力弱弱的人来说,自己花三分钟理解一个知识点,当别人问起时,也许需要30分钟才只是让别人知道自己在说什么,一点也不夸张,希望在博客上可以练习 ...

  3. Syntax highlighter for CKEditor

    http://www.cnblogs.com/moozi/archive/2010/01/06/1640034.html

  4. xmlns="http://schemas.xmlsoap.org/wsdl/",这是什么意思,我只知道:xmlns:xx=....,

    表示没有prefix,相当于你的xsi为空.这个很常用,后面就省得每行都要加一个前缀了. 解决方案 » "后面就省得每行都要加一个前缀了",意思是,后面的子元素如果没有名称空间前缀 ...

  5. javaweb学习总结六(泛型)

    一:泛型的概念 泛型用来现在集合中的存储类型,防止取出时强制转换发生错误. 1:没有使用泛型时,如下: @Test public void test1() { List list = new Arra ...

  6. UseAdaptiveSizePolicy与CMS垃圾回收同时使用导致的JVM报错

    系统在灰度环境上变更时发现JVM启动报错,详细检查JVM配置参数,发现新境了如下配置: -XX:+UseAdaptiveSizePolicy和-XX:+UseConcMarkSweepGC 初步猜想是 ...

  7. https抓包判断证书问题

    openssl s_client -connect 61.135.250.130:443这个是reg.163.com的 tcpdump 也可

  8. Codevs 2307[SDOI2009]HH的项链

    同题:     Codevs 2307 HH的项链     BZOJ    1878 HH的项链     洛谷      1972 HH的项链 2009年省队选拔赛山东  时间限制: 1 s  空间限 ...

  9. jQuery之手势密码

    <!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8&quo ...

  10. centos6.5下磁盘分区及挂载

    1..查看磁盘空间 2.磁盘分区 3.格式化分区 4.挂载/卸载