Chinaunix首页 | 论坛 | 博客
  • 博客访问: 391941
  • 博文数量: 80
  • 博客积分: 1982
  • 博客等级: 上尉
  • 技术积分: 1737
  • 用 户 组: 普通用户
  • 注册时间: 2012-08-26 22:41
文章存档

2013年(9)

2012年(71)

分类: LINUX

2012-10-10 13:50:44

测试平台:MINI2440  NOR:S29AL016  NAND:K9F2G08U0B  SDRAM:K4S561632N
ARM裸机程序框架:
1. 设置为管理模式
2. 关看门狗,屏蔽所有中断
3. 初始化时钟
4. 初始化内存控制器
5. 初始化NAND控制器,从NAND拷贝代码到SDRAM
6. 跳转到main函数

    2440支持两种启动方式,nor启动和nand启动。当使用nand启动时,硬件会把nand前面4K代码拷贝到2440内部SRAM中,并从SRAM开始取指令执行。因此如果代码大于4K,需要进行代码的搬运。

    下面这个例子实现从串口0输出"hello world"字符串,由于程序代码远远小于4K,所以为了简单起见,省去了步骤4和步骤5。
简要分析:
1. 设置为管理模式
.global _start
_start:
    /* set the cpu to SVC32 mode */
    mrs    r0,cpsr
    bic    r0,r0,#0x1f
    orr    r0,r0,#0xd3
    msr    cpsr,r0
2. 关看门狗,屏蔽所有中断
    /* turn off the watchdog */
#define pWTCON        0x53000000

    ldr r0, =pWTCON
    mov r1, #0x0
    str r1, [r0]

    /* mask all IRQs by setting all bits in the INTMR - default */
#define INTMSK       0x4A000008   /* Interupt-Controller base addresses */
#define INTSUBMSK    0x4A00001C

    mov    r1, #0xffffffff
    ldr    r0, =INTMSK
    str    r1, [r0]

    ldr    r1, =0x7ff
    ldr    r0, =INTSUBMSK
    str    r1, [r0]
3. 初始化时钟
#define CLKDIVN        0x4C000014    /* clock divisor register */
    /* FCLK:HCLK:PCLK = 1:4:8 */
    ldr    r0, =CLKDIVN
    mov    r1, #5
    str    r1, [r0]

    /* MMU_SetAsyncBusMode */
    mrc p15,0,r0,c1,c0,0
    orr r0,r0,#0xc0000000
    mcr p15,0,r0,c1,c0,0

#define MPLLCON        0x4C000004
#define MPLL_FCLK_405M    ((0x7f<<12) | (0x02<<4) | (0x01))

    ldr r0, =MPLLCON
    ldr r1, =MPLL_FCLK_405M
    str r1, [r0]

6. 跳转到main函数
    ldr sp, =4096
    bl     main

halt:
    b     halt

    在main函数中完成串口0的初始化和字符串的输出。上述代码都是用位置无关码写的,因此代码的链接地址可以随便指定,我在Makefile中指定为0地址。
完整代码下载
    在Linux系统下执行make,将生成的可执行二进制文件烧写到nand中,便可以从串口上看到输出。

                       ——忠于梦想 勇于实践    linux_xpj@opencores.org

阅读(1724) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~