S3C2440启动代码分析
时间:11-21
来源:互联网
点击:
- ,r0,#52;EndaddressofSMRDATA
- 0
- ldrr3,[r0],#4;数据处理后R0自加4,[R0]->R3,R0+4->R0
- strr3,[r1],#4
- cmpr2,r0
- bne%B0
- ;//设置所有的memorycontrolregister,他的初始地址为BWSCON,初始化
- ;//数据在以SMRDATA为起始的存储区
- movr1,#256
- 0
- subsr1,r1,#1;1)waituntiltheSelfRefreshisreleased.
- bne%B0
- ;//1)waituntiltheSelfRefreshisreleased.
- ldrr1,=GSTATUS3;GSTATUS3hasthestartaddressjustafterSLEEPwake-up
- ldrr0,[r1]
- movpc,r0
- ;//跳出SleepMode,进入Sleep状态前的PC
- ;============================================================================================
- ;如上所说,这里采用HANDLER宏去建立Hander***和Handle***之间的联系
- LTORG;声明文字池,因为我们用了ldr伪指令
- HandlerFIQHANDLERHandleFIQ
- HandlerIRQHANDLERHandleIRQ
- HandlerUndefHANDLERHandleUndef
- HandlerSWIHANDLERHandleSWI
- HandlerDabortHANDLERHandleDabort
- HandlerPabortHANDLERHandlePabort
- ;===================================================================================
- ;呵呵,来了来了.好戏来了,这一段程序就是用来进行第二次查表的过程了.
- ;如果说第一次查表是由硬件来完成的,那这一次查表就是由软件来实现的了.
- ;为什么要查两次表??
- ;没有办法,ARM把所有的中断都归纳成一个IRQ中断异常和一个FIRQ中断异常
- ;第一次查表主要是查出是什么异常,可我们总要知道是这个中断异常中的什么中断呀!
- ;没办法了,再查一次表呗!
- ;===================================================================================
- ;//外部中断号判断,通过中断服务程序入口地址存储器的地址偏移确定
- ;//PC=[HandleEINT0+[INTOFFSET]]
- ;H|------|
- ;|///|
- ;|--isr-|====>pc
- ;L|--r8--|
- ;|--r9--|<----sp
- IsrIRQ
- subsp,sp,#4;给PC寄存器保留reservedforPC
- stmfdsp!,{r8-r9};把r8-r9压入栈
- ldrr9,=INTOFFSET;把INTOFFSET的地址装入r9INTOFFSET是一个内部的寄存器,存着中断的偏移
- ldrr9,[r9];I_ISR
- ldrr8,=HandleEINT0;这就是我们第二个中断向量表的入口的,先装入r8
- ;===================================================================================
- ;哈哈,这查表方法够好了吧,r8(入口)+index*4(别望了一条指令是4bytes的喔),
- ;这不就是我们要找的那一项了吗.找到了表项,下一步做什么?肯定先装入了!
- ;==================================================================================
- addr8,r8,r9,lsl#2;地址对齐,因为每个中断向量占4个字节,即isr=IvectTable+Offeset*4
- ldrr8,[r8];装入中断服务程序的入口
- strr8,[sp,#8];把入口也入栈,准备用旧招
- ldmfdsp!,{r8-r9,pc};施招,弹出栈,哈哈,顺便把r8弹出到PC了,跳转成功!
- LTORG
- ;==============================================================================
- ;ENTRY(好了,我们的CPU要在这复位了.)
- ;==============================================================================
- ResetHandler
- ldrr0,=WTCON;1.关看门狗
- ldrr1,=0x0;bit[5]:0-disable;1-enable(reset默认)
- strr1,[r0]
- ldrr0,=INTMSK
- ldrr1,=0xffffffff;2.关中断
- strr1,[r0]
- ldrr0,=INTSUBMSK
- ldrr1,=0x7fff;3.关子中断
- strr1,[r0]
- [{FALSE};4.得有些表示了,该点点LED灯了,不过被FALSE掉了.
- ;rGPFDAT=(rGPFDAT&~(0xf<4))|((~data&0xf)<4);
- ;Led_Display
- ldrr0,=GPFCON
- ldrr1,=0x5500
- strr1,[r0]
- ldrr0,=GPFDAT
- ldrr1,=0x10
- strr1,[r0]
- ]
- ;5.为了减少PLL的locktime,调整LOCKTIME寄存器.
- ;ToreducePLLlocktime,adjusttheLOCKTIMEregister.
- ldrr0,=LOCKTIME
- ldrr1,=0xffffff;reset的默认值
- strr1,[r0]
- ;6.下面就来设置PLL了,你的板快不快就看这了!!
- ;这里介绍一下计算公式
- ;//Fpllo=(m*Fin)/(p*2^s)
- ;//m=Mdiv+8,p=Pdiv+2,s=Sdiv
- ;TheproperrangeofPandM:1<=P<=62,1<=M<=248
- ;Fpllo必须大于200Mhz小于600Mhz
- ;Fpllo*2^s必须小于1.2GHz
- ;如下面的PLLCON设定中的M_divP_divS_div是取自option.h中
- ;#elif(MCLK==40000000)
- ;#definePLL_M(0x48)
- ;#definePLL_P(0x3)
- ;#definePLL_S(0x2)
- ;所以m=Mdiv+8=80,p=Pdiv+2=5,s=Sdiv=2
- ;硬件使用晶振为10Mhz,即Fin=10Mhz
- ;Fpllo=80*10/5*2^2=40Mhz
- [PLL_ON_START
- ;Addedforconfirmclockdivide.for2440.
- ;SettingvalueFclk:Hclk:Pclk
- ldrr0,=CLKdivN
- ldrr1,=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.option.inc中定义CLKdiv_VAL=7
- strr1,[r0];//数据表示分频数
- ;===============================================================================
- ;MMU_SetAs
S3C2440启动代 相关文章:
- 深入分析S3C2440启动代码中大小端问题(11-22)
- S3C2440启动代码中应用程序执行环境的初始化(11-22)
- S3C2440启动代码 中断分析(11-22)
- Windows CE 进程、线程和内存管理(11-09)
- RedHatLinux新手入门教程(5)(11-12)
- uClinux介绍(11-09)