内核体系结构和编译体系分析

2023-10-26

1、Linux操作系统体系结构

(1)操作系统可以分为两个层次:内核空间和用户空间。内核和用户空间使用不同的保护地址空间,内核不能将用户空间传递的地址进行直接的操作,需要先转换;
(2)系统调用:内核空间管理设备资源,应用程序通过内核提供的内核调用接口来申请资源;
(3)频繁的系统调用会影响操作系统性能,于是标准C库(glibc)对内核的系统调用进行了封装,glibc最终也是通过系统调用访问内核,但是增加了缓冲区,可以减少
系统调用的次数;

2、内核体系结构

在这里插入图片描述

(1)系统调用接口(SCI):提供某些机制实现用户空间到内核空间的函数调用;这些接口是依赖于体系结构的,在kernel目录中可以找到SCI的实现,并在arch目录中找到依赖于体系结构的部分;
(2)进程管理:程序在操作系统中是以进程/线程为单位运行的,内核要负责进程/线程的调度、进程/线程间通信和同步;
(3)内存管理:内存是很重要的资源,程序都要在内存中运行。内存按照内存页的方式进行管理,内核要负责数据再内存中的换进/换出,内存的分配和释放,以及物理地址和虚拟地址的映射;
(4)虚拟文件系统(VFS):
<1>文件系统有多种格式(ext2、ext3、fat等),是用来管理存储设备的。在存储设备中,存储的数据都是二进制的数,有了文件系统,当我们去访问存储设备的数据时,就可以按照文件名和文件路径的方式去访问;
<2>虚拟文件系统是文件系统的抽象层,虽然底层有各种文件系统,但是这些差异对上层来说是被屏蔽掉的。你在用open、write函数时,并不关心是何种文件系统;
<3>将内核中一些重要的数据结构抽象成文件,这样程序员就可以像读写文件一样去方便的修改和读取内核的数据;
(5)网络协议栈:网络协议栈在设计上采用分层的思想,从上到下分为:系统调用接口层、协议无关接口层(socker层)、网络协议层、设备无关层、设备驱动层;
补充:上面介绍的是通用的,CPU体系结构、设备驱动是和硬件驱动和具体硬件有依赖关系;

3、内核目录结构

在这里插入图片描述

参考博客:《Linux内核的目录结构》

4、内核配置与编译体系

4.1、交叉编译配置

//默认配置
ARCH	?= arm
CROSS_COMPILE	?= /opt/CodeSourcery/Sourcery_G++_Lite/bin/arm-none-linux-gnueabi-

//交叉编译工具链
AS		= $(CROSS_COMPILE)as
LD		= $(CROSS_COMPILE)ld
CC		= $(CROSS_COMPILE)gcc
CPP		= $(CC) -E
AR		= $(CROSS_COMPILE)ar
NM		= $(CROSS_COMPILE)nm
STRIP		= $(CROSS_COMPILE)strip
OBJCOPY		= $(CROSS_COMPILE)objcopy
OBJDUMP		= $(CROSS_COMPILE)objdump

(1)ARCH:指明CPU的架构,就是此次编译的内核要在何种结构的CPU上运行;
(2)CROSS_COMPILE:指定交叉编译工具链,前提是当前的环境中已经安装了对应的交叉编译工具链;
参考博客:《交叉编译工具链的安装以及介绍》

4.2、加载默认配置

(1)内核是高度可配置的,在编译前要先配置,也就是在顶层目录生成.config文件,.config文件是由/arch/xxx/configs/xxx拷贝而来;
(2)make ARCH=arm x210ii_qt_defconfig:这个操作效果等同于将缸ch/arm/configs 目录下的x210ii_qt_defconfig文件复制为顶层目录的 .config;

4.3、调整默认配置

(1)内核的配置项是很多的,于是内核开发者提供了界面化的配置选项,在顶层Makefile中支持"make menuconfig"进入配置界面,在此界面可以针对单个配置进行调整,也就是修改.config文件;

4.4、编译内核

root@ubuntu:~/dai_zhi_xin/kernel/jiuding_kernel/kernel# make zImage           
  CHK     include/linux/version.h
  CHK     include/generated/utsrelease.h
make[1]: `include/generated/mach-types.h' is up to date.
  CALL    scripts/checksyscalls.sh
  CHK     include/generated/compile.h
  Kernel: arch/arm/boot/Image is ready
  SHIPPED arch/arm/boot/compressed/lib1funcs.S
  AS      arch/arm/boot/compressed/lib1funcs.o
  LD      arch/arm/boot/compressed/vmlinux
  OBJCOPY arch/arm/boot/zImage
  Kernel: arch/arm/boot/zImage is ready
root@ubuntu:~/dai_zhi_xin/kernel/jiuding_kernel/kernel# 

(1)编译内核的前提是先配置内核,必须先生成对应的.config文件;
(2)生成的内核在arch/xxx/boot/目录下;
(3)make zImage:生成zImage;
(4)make uImage:生成uImage;
(5)make bzImage:生成bzImage;
(6)make modules:编译模块,也就是ko文件;

4.5、内核配置体系

(1)首先在命令行通过命令载入默认配置文件,在顶层目录生成.config文件;
(2)通过"make menuconfig"命令进入界面化配置,这里对配置文件进行微调;
(3)参考博客:《Linux内核配置——menuconfig》《Linux内核配置——Kconfig文件》
《Linux内核配置和编译原理 & menuconfig、Makefile、.config三者之间的关系》

4.6、内核的Makefile

4.6.1、目标定义

比如:
	obj-$(CONFIG_RTC_ORV_S3C) += rtc-s3c.o

(1)当配置文件中CONFIG_RTC_ORV_S3C=y时,则将rtc_s3c.c文件编译进内核;
(2)当配置文件中CONFIG_RTC_ORV_S3C=n时,则不编译rtc_s3c.c文件;
(3)当配置文件中CONFIG_RTC_ORV_S3C=m时,则将rtc_s3c.c文件单独编译成ko文件;

4.6.2、多文件模块定义

//构造的模块名字是module.ko
obj-m	+= module.o	
module-objs :=file1.o file2.o	#模块依赖file1.o和file2.o两个源文件

(1)要生成的模块名字时module,将来生成模块就是module.ko;
(2)要生成module.ko依赖file1.c和file2.c这两个文件;

4.6.3、目录层次迭代

obj-$(CONFIG_EXT3_FS) += ext3

当 CONFIG_EXT3_FS 的值为 y 或 m 时,内核构建系统会将 ext3 目录列入向下迭代的目标中,具体 ext3 目录下的文件是要作为模块编译,还是链入内核,由 ext3目录下的 Makefile 决定 。

4.7、在内核中添加代码

(1)编写的源代码复制到Linux 内核源代码的相应目录;
(2)目录的 Kconfig 文件中增加新源代码对应项目的编译配置选项;
(3)在目录的 Makefile 文件中增加对新源代码的编译条目;
补充:如果不知道怎么修改Kconfig和Makefile文件,可以参考别人已经添加好的文件时如何修改的;

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

内核体系结构和编译体系分析 的相关文章

  • msgget() 和 mq_open 之间的区别

    我阅读了有关消息队列操作的信息 例如 msgget msgsnd 和 msgrcv 但是当我在堆栈溢出上搜索消息队列相关问题时 我发现还有另一组消息队列操作 例如 mq open mq send mq receive 谁能告诉我这两种类型的
  • 如何在Linux中使用C或shell检查密码?

    我有一个用 C 编写的程序 运行在嵌入式 Linux 上 有时它想检查系统用户的密码 如果我能得到地穴盐 etc 密码 我可以使用 crypt 检查用户密码的正确性 有没有shell脚本可以帮助我检查密码 比如check passwd用户名
  • Vagrant、共享文件夹:利用 inotify 而非 NFS

    我们的 Symfony2 Web 应用程序在开发模式下使用 Assetic 观察器来动态重新编译资产 Web 应用程序在 Docker 容器中运行 该容器在 Vagrant VM Ubuntu 12 04 Precise 中运行 主机是 O
  • 如何将php cURL升级到7.36.0版本?

    我的 CentOS 服务器上有 php curl 7 19 7 但我需要升级到 7 36 0 I tried yum update php curl 但我得到了 Loaded plugins downloadonly fastestmirr
  • 如何正确创建可通过http访问的SVN存储库? (在 public_html 内)?

    情况是这样的 subversion 已安装在服务器中 并且我可以访问服务器中的共享帐户之一 不是 root 并且该共享托管帐户具有 SSH 访问权限 我想创建一个存储库 我可以在其中提交我正在处理的 PHP 文件 当我提交时 它应该可以在浏
  • Boost 更新失败,现在不确定我拥有哪个版本

    在 Ubuntu 22 04 上运行此命令以获得 Boost 1 82 sudo add apt repository ppa mhier libboost latest sudo apt update sudo apt install l
  • 访问附加到 ELF 二进制文件的数据

    我有一个静态 ELF 二进制文件 它从 zip 文件中读取数据 为了简化分发 我想将 zip 文件附加到二进制文件中 如下所示 cat mydata zip gt gt mybinary 我知道这样做不会损坏 mybinary 但我不知道如
  • 如何将回车符作为字符添加到文件中?

    我想要一个像这样的字符串 blablbabla
  • Linux 中的 C 聊天室 / Socket 编程

    我有一个简单的服务器和客户端 C 代码来使用线程 pthread 库 为多客户端创建一个聊天室 我一直遇到的问题是 我无法想出一种方法让服务器将客户端通过套接字发送到所有其他客户端的每条消息写入 我在这里读过其他类似的帖子 但很无奈 请帮助
  • cronjob 上的 PHP 错误,在提示时工作正常

    我正在 cronjob 上运行以下脚本 cd etc parselog php run all php gt dev null 并收到以下错误 05 May 2009 20 30 12 PHP Warning PHP Startup Una
  • 如何禁用浮点单元(FPU)?

    我想在 x86 系统中禁用 FPU MMX SSE 指令 并且我将为设备不可用异常实现一个处理程序 我已经提到过控制寄存器 wiki 页面 http en wikipedia org wiki Control register 看来我必须在
  • 如何在Linux shell脚本中将文本文件中的两行合并到同一行中

    我使用 wget 命令从 Nagios 下载了它的 html 文件 然后使用以下代码将该 html 文件转换为 Textfile html2text width 180 file html gt a txt 然后我剪切了前 10 行 因为我
  • 为什么我们可以将 sockaddr 转换为 sockaddr_in

    我明白为什么强制转换很有用sockaddr to sockaddr in 但我不明白这怎么可能 据我所知 它们的大小相同sockaddr in添加了sin zero使其大小相同 我想知道编译器如何知道从哪里获取信息sockaddr in如果
  • 请求失败的错误:GLXBadDrawable (C++ bgfx)

    我试图用 glfw 和 bgfx 创建一个紫色窗口作为我的游戏引擎的起点 但是在启动二进制文件时它会抛出一个错误 我正在尝试创建紫色窗口 如下图所示 我正在使用 cmake 错误是 anuj fedora D C C c o build g
  • 当非特权用户运行 C/asm 程序时,会对 Linux 造成什么危害?

    我一直在考虑一种场景 让用户 可以是任何人 可能有恶意 提交在 Linux PC 我们称之为基准节点 上运行的代码 目标是为单线程例程创建一种自动化基准测试环境 假设一个网站向代理发布了一些代码 该代理将此代码交给基准节点 而基准节点仅与代
  • mod_fcgid + PHP + apache 锁定

    我正在运行一个相当典型的 LAMP 堆栈 其中 PHP 通过 mod fcgid 运行 考虑到服务器收到的流量 我认为服务器处于 高负载 状态 存在一个间歇性问题 当访问依赖 PHP 的站点时 Apache 报告所有连接都处于 正在发送内容
  • 安装pipenv导致pip3无法使用

    我安装了pipenv using pip3 install pipenv 这给了我错误ImportError cannot import name main 为了解决这个错误我遵循这些说明 https stackoverflow com q
  • accept() 创建一个新套接字是什么意思?

    我的问题基于以下理解 套接字由 ip port 定义 服务器和客户端都有自己的套接字 Socket连接由五组server ip server port client ip client port protocol定义 套接字描述符是标识套接
  • Alsa:如何在 2 个输出上复制流并保存系统配置?

    我的声卡是 Audigy SE SB0570 我想不仅在扬声器上而且在耳机上同时播放相同的立体声流 我在空的 asoundrc 上尝试这个配置 pcm quad type multi slaves a pcm hw 0 0 green ho
  • 从该共享库中查找加载的共享库的位置?

    从共享库中的函数 在正在运行的进程 用 C 编写 内 我如何发现该共享库是从哪里加载的 我找到的所有答案都涉及使用诸如ldd在命令行中 或者通过查看 proc self maps 在 Win32 上 我只需使用GetModuleFileNa

随机推荐

  • 手风琴(折叠面板)

    目录 一 Layui手风琴 1 1 引用layui的css和js 1 2 开启手风琴的代码示例 1 3 静态数据 1 4 最终效果图 二 Bootstrap手风琴 2 1 引用Bootstrap的css和js 2 2 开启手风琴的代码示例
  • Python 第一章 基础知识(6) 函数

    函数就像可以用来实现特定功能的小程序一样 Python的很多函数都能做很奇妙的事情 先来介绍一个内建函数 即是Python自带的已经定义好的函数 可以直接用 gt gt gt pow 2 3 8 这个函数实现了2 2 2的算法 这种使用函数
  • Angular 中 web worker的使用

    web worker就是在web应用程序中使用的worker 这个worker是独立于web主线程的 在后台运行的线程 web worker的优点就是可以将工作交给独立的其他线程去做 这样就不会阻塞主线程 第一步 ng g webWorke
  • 快速生成26个英文字母

    在学习中经常会拿26个英文字母序列做为字符串的例子来说明 但是自己又不想每次都自己手动输入 所以就想写个方法能快速的生成这个字符串 generate 26 english Characters return void public stat
  • C# 9.0:Records

    转自 翁智华 cnblogs com wzh2010 p 13950647 html 概述 在C 9 0下record是一个关键字 微软官方目前暂时将它翻译为记录类型 传统面向对象的编程的核心思想是一个对象有着唯一标识 封装着随时可变的状态
  • JenKins结合cppcheck及cpplint进行代码风格及静态代码检测

    JenKins结合cppcheck及cpplint 最近公司需要在Jenkins上安装cppcheck及cpplint进行代码风格及静态代码检测 这里记录下过程 前提条件 安装了Jenkins 步骤如下 第一步 安装cppcheck并配置环
  • [Linux] yum和apt-get用法及区别

    一般来说著名的linux系统基本上分两大类 1 RedHat系列 Redhat Centos Fedora等 2 Debian系列 Debian Ubuntu等 RedHat 系列 1 常见的安装包格式 rpm包 安装rpm包的命令是 rp
  • vs2019调试时中文乱码解决办法

    vs2013 vs2019系列文章目录 文章目录 vs2013 vs2019系列文章目录 问题描述 一 解决 解决方法1 在我机器上仍然未解决 解决方法2 在我机器上可行 调试时中文显示效果 问题描述 vs2019调试时中文乱码 但是在vs
  • except Exception as e作用

    小记 今天在查看poc时 发现这段代码不理解 所以B站搜索了一下 把别人讲的内容爬了一下 coding utf 8 a int input 请输入数字0 try if a 0 print a except Exception as e 作用
  • Redis高可用集群(哨兵、集群)

    文章目录 前言 一 主从复制 1 1 主从复制的作用 1 2 主从复制流程 1 3 主从复制搭建 二 哨兵模式 2 1 哨兵模式的作用 2 2 哨兵结构的组成 2 3 故障转移机制 2 4 哨兵模式搭建 三 集群模式 3 1 集群的作用 3
  • shell 脚本调试工具

    bashdb 是一个类似GDB的脚本调试软件 具有断点 单步执行 观察变量等功能 安装方法 sudo apt get install bashdb bashdb 使用方法 bashdb options script name script
  • vue element-ui el-table表格二次封装 自定义el-table表格组件 vue封装表格组件

    CommTable vue table组件
  • 多人连线的枪战游戏

    Simple Blueprint Multiplayer 是一个完全由 蓝图 和 UMG 界面 编写的游戏 可以作为如何使用蓝图的 Session Nodes 打造游戏中的多人部分的使用示例 这里有一个主菜单 一个服务器列表 以及一个简单的
  • java如何将null转化为空串也就是empty

    java如何将null转化为空串也就是empty 前言 在说转换之前 简单说一下它们之间的区别 如下 1 null不指向任何对象 相当于没有任何值 而 代表一个长度为0的字符串 2 null不分配内存空间 而 会分配内存空间 那如何将nul
  • HTTP 2.0 与HTTP1.1的差别

    前面的话 在说HTTP2 0前 先说一说发展到HTTP1 1做了哪些升级 推荐好文 一文读懂HTTP 2及HTTP 3特性 HTTP1 1的升级 目前使用最广泛的HTTP1 1做了哪些重大升级 默认长连接 HTTP1 0也提供长连接 但是默
  • 拓扑排序(广度优先搜索实现)

    有向无环图可以用来表示各种事物的顺序 比如工作顺序 一些事情必须在另一些事情完成之后才能开始进行 那么 为了获得正确的工作顺序 一件事情开始之前 必须保证它的前置条件全部满足 就需要用到拓扑排序 拓扑排序其实就是在有向无环图中 只要存在边
  • nvm 查看所有可以下载node的版本

    nvm 查看所有可以下载node的版本 nvm list 命令 显示版本列表 nvm list 显示已安装的版本 同 nvm list installed nvm list installed 显示已安装的版本 nvm list avail
  • 三阶段提交协议(3PC)

    3PC 主要是为了解决两阶段提交协议的单点故障问题和缩小参与者阻塞范围 引入参与节点的超时机制之外 3PC把2PC的准备阶段分成事务询问 该阶段不会阻塞 和事务预提交 则三个阶段分别为CanCommit PreCommit DoCommit
  • codeforces 526D(kmp,数学)

    description One day Om Nom found a thread with n beads of different colors He decided to cut the first several beads fro
  • 内核体系结构和编译体系分析

    1 Linux操作系统体系结构 1 操作系统可以分为两个层次 内核空间和用户空间 内核和用户空间使用不同的保护地址空间 内核不能将用户空间传递的地址进行直接的操作 需要先转换 2 系统调用 内核空间管理设备资源 应用程序通过内核提供的内核调