satan 通过 Google 阅读器发送给您的内容:
于 11-12-12 通过 averiany涂鸦馆 作者:averainy
基于嵌入式系统的开发环境主要涉及到交叉编译器,汇编器、链接器等。这
些工具一般由开发 cpu 的厂商提供,可以直接在 windows 下或者在 linux 下运行。
本文的目的并不是具体的讲述如何去使用这些工具,而是当得不到这些现成的工
具时,自己如何去构造这些工具。构造的方法就是应用 gcc 的源代码建立针对目
标处理器的交叉编译平台。
GCC(GNU Compiler Collection)是现阶段被广泛使用的开放源码的编译器,
它 支 持 多 种 高 级 语 言 ( c,c++,fortran,java,ada ) , 同 时 支 持 多 种 处 理 器
(alpha,arm,avr,IA-64,intel 386,AMD,mips,mmix,powerpc,sparc,pdp-11…),它不仅
因为其支持多目标的特性而被广大厂商使用,更是因为其在生成代码的质量、速
度上的优秀表现而获得广泛的赞美。下面具体讲述交叉编译平台建立过程。
一、准备工作
1. 安装 linux 操作系统
这个平台是在 linux 下建立起来的,所用的 linux 版本为 redhatv9.2。所用
的本地编译器为 gcc3.2.2(redhatv9.2 自带的 gcc)。用这个本地编译器编译 gcc
的源代码使之产生针对 arm 处理器的交叉编译器。本地编译器是指它编译出来的
程序可在本地机(即运行编译器的机器)上运行;而交叉编译器编译出来的程序
不可以在本地机上运行。如下图所示:
Gcc3.2.3
本地编译器
Gcc 交 叉 编
译器
Gcc 源代码
C语言应
用程序
针 对 目 标 机 器
(arm)的可执行
文件
在本地机上
运行
需要说明的是,由于 linux 下的一些程序并不具有很好的兼容性和稳定性,
因此所用的 gcc 本地编译器最好是稳定的版本(比如 gcc3.2.2),而不要一味地追
求最高的版本。
2. 为目标机器建立 binutils.
Binutils 是一个工具包,它包含汇编器、链接器以及管理静态库、动态库的
一些工具。我们从网上下载的一般是 binutils 的源文件,我们需要把它编译成针
对目标机(arm)的工具,这样编译后得到的汇编器是针对 arm 的汇编器,链接
器也是针对 arm 的链接器。首先从网上下载 binutils-2.13.2.1.tar.gz,执行以下命令:
tar –xzvf binutils-2.13.2.1.tar.gz
新生成的 binutils-2.13.2.1 被称为源目录,用${srcdir}表示它。以后在出现
${srcdir}的地方,应该用真实的路径来替换它。
然后建立目标目录,目标目录(用${objdir}表示)是用来存放编译结果的地
方。GCC 建议编译后的文件不要放在源目录${srcdir}中(虽然这样做也可以),
最好单独存放在另外一个目录中,比如${srcdir}的同级目录。用 cd 命令进入目
标目录,然后执行以下命令:
${srcdir}/configure --prefix=/usr/local --target=arm-elf
--with-cpu=arm8
配置的目的是将 binutils 安装到什么地方,在这里为/usr/local,在 linux 系统下,
这个目录就是用来存放安装结果的地方。--targeth 和--with-cpu 选项说明了生成
的汇编器和链接器等是针对 arm 处理器的,具体是 arm 系列的 arm8 处理器,并且
该处理器上还没有运行操作系统(大多数嵌入式系统都是这样的)。
该命令执行${srcdir}目录下的 configure 文件,同时接受用户输入的选
项,然后生成 Makefile。Makefile 说明了 gcc 众多源文件的编译顺序和依
赖关系。用户在编译 gcc 源代码时,不需要依次对各源文件进行编译,只需执
行 make 命令即可,它能解释 makefile 里的编译顺序和依赖关系,一次性完
成全部的编译过程。关于 Makefile 的更进一步的探讨,有兴趣的同学可以参
考附录。
配置完成之后然后执行以下两个命令就完成了安装过程:
make
make install
其中执行 make install 要求用户具有超级权限。执行以下命令会看到编译生成
的工具:
ls /usr/local/bin
arm-elf-as
arm-elf-ld
arm-elf-ar
ls /usr/local/arm-elf
bin lib
我们可以看到/usr/local 是 binutils 安装用到的最上层目录,在执行 configure
命令时通过--prefix 设置了这个最上层目录。
二、 构造交叉编译器
如果准备工作已经就绪,剩下的就是构造这个新的编译器了。构造编译器所
需的步骤基本上与构造 binutils 的步骤相同,需要建立目标目录然后在目标目录
里执行 configure、make all-gcc、make install-gcc 命令就完成了编译过程。${srcdir}/configure --prefix=/usr/local --target=arm-elf
--with-cpu=arm8 --enable-languages=c --disable-shared
--disable-nls --with-gnu-as --with-gnu-ld
${srcdir}就是解压缩 gcc-3.2.3.tar.gz 之后生成的目录,比如……/gcc3.2.3.
在这里也设置了前缀(prefix),需要注意的是,这个前缀必须与配置 binutils
时的前缀一样。因为在编译 gcc 源码的过程中需要用到 prefix 目录里的一些工具,
比如 arm-elf-as、arm-elf-ld、arm-elf-ar 等等。
之后执行
Make all-gcc
make install-gcc
运行完毕之后,可以在/usr/local/bin 里找到构造好的交叉编译程序,如下:
ls /usr/local/bin
arm-elf-gcc
……
需要说明的是:
1.如果用户设置的 prefix 选项不是/usr/local,而是其他目录,用${prefix}
表示,那么在 make 之前需要执行:
PATH=$PATH: ${prefix}
这样设置了 PATH 变量之后,在编译时,arm-elf-as、arm-elf-ld 这些
工具就能够被找到。
2.在编译时,一定要是 make all-gcc,而不能是简单的 make 命令,make
all-gcc 只生成交叉编译程序,不生成 c 运行时库,这在很多情况下已经足够
了。
三、后续的工作
后续的工作就是生成 c 运行时库,有这些库的支持,c 语言应用程序的开发
才会变得功能强大。在这里,只简单的说明库的作用,至于如何生成 c 运行时库,
可参考《gcc 技术参考大全》第 17 章。
在 c 语言中,一些比较常用的函数,比如<math.h>里的函数,已经由编译器
的厂商写好,并且已经编译成二进制文件(目标文件),用户如果要用这些函数,
不需要再去写函数,只需调用即可。这些常用的函数范围相当广泛,涉及到输入
输出,文件读写,内存分配等,极大地方便了程序员开发出功能强大的应用程序。
这些函数的目标文件的集合就是库。不仅编译器或者操作系统提供这种一般功能
的库,也有其他软件开发商提供专门用途的库,这种类型的库称为 sdk(software
development kit),比如专门用于图像处理的工具包 VisualSDK、视频处理工具
包 OPENCV、图形界面开发工具包 GTK。另外,微软开发的 MFC 类库其实也是各种类定义的目标文件集合。使用库进行编程能省去程序员大量的重复劳动,一个高
效的程序员应该在开始写程序之前,应确定要写的模块是否能用现成的库来实
现,这样既保证了代码的可靠性又节省了时间。在 GCC 中生成库的例子如下:
gcc -c inlet.c outlet.c genspru.c
ar -r libspin.a inlet.o outlet.o genspru.o
gcc main.c libspin.a -o spinner
注:libspin.a 是 inlet.o outlet.o genspru.o 的集合,但在链接时,并不是
这三个目标文件都被链接进来,只有 main.c 中用到的目标文件才会被链接进来
可从此处完成的操作:
- 使用 Google 阅读器订阅averiany涂鸦馆
- 开始使用 Google 阅读器,轻松地与您喜爱的所有网站保持同步更新
没有评论:
发表评论