分类: LINUX
2010-12-17 12:34:58
说明:
1、主要依照参考文献[1]、[2],如果有需要可以直接参看参考文献;
报错问题的解决方案,大多源于网络,
如(UBUNTU 中文论坛);
2、字体颜色说明:
红色——报错提示,
黄色——需要注意的地方,
蓝色——需要修改的字体。
3、所用的编译环境为ubuntu10.10.
4、所用开发板为FL2440.
5、文章末尾提供完整的PDF格式文本供大家下载。
在嵌入式系统中,我们经常会听到一个词——交叉编译。那么什么是交叉编译?为什么要交叉编译? 我的理解,所谓交叉编译,就是解决一种平台上开发的程序,在其他平台上执行的问题。举个例子来说,当我们需要开发一个能在ARM系统上运行的程序,如果直接在ARM系统中开发,由于ARM平台的限制,很难实现。所以一般会在我们所熟悉的PC机上来开发,但是问题是,PC机上编译的程序格式,无法运行在ARM平台上,所以我们需要借助一个工具,能够将PC上的程序编译为ARM上能执行的格式。这个工具就是交叉编译工具链。
当我们知道了什么是交叉编译以后,接下来的问题就是,如何来构建一个交叉编译工具链。在linux系统下,最常用的构建工具链的方法有三种:一种为分步构建交叉编译链,这种方法比较复杂,难度也大,即使从业多年的人员,也不能保证一次构建成功,所以需要足够的耐心和毅力,如果为了深入学习的目的,可以使用这种方法进行构建;第二种方法通过crosstool脚本工具来实现构建编译链,这种方法操作简单,出错率也比较低,所以建议大多数情况下使用这种方法进行构建;第三种方法更为简单,就是从网上下载别人编译好的工具链来使用,这种方法最明显的缺陷就是不够灵活,别人编译的工具链无法完全适应于自己所使用的环境,而且也会出现一些莫名其妙的错误,所以这种方法一般不推荐使用。下面就详细介绍第二种方法——使用crosstool脚本工具建立交叉编译工具链。
第一步 确定软件版本号并下载所需的资源文件
交叉编译所用的工具主要有binutils、gcc 和 glibc 等。那么如何确定所需的软件版本号呢?首先要确定glibc的版本号,解压缩后,查看里面的INSTALL文件,这个文件里面就有glibc编译时所需要的binutils、gcc的最低版本要求。以glibc-2.3.2.tar.bz2为例。
操作步骤如下:
首先将glibc-2.3.2.tar.bz2放在一个目录下,以放在用户目录下为例,然后在终端输入以下命令:
$ cd ~ //切换到用户目录下
$ tar xjvf glibc-2.3.2.tar.bz2 //解压缩
解压缩完成后,会在当前目录下生成一个glibc-2.3.2文件夹,输入:
$ cd glibc-2.3.2
$ gedit INSTALL //打开INSTALL文件
INTALL文件中关于软件选型的建议如下:
Recommended Tools for Compilation
=================================
We recommend installing the following GNU tools before attempting to
build the GNU C library:
* GNU `make' 3.79 or newer
You need the latest version of GNU `make'. Modifying the GNU C
Library to work with other `make' programs would be so difficult
that we recommend you port GNU `make' instead. *Really.* We
recommend GNU `make' version 3.79. All earlier versions have
severe bugs or lack features.
* GCC 3.2 or newer
The GNU C library can only be compiled with the GNU C compiler
family. As of the 2.3 release, GCC 3.2 or higher is required. As
of this writing, GCC 3.2 is the compiler we advise to use.
You can use whatever compiler you like to compile programs that
use GNU libc, but be aware that both GCC 2.7 and 2.8 have bugs in
their floating-point support that may be triggered by the math
library.
Check the FAQ for any special compiler issues on particular
platforms.
* GNU `binutils' 2.13 or later
You must use GNU `binutils' (as and ld) to build the GNU C library.
No other assembler and linker has the necessary functionality in
the moment.
根据这个文件要求,gcc的版本号需要3.2以上,binutils版本需要2.13以上。本例选取的软件如下表所示,按照地址下载所需的安装包。
第二步 建立工作目录
首先,将crosstool-0.42.tar.gz压缩包放置在当前用户的目录下,然后解压缩,在终端输入命令:
$ cd ~ //跳转到用户目录下
$ ls //查看文件
$ tar zxvf crosstool-0.42.tar.gz //解压缩crosstool-0.42.tar.gz
$ ls //再查看用户目录会有一个crosstool- 0.42文件夹
$ mkdir downloads //创建一个文件夹用来存放下载的资源
然后将除去ctosstool-0.42.tar.gz以外的所有下载的压缩包都放在downloads下。
第三步建立脚本文件
需要建立的脚本文件为arm.sh,用demo-arm.sh作为模板进行修改即可。在终端输入以下命令:
$ cd crosstool-0.42 //进入到crosstool-0.42目录
$ cp demo-arm.sh arm.sh
//复制demo-arm.sh的内容到arm.sh中,并且创建arm.sh文件
$ gedit arm.sh //编辑arm.sh 中的内容
arm.sh的内容如下:
#!/bin/sh
set -ex
TARBALLS_DIR=$HOME/downloads //定义工具链源码所存放位置
RESULT_TOP=/opt/crosstool //定义工具链的安装目录
export TARBALLS_DIR RESULT_TOP
GCC_LANGUAGES="c,c++" //定义支持C,C++语言
export GCC_LANGUAGES
# Really, you should do the mkdir before running this,
# and chown /opt/crosstool to yourself so you don't need to run as root.
mkdir -p $RESULT_TOP
# Build the toolchain. Takes a couple hours and a couple gigabytes.
#eval `cat arm.dat gcc-2.95.3-glibc-2.1.3.dat` sh all.sh --notest
#eval `cat arm.dat gcc-2.95.3-glibc-2.2.2.dat` sh all.sh --notest
#eval `cat arm.dat gcc-3.2.3-glibc-2.2.5.dat` sh all.sh --notest
#eval `cat arm.dat gcc-3.3-glibc-2.2.5.dat` sh all.sh --notest
#eval `cat arm.dat gcc-3.3-glibc-2.3.2.dat` sh all.sh --notest
#eval `cat arm.dat gcc-3.3.1-glibc-2.3.2.dat` sh all.sh --notest
#eval `cat arm.dat gcc-3.3.2-glibc-2.3.2.dat` sh all.sh --notest
#eval `cat arm.dat gcc-3.3.3-glibc-2.3.2.dat` sh all.sh --notest
#eval `cat arm.dat gcc-3.3.4-glibc-2.3.2.dat` sh all.sh --notest
#eval `cat arm.dat gcc-3.3.4-glibc-2.3.3.dat` sh all.sh --notest --testlinux
#eval `cat arm.dat gcc-3.3.6-glibc-2.3.5.dat` sh all.sh --notest --testlinux
#eval `cat arm.dat gcc-3.4.0-glibc-2.3.2.dat` sh all.sh --notest
#eval `cat arm.dat gcc-3.4.1-glibc-2.3.2.dat` sh all.sh --notest
#eval `cat arm.dat gcc-3.4.1-glibc-2.3.3.dat` sh all.sh --notest
#eval `cat arm.dat gcc-3.4.2-glibc-2.2.5.dat` sh all.sh --notest --testlinux
#eval `cat arm.dat gcc-3.4.2-glibc-2.3.3.dat` sh all.sh --notest
#eval `cat arm.dat gcc-3.4.1-glibc-20040827.dat` sh all.sh --notest
eval `cat arm.dat gcc-4.1-20050709-glibc-2.3.2.dat` sh all.sh --notest
echo Done.
以上标注为蓝色的文字就是需要修改的部分,我们只修改两项,假定用户名为y,所以修改如下:
TARBALLS_DIR=/home/y/downloads
eval `cat arm.dat gcc-3.3.6-glibc-2.3.2.dat` sh all.sh –notest
其余不用修改,保存退出即可。
在命令行下输入:
$ sudo mkdir /opt/crosstool //建立文件夹
$ sudo chown y /opt/crosstool //给文件夹授权
第四步建立配置文件
修改arm.dat和gcc-3.3.6-glibc-2.3.2.dat这两个文件,命令如下
$ gedit arm.dat //编辑arm.dat文件
arm.dat的内容如下:
KERNELCONFIG=`pwd`/arm.config //内核的配置
TARGET=arm-unknown-linux-gnu //编译生成的工具链名称
TARGET_CFLAGS="-O" //编译选项
我们只需要更改蓝色部分的内容
TARGET=arm-linux
然后保存退出。
注意:在参考文献的两本书中,作者都将此处改为TARGET=arm-linux-,但是在编译的时候会报错:
unrecongnized target system type;please check config.sub.
更改为TARGET=arm-linux后可以正常编译。
继续修改gcc-3.3.6-glibc-2.3.2.dat文件,命令为
$ gedit gcc-3.3.6-glibc-2.3.2.dat //编辑gcc-3.3.6-glibc-2.3.2.dat
gcc-3.3.6-glibc-2.3.2.dat的内容如下:
BINUTILS_DIR=binutils-2.15
GCC_DIR=gcc-3.3.6
GLIBC_DIR=glibc-2.3.2
GLIBCTHREADS_FILENAME=glibc-linuxthreads-2.3.2
LINUX_DIR=linux-2.4.26
LINUX_SANITIZED_HEADER_DIR=linux-libc-headers-2.6.12.0
根据你所选用的软件进行修改,修改后的内容为:
LINUX_DIR=linux-2.6.10
保存并退出。
第五步执行脚本
在执行脚本之前,先安装所需要的包bison,flex,命令如下:
$ sudo apt-get install bison
$ sudo apt-get install flex
$ sudo apt-get install gcc-4.1 //解决报错<1>
$ sudo rm /usr/bin/gcc
$ sudo ln -s /usr/bin/gcc-4.1 /usr/bin/gcc
接下来请参看报错汇总中的<2>进行操作。在此过程中,保持联网,要不然更新会出错。
好了,到此我们的配置工作就完成了,接下来就要执行脚本,命令:
$ cd crosstool-0.42 //跳转到crosstool-0.42目录下
$ ./arm.sh //执行脚本
开始构建编译器,一般构建的过程都很漫长,都以小时为单位计,我们唯一能做的就是耐心的等待。
如果在编译过程中,存在什么问题,请参看错误汇总,当出现以下显示时,表示编译已经完成。
testhello: C compiler can in fact build a trivial program.
+ test = 1
+ test = 1
+ test = 1
+ test 1 =
+ echo Done.
Done.
我们可以检查/opt/crosstool/gcc-3.3.6-glibc-2.3.2/arm-linux/bin/下是否有文件:
# ls /opt/crosstool/gcc-3.3.6-glibc-2.3.2/arm-linux/bin
如果文件夹下有以下文件,则代表编译成功。
arm-linux-addr2line arm-linux-c++ arm-linux-g++
arm-linux-gccbug arm-linux-ld arm-linux-objdump arm-linux-size fix-embedded-paths arm-linux-ar arm-linux-c++filt arm-linux-gcc arm-linux-gcov arm-linux-nm arm-linux-ranlib arm-linux-strings
arm-linux-as arm-linux-cpp arm-linux-gcc-3.3.6 arm-linux-gprof arm-linux-objcopy arm-linux-readelf arm-linux-strip
第六步添加环境变量
在终端下输入:
$ sudo chown -R y /etc/bash.bashrc //授权
$ cd /etc
$ gedit bash.bashrc
在文件的末尾加上下面的语句
export PATH=/opt/crosstool/gcc-3.3.6-glibc-2.3.2/arm-linux/bin:$PATH
保存退出。
到此,交叉编译全部完成。如果要验证我们产生的编译工具是不是正确,可以用以下方法进行测试。
$ vi hello.c
在vi下输入以下程序
#include
int main()
{
printf(“Hello,world!\n”);
return 0;
}
保存退出。
在终端下输入:
$ su
# arm-linux-gcc -o hello hello.c //编译
# file hello //检查文件类型
注意:编译必须要在超级用户下才行,要不会报错。
如果出现下面的说明,则交叉编译成功并且正确。
hello: ELF 32-bit LSB executable, ARM, version 1, dynamically linked (uses shared libs), for GNU/Linux 2.4.3, not stripped
第七步执行阶段
这一步操作要借助于开发板来实现,我使用的是FL2440开发板,通过windows下的超级终端发送传送文件和调试。
下面将详细介绍操作的步骤:
首先在windows下打开超级终端,打开的方法如下:
开始——>程序——>附件——>通讯——>超级终端
打开后,会弹出对话框,在名称里面输入FL2440,点确定后会弹出选择串口的对话框,根据板子的实际情况进行选择,这里选择默认串口COM1,然后点确定。会弹出一个COM口属性配置窗口,实际配置见图1.
图1 串口配置
配置完成后,就进入超级终端的主界面了,和DNW很相似。
打开开发板电源开关,按回车就进入了菜单选择模式,在此我们选择[4] Boot Linux。这样,板子就进入了linux系统。
然后在超级终端中按回车,就出现了“#”符号,进入了命令模式。输入ls,查看板子文件信息,如图3.
图3 接收文件前
然后选择超级终端上面的发送——>发送文件,弹出图4发送文件对话框。
图4 发送文件
然后点“浏览”,选择我们在第六步所产生的 hello文件,点发送。等发送完成后,用ls查看目录,会看到这个文件已经被发送到了开发板上。图6
图5 接收文件后
在命令行输入“chmod +x hello”,增加可执行权限。然后输入“./hello”执行,会看到文件执行的结果,如图7所示。
图7 hello的执行结果
到此,整个编译器制作完成。
错误汇总:
<1>、在执行过程中会提示下面的错误:
configure: error:
*** These critical programs are missing or too old: gcc
*** Check the INSTALL file for required versions.
解决办法:
# sudo apt-get install gcc-4.1 //安装gcc-4.1
#sudo rm /usr/bin/gcc //删除文件
#sudo ln -s /usr/bin/gcc-4.1 /usr/bin/gcc //建立同步链接
问题即可解决。
<2>、出现错误
/home/y/crosstool-0.42/build/arm-linux/gcc-3.3.6-glibc-2.3.2/build- glibc/csu/version-info.h:1:1: missing terminating " character
系统在编译生成version.o时候发现version-info.h文件有错误
解决方案:
# cd ~ //切换到用户目录,然后把glibc-2.3.2.tar.bz2放在用户目录下
# tar zxvf glibc-2.3.2.tar.bz2 //解压缩
# cd glibc-2.3.2
# cd csu
# gedit Makefile
打开Makefile文件后,在最后可以找到这样几行代码:
echo "\"Compiled on a $$os $$version system" \
"on `date +%Y-%m-%d`.\\n\"" ;; \
*) ;; \
esac; \
files="$(all-Banner-files)"; \
if test -n "$$files"; then \
echo "\"Available extensions:\\n\""; \
sed -e '/^#/d' -e 's/^[[:space:]]*/ /' \
-e 's/\(^.*$$\)/\"\1\\n\"/' $$files; \
fi) > $@T
mv -f $@T $@
将蓝色标注处更改为:
"on `date +%Y-%m-%d`.\\\\n\"" ;; \
echo "\"Available extensions:\\\\n\""; \
保存退出。
然后,在终端输入命令:
# cd ~
# cd tar -cjvf glibc-2.3.2.tar.bz2 glibc-2.3.2
最后将生成的压缩包glibc-2.3.2.tar.gz移动到downloads下,替换原来的压缩包即可。
<3>、出现错误提示:
applying patch /home/ljd/downloads/crosstool-0.43/patches/glibc-2.3.2/arm-asm-clobber.patch getandpatch.sh: 1: patch: not found
解决方案:
# sudo apt-get install patch
参考文献:
[1]、李亚锋等——《ARM嵌入式linux系统开发从入门到精通》
[2]、弓雷等———《ARM嵌入式linux系统开发详解》
chinaunix网友2010-12-17 15:11:32
很好的, 收藏了 推荐一个博客,提供很多免费软件编程电子书下载: http://free-ebooks.appspot.com