⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 start.s

📁 国产CPU-龙芯(loongson)BIOS源代码
💻 S
📖 第 1 页 / 共 3 页
字号:
/*	$Id: start.S,v 1.3 2004/05/17 10:39:22 wlin Exp $ *//* * Copyright (c) 2001 Opsycon AB  (www.opsycon.se) *  * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright *    notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright *    notice, this list of conditions and the following disclaimer in the *    documentation and/or other materials provided with the distribution. * 3. All advertising materials mentioning features or use of this software *    must display the following acknowledgement: *	This product includes software developed by Opsycon AB, Sweden. * 4. The name of the author may not be used to endorse or promote products *    derived from this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * */#ifndef _KERNEL#define _KERNEL#endif#include <asm.h>#include <regnum.h>#include <cpu.h>#include <pte.h>#include "pmon/dev/ns16550.h"#include "target/i82371eb.h"#include "target/prid.h"#include "target/sbd.h"#include "target/bonito.h"#include "target/i8254.h"#include "target/pc97307.h"#include "target/isapnpreg.h"#define DEBUG_LOCORE#undef	DEBUG_DIMM_SPD#ifdef DEBUG_LOCORE#define	TTYDBG(x) \	.rdata;98: .asciz x; .text; la a0, 98b; bal stringserial; nop#else#define TTYDBG(x)#endif#define	PRINTSTR(x) \	.rdata;98: .asciz x; .text; la a0, 98b; bal stringserial; nop#define tmpsize		s1#define msize		s2#define sdShape		s3#define bonito		s4#define dbg		s5#define sdCfg		s6#define	CFG_IB 0x00000020#define CFG_DB 0x00000010#define CFG_C_WBACK 3#define CFG_BE 0x00008000#define CFG_EPMASK 0x0f000000#define CFG_EPD 0x00000000#define CFG_EM_R4K 0x00000000#define CFG_EMMASK 0x00c00000#define CFG_AD 0x00800000/* *   Register usage: * *	s0	link versus load offset, used to relocate absolute adresses. *	s1	free *	s2	memory size. *	s3	sdShape. *	s4	Bonito base address. *	s5	dbg. *	s6	sdCfg. *	s7	rasave. *	s8	L3 Cache size. */	.set	noreorder	.globl	_start	.globl	start	.globl	__main_start:start:	.globl	stackstack = start - 0x4000		/* Place PMON stack below PMON start in RAM *//* NOTE!! Not more that 16 instructions here!!! Right now it's FULL! */	mtc0	zero, COP_0_STATUS_REG	mtc0	zero, COP_0_CAUSE_REG	li	t0, SR_BOOT_EXC_VEC	/* Exception to Boostrap Location */	mtc0	t0, COP_0_STATUS_REG	la	sp, stack	la	gp, _gp	bal	uncached		/* Switch to uncached address space */	nop	bal	locate			/* Get current execute address */	nopuncached:	or	ra, UNCACHED_MEMORY_ADDR	j	ra	nop/* *  Reboot vector usable from outside pmon. */	.align	8ext_map_and_reboot:	bal	CPU_TLBClear	nop	li	a0, 0xc0000000	li	a1, 0x40000000	bal	CPU_TLBInit	nop	la	v0, tgt_reboot	la	v1, start	subu	v0, v1	lui	v1, 0xffc0	addu	v0, v1	jr	v0	nop/* *  Exception vectors here for rom, before we are up and running. Catch *  whatever comes up before we have a fully fledged exception handler. */	.align	9			/* bfc00200 */	la	a0, v200_msg	bal	stringserial	nop	b	exc_common	.align	7			/* bfc00280 */	la	a0, v280_msg	bal	stringserial	nop	b	exc_common/* Cache error */	.align	8			/* bfc00300 */	PRINTSTR("\r\nPANIC! Unexpected Cache Error exception! ")	mfc0	a0, COP_0_CACHE_ERR	bal	hexserial	nop	b	exc_common/* General exception */	.align	7			/* bfc00380 */	la	a0, v380_msg	bal	stringserial	nop	b	exc_common		.align	8			/* bfc00400 */	la	a0, v400_msg	bal	stringserial	nop	exc_common:	PRINTSTR("\r\nERRORPC=")	mfc0	a0, COP_0_ERROR_PC	bal	hexserial	nop	PRINTSTR("\r\nEPC=")	mfc0	a0, COP_0_EXC_PC	bal	hexserial	nop	PRINTSTR("\r\nDERR0=")	cfc0	a0, COP_0_DERR_0	bal	hexserial	nop	PRINTSTR("\r\nDERR1=")	cfc0	a0, COP_0_DERR_1	bal	hexserial	nop//	b	ext_map_and_reboot	nop	.align 8		nop	.align 8	.word read	.word write	.word open	.word close	.word nullfunction	.word printf	.word vsprintf	.word nullfunction	.word nullfunction	.word getenv	.word nullfunction	.word nullfunction	.word nullfunction	.word nullfunction/* *  We get here from executing a bal to get the PC value of the current execute *  location into ra. Check to see if we run from ROM or if this is ramloaded. */locate:	la	s0,start	subu	s0,ra,s0	and	s0,0xffff0000	li	t0,SR_BOOT_EXC_VEC	mtc0	t0,COP_0_STATUS_REG        mtc0    zero,COP_0_CAUSE_REG	.set noreorder 	li	bonito,PHYS_TO_UNCACHED(BONITO_REG_BASE)#if 0locate:	la	s0, start		/* RA set from BAL above! */	subu	s0, ra, s0		/* s0 is now load vs. link offset */	and	s0, 0xffff0000		/* Mask off lower bits */	mfc0    t0,COP_0_PRID        mfc0    v0,COP_0_STATUS_REG        mtc0    zero,COP_0_WATCH_LO        mtc0    zero,COP_0_WATCH_HI        and     v0,SR_SOFT_RESET                # preserve Soft Reset        or      v0,SR_BOOT_EXC_VEC               # set Boot Exceptions        beq     t0,0x0a11,1f            # R4200 rev 1.1: disable cache errors        nop	beq     t0,0x5413,1f            # R5432 rev 1.3: disable cache errors        nop	b       2f	nop1:      or      v0,SR_DIAG_DE2:/* *  Clean out and initialize the TLB */	bal	CPU_TLBClear	nop	li	a0, 0xc0000000	li	a1, 0x40000000	bal	CPU_TLBInit	nop/* *  Turn off all high decoders to avoid address conflicts. */        mtc0    v0,COP_0_STATUS_REG        mtc0    zero,COP_0_CAUSE_REG        mfc0    t1,COP_0_CONFIG        mfc0    t2,COP_0_PRID              # get PrID        mtc0    zero,$18                # C0_IWATCH/C0_WATCHLO        mtc0    zero,$19                # C0_DWATCH/C0_WATCHHI                                                                                 	li	bonito,PHYS_TO_UNCACHED(BONITO_REG_BASE)        	srl     t2,8        and     t2,0xff        	bne     t2,PRID_R4650,2f        nop                                                                                mtc0    zero,$0                 # C0_IBASE        mtc0    zero,$1                 # C0_IBOUND        mtc0    zero,$2                 # C0_DBASE        mtc0    zero,$3                 # C0_DBOUND        b       3f	nop                                                                                2:             and     t1,~0x3f                # set bits 5..0 only        or      t1,CFG_IB | CFG_DB | CFG_C_WBACK        and     t1,~CFG_EPMASK        or      t1,CFG_EPD        bne     t2,PRID_R5400,1f        nop	and     t1,~CFG_EMMASK        or      t1,CFG_EM_R4K        b       2f	nop1:      and     t1,~CFG_AD2:      mtc0    t1,COP_0_CONFIG3:      mfc0    t1,COP_0_STATUS_REG            # get Status        mtc0    zero,COP_0_CAUSE_REG        and     t1,SR_SOFT_RESET                # leave the SoftReset bit        or      t1,SR_BOOT_EXC_VEC               # force Boot Exception Vec        mtc0    t1,COP_0_STATUS_REG#endif#define MOD_MASK	0x00000003#define MOD_B		0x00000000 /* byte "modifier" */#define MOD_H		0x00000001 /* halfword "modifier" */#define MOD_W		0x00000002 /* word "modifier" */#if __mips64#	define MOD_D		0x00000003 /* doubleword "modifier" */#endif#define OP_MASK		0x000000fc#define	OP_EXIT		0x00000000 /* exit (status) */#define OP_DELAY	0x00000008 /* delay (cycles) */#define OP_RD		0x00000010 /* read (addr) */#define OP_WR		0x00000014 /* write (addr, val) */#define OP_RMW		0x00000018 /* read-modify-write (addr, and, or) */#define OP_WAIT		0x00000020 /* wait (addr, mask, value) */#define WR_INIT(mod,addr,val) \	.word	OP_WR|mod,PHYS_TO_UNCACHED(addr);\	.word	(val),0	#define RD_INIT(mod,addr) \	.word	OP_RD|mod,PHYS_TO_UNCACHED(addr);\	.word	0,0	#define RMW_INIT(mod,addr,and,or) \	.word	OP_RMW|mod,PHYS_TO_UNCACHED(addr);\	.word	(and),(or)	#define WAIT_INIT(mod,addr,and,or) \	.word	OP_WAIT|mod,PHYS_TO_UNCACHED(addr);\	.word	(mask),(val)#define DELAY_INIT(cycles) \	.word	OP_DELAY,(cycles);\	.word	0,0	#define EXIT_INIT(status) \	.word	OP_EXIT,(status);\	.word	0,0#define BONITO_INIT(r,v) WR_INIT(MOD_W,BONITO_BASE+/**/r,v)#define BONITO_BIS(r,b) RMW_INIT(MOD_W,BONITO_BASE+(r),~0,b)#define BONITO_BIC(r,b) RMW_INIT(MOD_W,BONITO_BASE+(r),~(b),0)#define BONITO_RMW(r,c,s) RMW_INIT(MOD_W,BONITO_BASE+(r),~(c),s)	#define CFGADDR(idsel,function,reg) ((1<<(11+(idsel)))+((function)<<8)+(reg))#define _ISABWR_INIT(mod,function,isabreg,val) \	WR_INIT(MOD_W,BONITO_BASE+BONITO_PCIMAP_CFG,CFGADDR(PCI_IDSEL_I82371,function,isabreg)>>16) ; \        RD_INIT(MOD_W,BONITO_BASE+BONITO_PCIMAP_CFG) ; \	WR_INIT(mod,PCI_CFG_SPACE+(CFGADDR(PCI_IDSEL_I82371,function,isabreg)&0xffff),val)	#define _ISABRD_INIT(mod,function,isabreg) \	WR_INIT(MOD_W,BONITO_BASE+BONITO_PCIMAP_CFG,CFGADDR(PCI_IDSEL_I82371,function,isabreg)>>16) ; \        RD_INIT(MOD_W,BONITO_BASE+BONITO_PCIMAP_CFG) ; \	RD_INIT(mod,PCI_CFG_SPACE+(CFGADDR(PCI_IDSEL_I82371,function,isabreg)&0xffff))#define _ISAWR_INIT(isareg,val) \	WR_INIT(MOD_B,PCI_IO_SPACE+(isareg),val)	#define _ISARD_INIT(isareg) \	RD_INIT(MOD_B,PCI_IO_SPACE+(isareg))	#define ISABBWR_INIT(function,isabreg,val) \	_ISABWR_INIT(MOD_B,function,(isabreg),val)#define ISABHWR_INIT(function,isabreg,val) \	_ISABWR_INIT(MOD_H,function,(isabreg),val)#define ISABWWR_INIT(function,isabreg,val) \	_ISABWR_INIT(MOD_W,function,isabreg,val)#define ISAWR_INIT(isareg,val) \	_ISAWR_INIT(isareg,val)#define ISARD_INIT(isareg) \	_ISARD_INIT(isareg)	bal	1f		nop	/* bonito endianess */	BONITO_BIC(BONITO_BONPONCFG,BONITO_BONPONCFG_CPUBIGEND)	BONITO_BIC(BONITO_BONGENCFG,BONITO_BONGENCFG_BYTESWAP|BONITO_BONGENCFG_MSTRBYTESWAP)	BONITO_BIS(BONITO_BONPONCFG, BONITO_BONPONCFG_IS_ARBITER)	        /*         * In certain situations it is possible for the Bonito ASIC         * to come up with the PCI registers uninitialised, so do them here         */#define PCI_CLASS_BRIDGE		0x06#define PCI_CLASS_SHIFT			24#define PCI_SUBCLASS_BRIDGE_HOST	0x00#define PCI_SUBCLASS_SHIFT		16#define PCI_COMMAND_IO_ENABLE		0x00000001#define PCI_COMMAND_MEM_ENABLE		0x00000002#define PCI_COMMAND_MASTER_ENABLE	0x00000004#define PCI_COMMAND_STATUS_REG		0x04#define PCI_MAP_IO			0X00000001#define	PCI_DEV_I82371			17#define PCI_CFG_SPACE			BONITO_PCICFG_BASE        BONITO_INIT(BONITO_PCICLASS,(PCI_CLASS_BRIDGE << PCI_CLASS_SHIFT) | (PCI_SUBCLASS_BRIDGE_HOST << PCI_SUBCLASS_SHIFT))	BONITO_INIT(BONITO_PCICMD, BONITO_PCICMD_PERR_CLR|BONITO_PCICMD_SERR_CLR|BONITO_PCICMD_MABORT_CLR|BONITO_PCICMD_MTABORT_CLR|BONITO_PCICMD_TABORT_CLR|BONITO_PCICMD_MPERR_CLR)	BONITO_INIT(BONITO_PCILTIMER, 0)	BONITO_INIT(BONITO_PCIBASE0, 0)	BONITO_INIT(BONITO_PCIBASE1, 0)	BONITO_INIT(BONITO_PCIBASE2, 0)	BONITO_INIT(BONITO_PCIEXPRBASE, 0)	BONITO_INIT(BONITO_PCIINT, 0)	BONITO_BIS(BONITO_PCICMD, BONITO_PCICMD_PERRRESPEN)		BONITO_BIS(BONITO_PCICMD, PCI_COMMAND_IO_ENABLE|PCI_COMMAND_MEM_ENABLE|PCI_COMMAND_MASTER_ENABLE)		/* enable i/o buffer cache and other go faster bits */	BONITO_BIS(BONITO_BONGENCFG, \			BONITO_BONGENCFG_BUSERREN| \			BONITO_BONGENCFG_PREFETCHEN| \			BONITO_BONGENCFG_WBEHINDEN| \			BONITO_BONGENCFG_PCIQUEUE| \			BONITO_BONGENCFG_SNOOPEN)	       BONITO_BIC(BONITO_BONGENCFG, 0x80)  #½ûÖ¹iobc#      BONITO_BIS(BONITO_BONGENCFG, BONITO_BONGENCFG_BUSERREN)	/* Set debug mode */	BONITO_BIS(BONITO_BONGENCFG, BONITO_BONGENCFG_DEBUGMODE)	/* Turn most special purpose pins into GPIO; set ISA mode */	ISABWWR_INIT(0, I82371_GENCFG, I82371_GENCFG_CFG)		/* disable RTC & KBD chip selects */	ISABHWR_INIT(0, I82371_XBCS, 0)		/* Enable PCI 2.1 timing support */	ISABBWR_INIT(0, I82371_DLC, I82371_DLC_DT /* | I82371_DLC_PR */ | I82371_DLC_USBPR | I82371_DLC_DTTE)	/* Set top of memory to 16MB, so all ISA bus master & DMA	   accesses are forwarded to PCI mem space	 */	ISABBWR_INIT(0, I82371_TOM, I82371_TOM_TOM(16) | I82371_TOM_FWD_LBIOS | I82371_TOM_FWD_AB | I82371_TOM_FWD_89)		/* Set the SMB base address */	ISABWWR_INIT(3, I82371_PCI3_SMBBA, SMB_PORT|PCI_MAP_IO)	/* enable the host controller */	ISABBWR_INIT(3, I82371_PCI3_SMBHSTCFG, I82371_PCI3_SMB_HST_EN)	/* enable the SMB IO ports */	ISABBWR_INIT(3, PCI_COMMAND_STATUS_REG, PCI_COMMAND_IO_ENABLE)		ISABWWR_INIT(3, I82371_PCI3_PMBA, 0x8000|PCI_MAP_IO)	ISABBWR_INIT(3, I82371_PCI3_PMREGMISC, 0x01)	/* 15us ISA bus refresh clock */#define ISAREFRESH (PT_CRYSTAL/(1000000/15))	ISARD_INIT(CTC_PORT+PT_CONTROL)		/* program i8254 ISA refresh counter */	ISAWR_INIT(CTC_PORT+PT_CONTROL,PTCW_SC(PT_REFRESH)|PTCW_16B|PTCW_MODE(MODE_RG))	ISAWR_INIT(CTC_PORT+PT_REFRESH, ISAREFRESH & 0xff)	ISAWR_INIT(CTC_PORT+PT_REFRESH, ISAREFRESH >> 8)	/* program ISA ICU */	ISAWR_INIT(ICU1_PORT,  0x11) /* ICW1 */	ISAWR_INIT(ICU1_PORT+1,0x00) /* ICW2: vector */	ISAWR_INIT(ICU1_PORT+1,0x04) /* ICW3: cascade on IRQ2 */	ISAWR_INIT(ICU1_PORT+1,0x01) /* ICW4: 8086 mode */	ISAWR_INIT(ICU1_PORT+1,0xff) /* OCW1: mask all */	ISAWR_INIT(ICU2_PORT,  0x11) /* ICW1 */	ISAWR_INIT(ICU2_PORT+1,0x08) /* ICW2: vector */	ISAWR_INIT(ICU2_PORT+1,0x02) /* ICW3:  */	ISAWR_INIT(ICU2_PORT+1,0x01) /* ICW4: 8086 mode */	ISAWR_INIT(ICU2_PORT+1,0xff) /* OCW1: mask all */			ISAWR_INIT(ICU1_PORT+1,~(1<<2)) /* enable IRQ2 */        /* set up ISA devices */                /* select logical device 1 (mouse) */        ISAWR_INIT(ISAPNP_MBADDR,ISAPNP_LOGICAL_DEV_NUM)        ISAWR_INIT(ISAPNP_MBDATA,1)        ISAWR_INIT(ISAPNP_MBADDR,ISAPNP_ACTIVATE)        ISAWR_INIT(ISAPNP_MBDATA,1)                                                                                       /* select logical device 4 (parallel) */        ISAWR_INIT(ISAPNP_MBADDR,ISAPNP_LOGICAL_DEV_NUM)        ISAWR_INIT(ISAPNP_MBDATA,4)        ISAWR_INIT(ISAPNP_MBADDR,ISAPNP_IO_DESC0+ISAPNP_IO_BASE_15_8)        ISAWR_INIT(ISAPNP_MBDATA,(ECP_PORT>>8) & 0xff)        ISAWR_INIT(ISAPNP_MBADDR,ISAPNP_IO_DESC0+ISAPNP_IO_BASE_7_0)        ISAWR_INIT(ISAPNP_MBDATA,ECP_PORT & 0xff)        ISAWR_INIT(ISAPNP_MBADDR,ISAPNP_IRQ_DESC0+ISAPNP_IRQ_CONTROL)        ISAWR_INIT(ISAPNP_MBDATA,ISAPNP_IRQ_HIGH)        ISAWR_INIT(ISAPNP_MBADDR,ISAPNP_ACTIVATE)        ISAWR_INIT(ISAPNP_MBDATA,1)                                                                                       /* select logical device 5 (COM2) */        ISAWR_INIT(ISAPNP_MBADDR,ISAPNP_LOGICAL_DEV_NUM)        ISAWR_INIT(ISAPNP_MBDATA,5)        ISAWR_INIT(ISAPNP_MBADDR,ISAPNP_ACTIVATE)        ISAWR_INIT(ISAPNP_MBDATA,1)        /* select logical device 6 (COM1) */        ISAWR_INIT(ISAPNP_MBADDR,ISAPNP_LOGICAL_DEV_NUM)        ISAWR_INIT(ISAPNP_MBDATA,6)        ISAWR_INIT(ISAPNP_MBADDR,ISAPNP_ACTIVATE)        ISAWR_INIT(ISAPNP_MBDATA,1)                                                                                                                                                       	EXIT_INIT(0)#define	Init_Op	0#define	Init_A0	4#define	Init_A1	8#define	Init_A2	12#define	Init_Size	161:	move a0,rareginit:			/* local name */	lw	t3, Init_Op(a0)	lw	t0, Init_A0(a0)	and	t4,t3,OP_MASK			/* 	 * EXIT(STATUS) 	 */	bne	t4, OP_EXIT, 8f	nop	move	v0,t0	b	.done	nop		/* 	 * DELAY(CYCLES) 	 */8:	bne	t4, OP_DELAY, 8f	nop1:	bnez	t0,1b	subu	t0,1	b	.next	nop	

⌨️ 快捷键说明

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