Build an embedded Linux distro from scratch 从无到有打造Linux发布包 之2 交叉编译

英文原文出现在

http://www.ibm.com/developerworks/linux/tutorials/l-embedded-distro/section3.html



Cross-compilation


What is cross-compiling?

Cross-compiling is using a compiler on one system to develop code to run on another. Cross-compilation is relatively rare among casual UNIX users, as the default is to have a compiler installed on the system for use on that system. However, cross-compilation becomes quite common (and relevant) when targeting embedded systems. Even when host and target are the same architecture, it is necessary to distinguish between their compilers; they may have different versions of libraries, or libraries built with different compiler options, so that something compiled with the host compiler could fail to run, or could behave unexpectedly, on the target.

什么是交叉编译?

交叉编译就是在一个系统上,使用编译器开发可以在另一个系统上运行的代码。在比较随意的UNIX用户中,交叉编译相对而言是比较少见的,因为默认的情况是安装的编译器都是用在它所在的系统上的。然而,当面对嵌入式系统的时候,交叉编译就变得很常见。即使是在主机和目标机是相同架构的时候,对它们的编译器进行区分也是必要的;它们可能有不同版本的库文件,或者由不同的编译器选项构建得来的库文件,因此,使用主机编译器编译的东西可能不能在目标机上运行,或者其行为在目标机上是不可预期的。


Obtaining cross-compilation tools

It is, in theory, quite possible to build a cross-compiler yourself, but it is rarely practical. The series of bootstrap stages needed can be difficult and time-consuming, and it is often necessary to build a very minimal compiler, which is used to partially configure and build libraries, the headers of which are then used to rebuild the compiler so it can use them, and so on. A number of commercial sources for working cross-compilers for various architecture combinations are available, as well as several free cross-compilation toolkits.

获取交叉编译工具

理论上,自己构建一个交叉编译器是可能的,但是却不是很实际。需要的启动阶段的序列是比较困难的部分,并且比较消耗时间,构建一个小型的编译器也是很必要的,可以用其部分地配置和构建库文件,而在那之后库文件的头文件用来重新构建编译器,因此,编译器可以使用那些库文件,如此往复。各种架构和各种编译器组合的商业的源有很多可用的,也有一些免费的交叉编译工具箱。


Introducing crosstool-ng

Dan Kegel's crosstool (see Resources for details) collects a variety of expertise and a few specialized patches to automatically build toolchains for a number of systems. Crosstool has not been updated in a while, but the new crosstool-ng project builds on this work. For this tutorial, I used crosstool-ng version 1.1.0, released in May of 2008. Download it from the distribution site (seeResources).

介绍crosstool-ng

Dan Kegel的crosstool可以收集很多专家的意见以及特定的补丁以自动地为很多的系统构建工具链。Crosstool已经有一段时间没有更新了,但是新的crosstool-ng项目在从事这个工作。对于本教程而言,为使用crosstool-ng 1.1.0版本,2008年5月份发布。


Installing crosstool-ng

Crosstool-ng has a configure script. To configure it, just run the script using--prefix to set a location. For instance:

安装crosstool-ng

Crosstool-ng 有一个configure脚本。为了配置croostool-ng,运行该脚本,使用--prefix选项以设置存放的位置。例如:

$ ./configure --prefix=$HOME/7800/ctng

Once you have configured it, build it using make and then make install. The build process creates actng directory in the 7800 working directory that holds the crosstool-ng build scripts. Add thectng/bin subdirectory to your path:

一旦配置完毕,使用make构建crosstool-ng,之后运行make install构建过程在7800工作目录中创建了一个ctng目录,用于保存croostool-ng的构建脚本。将ctng/bin子目录加入到PATH环境变量中

$ PATH=$PATH:$HOME/7800/ctng/bin

话外音,在configure过程中,翻译者另外还使用sudo apt-get install 命令安装了mawk,gawk,bison,flex, texinfo for makeinfo, automake, libtool, curl, patch, libncurses5-dev。


Configuring crosstool-ng

Crosstool-ng uses a .config file similar to those used by the Linux kernel. You need to create a configuration file matching your target to use crosstool-ng. Make a working directory for a crosstool-ng build:

配置crosstool-ng

Crosstool-ng 使用的是与Linux kernel使用的 .config 文件相似的 .config 文件。为了使用crosstool-ng,你需要创建一个与你的目标对象匹配的配置文件。为crosstool-ng构建创建一个工作目录:

$ mkdir toolchain-build
$ cd toolchain-build

Now, copy in a default configuration. It's possible to manually configure crosstool-ng, but one of the sample configurations happens to fit the target perfectly:

现在拷贝默认的配置。也可能是手动配置crosstool-ng,但是,例子配置中的某一个或许会较好的匹配你的目标对象:

$ cp ../ctng/lib/ct-ng-1.1.0/samples/arm-unknown-linux-uclibc/* .

Finally, rename the crosstool.config file:

最后,改crosstool-ng.config文件名为.config

$ mv crosstool.config .config


This copies in a configuration file that targets an armv5te processor, the model used on the TS-7800. It builds with uClibc, a libc variant intended for embedded systems. However, the configuration file does need one modification.

这拷贝了一个面向armv5te处理器的配置文件,也就是TS-7800使用的模型。它与uClibc一起构建,uClibc是libc的一个变种,应用于嵌入式系统。然而,配置文件还需要做一处改动。

话外音,翻译者使用的crosstool-ng是1.13.3版本的,所以对应的是 arm-unknown-linux-uclibcgnueabi/ 。并且,利用mv修改名字之后,.config 文件使用 ls -l 查看不到的。


Fixing the configuration path

The default target directory for a crosstool-ng build is$HOME/x-tools/$TARGET. For instance, on this build, it would come out asx-tools/arm-unknown-linux-uclibc. This is very useful if you are building for a lot of targets, but not so useful if you are building for only one. Edit the.config file and changeCT_PREFIX_DIR to${HOME}/7800/toolchain.

调整配置路径

对于crosstool-ng构建而言,默认的目标路径是 $HOME/x-tools/$TARGET。例如,在当前这个构建中,路径会是

x-tools/arm-unknown-linux-uclibc 。如果你在构建很多的对象,这会显得很有用,但是,如果仅仅构建一个对象的话,就不是那么有用了。编辑 .config 文件,改变 CT_PREFIX_DIR为 ${HOME}/7800/toolchain 。


Building the toolchain

To build the toolchain, run the ct-ng script with thebuild argument. To improve performance, especially on a multi-core system, you may want to run with multiple jobs, specified asbuild.#. For example, this command builds with four jobs:

$ ct-ng build.4

This may take quite a while, depending on your host system. When it's done, the toolchain is installed in$HOME/7800/toolchain. The directory and its contents are marked read-only; if you need to delete or move them, usechmod u+w The ct-ng script takes other arguments, such ashelp. Note thatct-ng is a script for the standardmake utility, and as a result, the output from--help is just the standardmake help; usect-ng help to get the help for crosstool-ng.

If you haven't seen this trick before, it's a neat one. Modern UNIX systems interpret an executable file in which the first line starts with#! as a script, specifically, a script for the program named on the rest of the line. For instance, many shell scripts start with#!/bin/sh. The name of the file is passed to the program. For programs that treat their first argument as a script to run, this is sufficient. Whilemake does not do that automatically, you can give it a file to run with using the-f flag. The first line ofct-ng is#!/usr/bin/make -rf. The-r flag suppresses the built-in default construction rules ofmake, and the-f flag tells it that the following word (which is the script's file name) is the name of a file to use instead of one namedMakefile. The result is an executable script that usesmake syntax instead of shell syntax.

构建工具链

为了构建工具链,以build为参数运行ct-ng脚本。为了提高性能,特别是在多核的系统上,你可能想要运行多个任务,以build.#来指定。例如,下面的命令以4个任务来构建:

$ ct-ng build.4

这可能要花一些时间,依赖于你的主机系统。当该命令结束后,工具链安装在了 $HOME/7800/toolchain目录下 。这个目录和其中的内容是只读的;如果你需要删除或者移动它们,使用 chmod u+w。ct-ng脚本也有其他的参数,例如help。注意到,ct-ng是标准的make工具的脚本,结果就是,--help的输出就是标准的make的help;使用ct-ng help可以得到crosstool-ng的help。

如果你以前没有看到过这个小技巧,它其实是较简洁的一个。若可执行文件的第一行以 #! 开头,现代的UNIX系统会将其翻译为一个脚本,特别地,是以该行的其他内容所命名的程序的一个脚本。例如,许多shell脚本以#!/bin/sh开头。文件的名字会传递给这个程序。对于那些将其第一个参数视作要运行的脚本的程序而言,这就足够了。而make不会自动地做这件事,可以使用 -f 标志告诉它运行那个文件。ct-ng的第一行是 #! /usr/bin/make -rf 。-r标志废止了make内嵌的默认的构建规则,而 -f 标志告诉make接下来的字(脚本的文件名)是它要使用的文件,而不是使用名为Makefile的文件。这样做的结果就是,使用make语法的可执行脚本代替了shell语法。


Using the toolchain

For starters, add the directory containing the compiler to your path:

$ PATH=~/7800/toolchain/bin:$PATH


With that in your path, you can now compile programs:

$ arm-unknown-linux-uclibc-gcc -o hello hello.c $file hello
hello: ELF 32-bit LSB executable, ARM, version 1 (SYSV), for
GNU/Linux 2.4.17, dynamically linked (uses shared libs), not stripped


使用工具链

对于初学者而言,将包含编译器的目录添加到你的路径中:

$ PATH=~/7800/toolchain/bin:$PATH


将该目录加入到路径中,现在,你就可以编译程序了:

$ arm-unknown-linux-uclibc-gcc -o hello hello.c

$ file hello

hello: ELF 32-bit LSB executable, ARM, version 1 (SYSV), for
GNU/Linux 2.4.17, dynamically linked (uses shared libs), not stripped


Where are the libraries?

The libraries used by the toolchain to link binaries are stored inarm-unknown-linux-uclibc/sys-root, under thetoolchain directory. This directory forms the basis of an eventual root file system, a topic we'll cover underFilesystems, once the kernel is built.

库文件在哪?

工具链链接二进制文件所使用的库文件存储在arm-unknown-linux-uclibc/sys-root中,该目录在toolchain目录中。该路径是root file system的基础,一旦kernel构建完毕,我们会在Filesystems下对其进行讨论。


Kernel setup

The kernel distribution tree provided by the vendor is already configured for cross compilation. In the simplest case (which this is), the only thing you have to do to cross compile a Linux kernel is to set theCROSS_COMPILE variable in the top-level Makefile. This is a prefix that is prepended to the names of the various programs (gcc, as, ld) used during the build. For instance, if you set CROSS_COMPILE toarm-, the compile will try to find a program named arm-gcc in your path. For this build, then, the correct value isarm-unknown-linux-uclibc. Or, if you don't want to rely on path settings, you can specify the whole path, as in this example:

CROSS_COMPILE ?= $(HOME)/7800/toolchain/bin/arm-unknown-linux-uclibc-

建立内核

供应商提供的kernel发布包已经为交叉编译进行了配置。最简单的情况是,为交叉编译Linux kernel你需要做的唯一一件事情是,在顶层的Makefile中,设置CROSS_COMPILE变量。它是一个前缀,会添加到构建期间所使用的各种程序(gcc, as, ld)的名字的前面。例如,如果你设置CROSS_COMPILE为 arm-,编译会尝试在你的路径中查找名为 arm-gcc的程序。对于当前的构建而言,正确的值是 arm-unknown-linux-uclibc 。或者,如果你不打算依赖路径的设置,你可以像下面的例子那样,定义整个完整的路径:

CROSS_COMPILE ?= $(HOME)/7800/toolchain/bin/arm-unknown-linux-uclibc-


话外音:

在译者使用ct-ng build.4命令后,出现下面的信息:

[INFO ]  Performing some trivial sanity checks
[INFO ]  Build started 20120202.201249
[INFO ]  Building environment variables
[EXTRA]  Preparing working directories
[EXTRA]  Installing user-supplied crosstool-NG configuration
[EXTRA]  =================================================================
[EXTRA]  Dumping internal crosstool-NG configuration
[EXTRA]    Building a toolchain for:
[EXTRA]      build  = i686-pc-linux-gnu
[EXTRA]      host   = i686-pc-linux-gnu
[EXTRA]      target = arm-unknown-linux-uclibcgnueabi
[EXTRA]  Dumping internal crosstool-NG configuration: done in 0.17s (at 00:02)
[INFO ]  =================================================================
[INFO ]  Retrieving needed toolchain components' tarballs
[EXTRA]    Retrieving 'linux-2.6.33.19'
[EXTRA]    Saving 'linux-2.6.33.19.tar.xz' to local storage
[EXTRA]    Retrieving 'gmp-4.3.2'
[EXTRA]    Saving 'gmp-4.3.2.tar.bz2' to local storage
[EXTRA]    Retrieving 'mpfr-2.4.2'
[EXTRA]    Saving 'mpfr-2.4.2.tar.xz' to local storage
[EXTRA]    Retrieving 'ppl-0.10.2'
[EXTRA]    Saving 'ppl-0.10.2.tar.bz2' to local storage
[EXTRA]    Retrieving 'cloog-ppl-0.15.9'
[EXTRA]    Saving 'cloog-ppl-0.15.9.tar.gz' to local storage
[EXTRA]    Retrieving 'libelf-0.8.13'
[EXTRA]    Saving 'libelf-0.8.13.tar.gz' to local storage

其实,需要下载的packages是:

shawn@shawn-ThinkPad-T410:~/src$ ls -al
total 168192
drwxrwxr-x  2 shawn shawn     4096 2012-02-03 20:05 .
drwxr-xr-x 32 shawn shawn     4096 2012-02-03 21:36 ..
-rw-rw-r--  1 shawn shawn 16306586 2012-02-02 22:31 binutils-2.19.1a.tar.bz2
-rw-rw-r--  1 shawn shawn   767694 2012-02-02 20:47 cloog-ppl-0.15.9.tar.gz
-rw-rw-r--  1 shawn shawn   666608 2012-02-03 18:36 dmalloc-5.5.2.tgz
-rw-rw-r--  1 shawn shawn   240479 2012-02-03 18:47 duma_2_5_15.tar.gz
-rw-rw-r--  1 shawn shawn   446456 2012-02-03 19:21 expat-2.0.1.tar.gz
-rw-r--r--  1 shawn shawn 62944934 2012-02-03 16:28 gcc-4.4.3.tar.bz2
-rw-rw-r--  1 shawn shawn 18386633 2012-02-03 18:55 gdb-7.1a.tar.bz2
-rw-rw-r--  1 shawn shawn  1897483 2012-02-02 20:39 gmp-4.3.2.tar.bz2
-rw-rw-r--  1 shawn shawn   148529 2012-02-02 20:47 libelf-0.8.13.tar.gz
-rw-rw-r--  1 shawn shawn 54336376 2012-02-02 20:38 linux-2.6.33.19.tar.xz
-rw-rw-r--  1 shawn shawn   147198 2012-02-03 19:26 ltrace_0.5.3.orig.tar.gz
-rw-rw-r--  1 shawn shawn   951620 2012-02-02 20:40 mpfr-2.4.2.tar.xz
-rw-rw-r--  1 shawn shawn  2826473 2012-02-03 18:56 ncurses-5.9.tar.gz
-rw-rw-r--  1 shawn shawn  9820135 2012-02-02 20:44 ppl-0.10.2.tar.bz2
-rw-rw-r--  1 shawn shawn   499565 2012-02-03 20:03 strace-4.5.19.tar.bz2
-rw-rw-r--  1 shawn shawn  1804960 2012-02-03 18:36 uClibc-0.9.30.2.tar.xz
shawn@shawn-ThinkPad-T410:~/src$


另外,还需要安装 libexpat1-dev

sudo apt-get install libexpat1-dev.

这样,[INFO ]  Installing cross-gdb  这一步才能通过


ct-ng运行信息:

shawn@shawn-ThinkPad-T410:~/linux-from-scratch/crosstool-ng-build$ ct-ng build.4

[INFO ]  Performing some trivial sanity checks
[INFO ]  Build started 20120203.213704
[INFO ]  Building environment variables
[EXTRA]  Preparing working directories
[EXTRA]  Installing user-supplied crosstool-NG configuration
[EXTRA]  =================================================================
[EXTRA]  Dumping internal crosstool-NG configuration
[EXTRA]    Building a toolchain for:
[EXTRA]      build  = i686-pc-linux-gnu
[EXTRA]      host   = i686-pc-linux-gnu
[EXTRA]      target = arm-unknown-linux-uclibcgnueabi
[EXTRA]  Dumping internal crosstool-NG configuration: done in 0.18s (at 00:03)
[INFO ]  =================================================================
[INFO ]  Retrieving needed toolchain components' tarballs
[INFO ]  Retrieving needed toolchain components' tarballs: done in 0.15s (at 00:03)
[INFO ]  =================================================================
[INFO ]  Extracting and patching toolchain components
[INFO ]  Extracting and patching toolchain components: done in 0.17s (at 00:03)
[INFO ]  =================================================================
[INFO ]  Checking C library configuration
[EXTRA]    Munging uClibc configuration
[INFO ]  Checking C library configuration: done in 0.08s (at 00:03)
[INFO ]  =================================================================
[INFO ]  Installing GMP
[EXTRA]    Configuring GMP
[EXTRA]    Building GMP
[EXTRA]    Installing GMP
[INFO ]  Installing GMP: done in 89.98s (at 01:33)
[INFO ]  =================================================================
[INFO ]  Installing MPFR
[EXTRA]    Configuring MPFR
[EXTRA]    Building MPFR
[EXTRA]    Installing MPFR
[INFO ]  Installing MPFR: done in 25.25s (at 01:59)
[INFO ]  =================================================================
[INFO ]  Installing PPL
[EXTRA]    Configuring PPL
[EXTRA]    Building PPL
[EXTRA]    Installing PPL
[INFO ]  Installing PPL: done in 260.42s (at 06:19)
[INFO ]  =================================================================
[INFO ]  Installing CLooG/ppl
[EXTRA]    Configuring CLooG/ppl
[EXTRA]    Building CLooG/ppl
[EXTRA]    Installing CLooG/ppl
[INFO ]  Installing CLooG/ppl: done in 8.57s (at 06:28)
[INFO ]  =================================================================
[INFO ]  Installing binutils
[EXTRA]    Configuring binutils
[EXTRA]    Building binutils
[EXTRA]    Installing binutils
[INFO ]  Installing binutils: done in 64.41s (at 07:32)
[INFO ]  =================================================================
[INFO ]  Installing kernel headers
[EXTRA]    Installing kernel headers
[EXTRA]    Checking installed headers
[INFO ]  Installing kernel headers: done in 7.20s (at 07:39)
[INFO ]  =================================================================
[INFO ]  Installing C library headers
[EXTRA]    Copying sources to build dir
[EXTRA]    Applying configuration
[EXTRA]    Building headers
[EXTRA]    Installing headers
[INFO ]  Installing C library headers: done in 8.82s (at 07:48)
[INFO ]  =================================================================
[INFO ]  Installing static core C compiler
[EXTRA]    Configuring static core C compiler
[EXTRA]    Building static core C compiler
[EXTRA]    Installing static core C compiler
[INFO ]  Installing static core C compiler: done in 199.19s (at 11:07)
[INFO ]  =================================================================
[INFO ]  Installing C library
[EXTRA]    Copying sources to build dir
[EXTRA]    Applying configuration
[EXTRA]    Building C library
[EXTRA]    Installing C library
[INFO ]  Installing C library: done in 67.64s (at 12:15)
[INFO ]  =================================================================
[INFO ]  Installing final compiler
[EXTRA]    Configuring final compiler
[EXTRA]    Building final compiler
[EXTRA]    Installing final compiler
[INFO ]  Installing final compiler: done in 328.90s (at 17:44)
[INFO ]  =================================================================
[INFO ]  Installing libelf for the target
[EXTRA]    Configuring libelf
[EXTRA]    Building libelf
[EXTRA]    Installing libelf
[INFO ]  Installing libelf for the target: done in 9.58s (at 17:53)
[INFO ]  =================================================================
[INFO ]  Installing binutils for target
[EXTRA]    Configuring binutils for target
[EXTRA]    Building binutils' libraries (libiberty bfd) for target
[EXTRA]    Installing binutils' libraries (libiberty bfd) for target
[INFO ]  Installing binutils for target: done in 106.62s (at 19:40)
[INFO ]  =================================================================
[INFO ]  Installing dmalloc
[EXTRA]    Configuring dmalloc
[EXTRA]    Building dmalloc
[EXTRA]    Installing dmalloc
[INFO ]  Installing dmalloc: done in 13.40s (at 19:54)
[INFO ]  =================================================================
[INFO ]  Installing D.U.M.A.
[EXTRA]    Copying sources
[EXTRA]    Building libraries 'libduma.a libduma.so.0.0.0'
[EXTRA]    Installing libraries 'libduma.a libduma.so.0.0.0'
[EXTRA]    Installing shared library link
[EXTRA]    Installing wrapper script
[INFO ]  Installing D.U.M.A.: done in 2.28s (at 19:56)
[INFO ]  =================================================================
[INFO ]  Installing cross-gdb
[EXTRA]    Configuring cross-gdb
[EXTRA]    Building cross-gdb
[EXTRA]    Installing cross-gdb
[EXTRA]    Install '.gdbinit' template
[INFO ]  Installing cross-gdb: done in 196.42s (at 23:12)
[INFO ]  =================================================================
[INFO ]  Installing native gdb
[EXTRA]    Building static target ncurses
[EXTRA]    Building static target expat
[EXTRA]    Configuring native gdb
[EXTRA]    Building native gdb
[EXTRA]    Installing native gdb
[EXTRA]    Cleaning up ncurses
[INFO ]  Installing native gdb: done in 321.68s (at 28:34)
[INFO ]  =================================================================
[INFO ]  Installing gdbserver
[EXTRA]    Configuring gdbserver
[EXTRA]    Building gdbserver
[EXTRA]    Installing gdbserver
[INFO ]  Installing gdbserver: done in 12.79s (at 28:47)
[INFO ]  =================================================================
[INFO ]  Installing ltrace
[EXTRA]    Copying sources to build dir
[EXTRA]    Configuring ltrace
[EXTRA]    Building ltrace
[EXTRA]    Installing ltrace
[INFO ]  Installing ltrace: done in 8.41s (at 28:55)
[INFO ]  =================================================================
[INFO ]  Installing strace
[EXTRA]    Configuring strace
[EXTRA]    Building strace
[EXTRA]    Installing strace
[INFO ]  Installing strace: done in 29.53s (at 29:25)
[INFO ]  =================================================================
[INFO ]  Cleaning-up the toolchain's directory
[INFO ]    Stripping all toolchain executables
[EXTRA]    Installing the populate helper
[EXTRA]    Installing a cross-ldd helper
[EXTRA]    Creating toolchain aliases
[EXTRA]    Removing access to the build system tools
[EXTRA]    Removing installed documentation
[INFO ]  Cleaning-up the toolchain's directory: done in 1.65s (at 29:26)
[INFO ]  Build completed at 20120203.220630
[INFO ]  (elapsed: 29:26.65)
[INFO ]  Finishing installation (may take a few seconds)...
[29:26] / shawn@shawn-ThinkPad-T410:~/linux-from-scratch/crosstool-ng-build$


  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值