首次 LFS 搭建全過程

    LFS linux全稱爲Linux From Scratch,重點是 Linux From Scratch 這個項目以及使用 LFS 系統帶來的好處。用戶可以控制系統的所有特徵,包括目錄佈局、腳本設置和安全設置等等。最終的系統將從源代碼直接編譯生成,用戶可以指定在哪裏安裝、爲什麼安裝以及怎樣安裝每一個程序。可以完全按照自己的需求定製他們的 Linux 系統,而且使用戶對他們的系統有更多的控制權。

Linux From Scratch 7.7 官方在線手冊

Linux From Scratch 7.7 官方文檔 PDF版

Linux From Scratch 7.7 工具包


本案環境:CentOS 6.6 全新最小安裝。

[root@lft ~]# cat /etc/centos-release && uname -r
CentOS release 6.6 (Final)
2.6.32-504.el6.x86_64

1.環境檢測:

cat > version-check.sh << "EOF"
#!/bin/bash
# Simple script to list version numbers of critical development tools

export LC_ALL=C
bash --version | head -n1 | cut -d" " -f2-4
echo "/bin/sh -> `readlink -f /bin/sh`"
echo -n "Binutils: "; ld --version | head -n1 | cut -d" " -f3-
bison --version | head -n1

if [ -h /usr/bin/yacc ]; then
  echo "/usr/bin/yacc -> `readlink -f /usr/bin/yacc`";
elif [ -x /usr/bin/yacc ]; then
  echo yacc is `/usr/bin/yacc -V | head -n1`
else
  echo "yacc not found" 
fi

bzip2 --version 2>&1 < /dev/null | head -n1 | cut -d" " -f1,6-
echo -n "Coreutils: "; chown --version | head -n1 | cut -d")" -f2
diff --version | head -n1
find --version | head -n1
gawk --version | head -n1

if [ -h /usr/bin/awk ]; then
  echo "/usr/bin/awk -> `readlink -f /usr/bin/awk`";
elif [ -x /usr/bin/awk ]; then
  echo yacc is `/usr/bin/awk --version | head -n1`
else 
  echo "awk not found" 
fi

gcc --version | head -n1
g++ --version | head -n1
ldd --version | head -n1 | cut -d" " -f2-  # glibc version
grep --version | head -n1
gzip --version | head -n1
cat /proc/version
m4 --version | head -n1
make --version | head -n1
patch --version | head -n1
echo Perl `perl -V:version`
sed --version | head -n1
tar --version | head -n1
makeinfo --version | head -n1
xz --version | head -n1

echo 'main(){}' > dummy.c && g++ -o dummy dummy.c
if [ -x dummy ]
  then echo "g++ compilation OK";
  else echo "g++ compilation failed"; fi
rm -f dummy.c dummy
EOF

bash version-check.sh

編譯庫環境檢查:

cat > library-check.sh << "EOF"
#!/bin/bash
for lib in lib{gmp,mpfr,mpc}.la; do
  echo $lib: $(if find /usr/lib* -name $lib|
               grep -q $lib;then :;else echo not;fi) found
done
unset lib
EOF

bash library-check.sh

本案需要:

yum install epel-release -y
yum install gcc bison binutils byacc perl patch xz texinfo gcc-c++ -y
yum install gmp-devel mpfr-devel libmpc-devel -y

2 LFS前期準備

1.LFS存儲準備:

爲LFS創建一個獨立磁盤20G,這裏可以按照你自己的需要的分區,這裏我按照設置一個根分區和一個交換分區爲例,交換分區佔用1G,其餘的全部分給根分區。

磁盤分區    作用

/dev/sda1    swap

/dev/sda2  作爲目標系統根目錄

創建及掛載目標根分區:

cfdisk /dev/sdb              #使用cfdisk分區工具
mkfs -v -t ext4 /dev/sdb2    #格式化目標系統根目錄
mkswap /dev/sdb1             #格式化交換分區格
blkid                        #查看分區情況
export LFS=/mnt/lfs          #創建環境變量,$LFS來作爲lfs工程的存儲根目錄
mkdir -pv $LFS/lfs           #創建目標根目錄掛載點
mount /dev/sdb2 $LFS         #掛載目標根目錄

2.創建必要的目錄並下載源碼文件

創建源代碼編譯用目錄,修改權限並下載文件

代碼:

mkdir -v $LFS/sources
chmod -v a+wt $LFS/sources
cd $LFS/sources
wget ftp://mirrors-usa.go-parts.com/lfs/lfs-packages/7.7/wget-list
wget --input-file=wget-list --continue --directory-prefix=$LFS/sources

相關知識點:

  chmod a+wt是將目錄或文件的屬性設置爲1777,這樣任何人都可以對其進行讀寫。

驗證下載的文件

pushd $LFS/sources
md5sum -c md5sums
popd

3.創建工具鏈目錄

mkdir -v /lfs/tools
ln -sv /lfs/tools /

注意:

  ln -sv /lfs/tools執行後應該會輸出

    `/tools' -> `/lfs/tools'

  表示正確。


4.加載交換分區(如果不想用交換分區或者沒有交換分區可跳過此步驟)

swapon /dev/hda1

5.建立工具鏈的鏈接

ln -sv $LFS/tools /

6.創建lfs用戶

爲了避免使用權限大的賬號誤操作造成宿主機損失,新建一個lfs賬戶,加入lfs組,並且將$LFS下的src和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用戶環境

7.建立lfs用戶的環境

cat > ~/.bash_profile << "EOF"
exec env -i HOME=$HOME TERM=$TERM PS1='\u:\w\$ ' /bin/bash
EOF
cat > ~/.bashrc << "EOF"
set +h
umask 022
LFS=/lfs
LC_ALL=POSIX
PATH=/tools/bin:/bin:/usr/bin
export LFS LC_ALL PATH
EOF
source ~/.bash_profile

8.檢查一下

export命令查看輸出,應該是

declare -x HOME="/home/lfs"

declare -x LC_ALL="POSIX"

declare -x LFS="/lfs"

declare -x OLDPWD

declare -x PATH="/tools/bin:/bin:/usr/bin"

declare -x PS1="\\u:\\w\\\$ "

declare -x PWD="/home/lfs"

declare -x SHLVL="1"

declare -x TERM="linux"

9.進入編譯目錄

cd $LFS/sources

基本上就恢復工作狀態了。


3.開始工具鏈的製作

進入LFS包編譯目錄,基於新版本的tar包支持自動識別文件後綴,本案所有的tar包使用xvf 選擇解壓。

3.1 Binutils-2.25 首次編譯

3.1.1 解包和編譯目錄創建

cd $LFS/sources
tar xvf $LFS/sources/binutils-2.25.tar.bz2
cd binutils-2.17
mkdir -v ../binutils-build
cd ../binutils-build

3.1.2 配置編譯環境

../binutils-2.25/configure --prefix=/tools --with-sysroot=$LFS \
    --with-lib-path=/tools/lib --target=$LFS_TGT --disable-nls \
    --disable-werror

--prefix=/tools

這告訴配置腳本安裝Binutils項目做準備 /tools目錄中。

--with-sysroot=$LFS

對於交叉編譯,這講述了構建系統在$ LFS尋找目標系統所需的庫。

--with-lib-path=/tools/lib

這指定庫路徑鏈接器應該配置爲使用。

--target=$LFS_TGT

因爲機器的描述 LFS_TGT變量比返回的值略有不同 config.guess腳本,這個開關會告訴的 配置腳本調整Binutil構建系統的交聯劑。

--disable-nls

這種禁用國際化i18n是暫時不需要工具。

--disable-werror

編譯器中止編譯了

3.1.3 安裝

make
---------- 64位系統 ----------
case $(uname -m) in
  x86_64) mkdir -v /tools/lib && ln -sv lib /tools/lib64 ;;
esac
---------- 64位系統 ----------
make install

3.2 GCC-4.9.2 首次編譯

3.2.1 解壓GCC包,並進入解壓後的文件夾,將mpfr,gmp,mpc解壓到gcc-4.9.2內。

cd $LFS/sources
tar xvf sources/gcc-4.9.2.tar.bz2
cd gcc-4.9.2
tar -xf ../mpfr-3.1.2.tar.xz
mv -v mpfr-3.1.2 mpfr
tar -xf ../gmp-6.0.0a.tar.xz
mv -v gmp-6.0.0 gmp
tar -xf ../mpc-1.0.2.tar.gz
mv -v mpc-1.0.2 mpc
mkdir -v ../gcc-build
cd ../gcc-build

3.2.2 配置編譯環境:

for file in \
 $(find gcc/config -name linux64.h -o -name linux.h -o -name sysv4.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

3.2.3 配置編譯:

sed -i '/k prot/agcc_cv_libc_provides_ssp=yes' gcc/configure

3.2.4 創建編譯目錄

mkdir -v ../gcc-build
cd ../gcc-build

3.2.5 編譯和安裝:

../gcc-4.9.2/configure --target=$LFS_TGT --prefix=/tools  --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-libitm --disable-libquadmath    \
    --disable-libsanitizer  --disable-libssp --disable-libvtv  --disable-libcilkrts \
    --disable-libstdc++-v3 --enable-languages=c,c++
make
make install

3.3 Linux-3.19 API Headers

cd $LFS/sources
tar xvf linux-3.19
make mrproper
make INSTALL_HDR_PATH=dest headers_installcp -rv dest/include/* /tools/include

3.4 Glibc-2.21

3.4.1 

cd $LFS/sources
tar xvf glibc-2.21
cd glibc-2.21

3.4.2 

if [ ! -r /usr/include/rpc/types.h ]; then
  su -c 'mkdir -pv /usr/include/rpc'
  su -c 'cp -v sunrpc/rpc/*.h /usr/include/rpc'
fi

3.4.3 

sed -e '/ia32/s/^/1:/' \
    -e '/SSE2/s/^1://' \
    -i  sysdeps/i386/i686/multiarch/mempcpy_chk.S

3.4.4 

mkdir -v ../glibc-build
cd ../glibc-build

3.4.5 

../glibc-2.21/configure                             \
      --prefix=/tools                               \
      --host=$LFS_TGT                               \
      --build=$(../glibc-2.21/scripts/config.guess) \
      --disable-profile                             \
      --enable-kernel=2.6.32                        \
      --with-headers=/tools/include                 \
      libc_cv_forced_unwind=yes                     \
      libc_cv_ctors_header=yes                      \
      libc_cv_c_cleanup=yes
make
make install

3.4.6 測試:

echo 'main(){}' > dummy.c
$LFS_TGT-gcc dummy.c
readelf -l a.out | grep ': /tools'

測試結果:

[Requesting program interpreter: /tools/lib/ld-linux.so.2]
rm -v dummy.c a.out

3.5 Libstdc++-4.9.2 

刪掉之前的GCC編譯目錄,重新新建GCC-build目錄:

rm -rf ../gcc-build
mkdir -pv ../gcc-build
cd ../gcc-build
../gcc-4.9.2/libstdc++-v3/configure \
    --host=$LFS_TGT                 \
    --prefix=/tools                 \
    --disable-multilib              \
    --disable-shared                \
    --disable-nls                   \
    --disable-libstdcxx-threads     \
    --disable-libstdcxx-pch         \
    --with-gxx-include-dir=/tools/$LFS_TGT/include/c++/4.9.2
make
make install

3.6 Binutils-2.25 二次編譯

rm -rf ../binutils-build
mkdir -v ../binutils-build
cd ../binutils-build
CC=$LFS_TGT-gcc                \
AR=$LFS_TGT-ar                 \
RANLIB=$LFS_TGT-ranlib         \
../binutils-2.25/configure     \
    --prefix=/tools            \
    --disable-nls              \
    --disable-werror           \
    --with-lib-path=/tools/lib \
    --with-sysroot
make
make install
make -C ld clean
make -C ld LIB_PATH=/usr/lib:/lib
cp -v ld/ld-new /tools/bin

3.7 GCC-4.9.2 二次編譯

3.7.1 進入gcc解壓目錄

cd $LFS/sources/gcc-4.9.2

3.7.2 限制文件:

cat gcc/limitx.h gcc/glimits.h gcc/limity.h > \
  `dirname $($LFS_TGT-gcc -print-libgcc-file-name)`/include-fixed/limits.h

3.7.3 編譯環境:

for file in \
 $(find gcc/config -name linux64.h -o -name linux.h -o -name sysv4.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

3.7.4 加入mpfr,gmp,mpc三個包的支持

tar -xf ../mpfr-3.1.2.tar.xz
mv -v mpfr-3.1.2 mpfr
tar -xf ../gmp-6.0.0a.tar.xz
mv -v gmp-6.0.0 gmp
tar -xf ../mpc-1.0.2.tar.gz
mv -v mpc-1.0.2 mpc

3.7.5 重新創建GCC 編譯目錄

rm -rf ../gcc-build
mkdir -v ../gcc-build
cd ../gcc-build

3.7.6 配置編譯選項,以及安裝:

CC=$LFS_TGT-gcc                                      \
CXX=$LFS_TGT-g++                                     \
AR=$LFS_TGT-ar                                       \
RANLIB=$LFS_TGT-ranlib                               \
../gcc-4.9.2/configure                               \
    --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
make
make install

3.7.8 做個軟連接

ln -sv gcc /tools/bin/cc

3.7.9 測試:

echo 'main(){}' > dummy.c
cc dummy.c
readelf -l a.out | grep ': /tools'

測試結果

      [Requesting program interpreter: /tools/lib64/ld-linux-x86-64.so.2]

記得刪除測試文件

rm -v dummy.c a.out


3.8 Tcl-8.6.3

編譯安裝並測試

cd /mnt/lfs/sources/
tar xvf tcl8.6.3-src.tar.gz
cd tcl8.6.3
./configure --prefix=/tools
make
TZ=UTC make test

wKioL1VGAwKjgCtzAADHW2oYSpE465.jpg

根據以上信息,一共測試116項,全通過,意味可以安裝

chmod -v u+w /tools/lib/libtcl8.6.so                           #給tcl庫文件加上屬主寫權限
mode of `/tools/lib/libtcl8.6.so' changed to 0755 (rwxr-xr-x)  #回顯信息
make install-private-headers                                   #安裝tcl頭文件
Installing private header files to /tools/include/             #回顯信息
ln -sv tclsh8.6 /tools/bin/tclsh                               #製作軟連接
`/tools/bin/tclsh' -> `tclsh8.6'                               #回顯信息

3.9 Expect-5.45

cd $LFS/sources
tar xvf expect5.45.tar.gz
cd expect5.45

重寫configure文件

cp -v configure{,.orig}
sed 's:/usr/local/bin:/bin:' configure.orig > configure

編譯安裝

./configure --prefix=/tools       \
            --with-tcl=/tools/lib \
            --with-tclinclude=/tools/include
make
make test

wKioL1VGBnKT-mblAAC8Ltxh35Q910.jpg

測試26個文件,成功一半失敗一半。官方文檔說明本次測試的失敗結果可以忽略。

繼續安裝:

make SCRIPTS="" install

3.10 DejaGNU-1.5.2


cd $LFS/sources
tar xvf dejagnu-1.5.2.tar.gz
cd dejagnu-1.5.2
./configure --prefix=/tools
make install
make check


3.11 Check-0.9.14

返回$LFS/sources 解壓並安裝Check

cd $LFS/sources
tar xvf check-0.9.14.tar.gz 
cd check-0.9.14

編譯選項

PKG_CONFIG= ./configure --prefix=/tools
make
make check

wKioL1VGCtnwBba5AAEKt47frao599.jpg

從圖中可以看到7個測試全通過,繼續安裝即可

make install

3.12 Ncurses-5.9

米什麼好說的,編譯安裝三部曲。

cd $LFS/sources
tar xvf ncurses-5.9.tar.gz
cd ncurses-5.9
./configure --prefix=/tools --with-shared --without-debug --without-ada  --enable-widec \    --enable-overwrite
make
make install

3.13 Bash-4.3.30

編譯安裝後加個軟鏈

cd $LFS/sources
tar xvf bash-4.3.30.tar.gz
cd bash-4.3.30
./configure --prefix=/tools --without-bash-malloc
make
make tests
make install
ln -sv bash /tools/bin/sh

3.14 Bzip2-1.0.6

cd $LFS/sources
tar xvf bzip2-1.0.6.tar.gz
cd bzip2-1.0.6
make
make PREFIX=/tools install

3.15 Coreutils-8.23

tar xvf coreutils-8.23.tar.xz
cd coreutils-8.23
./configure --prefix=/tools --enable-install-program=hostname
make
make RUN_EXPENSIVE_TESTS=yes check        #只要測試沒有失敗或錯誤,即繼續安裝
make install

3.16 Diffutils-3.3

3.17 File-5.22 

3.18 Findutils-4.4.2

3.19 Gawk-4.1.1

3.20 Gettext-0.19.4

tar xvf gettext-0.19.4.tar.xz 
cd gettext-0.19.4

編譯

cd gettext-tools
EMACS="no" ./configure --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

3.21 Grep-2.21

3.22 Gzip-1.6

3.23 M4-1.4.17

3.24 Patch-2.7.4

3.25 Perl-5.20.2

3.26 Sed-4.2.2

3.27 Tar-1.28

3.28 Texinfo-5.2

3.29 Util-linux-2.26

3.30 Xz-5.2.0

3.31 Stripping

    工具已經安裝,這一步是清理,是可有可無的,如果你打算今後還要用/tools裏面的東西,那麼可以strip一下來減少佔用的磁盤空間,但如果做完目標系統後就刪除了,不Strip也可以,反正最後也是要刪掉的。

strip --strip-debug /tools/lib/*
#/usr/bin/strip --strip-unneeded /tools/{,s}bin/*
#rm -rf /tools/{,share}/{info,man,doc}


後面的步驟不再需要lfs用戶權限,退出lfs用戶,用root修改文件權限。

   以後的操作也直接用root操作,注意時刻檢查變量$LFS的值

exit
chown -R root:root $LFS/tools

至此,工具鏈完全製作完畢。


4.準備虛擬內核文件系統

建立系統掛載目錄

export LFS=/mnt/lfs
mkdir -pv $LFS/{dev,proc,sys,run}

4.1 創建初始設備節點

mknod -m 600 $LFS/dev/console c 5 1
mknod -m 666 $LFS/dev/null c 1 3

4.2 掛載並填充設備目錄

mount -v --bind /dev $LFS/dev

4.3 掛載虛擬內核文件系統

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

4.4 進入chroot環境

chroot "$LFS" /tools/bin/env -i \
    HOME=/root                  \
    TERM="$TERM"                \
    PS1='\u:\w\$ '              \
    PATH=/bin:/usr/bin:/sbin:/usr/sbin:/tools/bin \
    /tools/bin/bash --login +h

4.5 建立必要目錄、符號鏈接與文件

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
 x86_64) ln -sv lib /lib64
         ln -sv lib /usr/lib64
         ln -sv lib /usr/local/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}

4.6 建立基本文件和符號鏈接

ln -sv /tools/bin/{bash,cat,echo,pwd,stty} /bin
ln -sv /tools/bin/perl /usr/bin
ln -sv /tools/lib/libgcc_s.so{,.1} /usr/lib
ln -sv /tools/lib/libstdc++.so{,.6} /usr/lib
sed 's/tools/usr/' /tools/lib/libstdc++.la > /usr/lib/libstdc++.la
ln -sv bash /bin/sh

ln -sv /proc/self/mounts /etc/mtab

創建用戶存儲文件passwd

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/falseEOF

創建用戶組文件group

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

這時候可以把用戶名位置那討厭的“I have no name!”去掉了

exec /tools/bin/bash --login +h

用戶名成功變身root

再建立一些必要的日誌文件,就可以進行系統編譯啦

touch /var/log/{btmp,lastlog,wtmp}
chgrp -v utmp /var/log/lastlog
chmod -v 664  /var/log/lastlog
chmod -v 600  /var/log/btmp

以下是LFS系統的基礎系統編譯

4.7 Linux-3.19 API Headers

#進入linux包
cd /sources/linux-3.19
#
make mrproper
#重新編譯
make INSTALL_HDR_PATH=dest headers_install
# 刪除非必要文件
find dest/include \( -name .install -o -name ..install.cmd \) -deletecp -rv dest/include/* /usr/include

4.8 Man-pages-3.79

cd /sources
tar xvf man-pages-3.79.tar.xz 
cd man-pages-3.79
make install

4.9 Glibc-2.21

cd /sources/glibc-2.21
patch -Np1 -i ../glibc-2.21-fhs-1.patch    #打補丁

解決32位兼容問題

sed -e '/ia32/s/^/1:/' \
    -e '/SSE2/s/^1://' \
    -i  sysdeps/i386/i686/multiarch/mempcpy_chk.S

重新創立glibc-build 目錄

rm -rf ../glibc-build
mkdir -v ../glibc-build
cd ../glibc-build
../glibc-2.21/configure --prefix=/usr --disable-profile --enable-kernel=2.6.32 --enable-obsolete-rpc
make
make check
touch /etc/ld.so.conf  #官方說明:爲預防安裝中的警告,建立一個文件
make install

爲nscd建立配置文件和運行時目錄

cp -v ../glibc-2.21/nscd/nscd.conf /etc/nscd.conf
mkdir -pv /var/cache/nscd

地方配置

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

配置glic

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 ../tzdata2015a.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

其中America/New_York可以改成其他地區,官方文檔上是按紐約時間走的。不過沒關係,時區和語言設置可以在系統運行之後再調整。


現在也可以調整,使用tzselect

然後按照提示選擇:大洲->國家->時區->確認

tzselect

或者直接將地區文件複製替換/etc/localtime,比如將時間調整爲上海時間

cp -v /usr/share/zoneinfo/Asia/Shanghai /etc/localtime

配置動態加載

cat > /etc/ld.so.conf << "EOF"
# Begin /etc/ld.so.conf
/usr/local/lib
/opt/lib
EOF

cat >> /etc/ld.so.conf << "EOF"
# Add an include directory
include /etc/ld.so.conf.d/*.conf
EOF


mkdir -pv /etc/ld.so.conf.d

4.10 調整工具鏈

mv -v /tools/bin/{ld,ld-old}
mv -v /tools/$(gcc -dumpmachine)/bin/{ld,ld-old}
mv -v /tools/bin/{ld-new,ld}
ln -sv /tools/bin/ld /tools/$(gcc -dumpmachine)/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 'main(){}' > dummy.c
cc dummy.c -v -Wl,--verbose &> dummy.log
readelf -l a.out | grep ': /lib'
grep -o '/usr/lib.*/crt[1in].*succeeded' dummy.log
grep -B1 '^ /usr/include' dummy.log
grep 'SEARCH.*/usr/lib' dummy.log |sed 's|; |\n|g'
grep "/lib.*/libc.so.6 " dummy.log
grep found dummy.log

wKioL1VGU8KRDLjCAAPlqjrcIH8748.jpg

最後刪除測試文件

rm -v dummy.c a.out dummy.log

4.11 Zlib-1.2.8

cd /sources
tar xvf zlib-1.2.8.tar.xz
./configure --prefix=/usr
make
make check
make install
mv -v /usr/lib/libz.so.* /lib
ln -sfv ../../lib/$(readlink /usr/lib/libz.so) /usr/lib/libz.so

4.12 File-5.22

cd ../file-5.22
./configure --prefix=/usr
make && make check
make install

4.13 Binutils-2.25

由於chroot進來,需要先進行一個環境測試

expect -c "spawn ls"

回顯:

spawn ls

重建目錄

rm -rf ../binutils-build/
mkdir -v ../binutils-build
cd ../binutils-build

配置編譯選項

../binutils-2.25/configure --prefix=/usr --enable-shared --disable-werror
make tooldir=/usr
make -k check
make tooldir=/usr install

4.14 GMP-6.0.0a

進入目錄:

cd /sources
tar xf gmp-6.0.0a.tar.xz
cd gmp-6.0.0

32位系統的加前綴: 

ABI=32 ./configure ...

64位系統,無須前綴,直接繼續

./configure --prefix=/usr --enable-cxx --docdir=/usr/share/doc/gmp-6.0.0a
make
make html
make check 2>&1 | tee gmp-check-log

測試,確保188個項目全部通過。用以下命令提取

awk '/tests passed/{total+=$2} ; END{print total}' gmp-check-log

安裝包和文檔

make install && make install-html

4.15 MPFR-3.1.2

cd /sources 
tar xvf mpfr-3.1.2.tar.xz
cd mpfr-3.1.2
patch -Np1 -i ../mpfr-3.1.2-upstream_fixes-3.patch        #打個補丁
./configure --prefix=/usr --enable-thread-safe --docdir=/usr/share/doc/mpfr-3.1.2
make && make html
make check
make install && make install-html

4.16 MPC-1.0.2

cd /sources 
tar xvf mpc-1.0.2.tar.gz
./configure --prefix=/usr --docdir=/usr/share/doc/mpc-1.0.2
make && make html
make check
make install && make install-html

4.17 GCC-4.9.2

rm -rf ../gcc-build
mkdir -v ../gcc-build
cd ../gcc-build

重新配置

SED=sed                       \
../gcc-4.9.2/configure        \
     --prefix=/usr            \
     --enable-languages=c,c++ \
     --disable-multilib       \
     --disable-bootstrap      \
     --with-system-zlib
make

編譯完成,在測試之前需要修改堆棧限制

ulimit -s 32768

測試,測試時間會很長!!

make -k check
../gcc-4.9.2/contrib/test_summary     #執行腳本查看測試結果

安裝:

make install
ln -sv ../usr/bin/cpp /lib
ln -sv gcc /usr/bin/cc
install -v -dm755 /usr/lib/bfd-plugins
ln -sfv ../../libexec/gcc/$(gcc -dumpmachine)/4.9.2/liblto_plugin.so /usr/lib/bfd-plugins/

測試:

echo 'main(){}' > dummy.c
cc dummy.c -v -Wl,--verbose &> dummy.log
readelf -l a.out | grep '/lib'              #官方文檔使用的是grep ': /lib'
grep -o '/usr/lib.*/crt[1in].*succeeded' dummy.log
grep -B4 '^ /usr/include' dummy.log
grep 'SEARCH.*/usr/lib' dummy.log |sed 's|; |\n|g'
grep "/lib.*/libc.so.6 " dummy.log
grep found dummy.log

回顯:

wKiom1VG9srSPQ4PAAZtfa6Kp14822.jpg

刪除測試文件:

rm -v dummy.c a.out dummy.log

移動錯位的文件:

mkdir -pv /usr/share/gdb/auto-load/usr/lib
mv -v /usr/lib/*gdb.py /usr/share/gdb/auto-load/usr/lib

4.18 Bzip2-1.0.6

rm -rf bzip2-1.0.6                #記得刪除之前的目錄!否則在下面準備編譯的時候會報錯
tar xvf bzip2-1.0.6
patch -Np1 -i ../bzip2-1.0.6-install_docs-1.patch        #打補丁,
sed -i 's@\(ln -s -f \)$(PREFIX)/bin/@\1@' Makefile        #修正一些錯誤。
sed -i "s@(PREFIX)/man@(PREFIX)/share/man@g" Makefile

Bzip2準備編譯:

make -f Makefile-libbz2_so            #如果直接使用上次目錄,會報錯。
make clean

編譯和安裝

make && make PREFIX=/usr install

共享bzip2二進制安裝到/ bin目錄中,做一些必要的符號鏈接,和清理:

cp -v bzip2-shared /bin/bzip2
cp -av libbz2.so* /lib
ln -sv ../../lib/libbz2.so.1.0 /usr/lib/libbz2.so
rm -v /usr/bin/{bunzip2,bzcat,bzip2}
ln -sv bzip2 /bin/bunzip2
ln -sv bzip2 /bin/bzcat

4.19 Pkg-config-0.28

4.20 Ncurses-5.9

4.21 Attr-2.4.47

4.22 Acl-2.2.52

4.23 Libcap-2.24

4.24 Sed-4.2.2

4.25 Shadow-4.2.1
4.26 Psmisc-22.21

4.27 Procps-ng-3.3.10

4.28 E2fsprogs-1.42.12

4.29 Coreutils-8.23

錯誤

wKioL1VHIB6TkXyjAAOXOWbSlXM605.jpg

  GEN      man/cp.1
help2man: can't get `--help' info from man/cp.td/cp
Try `--no-discard-stderr' if option outputs to stderr
Makefile:14066: recipe for target 'man/cp.1' failed
make[2]: *** [man/cp.1] Error 127
make[2]: Leaving directory '/sources/coreutils-8.23'
Makefile:11098: recipe for target 'all-recursive' failed
make[1]: *** [all-recursive] Error 1
make[1]: Leaving directory '/sources/coreutils-8.23'
Makefile:5765: recipe for target 'all' failed
make: *** [all] Error 2


解決方案:

開啓另一個終端,

vi /mnt/lfs/sources/coreutils-8.23/Makefile 
#找到行:
run_help2man = $(PERL) -- $(srcdir)/man/help2man 
#將上面行修改爲:
run_help2man = $(PERL) -- $(srcdir)/man/help2man --no-discard-stderr


卡殼了,處理完再繼續!!


現在出現的問題是, make 之後,

make NON_ROOT_USERNAME=nobody check-root

測試無法正常結束,停止在離開目錄界面, 跳過測試,強行make install ,發現lib多個lib文件無法找到。 將lib文件由源lib連接到lib64後make install 可以完成,再接着mv 後, 發現後面的tar包無法再解壓,無法make ,無法ls ... 大部分命令無法操作。。

請求指點!















發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章