前面的两篇文章中都用到了make的方式来构造hello内核模块,下面就来
简单的分析一下其中的Makefile的语法:
- # 如果已定义了KERNELRELEASE,则说明是从内核构造系统调用的,
-
# 因此可利用其内建语句:obj-m := hello.o
-
ifneq ($(KERNELRELEASE),)
-
obj-m := hello.o # 该语句使用了GNU make的扩展语法,说明了有一个模块需要从
- # 目标文件hello.o中构造,而从该目标文件中构造的模块名称
- # 为hello.ko。如果我们要构造的模块名称为modules.ko,并由
- # 两个源文件file1.c & file2.c生成,则这里应该写为:
- # obj-m := module.o
- # module-objs := file1.o file2.o
-
-
# 否则,是直接从命令行调用的,此时要调用内核构造系统。
-
else
-
KERNELDIR ?= /home/moran/program/micro2440/kernel/linux-2.6.32.2
-
PWD := $(shell pwd)
-
-
default:
-
$(MAKE) -C $(KERNELDIR) M=$(PWD) # 此命令首先改变目录到-C选项指定的位
- # 置(即内核源代码目录),其中保存有
- # 内核的顶层Makefile文件。 M=选项让
- # 该Makefile在构造modules目标之前返
- # 回到模块源代码目录。然后,modules目
- # 标指向obj-m变量中设定的模块,此例
- # 中,我们设置成了hello.o
-
-
clean:
-
rm -rf *.o *~ core .depend .*.cmd *.ko *.mod.c .tmp_versions
-
-
endif
在一个典型的构造过程中,该Makefile将被读取两次。
当从命令行执行make命令时,该Makefile将会被调用,此时是第一次读取
该Makefile,变量KERNELRELEASE没有设置,ifneq条件不满足,所以会运行else
分支,根据变量KERNELDIR指定的路径找到内核源码树。
接着第二次运行make命令,以便运行内核构造系统,在第二次读取该
Makefile文件时,它设置了obj-m,而内核的Makefile真正负责构造此模块。
阅读(3796) | 评论(0) | 转发(0) |