start.s

来自「U-boot源码 ARM7启动代码」· S 代码 · 共 1,074 行 · 第 1/2 页

S
1,074
字号
/* * Copyright 2004, 2007 Freescale Semiconductor. * Copyright (C) 2003  Motorola,Inc. * * See file CREDITS for list of people who contributed to this * project. * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation; either version 2 of * the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.	 See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, * MA 02111-1307 USA *//* U-Boot Startup Code for Motorola 85xx PowerPC based Embedded Boards * * The processor starts at 0xfffffffc and the code is first executed in the * last 4K page(0xfffff000-0xffffffff) in flash/rom. * */#include <config.h>#include <mpc85xx.h>#include <version.h>#define _LINUX_CONFIG_H 1	/* avoid reading Linux autoconf.h file	*/#include <ppc_asm.tmpl>#include <ppc_defs.h>#include <asm/cache.h>#include <asm/mmu.h>#ifndef	 CONFIG_IDENT_STRING#define	 CONFIG_IDENT_STRING ""#endif#undef	MSR_KERNEL#define MSR_KERNEL ( MSR_ME )	/* Machine Check *//* * Set up GOT: Global Offset Table * * Use r14 to access the GOT */	START_GOT	GOT_ENTRY(_GOT2_TABLE_)	GOT_ENTRY(_FIXUP_TABLE_)	GOT_ENTRY(_start)	GOT_ENTRY(_start_of_vectors)	GOT_ENTRY(_end_of_vectors)	GOT_ENTRY(transfer_to_handler)	GOT_ENTRY(__init_end)	GOT_ENTRY(_end)	GOT_ENTRY(__bss_start)	END_GOT/* * e500 Startup -- after reset only the last 4KB of the effective * address space is mapped in the MMU L2 TLB1 Entry0. The .bootpg * section is located at THIS LAST page and basically does three * things: clear some registers, set up exception tables and * add more TLB entries for 'larger spaces'(e.g. the boot rom) to * continue the boot procedure. * Once the boot rom is mapped by TLB entries we can proceed * with normal startup. * */	.section .bootpg,"ax"	.globl _start_e500_start_e500:/* clear registers/arrays not reset by hardware */	/* L1 */	li	r0,2	mtspr	L1CSR0,r0	/* invalidate d-cache */	mtspr	L1CSR1,r0 	/* invalidate i-cache */	mfspr	r1,DBSR	mtspr	DBSR,r1		/* Clear all valid bits */	/*	 *	Enable L1 Caches early	 *	 */	lis	r2,L1CSR0_CPE@H	/* enable parity */	ori	r2,r2,L1CSR0_DCE	mtspr	L1CSR0,r2	/* enable L1 Dcache */	isync	mtspr	L1CSR1,r2	/* enable L1 Icache */	isync	msync	/* Setup interrupt vectors */	lis	r1,TEXT_BASE@h	mtspr	IVPR,r1	li	r1,0x0100	mtspr	IVOR0,r1	/* 0: Critical input */	li	r1,0x0200	mtspr	IVOR1,r1	/* 1: Machine check */	li	r1,0x0300	mtspr	IVOR2,r1	/* 2: Data storage */	li	r1,0x0400	mtspr	IVOR3,r1	/* 3: Instruction storage */	li	r1,0x0500	mtspr	IVOR4,r1	/* 4: External interrupt */	li	r1,0x0600	mtspr	IVOR5,r1	/* 5: Alignment */	li	r1,0x0700	mtspr	IVOR6,r1	/* 6: Program check */	li	r1,0x0800	mtspr	IVOR7,r1	/* 7: floating point unavailable */	li	r1,0x0900	mtspr	IVOR8,r1	/* 8: System call */	/* 9: Auxiliary processor unavailable(unsupported) */	li	r1,0x0a00	mtspr	IVOR10,r1	/* 10: Decrementer */	li	r1,0x0b00	mtspr	IVOR11,r1	/* 11: Interval timer */	li	r1,0x0c00	mtspr	IVOR12,r1	/* 12: Watchdog timer */	li	r1,0x0d00	mtspr	IVOR13,r1	/* 13: Data TLB error */	li	r1,0x0e00	mtspr	IVOR14,r1	/* 14: Instruction TLB error */	li	r1,0x0f00	mtspr	IVOR15,r1	/* 15: Debug */	/*	 * After reset, CCSRBAR is located at CFG_CCSRBAR_DEFAULT, i.e.	 * 0xff700000-0xff800000. We need add a TLB1 entry for this 1MB	 * region before we can access any CCSR registers such as L2	 * registers, Local Access Registers,etc. We will also re-allocate	 * CFG_CCSRBAR_DEFAULT to CFG_CCSRBAR immediately after TLB1 setup.	 *	 * Please refer to board-specif directory for TLB1 entry configuration.	 * (e.g. board/<yourboard>/init.S)	 *	 */	bl	tlb1_entry	mr	r5,r0	lwzu	r4,0(r5)	/* how many TLB1 entries we actually use */	mtctr	r40:	lwzu	r6,4(r5)	lwzu	r7,4(r5)	lwzu	r8,4(r5)	lwzu	r9,4(r5)	mtspr	MAS0,r6	mtspr	MAS1,r7	mtspr	MAS2,r8	mtspr	MAS3,r9	isync	msync	tlbwe	isync	bdnz	0b1:#if (CFG_CCSRBAR_DEFAULT != CFG_CCSRBAR)	/* Special sequence needed to update CCSRBAR itself */	lis	r4,CFG_CCSRBAR_DEFAULT@h	ori	r4,r4,CFG_CCSRBAR_DEFAULT@l	lis	r5,CFG_CCSRBAR@h	ori	r5,r5,CFG_CCSRBAR@l	srwi	r6,r5,12	stw	r6,0(r4)	isync	lis	r5,0xffff	ori	r5,r5,0xf000	lwz	r5,0(r5)	isync	lis	r3,CFG_CCSRBAR@h	lwz	r5,CFG_CCSRBAR@l(r3)	isync#endif	/* set up local access windows, defined at board/<boardname>/init.S */	lis	r7,CFG_CCSRBAR@h	ori	r7,r7,CFG_CCSRBAR@l	bl	law_entry	mr	r6,r0	lwzu	r5,0(r6)	/* how many windows we actually use */	mtctr	r5	li	r2,0x0c28	/* the first pair is reserved for */	li	r1,0x0c30	/* boot-over-rio-or-pci */0:	lwzu	r4,4(r6)	lwzu	r3,4(r6)	stwx	r4,r7,r2	stwx	r3,r7,r1	addi	r2,r2,0x0020	addi	r1,r1,0x0020	bdnz	0b	/* Clear and set up some registers. */	li      r0,0	mtmsr   r0	li	r0,0x0000	lis	r1,0xffff	mtspr	DEC,r0			/* prevent dec exceptions */	mttbl	r0			/* prevent fit & wdt exceptions */	mttbu	r0	mtspr	TSR,r1			/* clear all timer exception status */	mtspr	TCR,r0			/* disable all */	mtspr	ESR,r0			/* clear exception syndrome register */	mtspr	MCSR,r0			/* machine check syndrome register */	mtxer	r0			/* clear integer exception register */	lis	r1,0x0002		/* set CE bit (Critical Exceptions) */	ori	r1,r1,0x1200		/* set ME/DE bit */	mtmsr	r1			/* change MSR */	isync	/* Enable Time Base and Select Time Base Clock */	lis	r0,HID0_EMCP@h		/* Enable machine check */#if defined(CONFIG_ENABLE_36BIT_PHYS)	ori	r0,r0,(HID0_TBEN|HID0_ENMAS7)@l	/* Enable Timebase & MAS7 */#else	ori	r0,r0,HID0_TBEN@l	/* enable Timebase */#endif	mtspr	HID0,r0	li	r0,(HID1_ASTME|HID1_ABE)@l	/* Addr streaming & broadcast */	mtspr	HID1,r0	/* Enable Branch Prediction */#if defined(CONFIG_BTB)	li	r0,0x201		/* BBFI = 1, BPEN = 1 */	mtspr	BUCSR,r0#endif#if defined(CFG_INIT_DBCR)	lis	r1,0xffff	ori	r1,r1,0xffff	mtspr	DBSR,r1			/* Clear all status bits */	lis	r0,CFG_INIT_DBCR@h	/* DBCR0[IDM] must be set */	ori	r0,r0,CFG_INIT_DBCR@l	mtspr	DBCR0,r0#endif/* L1 DCache is used for initial RAM */	/* Allocate Initial RAM in data cache.	 */	lis	r3,CFG_INIT_RAM_ADDR@h	ori	r3,r3,CFG_INIT_RAM_ADDR@l	li	r2,(CFG_DCACHE_SIZE / (2 * CFG_CACHELINE_SIZE))	mtctr	r2	li	r0,01:	dcbz	r0,r3	dcbtls	0,r0,r3	addi	r3,r3,CFG_CACHELINE_SIZE	bdnz	1b	/* Jump out the last 4K page and continue to 'normal' start */#ifdef CFG_RAMBOOT	b	_start_cont#else	/* Calculate absolute address in FLASH and jump there		*/	/*--------------------------------------------------------------*/	lis	r3,CFG_MONITOR_BASE@h	ori	r3,r3,CFG_MONITOR_BASE@l	addi	r3,r3,_start_cont - _start + _START_OFFSET	mtlr	r3	blr#endif	.text	.globl	_start_start:	.long	0x27051956		/* U-BOOT Magic Number */	.globl	version_stringversion_string:	.ascii U_BOOT_VERSION	.ascii " (", __DATE__, " - ", __TIME__, ")"	.ascii CONFIG_IDENT_STRING, "\0"	.align	4	.globl	_start_cont_start_cont:	/* Setup the stack in initial RAM,could be L2-as-SRAM or L1 dcache*/	lis	r1,CFG_INIT_RAM_ADDR@h	ori	r1,r1,CFG_INIT_SP_OFFSET@l	li	r0,0	stwu	r0,-4(r1)	stwu	r0,-4(r1)		/* Terminate call chain */	stwu	r1,-8(r1)		/* Save back chain and move SP */	lis	r0,RESET_VECTOR@h	/* Address of reset vector */	ori	r0,r0,RESET_VECTOR@l	stwu	r1,-8(r1)		/* Save back chain and move SP */	stw	r0,+12(r1)		/* Save return addr (underflow vect) */	GET_GOT	bl	cpu_init_f	bl	board_init_f	isync	. = EXC_OFF_SYS_RESET	.globl	_start_of_vectors_start_of_vectors:/* Critical input. */	CRIT_EXCEPTION(0x0100, CriticalInput, CritcalInputException)/* Machine check */	MCK_EXCEPTION(0x200, MachineCheck, MachineCheckException)/* Data Storage exception. */	STD_EXCEPTION(0x0300, DataStorage, UnknownException)/* Instruction Storage exception. */	STD_EXCEPTION(0x0400, InstStorage, UnknownException)/* External Interrupt exception. */	STD_EXCEPTION(0x0500, ExtInterrupt, ExtIntException)/* Alignment exception. */	. = 0x0600Alignment:	EXCEPTION_PROLOG(SRR0, SRR1)	mfspr	r4,DAR	stw	r4,_DAR(r21)	mfspr	r5,DSISR	stw	r5,_DSISR(r21)	addi	r3,r1,STACK_FRAME_OVERHEAD	li	r20,MSR_KERNEL	rlwimi	r20,r23,0,16,16		/* copy EE bit from saved MSR */	lwz	r6,GOT(transfer_to_handler)	mtlr	r6	blrl.L_Alignment:	.long	AlignmentException - _start + _START_OFFSET	.long	int_return - _start + _START_OFFSET/* Program check exception */	. = 0x0700ProgramCheck:	EXCEPTION_PROLOG(SRR0, SRR1)	addi	r3,r1,STACK_FRAME_OVERHEAD	li	r20,MSR_KERNEL	rlwimi	r20,r23,0,16,16		/* copy EE bit from saved MSR */	lwz	r6,GOT(transfer_to_handler)	mtlr	r6	blrl.L_ProgramCheck:	.long	ProgramCheckException - _start + _START_OFFSET	.long	int_return - _start + _START_OFFSET	/* No FPU on MPC85xx.  This exception is not supposed to happen.	*/	STD_EXCEPTION(0x0800, FPUnavailable, UnknownException)	. = 0x0900/* * r0 - SYSCALL number * r3-... arguments */SystemCall:	addis	r11,r0,0	/* get functions table addr */	ori	r11,r11,0	/* Note: this code is patched in trap_init */	addis	r12,r0,0	/* get number of functions */	ori	r12,r12,0	cmplw	0,r0,r12	bge	1f	rlwinm	r0,r0,2,0,31	/* fn_addr = fn_tbl[r0] */	add	r11,r11,r0	lwz	r11,0(r11)	li	r20,0xd00-4	/* Get stack pointer */	lwz	r12,0(r20)	subi	r12,r12,12	/* Adjust stack pointer */	li	r0,0xc00+_end_back-SystemCall	cmplw	0,r0,r12	/* Check stack overflow */	bgt	1f	stw	r12,0(r20)	mflr	r0	stw	r0,0(r12)	mfspr	r0,SRR0	stw	r0,4(r12)	mfspr	r0,SRR1	stw	r0,8(r12)	li	r12,0xc00+_back-SystemCall	mtlr	r12	mtspr	SRR0,r111:	SYNC	rfi_back:	mfmsr	r11			/* Disable interrupts */	li	r12,0	ori	r12,r12,MSR_EE	andc	r11,r11,r12	SYNC				/* Some chip revs need this... */	mtmsr	r11	SYNC	li	r12,0xd00-4		/* restore regs */	lwz	r12,0(r12)	lwz	r11,0(r12)	mtlr	r11	lwz	r11,4(r12)	mtspr	SRR0,r11	lwz	r11,8(r12)	mtspr	SRR1,r11	addi	r12,r12,12		/* Adjust stack pointer */	li	r20,0xd00-4	stw	r12,0(r20)	SYNC	rfi_end_back:	STD_EXCEPTION(0x0a00, Decrementer, timer_interrupt)	STD_EXCEPTION(0x0b00, IntervalTimer, UnknownException)	STD_EXCEPTION(0x0c00, WatchdogTimer, UnknownException)	STD_EXCEPTION(0x0d00, DataTLBError, UnknownException)	STD_EXCEPTION(0x0e00, InstructionTLBError, UnknownException)	CRIT_EXCEPTION(0x0f00, DebugBreakpoint, DebugException )	.globl	_end_of_vectors_end_of_vectors:	. = . + (0x100 - ( . & 0xff ))	/* align for debug *//* * This code finishes saving the registers to the exception frame * and jumps to the appropriate handler for the exception. * Register r21 is pointer into trap frame, r1 has new stack pointer. */	.globl	transfer_to_handlertransfer_to_handler:	stw	r22,_NIP(r21)	lis	r22,MSR_POW@h	andc	r23,r23,r22	stw	r23,_MSR(r21)	SAVE_GPR(7, r21)	SAVE_4GPRS(8, r21)	SAVE_8GPRS(12, r21)	SAVE_8GPRS(24, r21)	mflr	r23	andi.	r24,r23,0x3f00		/* get vector offset */	stw	r24,TRAP(r21)	li	r22,0	stw	r22,RESULT(r21)	mtspr	SPRG2,r22		/* r1 is now kernel sp */	lwz	r24,0(r23)		/* virtual address of handler */	lwz	r23,4(r23)		/* where to go when done */	mtspr	SRR0,r24	mtspr	SRR1,r20	mtlr	r23	SYNC	rfi				/* jump to handler, enable MMU */int_return:	mfmsr	r28		/* Disable interrupts */	li	r4,0	ori	r4,r4,MSR_EE	andc	r28,r28,r4	SYNC			/* Some chip revs need this... */	mtmsr	r28	SYNC	lwz	r2,_CTR(r1)	lwz	r0,_LINK(r1)	mtctr	r2	mtlr	r0	lwz	r2,_XER(r1)	lwz	r0,_CCR(r1)	mtspr	XER,r2	mtcrf	0xFF,r0	REST_10GPRS(3, r1)	REST_10GPRS(13, r1)	REST_8GPRS(23, r1)	REST_GPR(31, r1)	lwz	r2,_NIP(r1)	/* Restore environment */	lwz	r0,_MSR(r1)	mtspr	SRR0,r2	mtspr	SRR1,r0	lwz	r0,GPR0(r1)	lwz	r2,GPR2(r1)	lwz	r1,GPR1(r1)	SYNC	rficrit_return:	mfmsr	r28		/* Disable interrupts */	li	r4,0	ori	r4,r4,MSR_EE	andc	r28,r28,r4	SYNC			/* Some chip revs need this... */	mtmsr	r28	SYNC	lwz	r2,_CTR(r1)	lwz	r0,_LINK(r1)	mtctr	r2	mtlr	r0	lwz	r2,_XER(r1)	lwz	r0,_CCR(r1)	mtspr	XER,r2

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?