您的位置 首页 模拟

S3C2440-发动剖析

本文是我对bootloader中2440inits文件的一些理解,详细注释了一下,希望对大家有所帮助,下一步我准备移植一下uboot。;==================

本文是我对bootloader中2440init.s文件的一些了解,具体注释了一下,期望对咱们有所协助,下一步我预备移植一下uboot。

;=========================================
; NAME: 2440INIT.S
; DESC: C start up codes
; Configure memory, ISR ,stacks
; Initialize C-variables
; HISTORY:
; 2002.02.25:kwtark: ver 0.0
; 2002.03.20:purnnamu: Add some functions for testing STOP,Sleep mode
; 2003.03.14onGo: Modified for 2440.
;=========================================
GET option.inc ;GET相当于C语言中的include,也便是包括一个源文件到当文
GET memcfg.inc ;件中,并将被包括的文件在当时方位进行汇编。
GET 2440addr.inc
BIT_SELFREFRESH EQU (1<<22) ;EQU相当于C语言中的define,为(1<<2)界说的符号称号
re-defined constants
USERMODE EQU 0x10 ;预界说一下各种作业形式
FIQMODE EQU 0x11
IRQMODE EQU 0x12
SVCMODE EQU 0x13
ABORTMODE EQU 0x17
UNDEFMODE EQU 0x1b
MODEMASK EQU 0x1f
NOINT EQU 0xc0
;界说了一下仓库的地址我只用的开发板SDRAM中仓库的地址规模是0x33ff4800″0x33ff7fff。
;The location of stacks
UserStack EQU (_STACK_BASEADDRESS-0x3800) ;0x33ff4800 “
SVCStack EQU (_STACK_BASEADDRESS-0x2800) ;0x33ff5800 “
UndefStack EQU (_STACK_BASEADDRESS-0x2400) ;0x33ff5c00 “
AbortStack EQU (_STACK_BASEADDRESS-0x2000) ;0x33ff6000 “
IRQStack EQU (_STACK_BASEADDRESS-0x1000) ;0x33ff7000 “
FIQStack EQU (_STACK_BASEADDRESS-0x0) ;0x33ff8000 “
;ARM有两种作业状况16位的Thumb和32位的Arm,编译器有相对应的16位和32位两种编译方法。16位环境运用tasm.exe编译。[|]相当于C语言中的IF ELSE ENDIF。
;Check if tasm.exe(armasm -16 …@ADS 1.0) is used.
GBLL THUMBCODE
[ {CONFIG} = 16
THUMBCODE SETL {TRUE} ;SETL伪操作给一个大局或局部变量赋值
CODE32 ;CODE32告知咱们下面是32位的arm指令
|
THUMBCODE SETL {FALSE}
]
/*******************************************************************
下面是一个宏,用来完成子程序回来的。也便是将LR(子程序链接寄存器)的内容放入PC中。假如是THUMBCODE为真,那么bx lr。也便是跳转到lr所指向的方位履行。bx能够用来进行作业状况的切换。
*******************************************************************/
MACRO
MOV_PC_LR
[ THUMBCODE
bx lr
|
mov pc,lr
]
MEND
;与上边的相似,仅仅加了一个是否持平的判别。
MACRO
MOVEQ_PC_LR
[ THUMBCODE
bxeq lr
|
moveq pc,lr
]
MEND
/*******************************************************************
这个宏用来把HandlerLabel这个地址标号和HandleLabel这个地址标号绑定在一起。留意前面比后边多了一个r。在后边能够看到这样的指令 b HandlerUndef ;这是硬件主动发生的中止向量表,也是榜首级中止向量表。比方发生了一个ENT0中止,假如在矢量形式下,首要是跳转b HandlerIRQ,然后便是这个宏,进入HandleIRQ,但是到底是那个中止呢,在HandleIRQ这个方位,硬件会主动发生跳转到中止处理程序的指令,也便是说是哪个中止源由硬件自己判别,并将跳转指令主动送过来。假如对错矢量形式,首要跳转到b b HandlerIRQ,然后宏打开,跳转到HandleIRQ的方位,HandleIRQ里寄存的是IsrIRQ,IsrIRQ用于找到是哪一个中止源,并定位它在中止向量表中的方位。这个中止向量表在SDRAM的0x33ffff00 ” 0x33ffffff,共256个字节,一个中止向量占4个字节,即一个字,所以这个方位能够寄存64个中止源。2440只能有60个中止源。这个方位也是SDRAM最终的地址。我的SDRAM是64M,从0x30000000″0x34000000。
*******************************************************************/
MACRO
$HandlerLabel HANDLER $HandleLabel
$HandlerLabel
sub sp,sp,#4 ;decrement sp(to store jump address)
stmfd sp!,{r0} USH the work register to stack(lr does t push because it return to original address)
ldr r0,=$HandleLabel;load the address of HandleXXX to r0
ldr r0,[r0] ;load the contents(service routine start address) of HandleXXX
str r0,[sp,#4] ;store the contents(ISR) of HandleXXX to stack
ldmfd sp!,{r0,pc} OP the work register and pc(jump to ISR)
MEND
;这些符号是ADS生成的,是依据咱们填的RO,RW,ZI生成的。IMPORT伪操作是导入其他文件生命的变量
IMPORT |Image$$RO$$Base| ; Base of ROM code
IMPORT |Image$$RO$$Limit| ; End of ROM code (=start of ROM data)
IMPORT |Image$$RW$$Base| ; Base of RAM to initialise
IMPORT |Image$$ZI$$Base| ; Base and limit of area
IMPORT |Image$$ZI$$Limit| ; to zero initialise
IMPORT MMU_SetAsyncBusMode
IMPORT MMU_SetFastBusMode
IMPORT Main ; The main entry of mon program
AREA Init,CODE,READONLY
ENTRY
EXPORT __ENTRY
__ENTRY
;========
;复位
;========
ResetEntry
;1)The code, which converts to Big-endian, should be in little endian code.
;2)The following little endian code will be compiled in Big-Endian mode.
; The code byte order should be changed as the memory bus width.
;3)The pseudo instruction,DCD can t be used here because the linker generates error.
/*******************************************************************
是否进行巨细端切换。ASSERT断语过错伪操作,假如表达式为假就报错,这儿假如未界说ENDIAN_CHANGE就报错,假如ENDIAN_CHANGE为true,假如未界说ENTRY_BUS_WIDTH,就报错。依据不同的总线宽度32,16,8进行巨细段的切换。andeq r14,r7,r0,lsl #20 ,streq r0,[r0,-r10,ror #1] ,与b ChangeBigEndian的效果相同。
*******************************************************************/
ASSERT EF:ENDIAN_CHANGE
[ ENDIAN_CHANGE
ASSERT EF:ENTRY_BUS_WIDTH
[ ENTRY_BUS_WIDTH=32
b ChangeBigEndian ;DCD 0xea000007
]
[ ENTRY_BUS_WIDTH=16
andeq r14,r7,r0,lsl #20 ;DCD 0x0007ea00
]
[ ENTRY_BUS_WIDTH=8
streq r0,[r0,-r10,ror #1] ;DCD 0x070000ea
]
|
b ResetHandler
;这段是复位程序,先进行巨细段切换,然后进入复位反常处理程序
]
;这段时反常中止向量表
b HandlerUndef ;handler for Undefined mode
b HandlerSWI ;handler for SWI interrupt
b HandlerPabort ;handler for PAbort
b HandlerDabort ;handler for DAbort
b . ;reserved
b HandlerIRQ ;handler for IRQ interrupt
b HandlerFIQ ;handler for FIQ interrupt
;电源办理 EnterPWDN在后边进行了完成,主要是进入IDLE形式和SLEEP形式
;@0x20
b EnterPWDN ; Must be @0x20.
;从小端切换到大端的完成进程
ChangeBigEndian
;@0x24
[ ENTRY_BUS_WIDTH=32
DCD 0xee110f10 ;0xee110f10 => mrc p15,0,r0,c1,c0,0
DCD 0xe3800080 ;0xe3800080 => orr r0,r0,#0x80; //Big-endian
DCD 0xee010f10 ;0xee010f10 => mcr p15,0,r0,c1,c0,0
]
[ ENTRY_BUS_WIDTH=16
DCD 0x0f10ee11
DCD 0x0080e380
DCD 0x0f10ee01
]
[ ENTRY_BUS_WIDTH=8
DCD 0x100f11ee
DCD 0x800080e3
DCD 0x100f01ee
]
;相当于NOP指令,效果是等候从小端形式向大端形式切换
DCD 0xffffffff ;swinv 0xffffff is similar with NOP and run well in both endian mode.
DCD 0xffffffff
DCD 0xffffffff
DCD 0xffffffff
DCD 0xffffffff
b ResetHandler
;将HandlerLabel与HandleLabel进行相关,所谓的“加载程序”
HandlerFIQ HANDLER HandleFIQ
HandlerIRQ HANDLER HandleIRQ
HandlerUndef HANDLER HandleUndef
HandlerSWI HANDLER HandleSWI
HandlerDabort HANDLER HandleDabort
HandlerPabort HANDLER HandlePabort
/*******************************************************************
下面这段代码用于非矢量中止。INTOFFSET中止偏移寄存器。中止偏移寄存器显现了哪个IRQ中止形式的恳求在INTPND寄存器中。该位能够经过铲除SRCPND和INTPND寄存器被主动铲除。 在汇编中INTOFFSET等寄存器的姓名是指寄存器的地址,比方INTOFFSET是INTOFFSET这个寄存器的地址,所以ldr r9 = INTOFFSET,在C语言中,INTOFFSET是INTOFFSET这个寄存器的内容。
*******************************************************************/

声明:本文内容来自网络转载或用户投稿,文章版权归原作者和原出处所有。文中观点,不代表本站立场。若有侵权请联系本站删除(kf@86ic.com)https://www.86ic.net/zhishi/moni/254715.html

为您推荐

联系我们

联系我们

在线咨询: QQ交谈

邮箱: kf@86ic.com

关注微信
微信扫一扫关注我们

微信扫一扫关注我们

返回顶部