LFS原理
LFS的基本原理是:从host(发行版linux或liveCD)环境中,先创建一个临时环境(也就是在tools目录下建立个各种工具),此时还会部分利用host的工具,然后利用这个临时环境,此时脱离了host的所有工具,来建立目标机的所有工具。
- 第一遍的binutils和gcc只用来编译glibc,在编译过程中还需要利用host的库文件来执行程序,而glibc不需要C++,所以不用编译。
- 第二遍的binutils、gcc、glibc作为一个完整的工具链,用来编译临时系统,所生成的程序都会从tools/lib目录下查找动态链接库来执行,因此生成的程序就与host系统无关了,也是因为这个原因不能使用第一遍的bintuils和gcc。
- 第三遍的binutils和gcc是编译最终系统上的工具链,如果你不需要在最终系统上编译包的话,就可以不用进行这第三次编译。
主机环境
- CPU:Loongson3A3000
- 架构:MIPS64el
- 系统:Loongnix based on Fedora21
- 参考:LFS-8.2官方文档
- 其他:LFS on MIPS相关文档
- 备注:在Loongson上构建LFS的整体过程和LFS-8.2的官方文档过程大致相同,不同的是用户环境变量的设置以及在编译各个包时的参数有所调整。
创建新分区
#1.查看分区:
fdisk -l
#2.创建分区:
fdisk /dev/<xxx> <xxx>是你要分的区,比如fdisk /dev/sdb , p:新建 t:改变类型
#3.在分区上创建文件系统
mkfs -v -t ext4 /dev/<xxx> 主分区
mkswap /dev/<xxx> 交换分区
#4.挂载文件系统
export LFS=/mnt/lfs
mkdir -pv $LFS
mount -v -t ext4 /dev/<xxx> $LFS 注:<xxx>为主分区
创建资源文件夹和工具文件夹
mkdir -v $LFS/sources
chmod -v a+wt $LFS/sources
mkdir -v $LFS/tools
ln -sv $LFS/tools /
添加LFS用户
groupadd lfs
useradd -s /bin/bash -g lfs -m -k /dev/null lfs
passwd lfs
chown -v lfs $LFS/tools
chown -v lfs $LFS/sources
su - lfs
LFS用户下环境变量的设置:
其中尤其要注意LFS_TGT的设置,之前因为我将其设为(uname -m)-lfs-linux-gnu后,在chroot后就发生了包mips64-lfs-linux-gnu下面的as等文件能看但是不能执行的结果,经分析,mips64el和mips64是不一样的,如果你要在mips64el即小端的机器上运行最终系统,那么现在编译的LFS_TGT也要设置为与原系统同平台的。
创建新的.bash_profile文件:
cat > ~/.bash_profile << "EOF"
exec env -i HOME=$HOME TERM=$TERM PS1='\u:\w\$ ' /bin/bash
EOF
创建.bashrc文件(非常重要):
cat > ~/.bashrc << "EOF"
set +h
umask 022
LFS=/mnt/lfs
LC_ALL=POSIX
LFS_TGT=$(uname -m)el-lfs-linux-gnu //目标机三元组
LFS_BLD=mips64el-redhat-linux-gnu //主机平台三元组
PATH=/tools/bin:/bin:/usr/bin
BUILD64="-mabi=64 -march=mips64r2 -mtune=loongson3a"
export LFS LC_ALL LFS_TGT PATH BUILD64
EOF
(LFS8.2第五章)接下来是各个包的编译(默认当前路径是在各个包的根目录下):
首先进行工具链的编译
1--- binutils---第一遍
mkdir build
cd build
../configure --build=$LFS_BLD \
--prefix=/tools \
--with-sysroot=$LFS \
--with-lib-path=/tools/lib \
--target=$LFS_TGT \
--disable-nls \
--disable-werror \
--with-abi=64 \
--with-endlan=little
make
make install
case $(uname -m) in
mips64) mkdir -v /tools/lib && ln -sv lib /tools/lib64 ;;
esac
1--- gcc---第一遍
tar -xf ../mpfr-4.0.1.tar.xz
mv -v mpfr-4.0.1 mpfr
tar -xf ../gmp-6.1.2.tar.xz
mv -v gmp-6.1.2 gmp
tar -xf ../mpc-1.1.0.tar.gz
mv -v mpc-1.1.0 mpc
for file in gcc/config/{linux,mips/linux}.h
do
cp -uv $file{,.orig}
sed -e 's@/lib\(64\)\?\(32\)\?/ld@/tools&@g' \
-e 's@/usr@/tools@g' $file.orig > $file
echo '
#undef STANDARD_STARTFILE_PREFIX_1
#undef STANDARD_STARTFILE_PREFIX_2
#define STANDARD_STARTFILE_PREFIX_1 "/tools/lib/"
#define STANDARD_STARTFILE_PREFIX_2 ""' >> $file
touch $file.orig
done
case $(uname -m) in mips64)
sed -e's/lib64/lib/g' \
-i.orig gcc/config/mips/t-linux64
;;
esac
mkdir -v build
cd build
../configure \
--build=$LFS_BLD \
--target=$LFS_TGT \
--prefix=/tools \
--with-glibc-version=2.11 \
--with-sysroot=$LFS \
--with-newlib \
--without-headers \
--with-local-prefix=/tools \
--with-native-system-header-dir=/tools/include \
--disable-nls \
--disable-shared \
--disable-multilib \
--disable-decimal-float \
--disable-threads \
--disable-libatomic \
--disable-libgomp \
--disable-libmpx \
--disable-libquadmath \
--disable-libssp \
--disable-libvtv \
--disable-libstdcxx \
--enable-languages=c,c++ \
--with-abi=64 \
--with-arch=mips64r2 \
--with-tune=loongson3a \
--without-madd4
make
make install
---Linux-4.15.3 API
make mrproper
make INSTALL_HDR_PATH=dest headers_install
cp -rv dest/include/* /tools/include
---Glibc-2.27
mkdir -v build
cd build
../configure \
--prefix=/tools \
--host=$LFS_TGT \
--build=$LFS_BLD \
--enable-kernel=3.2 \
--with-headers=/tools/include \
libc_cv_forced_unwind=yes \
libc_cv_c_cleanup=yes \
--with-abi=64 \
--with-endlan=little
make
make install
-----libstdc++
tar gcc
mkdir -v build
cd build
../libstdc++-v3/configure \
--build=$LFS_BLD \
--host=$LFS_TGT \
--prefix=/tools \
--disable-multilib \
--disable-nls \
--disable-libstdcxx-threads \
--disable-libstdcxx-pch \
--with-gxx-include-dir=/tools/$LFS_TGT/include/c++/7.3.0
make
make install
构建临时系统工具链,编译临时系统需要的工具
#2-------binutils---第二遍
mkdir -v build
cd build
#--host=$LFS_BLD \
CC=$LFS_TGT-gcc \
AR=$LFS_TGT-ar \
RANLIB=$LFS_TGT-ranlib \
../configure \
--build=$LFS_TGT \
--prefix=/tools \
--disable-nls \
--disable-werror \
--with-lib-path=/tools/lib \
--with-sysroot \
--with-abi=64 \
--with-endlan=little
make
make install
#为下面的调整工具链做准备
make -C ld clean
make -C ld LIB_PATH=/usr/lib:/lib
cp -v ld/ld-new /tools/bin
#2-------gcc---第二遍
tar -xf ../mpfr-4.0.1.tar.xz
mv -v mpfr-4.0.1 mpfr
tar -xf ../gmp-6.1.2.tar.xz
mv -v gmp-6.1.2 gmp
tar -xf ../mpc-1.1.0.tar.gz
mv -v mpc-1.1.0 mpc
cat gcc/limitx.h gcc/glimits.h gcc/limity.h > \
`dirname $($LFS_TGT-gcc -print-libgcc-file-name)`/include-fixed/limits.h
for file in gcc/config/{linux,mips/linux}.h
do
cp -uv $file{,.orig}
sed -e 's@/lib\(64\)\?\(32\)\?/ld@/tools&@g' \
-e 's@/usr@/tools@g' $file.orig > $file
echo '
#undef STANDARD_STARTFILE_PREFIX_1
#undef STANDARD_STARTFILE_PREFIX_2
#define STANDARD_STARTFILE_PREFIX_1 "/tools/lib/"
#define STANDARD_STARTFILE_PREFIX_2 ""' >> $file
touch $file.orig
done
case $(uname -m) in mips64)
sed -e's/lib64/lib/g' \
-i.orig gcc/config/mips/t-linux64
;;
esac
mkdir -v build
cd build
CC=$LFS_TGT-gcc \
CXX=$LFS_TGT-g++ \
AR=$LFS_TGT-ar \
RANLIB=$LFS_TGT-ranlib \
../configure \
--build=$LFS_TGT \
--prefix=/tools \
--with-local-prefix=/tools \
--with-native-system-header-dir=/tools/include \
--enable-languages=c,c++ \
--disable-libstdcxx-pch \
--disable-multilib \
--disable-bootstrap \
--disable-libgomp \
--with-abi=64 \
--with-arch=mips64r2 \
--with-tune=loongson3a \
--without-madd4
make
make install
ln -sv gcc /tools/bin/cc
测试:
echo 'int main(){}' > dummy.c
cc dummy.c
readelf -l a.out | grep ': /tools'
输出为:
[Requesting program interpreter: /tools/lib64/ld.so.1]
删除测试文件:
rm -rf dummy.c a.out
至此,新的工具链已经制作完毕,下一步就是利用该工具链构建临时系统:
---Tcl---
cd unix
./configure --prefix=/tools --build=$LFS_TGT
make
TZ=UTC make test
make install
chmod -v u+w /tools/lib/libtcl8.6.so
make install-private-headers
ln -sv tclsh8.6 /tools/bin/tclsh
---Expext---
cp -v configure{,.orig}
sed 's:/usr/local/bin:/bin:' configure.orig > configure
./configure --prefix=/tools \
--build=$LFS_TGT \
--with-tcl=/tools/lib \
--with-tclinclude=/tools/include
make
make test
make SCRIPTS="" install
---DejaGNU---
./configure --prefix=/tools --build=$LFS_TGT
make install
---M4---
./configure --prefix=/tools --build=$LFS_TGT
make
make install
---Ncurses---
sed -i s/mawk// configure
./configure --prefix=/tools \
--build=$LFS_TGT \
--with-shared \
--without-debug \
--without-ada \
--enable-widec \
--enable-overwrite
make
make install
---Bash---
./configure --build=$LFS_TGT --prefix=/tools --without-bash-malloc
make
make tests
make install
ln -sv bash /tools/bin/sh
---Bison---
./configure --build=$LFS_TGT --prefix=/tools
make
make install
---Bzip2---包格式有问题,需重新下载,命令如下:
wget http://ftp.clfs.org/pub/clfs/conglomeration/bzip2/bzip2-1.0.6.tar.gz
make
make PREFIX=/tools install
---Coreutils---
./configure --build=$LFS_TGT --prefix=/tools --enable-install-program=hostname
make
make install
---Diffutils---
./configure --build=$LFS_TGT --prefix=/tools
make
make install
---File---
./configure --build=$LFS_TGT --prefix=/tools
make
make install
---Findutils---
./configure --build=$LFS_TGT --prefix=/tools
make
make install
---Gawk---
./configure --build=$LFS_TGT --prefix=/tools
make
make install
---Gettext---
cd gettext-tools
EMACS="no" ./configure --build=$LFS_TGT --prefix=/tools --disable-shared
make -C gnulib-lib
make -C intl pluralx.c
make -C src msgfmt
make -C src msgmerge
make -C src xgettext
cp -v src/{msgfmt,msgmerge,xgettext} /tools/bin
---Grep---
./configure --build=$LFS_TGT --prefix=/tools
make
make install
---Gzip---
./configure --build=$LFS_TGT --prefix=/tools
make
make install
---Make---
sed -i '211,217 d; 219,229 d; 232 d' glob/glob.c
./configure --build=$LFS_TGT --prefix=/tools --without-guile
make
make install
---Patch---
./configure --build=$LFS_TGT --prefix=/tools
make
make install
---Perl---
sh Configure -des -Dprefix=/tools -Dlibs=-lm
make
cp -v perl cpan/podlators/scripts/pod2man /tools/bin
mkdir -pv /tools/lib/perl5/5.26.1
cp -Rv lib/* /tools/lib/perl5/5.26.1
---Sed---
./configure --build=$LFS_TGT --prefix=/tools
make
make install
---Tar---
./configure --build=$LFS_TGT --prefix=/tools
make
make install
---Textinfo---
./configure --build=$LFS_TGT --prefix=/tools
make
make install
---Util-linux---
./configure --build=$LFS_TGT \
--prefix=/tools \
--without-python \
--disable-makeinstall-chown \
--without-systemdsystemunitdir \
--without-ncurses \
PKG_CONFIG=""
make
make install
---Xz---
./configure --build=$LFS_TGT --prefix=/tools
make
make install
可选:删除不必要的符号和文档:
strip --strip-debug /tools/lib/*
/usr/bin/strip --strip-unneeded /tools/{,s}bin/*
rm -rf /tools/{,share}/{info,man,doc}
find /tools/{lib,libexec} -name \*.la -delete
改变所有权:(可以备份tools文件夹保留临时工具)
chown -R root:root $LFS/tools
接下来就是chroot进入临时系统(在root用户下进行):
mkdir -pv $LFS/{dev,proc,sys,run}
mknod -m 600 $LFS/dev/console c 5 1
mknod -m 666 $LFS/dev/null c 1 3
mount -v --bind /dev $LFS/dev
mount -vt devpts devpts $LFS/dev/pts -o gid=5,mode=620
mount -vt proc proc $LFS/proc
mount -vt sysfs sysfs $LFS/sys
mount -vt tmpfs tmpfs $LFS/run
if [ -h $LFS/dev/shm ]; then
mkdir -pv $LFS/$(readlink $LFS/dev/shm)
fi
chroot "$LFS" /tools/bin/env -i \
HOME=/root \
TERM="$TERM" \
PS1='(lfs chroot) \u:\w\$ ' \
PATH=/bin:/usr/bin:/sbin:/usr/sbin:/tools/bin \
/tools/bin/bash --login +h
创建标准目录树:
mkdir -pv /{bin,boot,etc/{opt,sysconfig},home,lib/firmware,mnt,opt}
mkdir -pv /{media/{floppy,cdrom},sbin,srv,var}
install -dv -m 0750 /root
install -dv -m 1777 /tmp /var/tmp
mkdir -pv /usr/{,local/}{bin,include,lib,sbin,src}
mkdir -pv /usr/{,local/}share/{color,dict,doc,info,locale,man}
mkdir -v /usr/{,local/}share/{misc,terminfo,zoneinfo}
mkdir -v /usr/libexec
mkdir -pv /usr/{,local/}share/man/man{1..8}
case $(uname -m) in
mips64) mkdir -v /lib64 ;;
esac
mkdir -v /var/{log,mail,spool}
ln -sv /run /var/run
ln -sv /run/lock /var/lock
mkdir -pv /var/{opt,cache,lib/{color,misc,locate},local}
创建基本文件和符号链接
ln -sv /tools/bin/{bash,cat,dd,echo,ln,pwd,rm,stty} /bin
ln -sv /tools/bin/{install,perl} /usr/bin
ln -sv /tools/lib/libgcc_s.so{,.1} /usr/lib
ln -sv /tools/lib/libstdc++.{a,so{,.6}} /usr/lib
ln -sv bash /bin/sh
ln -sv /proc/self/mounts /etc/mtab
cat > /etc/passwd << "EOF"
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/dev/null:/bin/false
daemon:x:6:6:Daemon User:/dev/null:/bin/false
messagebus:x:18:18:D-Bus Message Daemon User:/var/run/dbus:/bin/false
nobody:x:99:99:Unprivileged User:/dev/null:/bin/false
EOF
cat > /etc/group << "EOF"
root:x:0:
bin:x:1:daemon
sys:x:2:
kmem:x:3:
tape:x:4:
tty:x:5:
daemon:x:6:
floppy:x:7:
disk:x:8:
lp:x:9:
dialout:x:10:
audio:x:11:
video:x:12:
utmp:x:13:
usb:x:14:
cdrom:x:15:
adm:x:16:
messagebus:x:18:
systemd-journal:x:23:
input:x:24:
mail:x:34:
nogroup:x:99:
users:x:999:
EOF
exec /tools/bin/bash --login +h
touch /var/log/{btmp,lastlog,faillog,wtmp}
chgrp -v utmp /var/log/lastlog
chmod -v 664 /var/log/lastlog
chmod -v 600 /var/log/btmp
下面开始最终系统包的编译
---Linux-4.15.3 API---
make mrproper
ln -sv /bin/awk /bin/gawk
ln -sv /bin/gawk /tools/bin/gawk
make INSTALL_HDR_PATH=dest headers_install
find dest/include \( -name .install -o -name ..install.cmd \) -delete
cp -rv dest/include/* /usr/include
---man-pages---
make install
---Glibc---
patch -Np1 -i ../glibc-2.27-fhs-1.patch
ln -sfv /tools/lib/gcc /usr/lib
export GCC_INCDIR=/usr/lib/gcc/$(uname -m)el-pc-linux-gnu/7.3.0/include
ln -sfv ../lib/ld.so.1 /lib64
ln -sfv ../lib/ld.so.1 /lib64/lib64-lsb-mips64el.so.2
rm -rf /usr/include/limits.h
mkdir -v build
cd build
CC="gcc -isystem $GCC_INCDIR -isystem /usr/include" \
../configure --prefix=/usr \
--disable-werror \
--enable-kernel=3.2 \
--enable-stack-protector=strong \
libc_cv_slibdir=/lib
unset GCC_INCDIR
make
make check
touch /etc/ld.so.conf
sed '/test-installation/s@$(PERL)@echo not running@' -i ../Makefile
make install
cp -v ../nscd/nscd.conf /etc/nscd.conf
mkdir -pv /var/cache/nscd
```bash
mkdir -pv /usr/lib/locale
localedef -i cs_CZ -f UTF-8 cs_CZ.UTF-8
localedef -i de_DE -f ISO-8859-1 de_DE
localedef -i de_DE@euro -f ISO-8859-15 de_DE@euro
localedef -i de_DE -f UTF-8 de_DE.UTF-8
localedef -i en_GB -f UTF-8 en_GB.UTF-8
localedef -i en_HK -f ISO-8859-1 en_HK
localedef -i en_PH -f ISO-8859-1 en_PH
localedef -i en_US -f ISO-8859-1 en_US
localedef -i en_US -f UTF-8 en_US.UTF-8
localedef -i es_MX -f ISO-8859-1 es_MX
localedef -i fa_IR -f UTF-8 fa_IR
localedef -i fr_FR -f ISO-8859-1 fr_FR
localedef -i fr_FR@euro -f ISO-8859-15 fr_FR@euro
localedef -i fr_FR -f UTF-8 fr_FR.UTF-8
localedef -i it_IT -f ISO-8859-1 it_IT
localedef -i it_IT -f UTF-8 it_IT.UTF-8
localedef -i ja_JP -f EUC-JP ja_JP
localedef -i ru_RU -f KOI8-R ru_RU.KOI8-R
localedef -i ru_RU -f UTF-8 ru_RU.UTF-8
localedef -i tr_TR -f UTF-8 tr_TR.UTF-8
localedef -i zh_CN -f GB18030 zh_CN.GB18030
make localedata/install-locales
cat > /etc/nsswitch.conf << "EOF"
# Begin /etc/nsswitch.conf
passwd: files
group: files
shadow: files
hosts: files dns
networks: files
protocols: files
services: files
ethers: files
rpc: files
# End /etc/nsswitch.conf
EOF
tar -xf ../../tzdata2018c.tar.gz
ZONEINFO=/usr/share/zoneinfo
mkdir -pv $ZONEINFO/{posix,right}
for tz in etcetera southamerica northamerica europe africa antarctica \
asia australasia backward pacificnew systemv; do
zic -L /dev/null -d $ZONEINFO -y "sh yearistype.sh" ${tz}
zic -L /dev/null -d $ZONEINFO/posix -y "sh yearistype.sh" ${tz}
zic -L leapseconds -d $ZONEINFO/right -y "sh yearistype.sh" ${tz}
done
cp -v zone.tab zone1970.tab iso3166.tab $ZONEINFO
zic -d $ZONEINFO -p America/New_York
unset ZONEINFO
tzselect
cp -v /usr/share/zoneinfo/<xxx> /etc/localtime
cat > /etc/ld.so.conf << "EOF"
# Begin /etc/ld.so.conf
/usr/local/lib
/opt/lib
EOF
调整工具链:
mv -v /tools/bin/{ld,ld-old}
mv -v /tools/$(uname -m)el-lfs-linux-gnu/bin/{ld,ld-old}
mv -v /tools/bin/{ld-new,ld}
ln -sv /tools/bin/ld /tools/$(uname -m)el-lfs-linux-gnu/bin/ld
gcc -dumpspecs | sed -e 's@/tools@@g' \
-e '/\*startfile_prefix_spec:/{n;s@.*@/usr/lib/ @}' \
-e '/\*cpp:/{n;s@$@ -isystem /usr/include@}' > \
`dirname $(gcc --print-libgcc-file-name)`/specs
#现在对工具链的基本功能(编译和链接)进行测试
echo 'int main(){}' > dummy.c
cc dummy.c -v -Wl,--verbose &> dummy.log
readelf -l a.out | grep ': /lib'
输出:
[Requesting program interpreter: /lib64/ld.so.1]
grep -o '/usr/lib.*/crt[1in].*succeeded' dummy.log
输出:
/usr/lib/../lib/crt1.o succeeded
/usr/lib/../lib/crti.o succeeded
/usr/lib/../lib/crtn.o succeeded
grep -B1 '^ /usr/include' dummy.log
输出:
#include <...> search starts here:
/usr/include
grep 'SEARCH.*/usr/lib' dummy.log |sed 's|; |\n|g'
输出(忽略带有-linux-gnu的路径):
SEARCH_DIR("/usr/lib")
SEARCH_DIR("/lib");
grep "/lib.*/libc.so.6 " dummy.log
输出:
attempt to open /lib/libc.so.6 succeeded
grep found dummy.log
输出:
found ld-linux.so.2 at /lib/ld.so.1
删除测试文件:
rm -v dummy.c a.out dummy.log
编译最终系统的包
精简版系统(只有简单的几个命令比如ls cd 的版本,完整版请看下面)
---bc----
cat > bc/fix-libmath_h << "EOF"
#! /bin/bash
sed -e '1 s/^/{"/' \
-e 's/$/",/' \
-e '2,$ s/^/"/' \
-e '$ d' \
-i libmath.h
sed -e '$ s/$/0}/' \
-i libmath.h
EOF
ln -sv /tools/lib/libncursesw.so.6 /usr/lib/libncursesw.so.6
ln -sfv libncurses.so.6 /usr/lib/libncurses.so
sed -i -e '/flex/s/as_fn_error/: ;; # &/' configure
./configure --prefix=/usr \
--with-readline \
--mandir=/usr/share/man \
--infodir=/usr/share/info
make
make install
----Ncurses---
sed -i '/LIBTOOL_INSTALL/d' c++/Makefile.in
./configure --prefix=/usr \
--mandir=/usr/share/man \
--with-shared \
--without-debug \
--without-normal \
--enable-pc-files \
--enable-widec
make
make install
mv -v /usr/lib/libncursesw.so.6* /lib
ln -sfv ../../lib/$(readlink /usr/lib/libncursesw.so) /usr/lib/libncursesw.so
for lib in ncurses form panel menu ; do
rm -vf /usr/lib/lib${lib}.so
echo "INPUT(-l${lib}w)" > /usr/lib/lib${lib}.so
ln -sfv ${lib}w.pc /usr/lib/pkgconfig/${lib}.pc
done
rm -vf /usr/lib/libcursesw.so
echo "INPUT(-lncursesw)" > /usr/lib/libcursesw.so
ln -sfv libncurses.so /usr/lib/libcurses.so
----Bison---
./configure --prefix=/usr --docdir=/usr/share/doc/bison-3.0.4
make
make install
---Flex---
sed -i "/math.h/a #include <malloc.h>" src/flexdef.h
HELP2MAN=/tools/bin/true \
./configure --prefix=/usr --docdir=/usr/share/doc/flex-2.6.4
make
make install
ln -sv flex /usr/bin/lex
---Bash---
./configure --prefix=/usr \
--docdir=/usr/share/doc/bash-4.4.18 \
--without-bash-malloc \
--with-installed-readline
make
make install
mv -vf /usr/bin/bash /bin
exec /bin/bash --login +h
----CoreUtils---
FORCE_UNSAFE_CONFIGURE=1 ./configure \
--prefix=/usr \
--enable-no-install-program=kill,uptime
FORCE_UNSAFE_CONFIGURE=1 make
make install
mv -v /usr/bin/{cat,chgrp,chmod,chown,cp,date,dd,df,echo} /bin
mv -v /usr/bin/{false,ln,ls,mkdir,mknod,mv,pwd,rm} /bin
mv -v /usr/bin/{rmdir,stty,sync,true,uname} /bin
mv -v /usr/bin/chroot /usr/sbin
mv -v /usr/share/man/man1/chroot.1 /usr/share/man/man8/chroot.8
sed -i s/\"1\"/\"8\"/1 /usr/share/man/man8/chroot.8
mv -v /usr/bin/{head,sleep,nice} /bin
---Grub---
./configure --prefix=/usr \
--with-platform=loongson \
--with-target=mips64 \
--sbindir=/sbin \
--sysconfdir=/etc \
--disable-efiemu \
--disable-werror
make
make install
完整版系统
完整版LFS系统的编译就是按照LFS-8.2文档将其第六章所有的包均下载编译进系统,注意编译时也是要在chroot环境下进行,和精简版系统的编译流程相同,除了精简版系统提及的包,其他包可以按照官方文档进行编译。
添加systemd所需的os-release文件
注:无此文件在启动时会提示failed to switch with root
cat > /etc/os-release << "EOF"
NAME="Linux From Scratch On Loongson"
VERSION="8.2-systemd"
ID=lfs-loongson
PRETTY_NAME="Linux From Scratch On Loongson 8.2-systemd"
EOF
重新进入chroot:
chroot "$LFS" /usr/bin/env -i \
HOME=/root TERM="$TERM" \
PS1='(lfs chroot) \u:\w\$ ' \
PATH=/bin:/usr/bin:/sbin:/usr/sbin \
/bin/bash --login
cat > /etc/fstab << "EOF"
#Begin /etc/fstab
#file system mount-point type options dump fsck
#order
/dev/sdb1 / ext4 defaults 1 1
/dev/sdb2 swap swap pri=1 0 0
proc /proc proc nosuid,noexec,nodev 0 0
sysfs /sys sysfs nosuid,noexec,nodev 0 0
devpts /dev/pts devpts gid=5,mode=620 0 0
tmpfs /run tmpfs defaults 0 0
devtmpfs /dev devtmpfs mode=0755,nosuid 0 0
# End /etc/fstab
EOF
此外,还有一些其他配置,按照LFS-8.2官方文档的做即可。
移植内核
在该部分,为了节约时间,我们可以直接使用宿主机的内核镜像,即宿主机/boot目录下的vmlinuz文件,将/boot/vmlinuz, /boot/System.map, /boot/initramfs.img这三个文件拷贝到最终系统的boot目录下即可,或者是直接修改主机的grub.cfg文件,借用主机的内核来启动文件系统。
启动系统
有两种方法:
- 按照LFS-8.2官方文档的做法做下去,不过可能遇到grub-install失败的问题。
- 直接修改宿主机的grub文件(我采用的),由于我的机器是昆仑固件,所以修改了/boot/grub.cfg文件,具体添加内容如下:
menuentry 'GNU/Linux,LFS on MIPS-8.2'{
set root='hd1,msdos1'
linux /boot/vmlinuz root=/dev/sdb1 rootdelay=8
initrd /boot/initramfs-3.10.84-22.fc21.loongson.7.mips64el.img
boot
}
问题总结:
- 在编译最终系统的环节中,编译Linux API这个包时出现问题:在make install时,提示找不到mips64el-lfs-linux-gnu/bin/as,这个文件,猜测是主机环境被污染,需重新构建LFS,经分析是因为LFS_TGT设置错误,应设为mips64el-lfs-linux-gnu,而不是mips64-lfs-linux-gnu。
- 在编译最终系统时,grub包编译出错,提示:GRUB的configure对mips{,64}el-*都给出龙芯平台(platform=loongson)的猜测,抛出了configure: error: qemu, coreboot and loongson ports need build-time grub-mkfont (need freetype2 library)的错误,但是这个时候因为LFS没有给出编译freetype2的步骤,加上已经chroot了,并没有grub-mkfont可以用。
因此GRUB的configure对mipsisa64r2el-*直接判定未知处理器类型,不编译平台特定代码,绕过这一问题有两种办法:
给configure传–with-platform=none,让GRUB不编译平台特定的代码(同上,功能缺失)
在Host上复制一份,我没试过
3.grub-install失败,提示:grub-install: error: /usr/lib/grub/mipsel-loongson/modinfo.sh doesn’t exist. Please specify --target or --directory.
目前并未解决。不过有另外一种方法,可以绕过该过程:直接在宿主机的grub启动文件写入最终系统的启动信息即可。