×
单片机 > 单片机程序设计 > 详情

ARM裸板程序的开发和编译(以点亮LED灯为例)

发布时间:2021-12-15 发布时间:
|

制作好交叉编译工具链后,怎么确定是否有效呢,当然是编译一个程序烧写到板上跑一下了。这里我们以点亮LED灯为例描述如何使用我们制作的交叉编译工具链编译裸板程序。


首先,需要了解下Nor flash,Nand flash,片内内存,片外内存,地址空间这几个概念。其中,Nor flash是CPU可以直接通过硬件信号读取的,不需要配置,但是Norflash的写操作是需要配置和实现驱动的。片内内存不需要配置,CPU可以直接通过硬件信号读写。这是因为Nor flash和片内内存在硬件设计上就已经固化了他们的电气特性。而Nand flash的读写都必须配置,并且需要实现驱动。CPU通过相应的Nand flash控制器间接的读写数据。片外内存的读写也是需要配置的,通过内存控制器进行配置,配置好后CPU就可以发出合适的硬件信号进行直接读写。


通常,Nor flash,片内内存,片外内存是统一编址的,他们在CPU的地址空间内,而Nand flash是独立编址的。原因就是前面的描述,CPU无法直接访问Nand flash的地址。S3C2440的地址空间如下,注意,不同启动模式下,片内内存(Internal SRAM)的地址是不一样的。

这里的地址空间只是存储器的地址空间,还有CPU内部的寄存器地址空间,这些地址也是可以直接访问的,同常在高位地址。S3C2440的寄存器地址空间为0x4800000~0x5fffffff。


因为Norflash和片内内存不需要配置就可以读取,因此开发板只能从这两个地方启动。具体就是把代码烧写到Nor flash或者Nand flash处,如果在Nand flash,启动时硬件会自动拷贝代码到4KB的内部RAM。GT2440开发板nGCS0接的是Norflash。无论哪种模式启动,上电后CPU跳转到0地址处开始执行。如果在片内内存中,我们必须用4KB的代码完成Nand flash,内存控制器的初始化,并且把代码搬运到片外内存中。如果在Nor flash中,我们同样需要初始化内存控制器。由于裸板程序较小,不会超过4KB,因此我们暂时不需要做这些操作(如果在Norflash中我们可直接运行的代码量更大)。


此外,ARM处理器还有多种异常。系统上电和看门狗超时都会产生复位异常,跳转到0地址处执行。因此如果没有喂狗程序,我们必须先关闭看门狗,这是裸板程序必须实现的操作。此外,如果我们需要进入C语言代码,C语言都是由函数构成的。函数的调用需要堆栈,因此我们也要设置堆栈寄存器SP。注意SP必须指向我们当前CPU可以直接读写的内存(当前只有4KB内部RAM是可以直接读写的)。因此如果我们从Nor flash启动,在没有设置内存控制器前,我们是不能进入C代码的。这里我们将从Nand flash启动。


下面,我们开始写代码点亮LED等。GT2440的LED管脚如下:

我们在汇编代码start.s中关闭看门狗,初始化堆栈SP。


.text

.global _start

_start:

ldr r0,=0x53000000

mov r1,#0

str r1,[r0] /*关闭看门狗*/

ldr sp,=1024*4 /*不能超过内部ram,sdram还没有初始化*/

bl main

loop:

b loop


在C代码test.c中,我们点亮LED灯。注意GPIO寄存器是CPU内部寄存器,不需要配置即可直接读写。

#define GPBCON (*(volatile unsigned int *)0x56000010)

#define GPBDAT (*(volatile unsigned int *)0x56000014)

int main(int argc, char *argv[])

{

GPBCON = 1 << 10 | 1 << 12 | 1 << 14 | 1 << 16;/*设置LED管脚为输出模式*/

GPBDAT = ~(0x1 << 5); /*点亮其中两盏灯*/

return 0;

}

Makefile如下:

ARCH=arm

CC=$(ARCH)-linux-gcc

LD=$(ARCH)-linux-ld

OBJCOPY=$(ARCH)-linux-objcopy

led.bin:start.s test.c

$(CC) -g -c start.s test.c

$(LD) -Ttext 0x0 -g start.o test.o -o led_elf

#裸板程序,非操作系统环境,必须去除ELF可执行文件中的操作系统头部,转换为二进制文件

$(OBJCOPY) -O binary -S led_elf led.bin

clean:

rm -rf led.bin led_elf *.o


为了使我们制作的交叉编译工具可用,我们还需要设置环境变量。

source setenv.sh


#!/bin/sh

#指向交叉编译工具链

export PATH=${PATH}:/project/trunk/easyLinux/buildroot/ext/usr/bin

export LD_LIBRARY_PATH=/project/trunk/easyLinux/buildroot/ext/usr/lib

make, 即可得到led.bin。


把led.bin烧写到Nand flash中,设置开发板从Nand flash中启动,我们发现LED灯被成功点亮了。


『本文转载自网络,版权归原作者所有,如有侵权请联系删除』

热门文章 更多
C51 特殊功能寄存器SFR的名称和地址