1 /* *********************************************************************
2 * SB1250 Board Support Package
4 * Board-specific initialization File: LITTLESUR_INIT.S
6 * This module contains the assembly-language part of the init
7 * code for this board support package. The routine
8 * "board_earlyinit" lives here.
10 * Author: Mitch Lichtenberg (mpl@broadcom.com)
12 *********************************************************************
14 * Copyright 2000,2001,2002,2003
15 * Broadcom Corporation. All rights reserved.
17 * This software is furnished under license and may be used and
18 * copied only in accordance with the following terms and
19 * conditions. Subject to these conditions, you may download,
20 * copy, install, use, modify and distribute modified or unmodified
21 * copies of this software in source and/or binary form. No title
22 * or ownership is transferred hereby.
24 * 1) Any source code used, modified or distributed must reproduce
25 * and retain this copyright notice and list of conditions
26 * as they appear in the source file.
28 * 2) No right is granted to use any trade name, trademark, or
29 * logo of Broadcom Corporation. The "Broadcom Corporation"
30 * name may not be used to endorse or promote products derived
31 * from this software without the prior written permission of
32 * Broadcom Corporation.
34 * 3) THIS SOFTWARE IS PROVIDED "AS-IS" AND ANY EXPRESS OR
35 * IMPLIED WARRANTIES, INCLUDING BUT NOT LIMITED TO, ANY IMPLIED
36 * WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
37 * PURPOSE, OR NON-INFRINGEMENT ARE DISCLAIMED. IN NO EVENT
38 * SHALL BROADCOM BE LIABLE FOR ANY DAMAGES WHATSOEVER, AND IN
39 * PARTICULAR, BROADCOM SHALL NOT BE LIABLE FOR DIRECT, INDIRECT,
40 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
41 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
42 * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
43 * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
44 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
45 * TORT (INCLUDING NEGLIGENCE OR OTHERWISE), EVEN IF ADVISED OF
46 * THE POSSIBILITY OF SUCH DAMAGE.
47 ********************************************************************* */
51 #include "sb1250_genbus.h"
52 #include "sb1250_regs.h"
53 #include "sb1250_scd.h"
54 #include "bsp_config.h"
55 #include "littlesur.h"
56 #include "mipsmacros.h"
57 #include "sb1250_draminit.h"
62 /* *********************************************************************
64 ********************************************************************* */
68 * Define this to send the LED messages to the serial port instead
72 /*#define _SERIAL_PORT_LEDS_*/
73 #if (defined(_CSWARM_DIAG3E_CFG_) || defined(_CSWARM_DIAG_CFG_))
74 #define _PROMICE_PORT_LEDS_
77 #ifdef _SERIAL_PORT_LEDS_
78 #include "sb1250_uart.h" /* need this for serial defs */
81 #ifdef _PROMICE_PORT_LEDS_
82 #define BOARD_PROMICE_BASE (0x1FDFFC00)
83 #define BOARD_PROMICE_ZERO (0)
84 #define BOARD_PROMICE_ONE (1)
85 #define BOARD_PROMICE_DATA (2)
86 #define BOARD_PROMICE_STATUS (3)
88 #define TDA 0x01 /* Target data available */
89 #define HDA 0x02 /* Host data available */
90 #define OVR 0x04 /* Host data overflow */
95 #if (CFG_UNIPROCESSOR_CPU0 && !CFG_MULTI_CPUS)
96 /* *********************************************************************
97 * sb1250_switch_unicpu0
99 * Switch the processor into uniprocessor CPU0 mode - this
100 * effectively disables CPU1 and changes the CPU to look
101 * like an 1125 with a big L2 cache (an 1150, if you will).
103 * This routine will do one of two things: If we are already in
104 * uniprocessor mode, it just returns. If we are not in uni
105 * mode, we muck with the SCD to enable uni mode and do a
106 * soft reset. The processor will reset and eventuall wind
107 * back here, where it will notice that the uni mode is turned
108 * on and execution will continue.
118 * register s0 must be preserved, it contains the return address
119 ********************************************************************* */
121 LEAF(sb1250_switch_unicpu0)
124 * If the CPU is a 1250 or hybrid, certain initialization has
125 * to be done so that the chip can be used like an 112x.
128 /* First, figure out what type of SOC we're on. */
129 ld t0, PHYS_TO_K1(A_SCD_SYSTEM_REVISION)
130 and t1, t0, M_SYS_PART
131 dsrl t1, t1, S_SYS_PART # part number now in t1
132 and t2, t0, M_SYS_REVISION
133 dsrl t2, t2, S_SYS_REVISION # revision now in t2
136 * Calculating SOC type:
137 * soc_type = part & 0xf;
138 * if (system_revision <= PASS2
139 * && (soc_type == 2 || soc_type == 5))
140 * soc_type = 0; # really a 1250.
143 andi t3, t1, 0xf # soc_type (t3) = part & 0xf;
144 bgt t2, K_SYS_REVISION_PASS2, soc_type_ok
145 beq t3, 2, soc_type_bogus
146 beq t3, 5, soc_type_bogus
155 * We have a 1250 or hybrid. Initialize registers as appropriate.
160 * If we're not already running as a uniprocessor, get us there.
163 dsrl t3, t3, 8 # t3 = numcpus
165 ld t4, PHYS_TO_K1(A_SCD_SYSTEM_CFG)
166 or t4, t4, M_SYS_SB_SOFTRES
167 xor t4, t4, M_SYS_SB_SOFTRES
168 sd t4, PHYS_TO_K1(A_SCD_SYSTEM_CFG) /* clear soft reset */
172 or t4, t4, M_SYS_SB_SOFTRES | M_SYS_UNICPU0
173 sd t4, PHYS_TO_K1(A_SCD_SYSTEM_CFG) /* go unicpu */
176 1: b 1b # loop till reset sinks in
180 END(sb1250_switch_unicpu0)
183 /* *********************************************************************
186 * Initialize board registers. This is the earliest
187 * time the BSP gets control. This routine cannot assume that
188 * memory is operational, and therefore all code in this routine
189 * must run from registers only. The $ra register must not
190 * be modified, as it contains the return address.
192 * This routine will be called from uncached space, before
193 * the caches are initialized. If you want to make
194 * subroutine calls from here, you must use the CALLKSEG1 macro.
196 * Among other things, this is where the GPIO registers get
197 * programmed to make on-board LEDs function, or other startup
198 * that has to be done before anything will work.
205 ********************************************************************* */
207 LEAF(board_earlyinit)
211 # If configured, switch the chip into uniprocessor mode
213 #if (CFG_UNIPROCESSOR_CPU0 && !CFG_MULTI_CPUS)
214 move s0,ra # need this to get out of here
215 bal sb1250_switch_unicpu0 # might not return
216 move ra,s0 # restore saved return address
220 # Reprogram the SCD to make sure UART0 is enabled.
221 # Some CSWARM boards have the SER0 enable bit when
222 # they're not supposed to, which switches the UART
223 # into synchronous mode. Kill off the SCD bit.
224 # XXX this should be investigated in hardware, as
225 # XXX it is a strap option on the CPU.
228 li t0,PHYS_TO_K1(A_SCD_SYSTEM_CFG)
230 dli t2,~M_SYS_SER0_ENABLE
235 # Configure the GPIOs
238 li t0,PHYS_TO_K1(A_GPIO_DIRECTION)
239 li t1,GPIO_OUTPUT_MASK
242 li t0,PHYS_TO_K1(A_GPIO_INT_TYPE)
243 li t1,GPIO_INTERRUPT_MASK
252 li t0,PHYS_TO_K1(A_IO_EXT_CS_BASE(LEDS_CS))
253 li t1,LEDS_PHYS >> S_IO_ADDRBASE
254 sd t1,R_IO_EXT_START_ADDR(t0)
256 li t1,LEDS_SIZE-1 /* Needs to be 1 smaller, se UM for details */
257 sd t1,R_IO_EXT_MULT_SIZE(t0)
260 sd t1,R_IO_EXT_TIME_CFG0(t0)
263 sd t1,R_IO_EXT_TIME_CFG1(t0)
266 sd t1,R_IO_EXT_CFG(t0)
272 li t0,PHYS_TO_K1(A_IO_EXT_CS_BASE(RTC_CS))
273 li t1,RTC_PHYS >> S_IO_ADDRBASE
274 sd t1,R_IO_EXT_START_ADDR(t0)
276 li t1,RTC_SIZE-1 /* Needs to be 1 smaller, se UM for details */
277 sd t1,R_IO_EXT_MULT_SIZE(t0)
280 sd t1,R_IO_EXT_TIME_CFG0(t0)
283 sd t1,R_IO_EXT_TIME_CFG1(t0)
286 sd t1,R_IO_EXT_CFG(t0)
290 # Configure the IDE interface
293 li t0,PHYS_TO_K1(A_IO_EXT_CS_BASE(IDE_CS))
295 li t1,IDE_PHYS >> S_IO_ADDRBASE
296 sd t1,R_IO_EXT_START_ADDR(t0)
299 sd t1,R_IO_EXT_MULT_SIZE(t0)
302 sd t1,R_IO_EXT_TIME_CFG0(t0)
305 sd t1,R_IO_EXT_TIME_CFG1(t0)
308 sd t1,R_IO_EXT_CFG(t0)
311 #ifdef _SERIAL_PORT_LEDS_
314 * If sending the LED messages to the serial port, we will need
315 * to initialize the port now.
318 # Program the mode register for 8 bits/char, no parity
320 li t0,PHYS_TO_K1(A_DUART_MODE_REG_1_A)
321 li t1,V_DUART_BITS_PER_CHAR_8 | V_DUART_PARITY_MODE_NONE
324 # Program the mode register for 1 stop bit, ignore CTS
327 li t0,PHYS_TO_K1(A_DUART_MODE_REG_1_A)
328 ld t1,(t0) # Errata 1956 workaround
329 li t0,PHYS_TO_K1(A_DUART_MODE_REG_2_A)
330 li t1,M_DUART_STOP_BIT_LEN_1
333 # Program the baud rate to 115200
335 li t0,PHYS_TO_K1(A_DUART_MODE_REG_1_A)
336 ld t1,(t0) # Errata 1956 workaround
337 li t0,PHYS_TO_K1(A_DUART_CLK_SEL_A)
338 li t1,V_DUART_BAUD_RATE(CFG_SERIAL_BAUD_RATE)
341 # Dont use any interrupts
343 li t0,PHYS_TO_K1(A_DUART_MODE_REG_1_A)
344 ld t1,(t0) # Errata 1956 workaround
345 li t0,PHYS_TO_K1(A_DUART_IMR)
347 and t1,~M_DUART_IMR_ALL_A
350 # Enable sending and receiving
352 li t0,PHYS_TO_K1(A_DUART_MODE_REG_1_A)
353 ld t1,(t0) # Errata 1956 workaround
354 li t0,PHYS_TO_K1(A_DUART_CMD_A)
355 li t1,M_DUART_RX_EN | M_DUART_TX_EN
360 #ifdef _PROMICE_PORT_LEDS_
363 * Initialize the promice port. read status until
364 * it does not read 0xCC, then do a dummy read from the
368 li t1,PHYS_TO_K1(BOARD_PROMICE_BASE)
373 lbu t0,BOARD_PROMICE_STATUS(t1)
376 2: lbu t0,BOARD_PROMICE_DATA(t1)
387 /* *********************************************************************
390 * Return the address of the DRAM information table
396 * v0 - DRAM info table, return 0 to use default table
397 ********************************************************************* */
404 #ifdef _HARDWIRED_MEMORY_TABLE
407 move v0,zero # auto configure
416 DRAM_GLOBALS(CFG_DRAM_INTERLEAVE)
419 /* 128MB on MC0 (SDRAM) */
420 DRAM_CHAN_CFG(MC_CHAN0, DRT10(8,0), JEDEC,CASCHECK, BLKSIZE32, CFG_DRAM_CSINTERLEAVE, CFG_DRAM_ECC, 0)
421 DRAM_CS_GEOM(MC_CS0, 12, 8, 2)
422 DRAM_CS_TIMING(DRT10(7,5), JEDEC_RFSH_64khz, JEDEC_CASLAT_25, 0, 45, DRT4(20,0), DRT4(15,0), DRT4(20,0), 0, 0)
429 /* *********************************************************************
432 * Transmit a single character via UART A
435 * a0 - character to transmit (low-order 8 bits)
442 ********************************************************************* */
443 #ifdef _SERIAL_PORT_LEDS_
444 LEAF(board_uarta_txchar)
446 # Wait until there is space in the transmit buffer
448 1: li t0,PHYS_TO_K1(A_DUART_MODE_REG_1_A)
449 ld t1,(t0) # Errata 1956 workaround
450 li t0,PHYS_TO_K1(A_DUART_STATUS_A)
451 ld t1,(t0) # Get status bits
452 and t1,M_DUART_TX_RDY # test for ready
453 beq t1,0,1b # keep going till ready
455 # Okay, now send the character.
457 li t0,PHYS_TO_K1(A_DUART_MODE_REG_1_A)
458 ld t1,(t0) # Errata 1956 workaround
459 li t0,PHYS_TO_K1(A_DUART_TX_HOLD_A)
466 END(board_uarta_txchar)
469 /* *********************************************************************
472 * Transmit a single character via UART A
475 * a0 - character to transmit (low-order 8 bits)
482 ********************************************************************* */
484 #ifdef _PROMICE_PORT_LEDS_
486 LEAF(board_piai2_txchar)
488 # Wait until there is space in the transmit buffer
490 li t0,PHYS_TO_K1(BOARD_PROMICE_BASE)
492 1: lb t1,BOARD_PROMICE_STATUS(t0)
496 # Okay, now send the character.
498 sb a0,BOARD_PROMICE_ZERO(t0)
504 END(board_piai2_txchar)
508 /* *********************************************************************
511 * Set LEDs for boot-time progress indication. Not used if
512 * the board does not have progress LEDs. This routine
513 * must not call any other routines, since it may be invoked
514 * either from KSEG0 or KSEG1 and it may be invoked
515 * whether or not the icache is operational.
518 * a0 - LED value (8 bits per character, 4 characters)
525 ********************************************************************* */
528 #define LED_CHAR0 (0x38)
529 #define LED_CHAR1 (0x39)
530 #define LED_CHAR2 (0x3A)
531 #define LED_CHAR3 (0x3B)
535 #if defined(_SERIAL_PORT_LEDS_)
538 * Sending to serial port
544 bal board_uarta_txchar
548 bal board_uarta_txchar
550 bal board_uarta_txchar
552 bal board_uarta_txchar
554 bal board_uarta_txchar
557 bal board_uarta_txchar
561 #elif defined(_PROMICE_PORT_LEDS_)
566 bal board_piai2_txchar
570 li t0,PHYS_TO_K1(LEDS_PHYS)
572 bal board_piai2_txchar
575 li t0,PHYS_TO_K1(LEDS_PHYS)
577 bal board_piai2_txchar
580 li t0,PHYS_TO_K1(LEDS_PHYS)
582 bal board_piai2_txchar
585 li t0,PHYS_TO_K1(LEDS_PHYS)
587 bal board_piai2_txchar
590 bal board_piai2_txchar
592 bal board_piai2_txchar
594 bal board_piai2_txchar
602 li t0,PHYS_TO_K1(LEDS_PHYS)