diff options
Diffstat (limited to 'arch/arm/cpu/s3c44b0/start.S')
| -rw-r--r-- | arch/arm/cpu/s3c44b0/start.S | 174 | 
1 files changed, 174 insertions, 0 deletions
| diff --git a/arch/arm/cpu/s3c44b0/start.S b/arch/arm/cpu/s3c44b0/start.S index 0063063f4..e1ab5ccb3 100644 --- a/arch/arm/cpu/s3c44b0/start.S +++ b/arch/arm/cpu/s3c44b0/start.S @@ -63,12 +63,15 @@ _start:	b       reset   *************************************************************************   */ +.globl _TEXT_BASE  _TEXT_BASE:  	.word	TEXT_BASE +#if defined(CONFIG_SYS_ARM_WITHOUT_RELOC)  .globl _armboot_start  _armboot_start:  	.word _start +#endif  /*   * These are defined in the board-specific linker script. @@ -93,7 +96,177 @@ FIQ_STACK_START:  	.word 0x0badc0de  #endif +#if !defined(CONFIG_SYS_ARM_WITHOUT_RELOC) +/* IRQ stack memory (calculated at run-time) + 8 bytes */ +.globl IRQ_STACK_START_IN +IRQ_STACK_START_IN: +	.word	0x0badc0de + +.globl _datarel_start +_datarel_start: +	.word __datarel_start + +.globl _datarelrolocal_start +_datarelrolocal_start: +	.word __datarelrolocal_start + +.globl _datarellocal_start +_datarellocal_start: +	.word __datarellocal_start + +.globl _datarelro_start +_datarelro_start: +	.word __datarelro_start + +.globl _got_start +_got_start: +	.word __got_start + +.globl _got_end +_got_end: +	.word __got_end + +/* + * the actual reset code + */ + +reset: +	/* +	 * set the cpu to SVC32 mode +	 */ +	mrs	r0,cpsr +	bic	r0,r0,#0x1f +	orr	r0,r0,#0xd3 +	msr	cpsr,r0 + +	/* +	 * we do sys-critical inits only at reboot, +	 * not when booting from ram! +	 */ +#ifndef CONFIG_SKIP_LOWLEVEL_INIT +	bl	cpu_init_crit +	/* +	 * before relocating, we have to setup RAM timing +	 * because memory timing is board-dependend, you will +	 * find a lowlevel_init.S in your board directory. +	 */ +	bl	lowlevel_init +#endif + +/* Set stackpointer in internal RAM to call board_init_f */ +call_board_init_f: +	ldr	sp, =(CONFIG_SYS_INIT_SP_ADDR) +	ldr	r0,=0x00000000 +	bl	board_init_f + +/*------------------------------------------------------------------------------*/ + +/* + * void relocate_code (addr_sp, gd, addr_moni) + * + * This "function" does not return, instead it continues in RAM + * after relocating the monitor code. + * + */ +	.globl	relocate_code +relocate_code: +	mov	r4, r0	/* save addr_sp */ +	mov	r5, r1	/* save addr of gd */ +	mov	r6, r2	/* save addr of destination */ +	mov	r7, r2	/* save addr of destination */ + +	/* Set up the stack						    */ +stack_setup: +	mov	sp, r4 + +	adr	r0, _start +	ldr	r2, _TEXT_BASE +	ldr	r3, _bss_start +	sub	r2, r3, r2		/* r2 <- size of armboot	    */ +	add	r2, r0, r2		/* r2 <- source end address	    */ +	cmp	r0, r6 +	beq	clear_bss + +#ifndef CONFIG_SKIP_RELOCATE_UBOOT +copy_loop: +	ldmia	r0!, {r9-r10}		/* copy from source address [r0]    */ +	stmia	r6!, {r9-r10}		/* copy to   target address [r1]    */ +	cmp	r0, r2			/* until source end addreee [r2]    */ +	ble	copy_loop + +#ifndef CONFIG_PRELOADER +	/* fix got entries */ +	ldr	r1, _TEXT_BASE		/* Text base */ +	mov	r0, r7			/* reloc addr */ +	ldr	r2, _got_start		/* addr in Flash */ +	ldr	r3, _got_end		/* addr in Flash */ +	sub	r3, r3, r1 +	add	r3, r3, r0 +	sub	r2, r2, r1 +	add	r2, r2, r0 + +fixloop: +	ldr	r4, [r2] +	sub	r4, r4, r1 +	add	r4, r4, r0 +	str	r4, [r2] +	add	r2, r2, #4 +	cmp	r2, r3 +	bne	fixloop +#endif +/* +	now copy to sram the interrupt vector +*/ +	adr	r0, real_vectors +	add	r2, r0, #1024 +	ldr	r1, =0x0c000000 +	add	r1, r1, #0x08 +vector_copy_loop: +	ldmia	r0!, {r3-r10} +	stmia	r1!, {r3-r10} +	cmp	r0, r2 +	ble	vector_copy_loop +#endif	/* #ifndef CONFIG_SKIP_RELOCATE_UBOOT */ + +clear_bss: +#ifndef CONFIG_PRELOADER +	ldr	r0, _bss_start +	ldr	r1, _bss_end +	ldr	r3, _TEXT_BASE		/* Text base */ +	mov	r4, r7			/* reloc addr */ +	sub	r0, r0, r3 +	add	r0, r0, r4 +	sub	r1, r1, r3 +	add	r1, r1, r4 +	mov	r2, #0x00000000		/* clear			    */ + +clbss_l:str	r2, [r0]		/* clear loop...		    */ +	add	r0, r0, #4 +	cmp	r0, r1 +	bne	clbss_l + +	bl coloured_LED_init +	bl red_LED_on +#endif + +/* + * We are done. Do not return, instead branch to second part of board + * initialization, now running from RAM. + */ +	ldr	r0, _TEXT_BASE +	ldr	r2, _board_init_r +	sub	r2, r2, r0 +	add	r2, r2, r7	/* position from board_init_r in RAM */ +	/* setup parameters for board_init_r */ +	mov	r0, r5		/* gd_t */ +	mov	r1, r7		/* dest_addr */ +	/* jump to it ... */ +	mov	lr, r2 +	mov	pc, lr + +_board_init_r: .word board_init_r +#else /* #if !defined(CONFIG_SYS_ARM_WITHOUT_RELOC) */  /*   * the actual reset code   */ @@ -169,6 +342,7 @@ stack_setup:  _start_armboot:	.word start_armboot +#endif /* #if !defined(CONFIG_SYS_ARM_WITHOUT_RELOC) */  /*   ************************************************************************* |