[TOC]

art-pi 构建命令

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
export CROSS_COMPILE=arm-none-eabi- ARCH=arm
make stm32_defconfig

make menuconfig
> General setup
[*] Initial RAM filesystem and RAM disk (initramfs/initrd) support
> Device Drivers > Block devices
[*] RAM block device support
(1) Default number of RAM disks
(2048) Default RAM disk size (kbytes)
> System Type
(0xC0000000) (S)DRAM Base Address
(0x02000000) (S)DRAM SIZE
> Boot options
[ ] Kernel Execute-In-Place from ROM
> File systems
[*] Enable POSIX file locking API
linux-5.13.19\arch\arm\boot\dts\stm32h750i-art-pi.dts
chosen {
bootargs = "root=/dev/ram";
stdout-path = "serial0:2000000n8";
};
chosen {
bootargs = "root=/dev/ram";
stdout-path = "serial0:115200n8";
};

make -j

# 将 u-boot.bin zImage rootfs.ext2 stm32h750i-art-pi.dtb(“linux-5.13.19->arch->arm->boot->dts”目录下)都放到同一个目录下。
mkimage -f APT_Pi_Krl.its APT_Pi_Krl.itb.bin

makefile选项

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
make V=n   [targets] 1: 详细构建
2: 给出目标重建的原因
V=1 和 V=2 可以组合使用 V=12
make O=dir [targets] 将所有输出文件定位在 "dir" 中,包括 .config
make C=1 [targets] 使用 $CHECK 检查重新编译的 c 源文件
(默认使用 sparse)
make C=2 [targets] 强制检查所有 c 源文件,使用 $CHECK
make RECORDMCOUNT_WARN=1 [targets] 警告被忽略的 mcount 部分
make W=n [targets] 启用额外的构建检查,n=1,2,3,c,e 其中
1: 可能相关且不经常发生的警告
2: 经常发生但可能仍然相关的警告
3: 更晦涩的警告,很可能可以忽略
c: 配置阶段的额外检查(Kconfig)
e: 将警告视为错误
多个级别可以组合使用 W=12 或 W=123
make CHECK_DTBS=1 [targets] 根据模式检查所有生成的 dtb 文件
这可以应用于 "dtbs" 和单个 "foo.dtb" 目标

内核镜像

在 Linux 内核构建过程中,会生成不同类型的内核映像文件。以下是 vmlinux、ImagezImageuImage 的区别和用途:

vmlinux

  • 描述:vmlinux 是内核的未压缩可执行映像,包含了内核代码、数据和符号信息。
  • 用途:vmlinux 通常用于调试,因为它包含完整的符号信息,可以使用调试工具(如 gdb)来调试内核。
  • 生成方式:在内核构建过程中,通过链接所有的内核对象文件生成 vmlinux。

Image

  • 描述Image 是一个未压缩的内核映像文件,通常用于直接加载到内存中执行。
  • 用途Image 文件适用于某些引导加载程序或开发环境,直接加载和执行内核。
  • 生成方式Image 通常通过对 vmlinux 进行一些处理生成,例如去除调试符号等。

zImage

  • 描述zImage 是一个压缩的内核映像文件,使用 gzip 压缩算法进行压缩。
  • 用途zImage 文件适用于大多数引导加载程序,因为它体积较小,便于传输和加载。
  • 生成方式zImage 通过对 vmlinux 进行 gzip 压缩生成。内核启动时,解压缩代码会首先运行,然后解压缩内核并启动。

uImage

  • 描述uImage 是一个适用于 U-Boot 引导加载程序的内核映像文件,包含了一个 U-Boot 头部信息。
  • 用途uImage 文件专门用于 U-Boot 引导加载程序,广泛应用于嵌入式系统中。
  • 生成方式uImage 通过使用 mkimage 工具对 zImageImage 进行处理生成,添加了 U-Boot 头部信息。
1
2
3
4
5
6
7
8
9
10
11
12
13
架构特定目标 (arm):
* zImage - 压缩内核映像 (arch/arm/boot/zImage)
Image - 未压缩内核映像 (arch/arm/boot/Image)
* xipImage - 如果配置,XIP 内核映像 (arch/arm/boot/xipImage)
uImage - U-Boot 包装的 zImage
bootpImage - 组合的 zImage 和初始 RAM 磁盘
(通过 make 变量 INITRD=<path> 提供 initrd 映像)
install - 安装未压缩内核
zinstall - 安装压缩内核
uinstall - 安装 U-Boot 包装的压缩内核
使用(你的)~/bin/installkernel 或
(发行版)/sbin/installkernel 安装,或
安装到 $(INSTALL_PATH) 并运行 lilo

.map

  • linux编译后仅有system.map文件,可以添加代码生成vmlinux.map文件
1
2
3
#顶层makefile
KBUILD_LDFLAGS :=
KBUILD_LDFLAGS += -Map=vmlinux.map

在 U-Boot 和 Linux 内核的构建过程中,生成的文件有所不同,主要是因为它们的构建系统和用途不同。

U-Boot

U-Boot 是一个引导加载程序,它的构建过程会生成多个文件,其中包括 u-boot.map 和 system.map 文件。

  • u-boot.map:这个文件包含了详细的链接信息,包括每个符号的地址和大小。它是由链接器生成的,用于调试和分析 U-Boot 的内存布局。
  • system.map:这个文件列出了所有符号及其对应的地址,主要用于调试和内核模块的加载。

Linux 内核

Linux 内核的构建过程也会生成多个文件,但通常只会生成一个 system.map 文件。

  • system.map:这个文件列出了内核中所有符号及其对应的地址,主要用于调试和内核模块的加载。

为什么 U-Boot 有 u-boot.map 和 system.map,而 Linux 只有 system.map

  1. 构建系统的差异:U-Boot 和 Linux 内核的构建系统有所不同。U-Boot 的构建系统会生成更多的中间文件来帮助调试和分析,而 Linux 内核的构建系统则更简洁,通常只生成 system.map 文件。

  2. 用途不同:U-Boot 是一个引导加载程序,需要详细的链接信息来确保正确加载和执行。而 Linux 内核是一个操作系统内核,主要关注符号地址和内核模块的加载,因此只需要一个 system.map 文件。

  3. 历史原因:U-Boot 和 Linux 内核的开发历史和社区习惯也有所不同,导致它们在构建过程中生成的文件有所不同。

总结

U-Boot 编译后生成 u-boot.map 和 system.map 文件,是为了提供详细的链接信息和符号地址,方便调试和分析。而 Linux 内核编译后通常只生成 system.map 文件,主要用于调试和内核模块的加载。这些差异主要是由于它们的构建系统、用途和开发历史不同所导致的。

lds 链接脚本

  • arch/arm/kernel/vmlinux.lds

内核压缩算法 Kernel compression mode

linux 配置选项

  • linux 内核是一种自解压的可执行文件。有几种压缩算法可用,它们各不相同.在效率、压缩和解压缩速度方面。压缩速度仅在构建内核时相关。每次引导的解压缩速度都很重要。
1
2
3
4
5
6
7
choice
prompt "Kernel compression mode"
default KERNEL_GZIP
depends on HAVE_KERNEL_GZIP || HAVE_KERNEL_BZIP2 || HAVE_KERNEL_LZMA || HAVE_KERNEL_XZ || HAVE_KERNEL_LZO || HAVE_KERNEL_LZ4 || HAVE_KERNEL_ZSTD || HAVE_KERNEL_UNCOMPRESSED
help
This option allows you to select the compression algorithm
used to compress the kernel image. The default is gzip.
  • 通过makefile的指令可以看出使用的是linux系统的gzip命令
1
cat arch/arm/boot/compressed/../Image | gzip -n -f -9 > arch/arm/boot/compressed/piggy_data

压缩算法的对比

在 Makefile 中定义了几种不同的压缩算法,用于创建压缩的内核镜像。以下是这些压缩算法的对比:

  1. gzip

    • 特点:gzip 是一种广泛使用的压缩算法,具有良好的压缩比和解压速度。它基于 DEFLATE 算法,适用于大多数情况。
  2. lzo

    • 特点:LZO 是一种快速压缩算法,特别适合需要快速解压的场景。虽然压缩比不如 gzip,但解压速度非常快,适用于嵌入式系统和实时应用。
  3. lzma

    • 特点:LZMA 提供了非常高的压缩比,但压缩和解压速度较慢。适用于需要最大限度减少存储空间的场景,如固件和嵌入式系统。
  4. xz

    • 特点:XZ 基于 LZMA2 算法,提供了高压缩比和较好的解压速度。它在压缩比和解压速度之间取得了平衡,适用于需要高压缩比和较快解压速度的场景。
  5. lz4

    • 特点:LZ4 是一种非常快速的压缩算法,具有极快的压缩和解压速度,但压缩比相对较低。适用于需要快速压缩和解压的场景,如内存压缩和实时数据处理。

U-boot配置选项

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
static const table_entry_t uimage_comp[] = {
{ IH_COMP_NONE, "none", "uncompressed", },
{ IH_COMP_BZIP2, "bzip2", "bzip2 compressed", },
{ IH_COMP_GZIP, "gzip", "gzip compressed", },
{ IH_COMP_LZMA, "lzma", "lzma compressed", },
{ IH_COMP_LZO, "lzo", "lzo compressed", },
{ IH_COMP_LZ4, "lz4", "lz4 compressed", },
{ IH_COMP_ZSTD, "zstd", "zstd compressed", },
{ -1, "", "", },
};
//lib/Kconfig
menu "Compression Support"

config LZ4
bool "Enable LZ4 decompression support"
help
如果设置了此选项,则支持 LZ4 压缩图像
包括在内。LZ4 算法可以就地运行,只要
压缩图像被加载到输出缓冲区的末尾,并且
以较低的压缩率换取更快的解压缩。

注意:这将实现 LZ4 帧的发布版本格式。
这与过时、效率较低的遗留问题不同
目前 (2015) 在 Linux 内核中实现的帧格式
(由 'lz4 -l' 生成)。这两种格式不兼容。

config LZMA
bool "Enable LZMA decompression support"
help
这将启用对 LZMA(Lempel-Ziv-Markov 链算法)的支持,
一种字典压缩算法,可提供高压缩率
比率和相当快的解压缩速度。另请参阅
CONFIG_CMD_LZMADEC,它提供了一个 decode 命令。

config LZO
bool "Enable LZO decompression support"
help
这将启用对 LZO 压缩CONFIG_GZIPalgorithm的支持。

config GZIP
bool "Enable gzip decompression support"
select ZLIB
default y
help
这将启用对 GZIP 压缩算法的支持。

应用

  1. gzip:适用于大多数情况,提供良好的压缩比和解压速度。
  2. lz4:适用于需要快速解压的场景,如嵌入式系统和实时应用。
  3. 不压缩: 不适应.对应硬件读取效率来说,通过压缩算法,可以提高读取效率.进而比较不压缩的方式,提高读取速度.