当前位置: 首页 > article >正文

系统移植相关概念总结

文章目录

    • (一)u-boot
      • 1. 启动流程
      • 2. u-boot如何传参
      • 3. 如果u-boot引导内核启动失败,分析原因
    • (二)内核移植
      • 1. 内核移植的步骤
      • 2. 内核启动流程
      • 3. 内核启动运行的第一个进程是什么,都做了什么
      • 4. 如果内核启动失败,分析下原因
    • (三)宏内核和微内核
    • (四)Linux系统启动级别
    • (五)设备树
      • 1、什么是设备树
      • 2、如何解析设备树

(一)u-boot

“the Universal Boot Loader”,通用引导加载程序
在系统启动时,初始化处理器、内存、存储设备、网络接口等硬件资源
加载操作系统内核并传递给处理器
通过环境变量存储启动参数和配置信息
提供命令行界面,允许用户执行内存读写、设备检测、文件传输等操作
U-Boot还可以提供安全启动功能,确保只有经过验证的操作系统内核和应用程序才能被加载和执行

1. 启动流程

U-Boot的启动流程可以分为两个阶段。
① 第一阶段(汇编语言实现)

CPU自身初始化
初始化CPU的相关寄存器,设置CPU的工作模式(如SVC模式)。
关闭内存管理单元(MMU)和高速缓存(Cache)。
初始化时钟系统、看门狗定时器、中断控制器等。

重定位
将U-Boot自身的代码从Flash中复制到RAM中,以便后续执行。

设置堆栈
分配堆栈空间,并设置堆栈指针。

清零BSS段
对未初始化的全局变量(BSS段)进行清零操作。

跳转到第二阶段入口
执行跳转指令,跳转到第二阶段代码的入口函数(如start_armboot())。

② 第二阶段(C语言实现)

为U-Boot内部私有数据分配存储空间
分配并清零U-Boot内部使用的数据结构。

依次调用初始化函数
通过一个函数指针数组(如init_sequence),依次调用各个初始化函数,对系统进行进一步的初始化。

Flash、LCD等设备的初始化
如果系统支持NOR Flash,调用相关函数进行初始化,并显示检测到的器件信息。
如果系统支持LCD或VFD,计算帧缓存(Framebuffer)大小,并在BSS数据段之后为其分配空间,初始化起始地址。

存储分配系统的初始化
初始化存储分配系统(类似于C语言中的堆),为后续的动态内存分配做准备。

环境变量的重定位
将环境变量从Flash中复制到RAM中,以便后续快速访问。

网络、IP地址等初始化
如果系统支持网络功能,进行网络接口的初始化。
从环境变量中读取IP地址和MAC地址,并进行相应的初始化。

控制台初始化
初始化控制台,以便输出调试信息和用户交互。

打开中断
配置中断控制器,打开中断功能。

进入主循环
最后,U-Boot进入一个主循环,等待用户的输入命令。用户可以通过命令行界面输入命令来加载内核、设置参数或执行其他操作。

在开机后,BIOS会进行硬件自检,并从硬盘的MBR中读取引导程序。然后,MBR会将控制权交给U-Boot,由U-Boot完成后续的硬件初始化和操作系统引导工作。

2. u-boot如何传参

  1. 可以通过环境变量来传递参数给内核。U-Boot提供了一个环境变量表,用户可以在其中设置一些参数(如bootargs),并在启动内核时将这些参数传递给内核。
  2. 参数链表方式中,U-Boot将每一个要传递给内核的参数封装成一个结构体(称为tag),并将这些结构体连续存储在内存的一片区域内。然后,U-Boot将这片区域的起始地址传递给内核。内核通过这个地址来解析U-Boot传递的参数。

3. 如果u-boot引导内核启动失败,分析原因

1、U-Boot配置问题
① 检查启动参数是否配置正确:
命令行参数中的console设置、bootargs、内存大小、根文件系统位置等关键参数。
② 环境变量设置:
bootcmd、bootfile等环境变量设置错误,导致U-Boot无法正确加载内核镜像。
③ 环境变量中的地址与实际内存布局不匹配。
④ U-Boot版本与内核版本不兼容
2、内核镜像问题
① 内核镜像格式不正确:
U-Boot可能不支持当前的内核镜像格式(如uImage、zImage等)。
② 内核镜像可能已损坏或未正确生成。
③ 内核镜像加载地址错误
④ 内核解压失败
3、硬件问题
内存问题:
内存初始化失败或内存存在故障。
内存大小与U-Boot或内核配置不匹配。
存储设备问题:
存储设备(如NAND、NOR Flash、SD卡等)存在故障或未正确连接。
存储设备上的内核镜像文件损坏或未正确写入。
处理器问题:
处理器配置不正确或存在故障。
处理器时钟频率与U-Boot或内核配置不匹配。

(二)内核移植

对Linux内核源码进行配置和编译,使linux内核源码支持自己的开发板并生成对应的镜像文件。

1. 内核移植的步骤

  1. 硬件平台选择
    根据项目需求选择合适的处理器类型,如ARM、MIPS、x86等。
    考虑处理器的性能,确保满足系统的运行效率需求。
    根据项目需求选择合适的外设资源,如内存大小、存储空间、网络接口等。
    选择与处理器类型相匹配的开发工具,如编译器、调试器等。
  2. 内核版本选择:
    选择一个稳定版本的内核,避免因为内核bug导致系统崩溃。
    确保所选内核版本支持当前硬件平台。
    根据项目需求选择具有相应功能的内核版本,如网络协议栈、文件系统等。
  3. 内核配置:
    安装相应的开发工具和依赖库。
    解压内核源码包,并进入内核源码目录。
    执行配置命令(如make menuconfig),进入内核配置界面,根据项目需求选择相应的内核选项。
    保存配置文件。
  4. 编译内核:
    执行编译命令(如make),开始编译内核。
    编译完成后,会生成内核镜像文件(如zImage)。
  5. 内核部署:
    将编译好的内核镜像文件部署到目标平台上

2. 内核启动流程

硬件设备初始化:
U-Boot在启动过程中会进行硬件设备的初始化,包括CPU、内存、外设等。

加载内核到内存:
U-Boot会将内核镜像文件从存储设备(如Flash)加载到内存中。

校验内核格式:
U-Boot会校验内核镜像文件的格式和CRC等校验码,确保内核文件的完整性和正确性。

准备启动参数:
U-Boot会根据配置的环境变量和启动参数,为内核准备启动所需的参数。

跳转执行内核:
U-Boot会将控制权交给内核,内核开始执行。
在执行过程中,内核会进行一系列的初始化操作,包括内存管理、设备驱动初始化、文件系统挂载等。

进入用户态:
当内核完成初始化并挂载了根文件系统后,会加载init进程(通常是/sbin/init或/bin/sh),进入用户态,此时用户可以开始使用系统。

3. 内核启动运行的第一个进程是什么,都做了什么

内核启动后运行的第一个进程通常是init进程,它是内核直接创建的第一个用户空间进程,其进程编号(PID)始终为1。

1、 进程管理
init进程负责启动、停止和管理系统中的其他进程。它会根据系统的配置和运行状态,启动必要的服务或进程,并在系统关闭时停止这些服务或进程。
2、系统初始化
init进程在启动时会读取系统的配置文件(如/etc/inittab或systemd的配置文件),以确定系统的运行级别和初始化脚本的执行。这些初始化脚本会负责设置系统的环境变量、挂载文件系统、启动必要的服务等。
3、运行级别管理
init进程还负责管理系统的运行级别,不同的运行级别会启动不同的服务和进程,以满足系统的不同需求。

读取配置文件:init进程首先会读取系统的配置文件,这些文件通常位于/etc目录下,如/etc/inittab(对于传统的SysV init系统)或systemd的配置文件(对于现代的systemd系统)。
确定运行级别:根据配置文件的设置,init进程会确定系统的运行级别。运行级别是一个数字,用于表示系统的运行状态。不同的运行级别会启动不同的服务和进程。
执行初始化脚本:init进程会根据运行级别的设置,执行相应的初始化脚本。这些脚本通常位于/etc/rc.d/或/etc/init.d/目录下,它们会负责设置系统的环境变量、挂载文件系统、启动网络服务、启动系统日志服务等。
启动必要的服务:除了初始化脚本外,init进程还会根据配置文件的设置,启动一些必要的服务或进程,如守护进程、登录进程等。
等待用户登录:最后,init进程会启动一个登录进程(通常是getty或mingetty),等待用户输入用户名和密码进行登录。

4. 如果内核启动失败,分析下原因

1、检查内存、存储设备、处理器和主板等硬件是否连接正确、无故障。
2、检查启动参数和配置文件,确保启动参数(如bootargs)和配置文件(如/etc/fstab)设置正确。
3、检查文件系统,使用文件系统检查工具(如fsck)检查并修复文件系统错误。
4、尝试不同的内核版本,检查是否是内核本身的问题。
5、确保boot loader版本与硬件和操作系统兼容
6、检查内核启动过程中的错误和异常。

(三)宏内核和微内核

宏内核,将操作系统的所有核心功能集中到一个内核空间。
将系统的所有基本服务(包括设备驱动程序、文件系统、内存管理、进程调度、系统调用等)都作为内核的一部分。
特点是操作系统的大部分功能都在内核态中运行,这样可以减少上下文切换的开销,但也使内核的复杂性增加。
宏内核的优点:
高性能,不需要频繁的用户态和内核态之间的上下文切换
硬件控制较高效,设备驱动和其他核心模块在内核中直接控制硬件,减少了延迟。
宏内核的缺点:不易维护和扩展、稳定性和安全性较低

微内核,将操作系统的核心功能进行分解,只保留一些最基本的服务,例如进程管理和内存管理等。而其他的服务则以独立的进程形式运行,这些进程可以在需要时动态加载和卸载。这种设计使得操作系统内核更加灵活,易于维护和扩展。
但是,由于在进程间通信时需要进行系统调用,因此微内核的性能通常较差。

(四)Linux系统启动级别

Linux系统通常有七个启动级别(0-6):

0级(系统停机状态):
系统默认运行级别不能设为0,否则无法正常启动。
一开机就自动关机,机器处于完全关闭状态。

1级(单用户模式):
类似于Windows的安全模式,具有root权限。
用于系统维护,禁止远程登录,没有网络功能。

2级(多用户模式,无NFS):
支持多用户登录,但没有NFS(网络文件系统)和网络支持。

3级(完整的多用户文本模式):
具有NFS和网络支持,登录后进入控制台命令行模式。
是标准的Linux运行级别之一,适用于服务器和需要命令行界面的场景。

4级(系统未使用,保留):
通常不使用此级别,但在一些特殊情况下可能会用到。
例如,在笔记本电脑电池即将用尽时,可以切换到这个模式来做一些设置。

5级(图形化模式):
登录后进入图形GUI模式,如GNOME、KDE等图形化界面。
适用于桌面环境和需要图形界面的场景。

6级(系统重启模式):
系统默认运行级别不能设为6,否则将无限重启,无法正常启动。
运行此级别时,系统会正常关闭并重启。

(五)设备树

1、什么是设备树

用于描述硬件设备的配置信息,使得操作系统(如Linux)能够正确地识别、配置和管理这些硬件设备

2、如何解析设备树

定义结构体:驱动要解析设备树,必须定义struct platform_driver类型结构体变量,并通过函数platform_driver_register()注册。同时,设备树节点会封装在struct device_node结构体变量中,各个属性信息会封装在struct property结构体变量中。
匹配设备树节点:内核在解析设备树的过程中,会根据设备节点的“compatible”属性来匹配相应的驱动程序。一旦找到匹配的驱动程序,内核就会将其加载并用于设备的初始化和管理。
解析设备树属性:在驱动程序的probe函数中,可以使用设备树提供的API(如of_property_read_u32、of_property_read_string等)来解析设备树节点的属性,并根据这些属性信息来配置和初始化硬件设备。


http://www.kler.cn/news/363631.html

相关文章:

  • VMware虚拟机中centos磁盘扩容(非VG分区挂载方案)
  • 负载均衡服务器攻击怎么解决最有效?
  • 高效改进!防止DataX从HDFS导入关系型数据库丢数据
  • LabVIEW提高开发效率技巧----插入式架构
  • STM32(二十一):看门狗
  • MySQL - Navicat自动备份MySQL数据
  • 大数据-MySQL集群
  • 使用electron 打包构建cocosCreator 的window exe
  • 鸿蒙应用开发:数据持久化
  • windows 上编译ceres suitesparse
  • #Swift 下标 Subscript - Access the elements of a collection
  • 【C++指南】运算符重载详解
  • 【JAVA毕设】基于JAVA的酒店管理系统
  • Flink SQL+Hudi数据入湖与分析实践
  • Scala的reduce
  • 昆虫种类识别数据集昆虫物种分类数据集YOLO格式VOC格式 目标检测 机器视觉数据集
  • 牛客周赛64(C++实现)
  • 你真的了解Canvas吗--解密十二【ZRender篇】
  • 【AI创新】优化ChatGPT提示词Prompt设计:释放AI的无限潜能
  • 使用AITemplate和AMD GPU的高效图像生成:结合Stable Diffusion模型
  • 数据结构(8.2_1)——插入排序
  • KOC营销崛起:怎样统计每个达人的App推广效果?
  • vscode连接keil-5 开发STM32 程序
  • Windows下搭建VUE开发环境
  • 一文搞定二叉树
  • 智慧楼宇平台,构筑未来智慧城市的基石