内核头文件

根据 Glibc 的 FAQ ,编译 Glibc 时使用的内核头文件版本可以比实际运行 Glibc 的内核版本高。比如用于编译 Glibc 的内核头文件版本为 2.6.24 ,但是实际运行 Glibc 的可以是 2.6.16 版本的内核(编译 Glibc 时必须使用 –enable-kernel=2.6.16 而不能使用 –enable-kernel=2.6.24 )。允许这样做的好处是即使将来把内核升级到 2.6.24 也不需要重新编译 Glibc 了。

另一方面,如果实际运行的内核版本比头文件版本高,那么新内核的新特性(主要是系统调用)将无法被Glibc使用。[注意]不要直接 INSTALL_HDR_PATH=/usr ,这样可能使得Glibc变得不稳定。

[小提示]如果将来把内核升级为更高版本,头文件是不是也需要跟着一起升级?答案是:NO!! 关于内核头文件变迁的历史,这里有一篇《[八卦故事]内核头文件传奇》,可以当作课外读物 

( test ! -f $SRC/build.log ) && [ "`pwd`" = "$SRC" ] &&
R=/root/linux-headers-2.6.24.2/ &&
tar -xf linux-2.6.24.2.tar.bz2 && cd linux-2.6.24.2 &&
make distclean && make headers_check ARCH=x86 &&
make headers_install ARCH=x86 INSTALL_HDR_PATH=$R/usr &&
cp -r $R/usr/include /usr/ &&
cd $SRC && rm */ &&
echo '1-kernel-headers' >> $SRC/build.log && sync &&Glibc

Glibc 的安装指南中说测试套件中的某些测试项目是假定以非 root 身份运行的,因此建议使用普通用户身份进行编译与安装。不过经过实践,以 root 用户进行编译和安装也没问题。这里仅安装了 zh_CN.UTF-8 的 locale 支持,如果你想支持更多的 locale 请自己添加适当的 localedef 命令。出于安全最大化的考虑还禁用了 DNS 。将时区设为UTC(相当于取消时区的概念,如果你有使用时区的需求可以设为”PRC”)。

更多关于安装 Glibc 的信息,请查看源码树下的 configure INSTALL FAQ 三个文件。[提示]由于没有安装C++编译器的缘故,bug-atexit3-lib.os tst-cancel24.o c++-types-check 测试将会失败,你可以安全的忽略它。touch用于阻止可能发生的Autoconf调用(当Makefile检测到一个configure文件的时间戳比它对应的configure.in文件旧的时候),这种调用有时候会导致编译失败。

将”/dev/log”修改为”/dev/shm/log”是因为将来的根文件系统是只读挂载的,而syslogd会在启动的时候删除并重建此socket。Glibc GCC Binutils 三者是整个工具链的核心,因此如何对其进行定制就显得很重要。这里有一篇文章《Glibc 安装指南》,可以在漫长的编译过程中作为参考资料读一读。

R=/root/glibc-2.6.1/ && mkdir {,$R}/usr/lib/locale &&
tar -xf glibc-2.6.1.tar.bz2 && cd glibc-2.6.1 &&
sed -i 's|libs -o|libs -L/usr/lib -Wl,-dynamic-linker=/lib/ld-linux.so.2 -o|' scripts/test-installation.pl &&
sed -r -i 's:/bin/(pwd|cat):\1:g' configure{.in,} io/ftwtest-sh stdio-common/{test-popen,xbug,tstscanf}.c &&
sed -i -e's|^rootsbindir =.*|rootsbindir=/usr/bin|' -e's|^sbindir =.*|sbindir=/usr/bin|' Makeconfig &&
sed -i 's|^sbindir=.*|sbindir=/usr/bin|' {,posix/glob/}configure &&
sed -i 's|libc_cv_rootsbindir=.*|libc_cv_rootsbindir=/usr/bin|' sysdeps/unix/sysv/linux/configure &&
sed -i 's|/dev/log|/dev/shm/log|' bits/syslog-path.h &&
find . -name configure | xargs touch &&
mkdir ../glibc-build && cd ../glibc-build &&
../glibc-2.6.1/configure --prefix=/usr --sbindir=/usr/bin --enable-add-ons=nptl --enable-shared --enable-kernel=2.6.22 --disable-oldest-abi --enable-omitfp --disable-profile --with-headers=/usr/include --with-binutils=/www/bin --without-cvs --with-elf --without-gd --without-gmp --without-selinux --with-tls &&
echo 'MAKEINFO = :' >> configparms &&
make && ( make -k check 2> $SRC/build_glibc.log ; make install ) &&
make install install_root=$R &&
localedef -i zh_CN -f UTF-8 zh_CN.UTF-8 && cp /usr/lib/locale/* $R/usr/lib/locale/ &&
rm {,$R}/etc/rpc {,$R}/{,usr}/lib/*_g.* {,$R}/usr/libexec/pt_chown {,$R}/usr/share/locale &&
echo 'passwd: files
group: files
shadow: files
hosts: files
networks: files
protocols: files
services: files
ethers: files
rpc: files' | tee {,$R}/etc/nsswitch.conf &&
cp --remove-destination /usr/share/zoneinfo/UTC   /etc/localtime &&
cp --remove-destination /usr/share/zoneinfo/UTC $R/etc/localtime &&
cp /etc/{passwd,group,hosts}  $R/etc/ &&
cd $SRC && rm */ &&
echo '2-glibc' >> $SRC/build.log && sync &&   ##再次调整工具链
mv /www/bin/{ld-new,ld} &&
gcc -dumpspecs | sed -e'/^\*link:$/{n;s@$@ -L/usr/lib@}' -e's@/www/lib/ld-linux.so.2@/lib/ld-linux.so.2@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 | fgrep '[Requesting program interpreter: /lib/ld-linux.so.2]' &&
fgrep 'attempt to open /usr/lib/crt1.o succeeded' dummy.log &&
fgrep 'attempt to open /usr/lib/crti.o succeeded' dummy.log &&
fgrep 'attempt to open /usr/lib/crtn.o succeeded' dummy.log &&
fgrep '#include <...> search starts here:
/usr/include
/www/include' dummy.log &&
# fgrep 'SEARCH_DIR("/www/i686-pc-linux-gnu/lib"); SEARCH_DIR("/lib"); SEARCH_DIR("/usr/lib");' dummy.log &&
fgrep 'attempt to open /lib/libc.so.6 succeeded' dummy.log &&
fgrep 'found ld-linux.so.2 at /lib/ld-linux.so.2' dummy.log &&
rm dummy.c a.out dummy.log &&
echo '3-adjusting' >> $SRC/build.log && sync &&Tcl + Expect + DejaGNU

[提示]使用 –with(out)-tk 将导致 expect 配置失败,使用了 –with-tcl 之后就不需要再详细指定 –with-tclconfig –with-tcllib –with-tcllibdir 了。使用 –with(out)-docbook 或 –with(out)-oskith 将导致 dejagnu 配置失败。sed 一定要先修改 configure.in 再修改 configure ,否则会导致 Autoconf 的调用。dejagnu 的安装指南说测试套件需要以非 root 身份运行,可是经过实践,无论 root 与否,都不能在第一次安装后立即通过测试,一般需要安装两次甚至三次才能测试成功(无论是否root都是这样),不知何故。再加上dejagnu的测试程序依赖于这里并不存在的C++编译器,因此这里跳过dejagnu测试。

R=/root/tcl8.4.18/ &&
tar -xf tcl8.4.18-src.tar.gz && cd tcl8.4.18/unix &&
sed -i 's:/bin/rm:rm:g' ../library/ldAout.tcl &&
./configure --prefix=/usr --sbindir=/usr/bin --enable-threads --enable-shared --enable-load --enable-gcc --disable-symbols --disable-64bit --disable-64bit-vis --disable-langinfo --disable-corefoundation --disable-dtrace --disable-framework --disable-man-symlinks --disable-man-compression --disable-man-suffix &&
make && TZ=UTC make test &&
make install install-private-headers  &&
ln -sf tclsh8.4   /usr/bin/tclsh &&
make install install-private-headers INSTALL_ROOT=$R &&
ln -sf tclsh8.4 $R/usr/bin/tclsh &&
cd $SRC &&
rm */ && sync &&
tar -xf expect-5.43.0.tar.bz2 && cd expect-5.43 &&
patch $SRC/expect-5.43.0-spawn-2.patch &&
sed -i 's/STTY_BIN=.*/STTY_BIN=stty/g' configure{.in,} &&
./configure --prefix=/usr --sbindir=/usr/bin --enable-threads --enable-shared --enable-load --enable-gcc --with-tcl=/usr/lib --with-tclinclude=/usr/include --with-x=no --disable-symbols &&
make expect && make test &&
make install SCRIPTS="" &&
make install SCRIPTS="" INSTALL_ROOT=/root/expect-5.43.0/ &&
cd $SRC && rm */ && sync &&
tar -xf dejagnu-1.4.4.tar.gz &&
cd dejagnu-1.4.4 &&
./configure --prefix=/usr --sbindir=/usr/bin &&
make install &&
make install DESTDIR=/root/dejagnu-1.4.4/ &&
cd $SRC && rm */ &&
echo '4-tcl-expect-dejagnu' >> $SRC/build.log &&
sync &&Binutils

由于”-finline-functions”会导致ld测试出现多处错误,因此这里需要专门禁用它。对Makefile.in的修改用于移除对makeinfo的依赖,否则编译将会失败(因为工具链中并未安装Texinfo)。

[提示]由于 binutils-2.17 的测试套件将路径 /bin/stty 进行了硬编码,且本文作者尚未找到简便的迂回方法,因此如果你使用的是 2.17 ,那么要先建立一个符号链接来满足测试套件的需求,安装完毕后再删除它。对于如何安装 Binutils 和 GCC 可以参考一下《Binutils与GCC配置选项简介》。

R=/root/binutils-2.18/ &&
tar -xf binutils-2.18.tar.bz2 &&
mkdir binutils-build &&
cd binutils-build &&
echo 'MAKEINFO = :' >> ../binutils-2.18/Makefile.in &&
CFLAGS="$CFLAGS -fno-inline-functions" \
../binutils-2.18/configure --prefix=/usr --sbindir=/usr/bin --with-lib-path=/lib:/usr/lib --disable-nls --disable-rpath --disable-multilib --enable-shared --disable-static --disable-werror --without-gmp --without-mpfr --without-included-gettext --without-libiconv-prefix --without-libintl-prefix --with-pic &&
make all check install tooldir=/usr/  &&
cp ../binutils-2.18/include/libiberty.h   /usr/include/ &&
make install tooldir=/usr/ DESTDIR=$R &&
cp ../binutils-2.18/include/libiberty.h $R/usr/include/ &&
cd $SRC &&
rm */ &&
echo '5-binutils' >> $SRC/build.log &&
sync &&
GCC

因为GCC的Makefile.in并不传递LDFLAGS,所以需要sed一下。为了得到更加高效的编译器,这里使用”make profiledbootstrap”代替”make”。对”LINK_SPEC”的修改是为了将”–hash-style=gnu”选项添加到默认的连接器选项中去,如果你希望这样的话,就去掉相应的注释。[提示]如果Glibc的CFLAGS中使用了-freg-struct-return的话,gcc.dg/struct-ret-libc.c测试将会失败,不过这是二进制兼容性所致,可以安全的忽略它。

R=/root/gcc-4.2.3/ &&
tar -xf gcc-core-4.2.3.tar.bz2 &&
tar -xf gcc-testsuite-4.2.3.tar.bz2 &&
cd gcc-4.2.3 &&
sed -r -i 's|^LDFLAGS(_FOR_TARGET)? =|& @LDFLAGS@|' Makefile.in &&
sed -i -e's@\./fixinc\.sh@-c true@' -e'/^LIBGCC2_DEBUG_CFLAGS/d' gcc/Makefile.in &&
sed -i '/MULTILIB_OSDIRNAMES/d' gcc/config/i386/t-linux64 &&
sed -i 's/install_to_$(INSTALL_DEST) //' libiberty/Makefile.in &&
# sed -i '/LINK_SPEC/s/ "/&--hash-style=gnu /' gcc/config/i386/linux{,64}.h &&
mkdir ../gcc-build &&
cd ../gcc-build &&
../gcc-4.2.3/configure --prefix=/usr --sbindir=/usr/bin --with-local-prefix=/usr/local --enable-languages=c --enable-bootstrap --disable-nls --disable-rpath --disable-multilib --enable-shared=libgcc --disable-static --disable-libgomp --disable-libmudflap --disable-libssp --enable-linux-futex --enable-threads=posix --enable-tls --disable-symvers --with-as=/usr/bin/as --with-ld=/usr/bin/ld --without-included-gettext --without-libiconv-prefix --without-libintl-prefix --without-gmp --without-mpfr --without-system-libunwind --without-system-zlib --with-pic --without-x &&
make profiledbootstrap LIBCFLAGS="$CFLAGS" BOOT_CFLAGS="$CFLAGS" BOOT_LDFLAGS="$LDFLAGS" &&
( make -k check | tee $SRC/build_gcc.log ; make install ) &&
make install DESTDIR=$R &&
ln -sf gcc   /usr/bin/cc &&
ln -sf gcc $R/usr/bin/cc &&
INC=`gcc -print-file-name=include` &&
TOL=`gcc -print-file-name=install-tools` &&
rm  {,$R}/$INC/* &&
cp  $TOL/include/*     $INC &&
cp  $TOL/include/*  $R/$INC &&
cp  $TOL/gsyslimits.h     $INC/syslimits.h &&
cp  $TOL/gsyslimits.h  $R/$INC/syslimits.h &&
unset INC TOL &&
cd $SRC &&
rm */ &&
sync &&
echo 'main(){}' > dummy.c &&
cc dummy.c -v -Wl,--verbose &> dummy.log &&
readelf -l a.out | fgrep '[Requesting program interpreter: /lib/ld-linux.so.2]' &&
fgrep 'attempt to open /usr/lib/gcc/i686-pc-linux-gnu/4.2.3/../../../crt1.o succeeded' dummy.log &&
fgrep 'attempt to open /usr/lib/gcc/i686-pc-linux-gnu/4.2.3/../../../crti.o succeeded' dummy.log &&
fgrep 'attempt to open /usr/lib/gcc/i686-pc-linux-gnu/4.2.3/../../../crtn.o succeeded' dummy.log &&
fgrep '#include <...> search starts here:
/usr/lib/gcc/i686-pc-linux-gnu/4.2.3/include
/usr/include
End of search list.' dummy.log &&
fgrep 'SEARCH_DIR("/usr/i686-pc-linux-gnu/lib"); SEARCH_DIR("/lib"); SEARCH_DIR("/usr/lib");' dummy.log &&
fgrep 'attempt to open /lib/libc.so.6 succeeded' dummy.log &&
fgrep 'found ld-linux.so.2 at /lib/ld-linux.so.2' dummy.log &&
rm dummy.c a.out dummy.log &&
echo '6-gcc' >> $SRC/build.log &&
sync &&

到此,最终系统的工具链核心安装完毕。


相关内容

    暂无相关文章