;导出符号__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 thememory bus width.
;3)Thepseudo instruction,DCD can not be used here because the linker generates error.
;条件编译,在编译成机器码前就设定好大小端转换
;判断ENDIAN_CHANGE是否已定义,ASSERT 是断言伪指令,语法是:ASSERT + 逻辑表达式,def 是逻辑伪操作符,
;格式为::DEF:label,作用是:判断label是否定义过
ASSERT :DEF:ENDIAN_CHANGE
[ ENDIAN_CHANGE ;在 option.inc 有定义。默认是FALSE,所以此句不会加入代码中
ASSERT :DEF:ENTRY_BUS_WIDTH ;断言指令,检测是否定义该变量,若未定义,报错
[ ENTRY_BUS_WIDTH=32 ;defined in option.inc
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 ;本硬件用的是小端模式,这是第一个执行语句,
;直接跳转到复位指令处 0X00
]
;-------------------------------------------------------------------------------------------------
;这7个中断,每个中断都有固定的中断入口地址,它们位于代码的最前端,不允许另作他用
b HandlerUndef ;handler for Undefined mode 0X04
b HandlerSWI ;handlerfor SWI interrupt 0X08
b HandlerPabort ;handler for PAbort,指令预取中止 0X0C
b HandlerDabort ;handler for DAbort,数据中止 0X10
b . ;reserved 保留未用 注意小圆点 0X14
b HandlerIRQ ;handlerfor IRQ interrupt 0X18
b HandlerFIQ ;handlerfor FIQ interrupt 0X1C
;-------------------------------------------------------------------------------------------------
;@0x20
b EnterPWDN ;Must be @0x20
;------------------------------------------------------------------------------------------------
;下面是改变大小端的程序,采用直接定义 <机器码> 的方式,为什么这么做就得问三星了
;反正我们程序里这段代码也不会去执行,不用去管它
;每一个汇编指令,都对应着一个二进制机器码,这里没有使用指令,直接用了机器码,含义未知
ChangeBigEndian
;@0x24
;对存储器控制寄存器操作,指定内存模式为Big-endian
;因为刚开始CPU都是按照32位总线的指令格式运行的,如果采用其他的话,CPU运行不了,必须转化
;但当系统初始化好以后,则CPU能自动识别
[ 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
]
;因为采用Big-endian模式,采用16位总线时,物理地址的高位和数据的地位对应
;所以指令的机器码也相应的高低对调
[ ENTRY_BUS_WIDTH=16
DCD 0x0f10ee11
DCD 0x0080e380
DCD 0x0f10ee01
]
[ ENTRY_BUS_WIDTH=8
DCD 0x100f11ee
DCD 0x800080e3
DCD 0x100f01ee
]
DCD 0xffffffff ;swinv 0xffffff is similarwith NOP and run well in both endian mode.
DCD 0xffffffff
DCD 0xffffffff
DCD 0xffffffff
DCD 0xffffffff
b ResetHandler ;设置成大端后,再次跳到复位指令处
;-------------------------------------------------------------------------------------------------
;本文件底部定义了一个数据区(在文件最后),34个字空间,存放相应中断服务程序的首地址。每个字空间都
;有一个标号,以Handle***命名。
;这是宏实例,在这里Handler***就是通过HANDLER这个宏和Handle***建立联系的.