前言
LFS(Linux From Scratch)是一本指导从源代码构建Linux系统的电子书。通过LFS,可以得到一个及其精简,完全适合特定硬件的Linux系统,同时对Linux系统的结构和软件编译过程有更深入的了解。
4年前曾尝试过LFS8.0,因为水平有限卡在了内核配置上,编译出的内核没进入用户空间就panic,于是烂尾,留下了遗憾。之后一直对LFS念念不忘,现在趁暑假有时间,再次尝试LFS。
使用的LFS版本是8.4 SysV,其它版本的LFS章节序号可能与本文不对应
准备工作
宿主机系统
宿主机系统需要能通过LFS手册提供的version-check.sh
脚本的环境检查,gcc版本和内核版本越接近lfs所用的版本越好,可以降低出现玄学问题的概率
理论上任何一个linux发行版都可以,不过根据LFS用户的反馈,Ubuntu很接近LFS环境要求,并且由于使用ubuntu进行LFS的人多一些,出现问题查找到解决方案的几率也更大,因此更容易成功。为了让这次进行LFS的过程顺利些,我用ubuntu 20.04 LTS作为宿主机环境划分出LFS分区
不需要太大,如果不打算把完成的LFS系统拿来用,10G就够了,要用就视情况划分,可以单独划分分区给某些挂载点(/home,/boot等),就像安装普通的发行版一样梯子
不是必须,但是出现问题时需要上google搜索。国内访问LFS官网和一些含有有用信息的网站有时会很慢准备好LFS-BOOK和源码包
LFS提供了一个wgetlist来下载所有源代码包,使用的都是国外镜像站的地址,国内下载很慢甚至根本无法下载。幸好中科大镜像站的lfs源提供了所有软件源码包的打包,下载对应版本的tar包就行,它包含了所有源码包。可靠的电力供应
如果电脑性能一般,gcc的编译时间可能会非常长。小心这个过程中不要断电了
如果因为某些原因离开LFS编译环境(如重启),需要根据第2.3节恢复LFS环境
调整宿主机环境
首先运行一下LFS书提供的version-check.sh
脚本,根据输出内容调整宿主机系统软件包
运行脚本之后,发现ubuntu20.04有这些问题:
- /bin/sh没有链接到bash
- bison命令为找到(缺少软件包)
- yacc未找到
- gawk未找到
- m4未找到
- makeinfo未找到
问题还真不少,一个一个来解决
ubuntu默认将/bin/sh链接到dash,而lfs构建要求链接到bash
执行sudo dpkg-reconfigure dash
取消将dash设为默认shell
然后执行ll /bin/sh
可以看到已经链接到bash了
命令未找到只需安装对应软件包即可
使用包管理安装bison,gawk,texinfo
再次运行脚本检查一下环境,没有问题了
之后跟着手册指导完成准备工作
构建工具链
挂载LFS分区,设置好环境变量
将中科大镜像站下载的源代码合集tar包解压到$LFS/sources
下,然后开始构建工具链
第一个编译的软件包是Binutils,LFS手册以第一次编译它的时间作为SBU时间衡量单位,通过time make
来对编译过程计时。这个时间用来估计后面每一个软件包的构建时间
整个LFS过程中编译耗时最久的地方是正式编译LFS系统的gcc,算上测试时间大约是92 SBU,也就是第一次编译Binutils的时间的92倍
我的CPU是Intel Xeon X5680,已经面世12年了,构建Binutils花费的时间是2分45秒
第五章的内容是构建工具链,这一章没有必要对编译后的软件进行测试,只要工具链基本功能正常(编译出dummy.c的二进制能正常链接)就可以放心继续。在第6.10节调整工具链中会在继续之前对工具链再次检查
5.30编译python有个坑,pdf格式的手册给出修改setup的命令会导致修改后的setup.py脚本缩进不正确从而导致编译失败,需要手动定位到第467行修正缩进
编译LFS系统
从第五章结尾的改变/tools目录所有者开始,需要一直使用root权限
从这一章开始LFS手册会建议对每个软件包进行测试,可以只做必要的测试(Binutils,glibc,gmp,mpfr,gcc),这样可以节约时间。如果编译套件没有问题,编译其它软件出现问题一般只是因为没有在编译前正确配置,或者是某个依赖没有正确安装,这种情况很好处理。如果编译套件的测试没有通过就是大麻烦了,这种问题有时难以定位其根源,可能在构建工具链时就出现了错误,在最坏的情况下需要从头开始构建工具链。
gcc的测试可能会因错误终止,如果之前的操作正确,一般可以认为是正常的错误,放心继续就好
我的gcc测试结果如下,有几百个错误,但最后还是成功完成了LFS
1 | === g++ Summary === |
配置系统
这一步需要写几个配置文件,手册写得比较难懂,不过就算不太明白也能照着手册内容完成。即使一些非关键配置不正确,最后也能成功进入系统。
内核配置比较复杂,但如果只是为了尽快完成LFS,在内核配置上可以不那么较真,在make defconfig
的基础上选上对应驱动和文件系统支持的内核一般就可以用。看不懂的选项保持默认值就好
安装好内核后,配置好引导加载器就该重启进入LFS系统了。LFS提供的grub可以不用,通过宿主系统的引导加载器添加LFS启动项就行
完成之后
到lfs官网去注册一下,看看你是第几个!
如果有兴趣可以继续进行BLFS,把LFS打造成能够日常使用的系统
出现报错怎么办
LFS手册中的命令都是测试过了的,严格按照手册指导来进行LFS是不太可能出现重大错误的,除非从一开始宿主机环境就没有配置好。当出现编译错误时,应该首先检查一下是不是漏掉了某一步,或者是命令敲错了
如果在操作正确的情况下出现了一些非致命错误,应该先看手册中是否提到过错误可以忽略,如果没有,找到LFS8.4对应的build log看一下LFS的编者在构建过程中是否出现的同样的输出信息,如果有,则可以安全地忽略它,否则可能需要在继续编译之前进一步检查
当然,构建LFS的过程不一定有那么顺利,因为宿主机系统环境的不同,严格按照手册指导可能还是出现了意料之外的问题。这时候应该去网络上寻找答案了。一般提取报错信息的关键段并后面加上lfs
的关键词到google上搜索可以找到相关帖子。大部分解决方案来自linuxquestions.org论坛的lfs板块。
如果这个问题没有人问过就只能自己发帖求助了。在LQ论坛上应该贴出LFS版本,宿主机系统,出现问题的章节,足够多的报错信息并且说明情况,最好附上version-check.sh
的输出。
后记
LFS构建真的是体力活,需要耗费大量的时间,还需要有足够的耐心,在出现问题时能正确排查错误
至于收获?收获最大的应该是敲键盘的手速吧
LFS构建过程记录
2021-06-28 安装ubuntu用来编译LFS,调整宿主机环境
2021-07-01 开始编译,进行到第6.12节
2021-07-02 完成