文档库 最新最全的文档下载
当前位置:文档库 › 基于ARM嵌入式的以太网通信程序设计

基于ARM嵌入式的以太网通信程序设计

基于ARM嵌入式的以太网通信程序设计
基于ARM嵌入式的以太网通信程序设计

1

目次

1 绪论 (2)

1.1 课题研究背景及意义 (2)

1.2 嵌入式系统的现状和发展趋势 (2)

1.3 嵌入式网络的关键问题 (4)

1.4 本论文的主要工作 (4)

2 ARM嵌入式系统 (6)

2.1 系统开发环境 (6)

2.2 ARM嵌入式硬件平台 (6)

2.3 搭建ARM嵌入式开发环境 (9)

2.4 PC机Linux开发环境的建立 (22)

2.5 本章小结 (22)

3 ARM嵌入式以太网通信的开发 (24)

3.1 OSI网络模型 (24)

3.2 TCP/IP协议栈的基本概念 (24)

3.3 TCP协议基本概念 (25)

3.4 UDP协议 (28)

3.5 本章小结 (29)

4 ARM嵌入式的以太网通信程序设计 (31)

4.1 TCP通信程序设计 (31)

4.2 TCP网络程序设计流程 (33)

4.3 TCP服务器/客户端网络程序的实现 (42)

4.4 UDP通信程序设计 (46)

4.5 UDP服务器/客户端网络程序的实现 (52)

4.6 本章小结 (54)

结论 (55)

致谢 (56)

参考文献 (57)

附录 1 (58)

附录 2 (61)

附录 3 (64)

1 绪论

随着信息技术的迅猛发展,在我们的生活工作中,对于网络通信的要求逐年增高,且随着移动互联网络的发展与需求,嵌入式系统与通信网络,日日夜夜伴随着我们。嵌入式系统与网络技术融合已经是必然的发展趋势,当嵌入式设备具有网络功能时,人们可以在任何地方、任何时间、任何平台随时浏览设备的信息,并进行操作和测试。这是在嵌入式系统在其网络性和开放性的发展趋势。

1.1 课题研究背景及意义

如今,我们的生活与工作中已经无法离开网络。人们进行信息的传送和交流,之所可以实时且效地,恰是因为有“信息高速公路”,而“信息高速公路”的重要支撑网就是以太网[1]。“以太(Ether)”这个词,是来源自十九世纪的物理学家们假设出的某种媒介,用以传播电磁波的辐射。在下,他们认为“以太”充斥于世界各处,因此,到后来将“以太”这个假说引入到计算机局域网中,从而用来表现它在通信领域也是无处不在,就像“以太”充斥于世界中那样普遍存在。以太网可以方便的接入网络,以太网使用的通信协议也因为适用性,有着十分优异的兼容性。

当前,在嵌入式系统接入因特网的所有技术中,被使用最多的局域网通信技术即是以太网通信。通过以太网可以十分方便地搭建局域网,因而能与因特网链接。嵌入式系统的开发与设计有了前所未有的空间与机遇,对于嵌入式系统的发展应用,任何时候都有机会跨入嵌入式以太网时代,这些都是需要两者技术上的完美融合。

只要完成了嵌入式系统与以太网的链接,使嵌入式系统发展成为以太网中单独的一个节点,用户在节点可以通过网络,便捷且低代价地进行数据传输。所以为了实现整个系统的数据的传输功能,而在嵌入式系统与以太网链接的方法上做相应的研究,是具有十分重要的经济价值和现实意义的。

在这种背景下,本文对基于ARM的以太网通信的这一问题,进行研究与应用,具有充分的实际意义。

1.2 嵌入式系统的现状和发展趋势

几乎电子设备所有新的生机都与嵌入式系统的发展关系紧密,在电子通信、医疗卫生、轻工业产品、监控安防、消费类电子、工业自动化系统等行业都有重要的嵌入式相关产品。尤其是在消费电子相关产业,占有最高的嵌入式系统的产品的市场比重,监控安防、电子通信、医疗卫生以及其他领域紧随其后。

近十几年来,嵌入式系统得到了根本性的发展。微处理器、微控制器大量在产品中使用,CPU 也从当初8 位的单片机发展到现在的16位、32位甚至64 位的高端微处理器;从仅具备单一内核发展到提供丰富外设及接口功能;从几兆的频率发展到现在几百兆甚至1~2G 的处理速度。伴随着CPU性能的不断攀升,嵌人式系统也具备了文件系统、网络系统、图形界面系统等功能,并形成了以嵌入式操作系统为核心的嵌入式软件体系。跟随应用程度的不断加深扩大的嵌入式系统,全新领域应用以及商品化的需求在嵌入式系统软硬件上面表现出了更高的需求。嵌入式系统不仅仅具有微小性、低功耗、高可靠性的特点,还要向高实时性、高自适应性、易于操作和棋块化的方向发展[2]。总的说来,嵌入式系统在以下几个方面将会有更大的发展:

1. 嵌入式操作系统:

嵌入式系统刚刚发展的时候,软件系统还是前后台方式的系统开发,这种开发方式也被大多数人比喻为“裸奔”。前后台方式下的软件系统的实时性差、功能单一、代码不易于维护等缺点越来越不适应嵌入式系统的高速发展,为此嵌入式操作系统被引人。嵌入式操作系统的使用能够更加丰富嵌人式系统的功能,使得产品更加稳定可靠,多任务并发的处理方式也让系统的实时性要求得到满足,模块化的编程方式让产品的可定制性进一步增强。当前普遍使用的嵌入式的操作系统有Windows CE、μC/OS-II、Linux、VxWorks等。

这些嵌入式操作系统中当属Linux具有最高的人气和应用潜力,原因是其源代码公开且具有很好的定制性和可利用性,支持硬件广泛、安全可靠、拥有众多的开发者,另外有一重要原由便是产品生产商们在研发基于Linux系统的相关产品时,通常不必为发行软件或者生产产品而支付Linux的许可费用。目前广泛应用在手机、PAD等消费电子产品上的安卓操作系统,便是由Linux的内核所开发出来的。由此可见嵌入式操作系统,特别是嵌入式Linux系统应用潜力巨大。

2.网络互连:

网络技术已经深入到我们生活和工业生产的各个领域,由互联网引发的物联网技术正在快速发展中,网络也使得人与人、设备与设备之间的联系更加紧密,嵌人式设备为了适应网络技术的发展,必然要求在硬件上提供各种网络通信接口。传统单片机的系统对于网络连接有很大欠缺,然而现在的嵌入式处理器,却拥有了内置的网络端口,不仅拥有对TCP/IP协议的支持外,对于USB、总线、IEEE1394、蓝牙、或红外通信接口的支持,拥有上述通信接口中的一项或者多项,而且还对物理层提供其驱动的

软件,以及对应的通讯网的协议脚本。

3.易于操作的人机界面:

嵌入式产品是为人们的生产生活服务的,如果目前的嵌入式设备还像以前DOS系统那样使用命令行操作方式的话,就不会便于人们使用和操作,那些给我们生产生活带来方便和事受的电子高科技产品也不会产生,嵌人式产品被大家使用和接受的程度也将大大降低。

嵌入式系统的普及和应用离不开亿万大众,嵌入式产品的亲和力和人机互动性起着决定性的作用。我们都希望在一套图形漂亮、直观简洁的界面下,仅仅通过手指点击就完成我们的操作。苹果产品的热卖,平板电脑、智能手机的普及就充分说明了这点。

1.3 嵌入式网络的关键问题

在嵌入式网络上面,主要关心如下2部分的问题

1.嵌入式本身的内存大小以及其运算速度,这些硬件问题需要被考虑,虽然AT91SAM9G20有着较高的主频,但也要尽量的减少系统开支,达到最大的效率。

2.搭建合适的平台以完成通信,选择合适的平台将大大降低网络搭建的工作量,所以依照所需要的功能搭建通信平台。

1.4 本论文的主要工作

本课题通过对基于ARM嵌入式的以太网通信的研究,主要采用由Atmel公司推出的AT91SAM9G20芯片、DM9161AEP网络芯片、Nand Flash等形成设计基础,在ARM嵌入式平台中移植Linux内核,通过Linux操作系统完成TCP/IP、UDP/IP通信的功能,最终在YL-9G20开发板上进行硬件测试。

本文第2章介绍了基于ARM的嵌入式系统硬件平台,介绍了基于ARM的嵌入式系统硬件平台的组成以及开发平台的组建,重要硬件实现部分的构成,囊括相关芯片的问题进行依次进行叙述,且对核心处理器芯片、网络控制芯片的内部结构、实现功能以及其工作的原理,分别做了相关简介;以及论述服务器端的开发环境搭建,以及基于ARM的AT91Bootstrap的移植,U-Boot的移植,Linux内核配置与根文件系统的移植。

本文第3章介绍了以太网通信的基本理论,通过Linux系统实现TCP/IP、UDP通信协议,体现了Linux操作系统实现网络通信的技术优势,分别讲述协议栈中ARP、

IP、ICMP、TCP、UDP协议的实现过程,同时也介绍了协议栈与底层设备及应用层的接口设计。最后介绍了运用socket套接字接口进行网络程序编写的流程。

本文第4章介绍了基于ARM嵌入式的以太网通信程序的设计。论述了TCP、UDP 网络编程,且在服务器和客户端测试TCP、UDP通信,实现基于ARM嵌入式的以太网通信功能,完成通信程序的编写。

2 ARM嵌入式系统

目前,嵌入式系统相关技术已经在工业系统、个人消费电子产品、工业系统、智能家居等领域有着良好发展,其中多数伴随嵌入式系统产品的就是其嵌入式网络系统的开发,ARM嵌入式微处理器一般具有如下特点:体积小、低功耗、低成本、高性能;支持Thumb(16位)/ARM(32位)双指令集,能很好地兼容8位/16位器件[3]。本章,主要讲述嵌入式系统的硬件平台模块以及发开环境。

2.1 系统开发环境

系统开发环境主要由硬件部分包括计算机、ARM9开发板、网络设备;软件中包含:嵌入式Linux的开发环境以及相关设备驱动、SecureCRT组成。软件部分的工作均在计算机PC(Personal Computer)上完成,嵌入式Linux开发环境负责程序的开发和调试,SecureCRT可以打印串口输出的数据,以及通过串口向开发板发送数据。

ARM嵌入式系统的开发环境如下图 2.1 所示。

图2.1 系统开发环境图

PC机提供了程序编写开发和调试的平台,搭载了Linux操作系统的开发环境和SecureCRT串口调试工具,完成嵌入式Linux系统的移植以及相关环境的搭建、程序的编写以及调试的功能。通过串口和USB接口连接开发板,在PC机上进行对开发板的相关操作,通过以太网口完成PC机与开发板中的网络芯片的以太网通信的硬件连接,实现以太网通信。

2.2 ARM嵌入式硬件平台

硬件系统是ARM嵌入式系统一切的根本,实现产品的基础就是硬件平台,实现产

品的附加服务,则需要软件的帮助。为了实现本文的目标 - 基于ARM嵌入式的以太网通信程序设计,我第一步要做的就是进行对ARM嵌入式系统硬件的学习和了解,所以在下面几节对于ARM嵌入式系统的硬件平台结构以及关键器件芯片进行介绍。

2.2.1 嵌入式硬件平台结构

由上一节图2.1可以看出,ARM嵌入式平台需要通过以太网网络芯片和以太网口完成网络的联通;以及需要USB和串口对程序和内核等进行下载烧写以及调试;同时,我们还需要存储部分以及实时时钟来提供支持,当然电源模块为整个ARM嵌入式开发平台提供运行的保障。如图2.2 所示为本文所需的ARM嵌入式系统的硬件结构。

图 2.2 ARM嵌入式平台硬件结构

通过RJ45连接到PC机,在完成前期工作后,通过设置端口,运行服务器端(PC 机)和客户端(ARM嵌入式平台)中的网络程序即可实现TCP或UDP协议的通信。

2.2.2 嵌入式处理器

在嵌入式系统中,处理器依照其性能高低分别为嵌入式微控制器以及嵌入式微处理器。在一些低端如:简单运算处理、逻辑控制、IO控制等场合中,通常使用微控制器,这些微控制器大多是16位或8位的。而在应用一些复杂运算、有处理速度需求且实时性要求的场合中,使用的处理器多是32位甚是64位的微处理器。从2.1.1节的硬件结构可以看出,我们需要完成通信和数据处理的相关任务,要求处理器具有较快的处理速度,然而处理器的系统时钟对处理速度起决定性作用。

本文使用的ARM嵌入式硬件平台使用的处理器AT91SAM9G20,Atmel公司的AT91SAM9G20芯片主频达400MHz,完全满足应用需求[4]。AT91SAM9G20微处理器基于ARM926EJ-S处理器核心内核,包含3个32位并行的I/O控制器,可控制SDRAM以及

包括Nand Flash在内的静态存储器。如图2.3为该处理器的结构图。

图2.3 AT91SAM9G20结构图

2.2.3 网络芯片

时今网络硬、软件技术的快速发展使得网络设备的应用呈现大幅增长的态势。控制各类仪器仪表、智能家电、消费电子产品、工业生产中的设备,以及它们相关数据采集的设备都开始了网络化,在Internet中共享及获取资源,从而进一步方便我们的工作和生活。

以太网通信,顾名思义,我们需要实现网络连接,也就离不开网络控制芯片。在我完成设计的过程中,必要解决的就是硬件平台同以太网的通信问题。本文中使用的ARM嵌入式平台采用了DM9161系列的网络控制芯片DM9161AEP,DM9161AEP的结构图如图2.4所示。

DM9161AEP的芯片特点如下所示:

1.48pin LQFP封装

2.工艺:0.25μm,输入输出供电电压

3.3V,模拟部分2.5V

3.支持MII和RMII连接方式(推荐使用MII)

4.支持双绞线自适应(AUTO-mix)

5.支持TCP/IP硬加速

6.与大部分厂家的微控制器是完全兼容。使用的单口PHY。

图 2.4 DM9161AEP 结构图

2.3 搭建ARM嵌入式开发环境

在上面介绍完ARM嵌入式系统的硬件平台,展开了软件方面的工作。对于嵌入式系统的软件开发来说,需要完成建立交叉编译工具;由于嵌入式系统所使用的芯片型号多种多样,很多芯片和硬件接口不能直接兼容[6],我们需要完成移植的工作:AT91Bootstarp移植,U-Boot移植与烧写,Linux内核移植与烧写,根文件系统移植与烧写,PC机上开发环境的建立等任务。

2.3.1 嵌入式Linux简介

Linux最早是由Linus Torvalds所创建的,经过20年时间的发展,Linux已经成为一个有着强大功能且稳定可靠的OS。经过对原有的Linux操作系统进行调整和剪裁,形成了可在嵌入式平台运行的嵌入式Linux操作系统。嵌入式Linux操作系统拥有嵌入式操作系统的全部特征,同时保留了十分丰富的开放的源代码,所以应用在嵌入式系统中是越来越普遍。

嵌入式Linux操作系统与其它嵌入式操作系统相比具有以下特点:

1.开放源代码。Linux最大的特点就是源代码公开并且执行GPL协议,嵌入式

Linux开发人员根据自己产品的需求可以更改内核源码来满足功能使用;不存在黑箱技术,遍布全球的众多Linux爱好者又是Linux开发的强大技术后盾[5]。

2.可裁剪、高效率的微小内核。Linux小内核、高效率,内核的更新速度快而且可以被定制。它的系统内核最小可以到134KB,这么优秀的内核设计可以使系统的仅仅占据更小的资源便可以可靠且稳定的运行。独特的模块机制可以将用户的驱动或者应用程序模块动态的从内核中插入或卸载。

3.免费。产品制造生产商在开发完基于嵌入式Linux的产品以后无需为产品的发布支付相关的许可费。

4.支持众多硬件。嵌入式Linux操作系统可以支持多种处理器和多种硬件体系,是一种可以跨越平台的操作系统。

5.安全、可靠。嵌入式Linux十分可靠,可以毫无故障的运行数年,一直广泛被数据中心所应用。与此同时,嵌入式Linux的开发人员还可以使用systrace或者grsecurity此类的工具来加强其安全性,这是Windows操作系统开发者无法想象的。

6.优秀的网路功能。嵌入式Linux在网络方面有着十分完整的内核结构,Linux 对网络中最常用的网络协议,如TCP/IP网络通信协议有着整体的支持。并且提供包括了10兆、100兆、1000兆的以太网络的支持。因此嵌入式Linux十分适用于网络相关产品的开发。

嵌入式Linux的应用,主要在数字电话、机顶盒、视频通信、数据网络、以太网交换机、Hub、远程通信、网桥、医疗电子、信息家电、PDA、工业等领域。可以说嵌入式Linux在民用还是工用范畴都有着普遍应用,当前很多平板电脑和智能手机采用的安卓也是采用Linux的内核。

2.3.2 ARM嵌入式系统一般的开发方法

与多数常见的桌面软件的开发所不同,当嵌入式软件开发人员开发一个基于嵌入式系统的应用时,首先会在PC机上选择合适的嵌入式开发环境并且进行软件开发,然后在实验板或者开发平台上对其代码进行测试,最后PC机编译生成正确的映像文件或者可执行的文件,并且烧写到最终的目标产品中,如图2.5所示。

图 2.5 ARM嵌入式系统开发的一般方法

对于ARM嵌入式平台的Linux软件开发一般步骤如下:

1.PC机的开发环境选择。这里本文选择的是Fedora 14 系统。通过在Windows 系统中的虚拟机来安装Fedora 14操作系统,便于调试。

2.建立交叉编译工具:Fedora 14自带的GCC都是针对x86架构的,为了可以让编写的代码在开发板或者最终产品上良好运行,建立交叉编译工具是所必须条件。

3.开发、移植Bootloader。

4.配置、烧写U-Boot。

5.配置、移植Linux内核。

6.建立根文件系统。

7.开发程序。

2.3.3 嵌入式Linux交叉编译环境的建立

嵌入式系统的硬件性能和其存储空间有限,因此,在对程序进行开发的时候都是在PC机上进行操作,首先建立一个用于开发板的交叉编译工具,用其在PC机上编译程序用于开发板。可以看出,可以在一个系统平台中编译出能够运行在不同的体系架构上的代码,这就是交叉编译。比如在处理器架构为x86的微机中编译出可以运行在ARM嵌入式中的代码。若使用桌面级编译环境,则无法生成在ARM平台上运行的程序代码。

在PC机Linux系统下利用GCC编译程序,这样的编译方法称之为本地编译,本地编译的代码只能够在本地运行。与本地编译相对应的,即是上面所介绍的交叉编译,

通过交叉编译器可以编译出这种跨平台程序。

采用arm-linux-gcc-4.3.2版本的交叉编译工具,通过网络下载到的文件解压到个人目录中。随后由终端进入解压后生成的/usr/local/目录中,将目录下的arm目录整体复制到系统文件根目录/usr/local/下面。然后所有交叉编译工具都存储在其中,如图2.6所示。

图2.6 交叉编译工具 arm-linux-gcc-4.3.2

然后更改环境变量PATH的函数,将统一存储的交叉编译工具的路径目录添加到其中。在终端中对PATH进行修改,键入:

#export PATH = /usr/local/arm/4.3.2/bin: $PATH

继而检查是否正确添加路径到PATH中,键入:

#echo $PATH

如图2.7所示,可以看到,有显示包含有交叉编译工具的路径,说明已完成添加新路径至PATH。至此,已经完成交叉编译环境的搭建。

图2.7 添加交叉编译工具环境变量

2.3.4 开发、移植AT91Bootstrap

在AT91SAM9G20芯片内部含有一个BootRom代码。当没有烧写任何Bootloader 和内核文件的情况之下给芯片上电启动,通过串口调试工具(本文使用SecureCRT)可以看到串口是有打印消息的,显示的内容为“RomBoot”,此RomBoot代码是Atmel厂商定制在芯片中的,人为不能对其作修改。作为ARM嵌入式开发人员,在启动代码的编写、修改和学习中,AT91Bootstrap是最先面对的环节。

AT91Bootstrap它的主要作用即是对SDRAM初始化以及相关的存储器(Nand Flash)初始化,然后加载U-Boot到SDRAM中的指定字节并开始运行U-Boot。AT91Bootstrap 源代码由公共的硬件驱动、头文件以及库文件等组成。

首先,解压下载的AT91Bootstrap,在终端中输入:

#unzip AT91Boostrap1.13.zip

解压后,在当前目录下生成AT91Bootstrap目录。进入相应9g20源码区,修改编译工具的路径,打开其文件夹,使用vi进行函数修改

此时,可以直接编译,在源目录下执行“make”指令。编译过后可在该目录下看到nandflash_at91sam9g20ek.bin文件,如图2.8所示。

#cd /home/dietrich/Bootstrap-v1.13/board/at91sam9g20ek/nandflash

#make

图2.8 make编译后生成bin文件

在这里就完成了ARM嵌入式系统的Bootstrap编译,接下来使用SAM-BA2.8烧写生成的.bin文件至Nand Flash内存的起始地址处,即0x0,也就是处理器启动以后首先要从NandFlash上的)0x0地址位上读取AT91Bootstrap且开始运行,这也说明在启动代码中,AT91Bootstrap是第一部分。

2.3.5 U-Boot移植与烧写

U-Boot的编译形式、源码目录都喝Linux的内很很相似。实际上,很多U-Boot 源代码就是通过对应的Linux系统内核弱化而来,特别是很多设备驱动程序。可以在U-Boot源代码的注释行中有很多表现。随着U-Boot版本不断的升级,其所支持的硬件资源和系统资源也是越来越丰富。

U-Boot有着诸多优点:源代码开放、对很多系列的处理器支持、对很多嵌入式OS内核支持、十分灵活的功能设置、优异的稳定以及可靠性、多种设备的驱动源代码以及对网络的强大支持。正是因为这些特点使得U-Boot被越来越多的嵌入式操作系统所应用,也有着更好的使用前景。

U-Boot启动并且引导Linux内核这一过程可以分为两个阶段,第一个阶段即为实现设备的初始化,绝大多数是采用汇编语言所编写来达到目的的;第二个阶段则是采用C语言编写,可读性强,并可实现相对复杂的功能。两个阶段实现的功能如下:

1.第一阶段功能:

设置异常项和异常处理函数;

- 设置控制寄存器地址;

- 关闭着门狗和屏蔽中断;

- 配置PLLCO飞等寄存器,确定系统的主频;

- 关闭MMU功能;

- 初始化RAM控制寄存器;

- 拷贝数据至SDRAM;

- 设置堆拢;

- 消除BSS段;

- 跳转到第二阶段代码人口。

2.第二阶段功能:

- 初始化本阶段所涉及的硬件设备;

- 设置SDRAM的起始地址和大小;

- 读取内核到RAM 中;

- 为内核设置启动参数;

- 调用内核。

可以从网络上下载U-Boot。本文采用的版本是1.3.4。在终端中使用解压命令将U-Boot-1.3.4.tar.bz2压缩文件在个人文件夹内进行解压操作,然后进入生成的

u-boot-1.3.4目录对Makefile文件进行修改,将CROSS_COMPILE变量修改为编译器所在目录(本文2.2.3节)。保存退出vi后对U-Boot进行make编译,即可在文件目录下生成我们需要的二进制.bin文件。

图2.9 编译后生成的bin文件

烧写U-Boot的方法仍然与上一节烧写AT91SAM9G20相同,如图2.10所示,也是通过SAM-BA软件。不过需要注意的是烧写起始地址应为NandFlash的0x200000地址处,然后Send File开始烧写u-boot.bin。

图2.10 烧写U-Boot.bin

2.3.6 嵌入式Linux内核的移植及烧写

嵌入式Linux内核在本文中选择Linux-2.6.27这个一个版本,解压Linux-2.6.27.tar.bz2压缩文件,可以观察到源码包内有相当多的文件和目录,为了掌握Linux内核的移植方法,了解其结构很有必要的。

Linux-2.6.27内核包中一共有20个文件夹,有很多都与本文无关,不做介绍,下面只介绍最为重要的7个文件目录:

1. arch目录。arch子目录包括了和硬件体系相关的核心代码。它的每一个子目录都是代表一种可以支持的硬件体系结构,例如i386 就是关于Intel CPU 及与之相兼容体系结构的子目录(PC 机一般都基于此目录)。其中的arm 目录是我们需要特别关心的,里面包含的是基于ARM处理器的体系结构,是本文对Linux 进行移植所需用到的目录。

2. drivers目录。drivers 子目录里面是Linux系统所支持的硬件设备驱动程序;每种驱动程序各占用一个下级子目录,如/usb目录下为通用串行总线USB设备驱动程序。对drivers/block/这个目录下的genhd.c文件进行查看,其中的device_setup()函数可以了解设备初始化的过程。

3. fs目录。fs子目录包含的是所有文件系统和各种类型的文件操作代码,此目录包含用于配置核心的脚本文件等。

4. kenerl目录。此目录内为核心代码,包含了进程通信、进程调度、内存管理、虚拟文件系统等在内的Linux系统大多数的内核函数。

5. include 目录。include 子目录包括编译核心所需要的大部分头文件。

6. init 目录。这个目录内包含初始化代码。

7. lib 目录。lib 子目录里面包含Linux 内核库函数代码。

在Linux 内核源码的根目录下还有一个文件需要特别注意,就是“Makefile文件”。它是Linux内核里面的第一个Makefile文件,其主要用来联系内核的各个模块,保存各种模块互相间的承接关系以及连接,在进行内核编译的时候需要修改这个文件。

对Linux内核的配置修改,是移植Linux内核的流程中所做的第一步,亦是相当重要且十分繁杂的一步。内核配置相当繁杂,有3000条左右需要配置,掌握一些方法可以降低工作的难度。

在内核源代码/arch/arm/configs目录中的配置文件可以看出Linux内核所支持的硬件都有哪些,在这里本文使用的ARM嵌入式硬件平台与Linux内核中提供的AT91SAM9G20EK很匹配,所以在配置内核的过程中可以直接加载AT91SAM9G20EK这个配置文件,然后在这个配置文件的基础上再做修改就可以了。这样大大的提高了内核的配置效率和准确度。

在Linux内核的配置上,需要对文件系统、杂项、网络设备支持、设备驱动等进行设置,第一次设置之前需要在终端里清除设置,以免出错。通过make menuconfig。如图2.11所示进入配置菜单界面。

图2.11 Linux内核配置界面

进入File systems文件系统选项,如图2.12所示,从杂项文件系统中查看是否支持cramfs文件系统(本文使用的文件系统)。

图2.12 cramfs文件系统支持

然后进入Device Drivers选项中的网络设备支持。如图2.13所示然后进入

图 2.13 网络芯片驱动支持

Ethernet(10 or 100Mbit)选项,选择需要的网络芯片的驱动,进行添加。

最后退出配置界面并且保存设置,即完成Linux内核的配置。然后在终端进入Linux内核源码的目录下,为了防止编译报错,执行make clean 清除之前生成的过程文件。然后执行make uImage,如图2.14所示生成zImage镜像文件。

图2.14 编译生成的内核镜像文件

然而,还需要使用mkimage工具去编译内核文件,可以将其放在/usr/bin文件夹中,这样可以直接编译生成uImage。

然后烧写内核文件,同之前一样,也是利用SAM-BA软件。在烧写完成AT91Bootstrap以及U-Boot后继续烧写uImage内核。但是还要注意烧写的目的地址为0xA0000。然后开始下载内核镜像文件uImage到Nand Flash中。

2.3.7 根文件系统的移植

Linux必须在硬件的一个分区上存放系统启动所必需的一些文件[7],即根文件系统,它是嵌入式Linux组成中一个特别重要的组成,它是嵌入式Linux运行里所必须的,Linux内核运行以后,会自动寻找并且挂载自己的根文件系统,然后执行根文件系统中的可执行文件或启动脚本,嵌入式Linux的应用程序在经过交叉编译后,生成的可执行文件也是需要放在根文件系统里的。

CramFS是本文所采用的根文件系统,它是一个压缩式的、十分小且简单的文件系统。

首先在用户文件夹创立一个名为cramfs的目录,并且将根文件挂载到目录下,

试验二ARM汇编语言程序设计

实验二 ARM汇编语言程序设计 一、实验目的 1.了解ARM汇编语言的基本框架,学会使用ARM的汇编语言编程 2.掌握ARM汇编指令 二、实验设备 1. EL-ARM-830教学实验箱,PentiumII以上的PC机,仿真器电缆。 2. PC操作系统WIN98或WIN2000或WINXP, ADS1.2集成开发环境,仿真器驱动程序。 三、汇编语言简介 1.ARM汇编的一些简要的书写规范 ARM汇编中,所有标号必须在一行的顶格书写,其后面不要添加“:”,而所有指令均不能顶格书写。ARM汇编对标识符的大小写敏感,书写标号及指令时字母大 小写要一致。在ARM汇编中,ARM指令、伪指令、寄存器名等可以全部大写或者全 部小写,但不要大小写混合使用。注释使用“;”号,注释的内容由“;”号起到此 行结束,注释可以在一行的顶格书写。 详细的汇编语句及规范请参照ARM汇编的相关书籍、文档。 2. ARM汇编语言程序的基本结构 在ARM汇编语言程序中,是以程序段为单位来组织代码。段是相对独立的指令或数据序列,具有特定的名称。段可以分为代码段的和数据段,代码段的内容为执 行代码,数据段存放代码运行时所需的数据。一个汇编程序至少应该有一个代码段,当程序较长时,可以分割为多个代码段和数据段,多个段在程序编译链接时最终形 成一个可执行文件。可执行映像文件通常由以下几部分构成: ◆ 一个或多个代码段,代码段为只读属性。 ◆ 零个或多个包含初始化数据的数据段,数据段的属性为可读写。 ◆ 零个或多个不包含初始化数据的数据段,数据段的属性为可读写。 链接器根据系统默认或用户设定的规则,将各个段安排在存储器中的相应位置。源程序中段之间的相邻关系与执行的映象文件中的段之间的相邻关系不一定 相同。 3. 简单的小例子 下面是一个代码段的小例子 AREA Init,CODE,READONLY ENTRY LDR R0, =0x3FF5000 LDR R1, 0x0f STR R1, [R0]

ARM汇编程序设计

cmp r0,#5 bcs aaa add r0,r0,#1 aaa nop cmp r0,#5 addcc r0,r0,#1 bl指令完成两个功能:将子程序的返回地址保存在LR即R14同时将PC的值改为目标子程序的第一条指令的地址。 Start: Mov r0,#10 Mov r1,#3 Bl doadd Mov r1,r1,r0 Doadd Add r0,r0,r1 Mov pc,lr .end 用汇编程序实现IF语句的功能: Mov r0,#15 Mov r1,#12 Cmp r0,r1

Movhi r2,#100 Movls r2,#50 用汇编程序实现FOR循环的功能:Mov r0,#0 Mov r1,#10 Mov r2,#0 L1: cmp r0,r1 Bhs l2 Add r2,r2,#1 Add r0,r0,#1 B l1 L2: .end 用汇编语言实现WHILE循环While(x<=y) X=x*2; mov r0,#1 mov r1,#20 b l2 l1: mov r0,r0, lsl #1 l2: cmp r0,r1 bls l1 end

用汇编语言实现计算算术功能:n equ 100 .global _start -start: .arm arm_code: Ldr sp,=0x40003f00 Adr r0,thumbcode+1 Bx r0 .ltorg .thumb Thumb_code: Ldr r0,=n Bl sum_n B thumb_code Sum_n: Push {r1-r7,lr} Movs r2,r0 Beq sum_end Cmp r2,#1 Beq sum_end Mov r1,#1

实验二_ARM汇编语言程序设计

实验二ARM汇编语言程序设计 实验目的 1、了解ARM汇编语言程序的结构特点 2、了解ARM汇编语言程序的编写方法 3、掌握用ARM汇编语言设计简单程序 实验仪器设备及软件 ARM实验箱,计算机,ADS程序开发软件 实验原理 1、存储空间的格式 ARM920将存储空间视为从0开始由字节组成的线性集合,字节0-3中保存了第一个字,字节4-7中保存了第二个字,依此类推。字节还可以按小端格式或大端格式排列。ARM实验箱中存储器的配置见附录C。 2、ARM的寄存器 ARM状态下任何时刻都可以看到16个通过寄存器(r0-r15),1或2个状态寄存器(CPSR,SPSR),在特权模式下会切换到具体模下的寄存器组。每个寄存器都是32位的,并且每个通用寄存器都可以作为数据处理的源数据或目标数据寄存器。因此可以编写出更精简的程序。 3、ARM指令的条件执行 状态寄存器中的N,Z,C,V是数据处理指令影响的标志。几乎每条ARM指令可以根据状态位或状态位的逻辑运算有条件执行。条件执行的指令后缀参考教材。 4、桶形移器 ARM的桶形移位器,使ARM指令的中第二个操作数非常录活。利用移位器,一条ARM 指令可以完成更多功能。移位操作有: LSL 逻辑左移 LSR 逻辑右移 ASL 算术左移 ASR 算术右移 ROR 循环右移 RRX 带扩展循环右称 实验内容 1、把内存中ramaddr开始的ramword个字清零 (1)用后变址法 ramaddr equ 0x31000000 ramword equ 64 clrram mov r0,#0 mov r1,#ramword ldr r2,=ramaddr clrram1 str r0,[r2],#4 subs r1,r1,#1

实验二A ARM汇编语言程序设计实验

实验三ARM汇编语言程序设计实验(一) 一、实验目的 1.掌握ADS1.2集成开发环境 2.了解ARM汇编指令用法,并能够编写简单的汇编程序 3.掌握指令的条件执行,掌握LDR/STR指令,完成存储器的访问 二、实验内容 1.用LDR指令读取0x40003100地址上的数据,将该数据加1,若结果大于10,则使用STR指令将结果写入原地址,否则,将把0写入原地址。 2.用ADS1.2软件仿真,单步、全速运行程序,设置断点,打开寄存器窗口(ProcessorRegister)监视R0、R1的值,打开存储器观察窗口(Memory)监视0x40003100地址处的值。 三、预备知识 1、用ARM ADS集成开发环境,编写和调试程序的基本过程。 2、ARM指令的使用 四、实验设备及工具(包括软件调试工具) 硬件:PC机Pentium100以上。 软件:PC机Windows操作系统、ARM ADS 1.2集成开发环境、AXD 五、实验步骤 1.启动ADS1.2,使用ARM Executable Image工程模板建立一个工程。如SY3 2.建立汇编源文件Test3.s,加入工程中。 3.设置工程连接地址R0 Base 0x40000000,RW Base 0x40003000。 4.编译、连接工程,选择Project Debug ,启动AXD软件仿真调试。 5.打开寄存器窗口,监视R0、R1的值,设置观察地址0x40003100,显示方式为32bit,

监测0x40003100上的值。 6.可以单步运行程序,可以设置、取消断点,或者全速运行,停止运行,调试时观察寄存器0x40003100上的值,运行结果见图3-1。 图3-1 ARM实验3的运行结果 六、实验参考程序 COUNT EQU 0X40003100 AREA TEST3, CODE,READONLY ENTRY CODE32 START LDR R1,=COUNT MOV R0,#0 STR R0,[R1] LOOP LDR R1,=COUNT LDR R0,[R1] ADD R0,R0,#1 CMP R0,#10 MOVHS R0,#0 STR R0,[R1]

arm汇编快速入门

ARM汇编语言 ARM汇编语言源程序语句,一般由指令,伪操作,宏指令和伪指令作成. ARM汇编语言的设计基础是汇编伪指令,汇编伪操作和宏指令. 伪操作,是ARM汇编语言程序里的一些特殊的指令助记符,其作用主要是为完成汇编程序做各种准备工作,在源程序运行汇编程序处理,而不是在计算机运行期间有机器执行.也就是说,这些伪操作只是汇编过程中起作用,一旦汇编结束,伪操作的使命也就随之消失. 宏指令,是一段独立的程序代码,可以插在程序中,它通过伪操作来定义,宏在被使用之前必须提前定义好,宏之间可以互相调用,也可自己递归调用.通过直接书写宏名来使用宏.并本具宏指令的格式输入输出参数.宏定义本身不产生代码,只是在调用它时把宏体插入到原程序中.宏与C语言中的子函数形参和实参的调用相似,调用宏时通过实际的指令来代替宏体实现相关的一段代码,但宏的调用与子程序的调用有本质的区别,既宏并不会节省程序的空间,其优点是简化程序代码,提高程序的可读性以及宏内容可以同步修改. 伪操作,宏指令一般与编译程序有关,因此ARM汇编语言的伪操作,宏指令在不同的编译环境下有不同的编写形式和规则. 伪指令也是ARM汇编语言程序里的特殊助记符,也不在处理器运行期间由机器执行,他们在汇编时将被合适的机器指令代替成ARM或Thumb指令,从而实现真正的指令操作. 目前常用的ARM编译环境有2种.

1. ADS/SDT IDE:ARM公司开发,使用了CodeWarrior公司的编译器. 2. 集成了GNU开发工具的IDE开发环境;它由GNU的汇编器as,交叉汇编器gcc和连接器id组成. ADS编译环境下的ARM伪操作和宏指令,可参考北航出版社的<

1冒泡排序的ARM汇编程序

1冒泡排序的ARM汇编程序ORG 09B0H QUE:MOV R3,#50H QUE1:MOV A,R3 MOV R0,A MOV R7,#0AH CLR 00H MOV A,@R0 Q12:INC R0 MOV R2,A CLR C MOV 22H,@R0 CJNE A,22H,Q13 SETB C Q13:MOV A,R2 JC Q11 SETB 00H XCH A,@R0 DEC R0 XCH A,@R0 INC R0 Q11:MOV A,@R0 DJNZ R7,Q12 JB 00H,QUE1 SJMP $ END

2 ARM汇编希尔排序法对10个带符号数进行排序Code: void shell(int src[],int l,int r){ int ih; r++; for(ih=1;ih<(r-l)/9;ih=ih*3+1); //eax,ih //ebx,il //ecx,ir //edx,cmps _asm{ push eax push ebx push ecx push edx push esi push edi;貌似这堆进栈用处不大哎 mov edi,src mov eax,dword ptr [ih] LIH: cmp eax,0 jna EXIH mov ebx,eax dec ebx LLH: cmp ebx,dword ptr [r] jnb EXLLH mov ecx,ebx mov edx,dword ptr [edi+ecx*4]

LCMP: mov esi,eax dec esi cmp ecx,esi jna EXCMP push ecx sub ecx,eax cmp edx,dword ptr [edi+ecx*4] pop ecx jnb EXCMP push ebx push ecx sub ecx,eax mov ebx,dword ptr [edi+ecx*4] pop ecx mov dword ptr [edi+ecx*4],ebx pop ebx sub ecx,eax jmp LCMP EXCMP: mov dword ptr [edi+ecx*4],edx inc ebx jmp LLH EXLLH: push ecx mov ecx,3 push edx cdq

ARM汇编语言程序设计总结

1.存储器访问指令 LDR STR LDR Load 32-bit word to Memory. Syntax LDR{cond} Rd, [Rn] LDR{cond} Rd, [Rn, offset] LDR{cond} Rd, [Rn, offset]! LDR{cond} Rd, label LDR{cond} Rd, [Rn], offset Description LDR{cond} Rd, [Rn] (zero offset) Rn is used as address value. LDR{cond} Rd, [Rn, offset] (Pre-indexed offset) Rn and offset are added and used as address value. LDR{cond} Rd, [Rn, offset]{!} (Pre-indexed offset with update) Rn and offset are added and used as address value. The new address value is written to Rn. LDR{cond} Rd, label (Program-relative) The assembler calculates the PC offset and generates LDR{cond} Rd, [R15, offset]. LDR{cond} Rd, [Rn], offset (Post-indexed offset) Rn is used as address value. After memory transfer, the offset is added to Rn. Example LDR R8,[R10] //loads r8 from the address in r10. LDRNE R2,[R5,#960]! //(conditionally) loads r2 from a word 960 bytes above the address in r5, and increments r5 by 960. LDR R0,localdata //loads a word located at label localdata STR Store register 32-bit words to Memory. The address must be 32-bit word-aligned. Syntax STR{cond} Rd, [Rn] STR{cond} Rd, [Rn, offset] STR{cond} Rd, [Rn, offset]! STR{cond} Rd, label

ARM汇编语言程序设计总结.

ARM汇编语言程序设计总结 一、常用指令 1.存储器访问指令 LDR STR LDR Load 32-bit word to Memory. Syntax LDR{cond} Rd, [Rn] LDR{cond} Rd, [Rn, offset] LDR{cond} Rd, [Rn, offset]! LDR{cond} Rd, label LDR{cond} Rd, [Rn], offset Description LDR{cond} Rd, [Rn] (zero offset) Rn is used as address value. LDR{cond} Rd, [Rn, offset] (Pre-indexed offset) Rn and offset are added and used as address value. LDR{cond} Rd, [Rn, offset]{!} (Pre-indexed offset with update) Rn and offset are added and used as address value. The new address value is written to Rn. LDR{cond} Rd, label (Program-relative) The assembler calculates the PC offset and generates LDR{cond} Rd, [R15, offset]. LDR{cond} Rd, [Rn], offset (Post-indexed offset) Rn is used as address value. After memory transfer, the offset is added to Rn. Example LDR R8,[R10] //loads r8 from the address in r10. LDRNE R2,[R5,#960]! //(conditionally) loads r2 from a word 960 bytes above the address in r5, and increments r5 by 960. LDR R0,localdata //loads a word located at label localdata STR Store register 32-bit words to Memory. The address must be 32-bit word-aligned.

ADS下简单ARM总汇编程序实验

实验一ADS下简单ARM汇编程序实验 实验目的: 1、熟悉ADS1.2下进行汇编语言程序设计的基本流程; 2、熟悉在ADS中创建工程及编写、编译和运行汇编语言程序的方法; 3、熟悉AXD中各种调试功能。 实验环境: 1、硬件:PC机。 2、软件ADS1.2。 实验容: 1、在ADS中新建工程,并设置开发环境。 2、在Code Warrior 环境中编辑、编译和汇编语言程序,并生成可执行文件。 3、在AXD中调试汇编程序; 4、使用命令行界面编辑、编译和汇编程序。 实验过程: 本实验要求在ADS环境下,编写一个汇编程序,计算S=1+2+3……+n的累加值。 把累加结果S存入到存储器的指定位置;在AXD中调试该程序,使用ARMulator模拟目标机。 1、新建工程。 打开Code Warrior,选择File->New(project)选项,使用ARM Executable Image模版新建一个工程。

2、设置编译和选项。 由于我们使用的是模拟机,设置汇编语言编译器的模拟处理器架构为Xscale;在ARM Linker中,选择output选项卡并选择Linktype为Simple类型,确认RO Base为0x8000,修改RW Base为0x9000,如下图所示。

3、为当前工程添加源程序文件。 ARM汇编程序源文件后缀名为S大小写均可。

确保添加入当前工程复选框选上。 4、编辑源程序代码。 参考程序add.s : ;armadd源程序 N EQU 7 ;累加次数;定义名为Adding的代码段 AREA Adding,CODE,READONLY ENTRY MOV R0,#0 MOV R1,#1 REPEAT ADD R0,R0,R1

相关文档
相关文档 最新文档