arm c语言的交叉编译环境ads代码,交叉编译环境的概念以及建立步骤
什么是交叉编译?
交叉编译(cross-compilation)是指,在某个主机平台上(比如PC上)用交叉编译器编译出可在其他平台上(比如ARM上)运行的代码的过程。
具体:
交叉编译这个概念的出现和流行是和嵌入式系统的广泛发展同步的。我们常用的计算机软件,都需要通过编译的方式,把使用高级计算机语言编写的代码(比如 C代码)编译(compile)成计算机可以识别和执行的二进制代码。比如,我们在 Windows 平台上,可使用 Visual C++ 开发环境,编写程序并编译成可执行程序。这种方式下,我们使用 PC 平台上的 Windows 工具开发针对 Windows 本身的可执行程序,这种编译过程称为 native compilation,中文可理解为本机编译。然而,在进行嵌入式系统的开发时,运行程序的目标平台通常具有有限的存储空间和运算能力,比如常见的 ARM 平台,其一般的静态存储空间大概是 16 到 32 MB,而 CPU 的主频大概在 100MHz 到 500MHz 之间。这种情况下,在 ARM 平台上进行本机编译就不太可能了,这是因为一般的编译工具链(compilation tool chain)需要很大的存储空间,并需要很强的 CPU 运算能力。为了解决这个问题,交叉编译工具就应运而生了。通过交叉编译工具,我们就可以在 CPU 能力很强、存储控件足够的主机平台上(比如 PC 上)编译出针对其他平台的可执行程序。
要进行交叉编译,我们需要在主机平台上安装对应的交叉编译工具链(cross compilation tool chain),然后用这个交叉编译工具链编译我们的源代码,最终生成可在目标平台上运行的代码。常见的交叉编译例子如下:
在 Windows PC 上,利用 ADS(ARM 开发环境),使用 armcc 编译器,则可编译出针对 ARM CPU 的可执行代码。
在 Linux PC 上,利用 arm-linux-gcc 编译器,可编译出针对 Linux ARM 平台的可执行代码。
在 Windows PC 上,利用 cygwin 环境,运行 arm-elf-gcc 编译器,可编译出针对 ARM CPU 的可执行代码。
另外,在业界广泛使用嵌入式 Linux 操作系统的今天,大多数交叉编译过程都是在 Linux PC 平台上完成。这时,程序员会在某个运行 Linux 操作系统的 PC 上安装交叉编译工具链,并使用 GNU 提供的开发工具方便地开发和调试嵌入式应用软件。
一步一步的制作arm-linux交叉编译环境
我们使用以下版本的文件为例子建立 arm-linux 交叉编译环境:
编译环境 redhat 7.2 或 8.0
binutils-2.14.tar.gzgcc-core-2.95.3.tar.gzgcc-g++2.95.3.tar.gzglibc-2.2.4.tar.gzglibc-linuxthreads-2.2.4.tar.gzlinux-2.4.21.tar.gzpatch-2.4.21-rmk1.gz # linux kernel patch for arm我们在 bash 下工作,先设定一些变量:
$ export VBINUTILS=2.14
$ export VGCC=2.95.3
$ export VGLIBC=2.2.4
$ export VLINUX=2.4.21
$ export VLINUX_PATCH=rmk1
$
$ export PREFIX=/armtools
$ export TARGET=arm-linux
你可以把它们加到 .bashrc 中。如果你这么做了,你需要 logout 再 login 才能生效。
否则在 bash 的命令行上输入它们并立即生效,但你 logout 再 login 时它就无效了。
我们的工作路径是:
...../ ----- ~ -- tars -------- SourceDir
............|................|---- BuildDir
............|--- armtools
$ cd ~
$ mkdir -p tars/SourceDir
$ mkdir tars/BuildDir
$ mkdir arm_tools
$ su
# mv arm_tools $PREFIX
# exit
$
tars --------------- 在这里放我们的下载来的 .tar.gz 文件
SourceDir ------ 这个临时目录放我们解压缩后的源文件
BuildDir --------- 我们在这里编译
armtools -------- 把arm-linux 交叉编译环境的安装在这里
1.安装linux 的头文件
当你为不同类型的ARM编译gcc,或编译不同版本的kernel,或交叉编译gcc 时都需要一套不同的linux头文件。
1.1解压缩,打补丁
$ cd ~/tars/SourceDir
$ tar -zxf ../linux-$VLINUX.tar.gz
$ cd linux
$ zcat ../../patch- $VLINUX-$VLINUX_PATCH.gz | patch -p1
1.2清理一下
$ make mrproper
1.3修改 Makefile
将Makefile中ARCH := $(shell uname -m | sed -e s/i.86/i386/ -e s/sun4u/sparc64/ -e s/arm.*/arm/ -e s/sa110/arm/) 这一行注释掉,并加一行 ARCH=arm。修改后象这样:
ARCH=arm
# ARCH := $(shell uname -m | sed -e s/i.86/i386/ -e s/sun4u/sparc64/ -e s/arm.*/arm/ -e s/sa110/arm/)
如果你的系统里的 sed 程序支持用 '\' 续行(通常都支持),你可以用这个 script 去修改 Makefile
#!/bin/sh
mv Makefile Makefile.orig
sed 's/ARCH := $(shell uname -m/ARCH=arm# ARCH := $(shell uname -m/' < Makefile.orig > Makefile
#end of script
注意:
这个 script 里的 # ARCH := 是上一行的续行,不是 shell 里的注释,它也是要输入的。
如果你从浏览器(IE, netscape, etc)上 copy-paste 这个 script 到你的 bash console,它很有可能不工作;
但你在 bash console 里手工输入就可以工作。
因为有时 copy 过来后,是 'ARCH=arm\r\n',而能工作的是 'ARCH=arm\n'。
1.4建立连接
1.4.1如果是LART板子
$ make lart_config
$ yes "" | make oldconfig
$ make include/linux/version.h
或:
$ make lart_config
$ make menuconfig 选择
网上有的文章用的是:
$ make symlinks include/linux/version.h
那是不完全的。make symlinks 的作用相当于:
$ cd include/asm-arm
$ rm -f arch proc
$ ln -s arch-sa1100 arch
$ ln -s proc-armv proc
$ cd ../../
它并没有产生一个很重要的文件 include/linux/autoconf.h。
而 yes "" | make oldconfig 不仅是 make symlinks,
还产生了 include/linux/autoconf.h。但它也没有产生
include/linux/version.h。
1.4.2如果是clps711x的CPU
连接应该为:
$ cd include/asm-arm
$ rm -f arch proc
$ ln -s arch-clps711x arch
$ ln -s proc-armv proc
$ cd ../../
为你自己的系统定制:
$ make menuconfig
在这里你只需要选你使用的 CPU 或选则有你使用的 CPU 的板子即可,
当然进行更详细的配置更好。
注:
include/asm-arm/proc-armo 是26位ARM
include/asm-arm/proc-armv 是32位ARM
注:背景知识
在ARM1中实现26位地址空间,但没有被商用。
在ARM2,2a 中还有26位地址空间,现在已经废弃。
在ARM3中扩展到32位地址空间,但是还反向兼容26位。
在ARM4中是32位地址空间,停止兼容26位地址空间。在 T 系列中加入 Thumb 指令。
在ARM5中是32位地址空间,在所有系列中均支持 16 位的 Thumb 指令。
1.5拷贝头文件
$ mkdir -p $PREFIX/$TARGET/include
$ cp -dR include/linux $PREFIX/$TARGET/include
$ cp -dR include/asm-arm $PREFIX/$TARGET/include/asm
1.6为 gcc 建立一个 linux kernel 头文件的连接
编译gcc时,它需要 linux kernel 的头文件,你可以用 --with-headers=$PREFIX/$TARGET/include 来指定头文件的位置,gcc 把它拷贝到 $PREFIX/$TARGET/sys-include。我们可以建立个 sys-include 连接,就不用 --with-headers 了。
$ cd $PREFIX/$TARGET
$ ln -s include sys-include
2编译安装binutils
这里用不到前面准备的 linux 头文件
2.1解压缩
$ cd ~/tars/SourceDir
$ tar -zxf ../binutils-$VBINUTILS.tar.gz
2.2编译
$ cd ~/tars/BuildDir
$ mkdir binutils
$ cd binutils
$ ../../SourceDir/binutils-$VBINUTILS/configure --target=$TARGET --prefix=$PREFIX
$ make all install
2.3输出 binutils 的路径到环境变量中
你可以把它加到 .bashrc 中。如果你这么做了,你需要 logout 再 login 才能生效。
否则在 bash 的命令行上输入它并立即生效,但你 logout 再 login 时它就无效了。
export PATH=$PREFIX/bin:$PATH
3.编译安装gcc 的c 编译器
3.1解压缩
$ cd ~/tars/SourceDir
$ tar -zxf ../gcc-core-$VGCC.tar.gz
注意:为什么不用 all-in-one 的 gcc-$VGCC.tar.gz 呢?
all-in-one 的 gcc 包里面有 chill, fortran, java 等语言的编译器,虽然在下面 configure 时指定 -enable-languages=c,但编译时还是把所有的都编译一便,这不是我们需要的,而且它也总会有错误。因此我们只编译 C 语言的编译器。后面第二次编译的时候也是这个问题,我们只编译 C 和 C++ 的编译器。
3.2修改 gcc 的 t-linux 文件
在 t-linux 文件中的 TARGET_LIBGCC2_CFLAGS 上加上 __gthr_posix_h 和 inhibit_libc
$ cd gcc-$VGCC/gcc/config/arm
$ mv t-linux t-linux-orig
$ sed 's/TARGET_LIBGCC2_CFLAGS =/TARGET_LIBGCC2_CFLAGS = -D__gthr_posix_h -Dinhibit_libc/' < t-linux-orig > t-linux-core
$ cp ./t-linux-core ./t-linux
3.4编译
$ cd ~/tars/BuildDir
$ mkdir gcc-core
$ cd gcc-core
$ ../../SourceDir/gcc-$VGCC/configure --target=$TARGET --prefix=$PREFIX --enable-languages=c --disable-shared --disable-threads
$ make all install
4.编译安装 glibc
4.1解压缩
$ cd ~/tars/SourceDir
$ tar -zxf ../glibc-$VGLIBC.tar.gz
$ cd glibc-$VGLIBC
$ tar -zxf ../../glibc-linuxthreads-$VGLIBC.tar.gz
4.2编译
$ cd ~/tars/BuildDir
$ mkdir glibc
$ cd glibc
$ CC=$TARGET-gcc AR=$TARGET-ar RANLIB=$TARGET-ranlib ../../SourceDir/glibc-$VGLIBC/configure $TARGET --prefix=$PREFIX/$TARGET --enable-add-ons
$ make all install
5.编译安装gcc 的c, c++ 编译器
5.1恢复t-linux 文件
$ cd ~/tars/SourceDir/gcc-$VGCC/gcc/config/arm/
$ cp t-linux-orig t-linux
5.2解压缩 c++ 编译器
$ cd ~/tars/SourceDir/
$ tar -zxf ../gcc-g++-$VGCC.tar.gz
$
$ cd ~/tars/BuildDir
$ mkdir gcc
$ cd gcc
5.3编译
$ ../../SourceDir/gcc-$VGCC/configure \
--target=$TARGET \
--prefix=$PREFIX \
--enable-languages=c,c++ \
--with-included-gettext
$ make all
$ make install
注:
如果你下载的是 filename.tar.bz2,你可以用如下命令之一解压缩,第三种方式在任何系统中都好使。
$ tar -jxf filename.tar.bz2
$ tar -Ixf filename.tar.bz2
$ bzip2 -dc filename.tar.bz2 | tar xf -
如果你是第一次制作 arm-linux 交叉编译环境,强烈建议你用本文所使用的各个程序的版本。如果用其它版 本,按照本文的方法可能会在编译的时候出问题,因为我没有时间去测试各个版本的组合。这里是源程序: crossarm.sh,它使用的是:
linux-2.4.21.tar.bz2
patch-2.4.21.bz2
binutils-2.14.tar.gz
gcc-core-2.95.3.tar.gz
gcc-g++-2.95.3.tar.gz
glibc-2.2.4.tar.gz
生成的 toolchain 大于 150 兆,用如下方法压缩:
$ cd ~
$ tar -cf armtools.tar /armtools
$ bzip2 -z armtools.tar
压缩后生成的 armtools.tar.bz2 大概有 30 几兆。
arm c语言的交叉编译环境ads代码,交叉编译环境的概念以及建立步骤相关推荐
- ADS集成开发环境介绍
ARM的学习和开发都需要学习哪些软件 1 ADS调试用 ADS是编译器,AXD是调试器.编译成AXF以后再在ARM的RAM里调试. 2 FLASHPGM FLASH烧写的软件. AXF在RAM里调试, ...
- ARM 汇编基础教程番外篇 ——配置实验环境
From:https://zhuanlan.zhihu.com/p/29145513 win10 arm 汇编环境 Windows 平台下搭建 ARM 汇编集成环境:https://jingyan.b ...
- Go语言从入门到规范-1.1、Go语言官网文档大纲及环境搭建
Go语言从入门到规范-1.1.Go语言官网文档大纲及环境搭建 文章目录 Go语言从入门到规范-1.1.Go语言官网文档大纲及环境搭建 前言 一.go简介及学习路径 二.安装go 1.下载Go发行版 2 ...
- 基于RK3308的ROS运行环境搭建和交叉编译
基于RK3308的ROS运行环境搭建和交叉编译 固件编译环境 准备工作 软件包安装 交叉编译工具链介绍 下载 SDK SDK 目录结构 全自动编译脚本 烧写镜像文件 第一步,编译固件(ubuntu18 ...
- Hi3516EV200 编译环境配置及交叉编译软件包
原文地址:Hi3516EV200 编译环境配置及交叉编译软件包 - WindSpiritIT 基础信息 OS: Ubuntu 16.04 xenial SDK 版本: Hi3516EV200R001C ...
- [跳舞吧多人视频空间]ADS集成开发环境先容
[跳舞吧多人视频空间]ADS集成开发环境先容 2012年01月11日 [b]跳舞吧[/b][b]视频空间美女主播聊天交友,尽在[/b][b]同城聊天室[/b][b]跳舞吧 [/b] ADS全称为ARM ...
- python软件包自带的集成开发环境-Python的10大集成开发环境和代码编辑器(指南)...
使用IDLE或者Python Shell来编写Python是非常适合于简单程序的,但是这些工具往往将大型的编程项目变成一个个充满绝望和沮丧的"坑".使用一款集成开发环境甚至是一款好 ...
- python自带的集成开发环境是什么-Python的10大集成开发环境和代码编辑器(指南)...
使用IDLE或者Python Shell来编写Python是非常适合于简单程序的,但是这些工具往往将大型的编程项目变成一个个充满绝望和沮丧的"坑".使用一款集成开发环境甚至是一款好 ...
- 【C++ 语言】Visual Studio 配置 FFMPEG 开发环境 ( VS2019 CMake 环境安装 | 下载 FFMPEG 开发包 | 配置 FFMPEG )
文章目录 Visual Studio 2019 社区版 CMakeList 开发环境安装 创建 FFMPEG 配置项目 FFMPEG 开发包下载 FFMPEG 头文件 静态链接库 ( .lib ) 动 ...
- C语言 03-第一个C程序代码分析
本文目录 一.代码分析 二.开发和运行C程序的步骤 三.总结 说明:这个C语言专题,是学习iOS开发的前奏.也为了让有面向对象语言开发经验的程序员,能够快速上手C语言.如果你还没有编程经验,或者对C语 ...
最新文章
- 使用json-server搭建模拟api接口
- python3--装饰器
- Linux日志系统-08:定时执行脚本
- css 中的若干心得
- Xcode 修改系统的代码块样式 Code Snippet
- TCP请求发送和接收,如果接收端终止,发送端继续发送会出什么错
- 开源知识管理系统_Zboot权限后台管理系统开源啦
- bt解析 开源 java_开源一个BT客户端:BitWave
- DevOps使用教程 华为云(18)git 把单个文件回退到某一版本
- 安卓设备手柄无法映射线性扳机的解决思路(1)
- sql server插入语句
- 三大主流负载均衡器LVS、Nginx、HAproxy详解
- document.getelementbyid是什么意思
- 雷电三接口有什么用_三坐标中的矢量是干什么用的?
- 手把手教你用Arcgis绘制地图【热力图】
- 3.1 YOLO系列理论(YOLOV1、YOLOV2、YOLOV3)
- 线性回归与逻辑回归的原理、计算步骤、区别、联系
- Linux中 ps命令详解
- 服务端解决故障的处理思路
- 计算机水平一般良好怎么填,计算机水平一般怎么填
热门文章
- 【数据库查询--电影制片系列】--查询比电影M1时间更长的电影。
- HDOJ1201-18岁生日
- 厉害了:杭州有了人工智能斑马线,南京用人工智能给非洲人远程看病
- Ubuntu16.04 安装Nvidia驱动【电脑黑屏】
- Traceback (most recent call last): File “/home/xwt/.conda/envs/smpl/bin/pip“, line 5, in <module>
- 登了外网VPN后再断开,连不上网了
- swagger 生成接口文档,并导出html和pdf的过程
- 攻防世界-catch-me
- 【CSDN竞赛第13期】75分简要题解
- c语言实现logfile库(打印日志库的实现)