文章目录
  1. 1. 内核源码中的make
  2. 2. 实例
  3. 3. makefile实例解读
  4. 4. make中报错
  5. 5. tipsl:

吉姆雷诺

在linux下编写C程序一般要通过make工程管理器完成编译,编译过程分为编译、汇编、链接3个阶段。在编译过阶段自动读入makefile文件(makefile的内容)来执行编译工作。同时根据文件时间戳自动发现更新过的文件而减少编译的过程。

linux下软件开发流程

规则的格式

1
2
target(目标): dependency_files(依赖文件)
<tab> :command(命令)

内核源码中的make

  1. 设置编译器路径

    1
    2
    3
    4
    5
    export KBUILD_BUILDHOST := $(SUBARCH)
    ARCH ?= arm

    CROSS_COMPILE ?= /usr/local/arm/arm-2009q3/bin/arm-none-linux-gnueabi- #这个与.bashrc中的编译器一样
    #CROSS_COMPILE ?= /usr/local/arm/4.5.1/bin/arm-none-linux-gnueabi-
    CROSS_COMPILE ?= $(CONFIG_CROSS_COMPILE:"%"=%)

  2. 强制编译

    源码开发者强制要求编译进内核的文件

打开内核源码中drivers/Makefile文件
类似下面写法,只要编译内核就必须编译这个文件

1
2
3
4
5
6
obj-y                           += gpio/
obj-$(CONFIG_PCI) += pci/
obj-$(CONFIG_PARISC) += parisc/
obj-$(CONFIG_RAPIDIO) += rapidio/
obj-y += video/
obj-y += idle/

  1. 配置编译

    通过源码中Kconfig 配置选择编译
    例如打开drivers/char/Makefile文件如果定义了宏文件

    1
    obj-$(CONFIG_MAX485_CTL)        += max485_ctl.o
    obj-$(CONFIG_LEDS_CTL)          += itop4412_leds.o
    obj-$(CONFIG_BUZZER_CTL)        += itop4412_buzzer.o
    obj-$(CONFIG_ADC_CTL)           += itop4412_adc.o
    obj-$(CONFIG_RELAY_CTL)         += itop4412_relay.o

如果定义了这个宏 CONFIG_LEDS_CT 把itop4412/leds.c编译成.o文件

CONFIG_LEDS_CTL这个宏在源码中.config中定义了

1
2
3
4
5
6
CONFIG_S3C_MEM=y
CONFIG_EXYNOS_MEM=y
CONFIG_GPS_PM=y
CONFIG_MAX485_CTL=y
CONFIG_HELLO_CTL=y
CONFIG_LEDS_CTL=y

在menuconfig中配置,编译根据.config中宏是否定义而进行编译

  1. 依赖编译
    – 一个驱动的编译需要另外驱动的支持
    – 这一部分不需要另外写编译脚本,只需要在Kconfig中配置即可
    • 例如显卡驱动VIDEO_JPEG_V2X中需要MEDIA_SUPPORT等驱动,那么编
    译显卡驱动的同时也需要将依赖的驱动选上

VIDEO_JPEG_V2X中需要MEDIA_SUPPORT等驱动

Linux内核编译流程分析

  • make menuconfig调用scripts通过各级Kconfig文件构成menuconfig配置界面 保存生成config

    强制编译无法在menucofing配置

  • 执行Make ,编译器找各级Makefile生成zImage二进制镜像

实例

实例1.
驱动进内核
在menuconfig选中

在4412目标版上执行

1
[root@iTOP-4412]# ls /dev/led*

menuconfig选中LEDS

在PC上烧写zImgae

1
2
3
4
5
6
7
8
9
10
11
12
13
D:\T\platform-tools>fastboot.exe flash kernel zImage
sending 'kernel' (3919 KB)...
OKAY [ 0.613s]
writing 'kernel'...
OKAY [ 0.400s]
finished. total time: 1.013s

D:\T\platform-tools>fastboot reboot
rebooting...

finished. total time: 0.003s

D:\T\platform-tools>

在目标板上查询

1
2
[root@iTOP-4412]# ls /dev/led*
/dev/leds

如果重新在menuconfig不选择

1
[*] Enable LEDS config

则在重新给开发板烧写zImage是则不能查询到leds

1
2
  [root@iTOP-4412]# ls /dev/led*
ls: /dev/led*: No such file or directory

makefile实例解读

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
TARGET          = ../../debug/libGate_Gunnebo.so
CFLAG = -g -D __LINUX__ -D linux -std=gnu++11 -lpthread
LIBCREATE = -shared -fPIC
LDFLAG = -L. -lZBLCommunication -Wl,-rpath,./
#两个功能; 一个是加载./libZBLCommunication.so 两个功能,一个是加载./libZBLCommunication.so
SOURCE = CGate_Gunnebo.cpp gate.cpp

HEADER = CGate_Gunnebo.h pch.h gate.h

$(TARGET):$(SOURCE) $(HEADER) libZBLCommunication.so
g++ $(CFLAG) $(LIBCREATE) $(LDFLAG) $(SOURCE) -o $@
#` $@` 等价于 `$TARGET`

#CGate_Gunnebo.o:CGate_Gunnebo.cpp
# g++ $^ $(CFLAG) -c CGate_Gunnebo.cpp

#gate.o:gate.cpp
# g++ $^ $(CFLAG) -c gate.cpp

clean:
rm *.o

make中报错

1
2
3
4
5
6
7
8
9
10
11
12
13
14
../release/libPCM_YCMJX.so:CFLAGS= -g
../release/libPCM_YCMJX.so:MIS_Commonality.o PCM_YCMJX.o
# g++ $(CFLAGS) -D __LINUX__ -shared -fPIC -o ../release/libPCM_YCMJX.so MIS_Commonality.o PCM_YCMJX.o -lpthread -L. -lZBLCommunication -Wl,-rpath,./
g++ $(CFLAGS) -D __LINUX__ -lmcheck -shared -fPIC -o ../release/libPCM_YCMJX.so MIS_Commonality.o PCM_YCMJX.o -lpthread -L. -lZBLCommunication -Wl,-rpath,./
rm *.o

PCM_YCMJX.o:PCM_YCMJX.cpp
g++ $(CFLAGS) -D __LINUX__ -c -fPIC PCM_YCMJX.cpp

MIS_Commonality.o:../MIS_Commonality/MIS_Commonality.cpp
g++ $(CFLAGS) -D __LINUX__ -c -fPIC ../MIS_Commonality/MIS_Commonality.cpp

clean:
rm *.o
  1. make: * No rule to make target ‘MIS_Commonality.cpp’, needed by ‘MIS_Commonality.o’. Stop.

解决:

makefile里面的文件依赖关系有问题,导致头文件找不到。

解决办法:
MIS_Commonality/MIS_Commonality.cpp这个目录文件放到相应的位置,即可

  • No rule to make target
    1
    root@vmubuntu:/home/takethat/test_so/class_dynamic# make
    rm -rf *.so a.out b.out
    make: *** No rule to make target `test_1.o', needed by `test_1.so'.  Stop.

解决:
目标文件的依赖文件不存在

也可能是依赖文件名对不上


tipsl:

shell脚本及makefile中的特殊变量

文章目录
  1. 1. 内核源码中的make
  2. 2. 实例
  3. 3. makefile实例解读
  4. 4. make中报错
  5. 5. tipsl: