linux kexec内核引导

linux kexec 介绍

kexec的功能是用一个运行的内核去运行一个新内核,就像运行一个应用程序一样。这种机制因为跳过了bootloader,可以实现系统的快速重启。另外kdump也是基于kexec实现(示意如下)。

kexec的实现有几点难点:

  1. 在当前内核的上下文中,如何用新内核去替换现有内核?
  2. 正常复位启动过程中,设备会被复位(或初始化)到已知状态。跳过了复位阶段,那如何在新内核kexec启动时,保证设备状态的可靠?

kexec的使用示例如下,其分为2部分:kexec内核加载和kexec内核执行。

    kexec -l /bzImage --initrd=/initrd.img.gz --append="ro nosmap loglevel=4 console=ttyS0,9600n8 acpi_rsdp=0x7b7fe014"
    kexec -e

kexec 内核加载

  1. 将内核镜像文件、根文件系统、命令行参数等segment加载到用户态内存;
  2. 对segment sha256检查,确保内核数据没有被破坏;如果是kdump,备份相关数据到备份区(如i386,最开始的640K配置数据用于SMP内核启动,需要备份;或者powerpc,固定位置的异常向量等信息需要备份等)。这个环节又叫purgatory,其流程可以在用户态控制实现,也可以在内核态控制实现(如使能--kexec-file-syscall选项);
  3. 分配内核态页面,并将segment从用户态内存copy到内核态页面;如果使能--kexec-file-syscall选项,则跳过前面两步,直接将segment加载到内核页面,并进行purgatory。
  4. 分配页面并初始化image->control_code_page,对其建立页表,为下一步进行覆盖当前内核时代码寻址的页表映射。初始化LEVEL4/3/2/1 4层页表,并建立映射关系(如下图所示)。

kexec 内核运行

  1. 调用设备驱动shutdown接口关闭设备;
  2. 关闭中断,如IO-APIC, local irq, LAPIC;
  3. 关闭非0号CPU核;
  4. 清空TLB(此处以下代码为汇编实现,具体实现与arch相关,一般名叫relocate_new_kernel);
  5. 设置段寄存器、gdt、idt等;
  6. 建立一个新栈,并将新内核的入口地址压入栈中;
  7. 设置cr0寄存器:使能分页功能和页面保护功能;
  8. 设置cr4寄存器:使能扩展地址;
  9. 设置cr3寄存器,使cr3指向新的页表根目录;设置后,从此就与旧内核bye bye了;
  10. 将内核segment页面copy到指定位置,覆盖当前内核;
  11. 调用ret指令,从栈中弹出之前压栈的新内核bzImage入口地址,进入新内核引导;

kexec 调试注意实现

  1. kexec不会同步或卸载文件系统,此过程需要用户来保证;
  2. 从上面的流程中可以看出,kexec不会对cpu或设备进行复位,但系统重启过程中会调用reboot_notifier_list,所以register_reboot_notifier注册的接口不要有执行CPU复位等操作;
  3. 为了保证设备在kexec时处于稳定状态,kexec会调用设备驱动的shutdown接口来关闭,确保用户自己的设备驱动提供了正确的shutdown接口,或用户通过其他方式进行关闭;

--EOF--

时间: 2024-10-03 22:42:55

linux kexec内核引导的相关文章

Linux 内核引导参数简介

概述 内核引导参数大体上可以分为两类:一类与设备无关.另一类与设备有关.与设备有关的引导参数多如牛毛,需要你自己阅读内核中的相应驱动程序源码以获取其能够接受的引导参数.比如,如果你想知道可以向 AHA1542 SCSI 驱动程序传递哪些引导参数,那么就查看 drivers/scsi/aha1542.c 文件,一般在前面 100 行注释里就可以找到所接受的引导参数说明.大多数参数是通过"__setup(... , ...)"函数设置的,少部分是通过"early_param(..

【Linux管理】Linux系统启动和引导

************************************************************************   ****原文:blog.csdn.net/clark_xu 徐长亮的专栏 ************************************************************************ 1 linux系统启动和引导 linux的启动过程为:计算机执行BIOS代码,确认加载并启动内核,内核检测系统的硬件,产生系统的i

Linux系统管理09——引导过程与服务控制

Linux系统管理09--引导过程与服务控制 一.引导过程总览 1.init进程 ·由linux内核加载运行/sbin/init程序 ·是系统中的第一个进程,所有进程的父进程 ·PID(进程标记)号永远为1 2.Upstart启动方式 初始化配置分散存放,响应不同的启动事件 参数 说明 /etc/inittab 配置默认运行级别 /etc/sysconfig/init 控制tty终端的开启数量.终端颜色方案 /etc/init/rcS.conf 加载rc.sysinit脚本,完成系统初始化任务

The Kernel Boot Process.内核引导过程

原文标题:The Kernel Boot Process 原文地址:http://duartes.org/gustavo/blog/ [注:本人水平有限,只好挑一些国外高手的精彩文章翻译一下.一来自己复习,二来与大家分享.] 上一篇文章解释了计算机的引导过程,正好讲到引导装载程序把系统内核镜像塞进内存,准备跳转到内核入口点去执行的时刻.作为引导启动系列文章的最后一篇,就让我们深入内核,去看看操作系统是怎么启动的吧.由于我习惯以事实为依据讨论问题,所以文中会出现大量的链接引用Linux 内核2.6

centos内核引导参数

绝大部分的内核引导参数的格式如下(每个参数的值列表中最多只能有十项): name[=value_1][,value_2]...[,value_10] 如果"name"不能被识别并且满足"name=value"的格式,那么将被解译为一个环境变量(比如"TERM=linux"或"BOOT_IMAGE=vmlinuz.bak"),否则将被原封不动的传递给 init 程序(比如"single"). 内核可以接受的参

Linux系统开机引导和启动过程-img文件

操作系统的启动分为两个阶段: 引导boot 启动startup 引导阶段开始于打开电源开关,结束于内核初始化完成和 systemd 进程成功运行.启动阶段接管了剩余工作,直到操作系统进入可操作状态. 总体来说,Linux 的开机引导和启动过程是相当容易理解,下文将分节对于不同步骤进行详细说明. BIOS 上电自检(POST) 引导装载程序 (GRUB2) 内核初始化 启动 systemd,其是所有进程之父. 注意,本文以 GRUB2 和 systemd 为载体讲述操作系统的开机引导和启动过程,是

Linux的内核源码树的根目录下的每个文件的含义简介

在下载Linux内核源码包解压后,Linux的内核源码树的根目录的每一个含义看不太明白,估计每个喜欢研究内核源码的小伙伴刚开始都会有此疑问,因此,在这里对Linux内核源码的根目录的每个文件包做些简介,让喜欢研究内核源码的小伙伴对内核这个看起来特别神秘且复杂的东西有个大体的了解. 具体的详情请见下表: Linux 内核源码树的根目录描述 目录 含义描述 arch 特定体系结构的源码 block 块设备 I/O层 crypto 加密API Documentation 内核源码文档 drivers

自制linux和内核编译

自制linux和内核编译 1.分区并创建文件系统 fdisk /dev/sdb分两个必要的分区/dev/sdb1对应/boot /dev/sdb2对应根/mkfs.ext4 /dev/sdb1mkfs.ext4 /dev/sdb2 2.挂载boot mkdir/mnt/bootmount /dev/sdb1 /mnt/boot 3.安装grub grub-install --root-directory=/mnt  /dev/sdb 4.建立grub.conf: vim /mnt/boot/gr

Linux大脑 "内核" 内核编译(NTFS)

Linux大脑 "内核" 关于它 什么是内核 kernel(内核)是操作系统的核心,相当于人的大脑,掌控所有的硬件设备的控制权,也就是希望计算机帮你完成各项工作,那都需要通过内核的帮助才能完成,当然,如果你想实现的功能内核没有提供,那就必须添加相关的模块到内核中,就类似驱动程序,有了模块的支持我们计算机才能去操控硬件,完成我们想完成的工作 内核其实就是系统上面的一个文件,这个文件包含了驱动硬件的检测程序与驱动模块,内核文件在/boot目录下一个以vmlinuz开头的文件,有时候/boo