新路程----海思 uboot(1)

先看start.s吧

.globl _start  //.global声明_start为全局符号,_start就会被连接器链接到,也就是链接脚本中的入口地址了。
_start: b	reset   //跳转到reset  下面的代码是设置arm的异常向量表
	ldr	pc, _undefined_instruction  //把label后的数据或者指令内容赋值给pc
	ldr	pc, _software_interrupt
	ldr	pc, _prefetch_abort
	ldr	pc, _data_abort
	ldr	pc, _not_used
	ldr	pc, _irq
	ldr	pc, _fiq
8种异常分别占用4个字节,因此每种异常入口处都填写一条跳转指令,直接跳转到相应的异常处理函数中,reset异常是直接跳转到reset函数,其他7种异常是用ldr将处理函数入口地址加载到pc中。
_undefined_instruction: .word undefined_instruction
_software_interrupt:	.word software_interrupt
_prefetch_abort:	.word prefetch_abort
_data_abort:		.word data_abort
_not_used:		.word not_used
_irq:			.word irq
_fiq:			.word fiq
_pad:			.word 0x12345678 /* now 16*4=64 */
__blank_zone_start:
.fill 1024*4,1,0
__blank_zone_end:

.globl _blank_zone_start
_blank_zone_start:
.word __blank_zone_start


.globl _blank_zone_end
_blank_zone_end:
.word __blank_zone_end

	.balignl 16,0xdeadbeef  //接下来定义的_end_vect中用.balignl来指定接下来的代码要16字节对齐,空缺的用0xdeadbeef,方便更加高效的访问内存。
接下来看第二段

	mov r0, pc, lsr#28    // pc中的内容逻辑右移28位后 再传送到 R0
	cmp r0, #8      // r0减去立即数8 并根据结果设置CPSR程序状态寄存器的标志位
	bleq    relocate

	ldr     r0, _blank_zone_start
	ldr     r1, _TEXT_BASE
	sub     r0, r0, r1      // r0=r0-r1
	adrl    r1, _start   //伪指令----中等范围的地址读取
	add     r0, r0, r1  //r0=r0+r1
	mov     r1, #0          /* flags: 0->normal 1->pm */ 清零
	bl      init_registers  //当程序无条件跳转到标号 init_registers  处执行时,同时将当前的 PC 值保存到 R14 中

	ldr	sp, =STACK_TRAINING //STACK_TRAINING 运行地址赋值为pc
#ifdef  CONFIG_SVB_ENABLE
	bl	start_svb
#endif

#ifdef CONFIG_DDR_TRAINING_V300
	ldr	r0, =REG_BASE_SCTL
	bl	start_ddr_training       /* DDR training */
#endif

#ifndef CONFIG_SKIP_RELOCATE_UBOOT
relocate:
	@copy arm exception table in 0 address
	adrl	r0, _start
	mov	r1, #0
	mov	r2, #0x100		/* copy arm Exception table to 0 addr */
	add     r2, r0, r2
copy_exception_table:
	ldmia   r0!, {r3 - r10}
//LDMIA R0!,{R1-R4}  

                               ;R1<----[R0]                                ;R2<----[R0+4]                                ;R3<----[R0+8]                                ;R4<----[R0+12]     

stmia r1!, {r3 - r10} 将R3-R9的数据存储到R1指向的地址上,R1值更新 cmp r0, r2 ble copy_exception_table @ relocate U-Boot to RAM adrl r0, _start @ r0 <- current position of code ldr r1, _TEXT_BASE @ test if we run from flash or RAM cmp r0, r1 @ don't reloc during debug

第三段

	ldr	r0, _armboot_start		@ get data regions start
	@ move past malloc pool
	sub	r0, r0, #(CONFIG_SYS_MALLOC_LEN)
	@ move past gbl and a couple
	sub	r0, r0, #(CONFIG_SYS_GBL_DATA_SIZE + 8)
						@ spots for abort stack
	str	lr, [r0]			@ save caller lr in position 0将r1寄存器的值,传送到地址值为r0的(存储器)内存中
						@ of saved stack
	mrs	r0, spsr			@ get the spsr   MRS指令用于将状态寄存器的内容读到通用寄存器中  程序状态保存寄存器 SPSR用于保存CPSR的状态
	str	lr, [r0, #4]			@ save spsr in position 1 of 
						@ saved stack
	ldr	r0, [r13]			@ restore r0
	add	r13, r13, #4			@ pop stack entry
	.endm

	.macro get_irq_stack			@ setup IRQ stack
	ldr	sp, IRQ_STACK_START
	.endm

	.macro get_fiq_stack			@ setup FIQ stack
	ldr	sp, FIQ_STACK_START
	.endm

/*
 * exception handlers
 */
	.align	5
undefined_instruction:
	get_bad_stack
	bad_save_user_regs
	bl	do_undefined_instruction

	.align	5
software_interrupt:
	get_bad_stack_swi
	bad_save_user_regs
	bl	do_software_interrupt

	.align	5
prefetch_abort:
	get_bad_stack
	bad_save_user_regs
	bl	do_prefetch_abort

	.align	5
data_abort:
	get_bad_stack
	bad_save_user_regs
	bl	do_data_abort

	.align	5
not_used:
	get_bad_stack
	bad_save_user_regs
	bl	do_not_used

#ifdef CONFIG_USE_IRQ

	.align	5
irq:
	get_irq_stack
	irq_save_user_regs
	bl	do_irq
	irq_restore_user_regs

	.align	5
fiq:
	get_fiq_stack
	/* someone ought to write a more effective fiq_save_user_regs */
	irq_save_user_regs
	bl	do_fiq
	irq_restore_user_regs

#else

	.align	5
irq:
	get_bad_stack
	bad_save_user_regs
	bl	do_irq

	.align	5
fiq:
	get_bad_stack
	bad_save_user_regs
	bl	do_fiq
其他部分参考链接http://blog.csdn.net/skyflying2012/article/details/25804209

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值