ARM11学习笔记(一)

来源:互联网 发布:淘宝买家秀裸露店铺 编辑:程序博客网 时间:2024/05/17 15:01

学习ARM11裸机开发已经一个月了,从最开始的迷茫,毫无头绪,一步一步地走过来,总算有点收获吧。再深刻的记忆总是敌不过时间的侵蚀,因此有必要把这段时间来的心得体会记录下来,供以后的自己参考。

(1)      ARM的软件结构

为理解ARM程序的运行流程,得先知道程序在ARM中是怎么放置的。

一个程序包含很多源文件,而每个源文件都有三个输入段组成:代码段(CODE,RO),初始化的变量段(DATA,RW)和未初始化的变量段(BSS,ZI)。所有源文件中的相同的输入段组成一个域的输出段,所以一个域也是包含三个输出段:RO,RW,ZI。此外,程序在内存中的存放还涉及两个概念:装载域和执行域。装载域是指将程序(bin文件)下载到ARM板子上时存放的位置,此时RW段是存放在RO段后面连续的空间内,还没有ZI段。执行域是程序执行时各个段的位置。这就引出,怎样设定执行域呢?

如果是用ADS1.2(不支持ARM11内核~~)或RVDS2.2编写编译程序的话,在ARM Linker设置一栏可以设置RO_BASE,RW_BASE的值(LinkerType选择Simple)。RO_BASE,RW_BASE就分别是程序的RO段和RW段存放的起始位置,ZI段接着RW段后存放。用这种方式指定执行域的话,会产生几个重要的编译器常量(看名字就知道是什么意思了):Image$$RO$$Base,Image$$RO$$Limit,Image$$RW$$Base,Image$$ZI$$Base,Image$$ZI$$Limit。这几个变量在将程序从装载域搬到执行域的时候需要用到。

还有一种方式就是选择LinkerType为Scattered,然后在Scatter中指定Scatter文件。这种方式可以完成非常复杂的程序映射。例如,可以指定某个文件的某个段放在某个地方。Scatter文件同样可以产生一些编译器常量,Image$$Region_Name$$Base,Image$$ Region_Name$$Limit。其中的Region_Name就是在Scatter文件中定义的执行域的名称了。用这种方式的话,一般将主函数写为main(),即可调用C库函数自动完成程序的搬移和堆栈的初始化(这里有个问题是,某些库函数需要改写,以后再说)。

(2)      ARM汇编与C编程

这部分只要随便找本教材看看就行。

(3)      我的第一个裸机程序

了解了一些基本知识后就可以写最简单的裸机程序啦——点亮led灯。

查看板子的电路图看led灯是与哪个GPIO口相连,以及高低电平。


现在只要通过设置M端口的三个寄存器GPMCON,GPMDAT,GPMPUD就可以实现led1,led2流水灯啦。程序源码如下:

GPIO_BASE                EQU         0x7F008000

GPMCON                   EQU                    0x7F008820

GPMDAT                    EQU                    0x7F008824

GPMPUD                    EQU                    0x7F008828

 

MACRO

         SETGP       $RegName,$SetBit,$SetValue

         ldr    r2,=$RegName

         ldr    r3,[r2]

         bic    r3,$SetBit

         orr    r3,$SetValue

         str    r3,[r2]

         MEND

        

         AREA        Init,CODE,READONLY

         ENTRY

        

         ;Init the GPM0,1

         SETGP       GPMCON,#0xff,#0x11;设置GPM0,GPM1为输出端口

         SETGP       GPMPUD,#0xf,#0x0;Disablepull up/down

         SETGP       GPMDAT,#0x3,#0x0;初始电平为0,即不点亮led灯

 

ledflow

         SETGP       GPMDAT,#0x3,#0x1;01,led1亮

         bl delay

         SETGP       GPMDAT,#0x3,#0x2;10,led2亮

         bl delay

         b       ledflow

        

delay         ldr r0,=0x186A0

                   mov r1,#0

loop

                   add  r1,r1,#1

                   cmp r0,r1

                   bne  loop

                   mov pc,lr

         LTORG

        

         END

设置一下:Assemble和Compile项都设置为ARM1176JZF-S;Linker项LinkerType选Simple,RO_BASE设为0x50000000(SDRAM);FromELF项Outputformat设为Plain Binary,输出文件名设为ledtest.bin。make一下,bin文件生成。下载到板子中去…

第一个裸跑程序完成啦~
原创粉丝点击