【问题标题】:Do initrd really reduce kernel image size in case of Bootpimage?在 Bootpimage 的情况下,initrd 真的会减小内核映像的大小吗?
【发布时间】:2015-01-11 16:38:26
【问题描述】:

根据维基百科关于 initrd 的文章 "许多 Linux 发行版都提供一个单一的通用内核映像 - 发行版的开发人员打算在尽可能广泛的硬件上启动。这个通用内核映像的设备驱动程序作为可加载模块包含在内,因为将许多驱动程序静态编译到一个内核中会导致内核映像变得更大,可能太大而无法在内存有限的计算机上启动。这会引发在启动时检测和加载挂载根文件系统所需的模块的问题,或者就此而言,推断根文件系统的位置或内容。 为了避免将这么多特殊情况的处理硬编码到内核中,使用了带有临时根文件系统(现在称为早期用户空间)的初始引导阶段。这个根文件系统可以包含用户空间助手,这些助手执行硬件检测、模块加载和设备发现,以安装真正的根文件系统。 "

我的问题是,如果我们在 initrd 中而不是在实际的内核映像中添加加载实际文件系统所需的模块等来保存保存,那么在内核和 initrd 组合形成单个 bootpimage 的 Bootpimage 情况下我们将实现什么。即使使用 initrd,内核的大小也会增加。

有人可以澄清一下吗?

【问题讨论】:

  • 您将问题标记为 arm,这使诸如“单个通用内核映像 - 发行版的开发人员打算在尽可能广泛的硬件上启动”之类的任何概括都无效。因为 arm 内核/系统映像是完全定制的。
  • @auselen 嘿,我们也有 CONFIG_MULTIPLATFORM !另外,对于 arch/arm64 单张图片是强制性的,所以它并不是 无关紧要的。
  • @Notlikethat arm64 单张图像是强制性的吗?
  • @auselen 好吧,这是“强制性的”,因为维护者将拒绝接受任何特定于平台的代码(即always the intention),并且仍然非常热衷于保留a single config。至少对于支持 FDT 的系统而言,即 EFI/ACPI 支持在其显着成熟之前可能仍然是可选的。
  • @Notlikethat 谢谢!

标签: linux linux-kernel arm initrd


【解决方案1】:

定义“内核的大小”。

是的,如果你有一个最小的内核映像加上一个包含数百个模块的 initrd,它可能会比所有编译的等效内核占用更多的总存储空间,那么所有的模块头等。然而,一旦它启动,确定它在什么硬件上,加载一些模块并把其余的都扔掉(initrd中的init),它会占用相当少的强>记忆。另一方面,全内置内核映像一旦启动,在内存中仍然和在磁盘上一样大,所有不需要的驱动程序代码都在浪费空间。

存储几乎总是比 RAM 更便宜且更丰富,因此以减少系统运行时可用内存为代价优化存储空间通常有点愚蠢。即使对于网络启动,为了加快启动速度而牺牲总映像大小的运行时能力也是没有意义的。这种考虑可能有任何优点的少数几种系统几乎肯定不会首先使用通用多平台内核。

【讨论】:

    【解决方案2】:

    大小有几个方面,这可能令人困惑。

    • 磁盘/网络上的二进制大小

    • 启动时间大小

    • 运行时间大小

      tl-博士;将initrd 与模块一起使用可为通用映像提供最小的运行时内存占用以及当前 (3.17) Linux 内核代码。

    我的问题是,如果我们在 initrd 中而不是在实际的内核映像中添加加载实际文件系统所需的模块等来保存保存,那么在内核和 initrd 组合形成单个 bootpimage 的 Bootpimage 情况下我们将实现什么。即使使用 initrd,内核的大小也会增加。

    您是正确的,无论您选择哪种机制,都会传输相同数量的数据。事实上,带有模块加载的 initrd 会比完全静态链接的内核更大,并且启动时间会更慢。听起来很糟糕。

    专门为设备构建且不包含额外硬件驱动程序或模块支持的定制内核始终是最好的。 Debian handbook on kernel compilation 给出了用户可能想要制作自定义内核的两个原因。

    1. 通过功能最小化来限制安全问题的风险
    2. 优化内存消耗

    第二个选项通常是最关键的参数。最小化正在运行的内核消耗的内存量。 initrd(或 initramfs)是作为 ram 磁盘加载的二进制磁盘映像。它是所有用户代码,具有探测设备和使用 模块加载 为系统获取正确驱动程序的单一任务。完成这项工作后,它会挂载一个真正的 引导设备或普通的root 文件系统。发生这种情况时,initrd 图像将被丢弃。

    initrd 不消耗运行时内存。您会得到一个通用图像和一个具有相当小的运行时间占用空间的图像。

    我会说发行版人员所做的努力有时会产生性能问题。通常 ARM 驱动程序只为 一个 SOC 编译;虽然source支持一个SOC系列,但是通过条件只能选择一个。在最近的内核中,ARM 驱动程序始终支持整个 SOC 系列。内存开销是最小的。但是,将函数指针用于低级驱动程序传输函数会限制控制器的带宽。

    cacheflush 例程有一个多缓存选项。函数指针导致编译器自动溢出。但是,如果您针对特定的缓存类型进行编译,编译器可以内联 函数。这通常会生成更好更小的代码。大多数驱动程序没有这种类型的基础设施。但是,如果您编译一个针对您的 CPU 进行调整的单片内核,您将获得更好的运行时行为。几个关键的内核函数将使用内联函数。

    驱动程序在编译到内核时通常不会更快。许多系统支持通过 USB、PCMCIA、SDIO 等进行热插拔。这些系统在模块加载方面也具有内存优势。

    【讨论】:

      猜你喜欢
      • 2020-08-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-04-28
      • 2016-02-04
      • 2016-05-17
      • 1970-01-01
      • 2020-12-27
      相关资源
      最近更新 更多