linux驱动内核哪个文件夹,linux设备驱动归纳总结(一):内核的相关基础概念...

linux设备驱动归纳总结(一):内核的相关基础概念

1. 内核与 linux 设备驱动的作用与关系

内核:用于管理软硬件资源,并提供运行环境。如分配 4G 虚拟空间等。

linux 设备驱动:是连接硬件和内核之间的桥梁。

linux 系统按个人理解可按下划分:

1). 应用层:包括 POSIX 接口, LIBC ,图形库等,用于给用户提供访问内核的接口。属于用户态 ARM 运行在用户模式 (usr) 或者系统模式 (sys) 下。

2). 内核层:应用程序调用相关接口后,会通过系统调用,执行 SWI 指令切换 ARM 的工作模式到超级用户(svc) 模式下,根据用户函数的要求执行相应的操作。

3). 硬件层:硬件设备,当用户需要操作硬件时,内核会根据驱动接口操作硬件设备

图结构如下:

67d69e1988eac3d07ee1ee864ec29244.png

举一个相对比较邪恶的类比:

在深圳的酒店经常会在门缝看到一些卡片,上面说可以通过打电话送货上门提供某中服务。

57d1556fece1316e0db112ffd1bfc850.png

===============================================

2. 内核代码树介绍

linux-2.6.29

|- arch :包含和硬件体系结构相关的代码

|- block:硬盘调度算法,不是驱动

|- firmware:固件

|- Documentation:标准官方文档

|- dirver: linux 设备驱动

|- fs:内核所支持的文件体系

|- include:头文件。 linux/module.h linux/init.h常用库。

|- init:库文件代码, C 库函数在内核中的实现。

init/main.c ->start_kernel-> 内核执行第一条代码

|- ipc :进程件通信

|- mm:内存管理

|- kernel:内核核心部分,包括进程调度等

|- net:网络协议

|- sound:所有音频相关

其中,跟设备驱动有关并且经常查阅的文件夹有:

init

include : linux, asm-arm

drivers:

arch:

===============================================

3. 内核补丁:

补丁一般都是基于某个版本内核生成的,用于升级旧内核。

打补丁需要注意:

1. 对应版本的补丁只能用于对应版本的内核。

2. 如果在已打补丁的内核再打补丁,需要先卸载原来补丁。

打补丁的方法:

1. 制作补丁:

diff -Nur linux-2.6.30/ linux-2.6.30.1/ > linux-2.6.30.1.patch

//N 为新加的文件全部修改

//linux-2.6.30旧版本

//linux-2.6.30.1新版本

// 目标补丁

2. 打补丁:

cd linux-2.6.30// !!注意在原文件夹的目录中打补丁

patch -p1 < ../linux-2.6.30.1.patch//-p1 是忽略一级目录

3. 恢复:

cd linux-2.6.30// !!注意在原文件夹的目录中打补丁

patch -R < ../linux-2.6.30.1.patch// 撤销补丁

===============================================

4. 内核中的 Makefile :

对于内核, Makefile 分为 5 类:

Documentation/kbuild/makefiles.txt 描述如下:

50 The Makefiles have five parts:

51

52Makefile总Makefile,控制内核的编译

53.config内核配置文件,配置内核时生成,如make menuconfig后

54arch/$(ARCH)/Makefile对应体系结构的Makefile

55scripts/Makefile.*Makefile共用的规则,如图形配置界面。

56kbuild Makefiles各子目录下的Makefile,被上层的Makefile调用

简单来说,编译内核会执行以下事情。

1.make menuconfig

1.1 拷贝一个对应体系结构的配置文件到主目录下并改名为 .config ,这样就在 makemenuconfig生成的图形配置中已经有了一些默认的配置,减少用户的劳动量。

1.2 从内核顶层目录的 Makefile 决定编译的体系结构 (ARCH). 编译工具 (CROSS_COMPILE) 和需要进去编译的目录。

1.3 根据总 Makefile 的 ARCH 变量,进入相应体系结构的目录,读取 arch/$(ARCH)/Makefile, 决定对应的体系结构下还有哪些目录需要编译。

1.4 根据 arch/$(ARCH)/Makefile ,一个一个地递归进入指定的目录下调用该目录下的 makefile ,并根据目录下的 Kconfig 生成配置界面并由用户决定将该文件编译成模块还是编译进内核。

1.5 配置完毕后保存退出,会更改原来的 .config 的内容。

2.make

1.1 将生成的 .config 去掉注释,新建一份配置文件,文件名为 include/config/auto.conf 。

1.2 根据配置文件的要求,将需要编译的文件的各个子目录下生成一个 .o 或者 .a 文件,然后由总Makefile 指定的连接脚本 arch/$(ARCH)/kernel/vmlinux.lds 生成 vmlinux ,并通过压缩变成bzImage ,或者按要求在对应的子目录下编译成模块。

但是,具体是怎么生成配置文件的呢?

注:我使用的内核是被修改过的,可能有些地方和原内核不一样,如我内核里面 $(ARCH) 写成$(SRCARCH) 。还有在文件中的行数和原内核不一致,但这些不影响分析,搜索一下就出来了。

1. 在总 Makefile 中,根据以下语句进入需要编译的目录

470 # Objects we will link into vmlinux / subdirs we need to visit

471 init-y:= init/

472 drivers-y:= drivers/ sound/ firmware/

473 net-y:= net/

474 libs-y:= lib/

475 core-y:= usr/

476 endif # KBUILD_EXTMOD

639 core-y+= kernel/ mm/ fs/ ipc/ security/ crypto/ block/

#另外还有一个体系相关的arch目录

529 include $(srctree)/arch/$(SRCARCH)/Makefile

这样,就根据了体系结构决定了需要进去编译的目录了。

2. 在总 Makefile 中包含的目录还是不够的,内核还需要根据对应的 CPU 体系架构,决定还需要将哪些子目录将要编译进内核,在总 Makefile 中进去读取相应体系结构的 Makefile : arch/$(SRCARCH)/Makefile。

在总 Makefile 和体系架构下的 arch/(SRCARCH)/Makefile 中包含的子目录会根据该目录下的 Makefile的要求编译成模块还是编译进内核,当然也可以不编译。

如在arch/arm/Makefile下:

187 # If we have a machine-specific directory, then include it in the build.

188 core-y+= arch/arm/kernel/ arch/arm/mm/ arch/arm/common/

189 core-y+= $(machdirs) $(platdirs)

190 core-$(CONFIG_FPE_NWFPE)+= arch/arm/nwfpe/

191 core-$(CONFIG_FPE_FASTFPE)+= $(FASTFPE_OBJ)

192 core-$(CONFIG_VFP)+= arch/arm/vfp/

193

194 drivers-$(CONFIG_OPROFILE)+= arch/arm/oprofile/

195

196 libs-y:= arch/arm/lib/ $(libs-y)

其中, y 表示编译成模块, m 表示编译进内核 ( 上面没有,因为默认情况下 ARM 全部编译进内核 ) ,但$(CONFIG_OPROFILE) 又是什么呢?

这些是根据用户在 make menuconfig 中设置后,生成的值赋给了 CONFIG_OPROFILE 。这是由各子目录下的 Kconfig 提供选项功用户选择并配置。如 arch/arm/Kconfig 。

另外有些配置会根据 arch/$(ARCH)/Kconfig 文件通过 Kconfig 的语法 source 读取各个包含的子目录Kconfig 来生成一个配置界面。每个 Makefile 目录下都有一个对应 Kconfig 文件,用于生成配置界面来给用户决定内核如何配置。

总结 Kconfig 的作用:

2.1. 在 make menuconfig 下可以配置选项 ;

2.2. 在 .config 中确定 CONFIG_XXX 的的值。

3. 只是读取以上的两个 Makefile 还是不够了,内核还会把包含的子目录一层一层的读取它里面的 Makefile和 Kconfig 。

假设我现在配置内核

1. 最简单的方法,直接修改子目录的 Makefile

如在我要取消 s3c2440 的时钟 ( 当然这是必须要开的,只是举例 ) 。

可以直接修改 arch/arm/mach-s3c2440/Makefile

12 obj-$(CONFIG_CPU_S3C2440)+= s3c2440.o dsc.o

13 obj-$(CONFIG_CPU_S3C2440)+= irq.o

14 obj-$(CONFIG_CPU_S3C2440)+= clock.o

15 obj-$(CONFIG_S3C2440_DMA)+= dma.o

将 obj-$(CONFIG_CPU_S3C2440)+= clock.o 改为

obj-+= clock.o

也可以编译成模块:

obj-m+= clock.o

2. 当然有更方便的通过图形界面, make menuconfig ,接下来我实现一下如何将一个选项加入到图形配置界面中。

2.1. 进入内核目录

cd linux-2.6.29

2.2. 在 driver 目录下模拟一个名为 test1 驱动的文件夹

mkdir driver/test1

2.3. 在 test1 目录下随便写个 C 文件

cd driver/test1

vim test1.c

1 void foo()

2 {

3 ;

4 }

2.4. 在目录下编写一个简单的 Makefile

vim Makefile

obj-$(CONFIG_TEST1) += test1.o

CONFIG_TEST1 是决定 test1 是否编译进内核或者编译成模块的。这就通过 Kconfig 由用户在make menuconfig 中选择。

2.5. 所以还要在目录下写一个 Kconfig

vim Kconfig

1 menu "test1 driver here"

2 config TEST1

3bool "xiaobai test1 driver"

4help

5This is test1

6 endmenu

说白了,就是在图形配置的 driver 下多了一个配置选项,用户配置后将 CONFIG_TEST1 的值存放在.config 中, Makefile 通过读取 .config 的去注释版 autoconf 读取到 CONFIG_TEST 的值,再进行编译。但是,以上几步还不能达到目的,因为虽然在总 Makefile 中已经包含了目录 driver, 但是 driver 目录的 Makefile 中并没有包含 test 目录。因此需要在 driver/Makefile 中添加:

2.6.vim driver/Makefile

再最后加上一句:

104 obj-$(CONFIG_OF)+= of/

105 obj-$(CONFIG_SSB)+= ssb/

106 obj-$(CONFIG_VIRTIO) += virtio/

107 obj-$(CONFIG_STAGING)+= staging/

108 obj-y+= platform/

109 obj-$(CONFIG_TEST1)+= test1///添加这句

虽然 Makefile 中已经包含了,但这样还是不行。因为当需要配置 ARM 时, ARM 结构下的 Kconfig并没有包含 test 的 Kconfig 。这样的话就不会出现在图形配置界面中,因此在 arch/arm/Kconfig 中添加语句。

2.7.vim arch/arm/Kconfig

1230 menu "Device Drivers"

1231

1232 source "drivers/base/Kconfig"

…..............................................

1328 source "drivers/staging/Kconfig"

1329

1330 source "drivers/test1/Kconfig"

1331

1332 endmenu

大功告成!

这样, make menuconfig 界面写的 Driver Devices 下就多了一个 "test1 driver here" 的目录,里面有一个配置选项 "xiaobai test1 driver" 。

Kconfig 文件的语法在 documentation/kbuild/kconfig-language.txt 文件中有详细的讲解,上面我只是简单实现了一下 , 但都是皮毛。

==============================================

5. 编译内核

编译内核很简单,只需要配置完毕后执行 make 命令,将指定的文件编译进内核

bzImage 或者编译成模块。

make = make bzImage + make modules

因此如果值编译内核,即只编译配置文件中 -y 选项,可以直接用命令

make bzImage

如果值编译模块,即只编译配置文件中的 -m 选项,可以之直接使用命令

make modules

模块可以编译当然也可以清除,使用命令

make modules clean

如果只想单独编译一个模块,可以使用命令

make M=drivers/test/ modules // 只单独编译 drivers/test 中的 .ko

make M=drivers/test/ modules clean// 清除

上面的是在内核目录下的操作,但当我写驱动时,我并不可能在内核目录下编

写,但我编译时却要依赖内核中的规则和 Makefile ,所以就有了以下的方法,

同时这也是一般的编写驱动时 Makefile 的格式。

指定内核 Makefile 并单独编译

make -C /root/linux-2.6.29 M=`pwd` module

make -C /root/linux-2.6.29 M=`pwd` module clean

//-C指定内核 Makefile 的路径,可以使用相对路径。

//-M指定要编译的文件的路径,同样课使用相对路径。

编译生成的模块可以指定存放的目录

make -C /root/linux-2.6.29 M=`pwd` modules_install INSTALL_MOD_PATH=/nfsroot

=======================================================================

以上都是个人理解,如内核的 Makefile 配置和编译时一个复杂的过程,我简单地描述了一下,并不保证一定正确。

错误地方,请指正。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/298736.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

怪不得超市不让带宠物...

1 难怪超市不让带狗啊▼2 医学生的聊天记录过于硬核▼3 你身边的外卖小哥头盔上都顶着什么呢&#xff1f;▼4 表妹非要把猫脸P到蜜蜂身上▼5 其实主要还是看脸脸到位了&#xff0c;祖安小公举问题都不大▼6 就你们这个送别方式我觉得他是回不来了......▼7 妹妹沦为工具…

自定义控件复选框和单选框的实现

我们先实现单个按钮&#xff0c;为了复用&#xff0c;不管单选还是复选按钮都是使用同一个类来实现&#xff0c;为了区别单选还是复选&#xff0c;我们用一个自定义枚举类型CheckButtonStyle属性style来区别&#xff0c;当其值设置为CheckButtonStyleDefault或CheckButtonStyle…

单文件组件的组件传值_移动端组件化架构(下)

我的组件化方案对于项目架构来说&#xff0c;一定要建立于业务之上来设计架构。不同的项目业务不同&#xff0c;组件化方案的设计也会不同&#xff0c;应该设计最适合公司业务的架构。架构设计以我之前公司项目为例&#xff0c;项目是一个地图导航应用&#xff0c;业务层之下的…

为什么圆是360度?超颠覆的解释

圆为什么有360度&#xff1f;为什么不是300度呢&#xff1f;古文明时期人类把很多不能解释的自然现象归结为“天意”真的有天意吗&#xff1f;我们把圆分成等份&#xff0c;奇迹出现了.....依次等分下去&#xff0c;结果一样...任何被分成等分的角度的所有数字之和为9现在我们来…

我获得“微软MVP”奖项,后续将会贡献更多技术内容

昨天晚上&#xff0c;我收到了微软总部发来的“恭喜获得MVP”的邮件。请点击【阅读原文】查看我的MVP Profile页面。有的朋友说“一直以为你早就是MVP了”。其实这么多年我做的技术贡献主要是录编程视频教程&#xff0c;而这些视频教程都是通过BT下载等方式传播&#xff0c;没有…

[Spring MVC] - InitBinder验证

Spring MVC使用InitBinder验证&#xff1a; 使用InitBinder做验证的情况一般会在此Controller中提交的数据需要有一些是业务性质的&#xff0c;也即比较复杂的验证情况下才会使用。大部份简单的表单验证&#xff0c;使用annotation验证即可以解决。 Annotation验证使用方法可参…

linux6.5进入救援模式,rhel6.5救援模式修复系统

如果系统中很多重要的部分被删除了例如/boot下的所有东西&#xff0c;则可以通过救援模式[rootdazzle1 桌面]# mkdir /backup[rootdazzle1 桌面]# cp /etc/fstab /backup/fstab  //先备份以下fstab文件&#xff0c;也可以不备份自己写[rootdazzle1 桌面]# rm -rf /boot/*  …

一名毕业生的自述:我知道我必须写论文,但没聪明到可以写出来......

全世界只有3.14 % 的人关注了爆炸吧知识2020年转眼就到了4月。在即将毕业的学子之间&#xff0c;每天的狂野问候语是这样的&#xff1a;“你论文改完了吗&#xff1f;”“你论文查重率是多少&#xff1f;”“你什么时候答辩&#xff1f;”在微博上实时搜索“翟天临”三个字&…

不是架构的架构之四:业务层的实现与自动代理

我们在开篇中提到&#xff0c;希望能有一种办法&#xff0c;能自动适应系统的环境配置&#xff0c;在局域网小型应用中将直接访问数据库以获得最高的性能&#xff0c;在分布式环境中自动使用WCF来获得较好的安全性和连通性。 但是&#xff0c;我们不希望这样的特性使我们的开发…

python程序设计实践教程陈东_Python

“我们正步入一个数据或许比软件更重要的新时代。——Tim OReilly” 运用数据是精准刻画事物、呈现发展规律的主要手段&#xff0c;分析数据展示规律&#xff0c;把思想变得更精细&#xff01; 本课程面向各类编程学习者&#xff0c;讲解利用Python语言表达N维数据并结合数据特…

Silverlight中开发和设计人员的合作文档信息

-----------------------------------------------------------------------------------> copyright:http://www.docin.com/p-34191215.html转载于:https://www.cnblogs.com/molin/archive/2009/12/08/silverlight_manager.html

和男朋友一块儿吃VS单独一人在家吃饭

1 和男朋友一块儿吃VS单独一人在家吃饭2 忍不住要为这位跳高选手鼓掌了3 我们家的蔬菜就没有这种觉悟4 这螳螂拳算是练到家了5 现实中的你胖的一批 6 这套户型咋样&#xff1f;7 你能看出几个字你点的每个赞&#xff0c;我都认真当成了喜欢

指针04 - 零基础入门学习C语言44

第八章&#xff1a;指针04 让编程改变世界 Change the world by program 小结 归纳起来, 如果有一个实参数组, 想在函数中改变此数组中的元素的值, 实参与形参的对应关系有以下&#xff14;种情况&#xff1a; (1) 形参和实参都用数组名, 如&#xff1a; [codesyntax lang&…

填坑 | .NET 5在Docker中访问MSSQL报错

【.NET Core】| 作者 / Edison Zhou不知道你有没有在.NET Core/.NET 5的Docker访问MS SQL Server数据库&#xff0c;如果有&#xff0c;那么很有可能会遇到这个错误。1SSL版本错误最近在公司用.NET 5重构部分业务服务&#xff0c;由于之前老系统使用了MS SQL Server数据库&…

六个机械原理,动图形象直观、解读通俗易懂

全世界只有3.14 % 的人关注了爆炸吧知识01间歇运动机构▼间歇运动机构能够将原动件的连续转动转变为从动件周期性运动和停歇的机构&#xff0c;称为间歇运动机构。例如牛头刨床工作台的横向进给运动&#xff0c;电影放映机的送片运动等都用有间歇运动机构。常见的间歇运动机构有…

linux读写usb host,LINUX下USB1.1设备学习小记(3)_host与device

各位还记得”任何传输都是由host发起的”这句话么~在usb设备插入pc中到拔出usb设备,都是由host进行询问的一个usb鼠标的工作流程可以表达如下:usb鼠标插入pc中:主机询问设备:给我你的设备信息(控制传输)主机根据usb鼠标的设备信息进行驱动配置,配置结束后主机询问设备:给我你的…

java判断时间区间 隔天_Java初中级程序员面试题宝典

Java基础部分&与&&区别&#xff1f;&和&&都是逻辑运算符&#xff0c;都是判断两边同时真则为真&#xff0c;否则为假&#xff1b;但是&&当第一个条件不成之后&#xff0c;后面的条件都不执行了&#xff0c;而&则还是继续执行&#xff0c;直…

什么是sns

SNS 目录[隐藏] 第一章 什么是SNS&#xff1f; 第二章 SNS带给顾客的特殊价值描绘 第三章 观察SNS的技术与服务 第四章 SNS市场与竞争 第五章 SNS的主要营销策略简介 第六章 中国SNS的发展与主要网站及产品SNSSNS&#xff0c;全称Social Networking Services&#xff0c;即社会…

elsa-core——1.Hello World:Console

github上有一个开源的工作流项目elsa&#xff0c;elsa-core是core语言的版本&#xff0c;其文档因为是英文&#xff0c;因此会让很多人不想看&#xff0c;或者是看不下去&#xff0c;从这篇文章开始我将开始对elsa-core的文档翻译成中文并分享出来&#xff0c;方便大家查看与学…

docker 查看容器_Docker介绍

docker介绍什么是docker&#xff1f;我们先看一下官方文档对docker的定义。翻译一下就是&#xff1a;Docker是一个集开发&#xff0c;发布和运行应用程序的开放平台。Docker能够分离应用和基础架构&#xff0c;从而可以使得用户可以快速交付软件。借助于Docker&#xff0c;用户…