菜鸟学习S3C2440bootloader第一话

按照gooogleman老兄的建议,从优龙2440板子的bootloader学起。首先先将程序运行起来,step执行,搞清楚每步做了什么,为什么这么做。将整体的流程学习一遍。等1个月,2个月,无论多长时间,当自己真正掌握后,再将整体的代码加上注释,做成PDF文档。分给后来者,去帮助像我现在这样水平的小小鸟。

  OK,第一话开始:

  程序入口点:

  程序最开始跳到2440init.s文件,执行如下代码:b   ResetHandler 跳转到复位异常处理程序。

ResetHandler

       ldr   r0,=WTCON       ;watch dog disable

       ldr   r1,=0x0

       str   r1,[r0]

(将看门狗定时器清零,查看datasheet,WTCON的第0位是看门狗定时器复位输出信号开关。为0,则程序关闭了S3C2440A的看门狗复位功能。)

       ldr   r0,=INTMSK

       ldr   r1,=0xffffffff  ;all interrupt disable

       str   r1,[r0]

(将中断屏蔽寄存器全部置1,将对应的中断全部关闭。)

    ldr r0,=INTSUBMSK

       ldr   r1,=0x7fff             ;all sub interrupt disable  `  

str r1,[r0]

(将子中断屏蔽寄存器全不置1,将子中断屏蔽寄存器对应的中断全部关闭。)

       ldr   r0,=LOCKTIME

       ldr   r1,=0xffffff

       str   r1,[r0]

(LOCKTIME是锁定时间计数寄存器,分别设定了UPLL 对于UCLK 的锁定时间计数值和

MPLL对于FCLK、HCLK、PCLK的锁定时间计数值。具体查看datasheet第7章时钟部分。)

    [ PLL_ON_START

       ; Added for confirm clock divide. for 2440.

       ; Setting value Fclk:Hclk:Pclk

       ldr    r0,=CLKDIVN

       ldr    r1,=CLKDIV_VAL   ; 0=1:1:1, 1=1:1:2, 2=1:2:2, 3=1:2:4, 4=1:4:4, 5=1:4:8, 6=1:3:3, 7=1:3:6.

       str   r1,[r0]

(这里先明确一下,在ADS下的bootloader代码常看到

       [

       |

       ]

他们其实就相当于c语言里面的

       Ifdef

       Else

       Endif)

(CLKDIVN是时钟分频器控制寄存器,设置的值为CLKDIV_VAL宏。我这里设置的是CLKDIV_VAL          EQU       5            ;1:4:8)

继续执行:

       [ CLKDIV_VAL>1               ; means Fclk:Hclk is not 1:1.

       mrc p15,0,r0,c1,c0,0

       orr r0,r0,#0xc0000000;R1_nF:OR:R1_iA

       mcr p15,0,r0,c1,c0,0

       |

       mrc p15,0,r0,c1,c0,0

       bic r0,r0,#0xc0000000;R1_iA:OR:R1_nF

       mcr p15,0,r0,c1,c0,0

       ]

由于我这里CLKDIV_VAL的值为5,所以执行

       mrc p15,0,r0,c1,c0,0                        <1>

       orr r0,r0,#0xc0000000;R1_nF:OR:R1_iA        <2>

       mcr p15,0,r0,c1,c0,0                                        <3>

<1> mrc是协处理器命令。用于读取协处理器中的寄存器的数据到ARM处理器的寄存器里面。这句话的意思应该是读协处理器中的寄存器数据到ARM处理器的r0里面。应该是ARM访问MMU,一般cp15就是MMU。这三条指令的目的是将MMU的30,31位置1。

       功能如下:31位(iA bit)Function:Asynchronous clock select (选择异步时钟)

                       30位(nF bit)Function: notFastBus select

未完待续。。。。


本文来自CSDN博客,转载请标明出处:http://blog.csdn.net/joyzml/archive/2009/10/16/4683610.aspx

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
非常感谢您的提问。以下是一个简单的s3c2440 bootloader的C语言代码示例: ``` #include <stdio.h> #include <stdlib.h> #include <string.h> #define BOOTLOADER_SIZE 0x8000 #define KERNEL_LOAD_ADDRESS 0x30008000 int main(int argc, char **argv) { FILE *bootloader_file, *kernel_file; unsigned char *bootloader, *kernel; int bootloader_size, kernel_size; // Open bootloader file bootloader_file = fopen("bootloader.bin", "rb"); if (!bootloader_file) { printf("Error: Could not open bootloader file\n"); return 1; } // Read bootloader into memory fseek(bootloader_file, 0, SEEK_END); bootloader_size = ftell(bootloader_file); fseek(bootloader_file, 0, SEEK_SET); bootloader = (unsigned char *) malloc(bootloader_size); fread(bootloader, 1, bootloader_size, bootloader_file); fclose(bootloader_file); // Open kernel file kernel_file = fopen("kernel.bin", "rb"); if (!kernel_file) { printf("Error: Could not open kernel file\n"); return 1; } // Read kernel into memory fseek(kernel_file, 0, SEEK_END); kernel_size = ftell(kernel_file); fseek(kernel_file, 0, SEEK_SET); kernel = (unsigned char *) malloc(kernel_size); fread(kernel, 1, kernel_size, kernel_file); fclose(kernel_file); // Copy bootloader to memory memcpy((void *) 0, bootloader, bootloader_size); // Copy kernel to memory memcpy((void *) KERNEL_LOAD_ADDRESS, kernel, kernel_size); // Jump to kernel void (*kernel_entry)(void) = (void (*)(void)) KERNEL_LOAD_ADDRESS; kernel_entry(); return 0; } ``` 这个示例代码可以读取一个名为"bootloader.bin"的文件和一个名为"kernel.bin"的文件,将它们分别加载到内存的0地址和0x30008000地址处,然后跳转到0x30008000地址开始执行内核代码。 希望这个示例代码对您有所帮助。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值