romInit.s
资源名称:idt438.rar [点击查看]
上传用户:yingyi0918
上传日期:2022-06-26
资源大小:214k
文件大小:17k
源码类别:
VxWorks
开发平台:
C/C++
- /* romInit.s - IDT 79PMC438 ROM initialization module */
- /* Copyright 1984-2002 Wind River Systems, Inc. */
- #include "copyright_wrs.h"
- /*
- * This file has been developed or significantly modified by the
- * MIPS Center of Excellence Dedicated Engineering Staff.
- * This notice is as per the MIPS Center of Excellence Master Partner
- * Agreement, do not remove this notice without checking first with
- * WR/Platforms MIPS Center of Excellence engineering management.
- */
- .data
- .globl copyright_wind_river
- /*
- modification history
- --------------------
- 01a,19Oct02,krao New Code from IDT for IDT79PMC438 Board.
- */
- /*
- DESCRIPTION
- This module contains the entry code for the VxWorks bootrom.
- The entry point romInit, is the first code executed on power-up.
- The routine sysToMonitor() jumps to romInit() to perform a
- "warm boot".
- */
- /*includes */
- #define _ASMLANGUAGE
- #include "vxWorks.h"
- #include "arch/mips/ivMips.h"
- #include "arch/mips/asmMips.h"
- #include "arch/mips/esfMips.h"
- #include "sysLib.h"
- #include "config.h"
- /* defines */
- #define ROM_ISP_BASE 0xa0100000 /* ROM exception save area */
- /* externals */
- .extern cache4kcReset
- /* locals */
- /* source file includes */
- #include "romMipsInit.s" /* MIPS common startup code */
- /*****************************************************************************
- *
- * sysMemInit - Initialize memory and chip selects.
- *
- * This function performs low-level memory chip select and controller
- * initialization. It is called by romMipsInit.s/romReboot very
- * early in the ROM boot sequence.
- *
- * RETURNS: N/A
- *
- * void sysMemInit (void)
- *
- */
- .ent sysMemInit
- sysMemInit:
- /* Disable WatchDog Timer */
- li t1, DISABLE_TIMER
- li t0, WTC_CTL_REG
- sw t1, 0(t0)
- nop
- li t0, ERR_CNTL_STATUS
- lw t1, 0(t0)
- li t2, ERR_CNTL_VALUE
- and t1, t2
- sw t1, 0(t0)
- /* Reduce Bus Timeout Count */
- li t1, TIMEOUT_COUNT
- li t0, BT_TIMER_COMPARE
- sw t1, 0(t0)
- /* Program The GPIO Registers */
- li t1, GPIO_DATA_REG
- sw zero, 0(t1)
- li t1, GPIO_INT_LVL
- sw zero, 0(t1)
- /*Initialize CS0 - either EPROM or flash */
- li t0, DEV_CTL_BASE
- li t1, MCR_CS0_BS
- sw t1, DEV0BASE_OFF(t0)
- li t1, MCR_CS0_MASK
- sw t1, DEV0MASK_OFF(t0)
- li t1, MCR_CS0_CTRL
- sw t1, DEV0C_OFF(t0)
- li t1, MCR_CS0_TC
- sw t1, DEV0TC_OFF(t0)
- /*Initialize CS1 - either flash or EPROM */
- li t0, DEV_CTL_BASE
- li t1, MCR_CS1_BS
- sw t1, DEV1BASE_OFF(t0)
- li t1, MCR_CS1_MASK
- sw t1, DEV1MASK_OFF(t0)
- li t1, MCR_CS1_CTRL
- sw t1, DEV1C_OFF(t0)
- li t1, MCR_CS1_TC
- sw t1, DEV1TC_OFF(t0)
- /* Initialize CS2 - 8 bit port */
- li t0, DEV_CTL_BASE
- li t1, MCR_CS2_BS
- sw t1, DEV2BASE_OFF(t0)
- li t1, MCR_CS2_MASK
- sw t1, DEV2MASK_OFF(t0)
- li t1, MCR_CS2_CTRL
- sw t1, DEV2C_OFF(t0)
- li t1, MCR_CS2_TC
- sw t1, DEV2TC_OFF(t0)
- /* Initialize CS3 - 16 bit port */
- li t0, DEV_CTL_BASE
- li t1, MCR_CS3_BS
- sw t1, DEV3BASE_OFF(t0)
- li t1, MCR_CS3_MASK
- sw t1, DEV3MASK_OFF(t0)
- li t1, MCR_CS3_CTRL
- sw t1, DEV3C_OFF(t0)
- li t1, MCR_CS3_TC
- sw t1, DEV3TC_OFF(t0)
- /* GPIO Controller setting */
- li t0, PIO_FUNCSEL_REG
- li t1, PIO_FUNCSEL_VAL
- sw t1, 0x0(t0)
- /* DDR Initialization starts here */
- li t0, DDRD_LLC_REG /* Hidden register in RC32438 */
- li t1, DDRD_LLC_VAL
- sw t1, 0x0(t0)
- li t1, 0x0 /* Add 200 microseconds of delay */
- li t2, DELAY_200USEC
- 1:
- add t1, 1
- bne t1, t2, 1b
- nop
- /* Load the DDR Controller Base Address */
- li t0, DDR_BASE
- li t1, DDRC_VAL_AT_INIT /*load DDRC reset refresh enable */
- sw t1, 0x10(t0)
- sw zero, 4(t0)
- sw zero, 0xc(t0)
- sw zero, 0x18(t0)
- /* Store DDR0BASE */
- li t1, DDR0_BASE_VAL
- sw t1, 0x0(t0)
- /* Store DDR0MASK */
- li t1, DDR0_MASK_VAL
- sw t1, 0x4(t0)
- /* Load DDR1MASK to disable CS1 */
- li t1, DDR1_BASE_VAL
- sw t1, 0x08(t0)
- li t1, DDR1_MASK_VAL
- sw t1, 0x0C(t0)
- /* Load DDR0AMASK to disable alternate Mapping */
- li t1, DDR0_BASE_VAL
- sw t1, 0x14(t0)
- li t1, DDR0_AMASK_VAL
- sw t1, 0x18(t0)
- li t1, DDR_CUST_NOP
- sw t1, 0x20(t0)
- li t2, DATA_PATTERN
- li t1, 0xA0000000 | DDR0_BASE_VAL
- sw t2, 0x0(t1)
- li t1, 0x0
- li t2, DELAY_200USEC
- 1:
- add t1, 1
- bne t1, t2, 1b
- nop
- /* Register t0 carries pointer to the DDR_BASE: 0xB8018000 */
- li t1, DDR_CUST_PRECHARGE
- sw t1, 0x20(t0) /* Write to DDR Custom transaction register */
- /* Generate A10 high to pre-charge both the banks */
- li t2, DATA_PATTERN
- li t1, 0xA0001000 | DDR0_BASE_VAL
- sw t2, 0x0(t1)
- /* Register t0 carries pointer to the DDR_BASE: 0xB8018000 */
- li t1, DDR_LD_EMODE_REG
- sw t1, 0x20(t0) /* Write to DDR Custom transaction register */
- /* Generate EMODE register contents on A12-A0 */
- li t2, DATA_PATTERN
- li t1, 0xA0000000 | DDR_EMODE_VAL | DDR0_BASE_VAL
- sw t2, 0x0(t1)
- /* Register t0 carries pointer to the DDR_BASE: 0xB8018000 */
- li t1, DDR_LD_MODE_REG
- sw t1, 0x20 (t0) /* Write to DDR Custom transaction register */
- /* Generate Mode register contents on the address bus A12-A0 */
- li t2, DATA_PATTERN
- li t1, 0xA0000000 | DDR_DLL_RES_MODE_VAL | DDR0_BASE_VAL
- sw t2, 0x0(t1)
- /* Delay of 1.6 microseconds ~ 300 delay iteration value */
- li t1, 0x0
- li t2, 500
- 1:
- add t1, 1
- bne t1, t2, 1b
- nop
- /* Register t0 carries pointer to the DDR_BASE: 0xB8018000 */
- li t1, DDR_CUST_PRECHARGE
- sw t1, 0x20(t0) /* Write to DDR Custom transaction register */
- /* Generate A10 high to pre-charge both the banks */
- li t2, DATA_PATTERN
- li t1, 0xA0001000 | DDR0_BASE_VAL
- sw t2, 0x0(t1)
- /* Implements 9 cycles of Auto refresh allowing sufficient margin for
- * stability
- */
- li t4, 9
- li t3, 0
- 1:
- li t1, DDR_CUST_REFRESH
- sw t1, 0x20(t0) /* Write to DDR Custom transaction register */
- /* Read it back to flush CPU write buffers */
- lw t1, 0x20(t0)
- /* Perform a write to DDR space to register the command */
- li t2, DATA_PATTERN
- li t1, 0xA0000000 | DDR0_BASE_VAL
- sw t2, 0x0(t1)
- add t3, 1
- bne t3, t4, 1b
- nop
- /* Register t0 carries pointer to the DDR_BASE: 0xB8018000 */
- li t1, DDR_LD_MODE_REG
- sw t1, 0x20(t0) /* Write to DDR Custom transaction register */
- /* Generate Mode Register contents on the address bus A12-A0 */
- li t2, DATA_PATTERN
- li t1, 0xA0000000 | DDR_DLL_MODE_VAL | DDR0_BASE_VAL
- sw t2, 0x0(t1)
- /* Post DDR SDRAM initialization code :
- * Initialize the refresh timer with fast refresh count
- */
- li t0, RCOUNT
- li t1, DDR_REF_CMP_FAST
- /* Set the RCOMPARE register */
- sw t1, 0x4(t0)
- /* Enable the Refresh timer */
- li t1, 0x1 /* CE set to enabled the Refresh counter */
- sw t1, 0x08(t0)
- /* Enable RE-refresh enable in the DDRC register */
- li t0, DDR_BASE
- li t1, DDRC_VAL_NORMAL
- sw t1, 0x10(t0)
- /* Add 200 microseconds of delay */
- li t1, 0x0
- li t2, DELAY_200USEC
- 1:
- add t1, 1
- bne t1, t2, 1b
- nop
- /* Disable the refresh counter before changing the compare value */
- li t0, RCOUNT
- li t1, 0x0
- sw t1, 0x08(t0)
- /* Set the RCOMPARE register */
- li t1, DDR_REF_CMP_VAL
- sw t1, 0x4(t0)
- /* Enable the Refresh timer */
- li t1, 0x1 /* CE set to enabled the Refresh counter */
- sw t1, 0x08(t0)
- /* Add 200 microseconds of delay */
- li t1, 0x0
- li t2, DELAY_200USEC
- 1:
- add t1, 1
- bne t1, t2, 1b
- nop
- nop
- /* This completes the DDR controller and the DDR SDRAM initialization
- * and the DDR memory is ready for use.
- */
- /* Disable the write transaction merging in IPBus arbiter control reg */
- li t0, IPAC
- li t1, IPAC_VALUE
- sw t1, 0x0(t0)
- nop
- nop
- j ra /* just in case */
- nop
- .end sysMemInit
- /*****************************************************************************
- *
- * sysCacheInit - Initialize RC32438 cache
- *
- * This function performs low-level cache initialization. It is called by
- * romMipsInit.s/romReboot very early in the ROM boot sequence.
- *
- * RETURNS: N/A
- *
- * void sysCacheInit (void)
- *
- */
- .ent sysCacheInit
- sysCacheInit:
- move s7, ra /* Save return address */
- #if defined AUTO_CACHE_DETECT
- detect:
- /* the 4kc processors carry enough information in the
- CONFIG1 register to identify the cache size and line size of the
- data and instruction caches. since this information may change
- from one variant to another, the only safe way to know how to
- specify the cache sizes is to read the CONFIG1 fields and act
- accordingly.
- The instruction cache information is:
- line size = IL
- cache size = IS * IL * IA
- Similarly, the data cache information is:
- line size = DL
- cache size = DS * DL * DA
- The following processing is performed on the fields coming from
- CONFIG1 to translate the bit patterns into the correct values:
- IS, DS: (number of cache lines)
- 64 shifted left by n, where 'n' is the value from the
- IS or DS field in CONFIG1. Technically, if 'n' is 7, the
- value is invalid (reserved), but since this should not happen,
- we don't test for it. The result implements the following table:
- n value
- 0 64
- 1 128
- 2 256
- 3 512
- 4 1024
- 5 2048
- 6 4096
- 7 8192 (invalid)
- IL, DL (number of bytes per cache line)
- 2 shifted left by n, where 'n' is the value from the
- IL or DL field in CONFIG1. If the result is '2', the value
- is set to 0, because if IL or DL is 0, there is no cache.
- also, there is an invalid value calculated if 'n' is 7, since
- that value is reserved. But since it should not happen, we don't
- test for it. The result implements the following table:
- n value
- 0 0 (after adjustment)
- 1 4
- 2 8
- 3 16
- 4 32
- 5 64
- 6 128
- 7 256 (invalid)
- IA, DA (number of cache ways)
- n + 1, where 'n' is the value from the IA or DA field of the
- CONFIG1 register. This implements the following table:
- n value
- 0 1 (direct mapped)
- 1 2
- 2 3
- 3 4
- 4 5
- 5 6
- 6 7
- 7 8
- */
- /* read the config1 register to determine the cache parameters */
- /* N.B.: the mfc0 instruction to access config1 is not supported by
- the assembler, so we have to synthesize it. */
- .word 0x40028001
- /* calculate instruction cache parameters */
- lui v1, (IDT32438_CONFIG1_IS_MSK >> 16)
- and v1, v1,v0
- srl v1, v1,IDT32438_CONFIG1_IS_SHF
- li t0, 64
- sll t0, v1 /* number of cache lines */
- lui v1, (IDT32438_CONFIG1_IA_MSK >> 16)
- and v1, v1, v0
- srl v1, v1, IDT32438_CONFIG1_IA_SHF
- add t1, v1, 1 /* number of cache ways */
- mul t0, t0, t1 /* t0 = IS * IA */
- lui v1, (IDT32438_CONFIG1_IL_MSK >> 16)
- and v1, v1, v0
- srl v1, v1, IDT32438_CONFIG1_IL_SHF
- li t1, 2
- sll t1, t1, v1 /* t1 = IL */
- bnez t1, 1f
- li t1, 0
- 1:
- mul t0, t0, t1 /* t0 = IS * IA * IL */
- /* calculate data cache parameters */
- andi v1, v0, IDT32438_CONFIG1_DS_MSK
- srl v1, v1, IDT32438_CONFIG1_DS_SHF
- li t2, 64
- sll t2, v1 /* number of cache line */
- andi v1, v0, IDT32438_CONFIG1_DA_MSK
- srl v1, v1, IDT32438_CONFIG1_DA_SHF
- add t3, v1, 1 /* number of cache ways */
- mul t2, t2, t3 /* t2 = DS * DA */
- andi v1, v0, IDT32438_CONFIG1_DL_MSK
- srl v1, v1, IDT32438_CONFIG1_DL_SHF
- li t3, 2
- sll t3, t3, v1 /* t3 = DL */
- bnez t3, 1f
- li t3, 0
- 1:
- mul t2, t2, t3 /* t2 = DS * DA * DL */
- /* t0..t3 are now loaded with cache parameters */
- #else
- li t0, ICACHE_SIZE /* I-cache size */
- li t1, ICACHE_LINE_SIZE /* I-cache line size */
- li t2, DCACHE_SIZE /* D-cache size */
- li t3, DCACHE_LINE_SIZE /* D-cache line size */
- #endif
- move a0, s0 /* start type */
- RELOC(v0,cache4kcReset)
- andi a0, s0, BOOT_CLEAR
- jal v0
- nop
- move ra, s7
- j ra
- .end sysCacheInit
- /*****************************************************************************
- *
- * romClearEdac - clear error detection and correction logic
- *
- * This routine clears the memory and error detection logic by
- * doing word writes to each DRAM location. It sizes memory by
- * probing memory locations. It is called by romMipsInit.s/romReboot
- * very early in the ROM boot sequence.
- *
- * RETURNS: N/A
- *
- * void romClearEdac (void)
- *
- */
- .ent romClearEdac
- romClearEdac:
- mfc0 v1, C0_SR /* disable parity errors */
- or v0, v1, SR_DE
- mtc0 v0, C0_SR
- HAZARD_CP_WRITE
- move v0, ra /* save return address */
- RELOC(t0,1f) /* run the loop from cache */
- and t0, 0x1fffffff
- or t0, K0BASE
- j t0
- 1:
- li a0, (LOCAL_MEM_SIZE | K1BASE )
- clearloop:
- sw zero, -4(a0)
- sw zero, -8(a0)
- sw zero, -12(a0)
- sw zero, -16(a0)
- sw zero, -20(a0)
- sw zero, -24(a0)
- sw zero, -28(a0)
- sw zero, -32(a0)
- subu a0, 32
- bne a0, K1BASE, clearloop
- nop
- done:
- mtc0 v1, C0_SR
- HAZARD_CP_WRITE
- j v0
- .end romClearEdac
- /*****************************************************************************
- * romExcHandle - ROM based exception/interrupt handler
- *
- * This routine is invoked on an exception or interrupt while
- * the status register is using the bootstrap exception vectors.
- * It saves a state frame to a known uncached location and displays a
- * summary of the error on the board's alphanumeric LED display.
- *
- * THIS ROUTIINE IS NOT CALLABLE FROM "C"
- *
- * RETURNS: N/A
- *
- * void romExcHandle (void)
- */
- .ent romExcHandle
- romExcHandle:
- .set noat
- li sp, ROM_ISP_BASE /* sp to known uncached location */
- SW sp, E_STK_SP-ESTKSIZE(sp) /* save sp in new intstk frame */
- subu sp, ESTKSIZE /* make new exc stk frame */
- SW k0, E_STK_K0(sp) /* save k0, (exception type) */
- SW AT, E_STK_AT(sp) /* save asmbler resvd reg */
- .set at
- SW v0, E_STK_V0(sp) /* save func return 0, used */
- /* To hold masked cause */
- mfc0 k1, C0_BADVADDR /* read bad VA reg */
- sw k1, E_STK_BADVADDR(sp) /* save bad VA on stack */
- mfc0 k1, C0_EPC /* read exception pc */
- sw k1, E_STK_EPC(sp) /* save EPC on stack */
- mfc0 v0, C0_CAUSE /* read cause register */
- sw v0, E_STK_CAUSE(sp) /* save cause on stack */
- mfc0 k1, C0_SR /* read status register */
- sw k1, E_STK_SR(sp) /* save status on stack */
- .set noat
- mflo AT /* read entry lo reg */
- SW AT, E_STK_LO(sp) /* save entry lo reg */
- mfhi AT /* read entry hi reg */
- SW AT, E_STK_HI(sp) /* save entry hi reg */
- .set at
- SW zero, E_STK_ZERO(sp) /* save zero ?! */
- SW v1, E_STK_V1(sp) /* save func return 1 */
- SW a0, E_STK_A0(sp) /* save passed param 0 */
- SW a1, E_STK_A1(sp) /* save passed param 1 */
- SW a2, E_STK_A2(sp) /* save passed param 2 */
- SW a3, E_STK_A3(sp) /* save passed param 3 */
- SW t0, E_STK_T0(sp) /* save temp reg 0 */
- SW t1, E_STK_T1(sp) /* save temp reg 1 */
- SW t2, E_STK_T2(sp) /* save temp reg 2 */
- SW t3, E_STK_T3(sp) /* save temp reg 3 */
- SW t4, E_STK_T4(sp) /* save temp reg 4 */
- SW t5, E_STK_T5(sp) /* save temp reg 5 */
- SW t6, E_STK_T6(sp) /* save temp reg 6 */
- SW t7, E_STK_T7(sp) /* save temp reg 7 */
- SW t8, E_STK_T8(sp) /* save temp reg 8 */
- SW t9, E_STK_T9(sp) /* save temp reg 9 */
- SW s0, E_STK_S0(sp) /* save saved reg 0 */
- SW s1, E_STK_S1(sp) /* save saved reg 1 */
- SW s2, E_STK_S2(sp) /* save saved reg 2 */
- SW s3, E_STK_S3(sp) /* save saved reg 3 */
- SW s4, E_STK_S4(sp) /* save saved reg 4 */
- SW s5, E_STK_S5(sp) /* save saved reg 5 */
- SW s6, E_STK_S6(sp) /* save saved reg 6 */
- SW s7, E_STK_S7(sp) /* save saved reg 7 */
- SW s8, E_STK_FP(sp) /* save saved reg 8 */
- SW gp, E_STK_GP(sp) /* save global pointer? */
- SW ra, E_STK_RA(sp) /* save return address */
- excLoop:
- b excLoop
- .end romExcHandle